1、32bit乘法器乘法器:乘法用运算符表示:左移一表示*2,左移两位表示*4,左移3位表示*8
2、设计原理:如:1111*1011 = (1111*0001) + (1111*0010 ) + (1111* 0000) + (1111*1000);解释:1111分别乘以1011的每一个数相加。
那么就可以判断每一位1011是否是1,是一那么就让1111位移对应位表示相乘;如:1111*0010表示左移两位;(走后全部加起来)。
代码设计:又可以在每一个周期左移一位1111,再判断1011每一位(每个周期也是左移判断一位)是否为1,如果是1,那么表示这一位可以相加。
3、参考代码
module mul(
input clk , //system clock 50MHz
input rst_n , //reset, low valid
input [31:0] mul_a , //
input [31:0] mul_b , //
input mul_vld ,
output res_vld , //
output [63:00] res_mul //
);
reg [64:0] tmp_b;//最后输出结果
reg data_vld;
reg [64:0] tmp_a;//{32'b0,a}
reg mul_flag;
reg [4:00] cnt ; //Counter 32次
wire add_cnt ; //Counter Enable
wire end_cnt ; //Counter Reset
//mul_vld_r
always @(posedge clk or negedge rst_n)begin
if(!rst_n)begin
mul_flag <= 1'b0;
end
else if(mul_vld)begin
mul_flag <= 1'b1;
end
else if(end_cnt)begin
mul_flag <= 1'b0;
end
end //always end
//cnt
always @(posedge clk or negedge rst_n)begin
if(!rst_n)begin
cnt <= 'd0;
end
else if(add_cnt)begin
if(end_cnt)begin
cnt <= 'd0;
end
else begin
cnt <= cnt + 1'b1;
end
end
else begin
cnt <= cnt;
end
end
assign add_cnt = mul_flag;
assign end_cnt = add_cnt && cnt >= (32 - 1);
//tmp_a tmp_b
always @(posedge clk or negedge rst_n)begin
if(!rst_n)begin
tmp_a <= 64'b0;
tmp_b <= 64'b0;
end
else if(mul_vld)begin//初值
tmp_a <= {32'b0,mul_a};
tmp_b <= 64'b0;
end
else if(mul_flag)begin
if(mul_b[cnt] == 1)begin
tmp_b <= tmp_a + tmp_b;
end
tmp_a <= {tmp_a[62:0] ,1'b0};
end
end //always end
//data_vld
always @(posedge clk or negedge rst_n)begin
if(!rst_n)begin
data_vld <= 1'b0;
end
else begin
data_vld <= end_cnt;
end
end //always end
assign res_mul = tmp_b;
assign res_vld = data_vld;
endmodule
没有回复内容