- bugfix: instructions uncached LW => cached LW (with cache-miss) was buggy.

Symptoms:
  ...
1.: lw     $a0, 32($s0)  # Uncached load from memory mapped I/O
2.: lw     $a2, 4($v0)   # Cached load and cache-miss.
                                  # $a0 receives same value as $a2.
                                  # CPU skips writing $a0 due to busy flag of D-Cache,
                                  # which is already active in the previous cycle
...

Committed on the Free edition of March Hare Software CVSNT Server.
Upgrade to CVS Suite for more features and support:
http://march-hare.com/cvsnt/


git-svn-id: http://moon:8086/svn/vhdl/trunk@681 cc03376c-175c-47c8-b038-4cd826a8556b
This commit is contained in:
2009-11-24 11:33:37 +00:00
parent 3eef19bb28
commit 21b41da6e2
+6 -6
View File
@@ -86,7 +86,6 @@ architecture behavior of biu is
STB_O : out STD_LOGIC;
CYC_O : out STD_LOGIC;
ctrl : in cache_ctrl_t;
en : in STD_LOGIC;
cpu_en : in STD_LOGIC;
cpu_addr : in word_t;
cpu_dout : out word_t;
@@ -111,7 +110,6 @@ architecture behavior of biu is
STB_O : out STD_LOGIC;
CYC_O : out STD_LOGIC;
ctrl : in cache_ctrl_t;
en : in STD_LOGIC;
cpu_en : in STD_LOGIC;
cpu_we : in STD_LOGIC;
cpu_be : in unsigned(3 downto 0);
@@ -154,6 +152,7 @@ architecture behavior of biu is
signal SEL_O_dmem_wr : unsigned(3 downto 0);
signal SEL_O_dmem_rd : unsigned(3 downto 0);
signal dcached : std_logic;
signal dcache_en2 : std_logic;
signal dcache_en : std_logic;
signal uncached_access : std_logic;
@@ -242,7 +241,6 @@ inst_icache : icache
ACK_I => ACK_I,
SRDY_I => SRDY_I_icache,
ctrl => cop0_ctrl_in.icache,
en => '1',
cpu_en => cpu_imem_en,
cpu_addr => cpu_imem_addr,
cpu_dout => cpu_imem_din,
@@ -268,7 +266,6 @@ inst_dcache : dcache
ACK_I => ACK_I,
SRDY_I => SRDY_I_dcache,
ctrl => cop0_ctrl_in.dcache,
en => dcached,
cpu_en => dcache_en,
cpu_we => cpu_dmem_we,
cpu_be => cpu_dmem_be,
@@ -282,7 +279,7 @@ inst_dcache : dcache
dcached <= '1' when cpu_dmem_addr(31 downto 29) /= "101" else '0';
cpu_dmem_din <= dcache_dout when uncached_access = '0' else DAT_I_dmem_rd;
dcache_en <= cpu_dmem_en; -- and not (CYC_O_dmem_rd or write_busy);-- and not busy;
dcache_en <= dcached and cpu_dmem_en and dcache_en2; -- or write_busy);
-- Instantiate synchronous FIFO
inst_bout_fifo: entity work.fifo_sync
@@ -305,7 +302,7 @@ inst_bout_fifo: entity work.fifo_sync
data_r => bout_fifo_dout
);
bout_rdy <= not bout_fifo_full;
bout_fifo_re <= not bout_fifo_empty and SRDY_I;
bout_fifo_re <= SRDY_I;
bout_fifo_we <= STB_O_dmem_wr or STB_O_dmem_rd or STB_O_dcache or STB_O_icache;
@@ -360,14 +357,17 @@ dmem_rd_flags:
uncached_access <= '0';
if RST_I = '1' then
CYC_O_dmem_rd <= '0';
dcache_en2 <= '1';
else
if ACK_I = '1' and dmem_mem_rd_gnt = '1' then
uncached_access <= '1';
CYC_O_dmem_rd <= '0';
dcache_en2 <= '1';
end if;
if cpu_dmem_en = '1' and busy = '0' and cpu_dmem_we = '0' then
if dcached = '0' then
CYC_O_dmem_rd <= '1';
dcache_en2 <= '0';
end if;
end if;
end if;