在verilog中添加和移位

时间:2014-05-23 20:32:12

标签: algorithm verilog multiplying

这是关于添加和移位乘法的verilog代码 当我编译并初始化并添加输入和输出以获取波形并模拟它们时,我看不到任何结果,一切都是z ......问题是什么?

module multi(a, b, ans);
    input [3:0] a;
    input [3:0] b;
    output reg [15:0] ans;
    reg [15:0] aa;
    reg [15:0] bb;  
    reg [15:0] tmp=0;
    reg flag = 1'b1;

    always @( a, b)
        begin       
            aa = a;
            bb = b;
            while ( flag == 1'b1 )
            begin
            if( bb[0] == 1'b1 )
                tmp = tmp + aa; 
            aa = aa << 1;
            bb = bb >> 1;
            if ( bb==0 )
                flag = 1'b0;
            end
            ans = tmp;
        end  

endmodule

2 个答案:

答案 0 :(得分:1)

使用此代码时,有许多事情看起来很奇怪。

首先,你没有时钟输入,但正试图用组合逻辑做任何事情。

其次是在reg语句中将标志设置为1意味着您的模块只能进行单次乘法。顺便说一下,使用复位信号比在reg线中使用这种初始化更为正常(特别是对于ASIC设计)。

第三,4位数乘以4位数将导致8位答案,而不是16位。

在任何情况下,除非您以非常高的速度工作,否则您应该能够在一个周期内执行乘法运算。

以下是一些更自然地编写此代码的方法:

组合风格

module multi(a, b, ans);
    input [3:0] a;
    input [3:0] b;
    output reg [7:0] ans;

    always @(*)
        begin 
            ans = a * b;      
        end  
endmodule

时钟风格

module multi(clk, a, b, ans);
    input [3:0] a;
    input [3:0] b;
    output reg [7:0] ans;

    always @(posedge clk)
        begin 
            ans <= a * b;      
        end  
endmodule

答案 1 :(得分:0)

您的输入为4位宽,并且您指定为16位变量,前12位未分配,即x

input [3:0] a;
reg [15:0] aa;
//...
aa = a;

要分配aa的所有位,请尝试以下操作:

aa = {12'b0, a}; 
//{} is bit concatenation 

或者签名扩展a到16位,使用{width{value}}复制重复MSB 12次:

aa = {{12{a[3]}}, a};