精华内容
下载资源
问答
  • 一、选题目的1、学会使用quartus软件设计电路及对其进行仿真,设计实现8位二进制乘法电路。2、学习并掌握8位二进制乘法器的原理、设计、分析和测试方法。二、设计目标采用移位相加的方法实现8位二进制乘法电路。...

    一、选题目的

    1、学会使用quartus软件设计电路及对其进行仿真,设计实现8位二进制乘法器电路。

    2、学习并掌握8位二进制乘法器的原理、设计、分析和测试方法。

    二、设计目标

    采用移位相加的方法实现8位二进制乘法器电路。用户通过输入两个8位二进制数Y和B,八位乘法器可以实现其乘积,并输出结果。

    三、实现方案(包括原理框图和HDL设计流程图)

    该乘法器是由8位二进制加法器构成的以时序方式设计的乘法器,通过逐项移位相加原理来实现。用乘数的各位数码,从低位开始依次与被乘数相乘,每相乘一次得到的积称为部分积,将第一次(由乘数最低位与被乘数相乘)得到的部分积右移一位并与第二次得到的部分积相加,将加得的和右移一位再与第三次得到的部分积相加,再将相加的结果右移一位与第四次得到的部分积相加。直到所有的部分积都被加过一次即可得到相应的乘积。

    在这里,我们用Y代表被乘数,B寄存器存放乘数N,A累加寄存器存放部分积,而A和B相级联又构成了一个16bit的移位寄存器,每次移位时A中最低位的数被移入B的最高位,经过8次部分积相加位的操作,完成1次乘法运算,乘数N恰好被移出寄存器B,寄存器B中保存的就是运算积的低8位数据,而寄存器A中保存的是运算积的高8位数据。

    由于乘数的每一位不是0就是1 ,对应的部分积不是0就是被乘数本身,所以实际作部分积相加这一步时,只要根据乘数的对应位判断:如该位为1,则将累加器中的数据加上被乘数再移位;如该位为0时,就不加被乘数而直接移位。

    移位相加的次数用一个时钟控制计数器来控制,由于第一个时间脉冲被用于A累加寄存器的置数,并无移位操作,故设计电路时采用了模为9的计数器来实现8位移位操作。当计数器计得9个数时,发出一个信号,使电路停止操作,并输出运算结果。

    两个n位二进制数相乘的结果最多可以有2n位的二进制数。

    例如:被乘数(M7M6M5M4M3M2M1M0)和乘数(N7N6N5N4N3N2N1N0)

    分别为11010101和10010011,其计算过程如下图(a):


    原理框图和简单流程图如下图(b)和图(c):


    四、设计过程

    1、模9计数器cnt9的设计

    模9计数器由时钟控制,开始时由异步置数端RST进行清置“1”操作。当RST为高电平且使能端EN为高电平时,每来一个时钟上升沿,计数器计一个数,直到内部变量Q计到“10”时,即在第九个上升沿时,输出端COUT输出1,变量Q回到初始值“1”。

    该模块元件的程序如下:

    LIBRARY IEEE;

    USE IEEE.STD_LOGIC_1164.ALL;

    USEIEEE.STD_LOGIC_UNSIGNED.ALL;

    ENTITY cnt9 IS

        PORT(CLK,RST,EN:IN STD_LOGIC;

                    COUT:OUTSTD_LOGIC);

    END cnt9;

    ARCHITECTURE behav OF cnt9IS

    BEGIN

    PROCESS(CLK,RST,EN)

       VARIABLE Q:STD_LOGIC_VECTOR(3 DOWNTO 0);

    BEGIN   

      IF RST='0' THEN Q:="0001";

          ELSIF CLK'EVENT AND CLK='1' THEN

                        IF EN='0'THEN

                                 IFQ<"1010" THEN Q:=Q+1;

                                 ELSE Q:="0001"; 

                                   END IF;

                                END IF;

      END IF;

     IF Q="1010"       THEN COUT<='1';

        ELSE COUT<='0';

     END IF;

    END PROCESS;

    END behav;

    2、具有使能端的d触发器dffen的设计

    D触发器由使能端EN控制,当EN为低电平时对输出端Q进行清零操作,当EN为高电平时将输入端D赋给输出端Q。

    该模块元件的程序如下:

    LIBRARY IEEE;

    USE IEEE.STD_LOGIC_1164.ALL;

    USEIEEE.STD_LOGIC_UNSIGNED.ALL;

    ENTITY dffen IS

        PORT(EN:IN STD_LOGIC;

                   D:INSTD_LOGIC_VECTOR(7 DOWNTO 0);

                   Q:OUTSTD_LOGIC_VECTOR(7 DOWNTO 0));

    END dffen;

    ARCHITECTURE behav OF dffenIS

    BEGIN

    PROCESS(D,EN)

    BEGIN   

       IF EN='0' THEN Q<=(OTHERS=>'0');

          ELSE  Q<=D;

       END IF; 

    END PROCESS;

    END behav;

    3、累加寄存器SHFTA的设计

    累加寄存器A虽然与寄存器B相级联构成16位移位寄存器,但就累加寄存器A本来而言并不是严格意义上的寄存器。SHFTA工作时先由清零端CLR高电平清零,之后每一个时钟上升沿置一次数,用于存放部分积的和。输出端DOUT为一个8位二进制数,其最高位存放右移值SR,在乘法器电路中SR存放部分积和的进位;其后7位存放部分积和的高7位,形成模拟的“移位”操作。输出端QB存放部分积的最低位,用于向B寄存器移位。

    该模块元件的程序如下:

    LIBRARY IEEE;

    USE IEEE.STD_LOGIC_1164.ALL;

    USEIEEE.STD_LOGIC_UNSIGNED.ALL;

    ENTITY SHFTA IS

        PORT(CLK,CLR,SR:IN STD_LOGIC;

                   DIN:INSTD_LOGIC_VECTOR(7 DOWNTO 0);

                   QB:OUTSTD_LOGIC;

                   DOUT:OUTSTD_LOGIC_VECTOR(7 DOWNTO 0));

    END SHFTA;

    ARCHITECTURE behav OF SHFTAIS

     SIGNAL REG8:STD_LOGIC_VECTOR(7 DOWNTO 0);

     SIGNAL Q:STD_LOGIC;

    BEGIN

     PROCESS(CLK,CLR)

     BEGIN 

             IF CLR='1' THENREG8<=(OTHERS=>'0');Q<='0';

                ELSIF CLK'EVENT ANDCLK='1' THEN

                   REG8<=DIN;Q<=SR;

                        END IF;  

          DOUT<=Q&REG8(7 DOWNTO 1);

    END PROCESS;

    QB<=REG8(0);

    ENDbehav;

    4、移位寄存器B的设计

    移位寄存器B工作时先由输入端LOAD高电平置数,置入乘数B,再由时钟脉冲上升沿控制移位操作,先把内部信号REG8的高7位赋给它的低7位,再把输入端SR接收到的值赋给REG8的最高位,即把A的最低位移入B中。为了在输出最后结果时,乘积的低8位和高8位能够正常的连接,输出端DOUT的设计也与A规则相同,输出最高位为SR,低7位为REG8高7位的8位二进制数,QB输出B的最低位,用于控制加法器中从取出的右移后的部分积的和是与0相加还是与被乘数相加。

    该模块元件的程序如下:

    LIBRARY IEEE;

    USEIEEE.STD_LOGIC_1164.ALL;

    USEIEEE.STD_LOGIC_UNSIGNED.ALL;

    ENTITY SHFTB IS

        PORT(CLK,LOAD,SR:IN STD_LOGIC;

           DIN:IN STD_LOGIC_VECTOR(7 DOWNTO 0);

           QB:OUT STD_LOGIC;

           DOUT:OUT STD_LOGIC_VECTOR(7 DOWNTO 0));

    END SHFTB;

    ARCHITECTURE behav OF SHFTBIS

     SIGNAL REG8:STD_LOGIC_VECTOR(7 DOWNTO 0);

    BEGIN

     PROCESS(CLK,LOAD)

     BEGIN 

              IF LOAD='1' THENREG8<=DIN;

                ELSE IF CLK'EVENTAND CLK='1' THEN

                 REG8(6 DOWNTO0)<=REG8(7 DOWNTO 1);REG8(7)<=SR;

                       END IF;

               END IF;

    END PROCESS;

    QB<=REG8(0);

    DOUT<=SR&REG8(7DOWNTO 1);

    END behav;

    5、8位二进制乘法器的顶层设计

    其顶层电路图如图:


    如图所示,当异步输入端LOAD为高电平时,累加寄存器A清零,同时移位寄存器置乘数,之后每次时钟上升沿到来时,由B中数据最低位控制dffen的EN使能端,当EN为0时,输出0,当EN为1时,输出被乘数Y,由此可实现从A中取出的右移过的部分积的和是与0或被乘数Y相加的判断和选择,即实现了被乘数Y与0相乘或与1相乘的操作。B寄存器每次移位时,最高位置入的均为A中部分积的和的最低位,即实现A与B的级联移位操作。部分积的和移位8次完成时,即计数器计9次时间脉冲时,计数器的COUT端输出1到使能端EN,使计数器停止置数,同时控制乘积输出端的两个普通d触发器输出分别输出乘积的高8位和低8位。。

    五、遇到问题及解决方法

    1、一开始从电路尽可能简洁这方面考虑,想尽可能使用少一些的模块或者尽可能使用相同的模块简化电路设计,所以花了大量的时间试图让同一个移位寄存器模块实现累加器A和移位寄存器B的功能,但是由于A和B两寄存器工作原理很不相同,导致原理图连线反而更加复杂和逻辑错乱。

    解决方法:放弃用同一寄存器同时实现两个功能的想法,改而设计不同寄存器模块SHFTA和SHFTB分别实现累加寄存器A和移位寄存器B的功能。

    2、每一次进行累加操作时,部分积需要先移位,再与下一个部分积相加,而累加寄存器A每次时间脉冲到来时只实现置数操作,当我想改变程序实现累加寄存器A在同一时间上升沿既置数又移位时,却发现寄存器A根本不能工作,输出0。据分析,出现这种的原因在于在同一时间上升沿同时实现对同一个内部变量的操作会产生冲突,导致寄存器A不能正常工作。

    解决方法:放弃让累加寄存器进行移位操作,改用虚拟“移位”的方式,让8位二进制输出端DOUT的最高位置“右移输入端”SR的值,即将加法器的进位端置最高位,而后7位数据置内部变量REG8的前7位数,实现虚拟的“移位”操作。

    3、在进行乘法操作时,计数器cnt9从0计到9,理应在第九个时间脉冲时COUT输出1,控制输出端输出乘积,可是在进行仿真时我发现,COUT端在第八个时间脉冲到来时总要有一个窄脉冲出现(见最后一道波形),导致输出两次乘积。据分析,出现这种情况的原因在于计数器从7计到8,即从“0111”计到“1000”时,由于数据翻转出现延迟,会短暂的出现“1001”,导致计数器感应到“9”,从而COUT输出1,控制输出端输出乘积。

    其仿真波形如下:


    解决方法:改变计数器从0计到9的计数方式,使其从1计到10,即从“0001”计到“1010”,避免了由于翻转不及时导致的计数错误。

    六、实现结果

    输入 8位二进制数的乘数B和被乘数Y,该乘法器实现其乘积,并分高8位和低8位输出结果。

    仿真波形如下:


    如图所示,在第九个时间脉冲上升沿到来时,输出端h输出乘积的高8位,输出端l输出乘积的第8位。

    七、对该课程的实施意见及建议

    在程序设计和原理图设计的过程中,我通过对quartus的学习和使用,锻炼了自己的编程能力,也学会了如何在遇到错误的时候冷静分析原因,利用对中间量的观测对程序进行调试和改进,对EDA课程和HVDL语言的理解有了很大的提升。



    展开全文
  • 二进制乘法器是数字电路的一种元件,它可以将两个二进制数相乘,乘法器是由更基本的加法器组成。----------维基百科 一、两个二进制数相乘原理 举例:,实现相乘过程如下: 图1 两个二进制数相乘过程 由图...

    二进制的乘法器是数字电路的一种元件,它可以将两个二进制数相乘,乘法器是由更基本的加法器组成。----------维基百科

    一、两个二进制数相乘原理

    举例:\large a_3a_2a_1a_0\times b_3b_2b_1b_0,实现相乘过程如下:

    图1 两个二进制数相乘过程

    由图可知,如果b全是1的话,只需要实现a向左移位相加即可;如果b中有0,a也要移位,只是相对应的位加0,如只有\large b_1 = 0,a移位相加时,图中的\large b_1对应的这一行\large a_3a_2a_1a_0 = 0000,其它位仍然保持移位相加的状态。

    实现\large a_3a_2a_1a_0 = 1011 和\large b_3b_2b_1b_0 = 0101相乘

    二、ASM

    在理解两个二进制数相乘原理之后,接下来就要用流程图来表示两个二进制数相乘的过程,由于数字电路中使用算法状态机进行描述更加容易理解,这里使用算法状态机描述两个二进制数相乘的整个过程,然后根据算法状态机描述电路的数据路径(datapath)。算法状态机如下图所示:

    图2 算法状态机

     由图可知,首先在复位信号rst控制下进入s0状态,在s0状态,将输出结果result清零,如果start信号无效(0),继续保持在s0,如果有效(1),则进入下一状态s1,在s1状态执行data_a左移,data_b右移;flag信号是data_b右移完成的(data_b='d0)的标志信号,如果flag=0,判断data_b每次移位后的最低位data_bit0 = data_b[0]是否为1,如果为1,将result与移位后的data_a相加,否则,result保持不变;如果flag = 1,表示data_b以为已经完成,进入 s2状态,计算完成标志位done信号拉高,在s2状态,如果start信号为0,则返回s0状态,否则继续保持在s2状态。

    三、数据路径

    根据算法状态机图可知,实现两个二进制数相乘的基本块电路有移位寄存器和加法器电路。根据数据关系画出其dapapath如下图所示:

    图2 数据路径

     ASM和datapath已经完成,接下来就需要理清控制信号是如何起作用的,通过观察数据路径图的输入输出信号,可以在算法状态机图中得出在哪个状态哪些信号发挥作用。

    四、控制信号

    图3 控制信号

     在s0状态,load_c=1,此时寄存器result加载0;在s1状态,左移寄存器使能端en_a和右移寄存器en_b均使能,此时移位寄存器开始工作,并判断data_bit0是否为1,如果为1,result的使能端en_c=1,将相加结果存入寄存器result,否则,en_c=0,result中的值不变;在s2状态运算完成标志信号done=1,此时结果为最终结果。

    五、verilog描述

    顶层代码:

    module Multiplier(input clk,
    						input rst,
    						input start,开始进行乘法运算
    						input load_a,
    						input load_b,
    						input [3:0]data_a,
    						input [3:0]data_b,
    						output reg done,
    						output reg[7:0]result
    						
        );
    reg load_c = 'd0;///输出结果寄存器加载0信号
    reg en_c = 'd0;//输出结果寄存器使能信号
    reg en_a = 'd0;/左移移位寄存器使能信号
    reg en_b ='d0;//右移移位寄存器使能信号
    wire flag;/右移移位完成标志信号
    wire data_bit0;右移串行输出结果
    wire [7:0]data_o;
    状态分配
    parameter s0 = 'b001;
    parameter s1 = 'b010;
    parameter s2 = 'b100;
    定义当前状态、下一状态
    reg [2:0] current_state = 'd0;
    reg [2:0] next_state = 'd0;
    次态赋值给现态
    always@(posedge clk or negedge rst)
    	if(!rst)
    		current_state <= s0;
    	else
    		current_state <= next_state;
    //次态产生
    always@(*)
    	case(current_state)
    		s0:	begin
    			if(start)
    				next_state = s1;
    			else
    				next_state = s0;
    		end
    		s1:	begin
    			if(flag)
    				next_state = s2;
    			else
    				next_state = s1;
    		end
    		s2:	begin
    			if(!start)	
    				next_state = s0;
    			else
    				next_state = s2;
    		end
    		default:
    				next_state = s0;
    	endcase
    /产生输出结果
    always@(*)
    	case(current_state)
    		s0:	begin
    			load_c = 'd1;
    			en_a = 'd0;
    			en_b = 'd0;
    			en_c = 'd0;
    			done = 'd0;
    		end
    		s1:	begin
    			load_c = 'd0;
    			en_a = 'd1;
    			en_b = 'd1;
    			done = 'd0;
    			if(data_bit0)
    				en_c = 'd1;
    			else
    				en_c = 'd0;
    		end
    		s2:	begin
    			load_c = 'd0;
    			en_a = 'd0;
    			en_b = 'd0;
    			en_c = 'd0;
    			done = 'd1;
    		end
    		default:	begin
    			load_c = 'd1;
    			en_a = 'd0;
    			en_b = 'd0;
    			en_c = 'd0;
    			done = 'd0;
    		end
    	endcase
    ///相乘结果
    always @(posedge clk)
    	if(load_c)
    		result <= 'd0;
    	else if(en_c)	
    		result <= result + data_o;
    	else
    		result <= result;
    /左移移位寄存器例化
    left_shift left_shift (
        .clk(clk), 
        .load_a(load_a), 
        .en_a(en_a), 
        .data_a(data_a), 
        .data_o(data_o)
        );
    右移移位寄存器例化
    right_shift right_shift (
        .clk(clk), 
        .load_b(load_b), 
        .en_b(en_b), 
        .data_b(data_b), 
        .flag(flag), 
        .data_bit0(data_bit0)
        );
    endmodule

     左移寄存器代码:

    module left_shift(input clk,
    						input load_a,/左移寄存器加载信号
    						input en_a,//左移寄存器使能信号
    						input [3:0]data_a,///左移寄存器待加载数据
    						output reg [7:0]data_o///移位后输出数据
        );
    reg [7:0] data_o_1 = 'd0;
    always @(posedge clk)
    	if(load_a)
    		data_o_1 <= {4'b0,data_a[3:0]};
    	else if(en_a)	
    		data_o_1 <= {data_o_1[6:0],1'b0};
    	else
    		data_o_1 <= data_o_1;
    always @(posedge clk)
    	data_o <= data_o_1;
    endmodule
    

     右移寄存器代码:

    module right_shift(input clk,
    						input load_b,///移位寄存器加载信号
    						input en_b,/移位寄存器使能信号
    						input [3:0]data_b,///移位寄存器待加载数据
    						output flag,移位完成标志
    						output reg data_bit0移位寄存器串行输出数据
        );
    reg [3:0]data = 'd0;
    always @(posedge clk)
    	if(load_b)	begin
    		data <= data_b;
    		data_bit0 <= 'd0;
    	end
    	else if(en_b)	begin
    		data_bit0 <= data[0];
    		data <= {0,data[3:1]};
    	end
    	else begin
    		data_bit0 <= data_bit0;
    		data <= data;
    	end
    assign flag = ~(|data);
    endmodule
    

    仿真激励文件代码:

    module test_multiplier;
    
    	// Inputs
    	reg clk;
    	reg rst;
    	reg start;
    	reg load_a;
    	reg load_b;
    	reg [3:0] data_a;
    	reg [3:0] data_b;
    
    	// Outputs
    	wire done;
    	wire [7:0] result;
    
    	// Instantiate the Unit Under Test (UUT)
    	Multiplier uut (
    		.clk(clk), 
    		.rst(rst), 
    		.start(start), 
    		.load_a(load_a), 
    		.load_b(load_b), 
    		.data_a(data_a), 
    		.data_b(data_b), 
    		.done(done), 
    		.result(result)
    	);
    
    	initial begin
    		// Initialize Inputs
    		clk = 0;
    		rst = 0;
    		start = 0;
    		load_a = 0;
    		load_b = 0;
    		data_a = 0;
    		data_b = 0;
    
    		// Wait 100 ns for global reset to finish
    		#100;
            
    		// Add stimulus here
    
    	end
          always #5 clk = ~clk;
    	reg[4:0] cnt = 'd0;
    	always @(posedge clk)
    		if(cnt == 'd30)
    			cnt <= 'd30;
    		else
    			cnt <= cnt + 'd1;
    	///复位信号
    	always @(posedge clk)
    		if(cnt <= 'd2)
    			rst <= 'd0;
    		else
    			rst <= 'd1;
    	//加载信号和数据
    	always @(posedge clk)
    		if((cnt> 'd2)&&(cnt < 'd5))	begin
    			load_a <= 'd1;
    			load_b <= 'd1;
    			data_a <= 'b1011;
    			data_b <= 'b0101;
    		end
    		else	begin
    			load_a <= 'd0;
    			load_b <= 'd0;
    			data_a <= 'd0;
    			data_b <= 'd0;
    		end
    	///start信号
    	always @(posedge clk)
    		if((cnt> 'd8)&&(cnt < 'd25))
    			start <= 'd1;
    		else
    			start <= 'd0;
    endmodule
    

      Isim行为仿真结果:当data_a = 'b1011,data_b = 'b0101:

    第一种情况

       Isim行为仿真结果:当data_a = 'b0101,data_b = 'b1011:

    第二种情况

     上述仿真中,不论是data_a = 'b1011,data_b = 'b0101还是data_a = 'b0101,data_b = 'b1011,两者运行结果都是一样,但这两种情况从计算开始到生成计算结果所用的时间不一样(图中两条黄色线之间的时间)。由两幅图比较可知,第二种情况比第一种情况多用了一个时钟周期。这是因为当done信号的生成与flag信号有关,而flag信号是data_b移位完成标志信号,即当data_b='d0时,flag有效,紧接着done信号有效。所以,当两数相乘时,选用较小的数作为data_b可以提高乘法器的效率。

    展开全文
  • 八位二进制乘法器VHDL

    2020-11-02 21:56:08
    八位二进制乘法器VHDL工程文件一、 实验目的二、设计要求三、实验仪器与环境四、实现原理五、系统设计及仿真六、顶层设计:七、结果仿真:附录: 工程文件 点击下载八位二进制乘法器工程文件 一、 实验目的 熟习...

    工程文件

    点击下载八位二进制乘法器工程文件

    一、 实验目的

    1. 熟习Quartus Ⅱ软件的使用。
    2. 掌握原理图输入法和硬件描述语言**(VHDL)**方法来设计逻辑电路。
    3. 对设计电路作硬件验证。展示;

    二、设计要求

    1. 用移位相加的方法设计一个乘法器,实现八位二进制的乘法
    2. 考虑数据输入口的数量不足16位,实现分拍置数的功能

    三、实验仪器与环境

    1. 芯片:EP4CE1022C8
    2. 编程与仿真环境:Quartus Ⅱ 13.1
    3. 输入输出验证平台:西安电子科技大学数电试验箱

    四、实现原理

    (一)二进制数的乘法
    如下图(4.1.1)所示,这两种数制的乘法都是把被乘数和乘数的每一位分别相乘,然后将得到的乘积根据所乘的乘数的位数进行移位,比如,在十进制数乘法中,如果将被乘数与乘数的个位相乘,那就把得到的乘积向左移动0位;如果被乘数与乘数的十位相乘,那就把得到的乘积向左移动1位…移位操作完成后,最后将这些移位后的乘积相加,就是最开始这两个被乘数与乘数的结果。
    我们都知道,在二进制数中,只有数字0和1。在二进制数乘法中,如果与被乘数相乘的乘数的某一位为1,那结果就是被乘数本身,如果乘数的某一位为0,那此次的结果就是0。因此,二进制数乘法过程中的数次相乘,其实使用与门实现的。
    在这里插入图片描述图4.4.1
    (二)分拍输入原理
    两个8位二进制数相加需要16个输入引脚,但实验板空间有限,只好一次只输入一个8位二进制数,分两拍输入到上述的乘法器主体中。
    通过设计置数端完成节拍的掌控,第一个数输入完毕后置数端置一,若置数成功,则第一个灯亮起。第二个数置数完毕后,再将置数端置一。若置数成功,则第二个灯亮起。此时输入模块同时输出两个乘数。

    五、系统设计及仿真

    (一)乘法器主体模块(mulity_8bit)
    在这里插入图片描述

    图(5.1.1)
    该模块共有4个输入端,一个输出端,其中clk为1kHz时钟信号,x和y为两个8位二进制乘数。Start端为1时开始计数,8个时钟周期后result端输出结果。Start端为0时输出为零。
    该模块用一个模10计数器实现,亦可以认为是一个三状态的有限状态机。
    S0:在计数为0时为第一状态,初始化乘法器,所有变量赋初值。
    S1:在计数为1~8时,每次计数时完成以下三步
    (1) 乘数右移一位。
    (2) 根据乘数最后一位是否为1判断是否需要做移位后的加法。
    (3) 乘积向左移动1位
    S2:在计数为9时,输出结果。
    具体实现代码见附录
    仿真波形如图(5.1.2),仿真时实现了
    00100101×001010100000110×00000011
    在这里插入图片描述
    图(5.1.2)
    (二)分拍输入模块(inp)
    在这里插入图片描述
    图(5.2.1)
    该模块共有4个输入端,4个输出端,其中clk为1kHz时钟信号,num端为8位二进数输入端,set为置数端,clear为清零端。x,y为8位二进数输出端。ok_x,ok_y为置数成功显示端。
    分拍输入有寄存器实现,通过检测set的次数给X,Y赋值。使用流程如下:

    1. num的引脚置高低电平
    2. set置1,Led_x亮起,set置0。
    3. num的引脚置第二个数
    4. set置1,Led_y亮起,set置0。置数完成。
    5. clear恢复初始状态。
    6. 重复1~5步骤进行第二组输入。
      仿真实现上述步骤,如图(5.2.2):
      在这里插入图片描述
      如图(5.2.2)

    六、顶层设计:

    在这里插入图片描述
    图(6.1.1)

    七、结果仿真:

    软件仿真:在这里插入图片描述
    图(7.1.1)
    硬件测试:
    【1】选择对应芯片:
    在这里插入图片描述
    图(7.2.1)
    【2】无用管脚选三态:
    在这里插入图片描述
    图(7.2.2)
    【3】分配管脚:
    在这里插入图片描述

    图(7.2.3)
    【4】下载测试

    附录:

    (1)Inp.vhd:

    LIBRARY IEEE;
    USE IEEE.STD_LOGIC_1164.ALL;
    USE IEEE.STD_LOGIC_ARITH.ALL;
    USE IEEE.STD_LOGIC_UNSIGNED.ALL;
    ------------------------------------------------------
    ------------实体inp实现分拍输入数据---------------------
    ------------------------------------------------------
    ENTITY inp IS
    	PORT(
    		clk    : IN STD_LOGIC;									--系统时钟
    		num	 : IN STD_LOGIC_VECTOR(7 downto 0);			--输入两次8位操作数
    		set	 : IN STD_LOGIC;									--置数端,高电平有效. num的信号赋值结束后,产生一个高脉冲可输入一个数
    		clear  : IN STD_LOGIC;									--清零端,高电平有效. 恢复初始状态. set为1时不可用
    		OK_x	 : OUT STD_LOGIC;									--第一个数置数成功显示端
    		OK_Y	 : OUT STD_LOGIC;									--第二个数置数成功显示端
    		x	    : OUT STD_LOGIC_VECTOR(7 downto 0);		--输出8位乘数x
    		y      : OUT STD_LOGIC_VECTOR(7 downto 0)			--输出8位乘数y
    	);
    END ENTITY inp;
    ------------------------------------------------------
    ----------------分拍输入使用流程------------------------
    ------------------------------------------------------
    ----1. num的引脚置高低电平------------------------------
    ----2. set置1,Led_x亮起,set置0---------------------
    ----3. num的引脚置第二个数-----------------------------
    ----4. set置1,Led_y亮起,set置0---------------------
    ------------------------------------------------------
    ARCHITECTURE BEHAVIOR OF inp IS
    SIGNAL tem_x   : STD_LOGIC_VECTOR(7 downto 0);			--result的中间结果
    SIGNAL tem_y   : STD_LOGIC_VECTOR(7 downto 0);			--result的中间结果
    BEGIN
    process(clk)
    VARIABLE count : INTEGER:=0;
    VARIABLE Flag  : INTEGER:=0;									--Flag为set信号标志位,放置在第二个时钟信号到来时(count已经等于1)进入y的赋值阶段。
    begin
    IF(clk'EVENT AND clk = '1')THEN
    	IF(set = '1')THEN
    		IF(count=0)THEN
    			tem_x<=num;												--若count为0,则将操作数赋值给x。
    			OK_x<='1';												--将第一个led灯点亮。
    			count := count + 1;
    			Flag := 0;
    		ELSIF(count=1 and Flag = 1)THEN
    			tem_y<=num;												--若count为1,则将操作数赋值给y。
    			OK_y<='1';												--将第二个led灯点亮。
    			count:= count+1;
    			Flag := 0;
    		END IF;
    	ELSE
    		Flag := 1;													--set为零时,Flag记录为1IF(clear = '1')THEN										--clear为1时,清空状态信息。
    			tem_x<="00000000";
    			tem_y<="00000000";
    			OK_x<='0';
    			OK_Y<='0';
    			count := 0;
    			Flag := 0;
    		END IF;
    	END IF;
    	x<=tem_x;
    	y<=tem_y;
    END IF;
    end process;
    END BEHAVIOR;
    

    (2) mulity_8bit.vhd:

    LIBRARY IEEE;
    USE IEEE.STD_LOGIC_1164.ALL;
    USE IEEE.STD_LOGIC_ARITH.ALL;
    USE IEEE.STD_LOGIC_UNSIGNED.ALL;
    ------------------------------------------------------
    ----实体mulity_8bit通过串行乘法实现8位二进制乘法---------
    ------------------------------------------------------
    ENTITY mulity_8bit IS
    	PORT(
    		clk    : IN STD_LOGIC;									--系统时钟
    		x	    : IN STD_LOGIC_VECTOR(7 downto 0);			--8位乘数x
    		y      : IN STD_LOGIC_VECTOR(7 downto 0);			--8位乘数y
    		start	 : IN STD_LOGIC;									--START为1时置数,为0时不工作
    		result : OUT STD_LOGIC_VECTOR(15 downto 0)		--16位结果
    	);
    END ENTITY mulity_8bit;
    ------------------------------------------------------
    --------------------串行乘法---------------------------
    ------------------------------------------------------
    ARCHITECTURE BEHAVIOR OF mulity_8bit IS
    SIGNAL p     : STD_LOGIC_VECTOR(15 downto 0);			--p,t为中间变量,记录每次一位相乘的结果
    SIGNAL t     : STD_LOGIC_VECTOR(15 downto 0);
    SIGNAL tem   : STD_LOGIC_VECTOR(15 downto 0);			--result的中间结果
    SIGNAL y_reg : STD_LOGIC_VECTOR(7 downto 0);				--y变量寄存器
    BEGIN
    PROCESS(clk,start)
    VARIABLE count : INTEGER:=0;
    VARIABLE Flag : INTEGER:=0;									--计算完成标志,等于1时计算完成,终止计算进程,将结果持续输出
    BEGIN 
    IF(clk'EVENT and clk = '1')THEN
    	IF(start = '1')THEN
    		IF(Flag = 0)THEN
    			IF(count = 9) THEN 								   --count= 9时,完成8次累加后将结果寄存于tem,ok置1
    				count := 0;
    				tem <= p;
    				Flag := 1;
    			ELSIF(count = 0) THEN								--count = 0时,赋初值
    				p(15 downto 0) <= "0000000000000000";
    				y_reg <= y;
    				t(7 downto 0)<= x(7 downto 0);
    				t(15 downto 8)<="00000000";
    				count := 1;
    			ELSE														--count在1~8时,移位累加
    				IF (y_reg(0) = '1') THEN
    					p <= p + t;
    				ELSE p <= p;
    				END IF;
    			y_reg(6 downto 0)<=y_reg(7 downto 1);			 --y_reg右移一位
    			y_reg(7) <= '0';
    			t(15 downto 1) <= t(14 downto 0);				 --t左移一位
    			t(0) <= '0';
    			count := count + 1;
    			END IF;
    		ELSIF (Flag = 1) THEN
    			result <= tem;
    		END IF;
    	ELSIF(start = '0')THEN
    		result <= "0000000000000000";
    		Flag:= 0;
    	END IF;
    END IF;
    END  PROCESS;
    END BEHAVIOR;
    
    
    展开全文
  • 从最基础的莫尔斯编码到二进制,基础电路和布尔逻辑运算的神奇结合。产生了目前人类最伟大的发明-计算机。二进制(binary)二进制的提出者是德国数学家莱布尼茨,他和牛顿发现了高等数学中的微积分。用二进制记数只...

    最近看了一本书《编码》,如何从头开始构建一台计算机。从最基础的莫尔斯编码到二进制,基础电路和布尔逻辑运算的神奇结合。产生了目前人类最伟大的发明-计算机。

    二进制(binary)

    二进制的提出者是德国数学家莱布尼茨,他和牛顿发现了高等数学中的微积分。用二进制记数只需要用到0和1两个符号,逢二进一。我们一般习惯了十进制,用0-9十个符号来表示数,逢十进一。二进制和十进制记数原理相同,仅仅是符号用的少。

    下面是二进制和十进制0-10的对照表。

    十进制二进制
    00
    11
    210
    311
    4100
    5101
    6110
    7111
    81000
    91001
    101010

    布尔运算(逻辑运算)

    所有男人都必有一死;苏格拉底是男人;因此,苏格拉底会死。

    类似代数,布尔运算符号为:and、or、not。在计算机中的逻辑运算中也叫与、或、非。算子不是一般的数字,而是集合。

    逻辑运算且满足一般代数运算的交换率、结合率和分配率。

    二进制和布尔运算结合

    AND

    and01
    000
    101

    OR

    or01
    001
    111

    NOT

    not01
    10

    逻辑门

    三种最基本的门

    79e24713dcd944664154bd716fa15f69.png
    and输入输入输出
    000
    010
    100
    111
    ----------------
    or000
    011
    101
    111
    ------------------------
    not01
    10

    或非门(NOR)

    e094c65c5db409cea3c7699cbbd0c29b.png

    与非门(NAND)

    fc0221ab35966ecb963fafc79460105b.png
    NOR输入输入输出
    001
    010
    100
    110
    ------------------------
    NAND001
    011
    101
    110

    摩根定律('+'为OR,''为AND)

    加法器(二进制)

    只要造出了加法器,就可以通过加法得到减法、乘法和除法;再进行幂运算,解方程.......

    在数学运算里,

    1. 0加0等于0;
    2. 0加1等于1;
    3. 1加0等于1;
    4. 1加1等于0,进位为1。

    注意到,我们的运算结果和上面的几个逻辑门中的都不满足,但是见证奇迹的时刻到了。我们可以把计算的结果分为两部分,一部分为加法结果,一部分为进位。然后再把进位结果进行二次相加,以此反复,最终就可以得到结果。

    只要我们的逻辑门足够多,就可以计算任意大的数。这里我采用的是8位的二进制数,两个八位的进制数和最大为11111111+11111111=111111110,在十进制里为510。也就是说可以计算510以内的任意加法(整数)。

    当我们把一个或门、一个非门和与非门连接起来,得到异或门

    40a371940e4256753f85a5784ad66e61.png
    XOR输入输入输出
    000
    011
    101
    110

    通过异或门,可以得到加和输出,进位输出直接通过与门就可以得到。

    为了看起来简单一点,把异或门表示为如下

    0c0d88985f7bd68c5319b443e3921bc5.png

    当我们把一个异或门和与门连接起来,就可以计算一位的二进制数。

    3dcf0ebc1e06107d729000dc4f34b7ed.png

    s表示加和输出,c表示进位输出。为了查看方便,同样简画为

    327fb87a2db9c16f7e81ea5d8a611bbd.png

    这个东西之所以叫半加器,因为它将两个二进制数相加,得出一个加法位和一个进位位。但是绝大多数二进制是多于一位的。半加器没有做到的是将之前一次的加法可能产生的进位纳入下一次运算。所以为了对三个二进制数进行加法运算,需要将两个半加器和一个或门做连接。

    9d034e1ce738220c925bd0bacefc9451.png

    这就是加法器本尊啦。一个加法器共需要18个继电器,因为每个与门、或门和非门都需要两个,因此一个异或门中就需要6个继电器。一个半加器=一个异或门和一个与门组成,所以一个半加器需要8个继电器。每个全加器由两个半加器和一个或门组成。所以它需要18个继电器。那么,一个8位的二进制加法器就需要8个全加器,共需144个继电器。

    一个加法器的输入输出:

    输入A输入B进位输入加和输出进位输出
    00000
    01010
    10010
    11001
    00110
    01101
    10101
    11111

    把八个全加器连接起来,就得到了一个加器。

    534a3ae73c2180932bc9389f19ede070.png

    DONE

    这就是最基本的计算机运算逻辑了,后面还有减法器、乘除法。人与人之间的差距也太大了,究竟是什么样智商的一群人高出了计算机,只能膜拜献出自己的膝盖了。

    展开全文
  • 文章目录74LS138译码器实现2位二进制乘法器-QuartusII 软件仿真一、74LS138译码器介绍二、真值表和逻辑表达式构建三、原理图设计及实验仿真四、总结用译码器设计组合逻辑电路的方法前言一、pandas是什么?...
  • 利用逻辑门电路构造二进制加法器

    万次阅读 2014-12-31 10:53:35
    下面简单阐述二进制加法机的构造原理,这是cpu计算单元的基本计算原理。 加法计算实际上分为两步,计算和和计算进位。在一般人进行加法运算的时候先计算两个数和,然后计算数进位,依此依次从低位计算到高位。二进制...
  • 二进制乘法原理与十进制乘法原理类似,都是将乘数的每一位和被乘数相乘,除此之外,二进制乘法还有其自身的特点,这对于硬件设计极为关键。 二进制乘法器可以分为有符号数乘法和无符号数乘法。无符号数乘法较为简单...
  • 数字电路乘法器设计

    2013-10-20 21:29:17
    本实验利用两位二进制乘法中乘数各位与被乘数相乘后移位相加的原理,拓展得到两个四位二进制数相乘原理。在max+plus2上进行原理图设计和软件仿真,软件通过后,下载到EPF10K10中,在GW48系列EDA/SOC实验开发系统...
  • 从列出竖式的过程中,你会发现,二进制乘法有个很大的优点,就是这个过程你不需要背九九乘法口诀表了。因为单个位置上,乘数只能是 0 或者 1,所以实际的乘法,就退化成了位移和加法。 在 13×9 这个例子里面,被...
  • 和小学学习数学一样,学完了加法之后,我们自然而然就来学习乘法。既然是退回到小学,我们就把问题搞的简单一点,...从列出竖式的过程中,你会发现,二进制乘法有一个很大的有点,就是这个过程你不需要背九九乘法...
  • 两位乘法器的二进制运算方法:设输入端两位二进制数分别为A1、A0和B1、B0,其输出端乘法结果表示为:P3、P2、P1 、P0 ;用二进制乘法运算方法可以写出真值表,接着利用真值表可以直接写出各个输出端的最小项表达式...
  • 【摘要】基于计算机组成原理课程实践环节的建设,...【关键词】乘法器、定点原码一位乘法、计算机组成原理、计算机组成与结构一、引言在计算机组成原理知识教学过程中,关于二进制乘法运算是一个较难理解的环节,其中又
  • 1、十进制中13乘以9,转换成二进制整个计算的过程 乘法口诀表了,因为单个位置上,乘数只能是0或者1,所以实际的乘法,就退化成了位移和加法 2、我们可以用一个开关来决定,下面的输出是完全复制输入,还是讲...
  • 电路的功能 8位D-A转换器的作用是把数字系统中的数字信号经转换后输出给记录仪或X-Y监视器。本电路由廉价元件构成。 因为使用了C-MOS D-A...输出电压EO为(数字数据/256)*VE,数字数据范围为0~255的二进制数。
  • 1.1、用二进制表示数据 1.2、用布尔代数 进行运算 1.3、用电路实现布尔运算 所有 电路能进行计算,计算机就是由这样的电路构成的。 2、已经知道的 2.1、电路能完成计算,所以可以设计加法、减法、乘法...,用...
  • 唐朔飞计算机组成原理答案完整版

    热门讨论 2011-12-11 21:51:19
     存储元件:存储一位二进制信息的物理元件,是存储器中最小的存储单位,又叫存储基元或存储元,不能单独存取。  存储字:一个存储单元所存二进制代码的逻辑单位。  存储字长:一个存储单元所存二进制代码的...
  • 存储元件——存储一位二进制信息的物理元件,是存储器中最小的存储单位,又叫存储基元或存储元,不能单独存取; 存储字——一个存储单元所存二进制代码的逻辑单位; 存储字长——一个存储单元所存二进制代码的位数;...
  • 在“计算”部分,我为你讲解了计算机的“计算”部分是怎么执行的,数据的二进制表示是怎么样的,我们执行的加法和乘法又是通过什么样的电路来实现的。 然而,光知道在两部分还不能算是真正揭开了CPU的秘密,...
  • 1.1.4 二进制与八进制、十六进制之间的转换 1.1.5 二进制数与十进制数之间的转换 1.2 编码 1.2.1 十进制数的二进制编码 1.2.2 带符号的二进制数的编码 1.2.3 带小数点的数的编码 1.2.4 字符编码 习题 第二章 组合...
  • 异步二进制计数器.ms9 异步二-十进制计数器.ms9 异步二-十进制计数器.ms9 (Security copy) 微分积分电路.ms10 恒流源式差分放大电路.ms10 戴维南等效电路.ms9 批量复制文件名.bat 数据选择器74LS153.ms9 数据选择...
  • 二进制的加法与乘法运算法则如下: 8、二进制 十进制: 乘权求和` 如(1101.01)2=1×23+1×22+0×21+1×20+0×2-1+1×2-2=8+4+0+1+0+0.25=(13.25)10 9、我们把二进制信息的一个数位叫作一个比特(Bit),它是计算机...
  • 1.4 二进制与十六进制 1.4.1 二进制 1.4.2 十六进制 1.5 二进制的逻辑运算 1.5.1 与 1.5.2 或 1.5.3 非 1.5.4 同或 1.5.5 异或 1.6 单片机的C51基础知识介绍 1.6.1 利用C语言开发单片机的优点 1.6.2 C51中的基本...
  • DSP控制器及其应用

    2009-08-22 00:04:47
    1.2 二进制、补码及其运算 1.2.1 数制 1.2.2 补码与加、乘运算 1.3 DSP控制器的基本原理 第2章 总体结构 2.1 总线结构 2.2 中央处理单元 2.2.1 输入比例部分 2.2.2 中央算术逻辑部分 2.2.3 乘法部分 2.3 辅助寄存器...
  • cpu模型机课程设计.zip

    2010-12-07 13:59:04
    考虑到成本与设备因素,本模型机采用最简单的二进制开关输入和发光二极管显示的方法,换句话说,本模型机中只使用两种“外部设备”:一种是二进制代码开关,它作为输入设备;另一种是发光二极管,它作为输出设备。 ...
  • 14.7.1 二进制码与ASCII码的转换 14.7.2 二进制码到BCD码的转换 14.7.3 BCD码到二进制码的转换 14.8 数字滤波 14.8.1 算术平均值法 14.8.2 滑动平均值法 14.8.3 防脉冲干扰平均值法 第15章 MCS—51应用系统设计、...
  • 11.3.1 用n的二进制分解式计算xn 250 11.3.2 用Fortran语言计算2n 251 11.4 整数对数 252 11.4.1 以2为底的整数对数 253 11.4.2 以10为底的整数对数 253 11.5 习题 257 第12章 以特殊值为底的数制 258 12.1 ...
  • 1. 0.6875D的二进制为 ( ) ① 0.0111B ② 0.1101B ③ 0.1011B ④ 0.1111B 2. 一条指令执行完后,CS=1000H,IP=1052H,则下一条指令的地址为 ( ) ① 2025H ② 11052H ③ 01052H ④ 10520...
  • 7.4 加1指令实验,让P1口的8个发光二极管模拟二进制的加法运算61 7.4.1 实现方法61 7.4.2 源程序文件61 7.4.3 程序分析解释62 7.5 加1指令实验(不进行二十进制调整)62 7.5.1 实现方法62 7.5.2 源程序文件63 7.5.3 ...

空空如也

空空如也

1 2
收藏数 28
精华内容 11
关键字:

二进制乘法原理电路