diff options
Diffstat (limited to 'tests')
225 files changed, 6388 insertions, 467 deletions
diff --git a/tests/arch/anlogic/blockram.ys b/tests/arch/anlogic/blockram.ys new file mode 100644 index 000000000..da23409ba --- /dev/null +++ b/tests/arch/anlogic/blockram.ys @@ -0,0 +1,13 @@ +read_verilog ../common/blockram.v +hierarchy -top sync_ram_sp +proc +memory -nomap +equiv_opt -run :prove -map +/anlogic/cells_sim.v synth_anlogic +memory +opt -full + +design -load postopt +cd sync_ram_sp + +select -assert-count 1 t:EG_PHY_BRAM +select -assert-none t:EG_PHY_BRAM %% t:* %D diff --git a/tests/arch/anlogic/lutram.ys b/tests/arch/anlogic/lutram.ys index 6dbdbdac3..fe6135c73 100644 --- a/tests/arch/anlogic/lutram.ys +++ b/tests/arch/anlogic/lutram.ys @@ -2,7 +2,7 @@ read_verilog ../common/lutram.v hierarchy -top lutram_1w1r proc memory -nomap -equiv_opt -run :prove -map +/anlogic/cells_sim.v synth_anlogic +equiv_opt -run :prove -map +/anlogic/cells_sim.v synth_anlogic -nobram memory opt -full diff --git a/tests/arch/common/adffs.v b/tests/arch/common/adffs.v index 576bd81a6..966e7c2b8 100644 --- a/tests/arch/common/adffs.v +++ b/tests/arch/common/adffs.v @@ -1,7 +1,9 @@ module adff( input d, clk, clr, output reg q ); +`ifndef NO_INIT initial begin q = 0; end +`endif always @( posedge clk, posedge clr ) if ( clr ) q <= 1'b0; @@ -10,9 +12,11 @@ module adff( input d, clk, clr, output reg q ); endmodule module adffn( input d, clk, clr, output reg q ); +`ifndef NO_INIT initial begin q = 0; end +`endif always @( posedge clk, negedge clr ) if ( !clr ) q <= 1'b0; @@ -21,9 +25,11 @@ module adffn( input d, clk, clr, output reg q ); endmodule module dffs( input d, clk, pre, clr, output reg q ); +`ifndef NO_INIT initial begin q = 0; end +`endif always @( posedge clk ) if ( pre ) q <= 1'b1; @@ -32,9 +38,11 @@ module dffs( input d, clk, pre, clr, output reg q ); endmodule module ndffnr( input d, clk, pre, clr, output reg q ); +`ifndef NO_INIT initial begin q = 0; end +`endif always @( negedge clk ) if ( !clr ) q <= 1'b0; diff --git a/tests/arch/common/dffs.v b/tests/arch/common/dffs.v index 636252d16..0c607af50 100644 --- a/tests/arch/common/dffs.v +++ b/tests/arch/common/dffs.v @@ -4,9 +4,11 @@ module dff ( input d, clk, output reg q ); endmodule module dffe( input d, clk, en, output reg q ); +`ifndef NO_INIT initial begin q = 0; end +`endif always @( posedge clk ) if ( en ) q <= d; diff --git a/tests/arch/common/shifter.v b/tests/arch/common/shifter.v index 3030608ab..06e63c9af 100644 --- a/tests/arch/common/shifter.v +++ b/tests/arch/common/shifter.v @@ -1,7 +1,13 @@ module top(out, clk, in); output [7:0] out; input signed clk, in; - reg signed [7:0] out = 0; + reg signed [7:0] out; + +`ifndef NO_INIT + initial begin + out = 0; + end +`endif always @(posedge clk) begin diff --git a/tests/arch/ecp5/memories.ys b/tests/arch/ecp5/memories.ys index 44651ba25..5cddcb952 100644 --- a/tests/arch/ecp5/memories.ys +++ b/tests/arch/ecp5/memories.ys @@ -1,11 +1,11 @@ # ================================ RAM ================================ -# RAM bits <= 18K; Data width <= 36; Address width <= 9: -> PDPW16KD +# RAM bits <= 18K; Data width <= 36; Address width <= 9: -> DP16KD design -reset; read_verilog -defer ../common/blockram.v chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 36 sync_ram_sdp hierarchy -top sync_ram_sdp synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:PDPW16KD +select -assert-count 1 t:DP16KD ## With parameters @@ -13,7 +13,7 @@ design -reset; read_verilog -defer ../common/blockram.v chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp hierarchy -top sync_ram_sdp synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 0 t:PDPW16KD # too inefficient +select -assert-count 0 t:DP16KD # too inefficient select -assert-count 9 t:TRELLIS_DPR16X4 design -reset; read_verilog -defer ../common/blockram.v @@ -21,28 +21,29 @@ chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp hierarchy -top sync_ram_sdp setattr -set syn_ramstyle "block_ram" m:memory synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:PDPW16KD +select -assert-count 1 t:DP16KD design -reset; read_verilog -defer ../common/blockram.v chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp hierarchy -top sync_ram_sdp setattr -set syn_ramstyle "Block_RAM" m:memory synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:PDPW16KD # any case works +select -assert-count 1 t:DP16KD # any case works design -reset; read_verilog -defer ../common/blockram.v chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp hierarchy -top sync_ram_sdp setattr -set ram_block 1 m:memory synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:PDPW16KD +select -assert-count 0 t:DP16KD +select -assert-count 9 t:TRELLIS_DPR16X4 design -reset; read_verilog -defer ../common/blockram.v chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp hierarchy -top sync_ram_sdp setattr -set syn_ramstyle "registers" m:memory synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 0 t:PDPW16KD # requested FFRAM explicitly +select -assert-count 0 t:DP16KD # requested FFRAM explicitly select -assert-count 180 t:TRELLIS_FF design -reset; read_verilog -defer ../common/blockram.v @@ -50,37 +51,9 @@ chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp hierarchy -top sync_ram_sdp setattr -set logic_block 1 m:memory synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 0 t:PDPW16KD # requested FFRAM explicitly +select -assert-count 0 t:DP16KD # requested FFRAM explicitly select -assert-count 180 t:TRELLIS_FF -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set syn_romstyle "ebr" m:memory -synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BROM but this is a RAM - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set rom_block 1 m:memory -synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BROM but this is a RAM - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set syn_ramstyle "block_ram" m:memory -synth_ecp5 -top sync_ram_sdp -nobram; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BRAM but BRAM is disabled - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set ram_block 1 m:memory -synth_ecp5 -top sync_ram_sdp -nobram; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BRAM but BRAM is disabled - # RAM bits <= 18K; Data width <= 18; Address width <= 10: -> DP16KD design -reset; read_verilog -defer ../common/blockram.v @@ -141,7 +114,8 @@ chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_ram_sdp hierarchy -top sync_ram_sdp setattr -set ram_block 1 m:memory synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:DP16KD +select -assert-count 0 t:DP16KD # too inefficient +select -assert-count 5 t:TRELLIS_DPR16X4 design -reset; read_verilog -defer ../common/blockram.v chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_ram_sdp @@ -159,34 +133,6 @@ synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp select -assert-count 0 t:DP16KD # requested FFRAM explicitly select -assert-count 90 t:TRELLIS_FF -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set syn_romstyle "ebr" m:memory -synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BROM but this is a RAM - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set rom_block 1 m:memory -synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BROM but this is a RAM - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set syn_ramstyle "block_ram" m:memory -synth_ecp5 -top sync_ram_sdp -nobram; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BRAM but BRAM is disabled - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set ram_block 1 m:memory -synth_ecp5 -top sync_ram_sdp -nobram; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BRAM but BRAM is disabled - # RAM bits <= 64; Data width <= 4; Address width <= 4: -> DPR16X4 design -reset; read_verilog -defer ../common/blockram.v @@ -220,21 +166,14 @@ synth_ecp5 -top sync_ram_sdp; cd sync_ram_sdp select -assert-count 0 t:TRELLIS_DPR16X4 # requested FFRAM explicitly select -assert-count 68 t:TRELLIS_FF -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 4 -set DATA_WIDTH 4 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set syn_ramstyle "distributed" m:memory -synth_ecp5 -top sync_ram_sdp -nolutram; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested LUTRAM but LUTRAM is disabled - # ================================ ROM ================================ -# ROM bits <= 18K; Data width <= 36; Address width <= 9: -> PDPW16KD +# ROM bits <= 18K; Data width <= 36; Address width <= 9: -> DP16KD design -reset; read_verilog -defer ../common/blockrom.v chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 36 sync_rom hierarchy -top sync_rom synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 1 t:PDPW16KD +select -assert-count 1 t:DP16KD ## With parameters @@ -242,7 +181,7 @@ design -reset; read_verilog -defer ../common/blockrom.v chparam -set ADDRESS_WIDTH 3 -set DATA_WIDTH 36 sync_rom hierarchy -top sync_rom synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 0 t:PDPW16KD # too inefficient +select -assert-count 0 t:DP16KD # too inefficient select -assert-min 18 t:LUT4 design -reset; read_verilog -defer ../common/blockrom.v @@ -250,21 +189,21 @@ chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_rom hierarchy -top sync_rom setattr -set syn_romstyle "ebr" m:memory synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 1 t:PDPW16KD +select -assert-count 1 t:DP16KD design -reset; read_verilog -defer ../common/blockrom.v chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_rom hierarchy -top sync_rom setattr -set rom_block 1 m:memory synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 1 t:PDPW16KD +select -assert-count 1 t:DP16KD design -reset; read_verilog -defer ../common/blockrom.v chparam -set ADDRESS_WIDTH 3 -set DATA_WIDTH 36 sync_rom hierarchy -top sync_rom setattr -set syn_romstyle "logic" m:memory synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 0 t:PDPW16KD # requested LUTROM explicitly +select -assert-count 0 t:DP16KD # requested LUTROM explicitly select -assert-min 18 t:LUT4 design -reset; read_verilog -defer ../common/blockrom.v @@ -272,37 +211,9 @@ chparam -set ADDRESS_WIDTH 3 -set DATA_WIDTH 36 sync_rom hierarchy -top sync_rom setattr -set logic_block 1 m:memory synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 0 t:PDPW16KD # requested LUTROM explicitly +select -assert-count 0 t:DP16KD # requested LUTROM explicitly select -assert-min 18 t:LUT4 -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_rom -hierarchy -top sync_rom -setattr -set syn_ramstyle "block_ram" m:memory -synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BRAM but this is a ROM - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_rom -hierarchy -top sync_rom -setattr -set ram_block 1 m:memory -synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BRAM but this is a ROM - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_rom -hierarchy -top sync_rom -setattr -set syn_ramstyle "block_rom" m:memory -synth_ecp5 -top sync_rom -nobram; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BROM but BRAM is disabled - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 36 sync_rom -hierarchy -top sync_rom -setattr -set rom_block 1 m:memory -synth_ecp5 -top sync_rom -nobram; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BROM but BRAM is disabled - # ROM bits <= 18K; Data width <= 18; Address width <= 10: -> DP16KD design -reset; read_verilog -defer ../common/blockrom.v @@ -349,31 +260,3 @@ setattr -set logic_block 1 m:memory synth_ecp5 -top sync_rom; cd sync_rom select -assert-count 0 t:DP16KD # requested LUTROM explicitly select -assert-min 9 t:LUT4 - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_rom -hierarchy -top sync_rom -setattr -set syn_ramstyle "block_ram" m:memory -synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BRAM but this is a ROM - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_rom -hierarchy -top sync_rom -setattr -set ram_block 1 m:memory -synth_ecp5 -top sync_rom; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BRAM but this is a ROM - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_rom -hierarchy -top sync_rom -setattr -set syn_ramstyle "block_rom" m:memory -synth_ecp5 -top sync_rom -nobram; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BROM but BRAM is disabled - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 18 sync_rom -hierarchy -top sync_rom -setattr -set rom_block 1 m:memory -synth_ecp5 -top sync_rom -nobram; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BROM but BRAM is disabled diff --git a/tests/arch/efinix/lutram.ys b/tests/arch/efinix/lutram.ys index dcf647ce0..8412d1389 100644 --- a/tests/arch/efinix/lutram.ys +++ b/tests/arch/efinix/lutram.ys @@ -1,17 +1,6 @@ read_verilog ../common/lutram.v hierarchy -top lutram_1w1r -proc -memory -nomap -equiv_opt -run :prove -map +/efinix/cells_sim.v synth_efinix -memory -opt -full - -miter -equiv -flatten -make_assert -make_outputs gold gate miter -#ERROR: Called with -verify and proof did fail! -#sat -verify -prove-asserts -seq 5 -set-init-zero -show-inputs -show-outputs miter -sat -prove-asserts -seq 5 -set-init-zero -show-inputs -show-outputs miter - -design -load postopt +synth_efinix cd lutram_1w1r select -assert-count 1 t:EFX_GBUFCE select -assert-count 1 t:EFX_RAM_5K diff --git a/tests/arch/gatemate/.gitignore b/tests/arch/gatemate/.gitignore new file mode 100644 index 000000000..9a71dca69 --- /dev/null +++ b/tests/arch/gatemate/.gitignore @@ -0,0 +1,4 @@ +*.log +/run-test.mk ++*_synth.v ++*_testbench diff --git a/tests/arch/gatemate/add_sub.ys b/tests/arch/gatemate/add_sub.ys new file mode 100644 index 000000000..bf261ba5a --- /dev/null +++ b/tests/arch/gatemate/add_sub.ys @@ -0,0 +1,9 @@ +read_verilog ../common/add_sub.v +hierarchy -top top +proc +equiv_opt -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd top # Constrain all select calls below inside the top module +select -assert-count 8 t:CC_ADDF +select -assert-max 4 t:CC_LUT1 +select -assert-none t:CC_ADDF t:CC_LUT1 %% t:* %D diff --git a/tests/arch/gatemate/adffs.ys b/tests/arch/gatemate/adffs.ys new file mode 100644 index 000000000..b2ded6e9d --- /dev/null +++ b/tests/arch/gatemate/adffs.ys @@ -0,0 +1,43 @@ +read_verilog -D NO_INIT ../common/adffs.v +design -save read + +hierarchy -top adff +proc +equiv_opt -async2sync -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd adff # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_DFF +select -assert-none t:CC_BUFG t:CC_DFF %% t:* %D + +design -load read +hierarchy -top adffn +proc +equiv_opt -async2sync -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd adffn # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_DFF +select -assert-none t:CC_BUFG t:CC_DFF %% t:* %D + +design -load read +hierarchy -top dffs +proc +equiv_opt -async2sync -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd dffs # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_DFF +select -assert-max 1 t:CC_LUT2 +select -assert-none t:CC_BUFG t:CC_DFF t:CC_LUT2 %% t:* %D + +design -load read +hierarchy -top ndffnr +proc +equiv_opt -async2sync -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd ndffnr # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_DFF +select -assert-max 1 t:CC_LUT2 +select -assert-none t:CC_BUFG t:CC_DFF t:CC_LUT2 %% t:* %D diff --git a/tests/arch/gatemate/counter.ys b/tests/arch/gatemate/counter.ys new file mode 100644 index 000000000..77ed858b3 --- /dev/null +++ b/tests/arch/gatemate/counter.ys @@ -0,0 +1,12 @@ +read_verilog ../common/counter.v +hierarchy -top top +proc +flatten +equiv_opt -assert -async2sync -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd top # Constrain all select calls below inside the top module + +select -assert-count 8 t:CC_ADDF +select -assert-count 1 t:CC_BUFG +select -assert-count 8 t:CC_DFF +select -assert-none t:CC_ADDF t:CC_BUFG t:CC_DFF %% t:* %D diff --git a/tests/arch/gatemate/dffs.ys b/tests/arch/gatemate/dffs.ys new file mode 100644 index 000000000..022322419 --- /dev/null +++ b/tests/arch/gatemate/dffs.ys @@ -0,0 +1,21 @@ +read_verilog -D NO_INIT ../common/dffs.v +design -save read + +hierarchy -top dff +proc +equiv_opt -assert -async2sync -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd dff # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_DFF +select -assert-none t:CC_BUFG t:CC_DFF %% t:* %D + +design -load read +hierarchy -top dffe +proc +equiv_opt -assert -async2sync -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd dffe # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_DFF +select -assert-none t:CC_BUFG t:CC_DFF %% t:* %D diff --git a/tests/arch/gatemate/fsm.ys b/tests/arch/gatemate/fsm.ys new file mode 100644 index 000000000..6b43ead7a --- /dev/null +++ b/tests/arch/gatemate/fsm.ys @@ -0,0 +1,20 @@ +read_verilog ../common/fsm.v +hierarchy -top fsm +proc +flatten + +equiv_opt -run :prove -map +/gatemate/cells_sim.v synth_gatemate -noiopad +async2sync +miter -equiv -make_assert -flatten gold gate miter +stat +sat -verify -prove-asserts -show-public -set-at 1 in_reset 1 -seq 20 -prove-skip 1 miter + +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd fsm # Constrain all select calls below inside the top module + +select -assert-count 1 t:CC_BUFG +select -assert-count 6 t:CC_DFF +select -assert-max 5 t:CC_LUT2 +select -assert-max 4 t:CC_LUT3 +select -assert-max 9 t:CC_LUT4 +select -assert-none t:CC_BUFG t:CC_DFF t:CC_LUT2 t:CC_LUT3 t:CC_LUT4 %% t:* %D diff --git a/tests/arch/gatemate/latches.ys b/tests/arch/gatemate/latches.ys new file mode 100644 index 000000000..5f64c6db5 --- /dev/null +++ b/tests/arch/gatemate/latches.ys @@ -0,0 +1,29 @@ +read_verilog ../common/latches.v +design -save read + +hierarchy -top latchp +proc +equiv_opt -async2sync -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd latchp # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_DLT +select -assert-none t:CC_DLT %% t:* %D + +design -load read +hierarchy -top latchn +proc +equiv_opt -async2sync -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd latchn # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_DLT +select -assert-none t:CC_DLT %% t:* %D + +design -load read +hierarchy -top latchsr +proc +equiv_opt -async2sync -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd latchsr # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_DLT +select -assert-max 2 t:CC_LUT3 +select -assert-none t:CC_DLT t:CC_LUT3 %% t:* %D diff --git a/tests/arch/gatemate/logic.ys b/tests/arch/gatemate/logic.ys new file mode 100644 index 000000000..026406bc8 --- /dev/null +++ b/tests/arch/gatemate/logic.ys @@ -0,0 +1,10 @@ +read_verilog ../common/logic.v +hierarchy -top top +proc +equiv_opt -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd top # Constrain all select calls below inside the top module +select -assert-max 1 t:CC_LUT1 +select -assert-max 6 t:CC_LUT2 +select -assert-max 2 t:CC_LUT4 +select -assert-none t:CC_LUT1 t:CC_LUT2 t:CC_LUT4 %% t:* %D diff --git a/tests/arch/gatemate/memory.ys b/tests/arch/gatemate/memory.ys new file mode 100644 index 000000000..e919920f8 --- /dev/null +++ b/tests/arch/gatemate/memory.ys @@ -0,0 +1,34 @@ +# 512 x 40 bit -> CC_BRAM_20K SDP RAM +read_verilog ../common/blockram.v +chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 40 sync_ram_sdp +synth_gatemate -top sync_ram_sdp -noiopad +cd sync_ram_sdp +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_BRAM_20K + +# 512 x 80 bit -> CC_BRAM_40K SDP RAM +design -reset +read_verilog ../common/blockram.v +chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 80 sync_ram_sdp +synth_gatemate -top sync_ram_sdp -noiopad +cd sync_ram_sdp +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_BRAM_40K + +# 512 x 40 bit -> CC_BRAM_20K SDP ROM +design -reset +read_verilog ../common/blockrom.v +chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 40 sync_rom +synth_gatemate -top sync_rom -noiopad +cd sync_rom +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_BRAM_20K + +# 512 x 80 bit -> CC_BRAM_40K SDP ROM +design -reset +read_verilog ../common/blockrom.v +chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 80 sync_rom +synth_gatemate -top sync_rom -noiopad +cd sync_rom +select -assert-count 1 t:CC_BUFG +select -assert-count 1 t:CC_BRAM_40K diff --git a/tests/arch/gatemate/mul.v b/tests/arch/gatemate/mul.v new file mode 100644 index 000000000..55e8f9006 --- /dev/null +++ b/tests/arch/gatemate/mul.v @@ -0,0 +1,79 @@ + +module mul_plain(a, b, p); + + parameter M = 6; + parameter N = 6; + + input wire [M-1:0] a; + input wire [N-1:0] b; + output wire [M+N-1:0] p; + + assign p = a * b; + +endmodule + +module mul_signed_async (clk, rst, en, a, b, p); + + parameter M = 8; + parameter N = 6; + + input wire signed clk, rst, en; + input wire signed [M-1:0] a; + input wire signed [N-1:0] b; + output reg signed [M+N-1:0] p; + + reg signed [M-1:0] a_reg; + reg signed [N-1:0] b_reg; + + // signed M*N multiplier with + // - input and output pipeline registers + // - asynchronous reset (active high) + // - clock enable (active high) + always @(posedge clk or posedge rst) + begin + if (rst) begin + a_reg <= 0; + b_reg <= 0; + p <= 0; + end + else if (en) begin + a_reg <= a; + b_reg <= b; + p <= a_reg * b_reg; + end + end + +endmodule + +module mul_unsigned_sync (clk, rst, en, a, b, p); + + parameter M = 6; + parameter N = 3; + + input wire clk, rst, en; + input wire [M-1:0] a; + input wire [N-1:0] b; + output reg [M+N-1:0] p; + + reg [M-1:0] a_reg; + reg [N-1:0] b_reg; + + // unsigned M*N multiplier with + // - input and output pipeline registers + // - synchronous reset (active high) + // - clock enable (active high) + always @(posedge clk) + begin + if (rst) begin + a_reg <= 0; + b_reg <= 0; + p <= 0; + end + else if (en) begin + a_reg <= a; + b_reg <= b; + p <= a_reg * b_reg; + end + end + +endmodule diff --git a/tests/arch/gatemate/mul.ys b/tests/arch/gatemate/mul.ys new file mode 100644 index 000000000..ded5fe729 --- /dev/null +++ b/tests/arch/gatemate/mul.ys @@ -0,0 +1,33 @@ +read_verilog mul.v +design -save read + +hierarchy -top mul_plain +proc +equiv_opt -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd mul_plain # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_MULT +select -assert-none t:CC_MULT %% t:* %D + +design -load read +hierarchy -top mul_signed_async +proc +equiv_opt -assert -async2sync -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd mul_signed_async # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_MULT +select -assert-count 1 t:CC_BUFG +select -assert-count 28 t:CC_DFF +select -assert-none t:CC_MULT t:CC_BUFG t:CC_DFF %% t:* %D + +design -load read +hierarchy -top mul_unsigned_sync +proc +equiv_opt -assert -async2sync -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd mul_unsigned_sync # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_MULT +select -assert-count 1 t:CC_BUFG +select -assert-max 18 t:CC_LUT4 +select -assert-count 18 t:CC_DFF +select -assert-none t:CC_MULT t:CC_BUFG t:CC_LUT4 t:CC_DFF %% t:* %D diff --git a/tests/arch/gatemate/mux.ys b/tests/arch/gatemate/mux.ys new file mode 100644 index 000000000..320ff33d7 --- /dev/null +++ b/tests/arch/gatemate/mux.ys @@ -0,0 +1,24 @@ +read_verilog ../common/mux.v +design -save read + +design -load read +hierarchy -top mux4 +proc +equiv_opt -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd mux4 # Constrain all select calls below inside the top module +select -assert-max 1 t:CC_LUT2 +select -assert-max 2 t:CC_LUT4 +select -assert-max 1 t:CC_MX2 +select -assert-none t:CC_LUT2 t:CC_LUT4 t:CC_MX2 %% t:* %D + +design -load read +hierarchy -top mux8 +proc +equiv_opt -assert -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd mux8 # Constrain all select calls below inside the top module +select -assert-max 1 t:CC_LUT3 +select -assert-max 5 t:CC_LUT4 +select -assert-max 1 t:CC_MX2 +select -assert-none t:CC_LUT3 t:CC_LUT4 t:CC_MX2 %% t:* %D diff --git a/tests/arch/gatemate/run-test.sh b/tests/arch/gatemate/run-test.sh new file mode 100755 index 000000000..4be4b70ae --- /dev/null +++ b/tests/arch/gatemate/run-test.sh @@ -0,0 +1,4 @@ +#!/usr/bin/env bash +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/arch/gatemate/shifter.ys b/tests/arch/gatemate/shifter.ys new file mode 100644 index 000000000..0006a298a --- /dev/null +++ b/tests/arch/gatemate/shifter.ys @@ -0,0 +1,10 @@ +read_verilog -D NO_INIT ../common/shifter.v +hierarchy -top top +proc +flatten +equiv_opt -assert -async2sync -map +/gatemate/cells_sim.v synth_gatemate -noiopad # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd top # Constrain all select calls below inside the top module +select -assert-count 1 t:CC_BUFG +select -assert-count 8 t:CC_DFF +select -assert-none t:CC_BUFG t:CC_DFF %% t:* %D diff --git a/tests/arch/gatemate/tribuf.ys b/tests/arch/gatemate/tribuf.ys new file mode 100644 index 000000000..d900fa5e4 --- /dev/null +++ b/tests/arch/gatemate/tribuf.ys @@ -0,0 +1,13 @@ +read_verilog ../common/tribuf.v +hierarchy -top tristate +proc +tribuf +flatten +synth +equiv_opt -assert -map +/gatemate/cells_sim.v -map +/simcells.v synth_gatemate # equivalency check +design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) +cd tristate # Constrain all select calls below inside the top module +select -assert-count 2 t:CC_IBUF +select -assert-max 1 t:CC_LUT1 +select -assert-count 1 t:CC_TOBUF +select -assert-none t:CC_IBUF t:CC_LUT1 t:CC_TOBUF %% t:* %D diff --git a/tests/arch/gowin/lutram.ys b/tests/arch/gowin/lutram.ys index 56f69e7c5..d668783a2 100644 --- a/tests/arch/gowin/lutram.ys +++ b/tests/arch/gowin/lutram.ys @@ -7,12 +7,11 @@ memory opt -full miter -equiv -flatten -make_assert -make_outputs gold gate miter -#ERROR: Called with -verify and proof did fail! -#sat -verify -prove-asserts -seq 5 -set-init-zero -show-inputs -show-outputs miter +sat -verify -prove-asserts -seq 5 -set-init-zero -show-inputs -show-outputs miter sat -prove-asserts -seq 5 -set-init-zero -show-inputs -show-outputs miter design -load postopt cd lutram_1w1r -select -assert-count 8 t:RAM16S4 +select -assert-count 8 t:RAM16SDP4 # other logic present that is not simple #select -assert-none t:RAM16S4 %% t:* %D diff --git a/tests/arch/ice40/memories.ys b/tests/arch/ice40/memories.ys index 4920a45e3..d480a3abe 100644 --- a/tests/arch/ice40/memories.ys +++ b/tests/arch/ice40/memories.ys @@ -71,34 +71,6 @@ synth_ice40 -top sync_ram_sdp; cd sync_ram_sdp select -assert-count 0 t:SB_RAM40_4K # requested FFRAM explicitly select -assert-min 1 t:SB_DFFE -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set syn_romstyle "ebr" m:memory -synth_ice40 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BROM but this is a RAM - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set rom_block 1 m:memory -synth_ice40 -top sync_ram_sdp; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BROM but this is a RAM - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set syn_ramstyle "block_ram" m:memory -synth_ice40 -top sync_ram_sdp -nobram; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BRAM but BRAM is disabled - -design -reset; read_verilog -defer ../common/blockram.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_ram_sdp -hierarchy -top sync_ram_sdp -setattr -set ram_block 1 m:memory -synth_ice40 -top sync_ram_sdp -nobram; cd sync_ram_sdp -select -assert-count 1 t:$mem_v2 # requested BRAM but BRAM is disabled - # ================================ ROM ================================ # ROM bits <= 4K; Data width <= 16; Address width <= 11: -> SB_RAM40_4K @@ -164,31 +136,3 @@ setattr -set logic_block 1 m:memory synth_ice40 -top sync_rom; cd sync_rom select -assert-count 0 t:SB_RAM40_4K # requested LUTROM explicitly select -assert-min 1 t:SB_LUT4 - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_rom -hierarchy -top sync_rom -setattr -set syn_ramstyle "block_ram" m:memory -synth_ice40 -top sync_rom; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BRAM but this is a ROM - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_rom -hierarchy -top sync_rom -setattr -set ram_block 1 m:memory -synth_ice40 -top sync_rom; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BRAM but this is a ROM - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_rom -hierarchy -top sync_rom -setattr -set syn_romstyle "ebr" m:memory -synth_ice40 -top sync_rom -nobram; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BROM but BRAM is disabled - -design -reset; read_verilog -defer ../common/blockrom.v -chparam -set ADDRESS_WIDTH 2 -set DATA_WIDTH 8 sync_rom -hierarchy -top sync_rom -setattr -set rom_block 1 m:memory -synth_ice40 -top sync_rom -nobram; cd sync_rom -select -assert-count 1 t:$mem_v2 # requested BROM but BRAM is disabled diff --git a/tests/arch/intel_alm/blockram.ys b/tests/arch/intel_alm/blockram.ys index c157c3165..3b61b9339 100644 --- a/tests/arch/intel_alm/blockram.ys +++ b/tests/arch/intel_alm/blockram.ys @@ -2,5 +2,6 @@ read_verilog ../common/blockram.v chparam -set ADDRESS_WIDTH 10 -set DATA_WIDTH 10 sync_ram_sdp synth_intel_alm -family cyclonev -noiopad -noclkbuf cd sync_ram_sdp +select -assert-count 1 t:MISTRAL_NOT select -assert-count 1 t:MISTRAL_M10K -select -assert-none t:MISTRAL_M10K %% t:* %D +select -assert-none t:MISTRAL_NOT t:MISTRAL_M10K %% t:* %D diff --git a/tests/arch/machxo2/mux.ys b/tests/arch/machxo2/mux.ys index 6c8aa857c..7b7e62d4c 100644 --- a/tests/arch/machxo2/mux.ys +++ b/tests/arch/machxo2/mux.ys @@ -35,6 +35,6 @@ proc equiv_opt -assert -map +/machxo2/cells_sim.v synth_machxo2 # equivalency check design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) cd mux16 # Constrain all select calls below inside the top module -select -assert-count 11 t:LUT4 +select -assert-max 12 t:LUT4 select -assert-none t:LUT4 t:FACADE_IO %% t:* %D diff --git a/tests/arch/machxo2/tribuf.ys b/tests/arch/machxo2/tribuf.ys index 9c00a8bcf..fce342e18 100644 --- a/tests/arch/machxo2/tribuf.ys +++ b/tests/arch/machxo2/tribuf.ys @@ -6,5 +6,5 @@ equiv_opt -assert -map +/machxo2/cells_sim.v synth_machxo2 # equivalency check design -load postopt # load the post-opt design (otherwise equiv_opt loads the pre-opt design) cd tristate # Constrain all select calls below inside the top module select -assert-count 3 t:FACADE_IO -select -assert-count 1 t:$not -select -assert-none t:FACADE_IO t:$not %% t:* %D +select -assert-count 1 t:LUT4 +select -assert-none t:FACADE_IO t:LUT4 %% t:* %D diff --git a/tests/arch/nexus/blockram.ys b/tests/arch/nexus/blockram.ys index 9540136d5..a85b5141e 100644 --- a/tests/arch/nexus/blockram.ys +++ b/tests/arch/nexus/blockram.ys @@ -3,7 +3,7 @@ design -save read # Check that we use the right dual and single clock variants -chparam -set ADDRESS_WIDTH 10 -set DATA_WIDTH 18 sync_ram_sdp +chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 36 sync_ram_sdp synth_nexus -top sync_ram_sdp cd sync_ram_sdp select -assert-count 1 t:PDPSC16K @@ -11,7 +11,7 @@ select -assert-none t:PDPSC16K t:INV t:IB t:OB t:VLO t:VHI %% t:* %D design -reset read_verilog blockram_dc.v -chparam -set ADDRESS_WIDTH 10 -set DATA_WIDTH 18 sync_ram_sdp_dc +chparam -set ADDRESS_WIDTH 9 -set DATA_WIDTH 36 sync_ram_sdp_dc synth_nexus -top sync_ram_sdp_dc cd sync_ram_sdp_dc select -assert-count 1 t:PDP16K diff --git a/tests/arch/xilinx/attributes_test.ys b/tests/arch/xilinx/attributes_test.ys index 58552d8fb..74861850f 100644 --- a/tests/arch/xilinx/attributes_test.ys +++ b/tests/arch/xilinx/attributes_test.ys @@ -11,7 +11,7 @@ read_verilog ../common/memory_attributes/attributes_test.v hierarchy -top distributed_ram synth_xilinx -top distributed_ram -noiopad cd distributed_ram # Constrain all select calls below inside the top module -select -assert-count 8 t:RAM32X1D +select -assert-count 1 t:RAM32M # Set ram_style distributed to blockram memory; will be implemented as distributed design -reset @@ -19,7 +19,7 @@ read_verilog ../common/memory_attributes/attributes_test.v setattr -set ram_style "distributed" block_ram/m:* synth_xilinx -top block_ram -noiopad cd block_ram # Constrain all select calls below inside the top module -select -assert-count 32 t:RAM128X1D +select -assert-count 16 t:RAM256X1S # Set synthesis, logic_block to blockram memory; will be implemented as distributed design -reset @@ -28,7 +28,6 @@ setattr -set logic_block 1 block_ram/m:* synth_xilinx -top block_ram -noiopad cd block_ram # Constrain all select calls below inside the top module select -assert-count 0 t:RAMB18E1 -select -assert-count 32 t:RAM128X1D # Set ram_style block to a distributed memory; will be implemented as blockram design -reset @@ -36,10 +35,3 @@ read_verilog ../common/memory_attributes/attributes_test.v synth_xilinx -top distributed_ram_manual -noiopad cd distributed_ram_manual # Constrain all select calls below inside the top module select -assert-count 1 t:RAMB18E1 - -# Set synthesis, ram_block block to a distributed memory; will be implemented as blockram -design -reset -read_verilog ../common/memory_attributes/attributes_test.v -synth_xilinx -top distributed_ram_manual_syn -noiopad -cd distributed_ram_manual_syn # Constrain all select calls below inside the top module -select -assert-count 1 t:RAMB18E1 diff --git a/tests/arch/xilinx/blockram.ys b/tests/arch/xilinx/blockram.ys index ed743cf44..c2b7aede7 100644 --- a/tests/arch/xilinx/blockram.ys +++ b/tests/arch/xilinx/blockram.ys @@ -2,7 +2,7 @@ ### currently. Checking instance counts instead. # Memory bits <= 18K; Data width <= 36; Address width <= 14: -> RAMB18E1 read_verilog ../common/blockram.v -chparam -set ADDRESS_WIDTH 10 -set DATA_WIDTH 1 sync_ram_sdp +chparam -set ADDRESS_WIDTH 12 -set DATA_WIDTH 1 sync_ram_sdp synth_xilinx -top sync_ram_sdp -noiopad cd sync_ram_sdp select -assert-count 1 t:RAMB18E1 @@ -35,7 +35,7 @@ chparam -set ADDRESS_WIDTH 8 -set DATA_WIDTH 2 sync_ram_sdp synth_xilinx -top sync_ram_sdp -noiopad cd sync_ram_sdp select -assert-count 0 t:RAMB18E1 -select -assert-count 4 t:RAM128X1D +select -assert-count 4 t:RAM64M # More than 18K bits, data width <= 36 (TDP), and address width from 10 to 15b (non-cascaded) -> RAMB36E1 design -reset @@ -50,7 +50,7 @@ select -assert-count 1 t:RAMB36E1 design -reset read_verilog ../common/blockram.v -hierarchy -top sync_ram_sdp -chparam ADDRESS_WIDTH 10 -chparam DATA_WIDTH 1 +hierarchy -top sync_ram_sdp -chparam ADDRESS_WIDTH 12 -chparam DATA_WIDTH 1 setattr -set ram_style "block" m:memory synth_xilinx -top sync_ram_sdp -noiopad cd sync_ram_sdp @@ -58,23 +58,7 @@ select -assert-count 1 t:RAMB18E1 design -reset read_verilog ../common/blockram.v -hierarchy -top sync_ram_sdp -chparam ADDRESS_WIDTH 10 -chparam DATA_WIDTH 1 -setattr -set ram_block 1 m:memory -synth_xilinx -top sync_ram_sdp -noiopad -cd sync_ram_sdp -select -assert-count 1 t:RAMB18E1 - -design -reset -read_verilog ../common/blockram.v -hierarchy -top sync_ram_sdp -chparam ADDRESS_WIDTH 10 -chparam DATA_WIDTH 1 -setattr -set ram_style "dont_infer_a_ram_pretty_please" m:memory -synth_xilinx -top sync_ram_sdp -noiopad -cd sync_ram_sdp -select -assert-count 0 t:RAMB18E1 - -design -reset -read_verilog ../common/blockram.v -hierarchy -top sync_ram_sdp -chparam ADDRESS_WIDTH 10 -chparam DATA_WIDTH 1 +hierarchy -top sync_ram_sdp -chparam ADDRESS_WIDTH 12 -chparam DATA_WIDTH 1 setattr -set logic_block 1 m:memory synth_xilinx -top sync_ram_sdp -noiopad cd sync_ram_sdp @@ -87,11 +71,3 @@ setattr -set ram_style "block" m:memory synth_xilinx -top sync_ram_sdp -noiopad cd sync_ram_sdp select -assert-count 1 t:RAMB18E1 - -design -reset -read_verilog ../common/blockram.v -hierarchy -top sync_ram_sdp -chparam ADDRESS_WIDTH 8 -chparam DATA_WIDTH 1 -setattr -set ram_block 1 m:memory -synth_xilinx -top sync_ram_sdp -noiopad -cd sync_ram_sdp -select -assert-count 1 t:RAMB18E1 diff --git a/tests/arch/xilinx/fsm.ys b/tests/arch/xilinx/fsm.ys index ace646af4..3b1919627 100644 --- a/tests/arch/xilinx/fsm.ys +++ b/tests/arch/xilinx/fsm.ys @@ -31,6 +31,7 @@ stat select -assert-count 1 t:BUFG select -assert-count 6 t:FDRE select -assert-count 1 t:LUT1 -select -assert-count 8 t:LUT4 +select -assert-max 1 t:LUT3 +select -assert-max 8 t:LUT4 select -assert-count 5 t:MUXF5 -select -assert-none t:BUFG t:FDRE t:LUT1 t:LUT4 t:MUXF5 %% t:* %D +select -assert-none t:BUFG t:FDRE t:LUT1 t:LUT3 t:LUT4 t:MUXF5 %% t:* %D diff --git a/tests/arch/xilinx/lutram.ys b/tests/arch/xilinx/lutram.ys index cc7354501..34caa8c6c 100644 --- a/tests/arch/xilinx/lutram.ys +++ b/tests/arch/xilinx/lutram.ys @@ -33,8 +33,8 @@ design -load postopt cd lutram_1w1r select -assert-count 1 t:BUFG select -assert-count 8 t:FDRE -select -assert-count 8 t:RAM32X1D -select -assert-none t:BUFG t:FDRE t:RAM32X1D %% t:* %D +select -assert-count 1 t:RAM32M +select -assert-none t:BUFG t:FDRE t:RAM32M %% t:* %D design -reset @@ -51,10 +51,11 @@ sat -verify -prove-asserts -seq 3 -set-init-zero -show-inputs -show-outputs mite design -load postopt cd lutram_1w1r +dump select -assert-count 1 t:BUFG select -assert-count 8 t:FDRE -select -assert-count 8 t:RAM64X1D -select -assert-none t:BUFG t:FDRE t:RAM64X1D %% t:* %D +select -assert-count 8 t:RAM64X1S +select -assert-none t:BUFG t:FDRE t:RAM64X1S %% t:* %D design -reset @@ -133,8 +134,8 @@ design -load postopt cd lutram_1w1r select -assert-count 1 t:BUFG select -assert-count 6 t:FDRE -select -assert-count 2 t:RAM64M -select -assert-none t:BUFG t:FDRE t:RAM64M %% t:* %D +select -assert-count 6 t:RAM64X1S +select -assert-none t:BUFG t:FDRE t:RAM64X1S %% t:* %D design -reset @@ -153,5 +154,5 @@ design -load postopt cd lutram_1w1r select -assert-count 1 t:BUFG select -assert-count 8 t:FDRE -select -assert-count 8 t:RAM16X1D -select -assert-none t:BUFG t:FDRE t:RAM16X1D %% t:* %D +select -assert-count 8 t:RAM16X1S +select -assert-none t:BUFG t:FDRE t:RAM16X1S %% t:* %D diff --git a/tests/arch/xilinx/tribuf.sh b/tests/arch/xilinx/tribuf.sh index bd44395cb..eca33e490 100644 --- a/tests/arch/xilinx/tribuf.sh +++ b/tests/arch/xilinx/tribuf.sh @@ -1,5 +1,5 @@ -! ../../../yosys -qp "synth_xilinx" ../common/tribuf.v -../../../yosys -qp "synth_xilinx -iopad; \ +../../../yosys -f verilog -qp "synth_xilinx" ../common/tribuf.v +../../../yosys -f verilog -qp "synth_xilinx -iopad; \ select -assert-count 2 t:IBUF; \ select -assert-count 1 t:INV; \ select -assert-count 1 t:OBUFT" ../common/tribuf.v diff --git a/tests/bram/run-single.sh b/tests/bram/run-single.sh index 98a45b613..429a79e3c 100644 --- a/tests/bram/run-single.sh +++ b/tests/bram/run-single.sh @@ -1,6 +1,6 @@ #!/bin/bash set -e -../../yosys -qq -p "proc; opt; memory -nomap -bram temp/brams_${2}.txt; opt -fast -full" \ +../../yosys -qq -f verilog -p "proc; opt; memory -nomap -bram temp/brams_${2}.txt; opt -fast -full" \ -l temp/synth_${1}_${2}.log -o temp/synth_${1}_${2}.v temp/brams_${1}.v iverilog -Dvcd_file=\"temp/tb_${1}_${2}.vcd\" -DSIMLIB_MEMDELAY=1 -o temp/tb_${1}_${2}.tb temp/brams_${1}_tb.v \ temp/brams_${1}_ref.v temp/synth_${1}_${2}.v temp/brams_${2}.v ../../techlibs/common/simlib.v diff --git a/tests/memlib/.gitignore b/tests/memlib/.gitignore new file mode 100644 index 000000000..03dbe82ae --- /dev/null +++ b/tests/memlib/.gitignore @@ -0,0 +1,5 @@ +t_*.log +t_*.out +t_*.v +t_*.ys +run-test.mk diff --git a/tests/memlib/generate.py b/tests/memlib/generate.py new file mode 100644 index 000000000..341486584 --- /dev/null +++ b/tests/memlib/generate.py @@ -0,0 +1,900 @@ +# TODO: + +# - memory initialization +# - clock polarity combinations +# - CE/srst/rdwr/be interactions +# - priority logic +# - byte enables, wrbe_separate +# - duplication for read ports +# - abits/dbits determination +# - mixed width +# - swizzles for weird width progressions + + +class Test: + def __init__(self, name, src, libs, defs, cells): + self.name = name + self.src = src + self.libs = libs + self.defs = defs + self.cells = cells + +TESTS = [] + +### basic sanity tests + +ASYNC = """ +module top(clk, ra, wa, rd, wd, we); + +localparam ABITS = {abits}; +localparam DBITS = {dbits}; + +input wire clk; +input wire we; +input wire [ABITS-1:0] ra, wa; +input wire [DBITS-1:0] wd; +output wire [DBITS-1:0] rd; + +reg [DBITS-1:0] mem [0:2**ABITS-1]; + +always @(posedge clk) + if (we) + mem[wa] <= wd; + +assign rd = mem[ra]; + +endmodule +""" + +ASYNC_SMALL = ASYNC.format(abits=6, dbits=6) +ASYNC_BIG = ASYNC.format(abits=11, dbits=10) + +TESTS += [ + Test("async_big", ASYNC_BIG, ["lut", "block_tdp"], [], {"RAM_LUT": 384}), + Test("async_big_block", ASYNC_BIG, ["block_tdp"], [], {"RAM_BLOCK_TDP": 0}), + Test("async_small", ASYNC_SMALL, ["lut", "block_tdp"], [], {"RAM_LUT": 8}), + Test("async_small_block", ASYNC_SMALL, ["block_tdp"], [], {"RAM_BLOCK_TDP": 0}), +] + +SYNC = """ +module top(clk, ra, wa, rd, wd, we); + +localparam ABITS = {abits}; +localparam DBITS = {dbits}; + +input wire clk; +input wire we; +input wire [ABITS-1:0] ra, wa; +input wire [DBITS-1:0] wd; +output reg [DBITS-1:0] rd; + +{attr} +reg [DBITS-1:0] mem [0:2**ABITS-1]; + +always @(posedge clk) + if (we) + mem[wa] <= wd; + +always @(posedge clk) + rd <= mem[ra]; + +endmodule +""" + +SYNC_SMALL = SYNC.format(abits=6, dbits=6, attr="") +SYNC_SMALL_BLOCK = SYNC.format(abits=6, dbits=6, attr='(* ram_style="block" *)') +SYNC_BIG = SYNC.format(abits=11, dbits=10, attr="") +SYNC_MID = SYNC.format(abits=6, dbits=16, attr="") + +TESTS += [ + Test("sync_big", SYNC_BIG, ["lut", "block_tdp"], [], {"RAM_BLOCK_TDP": 20}), + Test("sync_big_sdp", SYNC_BIG, ["lut", "block_sdp"], [], {"RAM_BLOCK_SDP": 20}), + Test("sync_big_lut", SYNC_BIG, ["lut"], [], {"RAM_LUT": 384}), + Test("sync_small", SYNC_SMALL, ["lut", "block_tdp"], [], {"RAM_LUT": 8}), + Test("sync_small_block", SYNC_SMALL, ["block_tdp"], [], {"RAM_BLOCK_TDP": 1}), + Test("sync_small_block_attr", SYNC_SMALL_BLOCK, ["lut", "block_tdp"], [], {"RAM_BLOCK_TDP": 1}), +] + +### basic TDP test + +TDP = """ +module top(clka, clkb, addra, addrb, rda, rdb, wda, wdb, wea, web); + +localparam ABITS = 6; +localparam DBITS = 6; + +input wire clka, clkb; +input wire wea, web; +input wire [ABITS-1:0] addra, addrb; +input wire [DBITS-1:0] wda, wdb; +output reg [DBITS-1:0] rda, rdb; + +reg [DBITS-1:0] mem [0:2**ABITS-1]; + +always @(posedge clka) + if (wea) + mem[addra] <= wda; + else + rda <= mem[addra]; + +always @(posedge clkb) + if (web) + mem[addrb] <= wdb; + else + rdb <= mem[addrb]; + +endmodule +""" + +TESTS += [ + Test("tdp", TDP, ["block_tdp", "block_sdp"], [], {"RAM_BLOCK_TDP": 1}), +] + +# shared clock + +SYNC_2CLK = """ +module top(rclk, wclk, ra, wa, rd, wd, we); + +localparam ABITS = 6; +localparam DBITS = 16; + +input wire rclk, wclk; +input wire we; +input wire [ABITS-1:0] ra, wa; +input wire [DBITS-1:0] wd; +output reg [DBITS-1:0] rd; + +reg [DBITS-1:0] mem [0:2**ABITS-1]; + +always @(posedge wclk) + if (we) + mem[wa] <= wd; + +always @(posedge rclk) + rd <= mem[ra]; + +endmodule +""" + +TESTS += [ + Test("sync_2clk", SYNC_2CLK, ["block_sdp"], [], {"RAM_BLOCK_SDP": 1}), + Test("sync_shared", SYNC_MID, ["block_sdp_1clk"], [], {"RAM_BLOCK_SDP_1CLK": 1}), + Test("sync_2clk_shared", SYNC_2CLK, ["block_sdp_1clk"], [], {"RAM_BLOCK_SDP_1CLK": 0}), +] + +# inter-port transparency + +SYNC_TRANS = """ +module top(clk, ra, wa, rd, wd, we); + +localparam ABITS = 6; +localparam DBITS = 16; + +input wire clk; +input wire we; +input wire [ABITS-1:0] ra, wa; +input wire [DBITS-1:0] wd; +output reg [DBITS-1:0] rd; + +reg [DBITS-1:0] mem [0:2**ABITS-1]; + +always @(negedge clk) + if (we) + mem[wa] <= wd; + +always @(negedge clk) begin + rd <= mem[ra]; + if (we && ra == wa) + rd <= wd; +end + +endmodule +""" + +TESTS += [ + Test("sync_trans_old_old", SYNC_MID, ["block_sdp_1clk"], ["TRANS_OLD"], {"RAM_BLOCK_SDP_1CLK": (1, {"OPTION_TRANS": 0})}), + Test("sync_trans_old_new", SYNC_MID, ["block_sdp_1clk"], ["TRANS_NEW"], {"RAM_BLOCK_SDP_1CLK": 1}), + Test("sync_trans_old_none", SYNC_MID, ["block_sdp_1clk"], [], {"RAM_BLOCK_SDP_1CLK": 1}), + Test("sync_trans_new_old", SYNC_TRANS, ["block_sdp_1clk"], ["TRANS_OLD"], {"RAM_BLOCK_SDP_1CLK": 1}), + Test("sync_trans_new_new", SYNC_TRANS, ["block_sdp_1clk"], ["TRANS_NEW"], {"RAM_BLOCK_SDP_1CLK": (1, {"OPTION_TRANS": 1})}), + Test("sync_trans_new_none", SYNC_TRANS, ["block_sdp_1clk"], [], {"RAM_BLOCK_SDP_1CLK": 1}), +] + +# rdwr checks + +SP_NO_CHANGE = """ +module top(clk, addr, rd, wd, we); + +input wire clk; +input wire we; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +always @(negedge clk) begin + if (we) + mem[addr] <= wd; + else + rd <= mem[addr]; +end + +endmodule +""" + +SP_NO_CHANGE_BE = """ +module top(clk, addr, rd, wd, we); + +input wire clk; +input wire [1:0] we; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +always @(negedge clk) begin + if (we) begin + if (we[0]) + mem[addr][7:0] <= wd[7:0]; + if (we[1]) + mem[addr][15:8] <= wd[15:8]; + end else + rd <= mem[addr]; +end + +endmodule +""" + +SP_NEW = """ +module top(clk, addr, rd, wd, we); + +input wire clk; +input wire we; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +always @(negedge clk) begin + if (we) begin + mem[addr] <= wd; + rd <= wd; + end else + rd <= mem[addr]; +end + +endmodule +""" + +SP_NEW_BE = """ +module top(clk, addr, rd, wd, we); + +input wire clk; +input wire [1:0] we; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +always @(negedge clk) begin + rd <= mem[addr]; + if (we[0]) begin + mem[addr][7:0] <= wd[7:0]; + rd[7:0] <= wd[7:0]; + end + if (we[1]) begin + mem[addr][15:8] <= wd[15:8]; + rd[15:8] <= wd[15:8]; + end +end + +endmodule +""" + +SP_OLD = """ +module top(clk, addr, rd, wd, we); + +input wire clk; +input wire we; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +always @(negedge clk) begin + if (we) + mem[addr] <= wd; + rd <= mem[addr]; +end + +endmodule +""" + +SP_OLD_BE = """ +module top(clk, addr, rd, wd, we); + +input wire clk; +input wire [1:0] we; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +always @(negedge clk) begin + if (we[0]) + mem[addr][7:0] <= wd[7:0]; + if (we[1]) + mem[addr][15:8] <= wd[15:8]; + rd <= mem[addr]; +end + +endmodule +""" + +TESTS += [ + Test("sp_nc_none", SP_NO_CHANGE, ["block_sp"], [], {"RAM_BLOCK_SP": 1}), + Test("sp_new_none", SP_NEW, ["block_sp"], [], {"RAM_BLOCK_SP": 1}), + Test("sp_old_none", SP_OLD, ["block_sp"], [], {"RAM_BLOCK_SP": 0}), + Test("sp_nc_nc", SP_NO_CHANGE, ["block_sp"], ["RDWR_NO_CHANGE"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_nc", SP_NEW, ["block_sp"], ["RDWR_NO_CHANGE"], {"RAM_BLOCK_SP": 1}), + Test("sp_old_nc", SP_OLD, ["block_sp"], ["RDWR_NO_CHANGE"], {"RAM_BLOCK_SP": 0}), + Test("sp_nc_new", SP_NO_CHANGE, ["block_sp"], ["RDWR_NEW"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_new", SP_NEW, ["block_sp"], ["RDWR_NEW"], {"RAM_BLOCK_SP": 1}), + Test("sp_old_new", SP_OLD, ["block_sp"], ["RDWR_NEW"], {"RAM_BLOCK_SP": 0}), + Test("sp_nc_old", SP_NO_CHANGE, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_old", SP_NEW, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_old_old", SP_OLD, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_nc_new_only", SP_NO_CHANGE, ["block_sp"], ["RDWR_NEW_ONLY"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_new_only", SP_NEW, ["block_sp"], ["RDWR_NEW_ONLY"], {"RAM_BLOCK_SP": 1}), + Test("sp_old_new_only", SP_OLD, ["block_sp"], ["RDWR_NEW_ONLY"], {"RAM_BLOCK_SP": 0}), + Test("sp_nc_new_only_be", SP_NO_CHANGE_BE, ["block_sp"], ["RDWR_NEW_ONLY"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_new_only_be", SP_NEW_BE, ["block_sp"], ["RDWR_NEW_ONLY"], {"RAM_BLOCK_SP": 2}), + Test("sp_old_new_only_be", SP_OLD_BE, ["block_sp"], ["RDWR_NEW_ONLY"], {"RAM_BLOCK_SP": 0}), + Test("sp_nc_new_be", SP_NO_CHANGE_BE, ["block_sp"], ["RDWR_NEW"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_new_be", SP_NEW_BE, ["block_sp"], ["RDWR_NEW"], {"RAM_BLOCK_SP": 1}), + Test("sp_old_new_be", SP_OLD_BE, ["block_sp"], ["RDWR_NEW"], {"RAM_BLOCK_SP": 0}), + Test("sp_nc_old_be", SP_NO_CHANGE_BE, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_old_be", SP_NEW_BE, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_old_old_be", SP_OLD_BE, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_nc_nc_be", SP_NO_CHANGE_BE, ["block_sp"], ["RDWR_NO_CHANGE"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_nc_be", SP_NEW_BE, ["block_sp"], ["RDWR_NO_CHANGE"], {"RAM_BLOCK_SP": 2}), + Test("sp_old_nc_be", SP_OLD_BE, ["block_sp"], ["RDWR_NO_CHANGE"], {"RAM_BLOCK_SP": 0}), + Test("sp_nc_auto", SP_NO_CHANGE, ["block_sp"], ["RDWR_NO_CHANGE", "RDWR_OLD", "RDWR_NEW"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_auto", SP_NEW, ["block_sp"], ["RDWR_NO_CHANGE", "RDWR_OLD", "RDWR_NEW"], {"RAM_BLOCK_SP": (1, {"OPTION_RDWR": "NEW"})}), + Test("sp_old_auto", SP_OLD, ["block_sp"], ["RDWR_NO_CHANGE", "RDWR_OLD", "RDWR_NEW"], {"RAM_BLOCK_SP": (1, {"OPTION_RDWR": "OLD"})}), + Test("sp_nc_auto_be", SP_NO_CHANGE_BE, ["block_sp"], ["RDWR_NO_CHANGE", "RDWR_OLD", "RDWR_NEW"], {"RAM_BLOCK_SP": 1}), + Test("sp_new_auto_be", SP_NEW_BE, ["block_sp"], ["RDWR_NO_CHANGE", "RDWR_OLD", "RDWR_NEW"], {"RAM_BLOCK_SP": (1, {"OPTION_RDWR": "NEW"})}), + Test("sp_old_auto_be", SP_OLD_BE, ["block_sp"], ["RDWR_NO_CHANGE", "RDWR_OLD", "RDWR_NEW"], {"RAM_BLOCK_SP": (1, {"OPTION_RDWR": "OLD"})}), +] + +SP_INIT = """ +module top(clk, addr, rd, wd, we, re); + +input wire clk; +input wire we, re; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +initial rd = {ival}; + +always @(posedge clk) begin + if (we) + mem[addr] <= wd; + if (re) + rd <= mem[addr]; +end + +endmodule +""" + +SP_INIT_X = SP_INIT.format(ival="16'hxxxx") +SP_INIT_0 = SP_INIT.format(ival="16'h0000") +SP_INIT_V = SP_INIT.format(ival="16'h55aa") + +TESTS += [ + Test("sp_init_x_x", SP_INIT_X, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_x_x_re", SP_INIT_X, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_x_x_ce", SP_INIT_X, ["block_sp"], ["CLKEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_0_x", SP_INIT_0, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_0_x_re", SP_INIT_0, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_0_0", SP_INIT_0, ["block_sp"], ["RDINIT_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_0_0_re", SP_INIT_0, ["block_sp"], ["RDINIT_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_0_any", SP_INIT_0, ["block_sp"], ["RDINIT_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_0_any_re", SP_INIT_0, ["block_sp"], ["RDINIT_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_v_x", SP_INIT_V, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_v_x_re", SP_INIT_V, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_v_0", SP_INIT_V, ["block_sp"], ["RDINIT_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_v_0_re", SP_INIT_V, ["block_sp"], ["RDINIT_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_v_any", SP_INIT_V, ["block_sp"], ["RDINIT_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_init_v_any_re", SP_INIT_V, ["block_sp"], ["RDINIT_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), +] + +SP_ARST = """ +module top(clk, addr, rd, wd, we, re, ar); + +input wire clk; +input wire we, re, ar; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +initial rd = {ival}; + +always @(posedge clk) begin + if (we) + mem[addr] <= wd; +end +always @(posedge clk, posedge ar) begin + if (ar) + rd <= {aval}; + else if (re) + rd <= mem[addr]; +end + +endmodule +""" + +SP_ARST_X = SP_ARST.format(ival="16'hxxxx", aval="16'hxxxx") +SP_ARST_0 = SP_ARST.format(ival="16'hxxxx", aval="16'h0000") +SP_ARST_V = SP_ARST.format(ival="16'hxxxx", aval="16'h55aa") +SP_ARST_E = SP_ARST.format(ival="16'h55aa", aval="16'h55aa") +SP_ARST_N = SP_ARST.format(ival="16'h1234", aval="16'h55aa") + +TESTS += [ + Test("sp_arst_x_x", SP_ARST_X, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_x_x_re", SP_ARST_X, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_x", SP_ARST_0, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_x_re", SP_ARST_0, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_0", SP_ARST_0, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_0_re", SP_ARST_0, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_any", SP_ARST_0, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_any_re", SP_ARST_0, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_init", SP_ARST_0, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_0_init_re", SP_ARST_0, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_x", SP_ARST_V, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_x_re", SP_ARST_V, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_0", SP_ARST_V, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_0_re", SP_ARST_V, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_any", SP_ARST_V, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_any_re", SP_ARST_V, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_init", SP_ARST_V, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_v_init_re", SP_ARST_V, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_x", SP_ARST_E, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_x_re", SP_ARST_E, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_0", SP_ARST_E, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_0_re", SP_ARST_E, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_any", SP_ARST_E, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_any_re", SP_ARST_E, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_init", SP_ARST_E, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_e_init_re", SP_ARST_E, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_x", SP_ARST_N, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_x_re", SP_ARST_N, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_0", SP_ARST_N, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_0_re", SP_ARST_N, ["block_sp"], ["RDINIT_ANY", "RDARST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_any", SP_ARST_N, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_any_re", SP_ARST_N, ["block_sp"], ["RDINIT_ANY", "RDARST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_init", SP_ARST_N, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_arst_n_init_re", SP_ARST_N, ["block_sp"], ["RDINIT_ANY", "RDARST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), +] + +SP_SRST = """ +module top(clk, addr, rd, wd, we, re, sr); + +input wire clk; +input wire we, re, sr; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +initial rd = {ival}; + +always @(posedge clk) begin + if (we) + mem[addr] <= wd; +end +always @(posedge clk) begin + if (sr) + rd <= {sval}; + else if (re) + rd <= mem[addr]; +end + +endmodule +""" + +SP_SRST_G = """ +module top(clk, addr, rd, wd, we, re, sr); + +input wire clk; +input wire we, re, sr; +input wire [3:0] addr; +input wire [15:0] wd; +output reg [15:0] rd; + +reg [15:0] mem [0:15]; + +initial rd = {ival}; + +always @(posedge clk) begin + if (we) + mem[addr] <= wd; +end +always @(posedge clk) begin + if (re) begin + if (sr) + rd <= {sval}; + else + rd <= mem[addr]; + end +end + +endmodule +""" + +SP_SRST_X = SP_SRST.format(ival="16'hxxxx", sval="16'hxxxx") +SP_SRST_0 = SP_SRST.format(ival="16'hxxxx", sval="16'h0000") +SP_SRST_V = SP_SRST.format(ival="16'hxxxx", sval="16'h55aa") +SP_SRST_E = SP_SRST.format(ival="16'h55aa", sval="16'h55aa") +SP_SRST_N = SP_SRST.format(ival="16'h1234", sval="16'h55aa") +SP_SRST_GV = SP_SRST_G.format(ival="16'hxxxx", sval="16'h55aa") + +TESTS += [ + Test("sp_srst_x_x", SP_SRST_X, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_x_x_re", SP_SRST_X, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_x", SP_SRST_0, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_x_re", SP_SRST_0, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_0", SP_SRST_0, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_0_re", SP_SRST_0, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_any", SP_SRST_0, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_any_re", SP_SRST_0, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_init", SP_SRST_0, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_0_init_re", SP_SRST_0, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_x", SP_SRST_V, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_x_re", SP_SRST_V, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_0", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_0_re", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_any", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_any_re", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_any_re_gated", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY_RE", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_any_ce", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "CLKEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_any_ce_gated", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY_CE", "CLKEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_init", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_v_init_re", SP_SRST_V, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_x", SP_SRST_E, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_x_re", SP_SRST_E, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_0", SP_SRST_E, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_0_re", SP_SRST_E, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_any", SP_SRST_E, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_any_re", SP_SRST_E, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_init", SP_SRST_E, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_e_init_re", SP_SRST_E, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_x", SP_SRST_N, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_x_re", SP_SRST_N, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_0", SP_SRST_N, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_0_re", SP_SRST_N, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_any", SP_SRST_N, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_any_re", SP_SRST_N, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_init", SP_SRST_N, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_n_init_re", SP_SRST_N, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_x", SP_SRST_GV, ["block_sp"], ["RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_x_re", SP_SRST_GV, ["block_sp"], ["RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_0", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_0_re", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_0", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_any", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_any_re", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_any_re_gated", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY_RE", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_any_ce", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY", "CLKEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_any_ce_gated", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_ANY_CE", "CLKEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_init", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), + Test("sp_srst_gv_init_re", SP_SRST_GV, ["block_sp"], ["RDINIT_ANY", "RDSRST_INIT", "RDEN", "RDWR_OLD"], {"RAM_BLOCK_SP": 1}), +] + +WIDE_SDP = """ +module top(rclk, ra, rd, re, rr, wclk, wa, wd, we); + +input wire rclk, wclk, re, rr; +input wire [2**({ww}-{bw})-1:0] we; +input wire [{aw}-{rw}+{xw}-1:0] ra; +input wire [{aw}-{ww}+{xw}-1:0] wa; +input wire [2**{ww}-1:0] wd; +output reg [2**{rw}-1:0] rd; + +reg mem [0:2**{aw}-1]; + +initial mem[3] = 0; +initial mem[17] = 1; +initial mem[23] = 0; +initial mem[24] = 1; + +integer i, j; +always @(posedge wclk) + for (i = 0; i < 2**{ww}; i = i + 2**{bw}) + if (we[i >> {bw}]) + for (j = 0; j < 2**{bw}; j = j + 1) + mem[wa << {ww} | i | j] <= wd[i | j]; + +always @(posedge rclk) + if (rr) + rd <= {sval}; + else if (re) + for (i = 0; i < 2**{rw}; i = i + 1) + rd[i] <= mem[ra << {rw} | i]; + +endmodule +""" + +for (aw, rw, ww, bw, xw, sval, cnt) in [ + (6, 1, 1, 1, 1, "2'h1", 1), + (7, 1, 1, 1, 1, "2'h2", 2), + (8, 1, 1, 1, 1, "2'h3", 4), + (6, 0, 0, 0, 0, "2'h0", 1), + (6, 1, 0, 0, 0, "2'h0", 1), + (6, 2, 0, 0, 0, "2'h0", 1), + (6, 3, 0, 0, 0, "2'h0", 1), + (6, 4, 0, 0, 0, "2'h0", 1), + (6, 5, 0, 0, 0, "2'h0", 2), + (6, 0, 1, 0, 0, "2'h0", 2), + (6, 0, 1, 1, 0, "2'h0", 1), + (6, 0, 2, 0, 0, "2'h0", 4), + (6, 0, 2, 2, 0, "2'h0", 1), + (6, 0, 3, 2, 0, "2'h0", 1), + (6, 0, 4, 2, 0, "2'h0", 1), + (6, 0, 5, 2, 0, "2'h0", 2), + (7, 0, 0, 0, 0, "2'h0", 2), + (7, 1, 0, 0, 0, "2'h0", 2), + (7, 2, 0, 0, 0, "2'h0", 2), + (7, 3, 0, 0, 0, "2'h0", 2), + (7, 4, 0, 0, 0, "2'h0", 2), + (7, 5, 0, 0, 0, "2'h0", 2), + (7, 0, 1, 0, 0, "2'h0", 2), + (7, 0, 1, 1, 0, "2'h0", 2), + (7, 0, 2, 0, 0, "2'h0", 4), + (7, 0, 2, 2, 0, "2'h0", 2), + (7, 0, 3, 2, 0, "2'h0", 2), + (7, 0, 4, 2, 0, "2'h0", 2), + (7, 0, 5, 2, 0, "2'h0", 2), +]: + TESTS.append(Test( + f"wide_sdp_a{aw}r{rw}w{ww}b{bw}x{xw}", + WIDE_SDP.format(aw=aw, rw=rw, ww=ww, bw=bw, xw=xw, sval=sval), + ["wide_sdp"], [], + {"RAM_WIDE_SDP": cnt} + )) + +WIDE_SP = """ +module top(clk, a, rd, re, rr, wd, we); + +input wire clk, re, rr; +input wire [2**({ww}-{bw})-1:0] we; +input wire [{aw}-1:0] a; +input wire [2**{ww}-1:0] wd; +output reg [2**{rw}-1:0] rd; + +reg mem [0:2**{aw}-1]; + +initial mem[3] = 0; +initial mem[17] = 1; +initial mem[23] = 0; +initial mem[24] = 1; + +integer i, j; +always @(posedge clk) begin + for (i = 0; i < 2**{ww}; i = i + 2**{bw}) + if (we[i >> {bw}]) + for (j = 0; j < 2**{bw}; j = j + 1) + mem[a & ~((1 << {ww}) - 1) | i | j] <= wd[i | j]; + if (rr) + rd <= {sval}; + else if (re) + for (i = 0; i < 2**{rw}; i = i + 1) + rd[i] <= mem[a & ~((1 << {rw}) - 1) | i]; +end + +endmodule +""" + +for (aw, rw, ww, bw, sval, cnt) in [ + (6, 1, 1, 1, "2'h1", 1), + (7, 1, 1, 1, "2'h2", 2), + (8, 1, 1, 1, "2'h3", 4), + (6, 0, 0, 0, "2'h0", 1), + (6, 1, 0, 0, "2'h0", 1), + (6, 2, 0, 0, "2'h0", 1), + (6, 3, 0, 0, "2'h0", 1), + (6, 4, 0, 0, "2'h0", 1), + (6, 5, 0, 0, "2'h0", 2), + (6, 0, 1, 0, "2'h0", 2), + (6, 0, 1, 1, "2'h0", 1), + (6, 0, 2, 0, "2'h0", 4), + (6, 0, 2, 2, "2'h0", 1), + (6, 0, 3, 2, "2'h0", 1), + (6, 0, 4, 2, "2'h0", 1), + (6, 0, 5, 2, "2'h0", 2), + (7, 0, 0, 0, "2'h0", 2), + (7, 1, 0, 0, "2'h0", 2), + (7, 2, 0, 0, "2'h0", 2), + (7, 3, 0, 0, "2'h0", 2), + (7, 4, 0, 0, "2'h0", 2), + (7, 5, 0, 0, "2'h0", 2), + (7, 0, 1, 0, "2'h0", 2), + (7, 0, 1, 1, "2'h0", 2), + (7, 0, 2, 0, "2'h0", 4), + (7, 0, 2, 2, "2'h0", 2), + (7, 0, 3, 2, "2'h0", 2), + (7, 0, 4, 2, "2'h0", 2), + (7, 0, 5, 2, "2'h0", 2), +]: + TESTS.append(Test( + f"wide_sp_mix_a{aw}r{rw}w{ww}b{bw}", + WIDE_SP.format(aw=aw, rw=rw, ww=ww, bw=bw, sval=sval), + ["wide_sp"], ["WIDTH_MIX"], + {"RAM_WIDE_SP": cnt} + )) + +for (aw, rw, ww, bw, sval, cnt) in [ + (6, 1, 1, 1, "2'h1", 1), + (7, 1, 1, 1, "2'h2", 2), + (8, 1, 1, 1, "2'h3", 4), + (6, 0, 0, 0, "2'h0", 1), + (6, 1, 0, 0, "2'h0", 2), + (6, 2, 0, 0, "2'h0", 4), + (6, 3, 0, 0, "2'h0", 4), + (6, 4, 0, 0, "2'h0", 4), + (6, 5, 0, 0, "2'h0", 8), + (6, 0, 1, 0, "2'h0", 2), + (6, 0, 1, 1, "2'h0", 1), + (6, 0, 2, 0, "2'h0", 4), + (6, 0, 2, 2, "2'h0", 1), + (6, 0, 3, 2, "2'h0", 1), + (6, 0, 4, 2, "2'h0", 1), + (6, 0, 5, 2, "2'h0", 2), + (7, 0, 0, 0, "2'h0", 2), + (7, 1, 0, 0, "2'h0", 2), + (7, 2, 0, 0, "2'h0", 4), + (7, 3, 0, 0, "2'h0", 8), + (7, 4, 0, 0, "2'h0", 8), + (7, 5, 0, 0, "2'h0", 8), + (7, 0, 1, 0, "2'h0", 2), + (7, 0, 1, 1, "2'h0", 2), + (7, 0, 2, 0, "2'h0", 4), + (7, 0, 2, 2, "2'h0", 2), + (7, 0, 3, 2, "2'h0", 2), + (7, 0, 4, 2, "2'h0", 2), + (7, 0, 5, 2, "2'h0", 2), +]: + TESTS.append(Test( + f"wide_sp_tied_a{aw}r{rw}w{ww}b{bw}", + WIDE_SP.format(aw=aw, rw=rw, ww=ww, bw=bw, sval=sval), + ["wide_sp"], [], + {"RAM_WIDE_SP": cnt} + )) + +WIDE_RW = """ +module top(clk, a, rd, re, wd, we); + +input wire clk, re; +input wire [2**({ww}-{bw})-1:0] we; +input wire [{aw}-1:0] a; +input wire [2**{ww}-1:0] wd; +output reg [2**{rw}-1:0] rd; + +(* ram_block *) +reg mem [0:2**{aw}-1]; + +initial mem[3] = 0; +initial mem[17] = 1; +initial mem[23] = 0; +initial mem[24] = 1; + +integer i, j; +always @(posedge clk) begin + for (i = 0; i < 2**{ww}; i = i + 2**{bw}) + if (we[i >> {bw}]) + for (j = 0; j < 2**{bw}; j = j + 1) + mem[a & ~((1 << {ww}) - 1) | i | j] <= wd[i | j]; + if (re) + for (i = 0; i < 2**{rw}; i = i + 1) + rd[i] <= mem[a & ~((1 << {rw}) - 1) | i]; +end + +endmodule +""" + +for (aw, rw, ww, bw, cntww, cntwr) in [ + (6, 1, 1, 1, 2, 1), + (7, 1, 1, 1, 4, 2), + (8, 1, 1, 1, 8, 4), + (6, 0, 0, 0, 4, 2), + (6, 1, 0, 0, 4, 2), + (6, 2, 0, 0, 4, 2), + (6, 3, 0, 0, 8, 2), + (6, 4, 0, 0, 16, 4), + (6, 5, 0, 0, 32, 8), + (6, 0, 1, 0, 4, 2), + (6, 0, 1, 1, 2, 1), + (6, 0, 2, 0, 4, 4), + (6, 0, 2, 2, 1, 2), + (6, 0, 3, 2, 1, 4), + (6, 0, 4, 2, 2, 8), + (6, 0, 5, 2, 4, 16), + (7, 0, 0, 0, 8, 4), + (7, 1, 0, 0, 8, 4), + (7, 2, 0, 0, 8, 4), + (7, 3, 0, 0, 8, 4), + (7, 4, 0, 0, 16, 4), + (7, 5, 0, 0, 32, 8), + (7, 0, 1, 0, 8, 4), + (7, 0, 1, 1, 4, 2), + (7, 0, 2, 0, 8, 4), + (7, 0, 2, 2, 2, 2), + (7, 0, 3, 2, 2, 4), + (7, 0, 4, 2, 2, 8), + (7, 0, 5, 2, 4, 16), +]: + TESTS.append(Test( + f"wide_read_a{aw}r{rw}w{ww}b{bw}", + WIDE_RW.format(aw=aw, rw=rw, ww=ww, bw=bw), + ["wide_read"], [], + {"RAM_WIDE_READ": cntwr} + )) + TESTS.append(Test( + f"wide_write_a{aw}r{rw}w{ww}b{bw}", + WIDE_RW.format(aw=aw, rw=rw, ww=ww, bw=bw), + ["wide_write"], [], + {"RAM_WIDE_WRITE": cntww} + )) + +with open("run-test.mk", "w") as mf: + mf.write("ifneq ($(strip $(SEED)),)\n") + mf.write("SEEDOPT=-S$(SEED)\n") + mf.write("endif\n") + mf.write("all:") + for t in TESTS: + mf.write(" " + t.name) + mf.write("\n") + mf.write(".PHONY: all\n") + + + for t in TESTS: + with open("t_{}.v".format(t.name), "w") as tf: + tf.write(t.src) + with open("t_{}.ys".format(t.name), "w") as sf: + sf.write("proc\n") + sf.write("opt\n") + sf.write("opt -full\n") + sf.write("memory -nomap\n") + sf.write("dump\n") + sf.write("memory_libmap") + for lib in t.libs: + sf.write(" -lib ../memlib_{}.txt".format(lib)) + for d in t.defs: + sf.write(" -D {}".format(d)) + sf.write("\n") + sf.write("memory_map\n") + for k, v in t.cells.items(): + if isinstance(v, tuple): + (cc, ca) = v + sf.write("select -assert-count {} t:{}\n".format(cc, k)) + for kk, vv in ca.items(): + sf.write("select -assert-count {} t:{} r:{}={} %i\n".format(cc, k, kk, vv)) + else: + sf.write("select -assert-count {} t:{}\n".format(v, k)) + mf.write("{}:\n".format(t.name)) + mf.write("\t@../tools/autotest.sh -G -j $(SEEDOPT) $(EXTRA_FLAGS) -p 'script ../t_{}.ys'".format(t.name)) + for lib in t.libs: + mf.write(" -l memlib_{}.v".format(lib)) + mf.write(" t_{}.v || (cat t_{}.err; exit 1)\n".format(t.name, t.name)) + mf.write(".PHONY: {}\n".format(t.name)) diff --git a/tests/memlib/memlib_block_sdp.txt b/tests/memlib/memlib_block_sdp.txt new file mode 100644 index 000000000..6c34c5a96 --- /dev/null +++ b/tests/memlib/memlib_block_sdp.txt @@ -0,0 +1,12 @@ +ram block \RAM_BLOCK_SDP { + cost 64; + abits 10; + widths 1 2 4 8 16 per_port; + init any; + port sw "W" { + clock anyedge; + } + port sr "R" { + clock anyedge; + } +} diff --git a/tests/memlib/memlib_block_sdp.v b/tests/memlib/memlib_block_sdp.v new file mode 100644 index 000000000..d8dac68e3 --- /dev/null +++ b/tests/memlib/memlib_block_sdp.v @@ -0,0 +1,26 @@ +module RAM_BLOCK_SDP( + input PORT_R_CLK, + input [9:0] PORT_R_ADDR, + output reg [15:0] PORT_R_RD_DATA, + input PORT_W_CLK, + input PORT_W_WR_EN, + input [9:0] PORT_W_ADDR, + input [15:0] PORT_W_WR_DATA +); + +parameter INIT = 0; +parameter PORT_R_WIDTH = 1; +parameter PORT_W_WIDTH = 1; +parameter PORT_R_CLK_POL = 0; +parameter PORT_W_CLK_POL = 0; + +reg [2**10-1:0] mem = INIT; + +always @(negedge (PORT_R_CLK ^ PORT_R_CLK_POL)) + PORT_R_RD_DATA <= mem[PORT_R_ADDR+:PORT_R_WIDTH]; + +always @(negedge (PORT_W_CLK ^ PORT_W_CLK_POL)) + if (PORT_W_WR_EN) + mem[PORT_W_ADDR+:PORT_W_WIDTH] <= PORT_W_WR_DATA; + +endmodule diff --git a/tests/memlib/memlib_block_sdp_1clk.txt b/tests/memlib/memlib_block_sdp_1clk.txt new file mode 100644 index 000000000..07c76c2a2 --- /dev/null +++ b/tests/memlib/memlib_block_sdp_1clk.txt @@ -0,0 +1,22 @@ +ram block \RAM_BLOCK_SDP_1CLK { + cost 64; + abits 10; + widths 1 2 4 8 16 per_port; + init any; + port sw "W" { + clock anyedge "C"; + ifdef TRANS_OLD { + option "TRANS" 0 { + wrtrans "R" old; + } + } + ifdef TRANS_NEW { + option "TRANS" 1 { + wrtrans "R" new; + } + } + } + port sr "R" { + clock anyedge "C"; + } +} diff --git a/tests/memlib/memlib_block_sdp_1clk.v b/tests/memlib/memlib_block_sdp_1clk.v new file mode 100644 index 000000000..5e8159f9d --- /dev/null +++ b/tests/memlib/memlib_block_sdp_1clk.v @@ -0,0 +1,36 @@ +module RAM_BLOCK_SDP_1CLK( + input CLK_C, + input PORT_R_CLK, + input [9:0] PORT_R_ADDR, + output reg [15:0] PORT_R_RD_DATA, + input PORT_W_CLK, + input PORT_W_WR_EN, + input [9:0] PORT_W_ADDR, + input [15:0] PORT_W_WR_DATA +); + +parameter PORT_R_CLK_POL = 0; +parameter PORT_W_CLK_POL = 0; +parameter CLK_C_POL = 0; +parameter INIT = 0; +parameter OPTION_TRANS = 2; +parameter PORT_R_WIDTH = 1; +parameter PORT_W_WIDTH = 1; + +reg [2**10-1:0] mem = INIT; + +always @(negedge (CLK_C ^ CLK_C_POL)) begin + if (OPTION_TRANS == 0) + PORT_R_RD_DATA <= mem[PORT_R_ADDR+:PORT_R_WIDTH]; + if (PORT_W_WR_EN) + mem[PORT_W_ADDR+:PORT_W_WIDTH] = 16'hx; + if (OPTION_TRANS == 2) + PORT_R_RD_DATA <= mem[PORT_R_ADDR+:PORT_R_WIDTH]; + if (PORT_W_WR_EN) + mem[PORT_W_ADDR+:PORT_W_WIDTH] = PORT_W_WR_DATA; + if (OPTION_TRANS == 1) + PORT_R_RD_DATA <= mem[PORT_R_ADDR+:PORT_R_WIDTH]; +end + + +endmodule diff --git a/tests/memlib/memlib_block_sp.txt b/tests/memlib/memlib_block_sp.txt new file mode 100644 index 000000000..f99320d73 --- /dev/null +++ b/tests/memlib/memlib_block_sp.txt @@ -0,0 +1,95 @@ +ram block \RAM_BLOCK_SP { + cost 2; + abits 4; + width 16; + byte 8; + port srsw "A" { + clock posedge; + ifdef CLKEN { + clken; + } + ifdef RDEN { + rden; + } + ifdef RDWR_NO_CHANGE { + option "RDWR" "NO_CHANGE" { + rdwr no_change; + } + } + ifdef RDWR_OLD { + option "RDWR" "OLD" { + rdwr old; + } + } + ifdef RDWR_NEW { + option "RDWR" "NEW" { + rdwr new; + } + } + ifdef RDWR_NEW_ONLY { + option "RDWR" "NEW_ONLY" { + rdwr new_only; + } + } + ifdef RDINIT_0 { + option "RDINIT" "ZERO" { + rdinit zero; + } + } + ifdef RDINIT_ANY { + option "RDINIT" "ANY" { + rdinit any; + } + } + ifdef RDARST_0 { + option "RDARST" "ZERO" { + rdarst zero; + } + } + ifdef RDARST_ANY { + option "RDARST" "ANY" { + rdarst any; + } + } + ifdef RDARST_INIT { + option "RDARST" "INIT" { + rdarst init; + } + } + ifdef RDSRST_0 { + option "SRST_GATE" 0 { + option "RDSRST" "ZERO" { + rdsrst zero ungated; + } + } + } + ifdef RDSRST_ANY { + option "SRST_GATE" 0 { + option "RDSRST" "ANY" { + rdsrst any ungated; + } + } + } + ifdef RDSRST_INIT { + option "SRST_GATE" 0 { + option "RDSRST" "INIT" { + rdsrst init ungated; + } + } + } + ifdef RDSRST_ANY_CE { + option "SRST_GATE" 1 { + option "RDSRST" "ANY" { + rdsrst any gated_clken; + } + } + } + ifdef RDSRST_ANY_RE { + option "SRST_GATE" 2 { + option "RDSRST" "ANY" { + rdsrst any gated_rden; + } + } + } + } +} diff --git a/tests/memlib/memlib_block_sp.v b/tests/memlib/memlib_block_sp.v new file mode 100644 index 000000000..1f7830137 --- /dev/null +++ b/tests/memlib/memlib_block_sp.v @@ -0,0 +1,81 @@ +module RAM_BLOCK_SP( + input PORT_A_CLK, + input PORT_A_CLK_EN, + input PORT_A_RD_EN, + input PORT_A_RD_ARST, + input PORT_A_RD_SRST, + input [1:0] PORT_A_WR_EN, + input [3:0] PORT_A_ADDR, + output reg [15:0] PORT_A_RD_DATA, + input [15:0] PORT_A_WR_DATA +); + +parameter OPTION_RDWR = "UNDEFINED"; +parameter OPTION_RDINIT = "UNDEFINED"; +parameter OPTION_RDARST = "UNDEFINED"; +parameter OPTION_RDSRST = "UNDEFINED"; +parameter OPTION_SRST_GATE = 0; +parameter PORT_A_RD_INIT_VALUE = 16'hxxxx; +parameter PORT_A_RD_ARST_VALUE = 16'hxxxx; +parameter PORT_A_RD_SRST_VALUE = 16'hxxxx; + +reg [15:0] mem [0:15]; + +initial + if (OPTION_RDINIT == "ZERO") + PORT_A_RD_DATA = 0; + else if (OPTION_RDINIT == "ANY") + PORT_A_RD_DATA = PORT_A_RD_INIT_VALUE; + +localparam ARST_VALUE = + (OPTION_RDARST == "ZERO") ? 16'h0000 : + (OPTION_RDARST == "INIT") ? PORT_A_RD_INIT_VALUE : + (OPTION_RDARST == "ANY") ? PORT_A_RD_ARST_VALUE : + 16'hxxxx; + +localparam SRST_VALUE = + (OPTION_RDSRST == "ZERO") ? 16'h0000 : + (OPTION_RDSRST == "INIT") ? PORT_A_RD_INIT_VALUE : + (OPTION_RDSRST == "ANY") ? PORT_A_RD_SRST_VALUE : + 16'hxxxx; + +pullup (PORT_A_CLK_EN); +pullup (PORT_A_RD_EN); +pulldown (PORT_A_RD_ARST); +pulldown (PORT_A_RD_SRST); + +always @(posedge PORT_A_CLK) begin + if (PORT_A_CLK_EN) begin + if (PORT_A_WR_EN[0]) + mem[PORT_A_ADDR][7:0] <= PORT_A_WR_DATA[7:0]; + if (PORT_A_WR_EN[1]) + mem[PORT_A_ADDR][15:8] <= PORT_A_WR_DATA[15:8]; + if (PORT_A_RD_EN && (!PORT_A_WR_EN || OPTION_RDWR != "NO_CHANGE")) begin + PORT_A_RD_DATA <= mem[PORT_A_ADDR]; + if (PORT_A_WR_EN && OPTION_RDWR == "NEW_ONLY") + PORT_A_RD_DATA <= 16'hx; + if (PORT_A_WR_EN[0]) + case (OPTION_RDWR) + "NEW": PORT_A_RD_DATA[7:0] <= PORT_A_WR_DATA[7:0]; + "NEW_ONLY": PORT_A_RD_DATA[7:0] <= PORT_A_WR_DATA[7:0]; + "UNDEFINED": PORT_A_RD_DATA[7:0] <= 8'hx; + endcase + if (PORT_A_WR_EN[1]) + case (OPTION_RDWR) + "NEW": PORT_A_RD_DATA[15:8] <= PORT_A_WR_DATA[15:8]; + "NEW_ONLY": PORT_A_RD_DATA[15:8] <= PORT_A_WR_DATA[15:8]; + "UNDEFINED": PORT_A_RD_DATA[15:8] <= 8'hx; + endcase + end + end + if (PORT_A_RD_SRST && (!OPTION_SRST_GATE || (OPTION_SRST_GATE == 2 && PORT_A_RD_EN) || (OPTION_SRST_GATE == 1 && PORT_A_CLK_EN))) + PORT_A_RD_DATA <= SRST_VALUE; +end + +always @(PORT_A_RD_ARST) + if (PORT_A_RD_ARST) + force PORT_A_RD_DATA = ARST_VALUE; + else + release PORT_A_RD_DATA; + +endmodule diff --git a/tests/memlib/memlib_block_tdp.txt b/tests/memlib/memlib_block_tdp.txt new file mode 100644 index 000000000..80cc7e504 --- /dev/null +++ b/tests/memlib/memlib_block_tdp.txt @@ -0,0 +1,10 @@ +ram block \RAM_BLOCK_TDP { + cost 64; + abits 10; + widths 1 2 4 8 16 per_port; + init any; + port srsw "A" "B" { + clock anyedge; + rdwr no_change; + } +} diff --git a/tests/memlib/memlib_block_tdp.v b/tests/memlib/memlib_block_tdp.v new file mode 100644 index 000000000..c6b876360 --- /dev/null +++ b/tests/memlib/memlib_block_tdp.v @@ -0,0 +1,38 @@ +module RAM_BLOCK_TDP( + input PORT_A_CLK, + input PORT_A_WR_EN, + input [9:0] PORT_A_ADDR, + input [15:0] PORT_A_WR_DATA, + output reg [15:0] PORT_A_RD_DATA, + input PORT_B_CLK, + input PORT_B_WR_EN, + input [9:0] PORT_B_ADDR, + input [15:0] PORT_B_WR_DATA, + output reg [15:0] PORT_B_RD_DATA +); + +parameter INIT = 0; +parameter PORT_A_WIDTH = 1; +parameter PORT_B_WIDTH = 1; +parameter PORT_A_CLK_POL = 0; +parameter PORT_B_CLK_POL = 0; + +reg [2**10-1:0] mem = INIT; + +always @(negedge (PORT_A_CLK ^ PORT_A_CLK_POL)) begin + if (PORT_A_WR_EN) begin + mem[PORT_A_ADDR+:PORT_A_WIDTH] <= PORT_A_WR_DATA; + end else begin + PORT_A_RD_DATA <= mem[PORT_A_ADDR+:PORT_A_WIDTH]; + end +end + +always @(negedge (PORT_B_CLK ^ PORT_B_CLK_POL)) begin + if (PORT_B_WR_EN) begin + mem[PORT_B_ADDR+:PORT_B_WIDTH] <= PORT_B_WR_DATA; + end else begin + PORT_B_RD_DATA <= mem[PORT_B_ADDR+:PORT_B_WIDTH]; + end +end + +endmodule diff --git a/tests/memlib/memlib_lut.txt b/tests/memlib/memlib_lut.txt new file mode 100644 index 000000000..0cc8fda15 --- /dev/null +++ b/tests/memlib/memlib_lut.txt @@ -0,0 +1,12 @@ +ram distributed \RAM_LUT { + abits 4; + width 4; + init any; + cost 4; + port ar "R" { + } + port arsw "RW" { + clock anyedge; + } +} + diff --git a/tests/memlib/memlib_lut.v b/tests/memlib/memlib_lut.v new file mode 100644 index 000000000..1f20a110a --- /dev/null +++ b/tests/memlib/memlib_lut.v @@ -0,0 +1,30 @@ +module RAM_LUT( + input [3:0] PORT_R_ADDR, + input [3:0] PORT_RW_ADDR, + input PORT_RW_CLK, + input PORT_RW_WR_EN, + input [3:0] PORT_RW_WR_DATA, + output [3:0] PORT_R_RD_DATA, + output [3:0] PORT_RW_RD_DATA +); + +parameter INIT = 0; +parameter PORT_RW_CLK_POL = 1; + +reg [3:0] mem [0:15]; + +integer i; +initial + for (i = 0; i < 16; i += 1) + mem[i] = INIT[i*4+:4]; + +assign PORT_R_RD_DATA = mem[PORT_R_ADDR]; +assign PORT_RW_RD_DATA = mem[PORT_RW_ADDR]; + +wire CLK = PORT_RW_CLK ~^ PORT_RW_CLK_POL; + +always @(posedge CLK) + if (PORT_RW_WR_EN) + mem[PORT_RW_ADDR] <= PORT_RW_WR_DATA; + +endmodule diff --git a/tests/memlib/memlib_wide_read.txt b/tests/memlib/memlib_wide_read.txt new file mode 100644 index 000000000..c11021045 --- /dev/null +++ b/tests/memlib/memlib_wide_read.txt @@ -0,0 +1,12 @@ +ram block \RAM_WIDE_READ { + cost 2; + abits 6; + widths 1 2 4 8 per_port; + init any; + port srsw "A" { + width rd 8 wr 2; + clock posedge; + rden; + rdwr old; + } +} diff --git a/tests/memlib/memlib_wide_read.v b/tests/memlib/memlib_wide_read.v new file mode 100644 index 000000000..e45f64376 --- /dev/null +++ b/tests/memlib/memlib_wide_read.v @@ -0,0 +1,25 @@ +module RAM_WIDE_READ #( + parameter [63:0] INIT = 64'hx, + parameter PORT_A_RD_WIDTH = 8, + parameter PORT_A_WR_WIDTH = 2 +) ( + input PORT_A_CLK, + input PORT_A_RD_EN, + input [5:0] PORT_A_ADDR, + output reg [7:0] PORT_A_RD_DATA, + input PORT_A_WR_EN, + input [1:0] PORT_A_WR_DATA +); + +reg [63:0] mem; + +initial mem = INIT; + +always @(posedge PORT_A_CLK) begin + if (PORT_A_RD_EN) + PORT_A_RD_DATA <= mem[{PORT_A_ADDR[5:3], 3'b000}+:8]; + if (PORT_A_WR_EN) + mem[{PORT_A_ADDR[5:1],1'b0}+:2] <= PORT_A_WR_DATA; +end + +endmodule diff --git a/tests/memlib/memlib_wide_sdp.txt b/tests/memlib/memlib_wide_sdp.txt new file mode 100644 index 000000000..ec90c45bd --- /dev/null +++ b/tests/memlib/memlib_wide_sdp.txt @@ -0,0 +1,17 @@ +ram block \RAM_WIDE_SDP { + cost 2; + abits 6; + widths 1 2 5 10 20 per_port; + byte 5; + init any; + port sr "R" { + clock posedge; + rden; + rdsrst any ungated; + } + port sw "W" { + clock posedge; + wrtrans "R" old; + wrbe_separate; + } +} diff --git a/tests/memlib/memlib_wide_sdp.v b/tests/memlib/memlib_wide_sdp.v new file mode 100644 index 000000000..456853177 --- /dev/null +++ b/tests/memlib/memlib_wide_sdp.v @@ -0,0 +1,45 @@ +module RAM_WIDE_SDP #( + parameter [79:0] INIT = 80'hx, + parameter PORT_R_WIDTH = 1, + parameter PORT_W_WIDTH = 1, + parameter PORT_W_WR_BE_WIDTH = 1, + parameter PORT_R_RD_SRST_VALUE = 16'hx +) ( + input PORT_R_CLK, + input PORT_R_RD_EN, + input PORT_R_RD_SRST, + input [5:0] PORT_R_ADDR, + output reg [PORT_R_WIDTH-1:0] PORT_R_RD_DATA, + input PORT_W_CLK, + input PORT_W_WR_EN, + input [PORT_W_WR_BE_WIDTH-1:0] PORT_W_WR_BE, + input [5:0] PORT_W_ADDR, + input [PORT_W_WIDTH-1:0] PORT_W_WR_DATA +); + +reg [79:0] mem; + +initial mem = INIT; + +always @(posedge PORT_R_CLK) + if (PORT_R_RD_SRST) + PORT_R_RD_DATA <= PORT_R_RD_SRST_VALUE; + else if (PORT_R_RD_EN) + PORT_R_RD_DATA <= mem[PORT_R_ADDR[5:2] * 5 + PORT_R_ADDR[1:0]+:PORT_R_WIDTH]; + +generate + if (PORT_W_WIDTH < 5) begin + always @(posedge PORT_W_CLK) + if (PORT_W_WR_EN && PORT_W_WR_BE[0]) + mem[PORT_W_ADDR[5:2] * 5 + PORT_W_ADDR[1:0]+:PORT_W_WIDTH] <= PORT_W_WR_DATA; + end else begin + integer i; + always @(posedge PORT_W_CLK) + if (PORT_W_WR_EN) + for (i = 0; i < PORT_W_WR_BE_WIDTH; i = i + 1) + if (PORT_W_WR_BE[i]) + mem[(PORT_W_ADDR[5:2] + i) * 5+:5] <= PORT_W_WR_DATA[i * 5+:5]; + end +endgenerate + +endmodule diff --git a/tests/memlib/memlib_wide_sp.txt b/tests/memlib/memlib_wide_sp.txt new file mode 100644 index 000000000..7780e4f9d --- /dev/null +++ b/tests/memlib/memlib_wide_sp.txt @@ -0,0 +1,22 @@ +ram block \RAM_WIDE_SP { + cost 2; + abits 6; + widths 1 2 5 10 20 per_port; + byte 5; + init any; + port srsw "A" { + ifdef WIDTH_MIX { + option "WIDTH_MIX" 1 { + width mix; + } + } else { + option "WIDTH_MIX" 0 { + width tied; + } + } + clock posedge; + rden; + rdwr old; + rdsrst any ungated; + } +} diff --git a/tests/memlib/memlib_wide_sp.v b/tests/memlib/memlib_wide_sp.v new file mode 100644 index 000000000..920a3339a --- /dev/null +++ b/tests/memlib/memlib_wide_sp.v @@ -0,0 +1,54 @@ +module RAM_WIDE_SP #( + parameter [79:0] INIT = 80'hx, + parameter PORT_A_RD_WIDTH = 1, + parameter PORT_A_WR_WIDTH = 1, + parameter PORT_A_WIDTH = 1, + parameter OPTION_WIDTH_MIX = 0, + parameter PORT_A_WR_EN_WIDTH = 1, + parameter PORT_A_RD_SRST_VALUE = 16'hx, + parameter RD_WIDTH = OPTION_WIDTH_MIX ? PORT_A_RD_WIDTH : PORT_A_WIDTH, + parameter WR_WIDTH = OPTION_WIDTH_MIX ? PORT_A_WR_WIDTH : PORT_A_WIDTH +) ( + input PORT_A_CLK, + input PORT_A_RD_EN, + input PORT_A_RD_SRST, + input [5:0] PORT_A_ADDR, + output reg [RD_WIDTH-1:0] PORT_A_RD_DATA, + input [PORT_A_WR_EN_WIDTH-1:0] PORT_A_WR_EN, + input [WR_WIDTH-1:0] PORT_A_WR_DATA +); + +reg [79:0] mem; + +initial mem = INIT; + +always @(posedge PORT_A_CLK) + if (PORT_A_RD_SRST) + PORT_A_RD_DATA <= PORT_A_RD_SRST_VALUE; + else if (PORT_A_RD_EN) + case (RD_WIDTH) + 1: PORT_A_RD_DATA <= mem[PORT_A_ADDR[5:2] * 5 + PORT_A_ADDR[1:0]+:1]; + 2: PORT_A_RD_DATA <= mem[PORT_A_ADDR[5:2] * 5 + PORT_A_ADDR[1] * 2+:2]; + 5: PORT_A_RD_DATA <= mem[PORT_A_ADDR[5:2] * 5+:5]; + 10: PORT_A_RD_DATA <= mem[PORT_A_ADDR[5:3] * 10+:10]; + 20: PORT_A_RD_DATA <= mem[PORT_A_ADDR[5:4] * 20+:20]; + endcase + +always @(posedge PORT_A_CLK) + case (WR_WIDTH) + 1: if (PORT_A_WR_EN) mem[PORT_A_ADDR[5:2] * 5 + PORT_A_ADDR[1:0]+:1] <= PORT_A_WR_DATA; + 2: if (PORT_A_WR_EN) mem[PORT_A_ADDR[5:2] * 5 + PORT_A_ADDR[1] * 2+:2] <= PORT_A_WR_DATA; + 5: if (PORT_A_WR_EN) mem[PORT_A_ADDR[5:2] * 5+:5] <= PORT_A_WR_DATA; + 10: begin + if (PORT_A_WR_EN[0]) mem[PORT_A_ADDR[5:3] * 10+:5] <= PORT_A_WR_DATA[4:0]; + if (PORT_A_WR_EN[1]) mem[PORT_A_ADDR[5:3] * 10 + 5+:5] <= PORT_A_WR_DATA[9:5]; + end + 20: begin + if (PORT_A_WR_EN[0]) mem[PORT_A_ADDR[5:4] * 20+:5] <= PORT_A_WR_DATA[4:0]; + if (PORT_A_WR_EN[1]) mem[PORT_A_ADDR[5:4] * 20 + 5+:5] <= PORT_A_WR_DATA[9:5]; + if (PORT_A_WR_EN[2]) mem[PORT_A_ADDR[5:4] * 20 + 10+:5] <= PORT_A_WR_DATA[14:10]; + if (PORT_A_WR_EN[3]) mem[PORT_A_ADDR[5:4] * 20 + 15+:5] <= PORT_A_WR_DATA[19:15]; + end + endcase + +endmodule diff --git a/tests/memlib/memlib_wide_write.txt b/tests/memlib/memlib_wide_write.txt new file mode 100644 index 000000000..59222b7fb --- /dev/null +++ b/tests/memlib/memlib_wide_write.txt @@ -0,0 +1,13 @@ +ram block \RAM_WIDE_WRITE { + cost 2; + abits 6; + widths 1 2 4 8 per_port; + byte 4; + init any; + port srsw "A" { + width rd 2 wr 8; + clock posedge; + rden; + rdwr old; + } +} diff --git a/tests/memlib/memlib_wide_write.v b/tests/memlib/memlib_wide_write.v new file mode 100644 index 000000000..afed6d00c --- /dev/null +++ b/tests/memlib/memlib_wide_write.v @@ -0,0 +1,29 @@ +module RAM_WIDE_WRITE #( + parameter [63:0] INIT = 64'hx, + parameter PORT_A_RD_WIDTH = 2, + parameter PORT_A_WR_WIDTH = 8, + parameter PORT_A_WR_EN_WIDTH = 2 +) ( + input PORT_A_CLK, + input PORT_A_RD_EN, + input [5:0] PORT_A_ADDR, + output reg [1:0] PORT_A_RD_DATA, + input [1:0] PORT_A_WR_EN, + input [7:0] PORT_A_WR_DATA +); + +reg [63:0] mem; + +initial mem = INIT; + +always @(posedge PORT_A_CLK) begin + if (PORT_A_RD_EN) + PORT_A_RD_DATA <= mem[{PORT_A_ADDR[5:1],1'b0}+:2]; + if (PORT_A_WR_EN[0]) + mem[{PORT_A_ADDR[5:3],3'b000}+:4] <= PORT_A_WR_DATA[3:0]; + if (PORT_A_WR_EN[1]) + mem[{PORT_A_ADDR[5:3],3'b100}+:4] <= PORT_A_WR_DATA[7:4]; +end + +endmodule + diff --git a/tests/memlib/run-test.sh b/tests/memlib/run-test.sh new file mode 100755 index 000000000..abe88a6cb --- /dev/null +++ b/tests/memlib/run-test.sh @@ -0,0 +1,15 @@ +#!/bin/bash +set -eu + +OPTIND=1 +seed="" # default to no seed specified +while getopts "S:" opt +do + case "$opt" in + S) seed="$OPTARG" ;; + esac +done +shift "$((OPTIND-1))" + +python3 generate.py +exec ${MAKE:-make} -f run-test.mk SEED="$seed" diff --git a/tests/memories/run-test.sh b/tests/memories/run-test.sh index b8657056a..c65066a9c 100755 --- a/tests/memories/run-test.sh +++ b/tests/memories/run-test.sh @@ -18,7 +18,7 @@ ${MAKE:-make} -f ../tools/autotest.mk SEED="$seed" EXTRA_FLAGS="$abcopt" *.v for f in `egrep -l 'expect-(wr-ports|rd-ports|rd-clk)' *.v`; do echo -n "Testing expectations for $f .." - ../../yosys -qp "proc; opt; memory -nomap;; dump -outfile ${f%.v}.dmp t:\$mem_v2" $f + ../../yosys -f verilog -qp "proc; opt; memory -nomap;; dump -outfile ${f%.v}.dmp t:\$mem_v2" $f if grep -q expect-wr-ports $f; then grep -q "parameter \\\\WR_PORTS $(gawk '/expect-wr-ports/ { print $3; }' $f)\$" ${f%.v}.dmp || { echo " ERROR: Unexpected number of write ports."; false; } diff --git a/tests/memories/trans_addr_enable.v b/tests/memories/trans_addr_enable.v new file mode 100644 index 000000000..f366f41ad --- /dev/null +++ b/tests/memories/trans_addr_enable.v @@ -0,0 +1,21 @@ +// expect-wr-ports 1 +// expect-rd-ports 1 +// expect-rd-clk \clk + +module top(input clk, we, rae, input [7:0] addr, wd, output [7:0] rd); + +reg [7:0] mem[0:255]; + +reg [7:0] rra; + +always @(posedge clk) begin + if (we) + mem[addr] <= wd; + + if (rae) + rra <= addr; +end + +assign rd = mem[rra]; + +endmodule diff --git a/tests/opt/bug3047.ys b/tests/opt/bug3047.ys new file mode 100644 index 000000000..6713877ce --- /dev/null +++ b/tests/opt/bug3047.ys @@ -0,0 +1,12 @@ +read_verilog << EOT + +module test (A, B, C, D, Y); + input A, B, C, D; + output Y; + assign Y = A^B^C^D^A; +endmodule + +EOT + +techmap +equiv_opt -assert extract_reduce diff --git a/tests/opt/bug3117.ys b/tests/opt/bug3117.ys new file mode 100644 index 000000000..177b3ab9a --- /dev/null +++ b/tests/opt/bug3117.ys @@ -0,0 +1,34 @@ +read_verilog << EOT + +module test (...); + +input [7:1] wa1; +input [7:1] wa2; +input [7:0] ra; +output [7:0] rd; +input clk; +input we1, we2; +input [15:0] wd1, wd2; + +reg [7:0] mem [0:255]; + +assign rd = mem[ra]; + +always @(posedge clk) begin + if (we1) begin + mem[{wa1, 1'b0}] <= wd1[7:0]; + mem[{wa1, 1'b1}] <= wd1[15:8]; + end else begin + mem[{wa2, 1'b0}] <= wd2[7:0]; + mem[{wa2, 1'b1}] <= wd2[15:8]; + end +end + +endmodule + +EOT + +proc +opt +memory_share +select -assert-count 1 t:$memwr_v2 diff --git a/tests/opt/memory_bmux2rom.ys b/tests/opt/memory_bmux2rom.ys new file mode 100644 index 000000000..039885965 --- /dev/null +++ b/tests/opt/memory_bmux2rom.ys @@ -0,0 +1,27 @@ +read_ilang << EOT + +module \top + wire width 4 input 0 \S + wire width 5 output 1 \Y + + cell $bmux $0 + parameter \WIDTH 5 + parameter \S_WIDTH 4 + connect \A 80'10110100011101110001110010001110101010111000110011111111111110100000110100111000 + connect \S \S + connect \Y \Y + end +end + +EOT + +hierarchy -auto-top + +design -save preopt +memory_bmux2rom +select -assert-count 1 t:$memrd_v2 +memory_map +opt_dff +design -stash postopt + +equiv_opt -assert -run prepare: dummy diff --git a/tests/opt/opt_merge_init.ys b/tests/opt/opt_merge_init.ys index 20b6cabee..7ee7d3dd7 100644 --- a/tests/opt/opt_merge_init.ys +++ b/tests/opt/opt_merge_init.ys @@ -75,3 +75,53 @@ EOT opt_merge select -assert-count 2 t:$dff + +design -reset +read_verilog -icells <<EOT +module top(input clk, i, (* init = 1'b0 *) output o, p); + \$dff #( + .CLK_POLARITY(1'h1), + .WIDTH(32'd1) + ) ffo ( + .CLK(clk), + .D(i), + .Q(o) + ); + \$dff #( + .CLK_POLARITY(1'h1), + .WIDTH(32'd1) + ) ffp ( + .CLK(clk), + .D(i), + .Q(p) + ); +endmodule +EOT + +opt_merge -keepdc +select -assert-count 1 t:$dff + +design -reset +read_verilog -icells <<EOT +module top(input clk, i, output o, p); + \$dff #( + .CLK_POLARITY(1'h1), + .WIDTH(32'd1) + ) ffo ( + .CLK(clk), + .D(i), + .Q(o) + ); + \$dff #( + .CLK_POLARITY(1'h1), + .WIDTH(32'd1) + ) ffp ( + .CLK(clk), + .D(i), + .Q(p) + ); +endmodule +EOT + +opt_merge -keepdc +select -assert-count 2 t:$dff diff --git a/tests/opt/opt_reduce_bmux.ys b/tests/opt/opt_reduce_bmux.ys new file mode 100644 index 000000000..55e0b6d4b --- /dev/null +++ b/tests/opt/opt_reduce_bmux.ys @@ -0,0 +1,117 @@ +read_ilang << EOT + +module \top + wire width 12 input 0 \A + wire width 2 input 1 \S + wire width 6 output 2 \Y + + cell $bmux $0 + parameter \WIDTH 6 + parameter \S_WIDTH 2 + connect \A { \A [11:10] \A [3:2] \A [10:9] \A [7] \A [7] \A [8] \A [2] \A [7:6] \A [5] \A [5] \A [3:2] \A [5:4] \A [1] \A [1] \A [3:0] } + connect \S \S + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 1 t:$bmux r:WIDTH=4 %i + +design -reset + +read_ilang << EOT + +module \top + wire width 6 input 0 \A + wire width 2 input 1 \S + wire width 6 output 2 \Y + + cell $bmux $0 + parameter \WIDTH 6 + parameter \S_WIDTH 2 + connect \A { \A [5:0] \A [5:0] \A [5:0] \A [5:0] } + connect \S \S + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 0 t:$bmux + +design -reset + +read_ilang << EOT + +module \top + wire width 160 input 0 \A + wire width 2 input 1 \S + wire width 5 output 2 \Y + + cell $bmux $0 + parameter \WIDTH 5 + parameter \S_WIDTH 5 + connect \A \A + connect \S { \S [1] 1'1 \S [0] \S [1] 1'0 } + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 1 t:$bmux r:S_WIDTH=2 %i + +design -reset + +read_ilang << EOT + +module \top + wire width 10 input 0 \A + wire input 1 \S + wire width 5 output 2 \Y + + cell $bmux $0 + parameter \WIDTH 5 + parameter \S_WIDTH 1 + connect \A \A + connect \S \S + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 0 t:$bmux +select -assert-count 1 t:$mux + +design -reset + +read_ilang << EOT + +module \top + wire width 5 input 0 \A + wire width 5 output 1 \Y + + cell $bmux $0 + parameter \WIDTH 5 + parameter \S_WIDTH 0 + connect \A \A + connect \S { } + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 0 t:$bmux diff --git a/tests/opt/opt_reduce_demux.ys b/tests/opt/opt_reduce_demux.ys new file mode 100644 index 000000000..3c5bd7d43 --- /dev/null +++ b/tests/opt/opt_reduce_demux.ys @@ -0,0 +1,91 @@ +read_ilang << EOT + +module \top + wire width 4 input 0 \A + wire width 2 input 1 \S + wire width 24 output 2 \Y + + cell $demux $0 + parameter \WIDTH 6 + parameter \S_WIDTH 2 + connect \A { \A [3] \A [1] 1'0 \A [2:0] } + connect \S \S + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 1 t:$demux r:WIDTH=4 %i + +design -reset + +read_ilang << EOT + +module \top + wire width 2 input 1 \S + wire width 24 output 2 \Y + + cell $demux $0 + parameter \WIDTH 6 + parameter \S_WIDTH 2 + connect \A 6'000000 + connect \S \S + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 0 t:$demux + +design -reset + +read_ilang << EOT + +module \top + wire width 5 input 0 \A + wire width 2 input 1 \S + wire width 160 output 2 \Y + + cell $demux $0 + parameter \WIDTH 5 + parameter \S_WIDTH 5 + connect \A \A + connect \S { \S [0] \S [1] 1'1 \S [0] 1'0 } + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 1 t:$demux r:S_WIDTH=2 %i + +design -reset + +read_ilang << EOT + +module \top + wire width 5 input 0 \A + wire width 20 output 2 \Y + + cell $demux $0 + parameter \WIDTH 5 + parameter \S_WIDTH 2 + connect \A \A + connect \S { 2'10 } + connect \Y \Y + end +end + +EOT + +equiv_opt -assert opt_reduce -fine +opt_reduce -fine +select -assert-count 0 t:$demux diff --git a/tests/proc/proc_rom.ys b/tests/proc/proc_rom.ys new file mode 100644 index 000000000..0ef2e2c61 --- /dev/null +++ b/tests/proc/proc_rom.ys @@ -0,0 +1,189 @@ +read_verilog << EOT + +module top(input [3:0] a, input en, output [7:0] d); + +always @* + if (en) + case(a) + 4'h0: d <= 8'h12; + 4'h1: d <= 8'h34; + 4'h2: d <= 8'h56; + 4'h3: d <= 8'h78; + 4'h4: d <= 8'h9a; + 4'h5: d <= 8'hbc; + 4'h6: d <= 8'hde; + 4'h7: d <= 8'hff; + 4'h8: d <= 8'h61; + 4'h9: d <= 8'h49; + 4'ha: d <= 8'h36; + 4'hb: d <= 8'h81; + 4'hc: d <= 8'h8c; + 4'hd: d <= 8'ha9; + 4'he: d <= 8'h99; + 4'hf: d <= 8'h51; + endcase + else + d <= 0; + +endmodule + +EOT + +hierarchy -auto-top + +design -save orig +proc +select -assert-count 1 t:$memrd_v2 +memory +opt_dff +design -stash postopt +design -load orig +proc -norom +design -stash preopt + +equiv_opt -assert -run prepare: dummy + + + +design -reset + +read_verilog << EOT + +module top(input [3:0] a, input en, output [7:0] d); + +always @* + if (en) + case(a) + 4'h0: d <= 8'h12; + 4'h1: d <= 8'h34; + 4'h2: d <= 8'h56; + 4'h3: d <= 8'h78; + 4'h4: d <= 8'h9a; + 4'h5: d <= 8'hbc; + 4'h6: d <= 8'hde; + 4'h7: d <= 8'hff; + 4'h8: d <= 8'h61; + 4'h9: d <= 8'h49; + 4'ha: d <= 8'h36; + 4'hb: d <= 8'h81; + 4'hc: d <= 8'h8c; + default: d <= 8'h11; + endcase + else + d <= 0; + +endmodule + +EOT + +hierarchy -auto-top + +design -save orig +proc +select -assert-count 1 t:$memrd_v2 +memory +opt_dff +design -stash postopt +design -load orig +proc -norom +design -stash preopt + +equiv_opt -assert -run prepare: dummy + + + +design -reset + +read_verilog << EOT + +module top(input [31:0] a, input en, output [7:0] d); + +always @* + if (en) + case(a) + 0: d <= 8'h12; + 1: d <= 8'h34; + 2: d <= 8'h56; + 3: d <= 8'h78; + 4: d <= 8'h9a; + 5: d <= 8'hbc; + 6: d <= 8'hde; + 7: d <= 8'hff; + 8: d <= 8'h61; + 9: d <= 8'h49; + 10: d <= 8'h36; + 11: d <= 8'h81; + 12: d <= 8'h8c; + default: d <= 8'h11; + endcase + else + d <= 0; + +endmodule + +EOT + +hierarchy -auto-top + +design -save orig +proc +select -assert-count 1 t:$memrd_v2 +memory +opt_dff +design -stash postopt +design -load orig +proc -norom +design -stash preopt + +equiv_opt -assert -run prepare: dummy + + +design -reset + +read_verilog << EOT + +module top(input [3:0] a, input en, output [7:0] d); + +always @* + if (en) + case(a) + 'h0: d <= 8'h12; + 'h1: d <= 8'h34; + 'h2: d <= 8'h56; + 'h3: d <= 8'h78; + 'h4: d <= 8'h9a; + 'h5: d <= 8'hbc; + 'h6: d <= 8'hde; + 'h7: d <= 8'hff; + 'h8: d <= 8'h61; + 'h9: d <= 8'h49; + 'ha: d <= 8'h36; + 'hb: d <= 8'h81; + 'hc: d <= 8'h8c; + 'hd: d <= 8'ha9; + 'he: d <= 8'h99; + 'hf: d <= 8'h51; + endcase + else + d <= 0; + +endmodule + +EOT + +hierarchy -auto-top + +design -save orig +proc +select -assert-count 1 t:$memrd_v2 +memory +opt_dff +design -stash postopt +design -load orig +proc -norom +design -stash preopt + +equiv_opt -assert -run prepare: dummy + + + diff --git a/tests/sat/.gitignore b/tests/sat/.gitignore index 8355de9dc..664425d73 100644 --- a/tests/sat/.gitignore +++ b/tests/sat/.gitignore @@ -1,2 +1,4 @@ *.log run-test.mk +*.vcd +*.fst diff --git a/tests/sat/alu.v b/tests/sat/alu.v new file mode 100644 index 000000000..9826fe05d --- /dev/null +++ b/tests/sat/alu.v @@ -0,0 +1,79 @@ +module alu( + input clk, + input [7:0] A, + input [7:0] B, + input [3:0] operation, + output reg [7:0] result, + output reg CF, + output reg ZF, + output reg SF +); + + localparam ALU_OP_ADD /* verilator public_flat */ = 4'b0000; + localparam ALU_OP_SUB /* verilator public_flat */ = 4'b0001; + localparam ALU_OP_ADC /* verilator public_flat */ = 4'b0010; + localparam ALU_OP_SBC /* verilator public_flat */ = 4'b0011; + + localparam ALU_OP_AND /* verilator public_flat */ = 4'b0100; + localparam ALU_OP_OR /* verilator public_flat */ = 4'b0101; + localparam ALU_OP_NOT /* verilator public_flat */ = 4'b0110; + localparam ALU_OP_XOR /* verilator public_flat */ = 4'b0111; + + localparam ALU_OP_SHL /* verilator public_flat */ = 4'b1000; + localparam ALU_OP_SHR /* verilator public_flat */ = 4'b1001; + localparam ALU_OP_SAL /* verilator public_flat */ = 4'b1010; + localparam ALU_OP_SAR /* verilator public_flat */ = 4'b1011; + + localparam ALU_OP_ROL /* verilator public_flat */ = 4'b1100; + localparam ALU_OP_ROR /* verilator public_flat */ = 4'b1101; + localparam ALU_OP_RCL /* verilator public_flat */ = 4'b1110; + localparam ALU_OP_RCR /* verilator public_flat */ = 4'b1111; + + reg [8:0] tmp; + + always @(posedge clk) + begin + case (operation) + ALU_OP_ADD : + tmp = A + B; + ALU_OP_SUB : + tmp = A - B; + ALU_OP_ADC : + tmp = A + B + { 7'b0000000, CF }; + ALU_OP_SBC : + tmp = A - B - { 7'b0000000, CF }; + ALU_OP_AND : + tmp = {1'b0, A & B }; + ALU_OP_OR : + tmp = {1'b0, A | B }; + ALU_OP_NOT : + tmp = {1'b0, ~B }; + ALU_OP_XOR : + tmp = {1'b0, A ^ B}; + ALU_OP_SHL : + tmp = { A[7], A[6:0], 1'b0}; + ALU_OP_SHR : + tmp = { A[0], 1'b0, A[7:1]}; + ALU_OP_SAL : + // Same as SHL + tmp = { A[7], A[6:0], 1'b0}; + ALU_OP_SAR : + tmp = { A[0], A[7], A[7:1]}; + ALU_OP_ROL : + tmp = { A[7], A[6:0], A[7]}; + ALU_OP_ROR : + tmp = { A[0], A[0], A[7:1]}; + ALU_OP_RCL : + tmp = { A[7], A[6:0], CF}; + ALU_OP_RCR : + tmp = { A[0], CF, A[7:1]}; + endcase + + CF <= tmp[8]; + ZF <= tmp[7:0] == 0; + SF <= tmp[7]; + + result <= tmp[7:0]; + end +endmodule + diff --git a/tests/sat/grom.ys b/tests/sat/grom.ys new file mode 100644 index 000000000..da0f3b620 --- /dev/null +++ b/tests/sat/grom.ys @@ -0,0 +1,9 @@ +read_verilog grom_computer.v grom_cpu.v alu.v ram_memory.v; +prep -top grom_computer; +sim -clock clk -reset reset -fst grom.fst -vcd grom.vcd -n 80 + +sim -clock clk -r grom.fst -scope grom_computer -start 25ns -stop 100ns -sim-cmp + +sim -clock clk -r grom.fst -scope grom_computer -stop 100ns -sim-gold + +sim -clock clk -r grom.fst -scope grom_computer -n 10 -sim-gate diff --git a/tests/sat/grom_computer.v b/tests/sat/grom_computer.v new file mode 100644 index 000000000..63a5c8ff8 --- /dev/null +++ b/tests/sat/grom_computer.v @@ -0,0 +1,31 @@ +module grom_computer + (input clk, // Main Clock + input reset, // reset + output hlt, + output reg[7:0] display_out + ); + + wire [11:0] addr; + wire [7:0] memory_out; + wire [7:0] memory_in; + wire mem_enable; + wire we; + wire ioreq; + + grom_cpu cpu(.clk(clk),.reset(reset),.addr(addr),.data_in(memory_out),.data_out(memory_in),.we(we),.ioreq(ioreq),.hlt(hlt)); + + assign mem_enable = we & ~ioreq; + + ram_memory memory(.clk(clk),.addr(addr),.data_in(memory_in),.we(mem_enable),.data_out(memory_out)); + + always @(posedge clk) + begin + if(ioreq==1 && we==1) + begin + display_out <= memory_in; + `ifdef DISASSEMBLY + $display("Display output : %h", memory_in); + `endif + end + end +endmodule diff --git a/tests/sat/grom_cpu.v b/tests/sat/grom_cpu.v new file mode 100644 index 000000000..914c0f56c --- /dev/null +++ b/tests/sat/grom_cpu.v @@ -0,0 +1,747 @@ +module grom_cpu( + input clk, + input reset, + output reg [11:0] addr, + input [7:0] data_in, + output reg [7:0] data_out, + output reg we, + output reg ioreq, + output reg hlt +); + + reg[11:0] PC /* verilator public_flat */; // Program counter + reg[7:0] IR /* verilator public_flat */; // Instruction register + reg[7:0] VALUE /* verilator public_flat */; // Temp reg for storing 2nd operand + reg[3:0] CS /* verilator public_flat */; // Code segment regiser + reg[3:0] DS /* verilator public_flat */; // Data segment regiser + reg[11:0] SP /* verilator public_flat */; // Stack pointer regiser + reg[7:0] R[0:3] /* verilator public_flat */; // General purpose registers + reg[11:0] FUTURE_PC /* verilator public_flat */; // PC to jump to + + localparam STATE_RESET /*verilator public_flat*/ = 5'b00000; + localparam STATE_FETCH_PREP /*verilator public_flat*/ = 5'b00001; + localparam STATE_FETCH_WAIT /*verilator public_flat*/ = 5'b00010; + localparam STATE_FETCH /*verilator public_flat*/ = 5'b00011; + localparam STATE_EXECUTE /*verilator public_flat*/ = 5'b00100; + localparam STATE_FETCH_VALUE_PREP /*verilator public_flat*/ = 5'b00101; + localparam STATE_FETCH_VALUE /*verilator public_flat*/ = 5'b00110; + localparam STATE_EXECUTE_DBL /*verilator public_flat*/ = 5'b00111; + localparam STATE_LOAD_VALUE /*verilator public_flat*/ = 5'b01000; + localparam STATE_LOAD_VALUE_WAIT /*verilator public_flat*/ = 5'b01001; + localparam STATE_ALU_RESULT_WAIT /*verilator public_flat*/ = 5'b01010; + localparam STATE_ALU_RESULT /*verilator public_flat*/ = 5'b01011; + localparam STATE_PUSH_PC_LOW /*verilator public_flat*/ = 5'b01100; + localparam STATE_JUMP /*verilator public_flat*/ = 5'b01101; + localparam STATE_RET_VALUE_WAIT /*verilator public_flat*/ = 5'b01110; + localparam STATE_RET_VALUE /*verilator public_flat*/ = 5'b01111; + localparam STATE_RET_VALUE_WAIT2 /*verilator public_flat*/ = 5'b10000; + localparam STATE_RET_VALUE2 /*verilator public_flat*/ = 5'b10001; + + reg [4:0] state /* verilator public_flat */ = STATE_RESET; + + reg [7:0] alu_a /* verilator public_flat */; + reg [7:0] alu_b /* verilator public_flat */; + reg [3:0] alu_op /* verilator public_flat */; + + reg [1:0] RESULT_REG /* verilator public_flat */; + + wire [7:0] alu_res /* verilator public_flat */; + wire alu_CF /* verilator public_flat */; + wire alu_ZF /* verilator public_flat */; + wire alu_SF /* verilator public_flat */; + reg jump; + + alu alu(.clk(clk),.A(alu_a),.B(alu_b),.operation(alu_op),.result(alu_res),.CF(alu_CF),.ZF(alu_ZF),.SF(alu_SF)); + + always @(posedge clk) + begin + if (reset) + begin + state <= STATE_RESET; + hlt <= 0; + end + else + begin + case (state) + STATE_RESET : + begin + PC <= 12'h000; + state <= STATE_FETCH_PREP; + CS <= 4'h0; + DS <= 4'h0; + R[0] <= 8'h00; + R[1] <= 8'h00; + R[2] <= 8'h00; + R[3] <= 8'h00; + SP <= 12'hfff; + end + + STATE_FETCH_PREP : + begin + addr <= PC; + we <= 0; + ioreq <= 0; + + state <= STATE_FETCH_WAIT; + end + + STATE_FETCH_WAIT : + begin + // Sync with memory due to CLK + state <= (hlt) ? STATE_FETCH_PREP : STATE_FETCH; + end + + STATE_FETCH : + begin + IR <= data_in; + PC <= PC + 1; + + state <= STATE_EXECUTE; + end + STATE_EXECUTE : + begin + `ifdef DISASSEMBLY + $display(" PC %h R0 %h R1 %h R2 %h R3 %h CS %h DS %h SP %h ALU [%d %d %d]", PC, R[0], R[1], R[2], R[3], CS, DS, SP, alu_CF,alu_SF,alu_ZF); + `endif + if (IR[7]) + begin + addr <= PC; + state <= STATE_FETCH_VALUE_PREP; + PC <= PC + 1; + end + else + begin + case(IR[6:4]) + 3'b000 : + begin + `ifdef DISASSEMBLY + $display("MOV R%d,R%d",IR[3:2],IR[1:0]); + `endif + R[IR[3:2]] <= R[IR[1:0]]; + state <= STATE_FETCH_PREP; + end + 3'b001 : + begin + alu_a <= R[0]; // first input R0 + alu_b <= R[IR[1:0]]; + RESULT_REG <= 0; // result in R0 + alu_op <= { 2'b00, IR[3:2] }; + + state <= STATE_ALU_RESULT_WAIT; + + `ifdef DISASSEMBLY + case(IR[3:2]) + 2'b00 : begin + $display("ADD R%d",IR[1:0]); + end + 2'b01 : begin + $display("SUB R%d",IR[1:0]); + end + 2'b10 : begin + $display("ADC R%d",IR[1:0]); + end + 2'b11 : begin + $display("SBC R%d",IR[1:0]); + end + endcase + `endif + end + 3'b010 : + begin + alu_a <= R[0]; // first input R0 + alu_b <= R[IR[1:0]]; + RESULT_REG <= 0; // result in R0 + alu_op <= { 2'b01, IR[3:2] }; + state <= STATE_ALU_RESULT_WAIT; + `ifdef DISASSEMBLY + case(IR[3:2]) + 2'b00 : begin + $display("AND R%d",IR[1:0]); + end + 2'b01 : begin + $display("OR R%d",IR[1:0]); + end + 2'b10 : begin + $display("NOT R%d",IR[1:0]); + end + 2'b11 : begin + $display("XOR R%d",IR[1:0]); + end + endcase + `endif + end + 3'b011 : + begin + RESULT_REG <= IR[1:0]; // result in REG + // CMP and TEST are not storing result + state <= IR[3] ? STATE_FETCH_PREP : STATE_ALU_RESULT_WAIT; + // CMP and TEST are having first input R0, for INC and DEC is REG + alu_a <= IR[3] ? R[0] : R[IR[1:0]]; + // CMP and TEST are having second input REG, for INC and DEC is 1 + alu_b <= IR[3] ? R[IR[1:0]] : 8'b00000001; + + case(IR[3:2]) + 2'b00 : begin + `ifdef DISASSEMBLY + $display("INC R%d",IR[1:0]); + `endif + alu_op <= 4'b0000; // ALU_OP_ADD + end + 2'b01 : begin + `ifdef DISASSEMBLY + $display("DEC R%d",IR[1:0]); + `endif + alu_op <= 4'b0001; // ALU_OP_SUB + end + 2'b10 : begin + `ifdef DISASSEMBLY + $display("CMP R%d",IR[1:0]); + `endif + alu_op <= 4'b0001; // ALU_OP_SUB + end + 2'b11 : begin + `ifdef DISASSEMBLY + $display("TST R%d",IR[1:0]); + `endif + alu_op <= 4'b0100; // ALU_OP_AND + end + endcase + end + 3'b100 : + begin + if (IR[3]==0) + begin + alu_a <= R[0]; // first input R0 + // no 2nd input + RESULT_REG <= 0; // result in R0 + alu_op <= { 1'b1, IR[2:0] }; + `ifdef DISASSEMBLY + case(IR[2:0]) + 3'b000 : begin + $display("SHL"); + end + 3'b001 : begin + $display("SHR"); + end + 3'b010 : begin + $display("SAL"); + end + 3'b011 : begin + $display("SAR"); + end + 3'b100 : begin + $display("ROL"); + end + 3'b101 : begin + $display("ROR"); + end + 3'b110 : begin + $display("RCL"); + end + 3'b111 : begin + $display("RCR"); + end + endcase + `endif + state <= STATE_ALU_RESULT_WAIT; + end + else + begin + if (IR[2]==0) + begin + `ifdef DISASSEMBLY + $display("PUSH R%d",IR[1:0]); + `endif + addr <= SP; + we <= 1; + ioreq <= 0; + data_out <= R[IR[1:0]]; + SP <= SP - 1; + state <= STATE_FETCH_PREP; + end + else + begin + `ifdef DISASSEMBLY + $display("POP R%d",IR[1:0]); + `endif + addr <= SP + 1; + we <= 0; + ioreq <= 0; + RESULT_REG <= IR[1:0]; + SP <= SP + 1; + state <= STATE_LOAD_VALUE_WAIT; + end + end + end + 3'b101 : + begin + `ifdef DISASSEMBLY + $display("LOAD R%d,[R%d]", IR[3:2], IR[1:0]); + `endif + addr <= { DS, R[IR[1:0]] }; + we <= 0; + ioreq <= 0; + RESULT_REG <= IR[3:2]; + + state <= STATE_LOAD_VALUE_WAIT; + end + 3'b110 : + begin + `ifdef DISASSEMBLY + $display("STORE [R%d],R%d", IR[3:2], IR[1:0]); + `endif + addr <= { DS, R[IR[3:2]] }; + we <= 1; + ioreq <= 0; + data_out <= R[IR[1:0]]; + + state <= STATE_FETCH_PREP; + end + 3'b111 : + begin + // Special instuctions + case(IR[3:2]) + 2'b00 : begin + CS <= R[IR[1:0]][3:0]; + state <= STATE_FETCH_PREP; + `ifdef DISASSEMBLY + $display("MOV CS,R%d",IR[1:0]); + `endif + end + 2'b01 : begin + DS <= R[IR[1:0]][3:0]; + state <= STATE_FETCH_PREP; + `ifdef DISASSEMBLY + $display("MOV DS,R%d",IR[1:0]); + `endif + end + 2'b10 : begin + case(IR[1:0]) + 2'b00 : begin + `ifdef DISASSEMBLY + $display("PUSH CS"); + `endif + addr <= SP; + we <= 1; + ioreq <= 0; + data_out <= { 4'b0000, CS}; + SP <= SP - 1; + state <= STATE_FETCH_PREP; + end + 2'b01 : begin + `ifdef DISASSEMBLY + $display("PUSH DS"); + `endif + addr <= SP; + we <= 1; + ioreq <= 0; + data_out <= { 4'b0000, DS}; + SP <= SP - 1; + state <= STATE_FETCH_PREP; + end + 2'b10 : begin + `ifdef DISASSEMBLY + $display("Unused opcode"); + `endif + end + 2'b11 : begin + `ifdef DISASSEMBLY + $display("Unused opcode"); + `endif + end + endcase + state <= STATE_FETCH_PREP; + end + 2'b11 : begin + case(IR[1:0]) + 2'b00 : begin + `ifdef DISASSEMBLY + $display("Unused opcode"); + `endif + state <= STATE_FETCH_PREP; + end + 2'b01 : begin + `ifdef DISASSEMBLY + $display("Unused opcode"); + `endif + state <= STATE_FETCH_PREP; + end + 2'b10 : begin + `ifdef DISASSEMBLY + $display("RET"); + `endif + addr <= SP + 1; + we <= 0; + ioreq <= 0; + SP <= SP + 1; + state <= STATE_RET_VALUE_WAIT; + end + 2'b11 : begin + hlt <= 1; + `ifdef DISASSEMBLY + $display("HALT"); + `endif + state <= STATE_FETCH_PREP; + end + endcase + end + endcase + end + endcase + end + end + STATE_FETCH_VALUE_PREP : + begin + // Sync with memory due to CLK + state <= STATE_FETCH_VALUE; + end + STATE_FETCH_VALUE : + begin + VALUE <= data_in; + state <= STATE_EXECUTE_DBL; + end + STATE_EXECUTE_DBL : + begin + case(IR[6:4]) + 3'b000 : + begin + if (IR[3]==0) + begin + case(IR[2:0]) + 3'b000 : + begin + `ifdef DISASSEMBLY + $display("JMP %h ",{ CS, VALUE[7:0] }); + `endif + jump = 1; + end + 3'b001 : + begin + `ifdef DISASSEMBLY + $display("JC %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_CF==1); + end + 3'b010 : + begin + `ifdef DISASSEMBLY + $display("JNC %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_CF==0); + end + 3'b011 : + begin + `ifdef DISASSEMBLY + $display("JM %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_SF==1); + end + 3'b100 : + begin + `ifdef DISASSEMBLY + $display("JP %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_SF==0); + end + 3'b101 : + begin + `ifdef DISASSEMBLY + $display("JZ %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_ZF==1); + end + 3'b110 : + begin + `ifdef DISASSEMBLY + $display("JNZ %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_ZF==0); + end + 3'b111 : + begin + `ifdef DISASSEMBLY + $display("Unused opcode %h",IR); + `endif + jump = 0; + end + endcase + + if (jump) + begin + PC <= { CS, VALUE[7:0] }; + addr <= { CS, VALUE[7:0] }; + we <= 0; + ioreq <= 0; + end + state <= STATE_FETCH_PREP; + end + else + begin + case(IR[2:0]) + 3'b000 : + begin + `ifdef DISASSEMBLY + $display("JR %h ", PC + {VALUE[7],VALUE[7],VALUE[7],VALUE[7],VALUE[7:0]} ); + `endif + jump = 1; + end + 3'b001 : + begin + `ifdef DISASSEMBLY + $display("JRC %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_CF==1); + end + 3'b010 : + begin + `ifdef DISASSEMBLY + $display("JRNC %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_CF==0); + end + 3'b011 : + begin + `ifdef DISASSEMBLY + $display("JRM %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_SF==1); + end + 3'b100 : + begin + `ifdef DISASSEMBLY + $display("JRP %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_SF==0); + end + 3'b101 : + begin + `ifdef DISASSEMBLY + $display("JRZ %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_ZF==1); + end + 3'b110 : + begin + `ifdef DISASSEMBLY + $display("JRNZ %h ",{CS, VALUE[7:0] }); + `endif + jump = (alu_ZF==0); + end + 3'b111 : + begin + `ifdef DISASSEMBLY + $display("Unused opcode %h",IR); + `endif + jump = 0; + end + endcase + if (jump) + begin + PC <= PC + {VALUE[7],VALUE[7],VALUE[7],VALUE[7],VALUE[7:0]}; + addr <= PC + {VALUE[7],VALUE[7],VALUE[7],VALUE[7],VALUE[7:0]}; + we <= 0; + ioreq <= 0; + end + state <= STATE_FETCH_PREP; + end + end + 3'b001 : + begin + `ifdef DISASSEMBLY + $display("JUMP %h ",{ IR[3:0], VALUE[7:0] }); + `endif + PC <= { IR[3:0], VALUE[7:0] }; + addr <= { IR[3:0], VALUE[7:0] }; + we <= 0; + ioreq <= 0; + state <= STATE_FETCH_PREP; + end + 3'b010 : + begin + `ifdef DISASSEMBLY + $display("CALL %h ",{ IR[3:0], VALUE[7:0] }); + `endif + FUTURE_PC <= { IR[3:0], VALUE[7:0] }; + addr <= SP; + we <= 1; + ioreq <= 0; + data_out <= { 4'b0000, PC[11:8]}; + SP <= SP - 1; + state <= STATE_PUSH_PC_LOW; + end + 3'b011 : + begin + `ifdef DISASSEMBLY + $display("MOV SP,%h ",{ IR[3:0], VALUE[7:0] }); + `endif + SP <= { IR[3:0], VALUE[7:0] }; + state <= STATE_FETCH_PREP; + end + 3'b100 : + begin + `ifdef DISASSEMBLY + $display("IN R%d,[0x%h]",IR[1:0], VALUE); + `endif + ioreq <= 1; + we <= 0; + addr <= { 4'b0000, VALUE }; + RESULT_REG <= IR[1:0]; + state <= STATE_LOAD_VALUE_WAIT; + end + 3'b101 : + begin + `ifdef DISASSEMBLY + $display("OUT [0x%h],R%d",VALUE,IR[1:0]); + `endif + ioreq <= 1; + we <= 1; + addr <= { 4'b0000, VALUE }; + data_out <= R[IR[1:0]]; + state <= STATE_FETCH_PREP; + end + 3'b110 : + begin + // Special instuctions + case(IR[1:0]) + 2'b00 : begin + `ifdef DISASSEMBLY + $display("MOV CS,0x%h",VALUE); + `endif + CS <= VALUE[3:0]; + state <= STATE_FETCH_PREP; + end + 2'b01 : begin + `ifdef DISASSEMBLY + $display("MOV DS,0x%h",VALUE); + `endif + DS <= VALUE[3:0]; + state <= STATE_FETCH_PREP; + end + 2'b10 : begin + `ifdef DISASSEMBLY + $display("Unused opcode %h",IR); + `endif + state <= STATE_FETCH_PREP; + end + 2'b11 : begin + `ifdef DISASSEMBLY + $display("Unused opcode %h",IR); + `endif + state <= STATE_FETCH_PREP; + end + endcase + end + 3'b111 : + begin + case(IR[3:2]) + 2'b00 : begin + `ifdef DISASSEMBLY + $display("MOV R%d,0x%h",IR[1:0],VALUE); + `endif + R[IR[1:0]] <= VALUE; + state <= STATE_FETCH_PREP; + end + 2'b01 : begin + `ifdef DISASSEMBLY + $display("LOAD R%d,[0x%h]",IR[1:0], {DS, VALUE}); + `endif + addr <= { DS, VALUE }; + we <= 0; + ioreq <= 0; + RESULT_REG <= IR[1:0]; + + state <= STATE_LOAD_VALUE_WAIT; + end + 2'b10 : begin + `ifdef DISASSEMBLY + $display("STORE [0x%h],R%d", {DS, VALUE}, IR[1:0]); + `endif + addr <= { DS, VALUE }; + we <= 1; + ioreq <= 0; + data_out <= R[IR[1:0]]; + + state <= STATE_FETCH_PREP; + end + 2'b11 : begin + `ifdef DISASSEMBLY + $display("Unused opcode %h",IR); + `endif + state <= STATE_FETCH_PREP; + end + endcase + end + endcase + end + STATE_LOAD_VALUE_WAIT : + begin + // Sync with memory due to CLK + state <= STATE_LOAD_VALUE; + end + STATE_LOAD_VALUE : + begin + R[RESULT_REG] <= data_in; + we <= 0; + state <= STATE_FETCH_PREP; + end + STATE_ALU_RESULT_WAIT : + begin + state <= STATE_ALU_RESULT; + end + STATE_ALU_RESULT : + begin + R[RESULT_REG] <= alu_res; + state <= STATE_FETCH_PREP; + end + STATE_PUSH_PC_LOW : + begin + addr <= SP; + we <= 1; + ioreq <= 0; + data_out <= PC[7:0]; + SP <= SP - 1; + state <= STATE_JUMP; + end + STATE_JUMP : + begin + `ifdef DISASSEMBLY + $display("Jumping to %h",FUTURE_PC); + `endif + PC <= FUTURE_PC; + state <= STATE_FETCH_PREP; + end + STATE_RET_VALUE_WAIT : + begin + // Sync with memory due to CLK + state <= STATE_RET_VALUE; + end + STATE_RET_VALUE : + begin + FUTURE_PC <= { 4'b0000, data_in }; + we <= 0; + state <= STATE_RET_VALUE_WAIT2; + + addr <= SP + 1; + we <= 0; + ioreq <= 0; + SP <= SP + 1; + end + STATE_RET_VALUE_WAIT2 : + begin + // Sync with memory due to CLK + state <= STATE_RET_VALUE2; + end + STATE_RET_VALUE2 : + begin + FUTURE_PC <= FUTURE_PC | ({ 4'b0000, data_in } << 8); + we <= 0; + state <= STATE_JUMP; + end + default : + begin + state <= STATE_FETCH_PREP; + end + endcase + end + end +endmodule diff --git a/tests/sat/ram_memory.v b/tests/sat/ram_memory.v new file mode 100644 index 000000000..0d91514b2 --- /dev/null +++ b/tests/sat/ram_memory.v @@ -0,0 +1,39 @@ +module ram_memory( + input clk, + input [11:0] addr, + input [7:0] data_in, + input we, + output reg [7:0] data_out +); + + reg [7:0] store[0:4095] /* verilator public_flat */; + + initial + begin + store[0] <= 8'b11100001; // MOV DS,2 + store[1] <= 8'b00000010; // + store[2] <= 8'b01010100; // LOAD R1,[R0] + store[3] <= 8'b00110001; // INC R1 + store[4] <= 8'b00110001; // INC R1 + store[5] <= 8'b01100001; // STORE [R0],R1 + store[6] <= 8'b11010001; // OUT [0],R1 + store[7] <= 8'b00000000; // + store[8] <= 8'b00110001; // INC R1 + store[9] <= 8'b10100001; // CALL 0x100 + store[10] <= 8'b00000000; // + store[11] <= 8'b01111111; // HLT + + + store[256] <= 8'b11010001; // OUT [0],R1 + store[257] <= 8'b00000000; // + store[258] <= 8'b01111110; // RET + + store[512] <= 8'b00000000; + end + + always @(posedge clk) + if (we) + store[addr] <= data_in; + else + data_out <= store[addr]; +endmodule diff --git a/tests/sat/sim_counter.ys b/tests/sat/sim_counter.ys new file mode 100644 index 000000000..a0ff41b6e --- /dev/null +++ b/tests/sat/sim_counter.ys @@ -0,0 +1,48 @@ +# Create stimulus file +read_verilog <<EOT +module top (clk, reset, cnt); + +input clk; +input reset; +output [7:0] cnt; + +reg [7:0] cnt; + +endmodule +EOT +prep -top top; +sim -clock clk -reset reset -fst stimulus.fst -n 10 +design -reset + +# Counter implementation +read_verilog <<EOT +module top (clk, reset, cnt); + +input clk; +input reset; +output [7:0] cnt; + +reg [7:0] cnt; + +always @(posedge clk) + if (!reset) + cnt = cnt + 1; + else + cnt = 0; + +endmodule +EOT +prep -top top; + +# Simulate with stimulus +sim -clock clk -scope top -r stimulus.fst + +# Stimulus does not have counter values +# x in FST can match any value in simulation +sim -clock clk -scope top -r stimulus.fst -sim-gate + +# Stimulus does not have counter values +# x in simulation can match any value in FST +# so we expect error +logger -expect error "Signal difference" 1 +sim -clock clk -scope top -r stimulus.fst -sim-gold diff --git a/tests/sim/.gitignore b/tests/sim/.gitignore new file mode 100644 index 000000000..2c96b65f8 --- /dev/null +++ b/tests/sim/.gitignore @@ -0,0 +1,6 @@ +*.log +/run-test.mk ++*_synth.v ++*_testbench +*.out +*.fst diff --git a/tests/sim/adff.v b/tests/sim/adff.v new file mode 100644 index 000000000..8c8fb0acf --- /dev/null +++ b/tests/sim/adff.v @@ -0,0 +1,7 @@ +module adff( input d, clk, rst, output reg q ); + always @( posedge clk, posedge rst ) + if (rst) + q <= 0; + else + q <= d; +endmodule diff --git a/tests/sim/adffe.v b/tests/sim/adffe.v new file mode 100644 index 000000000..55c7d8d4e --- /dev/null +++ b/tests/sim/adffe.v @@ -0,0 +1,8 @@ +module adffe( input d, clk, rst, en, output reg q ); + always @( posedge clk, posedge rst ) + if (rst) + q <= 0; + else + if (en) + q <= d; +endmodule diff --git a/tests/sim/adlatch.v b/tests/sim/adlatch.v new file mode 100644 index 000000000..5e8f48e49 --- /dev/null +++ b/tests/sim/adlatch.v @@ -0,0 +1,8 @@ +module adlatch( input d, rst, en, output reg q ); + always @* begin + if (rst) + q = 0; + else if (en) + q = d; + end +endmodule diff --git a/tests/sim/aldff.v b/tests/sim/aldff.v new file mode 100644 index 000000000..eeb0f0673 --- /dev/null +++ b/tests/sim/aldff.v @@ -0,0 +1,7 @@ +module aldff( input [0:3] d, input [0:3] ad, input clk, aload, output reg [0:3] q ); + always @( posedge clk, posedge aload) + if (aload) + q <= ad; + else + q <= d; +endmodule diff --git a/tests/sim/aldffe.v b/tests/sim/aldffe.v new file mode 100644 index 000000000..79c65afc4 --- /dev/null +++ b/tests/sim/aldffe.v @@ -0,0 +1,8 @@ +module aldffe( input [0:3] d, input [0:3] ad, input clk, aload, en, output reg [0:3] q ); + always @( posedge clk, posedge aload) + if (aload) + q <= ad; + else + if (en) + q <= d; +endmodule diff --git a/tests/sim/dff.v b/tests/sim/dff.v new file mode 100644 index 000000000..ce792b59a --- /dev/null +++ b/tests/sim/dff.v @@ -0,0 +1,4 @@ +module dff( input d, clk, output reg q ); + always @( posedge clk ) + q <= d; +endmodule diff --git a/tests/sim/dffe.v b/tests/sim/dffe.v new file mode 100644 index 000000000..853fcf66a --- /dev/null +++ b/tests/sim/dffe.v @@ -0,0 +1,5 @@ +module dffe( input clk, en, d, output reg q ); + always @( posedge clk ) + if ( en ) + q <= d; +endmodule diff --git a/tests/sim/dffsr.v b/tests/sim/dffsr.v new file mode 100644 index 000000000..2158708f1 --- /dev/null +++ b/tests/sim/dffsr.v @@ -0,0 +1,9 @@ +module dffsr( input clk, d, clr, set, output reg q ); + always @( posedge clk, posedge set, posedge clr) + if ( clr ) + q <= 0; + else if (set) + q <= 1; + else + q <= d; +endmodule diff --git a/tests/sim/dlatch.v b/tests/sim/dlatch.v new file mode 100644 index 000000000..315b43216 --- /dev/null +++ b/tests/sim/dlatch.v @@ -0,0 +1,6 @@ +module dlatch( input d, en, output reg q ); + always @* begin + if ( en ) + q = d; + end +endmodule diff --git a/tests/sim/dlatchsr.v b/tests/sim/dlatchsr.v new file mode 100644 index 000000000..1d13ac2ad --- /dev/null +++ b/tests/sim/dlatchsr.v @@ -0,0 +1,11 @@ +module dlatchsr( input d, set, clr, en, output reg q ); + always @* begin + if ( clr ) + q = 0; + else if (set) + q = 1; + else + if (en) + q = d; + end +endmodule diff --git a/tests/sim/run-test.sh b/tests/sim/run-test.sh new file mode 100755 index 000000000..d34d1f3c9 --- /dev/null +++ b/tests/sim/run-test.sh @@ -0,0 +1,12 @@ +#!/usr/bin/env bash +set -eu +source ../gen-tests-makefile.sh +echo "Generate FST for sim models" +find tb/* -name tb*.v | while read name; do + test_name=$(basename -s .v $name) + echo "Test $test_name" + verilog_name=${test_name:3}.v + iverilog -o tb/$test_name.out $name $verilog_name + ./tb/$test_name.out -fst +done +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/sim/sdff.v b/tests/sim/sdff.v new file mode 100644 index 000000000..6b25516e1 --- /dev/null +++ b/tests/sim/sdff.v @@ -0,0 +1,7 @@ +module sdff( input d, clk, rst, output reg q ); + always @( posedge clk) + if (rst) + q <= 0; + else + q <= d; +endmodule diff --git a/tests/sim/sdffce.v b/tests/sim/sdffce.v new file mode 100644 index 000000000..7d27d5741 --- /dev/null +++ b/tests/sim/sdffce.v @@ -0,0 +1,8 @@ +module sdffce( input d, clk, rst, en, output reg q ); + always @( posedge clk) + if(en) + if (rst) + q <= 0; + else + q <= d; +endmodule diff --git a/tests/sim/sdffe.v b/tests/sim/sdffe.v new file mode 100644 index 000000000..0a96693e1 --- /dev/null +++ b/tests/sim/sdffe.v @@ -0,0 +1,8 @@ +module sdffe( input d, clk, rst, en, output reg q ); + always @( posedge clk) + if (rst) + q <= 0; + else + if (en) + q <= d; +endmodule diff --git a/tests/sim/sim_adff.ys b/tests/sim/sim_adff.ys new file mode 100644 index 000000000..6efd804a9 --- /dev/null +++ b/tests/sim/sim_adff.ys @@ -0,0 +1,6 @@ +read_verilog adff.v +proc +opt_dff +stat +select -assert-count 1 t:$adff +sim -clock clk -r tb_adff.fst -scope tb_adff.uut -sim-cmp adff diff --git a/tests/sim/sim_adffe.ys b/tests/sim/sim_adffe.ys new file mode 100644 index 000000000..47a51ebce --- /dev/null +++ b/tests/sim/sim_adffe.ys @@ -0,0 +1,6 @@ +read_verilog adffe.v +proc +opt_dff +stat +select -assert-count 1 t:$adffe +sim -clock clk -r tb_adffe.fst -scope tb_adffe.uut -sim-cmp adffe diff --git a/tests/sim/sim_adlatch.ys b/tests/sim/sim_adlatch.ys new file mode 100644 index 000000000..eece7dc0d --- /dev/null +++ b/tests/sim/sim_adlatch.ys @@ -0,0 +1,10 @@ +read_verilog -icells <<EOT +module adlatch(input d, rst, en, output reg q); +$adlatch #(.EN_POLARITY(1'b1), .ARST_POLARITY(1'b1), .ARST_VALUE(1'b0), .WIDTH(1)) uut (.EN(en), .ARST(rst), .D(d), .Q(q)); +endmodule +EOT +proc +opt_dff +stat +select -assert-count 1 t:$adlatch +sim -r tb_adlatch.fst -scope tb_adlatch.uut -sim-cmp adlatch diff --git a/tests/sim/sim_aldff.ys b/tests/sim/sim_aldff.ys new file mode 100644 index 000000000..9c8b3bdfc --- /dev/null +++ b/tests/sim/sim_aldff.ys @@ -0,0 +1,6 @@ +read_verilog aldff.v +proc +opt_dff +stat +select -assert-count 1 t:$aldff +sim -clock clk -r tb_aldff.fst -scope tb_aldff.uut -sim-cmp aldff diff --git a/tests/sim/sim_aldffe.ys b/tests/sim/sim_aldffe.ys new file mode 100644 index 000000000..b191cf877 --- /dev/null +++ b/tests/sim/sim_aldffe.ys @@ -0,0 +1,6 @@ +read_verilog aldffe.v +proc +opt_dff +stat +select -assert-count 1 t:$aldffe +sim -clock clk -r tb_aldffe.fst -scope tb_aldffe.uut -sim-cmp aldffe diff --git a/tests/sim/sim_dff.ys b/tests/sim/sim_dff.ys new file mode 100644 index 000000000..12f402443 --- /dev/null +++ b/tests/sim/sim_dff.ys @@ -0,0 +1,6 @@ +read_verilog dff.v +proc +opt_dff +stat +select -assert-count 1 t:$dff +sim -clock clk -r tb_dff.fst -scope tb_dff.uut -sim-cmp dff diff --git a/tests/sim/sim_dffe.ys b/tests/sim/sim_dffe.ys new file mode 100644 index 000000000..f9b9e4767 --- /dev/null +++ b/tests/sim/sim_dffe.ys @@ -0,0 +1,6 @@ +read_verilog dffe.v +proc +opt_dff +stat +select -assert-count 1 t:$dffe +sim -clock clk -r tb_dffe.fst -scope tb_dffe.uut -sim-cmp dffe diff --git a/tests/sim/sim_dffsr.ys b/tests/sim/sim_dffsr.ys new file mode 100644 index 000000000..e99ee860d --- /dev/null +++ b/tests/sim/sim_dffsr.ys @@ -0,0 +1,6 @@ +read_verilog dffsr.v +proc +opt_dff +stat +select -assert-count 1 t:$dffsr +sim -clock clk -r tb_dffsr.fst -scope tb_dffsr.uut -sim-cmp dffsr diff --git a/tests/sim/sim_dlatch.ys b/tests/sim/sim_dlatch.ys new file mode 100644 index 000000000..79e4601e3 --- /dev/null +++ b/tests/sim/sim_dlatch.ys @@ -0,0 +1,6 @@ +read_verilog dlatch.v +proc +opt_dff +stat +select -assert-count 1 t:$dlatch +sim -r tb_dlatch.fst -scope tb_dlatch.uut -sim-cmp dlatch diff --git a/tests/sim/sim_dlatchsr.ys b/tests/sim/sim_dlatchsr.ys new file mode 100644 index 000000000..c83051c8b --- /dev/null +++ b/tests/sim/sim_dlatchsr.ys @@ -0,0 +1,10 @@ +read_verilog -icells <<EOT +module dlatchsr(input d, set, clr, en, output reg q); +$dlatchsr #(.EN_POLARITY(1'b1), .CLR_POLARITY(1'b1), .SET_POLARITY(1'b1), .WIDTH(1)) uut (.EN(en), .SET(set), .CLR(clr), .D(d), .Q(q)); +endmodule +EOT +proc +opt_dff +stat +select -assert-count 1 t:$dlatchsr +sim -r tb_dlatchsr.fst -scope tb_dlatchsr.uut -sim-cmp dlatchsr diff --git a/tests/sim/sim_sdff.ys b/tests/sim/sim_sdff.ys new file mode 100644 index 000000000..a812c5d80 --- /dev/null +++ b/tests/sim/sim_sdff.ys @@ -0,0 +1,6 @@ +read_verilog sdff.v +proc +opt_dff +stat +select -assert-count 1 t:$sdff +sim -clock clk -r tb_sdff.fst -scope tb_sdff.uut -sim-cmp sdff diff --git a/tests/sim/sim_sdffce.ys b/tests/sim/sim_sdffce.ys new file mode 100644 index 000000000..b28acb83d --- /dev/null +++ b/tests/sim/sim_sdffce.ys @@ -0,0 +1,6 @@ +read_verilog sdffce.v +proc +opt_dff +stat +select -assert-count 1 t:$sdffce +sim -clock clk -r tb_sdffce.fst -scope tb_sdffce.uut -sim-cmp sdffce diff --git a/tests/sim/sim_sdffe.ys b/tests/sim/sim_sdffe.ys new file mode 100644 index 000000000..044f78eb3 --- /dev/null +++ b/tests/sim/sim_sdffe.ys @@ -0,0 +1,6 @@ +read_verilog sdffe.v +proc +opt_dff +stat +select -assert-count 1 t:$sdffe +sim -clock clk -r tb_sdffe.fst -scope tb_sdffe.uut -sim-cmp sdffe diff --git a/tests/sim/tb/tb_adff.v b/tests/sim/tb/tb_adff.v new file mode 100755 index 000000000..f1bc3547e --- /dev/null +++ b/tests/sim/tb/tb_adff.v @@ -0,0 +1,40 @@ +`timescale 1ns/1ns +module tb_adff(); + reg clk = 0; + reg rst = 0; + reg d = 0; + wire q; + + adff uut(.clk(clk),.d(d),.rst(rst),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_adff"); + $dumpvars(0,tb_adff); + #10 + d = 1; + #10 + d = 0; + #10 + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_adffe.v b/tests/sim/tb/tb_adffe.v new file mode 100755 index 000000000..bb23f963d --- /dev/null +++ b/tests/sim/tb/tb_adffe.v @@ -0,0 +1,58 @@ +`timescale 1ns/1ns +module tb_adffe(); + reg clk = 0; + reg rst = 0; + reg d = 0; + reg en = 0; + wire q; + + adffe uut(.clk(clk),.d(d),.rst(rst),.en(en),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_adffe"); + $dumpvars(0,tb_adffe); + #10 + d = 1; + #10 + d = 0; + #10 + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + en = 1; + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_adlatch.v b/tests/sim/tb/tb_adlatch.v new file mode 100755 index 000000000..59dd498d2 --- /dev/null +++ b/tests/sim/tb/tb_adlatch.v @@ -0,0 +1,70 @@ +`timescale 1ns/1ns +module tb_adlatch(); + reg clk = 0; + reg rst = 0; + reg en = 0; + reg d = 0; + wire q; + + adlatch uut(.d(d),.rst(rst),.en(en),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_adlatch"); + $dumpvars(0,tb_adlatch); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + en = 1; + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_aldff.v b/tests/sim/tb/tb_aldff.v new file mode 100755 index 000000000..0591c8b3c --- /dev/null +++ b/tests/sim/tb/tb_aldff.v @@ -0,0 +1,73 @@ +`timescale 1ns/1ns +module tb_aldff(); + reg clk = 0; + reg aload = 0; + reg [0:3] d = 4'b0000; + reg [0:3] ad = 4'b1010; + wire [0:3] q; + + aldff uut(.clk(clk),.d(d),.ad(ad),.aload(aload),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_aldff"); + $dumpvars(0,tb_aldff); + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + aload = 1; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + aload = 0; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + aload = 1; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + aload = 0; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_aldffe.v b/tests/sim/tb/tb_aldffe.v new file mode 100755 index 000000000..c3cb57f4e --- /dev/null +++ b/tests/sim/tb/tb_aldffe.v @@ -0,0 +1,75 @@ +`timescale 1ns/1ns +module tb_aldffe(); + reg clk = 0; + reg aload = 0; + reg [0:3] d = 4'b0000; + reg [0:3] ad = 4'b1010; + reg en = 0; + wire [0:3] q; + + aldffe uut(.clk(clk),.d(d),.ad(ad),.aload(aload),.en(en),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_aldffe"); + $dumpvars(0,tb_aldffe); + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + aload = 1; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + aload = 0; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + en = 1; + aload = 1; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + aload = 0; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + d = 4'b1100; + #10 + d = 4'b0011; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_dff.v b/tests/sim/tb/tb_dff.v new file mode 100755 index 000000000..aa41d1c6c --- /dev/null +++ b/tests/sim/tb/tb_dff.v @@ -0,0 +1,47 @@ +`timescale 1ns/1ns +module tb_dff(); + reg clk = 0; + reg d = 0; + wire q; + + dff uut(.clk(clk),.d(d),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_dff"); + $dumpvars(0,tb_dff); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_dffe.v b/tests/sim/tb/tb_dffe.v new file mode 100755 index 000000000..4e262b928 --- /dev/null +++ b/tests/sim/tb/tb_dffe.v @@ -0,0 +1,42 @@ +`timescale 1ns/1ns +module tb_dffe(); + reg clk = 0; + reg en = 0; + reg d = 0; + wire q; + + dffe uut(.clk(clk),.d(d),.en(en),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_dffe"); + $dumpvars(0,tb_dffe); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + en = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_dffsr.v b/tests/sim/tb/tb_dffsr.v new file mode 100755 index 000000000..6ecb85d67 --- /dev/null +++ b/tests/sim/tb/tb_dffsr.v @@ -0,0 +1,69 @@ +`timescale 1ns/1ns +module tb_dffsr(); + reg clk = 0; + reg d = 0; + reg set = 0; + reg clr = 0; + wire q; + + dffsr uut(.d(d),.clk(clk),.set(set),.clr(clr),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_dffsr"); + $dumpvars(0,tb_dffsr); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + clr = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + clr = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + set = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + set = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_dlatch.v b/tests/sim/tb/tb_dlatch.v new file mode 100755 index 000000000..aea6cb0a3 --- /dev/null +++ b/tests/sim/tb/tb_dlatch.v @@ -0,0 +1,50 @@ +`timescale 1ns/1ns +module tb_dlatch(); + reg clk = 0; + reg en = 0; + reg d = 0; + wire q; + + dlatch uut(.d(d),.en(en),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_dlatch"); + $dumpvars(0,tb_dlatch); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + en = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_dlatchsr.v b/tests/sim/tb/tb_dlatchsr.v new file mode 100755 index 000000000..0105d3288 --- /dev/null +++ b/tests/sim/tb/tb_dlatchsr.v @@ -0,0 +1,65 @@ +`timescale 1ns/1ns +module tb_dlatchsr(); + reg d = 0; + reg set = 0; + reg clr = 0; + wire q; + + dlatchsr uut(.d(d),.set(set),.clr(clr),.q(q)); + + initial + begin + $dumpfile("tb_dlatchsr"); + $dumpvars(0,tb_dlatchsr); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + clr = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + clr = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + set = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + set = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_sdff.v b/tests/sim/tb/tb_sdff.v new file mode 100755 index 000000000..f8e2a1c9d --- /dev/null +++ b/tests/sim/tb/tb_sdff.v @@ -0,0 +1,48 @@ +`timescale 1ns/1ns +module tb_sdff(); + reg clk = 0; + reg rst = 0; + reg d = 0; + wire q; + + sdff uut(.clk(clk),.d(d),.rst(rst),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_sdff"); + $dumpvars(0,tb_sdff); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_sdffce.v b/tests/sim/tb/tb_sdffce.v new file mode 100755 index 000000000..1c9952806 --- /dev/null +++ b/tests/sim/tb/tb_sdffce.v @@ -0,0 +1,79 @@ +`timescale 1ns/1ns +module tb_sdffce(); + reg clk = 0; + reg rst = 0; + reg d = 0; + reg en = 0; + wire q; + + sdffce uut(.clk(clk),.d(d),.rst(rst),.en(en),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_sdffce"); + $dumpvars(0,tb_sdffce); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + en = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/sim/tb/tb_sdffe.v b/tests/sim/tb/tb_sdffe.v new file mode 100755 index 000000000..36072f93d --- /dev/null +++ b/tests/sim/tb/tb_sdffe.v @@ -0,0 +1,70 @@ +`timescale 1ns/1ns +module tb_sdffe(); + reg clk = 0; + reg rst = 0; + reg d = 0; + reg en = 0; + wire q; + + sdffe uut(.clk(clk),.d(d),.rst(rst),.en(en),.q(q)); + + always + #(5) clk <= !clk; + + initial + begin + $dumpfile("tb_sdffe"); + $dumpvars(0,tb_sdffe); + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + en = 1; + rst = 1; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + rst = 0; + #10 + d = 1; + #10 + d = 0; + #10 + d = 1; + #10 + d = 0; + #10 + $finish; + end +endmodule diff --git a/tests/simple/attrib01_module.v b/tests/simple/attrib01_module.v index adef34f5b..d6e36fb80 100644 --- a/tests/simple/attrib01_module.v +++ b/tests/simple/attrib01_module.v @@ -1,4 +1,4 @@ -module bar(clk, rst, inp, out); +module attrib01_bar(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; @@ -10,12 +10,12 @@ module bar(clk, rst, inp, out); endmodule -module foo(clk, rst, inp, out); +module attrib01_foo(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; output wire out; - bar bar_instance (clk, rst, inp, out); + attrib01_bar bar_instance (clk, rst, inp, out); endmodule diff --git a/tests/simple/attrib02_port_decl.v b/tests/simple/attrib02_port_decl.v index 3505e7265..989213b77 100644 --- a/tests/simple/attrib02_port_decl.v +++ b/tests/simple/attrib02_port_decl.v @@ -1,4 +1,4 @@ -module bar(clk, rst, inp, out); +module attrib02_bar(clk, rst, inp, out); (* this_is_clock = 1 *) input wire clk; (* this_is_reset = 1 *) @@ -13,13 +13,13 @@ module bar(clk, rst, inp, out); endmodule -module foo(clk, rst, inp, out); +module attrib02_foo(clk, rst, inp, out); (* this_is_the_master_clock *) input wire clk; input wire rst; input wire inp; output wire out; - bar bar_instance (clk, rst, inp, out); + attrib02_bar bar_instance (clk, rst, inp, out); endmodule diff --git a/tests/simple/attrib03_parameter.v b/tests/simple/attrib03_parameter.v index 562d225cd..d2ae98978 100644 --- a/tests/simple/attrib03_parameter.v +++ b/tests/simple/attrib03_parameter.v @@ -1,4 +1,4 @@ -module bar(clk, rst, inp, out); +module attrib03_bar(clk, rst, inp, out); (* bus_width *) parameter WIDTH = 2; @@ -17,12 +17,12 @@ module bar(clk, rst, inp, out); endmodule -module foo(clk, rst, inp, out); +module attrib03_foo(clk, rst, inp, out); input wire clk; input wire rst; input wire [7:0] inp; output wire [7:0] out; - bar # (.WIDTH(8)) bar_instance (clk, rst, inp, out); + attrib03_bar # (.WIDTH(8)) bar_instance (clk, rst, inp, out); endmodule diff --git a/tests/simple/attrib04_net_var.v b/tests/simple/attrib04_net_var.v index 8b5523406..98826e971 100644 --- a/tests/simple/attrib04_net_var.v +++ b/tests/simple/attrib04_net_var.v @@ -1,4 +1,4 @@ -module bar(clk, rst, inp, out); +module attrib04_bar(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; @@ -21,12 +21,12 @@ module bar(clk, rst, inp, out); endmodule -module foo(clk, rst, inp, out); +module attrib04_foo(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; output wire out; - bar bar_instance (clk, rst, inp, out); + attrib04_bar bar_instance (clk, rst, inp, out); endmodule diff --git a/tests/simple/attrib05_port_conn.v.DISABLED b/tests/simple/attrib05_port_conn.v.DISABLED index e20e66319..8cc471f4e 100644 --- a/tests/simple/attrib05_port_conn.v.DISABLED +++ b/tests/simple/attrib05_port_conn.v.DISABLED @@ -1,4 +1,4 @@ -module bar(clk, rst, inp, out); +module attrib05_bar(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; @@ -10,12 +10,12 @@ module bar(clk, rst, inp, out); endmodule -module foo(clk, rst, inp, out); +module attrib05_foo(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; output wire out; - bar bar_instance ( (* clock_connected *) clk, rst, (* this_is_the_input *) inp, out); + attrib05_bar bar_instance ( (* clock_connected *) clk, rst, (* this_is_the_input *) inp, out); endmodule diff --git a/tests/simple/attrib06_operator_suffix.v b/tests/simple/attrib06_operator_suffix.v index e21173c58..2bc136f9a 100644 --- a/tests/simple/attrib06_operator_suffix.v +++ b/tests/simple/attrib06_operator_suffix.v @@ -1,4 +1,4 @@ -module bar(clk, rst, inp_a, inp_b, out); +module attrib06_bar(clk, rst, inp_a, inp_b, out); input wire clk; input wire rst; input wire [7:0] inp_a; @@ -11,13 +11,13 @@ module bar(clk, rst, inp_a, inp_b, out); endmodule -module foo(clk, rst, inp_a, inp_b, out); +module attrib06_foo(clk, rst, inp_a, inp_b, out); input wire clk; input wire rst; input wire [7:0] inp_a; input wire [7:0] inp_b; output wire [7:0] out; - bar bar_instance (clk, rst, inp_a, inp_b, out); + attrib06_bar bar_instance (clk, rst, inp_a, inp_b, out); endmodule diff --git a/tests/simple/attrib07_func_call.v.DISABLED b/tests/simple/attrib07_func_call.v.DISABLED index f55ef2316..282fc5da7 100644 --- a/tests/simple/attrib07_func_call.v.DISABLED +++ b/tests/simple/attrib07_func_call.v.DISABLED @@ -1,4 +1,4 @@ -function [7:0] do_add; +function [7:0] attrib07_do_add; input [7:0] inp_a; input [7:0] inp_b; @@ -6,7 +6,7 @@ function [7:0] do_add; endfunction -module foo(clk, rst, inp_a, inp_b, out); +module attri07_foo(clk, rst, inp_a, inp_b, out); input wire clk; input wire rst; input wire [7:0] inp_a; @@ -15,7 +15,7 @@ module foo(clk, rst, inp_a, inp_b, out); always @(posedge clk) if (rst) out <= 0; - else out <= do_add (* combinational_adder *) (inp_a, inp_b); + else out <= attrib07_do_add (* combinational_adder *) (inp_a, inp_b); endmodule diff --git a/tests/simple/attrib08_mod_inst.v b/tests/simple/attrib08_mod_inst.v index c5a32234e..759e67c7b 100644 --- a/tests/simple/attrib08_mod_inst.v +++ b/tests/simple/attrib08_mod_inst.v @@ -1,4 +1,4 @@ -module bar(clk, rst, inp, out); +module attrib08_bar(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; @@ -10,13 +10,13 @@ module bar(clk, rst, inp, out); endmodule -module foo(clk, rst, inp, out); +module attrib08_foo(clk, rst, inp, out); input wire clk; input wire rst; input wire inp; output wire out; (* my_module_instance = 99 *) - bar bar_instance (clk, rst, inp, out); + attrib08_bar bar_instance (clk, rst, inp, out); endmodule diff --git a/tests/simple/attrib09_case.v b/tests/simple/attrib09_case.v index 8551bf9d0..a72b81dda 100644 --- a/tests/simple/attrib09_case.v +++ b/tests/simple/attrib09_case.v @@ -1,4 +1,4 @@ -module bar(clk, rst, inp, out); +module attrib09_bar(clk, rst, inp, out); input wire clk; input wire rst; input wire [1:0] inp; @@ -15,12 +15,12 @@ module bar(clk, rst, inp, out); endmodule -module foo(clk, rst, inp, out); +module attrib09_foo(clk, rst, inp, out); input wire clk; input wire rst; input wire [1:0] inp; output wire [1:0] out; - bar bar_instance (clk, rst, inp, out); + attrib09_bar bar_instance (clk, rst, inp, out); endmodule diff --git a/tests/simple/case_expr_const.v b/tests/simple/case_expr_const.v index 58267b965..d9169c084 100644 --- a/tests/simple/case_expr_const.v +++ b/tests/simple/case_expr_const.v @@ -1,6 +1,6 @@ // Note: case_expr_{,non_}const.v should be modified in tandem to ensure both // the constant and non-constant case evaluation logic is covered -module top( +module case_expr_const_top( // expected to output all 1s output reg a, b, c, d, e, f, g, h ); diff --git a/tests/simple/case_expr_extend.sv b/tests/simple/case_expr_extend.sv new file mode 100644 index 000000000..d4ca2aa9b --- /dev/null +++ b/tests/simple/case_expr_extend.sv @@ -0,0 +1,11 @@ +module top( + output logic [5:0] out +); +initial begin + out = '0; + case (1'b1 << 1) + 2'b10: out = '1; + default: out = '0; + endcase +end +endmodule diff --git a/tests/simple/case_expr_non_const.v b/tests/simple/case_expr_non_const.v index 7856e781c..6dfc2e54e 100644 --- a/tests/simple/case_expr_non_const.v +++ b/tests/simple/case_expr_non_const.v @@ -1,6 +1,6 @@ // Note: case_expr_{,non_}const.v should be modified in tandem to ensure both // the constant and non-constant case evaluation logic is covered -module top( +module case_expr_non_const_top( // expected to output all 1s output reg a, b, c, d, e, f, g, h ); diff --git a/tests/simple/case_expr_query.sv b/tests/simple/case_expr_query.sv new file mode 100644 index 000000000..844dfb713 --- /dev/null +++ b/tests/simple/case_expr_query.sv @@ -0,0 +1,32 @@ +module top( + output logic [5:0] out +); +initial begin + out = '0; + case ($bits (out)) 6: + case ($size (out)) 6: + case ($high (out)) 5: + case ($low (out)) 0: + case ($left (out)) 5: + case ($right(out)) 0: + case (6) $bits (out): + case (6) $size (out): + case (5) $high (out): + case (0) $low (out): + case (5) $left (out): + case (0) $right(out): + out = '1; + endcase + endcase + endcase + endcase + endcase + endcase + endcase + endcase + endcase + endcase + endcase + endcase +end +endmodule diff --git a/tests/simple/case_large.v b/tests/simple/case_large.v index a96ce86fe..ec8ed6038 100644 --- a/tests/simple/case_large.v +++ b/tests/simple/case_large.v @@ -1,4 +1,4 @@ -module top ( +module case_lage_top ( input wire [127:0] x, output reg [31:0] y ); diff --git a/tests/simple/const_branch_finish.v b/tests/simple/const_branch_finish.v index f585be87a..7e365eeb4 100644 --- a/tests/simple/const_branch_finish.v +++ b/tests/simple/const_branch_finish.v @@ -4,7 +4,7 @@ $finish; \ end -module top; +module case_branch_finish_top; parameter WIDTH = 32; integer j; initial begin diff --git a/tests/simple/const_fold_func.v b/tests/simple/const_fold_func.v index ee2f12e06..b3f476ce3 100644 --- a/tests/simple/const_fold_func.v +++ b/tests/simple/const_fold_func.v @@ -1,4 +1,4 @@ -module top( +module const_fold_func_top( input wire [3:0] inp, output wire [3:0] out1, out2, out3, out4, out5, output reg [3:0] out6 diff --git a/tests/simple/const_func_shadow.v b/tests/simple/const_func_shadow.v index ca63606d9..fb4f148f6 100644 --- a/tests/simple/const_func_shadow.v +++ b/tests/simple/const_func_shadow.v @@ -1,4 +1,4 @@ -module top(w, x, y, z); +module const_func_shadow_top(w, x, y, z); function [11:0] func; input reg [2:0] x; input reg [2:0] y; diff --git a/tests/simple/defvalue.sv b/tests/simple/defvalue.sv index b0a087ecb..77d7ba26b 100644 --- a/tests/simple/defvalue.sv +++ b/tests/simple/defvalue.sv @@ -1,4 +1,4 @@ -module top(input clock, input [3:0] delta, output [3:0] cnt1, cnt2); +module defvalue_top(input clock, input [3:0] delta, output [3:0] cnt1, cnt2); cnt #(1) foo (.clock, .cnt(cnt1), .delta); cnt #(2) bar (.clock, .cnt(cnt2)); endmodule diff --git a/tests/simple/func_block.v b/tests/simple/func_block.v index be759d1a9..0ac7ca3bf 100644 --- a/tests/simple/func_block.v +++ b/tests/simple/func_block.v @@ -1,6 +1,6 @@ `default_nettype none -module top(inp, out1, out2, out3); +module func_block_top(inp, out1, out2, out3); input wire [31:0] inp; function automatic [31:0] func1; diff --git a/tests/simple/func_recurse.v b/tests/simple/func_recurse.v index d61c8cc06..02cfbcddf 100644 --- a/tests/simple/func_recurse.v +++ b/tests/simple/func_recurse.v @@ -1,4 +1,4 @@ -module top( +module func_recurse_top( input wire [3:0] inp, output wire [3:0] out1, out2 ); diff --git a/tests/simple/func_width_scope.v b/tests/simple/func_width_scope.v index ce81e894e..2f82988ae 100644 --- a/tests/simple/func_width_scope.v +++ b/tests/simple/func_width_scope.v @@ -1,4 +1,4 @@ -module top(inp, out1, out2); +module func_width_scope_top(inp, out1, out2); input wire signed inp; localparam WIDTH_A = 5; diff --git a/tests/simple/genblk_collide.v b/tests/simple/genblk_collide.v index f42dd2cfc..118c0b008 100644 --- a/tests/simple/genblk_collide.v +++ b/tests/simple/genblk_collide.v @@ -1,6 +1,6 @@ `default_nettype none -module top1; +module genblock_collide_top1; generate if (1) begin : foo if (1) begin : bar @@ -12,7 +12,7 @@ module top1; endgenerate endmodule -module top2; +module genblock_collide_top2; genvar i; generate if (1) begin : foo diff --git a/tests/simple/genblk_dive.v b/tests/simple/genblk_dive.v index 98d0e1f4b..ca0c0d4a1 100644 --- a/tests/simple/genblk_dive.v +++ b/tests/simple/genblk_dive.v @@ -1,5 +1,5 @@ `default_nettype none -module top(output wire x); +module genblk_dive_top(output wire x); generate if (1) begin : Z if (1) begin : A diff --git a/tests/simple/genblk_order.v b/tests/simple/genblk_order.v index 7c3a7a756..c80c1ac1a 100644 --- a/tests/simple/genblk_order.v +++ b/tests/simple/genblk_order.v @@ -1,5 +1,5 @@ `default_nettype none -module top( +module genblk_order_top( output wire out1, output wire out2 ); diff --git a/tests/simple/genblk_port_shadow.v b/tests/simple/genblk_port_shadow.v index a04631a20..c1348632c 100644 --- a/tests/simple/genblk_port_shadow.v +++ b/tests/simple/genblk_port_shadow.v @@ -1,4 +1,4 @@ -module top(x); +module genblock_port_shadow_top(x); generate if (1) begin : blk wire x; diff --git a/tests/simple/hierarchy.v b/tests/simple/hierarchy.v index 123afaeab..b03044fde 100644 --- a/tests/simple/hierarchy.v +++ b/tests/simple/hierarchy.v @@ -1,6 +1,6 @@ (* top *) -module top(a, b, y1, y2, y3, y4); +module hierarchy_top(a, b, y1, y2, y3, y4); input [3:0] a; input signed [3:0] b; output [7:0] y1, y2, y3, y4; diff --git a/tests/simple/hierdefparam.v b/tests/simple/hierdefparam.v index c9368ca7a..a6e0ac1b7 100644 --- a/tests/simple/hierdefparam.v +++ b/tests/simple/hierdefparam.v @@ -1,6 +1,6 @@ `default_nettype none -module hierdefparam_top(input [7:0] A, output [7:0] Y); +module hierdefparam_top(input wire [7:0] A, output wire [7:0] Y); generate begin:foo hierdefparam_a mod_a(.A(A), .Y(Y)); end endgenerate @@ -8,7 +8,7 @@ module hierdefparam_top(input [7:0] A, output [7:0] Y); defparam foo.mod_a.bar[1].mod_b.addvalue = 43; endmodule -module hierdefparam_a(input [7:0] A, output [7:0] Y); +module hierdefparam_a(input wire [7:0] A, output wire [7:0] Y); genvar i; generate for (i = 0; i < 2; i=i+1) begin:bar @@ -19,7 +19,7 @@ module hierdefparam_a(input [7:0] A, output [7:0] Y); assign bar[0].a = A, bar[1].a = bar[0].y, Y = bar[1].y; endmodule -module hierdefparam_b(input [7:0] A, output [7:0] Y); +module hierdefparam_b(input wire [7:0] A, output wire [7:0] Y); parameter [7:0] addvalue = 44; assign Y = A + addvalue; endmodule diff --git a/tests/simple/ifdef_1.v b/tests/simple/ifdef_1.v index fa962355c..f1358185c 100644 --- a/tests/simple/ifdef_1.v +++ b/tests/simple/ifdef_1.v @@ -1,4 +1,4 @@ -module top(o1, o2, o3, o4); +module ifdef_1_top(o1, o2, o3, o4); `define FAIL input wire not_a_port; diff --git a/tests/simple/ifdef_2.v b/tests/simple/ifdef_2.v index 6dd89efed..9fae7570d 100644 --- a/tests/simple/ifdef_2.v +++ b/tests/simple/ifdef_2.v @@ -1,4 +1,4 @@ -module top(o1, o2, o3); +module ifdef_2_top(o1, o2, o3); output wire o1; diff --git a/tests/simple/implicit_ports.v b/tests/simple/implicit_ports.sv index 8b0a6f386..8b0a6f386 100644 --- a/tests/simple/implicit_ports.v +++ b/tests/simple/implicit_ports.sv diff --git a/tests/simple/lesser_size_cast.sv b/tests/simple/lesser_size_cast.sv new file mode 100644 index 000000000..8c0bc9814 --- /dev/null +++ b/tests/simple/lesser_size_cast.sv @@ -0,0 +1,7 @@ +module top ( + input signed [1:0] a, + input signed [2:0] b, + output signed [4:0] c +); + assign c = 2'(a) * b; +endmodule diff --git a/tests/simple/local_loop_var.sv b/tests/simple/local_loop_var.sv index 46b4e5c22..42860e218 100644 --- a/tests/simple/local_loop_var.sv +++ b/tests/simple/local_loop_var.sv @@ -1,4 +1,4 @@ -module top(out); +module local_loop_top(out); output integer out; initial begin integer i; diff --git a/tests/simple/loop_prefix_case.v b/tests/simple/loop_prefix_case.v index 7ee28ed70..0cfa00547 100644 --- a/tests/simple/loop_prefix_case.v +++ b/tests/simple/loop_prefix_case.v @@ -1,4 +1,4 @@ -module top( +module loop_prefix_case_top( input wire x, output reg y ); diff --git a/tests/simple/loop_var_shadow.v b/tests/simple/loop_var_shadow.v index 0222a4493..b75a15ab0 100644 --- a/tests/simple/loop_var_shadow.v +++ b/tests/simple/loop_var_shadow.v @@ -1,4 +1,4 @@ -module top(out); +module loop_var_shadow_top(out); genvar i; generate for (i = 0; i < 2; i = i + 1) begin : loop diff --git a/tests/simple/macro_arg_spaces.sv b/tests/simple/macro_arg_spaces.sv index 75c4cd136..5fc9e2881 100644 --- a/tests/simple/macro_arg_spaces.sv +++ b/tests/simple/macro_arg_spaces.sv @@ -1,4 +1,4 @@ -module top( +module macro_arg_spaces_top( input wire [31:0] i, output wire [31:0] x, y, z ); diff --git a/tests/simple/macro_arg_surrounding_spaces.v b/tests/simple/macro_arg_surrounding_spaces.v index 3dbb5ea01..e0239c08b 100644 --- a/tests/simple/macro_arg_surrounding_spaces.v +++ b/tests/simple/macro_arg_surrounding_spaces.v @@ -1,4 +1,4 @@ -module top( +module macr_arg_surrounding_spaces_top( IDENT_V_, IDENT_W_, IDENT_X_, diff --git a/tests/simple/matching_end_labels.sv b/tests/simple/matching_end_labels.sv index 09182ebcf..2d42e7e10 100644 --- a/tests/simple/matching_end_labels.sv +++ b/tests/simple/matching_end_labels.sv @@ -1,4 +1,4 @@ -module top( +module matching_end_labels_top( output reg [7:0] out1, out2, out3, out4 ); diff --git a/tests/simple/mem2reg_bounds_tern.v b/tests/simple/mem2reg_bounds_tern.v index 89d6dd3e8..0e6852fe7 100644 --- a/tests/simple/mem2reg_bounds_tern.v +++ b/tests/simple/mem2reg_bounds_tern.v @@ -1,4 +1,4 @@ -module top( +module mem2reg_bounds_term_top( input clk, input wire [1:0] sel, input wire [7:0] base, diff --git a/tests/simple/memwr_port_connection.sv b/tests/simple/memwr_port_connection.sv new file mode 100644 index 000000000..5bf414e08 --- /dev/null +++ b/tests/simple/memwr_port_connection.sv @@ -0,0 +1,13 @@ +module producer( + output logic [3:0] out +); + assign out = 4'hA; +endmodule + +module top( + output logic [3:0] out +); + logic [3:0] v[0:0]; + producer p(v[0]); + assign out = v[0]; +endmodule diff --git a/tests/simple/module_scope.v b/tests/simple/module_scope.v index 3e46b72ef..ceeab7311 100644 --- a/tests/simple/module_scope.v +++ b/tests/simple/module_scope.v @@ -1,29 +1,29 @@ `default_nettype none -module Example(o1, o2); +module module_scope_Example(o1, o2); parameter [31:0] v1 = 10; parameter [31:0] v2 = 20; - output [31:0] o1, o2; - assign Example.o1 = Example.v1; - assign Example.o2 = Example.v2; + output wire [31:0] o1, o2; + assign module_scope_Example.o1 = module_scope_Example.v1; + assign module_scope_Example.o2 = module_scope_Example.v2; endmodule -module ExampleLong(o1, o2); +module module_scope_ExampleLong(o1, o2); parameter [31:0] ThisIsAnExtremelyLongParameterNameToTriggerTheSHA1Checksum1 = 10; parameter [31:0] ThisIsAnExtremelyLongParameterNameToTriggerTheSHA1Checksum2 = 20; - output [31:0] o1, o2; - assign ExampleLong.o1 = ExampleLong.ThisIsAnExtremelyLongParameterNameToTriggerTheSHA1Checksum1; - assign ExampleLong.o2 = ExampleLong.ThisIsAnExtremelyLongParameterNameToTriggerTheSHA1Checksum2; + output wire [31:0] o1, o2; + assign module_scope_ExampleLong.o1 = module_scope_ExampleLong.ThisIsAnExtremelyLongParameterNameToTriggerTheSHA1Checksum1; + assign module_scope_ExampleLong.o2 = module_scope_ExampleLong.ThisIsAnExtremelyLongParameterNameToTriggerTheSHA1Checksum2; endmodule -module top( - output [31:0] a1, a2, b1, b2, c1, c2, - output [31:0] d1, d2, e1, e2, f1, f2 +module module_scope_top( + output wire [31:0] a1, a2, b1, b2, c1, c2, + output wire [31:0] d1, d2, e1, e2, f1, f2 ); - Example a(a1, a2); - Example #(1) b(b1, b2); - Example #(1, 2) c(c1, c2); - ExampleLong d(d1, d2); - ExampleLong #(1) e(e1, e2); - ExampleLong #(1, 2) f(f1, f2); + module_scope_Example a(a1, a2); + module_scope_Example #(1) b(b1, b2); + module_scope_Example #(1, 2) c(c1, c2); + module_scope_ExampleLong d(d1, d2); + module_scope_ExampleLong #(1) e(e1, e2); + module_scope_ExampleLong #(1, 2) f(f1, f2); endmodule diff --git a/tests/simple/module_scope_case.v b/tests/simple/module_scope_case.v index 1472b6912..bceba4424 100644 --- a/tests/simple/module_scope_case.v +++ b/tests/simple/module_scope_case.v @@ -1,11 +1,11 @@ -module top( +module module_scope_case_top( input wire x, output reg y ); always @* begin - case (top.x) - 1: top.y = 0; - 0: top.y = 1; + case (module_scope_case_top.x) + 1: module_scope_case_top.y = 0; + 0: module_scope_case_top.y = 1; endcase end endmodule diff --git a/tests/simple/named_genblk.v b/tests/simple/named_genblk.v index b8300fc4d..b98b7c8ce 100644 --- a/tests/simple/named_genblk.v +++ b/tests/simple/named_genblk.v @@ -1,5 +1,5 @@ `default_nettype none -module top; +module named_genblk_top; generate if (1) begin wire t; diff --git a/tests/simple/nested_genblk_resolve.v b/tests/simple/nested_genblk_resolve.v index da5593f8a..70bbc611b 100644 --- a/tests/simple/nested_genblk_resolve.v +++ b/tests/simple/nested_genblk_resolve.v @@ -1,5 +1,5 @@ `default_nettype none -module top; +module nested_genblk_resolve_top; generate if (1) begin wire x; diff --git a/tests/simple/signed_full_slice.v b/tests/simple/signed_full_slice.v new file mode 100644 index 000000000..f8a331578 --- /dev/null +++ b/tests/simple/signed_full_slice.v @@ -0,0 +1,29 @@ +module pass_through_a( + input wire [31:0] inp, + output wire [31:0] out +); + assign out[31:0] = inp[31:0]; +endmodule + +module top_a( + input wire signed [31:0] inp, + output wire signed [31:0] out +); + pass_through_a pt(inp[31:0], out[31:0]); +endmodule + +// tests both module declaration orderings + +module top_b( + input wire signed [31:0] inp, + output wire signed [31:0] out +); + pass_through_b pt(inp[31:0], out[31:0]); +endmodule + +module pass_through_b( + input wire [31:0] inp, + output wire [31:0] out +); + assign out[31:0] = inp[31:0]; +endmodule diff --git a/tests/simple/specify.v b/tests/simple/specify.v index f19418d90..2c784ef6d 100644 --- a/tests/simple/specify.v +++ b/tests/simple/specify.v @@ -1,4 +1,4 @@ -module test_specify; +module test_specify(input A, output B); specparam a=1; diff --git a/tests/simple/string_format.v b/tests/simple/string_format.v index ce45ca1e9..cb7b419ac 100644 --- a/tests/simple/string_format.v +++ b/tests/simple/string_format.v @@ -1,4 +1,4 @@ -module top; +module string_format_top; parameter STR = "something interesting"; initial begin $display("A: %s", STR); diff --git a/tests/simple/unnamed_block_decl.sv b/tests/simple/unnamed_block_decl.sv index e81b457a8..e78c577da 100644 --- a/tests/simple/unnamed_block_decl.sv +++ b/tests/simple/unnamed_block_decl.sv @@ -1,4 +1,4 @@ -module top(z); +module unnamed_block_decl(z); output integer z; initial begin integer x; diff --git a/tests/simple/wandwor.v b/tests/simple/wandwor.v index 34404aa26..40502acfc 100644 --- a/tests/simple/wandwor.v +++ b/tests/simple/wandwor.v @@ -5,9 +5,9 @@ module wandwor_test0 (A, B, C, D, X, Y, Z); output Z; assign X = A, X = B, Y = C, Y = D; - foo foo_0 (C, D, X); - foo foo_1 (A, B, Y); - foo foo_2 (X, Y, Z); + wandwor_foo foo_0 (C, D, X); + wandwor_foo foo_1 (A, B, Y); + wandwor_foo foo_2 (X, Y, Z); endmodule module wandwor_test1 (A, B, C, D, X, Y, Z); @@ -16,7 +16,7 @@ module wandwor_test1 (A, B, C, D, X, Y, Z); output wand [3:0] Y; output Z; - bar bar_inst ( + wandwor_bar bar_inst ( .I0({A, B}), .I1({B, A}), .O({X, Y}) @@ -27,10 +27,10 @@ module wandwor_test1 (A, B, C, D, X, Y, Z); assign Z = ^{X,Y}; endmodule -module foo(input I0, I1, output O); +module wandwor_foo(input I0, I1, output O); assign O = I0 ^ I1; endmodule -module bar(input [7:0] I0, I1, output [7:0] O); +module wandwor_bar(input [7:0] I0, I1, output [7:0] O); assign O = I0 + I1; endmodule diff --git a/tests/sva/.gitignore b/tests/sva/.gitignore index cc254049a..b1965c97d 100644 --- a/tests/sva/.gitignore +++ b/tests/sva/.gitignore @@ -3,5 +3,6 @@ /*_pass /*_fail /*.ok +/*.fst /vhdlpsl[0-9][0-9] /vhdlpsl[0-9][0-9].sby diff --git a/tests/sva/Makefile b/tests/sva/Makefile index 1b217f746..dcabcf42b 100644 --- a/tests/sva/Makefile +++ b/tests/sva/Makefile @@ -10,4 +10,5 @@ clean: rm -rf $(addsuffix .ok,$(TESTS)) $(addsuffix .sby,$(TESTS)) $(TESTS) rm -rf $(addsuffix _pass.sby,$(TESTS)) $(addsuffix _pass,$(TESTS)) rm -rf $(addsuffix _fail.sby,$(TESTS)) $(addsuffix _fail,$(TESTS)) + rm -rf $(addsuffix .fst,$(TESTS)) diff --git a/tests/sva/nested_clk_else.sv b/tests/sva/nested_clk_else.sv new file mode 100644 index 000000000..4421cb36a --- /dev/null +++ b/tests/sva/nested_clk_else.sv @@ -0,0 +1,11 @@ +module top (input clk, a, b); + always @(posedge clk) begin + if (a); + else assume property (@(posedge clk) b); + end + +`ifndef FAIL + assume property (@(posedge clk) !a); +`endif + assert property (@(posedge clk) b); +endmodule diff --git a/tests/sva/runtest.sh b/tests/sva/runtest.sh index 1b65ca9c9..2ecc9780c 100644 --- a/tests/sva/runtest.sh +++ b/tests/sva/runtest.sh @@ -22,18 +22,17 @@ generate_sby() { if [ -f $prefix.sv ]; then if [ "$1" = "fail" ]; then - echo "verific -sv ${prefix}_fail.sv" + echo "read -sv ${prefix}_fail.sv" else - echo "verific -sv $prefix.sv" + echo "read -sv $prefix.sv" fi fi if [ -f $prefix.vhd ]; then - echo "verific -vhdl $prefix.vhd" + echo "read -vhdl $prefix.vhd" fi cat <<- EOT - verific -import -extnets -all top prep -top top chformal -early -assume @@ -58,7 +57,9 @@ generate_sby() { fi } -if [ -f $prefix.sv ]; then +if [ -f $prefix.ys ]; then + $PWD/../../yosys -q -e "Assert .* failed." -s $prefix.ys +elif [ -f $prefix.sv ]; then generate_sby pass > ${prefix}_pass.sby generate_sby fail > ${prefix}_fail.sby sby --yosys $PWD/../../yosys -f ${prefix}_pass.sby diff --git a/tests/sva/sva_value_change_changed.sv b/tests/sva/sva_value_change_changed.sv new file mode 100644 index 000000000..8f3a05a2f --- /dev/null +++ b/tests/sva/sva_value_change_changed.sv @@ -0,0 +1,17 @@ +module top ( + input clk, + input a, b +); + default clocking @(posedge clk); endclocking + + assert property ( + $changed(b) + ); + +`ifndef FAIL + assume property ( + b !== 'x ##1 $changed(b) + ); +`endif + +endmodule diff --git a/tests/sva/sva_value_change_changed_wide.sv b/tests/sva/sva_value_change_changed_wide.sv new file mode 100644 index 000000000..c9147c4f3 --- /dev/null +++ b/tests/sva/sva_value_change_changed_wide.sv @@ -0,0 +1,22 @@ +module top ( + input clk, + input [2:0] a, + input [2:0] b +); + default clocking @(posedge clk); endclocking + + assert property ( + $changed(a) + ); + + assert property ( + $changed(b) == ($changed(b[0]) || $changed(b[1]) || $changed(b[2])) + ); + +`ifndef FAIL + assume property ( + a !== 'x ##1 $changed(a) + ); +`endif + +endmodule diff --git a/tests/sva/sva_value_change_rose.sv b/tests/sva/sva_value_change_rose.sv new file mode 100644 index 000000000..d1c5290f1 --- /dev/null +++ b/tests/sva/sva_value_change_rose.sv @@ -0,0 +1,20 @@ +module top ( + input clk, + input a, b +); + default clocking @(posedge clk); endclocking + + wire a_copy; + assign a_copy = a; + + assert property ( + $rose(a) |-> b + ); + +`ifndef FAIL + assume property ( + $rose(a_copy) |-> b + ); +`endif + +endmodule diff --git a/tests/sva/sva_value_change_sim.sv b/tests/sva/sva_value_change_sim.sv new file mode 100644 index 000000000..92fe30b23 --- /dev/null +++ b/tests/sva/sva_value_change_sim.sv @@ -0,0 +1,70 @@ +module top ( + input clk +); + +reg [7:0] counter = 0; + +reg a = 0; +reg b = 1; +reg c; +reg [2:0] wide_a = 3'b10x; +reg [2:0] wide_b = 'x; + +wire a_fell; assign a_fell = $fell(a, @(posedge clk)); +wire a_rose; assign a_rose = $rose(a, @(posedge clk)); +wire a_stable; assign a_stable = $stable(a, @(posedge clk)); + +wire b_fell; assign b_fell = $fell(b, @(posedge clk)); +wire b_rose; assign b_rose = $rose(b, @(posedge clk)); +wire b_stable; assign b_stable = $stable(b, @(posedge clk)); + +wire c_fell; assign c_fell = $fell(c, @(posedge clk)); +wire c_rose; assign c_rose = $rose(c, @(posedge clk)); +wire c_stable; assign c_stable = $stable(c, @(posedge clk)); + +wire wide_a_stable; assign wide_a_stable = $stable(wide_a, @(posedge clk)); +wire wide_b_stable; assign wide_b_stable = $stable(wide_b, @(posedge clk)); + +always @(posedge clk) begin + counter <= counter + 1; + + case (counter) + 0: begin + assert property ( $fell(a) && !$rose(a) && !$stable(a)); + assert property (!$fell(b) && $rose(b) && !$stable(b)); + assert property (!$fell(c) && !$rose(c) && $stable(c)); + assert property (!$stable(wide_a)); + assert property ($stable(wide_b)); + a <= 1; b <= 1; c <= 1; + end + 1: begin + a <= 0; b <= 1; c <= 'x; + wide_a <= 3'b101; wide_b <= 3'bxx0; + end + 2: begin + assert property ( $fell(a) && !$rose(a) && !$stable(a)); + assert property (!$fell(b) && !$rose(b) && $stable(b)); + assert property (!$fell(c) && !$rose(c) && !$stable(c)); + assert property (!$stable(wide_a)); + assert property (!$stable(wide_b)); + a <= 0; b <= 0; c <= 0; + end + 3: begin a <= 0; b <= 1; c <= 'x; end + 4: begin + assert property (!$fell(a) && !$rose(a) && $stable(a)); + assert property (!$fell(b) && $rose(b) && !$stable(b)); + assert property (!$fell(c) && !$rose(c) && !$stable(c)); + assert property ($stable(wide_a)); + assert property ($stable(wide_b)); + a <= 'x; b <= 'x; c <= 'x; + wide_a <= 'x; wide_b <= 'x; + end + 5: begin + a <= 0; b <= 1; c <= 'x; + wide_a <= 3'b10x; wide_b <= 'x; + counter <= 0; + end + endcase; +end + +endmodule diff --git a/tests/sva/sva_value_change_sim.ys b/tests/sva/sva_value_change_sim.ys new file mode 100644 index 000000000..e004520ce --- /dev/null +++ b/tests/sva/sva_value_change_sim.ys @@ -0,0 +1,3 @@ +read -sv sva_value_change_sim.sv +hierarchy -top top +sim -clock clk -fst sva_value_change_sim.fst diff --git a/tests/techmap/.gitignore b/tests/techmap/.gitignore index cfed22fc5..56c9ba8f9 100644 --- a/tests/techmap/.gitignore +++ b/tests/techmap/.gitignore @@ -1,2 +1,3 @@ *.log +*.out /*.mk diff --git a/tests/techmap/dfflegalize_adff.ys b/tests/techmap/dfflegalize_adff.ys index 135ae0ab7..fc579e7d6 100644 --- a/tests/techmap/dfflegalize_adff.ys +++ b/tests/techmap/dfflegalize_adff.ys @@ -39,6 +39,8 @@ design -save orig flatten equiv_opt -assert -multiclock dfflegalize -cell $_DFF_PP0_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP0P_ x +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ x +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ x @@ -73,6 +75,36 @@ select -assert-count 14 t:$_DFFE_PP0P_ select -assert-none t:$_DFFE_PP0P_ t:$_NOT_ top/* %% %n t:* %i +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ x + +select -assert-count 2 adff0/t:$_NOT_ +select -assert-count 2 adff1/t:$_NOT_ +select -assert-count 2 adffe0/t:$_NOT_ +select -assert-count 2 adffe1/t:$_NOT_ +select -assert-count 0 adff0/t:$_MUX_ +select -assert-count 0 adff1/t:$_MUX_ +select -assert-count 4 adffe0/t:$_MUX_ +select -assert-count 4 adffe1/t:$_MUX_ +select -assert-count 14 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ x + +select -assert-count 2 adff0/t:$_NOT_ +select -assert-count 2 adff1/t:$_NOT_ +select -assert-count 3 adffe0/t:$_NOT_ +select -assert-count 3 adffe1/t:$_NOT_ +select -assert-count 14 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ top/* %% %n t:* %i + + # Convert everything to DFFSRs. design -load orig diff --git a/tests/techmap/dfflegalize_adff_init.ys b/tests/techmap/dfflegalize_adff_init.ys index 7764e15a5..25ed59307 100644 --- a/tests/techmap/dfflegalize_adff_init.ys +++ b/tests/techmap/dfflegalize_adff_init.ys @@ -45,6 +45,10 @@ equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP0P_ 0 -cell $_DLATCH_P_ equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP0P_ 1 -cell $_DLATCH_P_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP1P_ 0 -cell $_DLATCH_P_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP1P_ 1 -cell $_DLATCH_P_ 1 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 1 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ 0 equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ 0 @@ -144,9 +148,9 @@ design -load orig dfflegalize -cell $_DFFE_PP0P_ 0 -cell $_DLATCH_P_ 1 select -assert-count 2 adff0/t:$_NOT_ -select -assert-count 16 adff1/t:$_NOT_ +select -assert-count 13 adff1/t:$_NOT_ select -assert-count 3 adffe0/t:$_NOT_ -select -assert-count 22 adffe1/t:$_NOT_ +select -assert-count 18 adffe1/t:$_NOT_ select -assert-count 0 adff0/t:$_MUX_ select -assert-count 3 adff1/t:$_MUX_ select -assert-count 0 adffe0/t:$_MUX_ @@ -164,9 +168,9 @@ select -assert-none t:$_DFFE_PP0P_ t:$_DLATCH_P_ t:$_MUX_ t:$_NOT_ top/* %% %n t design -load orig dfflegalize -cell $_DFFE_PP0P_ 1 -cell $_DLATCH_P_ 1 -select -assert-count 16 adff0/t:$_NOT_ +select -assert-count 13 adff0/t:$_NOT_ select -assert-count 8 adff1/t:$_NOT_ -select -assert-count 22 adffe0/t:$_NOT_ +select -assert-count 18 adffe0/t:$_NOT_ select -assert-count 11 adffe1/t:$_NOT_ select -assert-count 3 adff0/t:$_MUX_ select -assert-count 0 adff1/t:$_MUX_ @@ -185,31 +189,27 @@ select -assert-none t:$_DFFE_PP0P_ t:$_DLATCH_P_ t:$_MUX_ t:$_NOT_ top/* %% %n t design -load orig dfflegalize -cell $_DFFE_PP1P_ 0 -cell $_DLATCH_P_ 1 -select -assert-count 16 adff0/t:$_NOT_ +select -assert-count 10 adff0/t:$_NOT_ select -assert-count 2 adff1/t:$_NOT_ -select -assert-count 22 adffe0/t:$_NOT_ +select -assert-count 14 adffe0/t:$_NOT_ select -assert-count 3 adffe1/t:$_NOT_ select -assert-count 3 adff0/t:$_MUX_ select -assert-count 0 adff1/t:$_MUX_ select -assert-count 4 adffe0/t:$_MUX_ select -assert-count 0 adffe1/t:$_MUX_ -select -assert-count 6 adff0/t:$_DFFE_PP1P_ +select -assert-count 9 adff0/t:$_DFFE_PP1P_ select -assert-count 3 adff1/t:$_DFFE_PP1P_ -select -assert-count 8 adffe0/t:$_DFFE_PP1P_ +select -assert-count 12 adffe0/t:$_DFFE_PP1P_ select -assert-count 4 adffe1/t:$_DFFE_PP1P_ -select -assert-count 3 adff0/t:$_DLATCH_P_ -select -assert-count 0 adff1/t:$_DLATCH_P_ -select -assert-count 4 adffe0/t:$_DLATCH_P_ -select -assert-count 0 adffe1/t:$_DLATCH_P_ -select -assert-none t:$_DFFE_PP1P_ t:$_DLATCH_P_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i +select -assert-none t:$_DFFE_PP1P_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i design -load orig dfflegalize -cell $_DFFE_PP1P_ 1 -cell $_DLATCH_P_ 1 select -assert-count 8 adff0/t:$_NOT_ -select -assert-count 16 adff1/t:$_NOT_ +select -assert-count 13 adff1/t:$_NOT_ select -assert-count 11 adffe0/t:$_NOT_ -select -assert-count 22 adffe1/t:$_NOT_ +select -assert-count 18 adffe1/t:$_NOT_ select -assert-count 0 adff0/t:$_MUX_ select -assert-count 3 adff1/t:$_MUX_ select -assert-count 0 adffe0/t:$_MUX_ @@ -225,6 +225,60 @@ select -assert-count 4 adffe1/t:$_DLATCH_P_ select -assert-none t:$_DFFE_PP1P_ t:$_DLATCH_P_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 0 + +select -assert-count 2 adff0/t:$_NOT_ +select -assert-count 2 adff1/t:$_NOT_ +select -assert-count 2 adffe0/t:$_NOT_ +select -assert-count 2 adffe1/t:$_NOT_ +select -assert-count 0 adff0/t:$_MUX_ +select -assert-count 0 adff1/t:$_MUX_ +select -assert-count 4 adffe0/t:$_MUX_ +select -assert-count 4 adffe1/t:$_MUX_ +select -assert-count 14 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 1 + +select -assert-count 8 adff0/t:$_NOT_ +select -assert-count 8 adff1/t:$_NOT_ +select -assert-count 10 adffe0/t:$_NOT_ +select -assert-count 10 adffe1/t:$_NOT_ +select -assert-count 0 adff0/t:$_MUX_ +select -assert-count 0 adff1/t:$_MUX_ +select -assert-count 4 adffe0/t:$_MUX_ +select -assert-count 4 adffe1/t:$_MUX_ +select -assert-count 14 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 0 + +select -assert-count 2 adff0/t:$_NOT_ +select -assert-count 2 adff1/t:$_NOT_ +select -assert-count 3 adffe0/t:$_NOT_ +select -assert-count 3 adffe1/t:$_NOT_ +select -assert-count 14 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 1 + +select -assert-count 8 adff0/t:$_NOT_ +select -assert-count 8 adff1/t:$_NOT_ +select -assert-count 11 adffe0/t:$_NOT_ +select -assert-count 11 adffe1/t:$_NOT_ +select -assert-count 14 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ top/* %% %n t:* %i + + # Convert everything to DFFSRs. design -load orig diff --git a/tests/techmap/dfflegalize_adlatch_init.ys b/tests/techmap/dfflegalize_adlatch_init.ys index 7b22ea0c0..a55082d1d 100644 --- a/tests/techmap/dfflegalize_adlatch_init.ys +++ b/tests/techmap/dfflegalize_adlatch_init.ys @@ -45,7 +45,7 @@ select -assert-none t:$_DLATCH_PP0_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i design -load orig dfflegalize -cell $_DLATCH_PP0_ 1 -select -assert-count 16 adlatch0/t:$_NOT_ +select -assert-count 13 adlatch0/t:$_NOT_ select -assert-count 8 adlatch1/t:$_NOT_ select -assert-count 3 adlatch0/t:$_MUX_ select -assert-count 0 adlatch1/t:$_MUX_ @@ -68,7 +68,7 @@ design -load orig dfflegalize -cell $_DLATCH_PP1_ 1 select -assert-count 8 adlatch0/t:$_NOT_ -select -assert-count 16 adlatch1/t:$_NOT_ +select -assert-count 13 adlatch1/t:$_NOT_ select -assert-count 0 adlatch0/t:$_MUX_ select -assert-count 3 adlatch1/t:$_MUX_ select -assert-count 3 adlatch0/t:$_DLATCH_PP1_ diff --git a/tests/techmap/dfflegalize_aldff.ys b/tests/techmap/dfflegalize_aldff.ys new file mode 100644 index 000000000..1ee9e3af6 --- /dev/null +++ b/tests/techmap/dfflegalize_aldff.ys @@ -0,0 +1,92 @@ +read_verilog -icells <<EOT + +module aldff(input C, L, AD, D, output [2:0] Q); +$_ALDFF_PP_ ff0 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[0])); +$_ALDFF_PN_ ff1 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[1])); +$_ALDFF_NP_ ff2 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[2])); +endmodule + +module aldffe(input C, E, L, AD, D, output [3:0] Q); +$_ALDFFE_PPP_ ff0 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[0])); +$_ALDFFE_PPN_ ff1 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[1])); +$_ALDFFE_PNP_ ff2 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[2])); +$_ALDFFE_NPP_ ff3 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[3])); +endmodule + +module top(input C, E, L, AD, D, output [6:0] Q); +aldff aldff_(.C(C), .L(L), .AD(AD), .D(D), .Q(Q[2:0])); +aldffe aldffe_(.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[6:3])); +endmodule + +EOT + +design -save orig +flatten +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ x +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ x +#equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ x +#equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ x + + +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ x + +select -assert-count 2 aldff/t:$_NOT_ +select -assert-count 2 aldffe/t:$_NOT_ +select -assert-count 0 aldff/t:$_MUX_ +select -assert-count 4 aldffe/t:$_MUX_ +select -assert-count 7 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ x + +select -assert-count 2 aldff/t:$_NOT_ +select -assert-count 3 aldffe/t:$_NOT_ +select -assert-count 7 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to DFFSRs. + +design -load orig +dfflegalize -cell $_DFFSR_PPP_ x + +select -assert-count 2 aldff/t:$_AND_ +select -assert-count 3 aldffe/t:$_AND_ +select -assert-count 2 aldff/t:$_ANDNOT_ +select -assert-count 3 aldffe/t:$_ANDNOT_ +select -assert-count 1 aldff/t:$_OR_ +select -assert-count 1 aldffe/t:$_OR_ +select -assert-count 1 aldff/t:$_ORNOT_ +select -assert-count 1 aldffe/t:$_ORNOT_ +select -assert-count 3 aldff/t:$_NOT_ +select -assert-count 3 aldffe/t:$_NOT_ +select -assert-count 0 aldff/t:$_MUX_ +select -assert-count 4 aldffe/t:$_MUX_ +select -assert-count 7 t:$_DFFSR_PPP_ +select -assert-none t:$_DFFSR_PPP_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_OR_ t:$_ORNOT_ top/* %% %n t:* %i + + +# Convert everything to DFFSREs. + +design -load orig +dfflegalize -cell $_DFFSRE_PPPP_ x + +select -assert-count 2 aldff/t:$_AND_ +select -assert-count 3 aldffe/t:$_AND_ +select -assert-count 2 aldff/t:$_ANDNOT_ +select -assert-count 3 aldffe/t:$_ANDNOT_ +select -assert-count 1 aldff/t:$_OR_ +select -assert-count 1 aldffe/t:$_OR_ +select -assert-count 1 aldff/t:$_ORNOT_ +select -assert-count 1 aldffe/t:$_ORNOT_ +select -assert-count 3 aldff/t:$_NOT_ +select -assert-count 4 aldffe/t:$_NOT_ +select -assert-count 7 t:$_DFFSRE_PPPP_ +select -assert-none t:$_DFFSRE_PPPP_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_OR_ t:$_ORNOT_ top/* %% %n t:* %i diff --git a/tests/techmap/dfflegalize_aldff_init.ys b/tests/techmap/dfflegalize_aldff_init.ys new file mode 100644 index 000000000..f4db8dd32 --- /dev/null +++ b/tests/techmap/dfflegalize_aldff_init.ys @@ -0,0 +1,148 @@ +read_verilog -icells <<EOT + +module aldff(input C, L, AD, D, (* init = 3'b000 *) output [2:0] Q); +$_ALDFF_PP_ ff0 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[0])); +$_ALDFF_PN_ ff1 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[1])); +$_ALDFF_NP_ ff2 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[2])); +endmodule + +module aldffe(input C, E, L, AD, D, (* init = 4'b0000 *) output [3:0] Q); +$_ALDFFE_PPP_ ff0 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[0])); +$_ALDFFE_PPN_ ff1 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[1])); +$_ALDFFE_PNP_ ff2 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[2])); +$_ALDFFE_NPP_ ff3 (.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[3])); +endmodule + +module top(input C, E, L, AD, D, output [6:0] Q); +aldff aldff_(.C(C), .L(L), .AD(AD), .D(D), .Q(Q[2:0])); +aldffe aldffe_(.C(C), .L(L), .AD(AD), .E(E), .D(D), .Q(Q[6:3])); +endmodule + +EOT + +design -save orig +flatten +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 1 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 1 +#equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ 0 +#equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ 1 +#equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ 0 +#equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ 1 + + +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 0 + +select -assert-count 2 aldff/t:$_NOT_ +select -assert-count 2 aldffe/t:$_NOT_ +select -assert-count 0 aldff/t:$_MUX_ +select -assert-count 4 aldffe/t:$_MUX_ +select -assert-count 7 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 1 + +select -assert-count 11 aldff/t:$_NOT_ +select -assert-count 14 aldffe/t:$_NOT_ +select -assert-count 0 aldff/t:$_MUX_ +select -assert-count 4 aldffe/t:$_MUX_ +select -assert-count 7 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 0 + +select -assert-count 2 aldff/t:$_NOT_ +select -assert-count 3 aldffe/t:$_NOT_ +select -assert-count 7 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 1 + +select -assert-count 11 aldff/t:$_NOT_ +select -assert-count 15 aldffe/t:$_NOT_ +select -assert-count 7 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to DFFSRs. + +design -load orig +dfflegalize -cell $_DFFSR_PPP_ 0 + +select -assert-count 2 aldff/t:$_AND_ +select -assert-count 3 aldffe/t:$_AND_ +select -assert-count 2 aldff/t:$_ANDNOT_ +select -assert-count 3 aldffe/t:$_ANDNOT_ +select -assert-count 1 aldff/t:$_OR_ +select -assert-count 1 aldffe/t:$_OR_ +select -assert-count 1 aldff/t:$_ORNOT_ +select -assert-count 1 aldffe/t:$_ORNOT_ +select -assert-count 3 aldff/t:$_NOT_ +select -assert-count 3 aldffe/t:$_NOT_ +select -assert-count 0 aldff/t:$_MUX_ +select -assert-count 4 aldffe/t:$_MUX_ +select -assert-count 7 t:$_DFFSR_PPP_ +select -assert-none t:$_DFFSR_PPP_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_OR_ t:$_ORNOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_DFFSR_PPP_ 1 + +select -assert-count 2 aldff/t:$_AND_ +select -assert-count 3 aldffe/t:$_AND_ +select -assert-count 2 aldff/t:$_ANDNOT_ +select -assert-count 3 aldffe/t:$_ANDNOT_ +select -assert-count 1 aldff/t:$_OR_ +select -assert-count 1 aldffe/t:$_OR_ +select -assert-count 1 aldff/t:$_ORNOT_ +select -assert-count 1 aldffe/t:$_ORNOT_ +select -assert-count 12 aldff/t:$_NOT_ +select -assert-count 15 aldffe/t:$_NOT_ +select -assert-count 0 aldff/t:$_MUX_ +select -assert-count 4 aldffe/t:$_MUX_ +select -assert-count 7 t:$_DFFSR_PPP_ +select -assert-none t:$_DFFSR_PPP_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_OR_ t:$_ORNOT_ top/* %% %n t:* %i + + +# Convert everything to DFFSREs. + +design -load orig +dfflegalize -cell $_DFFSRE_PPPP_ 0 + +select -assert-count 2 aldff/t:$_AND_ +select -assert-count 3 aldffe/t:$_AND_ +select -assert-count 2 aldff/t:$_ANDNOT_ +select -assert-count 3 aldffe/t:$_ANDNOT_ +select -assert-count 1 aldff/t:$_OR_ +select -assert-count 1 aldffe/t:$_OR_ +select -assert-count 1 aldff/t:$_ORNOT_ +select -assert-count 1 aldffe/t:$_ORNOT_ +select -assert-count 3 aldff/t:$_NOT_ +select -assert-count 4 aldffe/t:$_NOT_ +select -assert-count 7 t:$_DFFSRE_PPPP_ +select -assert-none t:$_DFFSRE_PPPP_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_OR_ t:$_ORNOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_DFFSRE_PPPP_ 1 + +select -assert-count 2 aldff/t:$_AND_ +select -assert-count 3 aldffe/t:$_AND_ +select -assert-count 2 aldff/t:$_ANDNOT_ +select -assert-count 3 aldffe/t:$_ANDNOT_ +select -assert-count 1 aldff/t:$_OR_ +select -assert-count 1 aldffe/t:$_OR_ +select -assert-count 1 aldff/t:$_ORNOT_ +select -assert-count 1 aldffe/t:$_ORNOT_ +select -assert-count 12 aldff/t:$_NOT_ +select -assert-count 16 aldffe/t:$_NOT_ +select -assert-count 7 t:$_DFFSRE_PPPP_ +select -assert-none t:$_DFFSRE_PPPP_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_OR_ t:$_ORNOT_ top/* %% %n t:* %i diff --git a/tests/techmap/dfflegalize_dff.ys b/tests/techmap/dfflegalize_dff.ys index 63ab47865..374289678 100644 --- a/tests/techmap/dfflegalize_dff.ys +++ b/tests/techmap/dfflegalize_dff.ys @@ -70,6 +70,8 @@ equiv_opt -assert -multiclock dfflegalize -cell $_DFF_P_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFF_PP0_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP0P_ x +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ x +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ x equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ x equiv_opt -assert -multiclock dfflegalize -cell $_SDFF_PP0_ x @@ -176,6 +178,56 @@ select -assert-count 27 t:$_DFFE_PP0P_ select -assert-none t:$_DFFE_PP0P_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ x + +select -assert-count 1 dff/t:$_NOT_ +select -assert-count 1 dffe/t:$_NOT_ +select -assert-count 1 sdff0/t:$_NOT_ +select -assert-count 1 sdff1/t:$_NOT_ +select -assert-count 1 sdffe0/t:$_NOT_ +select -assert-count 1 sdffe1/t:$_NOT_ +select -assert-count 1 sdffce0/t:$_NOT_ +select -assert-count 1 sdffce1/t:$_NOT_ +select -assert-count 0 dff/t:$_MUX_ +select -assert-count 3 dffe/t:$_MUX_ +select -assert-count 3 sdff0/t:$_MUX_ +select -assert-count 3 sdff1/t:$_MUX_ +select -assert-count 8 sdffe0/t:$_MUX_ +select -assert-count 8 sdffe1/t:$_MUX_ +select -assert-count 8 sdffce0/t:$_MUX_ +select -assert-count 8 sdffce1/t:$_MUX_ +select -assert-count 27 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ x + +select -assert-count 1 dff/t:$_NOT_ +select -assert-count 2 dffe/t:$_NOT_ +select -assert-count 1 sdff0/t:$_NOT_ +select -assert-count 1 sdff1/t:$_NOT_ +select -assert-count 1 sdffe0/t:$_NOT_ +select -assert-count 1 sdffe1/t:$_NOT_ +select -assert-count 2 sdffce0/t:$_NOT_ +select -assert-count 2 sdffce1/t:$_NOT_ +select -assert-count 0 dff/t:$_MUX_ +select -assert-count 0 dffe/t:$_MUX_ +select -assert-count 3 sdff0/t:$_MUX_ +select -assert-count 3 sdff1/t:$_MUX_ +select -assert-count 8 sdffe0/t:$_MUX_ +select -assert-count 8 sdffe1/t:$_MUX_ +select -assert-count 4 sdffce0/t:$_MUX_ +select -assert-count 4 sdffce1/t:$_MUX_ +select -assert-count 27 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + # Convert everything to DFFSRs. design -load orig @@ -237,25 +289,18 @@ select -assert-count 2 sdff0/t:$_NOT_ select -assert-count 8 sdff1/t:$_NOT_ select -assert-count 2 sdffe0/t:$_NOT_ select -assert-count 10 sdffe1/t:$_NOT_ -select -assert-count 2 sdffce0/t:$_NOT_ -select -assert-count 10 sdffce1/t:$_NOT_ +select -assert-count 1 sdffce0/t:$_NOT_ +select -assert-count 1 sdffce1/t:$_NOT_ select -assert-count 0 dff/t:$_MUX_ select -assert-count 3 dffe/t:$_MUX_ select -assert-count 0 sdff0/t:$_MUX_ select -assert-count 0 sdff1/t:$_MUX_ select -assert-count 4 sdffe0/t:$_MUX_ select -assert-count 4 sdffe1/t:$_MUX_ -select -assert-count 4 sdffce0/t:$_MUX_ -select -assert-count 4 sdffce1/t:$_MUX_ -select -assert-count 0 t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ %% sdffce0/* sdffce1/* %u %n %i -select -assert-count 2 sdffce0/t:$_AND_ -select -assert-count 2 sdffce1/t:$_AND_ -select -assert-count 1 sdffce0/t:$_ORNOT_ -select -assert-count 1 sdffce1/t:$_ORNOT_ -select -assert-count 1 sdffce0/t:$_ANDNOT_ -select -assert-count 1 sdffce1/t:$_ANDNOT_ +select -assert-count 8 sdffce0/t:$_MUX_ +select -assert-count 8 sdffce1/t:$_MUX_ select -assert-count 27 t:$_SDFF_PP0_ -select -assert-none t:$_SDFF_PP0_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ top/* %% %n t:* %i +select -assert-none t:$_SDFF_PP0_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i # Convert everything to SDFFEs. diff --git a/tests/techmap/dfflegalize_dff_init.ys b/tests/techmap/dfflegalize_dff_init.ys index 741ac39d0..a170249c7 100644 --- a/tests/techmap/dfflegalize_dff_init.ys +++ b/tests/techmap/dfflegalize_dff_init.ys @@ -78,6 +78,10 @@ equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP0P_ 0 equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP0P_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP1P_ 0 equiv_opt -assert -multiclock dfflegalize -cell $_DFFE_PP1P_ 1 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 1 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ 0 equiv_opt -assert -multiclock dfflegalize -cell $_DFFSR_PPP_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ 0 @@ -371,6 +375,100 @@ select -assert-count 27 t:$_DFFE_PP1P_ select -assert-none t:$_DFFE_PP1P_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 0 + +select -assert-count 1 dff/t:$_NOT_ +select -assert-count 1 dffe/t:$_NOT_ +select -assert-count 1 sdff0/t:$_NOT_ +select -assert-count 1 sdff1/t:$_NOT_ +select -assert-count 1 sdffe0/t:$_NOT_ +select -assert-count 1 sdffe1/t:$_NOT_ +select -assert-count 1 sdffce0/t:$_NOT_ +select -assert-count 1 sdffce1/t:$_NOT_ +select -assert-count 0 dff/t:$_MUX_ +select -assert-count 3 dffe/t:$_MUX_ +select -assert-count 3 sdff0/t:$_MUX_ +select -assert-count 3 sdff1/t:$_MUX_ +select -assert-count 8 sdffe0/t:$_MUX_ +select -assert-count 8 sdffe1/t:$_MUX_ +select -assert-count 8 sdffce0/t:$_MUX_ +select -assert-count 8 sdffce1/t:$_MUX_ +select -assert-count 27 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 1 + +select -assert-count 5 dff/t:$_NOT_ +select -assert-count 7 dffe/t:$_NOT_ +select -assert-count 7 sdff0/t:$_NOT_ +select -assert-count 7 sdff1/t:$_NOT_ +select -assert-count 9 sdffe0/t:$_NOT_ +select -assert-count 9 sdffe1/t:$_NOT_ +select -assert-count 9 sdffce0/t:$_NOT_ +select -assert-count 9 sdffce1/t:$_NOT_ +select -assert-count 0 dff/t:$_MUX_ +select -assert-count 3 dffe/t:$_MUX_ +select -assert-count 3 sdff0/t:$_MUX_ +select -assert-count 3 sdff1/t:$_MUX_ +select -assert-count 8 sdffe0/t:$_MUX_ +select -assert-count 8 sdffe1/t:$_MUX_ +select -assert-count 8 sdffce0/t:$_MUX_ +select -assert-count 8 sdffce1/t:$_MUX_ +select -assert-count 27 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 0 + +select -assert-count 1 dff/t:$_NOT_ +select -assert-count 2 dffe/t:$_NOT_ +select -assert-count 1 sdff0/t:$_NOT_ +select -assert-count 1 sdff1/t:$_NOT_ +select -assert-count 1 sdffe0/t:$_NOT_ +select -assert-count 1 sdffe1/t:$_NOT_ +select -assert-count 2 sdffce0/t:$_NOT_ +select -assert-count 2 sdffce1/t:$_NOT_ +select -assert-count 0 dff/t:$_MUX_ +select -assert-count 0 dffe/t:$_MUX_ +select -assert-count 3 sdff0/t:$_MUX_ +select -assert-count 3 sdff1/t:$_MUX_ +select -assert-count 8 sdffe0/t:$_MUX_ +select -assert-count 8 sdffe1/t:$_MUX_ +select -assert-count 4 sdffce0/t:$_MUX_ +select -assert-count 4 sdffce1/t:$_MUX_ +select -assert-count 27 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 1 + +select -assert-count 5 dff/t:$_NOT_ +select -assert-count 8 dffe/t:$_NOT_ +select -assert-count 7 sdff0/t:$_NOT_ +select -assert-count 7 sdff1/t:$_NOT_ +select -assert-count 9 sdffe0/t:$_NOT_ +select -assert-count 9 sdffe1/t:$_NOT_ +select -assert-count 10 sdffce0/t:$_NOT_ +select -assert-count 10 sdffce1/t:$_NOT_ +select -assert-count 0 dff/t:$_MUX_ +select -assert-count 0 dffe/t:$_MUX_ +select -assert-count 3 sdff0/t:$_MUX_ +select -assert-count 3 sdff1/t:$_MUX_ +select -assert-count 8 sdffe0/t:$_MUX_ +select -assert-count 8 sdffe1/t:$_MUX_ +select -assert-count 4 sdffce0/t:$_MUX_ +select -assert-count 4 sdffce1/t:$_MUX_ +select -assert-count 27 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i + + # Convert everything to DFFSRs. design -load orig @@ -476,7 +574,7 @@ select -assert-count 2 sdff0/t:$_NOT_ select -assert-count 1 sdff1/t:$_NOT_ select -assert-count 2 sdffe0/t:$_NOT_ select -assert-count 1 sdffe1/t:$_NOT_ -select -assert-count 2 sdffce0/t:$_NOT_ +select -assert-count 1 sdffce0/t:$_NOT_ select -assert-count 1 sdffce1/t:$_NOT_ select -assert-count 0 dff/t:$_MUX_ select -assert-count 3 dffe/t:$_MUX_ @@ -484,14 +582,10 @@ select -assert-count 0 sdff0/t:$_MUX_ select -assert-count 3 sdff1/t:$_MUX_ select -assert-count 4 sdffe0/t:$_MUX_ select -assert-count 8 sdffe1/t:$_MUX_ -select -assert-count 4 sdffce0/t:$_MUX_ +select -assert-count 8 sdffce0/t:$_MUX_ select -assert-count 8 sdffce1/t:$_MUX_ -select -assert-count 0 t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ %% sdffce0/* %n %i -select -assert-count 2 sdffce0/t:$_AND_ -select -assert-count 1 sdffce0/t:$_ORNOT_ -select -assert-count 1 sdffce0/t:$_ANDNOT_ select -assert-count 27 t:$_SDFF_PP0_ -select -assert-none t:$_SDFF_PP0_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ top/* %% %n t:* %i +select -assert-none t:$_SDFF_PP0_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i design -load orig dfflegalize -cell $_SDFF_PP0_ 1 @@ -503,7 +597,7 @@ select -assert-count 8 sdff1/t:$_NOT_ select -assert-count 9 sdffe0/t:$_NOT_ select -assert-count 10 sdffe1/t:$_NOT_ select -assert-count 9 sdffce0/t:$_NOT_ -select -assert-count 10 sdffce1/t:$_NOT_ +select -assert-count 9 sdffce1/t:$_NOT_ select -assert-count 0 dff/t:$_MUX_ select -assert-count 3 dffe/t:$_MUX_ select -assert-count 3 sdff0/t:$_MUX_ @@ -511,13 +605,9 @@ select -assert-count 0 sdff1/t:$_MUX_ select -assert-count 8 sdffe0/t:$_MUX_ select -assert-count 4 sdffe1/t:$_MUX_ select -assert-count 8 sdffce0/t:$_MUX_ -select -assert-count 4 sdffce1/t:$_MUX_ -select -assert-count 0 t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ %% sdffce1/* %n %i -select -assert-count 2 sdffce1/t:$_AND_ -select -assert-count 1 sdffce1/t:$_ORNOT_ -select -assert-count 1 sdffce1/t:$_ANDNOT_ +select -assert-count 8 sdffce1/t:$_MUX_ select -assert-count 27 t:$_SDFF_PP0_ -select -assert-none t:$_SDFF_PP0_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ top/* %% %n t:* %i +select -assert-none t:$_SDFF_PP0_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i design -load orig dfflegalize -cell $_SDFF_PP1_ 0 @@ -529,7 +619,7 @@ select -assert-count 2 sdff1/t:$_NOT_ select -assert-count 1 sdffe0/t:$_NOT_ select -assert-count 2 sdffe1/t:$_NOT_ select -assert-count 1 sdffce0/t:$_NOT_ -select -assert-count 2 sdffce1/t:$_NOT_ +select -assert-count 1 sdffce1/t:$_NOT_ select -assert-count 0 dff/t:$_MUX_ select -assert-count 3 dffe/t:$_MUX_ select -assert-count 3 sdff0/t:$_MUX_ @@ -537,13 +627,9 @@ select -assert-count 0 sdff1/t:$_MUX_ select -assert-count 8 sdffe0/t:$_MUX_ select -assert-count 4 sdffe1/t:$_MUX_ select -assert-count 8 sdffce0/t:$_MUX_ -select -assert-count 4 sdffce1/t:$_MUX_ -select -assert-count 0 t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ %% sdffce1/* %n %i -select -assert-count 2 sdffce1/t:$_AND_ -select -assert-count 1 sdffce1/t:$_ORNOT_ -select -assert-count 1 sdffce1/t:$_ANDNOT_ +select -assert-count 8 sdffce1/t:$_MUX_ select -assert-count 27 t:$_SDFF_PP1_ -select -assert-none t:$_SDFF_PP1_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ top/* %% %n t:* %i +select -assert-none t:$_SDFF_PP1_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i design -load orig dfflegalize -cell $_SDFF_PP1_ 1 @@ -554,7 +640,7 @@ select -assert-count 8 sdff0/t:$_NOT_ select -assert-count 7 sdff1/t:$_NOT_ select -assert-count 10 sdffe0/t:$_NOT_ select -assert-count 9 sdffe1/t:$_NOT_ -select -assert-count 10 sdffce0/t:$_NOT_ +select -assert-count 9 sdffce0/t:$_NOT_ select -assert-count 9 sdffce1/t:$_NOT_ select -assert-count 0 dff/t:$_MUX_ select -assert-count 3 dffe/t:$_MUX_ @@ -562,14 +648,10 @@ select -assert-count 0 sdff0/t:$_MUX_ select -assert-count 3 sdff1/t:$_MUX_ select -assert-count 4 sdffe0/t:$_MUX_ select -assert-count 8 sdffe1/t:$_MUX_ -select -assert-count 4 sdffce0/t:$_MUX_ +select -assert-count 8 sdffce0/t:$_MUX_ select -assert-count 8 sdffce1/t:$_MUX_ -select -assert-count 0 t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ %% sdffce0/* %n %i -select -assert-count 2 sdffce0/t:$_AND_ -select -assert-count 1 sdffce0/t:$_ORNOT_ -select -assert-count 1 sdffce0/t:$_ANDNOT_ select -assert-count 27 t:$_SDFF_PP1_ -select -assert-none t:$_SDFF_PP1_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ORNOT_ t:$_ANDNOT_ top/* %% %n t:* %i +select -assert-none t:$_SDFF_PP1_ t:$_MUX_ t:$_NOT_ top/* %% %n t:* %i # Convert everything to SDFFEs. diff --git a/tests/techmap/dfflegalize_dlatch.ys b/tests/techmap/dfflegalize_dlatch.ys index b68ea741e..11683bc1a 100644 --- a/tests/techmap/dfflegalize_dlatch.ys +++ b/tests/techmap/dfflegalize_dlatch.ys @@ -11,6 +11,8 @@ design -save orig equiv_opt -assert -multiclock dfflegalize -cell $_DLATCH_P_ x equiv_opt -assert -multiclock dfflegalize -cell $_DLATCH_PP0_ x equiv_opt -assert -multiclock dfflegalize -cell $_DLATCHSR_PPP_ x +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ x +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ x # Convert everything to DFFs. @@ -40,3 +42,23 @@ dfflegalize -cell $_DLATCHSR_PPP_ x select -assert-count 1 t:$_NOT_ select -assert-count 2 t:$_DLATCHSR_PPP_ select -assert-none t:$_DLATCHSR_PPP_ t:$_NOT_ %% %n t:* %i + + +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ x + +select -assert-count 1 t:$_NOT_ +select -assert-count 2 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_NOT_ %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ x + +select -assert-count 1 t:$_NOT_ +select -assert-count 2 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ %% %n t:* %i diff --git a/tests/techmap/dfflegalize_dlatch_const.ys b/tests/techmap/dfflegalize_dlatch_const.ys index f30a534fd..159692249 100644 --- a/tests/techmap/dfflegalize_dlatch_const.ys +++ b/tests/techmap/dfflegalize_dlatch_const.ys @@ -24,14 +24,14 @@ equiv_opt -assert -multiclock dfflegalize -cell $_DFFSRE_PPPP_ 1 design -load orig dfflegalize -cell $_DFF_PP0_ 01 -select -assert-count 12 t:$_NOT_ +select -assert-count 8 t:$_NOT_ select -assert-count 8 t:$_DFF_PP0_ select -assert-none t:$_DFF_PP0_ t:$_NOT_ %% %n t:* %i design -load orig dfflegalize -cell $_DFF_PP?_ 0 -select -assert-count 12 t:$_NOT_ +select -assert-count 8 t:$_NOT_ select -assert-count 4 t:$_DFF_PP0_ select -assert-count 4 t:$_DFF_PP1_ select -assert-none t:$_DFF_PP0_ t:$_DFF_PP1_ t:$_NOT_ %% %n t:* %i @@ -41,13 +41,13 @@ select -assert-none t:$_DFF_PP0_ t:$_DFF_PP1_ t:$_NOT_ %% %n t:* %i design -load orig dfflegalize -cell $_DFFSRE_PPPP_ 0 -select -assert-count 12 t:$_NOT_ +select -assert-count 8 t:$_NOT_ select -assert-count 8 t:$_DFFSRE_PPPP_ select -assert-none t:$_DFFSRE_PPPP_ t:$_NOT_ %% %n t:* %i design -load orig dfflegalize -cell $_DFFSRE_PPPP_ 1 -select -assert-count 12 t:$_NOT_ +select -assert-count 8 t:$_NOT_ select -assert-count 8 t:$_DFFSRE_PPPP_ select -assert-none t:$_DFFSRE_PPPP_ t:$_NOT_ %% %n t:* %i diff --git a/tests/techmap/dfflegalize_dlatch_init.ys b/tests/techmap/dfflegalize_dlatch_init.ys index ccc9e41d7..9324c6691 100644 --- a/tests/techmap/dfflegalize_dlatch_init.ys +++ b/tests/techmap/dfflegalize_dlatch_init.ys @@ -16,6 +16,10 @@ equiv_opt -assert -multiclock dfflegalize -cell $_DLATCH_PP1_ 0 equiv_opt -assert -multiclock dfflegalize -cell $_DLATCH_PP1_ 1 equiv_opt -assert -multiclock dfflegalize -cell $_DLATCHSR_PPP_ 0 equiv_opt -assert -multiclock dfflegalize -cell $_DLATCHSR_PPP_ 1 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFF_PP_ 1 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 0 +equiv_opt -assert -multiclock dfflegalize -cell $_ALDFFE_PPP_ 1 # Convert everything to DFFs. @@ -80,3 +84,37 @@ dfflegalize -cell $_DLATCHSR_PPP_ 1 select -assert-count 5 t:$_NOT_ select -assert-count 2 t:$_DLATCHSR_PPP_ select -assert-none t:$_DLATCHSR_PPP_ t:$_NOT_ %% %n t:* %i + + +# Convert everything to ALDFFs. + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 0 + +select -assert-count 1 t:$_NOT_ +select -assert-count 2 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_NOT_ %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFF_PP_ 1 + +select -assert-count 5 t:$_NOT_ +select -assert-count 2 t:$_ALDFF_PP_ +select -assert-none t:$_ALDFF_PP_ t:$_NOT_ %% %n t:* %i + + +# Convert everything to ALDFFEs. + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 0 + +select -assert-count 1 t:$_NOT_ +select -assert-count 2 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ %% %n t:* %i + +design -load orig +dfflegalize -cell $_ALDFFE_PPP_ 1 + +select -assert-count 5 t:$_NOT_ +select -assert-count 2 t:$_ALDFFE_PPP_ +select -assert-none t:$_ALDFFE_PPP_ t:$_NOT_ %% %n t:* %i diff --git a/tests/techmap/dfflegalize_dlatchsr_init.ys b/tests/techmap/dfflegalize_dlatchsr_init.ys index 2d33634d1..b38a9eb3b 100644 --- a/tests/techmap/dfflegalize_dlatchsr_init.ys +++ b/tests/techmap/dfflegalize_dlatchsr_init.ys @@ -66,8 +66,8 @@ select -assert-none t:$_DLATCH_PP0_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_O design -load orig dfflegalize -cell $_DLATCH_PP1_ 0 -select -assert-count 22 dlatchsr0/t:$_NOT_ -select -assert-count 26 dlatchsr1/t:$_NOT_ +select -assert-count 18 dlatchsr0/t:$_NOT_ +select -assert-count 22 dlatchsr1/t:$_NOT_ select -assert-count 4 dlatchsr0/t:$_MUX_ select -assert-count 4 dlatchsr1/t:$_MUX_ select -assert-count 12 dlatchsr0/t:$_DLATCH_PP1_ @@ -81,8 +81,8 @@ select -assert-none t:$_DLATCH_PP1_ t:$_MUX_ t:$_NOT_ t:$_AND_ t:$_ANDNOT_ t:$_O design -load orig dfflegalize -cell $_DLATCH_PP1_ 1 -select -assert-count 22 dlatchsr0/t:$_NOT_ -select -assert-count 26 dlatchsr1/t:$_NOT_ +select -assert-count 18 dlatchsr0/t:$_NOT_ +select -assert-count 22 dlatchsr1/t:$_NOT_ select -assert-count 4 dlatchsr0/t:$_MUX_ select -assert-count 4 dlatchsr1/t:$_MUX_ select -assert-count 12 dlatchsr0/t:$_DLATCH_PP1_ diff --git a/tests/techmap/dfflegalize_inv.ys b/tests/techmap/dfflegalize_inv.ys index cb42e01a8..a74d74161 100644 --- a/tests/techmap/dfflegalize_inv.ys +++ b/tests/techmap/dfflegalize_inv.ys @@ -2,7 +2,7 @@ read_verilog -icells <<EOT -module top(input C, E, R, S, D, output [64:0] Q); +module top(input C, E, R, S, D, L, AD, output [71:0] Q); $_DFF_P_ ff0 (.C(C), .D(D), .Q(Q[0])); $_DFF_N_ ff1 (.C(C), .D(D), .Q(Q[1])); @@ -88,16 +88,25 @@ $_SR_PP_ ff62 (.R(R), .S(S), .Q(Q[62])); $_SR_PN_ ff63 (.R(R), .S(S), .Q(Q[63])); $_SR_NP_ ff64 (.R(R), .S(S), .Q(Q[64])); +$_ALDFF_PP_ ff65 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[65])); +$_ALDFF_PN_ ff66 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[66])); +$_ALDFF_NP_ ff67 (.C(C), .L(L), .AD(AD), .D(D), .Q(Q[67])); + +$_ALDFFE_PPP_ ff68 (.C(C), .L(L), .AD(AD), .D(D), .E(E), .Q(Q[68])); +$_ALDFFE_PPN_ ff69 (.C(C), .L(L), .AD(AD), .D(D), .E(E), .Q(Q[69])); +$_ALDFFE_PNP_ ff70 (.C(C), .L(L), .AD(AD), .D(D), .E(E), .Q(Q[70])); +$_ALDFFE_NPP_ ff71 (.C(C), .L(L), .AD(AD), .D(D), .E(E), .Q(Q[71])); + endmodule EOT design -save orig -equiv_opt -assert -multiclock dfflegalize -cell $_DFF_P_ x -cell $_DFFE_PP_ x -cell $_DFF_PP?_ x -cell $_DFFE_PP?P_ x -cell $_DFFSR_PPP_ x -cell $_DFFSRE_PPPP_ x -cell $_SDFF_PP?_ x -cell $_SDFFE_PP?P_ x -cell $_SDFFCE_PP?P_ x -cell $_DLATCH_P_ x -cell $_DLATCH_PP?_ x -cell $_DLATCHSR_PPP_ x -cell $_SR_PP_ x +equiv_opt -assert -multiclock dfflegalize -cell $_DFF_P_ x -cell $_DFFE_PP_ x -cell $_DFF_PP?_ x -cell $_DFFE_PP?P_ x -cell $_DFFSR_PPP_ x -cell $_DFFSRE_PPPP_ x -cell $_SDFF_PP?_ x -cell $_SDFFE_PP?P_ x -cell $_SDFFCE_PP?P_ x -cell $_DLATCH_P_ x -cell $_DLATCH_PP?_ x -cell $_DLATCHSR_PPP_ x -cell $_SR_PP_ x -cell $_ALDFF_PP_ x -cell $_ALDFFE_PPP_ x design -load postopt -select -assert-count 46 t:$_NOT_ +select -assert-count 51 t:$_NOT_ select -assert-count 2 t:$_DFF_P_ select -assert-count 3 t:$_DFFE_PP_ select -assert-count 3 t:$_DFF_PP0_ @@ -117,16 +126,18 @@ select -assert-count 3 t:$_DLATCH_PP0_ select -assert-count 3 t:$_DLATCH_PP1_ select -assert-count 4 t:$_DLATCHSR_PPP_ select -assert-count 3 t:$_SR_PP_ -select -assert-none t:$_DFF_P_ t:$_DFFE_PP_ t:$_DFF_PP?_ t:$_DFFE_PP?P_ t:$_DFFSR_PPP_ t:$_DFFSRE_PPPP_ t:$_SDFF_PP?_ t:$_SDFFE_PP?P_ t:$_SDFFCE_PP?P_ t:$_DLATCH_P_ t:$_DLATCH_PP?_ t:$_DLATCHSR_PPP_ t:$_SR_PP_ t:$_NOT_ %% %n t:* %i +select -assert-count 3 t:$_ALDFF_PP_ +select -assert-count 4 t:$_ALDFFE_PPP_ +select -assert-none t:$_DFF_P_ t:$_DFFE_PP_ t:$_DFF_PP?_ t:$_DFFE_PP?P_ t:$_DFFSR_PPP_ t:$_DFFSRE_PPPP_ t:$_SDFF_PP?_ t:$_SDFFE_PP?P_ t:$_SDFFCE_PP?P_ t:$_DLATCH_P_ t:$_DLATCH_PP?_ t:$_DLATCHSR_PPP_ t:$_SR_PP_ t:$_ALDFF_PP_ t:$_ALDFFE_PPP_ t:$_NOT_ %% %n t:* %i # Now try it again, targetting the opposite cells. design -load orig -equiv_opt -assert -multiclock dfflegalize -cell $_DFF_N_ x -cell $_DFFE_NN_ x -cell $_DFF_NN?_ x -cell $_DFFE_NN?N_ x -cell $_DFFSR_NNN_ x -cell $_DFFSRE_NNNN_ x -cell $_SDFF_NN?_ x -cell $_SDFFE_NN?N_ x -cell $_SDFFCE_NN?N_ x -cell $_DLATCH_N_ x -cell $_DLATCH_NN?_ x -cell $_DLATCHSR_NNN_ x -cell $_SR_NN_ x +equiv_opt -assert -multiclock dfflegalize -cell $_DFF_N_ x -cell $_DFFE_NN_ x -cell $_DFF_NN?_ x -cell $_DFFE_NN?N_ x -cell $_DFFSR_NNN_ x -cell $_DFFSRE_NNNN_ x -cell $_SDFF_NN?_ x -cell $_SDFFE_NN?N_ x -cell $_SDFFCE_NN?N_ x -cell $_DLATCH_N_ x -cell $_DLATCH_NN?_ x -cell $_DLATCHSR_NNN_ x -cell $_SR_NN_ x -cell $_ALDFF_NN_ x -cell $_ALDFFE_NNN_ x design -load postopt -select -assert-count 122 t:$_NOT_ +select -assert-count 135 t:$_NOT_ select -assert-count 2 t:$_DFF_N_ select -assert-count 3 t:$_DFFE_NN_ select -assert-count 3 t:$_DFF_NN0_ @@ -146,7 +157,9 @@ select -assert-count 3 t:$_DLATCH_NN0_ select -assert-count 3 t:$_DLATCH_NN1_ select -assert-count 4 t:$_DLATCHSR_NNN_ select -assert-count 3 t:$_SR_NN_ -select -assert-none t:$_DFF_N_ t:$_DFFE_NN_ t:$_DFF_NN?_ t:$_DFFE_NN?N_ t:$_DFFSR_NNN_ t:$_DFFSRE_NNNN_ t:$_SDFF_NN?_ t:$_SDFFE_NN?N_ t:$_SDFFCE_NN?N_ t:$_DLATCH_N_ t:$_DLATCH_NN?_ t:$_DLATCHSR_NNN_ t:$_SR_NN_ t:$_NOT_ %% %n t:* %i +select -assert-count 3 t:$_ALDFF_NN_ +select -assert-count 4 t:$_ALDFFE_NNN_ +select -assert-none t:$_DFF_N_ t:$_DFFE_NN_ t:$_DFF_NN?_ t:$_DFFE_NN?N_ t:$_DFFSR_NNN_ t:$_DFFSRE_NNNN_ t:$_SDFF_NN?_ t:$_SDFFE_NN?N_ t:$_SDFFCE_NN?N_ t:$_DLATCH_N_ t:$_DLATCH_NN?_ t:$_DLATCHSR_NNN_ t:$_SR_NN_ t:$_ALDFF_NN_ t:$_ALDFFE_NNN_ t:$_NOT_ %% %n t:* %i # Second test: make sure set/reset/enable are inverted before clock. diff --git a/tests/techmap/dfflegalize_minsrst.ys b/tests/techmap/dfflegalize_minsrst.ys index 0fc40dc08..689066147 100644 --- a/tests/techmap/dfflegalize_minsrst.ys +++ b/tests/techmap/dfflegalize_minsrst.ys @@ -23,9 +23,9 @@ design -load postopt select -assert-count 5 t:$_SDFF_PP0_ select -assert-count 1 t:$_SDFF_PP1_ -select -assert-count 3 t:$_SDFFE_PP0P_ +select -assert-count 1 t:$_SDFFE_PP0P_ select -assert-count 1 t:$_SDFFE_PP1P_ -select -assert-count 1 t:$_SDFFCE_PP0P_ +select -assert-count 3 t:$_SDFFCE_PP0P_ select -assert-count 1 t:$_SDFFCE_PP1P_ select -assert-count 8 t:$_MUX_ select -assert-count 0 n:ff0 %ci %ci t:$_MUX_ %i diff --git a/tests/techmap/dfflegalize_sr.ys b/tests/techmap/dfflegalize_sr.ys index 27e83be91..ee59a6e3c 100644 --- a/tests/techmap/dfflegalize_sr.ys +++ b/tests/techmap/dfflegalize_sr.ys @@ -39,7 +39,7 @@ select -assert-none t:$_DLATCH_PP0_ t:$_NOT_ %% %n t:* %i design -load orig dfflegalize -cell $_DLATCH_PP1_ x -select -assert-count 8 t:$_NOT_ +select -assert-count 5 t:$_NOT_ select -assert-count 3 t:$_DLATCH_PP1_ select -assert-none t:$_DLATCH_PP1_ t:$_NOT_ %% %n t:* %i diff --git a/tests/techmap/dfflegalize_sr_init.ys b/tests/techmap/dfflegalize_sr_init.ys index 52b797b9e..9d724de29 100644 --- a/tests/techmap/dfflegalize_sr_init.ys +++ b/tests/techmap/dfflegalize_sr_init.ys @@ -12,7 +12,7 @@ $_SR_PN_ ff1 (.R(R), .S(S), .Q(Q[1])); $_SR_NP_ ff2 (.R(R), .S(S), .Q(Q[2])); endmodule -module top(input C, E, R, D, output [5:0] Q); +module top(input R, S, output [5:0] Q); sr0 sr0_(.S(S), .R(R), .Q(Q[2:0])); sr1 sr1_(.S(S), .R(R), .Q(Q[5:3])); endmodule @@ -103,8 +103,8 @@ select -assert-none t:$_DLATCH_PP0_ t:$_NOT_ t:$_ANDNOT_ t:$_OR_ t:$_AND_ top/* design -load orig dfflegalize -cell $_DLATCH_PP1_ 0 -select -assert-count 11 sr0/t:$_NOT_ -select -assert-count 8 sr1/t:$_NOT_ +select -assert-count 8 sr0/t:$_NOT_ +select -assert-count 5 sr1/t:$_NOT_ select -assert-count 3 sr0/t:$_DLATCH_PP1_ select -assert-count 3 sr1/t:$_DLATCH_PP1_ select -assert-count 1 sr0/t:$_ANDNOT_ @@ -118,8 +118,8 @@ select -assert-none t:$_DLATCH_PP1_ t:$_NOT_ t:$_ANDNOT_ t:$_OR_ t:$_AND_ top/* design -load orig dfflegalize -cell $_DLATCH_PP1_ 1 -select -assert-count 8 sr0/t:$_NOT_ -select -assert-count 11 sr1/t:$_NOT_ +select -assert-count 5 sr0/t:$_NOT_ +select -assert-count 8 sr1/t:$_NOT_ select -assert-count 3 sr0/t:$_DLATCH_PP1_ select -assert-count 3 sr1/t:$_DLATCH_PP1_ select -assert-count 0 sr0/t:$_ANDNOT_ diff --git a/tests/techmap/mem_simple_4x1_runtest.sh b/tests/techmap/mem_simple_4x1_runtest.sh index 9c41fa56a..5b5838b9d 100644 --- a/tests/techmap/mem_simple_4x1_runtest.sh +++ b/tests/techmap/mem_simple_4x1_runtest.sh @@ -1,17 +1,3 @@ #!/bin/bash -set -e - -../../yosys -b 'verilog -noattr' -o mem_simple_4x1_synth.v -p 'proc; opt; memory -nomap; techmap -map mem_simple_4x1_map.v;; techmap; opt; abc;; stat' mem_simple_4x1_uut.v - -iverilog -o mem_simple_4x1_gold_tb mem_simple_4x1_tb.v mem_simple_4x1_uut.v -iverilog -o mem_simple_4x1_gate_tb mem_simple_4x1_tb.v mem_simple_4x1_synth.v mem_simple_4x1_cells.v - -./mem_simple_4x1_gold_tb > mem_simple_4x1_gold_tb.out -./mem_simple_4x1_gate_tb > mem_simple_4x1_gate_tb.out - -diff -u mem_simple_4x1_gold_tb.out mem_simple_4x1_gate_tb.out -rm -f mem_simple_4x1_synth.v mem_simple_4x1_tb.vcd -rm -f mem_simple_4x1_{gold,gate}_tb{,.out} -: OK - +exec ../tools/autotest.sh -G -j $@ -p 'proc; opt; memory -nomap; techmap -map ../mem_simple_4x1_map.v;; techmap; opt; abc;; stat' mem_simple_4x1_uut.v diff --git a/tests/techmap/recursive_runtest.sh b/tests/techmap/recursive_runtest.sh index 0725ccf40..564d678fa 100644 --- a/tests/techmap/recursive_runtest.sh +++ b/tests/techmap/recursive_runtest.sh @@ -1,3 +1,3 @@ set -e -../../yosys -p 'hierarchy -top top; techmap -map recursive_map.v -max_iter 1; select -assert-count 2 t:sub; select -assert-count 2 t:bar' recursive.v +../../yosys -p 'read_verilog recursive.v; hierarchy -top top; techmap -map recursive_map.v -max_iter 1; select -assert-count 2 t:sub; select -assert-count 2 t:bar' diff --git a/tests/techmap/zinit.ys b/tests/techmap/zinit.ys index 1670573dd..bc07f40e6 100644 --- a/tests/techmap/zinit.ys +++ b/tests/techmap/zinit.ys @@ -20,7 +20,8 @@ EOT equiv_opt -assert -multiclock zinit design -load postopt -select -assert-count 20 t:$_NOT_ +select -assert-count 16 t:$_NOT_ +select -assert-count 4 t:$xor select -assert-count 1 w:unused a:init %i select -assert-count 1 w:Q a:init=13'bxxxx1xxxxxxxx %i select -assert-count 4 c:dff0 c:dff2 c:dff4 c:dff6 %% t:$_DFF_??1_ %i @@ -52,7 +53,7 @@ design -load postopt select -assert-count 0 t:$_NOT_ select -assert-count 1 w:unused a:init %i -select -assert-count 1 w:Q a:init=13'bxxxx1xxxxxxxx %i +select -assert-count 1 w:Q a:init=13'bx00x100000000 %i select -assert-count 4 c:dff0 c:dff2 c:dff4 c:dff6 %% t:$_DFF_??0_ %i select -assert-count 4 c:dff1 c:dff3 c:dff5 c:dff7 %% t:$_DFF_??1_ %i @@ -142,7 +143,7 @@ EOT zinit select -assert-count 0 t:$_NOT_ -select -assert-count 0 w:Q a:init %i +select -assert-count 1 w:Q a:init=24'b0 %i select -assert-count 4 c:dff0 c:dff2 c:dff4 c:dff6 %% t:$_DFFE_??0P_ %i select -assert-count 4 c:dff1 c:dff3 c:dff5 c:dff7 %% t:$_DFFE_??1P_ %i select -assert-count 4 c:dff8 c:dff10 c:dff12 c:dff14 %% t:$_SDFF_??0_ %i diff --git a/tests/tools/vcdcd.pl b/tests/tools/vcdcd.pl index 58a92b44d..0f33371fb 100755 --- a/tests/tools/vcdcd.pl +++ b/tests/tools/vcdcd.pl @@ -11,7 +11,7 @@ $| = 1; my $opt_width = 0; my $opt_delay = 0; -while (1) +while ($#ARGV >= 0) { if ($ARGV[0] eq '-w') { $opt_width = +$ARGV[1]; @@ -74,10 +74,10 @@ for my $net (sort keys %gold_signals_hash) { # next unless $net eq "tst_bench_top.i2c_top.byte_controller.bit_controller.cnt"; my %orig_net_names; print "common signal: $net"; - for my $fullname (keys $gold_signals_hash{$net}) { + for my $fullname (keys %{$gold_signals_hash{$net}}) { $orig_net_names{$fullname} = 1; } - for my $fullname (keys $gate_signals_hash{$net}) { + for my $fullname (keys %{$gate_signals_hash{$net}}) { $orig_net_names{$fullname} = 1; } for my $net (sort keys %orig_net_names) { diff --git a/tests/various/.gitignore b/tests/various/.gitignore index 2bb6c7179..c6373468a 100644 --- a/tests/various/.gitignore +++ b/tests/various/.gitignore @@ -5,3 +5,4 @@ /run-test.mk /plugin.so /plugin.so.dSYM +/temp diff --git a/tests/various/async.sh b/tests/various/async.sh index 7c41d6d94..e83935d02 100644 --- a/tests/various/async.sh +++ b/tests/various/async.sh @@ -1,9 +1,9 @@ #!/bin/bash set -ex -../../yosys -q -o async_syn.v -p 'synth; rename uut syn' async.v -../../yosys -q -o async_prp.v -p 'prep; rename uut prp' async.v -../../yosys -q -o async_a2s.v -p 'prep; async2sync; rename uut a2s' async.v -../../yosys -q -o async_ffl.v -p 'prep; clk2fflogic; rename uut ffl' async.v +../../yosys -q -o async_syn.v -r uut -p 'synth; rename uut syn' async.v +../../yosys -q -o async_prp.v -r uut -p 'prep; rename uut prp' async.v +../../yosys -q -o async_a2s.v -r uut -p 'prep; async2sync; rename uut a2s' async.v +../../yosys -q -o async_ffl.v -r uut -p 'prep; clk2fflogic; rename uut ffl' async.v iverilog -o async_sim -DTESTBENCH async.v async_???.v vvp -N async_sim > async.out tail async.out diff --git a/tests/various/json_escape_chars.ys b/tests/various/json_escape_chars.ys new file mode 100644 index 000000000..f118357c0 --- /dev/null +++ b/tests/various/json_escape_chars.ys @@ -0,0 +1,14 @@ +! mkdir -p temp +read_verilog <<EOT +(* src = "\042 \057 \134 \010 \014 \012 \015 \011 \025 \033" *) +module foo; +endmodule +EOT +write_json temp/test_escapes.json +design -reset +read_json temp/test_escapes.json +write_json temp/test_escapes.json +design -reset +read_json temp/test_escapes.json +write_rtlil temp/test_escapes.json.il +! grep -F 'attribute \src "\" / \\ \010 \014 \n \015 \t \025 \033"' temp/test_escapes.json.il diff --git a/tests/various/logger_fail.sh b/tests/various/logger_fail.sh new file mode 100755 index 000000000..19b650007 --- /dev/null +++ b/tests/various/logger_fail.sh @@ -0,0 +1,42 @@ +#!/bin/bash + +fail() { + echo "$1" >&2 + exit 1 +} + +runTest() { + desc="$1" + want="$2" + shift 2 + echo "running '$desc' with args $@" + output=`../../yosys -q "$@" 2>&1` + if [ $? -ne 1 ]; then + fail "exit code for '$desc' was not 1" + fi + if [ "$output" != "$want" ]; then + fail "output for '$desc' did not match" + fi +} + +unmet() { + kind=$1 + runTest "unmet $kind" \ + "ERROR: Expected $kind pattern 'foobar' not found !" \ + -p "logger -expect $kind \"foobar\" 1" +} + +unmet log +unmet warning +unmet error + +runTest "too many logs" \ + "ERROR: Expected log pattern 'statistics' found 2 time(s), instead of 1 time(s) !" \ + -p "logger -expect log \"statistics\" 1" -p stat -p stat + +runTest "too many warnings" \ + "Warning: Found log message matching -W regex: +Printing statistics. +ERROR: Expected warning pattern 'statistics' found 2 time(s), instead of 1 time(s) !" \ + -p "logger -warn \"Printing statistics\"" \ + -p "logger -expect warning \"statistics\" 1" -p stat -p stat diff --git a/tests/various/param_struct.ys b/tests/various/param_struct.ys new file mode 100644 index 000000000..b8de67968 --- /dev/null +++ b/tests/various/param_struct.ys @@ -0,0 +1,50 @@ +read_verilog -sv << EOF +package p; +typedef struct packed { + logic a; + logic b; +} struct_t; + +typedef struct packed { + struct_t g; + logic [2:0] h; +} nested_struct_t; + +typedef union packed { + logic [4:0] x; +} nested_union_t; + +parameter struct_t c = {1'b1, 1'b0}; +parameter nested_struct_t x = {{1'b1, 1'b0}, 1'b1, 1'b1, 1'b1}; +endpackage + +module dut (); +parameter p::struct_t d = p::c; +parameter p::nested_struct_t i = p::x; + +parameter p::nested_union_t u = {5'b11001}; + +localparam e = d.a; +localparam f = d.b; + +localparam j = i.g.a; +localparam k = i.g.b; +localparam l = i.h; +localparam m = i.g; + +localparam o = u.x; + +always_comb begin + assert(d == 2'b10); + assert(e == 1'b1); + assert(f == 1'b0); + assert(j == 1'b1); + assert(k == 1'b0); + assert(l == 3'b111); + assert(m == 2'b10); + assert(u == 5'b11001); +end +endmodule +EOF +hierarchy; proc; opt +sat -verify -seq 1 -tempinduct -prove-asserts -show-all diff --git a/tests/various/sta.ys b/tests/various/sta.ys new file mode 100644 index 000000000..156c31c47 --- /dev/null +++ b/tests/various/sta.ys @@ -0,0 +1,81 @@ +read_verilog -specify <<EOT +module buffer(input i, output o); +specify +(i => o) = 10; +endspecify +endmodule + +module top(input i); +wire w; +buffer b(.i(i), .o(w)); +endmodule +EOT + +logger -expect warning "Critical-path does not terminate in a recognised endpoint\." 1 +sta + + +design -reset +read_verilog -specify <<EOT +module top(input i, output o, p); +assign o = i; +endmodule +EOT + +logger -expect log "No timing paths found\." 1 +sta + + +design -reset +read_verilog -specify <<EOT +module buffer(input i, output o); +specify +(i => o) = 10; +endspecify +endmodule + +module top(input i, output o, p); +buffer b(.i(i), .o(o)); +endmodule +EOT + +sta + + +design -reset +read_verilog -specify <<EOT +module buffer(input i, output o); +specify +(i => o) = 10; +endspecify +endmodule + +module top(input i, output o, p); +buffer b(.i(i), .o(o)); +const0 c(.o(p)); +endmodule +EOT + +logger -expect warning "Cell type 'const0' not recognised! Ignoring\." 1 +sta + + +design -reset +read_verilog -specify <<EOT +module buffer(input i, output o); +specify +(i => o) = 10; +endspecify +endmodule +module const0(output o); +endmodule + +module top(input i, output o, p); +buffer b(.i(i), .o(o)); +const0 c(.o(p)); +endmodule +EOT + +sta + +logger -expect-no-warnings diff --git a/tests/various/struct_access.sv b/tests/various/struct_access.sv new file mode 100644 index 000000000..d41a7114f --- /dev/null +++ b/tests/various/struct_access.sv @@ -0,0 +1,43 @@ +module dut(); +typedef struct packed { + logic a; + logic b; +} sub_sub_struct_t; + +typedef struct packed { + sub_sub_struct_t c; +} sub_struct_t; + +typedef struct packed { + sub_struct_t d; + sub_struct_t e; +} struct_t; + +parameter struct_t P = 4'b1100; + +localparam sub_struct_t f = P.d; +localparam sub_struct_t g = P.e; +localparam sub_sub_struct_t h = f.c; +localparam logic i = P.d.c.a; +localparam logic j = P.d.c.b; +localparam x = P.e; +localparam y = x.c; +localparam z = y.a; +localparam q = P.d; +localparam n = q.c.a; + +always_comb begin + assert(P == 4'b1100); + assert(f == 2'b11); + assert(g == 2'b00); + assert(h == 2'b11); + assert(i == 1'b1); + assert(j == 1'b1); + assert(x == 2'b00); + assert(y == 2'b00); + assert(x.c == 2'b00); + assert(y.b == 1'b0); + assert(n == 1'b1); + assert(z == 1'b0); +end +endmodule diff --git a/tests/various/struct_access.ys b/tests/various/struct_access.ys new file mode 100644 index 000000000..2282edd92 --- /dev/null +++ b/tests/various/struct_access.ys @@ -0,0 +1,5 @@ +read_verilog -sv struct_access.sv +hierarchy +proc +opt +sat -verify -seq 1 -prove-asserts -show-all diff --git a/tests/verilog/.gitignore b/tests/verilog/.gitignore index 34da23437..96ebe20ba 100644 --- a/tests/verilog/.gitignore +++ b/tests/verilog/.gitignore @@ -3,3 +3,4 @@ /run-test.mk /const_arst.v /const_sr.v +/doubleslash.v diff --git a/tests/verilog/always_comb_latch_1.ys b/tests/verilog/always_comb_latch_1.ys new file mode 100644 index 000000000..c98c79fa2 --- /dev/null +++ b/tests/verilog/always_comb_latch_1.ys @@ -0,0 +1,13 @@ +read_verilog -sv <<EOF +module top; +logic x; +always_comb begin + logic y; + if (x) + y = 1; + x = y; +end +endmodule +EOF +logger -expect error "^Latch inferred for signal `\\top\.\$unnamed_block\$1\.y' from always_comb process" 1 +proc diff --git a/tests/verilog/always_comb_latch_2.ys b/tests/verilog/always_comb_latch_2.ys new file mode 100644 index 000000000..567205a53 --- /dev/null +++ b/tests/verilog/always_comb_latch_2.ys @@ -0,0 +1,15 @@ +read_verilog -sv <<EOF +module top; +logic x; +always_comb begin + logic y; + if (x) + x = 1; + else + y = 1; + x = y; +end +endmodule +EOF +logger -expect error "^Latch inferred for signal `\\top\.\$unnamed_block\$1\.y' from always_comb process" 1 +proc diff --git a/tests/verilog/always_comb_latch_3.ys b/tests/verilog/always_comb_latch_3.ys new file mode 100644 index 000000000..b9b028ac7 --- /dev/null +++ b/tests/verilog/always_comb_latch_3.ys @@ -0,0 +1,20 @@ +read_verilog -sv <<EOF +module top; +logic x; +logic z; +assign z = 1'b1; +always_comb begin + logic y; + case (x) + 1'b0: + y = 1; + endcase + if (z) + x = y; + else + x = 1'b0; +end +endmodule +EOF +logger -expect error "^Latch inferred for signal `\\top\.\$unnamed_block\$1\.y' from always_comb process" 1 +proc diff --git a/tests/verilog/always_comb_latch_4.ys b/tests/verilog/always_comb_latch_4.ys new file mode 100644 index 000000000..46b78801b --- /dev/null +++ b/tests/verilog/always_comb_latch_4.ys @@ -0,0 +1,17 @@ +read_verilog -sv <<EOF +module top; +parameter AVOID_LATCH = 0; +logic x, z; +assign z = 1'b1; +always_comb begin + logic y; + if (z) + y = 0; + for (int i = 1; i == AVOID_LATCH; i++) + y = 1; + x = z ? y : 1'b0; +end +endmodule +EOF +logger -expect error "^Latch inferred for signal `\\top\.\$unnamed_block\$3\.y' from always_comb process" 1 +proc diff --git a/tests/verilog/always_comb_nolatch_1.ys b/tests/verilog/always_comb_nolatch_1.ys new file mode 100644 index 000000000..4d1952b52 --- /dev/null +++ b/tests/verilog/always_comb_nolatch_1.ys @@ -0,0 +1,16 @@ +read_verilog -sv <<EOF +module top; +logic [4:0] x; +logic z; +assign z = 1'b1; +always_comb begin + x = '0; + if (z) begin + for (int i = 0; i < 5; i++) begin + x[i] = 1'b1; + end + end +end +endmodule +EOF +proc diff --git a/tests/verilog/always_comb_nolatch_2.ys b/tests/verilog/always_comb_nolatch_2.ys new file mode 100644 index 000000000..2ec6ca0f4 --- /dev/null +++ b/tests/verilog/always_comb_nolatch_2.ys @@ -0,0 +1,17 @@ +read_verilog -sv <<EOF +module top; +logic [4:0] x; +logic z; +assign z = 1'b1; +always_comb begin + x = '0; + if (z) begin + int i; + for (i = 0; i < 5; i++) begin + x[i] = 1'b1; + end + end +end +endmodule +EOF +proc diff --git a/tests/verilog/always_comb_nolatch_3.ys b/tests/verilog/always_comb_nolatch_3.ys new file mode 100644 index 000000000..33f9833a2 --- /dev/null +++ b/tests/verilog/always_comb_nolatch_3.ys @@ -0,0 +1,21 @@ +read_verilog -sv <<EOF +module top; +logic x; +logic z; +assign z = 1'b1; +always_comb begin + logic y; + case (x) + 1'b0: + y = 1; + default: + y = 0; + endcase + if (z) + x = y; + else + x = 1'b0; +end +endmodule +EOF +proc diff --git a/tests/verilog/always_comb_nolatch_4.ys b/tests/verilog/always_comb_nolatch_4.ys new file mode 100644 index 000000000..bc29b2771 --- /dev/null +++ b/tests/verilog/always_comb_nolatch_4.ys @@ -0,0 +1,16 @@ +read_verilog -sv <<EOF +module top; +parameter AVOID_LATCH = 1; +logic x, z; +assign z = 1'b1; +always_comb begin + logic y; + if (z) + y = 0; + for (int i = 1; i == AVOID_LATCH; i++) + y = 1; + x = z ? y : 1'b0; +end +endmodule +EOF +proc diff --git a/tests/verilog/always_comb_nolatch_5.ys b/tests/verilog/always_comb_nolatch_5.ys new file mode 100644 index 000000000..132878626 --- /dev/null +++ b/tests/verilog/always_comb_nolatch_5.ys @@ -0,0 +1,15 @@ +read_verilog -sv <<EOF +module top; +logic [4:0] x; +logic z; +assign z = 1'b1; +always_comb begin : foo + x = '0; + if (z) begin : bar + for (int i = 0; i < 5; i++) + x[i] = 1'b1; + end +end +endmodule +EOF +proc diff --git a/tests/verilog/always_comb_nolatch_6.ys b/tests/verilog/always_comb_nolatch_6.ys new file mode 100644 index 000000000..90ee78a68 --- /dev/null +++ b/tests/verilog/always_comb_nolatch_6.ys @@ -0,0 +1,15 @@ +read_verilog -sv <<EOF +module top(input wire x, y, output reg z); +function automatic f; + input inp; + for (int i = 0; i < 1; i++) + f = inp + 0; +endfunction +always_comb + if (y) + z = f(x); + else + z = 0; +endmodule +EOF +proc diff --git a/tests/verilog/delay_time_scale.ys b/tests/verilog/delay_time_scale.ys new file mode 100644 index 000000000..f45ba7b26 --- /dev/null +++ b/tests/verilog/delay_time_scale.ys @@ -0,0 +1,25 @@ +logger -expect-no-warnings +read_verilog -sv <<EOT +module top; +wand x; +`define TEST(time_scale) if (1) assign #time_scale x = 1; + +`TEST(1s) +`TEST(1ms) +`TEST(1us) +`TEST(1ns) +`TEST(1ps) +`TEST(1fs) + +`TEST((1s)) +`TEST(( 1s)) +`TEST((1s )) +`TEST(( 1s )) + +`TEST(1.0s) +`TEST(1.1s) +`TEST(1.0e-1s) +`TEST(1e-1s) + +endmodule +EOT diff --git a/tests/verilog/doubleslash.ys b/tests/verilog/doubleslash.ys new file mode 100644 index 000000000..c41673ee5 --- /dev/null +++ b/tests/verilog/doubleslash.ys @@ -0,0 +1,21 @@ +read_verilog -sv <<EOT +module doubleslash + (input logic a, + input logic b, + output logic z); + + logic \a//b ; + + assign \a//b = a & b; + assign z = ~\a//b ; + +endmodule : doubleslash +EOT + +hierarchy +proc +opt -full + +write_verilog doubleslash.v +design -reset +read_verilog doubleslash.v diff --git a/tests/verilog/dynamic_range_lhs.sh b/tests/verilog/dynamic_range_lhs.sh new file mode 100755 index 000000000..618204aed --- /dev/null +++ b/tests/verilog/dynamic_range_lhs.sh @@ -0,0 +1,32 @@ +#!/bin/bash + +run() { + alt=$1 + span=$2 + left=$3 + right=$4 + echo "a=$alt s=$span l=$left r=$right" + + ../../yosys -q \ + -DALT=$alt \ + -DSPAN=$span \ + -DLEFT=$left \ + -DRIGHT=$right \ + -p "read_verilog dynamic_range_lhs.v" \ + -p "proc" \ + -p "equiv_make gold gate equiv" \ + -p "equiv_simple" \ + -p "equiv_status -assert" +} + +trap 'echo "ERROR in dynamic_range_lhs.sh span=$span left=$left right=$right" >&2; exit 1' ERR + +for alt in `seq 0 1`; do +for span in `seq 1 4`; do +for left in `seq -4 4`; do +for right in `seq $(expr $left + -3) $(expr $left + 3)`; do + run $alt $span $left $right +done +done +done +done diff --git a/tests/verilog/dynamic_range_lhs.v b/tests/verilog/dynamic_range_lhs.v new file mode 100644 index 000000000..ae291374d --- /dev/null +++ b/tests/verilog/dynamic_range_lhs.v @@ -0,0 +1,76 @@ +module gate( + output reg [`LEFT:`RIGHT] out_u, out_s, + (* nowrshmsk = `ALT *) + input wire data, + input wire [1:0] sel1, sel2 +); +always @* begin + out_u = 0; + out_s = 0; + case (`SPAN) + 1: begin + out_u[sel1*sel2] = data; + out_s[$signed(sel1*sel2)] = data; + end + 2: begin + out_u[sel1*sel2+:2] = {data, data}; + out_s[$signed(sel1*sel2)+:2] = {data, data}; + end + 3: begin + out_u[sel1*sel2+:3] = {data, data, data}; + out_s[$signed(sel1*sel2)+:3] = {data, data, data}; + end + 4: begin + out_u[sel1*sel2+:4] = {data, data, data, data}; + out_s[$signed(sel1*sel2)+:4] = {data, data, data, data}; + end + endcase +end +endmodule + +module gold( + output reg [`LEFT:`RIGHT] out_u, out_s, + input wire data, + input wire [1:0] sel1, sel2 +); +task set; + input integer a, b; + localparam LOW = `LEFT > `RIGHT ? `RIGHT : `LEFT; + localparam HIGH = `LEFT > `RIGHT ? `LEFT : `RIGHT; + if (LOW <= a && a <= HIGH) + out_u[a] = data; + if (LOW <= b && b <= HIGH) + out_s[b] = data; +endtask +always @* begin + out_u = 0; + out_s = 0; + case (sel1*sel2) + 2'b00: set(0, 0); + 2'b01: set(1, 1); + 2'b10: set(2, -2); + 2'b11: set(3, -1); + endcase + if (`SPAN >= 2) + case (sel1*sel2) + 2'b00: set(1, 1); + 2'b01: set(2, 2); + 2'b10: set(3, -1); + 2'b11: set(4, 0); + endcase + if (`SPAN >= 3) + case (sel1*sel2) + 2'b00: set(2, 2); + 2'b01: set(3, 3); + 2'b10: set(4, 0); + 2'b11: set(5, 1); + endcase + if (`SPAN >= 4) + case (sel1*sel2) + 2'b00: set(3, 3); + 2'b01: set(4, 4); + 2'b10: set(5, 1); + 2'b11: set(6, 2); + endcase +end +endmodule diff --git a/tests/verilog/func_upto.sv b/tests/verilog/func_upto.sv new file mode 100644 index 000000000..547e5d325 --- /dev/null +++ b/tests/verilog/func_upto.sv @@ -0,0 +1,77 @@ +`default_nettype none + +module evil; + parameter HI = 3; + parameter LO = 0; + parameter SPAN = 1; + parameter [HI:LO] A_VAL = 4'b0110; + parameter [HI:LO] B_VAL = 4'b1100; + parameter [2:0] SWAPS = 0; + + localparam D_LEFT = !(SWAPS[0]) ? HI : LO; + localparam D_RIGHT = (SWAPS[0]) ? HI : LO; + localparam E_LEFT = !(SWAPS[1]) ? HI : LO; + localparam E_RIGHT = (SWAPS[1]) ? HI : LO; + localparam F_LEFT = !(SWAPS[2]) ? HI : LO; + localparam F_RIGHT = (SWAPS[2]) ? HI : LO; + + localparam [HI:LO] A_CONST = A_VAL; + localparam [HI:LO] B_CONST = B_VAL; + localparam [HI:LO] C_CONST = F(A_CONST, B_CONST); + + reg [HI:LO] C_WIRE, C_FUNC; + always @* begin + assert (C_CONST == C_WIRE); + assert (C_CONST == C_FUNC); + end + + initial begin : blk + reg [HI:LO] A_WIRE; + reg [HI:LO] B_WIRE; + reg [D_LEFT:D_RIGHT] D; + reg [E_LEFT:E_RIGHT] E; + reg [F_LEFT:F_RIGHT] F_WIRE; + reg [31:0] i; + A_WIRE = A_VAL; + B_WIRE = B_VAL; + D = A_WIRE; + E = B_WIRE; + F_WIRE = 0; + for (i = LO; i + SPAN < HI; i = i + SPAN) + if (SPAN == 1) + F_WIRE[i] = D[i] && E[i]; + else + F_WIRE[i+:SPAN] = D[i+:SPAN] && E[i+:SPAN]; + C_WIRE = F_WIRE; + C_FUNC = F(A_WIRE, B_WIRE); + end + + function automatic [F_LEFT:F_RIGHT] F( + input [D_LEFT:D_RIGHT] D, + input [E_LEFT:E_RIGHT] E); + reg [31:0] i; + F = 0; + for (i = LO; i + SPAN < HI; i = i + SPAN) + if (SPAN == 1) + F[i] = D[i] && E[i]; + else + F[i+:SPAN] = D[i+:SPAN] && E[i+:SPAN]; + endfunction +endmodule + +module top; + for (genvar hi = 0; hi < 3; hi++) + for (genvar lo = 0; lo <= hi; lo++) + for (genvar span = 1; span <= hi - lo + 1; span++) + for (genvar a_val = 0; a_val < 2 ** (hi - lo + 1); a_val++) + for (genvar b_val = 0; b_val < 2 ** (hi - lo + 1); b_val++) + for (genvar swaps = 0; swaps < 2 ** 3; swaps++) + evil #( + .HI(hi), + .LO(lo), + .SPAN(span), + .A_VAL(a_val), + .B_VAL(b_val), + .SWAPS(swaps) + ) e(); +endmodule diff --git a/tests/verilog/func_upto.ys b/tests/verilog/func_upto.ys new file mode 100644 index 000000000..7a8c53506 --- /dev/null +++ b/tests/verilog/func_upto.ys @@ -0,0 +1,7 @@ +read_verilog -sv func_upto.sv +hierarchy -top top +proc +flatten +opt -full +select -module top +sat -verify -seq 1 -prove-asserts -enable_undef diff --git a/tests/verilog/net_types.sv b/tests/verilog/net_types.sv new file mode 100644 index 000000000..7226a7ee5 --- /dev/null +++ b/tests/verilog/net_types.sv @@ -0,0 +1,34 @@ +module top; + wire logic wire_logic_0; assign wire_logic_0 = 0; + wire logic wire_logic_1; assign wire_logic_1 = 1; + wand logic wand_logic_0; assign wand_logic_0 = 0; assign wand_logic_0 = 1; + wand logic wand_logic_1; assign wand_logic_1 = 1; assign wand_logic_1 = 1; + wor logic wor_logic_0; assign wor_logic_0 = 0; assign wor_logic_0 = 0; + wor logic wor_logic_1; assign wor_logic_1 = 1; assign wor_logic_1 = 0; + + wire integer wire_integer; assign wire_integer = 4'b1001; + wand integer wand_integer; assign wand_integer = 4'b1001; assign wand_integer = 4'b1010; + wor integer wor_integer; assign wor_integer = 4'b1001; assign wor_integer = 4'b1010; + + typedef logic [3:0] typename; + wire typename wire_typename; assign wire_typename = 4'b1001; + wand typename wand_typename; assign wand_typename = 4'b1001; assign wand_typename = 4'b1010; + wor typename wor_typename; assign wor_typename = 4'b1001; assign wor_typename = 4'b1010; + + always @* begin + assert (wire_logic_0 == 0); + assert (wire_logic_1 == 1); + assert (wand_logic_0 == 0); + assert (wand_logic_1 == 1); + assert (wor_logic_0 == 0); + assert (wor_logic_1 == 1); + + assert (wire_integer == 4'b1001); + assert (wand_integer == 4'b1000); + assert (wor_integer == 4'b1011); + + assert (wire_typename == 4'b1001); + assert (wand_typename == 4'b1000); + assert (wor_typename == 4'b1011); + end +endmodule diff --git a/tests/verilog/net_types.ys b/tests/verilog/net_types.ys new file mode 100644 index 000000000..9f75812ea --- /dev/null +++ b/tests/verilog/net_types.ys @@ -0,0 +1,5 @@ +read_verilog -sv net_types.sv +hierarchy +proc +opt -full +sat -verify -prove-asserts -show-all diff --git a/tests/verilog/past_signedness.ys b/tests/verilog/past_signedness.ys new file mode 100644 index 000000000..91f32328b --- /dev/null +++ b/tests/verilog/past_signedness.ys @@ -0,0 +1,35 @@ +logger -expect-no-warnings + +read_verilog -formal <<EOT +module top(input clk); + reg signed [3:0] value = -1; + reg ready = 0; + + always @(posedge clk) begin + if (ready) + assert ($past(value) == -1); + ready <= 1; + end +endmodule +EOT + +prep -top top +sim -n 3 -clock clk + +design -reset + +read_verilog -formal <<EOT +module top(input clk); + reg signed [3:0] value = -1; + reg ready = 0; + + always @(posedge clk) begin + if (ready) + assert ($past(value + 4'b0000) == 15); + ready <= 1; + end +endmodule +EOT + +prep -top top +sim -n 3 -clock clk diff --git a/tests/verilog/prefix.sv b/tests/verilog/prefix.sv new file mode 100644 index 000000000..2d7fbb134 --- /dev/null +++ b/tests/verilog/prefix.sv @@ -0,0 +1,95 @@ +module top; + genvar i, j; + if (1) begin : blk1 + integer a = 1; + for (i = 0; i < 2; i = i + 1) begin : blk2 + integer b = i; + for (j = 0; j < 2; j = j + 1) begin : blk3 + integer c = j; + localparam x = i; + localparam y = j; + always @* begin + assert (1 == a); + assert (1 == blk1.a); + assert (1 == top.blk1.a); + assert (i == b); + assert (i == blk2[i].b); + assert (i == blk1.blk2[i].b); + assert (i == top.blk1.blk2[i].b); + assert (i == blk2[x].b); + assert (i == blk1.blk2[x].b); + assert (i == top.blk1.blk2[x].b); + assert (j == c); + assert (j == blk3[j].c); + assert (j == blk2[x].blk3[j].c); + assert (j == blk1.blk2[x].blk3[j].c); + assert (j == top.blk1.blk2[x].blk3[j].c); + assert (j == c); + assert (j == blk3[y].c); + assert (j == blk2[x].blk3[y].c); + assert (j == blk1.blk2[x].blk3[y].c); + assert (j == top.blk1.blk2[x].blk3[y].c); + assert (j == top.blk1.blk2[x].blk3[y].c[0]); + assert (0 == top.blk1.blk2[x].blk3[y].c[1]); + assert (0 == top.blk1.blk2[x].blk3[y].c[j]); + end + end + always @* begin + assert (1 == a); + assert (1 == blk1.a); + assert (1 == top.blk1.a); + assert (i == b); + assert (i == blk2[i].b); + assert (i == blk1.blk2[i].b); + assert (i == top.blk1.blk2[i].b); + assert (0 == blk3[0].c); + assert (0 == blk2[i].blk3[0].c); + assert (0 == blk1.blk2[i].blk3[0].c); + assert (0 == top.blk1.blk2[i].blk3[0].c); + assert (1 == blk3[1].c); + assert (1 == blk2[i].blk3[1].c); + assert (1 == blk1.blk2[i].blk3[1].c); + assert (1 == top.blk1.blk2[i].blk3[1].c); + end + end + always @* begin + assert (1 == a); + assert (1 == blk1.a); + assert (1 == top.blk1.a); + assert (0 == blk2[0].b); + assert (0 == blk1.blk2[0].b); + assert (0 == top.blk1.blk2[0].b); + assert (1 == blk2[1].b); + assert (1 == blk1.blk2[1].b); + assert (1 == top.blk1.blk2[1].b); + assert (0 == blk2[0].blk3[0].c); + assert (0 == blk1.blk2[0].blk3[0].c); + assert (0 == top.blk1.blk2[0].blk3[0].c); + assert (1 == blk2[0].blk3[1].c); + assert (1 == blk1.blk2[0].blk3[1].c); + assert (1 == top.blk1.blk2[0].blk3[1].c); + assert (0 == blk2[1].blk3[0].c); + assert (0 == blk1.blk2[1].blk3[0].c); + assert (0 == top.blk1.blk2[1].blk3[0].c); + assert (1 == blk2[1].blk3[1].c); + assert (1 == blk1.blk2[1].blk3[1].c); + assert (1 == top.blk1.blk2[1].blk3[1].c); + end + end + always @* begin + assert (1 == blk1.a); + assert (1 == top.blk1.a); + assert (0 == blk1.blk2[0].b); + assert (0 == top.blk1.blk2[0].b); + assert (1 == blk1.blk2[1].b); + assert (1 == top.blk1.blk2[1].b); + assert (0 == blk1.blk2[0].blk3[0].c); + assert (0 == top.blk1.blk2[0].blk3[0].c); + assert (1 == blk1.blk2[0].blk3[1].c); + assert (1 == top.blk1.blk2[0].blk3[1].c); + assert (0 == blk1.blk2[1].blk3[0].c); + assert (0 == top.blk1.blk2[1].blk3[0].c); + assert (1 == blk1.blk2[1].blk3[1].c); + assert (1 == top.blk1.blk2[1].blk3[1].c); + end +endmodule diff --git a/tests/verilog/prefix.ys b/tests/verilog/prefix.ys new file mode 100644 index 000000000..ed3b3a111 --- /dev/null +++ b/tests/verilog/prefix.ys @@ -0,0 +1,5 @@ +read_verilog -sv prefix.sv +hierarchy +proc +select -module top +sat -verify -seq 1 -prove-asserts -show-all diff --git a/tests/verilog/size_cast.sv b/tests/verilog/size_cast.sv new file mode 100644 index 000000000..1636f8d70 --- /dev/null +++ b/tests/verilog/size_cast.sv @@ -0,0 +1,140 @@ +module top; + logic L1b0 = 0; + logic L1b1 = 1; + + logic signed L1sb0 = 0; + logic signed L1sb1 = 1; + + logic [1:0] L2b00 = 0; + logic [1:0] L2b01 = 1; + logic [1:0] L2b10 = 2; + logic [1:0] L2b11 = 3; + + logic signed [1:0] L2sb00 = 0; + logic signed [1:0] L2sb01 = 1; + logic signed [1:0] L2sb10 = 2; + logic signed [1:0] L2sb11 = 3; + + logic y = 1; + + always @* begin + + assert (1'(L1b0 ) == 1'b0); + assert (1'(L1b1 ) == 1'b1); + assert (1'(L1sb0 ) == 1'b0); + assert (1'(L1sb1 ) == 1'b1); + assert (1'(L2b00 ) == 1'b0); + assert (1'(L2b01 ) == 1'b1); + assert (1'(L2b10 ) == 1'b0); + assert (1'(L2b11 ) == 1'b1); + assert (1'(L2sb00) == 1'b0); + assert (1'(L2sb01) == 1'b1); + assert (1'(L2sb10) == 1'b0); + assert (1'(L2sb11) == 1'b1); + + assert (2'(L1b0 ) == 2'b00); + assert (2'(L1b1 ) == 2'b01); + assert (2'(L1sb0 ) == 2'b00); + assert (2'(L1sb1 ) == 2'b11); + assert (2'(L2b00 ) == 2'b00); + assert (2'(L2b01 ) == 2'b01); + assert (2'(L2b10 ) == 2'b10); + assert (2'(L2b11 ) == 2'b11); + assert (2'(L2sb00) == 2'b00); + assert (2'(L2sb01) == 2'b01); + assert (2'(L2sb10) == 2'b10); + assert (2'(L2sb11) == 2'b11); + + assert (3'(L1b0 ) == 3'b000); + assert (3'(L1b1 ) == 3'b001); + assert (3'(L1sb0 ) == 3'b000); + assert (3'(L1sb1 ) == 3'b111); + assert (3'(L2b00 ) == 3'b000); + assert (3'(L2b01 ) == 3'b001); + assert (3'(L2b10 ) == 3'b010); + assert (3'(L2b11 ) == 3'b011); + assert (3'(L2sb00) == 3'b000); + assert (3'(L2sb01) == 3'b001); + assert (3'(L2sb10) == 3'b110); + assert (3'(L2sb11) == 3'b111); + + assert (3'(L1b0 | '1) == 3'b111); + assert (3'(L1b1 | '1) == 3'b111); + assert (3'(L1sb0 | '1) == 3'b111); + assert (3'(L1sb1 | '1) == 3'b111); + assert (3'(L2b00 | '1) == 3'b111); + assert (3'(L2b01 | '1) == 3'b111); + assert (3'(L2b10 | '1) == 3'b111); + assert (3'(L2b11 | '1) == 3'b111); + assert (3'(L2sb00 | '1) == 3'b111); + assert (3'(L2sb01 | '1) == 3'b111); + assert (3'(L2sb10 | '1) == 3'b111); + assert (3'(L2sb11 | '1) == 3'b111); + + assert (3'(L1b0 | '0) == 3'b000); + assert (3'(L1b1 | '0) == 3'b001); + assert (3'(L1sb0 | '0) == 3'b000); + assert (3'(L1sb1 | '0) == 3'b001); + assert (3'(L2b00 | '0) == 3'b000); + assert (3'(L2b01 | '0) == 3'b001); + assert (3'(L2b10 | '0) == 3'b010); + assert (3'(L2b11 | '0) == 3'b011); + assert (3'(L2sb00 | '0) == 3'b000); + assert (3'(L2sb01 | '0) == 3'b001); + assert (3'(L2sb10 | '0) == 3'b010); + assert (3'(L2sb11 | '0) == 3'b011); + + assert (3'(y ? L1b0 : '1) == 3'b000); + assert (3'(y ? L1b1 : '1) == 3'b001); + assert (3'(y ? L1sb0 : '1) == 3'b000); + assert (3'(y ? L1sb1 : '1) == 3'b001); + assert (3'(y ? L2b00 : '1) == 3'b000); + assert (3'(y ? L2b01 : '1) == 3'b001); + assert (3'(y ? L2b10 : '1) == 3'b010); + assert (3'(y ? L2b11 : '1) == 3'b011); + assert (3'(y ? L2sb00 : '1) == 3'b000); + assert (3'(y ? L2sb01 : '1) == 3'b001); + assert (3'(y ? L2sb10 : '1) == 3'b010); + assert (3'(y ? L2sb11 : '1) == 3'b011); + + assert (3'(y ? L1b0 : '0) == 3'b000); + assert (3'(y ? L1b1 : '0) == 3'b001); + assert (3'(y ? L1sb0 : '0) == 3'b000); + assert (3'(y ? L1sb1 : '0) == 3'b001); + assert (3'(y ? L2b00 : '0) == 3'b000); + assert (3'(y ? L2b01 : '0) == 3'b001); + assert (3'(y ? L2b10 : '0) == 3'b010); + assert (3'(y ? L2b11 : '0) == 3'b011); + assert (3'(y ? L2sb00 : '0) == 3'b000); + assert (3'(y ? L2sb01 : '0) == 3'b001); + assert (3'(y ? L2sb10 : '0) == 3'b010); + assert (3'(y ? L2sb11 : '0) == 3'b011); + + assert (3'(y ? L1b0 : 1'sb0) == 3'b000); + assert (3'(y ? L1b1 : 1'sb0) == 3'b001); + assert (3'(y ? L1sb0 : 1'sb0) == 3'b000); + assert (3'(y ? L1sb1 : 1'sb0) == 3'b111); + assert (3'(y ? L2b00 : 1'sb0) == 3'b000); + assert (3'(y ? L2b01 : 1'sb0) == 3'b001); + assert (3'(y ? L2b10 : 1'sb0) == 3'b010); + assert (3'(y ? L2b11 : 1'sb0) == 3'b011); + assert (3'(y ? L2sb00 : 1'sb0) == 3'b000); + assert (3'(y ? L2sb01 : 1'sb0) == 3'b001); + assert (3'(y ? L2sb10 : 1'sb0) == 3'b110); + assert (3'(y ? L2sb11 : 1'sb0) == 3'b111); + + assert (3'(y ? L1b0 : 1'sb1) == 3'b000); + assert (3'(y ? L1b1 : 1'sb1) == 3'b001); + assert (3'(y ? L1sb0 : 1'sb1) == 3'b000); + assert (3'(y ? L1sb1 : 1'sb1) == 3'b111); + assert (3'(y ? L2b00 : 1'sb1) == 3'b000); + assert (3'(y ? L2b01 : 1'sb1) == 3'b001); + assert (3'(y ? L2b10 : 1'sb1) == 3'b010); + assert (3'(y ? L2b11 : 1'sb1) == 3'b011); + assert (3'(y ? L2sb00 : 1'sb1) == 3'b000); + assert (3'(y ? L2sb01 : 1'sb1) == 3'b001); + assert (3'(y ? L2sb10 : 1'sb1) == 3'b110); + assert (3'(y ? L2sb11 : 1'sb1) == 3'b111); + + end +endmodule diff --git a/tests/verilog/size_cast.ys b/tests/verilog/size_cast.ys new file mode 100644 index 000000000..6890cd2d5 --- /dev/null +++ b/tests/verilog/size_cast.ys @@ -0,0 +1,5 @@ +read_verilog -sv size_cast.sv +proc +opt -full +select -module top +sat -verify -prove-asserts -show-all diff --git a/tests/verilog/struct_access.sv b/tests/verilog/struct_access.sv index f13b8dd51..bc91e3f01 100644 --- a/tests/verilog/struct_access.sv +++ b/tests/verilog/struct_access.sv @@ -77,9 +77,8 @@ module top; `CHECK(s.y.a, 1, 0) `CHECK(s.y.b, 1, 1) - // TODO(zachjs): support access to whole sub-structs and unions - // `CHECK(s.x, 2, 0) - // `CHECK(s.y, 2, 1) + `CHECK(s.x, 2, 0) + `CHECK(s.y, 2, 1) assert (fail === 0); end diff --git a/tests/verilog/unbased_unsized_tern.sv b/tests/verilog/unbased_unsized_tern.sv new file mode 100644 index 000000000..ad8493394 --- /dev/null +++ b/tests/verilog/unbased_unsized_tern.sv @@ -0,0 +1,31 @@ +module pass_through #( + parameter WIDTH = 1 +) ( + input logic [WIDTH-1:0] inp, + output logic [WIDTH-1:0] out +); + assign out = inp; +endmodule + +module gate ( + input logic inp, + output logic [63:0] + out1, out2, out3, out4 +); + pass_through #(40) pt1('1, out1); + pass_through #(40) pt2(inp ? '1 : '0, out2); + pass_through #(40) pt3(inp ? '1 : 2'b10, out3); + pass_through #(40) pt4(inp ? '1 : inp, out4); +endmodule + +module gold ( + input logic inp, + output logic [63:0] + out1, out2, out3, out4 +); + localparam ONES = 40'hFF_FFFF_FFFF; + pass_through #(40) pt1(ONES, out1); + pass_through #(40) pt2(inp ? ONES : 0, out2); + pass_through #(40) pt3(inp ? ONES : 2'sb10, out3); + pass_through #(40) pt4(inp ? ONES : inp, out4); +endmodule diff --git a/tests/verilog/unbased_unsized_tern.ys b/tests/verilog/unbased_unsized_tern.ys new file mode 100644 index 000000000..5ef63c559 --- /dev/null +++ b/tests/verilog/unbased_unsized_tern.ys @@ -0,0 +1,6 @@ +read_verilog -sv unbased_unsized_tern.sv +hierarchy +proc +equiv_make gold gate equiv +equiv_simple +equiv_status -assert diff --git a/tests/verilog/unreachable_case_sign.ys b/tests/verilog/unreachable_case_sign.ys new file mode 100644 index 000000000..25bc0c6f0 --- /dev/null +++ b/tests/verilog/unreachable_case_sign.ys @@ -0,0 +1,33 @@ +logger -expect-no-warnings + +read_verilog -formal <<EOT +module top(input clk); + reg good = 0; + + always @(posedge clk) begin + case (4'sb1111) 15: good = 1; 4'b0000: ; endcase + assert (good); + end +endmodule +EOT + +prep -top top +sim -n 3 -clock clk + +design -reset + +read_verilog -formal <<EOT +module top(input clk); + reg good = 1; + reg signed [1:0] case_value = -1; + + always @(posedge clk) begin + case (4'sb1111) 4'b0000: ; case_value: good = 0; endcase + assert (good); + end +endmodule +EOT + +prep -top top +sim -n 3 -clock clk + |