library ieee; use ieee.std_logic_1164.all; use ieee.std_logic_arith.all; use ieee.std_logic_unsigned.all; entity tb_uart is end tb_uart; architecture testbench of tb_uart is component uart is generic ( output_fifo_width : integer := 2; input_fifo_width : integer := 2 ); port ( mclk : in std_logic; per_addr : in std_logic_vector (7 downto 0); per_din : in std_logic_vector (15 downto 0); per_en : in std_logic; per_wen : in std_logic_vector (1 downto 0); puc : in std_logic; per_irq_acc : in std_logic; per_irq : out std_logic; per_dout : out std_logic_vector (15 downto 0); rxd : in std_logic; txd : out std_logic ); end component; signal clk : std_logic; signal reset : std_logic; constant period : time := 200 ns; constant offset : time := 2 * period; signal per_addr : std_logic_vector (7 downto 0); signal per_din : std_logic_vector (15 downto 0); signal per_en : std_logic; signal per_wen : std_logic_vector (1 downto 0); signal per_dout : std_logic_vector (15 downto 0); signal per_irq : std_logic; signal rxd : std_logic; signal txd : std_logic; type per_test_record is record we : std_logic; word : std_logic; data : std_logic_vector (15 downto 0); addr : std_logic_vector (15 downto 0); end record; type per_test_array is array (positive range <>) of per_test_record; type rxd_test_array is array (positive range <>) of std_logic_vector (7 downto 0); constant addr_offset : std_logic_vector (15 downto 0) := X"0100"; constant per_test_vectors : per_test_array := ( ('1','1',X"0002",X"0000"), ('1','0',X"0065",X"0002") ); constant rxd_test_vectors : rxd_test_array := ( "01000011", "01000100" ); -------------------------------------------------------------------------------- begin UUT : uart port map ( mclk => clk, per_addr => per_addr, per_din => per_din, per_en => per_en, per_wen => per_wen, puc => reset, per_irq_acc => '0', per_irq => per_irq, per_dout => per_dout, rxd => rxd, txd => txd ); -- Clock generation process begin clk <= '0'; wait for offset; loop clk <= '1'; wait for period/2; clk <= '0'; wait for period/2; end loop; end process; -- Reset generation process begin reset <= '0'; wait for period; reset <= '1'; wait for period; reset <= '0'; wait; end process; -- Bus communication with UART peripherial (per_test_vector) process variable vector : per_test_record; begin per_addr <= X"00"; per_din <= X"0000"; per_en <= '0'; per_wen <= "00"; wait for 3.1 * period; for i in per_test_vectors'range loop vector := per_test_vectors(i); vector.addr := vector.addr + addr_offset; per_addr <= vector.addr (8 downto 1); per_en <= '1'; if (vector.word = '1') then per_wen <= "11"; per_din <= vector.data (15 downto 0); else if (vector.addr(0) = '1') then per_wen <= "10"; per_din <= vector.data (7 downto 0) & "00000000"; else per_wen <= "01"; per_din <= "00000000" & vector.data (7 downto 0); end if; end if; wait for period; per_addr <= X"00"; per_din <= X"0000"; per_en <= '0'; per_wen <= "00"; end loop; wait; end process; -- UART RXD signal generation (rxd_test_vector) process constant baud_period : time := 6 * period; constant extra_wait : time := 2 * baud_period; -- waiting between frames variable vector : std_logic_vector (7 downto 0); begin rxd <= '1'; wait for 4.1 * period; for i in rxd_test_vectors'range loop vector := rxd_test_vectors (i); rxd <= '0'; wait for baud_period; for j in 7 downto 0 loop rxd <= vector (j); wait for baud_period; end loop; rxd <= '1'; wait for baud_period; wait for extra_wait; end loop; wait; end process; end testbench;