diff --git a/coregen/coregen.cgc b/coregen/coregen.cgc
index 1b899f6..670b729 100644
--- a/coregen/coregen.cgc
+++ b/coregen/coregen.cgc
@@ -177,7 +177,7 @@
false
-
+
coregen
./
@@ -384,7 +384,7 @@
false
-
+
coregen
./
@@ -589,179 +589,9 @@
false
false
false
- 0
- 4
- 96
- 0
- 96
- spartan3
- 1
- 0
- 0
- 0
- 0
- 0
- 0
- 1
- 0
- 0
- 0
- 0
- 0
- 2
- 2
- 0
- 1
- 0
- 512x72
- 2
- 3
- 1
- 13
- 12
- 0
- 4
- 16
- 1
- 4
- 0
- 1
- 0
- 0
- 0
- 0
- 0
- 4
- 16
- 1
- 4
- 0
- 1
- 0
- 2
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 4
- 32
- 64
- 0
- 0
- 0
- 0
- 0
- 1
- 1
- 1
- 1
- 1
- 0
- 0
- 0
- 0
- 1
- 0
- 0
- 0
- 64
- 8
- 4
- 4
- 4
- 4
- 0
- 0
- 0
- 0
- 0
- 0
- 1
- 1
- 1
- 1
- 1
- 1
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 32
- 64
- 2
- 32
- 64
- 1
- 16
- 1024
- 16
- 16
- 1024
- 1024
- 4
- 10
- 4
- 4
- 10
- 10
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 0
- 1023
- 1023
- 1023
- 1023
- 1023
- 1023
- 0
- 0
- 0
- 0
- 0
- 0
- 1022
- 1022
- 1022
- 1022
- 1022
- 1022
- 0
- 0
- 0
- 0
- 0
- 0
-
+
coregen
./
@@ -794,528 +624,6 @@
2012-11-19+12:39
-
-
- apply_current_project_options_generator
-
-
- customization_generator
-
-
- model_parameter_resolution_generator
-
-
- ip_xco_generator
-
- ./wb_ddr_ctrl_wb_to_ddr.xco
- xco
- Mon Mar 18 11:03:09 GMT 2013
- 0xD72490DC
- generationID_1879581046
-
-
-
- associated_files_generator
-
- ./wb_ddr_ctrl_wb_to_ddr/doc/fifo_generator_v9_3_vinfo.html
- ignore
- unknown
- Tue Dec 18 04:53:03 GMT 2012
- 0x9B56C5A6
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/fifo_generator_v9_3_readme.txt
- ignore
- txt
- Tue Dec 18 04:53:03 GMT 2012
- 0x4A0AA28D
- generationID_1879581046
-
-
-
- ejava_generator
-
- ./wb_ddr_ctrl_wb_to_ddr/example_design/wb_ddr_ctrl_wb_to_ddr_exdes.ucf
- ignore
- ucf
- Mon Mar 18 11:03:11 GMT 2013
- 0xB547BB7D
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/example_design/wb_ddr_ctrl_wb_to_ddr_exdes.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:12 GMT 2013
- 0x672FACF1
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/implement.bat
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x618F0487
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/implement.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x41A64983
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/implement_synplify.bat
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xADC01C64
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/implement_synplify.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x0D228AAD
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/planAhead_ise.bat
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xB9AD0E43
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/planAhead_ise.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xA94EC195
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/planAhead_ise.tcl
- ignore
- tcl
- Mon Mar 18 11:03:12 GMT 2013
- 0xEB8CDEED
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/xst.prj
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x8D205C47
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/implement/xst.scr
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x22741F1E
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/simulate_isim.bat
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x1F7F07BB
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/simulate_isim.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x38E533B0
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/simulate_mti.bat
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x0C3CDB0C
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/simulate_mti.do
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x98C3788B
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/simulate_mti.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x5FDBD750
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/simulate_ncsim.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x27AF2605
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/simulate_vcs.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xC26A70F5
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/ucli_commands.key
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x32508805
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/vcs_session.tcl
- ignore
- tcl
- Mon Mar 18 11:03:12 GMT 2013
- 0xC160568F
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/wave_isim.tcl
- ignore
- tcl
- Mon Mar 18 11:03:12 GMT 2013
- 0x546AFE24
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/wave_mti.do
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xE1168216
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/functional/wave_ncsim.sv
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x7F129823
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/simulate_isim.bat
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x0E99F9F4
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/simulate_isim.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xC342CFF2
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/simulate_mti.bat
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x0C3CDB0C
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/simulate_mti.do
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xD9164D7B
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/simulate_mti.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x5FDBD750
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/simulate_ncsim.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x885E0CCA
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/simulate_vcs.sh
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x0AC98A7E
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/ucli_commands.key
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x32508805
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/vcs_session.tcl
- ignore
- tcl
- Mon Mar 18 11:03:12 GMT 2013
- 0xF61C74F1
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/wave_isim.tcl
- ignore
- tcl
- Mon Mar 18 11:03:12 GMT 2013
- 0x546AFE24
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/wave_mti.do
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0xE1168216
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/timing/wave_ncsim.sv
- ignore
- unknown
- Mon Mar 18 11:03:12 GMT 2013
- 0x7F129823
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/wb_ddr_ctrl_wb_to_ddr_dgen.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:11 GMT 2013
- 0x619FAB48
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/wb_ddr_ctrl_wb_to_ddr_dverif.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:11 GMT 2013
- 0xEB31B197
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/wb_ddr_ctrl_wb_to_ddr_pctrl.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:11 GMT 2013
- 0xC7914329
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/wb_ddr_ctrl_wb_to_ddr_pkg.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:11 GMT 2013
- 0xFE4BE8C9
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/wb_ddr_ctrl_wb_to_ddr_rng.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:11 GMT 2013
- 0x408CD90A
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/wb_ddr_ctrl_wb_to_ddr_synth.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:11 GMT 2013
- 0x1C68FC8F
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/simulation/wb_ddr_ctrl_wb_to_ddr_tb.vhd
- ignore
- vhdl
- Mon Mar 18 11:03:11 GMT 2013
- 0x2FFEFA4B
- generationID_1879581046
-
-
-
- ngc_netlist_generator
-
- ./wb_ddr_ctrl_wb_to_ddr.ngc
- ngc
- Mon Mar 18 11:05:11 GMT 2013
- 0xF374BB46
- generationID_1879581046
-
-
-
- obfuscate_netlist_generator
-
-
- padded_implementation_netlist_generator
-
-
- instantiation_template_generator
-
- ./wb_ddr_ctrl_wb_to_ddr.vho
- vho
- Mon Mar 18 11:05:12 GMT 2013
- 0xC315A144
- generationID_1879581046
-
-
-
- structural_simulation_model_generator
-
- ./wb_ddr_ctrl_wb_to_ddr.vhd
- vhdl
- Mon Mar 18 11:05:12 GMT 2013
- 0xF70C42D0
- generationID_1879581046
-
-
-
- all_documents_generator
-
- ./wb_ddr_ctrl_wb_to_ddr/doc/fifo_generator_v9_3_readme.txt
- ignore
- txt
- Mon Mar 18 11:05:12 GMT 2013
- 0x4A0AA28D
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/doc/fifo_generator_v9_3_vinfo.html
- ignore
- unknown
- Mon Mar 18 11:05:12 GMT 2013
- 0x9B56C5A6
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr/doc/pg057-fifo-generator.pdf
- ignore
- pdf
- Mon Mar 18 11:05:12 GMT 2013
- 0x90F23916
- generationID_1879581046
-
-
-
- readme_documents_generator
-
-
- asy_generator
-
- ./wb_ddr_ctrl_wb_to_ddr.asy
- asy
- Mon Mar 18 11:05:16 GMT 2013
- 0xD9BB306E
- generationID_1879581046
-
-
-
- xmdf_generator
-
- ./wb_ddr_ctrl_wb_to_ddr_xmdf.tcl
- tclXmdf
- tcl
- Mon Mar 18 11:05:16 GMT 2013
- 0xB793D0F0
- generationID_1879581046
-
-
-
- synthesis_ise_generator
-
- ./wb_ddr_ctrl_wb_to_ddr.gise
- ignore
- gise
- Mon Mar 18 11:05:24 GMT 2013
- 0x92BF8E11
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr.xise
- ignore
- xise
- Mon Mar 18 11:05:24 GMT 2013
- 0x84D636CD
- generationID_1879581046
-
-
-
- ise_generator
-
- ./wb_ddr_ctrl_wb_to_ddr.gise
- ignore
- gise
- Mon Mar 18 11:05:29 GMT 2013
- 0xA30A284B
- generationID_1879581046
-
-
- ./wb_ddr_ctrl_wb_to_ddr.xise
- ignore
- xise
- Mon Mar 18 11:05:29 GMT 2013
- 0x9FA2652A
- generationID_1879581046
-
-
-
- deliver_readme_generator
-
-
- flist_generator
-
- ./wb_ddr_ctrl_wb_to_ddr_flist.txt
- ignore
- txtFlist
- txt
- Mon Mar 18 11:05:29 GMT 2013
- 0x786A614F
- generationID_1879581046
-
-
-
- view_readme_generator
-
-
diff --git a/coregen/vga_pixeldata_fifo.xco b/coregen/vga_pixeldata_fifo.xco
index 6c51dd7..9e37bfb 100644
--- a/coregen/vga_pixeldata_fifo.xco
+++ b/coregen/vga_pixeldata_fifo.xco
@@ -1,7 +1,7 @@
##############################################################
#
# Xilinx Core Generator version 14.4
-# Date: Thu Mar 07 19:42:24 2013
+# Date: Sun Jun 2 10:25:49 2013
#
##############################################################
#
diff --git a/coregen/wb_ddr_ctrl_wb_from_ddr.xco b/coregen/wb_ddr_ctrl_wb_from_ddr.xco
index 739650a..52587aa 100644
--- a/coregen/wb_ddr_ctrl_wb_from_ddr.xco
+++ b/coregen/wb_ddr_ctrl_wb_from_ddr.xco
@@ -1,7 +1,7 @@
##############################################################
#
# Xilinx Core Generator version 14.4
-# Date: Sat Mar 02 09:52:53 2013
+# Date: Sun Jun 2 10:23:20 2013
#
##############################################################
#
diff --git a/coregen/wb_ddr_ctrl_wb_to_ddr.xco b/coregen/wb_ddr_ctrl_wb_to_ddr.xco
index 79130f5..c073af6 100644
--- a/coregen/wb_ddr_ctrl_wb_to_ddr.xco
+++ b/coregen/wb_ddr_ctrl_wb_to_ddr.xco
@@ -1,7 +1,7 @@
##############################################################
#
# Xilinx Core Generator version 14.4
-# Date: Mon Mar 18 11:03:09 2013
+# Date: Sun Jun 2 10:24:40 2013
#
##############################################################
#
diff --git a/src/wb_ddr_ctrl_wb_sc_fe.vhd b/src/wb_ddr_ctrl_wb_sc_fe.vhd
new file mode 100644
index 0000000..6780b4c
--- /dev/null
+++ b/src/wb_ddr_ctrl_wb_sc_fe.vhd
@@ -0,0 +1,457 @@
+----------------------------------------------------------------------------------
+-- Company:
+-- Engineer:
+--
+-- Create Date: 11/06/2012 03:04:35 PM
+-- Design Name:
+-- Module Name: wb_ddr_ctrl_wb_sc_fe - Behavioral
+-- Project Name:
+-- Target Devices:
+-- Tool Versions:
+-- Description: Memory controller - system clock domain - Cache front-end -
+-- Data path
+--
+-- Dependencies:
+--
+-- Revision:
+-- Revision 0.01 - File Created
+-- Additional Comments:
+--
+----------------------------------------------------------------------------------
+
+
+library IEEE;
+use IEEE.STD_LOGIC_1164.ALL;
+
+-- Uncomment the following library declaration if using
+-- arithmetic functions with Signed or Unsigned values
+use IEEE.NUMERIC_STD.ALL;
+
+-- Uncomment the following library declaration if instantiating
+-- any Xilinx primitives in this code.
+library UNISIM;
+use UNISIM.VComponents.all;
+
+use work.intercon_package.all;
+
+-- control slave port register map
+-- 0: 0 - invalidate
+-- write '1' to invalidate entire cache
+-- 1 - flush
+-- write '1' to flush all dirty lines
+-- 31..2 - reserved
+-- 1: reserved
+--
+-- When both flush and invalidate are set at the same time, the entire cache is
+-- invalidated, with all dirty lines being written back to memory before
+-- invalidation.
+
+entity wb_ddr_ctrl_wb_sc_fe is
+ generic (
+ line_size : integer := 8;
+ lines : integer := 64;
+ assoc : integer := 2;
+ line_size_ln2 : integer := 3;
+ lines_ln2 : integer := 6;
+ assoc_ln2 : integer := 1;
+ addr_width : integer := 23;
+ dontcare : std_logic := '-'
+ );
+ port (
+ -- Wishbone slave
+ clk_i : in std_logic;
+ rst_i : in std_logic;
+ wbs_i : in sdram_ctrl_wbs_i_type;
+ wbs_o : out sdram_ctrl_wbs_o_type;
+ wbs_cc_i : in sdram_ctrl_cc_wbs_i_type;
+ wbs_cc_o : out sdram_ctrl_cc_wbs_o_type;
+
+ -- To backend
+ mem_adr : out std_logic_vector(addr_width-line_size_ln2-1 downto 0);
+ mem_rdrq : out std_logic;
+ mem_wrrq : out std_logic;
+ mem_dat_o : out std_logic_vector(63 downto 0);
+ mem_ack : in std_logic;
+ mem_dat_i : in std_logic_vector(63 downto 0)
+ );
+end wb_ddr_ctrl_wb_sc_fe;
+
+architecture Behavioral of wb_ddr_ctrl_wb_sc_fe is
+ attribute ram_style : string;
+ attribute priority_extract : string;
+
+ component wb_ddr_ctrl_wb_sc_fe_fsm
+ generic (
+ line_size : integer;
+ lines : integer;
+ assoc : integer;
+ line_size_ln2 : integer;
+ lines_ln2 : integer;
+ assoc_ln2 : integer;
+ addr_width : integer);
+ port (
+ clk_i : in std_logic;
+ rst_i : in std_logic;
+ cyc_i : in std_logic;
+ stb_i : in std_logic;
+ we_i : in std_logic;
+ adr_tag_eq : in std_logic_vector(assoc-1 downto 0);
+ eject_dirty : in std_logic;
+ mem_offset : in unsigned(line_size_ln2-1 downto 0);
+ mfi_index : in unsigned(lines_ln2-assoc_ln2-1 downto 0);
+ user_cc_req_flush : in std_logic;
+ user_cc_req_inval : in std_logic;
+ user_cc_req_none : in std_logic;
+ adr_tag_eq_num_dirty : in std_logic;
+ mem_ack : in std_logic;
+ mfi_num_dirty : in std_logic;
+ cc_valid : in std_logic_vector(assoc-1 downto 0);
+ cc_dirty : in std_logic_vector(assoc-1 downto 0);
+ ack_o : out std_logic;
+ update_lru : out std_logic := '0';
+ set_clean : out std_logic := '0';
+ set_dirty : out std_logic := '0';
+ set_valid : out std_logic := '0';
+ set_invalid : out std_logic := '0';
+ cache_write : out std_logic := '0';
+ cache_from_mem : out std_logic := '0';
+ cache_to_mem : out std_logic := '0';
+ mem_rdrq : out std_logic := '0';
+ mem_wrrq : out std_logic := '0';
+ mfi : out std_logic := '0';
+ user_cc_ack_o : out std_logic := '0');
+ end component;
+
+ component wb_ddr_ctrl_wb_sc_fe_ram
+ generic (
+ lines : integer;
+ line_size : integer;
+ lines_ln2 : integer;
+ line_size_ln2 : integer
+ );
+ port (
+ clk_i : in std_logic;
+
+ rd_addr : in unsigned(lines_ln2+line_size_ln2-1 downto 0);
+ rd_data : out std_logic_vector(63 downto 0);
+
+ wr_addr : in unsigned(lines_ln2+line_size_ln2-1 downto 0);
+ wr_data : in std_logic_vector(63 downto 0);
+ bwe : in std_logic_vector(7 downto 0)
+ );
+ end component;
+
+ -- Derived parameters
+ constant tag_width : integer := addr_width-line_size_ln2-(lines_ln2-assoc_ln2);
+ constant index_width : integer := lines_ln2-assoc_ln2;
+ constant offset_width : integer := line_size_ln2;
+
+ -- Cache control signals / memory
+ subtype tag_t is std_logic_vector(assoc*tag_width-1 downto 0);
+ subtype lru_t is unsigned(assoc*assoc_ln2-1 downto 0);
+ type cc_tag_a is array(lines/assoc-1 downto 0) of tag_t;
+ type cc_lru_a is array(lines/assoc-1 downto 0) of lru_t;
+ type cc_valid_a is array(lines/assoc-1 downto 0) of std_logic_vector(assoc-1 downto 0);
+ type cc_dirty_a is array(lines/assoc-1 downto 0) of std_logic_vector(assoc-1 downto 0);
+ signal cc_tag : cc_tag_a := (others => (others => dontcare));
+ signal cc_lru : cc_lru_a := (others => (others => dontcare));
+ signal cc_valid : cc_valid_a := (others => (others => '0'));
+ signal cc_dirty : cc_dirty_a := (others => (others => dontcare));
+ attribute ram_style of cc_tag : signal is "block";
+ attribute ram_style of cc_lru : signal is "distributed";
+ attribute ram_style of cc_valid : signal is "distributed";
+ attribute ram_style of cc_dirty : signal is "distributed";
+ signal cc_we : std_logic := '0';
+ signal cc_wr_addr, cc_rd_addr : unsigned(lines_ln2-assoc_ln2-1 downto 0) := (others => dontcare);
+ signal cc_tag_wr_data, cc_tag_rd_data : tag_t := (others => dontcare);
+ signal cc_lru_wr_data, cc_lru_rd_data : lru_t := (others => dontcare);
+ signal cc_valid_wr_data, cc_valid_rd_data : std_logic_vector(assoc-1 downto 0) := (others => '0');
+ signal cc_dirty_wr_data, cc_dirty_rd_data : std_logic_vector(assoc-1 downto 0) := (others => dontcare);
+
+ -- Convenience variable for cc_tag_rd_data
+ type tag_a is array(assoc-1 downto 0) of std_logic_vector(tag_width-1 downto 0);
+ signal tags : tag_a := (others => (others => dontcare));
+
+ -- Cache data signals / memory
+ -- signal cache_we : std_logic := '0';
+ signal cache_wr_addr, cache_rd_addr : unsigned(lines_ln2+line_size_ln2-1 downto 0) := (others => '0');
+ signal cache_wr_data, cache_rd_data : std_logic_vector(63 downto 0) := (others => dontcare);
+ signal cache_bwe : std_logic_vector(7 downto 0) := (others => dontcare);
+
+
+ -- Convenience variables for adr_i
+ signal adr_index : unsigned(index_width-1 downto 0);
+ signal adr_offset : unsigned(offset_width-1 downto 0);
+ signal adr_tag : std_logic_vector(tag_width-1 downto 0);
+
+ -- Tag comparator output
+ signal adr_tag_eq : std_logic_vector(assoc-1 downto 0);
+
+ -- LRU comparator output
+ signal lru_eq0 : std_logic_vector(assoc-1 downto 0);
+
+ -- Priority encoders
+ signal adr_tag_eq_num, eject_num : unsigned(assoc_ln2-1 downto 0);
+ attribute priority_extract of adr_tag_eq_num : signal is "yes";
+ attribute priority_extract of eject_num : signal is "yes";
+
+ -- control signals
+ signal update_lru, set_dirty, set_valid, cache_write, cache_from_mem, eject_dirty : std_logic;
+ signal set_invalid, set_clean, cache_to_mem, adr_tag_eq_num_dirty : std_logic;
+ signal mem_offset, mem_offset_dly : unsigned(offset_width-1 downto 0);
+ signal mem_rdrq_int, mem_wrrq_int : std_logic;
+
+ -- Manual flush/invalidate control signals
+ signal mfi : std_logic;
+ signal mfi_index : unsigned(lines_ln2-assoc_ln2-1 downto 0);
+ signal mfi_num : unsigned(assoc_ln2-1 downto 0);
+ signal mfi_index_ctr_en, mfi_num_ctr_en : std_logic;
+ signal mfi_num_dirty : std_logic;
+ signal user_cc_req_flush, user_cc_req_inval, user_cc_req_none : std_logic;
+begin
+
+ cache_rd_addr <= adr_index & adr_tag_eq_num & adr_offset when cache_to_mem = '0' else
+ adr_index & eject_num & mem_offset when mem_ack = '1' and mfi = '0'else
+ adr_index & eject_num & mem_offset_dly when mfi = '0' else
+ mfi_index & eject_num & mem_offset when mem_ack = '1' and mfi = '1'else
+ mfi_index & eject_num & mem_offset_dly; -- when mfi = '1';
+ cache_wr_addr <= adr_index & adr_tag_eq_num & adr_offset when cache_from_mem = '0' else
+ adr_index & eject_num & mem_offset;
+ cache_wr_data <= wbs_i.dat_i & wbs_i.dat_i when cache_write = '1' else
+ mem_dat_i;-- when cache_from_mem = '1' else
+ --(others => dontcare);
+ cache_bwe <= "0000" & wbs_i.sel_i when cache_write = '1' and wbs_i.adr_i(2) = '0' else
+ wbs_i.sel_i & "0000" when cache_write = '1' and wbs_i.adr_i(2) = '1' else
+ "11111111" when cache_from_mem = '1' and mem_ack = '1' else
+ "00000000";
+
+ wb_ddr_ctrl_wb_sc_fe_ram_inst: wb_ddr_ctrl_wb_sc_fe_ram
+ generic map (
+ lines => lines,
+ line_size => line_size,
+ lines_ln2 => lines_ln2,
+ line_size_ln2 => line_size_ln2)
+ port map (
+ clk_i => clk_i,
+ rd_addr => cache_rd_addr,
+ rd_data => cache_rd_data,
+ wr_addr => cache_wr_addr,
+ wr_data => cache_wr_data,
+ bwe => cache_bwe);
+
+ wbs_o.dat_o <= cache_rd_data(63 downto 32) when wbs_i.adr_i(2) = '1' else
+ cache_rd_data(31 downto 0);
+ mem_dat_o <= cache_rd_data;
+
+ mem_adr <= adr_tag & std_logic_vector(adr_index) when cache_from_mem = '1' else
+ tags(to_integer(eject_num)) & std_logic_vector(adr_index) when cache_to_mem = '1' and mfi = '0' else
+ tags(to_integer(eject_num)) & std_logic_vector(mfi_index); -- when cache_to_mem = '1' and mfi = '1'
+
+ cc_wr_data_gen : for i in 0 to assoc-1 generate
+ cc_tag_wr_data((i+1)*tag_width-1 downto i*tag_width) <=
+ adr_tag when eject_num = i and set_valid = '1' else
+ cc_tag_rd_data((i+1)*tag_width-1 downto i*tag_width);
+
+ cc_lru_wr_data((i+1)*assoc_ln2-1 downto assoc_ln2*i) <=
+ to_unsigned(assoc-1,assoc_ln2) when adr_tag_eq(i) = '1' and update_lru = '1' else
+ cc_lru_rd_data((i+1)*assoc_ln2-1 downto assoc_ln2*i) when cc_lru_rd_data((i+1)*assoc_ln2-1 downto assoc_ln2*i) = 0 else
+ cc_lru_rd_data((i+1)*assoc_ln2-1 downto assoc_ln2*i)-1 when update_lru = '1' else
+ cc_lru_rd_data((i+1)*assoc_ln2-1 downto assoc_ln2*i);
+
+ cc_valid_wr_data(i) <=
+ '1' when eject_num = i and set_valid = '1' else
+ '0' when (adr_tag_eq(i) = '1' or mfi = '1') and set_invalid = '1' else
+ cc_valid_rd_data(i);
+
+ cc_dirty_wr_data(i) <=
+ '1' when adr_tag_eq(i) = '1' and set_dirty = '1' else
+ '0' when eject_num = i and set_valid = '1' else
+ '0' when mfi_num = i and set_clean = '1' else
+ cc_dirty_rd_data(i);
+ end generate;
+
+ cc_wr_addr <= mfi_index when mfi = '1' else
+ adr_index;-- when update_lru = '1' or set_dirty = '1' or set_valid = '1' or set_invalid = '1' else
+ --(others => dontcare);
+ cc_we <= update_lru or set_dirty or set_valid or set_invalid or set_clean;
+
+ -- Memory for cache control
+ cc_mem : process(clk_i)
+ variable cc_wr_addr_int : integer range 0 to lines/assoc-1;
+ variable cc_rd_addr_int : integer range 0 to lines/assoc-1;
+ begin
+ if falling_edge(clk_i) then
+ cc_wr_addr_int := to_integer(cc_wr_addr);
+ cc_rd_addr_int := to_integer(cc_rd_addr);
+ if cc_we = '1' then
+ cc_tag(cc_wr_addr_int) <= cc_tag_wr_data;
+ cc_lru(cc_wr_addr_int) <= cc_lru_wr_data;
+ cc_valid(cc_wr_addr_int) <= cc_valid_wr_data;
+ cc_dirty(cc_wr_addr_int) <= cc_dirty_wr_data;
+ end if;
+ cc_tag_rd_data <= cc_tag(cc_rd_addr_int);
+ cc_lru_rd_data <= cc_lru(cc_rd_addr_int);
+ cc_valid_rd_data <= cc_valid(cc_rd_addr_int);
+ cc_dirty_rd_data <= cc_dirty(cc_rd_addr_int);
+ end if;
+ end process cc_mem;
+
+ assert addr_width = (wbs_i.adr_i'high - wbs_i.adr_i'low) report "Invalid address width, check parameters" severity error;
+ adr_index <= unsigned(wbs_i.adr_i(offset_width+index_width+2 downto offset_width+3));
+ adr_offset <= --unsigned(wbs_cc_i.dat_i(offset_width+2 downto 3)) when user_cc = '1' else
+ unsigned(wbs_i.adr_i(offset_width+2 downto 3));
+ adr_tag <= --wbs_cc_i.dat_i(addr_width+2 downto offset_width+index_width+3) when user_cc = '1' else
+ wbs_i.adr_i(addr_width+2 downto offset_width+index_width+3);
+
+ tags_gen : for i in 0 to assoc-1 generate
+ tags(i) <= cc_tag_rd_data((i+1)*tag_width-1 downto i*tag_width);
+ end generate;
+
+ cc_rd_addr <= mfi_index when mfi = '1' else
+ adr_index;
+
+ tag_compare : for i in 0 to assoc-1 generate
+ adr_tag_eq(i) <= cc_valid_rd_data(i) when tags(i) = adr_tag else
+ '0';
+ end generate;
+
+ lru_compare : for i in 0 to assoc-1 generate
+ lru_eq0(i) <= '1' when cc_lru_rd_data((i+1)*assoc_ln2-1 downto assoc_ln2*i) = 0 else
+ '1' when cc_valid_rd_data(i) = '0' else
+ '0';
+ end generate;
+
+ -- The comb. process for..loop version does not synthesize properly, so do
+ -- this manually
+ assert assoc = 2 or assoc = 4 report "Unsupported associativity" severity error;
+ pe_assoc_2 : if assoc = 2 generate
+ adr_tag_eq_num <= to_unsigned(0,1) when adr_tag_eq(0) = '1' else
+ to_unsigned(1,1) when adr_tag_eq(1) = '1' else
+ (others => dontcare);
+ eject_num <= mfi_num when mfi = '1' else
+ to_unsigned(0,1) when lru_eq0(0) = '1' else
+ to_unsigned(1,1) when lru_eq0(1) = '1' else
+ to_unsigned(0,1);
+ end generate;
+ pe_assoc_4 : if assoc = 4 generate
+ adr_tag_eq_num <= to_unsigned(0,2) when adr_tag_eq(0) = '1' else
+ to_unsigned(1,2) when adr_tag_eq(1) = '1' else
+ to_unsigned(2,2) when adr_tag_eq(2) = '1' else
+ to_unsigned(3,2) when adr_tag_eq(3) = '1' else
+ (others => dontcare);
+ eject_num <= mfi_num when mfi = '1' else
+ to_unsigned(0,2) when lru_eq0(0) = '1' else
+ to_unsigned(1,2) when lru_eq0(1) = '1' else
+ to_unsigned(2,2) when lru_eq0(2) = '1' else
+ to_unsigned(3,2) when lru_eq0(3) = '1' else
+ to_unsigned(0,1);
+ end generate;
+
+ adr_tag_eq_num_dirty <= cc_dirty_rd_data(to_integer(adr_tag_eq_num)) and cc_valid_rd_data(to_integer(adr_tag_eq_num));
+ mfi_num_dirty <= cc_dirty_rd_data(to_integer(mfi_num)) and cc_valid_rd_data(to_integer(mfi_num));
+ eject_dirty <= cc_dirty_rd_data(to_integer(eject_num)) and cc_valid_rd_data(to_integer(eject_num));
+
+ -- Offset counter
+ mem_offset_ctr : process(clk_i)
+ begin
+ if rising_edge(clk_i) then
+ if mem_rdrq_int = '1' or mem_wrrq_int = '1' then
+ mem_offset <= to_unsigned(0,line_size_ln2);
+ mem_offset_dly <= to_unsigned(0, line_size_ln2);
+ elsif mem_ack = '1' then
+ mem_offset <= mem_offset + 1;
+ mem_offset_dly <= mem_offset;
+ end if;
+ end if;
+ end process mem_offset_ctr;
+
+ mfi_index_ctr_en <= '1' when ((user_cc_req_flush = '0' or to_integer(unsigned(cc_valid_rd_data and cc_dirty_rd_data)) = 0) and
+ (user_cc_req_inval = '0' or to_integer(unsigned(cc_valid_rd_data)) = 0)) else
+ '0';
+
+ mfi_index_ctr : process(clk_i)
+ begin
+ if rising_edge(clk_i) then
+ if mfi = '0' then
+ mfi_index <= to_unsigned(0, lines_ln2-assoc_ln2);
+ elsif mfi_index_ctr_en = '1' then
+ mfi_index <= mfi_index + 1;
+ end if;
+ end if;
+ end process mfi_index_ctr;
+
+ mfi_num_ctr_en <= '1' when user_cc_req_flush = '1' and mfi_num_dirty = '0' else
+ '0';
+
+ mfi_num_ctr : process(clk_i)
+ begin
+ if rising_edge(clk_i) then
+ if mfi = '0' or mfi_index_ctr_en = '1' then
+ mfi_num <= to_unsigned(0, assoc_ln2);
+ elsif mfi_num_ctr_en = '1' then
+ mfi_num <= mfi_num + 1;
+ end if;
+ end if;
+ end process mfi_num_ctr;
+
+ wb_ddr_ctrl_wb_sc_fe_fsm_inst: wb_ddr_ctrl_wb_sc_fe_fsm
+ generic map (
+ line_size => line_size,
+ lines => lines,
+ assoc => assoc,
+ line_size_ln2 => line_size_ln2,
+ lines_ln2 => lines_ln2,
+ assoc_ln2 => assoc_ln2,
+ addr_width => addr_width)
+ port map (
+ clk_i => clk_i,
+ rst_i => rst_i,
+ cyc_i => wbs_i.cyc_i,
+ stb_i => wbs_i.stb_i,
+ we_i => wbs_i.we_i,
+ adr_tag_eq => adr_tag_eq,
+ eject_dirty => eject_dirty,
+ mem_offset => mem_offset_dly,
+ mfi_index => mfi_index,
+ user_cc_req_flush => user_cc_req_flush,
+ user_cc_req_inval => user_cc_req_inval,
+ user_cc_req_none => user_cc_req_none,
+ adr_tag_eq_num_dirty => adr_tag_eq_num_dirty,
+ mem_ack => mem_ack,
+ mfi_num_dirty => mfi_num_dirty,
+ cc_valid => cc_valid_rd_data,
+ cc_dirty => cc_dirty_rd_data,
+
+ ack_o => wbs_o.ack_o,
+ update_lru => update_lru,
+ set_clean => set_clean,
+ set_dirty => set_dirty,
+ set_valid => set_valid,
+ set_invalid => set_invalid,
+ cache_write => cache_write,
+ cache_from_mem => cache_from_mem,
+ cache_to_mem => cache_to_mem,
+ mem_rdrq => mem_rdrq_int,
+ mem_wrrq => mem_wrrq_int,
+ mfi => mfi,
+ user_cc_ack_o => wbs_cc_o.ack_o);
+
+ mem_rdrq <= mem_rdrq_int;
+ mem_wrrq <= mem_wrrq_int;
+
+ user_cc_req_flush <=
+ wbs_cc_i.dat_i(1) when (wbs_cc_i.cyc_i = '1' and wbs_cc_i.stb_i = '1' and
+ wbs_cc_i.we_i = '1') else
+ '0';
+ user_cc_req_inval <=
+ wbs_cc_i.dat_i(0) when (wbs_cc_i.cyc_i = '1' and wbs_cc_i.stb_i = '1' and
+ wbs_cc_i.we_i = '1') else
+ '0';
+ user_cc_req_none <=
+ '1' when (wbs_cc_i.cyc_i = '1' and wbs_cc_i.stb_i = '1' and
+ (wbs_cc_i.we_i = '0' or wbs_cc_i.dat_i(1 downto 0) = "00")) else
+ '0';
+
+
+ wbs_cc_o.dat_o <= (others => '0');
+end Behavioral;
diff --git a/src/wb_ddr_ctrl_wb_sc_fe_fsm.vhd b/src/wb_ddr_ctrl_wb_sc_fe_fsm.vhd
new file mode 100644
index 0000000..9ed33c4
--- /dev/null
+++ b/src/wb_ddr_ctrl_wb_sc_fe_fsm.vhd
@@ -0,0 +1,374 @@
+----------------------------------------------------------------------------------
+-- Company:
+-- Engineer:
+--
+-- Create Date: 11/06/2012 03:04:35 PM
+-- Design Name:
+-- Module Name: wb_ddr_ctrl_wb_sc_fe_fsm - Behavioral
+-- Project Name:
+-- Target Devices:
+-- Tool Versions:
+-- Description: Memory controller - system clock domain - Cache front-end -
+-- Control path
+--
+-- Dependencies:
+--
+-- Revision:
+-- Revision 0.01 - File Created
+-- Additional Comments:
+--
+----------------------------------------------------------------------------------
+
+
+library IEEE;
+use IEEE.STD_LOGIC_1164.ALL;
+
+-- Uncomment the following library declaration if using
+-- arithmetic functions with Signed or Unsigned values
+use IEEE.NUMERIC_STD.ALL;
+
+-- Uncomment the following library declaration if instantiating
+-- any Xilinx primitives in this code.
+library UNISIM;
+use UNISIM.VComponents.all;
+
+use work.intercon_package.all;
+
+entity wb_ddr_ctrl_wb_sc_fe_fsm is
+ generic (
+ line_size : integer := 16;
+ lines : integer := 64;
+ assoc : integer := 2;
+ line_size_ln2 : integer := 4;
+ lines_ln2 : integer := 6;
+ assoc_ln2 : integer := 1;
+ addr_width : integer := 24
+ );
+ port (
+ clk_i : in std_logic;
+ rst_i : in std_logic;
+
+ cyc_i : in std_logic;
+ stb_i : in std_logic;
+ we_i : in std_logic;
+ adr_tag_eq : in std_logic_vector(assoc-1 downto 0);
+ eject_dirty : in std_logic;
+ mem_offset : in unsigned(line_size_ln2-1 downto 0);
+ mfi_index : in unsigned(lines_ln2-assoc_ln2-1 downto 0);
+ adr_tag_eq_num_dirty : in std_logic;
+ user_cc_req_flush : in std_logic;
+ user_cc_req_inval : in std_logic;
+ user_cc_req_none : in std_logic;
+ mem_ack : in std_logic;
+ mfi_num_dirty : in std_logic;
+ cc_valid : in std_logic_vector(assoc-1 downto 0);
+ cc_dirty : in std_logic_vector(assoc-1 downto 0);
+
+ ack_o : out std_logic;
+ update_lru : out std_logic := '0';
+ set_dirty : out std_logic := '0';
+ set_clean : out std_logic := '0';
+ set_valid : out std_logic := '0';
+ set_invalid : out std_logic := '0';
+ cache_write : out std_logic := '0';
+ cache_from_mem : out std_logic := '0';
+ cache_to_mem : out std_logic := '0';
+ mem_rdrq : out std_logic := '0';
+ mem_wrrq : out std_logic := '0';
+ mfi : out std_logic := '0';
+ user_cc_ack_o : out std_logic := '0'
+ );
+end wb_ddr_ctrl_wb_sc_fe_fsm;
+
+architecture Behavioral of wb_ddr_ctrl_wb_sc_fe_fsm is
+ type states is (S_IDLE, S_WRITEBACK1, S_WRITEBACK2, S_FETCH1, S_FETCH2, S_WAIT, S_WAIT_FETCH,
+ S_MFI, S_MFI_WRITEBACK1, S_MFI_WRITEBACK2, S_MFI_WAIT);
+ signal state : states := S_IDLE;
+begin
+
+ cache_ctrl : process(clk_i)
+ begin
+ if rising_edge(clk_i) then
+ ack_o <= '0';
+ update_lru <= '0';
+ set_dirty <= '0';
+ set_clean <= '0';
+ set_valid <= '0';
+ set_invalid <= '0';
+ cache_write <= '0';
+ cache_from_mem <= '0';
+ cache_to_mem <= '0';
+ mem_rdrq <= '0';
+ mem_wrrq <= '0';
+ mfi <= '0';
+ user_cc_ack_o <= '0';
+
+ case state is
+ when S_IDLE =>
+ if user_cc_req_flush = '1' or user_cc_req_inval = '1' then
+ mfi <= '1';
+ state <= S_MFI;
+ elsif user_cc_req_none = '1' then
+ user_cc_ack_o <= '1';
+ state <= S_WAIT;
+ elsif cyc_i = '1' and stb_i = '1' then
+ if we_i = '1' then
+ if to_integer(unsigned(adr_tag_eq)) = 0 then
+ -- miss
+ if eject_dirty = '1' then
+ cache_to_mem <= '1';
+ mem_wrrq <= '1';
+ state <= S_WRITEBACK1;
+ else
+ cache_from_mem <= '1';
+ mem_rdrq <= '1';
+ state <= S_FETCH1;
+ end if;
+ else
+ -- hit
+ ack_o <= '1';
+ update_lru <= '1';
+ set_dirty <= '1';
+ cache_write <= '1';
+ state <= S_WAIT;
+ end if;
+ else
+ if to_integer(unsigned(adr_tag_eq)) = 0 then
+ -- miss
+ if eject_dirty = '1' then
+ cache_to_mem <= '1';
+ mem_wrrq <= '1';
+ state <= S_WRITEBACK1;
+ else
+ cache_from_mem <= '1';
+ mem_rdrq <= '1';
+ state <= S_FETCH1;
+ end if;
+ else
+ -- hit
+ ack_o <= '1';
+ update_lru <= '1';
+ state <= S_WAIT;
+ end if;
+ end if;
+ end if;
+ when S_WAIT =>
+ state <= S_IDLE;
+ when S_FETCH1 =>
+ cache_from_mem <= '1';
+ state <= S_FETCH2;
+ when S_FETCH2 =>
+ cache_from_mem <= '1';
+ if mem_offset = line_size-1 then
+ set_valid <= '1';
+ state <= S_WAIT;
+ end if;
+ when S_WRITEBACK1 =>
+ cache_to_mem <= '1';
+ state <= S_WRITEBACK2;
+ when S_WRITEBACK2 =>
+ cache_to_mem <= '1';
+ if mem_offset = line_size-1 and mem_ack = '1' then
+ cache_to_mem <= '0';
+ state <= S_WAIT_FETCH;
+ end if;
+ when S_WAIT_FETCH =>
+ cache_from_mem <= '1';
+ mem_rdrq <= '1';
+ state <= S_FETCH1;
+ when S_MFI =>
+ mfi <= '1';
+ if ((user_cc_req_flush = '0' or to_integer(unsigned(cc_valid and cc_dirty)) = 0) and
+ (user_cc_req_inval = '0' or to_integer(unsigned(cc_valid)) = 0)) then
+ -- nothing to do for this set or done with it
+ if mfi_index = lines/assoc-1 then
+ user_cc_ack_o <= '1';
+ state <= S_WAIT;
+ end if;
+ else
+ if user_cc_req_flush = '1' and to_integer(unsigned(cc_valid and cc_dirty)) /= 0 then
+ if mfi_num_dirty = '1' then
+ cache_to_mem <= '1';
+ mem_wrrq <= '1';
+ state <= S_MFI_WRITEBACK1;
+ end if;
+ elsif user_cc_req_inval = '1' then
+ set_invalid <= '1';
+ end if;
+ end if;
+
+ --if user_cc_req_inval = '1' then
+ -- if to_integer(unsigned(adr_tag_eq)) = 0 then
+ -- -- address not in cache, nothing to invalidate
+ -- user_cc_ack_o <= '1';
+ -- state <= S_WAIT;
+ -- else
+ -- if adr_tag_eq_num_dirty = '1' then
+ -- -- line is dirty, flush first
+ -- cache_to_mem <= '1';
+ -- mem_wrrq <= '1';
+ -- state <= S_USER_WRITEBACK1;
+ -- else
+ -- set_invalid <= '1';
+ -- user_cc_ack_o <= '1';
+ -- state <= S_WAIT;
+ -- end if;
+ -- end if;
+ --elsif user_cc_req_flush = '1' then
+ -- if to_integer(unsigned(adr_tag_eq)) = 0 or adr_tag_eq_num_dirty = '0' then
+ -- -- address not in cache or clean, nothing to flush
+ -- user_cc_ack_o <= '1';
+ -- state <= S_WAIT;
+ -- else
+ -- cache_to_mem <= '1';
+ -- mem_wrrq <= '1';
+ -- state <= S_USER_WRITEBACK1;
+ -- end if;
+ --else -- WTF?
+ -- state <= S_WAIT;
+ --end if;
+ when S_MFI_WRITEBACK1 =>
+ mfi <= '1';
+ cache_to_mem <= '1';
+ state <= S_MFI_WRITEBACK2;
+ when S_MFI_WRITEBACK2 =>
+ mfi <= '1';
+ cache_to_mem <= '1';
+ if mem_offset = line_size-1 and mem_ack = '1' then
+ cache_to_mem <= '0';
+ set_clean <= '1';
+ state <= S_MFI_WAIT;
+ end if;
+ when S_MFI_WAIT =>
+ mfi <= '1';
+ state <= S_MFI;
+ end case;
+ end if;
+ end process cache_ctrl;
+
+ --cache_ctrl : process(clk_i)
+ -- begin
+ -- if rising_edge(clk_i) then
+ -- cache_we <= '0';
+ -- cache_wr_data <= (others => '-');
+ -- line_info_we <= '0';
+ -- line_info_wr_data <= dontcare_line_info;
+ -- mem_adr <= (others => '-');
+ -- mem_rdrq <= '0';
+ -- mem_wrrq <= '0';
+
+ -- case state is
+ -- when S_IDLE =>
+ -- if wbs_i.stb_i = '1' and wbs_i.cyc_i = '1' then
+ -- if wbs_i.we_i = '1' then
+ -- if to_integer(unsigned(adr_tag_eq)) = 0 then
+ -- -- miss
+ -- if line_info_rd_data.valid(eject_num) = '1' and
+ -- line_info_rd_data.dirty(eject_num) = '1' then
+ -- cache_rd_addr <= adr_index*line_size*assoc+eject_num*line_size+0;
+ -- ctr <= 0;
+ -- state <= S_WRITEBACK1;
+ -- else
+ -- mem_adr <= wbs_i.adr_i(addr_width+1 downto line_size_ln2+2);
+ -- mem_rdrq <= '1';
+ -- ctr <= 0;
+ -- state <= S_FETCH;
+ -- end if;
+ -- else
+ -- -- hit
+ -- wbs_o.ack_o <= '1';
+ -- cache_wr_data <= wbs_i.dat_i;
+ -- cache_wr_addr <= adr_index*line_size*assoc+adr_tag_eq_num*line_size+adr_offset;
+ -- cache_we <= '1';
+ -- line_info_wr_data <= line_info_rd_data;
+ -- line_info_wr_data.dirty(adr_tag_eq_num) <= '1';
+ -- for i in 0 to assoc-1 loop
+ -- if i = adr_tag_eq_num then
+ -- line_info_wr_data.lru(i) <= assoc-1;
+ -- else
+ -- if line_info_rd_data.lru(i) > 0 then
+ -- line_info_wr_data.lru(i) <= line_info_rd_data.lru(i) - 1;
+ -- end if;
+ -- end if;
+ -- end loop;
+ -- line_info_wr_addr <= line_info_rd_addr;
+ -- line_info_we <= '1';
+ -- state <= S_WAIT;
+ -- end if;
+ -- else
+ -- if to_integer(unsigned(adr_tag_eq)) = 0 then
+ -- -- miss
+ -- if line_info_rd_data.valid(eject_num) = '1' and
+ -- line_info_rd_data.dirty(eject_num) = '1' then
+ -- cache_rd_addr <= adr_index*line_size*assoc+eject_num*line_size+0;
+ -- ctr <= 0;
+ -- state <= S_WRITEBACK1;
+ -- else
+ -- mem_adr <= wbs_i.adr_i(addr_width+1 downto line_size_ln2+2);
+ -- mem_rdrq <= '1';
+ -- ctr <= 0;
+ -- state <= S_FETCH;
+ -- end if;
+ -- else
+ -- -- hit
+ -- cache_rd_addr <= adr_index*line_size*assoc+adr_tag_eq_num*line_size+adr_offset;
+ -- line_info_wr_data <= line_info_rd_data;
+ -- for i in 0 to assoc-1 loop
+ -- if i = adr_tag_eq_num then
+ -- line_info_wr_data.lru(i) <= assoc-1;
+ -- else
+ -- if line_info_rd_data.lru(i) > 0 then
+ -- line_info_wr_data.lru(i) <= line_info_rd_data.lru(i) - 1;
+ -- end if;
+ -- end if;
+ -- end loop;
+ -- line_info_wr_addr <= line_info_rd_addr;
+ -- line_info_we <= '1';
+ -- state <= S_READHIT;
+ -- end if;
+ -- end if;
+ -- end if;
+ -- when S_WAIT =>
+ -- state <= S_IDLE;
+ -- when S_READHIT =>
+ -- wbs_o.ack_o <= '1';
+ -- state <= S_WAIT;
+
+ -- when S_FETCH =>
+ -- if mem_ack = '1' then
+ -- cache_wr_data <= mem_dat_i;
+ -- cache_wr_addr <= adr_index*line_size*assoc+eject_num*line_size+ctr;
+ -- cache_we <= '1';
+ -- if ctr = line_size-1 then
+ -- line_info_wr_data <= line_info_rd_data;
+ -- line_info_wr_data.valid(eject_num) <= '1';
+ -- line_info_wr_data.dirty(eject_num) <= '0';
+ -- line_info_wr_data.tag(eject_num) <= adr_tag;
+ -- line_info_wr_addr <= line_info_rd_addr;
+ -- line_info_we <= '1';
+ -- state <= S_IDLE; -- restart request
+ -- else
+ -- ctr <= ctr + 1;
+ -- end if;
+ -- end if;
+ -- when S_WRITEBACK1 =>
+ -- mem_adr <= wbs_i.adr_i(addr_width+1 downto line_size_ln2+2);
+ -- mem_wrrq <= '1';
+ -- state <= S_WRITEBACK2;
+ -- when S_WRITEBACK2 =>
+ -- if mem_ack = '1' then
+ -- cache_rd_addr <= adr_index*line_size*assoc+eject_num*line_size+ctr;
+ -- if ctr = line_size-1 then
+ -- mem_adr <= wbs_i.adr_i(addr_width+1 downto line_size_ln2+2);
+ -- mem_rdrq <= '1';
+ -- ctr <= 0;
+ -- state <= S_FETCH;
+ -- else
+ -- ctr <= ctr + 1;
+ -- end if;
+ -- end if;
+ -- end case;
+ -- end if;
+ -- end process cache_ctrl;
+end Behavioral;
+