我正在尝试创建一个涉及移位寄存器的数据路径,但我希望在等待新输入时能够停止整个事情。我看到标准库中有一个带有启用行的移位寄存器(虽然默认为true)。
问题在于,当我尝试使用它时,编译的verilog在启用较低时似乎并没有实际停止移位寄存器。
考虑这个凿子代码:
package SR
import Chisel._
class SR extends Module {
val io = new Bundle {
val in = UInt(INPUT, 8)
val enable = Bool(INPUT)
val out = UInt(OUTPUT, 8)
}
io.out:= ShiftRegister(io.in, 10, io.enable)
}
class SRTests(c: SR) extends Tester(c) {
}
object SR {
def main(args: Array[String]): Unit = {
val tutArgs = args.slice(1, args.length)
chiselMainTest(tutArgs, () => Module(new SR())) {
c => new SRTests(c) }
}
}
我得到以下verilog:
module SR(input clk,
input [7:0] io_in,
input io_enable,
output[7:0] io_out
);
reg [7:0] R0;
reg [7:0] R1;
reg [7:0] R2;
reg [7:0] R3;
reg [7:0] R4;
reg [7:0] R5;
reg [7:0] R6;
reg [7:0] R7;
reg [7:0] R8;
reg [7:0] R9;
wire[7:0] T10;
`ifndef SYNTHESIS
integer initvar;
initial begin
#0.002;
R0 = {1{$random}};
R1 = {1{$random}};
R2 = {1{$random}};
R3 = {1{$random}};
R4 = {1{$random}};
R5 = {1{$random}};
R6 = {1{$random}};
R7 = {1{$random}};
R8 = {1{$random}};
R9 = {1{$random}};
end
`endif
assign io_out = R0;
assign T10 = io_enable ? io_in : R9;
always @(posedge clk) begin
R0 <= R1;
R1 <= R2;
R2 <= R3;
R3 <= R4;
R4 <= R5;
R5 <= R6;
R6 <= R7;
R7 <= R8;
R8 <= R9;
if(io_enable) begin
R9 <= io_in;
end
end
endmodule
似乎移位寄存器只保持第一个固定值而不是整个值。例如,如果你在连续的时钟周期中写入1,2,3,4,5但只为1,2,3保持高电平,则3将正确保持,但1和2最终会移出整个移位寄存器将填充值3。
我想要像凿子教程中看到的移位寄存器示例一样的行为。问题是我需要长的,可参数化的移位寄存器,因此不能手动编写每个寄存器。我非常感谢一个凿子代码的例子,它实现了一个带有启用行为的移位寄存器,就像在凿子教程中看到的那样,但是参数化不同,如标准库中所见。
答案 0 :(得分:0)
您可以在Chisel存储库的src / main / scala / ChiselUtil.scala中看到ShiftRegister的源代码:
object ShiftRegister
{
def apply[T <: Data](in: T, n: Int, en: Bool = Bool(true)): T =
{
// The order of tests reflects the expected use cases.
if (n == 1) {
RegEnable(in, en)
} else if (n != 0) {
RegNext(apply(in, n-1, en))
} else {
in
}
}
}
创建了RegNexts的递归链,但是基本情况创建了一个RegEnable。例如:
RegNext(RegNext(RegNext(RegEnable(in, en))))
您可以将该代码复制到您的hello世界中,将其重命名为object MyShiftRegister
,然后根据您的需要修改该循环。
我认为你在寻找的是:
} else if (n != 0) {
RegEnable(apply(in, n-1, en), en)
} ...
作为一般策略,我建议写出代码的样子&#34; un-rolled&#34;然后考虑如何打包它#34;转换为简洁且可参数化的Scala代码。