A Regholds its output value until the rising edge of its clock, at which time it takes on the value of its input.
1
val register = Reg(UInt(12.W))
By default, every Chisel Module has an implicit clock that is used by every register in the design. The implicit clock can be overridden for multi-clock designs.
Operations called on a register are performed on the output of the register, and the kind of operations depend on the register’s type.
You aren’t restricted to using UInts with registers, you can use any subclass of the base type chisel3.Data. This includes SInt for signed integers and a lot of other things.
1 2 3 4
// It means the value reg is of type UInt, // and you can do things you can normally do with UInts, like +, -, etc. val reg: UInt = Reg(UInt(4.W)) val reg: SInt = Reg(SInt(4.W))
RegNext()
We didn’t need to specify the register bitwidth this time. It gets inferred from the register’s output connection, in this case io.out.
1 2 3 4 5 6 7 8 9 10 11 12
classRegNextModuleextendsModule{ val io = IO(newBundle { val in = Input(UInt(12.W)) val out = Output(UInt(12.W)) })
// With name and init value val register = RegNext(io.in + 1.U, 0.U)
// register bitwidth is inferred from io.out io.out := RegNext(io.in + 1.U) }
In the latter case, register name is generated instead of explicity defined.
Create a register that resets to a given value with RegInit.
1 2
val myReg = RegInit(UInt(12.W), 0.U) val myReg = RegInit(0.U(12.W))
The generated verilog now has a block that checks if (reset) to reset the register to 0, inside the always @(posedge clock) block.
The register is still initialized to random junk before reset is called.
The PeekPokeTesters always call reset before running your test, but you can manually call reset as well using the reset(n) function, where reset is high for n cycles.
Between calls to poke() and expect(), there is a call to step(1). This tells the test harness to tick the clock once, which will cause the register to pass its input to its output.
Calling poke() on an input immediately propagates the updated values through combinational logic. Calling step() is only needed to update state elements in sequential logic.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
classRegisterModuleextendsModule{ val io = IO(newBundle { val in = Input(UInt(12.W)) val out = Output(UInt(12.W)) })
Registers are very similar to wires in terms of control flow. They have last connect semantics and can be assigned to conditionally with when, elsewhen, and otherwise.
Shift Register
Each element is a single bit wide.
Has a 4-bit output signal.
Takes a single input bit, which is the next value into the shift register.
Outputs the parallel output of the shift register, with the most significant bit being the last element of the shift register and the least significant bit being the first element of the shift register. Cat may come in handy.
The output initializes at b0001.
Shifts each clock cycle (no enable signal).
Note in Chisel, subword assignment IS ILLEGAL; something like out(0) := in will not work.
1 2 3 4 5 6 7 8 9 10 11
classMyShiftRegister(val init: Int = 1) extendsModule{ val io = IO(newBundle { val in = Input(Bool()) val out = Output(UInt(4.W)) })
val state = RegInit(UInt(4.W), init.U) val nextState = (state << 1) | io.in state := nextState io.out := state }
classMyOptionalShiftRegister(val n: Int, val init: BigInt = 1) extendsModule{ val io = IO(newBundle { val en = Input(Bool()) val in = Input(Bool()) val out = Output(UInt(n.W)) })
val state = RegInit(init.U(n.W)) val nextState = (state << 1) | io.in when (io.en) { state := nextState } io.out := state }
Clocks and resets can be overridden separately or together with withClock() {}, withReset() {}, and withClockAndReset() {}.
Clocks have their own type in Chisel Clock and should be declared as such.
Reset is always synchronous and of type Bool. Bool can be converted to Clocks by calling asClock() on them, but you should be careful that you aren’t doing something silly.
(?) Also note that chisel-testers do not currently have complete support for multi-clock designs.
// we need to import multi-clock features import chisel3.experimental.{withClock, withReset, withClockAndReset}
classClockExamplesextendsModule{ val io = IO(newBundle { val in = Input(UInt(10.W)) val alternateReset = Input(Bool()) val alternateClock = Input(Clock()) val outImplicit = Output(UInt()) val outAlternateReset = Output(UInt()) val outAlternateClock = Output(UInt()) val outAlternateBoth = Output(UInt()) })
val imp = RegInit(0.U(10.W)) imp := io.in io.outImplicit := imp
withReset(io.alternateReset) { // everything in this scope with have alternateReset as the reset val altRst = RegInit(0.U(10.W)) altRst := io.in io.outAlternateReset := altRst }