llvm / circt

Circuit IR Compilers and Tools
https://circt.org
Other
1.67k stars 298 forks source link

[FIRRTL][Seq] Running without randomization needs Async Reset reg initialization #4835

Closed seldridge closed 1 year ago

seldridge commented 1 year ago

The following FIRRTL compiled to Verilog needs to have an initial block that does a reset if reset is asserted. This happens without randomization, but not with:

circuit Foo :
  module Foo :
    input clock : Clock
    input reset : AsyncReset
    input d : UInt<1>
    output q : UInt<1>

    reg q_REG : UInt<1>, clock with :
      reset => (reset, UInt<1>("h0"))
    q_REG <= d
    q <= q_REG

This compiles to:

// Generated by CIRCT unknown git version
module Foo(
  input  clock,
         reset,
         d,
  output q
);

  reg q_REG;
  always @(posedge clock or posedge reset) begin
    if (reset)
      q_REG <= 1'h0;
    else
      q_REG <= d;
  end // always @(posedge, posedge)
  assign q = q_REG;
endmodule

This should have the following, possibly guarded only by ifndef SYNTHESIS:

initial begin
  if (reset)
    q_REG = 1'h0;
end
darthscsi commented 1 year ago

Isn't the always block going to be executed at t0 after reset gets a value? (x -> 1 ?)

seldridge commented 1 year ago

If you do an explicit x->1 transition, then I think this works. However, if the circuit is initialized to 1 then no reset happens. I don't think you get a free x->1.