✓
Passing This code compiles and runs correctly.
Code
// TEST: self|fpga — the kernel emits a SystemVerilog stage + testbench,
// and the BUILD runs them: iverilog compiles the pair, vvp simulates the
// dataset, $fatal on a wrong beat fails the build — a broken circuit is a
// red compile, never a shipped artifact.
//
// Port widths come from the |fpga refine facet's scoped meet: value is
// i64 & >=0 & <=255 on the fpga scope, so the port is logic [7:0]; mode is
// [1:0]. The host lowering is still the ordinary Zig loop — the circuit is
// the proven artifact, not the compute path.
//
// Pinned shape: `k.<field> <op>= <literal>` on an int shape with a declared
// |fpga facet, no step, no store backing.
import std/proto
import std/refine
import std/kernel
import std/io
std/proto(Sample) {
value: i64
mode: i64
}
std/refine(Sample)|fpga {
value: i64 & >=0 & <=255
mode: i64 & >=0 & <=3
}
std/kernel:shape(Sample) {
value: i64,
mode: i64,
}
std/kernel:init(Sample) {
{ value: 4, mode: 1 },
{ value: 8, mode: 2 },
{ value: 16, mode: 3 },
}
| kernel k |> std/kernel:self|fpga { k.value *= 2 }
| computed c |> std/io:print.blk {
v[0]={{ c[0].value:d }} v[1]={{ c[1].value:d }} v[2]={{ c[2].value:d }}
}
Supporting Files
// Generated by std/kernel:self|fpga — one kernel self op, one pipeline
// stage. Host lowering is the ordinary Zig loop; this artifact is gated
// by iverilog + the generated testbench + yosys check, all run by the build.
module koru_fpga_kernel_init_2407370252_data_self_0 (
input logic clk,
input logic rst_n,
input logic in_valid,
input logic [7:0] in_value,
input logic [1:0] in_mode,
output logic out_valid,
output logic [7:0] out_value,
output logic [1:0] out_mode
);
logic [7:0] mapped_value;
assign mapped_value = in_value * 8'd2;
always_ff @(posedge clk or negedge rst_n) begin
if (!rst_n) begin
out_valid <= 1'b0;
out_value <= 8'd0;
out_mode <= 2'd0;
end else begin
out_valid <= in_valid;
out_value <= mapped_value;
out_mode <= in_mode;
end
end
endmodule
// Generated testbench for koru_fpga_kernel_init_2407370252_data_self_0 — drives the init dataset on
// consecutive beats, checks the stage's output one beat later.
// errors exit nonzero via $fatal so the BUILD fails on a wrong circuit.
module tb;
logic clk = 0;
logic rst_n = 0;
logic in_valid = 0;
logic [7:0] in_value = 0;
logic [1:0] in_mode = 0;
logic out_valid;
logic [7:0] out_value;
logic [7:0] exp_value;
logic [1:0] out_mode;
logic [1:0] exp_mode;
logic signed [63:0] expw_value;
koru_fpga_kernel_init_2407370252_data_self_0 dut (.*);
always #5 clk = ~clk;
int errors = 0;
task check;
if (!out_valid || out_value !== exp_value || out_mode !== exp_mode) begin
$display("FAIL: got valid=%b value=%0d mode=%0d, want value=%0d mode=%0d", out_valid, out_value, out_mode, exp_value, exp_mode);
errors = errors + 1;
end else begin
$display("ok: value=%0d mode=%0d", out_value, out_mode);
if (expw_value != out_value) $display("note: value truncated %0d -> %0d (8-bit port)", expw_value, out_value);
end
endtask
initial begin
@(negedge clk); rst_n = 1;
// beat 1: drive element 0
@(negedge clk); in_valid = 1; in_value = 8'd4; in_mode = 2'd1;
expw_value = $signed({1'b0, in_value}) * 64'sd2; exp_value = expw_value[7:0];exp_mode = in_mode;
// beat 2: drive element 1
@(negedge clk); check(); in_valid = 1; in_value = 8'd8; in_mode = 2'd2;
expw_value = $signed({1'b0, in_value}) * 64'sd2; exp_value = expw_value[7:0];exp_mode = in_mode;
// beat 3: drive element 2
@(negedge clk); check(); in_valid = 1; in_value = 8'd16; in_mode = 2'd3;
expw_value = $signed({1'b0, in_value}) * 64'sd2; exp_value = expw_value[7:0];exp_mode = in_mode;
// drain: last check, then drop valid
@(negedge clk); check(); in_valid = 0;
if (errors == 0) $display("PASS: koru_fpga_kernel_init_2407370252_data_self_0 pipeline");
else $fatal(1, "FAIL: %0d errors", errors);
$finish;
end
endmodule
Actual
v[0]=8 v[1]=16 v[2]=32
Expected output
v[0]=8 v[1]=16 v[2]=32
Flows
flow ~std/proto click a branch to expand · @labels scroll to their anchor
std/proto (Sample, source: value: i64
mode: i64)
flow ~std/refine click a branch to expand · @labels scroll to their anchor
std/refine|fpga (Sample, source: value: i64 & >=0 & <=255
mode: i64 & >=0 & <=3)
flow ~shape click a branch to expand · @labels scroll to their anchor
shape (expr: Sample, source: value: i64,
mode: i64,)
flow ~init click a branch to expand · @labels scroll to their anchor
init (expr: Sample, source: { value: 4, mode: 1 },
{ value: 8, mode: 2 },
{ value: 16, mode: 3 },)
Test Configuration
MUST_RUN