第五篇 加法器

2024-06-04 12:28
文章标签 第五篇 加法器

本文主要是介绍第五篇 加法器,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

实验五 加法器

5.1 实验目的

  1. 掌握半加器和全加器的基本原理

  2. 掌握串行进位加法器的基本原理

  3. 掌握使用全加器实现串行进位加法器的基本原理

  4. 熟悉Verilog 代码设计

5.2 原理介绍

5.2.1 半加器

半加器和全加器是算数运算电路中的基本单元,它们是完成1位二进制数相加的一种组合逻辑电路。

如果只考虑两个加数本身,而没有考虑低位进位的加法运算,称为半加,实现半加运算的逻辑电路称为半加器。两个1位二进制的半加运算的真值表如表5.1所示,其中,a、b是两个加数,s表示和数,c_o表示进位数。

表5.1 半加运算真值表

​​

输入

输出

a

b

co

s

0

0

0

0

0

1

0

1

1

0

0

1

1

1

1

0

由真值表可得逻辑表达式:

$$
\begin{cases} s = \overline{a}\,b + a\,\overline{b} = a \bigoplus b \\ c_o = a b \end{cases}
$$

由上述表达式可以得出由异或门和门组成的半加器,如图5.1(a)所示为半加器的电路图,其输入为 a 和 b,输出为 s 和 c_o,图5.1(b)为半加器的图形符号。

(a)半加器电路         (b)半加器符号

图5.1 半加器

5.2.2 全加器

全加器是将加数、被加数和低位来的进位信号相加,并根据求和结果给出该位的进位信号。

根据全加器的功能,可列出它的真值表,如表5.2所示。其中 a 和 b 是两个加数,c_i为低位进位数,s 为本位和数(称为全加和),c_o为向高位的进位数。

表5.2 全加运算真值表

​​

输入

输出

a

b

ci

co

s

0

0

0

0

0

0

0

1

0

1

0

1

0

0

1

0

1

1

1

0

1

0

0

0

1

1

0

1

1

0

1

1

0

1

0

1

1

1

1

1

根据真值表分别画出 s 和 c_o 的卡诺图,如图5.2所示。

图5.2 全加器的s和co卡诺图

进而推导出全加器的逻辑表达式为:

$$
\begin{cases} s = \overline{a}\,\overline{b}\,c_i + \overline{a}\,b\,\overline{c_i} + a\,\overline{b}\,\overline{c_i} + a\,b\,c_i \\ \,\,\,\,\,= (\,(\,\overline{a}\,\overline{b}\,c_i\,) + (\,a\,b\,c_i\,)\,) + (\,(\,\overline{a}\,b\,\overline{c_i}\,) + (\,a\,\overline{b}\,\overline{c_i}\,)\,) \\ \,\,\,\,\,= (\,a\bigodot b\,)\,c_i + (\,a\bigoplus b\,)\,\overline{c_i} \\ \,\,\,\,\,= a\bigoplus b\bigoplus c_i \\ \\ c_o = \overline{a}\,b\,c_i + a\,\overline{b}\,c_i + a\,b \\ \,\,\,\,\,\,\,= (\,a\bigoplus b\,)\,c_i + a\,b \\ \end{cases}
$$

由上述表达式可以得出由异或门、门和门组成的全加器,如图5.3(a)所示为全加器的电路图,其输入为 a、b 和 c_i ,输出为 s 和 c_o,图5.3(b)为全加器的图形符号。

(a)全加器电路               (b)全加器符号

图5.3 全加器

5.2.3 串行进位加法器

若有多位数相加,则可采用并行相加串行进位的方式来完成。例如,有2个4位二进制数 a_3a_2a_1a_0和 b_3b_2b_1b_0相加,可以采用4个全加器构成4位数加法器,其原理图如图5.4所示。将低位的进位输出信号接到高位的进位输入端,因此,任意1位的加法运算必须在低1位的运算完成之后才能进行,这种进位方式称为串行进位。

图5.4 4位串行进位加法器

5.2.4 串行进位加(减)法器

减法运算的原理是将减法运算变成加法运算进行的。前面介绍的加法运算器既能实现加法运算,又可实现减法运算,从而简化数字系统结构。

若 n 位二进制的原码为 N_原,则与它相对应的 2 的补码为

$$
N_补 = 2^n - N_原
$$

补码与反码的关系式

$$
N_补 = N_反 + 1
$$

设两个数 a、b 相减,利用上面两个式子可得

$$
a - b = a + b_补 - 2^n = a + b_反 + 1 - 2^n
$$

上式表明,a 减 b 可由 a 加 b 的补码并减 2^n 完成。

图5.5 基于4位串行进位加法器的加减法电路

4位加减法运算电路如图5.5所示 ,具体原理如下:

    • 当 c_i = 0 时,执行加法运算。其中,第一个加数为 a_3a_2a_1a_0,第二个加数为 b_3b_2b_1b_0,加法器相加的结果 (a + b);

    • 当 c_i = 1 时,执行减法运算。首先将 b 的各位反相(求反),再加1,由此求得 b 的补码,加法器相加的结果为 (a + b_反 + 1)。

  1. 进位标志位

    • 当 c_i = 0 时,执行加法运算。进位标志位 c_o = c_4;

    • 当 c_i = 1 时,执行减法运算。由于 2^n = 2^4 = (10000)_B,相加结果与 2^n 相减可以由加法器进位输出信号完成。当进位输出信号为1时,它与 2^n 的差为0;当进位输出信号为0时,它与 2^n 的差为1,同时还会发出借位信号;因此,只要将进位信号反相即实现了减 2^n 的运算,反相后的输出为1时需要借位,故也可将其当作借位信号。进位标志位 c_o = \overline{c_4};

    进位标志位的逻辑表达式为:

    $$
    c_o = \overline{c_i}\,c_4 + c_i\,\overline{c_4} = c_i \bigoplus c_4
    $$

  2. 溢出标志位

    两个符号相反的数相加不会产生溢出,但两个符号相同的数相加,而和 s 的符号位又与加数的符号位相反,则会产生溢出。因此,我们可对最高数据位进位(c_3)和符号位进位(c_4)进行检测,判断是否产生溢出。

    • 当两个正数相加时, c_3 = 0 ,若c_4 = 1,则表明改变了结果符号位,产生溢出(上溢);

    • 当两个负数相加时, c_3 = 1 ,若c_4 = 0,则表明改变了结果符号位,产生溢出(下溢);

    溢出标志位的逻辑表达式为:

    $$
    overflow = \overline{c_3}\,c_4 + c_3\,\overline{c_4} = c_3 \bigoplus c_4
    $$

5.3 实验任务

  1. 使用Verilog HDL硬件描述语言设计实现2个3位二进制数的加减法运算;

  2. 并将此功能添加到实验四实现的计算器应用中。

5.4 设计实现

5.4.1 设计思路

在实验四实现的计算器中使用如下输入:

  • 使用SW[3:0]作为操作数a;

  • 使用SW[7:4]作为操作数b;

为了减少使用滑动开关的数量,更方便的设计有限状态机作为控制器,在本实验中,我们只使用一组滑动开关SW[3:0]​​来输入操作数a、b,如下图所示。

image-20240516170449569

image-20240516170712645

操作数b其实是来自上一个操作数a经过一个寄存器后的输出,计算器的数据通路部分框图如图所示。左上角增加了一个4位的输入寄存器。

image-20240516182011337

图5.6 计算器系统框图

如图5.6所示为本实验实现的计算器的系统框图,本实验是在实验四的基础上,添加一个加法器子模块和一个寄存器。SW3 ~ SW0作为加法器的加数 a,SW6作为加法器的进位输入 carry\_in,加法器的结果本位和数 s 以十六进制的形式显示在数码管HEX0上,并以二进制的形式显示在LEDR3 ~ LEDR0上,溢出标志位 overflow 、进位输出 c_o分别显示在LEDR5 ~ LEDR4上。

当数据选择器的选择位输入为 100 时,计算器可实现加法器的功能。当加法器的进位输入c_i = 0时,执行 (A + B) 运算;当c_i = 1时,执行 (A - B) 运算。

5.4.2 代码实现
  • 4位二选一数据选择器

    module mux2x1(// 2个4位的数据输入input       [3:0]   x,input       [3:0]   y,// 3位的选择输入input               s,// 1个4位的数据输出output  reg [3:0]   m
    );
    ​
    always@(x, y, s)
    begincase(s)1'b0: m = x;    // 当s = 0时,输出m = x1'b1: m = y;    // 当s = 1时,输出m = yendcase
    end
    ​
    endmodule

    代码5.1 mux2x1.v

    mux2x1子模块的RTL代码综合出的RTL视图如图5.7所示。

    图5.7 mux2x1子模块RTL视图

  • 6位八选一数据选择器

    module mux8x1(// 8个6位的数据输入input       [5:0]   r,input       [5:0]   t,input       [5:0]   u,input       [5:0]   v,input       [5:0]   w,input       [5:0]   x,input       [5:0]   y,input       [5:0]   z,// 3位的选择输入input       [2:0]   s,// 1个6位的数据输出output  reg [5:0]   m
    );always@(r, t, u, v, w, x, y, z, s)
    begincase(s)3'b000: m = r;      // 当s = 000时,输出m = r3'b001: m = t;      // 当s = 001时,输出m = t3'b010: m = u;      // 当s = 010时,输出m = u3'b011: m = v;      // 当s = 011时,输出m = v3'b100: m = w;      // 当s = 100时,输出m = w3'b101: m = x;      // 当s = 101时,输出m = x3'b110: m = y;      // 当s = 110时,输出m = y3'b111: m = z;      // 当s = 111时,输出m = zendcase
    end
    ​
    endmodule

    代码5.2 mux8x1.v

    mux8x1子模块的RTL代码综合出的RTL视图如图5.8所示。

    图5.8 mux8x1子模块RTL视图

  • 全加器

    module fa (input   a,      // 加数ainput   b,      // 加数binput   ci,     // 进位输入cioutput  s,      // 和数soutput  co      // 进位输出co
    );
    ​
    wire a_xor_b;
    ​
    assign a_xor_b = a ^ b;
    assign s = a_xor_b ^ ci;
    assign co = (a_xor_b & ci) | (a & b);
    ​
    endmodule

    代码5.3 fa.v

    fa子模块的RTL代码综合出的RTL视图如图5.9所示,可以看到和我们前面分析设计的结构(图5.3(a))是一致的。

    图5.9 fa子模块RTL视图

  • 4位串行进位加(减)法器

    module c5 (input   [ 3: 0] a,          // 加数ainput   [ 3: 0] b,          // 加数binput           ci,         // 进位输入cioutput  [ 5: 0] f           // 加(减)法器运算结果
    );
    ​
    wire [3:0] s;       // 和数s
    wire co;            // 进位标志位co
    wire overflow;      // 溢出标志位    
    ​
    wire [4:0] c;       // 串行进位加法器的进位输入、进位输出
    wire [3:0] m;       // 等效于串行进位加法器的第二个加数 
    ​
    assign c[0] = ci;
    ​
    // 若ci = 0,执行加法运算,第二个加数为b
    // 若ci = 1,执行减法运算,第二个加数为将b反相
    mux2x1 mux2x1_inst (.x(b),  .y(~b),  .s(ci),  .m(m));   fa fa_inst0 (.a(a[0]),  .b(m[0]),  .ci(c[0]),  .s(s[0]),  .co(c[1]));
    fa fa_inst1 (.a(a[1]),  .b(m[1]),  .ci(c[1]),  .s(s[1]),  .co(c[2]));
    fa fa_inst2 (.a(a[2]),  .b(m[2]),  .ci(c[2]),  .s(s[2]),  .co(c[3]));
    fa fa_inst3 (.a(a[3]),  .b(m[3]),  .ci(c[3]),  .s(s[3]),  .co(c[4]));// 若执行加法运算(ci = 0),则进位输出c4保持不变
    // 若执行减法运算(ci = 1),则将进位输出c4取反,以实现减2的n次方的运算
    assign co = ci ^ c[4];
    assign overflow = c[3] ^ c[4];
    assign f = {overflow, co, s};endmodule

    代码5.4 c5.v

    c5子模块的RTL代码综合出的RTL视图如图5.10所示,可以看到和我们前面分析设计的结构(图5.5)是一致的。

    图5.10 c5子模块RTL 视图

  • 计算器模块

    module calculator(input   [ 3: 0] a,//input   [ 3: 0]   b,input           carry_in,input   [ 2: 0] sel,input           en,input           clk,input           rst_n,output  [ 6: 0] hex0_out,output  [ 5: 0] ledr_out
    );
    wire [ 3: 0]    b;
    wire [3:0] f1,f2,f3,f4;
    wire [5:0] f5,f,g;
    wire carry_out;
    wire overflow;// 将输入a存入寄存器中reg4bits reg4bits_inst (.clk(clk), .rst_n(rst_n), .en(~en), .d(a), .q(b));    // a和b做与运算
    c1 c1_inst (.a(a), .b(b), .f(f1));
    // a和b做或运算
    c2 c2_inst (.a(a), .b(b), .f(f2));
    // a和b做异或运算
    c3 c3_inst (.a(a), .b(b), .f(f3));
    // a和b做非运算
    c4 c4_inst (.a(a), .f(f4));
    // a和b做加(减)法运算
    c5 c5_inst (.a(a), .b(b), .ci(carry_in), .f(f5));// 在前面的f1,f2,f3,f4,f5五种运算结果中,选择一个运算结果作为计算器的输出。
    // 其中,f1,f2,f3,f4需要将高位补0组成6位
    mux8x1 mux8x1_inst (.r({2'd0, f1}),.t({2'd0, f2}),.u({2'd0, f3}),.v({2'd0, f4}),.w(f5),.x(6'd0), .y(6'd0), .z(6'd0),.s(sel),.m(f)
    );// 将运算结果f存入寄存器中reg6bits reg6bits_inst (.clk(clk), .rst_n(rst_n), .en(~en), .d(f), .q(g));
    ​
    // 当执行c1、c2、c3、c4的逻辑运算时,g[3:0]为逻辑运算结果
    // 当执行c5的加法运算时,g[3:0]为和数s,g[5:4]分别为溢出标志位和进位标志位
    // 将g[3:0]以十六进制的形式显示在hex0_out上
    decod7seg decod7seg_inst (.hex(g[3:0]), .display(hex0_out));// 将g以二进制的形式显示在ledr_out[5:0]上
    assign ledr_out = g;endmodule

    代码5.5 calculator.v

    calculator子模块的RTL代码综合出的RTL视图如图5.11所示,可以看到和我们在5.3.1节中分析设计的结构(图5.6)是一致的。

    image-20240516200931551

    图5.11 calculator子模块RTL视图

5.5 实验步骤

5.5.1工程创建和代码输入
  1. 点击电脑右下角的开始菜单找到Quartus软件,双击Quartus (Quartus Prime 17.1)打开Quartus Prime软件。

  2. 点击菜单File-->New Project Wizard弹出工程创建的对话框。在弹出的对话框中点击Next。

  3. 在您的DE1-SOC 工作文件夹下创建一个lab5的文件夹,并将工程路径指向该文件夹,且工程的名称命名calculator。如下图所示。

img

​​

图5.13 创建Quartus工程

  1. 选择DE1-SOC对应的FPGA器件5CSEMA5F31C6,点击Next。

  1. 连续点击3次Next得到如下界面,通过器件过滤器筛选选中DE1-SoC的Cyclone V 5CSEMA5F31C6器件,点击Next两次后得到工程的生成报告窗口,检查无误后点击Finish完成工程创建。

img

  1. 完成创建工程后,打开后的工程Quartus Prime工程界面如下图所示。

​​

图5.14 Qaurtus软件打开lab5工程

  1. 在lab5文件夹下新建v文件夹。

img

​​

图5.15 在lab5文件夹下新建v文件夹

  1. 实验四 锁存器触发器寄存器中的c1.v、c2.v、c3.v、c4.v、reg4bits.v、decod7seg.v、calculator.v文件拷贝至本实验的工程路径,如图5.16所示。

img

​​

图5.16 拷贝文件到v文件夹中

  1. 新建reg6bits.v,并将如下代码保存在该文件中。

module reg6bits(input               clk,        // 时钟 50MHzinput               rst_n,      // 异步复位信号,低电平有效input               en,         // 同步使能信号,高电平有效input       [5:0]   d,          // 并行输入数据output  reg [5:0]   q           // 并行输出数据
);
​
//当检测到clk上升沿或rst_n下降沿时执行下面的语句
always@(posedge clk, negedge rst_n)
beginif(~rst_n)              // rst_n 为低电平复位,且不需要等待 clk 上升沿到来后再复位q <= 6'b000000;else if(en)q <= d;elseq <= q;
end
​
endmodule

代码5.7 reg6bits.v

image-20240516183153923

图5.17 修改reg6bits.v文件

  1. 参考代码5.5修改calculator.v文件(可以直接将代码5.5覆盖calculator.v的原始内容)。

img

​​

图5.18 修改calculator.v文件

  1. 点击Quartus软件工具栏的Assignments --> Settings --> Files,将前面拷贝的文件添加至本实验的Quartus工程,如图5.19所示。

image-20240516183528889

图5.19 添加拷贝的文件到Quartus工程

  1. 点击Quartus软件工具栏的File --> New --> Verilog HDL File,点击OK,新建一个空白Verilog HDL文件,再点击File --> Save As ...保存,命名为mux2x1.v,保存在v文件夹中,如图5.20所示。同样的步骤再依次创建mux8x1.v、fa.v、c5.v文件。

image-20240515162541561

图5.20 新建.v文件

  1. 依次将代码5.1、代码5.2、代码5.3、代码5.4中的设计代码添加到mux2x1.v、mux8x1.v、fa.v、c5.v文件中,并保存。

image-20240515164307275

图5.21 mux2x1.v

image-20240515164331066

图5.22 mux8x1.v

image-20240515164353754

图5.23 fa.v

image-20240515164420274

图5.24 c5.v

  1. 点击Quartus软件工具栏的Processing --> Start --> Start Analysis & Synthesis或点击

    image-20210603145513555

    按钮对Verilog HDL代码执行语法检查和综合。如果在该过程中提示有错误,请检查Verilog HDL代码语法,确保与上述代码块完全一致。

image-20240515171038490

图5.26 对Verilog代码进行分析和综合

5.5.2 仿真
  1. 点击Quartus软件工具栏的File --> New --> Verilog HDL File,点击OK,新建一个空白Verilog HDL文件,再点击File --> Save As ...保存,命名为calculator_tb.v,保存在v文件夹中,如图5.27所示。

image-20240515171818978

图5.27 新建并保存test bench文件

  1. 在calculator_tb.v文件中输入如下代码,并保存。

`timescale 1ns / 1ns
module calculator_tb;
​
// 产生时钟信号
reg clk;
localparam  PERIOD = 20;    // T = 1/frequency = 1/50MHz = 20ns
initial beginclk = 1'b0;forever#(PERIOD/2) clk = ~clk;
end
​
// 产生复位信号,用作6位寄存器的异步复位
reg rst_n;
initial beginrst_n = 1'b0;#(PERIOD)rst_n = 1'b1;
end
​
// 定义计算器的两个操作数a、b,加法器的进位输入carry_in,执行的运算选择位sel,6位寄存器的使能信号en
reg [3:0]   a;
//reg [3:0] b;
reg         carry_in;
reg [2:0]   sel;
reg         en;
​
initial 
begin#0; //sel = 3'b100;en = 1'b1;//rst_n = 1'b1;a = 4'b0000;//b = 4'b0001;carry_in = 1'b0;        #(PERIOD)sel = 3'b100;           //加法或减法//en = 1'b1;//rst_n = 1'b1;a = 4'b0110;//b = 4'b1101;carry_in = 1'b0;        // 0110 + 0000 = 0_0_0110#(PERIOD)//sel = 3'b100;//en = 1'b1;//rst_n = 1'b1;a = 4'b0110;//b = 4'b0101;carry_in = 1'b0;        // 0110 + 0110 = 1_0_1100#(PERIOD)//sel = 3'b100;//en = 1'b1;//rst_n = 1'b1;a = 4'b1010;//b = 4'b1101;carry_in = 1'b0;        // 1010 + 0110 = 0_1_0000#(PERIOD)
​//sel = 3'b100;//en = 1'b1;//rst_n = 1'b1;a = 4'b0010;//b = 4'b0001;carry_in = 1'b1;        // 0010 - 1010 = 1_1_1000#(PERIOD)//sel = 3'b100;//en = 1'b1;//rst_n = 1'b1;a = 4'b1000;//b = 4'b1010;carry_in = 1'b1;        // 1000 - 0010 = 1_0_0110#(PERIOD)//sel = 3'b100;//en = 1'b1;//rst_n = 1'b1;a = 4'b1001;//b = 4'b0110;carry_in = 1'b1;        // 1001 - 1000 = 0_0_0001#(PERIOD)//sel = 3'b100;//en = 1'b1;
//  rst_n = 1'b1;a = 4'b0100;//b = 4'b1001;carry_in = 1'b1;        // 0100 - 1001 = 1_1_1011#(PERIOD)   $stop;  
end
​
// 例化
wire [6:0] hex0_out;
wire [5:0] ledr_out;
​
calculator calculator_inst (
/* input            */      .clk        (clk),
/* input            */      .rst_n      (rst_n),
/* input            */      .en         (en),   
/* input    [3:0]   */      .a          (a),
/* input    [3:0]   */      //.b            (b),
/* input            */      .carry_in   (carry_in),
/* input    [2:0]   */      .sel        (sel),
​
/* output   [6:0]   */      .hex0_out   (hex0_out),
/* output   [5:0]   */      .ledr_out   (ledr_out)
);
​
endmodule

代码5.7 calculator_tb.v

image-20240517100306813

图5.28 Quartus软件中的calculator_tb.v文件

  1. 点击Quartus软件工具栏的Assignments --> Settings,在弹出的Settings窗口中,选中Simulation栏,Tool name选择ModelSim-Altera,设置Quartus自动调用ModelSim。然后选择添加Test Bench文件,如图5.29所示。

image-20240515172139261

图5.29 设置Quartus仿真选项

  1. 依次执行下面的步骤添加calculator_tb.v文件:

  • 在弹出的Test Benches窗口中点击New

  • 在弹出的New Test Bench Settings窗口中,在Test bench name栏填入calculator_tb

  • 点击

    图标;

image-20240515172353027

图5.30 添加Test Bench文件

  • 在弹出的Select File窗口,选中第一步中创建的calculator_tb.v文件;

  • 点击Open

image-20240515172443950

图5.31 添加Test Bench文件

  • 在File name栏会出现选中的calculator_tb.v文件;

  • 点击Add添加test bench文件(添加后该文件会出现在下面的框格中)

  • 点击OK,退出当前窗口;

image-20240515173943400

图5.32 添加Test Bench文件

  • 返回到Test Benches窗口,在Existing test bench settings框格中会出现前面设置好的test bench文件;

  • 点击OK,退出当前窗口;

  • 返回到Simulation设置界面,可以看到Compile test bench栏成功添加了calculator_tb仿真文件;

  • 点击Apply应用新的设置;

  • 点击OK或者Close关闭设置窗口。

image-20240515174040188

图5.33 添加Test Bench文件

  1. 点击Quartus软件工具栏的Tools --> Run Simulation Tool --> RTL Simulation启动ModelSim仿真,如图5.34所示。

image-20240515174817983

图5.34 点击Wave选项卡切换到仿真波形窗口

再点击Wave选项卡切换到仿真波形窗口,此时还看不到完整的仿真波形,可以通过点击如图5.35所示的Zoom Full按钮来显示完整的波形。

image-20240517100444711

图5.35 Zoom Full按钮

完整的仿真波形如图5.36所示。

image-20240517101244020

图5.36 calculator仿真波形

上面这个波形里面看不到操作数b的波形。接下来我们将中间信号b添加到波形当中。点击calculator_inst,选择信号b,右击,选择Add Wave。

image-20240517112429218

然后点击Restart按钮。

image-20240517113149491

接下来弹出的Restart对话框中点击OK。

image-20240517112534837

然后点击Run All和Zoo Full(F)按钮可以看到波形如下:

image-20240517153555181

下面对仿真波形进行分析:

  1. 0-30ns复位完成。

  2. 30 ~ 50 ns

    • 计算和:a = (0110)_B = (6)_D,b = (0000)_B = (0)_D;

      则:carry\_out = 0,s = a + b = (0110)_B = (6)_H。

    • 溢出位:a = (0110)_B = (+6)_D,b = (0000)_B = (+0)_D;

      则:overflow = 0。

    运算结果先是被存储到寄存器中,当 clk 上升沿到来时再输出,即在第30ns时:

    输出ledr\_out = 000110;输出hex\_out = 0000010,即在数码管上显示十六进制数字6。

  3. 50 ~ 70 ns

    • 计算和:a = (0110)_B = (6)_D,b = (0110)_B = (6)_D;

      则:carry\_out = 0,s = a + b = (1100)_B = (c)_H。

    • 溢出位:a = (0110)_B = (+6)_D,b = (0110)_B = (6)_D;

      则:overflow = 1。

    运算结果先是被存储到寄存器中,当 clk 上升沿到来时再输出,即在第50ns时:

    输出ledr\_out = 101100;输出hex\_out = 1000110,即在数码管上显示十六进制数字c。

  4. 70 ~ 90 ns

    • 计算和:a = (1010)_B = (10)_D,b = (0110)_B = (6)_D;

      则:carry\_out = 1,s = a + b = (0000)_B = (0)_H。

    • 溢出位:a = (0110)_B = (+10)_D,b = (0110)_B = (+6)_D;

      则:overflow = 0。

    运算结果先是被存储到寄存器中,当 clk 上升沿到来时再输出,即在第70ns时:

    输出ledr\_out = 010000;输出hex\_out = 1000000,即在数码管上显示十六进制数字0。

  5. 90 ~ 110 ns

    • 计算和:a = (0010)_B = (2)_D,b = (1010)_B = (10)_D;

      则:carry\_out = 1,s = a - b = (1000)_B = (8)_H。

    • 溢出位:a = (0010)_B = (+2)_D,b = (1010)_B = (-2)_D;

      则:overflow = 1。

    运算结果先是被存储到寄存器中,当 clk 上升沿到来时再输出,即在第90ns时:

    输出ledr\_out = 111000;输出hex\_out = 0000000,即在数码管上显示十六进制数字8。

  6. 110 ~ 130 ns

    • 计算和:a = (1000)_B = (8)_D,b = (0010)_B = (2)_D;

      则:carry\_out = 0,s = a - b = (0110)_B = (6)_H。

    • 溢出位:a = (1000)_B = (+8)_D,b = (0010)_B = (+2)_D;

      则:overflow = 1。

    运算结果先是被存储到寄存器中,当 clk 上升沿到来时再输出,即在第110ns时:

    输出ledr\_out = 100110;输出hex\_out = 0000010,即在数码管上显示十六进制数字6。

  7. 130 ~ 150 ns

    • 计算和:a = (1001)_B = (9)_D,b = (1000)_B = (8)_D;

      则:carry\_out = 0,s = a - b = (0001)_B = (1)_H。

    • 溢出位:a = (1001)_B = (-1)_D,b = (1000)_B = (-0)_D;

      则:overflow = 0。

    运算结果先是被存储到寄存器中,当 clk 上升沿到来时再输出,即在第110ns时:

    输出ledr\_out = 000001;输出hex\_out = 11110011,即在数码管上显示十六进制数字1。

  8. 150ns ~

    • 计算和:a = (0100)_B = (4)_D,b = (1001)_B = (9)_D;

      则:carry\_out =1 ,s = a - b = (1011)_B = (b)_H。

    • 溢出位:a = (0100)_B = (+4)_D,b = (1001)_B = (-1)_D;

      则:overflow = 1。

    运算结果先是被存储到寄存器中,当 clk 上升沿到来时再输出,即在第150ns时:

    输出ledr\_out = 111011;输出hex\_out = 0000011,即在数码管上显示十六进制数字b。

5.5.3 引脚分配、全编译与烧录

这个实验的操作数a及sel可以通过拨码开关SW0~SW3以及SW7~SW9来控制,carry_in从SW6输入。out信号分别输出到LEDR0到LEDR5,hex0_out输出到数码管0,en和rst_n连接到按键key1和key0。

  1. 点击Quartus菜单Assignments——Pin Planner进行引脚分配。

img

图4.41

关于引脚分配信息可以查看DE1-SoC_v.5.1.3_HWrevF.revG_SystemCD\UserManual\DE1-SoC_User_manual.pdf第 22、25、26、28页或者E:\CD_Package\01-DE1-SoC\DE1-SoC_v.5.1.3_HWrevF.revG_SystemCD\Schematic\DE1-SoC.pdf的第3页。

img

image-20240517165745573

img

image-20240517165857589

img

image-20240517170725526

  1. 点击Quartus软件工具栏的Processing --> Start Compilation或点击

    image-20210603145755433

    按钮编译lab5工程,并检查是否生成calculator.sof。

image-20240517171733209

图5.39 编译Verilog代码生成sof文件

  1. 连接好DE1-SOC开发板的电源和USB Blaster下载口,给板子开机。

  2. 点击Quartus软件工具栏的Tools --> Programmer

    image-20210603150014201

    按钮打开Programmer窗口,点击Hardware Setup选择USB-Blaster[USB-0],点击Auto Detect选择5CSEBA6器件,左键单击选中5CSEBA6器件再点击Change File,选择calculator.sof,勾选program/configure,点击Start下载calculator.sof。

image-20240517172243811

图5.40 Hardware Setup窗口

img

图5.41 选择5CSEBA6器件

img

图5.42 提示弹窗

烧录完成后,Progress进度条显示100%,如下图所示。

img

图5.43 烧录完成

5.5.4 实验现象观察
  1. 在lab5当中要用到的外设KEY、SW、LEDR和HEX如下图所示。

    image-20240517173820132

  2. 通过切换滑动开关SW到 up 或 down 位置,并按下按键KEY1KEY0,观察数码管HEX1~HEX0以及LEDR7~LEDR0的状态来测试设计的功能。

    本实验重点验证加法器的功能,因此将SW9~SW7拨动并保持为"up、down、down",即选择执行加(减)法运算。

    • 当拨动SW6为"down",SW3~SW0为"down、down、down、down",按下KEY1LEDR5~LEDR0显示为熄灭、熄灭、熄灭、熄灭、熄灭、熄灭,HEX0*上显示十六进制数字 0;

    1. 计算和:a = (0000)_B = (0)_D,b = (0000)_B = (0)_D;

    ​ 则:carry\_out = 0,s = a + b = (0000)_B = (0)_H。

    1. 溢出位:a = (0000)_B = (+0)_D,b = (0000)_B = (+0)_D;

    ​ 则:overflow = 0。

    图5.52 运行结果(1)

    • 当拨动SW6为"down",SW3~SW0为"down、up、up、down"时,按下KEY1LEDR5~LEDR0显示为点亮、熄灭、点亮、点亮、熄灭、熄灭,HEX0上显示十六进制数字 c;

    1. 计算和:a = (0110)_B = (6)_D,b = (0110)_B = (12)_D;

    ​ 则:carry\_out = 1,s = a + b = (1100)_B = (12)_H。

    1. 溢出位:a = (0110)_B = (+6)_D,b = (0110)_B = (+6)_D;

    ​ 则:overflow = 1​。

    图5.52 运行结果(1)

    • 当拨动SW6为"up",SW3~SW0为"down、down、up、down"时,按下KEY1LEDR5~LEDR0显示为熄灭、熄灭、熄灭、点亮、熄灭、熄灭,HEX0上显示十六进制数字 4;

    1. 计算和:a = (0010)_B = (2)_D,b = (0110)_B = (6)_D;

    ​ 则:carry\_out = 0,s = a - b = (1100)_B = (-4)_H。

    1. 溢出位:a = (0010)_B = (+2)_D,b = (0110)_B = (+6)_D;

    ​ 则:overflow = 0。

    图5.56 运行结果(5)

    • 当拨动SW16为"up",SW3~SW0为"up、down、down、down"时,按下KEY1LEDR5~LEDR0显示为熄灭、点亮、点亮、点亮、点亮、熄灭,HEX0*上显示十六进制数字 E;

    1. 计算和:a = (1000)_B = (8)_D,b = (0110)_B = (6)_D;

    ​ 则:carry\_out = 1,s = a - b = (0010)_B = (2)_H。

    1. 溢出位:a = (1000)_B = (-8)_D,b = (0010)_B = (+2)_D;

    ​ 则:overflow = 0。

    图5.57 运行结果(6)

5.6 实验小结

通过本实验,可掌握使用组合逻辑电路实现多位数的加(减)法运算,并验证加法器的功能。

这篇关于第五篇 加法器的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1030083

相关文章

《花100块做个摸鱼小网站! 》第五篇—通过xxl-job定时获取热搜数据

⭐️基础链接导航⭐️ 服务器 → ☁️ 阿里云活动地址 看样例 → 🐟 摸鱼小网站地址 学代码 → 💻 源码库地址 一、前言 我们已经成功实现了一个完整的热搜组件,从后端到前端,构建了这个小网站的核心功能。接下来,我们将不断完善其功能,使其更加美观和实用。今天的主题是如何定时获取热搜数据。如果热搜数据无法定时更新,小网站将失去其核心价值。之前,我采用了@Scheduled注解来实现定

iOS笔记:第五篇 C语言 函数

第一节 函数  1.有一段代码需要重用/复用    重用:这段代码需要在不同的地方使用到    循环:一段代码反复不停的执行    2.重用代码最简单的方式就是复制粘贴来实现    1)代码冗余    2)后期的维护和修改极其不方便    3.函数    作用:可以将一段代码科学的重用    重用的原理:将要被重用的代码塞到函数中,要执行时只需要调用就可以来,

经典查询练手第五篇

--经典查询练手第五篇 HR@PROD2> desc EMPLOYEESName Null? Type----------------------------------------------------- -------- ------------------------------------EMPLOYEE_ID NOT NULL

nginx教程第五篇:用HTTP核心模块配置一个静态Web服务器(一)

前言 静态Web服务器的主要功能由ngx_http_core_module模块( HTTP框架的主要成员) 实现, 当然, 一个完整的静态Web服务器还有许多功能是由其他的HTTP模块实现的。 本文主要讨 论如何配置一个包含基本功能的静态Web服务器, 文中会完整地说明ngx_http_core_module模 块提供的配置项及变量的用法, 但不会过多说明其他HTTP模块的配置项。 在阅读完本节

【MySQL】第五篇:MySQL之索引介绍

一、索引 MySQL 官方对索引的定义为:索引(Index)是帮助 MySQL 高效获取数据的数据结构。 可以得到索引的本质:索引是数据结构。可以简单理解为排好序的快速查找数据结构。 在数据之外,数据库系统还维护着满足特定查找算法的数据结构,这些数据结构以某种方式引用(指向)数据, 这样就可以在这些数据结构上实现高级查找算法。这种数据结构,就是索引。下图就是一种可能的索引方式示例: 左边是数据

第五篇:稳定性之提升团队潜意识【依赖简化、谨慎变更】

依赖简化 在分布式或微服务系统中,服务肩负不同职责,服务间必然存着依赖关系、往往系统复杂度的根源除了业务的本身复杂度,就是设计不恰当的耦合关系、或者服务划分不合理。在实际开发过程中,对单体服务进行重构的时候并不多。更多的时候,我们一开始做服务架构时便在使用微服务的架构模式。随着系统需求的渐渐复杂化,我们会发现,服务间的耦合越来越严重,甚至出现了循环依赖。这种时候我们不得不质疑自己,当初的模块

机器学习第五篇----TF-IDF算法详解

TF-IDF是Term Frequency - Inverse Document Frequency的缩写,即“词频-逆文本频率”。它由两部分组成,TF和IDF。在前期的关键词提取和文本one-hot的时候使用较多 1、TF-IDF 算法 TF(词频):表示词w在文档Di中出现的频率,计算公式如下 其中count(w)为关键词w出现的次数,|Di| 为文档Di中所有词的数量。 IDF(逆文

嵌入式AI快速入门课程-K510篇 (第五篇 嵌入式AI系统与应用学习篇)

第五篇 嵌入式AI系统与应用学习篇 文章目录 第五篇 嵌入式AI系统与应用学习篇1.数据层-数据采集1.1 视频数据采集-V4L21.1.1 数据采集流程1.1.2 buffer的管理1.1.2 完整的使用流程 1.2 控制流程1.2.1 APP接口1.2.1.1 数据格式1.2.1.1 数据格式1.2.1.2 选择输入源1.2.1.3 其他参数 1.2.2 理解接口1.2.2.1 概念1

【计算机组成原理】二、数据的表示和运算:3.算术逻辑单元ALU(逻辑运算、加法器)

4.运算器ALU 文章目录 4.运算器ALU4.1逻辑运算非(NOT)与(AND)或(OR)异或(XOR)同或(XNOR) 4.2加法器4.2.1一位全加器4.2.2串行加法器4.2.3并行加法器 4.3ALU功能与结构 运算器由 算术逻辑单元ALU和若干 通用寄存器(用于暂存操作数和中间结果),如 累加器ACC, 乘商寄存器MQ, 操作数寄存器X, 变址寄存器IX

第五篇 zabbix汉化

zabbix有一个默认登陆的账号:Admin 密码:zabbix,这是一个超级管理员,登陆进去之后可以看到右上角的人形图标显示登陆的用户名为Admin Zabbix自带多种语言包,其中就包含中文,只需要简单的设置就可以将语言切换到中文。 Zabbix默认登陆界面是使用英文的,登陆进入主界面后点击右上角的人形图标 点击user选择language下拉框,选择中文点击update即可