Files
reflectometer_fpga_project/rtl/sampler/tests/sampler_tb.sv
2026-06-10 17:07:40 +03:00

194 lines
4.4 KiB
Systemverilog

`timescale 1ns / 1ps
module sampler_tb;
localparam DATA_WIDTH = 12;
localparam PACK_FACTOR = 1;
localparam PROCESS_MODE = 0;
localparam CLK_PERIOD = 15.3846;
logic clk;
logic rst;
logic [DATA_WIDTH-1:0] data_in;
logic out_of_range;
logic [31:0] smp_num;
logic done;
logic request;
logic [DATA_WIDTH*PACK_FACTOR-1:0] m_axis_tdata;
logic m_axis_tvalid;
int received_count;
sampler #(
.DATA_WIDTH (DATA_WIDTH),
.PACK_FACTOR (PACK_FACTOR),
.PROCESS_MODE(PROCESS_MODE)
) dut (
.clk_in (clk),
.rst (rst),
.data_in (data_in),
.out_of_range (out_of_range),
.smp_num (smp_num),
.done (done),
.m_axis_tdata (m_axis_tdata),
.m_axis_tvalid(m_axis_tvalid),
.request (request)
);
// =====================================================
// CLOCK
// =====================================================
initial begin
clk = 0;
forever #(CLK_PERIOD/2) clk = ~clk;
end
// =====================================================
// RESET
// =====================================================
initial begin
rst = 1;
data_in = 0;
out_of_range = 0;
done = 0;
smp_num = 0;
repeat(5) @(posedge clk);
rst = 0;
end
// =====================================================
// OUTPUT COUNTER
// =====================================================
always @(posedge clk) begin
if (m_axis_tvalid)
received_count++;
end
// =====================================================
// FEED DATA
// =====================================================
task automatic feed_data_stream(
input int num_words,
input bit random_data,
input bit random_out_of_range
);
logic [DATA_WIDTH-1:0] value;
bit oor;
begin
value = 1;
for (int i = 0; i < num_words; i++) begin
if (random_data)
value = $urandom_range(1, (1<<DATA_WIDTH)-1);
else
value = value + 1;
if (random_out_of_range)
oor = ($urandom_range(0,3) == 0);
else
oor = 0;
data_in = value;
out_of_range = oor;
@(posedge clk);
end
out_of_range = 0;
end
endtask
// =====================================================
// TEST CASE
// =====================================================
task automatic run_test_case(
input int n,
input bit random_data,
input bit random_out_of_range
);
begin
received_count = 0;
data_in = 0;
out_of_range = 0;
done = 0;
smp_num = n;
// handshake
@(posedge clk);
done <= 1'b1;
wait(request == 1'b1);
@(posedge clk);
done <= 1'b0;
// wait enable
wait(dut.enable == 1'b1);
// feed data
feed_data_stream(n + 10, random_data, random_out_of_range);
// wait completion
wait(dut.enable == 1'b0);
$display("Expected smp_num=%0d Received=%0d", smp_num, received_count);
if (received_count == smp_num)
$display("[OK]");
else
$display("[ERROR]");
repeat(10) @(posedge clk);
end
endtask
// =====================================================
// RANDOM TESTS
// =====================================================
task automatic random_stress_test;
int n;
begin
for (int i = 0; i < 20; i++) begin
n = $urandom_range(5,20);
$display("\n--- TEST %0d --- n=%0d", i, n);
run_test_case(
n,
1,
1
);
end
end
endtask
// =====================================================
// MAIN
// =====================================================
initial begin
$display("\n=== BASIC TEST ===");
run_test_case(10, 0, 0);
$display("\n=== OUT_OF_RANGE TEST ===");
run_test_case(20, 1, 1);
$display("\n=== RANDOM STRESS TEST ===");
random_stress_test();
$display("\n=== TEST FINISHED ===");
$finish;
end
endmodule