📄 boot_mul.v
字号:
module boot_mul(a_i,b_i,clk_i,sign_i,mul_o,sign_b,mul_tree);
parameter length=32;
parameter number=length/2;
input[length-1:0] a_i;
input[length-1:0] b_i;
input clk_i;
input sign_i; //sign_i=0,unsign operation; otherwise, sign operation;
output[2*length-1:0] mul_o;
output[63:0]mul_tree;
output[2*length-1:0] sign_b;
wire[length:0] temp_a;
wire sign_a;
wire[length+1:0] temp_b;
//unsigned and signed preprocess
assign temp_a={a_i[length-1]&sign_i,a_i};//use the sign value to extern
assign temp_b={{2{b_i[length-1]&sign_i}},b_i};//use the sign value to extern
//unsigned multiplied result for compare
assign sign_b= a_i*b_i;
wire[number:0] as,ov,te,sub_valid;
bootcoder inst0 ({temp_b[1:0],1'b0},as[0], ov[0], te[0], sub_valid[0]);
bootcoder inst1 ( temp_b[3:1], as[1], ov[1], te[1], sub_valid[1]);
bootcoder inst2 ( temp_b[5:3], as[2], ov[2], te[2], sub_valid[2]);
bootcoder inst3 ( temp_b[7:5], as[3], ov[3], te[3], sub_valid[3]);
bootcoder inst4 ( temp_b[9:7], as[4], ov[4], te[4], sub_valid[4]);
bootcoder inst5 ( temp_b[11:9], as[5], ov[5], te[5], sub_valid[5]);
bootcoder inst6 ( temp_b[13:11], as[6], ov[6], te[6], sub_valid[6]);
bootcoder inst7 ( temp_b[15:13], as[7], ov[7], te[7], sub_valid[7]);
bootcoder inst8 ( temp_b[17:15], as[8], ov[8], te[8], sub_valid[8]);
bootcoder inst9 ( temp_b[19:17], as[9], ov[9], te[9], sub_valid[9]);
bootcoder inst10( temp_b[21:19], as[10],ov[10],te[10],sub_valid[10]);
bootcoder inst11( temp_b[23:21], as[11],ov[11],te[11],sub_valid[11]);
bootcoder inst12( temp_b[25:23], as[12],ov[12],te[12],sub_valid[12]);
bootcoder inst13( temp_b[27:25], as[13],ov[13],te[13],sub_valid[13]);
bootcoder inst14( temp_b[29:27], as[14],ov[14],te[14],sub_valid[14]);
bootcoder inst15( temp_b[31:29], as[15],ov[15],te[15],sub_valid[15]);
bootcoder inst16( temp_b[33:31], as[16],ov[16],te[16],sub_valid[16]);
reg[length+1:0] temp0 ;
reg[length+3:0] temp1 ;
reg[length+5:0] temp2 ;
reg[length+7:0] temp3 ;
reg[length+9:0] temp4 ;
reg[length+11:0] temp5 ;
reg[length+13:0] temp6 ;
reg[length+15:0] temp7 ;
reg[length+17:0] temp8 ;
reg[length+19:0] temp9 ;
reg[length+21:0] temp10;
reg[length+23:0] temp11;
reg[length+25:0] temp12;
reg[length+27:0] temp13;
reg[length+29:0] temp14;
reg[length+31:0] temp15;
reg[length+31:0] temp16;
reg[16:0] temp17;
//get partial result
always @(temp_a or ov or as or te)
begin
temp0 <= partient(ov[0], as[0], te[0], temp_a);
temp1 <= partient(ov[1], as[1], te[1], temp_a)<<2;
temp2 <= partient(ov[2], as[2], te[2], temp_a)<<4;
temp3 <= partient(ov[3], as[3], te[3], temp_a)<<6;
temp4 <= partient(ov[4], as[4], te[4], temp_a)<<8;
temp5 <= partient(ov[5], as[5], te[5], temp_a)<<10;
temp6 <= partient(ov[6], as[6], te[6], temp_a)<<12;
temp7 <= partient(ov[7], as[7], te[7], temp_a)<<14;
temp8 <= partient(ov[8], as[8], te[8], temp_a)<<16;
temp9 <= partient(ov[9], as[9], te[9], temp_a)<<18;
temp10<= partient(ov[10],as[10],te[10],temp_a)<<20;
temp11<= partient(ov[11],as[11],te[11],temp_a)<<22;
temp12<= partient(ov[12],as[12],te[12],temp_a)<<24;
temp13<= partient(ov[13],as[13],te[13],temp_a)<<26;
temp14<= partient(ov[14],as[14],te[14],temp_a)<<28;
temp15<= partient(ov[15],as[15],te[15],temp_a)<<30;
temp16<= partient(ov[16],as[16],te[16],temp_a)<<32;//if it is sign operation, the line is lost;if it is unsign, it is a or 0
temp17<= { sub_valid[16],
1'b0,sub_valid[15],
1'b0,sub_valid[14],
1'b0,sub_valid[13],
1'b0,sub_valid[12],
1'b0,sub_valid[11],
1'b0,sub_valid[10],
1'b0,sub_valid[9],
1'b0,sub_valid[8],
1'b0,sub_valid[7],
1'b0,sub_valid[6],
1'b0,sub_valid[5],
1'b0,sub_valid[4],
1'b0,sub_valid[3],
1'b0,sub_valid[2],
1'b0,sub_valid[1],
1'b0,sub_valid[0]};
end
// ********general add to test the result
wire[63:0] sum0;
wire[63:0] sum1;
wire[63:0] sum2;
wire[63:0] sum3;
wire[63:0] sum4;
wire[63:0] sum5;
wire[63:0] sum6;
wire[63:0] sum7;
wire[63:0] add0;
wire[63:0] add1;
wire[63:0] add2;
wire[63:0] add3;
wire[63:0] c0;
wire[63:0] c1;
wire[63:0] c2;
wire[63:0] cout;
assign sum0 = {{30{temp0[length+1]}},temp0}+{{28{temp1[length+3]}},temp1};
assign sum1 = {{26{temp2[length+5]}},temp2}+{{24{temp3[length+7]}},temp3};
assign sum2 = {{22{temp4[length+9]}},temp4}+{{20{temp5[length+11]}},temp5};
assign sum3 = {{18{temp6[length+13]}},temp6}+{{16{temp7[length+15]}},temp7};
assign sum4 = {{14{temp8[length+17]}},temp8}+{{12{temp9[length+19]}},temp9};
assign sum5 = {{10{temp10[length+21]}},temp10}+{{8{temp11[length+23]}},temp11};
assign sum6 = {{6{temp12[length+25]}},temp12}+{{4{temp13[length+27]}},temp13};
assign sum7 = {{2{temp14[length+29]}},temp14}+temp15;
assign add0 =sum0+sum1;
assign add1 =sum2+sum3;
assign add2= sum4+sum5;
assign add3= sum6+sum7;
assign c0 = add0+add1;
assign c1 = add2+add3;
assign c2 = temp16+temp17;
assign cout= c0+c1;
assign mul_o= cout+c2;
//***********************************************
//wallace tree
wire[63:0]s_l1_0_o;
wire[63:0]s_l1_1_o;
wire[63:0]s_l1_2_o;
wire[63:0]s_l1_3_o;
wire[63:0]s_l1_4_o;
wire[63:0]s_l1_5_o;
wire[63:0]c_l1_0_o;
wire[63:0]c_l1_1_o;
wire[63:0]c_l1_2_o;
wire[63:0]c_l1_3_o;
wire[63:0]c_l1_4_o;
wire[63:0]c_l1_5_o;
wire[64:0]s_l2_0_o;
wire[64:0]s_l2_1_o;
wire[64:0]s_l2_2_o;
wire[64:0]c_l2_0_o;
wire[64:0]c_l2_1_o;
wire[64:0]c_l2_2_o;
wire[63:0]s_l3_0_o;
wire[63:0]s_l3_1_o;
wire[63:0]c_l3_0_o;
wire[63:0]c_l3_1_o;
wire[64:0]s_l4_o;
wire[64:0]c_l4_o;
wire[63:0]mul_tree;
wire co_l2_0_o,co_l2_1_o,co_l2_2_o;
wire co_l4_o;
csa line1_0(.i0_i({{30{temp0[length+1]}},temp0}) ,.i1_i({{28{temp1[length+3]}},temp1}) ,.i2_i({{26{temp2[length+5]}},temp2}) ,.s_o(s_l1_0_o),.c_o(c_l1_0_o));
csa line1_1(.i0_i({{24{temp3[length+7]}},temp3}) ,.i1_i({{22{temp4[length+9]}},temp4}) ,.i2_i({{20{temp5[length+11]}},temp5}) ,.s_o(s_l1_1_o),.c_o(c_l1_1_o));
csa line1_2(.i0_i({{18{temp6[length+13]}},temp6}) ,.i1_i({{16{temp7[length+15]}},temp7}) ,.i2_i({{14{temp8[length+17]}},temp8}) ,.s_o(s_l1_2_o),.c_o(c_l1_2_o));
csa line1_3(.i0_i({{12{temp9[length+19]}},temp9}) ,.i1_i({{10{temp10[length+21]}},temp10}),.i2_i({{8{temp11[length+23]}},temp11}),.s_o(s_l1_3_o),.c_o(c_l1_3_o));
csa line1_4(.i0_i({{6{temp12[length+25]}},temp12}),.i1_i({{4{temp13[length+27]}},temp13}) ,.i2_i({{2{temp14[length+29]}},temp14}),.s_o(s_l1_4_o),.c_o(c_l1_4_o));
csa line1_5(.i0_i(temp15) ,.i1_i(temp16) ,.i2_i({{47{1'b0}},temp17}) ,.s_o(s_l1_5_o),.c_o(c_l1_5_o));
C42_l line2_0(.i0(s_l1_0_o),.i1(s_l1_1_o),.i2(s_l1_2_o), .i3(s_l1_3_o), .ci(1'b0),.d(s_l2_0_o),.c(c_l2_0_o),.co(co_l2_0_o));
C42_l line2_1(.i0(s_l1_4_o),.i1(s_l1_5_o),.i2(c_l1_0_o<<1),.i3(c_l1_1_o<<1),.ci(1'b0),.d(s_l2_1_o),.c(c_l2_1_o),.co(co_l2_1_o));
C42_l line2_2(.i0(c_l1_2_o),.i1(c_l1_3_o),.i2(c_l1_4_o), .i3(c_l1_5_o), .ci(1'b0),.d(s_l2_2_o),.c(c_l2_2_o),.co(co_l2_2_o));
csa line3_0(.i0_i(s_l2_0_o[63:0]),.i1_i(s_l2_1_o[63:0]),.i2_i(s_l2_2_o[63:0]<<1),.s_o(s_l3_0_o),.c_o(c_l3_0_o));
csa line3_1(.i0_i(c_l2_0_o[63:0]),.i1_i(c_l2_1_o[63:0]),.i2_i(c_l2_2_o[63:0]<<1),.s_o(s_l3_1_o),.c_o(c_l3_1_o));
C42_l line4_0(.i0(s_l3_0_o),.i1(c_l3_0_o<<1),.i2(s_l3_1_o<<1),.i3(c_l3_1_o<<2),.ci(1'b0),.d(s_l4_o),.c(c_l4_o),.co(co_l4_o));
assign mul_tree=(c_l4_o<<1)+s_l4_o;
function[34:0] partient;
input ov,as,te;
input[32:0] temp_a;
//always @(temp_a or ov or as or te)
begin
//got the partient result
if(ov) //operation a_i;
begin
if(as) partient={~temp_a[length],~temp_a}; //sub
else partient={temp_a[length],temp_a}; //add
end
else if(te) //operation 2*a_i
begin
if(as) partient=~(temp_a<<1); //sub
else partient= temp_a<<1; //add
end
else
partient=0;
end
endfunction
endmodule
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -