题目
将下面C函数改写成Verilog/VHDL代码
int seqsum(int a, int b){
int y=0;
for(int i=a; i<=b; i+=2)
y=y+i;
return y
脑子想出来的代码是这样的
第一版
module seqsum(
input [31:0]a,
input [31:0]b,
input clk,
input rst_n,
output reg [31:0] y
);
reg [31:0] cnt;
reg vld;
always@(posedge clk) begin
if (~rst_n) begin
cnt <= a;
vld <= 1'b0;
end
else if (cnt <=b) begin
cnt <= cnt + 2'd2;
vld <= 1'b1;
end
else
vld <= 1'b0;
end
always@(posedge clk) begin
if(~rst_n)
y <= 32'd0;
else if (vld == 1'b1)
y <= y + cnt;
end
endmodule
但是仿真结果不对
两个问题
- vld需要时间,只有复位后的第二个时钟vld才为1,也就是说,第一个cnt时钟加不上
- 由于vld需要时间(打了一拍),所以最后一个cnt不应该加的,但也被加上了
打个补丁
module seqsum(
input [31:0]a,
input [31:0]b,
input clk,
input rst_n,
output reg [31:0] y
);
reg [31:0] cnt;
reg vld;
always@(posedge clk) begin
if (~rst_n) begin
cnt <= a;
vld <= (a<=b);//(a<=b);
end
else if (cnt+2'd2<= b) begin//+2'd2
cnt <= cnt + 2'd2;
vld <= 1'b1;
end
else
vld <= 1'b0;
end
always@(posedge clk) begin
if(~rst_n)
y <= 32'd0;
else if (vld == 1'b1)
y <= y + cnt;
end
endmodule
组合vld
既然由于时序产生问题,为何不用组合呢?
module seqsum(
input [31:0]a,
input [31:0]b,
input clk,
input rst_n,
output reg [31:0] y
);
reg [31:0] cnt;
//reg vld;
wire vld;
always@(posedge clk) begin
if (~rst_n) begin
cnt <= a;
//vld <= (a<=b);//(a<=b);
end
else if (cnt<= b) begin//+2'd2
cnt <= cnt + 2'd2;
//vld <= 1'b1;
end
//else
//vld <= 1'b0;
end
always@(posedge clk) begin
if(~rst_n)
y <= 32'd0;
else if (vld == 1'b1)
y <= y + cnt;
end
assign vld = cnt<=b;
endmodule
改完以后,啥毛病没有