aboutsummaryrefslogtreecommitdiffstats
path: root/src/verilog/PrintVerilog.ml
diff options
context:
space:
mode:
Diffstat (limited to 'src/verilog/PrintVerilog.ml')
-rw-r--r--src/verilog/PrintVerilog.ml50
1 files changed, 45 insertions, 5 deletions
diff --git a/src/verilog/PrintVerilog.ml b/src/verilog/PrintVerilog.ml
index 5199872..292fcf2 100644
--- a/src/verilog/PrintVerilog.ml
+++ b/src/verilog/PrintVerilog.ml
@@ -92,9 +92,13 @@ let pprint_edge_top i = function
| Valledge -> "@*"
| Voredge (e1, e2) -> concat ["@("; pprint_edge e1; " or "; pprint_edge e2; ")"]
+let declare i t =
+ function (r, sz) ->
+ concat [ indent i; t; " ["; sprintf "%d" (Nat.to_int sz - 1); ":0] ";
+ register r; ";\n" ]
+
let pprint_module_item i = function
- | Vdecl (r, n, e) ->
- concat [indent i; "reg ["; sprintf "%d" (Nat.to_int n - 1); ":0] "; register r; " = "; pprint_expr e; ";\n"]
+ | Vdecl (r, sz) -> declare i "reg" (r, sz)
| Valways (e, s) ->
concat [indent i; "always "; pprint_edge_top i e; "\n"; pprint_stmnt (i+1) s]
@@ -105,12 +109,48 @@ let rec intersperse c = function
let make_io i io r = concat [indent i; io; " "; register r; ";\n"]
+let compose f g x = g x |> f
+
+let init_inputs i r = declare i "input" r
+
+let init_outputs i r = declare i "output reg" r
+
+let testbench = "module testbench;
+ reg start, reset, clk;
+ wire finish;
+ wire [31:0] return_val;
+
+ main m(start, reset, clk, finish, return_val);
+
+ initial begin
+ clk = 0;
+ start = 0;
+ reset = 0;
+ @(posedge clk) reset = 1;
+ @(posedge clk) reset = 0;
+ end
+
+ always #5 clk = ~clk;
+
+ always @(posedge clk) begin
+ if (finish == 1) begin
+ $display(\"finished: %d\", return_val);
+ $finish;
+ end
+ end
+endmodule
+"
+
let pprint_module i n m =
let inputs = m.mod_start :: m.mod_reset :: m.mod_clk :: m.mod_args in
let outputs = [m.mod_finish; m.mod_return] in
- concat [ indent i; "module "; n; "("; concat (intersperse ", " (List.map register (inputs @ outputs))); ");\n";
- fold_map (make_io (i+1) "input") inputs; fold_map (make_io (i+1) "output") outputs;
- fold_map (pprint_module_item (i+1)) m.mod_body; indent i; "endmodule\n"
+ concat [ indent i; "module "; n;
+ "("; concat (intersperse ", " (List.map (compose register fst) (inputs @ outputs))); ");\n";
+ fold_map (init_inputs (i+1)) inputs;
+ fold_map (init_outputs (i+1)) outputs;
+ fold_map (pprint_module_item (i+1)) m.mod_body;
+ indent i; "endmodule\n\n";
+ testbench
]
let print_program pp v = pstr pp (pprint_module 0 "main" v)