verilog练习:hdlbits网站上的做题笔记(4)

前言

3. Circuits

3.1 Combinational Logic

3.1.1 Basic Gates

3.1.1.1 Wire(Exams/m2014 q4h)

在这里插入图片描述

module top_module (
    input in,
    output out);
	assign out = in;
endmodule
3.1.1.2 GND(Exams/m2014 q4i)

在这里插入图片描述

module top_module (
    output out);
	assign out = 1'b0;
endmodule

3.1.1.3 NOR(Exams/m2014 q4e)

在这里插入图片描述

module top_module (
    input in1,
    input in2,
    output out);
    assign out = ~(in1|in2);
endmodule
3.1.1.4 Another gate(Exams/m2014 q4f)

在这里插入图片描述

module top_module (
    input in1,
    input in2,
    output out);
    assign out = in1&(~in2);

endmodule
3.1.1.5 Two gates(Exams/m2014 q4g)

在这里插入图片描述

module top_module (
    input in1,
    input in2,
    input in3,
    output out);
    assign out = (in1 ~^ in2)^in3;
endmodule
3.1.1.6 More logic gates(Gates)

There are 7 outputs, each with a logic gate driving it:

out_and: a and b
out_or: a or b
out_xor: a xor b
out_nand: a nand b
out_nor: a nor b
out_xnor: a xnor b
out_anotb: a and-not b

module top_module( 
    input a, b,
    output out_and,
    output out_or,
    output out_xor,
    output out_nand,
    output out_nor,
    output out_xnor,
    output out_anotb
);
	assign out_and	= a & b;
	assign out_or	= a | b;
	assign out_xor	= a ^ b;
    assign out_nand	=~ (a & b);
    assign out_nor	= ~(a | b);
	assign out_xnor	= a ~^ b;
	assign out_anotb= a & ~b;
    
endmodule

在这里插入图片描述

3.1.1.7 7420 chip(7420)

在这里插入图片描述

module top_module ( 
    input p1a, p1b, p1c, p1d,
    output p1y,
    input p2a, p2b, p2c, p2d,
    output p2y );
    assign p1y = ~(p1a & p1b & p1c & p1d);
    assign p2y = ~(p2a & p2b & p2c & p2d);

endmodule

在这里插入图片描述

3.1.1.8 Truth tables(Truthtable1)

3-8译码器
在这里插入图片描述
在这里插入图片描述

module top_module( 
    input x3,
    input x2,
    input x1,  // three inputs
    output f   // one output
);
	// assign f = x3 & x1 | x2 & x1 | ~x3 & x2;
    always@(*)begin
        case({x3,x2,x1})
            3'b000 : f = 0;
            3'b001 : f = 0;
            3'b010 : f = 1;
            3'b011 : f = 1;
            3'b100 : f = 0;
            3'b101 : f = 1;
            3'b110 : f = 0;
            3'b111 : f = 1;   
        endcase
    end
endmodule
3.1.1.9 Two-bit equality(Mt2015 eq2)

Create a circuit that has two 2-bit inputs A[1:0] and B[1:0], and produces an output z. The value of z should be 1 if A = B, otherwise z should be 0.

module top_module ( input [1:0] A, input [1:0] B, output z ); 
    assign z = A==B?1:0;
endmodule
3.1.1.10 Simple circuit A(Mt2015 q4a)

z = (x^y) & x

module top_module (input x, input y, output z);
    assign z = (x^y) & x;

endmodule
3.1.1.11 Simple circuit B(Mt2015 q4b)

在这里插入图片描述

module top_module ( input x, input y, output z );
	assign z = x ~^ y;
endmodule
3.1.1.12 Combine circuits A and B(Mt2015 q4)

在这里插入图片描述

module top_module (input x, input y, output z);
    wire z1,z2;
    
    assign z1 = (x^y) & x;
    assign z2 =  x ~^ y;
    assign z = (z1 | z2)^(z1 & z2);
endmodule
3.1.1.13 Ring or vibrate?(Ringer)

传入响铃信号时,如果处于振动状态则传入
在这里插入图片描述

module top_module (
    input ring,
    input vibrate_mode,
    output ringer,       // Make sound
    output motor         // Vibrate
);
    assign ringer = (ring & ~vibrate_mode)?1:0;
    assign motor = (ring & vibrate_mode)?1:0;
endmodule

在这里插入图片描述

3.1.1.14 Thermostat(Thermostat)

恒温器可以采用以下两种模式之一:加热(mode = 1)和冷却(mode = 0)。在加热模式下,当温度太低(too_cold = 1)时请打开加热器,但不要使用空调。在制冷模式下,当温度过高时(too_hot = 1)打开空调,但不要打开加热器。当加热器或空调打开时,还要打开风扇以使空气流通。此外,即使加热器和空调关闭,用户也可以要求风扇打开(fan_on = 1)。

尝试仅使用assign语句,以查看是否可以将问题描述转换为逻辑门的集合。

module top_module (
    input too_cold,
    input too_hot,
    input mode,
    input fan_on,
    output heater,
    output aircon,
    output fan
); 
    assign heater = mode & too_cold;
    assign aircon = ~mode & too_hot;
    assign fan = fan_on|heater|aircon;
endmodule

在这里插入图片描述

3.1.1.15 3-bit population count(Popcount3)

A “population count” circuit counts the number of '1’s in an input vector. Build a population count circuit for a 3-bit input vector.//也可以把各位直接加起来!

module top_module( 
    input [2:0] in,
    output [1:0] out );
    integer i;
    always@(*)begin
        out = 2'b00;
        for(i=0;i<3;i=i+1)begin
            if(in[i]==1'b1)
                out = out + 1'b1;
            else
                out = out;
        end
    end
endmodule

在这里插入图片描述

3.1.1.16 Gates and vectors(Gatesv)

You are given a four-bit input vector in[3:0]. We want to know some relationships between each bit and its neighbour:

  • out_both: Each bit of this output vector should indicate whether both the corresponding input bit and its neighbour to the left (higher index) are ‘1’. For example, out_both[2] should indicate if in[2] and in[3] are both 1. Since in[3] has no neighbour to the left, the answer is obvious so we don’t need to know out_both[3]. out_any: Each bit of this output vector should indicate whether any of the corresponding input bit and its neighbour to the right are ‘1’. For example,
  • out_any[2] should indicate if either in[2] or in[1] are 1. Since in[0] has no neighbour to the right, the answer is obvious so we don’t need to know out_any[0].
  • out_different: Each bit of this output vector should indicate whether the corresponding input bit is different from its neighbour to the left. For example, out_different[2] should indicate if in[2] is different from in[3]. For this part, treat the vector as wrapping around, so in[3]'s neighbour to the left is in[0].
module top_module( 
    input [3:0] in,
    output [2:0] out_both,
    output [3:1] out_any,
    output [3:0] out_different );
    assign out_both = {{in[3]&in[2]},{in[2]&in[1]},{in[1]&in[0]}};
    assign out_any = {{in[3]|in[2]},{in[2]|in[1]},{in[1]|in[0]}};
    assign out_different = {{in[3]^in[0]},{in[3]^in[2]},{in[2]^in[1]},{in[1]^in[0]}};
endmodule
//第二种方法:第一反应真的不是这个!
module top_module( 
    input [3:0] in,
    output [2:0] out_both,
    output [3:1] out_any,
    output [3:0] out_different );
    
    assign out_both = in[3:1] & in[2:0];
    assign out_any = in[3:1] | in[2:0];
    assign out_different = {in[0], in[3:1]} ^ in;
           
endmodule

在这里插入图片描述

3.1.1.17 Even longer vectors(Gatesv100)

在上一题的基础上扩展了

module top_module( 
    input [99:0] in,
    output [98:0] out_both,
    output [99:1] out_any,
    output [99:0] out_different );
   
    integer i;
    always@(*)begin
        for(i=0;i<100;i=i+1)begin
            if(i==99)  
                out_different[i] = {in[i]^in[0]};
            else begin
                out_both[i] = {{in[i+1]&in[i]}};
                out_any[i+1]={in[i+1]|in[i]};
                out_different[i] = {in[i+1]^in[i]};
            end
        end
    end
endmodule
//第二种方法:第一反应真的不是这个!
module top_module( 
    input [99:0] in,
    output [98:0] out_both,
    output [99:1] out_any,
    output [99:0] out_different );
   
 	assign out_both = in[99:1] & in[98:0];
    assign out_any = in[99:1] | in[98:0];
    assign out_different = {in[0], in[99:1]} ^ in;
endmodule

3.1.2 Multiplexers

3.1.2.1 2-to-1 multiplexer(Mux2to1)

Create a one-bit wide, 2-to-1 multiplexer. When sel=0, choose a. When sel=1, choose b.

module top_module( 
    input a, b, sel,
    output out ); 
	//assign out = sel?b:a;
    assign out = (~sel & a)|(sel & b);//这种写法是二选一多路选择器的本质!
endmodule

在这里插入图片描述

3.1.2.2 2-to-1 bus multiplexer(Mux2to1v)

Create a 100-bit wide, 2-to-1 multiplexer. When sel=0, choose a. When sel=1, choose b

在这里插入图片描述

3.1.2.3 9-to-1 multiplexer(Mux9to1v)

Create a 16-bit wide, 9-to-1 multiplexer. sel=0 chooses a, sel=1 chooses b, etc. For the unused cases (sel=9 to 15), set all output bits to ‘1’.

module top_module( 
    input [15:0] a, b, c, d, e, f, g, h, i,
    input [3:0] sel,
    output [15:0] out );
    always@(*)begin
        case(sel)
            'd0:out=a;
            'd1:out=b;
            'd2:out=c;
            'd3:out=d;
            'd4:out=e;
            'd5:out=f;
            'd6:out=g;
            'd7:out=h;
            'd8:out=i;
            default:out='hffff;
        endcase
    end

endmodule

在这里插入图片描述

3.1.2.4 256-to-1 multiplexer(Mux256to1)

Create a 1-bit wide, 256-to-1 multiplexer. The 256 inputs are all packed into a single 256-bit input vector. sel=0 should select in[0], sel=1 selects bits in[1], sel=2 selects bits in[2], etc.
Expected solution length: Around 1 line

//提示一行完成(本来想着用循环语句的,结果还可以这样!)
module top_module( 
    input [255:0] in,
    input [7:0] sel,
    output out );
    assign out = in[sel];
endmodule
3.1.2.5 256-to-1 4-bit multiplexer(Mux256to1v)

Create a 4-bit wide, 256-to-1 multiplexer. The 256 4-bit inputs are all packed into a single 1024-bit input vector. sel=0 should select bits in[3:0], sel=1 selects bits in[7:4], sel=2 selects bits in[11:8], etc.
Expected solution length: Around 1–5 lines.

module top_module( 
    input [1023:0] in,
    input [7:0] sel,
    output [3:0] out );
    
    assign out = {in[sel * 4 + 3], in[sel * 4 + 2], in[sel * 4 + 1], in[sel * 4]};

endmodule

这一题有意思!本来想着是用下面一行代码完事,结果编译不过去!

 assign out=in[(sel*4+3):sel*4];

于是乎,通过尝试,发现下面这种方式可以!

assign out = {in[sel * 4 + 3], in[sel * 4 + 2], in[sel * 4 + 1], in[sel * 4]};

但是,这还是不够!于是又通过检索,发现还有种高大上的写法!

  	//assign out=in[(sel*4+3):sel*4];(错误的写法)
    //assign out = {in[sel * 4 + 3], in[sel * 4 + 2], in[sel * 4 + 1], in[sel * 4]};
    assign out = in[sel*4+:4];//从sel*4开始,选择比特序号大于sel*4的4位bit,相当于[sel*4+3:sel*4]
	assign out = in[sel*4+3-:4];//从sel*4+3开始,选择比特序号小于sel*4+3的4位bit,相当于[sel*4+3:sel*4]

前面这两种写法,参考微信推文Verilog专题(七)如何用一行code描述256to1的Mux,担心下一次这个链接打不开了,于是截图
在这里插入图片描述
在这里插入图片描述

3.1.3 Arithmetic Circuits

3.1.3.1 Half adder(Hadd)

创建一个半加法器。半加法器将两个位相加(无进位),并产生总和与进位。

module top_module( 
    input a, b,
    output cout, sum );
   
    //assign {cout,sum} = a + b;
    assign cout = a & b;
    assign sum = a ^ b;
endmodule
3.1.3.2 Full adder(Fadd)

创建一个完整的加法器。一个全加法器将三个位(包括进位)相加,并产生一个总和与一个进位。

module top_module( 
    input a, b, cin,
    output cout, sum );
    //assign {cout,sum}=a+b+cin;
    
    assign sum = a^b^cin;
    //assign cout = ( a & b )|( a & cin )|( b & cin );
    assign cout = a & b | (a | b) & cin;
endmodule

在这里插入图片描述

3.1.3.3 3-bit binary adder(Adder3)

Now that you know how to build a full adder, make 3 instances of it to create a 3-bit binary ripple-carry adder. The adder adds two 3-bit numbers and a carry-in to produce a 3-bit sum and carry out. To encourage you to actually instantiate full adders, also output the carry-out from each full adder in the ripple-carry adder. cout[2] is the final carry-out from the last full adder, and is the carry-out you usually see.

//行波进位加法器
module top_module( 
    input [2:0] a, b,
    input cin,
    output [2:0] cout,
    output [2:0] sum );
   	
    integer i;
    always@(*)begin
        for(i=0;i<3;i=i+1)begin
            if(i == 0)begin
                sum[i] = a[i] ^ b[i] ^ cin;
                cout[i]=a[i]&b[i] | a[i]&cin | b[i]&cin;
            end
            else begin
                sum[i] = a[i] ^ b[i] ^ cout[i-1];
                cout[i]=a[i]&b[i] | a[i]&cout[i-1] | b[i]&cout[i-1];
            end
        end
    end
endmodule

在这里插入图片描述

3.1.3.4 Adder(Exams/m2014 q4j)

在这里插入图片描述

module top_module (
    input [3:0] x,
    input [3:0] y, 
    output [4:0] sum);
    //assign sum = x + y;//这一行代码就可以替换下面所有!
    wire [3:0] cout;
    wire [3:0] sum_i;
    assign sum_i[0]=x[0]^y[0];
    assign cout[0]=x[0]&y[0];
    
    assign sum_i[1]=x[1]^y[1]^cout[0];
    assign cout[1]=x[1]&y[1]|x[1]&cout[0]|y[1]&cout[0];
    
    assign sum_i[2]=x[2]^y[2]^cout[1];
    assign cout[2]=x[2]&y[2]|x[2]&cout[1]|y[2]&cout[1];
    
    assign sum_i[3]=x[3]^y[3]^cout[2];
    assign cout[3]=x[3]&y[3]|x[3]&cout[2]|y[3]&cout[2];
	
    assign sum = {cout[3],sum_i};
endmodule
3.1.3.5 Signed addition overflow(Exams/ece241 2014 q1c)

假设您有两个有符号的输入,即a [7:0]和b [7:0]。这些数字相加产生s [7:0]。同时计算是否发生(有符号的)溢出。

module top_module (
    input [7:0] a,
    input [7:0] b,
    output [7:0] s,
    output overflow
); //
 
    // assign s = ...
    // assign overflow = ...
    assign s = a + b;
    assign overflow = a[7] & b[7] & ~s[7] | ~a[7] & ~b[7] & s[7];
    //assign overflow = (a[7]==b[7])?((a[7])?(!s[7]?1:0):(s[7]?1:0)):0;

endmodule

在这里插入图片描述

一个有符号数的最高位代表正负,最高位是0代表正数,最高位是1代表负数。那什么时候会发生溢出(overflow)的情况?只有两个正数(负数)相加才会发生溢出,相减(即一正一负)是不会发生溢出的
两个正数相加(符号位都为0),如果结果为负数,则发生溢出;两个负数相加(符号位都为1),如果结果为正数,则发生溢出,其他情况都为没有发生溢出。

3.1.3.6 100-bit binary adder(Adder100)

创建一个100位二进制加法器。加法器将两个100位数字和一个进位相加,以产生100位总和并执行。

module top_module( 
    input [99:0] a, b,
    input cin,
    output cout,
    output [99:0] sum );
    assign {cout,sum}=a+b+cin;
endmodule
3.1.3.7 4-digit BCD adder(Bcdadd4)

You are provided with a BCD (binary-coded decimal) one-digit adder named bcd_fadd that adds two BCD digits and carry-in, and produces a sum and carry-out.

module bcd_fadd {
    input [3:0] a,
    input [3:0] b,
    input     cin,
    output   cout,
    output [3:0] sum );

Instantiate 4 copies of bcd_fadd to create a 4-digit BCD ripple-carry adder. Your adder should add two 4-digit BCD numbers (packed into 16-bit vectors) and a carry-in to produce a 4-digit sum and carry out.

module top_module( 
    input [15:0] a, b,
    input cin,
    output cout,
    output [15:0] sum );
    
   
    wire[2:0]	cout_1;
    
    bcd_fadd u1(
        .a      (a[3:0]		),
        .b      (b[3:0]		),
        .cin	(cin		),
        .cout	(cout_1[0]	),
        .sum	(sum[3:0]	)
    );
    bcd_fadd u2(
        .a      (a[7:4]		),
        .b      (b[7:4]		),
        .cin	(cout_1[0]	),
        .cout	(cout_1[1]	),
        .sum	(sum[7:4]	)
    );
    bcd_fadd u3(
        .a      (a[11:8]	),
        .b      (b[11:8]	),
        .cin	(cout_1[1]	),
        .cout	(cout_1[2]	),
        .sum	(sum[11:8]	)
    );
    bcd_fadd u4(
        .a      (a[15:12]	),
        .b      (b[15:12]	),
        .cin	(cout_1[2]	),
        .cout	(cout		),
        .sum	(sum[15:12]	)
    );

        
endmodule

在这里插入图片描述

3.1.4 Karnaugh Map to Circuit

为什么对这部分没有任何印象?

3.1.4.1 3-variable(Kmap1)

实现下面的卡诺图描述的电路在这里插入图片描述

module top_module(
    input a,
    input b,
    input c,
    output out  ); 
    assign out = a |b |c ;//只要不全为0,就输出1

endmodule

在这里插入图片描述

3.1.4.2 4-variable(Kmap2)

实现下面的卡诺图描述的电路。
在这里插入图片描述

module top_module(
    input a,
    input b,
    input c,
    input d,
    output out  ); 
	assign out = ~a & ~d | ~b & ~c | b & c & d | a & c & d;
endmodule

在这里插入图片描述

3.1.4.3 4-variable(Kmap3)

实现下面的卡诺图描述的电路。
在这里插入图片描述

module top_module(
    input a,
    input b,
    input c,
    input d,
    output out  ); 
	 assign out = ~b & c | a & c | a & ~d;
endmodule

在这里插入图片描述

3.1.4.4 4-variable(Kmap4)

实现下面的卡诺图描述的电路。
在这里插入图片描述

module top_module(
    input a,
    input b,
    input c,
    input d,
    output out  ); 
	assign out = ~a & b & ~c & ~d | a & ~b & ~c & ~d | 
        		 ~a & ~b & ~c & d | a & b & ~c & d | 
        		 ~a & b & c & d | a & ~b & c & d | 
        		 ~a & ~b & c & ~d | a & b & c & ~d;

endmodule

在这里插入图片描述

3.1.4.5 Minimum SOP and POS(Exams/ece241 2013 q3)

A single-output digital system with four inputs (a,b,c,d) generates a logic-1 when 2, 7, or 15 appears on the inputs, and a logic-0 when 0, 1, 4, 5, 6, 9, 10, 13, or 14 appears. The input conditions for the numbers 3, 8, 11, and 12 never occur in this system. For example, 7 corresponds to a,b,c,d being set to 0,1,1,1, respectively.

Determine the output out_sop in minimum SOP form, and the output out_pos in minimum POS form.

module top_module (
    input a,
    input b,
    input c,
    input d,
    output out_sop,
    output out_pos
); 
    assign out_sop = c & d | ~a & ~b & c;
    assign out_pos = ~((~c | ~d) & (a | b | ~c));


endmodule
3.1.4.6 Karnaugh map(Exams/m2014 q3)

考虑下面的卡诺图所示的函数f。实现此功能。d无关紧要,这意味着您可以选择输出任何方便的值。
在这里插入图片描述

3.1.4.7 Karnaugh map(Exams/2012 q1g)

考虑下面的卡诺图所示的函数f。实现此功能。(原始问题要求简化功能的SOP和POS形式。)
在这里插入图片描述

module top_module (
    input [4:1] x,
    output f
); 
	assign f = ~x[1] & x[3] | x[2] & x[3] & x[4] | ~x[2] & ~x[4];
endmodule

3.1.4.8 K-map implemented with a multiplexer(Exams/ece241 2014 q3)

对于以下卡诺图,请使用一个4对1多路复用器和所需的2对1多路复用器,但要使用尽可能少的电路,以给出电路实现方案。不允许使用任何其他逻辑门,并且必须使用a和b作为多路复用器选择器输入,如下面的4对1多路复用器所示。
在这里插入图片描述

module top_module (
    input c,
    input d,
    output [3:0] mux_in
); 
	assign mux_in[0] = c ? 1'b1 : d;
    assign mux_in[1] = 1'b0;
    assign mux_in[2] = d ? 1'b0 : 1'b1;
    assign mux_in[3] = c ? d : 1'b0;
    
    /*
    assign mux_in[0] = c | d;
    assign mux_in[1] = 1'b0;
    assign mux_in[2] = ~d;
    assign mux_in[3] = c & d;
    */

endmodule

在这里插入图片描述

后记

冲冲冲!

  • 5
    点赞
  • 26
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 5
    评论
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

杰之行

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值