verilog流水线设计


大纲

1,什么是流水线

2,什么时候用流水线

3,它的优缺点

4,使用流水线设计的实例

流水线实际上是将组合逻辑系统分割,然后在间隙插入寄存器,暂存中间数据。其思想就是要将大的操作分成尽量小的操作,每一步小的操作用的时间就越小,也就提高了频率,各小操作可以并行执行,所以提高了数据的吞吐率(操作的处理速度)。

2当对时序不满足,系统要工作的频率高时,也就是需要大的数据吞吐率的时候,具体会遇到的典型的情况如下:

(1)功能模块之间需要乒乓交换数据时,代价是增加了 memory 的数量,但是和获得的巨大性能提升相比,可以忽略不计。

(2)I/O 瓶颈,比如某个运算需要输入 8 个数据,而 memroy 只能同时提供 2 个数据,如果通过适当划分运算步骤,使用流水线反而会减少面积。

(3)片内 sram 的读操作,因为 sram 的读操作本身就是两极流水线,除非下一步操作依赖读结果,否则使用流水线是自然而然的事情。

(4)组合逻辑太长,比如(a+b)*c,那么在加法和乘法之间插入寄存器是比较稳妥的做法。

优点:

缺点:

4使用流水设计的实例

以一个8位全加器为实例,如下:

1)非流水线实现方式

module adder_8bits(din_1, clk, cin, dout, din_2, cout);
    input [7:0] din_1;
    input clk;
    input cin;
    output [7:0] dout;
    input [7:0] din_2;
    output cout;
     
     reg [7:0] dout;
     reg       cout;
     
     always @(posedge clk) begin
        {cout,dout} <= din_1 + din_2 + cin;
     end

endmodule2)2级流水线实现方式:

module adder_4bits_2steps(cin_a, cin_b, cin, clk, cout, sum);
    input [7:0] cin_a;
    input [7:0] cin_b;
    input cin;
    input clk;
    output cout;
    output [7:0] sum;
     
     reg cout;
     reg cout_temp;
     reg [7:0] sum;
     reg [3:0] sum_temp;
     
     always @(posedge clk) begin
        {cout_temp,sum_temp} = cin_a[3:0] + cin_b[3:0] + cin;
     end
     
     always @(posedge clk) begin
        {cout,sum} = {{1'b0,cin_a[7:4]} + {1'b0,cin_b[7:4]} + cout_temp, sum_temp};
     end
endmodule
注意:这里在always块内只能用阻塞赋值方式,否则会出现逻辑上的错误!

(3)4级流水线实现方式:

module adder_8bits_4steps(cin_a, cin_b, c_in, clk, c_out, sum_out);
    input [7:0] cin_a;
    input [7:0] cin_b;
    input c_in;
    input clk;
    output c_out;
    output [7:0] sum_out;
     
     reg c_out;
     reg c_out_t1, c_out_t2, c_out_t3;
     
     reg [7:0] sum_out;
     reg [1:0] sum_out_t1;
     reg [3:0] sum_out_t2;
     reg [5:0] sum_out_t3;
     
     always @(posedge clk) begin
        {c_out_t1, sum_out_t1} = {1'b0, cin_a[1:0]} + {1'b0, cin_b[1:0]} + c_in;
     end
     
     always @(posedge clk) begin
        {c_out_t2, sum_out_t2} = {{1'b0, cin_a[3:2]} + {1'b0, cin_b[3:2]} + c_out_t1, sum_out_t1};
     end
     
     always @(posedge clk) begin
        {c_out_t3, sum_out_t3} = {{1'b0, cin_a[5:4]} + {1'b0, cin_b[5:4]} + c_out_t2, sum_out_t2};
     end
     
     always @(posedge clk) begin
        {c_out, sum_out} = {{1'b0, cin_a[7:6]} + {1'b0, cin_b[7:6]} + c_out_t3, sum_out_t3};
     end
endmodule

对应的资源占用以及仿真波形如下:

emmm,后来才发现这只是功能仿真,看不出来组合逻辑器件的延时效果的~

优质内容筛选与推荐>>
1、ScriptManager.RegisterStartupScript方法
2、Struts2中使用OGNL表达式语言访问静态方法和静态属性
3、md5 结合 crypt =无敌密码? - 转
4、C#破解access数据库密码方法
5、字符串


长按二维码向我转账

受苹果公司新规定影响,微信 iOS 版的赞赏功能被关闭,可通过二维码转账支持公众号。

    阅读
    好看
    已推荐到看一看
    你的朋友可以在“发现”-“看一看”看到你认为好看的文章。
    已取消,“好看”想法已同步删除
    已推荐到看一看 和朋友分享想法
    最多200字,当前共 发送

    已发送

    朋友将在看一看看到

    确定
    分享你的想法...
    取消

    分享想法到看一看

    确定
    最多200字,当前共

    发送中

    网络异常,请稍后重试

    微信扫一扫
    关注该公众号