You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
123 lines
3.7 KiB
123 lines
3.7 KiB
library ieee; |
|
use ieee.std_logic_1164.all; |
|
use ieee.numeric_std.all; |
|
|
|
library work; |
|
use work.common.all; |
|
|
|
entity cr_file is |
|
generic ( |
|
SIM : boolean := false; |
|
-- Non-zero to enable log data collection |
|
LOG_LENGTH : natural := 0 |
|
); |
|
port( |
|
clk : in std_logic; |
|
|
|
d_in : in Decode2ToCrFileType; |
|
d_out : out CrFileToDecode2Type; |
|
|
|
w_in : in WritebackToCrFileType; |
|
ctrl : in ctrl_t; |
|
|
|
-- debug |
|
sim_dump : in std_ulogic; |
|
|
|
log_out : out std_ulogic_vector(12 downto 0) |
|
); |
|
end entity cr_file; |
|
|
|
architecture behaviour of cr_file is |
|
signal crs : std_ulogic_vector(31 downto 0) := (others => '0'); |
|
signal crs_updated : std_ulogic_vector(31 downto 0); |
|
signal xerc : xer_common_t := xerc_init; |
|
signal xerc_updated : xer_common_t; |
|
begin |
|
cr_create_0: process(all) |
|
variable hi, lo : integer := 0; |
|
variable cr_tmp : std_ulogic_vector(31 downto 0) := (others => '0'); |
|
begin |
|
cr_tmp := crs; |
|
|
|
for i in 0 to 7 loop |
|
if w_in.write_cr_mask(i) = '1' then |
|
lo := i*4; |
|
hi := lo + 3; |
|
cr_tmp(hi downto lo) := w_in.write_cr_data(hi downto lo); |
|
end if; |
|
end loop; |
|
|
|
crs_updated <= cr_tmp; |
|
|
|
if w_in.write_xerc_enable = '1' then |
|
xerc_updated <= w_in.write_xerc_data; |
|
else |
|
xerc_updated <= xerc; |
|
end if; |
|
|
|
end process; |
|
|
|
-- synchronous writes |
|
cr_write_0: process(clk) |
|
begin |
|
if rising_edge(clk) then |
|
if w_in.write_cr_enable = '1' then |
|
report "Writing " & to_hstring(w_in.write_cr_data) & " to CR mask " & to_hstring(w_in.write_cr_mask); |
|
crs <= crs_updated; |
|
end if; |
|
if w_in.write_xerc_enable = '1' then |
|
report "Writing XERC SO=" & std_ulogic'image(xerc_updated.so) & |
|
" OV=" & std_ulogic'image(xerc_updated.ov) & |
|
" CA=" & std_ulogic'image(xerc_updated.ca) & |
|
" OV32=" & std_ulogic'image(xerc_updated.ov32) & |
|
" CA32=" & std_ulogic'image(xerc_updated.ca32); |
|
xerc <= xerc_updated; |
|
end if; |
|
end if; |
|
end process; |
|
|
|
-- asynchronous reads |
|
cr_read_0: process(all) |
|
begin |
|
-- just return the entire CR to make mfcrf easier for now |
|
if d_in.read = '1' then |
|
report "Reading CR " & to_hstring(crs_updated); |
|
end if; |
|
d_out.read_cr_data <= crs_updated; |
|
d_out.read_xerc_data <= xerc_updated; |
|
end process; |
|
|
|
sim_dump_test: if SIM generate |
|
dump_cr: process(all) |
|
variable xer : std_ulogic_vector(31 downto 0); |
|
begin |
|
if sim_dump = '1' then |
|
report "CR 00000000" & to_hstring(crs); |
|
xer := (others => '0'); |
|
xer(31) := xerc.so; |
|
xer(30) := xerc.ov; |
|
xer(29) := xerc.ca; |
|
xer(19) := xerc.ov32; |
|
xer(18) := xerc.ca32; |
|
xer(17 downto 0) := ctrl.xer_low; |
|
report "XER 00000000" & to_hstring(xer); |
|
assert false report "end of test" severity failure; |
|
end if; |
|
end process; |
|
end generate; |
|
|
|
cf_log: if LOG_LENGTH > 0 generate |
|
signal log_data : std_ulogic_vector(12 downto 0); |
|
begin |
|
cr_log: process(clk) |
|
begin |
|
if rising_edge(clk) then |
|
log_data <= w_in.write_cr_enable & |
|
w_in.write_cr_data(31 downto 28) & |
|
w_in.write_cr_mask; |
|
end if; |
|
end process; |
|
log_out <= log_data; |
|
end generate; |
|
|
|
end architecture behaviour;
|
|
|