From 1d29cdcfb4a5c33189bde6c85bb2bd7d5e771cae Mon Sep 17 00:00:00 2001 From: Anton Blanchard Date: Wed, 11 Aug 2021 17:44:54 +1000 Subject: [PATCH] Remove Potato UART Signed-off-by: Anton Blanchard --- Makefile | 4 +- fpga/pp_fifo.vhd | 91 --------- fpga/pp_soc_uart.vhd | 395 ------------------------------------ fpga/pp_utilities.vhd | 90 -------- fpga/top-acorn-cle-215.vhdl | 6 +- fpga/top-arty.vhdl | 2 - fpga/top-generic.vhdl | 6 +- fpga/top-genesys2.vhdl | 6 +- fpga/top-nexys-video.vhdl | 2 - hello_world/hello_world.bin | Bin 6280 -> 6280 bytes hello_world/hello_world.elf | Bin 87184 -> 83136 bytes hello_world/hello_world.hex | 160 +++++++-------- include/microwatt_soc.h | 15 -- lib/console.c | 108 +--------- microwatt.core | 21 -- sim_pp_uart.vhdl | 135 ------------ soc.vhdl | 91 +++------ syscon.vhdl | 5 +- 18 files changed, 127 insertions(+), 1010 deletions(-) delete mode 100644 fpga/pp_fifo.vhd delete mode 100644 fpga/pp_soc_uart.vhd delete mode 100644 fpga/pp_utilities.vhd delete mode 100644 sim_pp_uart.vhdl diff --git a/Makefile b/Makefile index e486a29..2c836b5 100644 --- a/Makefile +++ b/Makefile @@ -63,7 +63,7 @@ soc_files = wishbone_arbiter.vhdl wishbone_bram_wrapper.vhdl sync_fifo.vhdl \ uart_files = $(wildcard uart16550/*.v) -soc_sim_files = $(core_files) $(soc_files) sim_console.vhdl sim_pp_uart.vhdl sim_bram_helpers.vhdl \ +soc_sim_files = $(core_files) $(soc_files) sim_console.vhdl sim_bram_helpers.vhdl \ sim_bram.vhdl sim_jtag_socket.vhdl sim_jtag.vhdl dmi_dtm_xilinx.vhdl \ sim_16550_uart.vhdl \ foreign_random.vhdl glibc_random.vhdl glibc_random_helpers.vhdl @@ -190,7 +190,7 @@ clkgen=fpga/clk_gen_bypass.vhd endif fpga_files = fpga/soc_reset.vhdl \ - fpga/pp_fifo.vhd fpga/pp_soc_uart.vhd fpga/main_bram.vhdl \ + fpga/main_bram.vhdl \ nonrandom.vhdl synth_files = $(core_files) $(soc_files) $(fpga_files) $(clkgen) $(toplevel) $(dmi_dtm) diff --git a/fpga/pp_fifo.vhd b/fpga/pp_fifo.vhd deleted file mode 100644 index 553a499..0000000 --- a/fpga/pp_fifo.vhd +++ /dev/null @@ -1,91 +0,0 @@ --- The Potato Processor - A simple processor for FPGAs --- (c) Kristian Klomsten Skordal 2014 - 2015 - -library ieee; -use ieee.std_logic_1164.all; - ---! @brief A generic FIFO module. ---! Adopted from the FIFO module in . -entity pp_fifo is - generic( - DEPTH : natural := 64; - WIDTH : natural := 32 - ); - port( - -- Control lines: - clk : in std_logic; - reset : in std_logic; - - -- Status lines: - full : out std_logic; - empty : out std_logic; - - -- Data in: - data_in : in std_logic_vector(WIDTH - 1 downto 0); - data_out : out std_logic_vector(WIDTH - 1 downto 0); - push, pop : in std_logic - ); -end entity pp_fifo; - -architecture behaviour of pp_fifo is - - type memory_array is array(0 to DEPTH - 1) of std_logic_vector(WIDTH - 1 downto 0); - signal memory : memory_array := (others => (others => '0')); - - subtype index_type is integer range 0 to DEPTH - 1; - signal top, bottom : index_type; - - type fifo_op is (FIFO_POP, FIFO_PUSH); - signal prev_op : fifo_op := FIFO_POP; - -begin - - empty <= '1' when top = bottom and prev_op = FIFO_POP else '0'; - full <= '1' when top = bottom and prev_op = FIFO_PUSH else '0'; - - read: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - bottom <= 0; - else - if pop = '1' then - data_out <= memory(bottom); - bottom <= (bottom + 1) mod DEPTH; - end if; - end if; - end if; - end process read; - - write: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - top <= 0; - else - if push = '1' then - memory(top) <= data_in; - top <= (top + 1) mod DEPTH; - end if; - end if; - end if; - end process write; - - set_prev_op: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - prev_op <= FIFO_POP; - else - if push = '1' and pop = '1' then - -- Keep the same value for prev_op - elsif push = '1' then - prev_op <= FIFO_PUSH; - elsif pop = '1' then - prev_op <= FIFO_POP; - end if; - end if; - end if; - end process set_prev_op; - -end architecture behaviour; diff --git a/fpga/pp_soc_uart.vhd b/fpga/pp_soc_uart.vhd deleted file mode 100644 index 1ed3bb9..0000000 --- a/fpga/pp_soc_uart.vhd +++ /dev/null @@ -1,395 +0,0 @@ --- The Potato Processor - A simple processor for FPGAs --- (c) Kristian Klomsten Skordal 2014 - 2016 - -library ieee; -use ieee.std_logic_1164.all; -use ieee.numeric_std.all; - ---! @brief Simple UART module. ---! The following registers are defined: ---! |--------------------|--------------------------------------------| ---! | Address | Description | ---! |--------------------|--------------------------------------------| ---! | 0x00 | Transmit register (write-only) | ---! | 0x08 | Receive register (read-only) | ---! | 0x10 | Status register (read-only) | ---! | 0x18 | Sample clock divisor register (read/write) | ---! | 0x20 | Interrupt enable register (read/write) | ---! |--------------------|--------------------------------------------| ---! ---! The status register contains the following bits: ---! - Bit 0: receive buffer empty ---! - Bit 1: transmit buffer empty ---! - Bit 2: receive buffer full ---! - Bit 3: transmit buffer full ---! ---! The sample clock divisor should be set according to the formula: ---! sample_clk = (f_clk / (baudrate * 16)) - 1 ---! ---! If the sample clock divisor register is set to 0, the sample clock ---! is stopped. ---! ---! Interrupts are enabled by setting the corresponding bit in the interrupt ---! enable register. The following bits are available: ---! - Bit 0: data received (receive buffer not empty) ---! - Bit 1: ready to send data (transmit buffer empty) -entity pp_soc_uart is - generic( - FIFO_DEPTH : natural := 64 --! Depth of the input and output FIFOs. - ); - port( - clk : in std_logic; - reset : in std_logic; - - -- UART ports: - txd : out std_logic; - rxd : in std_logic; - - -- Interrupt signal: - irq : out std_logic; - - -- Wishbone ports: - wb_adr_in : in std_logic_vector(11 downto 0); - wb_dat_in : in std_logic_vector( 7 downto 0); - wb_dat_out : out std_logic_vector( 7 downto 0); - wb_we_in : in std_logic; - wb_cyc_in : in std_logic; - wb_stb_in : in std_logic; - wb_ack_out : out std_logic - ); -end entity pp_soc_uart; - -architecture behaviour of pp_soc_uart is - - subtype bitnumber is natural range 0 to 7; --! Type representing the index of a bit. - - -- UART sample clock signals: - signal sample_clk : std_logic; - signal sample_clk_divisor : std_logic_vector(7 downto 0); - signal sample_clk_counter : std_logic_vector(sample_clk_divisor'range); - - -- UART receive process signals: - type rx_state_type is (IDLE, RECEIVE, STARTBIT, STOPBIT); - signal rx_state : rx_state_type; - signal rx_byte : std_logic_vector(7 downto 0); - signal rx_current_bit : bitnumber; - - subtype rx_sample_counter_type is natural range 0 to 15; - signal rx_sample_counter : rx_sample_counter_type; - signal rx_sample_value : rx_sample_counter_type; - - subtype rx_sample_delay_type is natural range 0 to 7; - signal rx_sample_delay : rx_sample_delay_type; - - -- UART transmit process signals: - type tx_state_type is (IDLE, TRANSMIT, STOPBIT); - signal tx_state : tx_state_type; - signal tx_byte : std_logic_vector(7 downto 0); - signal tx_current_bit : bitnumber; - - -- UART transmit clock: - subtype uart_tx_counter_type is natural range 0 to 15; - signal uart_tx_counter : uart_tx_counter_type := 0; - signal uart_tx_clk : std_logic; - - -- Buffer signals: - signal send_buffer_full, send_buffer_empty : std_logic; - signal recv_buffer_full, recv_buffer_empty : std_logic; - signal send_buffer_input, send_buffer_output : std_logic_vector(7 downto 0); - signal recv_buffer_input, recv_buffer_output : std_logic_vector(7 downto 0); - signal send_buffer_push, send_buffer_pop : std_logic := '0'; - signal recv_buffer_push, recv_buffer_pop : std_logic := '0'; - - -- IRQ enable signals: - signal irq_recv_enable, irq_tx_ready_enable : std_logic := '0'; - - -- Wishbone signals: - type wb_state_type is (IDLE, WRITE_ACK, READ_ACK); - signal wb_state : wb_state_type; - - signal rxd2 : std_logic := '1'; - signal rxd3 : std_logic := '1'; - signal txd2 : std_ulogic := '1'; -begin - - irq <= (irq_recv_enable and (not recv_buffer_empty)) - or (irq_tx_ready_enable and send_buffer_empty); - - ---------- UART receive ---------- - - recv_buffer_input <= rx_byte; - - -- Add a few FFs on the RX input to avoid metastability issues - process (clk) is - begin - if rising_edge(clk) then - rxd3 <= rxd2; - rxd2 <= rxd; - end if; - end process; - txd <= txd2; - - uart_receive: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - rx_state <= IDLE; - recv_buffer_push <= '0'; - else - case rx_state is - when IDLE => - if recv_buffer_push = '1' then - recv_buffer_push <= '0'; - end if; - - if sample_clk = '1' and rxd3 = '0' then - rx_sample_value <= rx_sample_counter; - rx_sample_delay <= 0; - rx_current_bit <= 0; - rx_state <= STARTBIT; - end if; - when STARTBIT => - if sample_clk = '1' then - if rx_sample_delay = 7 then - rx_state <= RECEIVE; - rx_sample_value <= rx_sample_counter; - rx_sample_delay <= 0; - else - rx_sample_delay <= rx_sample_delay + 1; - end if; - end if; - when RECEIVE => - if sample_clk = '1' and rx_sample_counter = rx_sample_value then - if rx_current_bit /= 7 then - rx_byte(rx_current_bit) <= rxd3; - rx_current_bit <= rx_current_bit + 1; - else - rx_byte(rx_current_bit) <= rxd3; - rx_state <= STOPBIT; - end if; - end if; - when STOPBIT => - if sample_clk = '1' and rx_sample_counter = rx_sample_value then - rx_state <= IDLE; - - if recv_buffer_full = '0' then - recv_buffer_push <= '1'; - end if; - end if; - end case; - end if; - end if; - end process uart_receive; - - sample_counter: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - rx_sample_counter <= 0; - elsif sample_clk = '1' then - if rx_sample_counter = 15 then - rx_sample_counter <= 0; - else - rx_sample_counter <= rx_sample_counter + 1; - end if; - end if; - end if; - end process sample_counter; - - ---------- UART transmit ---------- - - tx_byte <= send_buffer_output; - - uart_transmit: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - txd2 <= '1'; - tx_state <= IDLE; - send_buffer_pop <= '0'; - tx_current_bit <= 0; - else - case tx_state is - when IDLE => - if send_buffer_empty = '0' and uart_tx_clk = '1' then - txd2 <= '0'; - send_buffer_pop <= '1'; - tx_current_bit <= 0; - tx_state <= TRANSMIT; - elsif uart_tx_clk = '1' then - txd2 <= '1'; - end if; - when TRANSMIT => - if send_buffer_pop = '1' then - send_buffer_pop <= '0'; - elsif uart_tx_clk = '1' and tx_current_bit = 7 then - txd2 <= tx_byte(tx_current_bit); - tx_state <= STOPBIT; - elsif uart_tx_clk = '1' then - txd2 <= tx_byte(tx_current_bit); - tx_current_bit <= tx_current_bit + 1; - end if; - when STOPBIT => - if uart_tx_clk = '1' then - txd2 <= '1'; - tx_state <= IDLE; - end if; - end case; - end if; - end if; - end process uart_transmit; - - uart_tx_clock_generator: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - uart_tx_counter <= 0; - uart_tx_clk <= '0'; - else - if sample_clk = '1' then - if uart_tx_counter = 15 then - uart_tx_counter <= 0; - uart_tx_clk <= '1'; - else - uart_tx_counter <= uart_tx_counter + 1; - uart_tx_clk <= '0'; - end if; - else - uart_tx_clk <= '0'; - end if; - end if; - end if; - end process uart_tx_clock_generator; - - ---------- Sample clock generator ---------- - - sample_clock_generator: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - sample_clk_counter <= (others => '0'); - sample_clk <= '0'; - else - if sample_clk_divisor /= x"00" then - if sample_clk_counter = sample_clk_divisor then - sample_clk_counter <= (others => '0'); - sample_clk <= '1'; - else - sample_clk_counter <= std_logic_vector(unsigned(sample_clk_counter) + 1); - sample_clk <= '0'; - end if; - end if; - end if; - end if; - end process sample_clock_generator; - - ---------- Data Buffers ---------- - - send_buffer: entity work.pp_fifo - generic map( - DEPTH => FIFO_DEPTH, - WIDTH => 8 - ) port map( - clk => clk, - reset => reset, - full => send_buffer_full, - empty => send_buffer_empty, - data_in => send_buffer_input, - data_out => send_buffer_output, - push => send_buffer_push, - pop => send_buffer_pop - ); - - recv_buffer: entity work.pp_fifo - generic map( - DEPTH => FIFO_DEPTH, - WIDTH => 8 - ) port map( - clk => clk, - reset => reset, - full => recv_buffer_full, - empty => recv_buffer_empty, - data_in => recv_buffer_input, - data_out => recv_buffer_output, - push => recv_buffer_push, - pop => recv_buffer_pop - ); - - ---------- Wishbone Interface ---------- - - wishbone: process(clk) - begin - if rising_edge(clk) then - if reset = '1' then - wb_ack_out <= '0'; - wb_state <= IDLE; - send_buffer_push <= '0'; - recv_buffer_pop <= '0'; - sample_clk_divisor <= (others => '0'); - irq_recv_enable <= '0'; - irq_tx_ready_enable <= '0'; - else - case wb_state is - when IDLE => - if wb_cyc_in = '1' and wb_stb_in = '1' then - if wb_we_in = '1' then -- Write to register - if wb_adr_in = x"000" then - send_buffer_input <= wb_dat_in; - send_buffer_push <= '1'; - elsif wb_adr_in = x"018" then - sample_clk_divisor <= wb_dat_in; - elsif wb_adr_in = x"020" then - irq_recv_enable <= wb_dat_in(0); - irq_tx_ready_enable <= wb_dat_in(1); - end if; - - -- Invalid writes are acked and ignored. - wb_ack_out <= '1'; - wb_state <= WRITE_ACK; - else -- Read from register - if wb_adr_in = x"008" then - recv_buffer_pop <= '1'; - elsif wb_adr_in = x"010" then - wb_dat_out <= x"0" & send_buffer_full & recv_buffer_full & - send_buffer_empty & recv_buffer_empty; - wb_ack_out <= '1'; - elsif wb_adr_in = x"018" then - wb_dat_out <= sample_clk_divisor; - wb_ack_out <= '1'; - elsif wb_adr_in = x"020" then - wb_dat_out <= (0 => irq_recv_enable, - 1 => irq_tx_ready_enable, - others => '0'); - wb_ack_out <= '1'; - else - wb_dat_out <= (others => '0'); - wb_ack_out <= '1'; - end if; - wb_state <= READ_ACK; - end if; - end if; - when WRITE_ACK => - send_buffer_push <= '0'; - - if wb_stb_in = '0' then - wb_ack_out <= '0'; - wb_state <= IDLE; - end if; - when READ_ACK => - if recv_buffer_pop = '1' then - recv_buffer_pop <= '0'; - else - wb_dat_out <= recv_buffer_output; - wb_ack_out <= '1'; - end if; - - if wb_stb_in = '0' then - wb_ack_out <= '0'; - wb_state <= IDLE; - end if; - end case; - end if; - end if; - end process wishbone; - -end architecture behaviour; diff --git a/fpga/pp_utilities.vhd b/fpga/pp_utilities.vhd deleted file mode 100644 index 959b7a4..0000000 --- a/fpga/pp_utilities.vhd +++ /dev/null @@ -1,90 +0,0 @@ --- The Potato Processor - A simple processor for FPGAs --- (c) Kristian Klomsten Skordal 2014 - -library ieee; -use ieee.std_logic_1164.all; - -package pp_utilities is - - --! Converts a boolean to an std_logic. - function to_std_logic(input : in boolean) return std_logic; - - -- Checks if a number is 2^n: - function is_pow2(input : in natural) return boolean; - - --! Calculates log2 with integers. - function log2(input : in natural) return natural; - - -- Gets the value of the sel signals to the wishbone interconnect for the specified - -- operand size and address. - function wb_get_data_sel(size : in std_logic_vector(1 downto 0); address : in std_logic_vector) - return std_logic_vector; - -end package pp_utilities; - -package body pp_utilities is - - function to_std_logic(input : in boolean) return std_logic is - begin - if input then - return '1'; - else - return '0'; - end if; - end function to_std_logic; - - function is_pow2(input : in natural) return boolean is - variable c : natural := 1; - begin - for i in 0 to 31 loop - if input = c then - return true; - end if; - - c := c * 2; - end loop; - - return false; - end function is_pow2; - - function log2(input : in natural) return natural is - variable retval : natural := 0; - variable temp : natural := input; - begin - while temp > 1 loop - retval := retval + 1; - temp := temp / 2; - end loop; - - return retval; - end function log2; - - function wb_get_data_sel(size : in std_logic_vector(1 downto 0); address : in std_logic_vector) - return std_logic_vector is - begin - case size is - when b"01" => - case address(1 downto 0) is - when b"00" => - return b"0001"; - when b"01" => - return b"0010"; - when b"10" => - return b"0100"; - when b"11" => - return b"1000"; - when others => - return b"0001"; - end case; - when b"10" => - if address(1) = '0' then - return b"0011"; - else - return b"1100"; - end if; - when others => - return b"1111"; - end case; - end function wb_get_data_sel; - -end package body pp_utilities; diff --git a/fpga/top-acorn-cle-215.vhdl b/fpga/top-acorn-cle-215.vhdl index bcbadad..4c3609b 100644 --- a/fpga/top-acorn-cle-215.vhdl +++ b/fpga/top-acorn-cle-215.vhdl @@ -19,8 +19,7 @@ entity toplevel is SPI_FLASH_OFFSET : integer := 10485760; SPI_FLASH_DEF_CKDV : natural := 1; SPI_FLASH_DEF_QUAD : boolean := true; - LOG_LENGTH : natural := 2048; - UART_IS_16550 : boolean := true + LOG_LENGTH : natural := 2048 ); port( clk200_p : in std_ulogic; @@ -133,8 +132,7 @@ begin SPI_FLASH_OFFSET => SPI_FLASH_OFFSET, SPI_FLASH_DEF_CKDV => SPI_FLASH_DEF_CKDV, SPI_FLASH_DEF_QUAD => SPI_FLASH_DEF_QUAD, - LOG_LENGTH => LOG_LENGTH, - UART0_IS_16550 => UART_IS_16550 + LOG_LENGTH => LOG_LENGTH ) port map ( -- System signals diff --git a/fpga/top-arty.vhdl b/fpga/top-arty.vhdl index 8e6ff02..7aeb308 100644 --- a/fpga/top-arty.vhdl +++ b/fpga/top-arty.vhdl @@ -25,7 +25,6 @@ entity toplevel is SPI_FLASH_DEF_QUAD : boolean := true; LOG_LENGTH : natural := 512; USE_LITEETH : boolean := false; - UART_IS_16550 : boolean := false; HAS_UART1 : boolean := true; USE_LITESDCARD : boolean := false; NGPIO : natural := 32 @@ -204,7 +203,6 @@ begin SPI_FLASH_DEF_QUAD => SPI_FLASH_DEF_QUAD, LOG_LENGTH => LOG_LENGTH, HAS_LITEETH => USE_LITEETH, - UART0_IS_16550 => UART_IS_16550, HAS_UART1 => HAS_UART1, HAS_SD_CARD => USE_LITESDCARD, NGPIO => NGPIO diff --git a/fpga/top-generic.vhdl b/fpga/top-generic.vhdl index c75e465..d522fb1 100644 --- a/fpga/top-generic.vhdl +++ b/fpga/top-generic.vhdl @@ -15,8 +15,7 @@ entity toplevel is HAS_BTC : boolean := false; ICACHE_NUM_LINES : natural := 64; LOG_LENGTH : natural := 512; - DISABLE_FLATTEN_CORE : boolean := false; - UART_IS_16550 : boolean := true + DISABLE_FLATTEN_CORE : boolean := false ); port( ext_clk : in std_ulogic; @@ -76,8 +75,7 @@ begin HAS_BTC => HAS_BTC, ICACHE_NUM_LINES => ICACHE_NUM_LINES, LOG_LENGTH => LOG_LENGTH, - DISABLE_FLATTEN_CORE => DISABLE_FLATTEN_CORE, - UART0_IS_16550 => UART_IS_16550 + DISABLE_FLATTEN_CORE => DISABLE_FLATTEN_CORE ) port map ( system_clk => system_clk, diff --git a/fpga/top-genesys2.vhdl b/fpga/top-genesys2.vhdl index fcd190f..642b6d4 100644 --- a/fpga/top-genesys2.vhdl +++ b/fpga/top-genesys2.vhdl @@ -20,8 +20,7 @@ entity toplevel is SPI_FLASH_OFFSET : integer := 10485760; SPI_FLASH_DEF_CKDV : natural := 1; SPI_FLASH_DEF_QUAD : boolean := true; - LOG_LENGTH : natural := 2048; - UART_IS_16550 : boolean := true + LOG_LENGTH : natural := 2048 ); port( clk200_p : in std_ulogic; @@ -136,8 +135,7 @@ begin SPI_FLASH_OFFSET => SPI_FLASH_OFFSET, SPI_FLASH_DEF_CKDV => SPI_FLASH_DEF_CKDV, SPI_FLASH_DEF_QUAD => SPI_FLASH_DEF_QUAD, - LOG_LENGTH => LOG_LENGTH, - UART0_IS_16550 => UART_IS_16550 + LOG_LENGTH => LOG_LENGTH ) port map ( -- System signals diff --git a/fpga/top-nexys-video.vhdl b/fpga/top-nexys-video.vhdl index 1cf1df2..0d0a242 100644 --- a/fpga/top-nexys-video.vhdl +++ b/fpga/top-nexys-video.vhdl @@ -23,7 +23,6 @@ entity toplevel is SPI_FLASH_DEF_CKDV : natural := 1; SPI_FLASH_DEF_QUAD : boolean := true; LOG_LENGTH : natural := 2048; - UART_IS_16550 : boolean := true; USE_LITEETH : boolean := false; USE_LITESDCARD : boolean := false ); @@ -180,7 +179,6 @@ begin SPI_FLASH_DEF_CKDV => SPI_FLASH_DEF_CKDV, SPI_FLASH_DEF_QUAD => SPI_FLASH_DEF_QUAD, LOG_LENGTH => LOG_LENGTH, - UART0_IS_16550 => UART_IS_16550, HAS_LITEETH => USE_LITEETH, HAS_SD_CARD => USE_LITESDCARD ) diff --git a/hello_world/hello_world.bin b/hello_world/hello_world.bin index e4b14ca6f70843d9d43a149c8d18fb1f22072fe5..7f49a41c778cb41a3d93cadc90fbc06246654672 100755 GIT binary patch delta 513 zcmZ9JF-QVY7{@n1@h-G-oZvm;vpP}?Kc-{1`#yEXE7#^_YShx=5M z(#ots{%6R#o?+MMU~!6G#I=QoDXT{yqeP)kVt8(kvHJPQCH|Ei80{kE$60-7jd!^ff`~x+LY7H2}FJ;PF9R0dgAO<6|}bhpM`N zTo%2Sw4gGfFH&ATnlQ${golX2MsS5}lLHI|MNrRlCAqo=Q^q*q!K-al64@A69-LjG S#>i^-y<~Teo(4V#Dd!ig@0E`L delta 727 zcmZuvF>4f25dL;Ojx{8>xhSln@o`C!jjJY&+!lMjXb!^$a!u4mVdJGyv=A&@xFyS( zV$;d3g*JkPjieB)><;4(@F%474z;m~5c8aQ8#ROs4Ey-zdvCsPX0zFB_Pu9Uz8hEo z5a~?s)ovPj-9B^bBMNu~=e=#!kwb`TZ}Ug?#KY%lb%V)Sdd&xpdo$?F0n`1HaQ)2^ z+V7S`V!(a;O)>u9tH#EocD>wM7D$(vYwvRh|GAR67Fspt4~YLosl~i!JFABqdPg)A z{~AvBb;D-VKB}2j@MOJwe;EihcW_%I-O>5e^LuJ>2;)=3=*SVW+aLi?e{QV>`Q6dR znhXTO70Or(yd@L#M1XP_)0>351x|)oi^CeJE)Ug8J8p~~f~^zu6&BsIV(4L-zs>>y zW8LdvvaUTMG9Y~N{|Z;=(l8ZMC49c5P2LbmmR9!-OMNy!g>mWcCYmz8T9M}>rNZJB zQsjsOYMYXrJ9k(?G37}Q*tlFMs`h8_dTx@Gn2@yU3D2UlK~p%;fZXy*rN2$n;<|}e zL=(`z!hp7r_bQ&bu$%v=TynErrPk?j4x5siVTZ7kz8q7Ol5#a~j9s|+^0!iqa4~P3(C)XN{3^#F$1~CkOkmJ?`QWsEMAuW>kDR#Ghlgn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@LO=)z0U;m+gn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@LO=)z0U;m+gn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@LO=)z0U;m+gn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@LO=)z0U;m+gn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@LO=)z0U;m+gn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@LO=)z0U;m+gn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@LO=)z0U;m+gn$qb0zyCt z2mv7=1cZPP5CTF#2nYcoAOwVf5D)@FKnMr{As_^VfDjM@|62lUwc1(g3n98fsh!8; z>P+fUrMJzf@bR6_nT@+u%khWzoH_oRd(P}t&WaCUQ|kB2TE5othRk@qO-gmd->B%A zL_VaJcEpvM-mKKqi8m^qoyg#TSZ z936_Q>4DyV_V>>CE}KubKYnaWWbojY$m|2ht*%xrU3+2nL|>JP_ol4w-0bWgJ19M^ zmE!g&?#bz8@3p8k8($2mV=wIUj%&5%@Vm1ow)%Ag?;8D*xM_#_YU7yfN^!h7ahAPj z;_Q!`@s^9hV+Ws)XJ`NA4rZX$+s`PqWo?5x(bugydePf8TMG54S3?LVaJL&iK&0dAk$ptU}D)Q#D=`{?VzE)7w5;tPm4* z&mCBEe0sLe=YLn{As|=4CR(Dq z{M@ZrtCR=Z6I&hRN-bYYWvqh)z+ioBd#|+pV4MaR(WM`|SA{0G>h>C~S|L+f{qxz` zajN`OU3cTw&(2`!sdDzDBl|3rRyCu);%qnZ zcU0A>ZEyc5vb7pj%3?mYIULEC%5YRE{1+6$;*`Q-j&e(L_GK)=TBRqnYfZxftAI-YO6O zjXy>EjCbsq*F`}{^6rSm$Qf5TF@E$YyuB**S!~83Gq|W8L|(HHA8Fd51DB&CRZuxj z_#|rGP&hS~S57qi93)3aqo%H617)F#HIzjwRv-%<#s{VF!}$1ZvTZ~mLaGWRr6aWo zWRR7L-Y$`z*k4`i0hXCW`7vZ{_w;tm;7ot{+sot?^E1@bF-+hP~E|`qU7&!tX<9 z%$EpF`hdP220d1Xhc(s6ExZB&2F0;Lz8T2@77ScJi85bL*88RBQ9~2*H6%UV3D6<6 z&{&)KI)wgFbszT=UOz>;(tL$>z}Sto8a(CZE_4wQ-P_u-6v)owx1b7rZxN}&8veSj zaTw)F_avR!xFV-XI~_UMeKt-TJgH6T|#AjpyKmJy2VHbqf4<8p0#e83*CMg zrB67Oy)ak>`6i^wwGj5Aup6mr2ZS678Kml0AiT(N8mNhNPUYW|616WNRsIbGnvx$P z;c~R|O_)W9gnl$~s?liGB|pRB=)}!Y^A`1aw3>!X^Q4e!eoVSCqg#dIO{9B-TFe;T zUdX#i_Z;cQjV=p$9I5sKI`O=1D$IozZZlgKf=}g7U~~%BUqq_cD3AH)13^8XVEE1+G5q-v>6kK5!z!GELk2>H{3*oDGfBvAWD zP{?xf_Lj zNWRZO_IaLsHaS0KpGlbH+2>UhULhZ|xQE#19QkbV7x%xS`U2ap4lA`1iLS;E$SNMi zFQjVR&iZOo1NG@6aB0e+zMV=3;jGU_-|Xp*=V?(SEG&T}Z)0SUx|a;3=gK*7w717@8rZg*&aY-9%I~Hr@xK)Wp-M zehO*PgVuziRw1=wi`}f+;w5URoZqG98|m=SyG_5|Y#@zNJNyhoUW{-}XkfQFPW~Ly zH<4;nn5gsC*x^FquGkxW35`})Vdv$#(A@~BJE|)eLHT`zIFD3M%BtniR3Kg$30L$U z^qfz0aw91O~LD-Ha5a^~**s7Yf!Z{rRSl`;p9=`YZ~^kZ?89>8Q7xu|H{@ zcA6TfPtz@2`vfeXwp9)n3M0L<^2;zXBjvh~hX8t!Khm$lo9?%IQks#Thx8T_uILfu zU$?O}7Ycp9t1?OiS?_Y8V6eE-(EJEd{tL;3UkQ&DNVslThPz$&)M`2_+Rd)ovtk$( zi-%H2ur)Mfja4^Ut*O<-sNEbnYgW=B({2u&HMdfEaVm+Gc}vxu#^Y6jwxU+kBDfK2 zW5o)iUs6qxme!gRYRR`qxS@e+^pd?KEbwcVPLa^CkXqL?dw$m%){&xpv8mkcckOS{ zkmI$uw0qxpB$0-&oC3E04y+t+gRxrrF(#Tu_=GV5ZrP{^DtKA$X%KIT%h89r> z*S8AYQnZTr!&ACZ-&EIJ?bfx|-M6SwH!OnF3RPXb1u8h&A{q*5y{lO_W94?JUCmv1 zd5)|^0js%3xplW!-%-7>dRMc9`!pKUzuv~GRc*dkWmvgUw!-wq)La{^t9mp`0c+;g zVOa(PHtME|zSb{oYr|GqjS)0eP{-=gkwO#BqHk}*SQ@@?LaRo-4%Lk)!j_6nPeJRn z{@ym)Rdl0jh#-b024E33x@)Dfuw?LH6J!yY+x0@nslOFKG8f#9=-s{gQ^ima7Za_bp=EnmO(J2x<#<#i-PLT|v+O24c0okGN4oU^ch=yPD?= zps93DZ4aBvOhOCK>;iwqEcE9LTQ^S$wcJ`VDQ#SV8#{)H@fXgjHm{m2+e^V=*_Sqn zd#AKlN-c>MDAQW>Ky+zoNK#QyFQ~*aQ0i{G|Mc_5r4AT<$%j@an|$%C&9ypMQg4do zjOIn6#|4h{yp83k?inr@<3BV%K0nv8QLQRIc`pymT-`ydGEv{Ohv+$*YelbVfs3Ct z`Dw09Bvd7mOi({~nqi&lwE+Eu+A}PFROcr*O16<@hf?3F^Wiu?Fw5CyCzg*9-=2T$= z@IB@)ruhxh#>0`>U(esxO(^u3-(I?l{pDhhRk`XJJ;TDzf?bA-|(Hd(*bZ@4CD|;x+)Us?}EJ8{?9d`LSfDm4g|NhuaO- z^E7dO%Jzq6A!yHQl=BPLo|je&nE}xJ8b-&HV+;@L4Q6CI1e5nL3`fOIX`6EN!vVlECl^uw04}o zY~`~y58Cs(;dRP6uT#!>opR3WlyhFEoS(Z)d(-HEt2W^?q(82!#nEIAC)__e7VAol z4W=iClK81PnNDZ=@taC|C^kra9?Xp8GU;UOkfO6JtW~AMOW$qMVW%ssBaLBaPo#Tq z*li9ki0H5z*&L2UI>PSKNEZq^9Ex-~6=*Sw2(G#jpY!^Fh7&_EyMb2v8wXjh)B9$e z^$TWhdg!5!4ky(XeaHXj^fed$lcpe`@C2^tJM`&jv`XJNy6VYttzzWq)PO1h&^3|E zlCEoHaIkAUb2OP9AKcKBPIjhKV-u5|BV!X?>$;1$m=3-sQ7V-IC3HQPAHr`zornM# zuQ-s0lEZ%4C&-iUzOHn*1z%d|?r@Z{#&9iV?%g0ug_e*LUSu?*tRbm6q{G!zh`0?J zCdSqs-(*x>=2OGOgmgEGr7DD-S47n%@nE| z-`pYNu2B?{i(MOJ4XI1Ic0;ji!@;hZknUfh4eDF1dq4FEBWZCTqf%ryjja=1iZnYR z?i=3|?px&7)q>jka2>T8N%@_Mc#$6R!5VZQ+tkdfFYLkyOO;SNHx~o)P32yofX#lu z%8qa}vaGO}I`? z2FE7~!id+oKj(E~i`qPh4tEZtwOl?i_-N;NHj_^d<}+C+hqK8fw1^HYox?+ke4-N_ z&ZlrVQ1!%^DHn8VBmH>$^&h7fY1b8roC<(Hx%y#Bl2YZ+-06UyH3% zxzuCHe#}CCsDC1n&G#S8rt(Q;J_l58DhK$(8I{E$GN2|9YC{jKF@(W>^!+gWvh*_! z)gM+Sz(69GEQZTZ_76{_(`q0wF_bH+&5Rb>%q8>vsqEo?1fnK-OZ$_Z>`#u4=coMO zrZfKG(p5YnOuP7UK9$R46fe^hq>EjmAt7;^ykZiqDt1`bgoebFRLk@b)}c zA62{+&(&8JzD}I0uTtfni(G~8M)`NP5(ih+DE<+@M2)k&wp1*XU4>r`%3Q9pf3gs$ zbIZYmjmvL|^X$t%)VZoTVCjpPm3ex4dJCza%myo{hq{ErNo#j5;hXS4>=B=wORv!wiw>{7|#f$5Q-|Og+u_<0$KXJ%(J&1(Al~rqL z;3XG5)HcP7>*tcK8#nsm`r-G!C!nV|!RskwUtIs>PuDX@P4VLT=Qv*?y(+Hf)nrUp z$(D#GZa$m>yN21VVh8tckE#AFw&IcTYI3 zJ6Mo%1y8d*`+Dx7*?i}!O18yV@({N6#As5*=s3b(hxw;^Y#^756?gd9P;y{m#6KNu zIWaJhO&)=psYz!BxtPc%#zvCplV3Ae!t*~hWqd$D#RfB@qu}dL;{W}#9U*9y;rHgi z<*&Wq_aMO)*#WOP{(S#5_?E#P0WU>!u2lhl-q%~KKd*0g3i{t3@aO&iN$bz|!R7p^ zzO?^*PP}RT`F_8g|NQ}fephH{^v54(N1F%xp9uK#tHHSSFWj$}@u%-5OZ(5~(<$qJ z$@*~?Z2xlse|`i$+2r^CYW%)z{rT0I&%1Nh|2#Kr^I-dbYW?xP>R)^=w)*X#WWCL! z0r@W=laBrQ{5)y>gZ4rBHTe21%?-@{7c1xLgSLNn8UNHW-||N8m<<#3r@wy->d5r- z^oMM?b_F^dwEZ{O1a;(huG80EAfe>q+mluQi9$L5mtwy5C7xL85VUon2rWDFcTWAZ-BrRQNp~cV^=|9V#7NPhjNs~#NZITI- z32mXJu~w-pE1)P{>=M?MD#*GV(RFc^E#h*}v#zMP>K+!WfLj4w{IhOVH2eGRyWg9c zH&dv~;q>VF9=-2=_q*S}`@8qud*7WG_FTN~&5qWJFGo#Qrd029I&8&d>wOsq|gw4&=S+^p-BA#+E5{OZVedx9mioX{x`a z`;hy--7S%^^}ys$0;50HzCFRXPj(-P{}b$}H%RPcx9ip`%f6EKS@F9|C8IT zCma8h?f>MWFMBlU|C2oePp<#h>i?5n|3;&8vfKAs{@>8{zdZ5ii}gw$JvQ-!7Z17d zU7i|SuT{rVbzu48Lr#1b_`gN{v2RSY9Q%oXR?vljy42X_#aG($YJU#x+A)34t_x#5 z8!wDaT=lT!CDrNkk4)_Cs8L;u@3p)qCnna~M(HuF6#FB)w~ftwALaYUmM>ANdVagw zdy!IS{kTcZTk=3e?Ye)xw_B@u*S<7C{69Zxcr&_;Uy7Y%>#ghy1=$XgjjNu;B>w{B zi()XLyjl$NE5zUhF`V^d6T_ul2D`BTxG&dnVXS|nQfrLt3s-r&{aB6b690@j`sKG1 z6VG12*lYFuTa~(Se!be;(XLt+1ER$%e?PIdM$MR83tkfCi-GHoUp%&F8S(6`Jv$<^}X{e{YIUfEQeX{m; zZ`Urbjf_yqyC9t=Wn7htUE8-q+pAGGVt$Ai4C4AmgwQJ@^ zQ1M>eoLKZcWS^p%9+Xm4QZ;+XThvs=?;^U&(BC1kk$ev2DMYJ8d6ig_4_YHoaA;?;_M{_q=I2GGzPlGw>Pt##CZOFN8B)7yAh4YWFr; z({MT3*#drSF?4l(st>GccfYNy+DIzji!E(5vWnLreei5*zzwE$1{s`(L?f-b#_-N2 zp59nRGX)82$s`&AS^4dMZ$fW;30>ClP_)pF{Fxq{J~uPX#)Yk&>HG!y4{w6!Q!xkpuHW z)GkFz^r4UiF^EK06^(xVNUXlW6cuj;^uc{m4Dg@9g+831Zn^^+A3&N^jhlYd@E!*F zIpW<%ye}Ev5s*(4Zw>i>%1&W`zl6ej zLF_|P^`yVZ>gxw7xX0@nQDbyI3F1Da6jd0-Z=>`rBr2c5HnVO1L7Ex zF)%x#)J!B*zXxOE0P7zi&);}1pdv+##si@0+Ylkkx%C9g?kOK9+v`xV8VZ+? z5?;AzqAHTDVkP@5D80w|FVdqSmxInQk{NObLEMGp>py5?a+nB4%9t~UR7n3Z5RX!U zhV08Aeu{)Pq4WjT@1R)U<-Co=NM|bgzY)pkybZ)ABwy!A))^+9z0R$y^InMTWu32r zcp}hwj&&X+op(DFlJWC%i2Rgw&W)jek^IN+m#jl$O25Z{{N9P`YmiJ_9|ds_$wT83 zJPFPG+<1Uaf7@-?2xf{3ja{J3v&AwoCW2A0-f5s`%REz0!0O{jb@WWJWSogW#Xes@ zh2%>}4fK4OtLYSq`62T{bu{Jk=Gr=a@M~!BscervibFufgNOr~W{-#dkj{~L@vPR9F{{`jO$$hBjf zrje!{w#q!@reHn0KTa;*it3F>r#xvz$Z9vzbgW#<)T!SsVuR(ppWL6;i<`dF#HBw7 z;Tf=Zr@tsS(W0zxHg)^#s<)4naOs2eaMe_!gFa@f942g8>A$Q=p%KZi17EI-c%=N! zMB)gTWCAb0=xi`+UjpZcC>=qi$;v-viRvU!Hg$qUgN6R7+INC zZDyl)K=CT16fw<|bQq;akjz#0HBe7l_YM=btn}?Qwa-A{d8B8N>L>yhiZT&MpAk<` zG&K|vk_n21st&^+2ek;bX`~b}O;C5D^dTg3d0jO0Z%Ardj$6z!aKr3ARL$(|zYghF-0S=)!tq;Q zsRv2Hv}5g@LOb4K+wo5n)$*jKkw8%`pG{BD%(MLxyG;|EDgdc-8Eu zDaNU0yQOJ`@+GI9MUravL9)>>g}O!4bmzCVVF58(t}&Hs{61Tbg45RI(#l~xIBlk9 zTfS;4&hw=jso*uaG^%|mZx;23FXf$Uq-M8})U;*_(4|MuubnoZYE2uR=@x3vZbLFl;awmOAmOT^A$FPd-8CWpJL=fEqe`a_Nl0QT;GXo37JsMkfx~hZWI8ut3W@fk+r7RL%b@U)@wQ)I2 z1YYiO6W2rF!;roMsdgUQ z;&!F(MD06}%ue|IAZ|u7mrm(3>KYSn-SoOEr>1oMR1CV=Dv`JlEDStLqLU(8uWr=X zX+&Gp>c%zz5<3$FHq(ogTX%lqg2a-<>P826$J6>v)0j19ny*zIRc@T6&{=6!DudW2 z!7UlAEv-Yl!Uj{ip{k?#&gIj9ZUQZ6sG`6oA&|g@Gxc-J(U$u6?bRx!7oa)?60$@# z+zhVMeEV`59Xh4zW3ZtK17LyK3cM3VWlB-wflV;9;mGtC!mDTW(!a&d$>GEWDcK_lCP zjoHOEh(+O@kwzZ{%~$G7(>Lh6IRs|`bCSh%nVk+gZLZY@!w=o~h=AXAA;#o`z9F1| z{6cRS59ui#91!p;x>g%cM5rtbthKoKlwqs&>ZtZ{ruSK%R@X4ePD!lXYu+l1**vL& zvys@W$O$OGQ`o8#97^01gj3dFEX9Es<5&bKYgUFd5{(AR#qDF7wJUU`4vs7SAR$-9 zy)rc1GFv6^orprk2v;`vkgl@1R-3{Y7Y-%%2SQ~X;c6Y>BabdCM#F$<&MVlDxb6w5 zR;!(=b^_NaW#~jT`<`!o$5gF{Bf&CBrCEaW3ZqJEK89gbVFo6lt`AmRizzHDto)%9xe85J6US41oFbR~DSTL~cln>5whcsQWW!A4SXBtz8c)yMF6NPx0e893?b*mod!r?$J%Op41$d!i} z_E33Q4I9&HC~OL+kpP)bmL9O1kCNxCX`I=g3HBzNnB+X95q6_A3vymzK)b;y)Dzax ztIZ)17UH}@hv3~77auUaT&Z>Oab_P2TDO78xb2vd*5QE(Uk=B>d4*WCd&D~6yaEJK z%?D2`gzq%U{Nb1loyL;it<_Dl4jMHxlx)0Ij<10KY-?1pxP?|)-=xS z#lb+|#3bh>u{2ePg#|gU5DUJ2u?{W^9Bl~q6+XnVmFsN&Dx<7ixKhumE^Dbba9cKm z#x%#o!j*a!I|=kGOI~fwm0(jp&TKXWB$(tpq!GqIX%^(X0-8>6?yw_hRvDV~s=U=! z57<10nK+KE7?%s`<*2+~b@t6ZDoup(AVQXUl^&-aV58iCKcGPd>G`uEX-Y*X8_}_4A6&!yD$Xe!a!1$>#j) zX*lOya#){_Lpa}I?Tj49+o%o`KQc45r=8z(BSW-*64|rhCXnPj+Y|JCI3l z#pxAJR<){jcR2l3tc|s=i@J@`$uS*uW6PqkSWDDBJ=O+7Me@;hZ@Q*k_0mQp; z#h<4;K3dZHEbKsCMe}l*SG0Vff3qqAplx&{N4&NzJw0v1+3lI!aL>7m1~RP!{X?TW zTDJ_1wk>Ecz{Tj`r#Gegvp@-DX5MzKc8+O;YAwifSU7B2ILw;T+n-EGjlebTmOk%>9ni5Hiy4eS6Y|*=FtjL>{eipHe!iXWGC{xHv!)`uyxm215@3De)9>(nEL}CLw9^nI@U&5MC0xUEM`g5 z8H8Dr`;bwJEroz~|5a%(+T_Q+z($>l`Y_#E5vD$d<@LZcMdRqx07ZAt+yIpO6X2C} zKWZWbSV?!IZEKU8GL*(M=}tC-#ogwi4Kep;)YGxX0(d<8xc3_Hnov6_T4&t#`(rHT z#TJncxx9X9BR}U+7ebg62oLA1fpdpK4{39C1fCacc|(N?xat03g} zYLokkAozc$=D7EBz?kqbN$vE~6!l94rTYsLAx6FLrNxX&GMsc*l!i)B50be?+x$=2 zpa-{i4rI4vRa<^=xNVTXY;G%B7uD#{NdK0hOt06owL2GDF$c0kTf9JkK0zMYn$6`) zS;M1wqiR==&i?!31m zmmL|g)vf2u^I8W-GCiZYOzZGKo(kE%d~4r87Lu)lL)q5B(Sdyb@Ib~dT{p7BC%VDC zF4Kd;Kz}}u)h#pB+uuEeGCtnw@5#4z51@r8=0}Gz%gi#k7^R-!(V(!!YrS;DYsK2O ztOo(N_QBgozPo2z>u@fc&-CQ8IWYTjnGCqF4p>_Idb{)8tq3^Zk6i^-j}93+;HfPc z9~vJu!p|T|1W+5{Z35wR(FSi}`kX&YFHj@>*JnB*kj;1Jvz?>exqRpLTz@`8D{pbJ zSRj|#(wW1aLyhblK?n3@6_qxtQMfvH5n0P+dpZ&SwaVDq3}ZR^Mvla;E%9Z#&v@P3 zJ(BUouPyk_@969s9T-rXyGMIR3T&el1UQn(clPJ5?Suo0U@-y+>T)|eGlRqVoyz#Y zcTD{w*_>Z6ffqNc$WC`}Z>}UxYO;@uzwc=)>|TmZaJYa7%^ zCt~+$10av{qTo80XR`xEO{AVcJIUcCD^{HE%|#E-JK@Iwd%IV=T(fsAm%v(uZxbr< zUB#Q+;#wEK>+;sEl#icy>~^D+9}CW*OZip7d3q^7u6W@qc?{2sOX!EAsUuOA*`Vg0+TJ|8Xdy7{2hf2!17 zng5SjeVpg`7q73)zW@Eqw|P8N{xr(OV|`wS_gnq2e7O8*NT1hh*7u_*I1QJ-iK;M< zq*?z*p`|`7`^<6lhvxW_=5M6PpuNKSFM%KCk?7CQ^0{B(PhpRv|G&r4KfKu2KVtPb z-scwV zoP8Yq>sR@bi$Zq8`c&qzUo85d)jw?g(>`bh5|2L~=J*6U7`w&#!|Qxc_ZKrkvwvpO VbQ5Z#sX7J!w+Xryg%m '0'); - irq_recv_enable <= '0'; - irq_tx_ready_enable <= '0'; - else - case wb_state is - when IDLE => - if wb_cyc_in = '1' and wb_stb_in = '1' then - if wb_we_in = '1' then -- Write to register - if wb_adr_in(11 downto 0) = x"000" then - sim_console_write(x"00000000000000" & wb_dat_in); - elsif wb_adr_in(11 downto 0) = x"018" then - sample_clk_divisor <= wb_dat_in; - elsif wb_adr_in(11 downto 0) = x"020" then - irq_recv_enable <= wb_dat_in(0); - irq_tx_ready_enable <= wb_dat_in(1); - end if; - wb_ack <= '1'; - wb_state <= WRITE_ACK; - else -- Read from register - if wb_adr_in(11 downto 0) = x"008" then - sim_console_read(sim_tmp); - wb_dat_out <= sim_tmp(7 downto 0); - elsif wb_adr_in(11 downto 0) = x"010" then - sim_console_poll(sim_tmp); - wb_dat_out <= "00000" & sim_tmp(0) & '1' & not sim_tmp(0); - elsif wb_adr_in(11 downto 0) = x"018" then - wb_dat_out <= sample_clk_divisor; - elsif wb_adr_in(11 downto 0) = x"020" then - wb_dat_out <= (0 => irq_recv_enable, - 1 => irq_tx_ready_enable, - others => '0'); - else - wb_dat_out <= (others => '0'); - end if; - wb_ack <= '1'; - wb_state <= READ_ACK; - end if; - end if; - when WRITE_ACK|READ_ACK => - if wb_stb_in = '0' then - wb_ack <= '0'; - wb_state <= IDLE; - end if; - end case; - end if; - end if; - end process wishbone; - -end architecture behaviour; diff --git a/soc.vhdl b/soc.vhdl index 8c0401a..ddaac14 100644 --- a/soc.vhdl +++ b/soc.vhdl @@ -71,7 +71,6 @@ entity soc is SPI_BOOT_CLOCKS : boolean := true; LOG_LENGTH : natural := 512; HAS_LITEETH : boolean := false; - UART0_IS_16550 : boolean := true; HAS_UART1 : boolean := false; ICACHE_NUM_LINES : natural := 64; ICACHE_NUM_WAYS : natural := 2; @@ -244,6 +243,8 @@ architecture behaviour of soc is SLAVE_IO_NONE); signal slave_io_dbg : slave_io_type; + signal uart0_irq_l : std_ulogic; + function wishbone_widen_data(wb : wb_io_master_out) return wishbone_master_out is variable wwb : wishbone_master_out; begin @@ -737,7 +738,6 @@ begin SPI_FLASH_OFFSET => SPI_FLASH_OFFSET, HAS_LITEETH => HAS_LITEETH, HAS_SD_CARD => HAS_SD_CARD, - UART0_IS_16550 => UART0_IS_16550, HAS_UART1 => HAS_UART1 ) port map( @@ -750,74 +750,41 @@ begin soc_reset => open -- XXX TODO ); - -- -- UART0 - -- - -- Either potato (legacy) or 16550 - -- - uart0_pp: if not UART0_IS_16550 generate - uart0: entity work.pp_soc_uart - generic map( - FIFO_DEPTH => 32 - ) - port map( - clk => system_clk, - reset => rst_uart, - txd => uart0_txd, - rxd => uart0_rxd, - irq => uart0_irq, - wb_adr_in => wb_uart0_in.adr(11 downto 0), - wb_dat_in => wb_uart0_in.dat(7 downto 0), - wb_dat_out => uart0_dat8, - wb_cyc_in => wb_uart0_in.cyc, - wb_stb_in => wb_uart0_in.stb, - wb_we_in => wb_uart0_in.we, - wb_ack_out => wb_uart0_out.ack - ); - end generate; + uart0: uart_top + port map ( + wb_clk_i => system_clk, + wb_rst_i => rst_uart, + wb_adr_i => wb_uart0_in.adr(4 downto 2), + wb_dat_i => wb_uart0_in.dat(7 downto 0), + wb_dat_o => uart0_dat8, + wb_we_i => wb_uart0_in.we, + wb_stb_i => wb_uart0_in.stb, + wb_cyc_i => wb_uart0_in.cyc, + wb_ack_o => wb_uart0_out.ack, + int_o => uart0_irq_l, + stx_pad_o => uart0_txd, + srx_pad_i => uart0_rxd, + rts_pad_o => open, + cts_pad_i => '1', + dtr_pad_o => open, + dsr_pad_i => '1', + ri_pad_i => '0', + dcd_pad_i => '1' + ); - uart0_16550 : if UART0_IS_16550 generate - signal irq_l : std_ulogic; + -- Add a register on the irq out, helps timing + uart0_irq_latch: process(system_clk) begin - uart0: uart_top - port map ( - wb_clk_i => system_clk, - wb_rst_i => rst_uart, - wb_adr_i => wb_uart0_in.adr(4 downto 2), - wb_dat_i => wb_uart0_in.dat(7 downto 0), - wb_dat_o => uart0_dat8, - wb_we_i => wb_uart0_in.we, - wb_stb_i => wb_uart0_in.stb, - wb_cyc_i => wb_uart0_in.cyc, - wb_ack_o => wb_uart0_out.ack, - int_o => irq_l, - stx_pad_o => uart0_txd, - srx_pad_i => uart0_rxd, - rts_pad_o => open, - cts_pad_i => '1', - dtr_pad_o => open, - dsr_pad_i => '1', - ri_pad_i => '0', - dcd_pad_i => '1' - ); - - -- Add a register on the irq out, helps timing - uart0_irq_latch: process(system_clk) - begin - if rising_edge(system_clk) then - uart0_irq <= irq_l; - end if; - end process; - end generate; + if rising_edge(system_clk) then + uart0_irq <= uart0_irq_l; + end if; + end process; wb_uart0_out.dat <= x"000000" & uart0_dat8; wb_uart0_out.stall <= not wb_uart0_out.ack; - -- -- UART1 - -- - -- Always 16550 if it exists - -- uart1: if HAS_UART1 generate signal irq_l : std_ulogic; begin diff --git a/syscon.vhdl b/syscon.vhdl index 2f8bd47..abef925 100644 --- a/syscon.vhdl +++ b/syscon.vhdl @@ -19,7 +19,6 @@ entity syscon is SPI_FLASH_OFFSET : integer; HAS_LITEETH : boolean; HAS_SD_CARD : boolean; - UART0_IS_16550 : boolean; HAS_UART1 : boolean ); port ( @@ -88,7 +87,7 @@ architecture behaviour of syscon is -- UART0/1 info registers bits -- -- 0 ..31 : UART clock freq (in HZ) - -- 32 : UART is 16550 (otherwise pp) + -- 32 : UART is 16550 -- -- Ctrl register @@ -160,7 +159,7 @@ begin SYS_REG_CTRL_BITS-1 downto 0 => reg_ctrl); -- UART info registers read composition - uinfo_16550 <= '1' when UART0_IS_16550 else '0'; + uinfo_16550 <= '1'; uinfo_freq <= std_ulogic_vector(to_unsigned(CLK_FREQ, 32)); reg_uart0info <= (32 => uinfo_16550, 31 downto 0 => uinfo_freq,