Merge branch 'fpga' into main

This commit is contained in:
Ross Thompson 2021-12-02 14:28:10 -06:00
commit b7e8c74e61
87 changed files with 110432 additions and 290 deletions

2
.gitignore vendored
View file

@ -35,3 +35,5 @@ tests/linux-testgen/buildroot-config-src/linux.config.old
tests/linux-testgen/buildroot-config-src/busybox.config.old
wally-pipelined/regression/slack-notifier/slack-webhook-url.txt
wally-pipelined/regression/logs
fpga/generator/IP
fpga/generator/vivado.*

View file

@ -0,0 +1,294 @@
# The main clocks are all autogenerated by the Xilinx IP
# mmcm_clkout1 is the 22Mhz clock from the DDR4 IP used to drive wally and the AHBLite Bus.
# mmcm_clkout0 is the clock output of the DDR4 memory interface / 4.
# This clock is not used by wally or the AHBLite Bus. However it is used by the AXI BUS on the DD4 IP.
# generate 1 clock for the slow speed SD Card hardware. However we need to time at the mmcm_clkout1
# clock speed.
#create_generated_clock -name r_fd_Q -source [get_pins wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/toggle_flip_flop/i_CLK] -divide_by 50 [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/toggle_flip_flop/r_fd_Q]
#create_clock -period 4.000 [get_ports default_250mhz_clk1_0_p]
# need to create a clock for mmcm_clkout1. In the gui flow this was auto generated somehow.
# turns out this clock is auto generated but has a different name. wtf
# 10 Mhz
#create_clock -name mmcm_clkout1 -period 100 [get_pins xlnx_ddr4_c0/addn_ui_clkout1]
#create_generated_clock -name mmcm_clkout1 -source [get_pins xlnx_ddr4_c0/c0_sys_clk_p] -edges {1 2 3} -edge_shift {0.000 48.000 96.000} [get_pins xlnx_ddr4_c0/addn_ui_clkout1]
create_generated_clock -name mmcm_clkout1 xlnx_ddr4_c0/addn_ui_clkout1
create_generated_clock -name CLKDiv64_Gen -source [get_pins wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/I0] -multiply_by 1 [get_pins wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/O]
#create_generated_clock -name mmcm_clkout1_Gen -source [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/I0] -divide_by 1 -add -master_clock mmcm_clkout1 [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/O]
#create_generated_clock -name CLKDiv64_Gen -source [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/I1] -divide_by 1 -add -master_clock mmcm_clkout1_Gen [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/O]
#create_generated_clock -name mmcm_clkout1_Gen_slow -source [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/I0] -divide_by 8 -add -master_clock mmcm_clkout1 [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/O]
#create_generated_clock -name CLKDiv64_Gen_slow -source [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/I1] -divide_by 8 -add -master_clock mmcm_clkout1_Gen_slow [get_pins wrapper_i/wallypipelinedsocwra_0/inst/wallypipelinedsoc/uncore/sdc.SDC/sd_top/slow_clk_divider/clkMux/O]
#set_clock_groups -logically_exclusive -group [get_clocks -include_generated_clocks mmcm_clkout1_Gen] -group [get_clocks -include_generated_clocks CLKDiv64_Gen]
#set_clock_groups -logically_exclusive -group [get_clocks -include_generated_clocks mmcm_clkout1_Gen] -group [get_clocks -include_generated_clocks CLKDiv64_Gen_slow]
##### GPI ####
set_property PACKAGE_PIN BB24 [get_ports {GPI[0]}]
set_property PACKAGE_PIN BF22 [get_ports {GPI[1]}]
set_property PACKAGE_PIN BD23 [get_ports {GPI[2]}]
set_property PACKAGE_PIN BE23 [get_ports {GPI[3]}]
set_property IOSTANDARD LVCMOS18 [get_ports {GPI[3]}]
set_property IOSTANDARD LVCMOS18 [get_ports {GPI[2]}]
set_property IOSTANDARD LVCMOS18 [get_ports {GPI[1]}]
set_property IOSTANDARD LVCMOS18 [get_ports {GPI[0]}]
set_input_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 2.000 [get_ports {GPI[*]}]
set_input_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 2.000 [get_ports {GPI[*]}]
set_max_delay -from [get_ports {GPI[*]}] 10.000
##### GPO ####
set_property PACKAGE_PIN AT32 [get_ports {GPO[0]}]
set_property PACKAGE_PIN AV34 [get_ports {GPO[1]}]
set_property PACKAGE_PIN AY30 [get_ports {GPO[2]}]
set_property PACKAGE_PIN BF32 [get_ports {GPO[4]}]
set_property PACKAGE_PIN BB32 [get_ports {GPO[3]}]
set_property IOSTANDARD LVCMOS12 [get_ports {GPO[4]}]
set_property IOSTANDARD LVCMOS12 [get_ports {GPO[3]}]
set_property IOSTANDARD LVCMOS12 [get_ports {GPO[2]}]
set_property IOSTANDARD LVCMOS12 [get_ports {GPO[1]}]
set_property IOSTANDARD LVCMOS12 [get_ports {GPO[0]}]
set_max_delay -to [get_ports {GPO[*]}] 10.000
set_output_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 0.000 [get_ports {GPO[*]}]
set_output_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 0.000 [get_ports {GPO[*]}]
##### UART #####
set_property PACKAGE_PIN AW25 [get_ports UARTSin]
set_property PACKAGE_PIN BB21 [get_ports UARTSout]
set_max_delay -from [get_ports UARTSin] 10.000
set_max_delay -to [get_ports UARTSout] 10.000
set_property IOSTANDARD LVCMOS18 [get_ports UARTSin]
set_property IOSTANDARD LVCMOS18 [get_ports UARTSout]
set_property DRIVE 6 [get_ports UARTSout]
set_input_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 2.000 [get_ports UARTSin]
set_input_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 2.000 [get_ports UARTSin]
set_output_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 0.000 [get_ports UARTSout]
set_output_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 0.000 [get_ports UARTSout]
##### reset #####
set_input_delay -clock [get_clocks default_250mhz_clk1_0_p] -min -add_delay 2.000 [get_ports reset]
set_input_delay -clock [get_clocks default_250mhz_clk1_0_p] -max -add_delay 2.000 [get_ports reset]
set_input_delay -clock [get_clocks mmcm_clkout0] -min -add_delay 0.000 [get_ports reset]
set_input_delay -clock [get_clocks mmcm_clkout0] -max -add_delay 0.000 [get_ports reset]
set_input_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 0.000 [get_ports reset]
set_input_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 0.000 [get_ports reset]
set_max_delay -from [get_ports reset] 15.000
set_false_path -from [get_ports reset]
##### cpu_reset #####
set_property PACKAGE_PIN AV36 [get_ports {cpu_reset}]
set_property IOSTANDARD LVCMOS12 [get_ports {cpu_reset}]
set_output_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 0.000 [get_ports {cpu_reset}]
set_output_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 0.000 [get_ports {cpu_reset}]
##### calib #####
set_property PACKAGE_PIN BA37 [get_ports calib]
set_property IOSTANDARD LVCMOS12 [get_ports calib]
set_output_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 0.000 [get_ports calib]
set_output_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 20.000 [get_ports calib]
set_max_delay -from [get_pins xlnx_ddr4_c0/inst/u_ddr4_mem_intfc/u_ddr_cal_top/calDone_gated_reg/C] -to [get_ports calib] 50.000
##### ahblite_resetn #####
set_property PACKAGE_PIN AU37 [get_ports {ahblite_resetn}]
set_property IOSTANDARD LVCMOS12 [get_ports {ahblite_resetn}]
set_output_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 0.000 [get_ports {ahblite_resetn}]
set_output_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 0.000 [get_ports {ahblite_resetn}]
##### south_rst #####
set_property PACKAGE_PIN BE22 [get_ports south_rst]
set_property IOSTANDARD LVCMOS18 [get_ports south_rst]
set_input_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 2.000 [get_ports south_rst]
set_input_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 2.000 [get_ports south_rst]
##### SD Card I/O #####
set_property PACKAGE_PIN AY14 [get_ports {SDCDat[3]}]
set_property IOSTANDARD LVCMOS18 [get_ports {SDCDat[3]}]
set_property IOSTANDARD LVCMOS18 [get_ports {SDCDat[2]}]
set_property IOSTANDARD LVCMOS18 [get_ports {SDCDat[1]}]
set_property IOSTANDARD LVCMOS18 [get_ports {SDCDat[0]}]
set_property PACKAGE_PIN AU16 [get_ports {SDCDat[2]}]
set_property PACKAGE_PIN AV16 [get_ports {SDCDat[1]}]
set_property PACKAGE_PIN AW15 [get_ports {SDCDat[0]}]
set_property IOSTANDARD LVCMOS18 [get_ports SDCCLK]
set_property IOSTANDARD LVCMOS18 [get_ports {SDCCmd}]
set_property PACKAGE_PIN AV15 [get_ports SDCCLK]
set_property PACKAGE_PIN AY15 [get_ports {SDCCmd}]
set_property PULLUP true [get_ports {SDCDat[3]}]
set_property PULLUP true [get_ports {SDCDat[2]}]
set_property PULLUP true [get_ports {SDCDat[1]}]
set_property PULLUP true [get_ports {SDCDat[0]}]
set_property PULLUP true [get_ports {SDCCmd}]
set_input_delay -clock [get_clocks CLKDiv64_Gen] -min -add_delay 2.500 [get_ports {SDCDat[*]}]
set_input_delay -clock [get_clocks CLKDiv64_Gen] -max -add_delay 21.000 [get_ports {SDCDat[*]}]
set_input_delay -clock [get_clocks CLKDiv64_Gen] -min -add_delay 2.500 [get_ports {SDCCmd}]
set_input_delay -clock [get_clocks CLKDiv64_Gen] -max -add_delay 14.000 [get_ports {SDCCmd}]
set_output_delay -clock [get_clocks CLKDiv64_Gen] -min -add_delay 2.000 [get_ports {SDCCmd}]
set_output_delay -clock [get_clocks CLKDiv64_Gen] -max -add_delay 6.000 [get_ports {SDCCmd}]
set_output_delay -clock [get_clocks CLKDiv64_Gen] 0.000 [get_ports SDCCLK]
set_property DCI_CASCADE {64} [get_iobanks 65]
set_property INTERNAL_VREF 0.9 [get_iobanks 65]
set_property PACKAGE_PIN E13 [get_ports c0_ddr4_act_n]
set_property PACKAGE_PIN D14 [get_ports {c0_ddr4_adr[0]}]
set_property PACKAGE_PIN C12 [get_ports {c0_ddr4_adr[10]}]
set_property PACKAGE_PIN B13 [get_ports {c0_ddr4_adr[11]}]
set_property PACKAGE_PIN C13 [get_ports {c0_ddr4_adr[12]}]
set_property PACKAGE_PIN D15 [get_ports {c0_ddr4_adr[13]}]
set_property PACKAGE_PIN H14 [get_ports {c0_ddr4_adr[14]}]
set_property PACKAGE_PIN H15 [get_ports {c0_ddr4_adr[15]}]
set_property PACKAGE_PIN F15 [get_ports {c0_ddr4_adr[16]}]
set_property PACKAGE_PIN B15 [get_ports {c0_ddr4_adr[1]}]
set_property PACKAGE_PIN B16 [get_ports {c0_ddr4_adr[2]}]
set_property PACKAGE_PIN C14 [get_ports {c0_ddr4_adr[3]}]
set_property PACKAGE_PIN C15 [get_ports {c0_ddr4_adr[4]}]
set_property PACKAGE_PIN A13 [get_ports {c0_ddr4_adr[5]}]
set_property PACKAGE_PIN A14 [get_ports {c0_ddr4_adr[6]}]
set_property PACKAGE_PIN A15 [get_ports {c0_ddr4_adr[7]}]
set_property PACKAGE_PIN A16 [get_ports {c0_ddr4_adr[8]}]
set_property PACKAGE_PIN B12 [get_ports {c0_ddr4_adr[9]}]
set_property PACKAGE_PIN G15 [get_ports {c0_ddr4_ba[0]}]
set_property PACKAGE_PIN G13 [get_ports {c0_ddr4_ba[1]}]
set_property PACKAGE_PIN H13 [get_ports {c0_ddr4_bg[0]}]
set_property PACKAGE_PIN F14 [get_ports {c0_ddr4_ck_t[0]}]
set_property PACKAGE_PIN E14 [get_ports {c0_ddr4_ck_c[0]}]
set_property PACKAGE_PIN A10 [get_ports {c0_ddr4_cke[0]}]
set_property PACKAGE_PIN F13 [get_ports {c0_ddr4_cs_n[0]}]
set_property PACKAGE_PIN F11 [get_ports {c0_ddr4_dq[0]}]
set_property PACKAGE_PIN M18 [get_ports {c0_ddr4_dq[10]}]
set_property PACKAGE_PIN M17 [get_ports {c0_ddr4_dq[11]}]
set_property PACKAGE_PIN N19 [get_ports {c0_ddr4_dq[12]}]
set_property PACKAGE_PIN N18 [get_ports {c0_ddr4_dq[13]}]
set_property PACKAGE_PIN N17 [get_ports {c0_ddr4_dq[14]}]
set_property PACKAGE_PIN M16 [get_ports {c0_ddr4_dq[15]}]
set_property PACKAGE_PIN L16 [get_ports {c0_ddr4_dq[16]}]
set_property PACKAGE_PIN K16 [get_ports {c0_ddr4_dq[17]}]
set_property PACKAGE_PIN L18 [get_ports {c0_ddr4_dq[18]}]
set_property PACKAGE_PIN K18 [get_ports {c0_ddr4_dq[19]}]
set_property PACKAGE_PIN E11 [get_ports {c0_ddr4_dq[1]}]
set_property PACKAGE_PIN J17 [get_ports {c0_ddr4_dq[20]}]
set_property PACKAGE_PIN H17 [get_ports {c0_ddr4_dq[21]}]
set_property PACKAGE_PIN H19 [get_ports {c0_ddr4_dq[22]}]
set_property PACKAGE_PIN H18 [get_ports {c0_ddr4_dq[23]}]
set_property PACKAGE_PIN F19 [get_ports {c0_ddr4_dq[24]}]
set_property PACKAGE_PIN F18 [get_ports {c0_ddr4_dq[25]}]
set_property PACKAGE_PIN E19 [get_ports {c0_ddr4_dq[26]}]
set_property PACKAGE_PIN E18 [get_ports {c0_ddr4_dq[27]}]
set_property PACKAGE_PIN G20 [get_ports {c0_ddr4_dq[28]}]
set_property PACKAGE_PIN F20 [get_ports {c0_ddr4_dq[29]}]
set_property PACKAGE_PIN F10 [get_ports {c0_ddr4_dq[2]}]
set_property PACKAGE_PIN E17 [get_ports {c0_ddr4_dq[30]}]
set_property PACKAGE_PIN D16 [get_ports {c0_ddr4_dq[31]}]
set_property PACKAGE_PIN D17 [get_ports {c0_ddr4_dq[32]}]
set_property PACKAGE_PIN C17 [get_ports {c0_ddr4_dq[33]}]
set_property PACKAGE_PIN C19 [get_ports {c0_ddr4_dq[34]}]
set_property PACKAGE_PIN C18 [get_ports {c0_ddr4_dq[35]}]
set_property PACKAGE_PIN D20 [get_ports {c0_ddr4_dq[36]}]
set_property PACKAGE_PIN D19 [get_ports {c0_ddr4_dq[37]}]
set_property PACKAGE_PIN C20 [get_ports {c0_ddr4_dq[38]}]
set_property PACKAGE_PIN B20 [get_ports {c0_ddr4_dq[39]}]
set_property PACKAGE_PIN F9 [get_ports {c0_ddr4_dq[3]}]
set_property PACKAGE_PIN N23 [get_ports {c0_ddr4_dq[40]}]
set_property PACKAGE_PIN M23 [get_ports {c0_ddr4_dq[41]}]
set_property PACKAGE_PIN R21 [get_ports {c0_ddr4_dq[42]}]
set_property PACKAGE_PIN P21 [get_ports {c0_ddr4_dq[43]}]
set_property PACKAGE_PIN R22 [get_ports {c0_ddr4_dq[44]}]
set_property PACKAGE_PIN P22 [get_ports {c0_ddr4_dq[45]}]
set_property PACKAGE_PIN T23 [get_ports {c0_ddr4_dq[46]}]
set_property PACKAGE_PIN R23 [get_ports {c0_ddr4_dq[47]}]
set_property PACKAGE_PIN K24 [get_ports {c0_ddr4_dq[48]}]
set_property PACKAGE_PIN J24 [get_ports {c0_ddr4_dq[49]}]
set_property PACKAGE_PIN H12 [get_ports {c0_ddr4_dq[4]}]
set_property PACKAGE_PIN M21 [get_ports {c0_ddr4_dq[50]}]
set_property PACKAGE_PIN L21 [get_ports {c0_ddr4_dq[51]}]
set_property PACKAGE_PIN K21 [get_ports {c0_ddr4_dq[52]}]
set_property PACKAGE_PIN J21 [get_ports {c0_ddr4_dq[53]}]
set_property PACKAGE_PIN K22 [get_ports {c0_ddr4_dq[54]}]
set_property PACKAGE_PIN J22 [get_ports {c0_ddr4_dq[55]}]
set_property PACKAGE_PIN H23 [get_ports {c0_ddr4_dq[56]}]
set_property PACKAGE_PIN H22 [get_ports {c0_ddr4_dq[57]}]
set_property PACKAGE_PIN E23 [get_ports {c0_ddr4_dq[58]}]
set_property PACKAGE_PIN E22 [get_ports {c0_ddr4_dq[59]}]
set_property PACKAGE_PIN G12 [get_ports {c0_ddr4_dq[5]}]
set_property PACKAGE_PIN F21 [get_ports {c0_ddr4_dq[60]}]
set_property PACKAGE_PIN E21 [get_ports {c0_ddr4_dq[61]}]
set_property PACKAGE_PIN F24 [get_ports {c0_ddr4_dq[62]}]
set_property PACKAGE_PIN F23 [get_ports {c0_ddr4_dq[63]}]
set_property PACKAGE_PIN E9 [get_ports {c0_ddr4_dq[6]}]
set_property PACKAGE_PIN D9 [get_ports {c0_ddr4_dq[7]}]
set_property PACKAGE_PIN R19 [get_ports {c0_ddr4_dq[8]}]
set_property PACKAGE_PIN P19 [get_ports {c0_ddr4_dq[9]}]
set_property PACKAGE_PIN D11 [get_ports {c0_ddr4_dqs_t[0]}]
set_property PACKAGE_PIN D10 [get_ports {c0_ddr4_dqs_c[0]}]
set_property PACKAGE_PIN P17 [get_ports {c0_ddr4_dqs_t[1]}]
set_property PACKAGE_PIN P16 [get_ports {c0_ddr4_dqs_c[1]}]
set_property PACKAGE_PIN K19 [get_ports {c0_ddr4_dqs_t[2]}]
set_property PACKAGE_PIN J19 [get_ports {c0_ddr4_dqs_c[2]}]
set_property PACKAGE_PIN F16 [get_ports {c0_ddr4_dqs_t[3]}]
set_property PACKAGE_PIN E16 [get_ports {c0_ddr4_dqs_c[3]}]
set_property PACKAGE_PIN A19 [get_ports {c0_ddr4_dqs_t[4]}]
set_property PACKAGE_PIN A18 [get_ports {c0_ddr4_dqs_c[4]}]
set_property PACKAGE_PIN N22 [get_ports {c0_ddr4_dqs_t[5]}]
set_property PACKAGE_PIN M22 [get_ports {c0_ddr4_dqs_c[5]}]
set_property PACKAGE_PIN M20 [get_ports {c0_ddr4_dqs_t[6]}]
set_property PACKAGE_PIN L20 [get_ports {c0_ddr4_dqs_c[6]}]
set_property PACKAGE_PIN H24 [get_ports {c0_ddr4_dqs_t[7]}]
set_property PACKAGE_PIN G23 [get_ports {c0_ddr4_dqs_c[7]}]
set_property PACKAGE_PIN C8 [get_ports {c0_ddr4_odt[0]}]
set_property PACKAGE_PIN N20 [get_ports c0_ddr4_reset_n]
set_property PACKAGE_PIN G11 [get_ports {c0_ddr4_dm_dbi_n[0]}]
set_property PACKAGE_PIN R18 [get_ports {c0_ddr4_dm_dbi_n[1]}]
set_property PACKAGE_PIN K17 [get_ports {c0_ddr4_dm_dbi_n[2]}]
set_property PACKAGE_PIN G18 [get_ports {c0_ddr4_dm_dbi_n[3]}]
set_property PACKAGE_PIN B18 [get_ports {c0_ddr4_dm_dbi_n[4]}]
set_property PACKAGE_PIN P20 [get_ports {c0_ddr4_dm_dbi_n[5]}]
set_property PACKAGE_PIN L23 [get_ports {c0_ddr4_dm_dbi_n[6]}]
set_property PACKAGE_PIN G22 [get_ports {c0_ddr4_dm_dbi_n[7]}]
set_max_delay -datapath_only -from [get_pins wrapper_i/ddr4_0/inst/u_ddr4_mem_intfc/u_ddr_cal_top/calDone_gated_reg/C] -to [get_pins wrapper_i/proc_sys_reset_0/U0/EXT_LPF/lpf_int_reg/D] 10.000
set_output_delay -clock [get_clocks mmcm_clkout1] -min -add_delay 0.000 [get_ports c0_ddr4_reset_n]
set_output_delay -clock [get_clocks mmcm_clkout1] -max -add_delay 20.000 [get_ports c0_ddr4_reset_n]
set_max_delay -from [get_pins {xlnx_ddr4_c0/inst/u_ddr4_mem_intfc/u_ddr_cal_top/cal_RESET_n_reg[0]/C}] -to [get_ports c0_ddr4_reset_n] 50.000

326
fpga/constraints/debug.xdc Normal file

File diff suppressed because one or more lines are too long

15
fpga/generator/Makefile Normal file
View file

@ -0,0 +1,15 @@
dst := IP
all: $(dst)/xlnx_proc_sys_reset.log \
$(dst)/xlnx_ddr4.log \
$(dst)/xlnx_axi_clock_converter.log \
$(dst)/xlnx_ahblite_axi_bridge.log
$(dst)/%.log: %.tcl
mkdir -p IP
cd IP;\
vivado -mode batch -source ../$*.tcl | tee $*.log
clean:
rm -rf IP vivado.jou vivado.log

107
fpga/generator/wally.tcl Normal file
View file

@ -0,0 +1,107 @@
# start by reading in all the IP blocks generated by vivado
set partNumber xcvu9p-flga2104-2L-e
set boardName xilinx.com:vcu118:part0:2.4
set ipName WallyFPGA
create_project $ipName . -force -part $partNumber
set_property board_part $boardName [current_project]
read_ip IP/xlnx_proc_sys_reset.srcs/sources_1/ip/xlnx_proc_sys_reset/xlnx_proc_sys_reset.xci
read_ip IP/xlnx_ahblite_axi_bridge.srcs/sources_1/ip/xlnx_ahblite_axi_bridge/xlnx_ahblite_axi_bridge.xci
read_ip IP/xlnx_axi_clock_converter.srcs/sources_1/ip/xlnx_axi_clock_converter/xlnx_axi_clock_converter.xci
read_ip IP/xlnx_ddr4.srcs/sources_1/ip/xlnx_ddr4/xlnx_ddr4.xci
read_verilog -sv [glob -type f ../../wally-pipelined/src/*/*.sv ../../wally-pipelined/src/*/*/*.sv]
read_verilog {../src/fpgaTop.v}
set_property include_dirs {../../wally-pipelined/config/fpga ../../wally-pipelined/config/shared} [current_fileset]
# contrainsts generated by the IP blocks
add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_0/bd_1ba7_microblaze_I_0.xdc
add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_1/bd_1ba7_rst_0_0.xdc
add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_2/bd_1ba7_ilmb_0.xdc
add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_3/bd_1ba7_dlmb_0.xdc
add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/par/xlnx_ddr4.xdc
add_files -fileset constrs_1 -norecurse IP/xlnx_axi_clock_converter.gen/sources_1/ip/xlnx_axi_clock_converter/xlnx_axi_clock_converter_clocks.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/ip_1/par/xlnx_ddr4_phy_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_10/bd_1ba7_iomodule_0_0_board.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_1/bd_1ba7_rst_0_0_board.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_0/bd_1ba7_microblaze_I_0_ooc_debug.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_9/bd_1ba7_second_lmb_bram_I_0_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/ip/ip_6/bd_1ba7_lmb_bram_I_0_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/bd_0/bd_1ba7_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/ip_0/xlnx_ddr4_microblaze_mcs_board.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/ip_0/xlnx_ddr4_microblaze_mcs_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.gen/sources_1/ip/xlnx_ddr4/xlnx_ddr4_board.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_axi_clock_converter.gen/sources_1/ip/xlnx_axi_clock_converter/xlnx_axi_clock_converter_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ahblite_axi_bridge.runs/xlnx_ahblite_axi_bridge_synth_1/dont_touch.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ahblite_axi_bridge.gen/sources_1/ip/xlnx_ahblite_axi_bridge/xlnx_ahblite_axi_bridge_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_proc_sys_reset.runs/xlnx_proc_sys_reset_synth_1/dont_touch.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_proc_sys_reset.gen/sources_1/ip/xlnx_proc_sys_reset/xlnx_proc_sys_reset_ooc.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_proc_sys_reset.gen/sources_1/ip/xlnx_proc_sys_reset/xlnx_proc_sys_reset.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_proc_sys_reset.gen/sources_1/ip/xlnx_proc_sys_reset/xlnx_proc_sys_reset_board.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_axi_clock_converter.runs/xlnx_axi_clock_converter_synth_1/.Xil/xlnx_axi_clock_converter_propImpl.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_axi_clock_converter.runs/xlnx_axi_clock_converter_synth_1/dont_touch.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.runs/xlnx_ddr4_synth_1/.Xil/xlnx_ddr4_propImpl.xdc
#add_files -fileset constrs_1 -norecurse IP/xlnx_ddr4.runs/xlnx_ddr4_synth_1/dont_touch.xdc
# constraints for wally top level
add_files -fileset constrs_1 -norecurse ../constraints/constraints.xdc
# define top level
set_property top fpgaTop [current_fileset]
update_compile_order -fileset sources_1
# this is elaboration not synthesis.
synth_design -rtl -name rtl_1
# this does synthesis? wtf?
launch_runs synth_1 -jobs 4
wait_on_run synth_1
open_run synth_1
exec mkdir -p reports/
exec rm -rf reports/*
check_timing -verbose -file reports/check_timing.rpt
report_timing -max_paths 10 -nworst 10 -delay_type max -sort_by slack -file reports/timing_WORST_10.rpt
report_timing -nworst 1 -delay_type max -sort_by group -file reports/timing.rpt
report_utilization -hierarchical -file reports/utilization.rpt
report_cdc -file reports/cdc.rpt
report_clock_interaction -file reports/clock_interaction.rpt
# set for RuntimeOptimized implementation
#set_property "steps.place_design.args.directive" "RuntimeOptimized" [get_runs impl_1]
#set_property "steps.route_design.args.directive" "RuntimeOptimized" [get_runs impl_1]
launch_runs impl_1
wait_on_run impl_1
launch_runs impl_1 -to_step write_bitstream
wait_on_run impl_1
open_run impl_1
# output Verilog netlist + SDC for timing simulation
exec mkdir -p sim/
exec rm -rf sim/*
write_verilog -force -mode funcsim sim/funcsim.v
write_verilog -force -mode timesim sim/timesim.v
write_sdf -force sim/timesim.sdf
# reports
check_timing -file reports/imp_check_timing.rpt
report_timing -max_paths 10 -nworst 10 -delay_type max -sort_by slack -file reports/imp_timing_WORST_10.rpt
report_timing -nworst 1 -delay_type max -sort_by group -file reports/imp_timing.rpt
report_utilization -hierarchical -file reports/imp_utilization.rpt

View file

@ -0,0 +1,20 @@
#set partNumber $::env(XILINX_PART)
#set boardNmae $::env(XILINX_BOARD)
set partNumber xcvu9p-flga2104-2L-e
set boardName xilinx.com:vcu118:part0:2.4
set ipName xlnx_ahblite_axi_bridge
create_project $ipName . -force -part $partNumber
set_property board_part $boardName [current_project]
# really just these two lines which change
create_ip -name ahblite_axi_bridge -vendor xilinx.com -library ip -module_name $ipName
set_property -dict [list CONFIG.C_M_AXI_DATA_WIDTH {64} CONFIG.C_S_AHB_DATA_WIDTH {64} CONFIG.C_M_AXI_THREAD_ID_WIDTH {4}] [get_ips $ipName]
generate_target {instantiation_template} [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
generate_target all [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
create_ip_run [get_files -of_objects [get_fileset sources_1] ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
launch_run -jobs 8 ${ipName}_synth_1
wait_on_run ${ipName}_synth_1

View file

@ -0,0 +1,20 @@
#set partNumber $::env(XILINX_PART)
#set boardNmae $::env(XILINX_BOARD)
set partNumber xcvu9p-flga2104-2L-e
set boardName xilinx.com:vcu118:part0:2.4
set ipName xlnx_axi_clock_converter
create_project $ipName . -force -part $partNumber
set_property board_part $boardName [current_project]
create_ip -name axi_clock_converter -vendor xilinx.com -library ip -module_name $ipName
set_property -dict [list CONFIG.ACLK_ASYNC {1} CONFIG.PROTOCOL {AXI4} CONFIG.ADDR_WIDTH {32} CONFIG.DATA_WIDTH {64} CONFIG.ID_WIDTH {4}] [get_ips $ipName]
generate_target {instantiation_template} [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
generate_target all [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
create_ip_run [get_files -of_objects [get_fileset sources_1] ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
launch_run -jobs 8 ${ipName}_synth_1
wait_on_run ${ipName}_synth_1

View file

@ -0,0 +1,165 @@
#set partNumber $::env(XILINX_PART)
#set boardNmae $::env(XILINX_BOARD)
set partNumber xcvu9p-flga2104-2L-e
set boardName xilinx.com:vcu118:part0:2.4
set ipName xlnx_ddr4
create_project $ipName . -force -part $partNumber
set_property board_part $boardName [current_project]
# really just these two lines which change
create_ip -name ddr4 -vendor xilinx.com -library ip -module_name $ipName
set_property -dict [list CONFIG.C0.ControllerType {DDR4_SDRAM} \
CONFIG.No_Controller {1} \
CONFIG.Phy_Only {Complete_Memory_Controller} \
CONFIG.C0.DDR4_PhyClockRatio {4:1} \
CONFIG.C0.DDR4_TimePeriod {1200} \
CONFIG.C0.DDR4_MemoryPart {MT40A256M16GE-083E} \
CONFIG.C0.DDR4_BurstLength {8} \
CONFIG.C0.DDR4_BurstType {Sequential} \
CONFIG.C0.DDR4_CasLatency {13} \
CONFIG.C0.DDR4_CasWriteLatency {10} \
CONFIG.C0.DDR4_Slot {Single} \
CONFIG.C0.DDR4_MemoryVoltage {1.2V} \
CONFIG.C0.DDR4_DataWidth {64} \
CONFIG.C0.DDR4_DataMask {DM_NO_DBI} \
CONFIG.C0.DDR4_Mem_Add_Map {ROW_COLUMN_BANK} \
CONFIG.C0.DDR4_Ordering {Normal} \
CONFIG.C0.DDR4_Ecc {false} \
CONFIG.C0.DDR4_AUTO_AP_COL_A3 {false} \
CONFIG.C0.DDR4_AutoPrecharge {false} \
CONFIG.C0.DDR4_UserRefresh_ZQCS {false} \
CONFIG.C0.DDR4_AxiDataWidth {64} \
CONFIG.C0.DDR4_AxiArbitrationScheme {RD_PRI_REG} \
CONFIG.C0.DDR4_AxiIDWidth {4} \
CONFIG.C0.DDR4_AxiAddressWidth {31} \
CONFIG.C0.DDR4_AxiNarrowBurst {false} \
CONFIG.C0.DDR4_CLKFBOUT_MULT {5} \
CONFIG.C0.DDR4_DIVCLK_DIVIDE {1} \
CONFIG.C0.DDR4_CLKOUT0_DIVIDE {6} \
CONFIG.Reference_Clock {Differential} \
CONFIG.ADDN_UI_CLKOUT1.INSERT_VIP {0} \
CONFIG.ADDN_UI_CLKOUT1_FREQ_HZ {10} \
CONFIG.ADDN_UI_CLKOUT2.INSERT_VIP {0} \
CONFIG.ADDN_UI_CLKOUT2_FREQ_HZ {208} \
CONFIG.ADDN_UI_CLKOUT3.INSERT_VIP {0} \
CONFIG.ADDN_UI_CLKOUT3_FREQ_HZ {None} \
CONFIG.ADDN_UI_CLKOUT4.INSERT_VIP {0} \
CONFIG.ADDN_UI_CLKOUT4_FREQ_HZ {None} \
CONFIG.Debug_Signal {Disable} \
CONFIG.MCS_DBG_EN {false} \
CONFIG.C0.DDR4_MCS_ECC {false} \
CONFIG.Simulation_Mode {BFM} \
CONFIG.Example_TG {SIMPLE_TG} \
CONFIG.C0.DDR4_SELF_REFRESH {false} \
CONFIG.RECONFIG_XSDB_SAVE_RESTORE {false} \
CONFIG.C0.DDR4_SAVE_RESTORE {false} \
CONFIG.C0.DDR4_RESTORE_CRC {false} \
CONFIG.C0.MIGRATION {false} \
CONFIG.AL_SEL {0} \
CONFIG.C0.ADDR_WIDTH {17} \
CONFIG.C0.BANK_GROUP_WIDTH {1} \
CONFIG.C0.CKE_WIDTH {1} \
CONFIG.C0.CK_WIDTH {1} \
CONFIG.C0.CS_WIDTH {1} \
CONFIG.C0.DDR4_ACT_SKEW {0} \
CONFIG.C0.DDR4_ADDR_SKEW_0 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_1 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_2 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_3 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_4 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_5 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_6 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_7 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_8 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_9 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_10 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_11 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_12 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_13 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_14 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_15 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_16 {0} \
CONFIG.C0.DDR4_ADDR_SKEW_17 {0} \
CONFIG.C0.DDR4_AxiSelection {true} \
CONFIG.C0.DDR4_BA_SKEW_0 {0} \
CONFIG.C0.DDR4_BA_SKEW_1 {0} \
CONFIG.C0.DDR4_BG_SKEW_0 {0} \
CONFIG.C0.DDR4_BG_SKEW_1 {0} \
CONFIG.C0.DDR4_CKE_SKEW_0 {0} \
CONFIG.C0.DDR4_CKE_SKEW_1 {0} \
CONFIG.C0.DDR4_CKE_SKEW_2 {0} \
CONFIG.C0.DDR4_CKE_SKEW_3 {0} \
CONFIG.C0.DDR4_CK_SKEW_0 {0} \
CONFIG.C0.DDR4_CK_SKEW_1 {0} \
CONFIG.C0.DDR4_CK_SKEW_2 {0} \
CONFIG.C0.DDR4_CK_SKEW_3 {0} \
CONFIG.C0.DDR4_CS_SKEW_0 {0} \
CONFIG.C0.DDR4_CS_SKEW_1 {0} \
CONFIG.C0.DDR4_CS_SKEW_2 {0} \
CONFIG.C0.DDR4_CS_SKEW_3 {0} \
CONFIG.C0.DDR4_Capacity {512} \
CONFIG.C0.DDR4_ChipSelect {true} \
CONFIG.C0.DDR4_Clamshell {false} \
CONFIG.C0.DDR4_CustomParts {no_file_loaded} \
CONFIG.C0.DDR4_EN_PARITY {false} \
CONFIG.C0.DDR4_Enable_LVAUX {false} \
CONFIG.C0.DDR4_InputClockPeriod {4000} \
CONFIG.C0.DDR4_LR_SKEW_0 {0} \
CONFIG.C0.DDR4_LR_SKEW_1 {0} \
CONFIG.C0.DDR4_MemoryName {MainMemory} \
CONFIG.C0.DDR4_ODT_SKEW_0 {0} \
CONFIG.C0.DDR4_ODT_SKEW_1 {0} \
CONFIG.C0.DDR4_ODT_SKEW_2 {0} \
CONFIG.C0.DDR4_ODT_SKEW_3 {0} \
CONFIG.C0.DDR4_OnDieTermination {RZQ/6} \
CONFIG.C0.DDR4_OutputDriverImpedenceControl {RZQ/7} \
CONFIG.C0.DDR4_PAR_SKEW {0} \
CONFIG.C0.DDR4_Specify_MandD {false} \
CONFIG.C0.DDR4_TREFI {0} \
CONFIG.C0.DDR4_TRFC {0} \
CONFIG.C0.DDR4_TRFC_DLR {0} \
CONFIG.C0.DDR4_TXPR {0} \
CONFIG.C0.DDR4_isCKEShared {false} \
CONFIG.C0.DDR4_isCustom {false} \
CONFIG.C0.DDR4_nCK_TREFI {0} \
CONFIG.C0.DDR4_nCK_TRFC {0} \
CONFIG.C0.DDR4_nCK_TRFC_DLR {0} \
CONFIG.C0.DDR4_nCK_TXPR {5} \
CONFIG.C0.LR_WIDTH {1} \
CONFIG.C0.ODT_WIDTH {1} \
CONFIG.C0.StackHeight {1} \
CONFIG.C0_CLOCK_BOARD_INTERFACE {default_250mhz_clk1} \
CONFIG.C0_DDR4_ARESETN.INSERT_VIP {0} \
CONFIG.C0_DDR4_BOARD_INTERFACE {Custom} \
CONFIG.C0_DDR4_CLOCK.INSERT_VIP {0} \
CONFIG.C0_DDR4_RESET.INSERT_VIP {0} \
CONFIG.C0_DDR4_S_AXI.INSERT_VIP {0} \
CONFIG.C0_SYS_CLK_I.INSERT_VIP {0} \
CONFIG.CLKOUT6 {0} \
CONFIG.DCI_Cascade {false} \
CONFIG.DIFF_TERM_SYSCLK {false} \
CONFIG.Default_Bank_Selections {false} \
CONFIG.EN_PP_4R_MIR {false} \
CONFIG.Enable_SysPorts {true} \
CONFIG.IOPowerReduction {OFF} \
CONFIG.IO_Power_Reduction {false} \
CONFIG.IS_FROM_PHY {1} \
CONFIG.PARTIAL_RECONFIG_FLOW_MIG {false} \
CONFIG.PING_PONG_PHY {1} \
CONFIG.RESET_BOARD_INTERFACE {reset} \
CONFIG.SET_DW_TO_40 {false} \
CONFIG.SYSTEM_RESET.INSERT_VIP {0} \
CONFIG.System_Clock {Differential} \
CONFIG.TIMING_3DS {false} \
CONFIG.TIMING_OP1 {false} \
CONFIG.TIMING_OP2 {false} \
] [get_ips $ipName]
generate_target {instantiation_template} [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
generate_target all [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
create_ip_run [get_files -of_objects [get_fileset sources_1] ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
launch_run -jobs 8 ${ipName}_synth_1
wait_on_run ${ipName}_synth_1

View file

@ -0,0 +1,24 @@
#set partNumber $::env(XILINX_PART)
#set boardNmae $::env(XILINX_BOARD)
set partNumber xcvu9p-flga2104-2L-e
set boardName xilinx.com:vcu118:part0:2.4
set ipName xlnx_proc_sys_reset
create_project $ipName . -force -part $partNumber
set_property board_part $boardName [current_project]
# really just these two lines which change
create_ip -name proc_sys_reset -vendor xilinx.com -library ip -module_name $ipName
set_property -dict [list CONFIG.C_AUX_RESET_HIGH {1} \
CONFIG.C_AUX_RST_WIDTH {1} \
CONFIG.C_EXT_RESET_HIGH {1} \
CONFIG.C_EXT_RST_WIDTH {1} \
CONFIG.C_NUM_BUS_RST {1}] [get_ips $ipName]
generate_target {instantiation_template} [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
generate_target all [get_files ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
create_ip_run [get_files -of_objects [get_fileset sources_1] ./$ipName.srcs/sources_1/ip/$ipName/$ipName.xci]
launch_run -jobs 8 ${ipName}_synth_1
wait_on_run ${ipName}_synth_1

11
fpga/sim/bufgce.sv Normal file
View file

@ -0,0 +1,11 @@
module BUFGCE (input logic I, input logic CE, output logic O);
logic CE_Q;
always_latch begin
if(~I) begin
CE_Q <= CE;
end
end
assign O = CE_Q & I;
endmodule

32
fpga/sim/bufgce_div.sv Normal file
View file

@ -0,0 +1,32 @@
module BUFGCE_DIV #(parameter string DivideAmt = "1")
(input logic I, input logic CLR, input logic CE, output logic O);
integer PulseCount = 0;
logic Q;
always_ff @(posedge I, posedge CLR) begin
if(CLR) PulseCount <= 0;
else begin
if(PulseCount < (DivideAmt.atoi()/2 - 1))
PulseCount <= PulseCount + 1;
else
PulseCount <= 0;
end
end
assign zero = PulseCount == 0;
flopenr #(1) ToggleFlipFLop
(.d(~Q),
.q(Q),
.clk(I),
.reset(CLR), // reset when told by outside
.en(zero)); // only update when counter overflows
if (DivideAmt != "1")
assign O = Q;
else
assign O = I;
endmodule

4
fpga/sim/bufgmux.sv Normal file
View file

@ -0,0 +1,4 @@
module BUFGMUX(input logic I1, input logic I0, input logic S, output logic O);
assign O = S ? I1 : I0;
endmodule

458
fpga/src/fpgaTop.v Normal file
View file

@ -0,0 +1,458 @@
///////////////////////////////////////////
// fpgaTop.sv
//
// Written: ross1728@gmail.com November 17, 2021
// Modified:
//
// Purpose: This is a top level for the fpga's implementation of wally.
// Instantiates wallysoc, ddr4, abh lite to axi converters, pll, etc
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module fpgaTop
(input default_250mhz_clk1_0_n,
input default_250mhz_clk1_0_p,
input reset,
input south_rst,
input [3:0] GPI,
output [4:0] GPO,
input UARTSin,
output UARTSout,
input [3:0] SDCDat,
output SDCCLK,
inout SDCCmd,
output calib,
output cpu_reset,
output ddr4_sdram_c1_062,
output ahblite_resetn,
output [16 : 0] c0_ddr4_adr,
output [1 : 0] c0_ddr4_ba,
output [0 : 0] c0_ddr4_cke,
output [0 : 0] c0_ddr4_cs_n,
inout [7 : 0] c0_ddr4_dm_dbi_n,
inout [63 : 0] c0_ddr4_dq,
inout [7 : 0] c0_ddr4_dqs_c,
inout [7 : 0] c0_ddr4_dqs_t,
output [0 : 0] c0_ddr4_odt,
output [0 : 0] c0_ddr4_bg,
output c0_ddr4_reset_n,
output c0_ddr4_act_n,
output [0 : 0] c0_ddr4_ck_c,
output [0 : 0] c0_ddr4_ck_t
);
wire CPUCLK;
wire c0_ddr4_ui_clk_sync_rst;
wire bus_struct_reset;
wire peripheral_reset;
wire interconnect_aresetn;
wire peripheral_aresetn;
wire mb_reset;
wire [`AHBW-1:0] HRDATAEXT;
wire HREADYEXT;
wire HRESPEXT;
wire HSELEXT;
wire HCLKOpen;
wire HRESETnOpen;
wire [31:0] HADDR;
wire [`AHBW-1:0] HWDATA;
wire HWRITE;
wire [2:0] HSIZE;
wire [2:0] HBURST;
wire [3:0] HPROT;
wire [1:0] HTRANS;
wire HMASTLOCK;
wire HREADY;
wire [31:0] GPIOPinsIn, GPIOPinsOut, GPIOPinsEn;
wire SDCCmdIn;
wire SDCCmdOE;
wire SDCCmdOut;
wire [3:0] m_axi_awid;
wire [7:0] m_axi_awlen;
wire [2:0] m_axi_awsize;
wire [1:0] m_axi_awburst;
wire [3:0] m_axi_awcache;
wire [31:0] m_axi_awaddr;
wire [2:0] m_axi_awprot;
wire m_axi_awvalid;
wire m_axi_awready;
wire m_axi_awlock;
wire [63:0] m_axi_wdata;
wire [7:0] m_axi_wstrb;
wire m_axi_wlast;
wire m_axi_wvalid;
wire m_axi_wready;
wire [3:0] m_axi_bid;
wire [1:0] m_axi_bresp;
wire m_axi_bvalid;
wire m_axi_bready;
wire [3:0] m_axi_arid;
wire [7:0] m_axi_arlen;
wire [2:0] m_axi_arsize;
wire [1:0] m_axi_arburst;
wire [2:0] m_axi_arprot;
wire [3:0] m_axi_arcache;
wire m_axi_arvalid;
wire [31:0] m_axi_araddr;
wire m_axi_arlock;
wire m_axi_arready;
wire [3:0] m_axi_rid;
wire [63:0] m_axi_rdata;
wire [1:0] m_axi_rresp;
wire m_axi_rvalid;
wire m_axi_rlast;
wire m_axi_rready;
wire [3:0] BUS_axi_arregion;
wire [3:0] BUS_axi_arqos;
wire [3:0] BUS_axi_awregion;
wire [3:0] BUS_axi_awqos;
wire [3:0] BUS_axi_awid;
wire [7:0] BUS_axi_awlen;
wire [2:0] BUS_axi_awsize;
wire [1:0] BUS_axi_awburst;
wire [3:0] BUS_axi_awcache;
wire [30:0] BUS_axi_awaddr;
wire [2:0] BUS_axi_awprot;
wire BUS_axi_awvalid;
wire BUS_axi_awready;
wire BUS_axi_awlock;
wire [63:0] BUS_axi_wdata;
wire [7:0] BUS_axi_wstrb;
wire BUS_axi_wlast;
wire BUS_axi_wvalid;
wire BUS_axi_wready;
wire [3:0] BUS_axi_bid;
wire [1:0] BUS_axi_bresp;
wire BUS_axi_bvalid;
wire BUS_axi_bready;
wire [3:0] BUS_axi_arid;
wire [7:0] BUS_axi_arlen;
wire [2:0] BUS_axi_arsize;
wire [1:0] BUS_axi_arburst;
wire [2:0] BUS_axi_arprot;
wire [3:0] BUS_axi_arcache;
wire BUS_axi_arvalid;
wire [30:0] BUS_axi_araddr;
wire BUS_axi_arlock;
wire BUS_axi_arready;
wire [3:0] BUS_axi_rid;
wire [63:0] BUS_axi_rdata;
wire [1:0] BUS_axi_rresp;
wire BUS_axi_rvalid;
wire BUS_axi_rlast;
wire BUS_axi_rready;
wire BUSCLK;
wire c0_init_calib_complete;
wire dbg_clk;
wire [511 : 0] dbg_bus;
wire CLK208;
assign GPIOPinsIn = {28'b0, GPI};
assign GPO = GPIOPinsOut[4:0];
assign ahblite_resetn = peripheral_aresetn;
assign cpu_reset = bus_struct_reset;
assign calib = c0_init_calib_complete;
// SD Card Tristate
IOBUF iobufSDCMD(.T(~SDCCmdOE), // iobuf's T is active low
.I(SDCCmdIn),
.O(SDCCmdOut),
.IO(SDCCmd));
// reset controller XILINX IP
xlnx_proc_sys_reset xlnx_proc_sys_reset_0
(.slowest_sync_clk(CPUCLK),
.ext_reset_in(c0_ddr4_ui_clk_sync_rst),
.aux_reset_in(south_rst),
.mb_debug_sys_rst(1'b0),
.dcm_locked(c0_init_calib_complete),
.mb_reset(mb_reset), //open
.bus_struct_reset(bus_struct_reset),
.peripheral_reset(peripheral_reset), //open
.interconnect_aresetn(interconnect_aresetn), //open
.peripheral_aresetn(peripheral_aresetn));
// wally
wallypipelinedsoc wallypipelinedsoc
(.clk(CPUCLK),
.reset_ext(bus_struct_reset),
// bus interface
.HRDATAEXT(HRDATAEXT),
.HREADYEXT(HREADYEXT),
.HRESPEXT(HRESPEXT),
.HSELEXT(HSELEXT),
.HCLK(HCLKOpen), // open
.HRESETn(HRESETnOpen), // open
.HADDR(HADDR),
.HWDATA(HWDATA),
.HWRITE(HWRITE),
.HSIZE(HSIZE),
.HBURST(HBURST),
.HPROT(HPROT),
.HTRANS(HTRANS),
.HMASTLOCK(HMASTLOCK),
.HREADY(HREADY),
// GPIO
.GPIOPinsIn(GPIOPinsIn),
.GPIOPinsOut(GPIOPinsOut),
.GPIOPinsEn(GPIOPinsEn),
// UART
.UARTSin(UARTSin),
.UARTSout(UARTSout),
// SD Card
.SDCDatIn(SDCDat),
.SDCCmdIn(SDCCmdIn),
.SDCCmdOut(SDCCmdOut),
.SDCCmdOE(SDCCmdOE),
.SDCCLK(SDCCLK));
// ahb lite to axi bridge
xlnx_ahblite_axi_bridge xlnx_ahblite_axi_bridge_0
(.s_ahb_hclk(CPUCLK),
.s_ahb_hresetn(peripheral_aresetn),
.s_ahb_hsel(HSELEXT),
.s_ahb_haddr(HADDR),
.s_ahb_hprot(HPROT),
.s_ahb_htrans(HTRANS),
.s_ahb_hsize(HSIZE),
.s_ahb_hwrite(HWRITE),
.s_ahb_hburst(HBURST),
.s_ahb_hwdata(HWDATA),
.s_ahb_hready_out(HREADYEXT),
.s_ahb_hready_in(HREADY),
.s_ahb_hrdata(HRDATAEXT),
.s_ahb_hresp(HRESPEXT),
.m_axi_awid(m_axi_awid),
.m_axi_awlen(m_axi_awlen),
.m_axi_awsize(m_axi_awsize),
.m_axi_awburst(m_axi_awburst),
.m_axi_awcache(m_axi_awcache),
.m_axi_awaddr(m_axi_awaddr),
.m_axi_awprot(m_axi_awprot),
.m_axi_awvalid(m_axi_awvalid),
.m_axi_awready(m_axi_awready),
.m_axi_awlock(m_axi_awlock),
.m_axi_wdata(m_axi_wdata),
.m_axi_wstrb(m_axi_wstrb),
.m_axi_wlast(m_axi_wlast),
.m_axi_wvalid(m_axi_wvalid),
.m_axi_wready(m_axi_wready),
.m_axi_bid(m_axi_bid),
.m_axi_bresp(m_axi_bresp),
.m_axi_bvalid(m_axi_bvalid),
.m_axi_bready(m_axi_bready),
.m_axi_arid(m_axi_arid),
.m_axi_arlen(m_axi_arlen),
.m_axi_arsize(m_axi_arsize),
.m_axi_arburst(m_axi_arburst),
.m_axi_arprot(m_axi_arprot),
.m_axi_arcache(m_axi_arcache),
.m_axi_arvalid(m_axi_arvalid),
.m_axi_araddr(m_axi_araddr),
.m_axi_arlock(m_axi_arlock),
.m_axi_arready(m_axi_arready),
.m_axi_rid(m_axi_rid),
.m_axi_rdata(m_axi_rdata),
.m_axi_rresp(m_axi_rresp),
.m_axi_rvalid(m_axi_rvalid),
.m_axi_rlast(m_axi_rlast),
.m_axi_rready(m_axi_rready));
xlnx_axi_clock_converter xlnx_axi_clock_converter_0
(.s_axi_aclk(CPUCLK),
.s_axi_aresetn(peripheral_aresetn),
.s_axi_awid(m_axi_awid),
.s_axi_awlen(m_axi_awlen),
.s_axi_awsize(m_axi_awsize),
.s_axi_awburst(m_axi_awburst),
.s_axi_awcache(m_axi_awcache),
.s_axi_awaddr(m_axi_awaddr[30:0]),
.s_axi_awprot(m_axi_awprot),
.s_axi_awregion(4'b0), // this could be a bug. bridge does not have these outputs
.s_axi_awqos(4'b0), // this could be a bug. bridge does not have these outputs
.s_axi_awvalid(m_axi_awvalid),
.s_axi_awready(m_axi_awready),
.s_axi_awlock(m_axi_awlock),
.s_axi_wdata(m_axi_wdata),
.s_axi_wstrb(m_axi_wstrb),
.s_axi_wlast(m_axi_wlast),
.s_axi_wvalid(m_axi_wvalid),
.s_axi_wready(m_axi_wready),
.s_axi_bid(m_axi_bid),
.s_axi_bresp(m_axi_bresp),
.s_axi_bvalid(m_axi_bvalid),
.s_axi_bready(m_axi_bready),
.s_axi_arid(m_axi_arid),
.s_axi_arlen(m_axi_arlen),
.s_axi_arsize(m_axi_arsize),
.s_axi_arburst(m_axi_arburst),
.s_axi_arprot(m_axi_arprot),
.s_axi_arregion(4'b0), // this could be a bug. bridge does not have these outputs
.s_axi_arqos(4'b0), // this could be a bug. bridge does not have these outputs
.s_axi_arcache(m_axi_arcache),
.s_axi_arvalid(m_axi_arvalid),
.s_axi_araddr(m_axi_araddr[30:0]),
.s_axi_arlock(m_axi_arlock),
.s_axi_arready(m_axi_arready),
.s_axi_rid(m_axi_rid),
.s_axi_rdata(m_axi_rdata),
.s_axi_rresp(m_axi_rresp),
.s_axi_rvalid(m_axi_rvalid),
.s_axi_rlast(m_axi_rlast),
.s_axi_rready(m_axi_rready),
.m_axi_aclk(BUSCLK),
.m_axi_aresetn(~reset),
.m_axi_awid(BUS_axi_awid),
.m_axi_awlen(BUS_axi_awlen),
.m_axi_awsize(BUS_axi_awsize),
.m_axi_awburst(BUS_axi_awburst),
.m_axi_awcache(BUS_axi_awcache),
.m_axi_awaddr(BUS_axi_awaddr),
.m_axi_awprot(BUS_axi_awprot),
.m_axi_awregion(BUS_axi_awregion),
.m_axi_awqos(BUS_axi_awqos),
.m_axi_awvalid(BUS_axi_awvalid),
.m_axi_awready(BUS_axi_awready),
.m_axi_awlock(BUS_axi_awlock),
.m_axi_wdata(BUS_axi_wdata),
.m_axi_wstrb(BUS_axi_wstrb),
.m_axi_wlast(BUS_axi_wlast),
.m_axi_wvalid(BUS_axi_wvalid),
.m_axi_wready(BUS_axi_wready),
.m_axi_bid(BUS_axi_bid),
.m_axi_bresp(BUS_axi_bresp),
.m_axi_bvalid(BUS_axi_bvalid),
.m_axi_bready(BUS_axi_bready),
.m_axi_arid(BUS_axi_arid),
.m_axi_arlen(BUS_axi_arlen),
.m_axi_arsize(BUS_axi_arsize),
.m_axi_arburst(BUS_axi_arburst),
.m_axi_arprot(BUS_axi_arprot),
.m_axi_arregion(BUS_axi_arregion),
.m_axi_arqos(BUS_axi_arqos),
.m_axi_arcache(BUS_axi_arcache),
.m_axi_arvalid(BUS_axi_arvalid),
.m_axi_araddr(BUS_axi_araddr),
.m_axi_arlock(BUS_axi_arlock),
.m_axi_arready(BUS_axi_arready),
.m_axi_rid(BUS_axi_rid),
.m_axi_rdata(BUS_axi_rdata),
.m_axi_rresp(BUS_axi_rresp),
.m_axi_rvalid(BUS_axi_rvalid),
.m_axi_rlast(BUS_axi_rlast),
.m_axi_rready(BUS_axi_rready));
xlnx_ddr4 xlnx_ddr4_c0
(.c0_init_calib_complete(c0_init_calib_complete),
.dbg_clk(dbg_clk), // open
.c0_sys_clk_p(default_250mhz_clk1_0_p),
.c0_sys_clk_n(default_250mhz_clk1_0_n),
.sys_rst(reset),
.dbg_bus(dbg_bus), // open
// ddr4 I/O
.c0_ddr4_adr(c0_ddr4_adr),
.c0_ddr4_ba(c0_ddr4_ba),
.c0_ddr4_cke(c0_ddr4_cke),
.c0_ddr4_cs_n(c0_ddr4_cs_n),
.c0_ddr4_dm_dbi_n(c0_ddr4_dm_dbi_n),
.c0_ddr4_dq(c0_ddr4_dq),
.c0_ddr4_dqs_c(c0_ddr4_dqs_c),
.c0_ddr4_dqs_t(c0_ddr4_dqs_t),
.c0_ddr4_odt(c0_ddr4_odt),
.c0_ddr4_bg(c0_ddr4_bg),
.c0_ddr4_reset_n(c0_ddr4_reset_n),
.c0_ddr4_act_n(c0_ddr4_act_n),
.c0_ddr4_ck_c(c0_ddr4_ck_c),
.c0_ddr4_ck_t(c0_ddr4_ck_t),
.c0_ddr4_ui_clk(BUSCLK),
.c0_ddr4_ui_clk_sync_rst(c0_ddr4_ui_clk_sync_rst),
.c0_ddr4_aresetn(~reset),
// axi
.c0_ddr4_s_axi_awid(BUS_axi_awid),
.c0_ddr4_s_axi_awaddr(BUS_axi_awaddr[30:0]),
.c0_ddr4_s_axi_awlen(BUS_axi_awlen),
.c0_ddr4_s_axi_awsize(BUS_axi_awsize),
.c0_ddr4_s_axi_awburst(BUS_axi_awburst),
.c0_ddr4_s_axi_awlock(BUS_axi_awlock),
.c0_ddr4_s_axi_awcache(BUS_axi_awcache),
.c0_ddr4_s_axi_awprot(BUS_axi_awprot),
.c0_ddr4_s_axi_awqos(BUS_axi_awqos),
.c0_ddr4_s_axi_awvalid(BUS_axi_awvalid),
.c0_ddr4_s_axi_awready(BUS_axi_awready),
.c0_ddr4_s_axi_wdata(BUS_axi_wdata),
.c0_ddr4_s_axi_wstrb(BUS_axi_wstrb),
.c0_ddr4_s_axi_wlast(BUS_axi_wlast),
.c0_ddr4_s_axi_wvalid(BUS_axi_wvalid),
.c0_ddr4_s_axi_wready(BUS_axi_wready),
.c0_ddr4_s_axi_bready(BUS_axi_bready),
.c0_ddr4_s_axi_bid(BUS_axi_bid),
.c0_ddr4_s_axi_bresp(BUS_axi_bresp),
.c0_ddr4_s_axi_bvalid(BUS_axi_bvalid),
.c0_ddr4_s_axi_arid(BUS_axi_arid),
.c0_ddr4_s_axi_araddr(BUS_axi_araddr[30:0]),
.c0_ddr4_s_axi_arlen(BUS_axi_arlen),
.c0_ddr4_s_axi_arsize(BUS_axi_arsize),
.c0_ddr4_s_axi_arburst(BUS_axi_arburst),
.c0_ddr4_s_axi_arlock(BUS_axi_arlock),
.c0_ddr4_s_axi_arcache(BUS_axi_arcache),
.c0_ddr4_s_axi_arprot(BUS_axi_arprot),
.c0_ddr4_s_axi_arqos(BUS_axi_arqos),
.c0_ddr4_s_axi_arvalid(BUS_axi_arvalid),
.c0_ddr4_s_axi_arready(BUS_axi_arready),
.c0_ddr4_s_axi_rready(BUS_axi_rready),
.c0_ddr4_s_axi_rlast(BUS_axi_rlast),
.c0_ddr4_s_axi_rvalid(BUS_axi_rvalid),
.c0_ddr4_s_axi_rresp(BUS_axi_rresp),
.c0_ddr4_s_axi_rid(BUS_axi_rid),
.c0_ddr4_s_axi_rdata(BUS_axi_rdata),
.addn_ui_clkout1(CPUCLK),
.addn_ui_clkout2(CLK208));
endmodule

View file

@ -0,0 +1,112 @@
CEXT := c
CPPEXT := cpp
AEXT := s
SEXT := S
SRCEXT := \([$(CEXT)$(AEXT)$(SEXT)]\|$(CPPEXT)\)
OBJEXT := o
DEPEXT := d
SRCDIR := .
BUILDDIR := OBJ
SOURCES ?= $(shell find $(SRCDIR) -type f -regex ".*\.$(SRCEXT)" | sort)
OBJECTS := $(SOURCES:.$(CEXT)=.$(OBJEXT))
OBJECTS := $(OBJECTS:.$(AEXT)=.$(OBJEXT))
OBJECTS := $(OBJECTS:.$(SEXT)=.$(OBJEXT))
OBJECTS := $(OBJECTS:.$(CPPEXT)=.$(OBJEXT))
OBJECTS := $(patsubst $(SRCDIR)/%,$(BUILDDIR)/%,$(OBJECTS))
TARGETDIR := bin
TARGET := $(TARGETDIR)/blink-led
ROOT := ..
LIBRARY_DIRS :=
LIBRARY_FILES :=
MARCH :=-march=rv64imfdc
MABI :=-mabi=lp64d
LINK_FLAGS :=$(MARCH) $(MABI) -nostartfiles
LINKER :=$(ROOT)/linker1000.x
AFLAGS =$(MARCH) $(MABI) -W
CFLAGS =$(MARCH) $(MABI) -mcmodel=medany -O2
AS=riscv64-unknown-elf-as
CC=riscv64-unknown-elf-gcc
AR=riscv64-unknown-elf-ar
#Default Make
all: directories $(TARGET).memfile
#Remake
remake: clean all
#Make the Directories
directories:
@mkdir -p $(TARGETDIR)
@mkdir -p $(BUILDDIR)
clean:
rm -rf $(BUILDDIR) $(TARGETDIR) *.memfile *.objdump
#Needed for building additional library projects
ifdef LIBRARY_DIRS
LIBS+=${LIBRARY_DIRS:%=-L%} ${LIBRARY_FILES:%=-l%}
INC+=${LIBRARY_DIRS:%=-I%}
${LIBRARY_DIRS}:
make -C $@ -j 1
.PHONY: $(LIBRARY_DIRS) $(TARGET)
endif
#Pull in dependency info for *existing* .o files
-include $(OBJECTS:.$(OBJEXT)=.$(DEPEXT))
#Link
$(TARGET): $(OBJECTS) $(LIBRARY_DIRS)
$(CC) $(LINK_FLAGS) -g -o $(TARGET) $(OBJECTS) ${LIBS} -T ${LINKER}
#Compile
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(CEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) $(INC) -c -o $@ $< > $(BUILDDIR)/$*.list
@$(CC) $(CFLAGS) $(INC) -MM $(SRCDIR)/$*.$(CEXT) > $(BUILDDIR)/$*.$(DEPEXT)
@cp -f $(BUILDDIR)/$*.$(DEPEXT) $(BUILDDIR)/$*.$(DEPEXT).tmp
@sed -e 's|.*:|$(BUILDDIR)/$*.$(OBJEXT):|' < $(BUILDDIR)/$*.$(DEPEXT).tmp > $(BUILDDIR)/$*.$(DEPEXT)
@sed -e 's/.*://' -e 's/\\$$//' < $(BUILDDIR)/$*.$(DEPEXT).tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$/:/' >> $(BUILDDIR)/$*.$(DEPEXT)
@rm -f $(BUILDDIR)/$*.$(DEPEXT).tmp
# gcc won't output dependencies for assembly files for some reason
# most asm files don't have dependencies so the echo will work for now.
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(AEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) -c -o $@ $< > $(BUILDDIR)/$*.list
@echo $@: $< > $(BUILDDIR)/$*.$(DEPEXT)
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(SEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) $(INC) -c -o $@ $< > $(BUILDDIR)/$*.list
@echo $@: $< > $(BUILDDIR)/$*.$(DEPEXT)
# C++
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(CPPEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) $(INC) -c -o $@ $< > $(BUILDDIR)/$*.list
@$(CC) $(CFLAGS) $(INC) -MM $(SRCDIR)/$*.$(CPPEXT) > $(BUILDDIR)/$*.$(DEPEXT)
@cp -f $(BUILDDIR)/$*.$(DEPEXT) $(BUILDDIR)/$*.$(DEPEXT).tmp
@sed -e 's|.*:|$(BUILDDIR)/$*.$(OBJEXT):|' < $(BUILDDIR)/$*.$(DEPEXT).tmp > $(BUILDDIR)/$*.$(DEPEXT)
@sed -e 's/.*://' -e 's/\\$$//' < $(BUILDDIR)/$*.$(DEPEXT).tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$/:/' >> $(BUILDDIR)/$*.$(DEPEXT)
@rm -f $(BUILDDIR)/$*.$(DEPEXT).tmp
# convert to hex
$(TARGET).memfile: $(TARGET)
@echo 'Making object dump file.'
@riscv64-unknown-elf-objdump -D $< > $<.objdump
@echo 'Making memory file'
exe2memfile0.pl $<
extractFunctionRadix.sh $<.objdump
mkdir -p ../../imperas-riscv-tests/work/rv64BP/
cp -f $(TARGETDIR)/* ../../imperas-riscv-tests/work/rv64BP/

View file

@ -0,0 +1,130 @@
PERIOD = 22000000
#PERIOD = 100
.section .init
.global _start
.type _start, @function
_start:
# Initialize global pointer
.option push
.option norelax
1:auipc gp, %pcrel_hi(__global_pointer$)
addi gp, gp, %pcrel_lo(1b)
.option pop
li x1, 0
li x2, 0
li x4, 0
li x5, 0
li x6, 0
li x7, 0
li x8, 0
li x9, 0
li x10, 0
li x11, 0
li x12, 0
li x13, 0
li x14, 0
li x15, 0
li x16, 0
li x17, 0
li x18, 0
li x19, 0
li x20, 0
li x21, 0
li x22, 0
li x23, 0
li x24, 0
li x25, 0
li x26, 0
li x27, 0
li x28, 0
li x29, 0
li x30, 0
li x31, 0
# write to gpio
li x2, 0xFF
la x3, 0x10012000
# +8 is output enable
# +C is output value
addi x4, x3, 8
addi x5, x3, 0xC
# write initial value of 0xFF to GPO
sw x2, 0x0(x5)
# enable output
sw x2, 0x0(x4)
# before jumping to led loop
# lets try writting to dram.
li x21, 0
li x23, 4096*16 # 64KB of data
li x22, 0x80000000
li x24, 0
write_loop:
add x25, x22, x24
sw x24, 0(x25)
addi x24, x24, 4
blt x24, x23, write_loop
li x24, 0
read_loop:
add x25, x22, x24
lw x21, 0(x25)
# check value
bne x21, x24, fail_loop
addi x24, x24, 4
#
blt x24, x23, read_loop
loop:
# delay
li x20, PERIOD
delay1:
addi x20, x20, -1
bge x20, x0, delay1
# new GPO
addi x2, x2, 1
sw x2, 0x0(x5)
j loop
fail_loop:
# delay
li x20, PERIOD/20
fail_delay1:
addi x20, x20, -1
bge x20, x0, fail_delay1
# clear GPO
sw x0, 0x0(x5)
# delay
li x20, PERIOD/20
fail_delay2:
addi x20, x20, -1
bge x20, x0, fail_delay2
# write GPO
sw x2, 0x0(x5)
j fail_loop

View file

@ -0,0 +1,112 @@
CEXT := c
CPPEXT := cpp
AEXT := s
SEXT := S
SRCEXT := \([$(CEXT)$(AEXT)$(SEXT)]\|$(CPPEXT)\)
OBJEXT := o
DEPEXT := d
SRCDIR := .
BUILDDIR := OBJ
SOURCES ?= $(shell find $(SRCDIR) -type f -regex ".*\.$(SRCEXT)" | sort)
OBJECTS := $(SOURCES:.$(CEXT)=.$(OBJEXT))
OBJECTS := $(OBJECTS:.$(AEXT)=.$(OBJEXT))
OBJECTS := $(OBJECTS:.$(SEXT)=.$(OBJEXT))
OBJECTS := $(OBJECTS:.$(CPPEXT)=.$(OBJEXT))
OBJECTS := $(patsubst $(SRCDIR)/%,$(BUILDDIR)/%,$(OBJECTS))
TARGETDIR := bin
TARGET := $(TARGETDIR)/fpga-test-sdc
ROOT := ..
LIBRARY_DIRS :=
LIBRARY_FILES :=
MARCH :=-march=rv64imfdc
MABI :=-mabi=lp64d
LINK_FLAGS :=$(MARCH) $(MABI) -nostartfiles
LINKER :=$(ROOT)/linker1000.x
AFLAGS =$(MARCH) $(MABI) -W
CFLAGS =$(MARCH) $(MABI) -mcmodel=medany -O2
AS=riscv64-unknown-elf-as
CC=riscv64-unknown-elf-gcc
AR=riscv64-unknown-elf-ar
#Default Make
all: directories $(TARGET).memfile
#Remake
remake: clean all
#Make the Directories
directories:
@mkdir -p $(TARGETDIR)
@mkdir -p $(BUILDDIR)
clean:
rm -rf $(BUILDDIR) $(TARGETDIR) *.memfile *.objdump
#Needed for building additional library projects
ifdef LIBRARY_DIRS
LIBS+=${LIBRARY_DIRS:%=-L%} ${LIBRARY_FILES:%=-l%}
INC+=${LIBRARY_DIRS:%=-I%}
${LIBRARY_DIRS}:
make -C $@ -j 1
.PHONY: $(LIBRARY_DIRS) $(TARGET)
endif
#Pull in dependency info for *existing* .o files
-include $(OBJECTS:.$(OBJEXT)=.$(DEPEXT))
#Link
$(TARGET): $(OBJECTS) $(LIBRARY_DIRS)
$(CC) $(LINK_FLAGS) -g -o $(TARGET) $(OBJECTS) ${LIBS} -T ${LINKER}
#Compile
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(CEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) $(INC) -c -o $@ $< > $(BUILDDIR)/$*.list
@$(CC) $(CFLAGS) $(INC) -MM $(SRCDIR)/$*.$(CEXT) > $(BUILDDIR)/$*.$(DEPEXT)
@cp -f $(BUILDDIR)/$*.$(DEPEXT) $(BUILDDIR)/$*.$(DEPEXT).tmp
@sed -e 's|.*:|$(BUILDDIR)/$*.$(OBJEXT):|' < $(BUILDDIR)/$*.$(DEPEXT).tmp > $(BUILDDIR)/$*.$(DEPEXT)
@sed -e 's/.*://' -e 's/\\$$//' < $(BUILDDIR)/$*.$(DEPEXT).tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$/:/' >> $(BUILDDIR)/$*.$(DEPEXT)
@rm -f $(BUILDDIR)/$*.$(DEPEXT).tmp
# gcc won't output dependencies for assembly files for some reason
# most asm files don't have dependencies so the echo will work for now.
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(AEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) -c -o $@ $< > $(BUILDDIR)/$*.list
@echo $@: $< > $(BUILDDIR)/$*.$(DEPEXT)
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(SEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) $(INC) -c -o $@ $< > $(BUILDDIR)/$*.list
@echo $@: $< > $(BUILDDIR)/$*.$(DEPEXT)
# C++
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(CPPEXT)
@mkdir -p $(dir $@)
$(CC) $(CFLAGS) $(INC) -c -o $@ $< > $(BUILDDIR)/$*.list
@$(CC) $(CFLAGS) $(INC) -MM $(SRCDIR)/$*.$(CPPEXT) > $(BUILDDIR)/$*.$(DEPEXT)
@cp -f $(BUILDDIR)/$*.$(DEPEXT) $(BUILDDIR)/$*.$(DEPEXT).tmp
@sed -e 's|.*:|$(BUILDDIR)/$*.$(OBJEXT):|' < $(BUILDDIR)/$*.$(DEPEXT).tmp > $(BUILDDIR)/$*.$(DEPEXT)
@sed -e 's/.*://' -e 's/\\$$//' < $(BUILDDIR)/$*.$(DEPEXT).tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$/:/' >> $(BUILDDIR)/$*.$(DEPEXT)
@rm -f $(BUILDDIR)/$*.$(DEPEXT).tmp
# convert to hex
$(TARGET).memfile: $(TARGET)
@echo 'Making object dump file.'
@riscv64-unknown-elf-objdump -D $< > $<.objdump
@echo 'Making memory file'
exe2memfile0.pl $<
extractFunctionRadix.sh $<.objdump
mkdir -p ../../imperas-riscv-tests/work/rv64BP/
cp -f $(TARGETDIR)/* ../../imperas-riscv-tests/work/rv64BP/

View file

@ -0,0 +1,101 @@
PERIOD = 11000000
#PERIOD = 20
.section .init
.global _start
.type _start, @function
_start:
# Initialize global pointer
.option push
.option norelax
1:auipc gp, %pcrel_hi(__global_pointer$)
addi gp, gp, %pcrel_lo(1b)
.option pop
li x1, 0
li x2, 0
li x4, 0
li x5, 0
li x6, 0
li x7, 0
li x8, 0
li x9, 0
li x10, 0
li x11, 0
li x12, 0
li x13, 0
li x14, 0
li x15, 0
li x16, 0
li x17, 0
li x18, 0
li x19, 0
li x20, 0
li x21, 0
li x22, 0
li x23, 0
li x24, 0
li x25, 0
li x26, 0
li x27, 0
li x28, 0
li x29, 0
li x30, 0
li x31, 0
# set the stack pointer to the top of memory - 8 bytes (pointer size)
li sp, 0x87FFFFF8
li a0, 0x00000000
li a1, 0x80000000
#li a2, 128*1024*1024/512 # copy 128MB
li a2, 127*1024*1024/512 # copy 127MB upper 1MB contains the return address (ra)
#li a2, 800 # copy 400KB
jal ra, copyFlash
fence.i
# now toggle led so we know the copy completed.
# write to gpio
li t2, 0xFF
la t3, 0x1001200C
li t4, 5
loop:
# delay
li t0, PERIOD/2
delay1:
addi t0, t0, -1
bge t0, x0, delay1
sw t2, 0x0(t3)
li t0, PERIOD/2
delay2:
addi t0, t0, -1
bge t0, x0, delay2
sw x0, 0x0(t3)
addi t4, t4, -1
bgt t4, x0, loop
# now that the card is copied and the led toggled we
# jump to the copied contents of the sd card.
jumpToLinux:
csrrs a0, 0xF14, x0 # copy hard ID to a0
li a1, 0x87000000 # end of memory? not 100% sure on this but it's 112MB
la a2, end_of_bios
li t0, 0x80000000 # start of code
jalr x0, t0, 0
end_of_bios:

View file

@ -0,0 +1,40 @@
///////////////////////////////////////////
// copyFlash.sv
//
// Written: Ross Thompson September 25, 2021
// Modified:
//
// Purpose: copies flash card into memory
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
#include "sdcDriver.h"
void copyFlash(long int blockAddr, long int * Dst, int numBlocks) {
setSDCCLK(1);
waitInitSDC();
int index;
for(index = 0; index < numBlocks; index++) {
copySDC512(blockAddr+(index*512), Dst+(index*512/8));
}
}

View file

@ -0,0 +1,154 @@
# start by writting the clock divider to 4 setting SDC to 25MHz
la x3, 0x12100
li x4, -4
sw x4, 0x0(x3)
# start by writting the clock divider to 1 setting SDC to 100MHZ
la x3, 0x12100
li x4, 1
sw x4, 0x0(x3)
# wait until the SDC is done with initialization
li x4, 0x1
wait_sdc_done_init:
lw x5, 4(x3)
and x5, x5, x4
bne x5, x4, wait_sdc_done_init
# now that it is done lets setup for a read
li x6, 0x20000000
sd x6, 0x10(x3) # write address register
# send read by writting to command register
li x7, 0x4
sw x7, 0x8(x3)
li x4, 0x2
wait_sdc_done_read:
lw x5, 4(x3)
and x5, x5, x4
beq x5, x4, wait_sdc_done_read
# copy data from mailbox
li x11, 0x80000000
li x9, 0
copy_sdc:
li x8, 512/8
ld x10, 0x18(x3) # read the mailbox
sd x10, 0x0(x11) # write to dram
addi x9, x9, 1
addi x11, x11, 8
blt x9, x8, copy_sdc
# second read of sdc
# now that it is done lets setup for a read
li x6, 0x20000200
sd x6, 0x10(x3) # write address register
# send read by writting to command register
li x7, 0x4
sw x7, 0x8(x3)
li x4, 0x2
wait_sdc_done_read2:
lw x5, 4(x3)
and x5, x5, x4
beq x5, x4, wait_sdc_done_read2
# copy data from mailbox
li x11, 0x80000200
li x9, 0
copy_sdc2:
li x8, 512/8
ld x10, 0x18(x3) # read the mailbox
sd x10, 0x0(x11) # write to dram
addi x9, x9, 1
addi x11, x11, 8
blt x9, x8, copy_sdc2
# write to gpio
li x2, 0xFF
la x3, 0x10012000
# +8 is output enable
# +C is output value
addi x4, x3, 8
addi x5, x3, 0xC
# write initial value of 0xFF to GPO
sw x2, 0x0(x5)
# enable output
sw x2, 0x0(x4)
# before jumping to led loop
# lets try writting to dram.
li x21, 0
li x23, 4096*16 # 64KB of data
li x22, 0x80000000
li x24, 0
write_loop:
add x25, x22, x24
sw x24, 0(x25)
addi x24, x24, 4
blt x24, x23, write_loop
li x24, 0
read_loop:
add x25, x22, x24
lw x21, 0(x25)
# check value
bne x21, x24, fail_loop
addi x24, x24, 4
#
blt x24, x23, read_loop
loop:
# delay
li x20, PERIOD
delay1:
addi x20, x20, -1
bge x20, x0, delay1
# new GPO
addi x2, x2, 1
sw x2, 0x0(x5)
j loop
fail_loop:
# delay
li x20, PERIOD/20
fail_delay1:
addi x20, x20, -1
bge x20, x0, fail_delay1
# clear GPO
sw x0, 0x0(x5)
# delay
li x20, PERIOD/20
fail_delay2:
addi x20, x20, -1
bge x20, x0, fail_delay2
# write GPO
sw x2, 0x0(x5)
j fail_loop

View file

@ -0,0 +1,68 @@
///////////////////////////////////////////
// SDC.sv
//
// Written: Ross Thompson September 25, 2021
// Modified:
//
// Purpose: driver for sdc reader.
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
#include "sdcDriver.h"
#define SDC_MAIL_BOX 0x12100
void copySDC512(long int blockAddr, long int * Dst) {
waitInitSDC();
volatile long int * mailBoxAddr;
volatile int * mailBoxCmd;
volatile int * mailBoxStatus;
volatile long int * mailBoxReadData;
mailBoxStatus = (int *) (SDC_MAIL_BOX + 0x4);
mailBoxCmd = (int *) (SDC_MAIL_BOX + 0x8);
mailBoxAddr = (long int *) (SDC_MAIL_BOX + 0x10);
mailBoxReadData = (long int *) (SDC_MAIL_BOX + 0x18);
// write the SDC address register with the blockAddr
*mailBoxAddr = blockAddr;
*mailBoxCmd = 0x4;
// wait until the mailbox has valid data
// this occurs when status[1] = 0
while((*mailBoxStatus & 0x2) == 0x2);
int index;
for(index = 0; index < 512/8; index++) {
Dst[index] = *mailBoxReadData;
}
}
volatile void waitInitSDC(){
volatile int * mailBoxStatus;
mailBoxStatus = (int *) (SDC_MAIL_BOX + 0x4);
while((*mailBoxStatus & 0x1) != 0x1);
}
void setSDCCLK(int divider){
volatile int * mailBoxCLK;
mailBoxCLK = (int *) (SDC_MAIL_BOX + 0x0);
*mailBoxCLK = divider;
}

View file

@ -0,0 +1,9 @@
#ifndef __SDCDRIVER_H
#define __SDCDRIVER_H
void copySDC512(long int, long int *);
volatile void waitInitSDC();
void setSDCCLK(int);
#endif

View file

@ -0,0 +1,97 @@
#PERIOD = 22000000
PERIOD = 20
.section .init
.global _start
.type _start, @function
_start:
# Initialize global pointer
.option push
.option norelax
1:auipc gp, %pcrel_hi(__global_pointer$)
addi gp, gp, %pcrel_lo(1b)
.option pop
li x1, 0
li x2, 0
li x4, 0
li x5, 0
li x6, 0
li x7, 0
li x8, 0
li x9, 0
li x10, 0
li x11, 0
li x12, 0
li x13, 0
li x14, 0
li x15, 0
li x16, 0
li x17, 0
li x18, 0
li x19, 0
li x20, 0
li x21, 0
li x22, 0
li x23, 0
li x24, 0
li x25, 0
li x26, 0
li x27, 0
li x28, 0
li x29, 0
li x30, 0
li x31, 0
# set the stack pointer to the top of memory - 8 bytes (pointer size)
li sp, 0x87FFFFF8
li a0, 0x20000000
li a1, 0x80000000
li a2, 2
jal ra, copyFlash
# now toggle led so we know the copy completed.
# write to gpio
li t2, 0xFF
la t3, 0x1001200C
li t4, 5
loop:
# delay
li t0, PERIOD/2
delay1:
addi t0, t0, -1
bge t0, x0, delay1
sw t2, 0x0(t3)
li t0, PERIOD/2
delay2:
addi t0, t0, -1
bge t0, x0, delay2
sw x0, 0x0(t3)
addi t4, t4, -1
bgt t4, x0, loop
jal ra, _halt
.section .text
.global _halt
.type _halt, @function
_halt:
li gp, 1
li a0, 0
ecall
j _halt

View file

@ -0,0 +1,193 @@
#!/usr/bin/perl -w
# exe2memfile.pl
# David_Harris@hmc.edu 26 November 2020
# Converts an executable file to a series of 32-bit hex instructions
# to read into a Verilog simulation with $readmemh
use File::stat;
use IO::Handle;
if ($#ARGV == -1) {
die("Usage: $0 executable_file");
}
# array to hold contents of memory file
my @memfilebytes = (0)*16384*4;
my $maxaddress = 0;
STDOUT->autoflush(1);
# *** Ross Thompson I think there is a bug here needs to be +1
print ("Processing $#ARGV memfiles: \n");
my $frac = $#ARGV/10;
for(my $i=0; $i<=$#ARGV; $i++) {
if ($i < 10 || $i % $frac == 0) { print ("$i ") };
my $fname = $ARGV[$i];
# print "fname = $fname";
my $ofile = $fname.".objdump";
my $memfile = $fname.".memfile";
my $needsprocessing = 0;
if (!-e $memfile) { $needsprocessing = 1; } # create memfile if it doesn't exist
else {
my $osb = stat($ofile) || die("Can't stat $ofile");
my $msb = stat($memfile) || die("Can't stat $memfile");
my $otime = $osb->mtime;
my $mtime = $msb->mtime;
if ($otime > $mtime) { $needsprocessing = 1; } # is memfile out of date?
}
if ($needsprocessing == 1) {
open(FILE, $ofile) || die("Can't read $ofile");
my $mode = 0; # parse for code
my $section = "";
my $data = "";
my $address;
my $first = 0;
my $firstAddress;
# initialize to all zeros;
# *** need to fix the zeroing range. Not always 64K
for (my $i=0; $i < 65536*4; $i++) {
$memfilebytes[$i] = "00";
}
while(<FILE>) {
# objdump fill is divided into several .sections of which only some we want to actually process.
# In general we want everything except the .comment and .*attributes
if (/Disassembly of section (.*):/) {
$section = $1;
print ("setting section to $section\n");
} else {
# now check if the section is one we are interested in processing.
#if ($section ne ".comment" && $section ne ".riscv.attributes" && $section =~ /\.debug.*/) {
if ($section =~ "\.init|\.text|\..*data|\..*bss") {
# the structure is: possible space(s) hex number: possible space(s) hex number space(s) junk
# there are also lines we need to skip: possible space(s) hex number <string>:
if (/^\s*([0-9A-Fa-f]{1,16}):\s+([0-9A-Fa-f]+).*$/) {
$address = &fixadr($1);
if ($first == 0) {
$first = 1;
$firstAddress = $address;
}
$data = $2;
&emitData($address, $data);
# my $len = length($data);
# for (my $i=0; $i<$len/2; $i++) {
# $memfilebytes[$address+$i] = substr($data, $len-2-2*$i, 2);
# }
# print ("Addr $address $data\n");
# } elsif (/^\s*\.\.\./) {
# print ("Got ...\n");
# } else {
# print ("No match\n");
}
}
}
# # *** this mode stuff does not work if a section is missing or reordered.
# if ($mode == 0) { # Parse code
# # print("Examining $_\n");
# if (/^\s*(\S{1,16}):\s+(\S+)\s+/) {
# $address = &fixadr($1);
# my $instr = $2;
# my $len = length($instr);
# for (my $i=0; $i<$len/2; $i++) {
# $memfilebytes[$address+$i] = substr($instr, $len-2-2*$i, 2);
# }
# print ("address $address $instr\n");
# }
# if (/Disassembly of section .data:/) { $mode = 1;}
# } elsif ($mode == 1) { # Parse data segment
# if (/^\s*(\S{1,16}):\s+(.*)/) {
# $address = &fixadr($1);
# # print "addresss $address maxaddress $maxaddress\n";
# if ($address > $maxaddress) { $maxaddress = $address; }
# my $line = $2;
# # merge chunks with spaces
# # *** might need to change
# $line =~ s/(\S)\s(\S)/$1$2/g;
# # strip off comments
# $line =~ /^(\S*)/;
# $payload = $1;
# &emitData($address, $payload);
# }
# if (/Disassembly of section .comment:/) { $mode = 2; }
# } elsif ($mode == 2) { # parse the comment section
# if (/Disassembly of section .riscv.attributes:/) { $mode = 3; }
# }
}
close(FILE);
$maxaddress = $address + 32; # pad some zeros at the end
# print to memory file
# *** this is a problem
if ($fname =~ /rv32/) {
open(MEMFILE, ">$memfile") || die("Can't write $memfile");
for (my $i=$firstAddress; $i<= $maxaddress; $i = $i + 4) {
for ($j=3; $j>=0; $j--) {
no warnings 'uninitialized';
my $value = $memfilebytes[$i+$j];
if ($value eq ""){
print MEMFILE "00";
} else {
print MEMFILE "$memfilebytes[$i+$j]";
}
}
print MEMFILE "\n";
}
close(MEMFILE);
} else {
open(MEMFILE, ">$memfile") || die("Can't write $memfile");
for (my $i=$firstAddress; $i<= $maxaddress; $i = $i + 8) {
for ($j=7; $j>=0; $j--) {
no warnings 'uninitialized';
my $value = $memfilebytes[$i+$j];
if ($value eq ""){
print MEMFILE "00";
} else {
print MEMFILE "$memfilebytes[$i+$j]";
}
}
print MEMFILE "\n";
}
close(MEMFILE);
}
}
}
print("\n");
sub emitData {
# print the data portion of the ELF into a memroy file, including 0s for empty stuff
# deal with endianness
my $address = shift;
my $payload = shift;
# print("Emitting data. address = $address payload = $payload\n");
my $len = length($payload);
if ($len <= 8) {
# print word or halfword
for(my $i=0; $i<$len/2; $i++) {
my $adr = $address+$i;
my $b = substr($payload, $len-2-2*$i, 2);
$memfilebytes[$adr] = $b;
# print(" $adr $b\n");
}
} elsif ($len == 12) {
# weird case of three halfwords on line
&emitData($address, substr($payload, 0, 4));
&emitData($address+2, substr($payload, 4, 4));
&emitData($address+4, substr($payload, 8, 4));
} else {
&emitData($address, substr($payload, 0, 8));
&emitData($address+4, substr($payload, 8, $len-8));
}
}
sub fixadr {
# strip off leading 8 from address and convert to decimal
# if the leading 8 is not present don't remove.
my $adr = shift;
#print "addr $adr\n";
return hex($adr);
}

View file

@ -27,6 +27,7 @@
// include shared configuration
`include "wally-shared.vh"
`define FPGA 1
`define QEMU 1
`define BUILDROOT 1
`define BUSYBEAR 0
@ -82,9 +83,15 @@
`define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIM_BASE 56'h00001000
`define BOOTTIM_RANGE 56'h00000FFF
`define TIM_SUPPORTED 1'b1
`define TIM_SUPPORTED 1'b0
`define TIM_BASE 56'h80000000
`define TIM_RANGE 56'h07FFFFFF
`define EXT_SUPPORTED 1'b1
`define EXT_BASE 56'h80000000
`define EXT_RANGE 56'h07FFFFFF
`define CLINT_SUPPORTED 1'b1
`define CLINT_BASE 56'h02000000
`define CLINT_RANGE 56'h0000FFFF
@ -97,6 +104,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Bus Interface width
`define AHBW 64

View file

@ -0,0 +1,130 @@
//////////////////////////////////////////
// busybear-config.vh
//
// Written: David_Harris@hmc.edu 4 January 2021
// Modified:
//
// Purpose: Specify which features are configured
// Macros to determine which modes are supported based on MISA
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
// include shared configuration
`include "wally-shared.vh"
`define QEMU 0
`define BUILDROOT 0
`define BUSYBEAR 1
`define LINUX_FIX_READ {'h10000005}
`define LINUX_TEST_VECTORS "/courses/e190ax/busybear_boot/"
//`define LINUX_TEST_VECTORS "../../../busybear_boot/"
// RV32 or RV64: XLEN = 32 or 64
`define XLEN 64
`define MISA (32'h0014112D)
`define ZICSR_SUPPORTED 1
`define ZIFENCEI_SUPPORTED 1
`define ZICOUNTERS_SUPPORTED 1
`define COUNTERS 32
`define DESIGN_COMPILER 0
// Microarchitectural Features
`define UARCH_PIPELINED 1
`define UARCH_SUPERSCALR 0
`define UARCH_SINGLECYCLE 0
`define MEM_DCACHE 1
`define MEM_DTIM 1
`define MEM_ICACHE 1
`define MEM_VIRTMEM 1
`define VECTORED_INTERRUPTS_SUPPORTED 1 // Domenico Ottolia 4/15: Support for vectored interrupts in _tvec csrs. Just implemented in src/privileged/trap.sv around line 75. Pretty sure this should be 1.
// TLB configuration. Entries should be a power of 2
`define ITLB_ENTRIES 32
`define DTLB_ENTRIES 32
// Cache configuration. Sizes should be a power of two
// typical configuration 4 ways, 4096 bytes per way, 256 bit or more blocks
`define DCACHE_NUMWAYS 4
`define DCACHE_WAYSIZEINBYTES 2048
`define DCACHE_BLOCKLENINBITS 256
`define DCACHE_REPLBITS 3
`define ICACHE_NUMWAYS 1
`define ICACHE_WAYSIZEINBYTES 4096
`define ICACHE_BLOCKLENINBITS 256
// Integer Divider Configuration
// DIV_BITSPERCYCLE must be 1, 2, or 4
`define DIV_BITSPERCYCLE 4
// Legal number of PMP entries are 0, 16, or 64
`define PMP_ENTRIES 16
// Address space
`define RESET_VECTOR 64'h0000000000001000
// Peripheral Addresses
// Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIM_SUPPORTED 1'b1
//`define BOOTTIM_BASE 56'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIM_RANGE 56'h00003FFF
`define BOOTTIM_BASE 56'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIM_RANGE 56'h00000FFF
`define TIM_SUPPORTED 1'b1
`define TIM_BASE 56'h80000000
`define TIM_RANGE 56'h07FFFFFF
`define CLINT_SUPPORTED 1'b1
`define CLINT_BASE 56'h02000000
`define CLINT_RANGE 56'h0000FFFF
`define GPIO_SUPPORTED 1'b1
`define GPIO_BASE 56'h10012000
`define GPIO_RANGE 56'h000000FF
`define UART_SUPPORTED 1'b1
`define UART_BASE 56'h10000000
`define UART_RANGE 56'h00000007
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Bus Interface width
`define AHBW 64
// Test modes
// Tie GPIO outputs back to inputs
`define GPIO_LOOPBACK_TEST 0
// Hardware configuration
//`define UART_PRESCALE 1
`define UART_PRESCALE 0
// Interrupt configuration
`define PLIC_NUM_SRC 53
`define PLIC_UART_ID 4
`define TWO_BIT_PRELOAD "../config/busybear/twoBitPredictor.txt"
`define BTB_PRELOAD "../config/busybear/BTBPredictor.txt"
`define BPTYPE "BPGSHARE" // BPGLOBAL or BPTWOBIT or BPGSHARE
`define BPRED_ENABLED 1

View file

@ -102,6 +102,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 34'h0C000000
`define PLIC_RANGE 34'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Test modes

View file

@ -103,6 +103,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Test modes

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,134 @@
//////////////////////////////////////////
// wally-config.vh
//
// Written: David_Harris@hmc.edu 4 January 2021
// Modified:
//
// Purpose: Specify which features are configured
// Macros to determine which modes are supported based on MISA
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
// include shared configuration
`include "wally-shared.vh"
`define FPGA 1
`define QEMU 0
`define BUILDROOT 0
`define BUSYBEAR 0
`define DESIGN_COMPILER 0
//`define LINUX_TEST_VECTORS "/courses/e190ax/buildroot_boot/"
// RV32 or RV64: XLEN = 32 or 64
`define XLEN 64
`define MISA (32'h0014112D)
`define ZICSR_SUPPORTED 1
`define ZIFENCEI_SUPPORTED 1
`define ZICOUNTERS_SUPPORTED 1
`define COUNTERS 32
// Microarchitectural Features
`define UARCH_PIPELINED 1
`define UARCH_SUPERSCALR 0
`define UARCH_SINGLECYCLE 0
`define MEM_DCACHE 1
`define MEM_DTIM 1
`define MEM_ICACHE 1
`define MEM_VIRTMEM 1
`define VECTORED_INTERRUPTS_SUPPORTED 1 // Domenico Ottolia 4/15: Support for vectored interrupts in _tvec csrs. Just implemented in src/privileged/trap.sv around line 75. Pretty sure this should be 1.
// TLB configuration. Entries should be a power of 2
`define ITLB_ENTRIES 32
`define DTLB_ENTRIES 32
// Cache configuration. Sizes should be a power of two
// typical configuration 4 ways, 4096 bytes per way, 256 bit or more blocks
`define DCACHE_NUMWAYS 4
`define DCACHE_WAYSIZEINBYTES 4096
`define DCACHE_BLOCKLENINBITS 256
`define DCACHE_REPLBITS 3
`define ICACHE_NUMWAYS 4
`define ICACHE_WAYSIZEINBYTES 4096
`define ICACHE_BLOCKLENINBITS 256
// Integer Divider Configuration
// DIV_BITSPERCYCLE must be 1, 2, or 4
`define DIV_BITSPERCYCLE 4
// Legal number of PMP entries are 0, 16, or 64
`define PMP_ENTRIES 64
// Address space
`define RESET_VECTOR 64'h0000000000001000
// Peripheral Addresses
// Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIM_BASE 56'h00001000
`define BOOTTIM_RANGE 56'h00000FFF
`define TIM_SUPPORTED 1'b0
`define TIM_BASE 56'h100000000
`define TIM_RANGE 56'h07FFFFFF
`define EXT_MEM_SUPPORTED 1'b1
`define EXT_MEM_BASE 56'h80000000
`define EXT_MEM_RANGE 56'h07FFFFFF
`define EXT_SUPPORTED 1'b0
`define EXT_BASE 56'h80000000
`define EXT_RANGE 56'h07FFFFFF
`define CLINT_SUPPORTED 1'b1
`define CLINT_BASE 56'h02000000
`define CLINT_RANGE 56'h0000FFFF
`define GPIO_SUPPORTED 1'b1
`define GPIO_BASE 56'h10012000
`define GPIO_RANGE 56'h000000FF
`define UART_SUPPORTED 1'b1
`define UART_BASE 56'h10000000
`define UART_RANGE 56'h00000007
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Bus Interface width
`define AHBW 64
// Test modes
// Tie GPIO outputs back to inputs
`define GPIO_LOOPBACK_TEST 0
// Hardware configuration
`define UART_PRESCALE 0
// Interrupt configuration
`define PLIC_NUM_SRC 53
`define PLIC_UART_ID 4
`define TWO_BIT_PRELOAD "../config/fpga/twoBitPredictor.txt"
`define BTB_PRELOAD "../config/fpga/BTBPredictor.txt"
`define BPRED_ENABLED 1
`define BPTYPE "BPGSHARE" // BPLOCALPAg or BPGLOBAL or BPTWOBIT or BPGSHARE
`define TESTSBP 1

View file

@ -97,6 +97,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 34'h0C000000
`define PLIC_RANGE 34'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 34'h00012100
`define SDC_RANGE 34'h0000001F
// Bus Interface width
`define AHBW 32

View file

@ -98,6 +98,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Bus Interface width
`define AHBW 64

View file

@ -99,6 +99,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Test modes

View file

@ -96,6 +96,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 34'h0C000000
`define PLIC_RANGE 34'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 34'h00012100
`define SDC_RANGE 34'h0000001F
// Bus Interface width
`define AHBW 32

View file

@ -60,22 +60,21 @@
// Cache configuration. Sizes should be a power of two
// typical configuration 4 ways, 4096 bytes per way, 256 bit or more blocks
`define DCACHE_NUMWAYS 4
`define DCACHE_WAYSIZEINBYTES 2048
`define DCACHE_WAYSIZEINBYTES 4096
`define DCACHE_BLOCKLENINBITS 256
`define DCACHE_REPLBITS 3
`define ICACHE_NUMWAYS 1
`define ICACHE_NUMWAYS 4
`define ICACHE_WAYSIZEINBYTES 4096
`define ICACHE_BLOCKLENINBITS 256
// Legal number of PMP entries are 0, 16, or 64
`define PMP_ENTRIES 64
// Integer Divider Configuration
// DIV_BITSPERCYCLE must be 1, 2, or 4
`define DIV_BITSPERCYCLE 4
// Legal number of PMP entries are 0, 16, or 64
`define PMP_ENTRIES 16
// Address space
`define RESET_VECTOR 64'h0000000000000000
`define RESET_VECTOR 64'h0000000000001000
// Bus Interface width
`define AHBW 64
@ -102,6 +101,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Test modes

View file

@ -102,6 +102,9 @@
`define PLIC_SUPPORTED 1'b1
`define PLIC_BASE 56'h0C000000
`define PLIC_RANGE 56'h03FFFFFF
`define SDC_SUPPORTED 1'b1
`define SDC_BASE 56'h00012100
`define SDC_RANGE 56'h0000001F
// Test modes

View file

@ -0,0 +1,55 @@
SD Flash interface
regsiter map:
1. clock divider
2. address
3. data register
4. command register
5. size register
Number of bytes to read or write.
6. status register
1. bits 11 to 0: bytes currently in the buffer
2. bits 12 to 29: reservered
3. bit 30: fault
4. bit 31: busy
5. bits XLEN-1 to 32: reservered
non dma read operation
1. write the address regsiter
2. write the command register to read
3. wait for interrupt or pool on status
4. Check status for fault and number of bytes.
5. read the data register for 512 bytes. (64 ld, or 128 lw)
non dma write operation
1. write address register
2. write data register for 512 bytes. (64 sd, or 128 sw)
3. write command register to write data to flash
4. wait for interrupt or pool on status
5. check status for fault and number of bytes written.
implement dma transfers later
interrupts
1. operation done
2. bus error (more of an exception)
Occurs if attempting to do an operation while the flash controller is busy.
ie. if status[31] is set generate an interrupt
This is tricky in a multiprocessor environment.
tasks
1. [-] Remove all AFRL identifiers
2. [X] get the existing sdc compiled on wally.
1. [X] use wally primatives over tcore's
3. build abhlite interface with the above registers and necessary fsm.
1. [ ] The sd card reader uses a 4 bit data interface. We can change this to be something
more pratical.
4. write test programs
5. [X] Convert VHDL to system verilog

View file

@ -0,0 +1,595 @@
onerror {resume}
quietly WaveActivateNextPane {} 0
add wave -noupdate /testbench/clk
add wave -noupdate /testbench/reset
add wave -noupdate /testbench/test
add wave -noupdate /testbench/memfilename
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/SATP_REGW
add wave -noupdate -expand -group {Execution Stage} /testbench/dut/wallypipelinedsoc/hart/ifu/PCE
add wave -noupdate -expand -group {Execution Stage} /testbench/InstrEName
add wave -noupdate -expand -group {Execution Stage} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrE
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrValidM
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/PCM
add wave -noupdate -expand -group {Memory Stage} /testbench/InstrMName
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/InstrM
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/lsu/MemAdrM
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ResultM
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ResultW
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrMisalignedFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrAccessFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/IllegalInstrFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/BreakpointFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/LoadMisalignedFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/StoreMisalignedFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/LoadAccessFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/StoreAccessFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/EcallFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrPageFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/LoadPageFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/StorePageFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InterruptM
add wave -noupdate -group HDU -group interrupts /testbench/dut/wallypipelinedsoc/hart/priv/trap/PendingIntsM
add wave -noupdate -group HDU -group interrupts /testbench/dut/wallypipelinedsoc/hart/priv/trap/CommittedM
add wave -noupdate -group HDU -group interrupts /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrValidM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/BPPredWrongE
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/CSRWritePendingDEM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/RetM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/TrapM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/LoadStallD
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/StoreStallD
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/ICacheStallF
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/LSUStall
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/MulDivStallD
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/hzu/FlushF
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushD
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushE
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushM
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushW
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallF
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallD
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallE
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallM
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallW
add wave -noupdate -group Bpred -color Orange /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHR
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPPredF
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/InstrClassE[0]}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPInstrClassE[0]}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPPredDirWrongE
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} -divider {class check}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightNonCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassWrongCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassWrongNonCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightBPRight
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightBPWrong
add wave -noupdate -group Bpred -radix hexadecimal -childformat {{{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[6]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[5]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[4]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[3]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[2]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[1]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[0]} -radix binary}} -subitemconfig {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[6]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[5]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[4]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[3]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[2]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[1]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[0]} {-height 16 -radix binary}} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRNext
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRUpdateEN
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr0
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr1
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateEN
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRLookup
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PCNextF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHT/RA1
add wave -noupdate -group Bpred -expand -group prediction -radix binary /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BTBValidF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPInstrClassF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BTBPredPCF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/RASPCF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/LookUpPCIndex
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/TargetPC
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex -radix binary /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredE
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/PCSrcE
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredDirWrongE
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdatePCIndex
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdateTarget
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdateEN
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdatePC
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdateTarget
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PCE
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHT/WA1
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/FallThroughWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/PredictionPCWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/InstrClassE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/PredictionInstrClassWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredClassNonCFIWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredWrongE
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredWrongE
add wave -noupdate -group {instruction pipeline} /testbench/InstrFName
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/FinalInstrRawF
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrD
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrE
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrM
add wave -noupdate -group {instruction pipeline} /testbench/InstrW
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCNextF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCPlus2or4F
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/BPPredPCF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCNext0F
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCNext1F
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/SelBPPredF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/BPPredWrongE
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PrivilegedChangePCM
add wave -noupdate -group {Decode Stage} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrD
add wave -noupdate -group {Decode Stage} /testbench/InstrDName
add wave -noupdate -group {Decode Stage} /testbench/dut/wallypipelinedsoc/hart/ieu/c/RegWriteD
add wave -noupdate -group {Decode Stage} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/RdD
add wave -noupdate -group {Decode Stage} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/Rs1D
add wave -noupdate -group {Decode Stage} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/Rs2D
add wave -noupdate -group RegFile -expand /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/rf
add wave -noupdate -group RegFile /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/a1
add wave -noupdate -group RegFile /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/a2
add wave -noupdate -group RegFile /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/a3
add wave -noupdate -group RegFile /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/rd1
add wave -noupdate -group RegFile /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/rd2
add wave -noupdate -group RegFile /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/we3
add wave -noupdate -group RegFile /testbench/dut/wallypipelinedsoc/hart/ieu/dp/regf/wd3
add wave -noupdate -group RegFile -group {write regfile mux} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ALUResultW
add wave -noupdate -group RegFile -group {write regfile mux} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ReadDataW
add wave -noupdate -group RegFile -group {write regfile mux} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/CSRReadValW
add wave -noupdate -group RegFile -group {write regfile mux} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ResultSrcW
add wave -noupdate -group RegFile -group {write regfile mux} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ResultW
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/a
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/b
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/alucontrol
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/result
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/flags
add wave -noupdate -group alu -divider internals
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/overflow
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/carry
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/zero
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/neg
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/lt
add wave -noupdate -group alu /testbench/dut/wallypipelinedsoc/hart/ieu/dp/alu/ltu
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/Rs1D
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/Rs2D
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/Rs1E
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/Rs2E
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/RdE
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/RdM
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/RdW
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/MemReadE
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/RegWriteM
add wave -noupdate -group Forward /testbench/dut/wallypipelinedsoc/hart/ieu/fw/RegWriteW
add wave -noupdate -group Forward -color Thistle /testbench/dut/wallypipelinedsoc/hart/ieu/fw/ForwardAE
add wave -noupdate -group Forward -color Thistle /testbench/dut/wallypipelinedsoc/hart/ieu/fw/ForwardBE
add wave -noupdate -group Forward -color Thistle /testbench/dut/wallypipelinedsoc/hart/ieu/fw/LoadStallD
add wave -noupdate -group {alu execution stage} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/WriteDataE
add wave -noupdate -group {alu execution stage} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ALUResultE
add wave -noupdate -group {alu execution stage} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/SrcAE
add wave -noupdate -group {alu execution stage} /testbench/dut/wallypipelinedsoc/hart/ieu/dp/SrcBE
add wave -noupdate -group PCS /testbench/dut/wallypipelinedsoc/hart/ifu/PCNextF
add wave -noupdate -group PCS /testbench/dut/wallypipelinedsoc/hart/PCF
add wave -noupdate -group PCS /testbench/dut/wallypipelinedsoc/hart/ifu/PCD
add wave -noupdate -group PCS /testbench/dut/wallypipelinedsoc/hart/PCE
add wave -noupdate -group PCS /testbench/dut/wallypipelinedsoc/hart/PCM
add wave -noupdate -group PCS /testbench/PCW
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/InstrD
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/SrcAE
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/SrcBE
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/Funct3E
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/MulDivE
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/W64E
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/StallM
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/StallW
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/FlushM
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/FlushW
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/MulDivResultW
add wave -noupdate -group muldiv /testbench/dut/wallypipelinedsoc/hart/mdu/DivBusyE
add wave -noupdate -group icache -color Gold /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/CurrState
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/BasePAdrF
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/WayHit
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/genblk1/cachereplacementpolicy/BlockReplacementBits
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/genblk1/cachereplacementpolicy/EncVicWay
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/VictimWay
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/SetValid}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -label TAG {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/CacheTagMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/ValidBits}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -expand -group Way0Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -expand -group Way0Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -group Way0Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -group Way0Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -group Way0Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -group Way0Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -group Way0Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way0 -group Way0Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[0]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/WriteWordEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -label TAG {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/CacheTagMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/ValidBits}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -expand -group Way1Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -expand -group Way1Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -group Way1Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -group Way1Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -group Way1Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -group Way1Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -group Way1Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way1 -group Way1Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[1]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/SetValid}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -label TAG {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/CacheTagMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/ValidBits}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -expand -group Way2Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -expand -group Way2Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -group Way2Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -group Way2Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -group Way2Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -group Way2Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -group Way2Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -group way2 -group Way2Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[2]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/SetValid}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -label TAG {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/CacheTagMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/DirtyBits}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/ValidBits}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word0 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -group Way3Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -group Way3Word1 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -group Way3Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -group Way3Word2 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -group Way3Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group icache -group {Cache SRAM writes} -expand -group way3 -group Way3Word3 {/testbench/dut/wallypipelinedsoc/hart/ifu/icache/MemWay[3]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/NextState
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/ITLBMissF
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/ITLBWriteF
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/ReadLineF
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/PCNextIndexF
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/ReadLineF
add wave -noupdate -group icache /testbench/dut/wallypipelinedsoc/hart/ifu/icache/BasePAdrF
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/hit
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/spill
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/ICacheStallF
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/SavePC
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/spillSave
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/UnalignedSelect
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/spillSave
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/CntReset
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/PreCntEn
add wave -noupdate -group icache -group {fsm out and control} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/CntEn
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/InstrPAdrF
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/InstrInF
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/FetchCountFlag
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/FetchCount
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/InstrReadF
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/InstrAckF
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/controller/ICacheMemWriteEnable
add wave -noupdate -group icache -expand -group memory /testbench/dut/wallypipelinedsoc/hart/ifu/icache/ICacheMemWriteData
add wave -noupdate -group AHB -color Gold /testbench/dut/wallypipelinedsoc/hart/ebu/BusState
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/NextBusState
add wave -noupdate -group AHB -expand -group {input requests} /testbench/dut/wallypipelinedsoc/hart/ebu/AtomicMaskedM
add wave -noupdate -group AHB -expand -group {input requests} /testbench/dut/wallypipelinedsoc/hart/ebu/InstrReadF
add wave -noupdate -group AHB -expand -group {input requests} /testbench/dut/wallypipelinedsoc/hart/ebu/MemSizeM
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HCLK
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HRESETn
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HRDATA
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HREADY
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HRESP
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HADDR
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HWDATA
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HWRITE
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HSIZE
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HBURST
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HPROT
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HTRANS
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HMASTLOCK
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HADDRD
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HSIZED
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/HWRITED
add wave -noupdate -group AHB /testbench/dut/wallypipelinedsoc/hart/ebu/StallW
add wave -noupdate -group lsu -expand -group {LSU ARB} /testbench/dut/wallypipelinedsoc/hart/lsu/arbiter/SelPTW
add wave -noupdate -group lsu -expand -group dcache -color Gold /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/dcachefsm/CurrState
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/WalkerPageFaultM
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/WriteDataM
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SRAMBlockWriteEnableM
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SRAMWordWriteEnableM
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SRAMWayWriteEnable
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SRAMWordEnable
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SRAMBlockWayWriteEnableM
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SelAdrM
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ReadDataBlockM
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/DCacheMemWriteData
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/FlushWay
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/VictimDirty
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/VDWriteEnableWay
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ClearDirty
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/SetValid}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/SetDirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -label TAG {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/CacheTagMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/DirtyBits}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/ValidBits}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way0 -expand -group Way0Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/DirtyBits}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/SetDirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/WriteWordEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -label TAG {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/CacheTagMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way1 -expand -group Way1Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/SetValid}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/SetDirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -label TAG {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/CacheTagMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/DirtyBits}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/ValidBits}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group way2 -expand -group Way2Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/SetValid}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/SetDirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -label TAG {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/CacheTagMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/DirtyBits}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/ValidBits}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[0]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[0]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[1]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[1]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[2]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[2]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[3]/CacheDataMem/WriteEnable}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way3 -expand -group Way3Word3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/word[3]/CacheDataMem/StoredData}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group valid/dirty /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SetValid
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group valid/dirty /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ClearValid
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group valid/dirty /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/SetDirty
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -group valid/dirty /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ClearDirty
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/WayHit}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/Valid}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/Dirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -group way0 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[0]/ReadTag}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/WayHit}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/Valid}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/Dirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way1 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[1]/ReadTag}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/WayHit}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/Valid}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/Dirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way2 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[2]/ReadTag}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/WayHit}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/Valid}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/Dirty}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} -expand -group way3 {/testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemWay[3]/ReadTag}
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/WayHit
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ReadDataBlockWayMaskedM
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ReadDataWordM
add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM read} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ReadDataWordMuxM
add wave -noupdate -group lsu -expand -group dcache -group Victim /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/VictimTag
add wave -noupdate -group lsu -expand -group dcache -group Victim /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/VictimWay
add wave -noupdate -group lsu -expand -group dcache -group Victim /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/VictimDirtyWay
add wave -noupdate -group lsu -expand -group dcache -group Victim /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/VictimDirty
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemRWM
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemAdrE
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemPAdrM
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/Funct3M
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/Funct7M
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/AtomicM
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/FlushDCacheM
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/CacheableM
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/WriteDataM
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/ReadDataM
add wave -noupdate -group lsu -expand -group dcache -expand -group {CPU side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/DCacheStall
add wave -noupdate -group lsu -expand -group dcache /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/FlushAdrFlag
add wave -noupdate -group lsu -expand -group dcache -group status /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/WayHit
add wave -noupdate -group lsu -expand -group dcache -group status -color {Medium Orchid} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/CacheHit
add wave -noupdate -group lsu -expand -group dcache -group status /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/FetchCount
add wave -noupdate -group lsu -expand -group dcache -expand -group {Memory Side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/FetchCountFlag
add wave -noupdate -group lsu -expand -group dcache -expand -group {Memory Side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/AHBPAdr
add wave -noupdate -group lsu -expand -group dcache -expand -group {Memory Side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/AHBRead
add wave -noupdate -group lsu -expand -group dcache -expand -group {Memory Side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/AHBWrite
add wave -noupdate -group lsu -expand -group dcache -expand -group {Memory Side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/AHBAck
add wave -noupdate -group lsu -expand -group dcache -expand -group {Memory Side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/HRDATA
add wave -noupdate -group lsu -expand -group dcache -expand -group {Memory Side} /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/HWDATA
add wave -noupdate -group lsu -group dtlb /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/genblk1/tlb/tlbcontrol/EffectivePrivilegeMode
add wave -noupdate -group lsu -group dtlb /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/genblk1/tlb/tlbcontrol/Translate
add wave -noupdate -group lsu -group dtlb /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/genblk1/tlb/tlbcontrol/DisableTranslation
add wave -noupdate -group lsu -group dtlb /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/TLBMiss
add wave -noupdate -group lsu -group dtlb /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/TLBHit
add wave -noupdate -group lsu -group dtlb /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/PhysicalAddress
add wave -noupdate -group lsu -group dtlb -expand -group faults /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/TLBPageFault
add wave -noupdate -group lsu -group dtlb -expand -group faults /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/LoadAccessFaultM
add wave -noupdate -group lsu -group dtlb -expand -group faults /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/StoreAccessFaultM
add wave -noupdate -group lsu -group dtlb /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/genblk1/tlb/TLBPAdr
add wave -noupdate -group lsu -group dtlb -expand -group write /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/genblk1/tlb/PTE
add wave -noupdate -group lsu -group dtlb -expand -group write /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/genblk1/tlb/TLBWrite
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/pmachecker/PhysicalAddress
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/pmachecker/SelRegions
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/Cacheable
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/Idempotent
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/AtomicAllowed
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/pmachecker/PMAAccessFault
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/PMAInstrAccessFaultF
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/PMALoadAccessFaultM
add wave -noupdate -group lsu -group pma /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/PMAStoreAccessFaultM
add wave -noupdate -group lsu -group pmp /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/PMPInstrAccessFaultF
add wave -noupdate -group lsu -group pmp /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/PMPLoadAccessFaultM
add wave -noupdate -group lsu -group pmp /testbench/dut/wallypipelinedsoc/hart/lsu/dmmu/PMPStoreAccessFaultM
add wave -noupdate -group lsu -group ptwalker -color Gold /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/genblk1/WalkerState
add wave -noupdate -group lsu -group ptwalker /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/PCF
add wave -noupdate -group lsu -group ptwalker /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/genblk1/TranslationVAdr
add wave -noupdate -group lsu -group ptwalker /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/TranslationPAdr
add wave -noupdate -group lsu -group ptwalker /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/HPTWReadPTE
add wave -noupdate -group lsu -group ptwalker /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/PTE
add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/ITLBMissF
add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/DTLBMissM
add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/ITLBWriteF
add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/DTLBWriteM
add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/WalkerInstrPageFaultF
add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/WalkerLoadPageFaultM
add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/wallypipelinedsoc/hart/lsu/hptw/WalkerStorePageFaultM
add wave -noupdate -group csr /testbench/dut/wallypipelinedsoc/hart/priv/csr/MIP_REGW
add wave -noupdate -group itlb /testbench/dut/wallypipelinedsoc/hart/ifu/immu/TLBWrite
add wave -noupdate -group itlb /testbench/dut/wallypipelinedsoc/hart/ifu/ITLBMissF
add wave -noupdate -group itlb /testbench/dut/wallypipelinedsoc/hart/ifu/immu/PhysicalAddress
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/VAdr
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/lsu/dcache/MemPAdrM
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HCLK
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HSELPLIC
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HADDR
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HWRITE
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HREADY
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HTRANS
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HWDATA
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/UARTIntr
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/GPIOIntr
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HREADPLIC
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HRESPPLIC
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/HREADYPLIC
add wave -noupdate -group plic /testbench/dut/wallypipelinedsoc/uncore/plic/plic/ExtIntM
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HCLK
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HSELGPIO
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HADDR
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HWDATA
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HWRITE
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HREADY
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HTRANS
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HREADGPIO
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HRESPGPIO
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/HREADYGPIO
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/GPIOPinsIn
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/GPIOPinsOut
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/GPIOPinsEn
add wave -noupdate -group GPIO /testbench/dut/wallypipelinedsoc/uncore/gpio/gpio/GPIOIntr
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HCLK
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HSELCLINT
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HADDR
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HWRITE
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HWDATA
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HREADY
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HTRANS
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HREADCLINT
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HRESPCLINT
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/HREADYCLINT
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/MTIME
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/MTIMECMP
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/TimerIntM
add wave -noupdate -group CLINT /testbench/dut/wallypipelinedsoc/uncore/clint/clint/SwIntM
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HCLK
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HRESETn
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HSELUART
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HADDR
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HWRITE
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HWDATA
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HREADUART
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HRESPUART
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HREADYUART
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/SIN
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/DSRb
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/DCDb
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/CTSb
add wave -noupdate -group uart /testbench/dut/wallypipelinedsoc/uncore/uart/uart/RIb
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/SOUT
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/RTSb
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/DTRb
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/OUT1b
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/OUT2b
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/INTR
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/TXRDYb
add wave -noupdate -group uart -expand -group outputs /testbench/dut/wallypipelinedsoc/uncore/uart/uart/RXRDYb
add wave -noupdate -group UART /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HCLK
add wave -noupdate -group UART /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HSELUART
add wave -noupdate -group UART /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HADDR
add wave -noupdate -group UART /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HWRITE
add wave -noupdate -group UART /testbench/dut/wallypipelinedsoc/uncore/uart/uart/HWDATA
add wave -noupdate -group SDC -color Gold -label {AHBLite FSM} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/CurrState
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HCLK
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/CLKGate
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/SDCCLKIn
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/SDCCLK
add wave -noupdate -group SDC -expand -group {SDC interfce} /testbench/dut/wallypipelinedsoc/SDCCLK
add wave -noupdate -group SDC -expand -group {SDC interfce} -color Brown /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/my_sd_cmd_fsm/o_SD_CMD_OE
add wave -noupdate -group SDC -expand -group {SDC interfce} /testbench/dut/SDCCmdOut
add wave -noupdate -group SDC -expand -group {SDC interfce} /testbench/dut/SDCCmdIn
add wave -noupdate -group SDC -expand -group {SDC interfce} /testbench/dut/SDCDatIn
add wave -noupdate -group SDC -expand -group {SDC FSMs} -color Gold -label {cmd fsm} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/my_sd_cmd_fsm/r_curr_state
add wave -noupdate -group SDC -expand -group {SDC FSMs} -color Gold -label {dat fsm} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/my_sd_dat_fsm/r_curr_state
add wave -noupdate -group SDC -expand -group {SDC FSMs} -color Gold -label {clk fsm} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/my_clk_fsm/r_curr_state
add wave -noupdate -group SDC -expand -group registers /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/CLKDiv
add wave -noupdate -group SDC -expand -group registers /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/Command
add wave -noupdate -group SDC -expand -group registers -color {Medium Orchid} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/Status
add wave -noupdate -group SDC -expand -group registers /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/Address
add wave -noupdate -group SDC -group {AHBLite interface} -color Aquamarine /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HSELSDC
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HADDR
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HADDRDelay
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HWRITE
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HREADY
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HTRANS
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HWDATA
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HREADSDC
add wave -noupdate -group SDC -group {AHBLite interface} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HRESPSDC
add wave -noupdate -group SDC -group {AHBLite interface} -color Goldenrod /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HREADYSDC
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/InitTrans
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/o_ERROR_CODE_Q
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/o_DATA_VALID
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/ReadData
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/WordCount
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/HREADSDC
add wave -noupdate -group SDC /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/o_READY_FOR_READ
add wave -noupdate -group SDC -group {Instruction Counter control} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/w_IC_EN
add wave -noupdate -group SDC -group {Instruction Counter control} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/w_IC_RST
add wave -noupdate -group SDC -group {Instruction Counter control} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/w_IC_UP_DOWN
add wave -noupdate -group SDC -group {Instruction Counter control} /testbench/dut/wallypipelinedsoc/uncore/sdc/SDC/sd_top/r_IC_OUT
add wave -noupdate -group boottim /testbench/dut/wallypipelinedsoc/uncore/bootdtim/bootdtim/HADDR
add wave -noupdate -group boottim /testbench/dut/wallypipelinedsoc/uncore/bootdtim/bootdtim/A
add wave -noupdate -group boottim /testbench/dut/wallypipelinedsoc/uncore/bootdtim/bootdtim/HWADDR
add wave -noupdate -group boottim /testbench/dut/wallypipelinedsoc/uncore/bootdtim/bootdtim/HSELTim
add wave -noupdate -group boottim /testbench/dut/wallypipelinedsoc/uncore/bootdtim/bootdtim/HREADYTim
add wave -noupdate -group boottim /testbench/dut/wallypipelinedsoc/uncore/bootdtim/bootdtim/HRESPTim
add wave -noupdate -group boottim /testbench/dut/wallypipelinedsoc/uncore/bootdtim/bootdtim/initTrans
add wave -noupdate /testbench/dut/wallypipelinedsoc/uncore/HSELRegions
add wave -noupdate /testbench/dut/wallypipelinedsoc/uncore/HSELDDR4
add wave -noupdate /testbench/dtim/HSELTim
add wave -noupdate /testbench/dut/wallypipelinedsoc/uncore/HRDATAEXT
add wave -noupdate /testbench/dut/wallypipelinedsoc/uncore/HREADYEXT
add wave -noupdate /testbench/dut/wallypipelinedsoc/uncore/HRESPEXT
add wave -noupdate /testbench/dut/wallypipelinedsoc/uncore/HSELEXT
add wave -noupdate /testbench/dtim/HCLK
add wave -noupdate /testbench/dtim/HRESETn
add wave -noupdate /testbench/dtim/HSELTim
add wave -noupdate /testbench/dtim/HADDR
add wave -noupdate /testbench/dtim/HWRITE
add wave -noupdate /testbench/dtim/HREADY
add wave -noupdate /testbench/dtim/HTRANS
add wave -noupdate /testbench/dtim/HWDATA
add wave -noupdate /testbench/dtim/HREADTim
add wave -noupdate /testbench/dtim/HRESPTim
add wave -noupdate /testbench/dtim/HREADYTim
TreeUpdate [SetDefaultTree]
WaveRestoreCursors {{Cursor 6} {1090427 ns} 1} {{Cursor 3} {1157417 ns} 1} {{Cursor 4} {2324620 ns} 0}
quietly wave cursor active 3
configure wave -namecolwidth 250
configure wave -valuecolwidth 297
configure wave -justifyvalue left
configure wave -signalnamewidth 1
configure wave -snapdistance 10
configure wave -datasetprefix 0
configure wave -rowmargin 4
configure wave -childrowmargin 2
configure wave -gridoffset 0
configure wave -gridperiod 1
configure wave -griddelta 40
configure wave -timeline 0
configure wave -timelineunits ns
update
WaveRestoreZoom {2324497 ns} {2324741 ns}

View file

@ -0,0 +1,56 @@
# wally-pipelined.do
#
# Modification by Oklahoma State University & Harvey Mudd College
# Use with Testbench
# James Stine, 2008; David Harris 2021
# Go Cowboys!!!!!!
#
# Takes 1:10 to run RV64IC tests using gui
# Use this wally-pipelined.do file to run this example.
# Either bring up ModelSim and type the following at the "ModelSim>" prompt:
# do wally-pipelined.do
# or, to run from a shell, type the following at the shell prompt:
# vsim -do wally-pipelined.do -c
# (omit the "-c" to see the GUI while running from the shell)
onbreak {resume}
# create library
if [file exists work] {
vdel -all
}
vlib work
# compile source files
# suppress spurious warnngs about
# "Extra checking for conflicts with always_comb done at vopt time"
# because vsim will run vopt
# default to config/rv64ic, but allow this to be overridden at the command line. For example:
# do wally-pipelined.do ../config/rv32ic
switch $argc {
0 {vlog +incdir+../config/fpga +incdir+../config/shared ../testbench/testbench-fpga.sv ../testbench/common/*.sv ../src/*/*.sv ../src/*/*/*.sv ../src/wally/wallypipelinedsocwrapper.v ../../fpga/sim/*.sv -suppress 2583}
1 {vlog +incdir+$1 +incdir+../config/shared ../testbench/testbench-imperas.sv ../testbench/common/*.sv ../src/*/*.sv -suppress 2583}
}
# start and run simulation
# remove +acc flag for faster sim during regressions if there is no need to access internal signals
vopt -fsmdebug +acc -gDEBUG=1 work.testbench -o workopt
vsim workopt -fsmdebug
#profile on
do fpga-wave.do
add log -r /*
#add wave /testbench/dtim/RAM[268435456]
#add wave /testbench/dtim/RAM[268435457]
#add wave /testbench/dtim/RAM[268435458]
#add wave /testbench/dtim/RAM[268435459]
#add wave /testbench/dtim/RAM[268435460]
#add wave /testbench/dtim/RAM[268435461]
#xadd wave /testbench/dtim/RAM[268435462]
-- Run the Simulation
#run 1000
run -all
#quit

View file

@ -4,116 +4,115 @@ add wave -noupdate /testbench/clk
add wave -noupdate /testbench/reset
add wave -noupdate /testbench/test
add wave -noupdate /testbench/memfilename
add wave -noupdate /testbench/dut/hart/SATP_REGW
add wave -noupdate -expand -group {Execution Stage} /testbench/FunctionName/FunctionName/FunctionName
add wave -noupdate -expand -group {Execution Stage} /testbench/dut/hart/ifu/PCE
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/SATP_REGW
add wave -noupdate -expand -group {Execution Stage} /testbench/dut/wallypipelinedsoc/hart/ifu/PCE
add wave -noupdate -expand -group {Execution Stage} /testbench/InstrEName
add wave -noupdate -expand -group {Execution Stage} /testbench/dut/hart/ifu/InstrE
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/hart/priv/trap/InstrValidM
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/hart/PCM
add wave -noupdate -expand -group {Execution Stage} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrE
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrValidM
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/PCM
add wave -noupdate -expand -group {Memory Stage} /testbench/InstrMName
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/hart/InstrM
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/hart/lsu/MemAdrM
add wave -noupdate /testbench/dut/hart/ieu/dp/ResultM
add wave -noupdate /testbench/dut/hart/ieu/dp/ResultW
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InstrMisalignedFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InstrAccessFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/IllegalInstrFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/BreakpointFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/LoadMisalignedFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/StoreMisalignedFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/LoadAccessFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/StoreAccessFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/EcallFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InstrPageFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/LoadPageFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/StorePageFaultM
add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InterruptM
add wave -noupdate -expand -group HDU -group interrupts /testbench/dut/hart/priv/trap/PendingIntsM
add wave -noupdate -expand -group HDU -group interrupts /testbench/dut/hart/priv/trap/CommittedM
add wave -noupdate -expand -group HDU -group interrupts /testbench/dut/hart/priv/trap/InstrValidM
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/BPPredWrongE
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/CSRWritePendingDEM
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/RetM
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/TrapM
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/LoadStallD
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/StoreStallD
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/ICacheStallF
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/hzu/LSUStall
add wave -noupdate -expand -group HDU -group hazards /testbench/dut/hart/MulDivStallD
add wave -noupdate -expand -group HDU -expand -group Flush -color Yellow /testbench/dut/hart/hzu/FlushF
add wave -noupdate -expand -group HDU -expand -group Flush -color Yellow /testbench/dut/hart/FlushD
add wave -noupdate -expand -group HDU -expand -group Flush -color Yellow /testbench/dut/hart/FlushE
add wave -noupdate -expand -group HDU -expand -group Flush -color Yellow /testbench/dut/hart/FlushM
add wave -noupdate -expand -group HDU -expand -group Flush -color Yellow /testbench/dut/hart/FlushW
add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallF
add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallD
add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallE
add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallM
add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallW
add wave -noupdate -group Bpred -color Orange /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHR
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPPredF
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/InstrClassE[0]}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPInstrClassE[0]}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPPredDirWrongE
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/InstrM
add wave -noupdate -expand -group {Memory Stage} /testbench/dut/wallypipelinedsoc/hart/lsu/MemAdrM
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ResultM
add wave -noupdate /testbench/dut/wallypipelinedsoc/hart/ieu/dp/ResultW
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrMisalignedFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrAccessFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/IllegalInstrFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/BreakpointFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/LoadMisalignedFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/StoreMisalignedFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/LoadAccessFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/StoreAccessFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/EcallFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrPageFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/LoadPageFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/StorePageFaultM
add wave -noupdate -group HDU -group traps /testbench/dut/wallypipelinedsoc/hart/priv/trap/InterruptM
add wave -noupdate -group HDU -group interrupts /testbench/dut/wallypipelinedsoc/hart/priv/trap/PendingIntsM
add wave -noupdate -group HDU -group interrupts /testbench/dut/wallypipelinedsoc/hart/priv/trap/CommittedM
add wave -noupdate -group HDU -group interrupts /testbench/dut/wallypipelinedsoc/hart/priv/trap/InstrValidM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/BPPredWrongE
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/CSRWritePendingDEM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/RetM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/TrapM
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/LoadStallD
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/StoreStallD
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/ICacheStallF
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/hzu/LSUStall
add wave -noupdate -group HDU -group hazards /testbench/dut/wallypipelinedsoc/hart/MulDivStallD
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/hzu/FlushF
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushD
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushE
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushM
add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/wallypipelinedsoc/hart/FlushW
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallF
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallD
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallE
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallM
add wave -noupdate -group HDU -group Stall -color Orange /testbench/dut/wallypipelinedsoc/hart/StallW
add wave -noupdate -group Bpred -color Orange /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHR
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPPredF
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/InstrClassE[0]}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPInstrClassE[0]}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPPredDirWrongE
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} -divider {class check}
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightNonCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassWrongCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassWrongNonCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightBPRight
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightBPWrong
add wave -noupdate -group Bpred -radix hexadecimal -childformat {{{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[6]} -radix binary} {{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[5]} -radix binary} {{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[4]} -radix binary} {{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[3]} -radix binary} {{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[2]} -radix binary} {{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[1]} -radix binary} {{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[0]} -radix binary}} -subitemconfig {{/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[6]} {-height 16 -radix binary} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[5]} {-height 16 -radix binary} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[4]} {-height 16 -radix binary} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[3]} {-height 16 -radix binary} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[2]} {-height 16 -radix binary} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[1]} {-height 16 -radix binary} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[0]} {-height 16 -radix binary}} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel
add wave -noupdate -group Bpred /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRNext
add wave -noupdate -group Bpred /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRUpdateEN
add wave -noupdate -group Bpred /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr
add wave -noupdate -group Bpred /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr0
add wave -noupdate -group Bpred /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr1
add wave -noupdate -group Bpred /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateEN
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRLookup
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PCNextF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHT/RA1
add wave -noupdate -group Bpred -expand -group prediction -radix binary /testbench/dut/hart/ifu/bpred/bpred/BPPredF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/BTBValidF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/BPInstrClassF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/BTBPredPCF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/RASPCF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/TargetPredictor/LookUpPCIndex
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/hart/ifu/bpred/bpred/TargetPredictor/TargetPC
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex -radix binary /testbench/dut/hart/ifu/bpred/bpred/BPPredE
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex /testbench/dut/hart/ifu/bpred/bpred/PCSrcE
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex /testbench/dut/hart/ifu/bpred/bpred/BPPredDirWrongE
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/hart/ifu/bpred/bpred/TargetPredictor/UpdatePCIndex
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/hart/ifu/bpred/bpred/TargetPredictor/UpdateTarget
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/hart/ifu/bpred/bpred/TargetPredictor/UpdateEN
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/hart/ifu/bpred/bpred/TargetPredictor/UpdatePC
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/hart/ifu/bpred/bpred/TargetPredictor/UpdateTarget
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PCE
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHT/WA1
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/hart/ifu/bpred/bpred/TargetWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/hart/ifu/bpred/bpred/FallThroughWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/hart/ifu/bpred/bpred/PredictionPCWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/hart/ifu/bpred/bpred/InstrClassE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/hart/ifu/bpred/bpred/PredictionInstrClassWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/hart/ifu/bpred/bpred/BPPredClassNonCFIWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/hart/ifu/bpred/bpred/BPPredWrongE
add wave -noupdate -group Bpred /testbench/dut/hart/ifu/bpred/bpred/BPPredWrongE
add wave -noupdate -expand -group {instruction pipeline} /testbench/InstrFName
add wave -noupdate -expand -group {instruction pipeline} /testbench/dut/hart/ifu/icache/FinalInstrRawF
add wave -noupdate -expand -group {instruction pipeline} /testbench/dut/hart/ifu/InstrD
add wave -noupdate -expand -group {instruction pipeline} /testbench/dut/hart/ifu/InstrE
add wave -noupdate -expand -group {instruction pipeline} /testbench/dut/hart/ifu/InstrM
add wave -noupdate -expand -group {instruction pipeline} /testbench/InstrW
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/PCNextF
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/PCF
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/PCPlus2or4F
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/BPPredPCF
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/PCNext0F
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/PCNext1F
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/SelBPPredF
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/BPPredWrongE
add wave -noupdate -group {PCNext Generation} /testbench/dut/hart/ifu/PrivilegedChangePCM
add wave -noupdate -group {Decode Stage} /testbench/dut/hart/ifu/InstrD
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightNonCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassWrongCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassWrongNonCFI
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightBPRight
add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPClassRightBPWrong
add wave -noupdate -group Bpred -radix hexadecimal -childformat {{{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[6]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[5]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[4]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[3]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[2]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[1]} -radix binary} {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[0]} -radix binary}} -subitemconfig {{/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[6]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[5]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[4]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[3]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[2]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[1]} {-height 16 -radix binary} {/testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel[0]} {-height 16 -radix binary}} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRMuxSel
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRNext
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRUpdateEN
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr0
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr1
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateEN
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHRLookup
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PCNextF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHT/RA1
add wave -noupdate -group Bpred -expand -group prediction -radix binary /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BTBValidF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPInstrClassF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BTBPredPCF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/RASPCF
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/LookUpPCIndex
add wave -noupdate -group Bpred -expand -group prediction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/TargetPC
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex -radix binary /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredE
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/PCSrcE
add wave -noupdate -group Bpred -expand -group prediction -expand -group ex /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredDirWrongE
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdatePCIndex
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdateTarget
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdateEN
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdatePC
add wave -noupdate -group Bpred -expand -group update -expand -group BTB /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetPredictor/UpdateTarget
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHTUpdateAdr
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PCE
add wave -noupdate -group Bpred -expand -group update -expand -group direction /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/Predictor/DirPredictor/PHT/WA1
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/TargetWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/FallThroughWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/PredictionPCWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/InstrClassE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/PredictionInstrClassWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredClassNonCFIWrongE
add wave -noupdate -group Bpred -expand -group {bp wrong} /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredWrongE
add wave -noupdate -group Bpred /testbench/dut/wallypipelinedsoc/hart/ifu/bpred/bpred/BPPredWrongE
add wave -noupdate -group {instruction pipeline} /testbench/InstrFName
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/icache/FinalInstrRawF
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrD
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrE
add wave -noupdate -group {instruction pipeline} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrM
add wave -noupdate -group {instruction pipeline} /testbench/InstrW
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCNextF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCPlus2or4F
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/BPPredPCF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCNext0F
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PCNext1F
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/SelBPPredF
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/BPPredWrongE
add wave -noupdate -group {PCNext Generation} /testbench/dut/wallypipelinedsoc/hart/ifu/PrivilegedChangePCM
add wave -noupdate -group {Decode Stage} /testbench/dut/wallypipelinedsoc/hart/ifu/InstrD
add wave -noupdate -group {Decode Stage} /testbench/InstrDName
add wave -noupdate -group {Decode Stage} /testbench/dut/hart/ieu/c/RegWriteD
add wave -noupdate -group {Decode Stage} /testbench/dut/hart/ieu/dp/RdD
@ -536,7 +535,7 @@ add wave -noupdate /testbench/dut/hart/ifu/icache/PCTagF
add wave -noupdate /testbench/dut/hart/ifu/icache/PCPSpillF
add wave -noupdate /testbench/dut/hart/ifu/icache/ICacheReadEn
TreeUpdate [SetDefaultTree]
WaveRestoreCursors {{Cursor 6} {122378 ns} 0}
WaveRestoreCursors {{Cursor 6} {598422 ns} 0} {{Cursor 3} {603500 ns} 1}
quietly wave cursor active 1
configure wave -namecolwidth 250
configure wave -valuecolwidth 297
@ -552,4 +551,4 @@ configure wave -griddelta 40
configure wave -timeline 0
configure wave -timelineunits ns
update
WaveRestoreZoom {122227 ns} {122479 ns}
WaveRestoreZoom {209690 ns} {1301658 ns}

View file

@ -61,13 +61,13 @@ module dcache
input logic WalkerPageFaultM,
output logic MemAfterIWalkDone,
// ahb side
output logic [`PA_BITS-1:0] AHBPAdr, // to ahb
output logic AHBRead,
output logic AHBWrite,
input logic AHBAck, // from ahb
input logic [`XLEN-1:0] HRDATA, // from ahb
output logic [`XLEN-1:0] HWDATA, // to ahb
output logic [2:0] DCtoAHBSizeM
(* mark_debug = "true" *)output logic [`PA_BITS-1:0] AHBPAdr, // to ahb
(* mark_debug = "true" *)output logic AHBRead,
(* mark_debug = "true" *)output logic AHBWrite,
(* mark_debug = "true" *)input logic AHBAck, // from ahb
(* mark_debug = "true" *)input logic [`XLEN-1:0] HRDATA, // from ahb
(* mark_debug = "true" *)output logic [`XLEN-1:0] HWDATA, // to ahb
(* mark_debug = "true" *)output logic [2:0] DCtoAHBSizeM
);
localparam integer BLOCKLEN = `DCACHE_BLOCKLENINBITS;
@ -141,7 +141,7 @@ module dcache
logic SelEvict;
logic LRUWriteEn;
logic [NUMWAYS-1:0] VDWriteEnableWay;
// Read Path CPU (IEU) side
@ -331,7 +331,7 @@ module dcache
.d(NextFlushWay),
.q(FlushWay));
assign VDWriteEnableWay = FlushWay & {NUMWAYS{VDWriteEnable}};
assign VDWriteEnableWay = FlushWay & {NUMWAYS{VDWriteEnable}};
assign NextFlushWay = {FlushWay[NUMWAYS-2:0], FlushWay[NUMWAYS-1]};

View file

@ -138,7 +138,7 @@ module dcachefsm
STATE_FLUSH_WRITE_BACK,
STATE_FLUSH_CLEAR_DIRTY} statetype;
statetype CurrState, NextState;
(* mark_debug = "true" *) statetype CurrState, NextState;
assign AnyCPUReqM = |MemRWM | (|AtomicM);
assign CntEn = PreCntEn & AHBAck;

View file

@ -55,7 +55,7 @@ module fsm_fpdiv (
current_state = next_state;
end
always @(*)
always_comb
begin
case(current_state)
S0: // iteration 0

View file

@ -0,0 +1,51 @@
///////////////////////////////////////////
// arrs.sv
//
// Written: Ross Thompson ross1728@gmail.com
// Modified: November 12, 2021
//
// Purpose: resets are typically asynchronous but need to be synchronized to
// a clock to prevent changing in the invalid window clock edge.
// arrs takes in the asynchronous reset and outputs an asynchronous
// rising edge, but then syncs the falling edge to the posedge clk.
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module arrs
(input logic clk,
input logic areset,
output logic reset);
logic metaStable;
logic resetB;
always_ff @(posedge clk , posedge areset) begin
if(areset) begin
metaStable <= 1'b0;
resetB <= 1'b0;
end else begin
metaStable <= 1'b1;
resetB <= metaStable;
end
end
assign reset = ~resetB;
endmodule

View file

@ -31,18 +31,26 @@ module clockgater
input logic CLK,
output logic ECLK);
// VERY IMPORTANT.
// This part functionally models a clock gater, but does not necessarily meet the timing constrains a real standard cell would.
// Do not use this in synthesis!
logic enable_q;
always_latch begin
if(~CLK) begin
enable_q <= E | SE;
if (`FPGA) begin
BUFGCE bufgce_i0 (
.I(CLK),
.CE(E | SE),
.O(ECLK)
);
end else begin
// *** BUG
// VERY IMPORTANT.
// This part functionally models a clock gater, but does not necessarily meet the timing constrains a real standard cell would.
// Do not use this in synthesis!
logic enable_q;
always_latch begin
if(~CLK) begin
enable_q <= E | SE;
end
end
end
assign ECLK = enable_q & CLK;
assign ECLK = enable_q & CLK;
end
endmodule

View file

@ -30,19 +30,22 @@ module adrdecs (
input logic [`PA_BITS-1:0] PhysicalAddress,
input logic AccessRW, AccessRX, AccessRWX,
input logic [1:0] Size,
output logic [6:0] SelRegions
output logic [8:0] SelRegions
);
// Determine which region of physical memory (if any) is being accessed
// *** eventually uncomment Access signals
adrdec boottimdec(PhysicalAddress, `BOOTTIM_BASE, `BOOTTIM_RANGE, `BOOTTIM_SUPPORTED, /*1'b1*/AccessRX, Size, 4'b1111, SelRegions[5]);
adrdec timdec(PhysicalAddress, `TIM_BASE, `TIM_RANGE, `TIM_SUPPORTED, /*1'b1*/AccessRWX, Size, 4'b1111, SelRegions[4]);
adrdec clintdec(PhysicalAddress, `CLINT_BASE, `CLINT_RANGE, `CLINT_SUPPORTED, AccessRW, Size, 4'b1111, SelRegions[3]);
adrdec gpiodec(PhysicalAddress, `GPIO_BASE, `GPIO_RANGE, `GPIO_SUPPORTED, AccessRW, Size, 4'b0100, SelRegions[2]);
adrdec uartdec(PhysicalAddress, `UART_BASE, `UART_RANGE, `UART_SUPPORTED, AccessRW, Size, 4'b0001, SelRegions[1]);
adrdec plicdec(PhysicalAddress, `PLIC_BASE, `PLIC_RANGE, `PLIC_SUPPORTED, AccessRW, Size, 4'b0100, SelRegions[0]);
adrdec ddr4dec(PhysicalAddress, `EXT_MEM_BASE, `EXT_MEM_RANGE, `EXT_MEM_SUPPORTED, AccessRWX, Size, 4'b1111, SelRegions[7]);
adrdec boottimdec(PhysicalAddress, `BOOTTIM_BASE, `BOOTTIM_RANGE, `BOOTTIM_SUPPORTED, /*1'b1*/AccessRX, Size, 4'b1111, SelRegions[6]);
adrdec timdec(PhysicalAddress, `TIM_BASE, `TIM_RANGE, `TIM_SUPPORTED, /*1'b1*/AccessRWX, Size, 4'b1111, SelRegions[5]);
assign SelRegions[6] = ~|(SelRegions[5:0]);
adrdec clintdec(PhysicalAddress, `CLINT_BASE, `CLINT_RANGE, `CLINT_SUPPORTED, AccessRW, Size, 4'b1111, SelRegions[4]);
adrdec gpiodec(PhysicalAddress, `GPIO_BASE, `GPIO_RANGE, `GPIO_SUPPORTED, AccessRW, Size, 4'b0100, SelRegions[3]);
adrdec uartdec(PhysicalAddress, `UART_BASE, `UART_RANGE, `UART_SUPPORTED, AccessRW, Size, 4'b0001, SelRegions[2]);
adrdec plicdec(PhysicalAddress, `PLIC_BASE, `PLIC_RANGE, `PLIC_SUPPORTED, AccessRW, Size, 4'b0100, SelRegions[1]);
adrdec sdcdec(PhysicalAddress, `SDC_BASE, `SDC_RANGE, `SDC_SUPPORTED, AccessRW, Size, 4'b1100, SelRegions[0]);
assign SelRegions[8] = ~|(SelRegions[7:0]);
endmodule

View file

@ -41,7 +41,7 @@ module pmachecker (
logic PMAAccessFault;
logic AccessRW, AccessRWX, AccessRX;
logic [6:0] SelRegions;
logic [8:0] SelRegions;
// Determine what type of access is being made
assign AccessRW = ReadAccessM | WriteAccessM;
@ -52,12 +52,13 @@ module pmachecker (
adrdecs adrdecs(PhysicalAddress, AccessRW, AccessRX, AccessRWX, Size, SelRegions);
// Only RAM memory regions are cacheable
assign Cacheable = SelRegions[5] | SelRegions[4];
assign Idempotent = SelRegions[4];
assign AtomicAllowed = SelRegions[4];
// *** Ross Thompson fix these. They should be part of adrdec
assign Cacheable = SelRegions[7] | SelRegions[6] | SelRegions[5];
assign Idempotent = SelRegions[7] | SelRegions[5];
assign AtomicAllowed = SelRegions[7] | SelRegions[5];
// Detect access faults
assign PMAAccessFault = SelRegions[6] & AccessRWX;
assign PMAAccessFault = SelRegions[8] & AccessRWX;
assign PMAInstrAccessFaultF = ExecuteAccessF && PMAAccessFault;
assign PMALoadAccessFaultM = ReadAccessM && PMAAccessFault;
assign PMAStoreAccessFaultM = WriteAccessM && PMAAccessFault;

View file

@ -64,27 +64,28 @@ module csrm #(parameter
MEDELEG_MASK = ~(ZERO | `XLEN'b1 << 11),
MIDELEG_MASK = {{(`XLEN-12){1'b0}}, 12'h222}
) (
input logic clk, reset,
input logic StallW,
input logic CSRMWriteM, MTrapM,
input logic [11:0] CSRAdrM,
input logic [`XLEN-1:0] NextEPCM, NextCauseM, NextMtvalM, MSTATUS_REGW,
input logic [`XLEN-1:0] CSRWriteValM,
output logic [`XLEN-1:0] CSRMReadValM, MEPC_REGW, MTVEC_REGW,
input logic clk, reset,
input logic StallW,
input logic CSRMWriteM, MTrapM,
input logic [11:0] CSRAdrM,
input logic [`XLEN-1:0] NextEPCM, NextCauseM, NextMtvalM, MSTATUS_REGW,
input logic [`XLEN-1:0] CSRWriteValM,
output logic [`XLEN-1:0] CSRMReadValM, MTVEC_REGW,
(* mark_debug = "true" *) output logic [`XLEN-1:0] MEPC_REGW,
output logic [31:0] MCOUNTEREN_REGW, MCOUNTINHIBIT_REGW,
output logic [`XLEN-1:0] MEDELEG_REGW, MIDELEG_REGW,
output logic [`XLEN-1:0] MEDELEG_REGW, MIDELEG_REGW,
// 64-bit registers in RV64, or two 32-bit registers in RV32
//output var logic [63:0] PMPCFG_ARRAY_REGW[`PMP_ENTRIES/8-1:0],
output var logic [7:0] PMPCFG_ARRAY_REGW[`PMP_ENTRIES-1:0],
output var logic [`XLEN-1:0] PMPADDR_ARRAY_REGW [`PMP_ENTRIES-1:0],
input logic [11:0] MIP_REGW, MIE_REGW,
output logic WriteMSTATUSM,
output logic IllegalCSRMAccessM, IllegalCSRMWriteReadonlyM
output var logic [7:0] PMPCFG_ARRAY_REGW[`PMP_ENTRIES-1:0],
output var logic [`XLEN-1:0] PMPADDR_ARRAY_REGW [`PMP_ENTRIES-1:0],
(* mark_debug = "true" *) input logic [11:0] MIP_REGW, MIE_REGW,
output logic WriteMSTATUSM,
output logic IllegalCSRMAccessM, IllegalCSRMWriteReadonlyM
);
logic [`XLEN-1:0] MISA_REGW, MHARTID_REGW;
logic [`XLEN-1:0] MSCRATCH_REGW, MCAUSE_REGW, MTVAL_REGW;
logic [`XLEN-1:0] MSCRATCH_REGW;
(* mark_debug = "true" *) logic [`XLEN-1:0] MCAUSE_REGW, MTVAL_REGW;
logic WriteMTVECM, WriteMEDELEGM, WriteMIDELEGM;
logic WriteMSCRATCHM, WriteMEPCM, WriteMCAUSEM, WriteMTVALM;
logic WriteMCOUNTERENM, WriteMCOUNTINHIBITM;

View file

@ -46,21 +46,22 @@ module csrs #(parameter
SEDELEG_MASK = ~(ZERO | `XLEN'b111 << 9)
) (
input logic clk, reset,
input logic StallW,
input logic CSRSWriteM, STrapM,
input logic [11:0] CSRAdrM,
input logic [`XLEN-1:0] NextEPCM, NextCauseM, NextMtvalM, SSTATUS_REGW,
input logic STATUS_TVM,
input logic [`XLEN-1:0] CSRWriteValM,
input logic [1:0] PrivilegeModeW,
output logic [`XLEN-1:0] CSRSReadValM, SEPC_REGW, STVEC_REGW,
output logic [31:0] SCOUNTEREN_REGW,
output logic [`XLEN-1:0] SEDELEG_REGW, SIDELEG_REGW,
input logic clk, reset,
input logic StallW,
input logic CSRSWriteM, STrapM,
input logic [11:0] CSRAdrM,
input logic [`XLEN-1:0] NextEPCM, NextCauseM, NextMtvalM, SSTATUS_REGW,
input logic STATUS_TVM,
input logic [`XLEN-1:0] CSRWriteValM,
input logic [1:0] PrivilegeModeW,
output logic [`XLEN-1:0] CSRSReadValM, STVEC_REGW,
(* mark_debug = "true" *) output logic [`XLEN-1:0] SEPC_REGW,
output logic [31:0] SCOUNTEREN_REGW,
output logic [`XLEN-1:0] SEDELEG_REGW, SIDELEG_REGW,
output logic [`XLEN-1:0] SATP_REGW,
input logic [11:0] SIP_REGW, SIE_REGW,
output logic WriteSSTATUSM,
output logic IllegalCSRSAccessM
(* mark_debug = "true" *) input logic [11:0] SIP_REGW, SIE_REGW,
output logic WriteSSTATUSM,
output logic IllegalCSRSAccessM
);
//logic [`XLEN-1:0] zero = 0;
@ -73,7 +74,8 @@ module csrs #(parameter
logic WriteSTVECM;
logic WriteSSCRATCHM, WriteSEPCM;
logic WriteSCAUSEM, WriteSTVALM, WriteSATPM, WriteSCOUNTERENM;
logic [`XLEN-1:0] SSCRATCH_REGW, SCAUSE_REGW, STVAL_REGW;
logic [`XLEN-1:0] SSCRATCH_REGW, STVAL_REGW;
(* mark_debug = "true" *) logic [`XLEN-1:0] SCAUSE_REGW;
assign WriteSSTATUSM = CSRSWriteM && (CSRAdrM == SSTATUS) && ~StallW;
assign WriteSTVECM = CSRSWriteM && (CSRAdrM == STVEC) && ~StallW;

View file

@ -27,15 +27,16 @@
`include "wally-config.vh"
module trap (
input logic clk,
input logic reset,
input logic InstrMisalignedFaultM, InstrAccessFaultM, IllegalInstrFaultM,
input logic BreakpointFaultM, LoadMisalignedFaultM, StoreMisalignedFaultM,
input logic LoadAccessFaultM, StoreAccessFaultM, EcallFaultM, InstrPageFaultM,
input logic LoadPageFaultM, StorePageFaultM,
input logic mretM, sretM, uretM,
(* mark_debug = "true" *) input logic InstrMisalignedFaultM, InstrAccessFaultM, IllegalInstrFaultM,
(* mark_debug = "true" *) input logic BreakpointFaultM, LoadMisalignedFaultM, StoreMisalignedFaultM,
(* mark_debug = "true" *) input logic LoadAccessFaultM, StoreAccessFaultM, EcallFaultM, InstrPageFaultM,
(* mark_debug = "true" *) input logic LoadPageFaultM, StorePageFaultM,
(* mark_debug = "true" *) input logic mretM, sretM, uretM,
input logic [1:0] PrivilegeModeW, NextPrivilegeModeM,
input logic [`XLEN-1:0] MEPC_REGW, SEPC_REGW, UEPC_REGW, UTVEC_REGW, STVEC_REGW, MTVEC_REGW,
input logic [11:0] MIP_REGW, MIE_REGW, SIP_REGW, SIE_REGW,
(* mark_debug = "true" *) input logic [`XLEN-1:0] MEPC_REGW, SEPC_REGW, UEPC_REGW, UTVEC_REGW, STVEC_REGW, MTVEC_REGW,
(* mark_debug = "true" *) input logic [11:0] MIP_REGW, MIE_REGW, SIP_REGW, SIE_REGW,
input logic STATUS_MIE, STATUS_SIE,
input logic [`XLEN-1:0] PCM,
input logic [`XLEN-1:0] InstrMisalignedAdrM, MemAdrM,
@ -52,7 +53,7 @@ module trap (
);
logic MIntGlobalEnM, SIntGlobalEnM;
logic [11:0] PendingIntsM;
(* mark_debug = "true" *) logic [11:0] PendingIntsM;
//logic InterruptM;
logic [`XLEN-1:0] PrivilegedTrapVector, PrivilegedVectoredTrapVector;
logic Exception1M;

View file

@ -0,0 +1,359 @@
///////////////////////////////////////////
// SDC.sv
//
// Written: Ross Thompson September 22, 2021
// Modified:
//
// Purpose: SDC interface to AHBLite BUS.
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
`define SDCCLKDIV -8'd2
module SDC
(input logic HCLK,
input logic HRESETn,
input logic HSELSDC,
input logic [4:0] HADDR,
input logic HWRITE,
input logic HREADY,
input logic [1:0] HTRANS,
input logic [`XLEN-1:0] HWDATA,
output logic [`XLEN-1:0] HREADSDC,
output logic HRESPSDC,
output logic HREADYSDC,
//sd card interface
// place the tristate drivers at the top. this level
// will use dedicated 1 direction ports.
output logic SDCCmdOut,
input logic SDCCmdIn,
output logic SDCCmdOE,
input logic [3:0] SDCDatIn,
output logic SDCCLK,
// interrupt to PLIC
output logic SDCIntM);
logic InitTrans;
logic RegRead;
logic RegWrite;
logic [4:0] HADDRDelay;
// Register outputs
logic [7:0] CLKDiv;
logic [2:0] Command;
logic [63:9] Address;
logic SDCDone;
logic [2:0] ErrorCode;
logic InvalidCommand;
logic SDCBusy;
logic StartCLKDivUpdate;
logic CLKDivUpdateEn;
logic SDCCLKEN;
logic CLKGate;
logic SDCCLKIn;
logic SDCDataValid;
logic [`XLEN-1:0] SDCReadData;
logic [`XLEN-1:0] SDCReadDataPreNibbleSwap;
logic [`XLEN-1:0] SDCWriteData;
logic FatalError;
logic [4095:0] ReadData512Byte;
logic [`XLEN-1:0] ReadData512ByteWords [4096/`XLEN-1:0] ;
logic SDCInitialized;
logic SDCRestarting;
logic SDCLast;
logic [$clog2(4096/`XLEN)-1:0] WordCount;
logic WordCountRst;
logic [5:0] Status;
logic CommandCompleted;
logic ReadDone;
genvar index;
assign HRESPSDC = 1'b0;
// registers
//| Offset | Name | Size | Purpose |
//|--------+---------+--------+------------------------------------------------|
//| 0x0 | CLKDiv | 4 | Divide HCLK to produce SDCLK |
//| 0x4 | Status | 4 | Provide status to software |
//| 0x8 | Control | 4 | Send commands to SDC |
//| 0xC | Size | 4 | Size of data command (only 512 byte supported) |
//| 0x10 | address | 8 | address of operation |
//| 0x18 | data | XLEN/8 | Data Bus interface |
// Status contains
// Status[0] initialized
// Status[1] Busy on read
// Status[2] invalid command
// Status[5:3] error code
// control contains 3 bit command
// control[2:0]
// 000 nop op
// xx1 initialize
// 010 Write no implemented
// 100 Read
// 110 Atomic read/write not implemented
// size is fixed to 512. Read only
// Currently using a mailbox style interface. Data is passed through the Data register (0x10)
// The card will support 3 operations
// 1. initialize
// 2. read
// 3. write
// all read and write operations will occur on 512 bytes (4096 bits) of data
// starting at the 512 byte aligned address in the address register This register
// is the byte address.
// currently does not support writes
assign InitTrans = HREADY & HSELSDC & (HTRANS != 2'b00);
//assign RegRead = InitTrans & ~HWRITE;
// register resolve combo loop
flopr #(1) RegReadReg(HCLK, ~HRESETn, InitTrans & ~HWRITE, RegRead);
// AHBLite Spec has write data 1 cycle after write command
flopr #(1) RegWriteReg(HCLK, ~HRESETn, InitTrans & HWRITE, RegWrite);
flopenr #(5) HADDRReg(HCLK, ~HRESETn, InitTrans, HADDR, HADDRDelay);
assign StartCLKDivUpdate = HADDRDelay == '0 & RegWrite;
flopenl #(8) CLKDivReg(HCLK, ~HRESETn, CLKDivUpdateEn, HWDATA[7:0], `SDCCLKDIV, CLKDiv);
// Control reg
flopenl #(3) CommandReg(HCLK, ~HRESETn, (HADDRDelay == 'h8 & RegWrite) | (CommandCompleted),
CommandCompleted ? '0 : HWDATA[2:0], '0, Command);
generate
if (`XLEN == 64) begin
flopenr #(64-9) AddressReg(HCLK, ~HRESETn, (HADDRDelay == 'h10 & RegWrite),
HWDATA[`XLEN-1:9], Address);
end else begin
flopenr #(32-9) AddressLowReg(HCLK, ~HRESETn, (HADDRDelay == 'h10 & RegWrite),
HWDATA[`XLEN-1:9], Address[31:9]);
flopenr #(32) AddressHighReg(HCLK, ~HRESETn, (HADDRDelay == 'h14 & RegWrite),
HWDATA, Address[63:32]);
end
endgenerate
flopen #(`XLEN) DataReg(HCLK, (HADDRDelay == 'h18 & RegWrite),
HWDATA, SDCWriteData);
assign InvalidCommand = (Command[2] | Command[1]) & Command[0];
assign Status = {ErrorCode, InvalidCommand, SDCBusy, SDCInitialized};
generate
if(`XLEN == 64) begin
always_comb
case(HADDRDelay[4:0])
'h0: HREADSDC = {24'b0, CLKDiv, 26'b0, Status};
'h4: HREADSDC = {26'b0, Status, 29'b0, Command};
'h8: HREADSDC = {29'b0, Command, 32'h200};
'hC: HREADSDC = {32'h200, Address[31:9], 9'b0};
'h10: HREADSDC = {Address, 9'b0};
'h18: HREADSDC = SDCReadData;
default: HREADSDC = {24'b0, CLKDiv, 26'b0, Status};
endcase // case (HADDRDelay[4:0])
end else begin
always_comb
case(HADDRDelay[4:0])
'h0: HREADSDC = {24'b0, CLKDiv};
'h4: HREADSDC = {26'b0, Status};
'h8: HREADSDC = {29'b0, Command};
'hC: HREADSDC = 'h200;
'h10: HREADSDC = {Address[31:9], 9'b0};
'h14: HREADSDC = Address[63:32];
'h18: HREADSDC = SDCReadData[31:0];
default: HREADSDC = {24'b0, CLKDiv};
endcase
end
endgenerate
for(index = 0; index < 4096/`XLEN; index++) begin
assign ReadData512ByteWords[index] = ReadData512Byte[(index+1)*`XLEN-1:index*`XLEN];
end
assign SDCReadDataPreNibbleSwap = ReadData512ByteWords[WordCount];
assign SDCReadData = {SDCReadDataPreNibbleSwap[59:56], SDCReadDataPreNibbleSwap[63:60],
SDCReadDataPreNibbleSwap[51:48], SDCReadDataPreNibbleSwap[55:52],
SDCReadDataPreNibbleSwap[43:40], SDCReadDataPreNibbleSwap[47:44],
SDCReadDataPreNibbleSwap[35:32], SDCReadDataPreNibbleSwap[39:36],
SDCReadDataPreNibbleSwap[27:24], SDCReadDataPreNibbleSwap[31:28],
SDCReadDataPreNibbleSwap[19:16], SDCReadDataPreNibbleSwap[23:20],
SDCReadDataPreNibbleSwap[11:8], SDCReadDataPreNibbleSwap[15:12],
SDCReadDataPreNibbleSwap[3:0], SDCReadDataPreNibbleSwap[7:4]};
flopenr #($clog2(4096/`XLEN)) WordCountReg
(.clk(HCLK),
.reset(~HRESETn | WordCountRst),
.en(HADDRDelay[4:0] == 'h18 & ReadDone),
.d(WordCount + 1'b1),
.q(WordCount));
typedef enum {STATE_READY,
// clock update states
STATE_CLK_DIV1,
STATE_CLK_DIV2,
STATE_CLK_DIV3,
STATE_CLK_DIV4,
// restart SDC
STATE_RESTART,
// SDC operation
STATE_PROCESS_CMD,
STATE_READ
} statetype;
statetype CurrState, NextState;
always_ff @(posedge HCLK, negedge HRESETn)
if (~HRESETn) CurrState <= STATE_READY;
else CurrState <= NextState;
always_comb begin
CLKDivUpdateEn = 1'b0;
HREADYSDC = 1'b0;
SDCCLKEN = 1'b1;
WordCountRst = 1'b0;
SDCBusy = 1'b0;
CommandCompleted = 1'b0;
ReadDone = 1'b0;
case (CurrState)
STATE_READY : begin
if (StartCLKDivUpdate)begin
NextState = STATE_CLK_DIV1;
HREADYSDC = 1'b0;
end else if (Command[2] | Command[1]) begin
NextState = STATE_PROCESS_CMD;
HREADYSDC = 1'b0;
end else if(HADDRDelay[4:0] == 'h18 & RegRead) begin
NextState = STATE_READ;
HREADYSDC = 1'b0;
end else begin
NextState = STATE_READY;
HREADYSDC = 1'b1;
end
end
STATE_CLK_DIV1: begin
NextState = STATE_CLK_DIV2;
SDCCLKEN = 1'b0;
end
STATE_CLK_DIV2: begin
NextState = STATE_CLK_DIV3;
CLKDivUpdateEn = 1'b1;
SDCCLKEN = 1'b0;
end
STATE_CLK_DIV3: begin
NextState = STATE_CLK_DIV4;
SDCCLKEN = 1'b0;
end
STATE_CLK_DIV4: begin
NextState = STATE_READY;
end
STATE_PROCESS_CMD: begin
HREADYSDC = 1'b1;
WordCountRst = 1'b1;
SDCBusy = 1'b1;
if(SDCDataValid) begin
NextState = STATE_READY;
CommandCompleted = 1'b1;
end else begin
NextState = STATE_PROCESS_CMD;
CommandCompleted = 1'b0;
end
end
STATE_READ: begin
NextState = STATE_READY;
HREADYSDC = 1'b1;
ReadDone = 1'b1;
end
default: begin
NextState = STATE_READY;
end
endcase
end
// clock generation divider
clockgater clockgater(.E(SDCCLKEN),
.SE(1'b0),
.CLK(HCLK),
.ECLK(CLKGate));
/* -----\/----- EXCLUDED -----\/-----
clkdivider #(8) clkdivider(.i_COUNT_IN_MAX(CLKDiv),
.i_EN(CLKDiv != 'b1),
.i_CLK(CLKGate),
.i_RST(~HRESETn | CLKDivUpdateEn),
.o_CLK(SDCCLKIn));
-----/\----- EXCLUDED -----/\----- */
assign SDCCLKIn = CLKGate;
sd_top sd_top(.CLK(SDCCLKIn),
.a_RST(~HRESETn),
.i_SD_CMD(SDCCmdIn),
.o_SD_CMD(SDCCmdOut),
.o_SD_CMD_OE(SDCCmdOE),
.i_SD_DAT(SDCDatIn),
.o_SD_CLK(SDCCLK),
.i_BLOCK_ADDR(Address[32:9]),
.o_READY_FOR_READ(SDCInitialized),
.o_SD_RESTARTING(SDCRestarting),
.i_READ_REQUEST(Command[2]),
.o_DATA_TO_CORE(),
.ReadData(ReadData512Byte),
.o_DATA_VALID(SDCDataValid),
.o_LAST_NIBBLE(SDCLast),
.o_ERROR_CODE_Q(ErrorCode),
.o_FATAL_ERROR(FatalError),
.i_COUNT_IN_MAX(-8'd62),
.LIMIT_SD_TIMERS(1'b0)); // *** must change this to 0 for real hardware.
endmodule

View file

@ -0,0 +1,103 @@
///////////////////////////////////////////
// clock divider.sv
//
// Written: Ross Thompson September 18, 2021
// Modified:
//
// Purpose: clock divider for sd flash
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module clkdivider #(parameter integer g_COUNT_WIDTH)
(
input logic [g_COUNT_WIDTH-1:0] i_COUNT_IN_MAX, //((Divide by value)/2) - 1
input logic i_EN, //Enable frequency division of i_clk
input logic i_CLK, // 1.2 GHz Base clock
input logic i_RST, // at start: clears flip flop and loads counter,
// i_RST must NOT be a_RST, it needs to be synchronized with the 50 MHz Clock to load the
// counter's initial value
output logic o_CLK // frequency divided clock
);
logic [g_COUNT_WIDTH-1:0] r_count_out; // wider for sign
logic w_counter_overflowed;
logic r_fd_Q;
logic w_fd_D;
logic w_load;
logic resetD, resetDD, resetPulse;
assign w_load = resetPulse | w_counter_overflowed; // reload when zero occurs or when set by outside
SDCcounter #(.WIDTH(g_COUNT_WIDTH)) // wider for sign, this way the (MSB /= '1') only for zero
my_counter (.clk(i_CLK),
.Load(w_load), // reload when zero occurs or when set by outside
.CountIn(i_COUNT_IN_MAX), // negative signed integer
.CountOut(r_count_out),
.Enable(1'b1), // ALWAYS COUNT
.reset(1'b0)); // no reset, only load
assign w_counter_overflowed = r_count_out[g_COUNT_WIDTH-1] == '0;
// to ensure the clock keeps running we need to make the reset last 1 cycle
// rather than until the reset is released. Alternatively we could do
// two resets. The first which resets this and the clk_fsm and the second
// which resets the rest of the design.
// Or we can make this clock divider not depend on reset.
flop #(1) pulseReset
(.d(i_RST),
.q(resetD),
.clk(i_CLK));
flop #(1) pulseReset2
(.d(resetD),
.q(resetDD),
.clk(i_CLK));
assign resetPulse = i_RST & ~resetDD;
flopenr #(1) toggle_flip_flop
(.d(w_fd_D),
.q(r_fd_Q),
.clk(i_CLK),
.reset(resetPulse),
.en(w_counter_overflowed)); // only update when counter overflows
assign w_fd_D = ~ r_fd_Q;
generate
if(`FPGA) begin
BUFGMUX
clkMux(.I1(r_fd_Q),
.I0(i_CLK),
.S(i_EN),
.O(o_CLK));
end else begin
assign o_CLK = i_EN ? r_fd_Q : i_CLK;
end
endgenerate
endmodule

View file

@ -0,0 +1,54 @@
///////////////////////////////////////////
// counter.sv
//
// Written: Ross Thompson
// Modified:
//
// Purpose: basic up counter
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module SDCcounter #(parameter integer WIDTH=32)
(
input logic [WIDTH-1:0] CountIn,
output logic [WIDTH-1:0] CountOut,
input logic Load,
input logic Enable,
input logic clk,
input logic reset);
logic [WIDTH-1:0] NextCount;
logic [WIDTH-1:0] count_q;
logic [WIDTH-1:0] CountP1;
flopenr #(WIDTH) reg1(.clk,
.reset,
.en(Enable | Load),
.d(NextCount),
.q(CountOut));
assign CountP1 = CountOut + 1'b1;
// mux between load and P1
assign NextCount = Load ? CountIn : CountP1;
endmodule

View file

@ -0,0 +1,62 @@
///////////////////////////////////////////
// crc16 sipo np ce
//
// Written: Ross Thompson September 18, 2021
// Modified:
//
// Purpose: CRC16 generator SIPO using register_ce
// w/o appending any zero-bits to the message
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module crc16_sipo_np_ce
(input logic CLK, // sequential device
input logic RST, // initial calue of CRC register must be "0000_0000_0000_0000"
input logic i_enable, // input is valid
input logic i_message_bit,
output logic [15:0] o_crc16);
logic [15:0] w_crc16_d;
flopenr #(16) crc16reg(.clk(CLK),
.reset(RST),
.en(i_enable),
.d(w_crc16_d),
.q(o_crc16));
assign w_crc16_d[15] = o_crc16[14];
assign w_crc16_d[14] = o_crc16[13];
assign w_crc16_d[13] = o_crc16[12];
assign w_crc16_d[12] = o_crc16[11] ^ (i_message_bit ^ o_crc16[15]);
assign w_crc16_d[11] = o_crc16[10];
assign w_crc16_d[10] = o_crc16[9];
assign w_crc16_d[9] = o_crc16[8];
assign w_crc16_d[8] = o_crc16[7];
assign w_crc16_d[7] = o_crc16[6];
assign w_crc16_d[6] = o_crc16[5];
assign w_crc16_d[5] = o_crc16[4] ^ (i_message_bit ^ o_crc16[15]);
assign w_crc16_d[4] = o_crc16[3];
assign w_crc16_d[3] = o_crc16[2];
assign w_crc16_d[2] = o_crc16[1];
assign w_crc16_d[1] = o_crc16[0];
assign w_crc16_d[0] = i_message_bit ^ o_crc16[15];
endmodule

View file

@ -0,0 +1,66 @@
///////////////////////////////////////////
// crc7 sipo np ce
//
// Written: Ross Thompson September 18, 2021
// Modified:
//
// Purpose: takes 40 bits of input, generates 7 bit CRC after a single
// clock cycle!
// w/o appending any zero-bits to the message
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module crc7_pipo
(input logic [39:0] i_DATA,
input logic i_CRC_ENABLE,
input logic RST,
input logic CLK,
output logic [6:0] o_CRC);
logic [6:0] r_lfsr_q;
logic [6:0] w_lfsr_d;
assign o_CRC = r_lfsr_q;
assign w_lfsr_d[0] = r_lfsr_q[1] ^ r_lfsr_q[2] ^ r_lfsr_q[4] ^ r_lfsr_q[6] ^ i_DATA[0] ^ i_DATA[4] ^ i_DATA[7] ^ i_DATA[8] ^ i_DATA[12] ^ i_DATA[14] ^ i_DATA[15] ^ i_DATA[16] ^ i_DATA[18] ^ i_DATA[20] ^ i_DATA[21] ^ i_DATA[23] ^ i_DATA[24] ^ i_DATA[30] ^ i_DATA[31] ^ i_DATA[34] ^ i_DATA[35] ^ i_DATA[37] ^ i_DATA[39];
assign w_lfsr_d[1] = r_lfsr_q[2] ^ r_lfsr_q[3] ^ r_lfsr_q[5] ^ i_DATA[1] ^ i_DATA[5] ^ i_DATA[8] ^ i_DATA[9] ^ i_DATA[13] ^ i_DATA[15] ^ i_DATA[16] ^ i_DATA[17] ^ i_DATA[19] ^ i_DATA[21] ^ i_DATA[22] ^ i_DATA[24] ^ i_DATA[25] ^ i_DATA[31] ^ i_DATA[32] ^ i_DATA[35] ^ i_DATA[36] ^ i_DATA[38];
assign w_lfsr_d[2] = r_lfsr_q[0] ^ r_lfsr_q[3] ^ r_lfsr_q[4] ^ r_lfsr_q[6] ^ i_DATA[2] ^ i_DATA[6] ^ i_DATA[9] ^ i_DATA[10] ^ i_DATA[14] ^ i_DATA[16] ^ i_DATA[17] ^ i_DATA[18] ^ i_DATA[20] ^ i_DATA[22] ^ i_DATA[23] ^ i_DATA[25] ^ i_DATA[26] ^ i_DATA[32] ^ i_DATA[33] ^ i_DATA[36] ^ i_DATA[37] ^ i_DATA[39];
assign w_lfsr_d[3] = r_lfsr_q[0] ^ r_lfsr_q[2] ^ r_lfsr_q[5] ^ r_lfsr_q[6] ^ i_DATA[0] ^ i_DATA[3] ^ i_DATA[4] ^ i_DATA[8] ^ i_DATA[10] ^ i_DATA[11] ^ i_DATA[12] ^ i_DATA[14] ^ i_DATA[16] ^ i_DATA[17] ^ i_DATA[19] ^ i_DATA[20] ^ i_DATA[26] ^ i_DATA[27] ^ i_DATA[30] ^ i_DATA[31] ^ i_DATA[33] ^ i_DATA[35] ^ i_DATA[38] ^ i_DATA[39];
assign w_lfsr_d[4] = r_lfsr_q[1] ^ r_lfsr_q[3] ^ r_lfsr_q[6] ^ i_DATA[1] ^ i_DATA[4] ^ i_DATA[5] ^ i_DATA[9] ^ i_DATA[11] ^ i_DATA[12] ^ i_DATA[13] ^ i_DATA[15] ^ i_DATA[17] ^ i_DATA[18] ^ i_DATA[20] ^ i_DATA[21] ^ i_DATA[27] ^ i_DATA[28] ^ i_DATA[31] ^ i_DATA[32] ^ i_DATA[34] ^ i_DATA[36] ^ i_DATA[39];
assign w_lfsr_d[5] = r_lfsr_q[0] ^ r_lfsr_q[2] ^ r_lfsr_q[4] ^ i_DATA[2] ^ i_DATA[5] ^ i_DATA[6] ^ i_DATA[10] ^ i_DATA[12] ^ i_DATA[13] ^ i_DATA[14] ^ i_DATA[16] ^ i_DATA[18] ^ i_DATA[19] ^ i_DATA[21] ^ i_DATA[22] ^ i_DATA[28] ^ i_DATA[29] ^ i_DATA[32] ^ i_DATA[33] ^ i_DATA[35] ^ i_DATA[37];
assign w_lfsr_d[6] = r_lfsr_q[0] ^ r_lfsr_q[1] ^ r_lfsr_q[3] ^ r_lfsr_q[5] ^ i_DATA[3] ^ i_DATA[6] ^ i_DATA[7] ^ i_DATA[11] ^ i_DATA[13] ^ i_DATA[14] ^ i_DATA[15] ^ i_DATA[17] ^ i_DATA[19] ^ i_DATA[20] ^ i_DATA[22] ^ i_DATA[23] ^ i_DATA[29] ^ i_DATA[30] ^ i_DATA[33] ^ i_DATA[34] ^ i_DATA[36] ^ i_DATA[38];
flopenr #(7)
lfsrReg(.clk(CLK),
.reset(RST),
.en(i_CRC_ENABLE),
.d(w_lfsr_d),
.q(r_lfsr_q));
endmodule

View file

@ -0,0 +1,61 @@
///////////////////////////////////////////
// crc16 sipo np ce
//
// Written: Ross Thompson September 18, 2021
// Modified:
//
// Purpose: CRC7 generator SIPO using register_ce
// w/o appending any zero-bits othe message
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module crc7_sipo_np_ce
(
input logic clk,
input logic rst,// initial CRC value must be b"000_0000"
input logic i_enable,
input logic i_message_bit,
output logic [6:0] o_crc7);
logic [6:0] w_crc7_d;
logic [6:0] r_crc7_q;
flopenr #(7)
crc7Reg(.clk(clk),
.reset(rst),
.en(i_enable),
.d(w_crc7_d),
.q(r_crc7_q));
assign w_crc7_d[6] = r_crc7_q[5];
assign w_crc7_d[5] = r_crc7_q[4];
assign w_crc7_d[4] = r_crc7_q[3];
assign w_crc7_d[3] = r_crc7_q[2] ^ (i_message_bit ^ r_crc7_q[6]);
assign w_crc7_d[2] = r_crc7_q[1];
assign w_crc7_d[1] = r_crc7_q[0];
assign w_crc7_d[0] = i_message_bit ^ r_crc7_q[6];
assign o_crc7 = r_crc7_q;
endmodule

View file

@ -0,0 +1,51 @@
///////////////////////////////////////////
// piso generic ce
//
// Written: Ross Thompson September 18, 2021
// Modified:
//
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module piso_generic_ce #(parameter integer g_BUS_WIDTH)
(
input logic clk,
input logic i_load,
input logic [g_BUS_WIDTH-1:0] i_data,
input logic i_en,
output o_data);
logic [g_BUS_WIDTH-1:0] w_reg_d;
logic [g_BUS_WIDTH-1:0] r_reg_q;
flopenr #(g_BUS_WIDTH)
shiftReg(.clk(clk),
.reset(1'b0),
.en(1'b1),
.d(w_reg_d),
.q(r_reg_q));
assign o_data = i_en ? r_reg_q[g_BUS_WIDTH - 1] : 1'b1;
assign w_reg_d = i_load ? i_data :
i_en ? {r_reg_q[g_BUS_WIDTH - 2 : 0], 1'b1} :
r_reg_q[g_BUS_WIDTH - 1 : 0];
endmodule

View file

@ -0,0 +1,49 @@
///////////////////////////////////////////
// regfile_p2r1w1_nibo
//
// Written: Ross Thompson September 18, 2021
// Modified: 2 port register file with 1 read and 1 write
//
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module regfile_p2r1w1_nibo #(parameter integer DEPTH = 10, parameter integer WIDTH = 4)
(input logic clk,
input logic we1,
input logic [DEPTH-1:0] ra1,
output logic [WIDTH-1:0] rd1,
output logic [(2**DEPTH)*WIDTH-1:0] Rd1All,
input logic [DEPTH-1:0] wa1,
input logic [WIDTH-1:0] wd1);
logic [WIDTH-1:0] regs [2**DEPTH-1:0];
genvar index;
always_ff @(posedge clk) begin
if(we1) begin
regs[wa1] <= wd1;
end
end
assign rd1 = regs[ra1];
for(index = 0; index < 2**DEPTH; index++)
assign Rd1All[index*WIDTH+WIDTH-1:index*WIDTH] = regs[index];
endmodule

View file

@ -0,0 +1,51 @@
///////////////////////////////////////////
// regfile_p2r1w1bwen
//
// Written: Ross Thompson September 18, 2021
// Modified: 2 port register file with 1 read and 1 write
//
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module regfile_p2r1w1bwen #(parameter integer DEPTH = 10, parameter integer WIDTH = 4)
(input logic clk,
input logic we1,
input logic [WIDTH-1:0] we1bit,
input logic [DEPTH-1:0] ra1,
output logic [WIDTH-1:0] rd1,
input logic [DEPTH-1:0] wa1,
input logic [WIDTH-1:0] wd1);
logic [WIDTH-1:0] regs [2**DEPTH-1:0];
integer i;
always_ff @(posedge clk) begin
if(we1) begin
for (i=0; i < WIDTH; i++) begin
if(we1bit[i]) begin
regs[wa1][i] <= wd1[i];
end
end
end
end
assign rd1 = regs[ra1];
endmodule

View file

@ -0,0 +1,94 @@
///////////////////////////////////////////
// sd_clk_fsm.sv
//
// Written: Ross Thompson September 19, 2021
// Modified:
//
// Purpose: Controls clock dividers.
// Replaces s_disable_sd_clocks, s_select_hs_clk, s_enable_hs_clk
// in sd_cmd_fsm.vhd. Attempts to correct issues with oversampling and
// under-sampling of control signals (for counter_cmd), that were present in my
// previous design.
// This runs on 50 MHz.
// sd_cmd_fsm will run on SD_CLK_Gated (50 MHz or 400 KHz, selected by this)
// asynchronous reset is used for both sd_cmd_fsm and for this.
// It must be synchronized with 50 MHz and held for a minimum period of a full
// 400 KHz pulse width.
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module sd_clk_fsm
(
input logic CLK,
input logic i_RST,
(* mark_debug = "true" *)output logic o_DONE,
(* mark_debug = "true" *)input logic i_START,
(* mark_debug = "true" *)input logic i_FATAL_ERROR,
(* mark_debug = "true" *)output logic o_HS_TO_INIT_CLK_DIVIDER_RST, // resets clock divider that is going from 50 MHz to 400 KHz
(* mark_debug = "true" *)output logic o_SD_CLK_SELECTED, // which clock is selected ('0'=HS or '1'=init)
(* mark_debug = "true" *)output logic o_G_CLK_SD_EN); // Turns gated clock (G_CLK_SD) off and on
logic [3:0] w_next_state;
(* mark_debug = "true" *) logic [3:0] r_curr_state;
// clock selection
parameter c_sd_clk_init = 1'b1;
parameter c_sd_clk_hs = 1'b0;
// States
localparam s_reset = 4'b0000;
localparam s_enable_init_clk = 4'b0001; // enable 400 KHz
localparam s_disable_sd_clocks = 4'b0010;
localparam s_select_hs_clk = 4'b0011;
localparam s_enable_hs_clk = 4'b0100;
localparam s_done = 4'b0101;
localparam s_disable_sd_clocks_2 = 4'b0110; // if error occurs
localparam s_select_init_clk = 4'b0111; // if error occurs
localparam s_safe_state = 4'b1111; //always provide a safe state return if all states are not used
flopenr #(4) stateReg(.clk(CLK),
.reset(i_RST),
.en(1'b1),
.d(w_next_state),
.q(r_curr_state));
assign w_next_state = i_RST ? s_reset :
r_curr_state == s_reset | (r_curr_state == s_enable_init_clk & ~i_START) | (r_curr_state == s_select_init_clk) ? s_enable_init_clk :
r_curr_state == s_enable_init_clk & i_START ? s_disable_sd_clocks :
r_curr_state == s_disable_sd_clocks ? s_select_hs_clk :
r_curr_state == s_select_hs_clk ? s_enable_hs_clk :
r_curr_state == s_enable_hs_clk | (r_curr_state == s_done & ~i_FATAL_ERROR) ? s_done :
r_curr_state == s_done & i_FATAL_ERROR ? s_disable_sd_clocks_2 :
r_curr_state == s_disable_sd_clocks_2 ? s_select_init_clk :
s_safe_state;
assign o_HS_TO_INIT_CLK_DIVIDER_RST = r_curr_state == s_reset;
assign o_SD_CLK_SELECTED = (r_curr_state == s_select_hs_clk) | (r_curr_state == s_enable_hs_clk) | (r_curr_state == s_done) ? c_sd_clk_hs : c_sd_clk_init;
assign o_G_CLK_SD_EN = (r_curr_state == s_enable_init_clk) | (r_curr_state == s_enable_hs_clk) | (r_curr_state == s_done);
assign o_DONE = r_curr_state == s_done;
endmodule

View file

@ -0,0 +1,592 @@
///////////////////////////////////////////
// sd_clk_fsm.sv
//
// Written: Ross Thompson September 19, 2021
// Modified:
//
// Purpose: Finite state machine for the SD CMD bus
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module sd_cmd_fsm
(
input logic CLK, // HS
//i_SLOWER_CLK : in std_logic;
input logic i_RST, // reset FSM,
// MUST COME OUT OF RESET
// SYNCHRONIZED TO THE 1.2 GHZ CLOCK!
output logic o_TIMER_LOAD, o_TIMER_EN, // Timer
output logic [18:0] o_TIMER_IN,
input logic [18:0] i_TIMER_OUT,
output logic o_COUNTER_LOAD, o_COUNTER_EN, // Counter
output logic [7:0] o_COUNTER_IN,
input logic [7:0] i_COUNTER_OUT,
output logic o_SD_CLK_EN, // Clock Gaters
input logic i_CLOCK_CHANGE_DONE, // Communication with CLK_FSM
output logic o_START_CLOCK_CHANGE, // Communication with CLK_FSM
output logic o_IC_RST, o_IC_EN, o_IC_UP_DOWN, // Instruction counter
input logic [3:0] i_IC_OUT, // stop when you get to 10 because that is CMD17
input logic [1:0] i_USES_DAT,
input logic [6:0] i_OPCODE,
input logic [2:0] i_R_TYPE,
// bit masks
input logic [31:0] i_NO_REDO_MASK,
input logic [31:0] i_NO_REDO_ANS,
input logic [31:0] i_NO_ERROR_MASK,
input logic [31:0] i_NO_ERROR_ANS,
(* mark_debug = "true" *) output logic o_SD_CMD_OE, // Enable ouptut on tri-state SD_CMD line
// TX Components
output logic o_TX_PISO40_LOAD, o_TX_PISO40_EN, // Shift register for TX command head
output logic o_TX_PISO8_LOAD, o_TX_PISO8_EN, // Shift register for TX command tail
output logic o_TX_CRC7_PIPO_RST, o_TX_CRC7_PIPO_EN, // Parallel-to-Parallel CRC7 Generator
output logic [1:0] o_TX_SOURCE_SELECT, // What gets sent to CMD_TX
// TX Memory
output logic o_CMD_TX_IS_CMD55_RST,
output logic o_CMD_TX_IS_CMD55_EN, // '1' means that the command that was just sent has index
// 55, so the subsequent command is to be
// viewed as ACMD by the SD card.
// RX Components
input logic i_SD_CMD_RX, // serial response input on SD_CMD
output logic o_RX_SIPO48_RST, o_RX_SIPO48_EN, // Shift Register for all 48 bits of Response
input logic [39:8] i_RESPONSE_CONTENT, // last 32 bits of RX_SIPO_40_OUT
input logic [45:40] i_RESPONSE_INDEX, // 6 bits from RX_SIPO_40_OUT
output logic o_RX_CRC7_SIPO_RST, o_RX_CRC7_SIPO_EN, // Serial-to-parallel CRC7 Generator
input logic [6:0] i_RX_CRC7,
// RX Memory
output logic o_RCA_REGISTER_RST, o_RCA_REGISTER_EN, // Relative Card Address
// Communication to sd_dat_fsm
output logic o_CMD_TX_DONE, // begin waiting for DAT_RX to complete
input logic i_DAT_RX_DONE, // now go to next state since data block rx was completed
(* mark_debug = "true" *) input logic i_ERROR_CRC16, // repeat last command
(* mark_debug = "true" *) input logic i_ERROR_DAT_TIMES_OUT,
// Commnuication to core
output logic o_READY_FOR_READ, // tell core that I have completed initialization
output logic o_SD_RESTARTING, // inform core the need to restart
input logic i_READ_REQUEST, // core tells me to execute CMD17
// Communication to Host
output logic o_DAT_ERROR_FD_RST,
output logic [2:0] o_ERROR_CODE_Q, // Indicates what caused the fatal error
output logic o_FATAL_ERROR, // SD Card is damaged beyond recovery, restart entire initialization procedure of card
input logic LIMIT_SD_TIMERS
);
logic [4:0] w_next_state;
(* mark_debug = "true" *) logic [4:0] r_curr_state;
logic w_resend_last_command, w_rx_crc7_check, w_rx_index_check, w_rx_bad_crc7, w_rx_bad_index, w_rx_bad_reply, w_bad_card;
logic [31:0] w_redo_result, w_error_result;
logic w_ACMD41_init_done;
logic w_fail_cnt_en, w_fail_count_rst;
logic [10:0] r_fail_count_out;
logic w_ACMD41_busy_timer_START, w_ACMD41_times_out_FLAG, w_ACMD41_busy_timer_RST; //give up after 1000 ms of ACMD41
logic [2:0] w_ERROR_CODE_D, r_ERROR_CODE_Q ; // Error Codes for fatal error on SD CMD FSM
logic w_ERROR_CODE_RST, w_ERROR_CODE_EN;
logic [18:0] Timer_In;
localparam s_reset_clear_error_reg = 5'b00000;
localparam s_idle_supply_no_clk = 5'b00001;
localparam s_idle_supply_sd_clk = 5'b00010;
localparam s_ld_head = 5'b00011;
localparam s_tx_head = 5'b00100;
localparam s_ld_tail = 5'b00101;
localparam s_tx_tail = 5'b00110;
localparam s_setup_rx = 5'b00111;
localparam s_idle_ncc = 5'b01000;
localparam s_fetch_next_cmd = 5'b01001;
localparam s_rx_48 = 5'b01010;
localparam s_rx_136 = 5'b01011;
localparam s_error_no_response = 5'b01100;
localparam s_idle_for_dat = 5'b01101;
localparam s_error_bad_card = 5'b01110;
localparam s_idle_nrc = 5'b01111;
localparam s_count_attempt = 5'b10000;
localparam s_reset_from_error = 5'b10001;
//localparam s_enable_hs_clk = 5'b10010;
localparam s_idle_for_start_bit = 5'b10011;
localparam s_fetch_prev_cmd = 5'b10100; // use to resend previous cmd55 if acmd is resent
// localparam s_setup_rx_b = 5'b10110;
// localparam s_idle_for_start_bit_b= 5'b10111;
// localparam s_rx_48_b = 5'b11000;
// localparam s_rx_136_b = 5'b11001;
localparam s_error_dat_time_out = 5'b11010; // don't advance states if the dat fsm times out
localparam s_idle_for_clock_change = 5'b11011; // replaces s_disable_sd_clocks, s_select_hs_clk, s_enable_hs_clk
localparam s_study_response = 5'b11100; // Do error checking here
localparam s_idle_for_read_request = 5'b11101; // After power up and initialization sequence is completed
localparam s_Error_TX_Failed = 5'b11110; // when fail_cnt_out exceeds c_max_attempts
localparam c_MAX_ATTEMPTS = 1500; // Give up sending a command after 3 failed attempts
// (except ACMD41) so the processor is not locked up forever
localparam c_response_type_R0_NONE = 0;
localparam c_response_type_R1_NORMAL = 1;
localparam c_response_type_R2_CID_CSD = 2;
localparam c_response_type_R3_OCR = 3;
localparam c_response_type_R6_RCA = 6;
localparam c_response_type_R7_CIC = 7;
localparam c_start_bit = 1'b0;
localparam c_DAT_none = 2'b00;
localparam c_DAT_busy = 2'b01;
localparam c_DAT_wide = 2'b10;
localparam c_DAT_block = 2'b11;
// Instructions mnemonics based on index (opcode(5 downto 0))
localparam logic [45:40] c_Go_Idle_State = 6'd0; //CMD0
localparam logic [45:40] c_All_Send_CID = 6'd02; // CMD2
localparam logic [45:40] c_SD_Send_RCA = 6'd03; // CMD3
localparam logic [45:40] c_Switch_Function = 6'd06; // CMD6
localparam logic [45:40] c_Set_Bus_Width = 6'd06; // ACMD6
localparam logic [45:40] c_Select_Card = 6'd07; // CMD7
localparam logic [45:40] c_Send_IF_State = 6'd08; // CMD8
localparam logic [45:40] c_Read_Single_Block = 6'd17; // CMD17
localparam logic [45:40] c_SD_Send_OCR = 6'd41; // ACMD41
localparam logic [45:40] c_App_Command = 6'd55; // CMD55
// clock selection
localparam c_sd_clk_init = 1'b1;
localparam c_sd_clk_hs = 1'b0;
//tx source selection
localparam logic [1:0] c_tx_low = 2'b00;
localparam logic [1:0] c_tx_high = 2'b01;
localparam logic [1:0] c_tx_head = 2'b10;
localparam logic [1:0] c_tx_tail = 2'b11;
// Error Codes for Error Register
localparam logic [2:0] c_NO_ERRORS = 3'b000; // no fatal errors occurred
// (default value when register is cleared during reset)
localparam [2:0] C_ERROR_NO_CMD_RESPONSE = 3'b100; // card timed out while waiting for a response on CMD, no start bit
// of response packet was ever received
// (possible causes: illegal command, card is disconnected,
// not meeting timing (you can fix timing by inverting the clock
// sent to card))
localparam logic [2:0] c_ERROR_NO_DAT_RESPONSE = 3'b101; // card timed out while waiting for a data block on DAT, no start bit
// of DAT packet was ever received
// (possible cause: card is disconnected)
localparam logic [2:0] C_ERROR_BAD_CARD_STATUS = 3'b110; // status bits of a response indicate a card is not supported
// or that the card is damaged internally
localparam logic [2:0] C_ERROR_EXCEED_MAX_ATTEMPTS = 3'b111; // if a command fails it may be resent,
// but after so many attempts you should just give up
//Alias for value of SD_CMD_Output_Enable
localparam c_TX_COMMAND = 1'b1; // Enable output on SD_CMD
localparam c_RX_RESPONSE = 1'b0; // Disable Output on SD_CMD
// load values in for timers and counters
localparam logic [7:0] c_NID_max = 8'd63; // counter_in: should be "4"
// downto 0 = 5 bits count
// but is not enough time for
// sdModel.v
localparam logic [7:0] c_NCR_max = 8'd63; // counter_in
localparam logic [7:0] c_NCC_min = 8'd7; // counter_in
localparam logic [7:0] c_NRC_min = 8'd8; // counter_in
//localparam logic [18:0] c_1000ms = 19'd400000; // ACMD41 timeout
//*** BUG this value is too bit to fit into 19 bits.
localparam logic [18:0] c_1000ms = 19'd40000; // ACMD41 timeout
// command instruction type (opcode(6))
localparam c_CMD = 1'b0;
localparam c_ACMD = 1'b1;
// counter direction for up_down
localparam c_increment = 1'b1; // count <= count + 1
localparam c_decrement = 1'b0; // count <= count - 1
logic COUNTER_OUT_GT_ZERO;
logic COUNTER_OUT_GE_ZERO;
logic COUNTER_OUT_GT_8;
logic COUNTER_OUT_EQ_8;
logic COUNTER_OUT_EQ_ZERO;
logic TIMER_OUT_GT_ZERO;
logic TIMER_OUT_EQ_ZERO;
logic fail_count_out_le_max_attempts;
logic fail_count_out_lt_max_attempts;
logic fail_count_out_gt_max_attempts;
logic IC_OUT_EQ_2;
logic IC_OUT_EQ_3;
logic IC_OUT_LT_9;
logic IC_OUT_GE_9;
assign Timer_In = LIMIT_SD_TIMERS ? 19'b0000000000000000011 : 19'b0011000011010100000; // 250 ms
//Fail Counter, tracks how many failed attempts at command transmission
SDCcounter #(11) fail_counter
(.CountIn(11'b0),
.CountOut(r_fail_count_out),
.Load(1'b0),
.Enable(w_fail_cnt_en),
.clk(CLK),
.reset(w_fail_count_rst));
// Simple timer for ACMD41 busy
simple_timer #(19) ACMD41_busy_timer
(.VALUE(c_1000ms),
.START(w_ACMD41_busy_timer_START),
.FLAG(w_ACMD41_times_out_FLAG),
.RST(w_ACMD41_busy_timer_RST),
.CLK(CLK));
// State Register, instantiate register_ce. 32 state state machine
flopenr #(5) state_reg
(.d(w_next_state),
.q(r_curr_state),
.en(1'b1),
.reset(i_RST),
.clk(CLK));
// Error register : indicates what type of fatal error occured for interrupt
flopenr #(3) error_reg
(.d(w_ERROR_CODE_D),
.q(r_ERROR_CODE_Q),
.en(w_ERROR_CODE_EN),
.reset(w_ERROR_CODE_RST),
.clk(CLK));
assign o_ERROR_CODE_Q = r_ERROR_CODE_Q;
assign COUNTER_OUT_GT_ZERO = i_COUNTER_OUT > 0;
assign COUNTER_OUT_GE_ZERO = i_COUNTER_OUT >= 0;
assign COUNTER_OUT_GT_8 = i_COUNTER_OUT > 8;
assign COUNTER_OUT_EQ_8 = i_COUNTER_OUT == 8;
assign COUNTER_OUT_EQ_ZERO = i_COUNTER_OUT == 0;
assign TIMER_OUT_GT_ZERO = i_TIMER_OUT > 0;
assign TIMER_OUT_EQ_ZERO = i_TIMER_OUT == 0;
assign fail_count_out_le_max_attempts = r_fail_count_out <= (c_MAX_ATTEMPTS-1);
assign fail_count_out_lt_max_attempts = r_fail_count_out < (c_MAX_ATTEMPTS-1);
assign fail_count_out_gt_max_attempts = r_fail_count_out > (c_MAX_ATTEMPTS-1);
assign IC_OUT_EQ_2 = i_IC_OUT == 2;
assign IC_OUT_EQ_3 = i_IC_OUT == 3;
assign IC_OUT_LT_9 = i_IC_OUT < 9;
assign IC_OUT_GE_9 = i_IC_OUT >= 9;
assign w_next_state = i_RST ? s_reset_clear_error_reg :
((r_curr_state == s_reset_clear_error_reg) |
(r_curr_state == s_Error_TX_Failed) |
(r_curr_state == s_error_no_response) |
(r_curr_state == s_error_bad_card) |
(r_curr_state == s_error_dat_time_out)) ? s_reset_from_error :
((r_curr_state == s_reset_from_error) |
((r_curr_state == s_idle_supply_no_clk) & (TIMER_OUT_GT_ZERO))) ? s_idle_supply_no_clk :
(((r_curr_state == s_idle_supply_no_clk) & (TIMER_OUT_EQ_ZERO)) |
((r_curr_state == s_idle_supply_sd_clk) & (COUNTER_OUT_GT_ZERO))) ? s_idle_supply_sd_clk :
(r_curr_state == s_ld_head) ? s_count_attempt :
(((r_curr_state == s_count_attempt) & (fail_count_out_le_max_attempts)) |
((r_curr_state == s_count_attempt) &
(((IC_OUT_EQ_2) & (i_OPCODE[5:0] == c_App_Command)) |
((IC_OUT_EQ_3) & (i_OPCODE == ({c_ACMD, c_SD_Send_OCR})))) // to work CMD55, ACMD41 MUST be lines 2, 3 of instruction fetch mux of sd_top.vhd
& (w_ACMD41_times_out_FLAG)
& (fail_count_out_gt_max_attempts))) ? s_tx_head :
((r_curr_state == s_count_attempt) & (fail_count_out_gt_max_attempts)) ? s_Error_TX_Failed :
((r_curr_state == s_tx_head) | ((r_curr_state == s_ld_tail) & (COUNTER_OUT_GT_8))) ? s_ld_tail :
(((r_curr_state == s_ld_tail) & (COUNTER_OUT_EQ_8)) |
((r_curr_state == s_tx_tail) & (COUNTER_OUT_GT_ZERO))) ? s_tx_tail :
(r_curr_state == s_tx_tail) & (COUNTER_OUT_EQ_ZERO) ? s_setup_rx :
(((r_curr_state == s_setup_rx) & (i_R_TYPE == c_response_type_R0_NONE)) |
((r_curr_state == s_idle_ncc) & (COUNTER_OUT_GT_ZERO))) ? s_idle_ncc :
(((r_curr_state == s_setup_rx) & (i_R_TYPE != c_response_type_R0_NONE)) |
((r_curr_state == s_idle_for_start_bit) & (i_SD_CMD_RX != c_start_bit) &
(COUNTER_OUT_GT_ZERO))) ? s_idle_for_start_bit :
((r_curr_state == s_idle_for_start_bit) & (i_SD_CMD_RX != c_start_bit) &
(COUNTER_OUT_EQ_ZERO)) ? s_error_no_response :
(((r_curr_state == s_idle_for_start_bit) & (i_SD_CMD_RX == c_start_bit) &
/* verilator lint_off UNSIGNED */
(COUNTER_OUT_GE_ZERO) & (i_R_TYPE == c_response_type_R2_CID_CSD)) |
/* verilator lint_on UNSIGNED */
((r_curr_state == s_rx_136) & (COUNTER_OUT_GT_ZERO))) ? s_rx_136 :
(((r_curr_state == s_idle_for_start_bit) & (i_SD_CMD_RX == c_start_bit) &
/* verilator lint_off UNSIGNED */
(COUNTER_OUT_GE_ZERO) & (i_R_TYPE != c_response_type_R2_CID_CSD)) |
/* verilator lint_on UNSIGNED */
((r_curr_state == s_rx_48) & (COUNTER_OUT_GT_ZERO))) ? s_rx_48 :
(((r_curr_state == s_rx_136) & (COUNTER_OUT_EQ_ZERO)) |
((r_curr_state == s_rx_48) & COUNTER_OUT_EQ_ZERO)) ? s_study_response :
(r_curr_state == s_study_response) & w_bad_card ? s_error_bad_card :
(((r_curr_state == s_study_response) & (~w_bad_card) & (i_USES_DAT != c_DAT_none)) |
((r_curr_state == s_idle_for_dat) & (~i_DAT_RX_DONE))) ? s_idle_for_dat :
((r_curr_state == s_idle_for_dat) & (i_DAT_RX_DONE) & (i_ERROR_DAT_TIMES_OUT)) ? s_error_dat_time_out :
(((r_curr_state == s_idle_for_dat) & (i_DAT_RX_DONE) &
(~i_ERROR_DAT_TIMES_OUT)) |
((r_curr_state == s_study_response) & (~w_bad_card) &
(i_USES_DAT == c_DAT_none)) |
((r_curr_state == s_idle_nrc) & (COUNTER_OUT_GT_ZERO))) ? s_idle_nrc :
((r_curr_state == s_idle_nrc) & (COUNTER_OUT_EQ_ZERO) &
(w_resend_last_command) & ((i_OPCODE[6] == c_ACMD) &
((i_OPCODE[5:0]) != c_App_Command))) ? s_fetch_prev_cmd :
((r_curr_state == s_fetch_prev_cmd) |
((r_curr_state == s_idle_supply_sd_clk) & (COUNTER_OUT_EQ_ZERO)) |
((r_curr_state == s_fetch_next_cmd) & // before CMD17
(IC_OUT_LT_9)) | // blindly load head of next command
((r_curr_state == s_idle_for_read_request) & (i_READ_REQUEST)) | // got the request, load head
((r_curr_state == s_idle_nrc) & (COUNTER_OUT_EQ_ZERO) &
(w_resend_last_command) & ((i_OPCODE[6] == c_CMD) |
((i_OPCODE[5:0]) == c_App_Command)))) ? s_ld_head :
(((r_curr_state == s_idle_nrc) & (COUNTER_OUT_EQ_ZERO) &
(~w_resend_last_command) & ((i_OPCODE) == ({c_CMD, c_Switch_Function}))) |
((r_curr_state == s_idle_for_clock_change) & (~i_CLOCK_CHANGE_DONE))) ? s_idle_for_clock_change :
(((r_curr_state == s_idle_ncc) & (COUNTER_OUT_EQ_ZERO)) |
((r_curr_state == s_idle_nrc) & (COUNTER_OUT_EQ_ZERO) &
(~w_resend_last_command) & ((i_OPCODE) != ({c_CMD, c_Switch_Function}))) |
((r_curr_state == s_idle_for_clock_change) & (i_CLOCK_CHANGE_DONE))) ? s_fetch_next_cmd :
(((r_curr_state == s_fetch_next_cmd) &
(IC_OUT_GE_9)) | // During and after CMD17, wait for request to send CMD17 from core
// waiting for request
(r_curr_state == s_idle_for_read_request)) ? s_idle_for_read_request :
s_reset_clear_error_reg;
// state outputs
assign w_ACMD41_busy_timer_START = ((r_curr_state == s_count_attempt) & (i_OPCODE == {c_ACMD, c_SD_Send_OCR}) & (r_fail_count_out == 1));
assign w_ACMD41_busy_timer_RST = ((r_curr_state == s_reset_from_error) | (w_ACMD41_init_done));
// Error Register
assign w_ERROR_CODE_RST = (r_curr_state == s_reset_clear_error_reg);
assign w_ERROR_CODE_EN = (r_curr_state == s_error_bad_card) | (r_curr_state == s_error_no_response) | (r_curr_state == s_Error_TX_Failed) | (r_curr_state == s_error_dat_time_out);
assign w_ERROR_CODE_D = (r_curr_state == s_Error_TX_Failed) ? C_ERROR_EXCEED_MAX_ATTEMPTS : // give up
(r_curr_state == s_error_bad_card) ? C_ERROR_BAD_CARD_STATUS : // card is damaged or unsupported
(r_curr_state == s_error_no_response) ? C_ERROR_NO_CMD_RESPONSE : // no response was received on CMD line
(r_curr_state == s_error_dat_time_out) ? c_ERROR_NO_DAT_RESPONSE : // no data packet was received on DAT bus
c_NO_ERRORS; // all is well
// Failure counter
assign w_fail_count_rst = ((r_curr_state == s_reset_from_error) | (r_curr_state == s_fetch_next_cmd & i_OPCODE[5:0] != c_App_Command));
assign w_fail_cnt_en = ((r_curr_state == s_count_attempt) & (i_OPCODE[6] != c_ACMD | i_OPCODE[5:0] == c_App_Command));
// & (i_OPCODE != ({c_ACMD, c_SD_Send_OCR})) else // NOT ACMD41, it can take up to 1 second
// Timer module
assign o_TIMER_EN = (r_curr_state == s_idle_supply_no_clk);
assign o_TIMER_LOAD = (r_curr_state == s_reset_from_error);
assign o_TIMER_IN = (r_curr_state == s_reset_from_error) ? Timer_In : '0;
// Clock selection/gater module(s) ...
assign o_SD_CLK_EN = ~((r_curr_state == s_reset_from_error) | (r_curr_state == s_idle_supply_no_clk) | (r_curr_state == s_idle_for_clock_change));
assign o_START_CLOCK_CHANGE = (r_curr_state == s_idle_for_clock_change);
// RCA register module
assign o_RCA_REGISTER_RST = (r_curr_state == s_reset_from_error);
assign o_RCA_REGISTER_EN = ((r_curr_state == s_idle_nrc) & (i_R_TYPE == c_response_type_R6_RCA));
// Instruction counter module
assign o_IC_RST = (r_curr_state == s_reset_from_error);
//assign o_IC_EN = (r_curr_state == s_fetch_next_cmd) | (r_curr_state == s_fetch_prev_cmd);
assign o_IC_EN = (((r_curr_state == s_fetch_next_cmd) & (i_IC_OUT < 10)) | (r_curr_state == s_fetch_prev_cmd));
assign o_IC_UP_DOWN = (r_curr_state == s_fetch_prev_cmd) ? c_decrement : c_increment;
// "Previous Command sent was CMD55, so the command I'm now sending is ACMD" module
assign o_CMD_TX_IS_CMD55_RST = (r_curr_state == s_reset_from_error);
assign o_CMD_TX_IS_CMD55_EN = (r_curr_state == s_ld_head);
// Output signals to DAT FSM
//o_CMD_TX_DONE = '0' when (r_curr_state == s_reset) else // reset
// '0' when (r_curr_state == s_idle_supply_no_clk) | (r_curr_state == s_idle_supply_sd_clk) else // power up
// '0' when ((r_curr_state == s_ld_head)
// | (r_curr_state == s_tx_head)
// | (r_curr_state == s_ld_tail)
// | (r_curr_state == s_tx_tail)) else // tx
// '1';
assign o_CMD_TX_DONE = (r_curr_state == s_setup_rx);
// Counter Module
assign o_COUNTER_LOAD = (r_curr_state == s_idle_supply_no_clk) |
(r_curr_state == s_ld_head) |
(r_curr_state == s_setup_rx) |
(r_curr_state == s_idle_for_start_bit) & (i_SD_CMD_RX == c_start_bit) |
(r_curr_state == s_rx_48) & (i_COUNTER_OUT == 0) |
(r_curr_state == s_rx_136) & (i_COUNTER_OUT == 0);
assign o_COUNTER_IN = (r_curr_state == s_idle_supply_no_clk) ? 8'd73 :
// | is it 73 downto 0 == 74 bits
(r_curr_state == s_ld_head) ? 8'd47 : // or is it 48
((r_curr_state == s_setup_rx) & (i_R_TYPE == c_response_type_R0_NONE)) ? c_NCC_min :
((r_curr_state == s_setup_rx)
& (i_R_TYPE != c_response_type_R0_NONE)
& (((i_OPCODE) == ({c_CMD, c_All_Send_CID})) |
((i_OPCODE) == ({c_ACMD, c_SD_Send_OCR})))) ? c_NID_max :
(r_curr_state == s_setup_rx) ? c_NCR_max :
((r_curr_state == s_idle_for_start_bit) & (i_R_TYPE == c_response_type_R2_CID_CSD)) ? 8'd135 : // | is it 136
(r_curr_state == s_idle_for_start_bit) ? 8'd46 : // | is it not48
(r_curr_state == s_rx_48) | (r_curr_state == s_rx_136) ? c_NRC_min : // | is it 8
8'd0;
assign o_COUNTER_EN = (r_curr_state == s_idle_supply_sd_clk) ? 1'b1 :
((r_curr_state == s_tx_head) | (r_curr_state == s_ld_tail) | (r_curr_state == s_tx_tail)) ? 1'b1 :
(r_curr_state == s_idle_for_start_bit) & (i_SD_CMD_RX == c_start_bit) ? 1'b0 :
(r_curr_state == s_idle_for_start_bit) ? 1'b1 :
(r_curr_state == s_rx_48) & (i_COUNTER_OUT == 0) ? 1'b0 :
(r_curr_state == s_rx_48) ? 1'b1 :
(r_curr_state == s_idle_nrc) ? 1'b1 :
(r_curr_state == s_rx_136) & (i_COUNTER_OUT == 0) ? 1'b0 :
(r_curr_state == s_rx_136) ? 1'b1 :
(r_curr_state == s_idle_ncc) ? 1'b1 :
1'b0;
// SD_CMD Tri-state Buffer Module
assign o_SD_CMD_OE = (r_curr_state == s_idle_supply_sd_clk) ? c_TX_COMMAND :
((r_curr_state == s_tx_head)
| (r_curr_state == s_ld_tail)
| (r_curr_state == s_tx_tail)) ? c_TX_COMMAND :
c_RX_RESPONSE;
// Shift Registers
// TX_PISO40 Transmit Command Head
assign o_TX_PISO40_LOAD = (r_curr_state == s_ld_head);
assign o_TX_PISO40_EN = (r_curr_state == s_tx_head) | (r_curr_state == s_ld_tail);
// TX_CRC7_PIPO Generate Tail
assign o_TX_CRC7_PIPO_RST = (r_curr_state == s_ld_head);
assign o_TX_CRC7_PIPO_EN = (r_curr_state == s_tx_head);
// TX_PISO8 Transmit Command Tail
assign o_TX_PISO8_LOAD = (r_curr_state == s_ld_tail);
assign o_TX_PISO8_EN = (r_curr_state == s_tx_tail);
// RX_CRC7_SIPO Calculate the CRC7 of the first 47-bits of reply (should be zero)
assign o_RX_CRC7_SIPO_RST = (r_curr_state == s_setup_rx);
assign o_RX_CRC7_SIPO_EN = (r_curr_state == s_rx_48) & (i_COUNTER_OUT > 0); // or (r_curr_state == s_rx_48_b)
// RX_SIPO40 Content bits of response
assign o_RX_SIPO48_RST = (r_curr_state == s_setup_rx);
assign o_RX_SIPO48_EN = (r_curr_state == s_rx_48 | r_curr_state == s_rx_48);
// Fatal Error Signal Wire
assign o_FATAL_ERROR = (r_curr_state == s_error_bad_card) | (r_curr_state == s_error_no_response) |
(r_curr_state == s_Error_TX_Failed) | (r_curr_state == s_error_dat_time_out);
assign o_DAT_ERROR_FD_RST = (r_curr_state == s_ld_head);
// I'm debating the merit of creating yet another state for sd_cmd_fsm.vhd to go into when and if sd_dat_fsm.vhd
// times out while waiting for start bit on the DAT bus resulting in Error_Time_Out going high in
// sd_Dat_fsm.vhd while sd_cmd_fsm.vhd is still in s_idle_for_dat
// TX source selection bits for mux
assign o_TX_SOURCE_SELECT = (r_curr_state == s_idle_supply_sd_clk) ? c_tx_high :
((r_curr_state == s_ld_head)
| (r_curr_state == s_tx_head)
| (r_curr_state == s_ld_tail)) ? c_tx_head :
(r_curr_state == s_tx_tail) ? c_tx_tail :
c_tx_high; // This occurs when not transmitting anything
// Study Response
assign w_rx_crc7_check = (r_curr_state == s_idle_nrc) &
((i_R_TYPE != c_response_type_R0_NONE) &
(i_R_TYPE != c_response_type_R3_OCR) &
(i_R_TYPE != c_response_type_R2_CID_CSD));
assign w_rx_index_check = (r_curr_state == s_idle_nrc) &
((i_R_TYPE != c_response_type_R0_NONE) &
(i_R_TYPE != c_response_type_R3_OCR) &
(i_R_TYPE != c_response_type_R2_CID_CSD));
assign w_redo_result = i_RESPONSE_CONTENT & i_NO_REDO_MASK;
assign w_rx_bad_reply = ((r_curr_state == s_idle_nrc | r_curr_state == s_study_response) & (w_redo_result != i_NO_REDO_ANS));
assign w_rx_bad_crc7 = ((r_curr_state == s_idle_nrc | r_curr_state == s_study_response) & ((w_rx_crc7_check) & (i_RX_CRC7 != 7'b0)));
assign w_rx_bad_index = ((r_curr_state == s_idle_nrc | r_curr_state == s_study_response)
& ((w_rx_index_check) & (i_RESPONSE_INDEX != i_OPCODE[5:0])));
assign w_resend_last_command = ((r_curr_state == s_idle_nrc | r_curr_state == s_study_response) &
((w_rx_bad_reply) | (w_rx_bad_index) | (w_rx_bad_crc7))) |
((r_curr_state == s_idle_nrc) &
((i_ERROR_CRC16) &
((i_USES_DAT == c_DAT_block) | (i_USES_DAT == c_DAT_wide))));
assign w_error_result = i_RESPONSE_CONTENT & i_NO_ERROR_MASK;
// Make assignment based on what was read from the OCR Register.
// Bit 31, Card power up status bit: '1' == SD Flash Card power up procedure is finished.
// '0' == SD Flash Card power up procedure is not finished.
// Bit 30, Card capacity status bit: '1' == Extended capacity card is in use (64 GB in size or greater).
// '0' == Extended capacity card is not in use.
assign w_ACMD41_init_done = ((i_IC_OUT == 3) & (i_OPCODE == ({c_ACMD, c_SD_Send_OCR}))) &
(~w_rx_bad_reply) & (r_curr_state == s_study_response);
assign w_bad_card = ((r_curr_state == s_study_response) & (w_error_result != i_NO_ERROR_ANS) &
((~w_ACMD41_times_out_FLAG) | (w_ACMD41_init_done)));
// Communication with core
assign o_READY_FOR_READ = (r_curr_state == s_idle_for_read_request);
assign o_SD_RESTARTING = (r_curr_state == s_Error_TX_Failed) |
(r_curr_state == s_error_dat_time_out) |
(r_curr_state == s_error_bad_card) |
(r_curr_state == s_error_no_response);
endmodule

View file

@ -0,0 +1,256 @@
///////////////////////////////////////////
// sd_dat_fsm.sv
//
// Written: Ross Thompson September 19, 2021
// Modified:
//
// Purpose: Runs in parallel with sd_cmd_fsm to control activity on the DAT
// bus of the SD card.
// 14 State Mealy FSM + Safe state = 15 State Mealy FSM
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module sd_dat_fsm
(
input logic CLK, // HS Clock (48 MHz)
input logic i_RST,
// Timer module control
input logic i_SD_CLK_SELECTED, // Which frequency I'm in determines what count in to load for a 100ms timer
output logic o_TIMER_LOAD, o_TIMER_EN, // Timer Control signals
output logic [22:0] o_TIMER_IN, // Need Enough bits for 100 milliseconds at 48MHz
input logic [22:0] i_TIMER_OUT, // (ceiling(log((clk freq)(delay desired)-1)/log(2))-1) downto 0
// Nibble counter module control
output logic o_COUNTER_RST, o_COUNTER_EN, // nibble counter
input logic [10:0] i_COUNTER_OUT, // max nibbles is 1024 + crc16 bits = 1040 bits
// CRC16 Generation control
(* mark_debug = "true" *)output logic o_CRC16_EN, o_CRC16_RST, // shared signals for all 4 CRC16_SIPO (one for each of 4 DAT lines)
(* mark_debug = "true" *)input logic i_DATA_CRC16_GOOD, // indicates that no errors in transmission when CRC16 are all zero
// For R1b
output logic o_BUSY_RST, o_BUSY_EN, // busy signal for R1b
(* mark_debug = "true" *)input logic i_DAT0_Q,
// Storage Buffers for DAT bits read
output logic o_NIBO_EN, // 512 bytes block data (Nibble In Block Out)
// From LUT
(* mark_debug = "true" *)input logic [1:0] i_USES_DAT, // current command needs use of DAT bus
// For communicating with core
output logic o_DATA_VALID, // indicates that DATA being send over o_DATA to core is valid
output logic o_LAST_NIBBLE, // indicates that the last nibble has been sent
// For communication with sd_cmd_fsm
(* mark_debug = "true" *)input logic i_CMD_TX_DONE, // command transmission completed, begin waiting for DATA
(* mark_debug = "true" *)output logic o_DAT_RX_DONE, // tell SD_CMD_FSM that DAT communication is completed, send next instruction to sd card
(* mark_debug = "true" *)output logic o_ERROR_DAT_TIMES_OUT, // error flag for when DAT times out (so don't fetch more instructions)
(* mark_debug = "true" *)output logic o_DAT_ERROR_FD_RST,
(* mark_debug = "true" *)output logic o_DAT_ERROR_FD_EN, // tell SD_CMD_FSM to resend command due to error in transmission
input logic LIMIT_SD_TIMERS
);
(* mark_debug = "true" *) logic [3:0] r_curr_state;
logic [3:0] w_next_state;
(* mark_debug = "true" *) logic w_error_crc16_fd_en, w_error_crc16_fd_rst, w_error_crc16_fd_d; // Save ERROR_CRC16 so CMD FSM sees it in IDLE_NRC (not just in IDLE_DAT)
logic r_error_crc16_fd_Q;
logic [22:0] Identify_Timer_In;
logic [22:0] Data_TX_Timer_In;
localparam logic [3:0] s_reset = 4'b0000;
localparam logic [3:0] s_idle = 4'b0001;
localparam logic [3:0] s_idle_for_start_bit = 4'b0010;
localparam logic [3:0] s_read_r1b = 4'b0011;
localparam logic [3:0] s_notify_r1b_completed = 4'b0100;
localparam logic [3:0] s_error_time_out = 4'b0101;
localparam logic [3:0] s_rx_wide_data = 4'b0110;
localparam logic [3:0] s_rx_block_data = 4'b0111;
localparam logic [3:0] s_rx_crc16 = 4'b1000;
localparam logic [3:0] s_error_crc16_fail = 4'b1001;
localparam logic [3:0] s_publish_block_data = 4'b1010;
localparam logic [3:0] s_publish_wide_data = 4'b1011;
localparam logic [3:0] s_reset_wide_data = 4'b1100;
localparam logic [3:0] s_reset_block_data = 4'b1101;
localparam logic [3:0] s_reset_nibble_counter = 4'b1110; // Before publishing CMD17 Block Data
localparam logic [1:0] c_DAT_none = 2'b00;
localparam logic [1:0] c_DAT_busy = 2'b01;
localparam logic [1:0] c_DAT_wide = 2'b10;
localparam logic [1:0] c_DAT_block = 2'b11;
localparam logic c_start_bit = 0;
localparam logic c_busy_bit = 0;
// load values in for timers and counters
localparam logic c_slow_clock = 1'b1; // use during initialization (card identification mode)
localparam logic c_HS_clock = 1'b0; // use after CMD6 switches clock frequency (CMD17)
logic TIMER_OUT_GT_0;
logic TIMER_OUT_EQ_0;
logic COUNTER_OUT_EQ_1023;
logic COUNTER_OUT_LT_1023;
logic COUNTER_OUT_LT_128;
logic COUNTER_OUT_EQ_128;
logic COUNTER_OUT_LT_144;
logic COUNTER_OUT_EQ_144;
logic COUNTER_OUT_LT_1040;
logic COUNTER_OUT_EQ_1040;
assign Identify_Timer_In = LIMIT_SD_TIMERS ? 23'b00000000000000001100011 : 23'b00000001001110001000000; // 40,000 unsigned.
assign Data_TX_Timer_In = LIMIT_SD_TIMERS ? 23'b00000000000000001100011 : 23'b11110100001001000000000; // 8,000,000 unsigned.
flopenr #(4) stateReg(.clk(CLK),
.reset(i_RST),
.en(1'b1),
.d(w_next_state),
.q(r_curr_state));
assign TIMER_OUT_GT_0 = i_TIMER_OUT > 0;
assign TIMER_OUT_EQ_0 = i_TIMER_OUT == 0;
assign COUNTER_OUT_EQ_1023 = i_COUNTER_OUT == 1023;
assign COUNTER_OUT_LT_1023 = i_COUNTER_OUT < 1023;
assign COUNTER_OUT_LT_128 = i_COUNTER_OUT < 128;
assign COUNTER_OUT_EQ_128 = i_COUNTER_OUT == 128;
assign COUNTER_OUT_LT_144 = i_COUNTER_OUT < 144;
assign COUNTER_OUT_EQ_144 = i_COUNTER_OUT == 144;
assign COUNTER_OUT_LT_1040 = i_COUNTER_OUT < 1040;
assign COUNTER_OUT_EQ_1040 = i_COUNTER_OUT == 1040;
assign w_next_state = ((i_RST) |
(r_curr_state == s_error_time_out) | // noticed this change is needed during emulation
(r_curr_state == s_notify_r1b_completed) |
(r_curr_state == s_error_crc16_fail) |
(r_curr_state == s_publish_wide_data) |
((r_curr_state == s_publish_block_data) & (COUNTER_OUT_EQ_1023))) ? s_reset :
((r_curr_state == s_reset) |
((r_curr_state == s_idle) & ((i_USES_DAT == c_DAT_none) | ((i_USES_DAT != c_DAT_none) & (~i_CMD_TX_DONE))))) ? s_idle :
((r_curr_state == s_idle) & (i_USES_DAT == c_DAT_wide) & (i_CMD_TX_DONE)) ? s_reset_wide_data :
((r_curr_state == s_idle) & (i_USES_DAT == c_DAT_block) & (i_CMD_TX_DONE)) ? s_reset_block_data :
((r_curr_state == s_reset_wide_data) |
((r_curr_state == s_idle) & (i_USES_DAT == c_DAT_busy) & (i_CMD_TX_DONE)) |
(r_curr_state == s_reset_block_data) |
((r_curr_state == s_idle_for_start_bit) & (TIMER_OUT_GT_0) & (i_DAT0_Q != c_start_bit))) ? s_idle_for_start_bit :
((r_curr_state == s_idle_for_start_bit) & // Apparently R1b's busy signal is optional,
(TIMER_OUT_EQ_0) & // Even if it never shows up,
(i_USES_DAT == c_DAT_busy)) ? s_notify_r1b_completed : // pretend it did, & move on
(((r_curr_state == s_idle_for_start_bit) & (TIMER_OUT_GT_0) &
(i_DAT0_Q == c_start_bit) & (i_USES_DAT == c_DAT_busy)) |
((r_curr_state == s_read_r1b) & (TIMER_OUT_GT_0) & (i_DAT0_Q == c_busy_bit))) ? s_read_r1b :
(((r_curr_state == s_read_r1b) & (TIMER_OUT_EQ_0)) |
((r_curr_state == s_idle_for_start_bit) & (TIMER_OUT_EQ_0) &
(i_USES_DAT != c_DAT_busy))) ? s_error_time_out :
((r_curr_state == s_read_r1b) & (i_DAT0_Q != c_busy_bit)) ? s_notify_r1b_completed :
(((r_curr_state == s_idle_for_start_bit) & (TIMER_OUT_GT_0) & (i_DAT0_Q == c_start_bit) &
(i_USES_DAT == c_DAT_wide)) |
((r_curr_state == s_rx_wide_data) & (COUNTER_OUT_LT_128))) ? s_rx_wide_data :
(((r_curr_state == s_idle_for_start_bit) & (TIMER_OUT_GT_0) &
(i_DAT0_Q == c_start_bit) & (i_USES_DAT == c_DAT_block)) |
((r_curr_state == s_rx_block_data) & (COUNTER_OUT_LT_1023))) ? s_rx_block_data :
(((r_curr_state == s_rx_wide_data) & (COUNTER_OUT_EQ_128)) |
((r_curr_state == s_rx_block_data) & (COUNTER_OUT_EQ_1023)) |
((r_curr_state == s_rx_crc16) &
(((i_USES_DAT == c_DAT_wide) & (COUNTER_OUT_LT_144)) |
((i_USES_DAT == c_DAT_block) & (COUNTER_OUT_LT_1040))))) ? s_rx_crc16 :
((r_curr_state == s_rx_crc16) &
(((i_USES_DAT == c_DAT_wide) & (COUNTER_OUT_EQ_144)) |
((i_USES_DAT == c_DAT_block) & (COUNTER_OUT_EQ_1040))) &
(~i_DATA_CRC16_GOOD)) ? s_error_crc16_fail :
((r_curr_state == s_rx_crc16) & (i_USES_DAT == c_DAT_wide) & (COUNTER_OUT_EQ_144) &
(i_DATA_CRC16_GOOD)) ? s_publish_wide_data :
((r_curr_state == s_rx_crc16) &
(i_USES_DAT == c_DAT_block) & (COUNTER_OUT_EQ_1040) & (i_DATA_CRC16_GOOD)) ? s_reset_nibble_counter :
((r_curr_state == s_reset_nibble_counter)) ? s_publish_block_data :
s_reset;
assign o_TIMER_IN = (r_curr_state == s_reset) & (i_SD_CLK_SELECTED == c_slow_clock) ? Identify_Timer_In : Data_TX_Timer_In;
assign o_TIMER_LOAD = ((r_curr_state == s_reset) |
(r_curr_state == s_reset_block_data));
assign o_TIMER_EN = ((r_curr_state == s_idle_for_start_bit) |
(r_curr_state == s_read_r1b));
// Nibble Counter module
assign o_COUNTER_RST = (r_curr_state == s_reset) | (r_curr_state == s_reset_nibble_counter);
assign o_COUNTER_EN = ((r_curr_state == s_rx_block_data) |
(r_curr_state == s_rx_wide_data) |
(r_curr_state == s_rx_crc16)) | (r_curr_state == s_publish_block_data);
// CRC16 Generation module
assign o_CRC16_RST = (r_curr_state == s_reset);
assign o_CRC16_EN = ((r_curr_state == s_rx_block_data) |
(r_curr_state == s_rx_wide_data) |
(r_curr_state == s_rx_crc16));
// Flip Flop Module (for R1b)
assign o_BUSY_RST = (r_curr_state == s_reset);
//o_BUSY_EN = '1' when ((r_curr_state == s_idle_for_start_bit) |
// (r_curr_state == s_read_r1b)) else
// '0';
assign o_BUSY_EN = 1'b1; // Always sample data
// DAT Storage Modules
assign o_NIBO_EN = (r_curr_state == s_rx_block_data);
// To sd_cmd_fsm
assign o_DAT_RX_DONE = ((r_curr_state == s_error_time_out) |
(r_curr_state == s_notify_r1b_completed) |
(r_curr_state == s_error_crc16_fail) |
(r_curr_state == s_publish_wide_data) |
(r_curr_state == s_publish_block_data));
assign o_ERROR_DAT_TIMES_OUT = (r_curr_state == s_error_time_out);
// o_RESEND_READ_WIDE (Error! This is not defined. Indicates switch command must be re-rent),
// should be a function of block busy logic
// For Communication with core
assign o_DATA_VALID = (r_curr_state == s_publish_block_data);
assign o_LAST_NIBBLE = ((r_curr_state == s_publish_block_data)
& (COUNTER_OUT_EQ_1023)) | (r_curr_state == s_error_time_out); // notify done if errors occur
// o_ERROR_CRC16 (note: saved to flip flop because otherwise is only 1 clock cycle, not what I want)
assign o_DAT_ERROR_FD_RST = (r_curr_state == s_reset_block_data) | (r_curr_state == s_reset_wide_data);
assign o_DAT_ERROR_FD_EN = (r_curr_state == s_rx_crc16);
endmodule

View file

@ -0,0 +1,659 @@
///////////////////////////////////////////
// sd_top.sv
//
// Written: Ross Thompson September 19, 2021
// Modified:
//
// Purpose: SD card controller
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module sd_top #(parameter g_COUNT_WIDTH = 8)
(
input logic CLK, // 1.2 GHz (1.0 GHz typical)
input logic a_RST, // Reset signal (Must be held for minimum of 24 clock cycles)
// a_RST MUST COME OUT OF RESET SYNCHRONIZED TO THE 1.2 GHZ CLOCK!
// io_SD_CMD_z : inout std_logic; // SD CMD Bus
(* mark_debug = "true" *)input logic i_SD_CMD, // CMD Response from card
(* mark_debug = "true" *)output logic o_SD_CMD, // CMD Command from host
(* mark_debug = "true" *)output logic o_SD_CMD_OE, // Direction of SD_CMD
(* mark_debug = "true" *)input logic [3:0] i_SD_DAT, // SD DAT Bus
(* mark_debug = "true" *)output logic o_SD_CLK, // SD CLK Bus
// For communication with core cpu
input logic [32:9] i_BLOCK_ADDR, // see "Addressing" in parts.fods (only 8GB total capacity is used)
output logic o_READY_FOR_READ, // tells core that initialization sequence is completed and
// sd card is ready to read a 512 byte block to the core.
// Held high during idle until i_READ_REQUEST is received
output logic o_SD_RESTARTING, // inform core the need to restart
input logic i_READ_REQUEST, // After Ready for read is sent to the core, the core will
// pulse this bit high to indicate it wants the block at this address
output logic [3:0] o_DATA_TO_CORE, // nibble being sent to core when DATA block is
output logic [4095:0] ReadData, // full 512 bytes to Bus
// being published
output logic o_DATA_VALID, // held high while data being read to core to indicate that it is valid
output logic o_LAST_NIBBLE, // pulse when last nibble is sent
output logic [2:0] o_ERROR_CODE_Q, // indicates which error occured
output logic o_FATAL_ERROR, // indicates that the FATAL ERROR register has updated
// For tuning
input logic [g_COUNT_WIDTH-1:0] i_COUNT_IN_MAX,
input logic LIMIT_SD_TIMERS
);
localparam logic c_CMD = 1'b0;
localparam logic c_ACMD = 1'b1;
// packet bit names
localparam logic c_start_bit = 1'b0; // bit 47
localparam logic c_stop_bit = 1'b1; // bit 0, AKA "end bit"
// transmitter bit, bit 46
localparam logic c_tx_host_command = 1'b1;
localparam logic c_tx_card_response = 1'b0;
// response types
localparam logic [2:0] c_response_type_R0_NONE = 3'd0;
localparam logic [2:0] c_response_type_R1_NORMAL = 3'd1;
localparam logic [2:0] c_response_type_R2_CID_CSD = 3'd2;
localparam logic [2:0] c_response_type_R3_OCR = 3'd3;
localparam logic [2:0] c_response_type_R6_RCA = 3'd6;
localparam logic [2:0] c_response_type_R7_CIC = 3'd7;
// uses dat
localparam logic [1:0] c_DAT_none = 2'b00;
localparam logic [1:0] c_DAT_busy = 2'b01;
localparam logic [1:0] c_DAT_wide = 2'b10;
localparam logic [1:0] c_DAT_block = 2'b11;
// tx source selection
localparam logic [1:0] c_tx_low = 2'b00;
localparam logic [1:0] c_tx_high = 2'b01;
localparam logic [1:0] c_tx_head = 2'b10;
localparam logic [1:0] c_tx_tail = 2'b11;
// command indexes
localparam logic [45:40] c_Go_Idle_State = 6'd00; // CMD0
localparam logic [45:40] c_All_Send_CID = 6'd02; // CMD2
localparam logic [45:40] c_SD_Send_RCA = 6'd03; // CMD3
localparam logic [45:40] c_Switch_Function = 6'd06; // CMD6
localparam logic [45:40] c_Set_Bus_Width = 6'd06; // ACMD6
localparam logic [45:40] c_Select_Card = 6'd07; // CMD7
localparam logic [45:40] c_Send_IF_State = 6'd08; // CMD8
localparam logic [45:40] c_Read_Single_Block = 6'd17; // CMD17
localparam logic [45:40] c_SD_Send_OCR = 6'd41; // ACMD41
localparam logic [45:40] c_App_Command = 6'd55; // CMD55
// bitmasks
localparam logic [127:96] c_CMD0_mask_check_redo_bits = 32'h00000000; // Go_Idle_State
localparam logic [127:96] c_CMD0_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD0_mask_check_error_bits = 32'h00000000;
localparam logic [127:96] c_CMD0_ans_error_free = 32'h00000000;
localparam logic [127:96] c_CMD2_mask_check_redo_bits = 32'h00000000; // All_Send_CID
localparam logic [127:96] c_CMD2_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD2_mask_check_error_bits = 32'h00000000;
localparam logic [127:96] c_CMD2_ans_error_free = 32'h00000000;
localparam logic [127:96] c_CMD3_mask_check_redo_bits = 32'h00000000; // SD_Send_RCA
localparam logic [127:96] c_CMD3_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD3_mask_check_error_bits = 32'h00002000;
localparam logic [127:96] c_CMD3_ans_error_free = 32'h00000000;
localparam logic [127:96] c_CMD6_mask_check_redo_bits = 32'h00000000; // Switch_Function
localparam logic [127:96] c_CMD6_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD6_mask_check_error_bits = 32'h82380000;
localparam logic [127:96] c_CMD6_ans_error_free = 32'h00000000;
localparam logic [127:96] c_ACMD6_mask_check_redo_bits = 32'h00000000; // Set_Bus_Width
localparam logic [127:96] c_ACMD6_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_ACMD6_mask_check_error_bits = 32'h8F398020;
localparam logic [127:96] c_ACMD6_ans_error_free = 32'h00000020;
localparam logic [127:96] c_CMD7_mask_check_redo_bits = 32'h00000000; // Select_Card
localparam logic [127:96] c_CMD7_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD7_mask_check_error_bits = 32'h0F398000;
localparam logic [127:96] c_CMD7_ans_error_free = 32'h00000000;
localparam logic [127:96] c_CMD8_mask_check_redo_bits = 32'h00000000; // Send_IF_State
localparam logic [127:96] c_CMD8_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD8_mask_check_error_bits = 32'h00000FFF;
localparam logic [127:96] c_CMD8_ans_error_free = 32'h000001FF;
localparam logic [127:96] c_CMD17_mask_check_redo_bits = 32'h00000000; // Read_Single_Block
localparam logic [127:96] c_CMD17_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD17_mask_check_error_bits = 32'hCF398000;
localparam logic [127:96] c_CMD17_ans_error_free = 32'h00000000;
localparam logic [127:96] c_ACMD41_mask_check_redo_bits = 32'h80000000; //32'h80000000; // SD_Send_OCR
localparam logic [127:96] c_ACMD41_ans_dont_redo = 32'h80000000; //32'h80000000;
localparam logic [127:96] c_ACMD41_mask_check_error_bits = 32'h41FF8000; // 32'h41FF8000;
localparam logic [127:96] c_ACMD41_ans_error_free = 32'h40FF8000; // 32'h40FF8000
localparam logic [127:96] c_CMD55_mask_check_redo_bits = 32'h00000000; // App_Command
localparam logic [127:96] c_CMD55_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_CMD55_mask_check_error_bits = 32'h0F398000;
localparam logic [127:96] c_CMD55_ans_error_free = 32'h00000000;
localparam logic [127:96] c_ACMD55_mask_check_redo_bits = 32'h00000000; // App_Command
localparam logic [127:96] c_ACMD55_ans_dont_redo = 32'h00000000;
localparam logic [127:96] c_ACMD55_mask_check_error_bits = 32'h0F398000;
localparam logic [127:96] c_ACMD55_ans_error_free = 32'h00000000;
// SD_CMD_FSM Connections
logic w_TIMER_LOAD, w_TIMER_EN;
logic [18:0] w_TIMER_IN;
logic [18:0] r_TIMER_OUT;
logic w_COUNTER_LOAD, w_COUNTER_EN;
logic [7:0] w_COUNTER_IN;
logic [7:0] r_COUNTER_OUT;
logic w_SD_CLK_EN;
logic w_CLOCK_CHANGE_DONE, w_START_CLOCK_CHANGE; // to clk fsm
logic w_HS_TO_INIT_CLK_DIVIDER_RST;
(* mark_debug = "true" *)logic w_IC_RST, w_IC_EN, w_IC_UP_DOWN;
(* mark_debug = "true" *)logic w_SD_CMD_OE;
logic w_TX_PISO40_LOAD, w_TX_PISO40_EN;
logic w_TX_PISO8_LOAD, w_TX_PISO8_EN;
logic w_TX_CRC7_PIPO_RST, w_TX_CRC7_PIPO_EN;
logic [1:0] w_TX_SOURCE_SELECT;
logic w_CMD_TX_IS_CMD55_RST;
logic w_CMD_TX_IS_CMD55_EN;
//logic w_CMD_RX;
logic w_RX_SIPO48_RST, w_RX_SIPO48_EN;
(* mark_debug = "true" *)logic [39:8] r_RESPONSE_CONTENT;
(* mark_debug = "true" *)logic [45:40] r_RESPONSE_INDEX;
logic w_RX_CRC7_SIPO_RST, w_RX_CRC7_SIPO_EN;
logic [6:0] r_RX_CRC7_Q;
logic w_RCA_REGISTER_RST, w_RCA_REGISTER_EN;
logic w_CMD_TX_DONE;
logic w_DAT_RX_DONE;
logic w_DAT_ERROR_FD_RST_DAT, w_DAT_ERROR_FD_RST_CMD, w_DAT_ERROR_FD_RST, w_DAT_ERROR_FD_EN;
(* mark_debug = "true" *)logic r_DAT_ERROR_Q; // CRC16 error or time out
(* mark_debug = "true" *)logic w_NOT_DAT_ERROR_Q; // '0'=no error, '1'=tx error on DAT bus
(* mark_debug = "true" *)logic w_ERROR_DAT_TIMES_OUT;
(* mark_debug = "true" *)logic w_FATAL_ERROR;
(* mark_debug = "true" *)logic [2:0] r_ERROR_CODE_Q; // indicates which fatal error occured
// Communication with core
(* mark_debug = "true" *)logic w_READY_FOR_READ;
(* mark_debug = "true" *)logic w_READ_REQUEST;
(* mark_debug = "true" *)logic [3:0] r_DATA_TO_CORE;
(* mark_debug = "true" *)logic w_DATA_VALID;
(* mark_debug = "true" *)logic w_LAST_NIBBLE;
//SD_DAT_FSM Connections
logic w_DAT_TIMER_LOAD, w_DAT_TIMER_EN;
logic w_DAT_COUNTER_RST, w_DAT_COUNTER_EN;
logic w_CRC16_EN, w_CRC16_RST;
logic w_BUSY_RST, w_BUSY_EN;
logic w_NIBO_EN;
logic w_DATA_CRC16_GOOD;
logic w_VALID_BLOCK_D, w_VALID_BLOCK_EN, w_VALID_WIDE_D, w_VALID_WIDE_EN;
logic [22:0] w_DAT_TIMER_IN;
logic [22:0] r_DAT_TIMER_OUT;
logic [10:0] r_DAT_COUNTER_OUT;
(* mark_debug = "true" *)logic [3:0] r_DAT_Q;
// RCA Register
logic [15:0] w_RCA_D_Q;
logic [15:0] r_RCA_Q2;
// Multiplexer Logics
logic [132:0] w_instruction_control_bits;
logic [132:130] w_R_TYPE ;
logic [129:128] w_USES_DAT ;
logic [127:96] w_NO_REDO_MASK ;
logic [95:64] w_NO_REDO_ANS ;
logic [63:32] w_NO_ERROR_MASK ;
logic [31:0] w_NO_ERROR_ANS ;
logic [45:40] w_command_index ;
logic [39:8] w_command_arguments ;
logic [47:8] w_command_head ;
(* mark_debug = "true" *)logic [6:0] w_OPCODE_Q ;
// TOP_LEVEL Connections
logic [40:9] w_BLOCK_ADDR ;
(* mark_debug = "true" *)logic [3:0] r_IC_OUT ;
logic [2:0] r_command_index_is_55_history ; // [0] is live index, [1] is currently saved index, [2] is index of previous command
logic r_previous_command_index_was_55_q; // is index of previous command 55, wired to r_command_index_is_55_history[2]
logic r_ACMD_Q; // if the previous command sent to the SD card successfully had index 55, then the SD card thinks the current command is ACMD
logic [4095:0] r_block_data ; // data block from CMD17
// TX
logic [45:8] w_command_content; // first 40 bits of command packet
logic w_tx_head_Q; // transmission of first part of command packet
logic w_tx_tail_Q; // transmission of last part of command packet
logic [7:0] r_command_tail; // last 8 bits of command packet
logic [6:0] r_TX_CRC7;
//logic w_TX_Q:= '0'; // actual transmission when tx is enabled
// RX
logic [47:0] r_RX_RESPONSE;
// Tri state IO Driver BC18MIMS
logic w_SD_CMD_TX_Q; // Write Data
logic w_SD_CMD_RX; // Read Data
// CLOCKS
//logic r_CLK_HS := '0'; // 50 MHz Divided Clock [static]
//logic r_SD_CLK_ungated := '0'; // Selected clock before it is clock gated
//logic r_SD_CLK := '0'; // GATED CLOCKS
logic r_TO_SD_CLK; // What is actually sent to the SD card
logic w_G_CLK_SD_EN;
logic r_CLK_SD, r_G_CLK_SD; // clocks
logic r_G_CLK_SD_n;
logic [15:0] r_CLK_FSM_RST ; // a_rst logic delayed by one 1.2 GHz period
logic w_SD_CLK_SELECTED;
//DAT FSM Connections
logic [15:0] r_DAT3_CRC16, r_DAT2_CRC16, r_DAT1_CRC16;
logic [15:0] r_DAT0_CRC16;
assign w_BLOCK_ADDR = {8'h00, i_BLOCK_ADDR}; // (40 downto 36 are zero since card is 64 GB)
// (35 downto 32 are zero since memeory is only 8GB total)
assign o_READY_FOR_READ = w_READY_FOR_READ;
assign w_READ_REQUEST = i_READ_REQUEST;
assign o_DATA_TO_CORE = r_DATA_TO_CORE;
assign o_DATA_VALID = w_DATA_VALID;
assign o_LAST_NIBBLE = (w_LAST_NIBBLE | w_FATAL_ERROR); // indicate done if (last nibble OR Fatal Error go high)
assign o_FATAL_ERROR = w_FATAL_ERROR;
sd_cmd_fsm my_sd_cmd_fsm
(
.CLK(r_G_CLK_SD),
.i_RST(a_RST),
.o_TIMER_LOAD(w_TIMER_LOAD),
.o_TIMER_EN(w_TIMER_EN),
.o_TIMER_IN(w_TIMER_IN),
.i_TIMER_OUT(r_TIMER_OUT),
.o_COUNTER_LOAD(w_COUNTER_LOAD),
.o_COUNTER_EN(w_COUNTER_EN),
.o_COUNTER_IN(w_COUNTER_IN),
.i_COUNTER_OUT(r_COUNTER_OUT),
.o_SD_CLK_EN(w_SD_CLK_EN),
.i_CLOCK_CHANGE_DONE(w_CLOCK_CHANGE_DONE),
.o_START_CLOCK_CHANGE(w_START_CLOCK_CHANGE),
.o_IC_RST(w_IC_RST),
.o_IC_EN(w_IC_EN),
.o_IC_UP_DOWN(w_IC_UP_DOWN),
.i_IC_OUT(r_IC_OUT),
.i_USES_DAT(w_USES_DAT),
.i_OPCODE(w_OPCODE_Q),
.i_R_TYPE(w_R_TYPE),
.i_NO_REDO_MASK(w_NO_REDO_MASK),
.i_NO_REDO_ANS(w_NO_REDO_ANS),
.i_NO_ERROR_MASK(w_NO_ERROR_MASK),
.i_NO_ERROR_ANS(w_NO_ERROR_ANS),
.o_SD_CMD_OE(w_SD_CMD_OE),
.o_TX_PISO40_LOAD(w_TX_PISO40_LOAD),
.o_TX_PISO40_EN(w_TX_PISO40_EN),
.o_TX_PISO8_LOAD(w_TX_PISO8_LOAD),
.o_TX_PISO8_EN(w_TX_PISO8_EN),
.o_TX_CRC7_PIPO_RST(w_TX_CRC7_PIPO_RST),
.o_TX_CRC7_PIPO_EN(w_TX_CRC7_PIPO_EN),
.o_TX_SOURCE_SELECT(w_TX_SOURCE_SELECT),
.o_CMD_TX_IS_CMD55_RST(w_CMD_TX_IS_CMD55_RST),
.o_CMD_TX_IS_CMD55_EN(w_CMD_TX_IS_CMD55_EN),
.i_SD_CMD_RX(w_SD_CMD_RX),
.o_RX_SIPO48_RST(w_RX_SIPO48_RST),
.o_RX_SIPO48_EN(w_RX_SIPO48_EN),
.i_RESPONSE_CONTENT(r_RESPONSE_CONTENT),
.i_RESPONSE_INDEX(r_RESPONSE_INDEX),
.o_RX_CRC7_SIPO_RST(w_RX_CRC7_SIPO_RST),
.o_RX_CRC7_SIPO_EN(w_RX_CRC7_SIPO_EN),
.i_RX_CRC7(r_RX_CRC7_Q),
.o_RCA_REGISTER_RST(w_RCA_REGISTER_RST),
.o_RCA_REGISTER_EN(w_RCA_REGISTER_EN),
.o_CMD_TX_DONE(w_CMD_TX_DONE),
.i_DAT_RX_DONE(w_DAT_RX_DONE),
.i_ERROR_CRC16(w_NOT_DAT_ERROR_Q),
.i_ERROR_DAT_TIMES_OUT(w_ERROR_DAT_TIMES_OUT),
.i_READ_REQUEST(w_READ_REQUEST),
.o_READY_FOR_READ(w_READY_FOR_READ),
.o_SD_RESTARTING(o_SD_RESTARTING),
.o_DAT_ERROR_FD_RST(w_DAT_ERROR_FD_RST_CMD),
.o_ERROR_CODE_Q(r_ERROR_CODE_Q),
.o_FATAL_ERROR(w_FATAL_ERROR),
.LIMIT_SD_TIMERS(LIMIT_SD_TIMERS));
assign o_ERROR_CODE_Q = r_ERROR_CODE_Q;
sd_dat_fsm my_sd_dat_fsm
(.CLK(r_G_CLK_SD),
.i_RST(a_RST),
.o_TIMER_LOAD(w_DAT_TIMER_LOAD),
.o_TIMER_EN(w_DAT_TIMER_EN),
.o_TIMER_IN(w_DAT_TIMER_IN),
.i_TIMER_OUT(r_DAT_TIMER_OUT),
.i_SD_CLK_SELECTED(w_SD_CLK_SELECTED),
.o_COUNTER_RST(w_DAT_COUNTER_RST),
.o_COUNTER_EN(w_DAT_COUNTER_EN),
.i_COUNTER_OUT(r_DAT_COUNTER_OUT),
.o_CRC16_EN(w_CRC16_EN),
.o_CRC16_RST(w_CRC16_RST),
.i_DATA_CRC16_GOOD(w_DATA_CRC16_GOOD),
.o_BUSY_RST(w_BUSY_RST),
.o_BUSY_EN(w_BUSY_EN),
.i_DAT0_Q(r_DAT_Q[0]),
.o_NIBO_EN(w_NIBO_EN),
.i_USES_DAT(w_USES_DAT),
.i_CMD_TX_DONE(w_CMD_TX_DONE),
.o_DAT_RX_DONE(w_DAT_RX_DONE),
.o_ERROR_DAT_TIMES_OUT(w_ERROR_DAT_TIMES_OUT),
.o_DATA_VALID(w_DATA_VALID),
.o_LAST_NIBBLE(w_LAST_NIBBLE),
.o_DAT_ERROR_FD_RST(w_DAT_ERROR_FD_RST_DAT),
.o_DAT_ERROR_FD_EN(w_DAT_ERROR_FD_EN),
.LIMIT_SD_TIMERS(LIMIT_SD_TIMERS));
assign w_DAT_ERROR_FD_RST = w_DAT_ERROR_FD_RST_CMD | w_DAT_ERROR_FD_RST_DAT;
flopenr #(1) dat_error_fd
(.clk(r_G_CLK_SD),
.d(w_DATA_CRC16_GOOD),
.q(r_DAT_ERROR_Q),
.en(w_DAT_ERROR_FD_EN),
.reset((w_DAT_ERROR_FD_RST)));
assign w_NOT_DAT_ERROR_Q = ~r_DAT_ERROR_Q;
up_down_counter #(23) dat_fsm_timer
(
.CountIn(w_DAT_TIMER_IN),
.CountOut(r_DAT_TIMER_OUT),
.Load(w_DAT_TIMER_LOAD),
.Enable(w_DAT_TIMER_EN),
.UpDown(1'b0), // Count DOWN only
.clk(r_G_CLK_SD),
.reset(1'b0)); // No Reset, Just Load
SDCcounter #(11) dat_nibble_counter
(
.CountIn('0),
.CountOut(r_DAT_COUNTER_OUT),
.Load(1'b0),
.Enable(w_DAT_COUNTER_EN),
.clk(r_G_CLK_SD),
.reset(w_DAT_COUNTER_RST));
regfile_p2r1w1_nibo #(.DEPTH(10), .WIDTH(4) ) regfile_cmd17_data_block // Nibble In - Nibble Out (NINO)
(.clk(r_G_CLK_SD),
.we1(w_NIBO_EN),
.ra1(r_DAT_COUNTER_OUT[9:0]), // Nibble Read (to core) Address
.rd1(r_DATA_TO_CORE), // output nibble to core
.Rd1All(ReadData),
.wa1(r_DAT_COUNTER_OUT[9:0]), // Nibble Write (to host) Address
.wd1(r_DAT_Q)); // input nibble from card
crc16_sipo_np_ce crc16_sipo_np_ce_DAT3
(.CLK(r_G_CLK_SD),
.RST(w_CRC16_RST),
.i_enable(w_CRC16_EN),
.i_message_bit(r_DAT_Q[3]),
.o_crc16(r_DAT3_CRC16));
crc16_sipo_np_ce crc16_sipo_np_ce_DAT2
(.CLK(r_G_CLK_SD),
.RST(w_CRC16_RST),
.i_enable(w_CRC16_EN),
.i_message_bit(r_DAT_Q[2]),
.o_crc16(r_DAT2_CRC16));
crc16_sipo_np_ce crc16_sipo_np_ce_DAT1
(.CLK(r_G_CLK_SD),
.RST(w_CRC16_RST),
.i_enable(w_CRC16_EN),
.i_message_bit(r_DAT_Q[1]),
.o_crc16(r_DAT1_CRC16));
crc16_sipo_np_ce crc16_sipo_np_ce_DAT0
(.CLK(r_G_CLK_SD),
.RST(w_CRC16_RST),
.i_enable(w_CRC16_EN),
.i_message_bit(r_DAT_Q[0]),
.o_crc16(r_DAT0_CRC16));
assign w_DATA_CRC16_GOOD = ({r_DAT3_CRC16, r_DAT2_CRC16, r_DAT1_CRC16, r_DAT0_CRC16}) == 64'h0000000000000000;
flopenr #(4) busy_bit_fd
(.en(w_BUSY_EN),
.clk(r_G_CLK_SD),
.d(i_SD_DAT),
.q(r_DAT_Q),
.reset(w_BUSY_RST));
sd_clk_fsm my_clk_fsm
(.CLK(CLK),
.i_RST(a_RST),
.o_DONE(w_CLOCK_CHANGE_DONE),
.i_START(w_START_CLOCK_CHANGE),
.o_HS_TO_INIT_CLK_DIVIDER_RST(w_HS_TO_INIT_CLK_DIVIDER_RST),
.o_SD_CLK_SELECTED(w_SD_CLK_SELECTED),
.i_FATAL_ERROR(w_FATAL_ERROR),
.o_G_CLK_SD_EN(w_G_CLK_SD_EN));
up_down_counter #(19) cmd_fsm_timer
(.CountIn(w_TIMER_IN),
.CountOut(r_TIMER_OUT),
.Load(w_TIMER_LOAD),
.Enable(w_TIMER_EN),
.UpDown(1'b0), // Count DOWN only
.clk(r_G_CLK_SD),
.reset(1'b0)); // No Reset, Just Load
up_down_counter #(8) cmd_fsm_counter
(.CountIn(w_COUNTER_IN),
.CountOut(r_COUNTER_OUT),
.Load(w_COUNTER_LOAD),
.Enable(w_COUNTER_EN),
.UpDown(1'b0), // Count DOWN only
.clk(r_G_CLK_SD),
.reset(1'b0)); // No RESET, only LOAD
up_down_counter #(4) instruction_counter
(.CountIn('0), // No CountIn, only RESET
.CountOut(r_IC_OUT),
.Load(1'b0), // No LOAD, only RESET
.Enable(w_IC_EN),
.UpDown(w_IC_UP_DOWN),
.clk(r_G_CLK_SD),
.reset(w_IC_RST | a_RST));
// Clock selection
clkdivider #(g_COUNT_WIDTH) slow_clk_divider // Divide 50 MHz to <400 KHz (Initial clock)
(.i_COUNT_IN_MAX(i_COUNT_IN_MAX),
.i_EN(w_SD_CLK_SELECTED),
//.i_EN(1'b1),
//.i_RST(w_HS_TO_INIT_CLK_DIVIDER_RST),
.i_RST(a_RST),
.i_CLK(CLK),
.o_CLK(r_CLK_SD));
clockgater sd_clk_gater // Select which clock goes to components
(.CLK(r_CLK_SD),
.E(w_G_CLK_SD_EN | a_RST),
.SE(1'b0),
.ECLK(r_G_CLK_SD));
clockgater to_sd_clk_gater // Enable activity on the SD_CLK line
(.CLK(r_G_CLK_SD),
.E(w_SD_CLK_EN),
.SE(1'b0),
.ECLK(r_TO_SD_CLK));
flopenr #(16) RCA_register_CE
(.clk(r_G_CLK_SD),
.en(w_RCA_REGISTER_EN),
.d(w_RCA_D_Q),
.q(r_RCA_Q2),
.reset(w_RCA_REGISTER_RST));
// ACMD_Detector
flopenr #(1) index_history_fd_2to1
(.clk(r_G_CLK_SD),
.reset(w_CMD_TX_IS_CMD55_RST),
.en(w_CMD_TX_IS_CMD55_EN),
.d(r_command_index_is_55_history[2]),
.q(r_command_index_is_55_history[1]));
flopenr #(1) index_history_fd_1to0
(.clk(r_G_CLK_SD),
.reset(w_CMD_TX_IS_CMD55_RST),
.en(w_CMD_TX_IS_CMD55_EN),
.d(r_command_index_is_55_history[1]),
.q(r_command_index_is_55_history[0]));
assign r_command_index_is_55_history[2] = (w_command_index == 55);
assign r_previous_command_index_was_55_q = r_command_index_is_55_history[0];
assign r_ACMD_Q = r_previous_command_index_was_55_q; // if the previous command WAS 55, the current command is ACMD
assign o_SD_CLK = r_TO_SD_CLK;
// Multiplexers
//Fetch index and argument of command
assign w_command_content = (r_IC_OUT == 0) ? ({c_Go_Idle_State, 32'h00000000}) : // CMD0
(r_IC_OUT == 1) ? ({c_Send_IF_State, 32'h000001FF}) : // CMD8
(r_IC_OUT == 2) ? ({c_App_Command, 32'h00000000}) : // CMD55
(r_IC_OUT == 3) ? ({c_SD_Send_OCR, 32'h40FF8000}) : // ACMD41
(r_IC_OUT == 4) ? ({c_All_Send_CID, 32'h00000000}) : // CMD2
(r_IC_OUT == 5) ? ({c_SD_Send_RCA, 32'h00000000}) : // CMD3
(r_IC_OUT == 6) ? ({c_Select_Card, r_RCA_Q2[15:0], 16'h0000}) : // CMD7
(r_IC_OUT == 7) ? ({c_App_Command, r_RCA_Q2[15:0], 16'h0000}) : // CMD55
(r_IC_OUT == 8) ? ({c_Set_Bus_Width, 32'h00000002}) : // ACMD6
(r_IC_OUT == 9) ? ({c_Switch_Function, 32'h80FFFFF1}) : // CMD6
(r_IC_OUT == 10) ? ({c_Read_Single_Block, w_BLOCK_ADDR}) : // CMD17
({c_Read_Single_Block, w_BLOCK_ADDR}); // when in doubt just send CMD17
assign w_command_index = w_command_content[45:40];
assign w_command_arguments = w_command_content[39:8];
assign w_command_head = {c_start_bit, c_tx_host_command, w_command_content};
assign w_OPCODE_Q = {r_ACMD_Q, w_command_index};
// TX
crc7_pipo tx_crc7_pipo
(.CLK(r_G_CLK_SD),
.i_DATA(w_command_head),
.i_CRC_ENABLE(w_TX_CRC7_PIPO_EN),
.RST(w_TX_CRC7_PIPO_RST),
.o_CRC(r_TX_CRC7));
assign r_command_tail = {r_TX_CRC7, c_stop_bit};
piso_generic_ce #(40) tx_piso40_command_head
(.clk(r_G_CLK_SD),
.i_load(w_TX_PISO40_LOAD),
.i_data(w_command_head),
.i_en(w_TX_PISO40_EN),
.o_data(w_tx_head_Q));
piso_generic_ce #(8) tx_piso8_command_tail
(.clk(r_G_CLK_SD),
.i_load(w_TX_PISO8_LOAD),
.i_data(r_command_tail),
.i_en(w_TX_PISO8_EN),
.o_data(w_tx_tail_Q));
assign w_SD_CMD_TX_Q = (w_TX_SOURCE_SELECT == c_tx_low) ? 1'b0 :
(w_TX_SOURCE_SELECT == c_tx_high) ? 1'b1 :
(w_TX_SOURCE_SELECT == c_tx_head) ? w_tx_head_Q :
(w_TX_SOURCE_SELECT == c_tx_tail) ? w_tx_tail_Q :
1'b0;
assign w_SD_CMD_RX = i_SD_CMD;
flopenr #(1) sd_cmd_out_reg
(.d(w_SD_CMD_TX_Q),
.q(o_SD_CMD),
.en(1'b1),
.clk(~r_G_CLK_SD),
.reset(a_RST));
flopenr #(1) sd_cmd_out_oe_reg
(.d(w_SD_CMD_OE),
.q(o_SD_CMD_OE),
.en(1'b1),
.clk(~r_G_CLK_SD),
.reset(a_RST));
// RX
sipo_generic_ce #(48) rx_sipo48_response_content
(.clk(r_G_CLK_SD),
.rst(w_RX_SIPO48_RST),
.i_enable(w_RX_SIPO48_EN),
.i_message_bit(w_SD_CMD_RX),
.o_data(r_RX_RESPONSE));
assign r_RESPONSE_CONTENT = r_RX_RESPONSE[39:8];
assign r_RESPONSE_INDEX = r_RX_RESPONSE[45:40];
assign w_RCA_D_Q = r_RESPONSE_CONTENT[39:24];
crc7_sipo_np_ce rx_crc7_sipo
(.clk(r_G_CLK_SD),
.rst(w_RX_CRC7_SIPO_RST),
.i_enable(w_RX_CRC7_SIPO_EN),
.i_message_bit(w_SD_CMD_RX),
.o_crc7(r_RX_CRC7_Q));
// Fetch control bits using r_opcode
assign w_instruction_control_bits = (w_OPCODE_Q == ({c_CMD, c_Go_Idle_State})) ? ({c_response_type_R0_NONE, c_DAT_none, c_CMD0_mask_check_redo_bits, c_CMD0_ans_dont_redo, c_CMD0_mask_check_error_bits, c_CMD0_ans_error_free}) : // CMD0
(w_OPCODE_Q == ({c_CMD, c_All_Send_CID})) ? ({c_response_type_R2_CID_CSD, c_DAT_none, c_CMD2_mask_check_redo_bits, c_CMD2_ans_dont_redo, c_CMD2_mask_check_error_bits, c_CMD2_ans_error_free}): // CMD2
(w_OPCODE_Q == ({c_CMD, c_SD_Send_RCA})) ? ({c_response_type_R6_RCA, c_DAT_none, c_CMD3_mask_check_redo_bits, c_CMD3_ans_dont_redo, c_CMD3_mask_check_error_bits, c_CMD3_ans_error_free}) : // CMD3
(w_OPCODE_Q == ({c_CMD, c_Switch_Function})) ? ({c_response_type_R1_NORMAL, c_DAT_wide, c_CMD6_mask_check_redo_bits, c_CMD6_ans_dont_redo, c_CMD6_mask_check_error_bits, c_CMD6_ans_error_free}): // CMD6
(w_OPCODE_Q == ({c_ACMD, c_Set_Bus_Width})) ? ({c_response_type_R1_NORMAL, c_DAT_none, c_ACMD6_mask_check_redo_bits, c_ACMD6_ans_dont_redo, c_ACMD6_mask_check_error_bits, c_ACMD6_ans_error_free}): //ACMD6
(w_OPCODE_Q == ({c_CMD, c_Select_Card})) ? ({c_response_type_R1_NORMAL, c_DAT_busy, c_CMD7_mask_check_redo_bits, c_CMD7_ans_dont_redo, c_CMD7_mask_check_error_bits, c_CMD7_ans_error_free}): // CMD7
(w_OPCODE_Q == ({c_CMD, c_Send_IF_State})) ? ({c_response_type_R7_CIC, c_DAT_none, c_CMD8_mask_check_redo_bits, c_CMD8_ans_dont_redo, c_CMD8_mask_check_error_bits, c_CMD8_ans_error_free}): // CMD8
(w_OPCODE_Q == ({c_CMD, c_Read_Single_Block})) ? ({c_response_type_R1_NORMAL, c_DAT_block, c_CMD17_mask_check_redo_bits, c_CMD17_ans_dont_redo, c_CMD17_mask_check_error_bits, c_CMD17_ans_error_free}): // CMD17
(w_OPCODE_Q == ({c_ACMD, c_SD_Send_OCR})) ? ({c_response_type_R3_OCR, c_DAT_none, c_ACMD41_mask_check_redo_bits, c_ACMD41_ans_dont_redo, c_ACMD41_mask_check_error_bits, c_ACMD41_ans_error_free}) : //ACMD41
(w_OPCODE_Q == ({c_CMD, c_App_Command})) ? ({c_response_type_R1_NORMAL, c_DAT_none, c_CMD55_mask_check_redo_bits, c_CMD55_ans_dont_redo, c_CMD55_mask_check_error_bits, c_CMD55_ans_error_free}) : // CMD55
(w_OPCODE_Q == ({c_ACMD, c_App_Command})) ? ({c_response_type_R1_NORMAL, c_DAT_none, c_ACMD55_mask_check_redo_bits, c_ACMD55_ans_dont_redo, c_ACMD55_mask_check_error_bits, c_ACMD55_ans_error_free}) : //ACMD55
({c_response_type_R1_NORMAL, c_DAT_none, c_ACMD55_mask_check_redo_bits, c_ACMD55_ans_dont_redo, c_ACMD55_mask_check_error_bits, c_ACMD55_ans_error_free}); // when in doubt just send ACMD55
assign w_R_TYPE = w_instruction_control_bits[132:130];
assign w_USES_DAT = w_instruction_control_bits[129:128];
assign w_NO_REDO_MASK = w_instruction_control_bits[127:96];
assign w_NO_REDO_ANS = w_instruction_control_bits[95:64];
assign w_NO_ERROR_MASK = w_instruction_control_bits[63:32];
assign w_NO_ERROR_ANS = w_instruction_control_bits[31:0];
endmodule

View file

@ -0,0 +1,76 @@
module sd_top_wrapper #(parameter g_COUNT_WIDTH = 8)
(
input clk_in1_p,
input clk_in1_n,
input a_RST, // Reset signal (Must be held for minimum of 24 clock cycles)
// a_RST MUST COME OUT OF RESET SYNCHRONIZED TO THE 1.2 GHZ CLOCK!
// io_SD_CMD_z : inout std_logic; // SD CMD Bus
inout SD_CMD, // CMD Response from card
input [3:0] i_SD_DAT, // SD DAT Bus
output o_SD_CLK, // SD CLK Bus
// For communication with core cpu
output o_READY_FOR_READ, // tells core that initialization sequence is completed and
// sd card is ready to read a 512 byte block to the core.
// Held high during idle until i_READ_REQUEST is received
output o_SD_RESTARTING, // inform core the need to restart
input i_READ_REQUEST, // After Ready for read is sent to the core, the core will
// pulse this bit high to indicate it wants the block at this address
output [3:0] o_DATA_TO_CORE, // nibble being sent to core when DATA block is
// being published
output o_DATA_VALID // held high while data being read to core to indicate that it is valid
);
wire CLK;
wire LIMIT_SD_TIMERS;
wire [g_COUNT_WIDTH-1:0] i_COUNT_IN_MAX;
wire [4095:0] ReadData; // full 512 bytes to Bus
wire [32:9] i_BLOCK_ADDR; // see "Addressing" in parts.fods (only 8GB total capacity is used)
wire o_SD_CMD; // CMD Command from host
wire i_SD_CMD; // CMD Command from host
wire o_SD_CMD_OE; // Direction of SD_CMD
wire [2:0] o_ERROR_CODE_Q; // indicates which error occured
wire o_FATAL_ERROR; // indicates that the FATAL ERROR register has updated
wire o_LAST_NIBBLE; // pulse when last nibble is sent
assign LIMIT_SD_TIMERS = 1'b0;
assign i_COUNT_IN_MAX = -8'd62;
assign i_BLOCK_ADDR = 23'h0;
clk_wiz_0 clk_wiz_0(.clk_in1_p(clk_in1_p),
.clk_in1_n(clk_in1_n),
.reset(1'b0),
.clk_out1(CLK),
.locked(locked));
IOBUF SDCMDIODriver(.T(~o_SD_CMD_OE),
.I(o_SD_CMD),
.O(i_SD_CMD),
.IO(SD_CMD));
sd_top #(g_COUNT_WIDTH)
sd_top(.CLK(CLK),
.a_RST(a_RST),
.i_SD_CMD(i_SD_CMD), // CMD Response from card
.o_SD_CMD(o_SD_CMD), // CMD Command from host
.o_SD_CMD_OE(o_SD_CMD_OE), // Direction of SD_CMD
.i_SD_DAT(i_SD_DAT), // SD DAT Bus
.o_SD_CLK(o_SD_CLK), // SD CLK Bus
.i_BLOCK_ADDR(i_BLOCK_ADDR), // see "Addressing" in parts.fods (only 8GB total capacity is used)
.o_READY_FOR_READ(o_READY_FOR_READ), // tells core that initialization sequence is completed and
.o_SD_RESTARTING(o_SD_RESTARTING), // inform core the need to restart
.i_READ_REQUEST(i_READ_REQUEST), // After Ready for read is sent to the core, the core will
.o_DATA_TO_CORE(o_DATA_TO_CORE), // nibble being sent to core when DATA block is
.ReadData(ReadData), // full 512 bytes to Bus
.o_DATA_VALID(o_DATA_VALID), // held high while data being read to core to indicate that it is valid
.o_LAST_NIBBLE(o_LAST_NIBBLE), // pulse when last nibble is sent
.o_ERROR_CODE_Q(o_ERROR_CODE_Q), // indicates which error occured
.o_FATAL_ERROR(o_FATAL_ERROR), // indicates that the FATAL ERROR register has updated
.i_COUNT_IN_MAX(i_COUNT_IN_MAX),
.LIMIT_SD_TIMERS(LIMIT_SD_TIMERS)
);
endmodule

View file

@ -0,0 +1,55 @@
///////////////////////////////////////////
// simple_timer.sv
//
// Written: Ross Thompson September 20, 2021
// Modified:
//
// Purpose: SD card controller
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module simple_timer #(parameter BUS_WIDTH = 4)
(
input logic [BUS_WIDTH-1:0] VALUE,
input logic START,
output logic FLAG,
input logic RST,
input logic CLK);
logic [BUS_WIDTH-1:0] count;
logic timer_en;
assign timer_en = count != 0;
always_ff @(posedge CLK, posedge RST) begin
if (RST) begin
count <= '0;
end else if (START) begin
count <= VALUE - 1'b1;
end else if(timer_en) begin
count <= count - 1'b1;
end
end
assign FLAG = count != 0;
endmodule

View file

@ -0,0 +1,53 @@
///////////////////////////////////////////
// sipo_generic_ce
//
// Written: Ross Thompson September 20, 2021
// Modified:
//
// Purpose: serial to n-bit parallel shift register using register_ce.
// When given a n-bit word as input transmit the message serially MSB (leftmost)
// bit first.
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module sipo_generic_ce #(g_BUS_WIDTH)
(input logic clk,
input logic rst,
input logic i_enable, // data valid, write to register
input logic i_message_bit, // serial data
output logic [g_BUS_WIDTH-1:0] o_data // message received, parallel data
);
logic [g_BUS_WIDTH-1:0] w_reg_d;
logic [g_BUS_WIDTH-1:0] r_reg_q;
flopenr #(g_BUS_WIDTH) shiftReg
(.d(w_reg_d),
.q(r_reg_q),
.en(i_enable),
.reset(rst),
.clk(clk));
assign w_reg_d = {r_reg_q[g_BUS_WIDTH-2:0], i_message_bit};
assign o_data = r_reg_q;
endmodule

View file

@ -0,0 +1,12 @@
#!/usr/bin/python3
import sys, fileinput
address = 0
for line in fileinput.input('-'):
# the 14- is to reverse the byte order to little endian
formatedLine = ' '.join(line[14-i:14-i+2] for i in range(0, len(line), 2))
sys.stdout.write('@{:08x} {:s}\n'.format(address, formatedLine))
address+=8

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,17 @@
onbreak {resume}
# create library
if [file exists work] {
vdel -all
}
vlib work
vlog +incdir+../../../config/rv64ic +incdir+../../../config/shared ../../../testbench/common/*.sv ../../*/*.sv sd_top_tb.sv -suppress 2583
vopt -fsmdebug +acc -gDEBUG=1 work.sd_top_tb -o workopt
vsim workopt -fsmdebug
do wave.do
add log -r /*
run 3000 us

View file

@ -0,0 +1,119 @@
///////////////////////////////////////////
// sd_top_tb.sv
//
// Written: Ross Thompson September 20, 2021
// Modified:
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module sd_top_tb();
localparam integer g_COUNT_WIDTH = 8;
logic a_RST;
logic i_SD_CMD;
logic o_SD_CMD;
logic o_SD_CMD_OE;
wire [3:0] i_SD_DAT;
logic o_SD_CLK;
logic [32:9] i_BLOCK_ADDR;
logic [g_COUNT_WIDTH-1:0] i_COUNT_IN_MAX;
logic o_READY_FOR_READ;
logic i_READ_REQUEST;
logic [3:0] o_DATA_TO_CORE;
logic o_DATA_VALID;
logic o_LAST_NIBBLE;
logic [4095:0] ReadData;
// Driver
wire PAD;
logic r_CLK;
// clock
sd_top #(g_COUNT_WIDTH) DUT
(.CLK(r_CLK),
.a_RST(a_RST),
.i_SD_CMD(i_SD_CMD),
.o_SD_CMD(o_SD_CMD),
.o_SD_CMD_OE(o_SD_CMD_OE),
.i_SD_DAT(i_SD_DAT),
.o_SD_CLK(o_SD_CLK),
.i_BLOCK_ADDR(i_BLOCK_ADDR),
.o_READY_FOR_READ(o_READY_FOR_READ),
.i_READ_REQUEST(i_READ_REQUEST),
.o_DATA_TO_CORE(o_DATA_TO_CORE),
.ReadData(ReadData),
.o_DATA_VALID(o_DATA_VALID),
.o_LAST_NIBBLE(o_LAST_NIBBLE),
.i_COUNT_IN_MAX(i_COUNT_IN_MAX),
.LIMIT_SD_TIMERS(1'b1));
sdModel sdcard
(.sdClk(o_SD_CLK),
.cmd(PAD),
.dat(i_SD_DAT));
// tri state pad
// replace with I/O standard cell or FPGA gate.
assign PAD = o_SD_CMD_OE ? o_SD_CMD : 1'bz;
assign i_SD_CMD = PAD;
always
begin
r_CLK = 1; # 5; r_CLK = 0; # 5;
end
initial $readmemh("ramdisk2.hex", sdcard.FLASHmem);
initial begin
a_RST = 1'b0;
i_BLOCK_ADDR = 24'h100000;
i_COUNT_IN_MAX = '0;
i_READ_REQUEST = 1'b0;
# 5;
i_COUNT_IN_MAX = -62;
# 10;
a_RST = 1'b1;
# 4800;
a_RST = 1'b0;
# 2000000;
i_READ_REQUEST = 1'b0;
# 10000;
i_READ_REQUEST = 1'b1;
# 10000;
i_READ_REQUEST = 1'b0;
end
endmodule

View file

@ -0,0 +1,128 @@
onerror {resume}
quietly WaveActivateNextPane {} 0
add wave -noupdate /sd_top_tb/DUT/a_RST
add wave -noupdate /sd_top_tb/DUT/CLK
add wave -noupdate /sd_top_tb/DUT/i_BLOCK_ADDR
add wave -noupdate /sd_top_tb/DUT/i_READ_REQUEST
add wave -noupdate /sd_top_tb/DUT/i_COUNT_IN_MAX
add wave -noupdate /sd_top_tb/DUT/LIMIT_SD_TIMERS
add wave -noupdate /sd_top_tb/DUT/o_READY_FOR_READ
add wave -noupdate /sd_top_tb/DUT/o_SD_RESTARTING
add wave -noupdate /sd_top_tb/DUT/o_DATA_TO_CORE
add wave -noupdate /sd_top_tb/DUT/o_DATA_VALID
add wave -noupdate /sd_top_tb/DUT/o_LAST_NIBBLE
add wave -noupdate /sd_top_tb/DUT/o_ERROR_CODE_Q
add wave -noupdate /sd_top_tb/DUT/o_FATAL_ERROR
add wave -noupdate -expand -group interface /sd_top_tb/DUT/o_SD_CLK
add wave -noupdate -expand -group interface /sd_top_tb/DUT/o_SD_CMD
add wave -noupdate -expand -group interface /sd_top_tb/DUT/o_SD_CMD_OE
add wave -noupdate -expand -group interface /sd_top_tb/DUT/i_SD_CMD
add wave -noupdate -expand -group interface /sd_top_tb/DUT/i_SD_DAT
add wave -noupdate -label {cmd fsm} /sd_top_tb/DUT/my_sd_cmd_fsm/r_curr_state
add wave -noupdate -label {dat fsm} /sd_top_tb/DUT/my_sd_dat_fsm/r_curr_state
add wave -noupdate -label {clk fsm} /sd_top_tb/DUT/my_clk_fsm/r_curr_state
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_RST
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_TIMER_OUT
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_COUNTER_OUT
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_CLOCK_CHANGE_DONE
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_IC_OUT
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_USES_DAT
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_OPCODE
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_R_TYPE
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_NO_REDO_MASK
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_NO_REDO_ANS
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_NO_ERROR_MASK
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_NO_ERROR_ANS
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_SD_CMD_RX
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_RESPONSE_CONTENT
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_RESPONSE_INDEX
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_RX_CRC7
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_DAT_RX_DONE
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_ERROR_CRC16
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_ERROR_DAT_TIMES_OUT
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/i_READ_REQUEST
add wave -noupdate -group old /sd_top_tb/DUT/my_sd_cmd_fsm/LIMIT_SD_TIMERS
add wave -noupdate -group old /sd_top_tb/DUT/my_clk_fsm/i_START
add wave -noupdate -group old /sd_top_tb/DUT/my_clk_fsm/i_FATAL_ERROR
add wave -noupdate -group old /sd_top_tb/DUT/my_clk_fsm/i_RST
add wave -noupdate -group old /sd_top_tb/DUT/my_clk_fsm/o_DONE
add wave -noupdate -group old /sd_top_tb/DUT/my_clk_fsm/o_G_CLK_SD_EN
add wave -noupdate -group old /sd_top_tb/DUT/my_clk_fsm/o_HS_TO_INIT_CLK_DIVIDER_RST
add wave -noupdate -group old /sd_top_tb/DUT/my_clk_fsm/o_SD_CLK_SELECTED
add wave -noupdate -group old -expand /sd_top_tb/DUT/w_OPCODE_Q
add wave -noupdate -group old /sd_top_tb/DUT/c_CMD
add wave -noupdate -group old /sd_top_tb/DUT/c_ACMD
add wave -noupdate -group old /sd_top_tb/DUT/c_Go_Idle_State
add wave -noupdate -group old /sd_top_tb/DUT/c_response_type_R0_NONE
add wave -noupdate -group old /sd_top_tb/DUT/c_response_type_R0_NONE
add wave -noupdate -group old /sd_top_tb/DUT/c_response_type_R1_NORMAL
add wave -noupdate -group old /sd_top_tb/DUT/c_response_type_R2_CID_CSD
add wave -noupdate -group old /sd_top_tb/DUT/c_response_type_R3_OCR
add wave -noupdate -group old /sd_top_tb/DUT/c_response_type_R6_RCA
add wave -noupdate -group old /sd_top_tb/DUT/c_response_type_R7_CIC
add wave -noupdate -group old /sd_top_tb/DUT/w_instruction_control_bits
add wave -noupdate -group old /sd_top_tb/DUT/w_command_index
add wave -noupdate -group old /sd_top_tb/DUT/r_IC_OUT
add wave -noupdate -group old /sd_top_tb/DUT/w_BLOCK_ADDR
add wave -noupdate /sd_top_tb/DUT/w_TX_SOURCE_SELECT
add wave -noupdate /sd_top_tb/DUT/w_tx_tail_Q
add wave -noupdate /sd_top_tb/DUT/w_TX_PISO8_LOAD
add wave -noupdate /sd_top_tb/DUT/w_TX_PISO8_EN
add wave -noupdate /sd_top_tb/DUT/r_command_tail
add wave -noupdate /sd_top_tb/DUT/r_TX_CRC7
add wave -noupdate /sd_top_tb/DUT/w_TX_CRC7_PIPO_RST
add wave -noupdate /sd_top_tb/DUT/w_TX_CRC7_PIPO_EN
add wave -noupdate /sd_top_tb/DUT/w_command_head
add wave -noupdate /sd_top_tb/DUT/my_sd_dat_fsm/i_DAT0_Q
add wave -noupdate /sd_top_tb/sdcard/oeDat
add wave -noupdate /sd_top_tb/sdcard/datOut
add wave -noupdate /sd_top_tb/sdcard/dat
add wave -noupdate /sd_top_tb/DUT/my_sd_cmd_fsm/w_resend_last_command
add wave -noupdate /sd_top_tb/DUT/my_sd_cmd_fsm/i_ERROR_CRC16
add wave -noupdate /sd_top_tb/DUT/r_DAT3_CRC16
add wave -noupdate /sd_top_tb/DUT/r_DAT2_CRC16
add wave -noupdate /sd_top_tb/DUT/r_DAT1_CRC16
add wave -noupdate /sd_top_tb/DUT/r_DAT0_CRC16
add wave -noupdate -radix decimal /sd_top_tb/DUT/my_sd_cmd_fsm/i_COUNTER_OUT
add wave -noupdate /sd_top_tb/DUT/CLK
add wave -noupdate /sd_top_tb/DUT/r_CLK_SD
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/i_COUNT_IN_MAX
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/i_EN
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/i_CLK
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/i_RST
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/g_COUNT_WIDTH
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/r_count_out
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/w_counter_overflowed
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/r_fd_Q
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/w_fd_D
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/w_load
add wave -noupdate -expand -group {clock divider} /sd_top_tb/DUT/slow_clk_divider/o_CLK
add wave -noupdate /sd_top_tb/sdcard/ByteAddr
add wave -noupdate /sd_top_tb/sdcard/write_out_index
add wave -noupdate /sd_top_tb/sdcard/inCmd
add wave -noupdate /sd_top_tb/DUT/w_TX_SOURCE_SELECT
add wave -noupdate /sd_top_tb/DUT/w_command_head
add wave -noupdate /sd_top_tb/DUT/r_IC_OUT
add wave -noupdate /sd_top_tb/DUT/w_BLOCK_ADDR
add wave -noupdate /sd_top_tb/DUT/i_BLOCK_ADDR
add wave -noupdate /sd_top_tb/DUT/regfile_cmd17_data_block/regs
add wave -noupdate /sd_top_tb/DUT/regfile_cmd17_data_block/ra1
add wave -noupdate /sd_top_tb/ReadData
TreeUpdate [SetDefaultTree]
WaveRestoreCursors {{Cursor 1} {2028326 ns} 0} {{Cursor 2} {4831 ns} 0}
quietly wave cursor active 1
configure wave -namecolwidth 245
configure wave -valuecolwidth 180
configure wave -justifyvalue left
configure wave -signalnamewidth 1
configure wave -snapdistance 10
configure wave -datasetprefix 0
configure wave -rowmargin 4
configure wave -childrowmargin 2
configure wave -gridoffset 0
configure wave -gridperiod 1
configure wave -griddelta 40
configure wave -timeline 0
configure wave -timelineunits ns
update
WaveRestoreZoom {1979107 ns} {2077545 ns}

View file

@ -0,0 +1,55 @@
///////////////////////////////////////////
// counter.sv
//
// Written: Ross Thompson
// Modified:
//
// Purpose: basic up counter
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module up_down_counter #(parameter integer WIDTH=32)
(
input logic [WIDTH-1:0] CountIn,
output logic [WIDTH-1:0] CountOut,
input logic Load,
input logic Enable,
input logic UpDown,
input logic clk,
input logic reset);
logic [WIDTH-1:0] NextCount;
logic [WIDTH-1:0] count_q;
logic [WIDTH-1:0] CountP1;
flopenr #(WIDTH) reg1(.clk,
.reset,
.en(Enable | Load),
.d(NextCount),
.q(CountOut));
assign CountP1 = UpDown ? CountOut + 1'b1 : CountOut - 1'b1;
// mux between load and P1
assign NextCount = Load ? CountIn : CountP1;
endmodule

View file

@ -25,7 +25,7 @@
`include "wally-config.vh"
module dtim #(parameter BASE=0, RANGE = 65535) (
module dtim #(parameter BASE=0, RANGE = 65535, string PRELOAD="") (
input logic HCLK, HRESETn,
input logic HSELTim,
input logic [31:0] HADDR,
@ -49,6 +49,51 @@ module dtim #(parameter BASE=0, RANGE = 65535) (
logic memwrite;
logic [3:0] busycount;
initial begin
//$readmemh(PRELOAD, RAM);
RAM[0] = 64'h94e1819300002197;
RAM[1] = 64'h4281420141014081;
RAM[2] = 64'h4481440143814301;
RAM[3] = 64'h4681460145814501;
RAM[4] = 64'h4881480147814701;
RAM[5] = 64'h4a814a0149814901;
RAM[6] = 64'h4c814c014b814b01;
RAM[7] = 64'h4e814e014d814d01;
RAM[8] = 64'h0110011b4f814f01;
RAM[9] = 64'h059b45011161016e;
RAM[10] = 64'h0004063705fe0010;
RAM[11] = 64'h05a000ef8006061b;
RAM[12] = 64'h0ff003930000100f;
RAM[13] = 64'h4e952e3110012e37;
RAM[14] = 64'hc602829b0053f2b7;
RAM[15] = 64'h2023fe02dfe312fd;
RAM[16] = 64'h829b0053f2b7007e;
RAM[17] = 64'hfe02dfe312fdc602;
RAM[18] = 64'h4de31efd000e2023;
RAM[19] = 64'h059bf1402573fdd0;
RAM[20] = 64'h0000061705e20870;
RAM[21] = 64'h0010029b01260613;
RAM[22] = 64'h11010002806702fe;
RAM[23] = 64'h84b2842ae426e822;
RAM[24] = 64'h892ee04aec064505;
RAM[25] = 64'h06e000ef07e000ef;
RAM[26] = 64'h979334fd02905563;
RAM[27] = 64'h07930177d4930204;
RAM[28] = 64'h4089093394be2004;
RAM[29] = 64'h04138522008905b3;
RAM[30] = 64'h19e3014000ef2004;
RAM[31] = 64'h64a2644260e2fe94;
RAM[32] = 64'h6749808261056902;
RAM[33] = 64'hdfed8b8510472783;
RAM[34] = 64'h2423479110a73823;
RAM[35] = 64'h10472783674910f7;
RAM[36] = 64'h20058693ffed8b89;
RAM[37] = 64'h05a1118737836749;
RAM[38] = 64'hfed59be3fef5bc23;
RAM[39] = 64'h1047278367498082;
RAM[40] = 64'h67c98082dfed8b85;
RAM[41] = 64'h0000808210a7a023;
end
assign initTrans = HREADY & HSELTim & (HTRANS != 2'b00);
@ -111,6 +156,9 @@ module dtim #(parameter BASE=0, RANGE = 65535) (
endgenerate
/* verilator lint_on WIDTH */
assign HREADTim = HREADYTim ? HREADTim0 : `XLEN'bz;
//assign HREADTim = HREADYTim ? HREADTim0 : `XLEN'bz;
// *** Ross Thompson: removed tristate as fpga synthesis removes.
assign HREADTim = HREADTim0;
endmodule

View file

@ -35,9 +35,9 @@ module uart (
input logic [`XLEN-1:0] HWDATA,
output logic [`XLEN-1:0] HREADUART,
output logic HRESPUART, HREADYUART,
input logic SIN, DSRb, DCDb, CTSb, RIb, // from E1A driver from RS232 interface
output logic SOUT, RTSb, DTRb, // to E1A driver to RS232 interface
output logic OUT1b, OUT2b, INTR, TXRDYb, RXRDYb); // to CPU
(* mark_debug = "true" *) input logic SIN, DSRb, DCDb, CTSb, RIb, // from E1A driver from RS232 interface
(* mark_debug = "true" *) output logic SOUT, RTSb, DTRb, // to E1A driver to RS232 interface
(* mark_debug = "true" *) output logic OUT1b, OUT2b, INTR, TXRDYb, RXRDYb); // to CPU
// UART interface signals
logic [2:0] A;

View file

@ -137,23 +137,26 @@ module uartPC16550D(
MCR <= #1 5'b0;
LSR <= #1 8'b01100000;
MSR <= #1 4'b0;
DLL <= #1 8'd1; // this cannot be zero with DLM also zer0.
DLM <= #1 8'b0;
if (`FPGA) begin
DLL <= #1 8'd11;
DLM <= #1 8'b0;
end else begin
DLL <= #1 8'd1; // this cannot be zero with DLM also zer0.
DLM <= #1 8'b0;
end
/* -----\/----- EXCLUDED -----\/-----
DLL <= #1 8'd11;
DLM <= #1 8'b0;
-----/\----- EXCLUDED -----/\----- */
SCR <= #1 8'b0; // not strictly necessary to reset
end else begin
if (~MEMWb) begin
case (A)
/* -----\/----- EXCLUDED -----\/-----
3'b000: if (DLAB) DLL <= #1 Din; // else TXHR <= #1 Din; // TX handled in TX register/FIFO section
3'b001: if (DLAB) DLM <= #1 Din; else IER <= #1 Din[3:0];
// *** BUG FIX ME for now for the divider to be 11. Our clock is 10 Mhz. 10Mhz /(11 * 16) = 56818 baud, which is close enough to 57600 baud
/* -----\/----- EXCLUDED -----\/-----
3'b000: if (DLAB) DLL <= #1 8'd11 else TXHR <= #1 Din; // TX handled in TX register/FIFO section
3'b001: if (DLAB) DLM <= #1 8'b0; else IER <= #1 Din[3:0];
-----/\----- EXCLUDED -----/\----- */
// *** BUG FIX ME for now for the divider to be 11. Our clock is 10 Mhz. 10Mhz /(11 * 16) = 56818 baud, which is close enough to 57600 baud
3'b000: if (DLAB) DLL <= #1 8'd11; //else TXHR <= #1 Din; // TX handled in TX register/FIFO section
3'b001: if (DLAB) DLM <= #1 8'b0; else IER <= #1 Din[3:0];
3'b010: FCR <= #1 {Din[7:6], 2'b0, Din[3], 2'b0, Din[0]}; // Write only FIFO Control Register; 4:5 reserved and 2:1 self-clearing
3'b011: LCR <= #1 Din;

View file

@ -43,6 +43,7 @@ module uncore (
input logic HREADYEXT, HRESPEXT,
output logic [`AHBW-1:0] HRDATA,
output logic HREADY, HRESP,
output logic HSELEXT,
// delayed signals
input logic [2:0] HADDRD,
input logic [3:0] HSIZED,
@ -53,38 +54,48 @@ module uncore (
output logic [31:0] GPIOPinsOut, GPIOPinsEn,
input logic UARTSin,
output logic UARTSout,
output logic SDCCmdOut,
output logic SDCCmdOE,
input logic SDCCmdIn,
input logic [3:0] SDCDatIn,
output logic SDCCLK,
output logic [63:0] MTIME_CLINT, MTIMECMP_CLINT
);
logic [`XLEN-1:0] HWDATA;
logic [`XLEN-1:0] HREADTim, HREADCLINT, HREADPLIC, HREADGPIO, HREADUART;
logic [`XLEN-1:0] HREADTim, HREADCLINT, HREADPLIC, HREADGPIO, HREADUART, HREADSDC;
logic [6:0] HSELRegions;
logic HSELTim, HSELCLINT, HSELPLIC, HSELGPIO, HSELUART;
logic HSELTimD, HSELCLINTD, HSELPLICD, HSELGPIOD, HSELUARTD;
logic HRESPTim, HRESPCLINT, HRESPPLIC, HRESPGPIO, HRESPUART;
logic HREADYTim, HREADYCLINT, HREADYPLIC, HREADYGPIO, HREADYUART;
logic [8:0] HSELRegions;
logic HSELTim, HSELCLINT, HSELPLIC, HSELGPIO, HSELUART, HSELSDC;
logic HSELEXTD, HSELTimD, HSELCLINTD, HSELPLICD, HSELGPIOD, HSELUARTD, HSELSDCD;
logic HRESPTim, HRESPCLINT, HRESPPLIC, HRESPGPIO, HRESPUART, HRESPSDC;
logic HREADYTim, HREADYCLINT, HREADYPLIC, HREADYGPIO, HREADYUART, HRESPSDCD;
logic [`XLEN-1:0] HREADBootTim;
logic HSELBootTim, HSELBootTimD, HRESPBootTim, HREADYBootTim;
logic HSELBootTim, HSELBootTimD, HRESPBootTim, HREADYBootTim, HREADYSDC;
logic HSELNoneD;
logic UARTIntr,GPIOIntr;
logic SDCIntM;
// Determine which region of physical memory (if any) is being accessed
// Use a trimmed down portion of the PMA checker - only the address decoders
// Set access types to all 1 as don't cares because the MMU has already done access checking
adrdecs adrdecs({{(`PA_BITS-32){1'b0}}, HADDR}, 1'b1, 1'b1, 1'b1, HSIZE[1:0], HSELRegions);
// unswizzle HSEL signals
assign {HSELBootTim, HSELTim, HSELCLINT, HSELGPIO, HSELUART, HSELPLIC} = HSELRegions[5:0];
assign {HSELEXT, HSELBootTim, HSELTim, HSELCLINT, HSELGPIO, HSELUART, HSELPLIC, HSELSDC} = HSELRegions[7:0];
// subword accesses: converts HWDATAIN to HWDATA
subwordwrite sww(.*);
generate
// tightly integrated memory
dtim #(.BASE(`TIM_BASE), .RANGE(`TIM_RANGE)) dtim (.*);
if (`TIM_SUPPORTED) begin : dtim
dtim #(.BASE(`TIM_BASE), .RANGE(`TIM_RANGE)) dtim (.*);
end
if (`BOOTTIM_SUPPORTED) begin : bootdtim
dtim #(.BASE(`BOOTTIM_BASE), .RANGE(`BOOTTIM_RANGE)) bootdtim(.HSELTim(HSELBootTim), .HREADTim(HREADBootTim), .HRESPTim(HRESPBootTim), .HREADYTim(HREADYBootTim), .*);
dtim #(.BASE(`BOOTTIM_BASE), .RANGE(`BOOTTIM_RANGE), .PRELOAD("blink-led.mem"))
bootdtim(.HSELTim(HSELBootTim), .HREADTim(HREADBootTim), .HRESPTim(HRESPBootTim), .HREADYTim(HREADYBootTim), .*);
end
// memory-mapped I/O peripherals
@ -111,31 +122,52 @@ module uncore (
end else begin : uart
assign UARTSout = 0; assign UARTIntr = 0;
end
if (`SDC_SUPPORTED == 1) begin : sdc
SDC SDC(.HCLK, .HRESETn, .HSELSDC, .HADDR(HADDR[4:0]), .HWRITE, .HREADY, .HTRANS,
.HWDATA, .HREADSDC, .HRESPSDC, .HREADYSDC,
// sdc interface
.SDCCmdOut, .SDCCmdIn, .SDCCmdOE, .SDCDatIn, .SDCCLK,
// interrupt to PLIC
.SDCIntM
);
end else begin : sdc
assign SDCCLK = 0;
assign SDCCmdOut = 0;
assign SDCCmdOE = 0;
end
endgenerate
// mux could also include external memory
// AHB Read Multiplexer
assign HRDATA = ({`XLEN{HSELTimD}} & HREADTim) |
assign HRDATA = ({`XLEN{HSELTimD}} & HREADTim) |
({`XLEN{HSELEXTD}} & HRDATAEXT) |
({`XLEN{HSELCLINTD}} & HREADCLINT) |
({`XLEN{HSELPLICD}} & HREADPLIC) |
({`XLEN{HSELGPIOD}} & HREADGPIO) |
({`XLEN{HSELBootTimD}} & HREADBootTim) |
({`XLEN{HSELUARTD}} & HREADUART);
({`XLEN{HSELUARTD}} & HREADUART) |
({`XLEN{HSELSDCD}} & HREADSDC);
assign HRESP = HSELTimD & HRESPTim |
HSELEXTD & HRESPEXT |
HSELCLINTD & HRESPCLINT |
HSELPLICD & HRESPPLIC |
HSELGPIOD & HRESPGPIO |
HSELBootTimD & HRESPBootTim |
HSELUARTD & HRESPUART;
assign HREADY = HSELTimD & HREADYTim |
HSELUARTD & HRESPUART |
HSELSDC & HRESPSDC;
assign HREADY = HSELTimD & HREADTim |
HSELEXTD & HREADYEXT |
HSELCLINTD & HREADYCLINT |
HSELPLICD & HREADYPLIC |
HSELGPIOD & HREADYGPIO |
HSELBootTimD & HREADYBootTim |
HSELUARTD & HREADYUART |
HSELSDCD & HREADYSDC |
HSELNoneD; // don't lock up the bus if no region is being accessed
// Address Decoder Delay (figure 4-2 in spec)
flopr #(7) hseldelayreg(HCLK, ~HRESETn, HSELRegions, {HSELNoneD, HSELBootTimD, HSELTimD, HSELCLINTD, HSELGPIOD, HSELUARTD, HSELPLICD});
flopr #(9) hseldelayreg(HCLK, ~HRESETn, HSELRegions, {HSELNoneD, HSELEXTD, HSELBootTimD, HSELTimD, HSELCLINTD, HSELGPIOD, HSELUARTD, HSELPLICD, HSELSDCD});
endmodule

View file

@ -52,7 +52,8 @@ module wallypipelinedhart (
// logic [1:0] ForwardAE, ForwardBE;
logic StallF, StallD, StallE, StallM, StallW;
logic FlushF, FlushD, FlushE, FlushM, FlushW;
logic RetM, TrapM;
logic RetM;
(* mark_debug = "true" *) logic TrapM;
// new signals that must connect through DP
logic MulDivE, W64E;
@ -63,13 +64,15 @@ module wallypipelinedhart (
logic [`XLEN-1:0] SrcAM;
logic [2:0] Funct3E;
// logic [31:0] InstrF;
logic [31:0] InstrD, InstrM;
logic [`XLEN-1:0] PCF, PCE, PCM, PCLinkE;
logic [31:0] InstrD, InstrW;
(* mark_debug = "true" *) logic [31:0] InstrM;
logic [`XLEN-1:0] PCF, PCD, PCE, PCLinkE;
(* mark_debug = "true" *) logic [`XLEN-1:0] PCM;
logic [`XLEN-1:0] PCTargetE;
logic [`XLEN-1:0] CSRReadValW, MulDivResultW;
logic [`XLEN-1:0] PrivilegedNextPCM;
logic [1:0] MemRWM;
logic InstrValidM;
(* mark_debug = "true" *) logic [1:0] MemRWM;
(* mark_debug = "true" *) logic InstrValidM;
logic InstrMisalignedFaultM;
logic IllegalBaseInstrFaultD, IllegalIEUInstrFaultD;
logic ITLBInstrPageFaultF, DTLBLoadPageFaultM, DTLBStorePageFaultM;
@ -119,8 +122,10 @@ module wallypipelinedhart (
// cpu lsu interface
logic [2:0] Funct3M;
logic [`XLEN-1:0] MemAdrM, MemAdrE, WriteDataM;
logic [`XLEN-1:0] ReadDataM;
logic [`XLEN-1:0] MemAdrE;
(* mark_debug = "true" *) logic [`XLEN-1:0] WriteDataM;
(* mark_debug = "true" *) logic [`XLEN-1:0] MemAdrM;
(* mark_debug = "true" *) logic [`XLEN-1:0] ReadDataM;
logic [`XLEN-1:0] ReadDataW;
logic CommittedM;

View file

@ -32,32 +32,39 @@
`include "wally-config.vh"
module wallypipelinedsoc (
input logic clk, reset_ext,
output logic reset,
input logic clk, reset_ext,
// AHB Lite Interface
// inputs from external memory
input logic [`AHBW-1:0] HRDATAEXT,
input logic HREADYEXT, HRESPEXT,
input logic [`AHBW-1:0] HRDATAEXT,
input logic HREADYEXT, HRESPEXT,
output logic HSELEXT,
// outputs to external memory, shared with uncore memory
output logic HCLK, HRESETn,
output logic [31:0] HADDR,
output logic HCLK, HRESETn,
output logic [31:0] HADDR,
output logic [`AHBW-1:0] HWDATA,
output logic HWRITE,
output logic [2:0] HSIZE,
output logic [2:0] HBURST,
output logic [3:0] HPROT,
output logic [1:0] HTRANS,
output logic HMASTLOCK,
output logic HWRITE,
output logic [2:0] HSIZE,
output logic [2:0] HBURST,
output logic [3:0] HPROT,
output logic [1:0] HTRANS,
output logic HMASTLOCK,
output logic HREADY,
// I/O Interface
input logic [31:0] GPIOPinsIn,
output logic [31:0] GPIOPinsOut, GPIOPinsEn,
input logic UARTSin,
output logic UARTSout
input logic [31:0] GPIOPinsIn,
output logic [31:0] GPIOPinsOut, GPIOPinsEn,
input logic UARTSin,
output logic UARTSout,
input logic SDCCmdIn,
output logic SDCCmdOut,
output logic SDCCmdOE,
input logic [3:0] SDCDatIn,
output logic SDCCLK
);
// Uncore signals
logic reset;
logic [`AHBW-1:0] HRDATA; // from AHB mux in uncore
logic HREADY, HRESP;
logic HRESP;
logic TimerIntM, SwIntM; // from CLINT
logic [63:0] MTIME_CLINT, MTIMECMP_CLINT; // from CLINT to CSRs
logic ExtIntM; // from PLIC
@ -80,6 +87,9 @@ module wallypipelinedsoc (
uncore uncore(.HCLK, .HRESETn,
.HADDR, .HWDATAIN(HWDATA), .HWRITE, .HSIZE, .HBURST, .HPROT, .HTRANS, .HMASTLOCK, .HRDATAEXT,
.HREADYEXT, .HRESPEXT, .HRDATA, .HREADY, .HRESP, .HADDRD, .HSIZED, .HWRITED,
.TimerIntM, .SwIntM, .ExtIntM, .GPIOPinsIn, .GPIOPinsOut, .GPIOPinsEn, .UARTSin, .UARTSout, .MTIME_CLINT, .MTIMECMP_CLINT
.TimerIntM, .SwIntM, .ExtIntM, .GPIOPinsIn, .GPIOPinsOut, .GPIOPinsEn, .UARTSin, .UARTSout, .MTIME_CLINT, .MTIMECMP_CLINT,
.HSELEXT,
.SDCCmdOut, .SDCCmdOE, .SDCCmdIn, .SDCDatIn, .SDCCLK
);
endmodule
endmodule

View file

@ -0,0 +1,120 @@
///////////////////////////////////////////
// wally-pipelinedsoc.sv
//
// Written: David_Harris@hmc.edu 6 November 2020
// Modified:
//
// Purpose: System on chip including pipelined processor and memories
// Full RV32/64IC instruction set
//
// Note: the CSRs do not support the following features
//- Disabling portions of the instruction set with bits of the MISA register
//- Changing from RV64 to RV32 by writing the SXL/UXL bits of the STATUS register
// As of January 2020, virtual memory is not yet supported
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
// modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
// is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
// OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
///////////////////////////////////////////
`include "wally-config.vh"
module wallypipelinedsocwrapper (
input clk, reset,
// AHB Lite Interface
// inputs from external memory
input [`AHBW-1:0] HRDATAEXT,
input HREADYEXT, HRESPEXT,
output HSELEXT,
// outputs to external memory, shared with uncore memory
output HCLK, HRESETn,
output [31:0] HADDR,
output [`AHBW-1:0] HWDATA,
output HWRITE,
output [2:0] HSIZE,
output [2:0] HBURST,
output [3:0] HPROT,
output [1:0] HTRANS,
output HMASTLOCK,
output HREADY,
// I/O Interface
input [3:0] GPIOPinsIn_IO,
output [4:0] GPIOPinsOut_IO,
input UARTSin,
output UARTSout,
input ddr4_calib_complete,
input [3:0] SDCDatIn,
output SDCCLK,
input SDCCmdIn,
output SDCCmdOut,
output SDCCmdOE
);
wire [31:0] GPIOPinsEn;
wire [31:0] GPIOPinsIn;
wire [31:0] GPIOPinsOut;
// to instruction memory *** remove later
wire [`XLEN-1:0] PCF;
// Uncore signals
wire [`AHBW-1:0] HRDATA; // from AHB mux in uncore
wire HRESP;
wire [5:0] HSELRegions;
wire InstrAccessFaultF, DataAccessFaultM;
wire TimerIntM, SwIntM; // from CLINT
wire [63:0] MTIME_CLINT, MTIMECMP_CLINT; // from CLINT to CSRs
wire ExtIntM; // from PLIC
wire [2:0] HADDRD;
wire [3:0] HSIZED;
wire HWRITED;
wire [15:0] rd2; // bogus, delete when real multicycle fetch works
wire [31:0] InstrF;
assign GPIOPinsOut_IO = GPIOPinsOut[4:0];
assign GPIOPinsIn = {28'b0, GPIOPinsIn_IO};
// wrapper for fpga
wallypipelinedsoc wallypipelinedsoc
(.clk(clk),
.reset_ext(reset),
.HRDATAEXT(HRDATAEXT),
.HREADYEXT(HREADYEXT),
.HRESPEXT(HRESPEXT),
.HSELEXT(HSELEXT),
.HCLK(HCLK),
.HRESETn(HRESETn),
.HADDR(HADDR),
.HWDATA(HWDATA),
.HWRITE(HWRITE),
.HSIZE(HSIZE),
.HBURST(HBURST),
.HPROT(HPROT),
.HTRANS(HTRANS),
.HMASTLOCK(HMASTLOCK),
.HREADY(HREADY),
.GPIOPinsIn(GPIOPinsIn),
.GPIOPinsOut(GPIOPinsOut),
.GPIOPinsEn(GPIOPinsEn),
.UARTSin(UARTSin),
.UARTSout(UARTSout),
.SDCDatIn(SDCDatIn),
.SDCCLK(SDCCLK),
.SDCCmdIn(SDCCmdIn),
.SDCCmdOut(SDCCmdOut),
.SDCCmdOE(SDCCmdOE));
endmodule

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,48 @@
// ==========================================================================
// CRC Generation Unit - Linear Feedback Shift Register implementation
// (c) Kay Gorontzi, GHSi.de, distributed under the terms of LGPL
// https://www.ghsi.de/CRC/index.php?
// https://www.ghsi.de/CRC/index.php?
// =========================================================================
module sd_crc_16(BITVAL, Enable, CLK, RST, CRC);
input BITVAL;// Next input bit
input Enable;
input CLK; // Current bit valid (Clock)
input RST; // Init CRC value
output reg [15:0] CRC; // Current output CRC value
// We need output registers
wire inv;
assign inv = BITVAL ^ CRC[15]; // XOR required?
always @(posedge CLK or posedge RST) begin
if (RST) begin
CRC = 0;
end
else begin
if (Enable==1) begin
CRC[15] = CRC[14];
CRC[14] = CRC[13];
CRC[13] = CRC[12];
CRC[12] = CRC[11] ^ inv;
CRC[11] = CRC[10];
CRC[10] = CRC[9];
CRC[9] = CRC[8];
CRC[8] = CRC[7];
CRC[7] = CRC[6];
CRC[6] = CRC[5];
CRC[5] = CRC[4] ^ inv;
CRC[4] = CRC[3];
CRC[3] = CRC[2];
CRC[2] = CRC[1];
CRC[1] = CRC[0];
CRC[0] = inv;
end
end
end
endmodule

View file

@ -0,0 +1,34 @@
module sd_crc_7(BITVAL, Enable, CLK, RST, CRC);
input BITVAL;// Next input bit
input Enable;
input CLK; // Current bit valid (Clock)
input RST; // Init CRC value
output [6:0] CRC; // Current output CRC value
reg [6:0] CRC;
// We need output registers
wire inv;
assign inv = BITVAL ^ CRC[6]; // XOR required?
always @(posedge CLK or posedge RST) begin
if (RST) begin
CRC = 0;
end
else begin
if (Enable==1) begin
CRC[6] = CRC[5];
CRC[5] = CRC[4];
CRC[4] = CRC[3];
CRC[3] = CRC[2] ^ inv;
CRC[2] = CRC[1];
CRC[1] = CRC[0];
CRC[0] = inv;
end
end
end
endmodule

View file

@ -0,0 +1,89 @@
//Read the documentation before changing values
`define BIG_ENDIAN
//`define LITLE_ENDIAN
`define SIM
//`define SYN
`define SDC_IRQ_ENABLE
`define ACTEL
//`define CUSTOM
//`define ALTERA
//`define XLINX
//`define SIMULATOR
`define RESEND_MAX_CNT 3
//MAX 255 BD
//BD size/4
`ifdef ACTEL
`define BD_WIDTH 5
`define BD_SIZE 32
`define RAM_MEM_WIDTH_16
`define RAM_MEM_WIDTH 16
`endif
//`ifdef CUSTOM
// `define NR_O_BD_4
// `define BD_WIDTH 5
// `define BD_SIZE 32
// `define RAM_MEM_WIDTH_32
// `define RAM_MEM_WIDTH 32
//`endif
`ifdef SYN
`define RESET_CLK_DIV 0
`define MEM_OFFSET 4
`endif
`ifdef SIM
`define RESET_CLK_DIV 0
`define MEM_OFFSET 4
`endif
//SD-Clock Defines ---------
//Use bus clock or a seperate clock
`define SDC_CLK_BUS_CLK
//`define SDC_CLK_SEP
// Use of internal clock divider
//`define SDC_CLK_STATIC
`define SDC_CLK_DYNAMIC
//SD DATA-transfer defines---
`define BLOCK_SIZE 512
`define SD_BUS_WIDTH_4
`define SD_BUS_W 4
//at 512 bytes per block, equal 1024 4 bytes writings with a bus width of 4, add 2 for startbit and Z bit.
//Add 18 for crc, endbit and z.
`define BIT_BLOCK 1044
`define CRC_OFF 19
`define BIT_BLOCK_REC 1024
`define BIT_CRC_CYCLE 16
//FIFO defines---------------
`define FIFO_RX_MEM_DEPTH 8
`define FIFO_RX_MEM_ADR_SIZE 4
`define FIFO_TX_MEM_DEPTH 8
`define FIFO_TX_MEM_ADR_SIZE 4
//---------------------------

View file

@ -52,6 +52,12 @@ module testbench();
string signame, memfilename;
logic [31:0] GPIOPinsIn, GPIOPinsOut, GPIOPinsEn;
logic UARTSin, UARTSout;
logic SDCCLK;
tri1 SDCCmd;
tri1 [3:0] SDCDat;
assign SDCmd = 1'bz;
assign SDCDat = 4'bz;
// instantiate device to be tested
assign GPIOPinsIn = 0;
assign UARTSin = 1;

View file

@ -53,6 +53,14 @@ module testbench();
string signame, memfilename;
logic [31:0] GPIOPinsIn, GPIOPinsOut, GPIOPinsEn;
logic UARTSin, UARTSout;
logic SDCCLK;
tri1 SDCCmd;
tri1 [3:0] SDCDat;
assign SDCmd = 1'bz;
assign SDCDat = 4'bz;
// instantiate device to be tested
assign GPIOPinsIn = 0;
assign UARTSin = 1;

View file

@ -503,7 +503,9 @@ string tests32f[] = '{
string tests[];
string ProgramAddrMapFile, ProgramLabelMapFile;
logic [`AHBW-1:0] HRDATAEXT;
logic HREADYEXT, HRESPEXT;
logic HREADYEXT, HRESPEXT, HREADY;
logic HSELEXT;
logic [31:0] HADDR;
logic [`AHBW-1:0] HWDATA;
logic HWRITE;
@ -517,12 +519,12 @@ string tests32f[] = '{
logic DCacheFlushDone, DCacheFlushStart;
flopenr #(`XLEN) PCWReg(clk, reset, ~dut.hart.ieu.dp.StallW, dut.hart.ifu.PCM, PCW);
flopenr #(32) InstrWReg(clk, reset, ~dut.hart.ieu.dp.StallW, dut.hart.ifu.InstrM, InstrW);
flopenr #(`XLEN) PCWReg(clk, reset, ~dut.wallypipelinedsoc.hart.ieu.dp.StallW, dut.wallypipelinedsoc.hart.ifu.PCM, PCW);
flopenr #(32) InstrWReg(clk, reset, ~dut.wallypipelinedsoc.hart.ieu.dp.StallW, dut.wallypipelinedsoc.hart.ifu.InstrM, InstrW);
// check assertions for a legal configuration
riscvassertions riscvassertions();
logging logging(clk, reset, dut.uncore.HADDR, dut.uncore.HTRANS);
logging logging(clk, reset, dut.wallypipelinedsoc.uncore.HADDR, dut.wallypipelinedsoc.uncore.HTRANS);
// pick tests based on modes supported
initial begin
@ -564,25 +566,49 @@ string tests32f[] = '{
end
end
string signame, memfilename, romfilename;
string signame, memfilename, romfilename, sdcfilename;
logic [31:0] GPIOPinsIn, GPIOPinsOut, GPIOPinsEn;
logic [3:0] GPIOPinsIn_IO;
logic [4:0] GPIOPinsOut_IO;
logic UARTSin, UARTSout;
logic ddr4_calib_complete;
logic SDCCLK;
tri1 SDCCmd;
tri1 [3:0] SDCDat;
logic SDCCmdIn;
logic SDCCmdOut;
logic SDCCmdOE;
logic [3:0] SDCDatIn;
assign SDCCmd = SDCCmdOE ? SDCCmdOut : 1'bz;
assign SDCCmdIn = SDCCmd;
assign SDCDatIn = SDCDat;
sdModel sdcard
(.sdClk(SDCCLK),
.cmd(SDCCmd),
.dat(SDCDat));
// instantiate device to be tested
assign GPIOPinsIn = 0;
assign UARTSin = 1;
assign HREADYEXT = 1;
assign HRESPEXT = 0;
assign HRDATAEXT = 0;
dtim #(.BASE(`TIM_BASE), .RANGE(`TIM_RANGE))
dtim (.*, .HSELTim(HSELEXT),
.HREADTim(HRDATAEXT),
.HREADYTim(HREADYEXT),
.HRESPTim(HRESPEXT));
wallypipelinedsoc dut(.*);
wallypipelinedsocwrapper dut(.*);
// Track names of instructions
instrTrackerTB it(clk, reset, dut.hart.ieu.dp.FlushE,
dut.hart.ifu.icache.FinalInstrRawF,
dut.hart.ifu.InstrD, dut.hart.ifu.InstrE,
dut.hart.ifu.InstrM, dut.hart.ifu.InstrW,
instrTrackerTB it(clk, reset, dut.wallypipelinedsoc.hart.ieu.dp.FlushE,
dut.wallypipelinedsoc.hart.ifu.icache.FinalInstrRawF,
dut.wallypipelinedsoc.hart.ifu.InstrD, dut.wallypipelinedsoc.hart.ifu.InstrE,
dut.wallypipelinedsoc.hart.ifu.InstrM, InstrW,
InstrFName, InstrDName, InstrEName, InstrMName, InstrWName);
// initialize tests
@ -606,19 +632,22 @@ string tests32f[] = '{
/* -----\/----- EXCLUDED -----\/-----
if (`TESTSBP) begin
for (i=MemStartAddr; i<MemEndAddr; i = i+1) begin
dut.uncore.dtim.RAM[i] = meminit;
dtim.RAM[i] = meminit;
end
end
-----/\----- EXCLUDED -----/\----- */
// read test vectors into memory
memfilename = {"../../imperas-riscv-tests/work/", tests[test], ".elf.memfile"};
romfilename = {"../../imperas-riscv-tests/work/rv64BP/blink-led.memfile"};
$readmemh(memfilename, dut.uncore.dtim.RAM);
$readmemh(romfilename, dut.uncore.bootdtim.bootdtim.RAM);
ProgramAddrMapFile = {"../../imperas-riscv-tests/work/", tests[test], ".elf.objdump.addr"};
ProgramLabelMapFile = {"../../imperas-riscv-tests/work/", tests[test], ".elf.objdump.lab"};
//romfilename = {"../../testsBP/fpga-test-sdc/bin/fpga-test-sdc.hex"};
romfilename = {"../../tests/testsBP/fpga-test-sdc/bin/fpga-test-sdc.memfile"};
sdcfilename = {"../src/sdc/tb/ramdisk2.hex"};
$readmemh(memfilename, dtim.RAM);
$readmemh(romfilename, dut.wallypipelinedsoc.uncore.bootdtim.bootdtim.RAM);
$readmemh(sdcfilename, sdcard.FLASHmem);
ProgramAddrMapFile = {"../../imperas-riscv-tests/work/rv64BP/fpga-test-sdc.objdump.addr"};
ProgramLabelMapFile = {"../../imperas-riscv-tests/work/rv64BP/fpga-test-sdc.objdump.lab"};
$display("Read memfile %s", memfilename);
reset = 1; # 42; reset = 0;
reset = 0; #97; reset = 1; # 1000; reset = 0;
end
// generate clock to sequence tests
@ -631,11 +660,11 @@ string tests32f[] = '{
always @(negedge clk)
begin
/* -----\/----- EXCLUDED -----\/-----
if (dut.hart.priv.EcallFaultM &&
(dut.hart.ieu.dp.regf.rf[3] == 1 ||
(dut.hart.ieu.dp.regf.we3 &&
dut.hart.ieu.dp.regf.a3 == 3 &&
dut.hart.ieu.dp.regf.wd3 == 1))) begin
if (dut.wallypipelinedsoc.hart.priv.EcallFaultM &&
(dut.wallypipelinedsoc.hart.ieu.dp.regf.rf[3] == 1 ||
(dut.wallypipelinedsoc.hart.ieu.dp.regf.we3 &&
dut.wallypipelinedsoc.hart.ieu.dp.regf.a3 == 3 &&
dut.wallypipelinedsoc.hart.ieu.dp.regf.wd3 == 1))) begin
-----/\----- EXCLUDED -----/\----- */
if (DCacheFlushDone) begin
//$display("Code ended with ecall with gp = 1");
@ -673,14 +702,14 @@ string tests32f[] = '{
/* verilator lint_off INFINITELOOP */
while (signature[i] !== 'bx) begin
//$display("signature[%h] = %h", i, signature[i]);
if (signature[i] !== dut.uncore.dtim.RAM[testadr+i] &&
if (signature[i] !== dtim.RAM[testadr+i] &&
(signature[i] !== DCacheFlushFSM.ShadowRAM[testadr+i])) begin
if (signature[i+4] !== 'bx || signature[i] !== 32'hFFFFFFFF) begin
// report errors unless they are garbage at the end of the sim
// kind of hacky test for garbage right now
errors = errors+1;
$display(" Error on test %s result %d: adr = %h sim (D$) %h sim (TIM) = %h, signature = %h",
tests[test], i, (testadr+i)*(`XLEN/8), DCacheFlushFSM.ShadowRAM[testadr+i], dut.uncore.dtim.RAM[testadr+i], signature[i]);
tests[test], i, (testadr+i)*(`XLEN/8), DCacheFlushFSM.ShadowRAM[testadr+i], dtim.RAM[testadr+i], signature[i]);
$stop;//***debug
end
end
@ -702,28 +731,30 @@ string tests32f[] = '{
end
else begin
memfilename = {"../../imperas-riscv-tests/work/", tests[test], ".elf.memfile"};
$readmemh(memfilename, dut.uncore.dtim.RAM);
$readmemh(memfilename, dtim.RAM);
$display("Read memfile %s", memfilename);
ProgramAddrMapFile = {"../../imperas-riscv-tests/work/", tests[test], ".elf.objdump.addr"};
ProgramLabelMapFile = {"../../imperas-riscv-tests/work/", tests[test], ".elf.objdump.lab"};
reset = 1; # 17; reset = 0;
reset = 0; #97; reset = 1; # 1000; reset = 0;
end
end
end // always @ (negedge clk)
// track the current function or global label
/* -----\/----- EXCLUDED -----\/-----
if (DEBUG == 1) begin : FunctionName
FunctionName FunctionName(.reset(reset),
.clk(clk),
.ProgramAddrMapFile(ProgramAddrMapFile),
.ProgramLabelMapFile(ProgramLabelMapFile));
end
-----/\----- EXCLUDED -----/\----- */
assign DCacheFlushStart = dut.hart.priv.EcallFaultM &&
(dut.hart.ieu.dp.regf.rf[3] == 1 ||
(dut.hart.ieu.dp.regf.we3 &&
dut.hart.ieu.dp.regf.a3 == 3 &&
dut.hart.ieu.dp.regf.wd3 == 1));
assign DCacheFlushStart = dut.wallypipelinedsoc.hart.priv.EcallFaultM &&
(dut.wallypipelinedsoc.hart.ieu.dp.regf.rf[3] == 1 ||
(dut.wallypipelinedsoc.hart.ieu.dp.regf.we3 &&
dut.wallypipelinedsoc.hart.ieu.dp.regf.a3 == 3 &&
dut.wallypipelinedsoc.hart.ieu.dp.regf.wd3 == 1));
DCacheFlushFSM DCacheFlushFSM(.clk(clk),
.reset(reset),
@ -736,8 +767,8 @@ string tests32f[] = '{
if (`BPRED_ENABLED == 1) begin : bpred
initial begin
$readmemb(`TWO_BIT_PRELOAD, dut.hart.ifu.bpred.bpred.Predictor.DirPredictor.PHT.memory);
$readmemb(`BTB_PRELOAD, dut.hart.ifu.bpred.bpred.TargetPredictor.memory.memory);
$readmemb(`TWO_BIT_PRELOAD, dut.wallypipelinedsoc.hart.ifu.bpred.bpred.Predictor.DirPredictor.PHT.mem);
$readmemb(`BTB_PRELOAD, dut.wallypipelinedsoc.hart.ifu.bpred.bpred.TargetPredictor.memory.mem);
end
end
endgenerate
@ -777,10 +808,10 @@ module DCacheFlushFSM
input logic start,
output logic done);
localparam integer numlines = testbench.dut.hart.lsu.dcache.NUMLINES;
localparam integer numways = testbench.dut.hart.lsu.dcache.NUMWAYS;
localparam integer blockbytelen = testbench.dut.hart.lsu.dcache.BLOCKBYTELEN;
localparam integer numwords = testbench.dut.hart.lsu.dcache.BLOCKLEN/`XLEN;
localparam integer numlines = testbench.dut.wallypipelinedsoc.hart.lsu.dcache.NUMLINES;
localparam integer numways = testbench.dut.wallypipelinedsoc.hart.lsu.dcache.NUMWAYS;
localparam integer blockbytelen = testbench.dut.wallypipelinedsoc.hart.lsu.dcache.BLOCKBYTELEN;
localparam integer numwords = testbench.dut.wallypipelinedsoc.hart.lsu.dcache.BLOCKLEN/`XLEN;
localparam integer lognumlines = $clog2(numlines);
localparam integer logblockbytelen = $clog2(blockbytelen);
localparam integer lognumways = $clog2(numways);
@ -806,10 +837,10 @@ module DCacheFlushFSM
.logblockbytelen(logblockbytelen))
copyShadow(.clk,
.start,
.tag(testbench.dut.hart.lsu.dcache.MemWay[way].CacheTagMem.StoredData[index]),
.valid(testbench.dut.hart.lsu.dcache.MemWay[way].ValidBits[index]),
.dirty(testbench.dut.hart.lsu.dcache.MemWay[way].DirtyBits[index]),
.data(testbench.dut.hart.lsu.dcache.MemWay[way].word[cacheWord].CacheDataMem.StoredData[index]),
.tag(testbench.dut.wallypipelinedsoc.hart.lsu.dcache.MemWay[way].CacheTagMem.StoredData[index]),
.valid(testbench.dut.wallypipelinedsoc.hart.lsu.dcache.MemWay[way].ValidBits[index]),
.dirty(testbench.dut.wallypipelinedsoc.hart.lsu.dcache.MemWay[way].DirtyBits[index]),
.data(testbench.dut.wallypipelinedsoc.hart.lsu.dcache.MemWay[way].word[cacheWord].CacheDataMem.StoredData[index]),
.index(index),
.cacheWord(cacheWord),
.CacheData(CacheData[way][index][cacheWord]),

View file

@ -65,8 +65,15 @@ module testbench();
logic HMASTLOCK;
logic [31:0] GPIOPinsIn;
logic [31:0] GPIOPinsOut, GPIOPinsEn;
logic UARTSin;
logic UARTSout;
logic UARTSin, UARTSout;
logic SDCCLK;
tri1 SDCCmd;
tri1 [3:0] SDCDat;
assign SDCmd = 1'bz;
assign SDCDat = 4'bz;
assign GPIOPinsIn = 0;
assign UARTSin = 1;
wallypipelinedsoc dut(.clk, .reset_ext, .reset,