tests/test.sh exit code (0 → resolved); the classification below is post-hoc and cannot change it.// Synthesizable UART-style receiver
module TopModule(
input wire clk,
input wire reset, // synchronous, active-high
input wire in, // serial input, idles high
input wire [15:0] baud_div_i,
input wire [2:0] frame_fmt_i,
input wire clear_err_i,
input wire data_ack_i,
output reg [7:0] out_byte,
output reg done,
output reg parity_err_o,
output reg frame_err_o,
output reg break_o,
output reg ovf_o,
output reg [7:0] byte_count_o
);
localparam IDLE = 3'd0,
START = 3'd1,
DATA = 3'd2,
PAR = 3'd3,
STOP = 3'd4;
reg [2:0] state;
reg [15:0] baud_lat; // latched baud (>=1)
reg [2:0] fmt_lat; // latched format
reg [20:0] cnt; // clock counter within a bit
reg [3:0] bitpos; // data-bit index
reg [1:0] stopidx; // stop-bit index
reg [7:0] shreg; // data shift/collect register
reg frame_bad; // this frame has an error -> no commit
reg in_d; // previous serial sample
// break detection (independent, live baud)
reg [23:0] low_cnt;
wire [20:0] bit_len = {baud_lat, 4'b0}; // 16 * baud
wire [20:0] half = {2'b0, baud_lat, 3'b0}; // 8 * baud
wire [23:0] brk_thr = {8'b0, baud_div_i} * 24'd176; // 11*16*baud
// Format decode (combinational from latched format)
reg [3:0] ndata;
reg has_par, par_odd;
reg [1:0] nstop;
always @* begin
case (fmt_lat)
3'b001: begin ndata = 4'd7; has_par = 1'b0; par_odd = 1'b0; nstop = 2'd1; end // 7N1
3'b010: begin ndata = 4'd8; has_par = 1'b1; par_odd = 1'b0; nstop = 2'd1; end // 8E1
3'b011: begin ndata = 4'd8; has_par = 1'b1; par_odd = 1'b1; nstop = 2'd1; end // 8O1
3'b100: begin ndata = 4'd8; has_par = 1'b0; par_odd = 1'b0; nstop = 2'd2; end // 8N2
default:begin ndata = 4'd8; has_par = 1'b0; par_odd = 1'b0; nstop = 2'd1; end // 8N1 / others
endcase
end
// XOR(data, parity_bit) at the parity midpoint (in == parity bit then)
wire par_calc = (^shreg) ^ in;
always @(posedge clk) begin
if (reset) begin
state <= IDLE;
baud_lat <= 16'd0;
fmt_lat <= 3'd0;
cnt <= 21'd0;
bitpos <= 4'd0;
stopidx <= 2'd0;
shreg <= 8'd0;
frame_bad <= 1'b0;
in_d <= 1'b1;
out_byte <= 8'd0;
done <= 1'b0;
parity_err_o <= 1'b0;
frame_err_o <= 1'b0;
break_o <= 1'b0;
ovf_o <= 1'b0;
byte_count_o <= 8'd0;
low_cnt <= 24'd0;
end else begin
in_d <= in;
// Sticky error/overflow clears; a same-cycle set later overrides.
if (clear_err_i) begin
parity_err_o <= 1'b0;
frame_err_o <= 1'b0;
ovf_o <= 1'b0;
end
// ack clears done; a commit later in this block overrides.
if (data_ack_i) done <= 1'b0;
// ---------------- break detection ----------------
if (in == 1'b0) begin
if (low_cnt < brk_thr) low_cnt <= low_cnt + 24'd1;
end else begin
low_cnt <= 24'd0;
end
if (in == 1'b0 && baud_div_i != 16'd0 && (low_cnt + 24'd1 >= brk_thr))
break_o <= 1'b1;
else if (in_d == 1'b1) // one clock after line returns high
break_o <= 1'b0;
// ---------------- receive FSM ----------------
case (state)
IDLE: begin
cnt <= 21'd0;
if (in_d == 1'b1 && in == 1'b0) begin // idle high->low starts a frame
baud_lat <= (baud_div_i == 16'd0) ? 16'd1 : baud_div_i;
fmt_lat <= frame_fmt_i;
shreg <= 8'd0;
bitpos <= 4'd0;
frame_bad <= 1'b0;
cnt <= 21'd0;
state <= START;
end
end
START: begin
cnt <= cnt + 21'd1;
if (cnt == half && in == 1'b1) begin
state <= IDLE; // high start midpoint -> abort, no flags
cnt <= 21'd0;
end else if (cnt == bit_len - 21'd1) begin
cnt <= 21'd0;
bitpos <= 4'd0;
state <= DATA;
end
end
DATA: begin
cnt <= cnt + 21'd1;
if (cnt == half) shreg[bitpos] <= in; // LSB-first
if (cnt == bit_len - 21'd1) begin
cnt <= 21'd0;
if (bitpos == ndata - 4'd1) begin
stopidx <= 2'd0;
state <= has_par ? PAR : STOP;
end else begin
bitpos <= bitpos + 4'd1;
end
end
end
PAR: begin
cnt <= cnt + 21'd1;
if (cnt == half) begin
// even -> par_calc must be 0 ; odd -> par_calc must be 1
if (par_calc != par_odd) begin
parity_err_o <= 1'b1;
frame_bad <= 1'b1;
end
end
if (cnt == bit_len - 21'd1) begin
cnt <= 21'd0;
stopidx <= 2'd0;
state <= STOP;
end
end
STOP: begin
cnt <= cnt + 21'd1;
if (cnt == half && in == 1'b0) begin
frame_err_o <= 1'b1;
frame_bad <= 1'b1;
end
if (cnt == bit_len - 21'd1) begin
cnt <= 21'd0;
if (stopidx == nstop - 2'd1) begin
state <= IDLE;
if (!frame_bad) begin // good frame commit
out_byte <= (ndata == 4'd7) ? {1'b0, shreg[6:0]} : shreg;
byte_count_o <= (byte_count_o == 8'hFF) ? 8'hFF
: byte_count_o + 8'd1;
if (done && !data_ack_i) ovf_o <= 1'b1; // unacked old byte
done <= 1'b1;
end
end else begin
stopidx <= stopidx + 2'd1;
end
end
end
default: state <= IDLE;
endcase
end
end
endmodule
Lint/compile the SystemVerilog
(iverilog -g2012 -o /tmp/dut.out dut.sv 2>&1 && echo "IVERILOG OK") || (which verilator >/dev/null 2>&1 && verilator --lint-only -Wall dut.sv 2>&1 || echo "no simulator found")
IVERILOG OK [stdout] IVERILOG OK
module tb;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1;
reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),
.frame_fmt_i(fmt),.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),
.out_byte(out_byte),.done(done),.parity_err_o(parity_err_o),
.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer i;
// send one bit (value b) lasting 16 clocks
task send_bit(input b); integer k; begin
for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end
end endtask
// send a byte 8N1 (start,8 data lsb-first,stop)
task send_8n1(input [7:0] v; input stopgood); integer k; begin
send_bit(0);
for(k=0;k<8;k=k+1) send_bit(v[k]);
send_bit(stopgood);
end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0;
in=1; repeat(4) @(posedge clk);
// Frame 1: 8N1 0xA5
send_8n1(8'hA5,1'b1);
repeat(2) @(posedge clk);
$display("F1 out=%h done=%b count=%d ferr=%b",out_byte,done,byte_count_o,frame_err_o);
if(out_byte!==8'hA5) $display("FAIL byte");
if(done!==1'b1) $display("FAIL done");
if(byte_count_o!==8'd1) $display("FAIL count");
// Frame 2 without ack -> overflow, replace byte 0x3C
in=1; repeat(4) @(posedge clk);
send_8n1(8'h3C,1'b1);
repeat(2) @(posedge clk);
$display("F2 out=%h ovf=%b count=%d",out_byte,ovf_o,byte_count_o);
if(ovf_o!==1'b1) $display("FAIL ovf");
if(out_byte!==8'h3C) $display("FAIL replace");
if(byte_count_o!==8'd2) $display("FAIL count2");
// ack clears
data_ack_i=1; @(posedge clk); data_ack_i=0; @(posedge clk);
if(done!==1'b0) $display("FAIL ackclear");
// clear errors
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk);
if(ovf_o!==1'b0) $display("FAIL clrovf");
// Frame with framing error (stop low)
in=1; repeat(4) @(posedge clk);
send_8n1(8'h55,1'b0);
repeat(2) @(posedge clk);
$display("F3 ferr=%b count=%d",frame_err_o,byte_count_o);
if(frame_err_o!==1'b1) $display("FAIL ferr");
if(byte_count_o!==8'd2) $display("FAIL count nochange");
// Even parity good frame 8E1: data 0xFF -> parity 0 (even # ones=8)
in=1; repeat(4) @(posedge clk);
clear_err_i=1; @(posedge clk); clear_err_i=0;
fmt=3'b010; in=1; repeat(4)@(posedge clk);
send_bit(0); for(i=0;i<8;i=i+1) send_bit(1'b1); send_bit(0); send_bit(1);
repeat(2) @(posedge clk);
$display("F4 8E1 out=%h perr=%b",out_byte,parity_err_o);
if(parity_err_o!==1'b0) $display("FAIL parity good");
if(out_byte!==8'hFF) $display("FAIL 8e1 byte");
// Even parity bad: data 0xFF parity 1 -> error
fmt=3'b010; in=1; repeat(4)@(posedge clk);
send_bit(0); for(i=0;i<8;i=i+1) send_bit(1'b1); send_bit(1); send_bit(1);
repeat(2) @(posedge clk);
$display("F5 perr=%b",parity_err_o);
if(parity_err_o!==1'b1) $display("FAIL parity bad");
// break test small baud
fmt=0; in=1; repeat(4)@(posedge clk);
in=0; repeat(16*11+4) @(posedge clk);
$display("BREAK brk=%b (expect1)",break_o);
if(break_o!==1'b1) $display("FAIL break");
in=1; @(posedge clk);
$display("after high brk=%b (expect still1)",break_o);
@(posedge clk);
$display("2 after high brk=%b (expect0)",break_o);
if(break_o!==1'b0) $display("FAIL break deassert");
$display("DONE");
$finish;
end
endmodule
Run self-test simulation
cd /tmp && iverilog -g2012 -o /tmp/sim.out /tmp/tb.sv /app/dut.sv 2>&1 && vvp /tmp/sim.out 2>&1
Exit code 2 /tmp/tb.sv:21: error: ';' is an invalid port declaration separator. /tmp/tb.sv:21: syntax error [error] tool reported failure
/tmp/tb.sv
task send_8n1(input [7:0] v; input stopgood); integer k; begin
task send_8n1(input [7:0] v, input stopgood); integer k; begin
Run self-test simulation
cd /tmp && iverilog -g2012 -o /tmp/sim.out /tmp/tb.sv /app/dut.sv 2>&1 && vvp /tmp/sim.out 2>&1
F1 out=a5 done=1 count= 1 ferr=0 F2 out=3c ovf=1 count= 2 FAIL ackclear FAIL clrovf F3 ferr=1 count= 2 F4 8E1 out=ff perr=0 F5 perr=1 BREAK brk=1 (expect1) after high brk=1 (expect still1) 2 after high brk=1 (expect0) FAIL break deassert DONE /tmp/tb.sv:84: $finish called at 10585 (1s) Shell cwd was reset to /app [stdout] F1 out=a5 done=1 count= 1 ferr=0 F2 out=3c ovf=1 count= 2 FAIL ackclear FAIL clrovf F3 ferr=1 count= 2 F4 8E1 out=ff perr=0 F5 perr=1 BREAK brk=1 (expect1) after high brk=1 (expect still1) 2 after high brk=1 (expect0) FAIL break deassert DONE /tmp/tb.sv:84: $finish called at 10585 (1s) [stderr] Shell cwd was reset to /app
Patch tb sampling races
cd /tmp && sed -i 's/@(posedge clk); if(done!==1.b0)/@(posedge clk); #1; if(done!==1'"'"'b0)/' /tmp/tb.sv
sed -i 's/@(posedge clk); if(ovf_o!==1.b0)/@(posedge clk); #1; if(ovf_o!==1'"'"'b0)/' /tmp/tb.sv
# break deassert: add settle
sed -i 's|@(posedge clk);\n \$display("2 after high|XX|' /tmp/tb.sv
grep -n "after high" /tmp/tb.sv79: $display("after high brk=%b (expect still1)",break_o);
81: $display("2 after high brk=%b (expect0)",break_o);
Shell cwd was reset to /app
[stdout]
79: $display("after high brk=%b (expect still1)",break_o);
81: $display("2 after high brk=%b (expect0)",break_o);
[stderr]
Shell cwd was reset to /app/tmp/tb.sv
78 in=1; @(posedge clk);
79 $display("after high brk=%b (expect still1)",break_o);
80 @(posedge clk);
81 $display("2 after high brk=%b (expect0)",break_o);
82 if(break_o!==1'b0) $display("FAIL break deassert");
83 $display("DONE");
/tmp/tb.sv
@(posedge clk);
$display("2 after high brk=%b (expect0)",break_o); @(posedge clk); #1;
$display("2 after high brk=%b (expect0)",break_o);Re-run self-test
cd /tmp && iverilog -g2012 -o /tmp/sim.out /tmp/tb.sv /app/dut.sv 2>&1 && vvp /tmp/sim.out 2>&1
F1 out=a5 done=1 count= 1 ferr=0 F2 out=3c ovf=1 count= 2 FAIL ackclear FAIL clrovf F3 ferr=1 count= 2 F4 8E1 out=ff perr=0 F5 perr=1 BREAK brk=1 (expect1) after high brk=1 (expect still1) 2 after high brk=0 (expect0) DONE /tmp/tb.sv:84: $finish called at 10586 (1s) Shell cwd was reset to /app [stdout] F1 out=a5 done=1 count= 1 ferr=0 F2 out=3c ovf=1 count= 2 FAIL ackclear FAIL clrovf F3 ferr=1 count= 2 F4 8E1 out=ff perr=0 F5 perr=1 BREAK brk=1 (expect1) after high brk=1 (expect still1) 2 after high brk=0 (expect0) DONE /tmp/tb.sv:84: $finish called at 10586 (1s) [stderr] Shell cwd was reset to /app
Find the check lines
cd /tmp && grep -n "ackclear\|clrovf" /tmp/tb.sv
47: if(done!==1'b0) $display("FAIL ackclear");
50: if(ovf_o!==1'b0) $display("FAIL clrovf");
Shell cwd was reset to /app
[stdout]
47: if(done!==1'b0) $display("FAIL ackclear");
50: if(ovf_o!==1'b0) $display("FAIL clrovf");
[stderr]
Shell cwd was reset to /app/tmp/tb.sv
44 if(byte_count_o!==8'd2) $display("FAIL count2");
45 // ack clears
46 data_ack_i=1; @(posedge clk); data_ack_i=0; @(posedge clk);
47 if(done!==1'b0) $display("FAIL ackclear");
48 // clear errors
49 clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk);
50 if(ovf_o!==1'b0) $display("FAIL clrovf");
51 // Frame with framing error (stop low)
/tmp/tb.sv
data_ack_i=1; @(posedge clk); data_ack_i=0; @(posedge clk);
if(done!==1'b0) $display("FAIL ackclear");
// clear errors
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk);
if(ovf_o!==1'b0) $display("FAIL clrovf"); data_ack_i=1; @(posedge clk); data_ack_i=0; @(posedge clk); #1;
if(done!==1'b0) $display("FAIL ackclear");
// clear errors
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk); #1;
if(ovf_o!==1'b0) $display("FAIL clrovf");Re-run self-test
cd /tmp && iverilog -g2012 -o /tmp/sim.out /tmp/tb.sv /app/dut.sv 2>&1 && vvp /tmp/sim.out 2>&1
F1 out=a5 done=1 count= 1 ferr=0 F2 out=3c ovf=1 count= 2 FAIL ackclear FAIL clrovf F3 ferr=1 count= 2 F4 8E1 out=ff perr=0 F5 perr=1 BREAK brk=1 (expect1) after high brk=1 (expect still1) 2 after high brk=0 (expect0) DONE /tmp/tb.sv:84: $finish called at 10586 (1s) Shell cwd was reset to /app [stdout] F1 out=a5 done=1 count= 1 ferr=0 F2 out=3c ovf=1 count= 2 FAIL ackclear FAIL clrovf F3 ferr=1 count= 2 F4 8E1 out=ff perr=0 F5 perr=1 BREAK brk=1 (expect1) after high brk=1 (expect still1) 2 after high brk=0 (expect0) DONE /tmp/tb.sv:84: $finish called at 10586 (1s) [stderr] Shell cwd was reset to /app
Trace done around ack
cd /tmp && cat > /tmp/tb2.sv <<'EOF'
module tb2;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
task s8(input [7:0] v); integer j; begin sb(0); for(j=0;j<8;j=j+1) sb(v[j]); sb(1); end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
s8(8'hA5); repeat(3)@(posedge clk);
$display("t=%0t after F1 done=%b ovf=%b",$time,done,ovf_o);
data_ack_i=1; @(posedge clk); #1; $display("t=%0t ack pulse done=%b",$time,done);
data_ack_i=0; @(posedge clk); #1; $display("t=%0t after ack done=%b",$time,done);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/s2.out /tmp/tb2.sv /app/dut.sv 2>&1 && vvp /tmp/s2.out 2>&1t=1685 after F1 done=1 ovf=0 t=1696 ack pulse done=0 t=1706 after ack done=0 /tmp/tb2.sv:20: $finish called at 1706 (1s) Shell cwd was reset to /app [stdout] t=1685 after F1 done=1 ovf=0 t=1696 ack pulse done=0 t=1706 after ack done=0 /tmp/tb2.sv:20: $finish called at 1706 (1s) [stderr] Shell cwd was reset to /app
Reproduce overflow then ack/clear
cd /tmp && cat > /tmp/tb3.sv <<'EOF'
module tb3;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
task s8(input [7:0] v); integer j; begin sb(0); for(j=0;j<8;j=j+1) sb(v[j]); sb(1); end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
s8(8'hA5); repeat(2)@(posedge clk);
in=1; repeat(4)@(posedge clk);
s8(8'h3C); repeat(2)@(posedge clk);
$display("after F2 done=%b ovf=%b count=%0d",done,ovf_o,byte_count_o);
data_ack_i=1; @(posedge clk); data_ack_i=0; @(posedge clk); #1;
$display("after ack done=%b (expect0)",done);
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk); #1;
$display("after clr ovf=%b (expect0)",ovf_o);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/s3.out /tmp/tb3.sv /app/dut.sv 2>&1 && vvp /tmp/s3.out 2>&1after F2 done=1 ovf=1 count=2 after ack done=1 (expect0) after clr ovf=1 (expect0) /tmp/tb3.sv:24: $finish called at 3376 (1s) Shell cwd was reset to /app [stdout] after F2 done=1 ovf=1 count=2 after ack done=1 (expect0) after clr ovf=1 (expect0) /tmp/tb3.sv:24: $finish called at 3376 (1s) [stderr] Shell cwd was reset to /app
Monitor state during ack
cd /tmp && cat > /tmp/tb4.sv <<'EOF'
module tb4;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
task s8(input [7:0] v); integer j; begin sb(0); for(j=0;j<8;j=j+1) sb(v[j]); sb(1); end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
s8(8'hA5); repeat(2)@(posedge clk);
in=1; repeat(4)@(posedge clk);
s8(8'h3C); repeat(2)@(posedge clk);
$monitor("t=%0t done=%b ovf=%b ack=%b state=%b in=%b",$time,done,ovf_o,data_ack_i,d.state,in);
data_ack_i=1; @(posedge clk); data_ack_i=0; @(posedge clk);@(posedge clk);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/s4.out /tmp/tb4.sv /app/dut.sv 2>&1 && vvp /tmp/s4.out 2>&1t=3335 done=1 ovf=1 ack=1 state=000 in=1 t=3345 done=1 ovf=1 ack=0 state=000 in=1 /tmp/tb4.sv:21: $finish called at 3365 (1s) Shell cwd was reset to /app [stdout] t=3335 done=1 ovf=1 ack=1 state=000 in=1 t=3345 done=1 ovf=1 ack=0 state=000 in=1 /tmp/tb4.sv:21: $finish called at 3365 (1s) [stderr] Shell cwd was reset to /app
Continuous trace at end of F2 then ack
cd /tmp && cat > /tmp/tb5.sv <<'EOF'
module tb5;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
task s8(input [7:0] v); integer j; begin sb(0); for(j=0;j<8;j=j+1) sb(v[j]); sb(1); end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
s8(8'hA5); repeat(2)@(posedge clk);
in=1; repeat(4)@(posedge clk);
s8(8'h3C);
// now trace continuously
repeat(6) begin @(posedge clk); #1;
$display("t=%0t st=%b done=%b ovf=%b cnt_bl done",$time,d.state,done,ovf_o); end
// do ack well clear of commit
data_ack_i=1; @(posedge clk); #1; data_ack_i=0;
$display("after ack done=%b (expect0)",done);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/s5.out /tmp/tb5.sv /app/dut.sv 2>&1 && vvp /tmp/s5.out 2>&1t=3326 st=000 done=1 ovf=1 cnt_bl done t=3336 st=000 done=1 ovf=1 cnt_bl done t=3346 st=000 done=1 ovf=1 cnt_bl done t=3356 st=000 done=1 ovf=1 cnt_bl done t=3366 st=000 done=1 ovf=1 cnt_bl done t=3376 st=000 done=1 ovf=1 cnt_bl done after ack done=0 (expect0) /tmp/tb5.sv:25: $finish called at 3386 (1s) Shell cwd was reset to /app [stdout] t=3326 st=000 done=1 ovf=1 cnt_bl done t=3336 st=000 done=1 ovf=1 cnt_bl done t=3346 st=000 done=1 ovf=1 cnt_bl done t=3356 st=000 done=1 ovf=1 cnt_bl done t=3366 st=000 done=1 ovf=1 cnt_bl done t=3376 st=000 done=1 ovf=1 cnt_bl done after ack done=0 (expect0) /tmp/tb5.sv:25: $finish called at 3386 (1s) [stderr] Shell cwd was reset to /app
Test clear, 7N1, 8N2, abort
cd /tmp && cat > /tmp/tb6.sv <<'EOF'
module tb6;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
// 8N1 with chosen stop level
task s8s(input [7:0] v, input st); integer j; begin sb(0); for(j=0;j<8;j=j+1) sb(v[j]); sb(st); end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
// framing error frame (stop=0), no byte/done/count update
s8s(8'h77,1'b0); in=1; repeat(6)@(posedge clk); #1;
$display("frame_err=%b done=%b count=%0d (exp 1,0,0)",frame_err_o,done,byte_count_o);
clear_err_i=1; @(posedge clk); clear_err_i=0; repeat(2)@(posedge clk); #1;
$display("after clear frame_err=%b (exp 0)",frame_err_o);
// 7N1 check upper bit zero, value 0x7F -> out 0x7F, and 0xFF data(7 used) -> 0x7F
fmt=3'b001; in=1; repeat(4)@(posedge clk);
sb(0); for(k=0;k<7;k=k+1) sb(1'b1); sb(1); // 7 ones
repeat(3)@(posedge clk); #1;
$display("7N1 out=%h (exp 7f) count=%0d",out_byte,byte_count_o);
// 8N2: two stop bits, second low => frame err
fmt=3'b100; in=1; repeat(4)@(posedge clk);
sb(0); for(k=0;k<8;k=k+1) sb(1'b0); sb(1); sb(0); // stop1 high stop2 low
repeat(3)@(posedge clk); #1;
$display("8N2 badstop2 frame_err=%b (exp1)",frame_err_o);
// 8N2 good
clear_err_i=1; @(posedge clk); clear_err_i=0; in=1; repeat(4)@(posedge clk);
sb(0); for(k=0;k<8;k=k+1) sb(k[0]); sb(1); sb(1);
repeat(3)@(posedge clk); #1;
$display("8N2 good out=%h frame_err=%b (exp 0)",out_byte,frame_err_o);
// abort: start goes high at midpoint
fmt=0; in=1; repeat(4)@(posedge clk);
in=0; repeat(4)@(posedge clk); in=1; repeat(20)@(posedge clk); #1;
$display("abort: done unchanged frame_err=%b parity=%b",frame_err_o,parity_err_o);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/s6.out /tmp/tb6.sv /app/dut.sv 2>&1 && vvp /tmp/s6.out 2>&1frame_err=1 done=0 count=0 (exp 1,0,0) after clear frame_err=1 (exp 0) 7N1 out=00 (exp 7f) count=0 8N2 badstop2 frame_err=1 (exp1) 8N2 good out=00 frame_err=1 (exp 0) abort: done unchanged frame_err=1 parity=0 /tmp/tb6.sv:41: $finish called at 4006 (1s) Shell cwd was reset to /app [stdout] frame_err=1 done=0 count=0 (exp 1,0,0) after clear frame_err=1 (exp 0) 7N1 out=00 (exp 7f) count=0 8N2 badstop2 frame_err=1 (exp1) 8N2 good out=00 frame_err=1 (exp 0) abort: done unchanged frame_err=1 parity=0 /tmp/tb6.sv:41: $finish called at 4006 (1s) [stderr] Shell cwd was reset to /app
Trace framing-error frame and clear
cd /tmp && cat > /tmp/tb7.sv <<'EOF'
module tb7;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
task s8s(input [7:0] v, input st); integer j; begin sb(0); for(j=0;j<8;j=j+1) sb(v[j]); sb(st); end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
s8s(8'h77,1'b0);
in=1;
repeat(8) begin @(posedge clk); #1; $display("t=%0t st=%b ferr=%b bad=%b in_d=%b",$time,d.state,frame_err_o,d.frame_bad,d.in_d); end
clear_err_i=1; @(posedge clk); #1; clear_err_i=0;
$display("clr cycle st=%b ferr=%b",d.state,frame_err_o);
@(posedge clk); #1; $display("post-clr st=%b ferr=%b",d.state,frame_err_o);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/s7.out /tmp/tb7.sv /app/dut.sv 2>&1 && vvp /tmp/s7.out 2>&1t=1666 st=000 ferr=1 bad=1 in_d=1 t=1676 st=000 ferr=1 bad=1 in_d=1 t=1686 st=000 ferr=1 bad=1 in_d=1 t=1696 st=000 ferr=1 bad=1 in_d=1 t=1706 st=000 ferr=1 bad=1 in_d=1 t=1716 st=000 ferr=1 bad=1 in_d=1 t=1726 st=000 ferr=1 bad=1 in_d=1 t=1736 st=000 ferr=1 bad=1 in_d=1 clr cycle st=000 ferr=0 post-clr st=000 ferr=0 /tmp/tb7.sv:22: $finish called at 1756 (1s) Shell cwd was reset to /app [stdout] t=1666 st=000 ferr=1 bad=1 in_d=1 t=1676 st=000 ferr=1 bad=1 in_d=1 t=1686 st=000 ferr=1 bad=1 in_d=1 t=1696 st=000 ferr=1 bad=1 in_d=1 t=1706 st=000 ferr=1 bad=1 in_d=1 t=1716 st=000 ferr=1 bad=1 in_d=1 t=1726 st=000 ferr=1 bad=1 in_d=1 t=1736 st=000 ferr=1 bad=1 in_d=1 clr cycle st=000 ferr=0 post-clr st=000 ferr=0 /tmp/tb7.sv:22: $finish called at 1756 (1s) [stderr] Shell cwd was reset to /app
Isolate 7N1 commit
cd /tmp && cat > /tmp/tb8.sv <<'EOF'
module tb8;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0;
fmt=3'b001; in=1; repeat(4)@(posedge clk);
sb(0); for(k=0;k<7;k=k+1) sb(1'b1); sb(1);
repeat(3)@(posedge clk); #1;
$display("7N1 out=%h done=%b count=%0d bad=%b ndata=%b",out_byte,done,byte_count_o,d.frame_bad,d.ndata);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/s8.out /tmp/tb8.sv /app/dut.sv 2>&1 && vvp /tmp/s8.out 2>&17N1 out=00 done=0 count=0 bad=0 ndata=0111 /tmp/tb8.sv:19: $finish called at 566 (1s) Shell cwd was reset to /app [stdout] 7N1 out=00 done=0 count=0 bad=0 ndata=0111 /tmp/tb8.sv:19: $finish called at 566 (1s) [stderr] Shell cwd was reset to /app
Trace state transitions in 7N1
cd /tmp && cat > /tmp/tb9.sv <<'EOF'
module tb9;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
integer k;
reg [3:0] pst;
task sb(input b); begin for(k=0;k<16;k=k+1) begin in=b; @(posedge clk); end end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0;
fmt=3'b001; in=1; repeat(4)@(posedge clk);
fork
begin sb(0); for(k=0;k<7;k=k+1) sb(1'b1); sb(1); repeat(4)@(posedge clk); $finish; end
begin forever begin @(posedge clk); #1;
if(d.state!==pst) $display("t=%0t st=%b->? bitpos=%0d stopidx=%0d cnt=%0d shreg=%h done=%b",$time,d.state,d.bitpos,d.stopidx,d.cnt,d.shreg,done);
pst<=d.state; end end
join
end
endmodule
EOF
iverilog -g2012 -o /tmp/s9.out /tmp/tb9.sv /app/dut.sv 2>&1 && vvp /tmp/s9.out 2>&1t=66 st=001->? bitpos=0 stopidx=0 cnt=0 shreg=00 done=0 t=226 st=010->? bitpos=0 stopidx=0 cnt=0 shreg=00 done=0 /tmp/tb9.sv:18: $finish called at 575 (1s) Shell cwd was reset to /app [stdout] t=66 st=001->? bitpos=0 stopidx=0 cnt=0 shreg=00 done=0 t=226 st=010->? bitpos=0 stopidx=0 cnt=0 shreg=00 done=0 /tmp/tb9.sv:18: $finish called at 575 (1s) [stderr] Shell cwd was reset to /app
Comprehensive correct testbench
cd /tmp && cat > /tmp/tf.sv <<'EOF'
module tf;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
integer errs=0;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
task sb(input b); integer i; begin for(i=0;i<16;i=i+1) begin in=b; @(posedge clk); end end endtask
// generic frame: nd data bits (lsb-first) from v, optional parity bit pb, ns stop bits value stv
task frame(input [7:0] v, input integer nd, input haspar, input pb, input integer ns, input stv);
integer i; begin
sb(0);
for(i=0;i<nd;i=i+1) sb(v[i]);
if(haspar) sb(pb);
for(i=0;i<ns;i=i+1) sb(stv);
end
endtask
task chk(input cond, input [255:0] msg); begin if(!cond) begin errs=errs+1; $display("FAIL: %0s",msg); end end endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
// 8N1 0xA5 good
fmt=0; frame(8'hA5,8,0,0,1,1); in=1; repeat(3)@(posedge clk); #1;
chk(out_byte===8'hA5,"8N1 byte"); chk(done===1,"8N1 done"); chk(byte_count_o===8'd1,"8N1 count");
// 8N1 0x3C without ack -> overflow, replace
frame(8'h3C,8,0,0,1,1); in=1; repeat(3)@(posedge clk); #1;
chk(out_byte===8'h3C,"ovf replace"); chk(ovf_o===1,"ovf set"); chk(byte_count_o===8'd2,"count2");
// ack clears done
data_ack_i=1; @(posedge clk); data_ack_i=0; @(posedge clk); #1; chk(done===0,"ack clears done");
// clear ovf
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk); #1; chk(ovf_o===0,"clear ovf");
// framing error (stop low): no commit, no count change
frame(8'h11,8,0,0,1,0); in=1; repeat(4)@(posedge clk); #1;
chk(frame_err_o===1,"frame_err set"); chk(byte_count_o===8'd2,"count unchanged on ferr");
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk); #1; chk(frame_err_o===0,"clear ferr");
// 7N1: 7 ones -> 0x7F, bit7=0
fmt=3'b001; in=1; repeat(4)@(posedge clk);
frame(8'hFF,7,0,0,1,1); in=1; repeat(3)@(posedge clk); #1;
chk(out_byte===8'h7F,"7N1 byte 7f"); chk(byte_count_o===8'd3,"7N1 count");
// 8E1 good: data 0xFF (8 ones, even) parity=0
fmt=3'b010; in=1; repeat(4)@(posedge clk);
frame(8'hFF,8,1,0,1,1); in=1; repeat(3)@(posedge clk); #1;
chk(out_byte===8'hFF,"8E1 byte"); chk(parity_err_o===0,"8E1 par ok"); chk(byte_count_o===8'd4,"8E1 count");
// 8E1 bad: data 0xFF parity=1 -> perr, no commit
frame(8'hFF,8,1,1,1,1); in=1; repeat(3)@(posedge clk); #1;
chk(parity_err_o===1,"8E1 par err"); chk(byte_count_o===8'd4,"count unchanged perr");
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk); #1;
// 8O1 good: data 0x01 (odd #ones=1) parity=0 -> XOR=1 odd ok
fmt=3'b011; in=1; repeat(4)@(posedge clk);
frame(8'h01,8,1,0,1,1); in=1; repeat(3)@(posedge clk); #1;
chk(out_byte===8'h01,"8O1 byte"); chk(parity_err_o===0,"8O1 par ok");
// 8N2 good: two stop high
fmt=3'b100; in=1; repeat(4)@(posedge clk);
frame(8'h5A,8,0,0,2,1); in=1; repeat(3)@(posedge clk); #1;
chk(out_byte===8'h5A,"8N2 byte"); chk(frame_err_o===0,"8N2 ok");
// 8N2 second stop low -> frame_err
frame(8'h5A,8,0,0,2,0); in=1; repeat(4)@(posedge clk); #1;
chk(frame_err_o===1,"8N2 stop2 low ferr");
clear_err_i=1; @(posedge clk); clear_err_i=0; @(posedge clk); #1;
// abort: high at start midpoint
fmt=0; in=1; repeat(4)@(posedge clk);
in=0; repeat(4)@(posedge clk); in=1; repeat(24)@(posedge clk); #1;
chk(frame_err_o===0 && parity_err_o===0,"abort no flags");
if(errs==0) $display("ALL PASS"); else $display("%0d FAILURES",errs);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/tf.out /tmp/tf.sv /app/dut.sv 2>&1 && vvp /tmp/tf.out 2>&1FAIL: ack clears done FAIL: clear ovf FAIL: clear ferr FAIL: 8O1 par ok FAIL: 8N2 ok FAIL: abort no flags 6 FAILURES /tmp/tf.sv:78: $finish called at 15966 (1s) Shell cwd was reset to /app [stdout] FAIL: ack clears done FAIL: clear ovf FAIL: clear ferr FAIL: 8O1 par ok FAIL: 8N2 ok FAIL: abort no flags 6 FAILURES /tmp/tf.sv:78: $finish called at 15966 (1s) [stderr] Shell cwd was reset to /app
Trace ack-clears-done cleanly
cd /tmp && cat > /tmp/tg.sv <<'EOF'
module tg;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
task sb(input b); integer i; begin for(i=0;i<16;i=i+1) begin in=b; @(posedge clk); end end endtask
task frame(input [7:0] v, input integer nd, input haspar, input pb, input integer ns, input stv);
integer i; begin sb(0); for(i=0;i<nd;i=i+1) sb(v[i]); if(haspar) sb(pb); for(i=0;i<ns;i=i+1) sb(stv); end
endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
fmt=0; frame(8'hA5,8,0,0,1,1); in=1; repeat(3)@(posedge clk); #1;
$display("done=%b st=%b",done,d.state);
data_ack_i=1; @(posedge clk); #1;
$display("during ack: done=%b st=%b ack=%b",done,d.state,data_ack_i);
data_ack_i=0; @(posedge clk); #1;
$display("after ack: done=%b",done);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/tg.out /tmp/tg.sv /app/dut.sv 2>&1 && vvp /tmp/tg.out 2>&1done=1 st=000 during ack: done=0 st=000 ack=1 after ack: done=0 /tmp/tg.sv:23: $finish called at 1706 (1s) Shell cwd was reset to /app [stdout] done=1 st=000 during ack: done=0 st=000 ack=1 after ack: done=0 /tmp/tg.sv:23: $finish called at 1706 (1s) [stderr] Shell cwd was reset to /app
Overflow frame then ack
cd /tmp && cat > /tmp/th.sv <<'EOF'
module th;
reg clk=0, reset, in=1, clear_err_i=0, data_ack_i=0;
reg [15:0] baud=1; reg [2:0] fmt=0;
wire [7:0] out_byte, byte_count_o;
wire done, parity_err_o, frame_err_o, break_o, ovf_o;
TopModule d(.clk(clk),.reset(reset),.in(in),.baud_div_i(baud),.frame_fmt_i(fmt),
.clear_err_i(clear_err_i),.data_ack_i(data_ack_i),.out_byte(out_byte),.done(done),
.parity_err_o(parity_err_o),.frame_err_o(frame_err_o),.break_o(break_o),.ovf_o(ovf_o),
.byte_count_o(byte_count_o));
always #5 clk=~clk;
task sb(input b); integer i; begin for(i=0;i<16;i=i+1) begin in=b; @(posedge clk); end end endtask
task frame(input [7:0] v, input integer nd, input haspar, input pb, input integer ns, input stv);
integer i; begin sb(0); for(i=0;i<nd;i=i+1) sb(v[i]); if(haspar) sb(pb); for(i=0;i<ns;i=i+1) sb(stv); end
endtask
initial begin
reset=1; @(posedge clk); @(posedge clk); reset=0; in=1; repeat(4)@(posedge clk);
fmt=0; frame(8'hA5,8,0,0,1,1); in=1; repeat(3)@(posedge clk); #1;
$display("F1 done=%b out=%h cnt=%0d",done,out_byte,byte_count_o);
frame(8'h3C,8,0,0,1,1); in=1; repeat(3)@(posedge clk); #1;
$display("F2 done=%b ovf=%b out=%h cnt=%0d st=%b",done,ovf_o,out_byte,byte_count_o,d.state);
data_ack_i=1; @(posedge clk); #1; $display("ackcyc done=%b st=%b",done,d.state);
data_ack_i=0; @(posedge clk); #1; $display("postack done=%b",done);
$finish;
end
endmodule
EOF
iverilog -g2012 -o /tmp/th.out /tmp/th.sv /app/dut.sv 2>&1 && vvp /tmp/th.out 2>&1F1 done=1 out=a5 cnt=1 F2 done=1 ovf=1 out=3c cnt=2 st=000 ackcyc done=0 st=000 postack done=0 /tmp/th.sv:23: $finish called at 3336 (1s) Shell cwd was reset to /app [stdout] F1 done=1 out=a5 cnt=1 F2 done=1 ovf=1 out=3c cnt=2 st=000 ackcyc done=0 st=000 postack done=0 /tmp/th.sv:23: $finish called at 3336 (1s) [stderr] Shell cwd was reset to /app
Instrument tf failing points
cd /tmp && sed -i 's|chk(done===0,"ack clears done");|chk(done===0,"ack clears done"); $display(" [dbg ack] done=%b st=%b bad=%b",done,d.state,d.frame_bad);|' /tmp/tf.sv
sed -i 's|chk(ovf_o===0,"clear ovf");|chk(ovf_o===0,"clear ovf"); $display(" [dbg clrovf] ovf=%b st=%b",ovf_o,d.state);|' /tmp/tf.sv
sed -i 's|chk(frame_err_o===0,"clear ferr");|chk(frame_err_o===0,"clear ferr"); $display(" [dbg clrferr] ferr=%b st=%b cnt=%0d",frame_err_o,d.state,d.cnt);|' /tmp/tf.sv
iverilog -g2012 -o /tmp/tf.out /tmp/tf.sv /app/dut.sv 2>&1 && vvp /tmp/tf.out 2>&1 | head -30FAIL: ack clears done [dbg ack] done=1 st=000 bad=0 FAIL: clear ovf [dbg clrovf] ovf=1 st=000 FAIL: clear ferr [dbg clrferr] ferr=1 st=000 cnt=0 FAIL: 8O1 par ok FAIL: 8N2 ok FAIL: abort no flags 6 FAILURES /tmp/tf.sv:78: $finish called at 15966 (1s) Shell cwd was reset to /app [stdout] FAIL: ack clears done [dbg ack] done=1 st=000 bad=0 FAIL: clear ovf [dbg clrovf] ovf=1 st=000 FAIL: clear ferr [dbg clrferr] ferr=1 st=000 cnt=0 FAIL: 8O1 par ok FAIL: 8N2 ok FAIL: abort no flags 6 FAILURES /tmp/tf.sv:78: $finish called at 15966 (1s) [stderr] Shell cwd was reset to /app
Fix tb race and rerun full suite
cd /tmp && python3 - <<'PY'
import re
s=open('/tmp/tf.sv').read()
# add #1 after each "@(posedge clk); XXX_i=0;" pattern -> "@(posedge clk); #1; XXX_i=0;"
s=s.replace("data_ack_i=1; @(posedge clk); data_ack_i=0;","data_ack_i=1; @(posedge clk); #1; data_ack_i=0;")
s=s.replace("clear_err_i=1; @(posedge clk); clear_err_i=0;","clear_err_i=1; @(posedge clk); #1; clear_err_i=0;")
# remove earlier debug displays to keep output clean
s=re.sub(r' \$display\(" \[dbg[^;]*\);','',s)
open('/tmp/tf.sv','w').write(s)
PY
iverilog -g2012 -o /tmp/tf.out /tmp/tf.sv /app/dut.sv 2>&1 && vvp /tmp/tf.out 2>&1ALL PASS /tmp/tf.sv:78: $finish called at 15966 (1s) Shell cwd was reset to /app [stdout] ALL PASS /tmp/tf.sv:78: $finish called at 15966 (1s) [stderr] Shell cwd was reset to /app
No file changes, the agent left the workspace untouched.
TEST dut_present: PASS (/app/dut.sv exists) TEST dut_forbidden: PASS (no forbidden constructs) TEST harness_prepare: PASS (harness names nonce-renamed) TEST dut_compiles: PASS (compiled with held-back reference/testbench) TEST simulation_completed: PASS (Mismatches: 14 in 155243 samples) TEST reference_equivalence: FAIL (14 mismatches in 155243 samples)
Reproduce this trial: git checkout 2f94510 && PYTHONPATH=src python3 scripts/build_site.py , then open trial/trial_6c9533cca45d4e81. Re-running the agent live requires EVAL_PLATFORM_ENABLE_OAUTH_SMOKE=1 and is non-deterministic.
Trial trial_6c9533cca45d4e81 · verifier authoritative; classifier explanatory.