LIBRARY IEEE;
USE IEEE.STD_LOGIC_1164.ALL;
USE IEEE.STD_LOGIC_ARITH.all;
USE IEEE.STD_LOGIC_UNSIGNED.all;
use std.textio.all;
use IEEE.std_logic_textio.all;
entity reg_file_tb is
generic (Na : Positive := 3;
Nd : positive := 16);
end reg_file_tb;
architecture a of reg_file_tb is
component reg_file is
generic (Na : Positive := 3;
Nd : positive := 16);
port(
clk : in std_logic;
rst_n : in std_logic;
we : in std_logic;
waddr : in std_logic_vector(Na-1 downto 0);
din : in std_logic_vector(Nd-1 downto 0);
raddra : in std_logic_vector(Na-1 downto 0);
raddrb : in std_logic_vector(Na-1 downto 0);
rdata : out std_logic_vector(Nd-1 downto 0);
rdatb : out std_logic_vector(Nd-1 downto 0) );
end component;
procedure check_read(
signal clk : in std_logic;
signal dout : in std_logic_vector(Nd-1 downto 0);
variable dexp : in std_logic_vector(Nd-1 downto 0)) is
variable L : line;
begin
wait until falling_edge(clk);
if (dexp /= dout) then
assert false
report "Unexpected read data"
severity WARNING;
write(L, string'(", expected "));
write(L, dexp);
write(L, string'(", but read "));
write(L, dout);
writeline(output, L);
end if;
end;
signal rst_n : std_logic;
signal clk : std_logic:= '1';
signal we : std_logic;
signal din : std_logic_vector(Nd-1 downto 0);
signal waddr : std_logic_vector(Na-1 downto 0);
signal raddra: std_logic_vector(Na-1 downto 0);
signal raddrb: std_logic_vector(Na-1 downto 0);
signal rdata : std_logic_vector(Nd-1 downto 0);
signal rdatb : std_logic_vector(Nd-1 downto 0);
type rftype is array(0 to 2**Na-1) of std_logic_vector(Nd-1 downto 0);
begin
clk <= not clk after 50 ns;
rf: reg_file
generic map(Na => Na,
Nd => Nd)
port map(
clk => clk,
rst_n => rst_n,
we => we,
waddr => waddr,
din => din,
raddra => raddra,
raddrb => raddrb,
rdata => rdata,
rdatb => rdatb);
process
variable rfile : rftype;
begin
rst_n <= '0';
raddra <= (others => '0');
raddrb <= (others => '0');
wait until falling_edge(clk);
wait until falling_edge(clk);
rst_n <= '1';
we <= '1';
for i in rftype'range loop
waddr <= conv_std_logic_vector(i, waddr'length);
din <= conv_std_logic_vector(i + 16*(i+1), din'length);
wait until falling_edge(clk);
rfile(i) := din;
end loop;
we <= '0';
rfile(5) := (others => '0'); -- emulate error
for i in rftype'range loop
raddra <= conv_std_logic_vector(i, raddra'length);
check_read(clk, rdata, rfile(i));
end loop;
for i in rftype'range loop
raddrb <= conv_std_logic_vector(i, raddrb'length);
check_read(clk, rdatb, rfile(i));
end loop;
wait until falling_edge(clk);
rst_n <= '0';
for i in rftype'range loop
rfile(i) := (others => '0');
end loop;
wait until falling_edge(clk);
rst_n <= '1';
for i in rftype'range loop
raddra <= conv_std_logic_vector(i, raddra'length);
check_read(clk, rdata, rfile(i));
end loop;
for i in rftype'range loop
raddrb <= conv_std_logic_vector(i, raddrb'length);
check_read(clk, rdatb, rfile(i));
end loop;
wait;
end process;
end;