单精度浮点乘法器.docx
《单精度浮点乘法器.docx》由会员分享,可在线阅读,更多相关《单精度浮点乘法器.docx(22页珍藏版)》请在冰豆网上搜索。
单精度浮点乘法器
EDA/SOPC课程设计报告
题目:
单精度浮点乘法器
姓名:
张恺
学号:
120260230
同组人:
刘龙
指导教师:
王晨旭
成绩:
第1章课程设计的要求
1.1课程设计的目的
●通过课堂所讲授的内容以及私下查阅资料,自主完成课程设计的题目,提高编程能力,培养用计算机解决实际问题的能力,积累调试程序的经验,更好的消化老师课堂所讲授的内容,对Verilog这种语言也有了更深的了解;
●掌握较大工程的基本开发技能;
●培养综合运用Modelsim,ISE,Debussy工具进行硬件开发的能力;
●培养数字系统设计的基本能力;
●通过课设积累起的编程以及硬件的能力对于今后的考研抑或是找工作都有非常实际性的效果;
1.2课程设计的条件
●设计条件1:
gVim编辑器以及Mentor公司开发的FPGA仿真软件Modelsim;
●设计条件2:
Xilinx公司开发的硬件设计工具ISE以及Xilinx公司的开发板;
●设计条件3:
虚拟机环境下的Linux系统具有的DesignCompiler工具;
●设计条件4:
虚拟机环境下的Linux系统具有的SDF工具以及Debussy工具;
1.3课程设计的要求
●设计要求1:
能够在Modelsim工具下正确的完成程序的编译以及成功的实现波形的仿真;
●设计要求2:
能够在ISE工具下正确的完成程序的综合以及合理的绑定管脚并成功的将程序下载到开发板里,在开发板中实现程序的功能;
●设计要求3:
能够在虚拟机的Linux系统下采用DesignCompiler完成逻辑综合,并且评估其时序面积;
●设计要求4:
能够在虚拟机的Linux系统下完成SDF反标仿真;
第2章课程设计的内容
2.1设计思路
对于单精度浮点乘法器这一课程题目,重点在于正确理解IEEE-754标准,设计出符合IEEE-754标准的单精度浮点乘法器。
2.1.1符合IEEE-754标准的单精度浮点乘法器规格
单精度浮点数32位由高位至低位可划分为1位符号位(s),8位阶码(e),23位尾数(f)。
0图2-1单精度浮点数的规格
2.1.2操作数类型
符号/1位
阶码/8位
尾数/23位
NaN
0/1
非0
无穷
0/1
23’b0
0
0/1
任意
正常
0/1
(0,255)
任意
表2-1
说明:
1、NaN和任何数相乘都为NaN;
2、无穷和0相乘为NaN,和其他数相乘都为无穷;
3、0和替他数相乘都为0;
4、正常数和正常数相乘再对他们的乘积进行判断(以上的每一种情况都是在其前面情况不成立情况下进行的);
5、如flout_a与flout_b中有至少一个异常,那么flout_c的尾数部分为优先级高的异常情况的尾数部分,无穷和0相乘特殊,指定其尾数为23’b01,0的符号位为0,其他为sign_a^sign_b;
2.1.3运算规则
两个规格化的单精度浮点数相乘时,运算规则如下:
(1)符号位相异或得结果;
(2)阶码为e=(e1-127)+(e2-127)+127;(3)尾数为两个尾数都扩展一位后再相乘,得出的为一个48位数cf1,取出cf1的第24位至第48位赋给cf3,即cf3=cf1[47:
23],此时若cf1[22]=0,舍去第1位至23位,若cf1[22]=1,向第24位进1,并且舍去第1位至第23位;尾数规格化:
判断cf3[24]是否为1,若cf3[24]=1,cf3右移1位,阶码位加1,若cf3[24]=0,则不用进行规格化;最后尾数取cf3[22:
0]。
2.1.4逻辑门级框图
图2-2逻辑门级框架简图
2.2软件流程图
图2-3总流程图
图2-4计算部分详细流程图
2.3HDL代码阐述
modulemux(flout_a,flout_b,clk,en,rst,flout_c,yichu);
modulemux(flout_a,flout_b,clk,en,rst,flout_c,yichu);
input[31:
0]flout_a;
input[31:
0]flout_b;//设置两个输入的单精度浮点数
inputclk;//时钟信号
inputen;//使能信号
inputrst;//复位信号
output[31:
0]flout_c;//输出的单精度浮点数
output[1:
0]yichu;//溢出信号
reg[31:
0]flout_c;
reg[1:
0]yichu;//变量类型声明
regsign_a,sign_b,sign_c;//符号位
reg[7:
0]zhishu_a,zhishu_b,zhishu_c;//阶码
reg[23:
0]zz_a,zz_b;
reg[47:
0]zz_c;//尾数
regjiayi;//中间变量
always@(posedgeclkornegedgerst)begin
if(~rst)begin
sign_a<=0;
sign_b<=0;
zhishu_a<=0;
zhishu_b<=0;
zz_a<=0;
zz_b<=0;
end//输入复位模块
elseif(en)begin
sign_a<=flout_a[31];
sign_b<=flout_b[31];
zhishu_a<=flout_a[30:
23];
zhishu_b<=flout_b[30:
23];
zz_a<={1'b1,flout_a[22:
0]};
zz_b<={1'b1,flout_b[22:
0]};
end//使能赋初值模块
end
always@(sign_aorsign_borzhishu_aorzhishu_borzz_aorzz_b)begin
if(~rst)begin
zhishu_c=0;
zz_c=0;
sign_c=0;
yichu=2'b01;
end//输出复位模块
elsebegin
if(zhishu_a==255&&(|zz_a[22:
0]))begin
zhishu_c=zhishu_a;
yichu=2'b11;
zz_c[46:
23]=zz_a;
sign_c=sign_a^sign_b;
end//数a不是一个数与数b任何数相乘都是不是一个数
elseif(zhishu_b==255&&(|zz_b[22:
0]))begin
zhishu_c=zhishu_b;
yichu=2'b11;
zz_c[46:
23]=zz_b;
sign_c=sign_a^sign_b;
end//数b不是一个数与数a任何数相乘都是不是一个数
elseif(zhishu_a==255&&(~(|zz_a[22:
0])))begin
if(zhishu_b==255&&(~(|zz_b[22:
0])))begin
zhishu_c=zhishu_a;
yichu=2'b10;
zz_c[46:
23]=zz_a;
sign_c=sign_a^sign_b;
end//数a无穷与数b无穷相乘还是无穷
elseif(zhishu_b==0)begin
zhishu_c=zhishu_a;
yichu=2'b11;
zz_c[46:
23]=1'b1;
sign_c=sign_a^sign_b;
end//数a无穷与数b0相乘为不是一个数
elseif(zhishu_b<255&&zhishu_b>0)begin
zhishu_c=zhishu_a;
yichu=2'b10;
zz_c[46:
23]=zz_a;
sign_c=sign_a^sign_b;
end//数a无穷与数b规格化数相乘为无穷
end
elseif(zhishu_b==255&&(~(|zz_b[22:
0])))begin
if(zhishu_a==0)begin
zhishu_c=zhishu_b;
yichu=2'b11;
zz_c[46:
23]=zz_b+1'b1;
sign_c=sign_a^sign_b;
end//数b无穷与数a0相乘为不是一个数
elseif(zhishu_a<255&&zhishu_a>0)begin
zhishu_c=zhishu_b;
yichu=2'b10;
zz_c[46:
23]=zz_b;
sign_c=sign_a^sign_b;
end//数b无穷与数a规格化数相乘为无穷
end
elseif((zhishu_a==0)||(zhishu_b==0))begin
yichu=2'b00;
zhishu_c=8'b00000000;
sign_c=0;
if(~(|zhishu_a))begin
zz_c[46:
23]=zz_a;
end
elsebegin
zz_c[46:
23]=zz_b;
end
end//数a0与数b0相乘还为0
elsebegin
sign_c=sign_a^sign_b;
zhishu_c=zhishu_a+zhishu_b-127;
zz_c=zz_a*zz_b;
if(zz_c[22]==1)begin
jiayi=1'b0;
zz_c[47:
23]=zz_c[47:
23]+1'b1;//zz_c[45:
23]
end
elseif(zz_c[47]==1)begin
zz_c[47:
23]={1'b0,zz_c[47:
24]};
jiayi=1'b1;
end
elsebegin
jiayi=1'b0;
zz_c[47:
23]=zz_c[47:
23];//zz_c[45:
23]
end
if(jiayi)begin
zhishu_c=zhishu_c+1;
end//数a规格化数与数b规格化数相乘按照ieee-754标准进行计算
if(zhishu_c>=255&&(|zz_c))begin
zhishu_c=8'hff;
yichu=2'b11;
end//得出的结果为不是一个数
if(zhishu_c>=255&&(~(|zz_c)))begin
zhishu_c=8'hff;
yichu=2'b10;
end//得出的结果为无穷
elseif(zhishu_a+zhishu_b<=127)begin
yichu=2'b00;
zhishu_c=8'b00000000;
sign_c=0;
end//得出的结果为0
elsebegin
yichu=2'b01;
zhishu_c=zhish