While循环与非恒定循环条件,但使用参数
我目前正试图编译一个使用两个while循环的移位器。 For-loops,shift功能和日志功能是不可能的。但是,当我尝试编译它时,它会在指定的行处抛出“具有非恒定循环条件的循环”错误。该线的边际条件是i < j,其中j是N-1,N是参数。我的问题是,由于N是一个参数,为什么即使在编译时它也不是常量,因此被认为是一个恒定的循环条件?While循环与非恒定循环条件,但使用参数
下面是代码:
module shifter(input logic [0:0] SW0, SW1, SW2, SW3, SW4, SW5, SW6, SW7, SW8, SW9, SW10,
input logic [0:0] KEY0, KEY1,
output logic [0:0] LEDG0, LEDG1, LEDG2, LEDG3, LEDG4, LEDG5, LEDG6, LEDG7);
parameter N=8;
//receive input from switches
logic [7:0] bits = '0;
logic [7:0] out = '0;
logic [0:0] move = '0;
logic [2:0] shift = '0;
logic next = 1;
always_comb
begin
bits[7] = SW7[0];
bits[6] = SW6[0];
bits[5] = SW5[0];
bits[4] = SW4[0];
bits[3] = SW3[0];
bits[2] = SW2[0];
bits[1] = SW1[0];
bits[0] = SW0[0];
shift[2] = SW10[0];
shift[1] = SW9[0];
shift[0] = SW8[0];
end
logic i = 0;
logic k = 0;
logic [31:0] j = N - 1;
[email protected](negedge KEY0)
begin
k <= shift[2:0];
do
begin
move <= bits[0];
do
begin
bits[i] <= bits[next];
i <= i + 1;
next <= i + 1;
end
while (i < j); //<-------indicated line
bits[7] <= move;
k <= k - 1;
end
while(k > 0);
out <= bits;
end
always_comb
begin
LEDG0 = out[0];
LEDG1 = out[1];
LEDG2 = out[2];
LEDG3 = out[3];
LEDG4 = out[4];
LEDG5 = out[5];
LEDG6 = out[6];
LEDG7 = out[7];
end
endmodule
的问题不在于j
,你可以很容易地解决这个问题,通过改变其声明的参数:
parameter j = N -1;
真正的问题是i
和您正在使用非阻止分配到i
。所以while
进入无限循环,因为(i<j)
从来没有机会改变 - 它总是0.
您将需要一个不同的方法来解决这个问题。
几个问题:
-
i
,k
和next
被定义为单位。他们的价值不能超过一个。声明为:parameter j = N - 1; bit [$clog2(N):0] next = 1; bit [$clog2(N):0] i = 0; logic [2:0] k = 0;
当您指定
i
,k
和next
你需要使用阻塞赋值(=
)。非阻塞(<=
)推迟更新;每个循环将评估i<j
,k>0
,i + 1;
与他们的前negedge KEY0
价值。阻塞赋值也应该在你的任务用于
move
和bits
出于同样的原因为i
,k
和next
。i
和next
需要设置为0和1,每个回路k
。bits
被分配两个不同的总是块,因此它不能合成。的
k
环不能静态UNROLL这也意味着它不会合成
可以通过从[email protected](negedge KEY0)
的循环逻辑移入的底部解决分2,3,4,和5 always_comb
已经指定bits
。然后将非阻塞更改为阻止已移动的逻辑。
据我所知,并不是每个合成器都支持while循环。即使您的合成器支持while循环,它也必须静态展开;所有可综合循环的要求。
我猜这是一个任务,你的老师要求你做一个没有for-loops的移位器。有一种方法可以在没有任何循环的情况下完成这项任务,并且可以减少比目前少得多的代码和变量。我不会给你代码,因为我认为这是作业。我会建议考虑和比较的概念:
>>
)和算术降档(>>>
)运营商-
case
语句(+:
),也可以被称作范围切片
您可能还需要对位级联(例如:{a,b}
)读取并复制器(例如:{4{1'b1}}
)。
尝试'我 noobuntu
@noobuntu我试过了,它抛出了另一个错误,说“循环必须在5000次迭代内终止” – user7231602
这通常是用for-循环。为什么认为这是不可能的? – toolic