Testbench Code
`timescale 1ns/1ps
module tb_nb_blocking_order;
// 1) Inputs
reg clk;
reg b;
// 2) DUT outputs
wire c_block;
wire c_nblk;
// 3) Expected (prefixed expected_)
reg expected_c_block;
reg expected_c_nblk;
// 4) Mismatch (HIGH on fail)
wire mismatch_block = (c_block !== expected_c_block);
wire mismatch_nblk = (c_nblk !== expected_c_nblk);
wire mismatch = mismatch_block | mismatch_nblk;
// Counters
integer TOTAL_TEST_CASES = 0;
integer TOTAL_PASSED_TEST_CASES = 0;
integer TOTAL_FAILED_TEST_CASES = 0;
// VCD limit
integer VCD_MAX_CASES = 32;
// DUT
nb_blocking_order dut(.clk(clk), .b(b), .c_block(c_block), .c_nblk(c_nblk));
// VCD dump (Inputs -> Outputs -> Expected -> Mismatch)
initial begin
$dumpfile("tb_nb_blocking_order.vcd");
$dumpvars(0,
tb_nb_blocking_order.clk, tb_nb_blocking_order.b, // Inputs
tb_nb_blocking_order.c_block, tb_nb_blocking_order.c_nblk, // Outputs
tb_nb_blocking_order.expected_c_block, tb_nb_blocking_order.expected_c_nblk, // Expected
tb_nb_blocking_order.mismatch // Mismatch
);
$dumpon; // start at t=0
end
// Clock
localparam T = 10;
initial clk = 0;
always #(T/2) clk = ~clk;
// Keep a 1-cycle history of b for expected model
reg prev_b;
initial begin
b = 0; prev_b = 0;
expected_c_block = 0; expected_c_nblk = 0;
$display(" time | clk b | c_block c_nblk | exp_block exp_nblk | mismatch");
$display("---------------------------------------------------------------");
// apply 12 edges (≤ 20 printed rows overall)
drive_and_check(0);
drive_and_check(1);
drive_and_check(1);
drive_and_check(0);
drive_and_check(1);
drive_and_check(0);
drive_and_check(1);
drive_and_check(0);
drive_and_check(1);
drive_and_check(0);
drive_and_check(1);
drive_and_check(0);
$display("---------------------------------------------------------------");
$display("TOTAL_TEST_CASES=%0d", TOTAL_TEST_CASES);
$display("TOTAL_PASSED_TEST_CASES=%0d", TOTAL_PASSED_TEST_CASES);
$display("TOTAL_FAILED_TEST_CASES=%0d", TOTAL_FAILED_TEST_CASES);
$display("ALL_TEST_CASES_PASSED=%s",
(TOTAL_FAILED_TEST_CASES==0) ? "true" : "false");
#(T) $finish;
end
// Drive next b on negedge; check at following posedge
task drive_and_check;
input next_b;
begin
@(negedge clk);
b = next_b;
@(posedge clk);
// Compute expected FIRST at the sampling edge
expected_c_block = b; // blocking chain ⇒ current b
expected_c_nblk = prev_b; // NBA+blocking chain ⇒ previous b
prev_b = b; // update history for next edge
#1; // let DUT NBAs settle
TOTAL_TEST_CASES++;
if (!mismatch) TOTAL_PASSED_TEST_CASES++; else TOTAL_FAILED_TEST_CASES++;
$display("%4t | %0d %0d | %0d %0d | %0d %0d | %0d",
$time, clk, b, c_block, c_nblk,
expected_c_block, expected_c_nblk, mismatch);
if (TOTAL_TEST_CASES == VCD_MAX_CASES) $dumpoff;
end
endtask
endmodule