【牛客】1 基础语法

VL1 四选一多路器

`timescale 1ns/1ns
module mux4_1(
input [1:0]d1,d2,d3,d0,
input [1:0]sel,
output [1:0]mux_out
);
//*************code***********//
assign mux_out = (sel==0)?d3:
                 ((sel==1)?d2:
                 ((sel==2)?d1:
                 d0));
//*************code***********//
endmodule

VL2 异步复位的串联T触发器

题目已经提示了是两个串联的T触发器,只要记得T触发器在输入高电平时,输出翻转即可。

`timescale 1ns/1ns
module Tff_2 (
input wire data, clk, rst,
output reg q  
);
//*************code***********//
reg q_r;
always@(posedge clk or negedge rst)
begin
    if(~rst) begin
        q_r <= 1'b0;
        q <= 1'b0;
    end
    else begin
        if(data)
            q_r <= ~ q_r;
        if(q_r)
            q <= ~q;
    end
end
//*************code***********//
endmodule

VL3 奇偶校验

按位异或即可。

`timescale 1ns/1ns
module odd_sel(
input [31:0] bus,
input sel,
output check
);
//*************code***********//
assign check = sel?(^bus):(~^bus);

//*************code***********//
endmodule

VL4 移位运算与乘法

写完才看到要求用移位运算,不过也简单,把乘法分解成移位相加即可。

注意把输入的d先保存起来。

`timescale 1ns/1ns
module multi_sel(
input [7:0]d ,
input clk,
input rst,
output reg input_grant,
output reg [10:0]out
);
//*************code***********//
reg [1:0]state;
reg [7:0]d_r;
always@(posedge clk or negedge rst)
begin
    if(~rst)begin
        input_grant <= 1'b0;
        out <= 'd0;
        state <= 'd0;
        d_r <= 'd0;
    end
    else begin
        if(state == 0)begin
            input_grant <= 1'b1;
            out <= d;
            d_r <= d;
            state <= 1;
        end else if(state == 1)begin
            input_grant <= 1'b0;
            out <= 3 * d_r;
            state <= 2;
        end else if(state == 2)begin
            out <= 7 * d_r;
            state <= 3;            
        end else if(state == 3)begin
            out <= 8 * d_r;
            state <= 0;            
        end
    end
end

//*************code***********//
endmodule

VL5 位拆分与运算

在sel==0时把d保存起来。

`timescale 1ns/1ns

module data_cal(
input clk,
input rst,
input [15:0]d,
input [1:0]sel,

output reg [4:0]out,
output reg validout
);
//*************code***********//
reg [15:0]d_r;
always@(*)
begin
    case(sel)
    0:begin
        validout=0;
        out=0;
    end
    1:begin
        validout=1;
        out=d_r[3:0]+d_r[7:4];
    end
    2:begin
        validout=1;
        out=d_r[3:0]+d_r[11:8];
    end
    3:begin
        validout=1;
        out=d_r[3:0]+d_r[15:12];
    end
    endcase
end

always@(posedge clk or negedge rst)
begin
    if(~rst)
        d_r <= 'd0;
    else begin if(sel == 0)
        d_r <= d;
    end
end

//*************code***********//
endmodule

VL6 多功能数据处理器

`timescale 1ns/1ns
module data_select(
    input clk,
    input rst_n,
    input signed[7:0]a,
    input signed[7:0]b,
    input [1:0]select,
    output reg signed [8:0]c
);
always@(posedge clk or negedge rst_n)
begin
    if(~rst_n)
    c=0;
    else begin
    case(select)
        0:c=a;
        1:c=b;
        2:c=a+b;
        3:c=a-b;
    endcase
    end
end
endmodule

VL7 求两个数的差值

`timescale 1ns/1ns
module data_minus(
    input clk,
    input rst_n,
    input [7:0]a,
    input [7:0]b,

    output  reg [8:0]c
);
always@(posedge clk or negedge rst_n)
begin
    if(~rst_n)
        c <= 'd0;
    else begin
        if(a>b)
            c<=a-b;
        else
            c<=b-a;
    end
end
endmodule

VL8 使用generate…for语句简化代码

这道题要求使用generate for语句,这个和for循环并不相同,首先generate for必须要使用genvar定义索引变量,其次generate for可以用来将一个模块例化多次,而for循环通常只是用于赋值。

这道题其实用for循环就够了。

`timescale 1ns/1ns
module gen_for_module( 
    input [7:0] data_in,
    output [7:0] data_out
);
genvar i;
generate
for(i=0;i<8;i=i+1)begin 
    assign data_out[i]=data_in[7-i]; 
end
endgenerate
endmodule

VL9 使用子模块实现三输入数的大小比较

这题要求通过例化子模块实现三个数的大小比较,又由于子模块是时序逻辑,所以要经过两次比较,延两个周期。

`timescale 1ns/1ns
module main_mod(
    input clk,
    input rst_n,
    input [7:0]a,
    input [7:0]b,
    input [7:0]c,
    
    output [7:0]d
);
wire [7:0]temp1;
wire [7:0]temp2;
child_mod u0(
    .clk(clk),
    .rst_n(rst_n),
    .a(a),
    .b(b),
    .c(temp1)
);
child_mod u1(
    .clk(clk),
    .rst_n(rst_n),
    .a(a),
    .b(c),
    .c(temp2)
);
child_mod u2(
    .clk(clk),
    .rst_n(rst_n),
    .a(temp1),
    .b(temp2),
    .c(d)
);
endmodule

module child_mod(
    input clk,
    input rst_n,
    input [7:0]a,
    input [7:0]b,
    
    output reg [7:0]c 
);
always@(posedge clk or negedge rst_n)
begin
    if(~rst_n)
        c <= 'd0;
    else begin
        if(a<b)
            c<=a;
        else
            c<=b;
    end
end
endmodule

VL10 使用函数实现数据大小端转换

这题要求用function,注意一下function怎么写就行了。

`timescale 1ns/1ns
module function_mod(
    input [3:0]a,
    input [3:0]b,
    
    output [3:0]c,
    output [3:0]d
);
function [3:0]convert;
input [3:0]in;
integer i;
for(i=0;i<4;i=i+1)begin
    convert[i] =in[3-i]; 
end
endfunction
assign c = convert(a);
assign d = convert(b);
endmodule

 

posted @ 2023-02-20 21:13  Magnolia666  阅读(102)  评论(0编辑  收藏  举报