dmi_dtm_tb.o: dmi_dtm_xilinx.o wishbone_debug_master.o
dmi_dtm_xilinx.o: wishbone_types.o sim-unisim/unisim_vcomponents.o
wishbone_debug_master.o: wishbone_types.o
+plru.o:
+plru_tb.o: plru.o
UNISIM_BITS = sim-unisim/unisim_vcomponents.vhdl sim-unisim/BSCANE2.vhdl sim-unisim/BUFG.vhdl
sim-unisim/unisim_vcomponents.o: $(UNISIM_BITS)
icache_tb: icache_tb.o
$(GHDL) -e $(GHDLFLAGS) -Wl,simple_ram_behavioural_helpers_c.o $@
+plru_tb: plru_tb.o
+ $(GHDL) -e $(GHDLFLAGS) $@
+
loadstore_tb: loadstore_tb.o
$(GHDL) -e $(GHDLFLAGS) $@
- insn_helpers.vhdl
- core.vhdl
- icache.vhdl
+ - plru.vhdl
- core_debug.vhdl
file_type : vhdlSource-2008
--- /dev/null
+library ieee;
+use ieee.std_logic_1164.all;
+use ieee.numeric_std.all;
+use ieee.math_real.all;
+
+entity plru is
+ generic (
+ BITS : positive := 2
+ )
+ ;
+ port (
+ clk : in std_ulogic;
+ rst : in std_ulogic;
+
+ acc : in std_ulogic_vector(BITS-1 downto 0);
+ acc_en : in std_ulogic;
+ lru : out std_ulogic_vector(BITS-1 downto 0)
+ );
+end entity plru;
+
+architecture rtl of plru is
+ constant count : positive := 2 ** BITS - 1;
+ subtype node_t is integer range 0 to count;
+ type tree_t is array(node_t) of std_ulogic;
+
+ signal tree: tree_t;
+begin
+
+ -- XXX Check if we can turn that into a little ROM instead that
+ -- takes the tree bit vector and returns the LRU. See if it's better
+ -- in term of FPGA resouces usage...
+ get_lru: process(all)
+ variable node : node_t;
+ begin
+ node := 0;
+ for i in 0 to BITS-1 loop
+ report "GET: i:" & integer'image(i) & " node:" & integer'image(node) & " val:" & std_ulogic'image(tree(node));
+ lru(BITS-1-i) <= tree(node);
+ if i /= BITS-1 then
+ node := node * 2;
+ if tree(node) = '1' then
+ node := node + 2;
+ else
+ node := node + 1;
+ end if;
+ end if;
+ end loop;
+ end process;
+
+ update_lru: process(clk)
+ variable node : node_t;
+ variable abit : std_ulogic;
+ begin
+ if rising_edge(clk) then
+ if rst = '1' then
+ tree <= (others => '0');
+ elsif acc_en = '1' then
+ node := 0;
+ for i in 0 to BITS-1 loop
+ abit := acc(BITS-1-i);
+ tree(node) <= not abit;
+ report "UPD: i:" & integer'image(i) & " node:" & integer'image(node) & " val" & std_ulogic'image(not abit);
+ if i /= BITS-1 then
+ node := node * 2;
+ if abit = '1' then
+ node := node + 2;
+ else
+ node := node + 1;
+ end if;
+ end if;
+ end loop;
+ end if;
+ end if;
+ end process;
+end;
+
+
--- /dev/null
+library ieee;
+use ieee.std_logic_1164.all;
+
+library work;
+use work.common.all;
+use work.wishbone_types.all;
+
+entity plru_tb is
+end plru_tb;
+
+architecture behave of plru_tb is
+ signal clk : std_ulogic;
+ signal rst : std_ulogic;
+
+ constant clk_period : time := 10 ns;
+
+ signal acc_en : std_ulogic;
+ signal acc : std_ulogic_vector(2 downto 0);
+ signal lru : std_ulogic_vector(2 downto 0);
+
+begin
+ plru0: entity work.plru
+ generic map(
+ BITS => 3
+ )
+ port map(
+ clk => clk,
+ rst => rst,
+
+ acc => acc,
+ acc_en => acc_en,
+ lru => lru
+ );
+
+ clk_process: process
+ begin
+ clk <= '0';
+ wait for clk_period/2;
+ clk <= '1';
+ wait for clk_period/2;
+ end process;
+
+ rst_process: process
+ begin
+ rst <= '1';
+ wait for 2*clk_period;
+ rst <= '0';
+ wait;
+ end process;
+
+ stim: process
+ begin
+ wait for 4*clk_period;
+
+ report "accessing 1:";
+ acc <= "001";
+ acc_en <= '1';
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 2:";
+ acc <= "010";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 7:";
+ acc <= "111";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 4:";
+ acc <= "100";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 3:";
+ acc <= "011";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 5:";
+ acc <= "101";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 3:";
+ acc <= "011";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 5:";
+ acc <= "101";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 6:";
+ acc <= "110";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ report "accessing 0:";
+ acc <= "000";
+ wait for clk_period;
+ report "lru:" & to_hstring(lru);
+
+ assert false report "end of test" severity failure;
+ wait;
+ end process;
+end;