Featured image of post 计算机系统-多功能 ALU 运算器设计实验

计算机系统-多功能 ALU 运算器设计实验

HDU_2025_计算机系统课程大实验1(2请见shiori

实验报告

实验目的:

  1. 学习多功能 ALU 的工作原理
  2. 掌握采用行为建模方式编程实现运算器的设计方法
  3. 学习利用顶层模块来协助实现板级验证的方法

逻辑程序设计

模块设计:

顶层模块为ALU_TOP,其中引入ALU_FUN和Display三个模块

以下为顶层模块输入输出信号,实例化另外两个模块的时候也使用顶层模块信号

输入 (Inputs):

  • Clk,时钟信号(控制ABF输入信号的显示和选择、ALU_OP信号的激活)
  • Button[2:0]: 选择信号,从2-0分别控制ABF三个的输入,
  • Reset:复位信号,ABF全部归零便于不同数据的输入和调试
  • Switch_reg[31:0]:32位信号,对应ABF,通过Button[2:0]来决定目前32位对应的信号是哪个;在选择到F的时候同时对应到ALU_OP信号来进行运算

输入 (Outputs)::

  • Led[31:0]用于输出ZF OF信号(低二位)
  • Enable:使能信号(默认为1,有效)
  • Seg_decode[7:0]:译码后数码管分组显示信号的控制信号

逻辑程序源代码

OF考虑到溢出符号判断的第一种方法OF= ​C31⊕C32​,AB操作数符号相同才可能发生溢出;通过F31判定符号位的同时结合C32判断进位完成溢出判定所以我们进行运算时留出32位来进行进位判定

分为三个模块
ALU_FUN模块:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
`timescale 1ns / 1ps
module ALU_FUN(
    input [31:0] A,
    input [31:0] B,
    input [3:0] ALU_OP, // 如题,用4根控制线来选择16种运算功能
    output reg [31:0] F,
    output ZF,
    output OF
);

assign ZF = (F == 32'b0); //零标志 Zero Flag

//补码加减法判定
wire [32:0] sum = {1'b0,A} + ((ALU_OP[3]) ? {1'b0,~B}+32'b1 : {1'b0,B});
wire C32 = sum[32];  // 第32位,用于判定

// overflow flag
assign OF = (ALU_OP == 4'b0000) ?  // ADD overflow
               ((A[31] == B[31]) && (F[31] != A[31])) :
             (ALU_OP == 4'b1000) ?  // SUB overflow
               ((A[31] != B[31]) && (F[31] != A[31])) :
             1'b0;


wire signed [31:0] A_signed=A;
wire signed [31:0] B_signed=B;

always @(*) begin
   case (ALU_OP) 
        4'b0000: F = A + B; //ADD
        4'b0001: F = A<<B[4:0]; // sll(shift left logical),只需要5位可以表示所有位数
        4'b0010: F = (A_signed < B_signed) ? 32'b1 : 32'b0; //slt(signed less than)有符号比较
        4'b0011: F = (A < B) ? 32'b1 : 32'b0; //sltu(unsigned less than)无符号比较
        4'b0100: F = A ^ B; //xor
        4'b0101: F = A >> B[4:0]; //srl(shift right logical)
        4'b0110: F = A | B; //or
        4'b0111: F = A & B; //and
        4'b1000: F = A - B; //sub
        4'b1001: F = A + 1; //inca
        4'b1010: F = A; //outa
        4'b1011: F = B+1;// incb
        4'b1100: F = 32'b0; //out0
        4'b1101: F = A_signed>>>B[4:0]; //sra
        default: F = 32'b0;
   endcase
end

endmodule

Display:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
`timescale 1ns / 1ps
module Display(
    input clk,              // 50MHz主时钟
    input [31:0] data,      // 32位显示数据
    output reg [2:0] which, // 3:8译码器输入
    output enable,          // 译码器使能 
    output reg [7:0] seg_decode    // 段选信号
);

// 分频计数器(2.5ms/数码管,分频实现整体刷新率50MHz)
reg [16:0] cnt;

// 数码管选择计数器(0-7循环)
always @(posedge clk) begin
    if(cnt == 17'd124_999) begin  // 50MHz/(8*50Hz)=125000
        cnt <=0;
        which <= (which == 3'd7) ? 3'd0 : which + 1;
    end else begin
       cnt <= cnt+1;
    end
end

// 当前显示的数字选择
wire [3:0] digit = data[31-which*4 -: 4]; // 每4位一组

// 7段译码器(共阳极低电平有效)
always @(*) begin
    case(digit)
            4'h0: seg_decode = 8'b0000_0011; // 0
            4'h1: seg_decode = 8'b1001_1111; // 1
            4'h2: seg_decode = 8'b0010_0101; // 2
            4'h3: seg_decode = 8'b0000_1101; // 3
            4'h4: seg_decode = 8'b1001_1001; // 4
            4'h5: seg_decode = 8'b0100_1001; // 5
            4'h6: seg_decode = 8'b0100_0001; // 6
            4'h7: seg_decode = 8'b0001_1111; // 7
            4'h8: seg_decode = 8'b0000_0001; // 8
            4'h9: seg_decode = 8'b0000_1001; // 9
            4'hA: seg_decode = 8'b0001_0001; // A
            4'hB: seg_decode = 8'b1100_0001; // B
            4'hC: seg_decode = 8'b0110_0011; // C
            4'hD: seg_decode = 8'b1000_0101; // D
            4'hE: seg_decode = 8'b0110_0001; // E
            4'hF: seg_decode = 8'b0111_0001; // F
            default: seg_decode = 8'b1111_1111; //全灭
    endcase
end

assign enable = 1'b1; // 常使能译码器

endmodule

分频这里cnt是一个17位计数器,从0计数到124,999(共125,000个时钟周期),默认设置clk周期50mhz

  • 扫描周期

    • 每个数码管显示时间 = 125,000 × 20ns = 2.5ms

    • 8个数码管完整扫描周期 = 8 × 2.5ms = 20ms

  • 刷新率

    • 整体刷新率 = 1/20ms = 50Hz(避免人眼看到闪烁)

ALU_TOP:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
`timescale 1ns / 1ps
module ALU_TOP(
    input clk,  //50Mhz
    input [31:0] switch_reg, //切换的赋值对象
    input [2:0] button,//控制对象,AB以及ALU
    output [31:0] led, //led输出信号,低两位ZF OF
    output [7:0] seg_decode, //用数码管分组显示信号
    output [2:0] which, //数码管如何选择
    output enable, //使能信号
    input reset// 清0信号
    );
//ALU模块提供
reg [31:0] A_reg;
reg [31:0] B_reg;
reg [3:0] ALU_OP;

wire [31:0] F;
wire ZF;
wire OF;

ALU_FUN uut(
    .A(A_reg),
    .B(B_reg),
    .ALU_OP(ALU_OP),
    .F(F),
    .ZF(ZF),
    .OF(OF)
);

always @(posedge clk) begin
    if(reset) begin
        A_reg<=32'b0;
        B_reg<=32'b0;
        ALU_OP<=4'b0;
    end else begin
        if(button[2]) A_reg <= switch_reg;
        if(button[1]) B_reg <= switch_reg;
        if(button[0]) ALU_OP <= switch_reg[3:0];
    end
end 

// 显示数据选择
wire [31:0] display_data = 
    button[0] ? A_reg :
    button[1] ? B_reg : 
    F;

// 数码管显示实例化
Display uut_display(
    .clk(clk),
    .data(display_data),
    .which(which),
    .enable(enable),
    .seg_decode(seg_decode)
);

assign led ={30'b0,OF,ZF}; //led输出标志位


endmodule

测试仿真设计

仿真程序源代码

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
`timescale 1ns / 1ps

module ALU_Sim();
    reg [31:0] A, B;
    reg [3:0] ALU_OP;
    wire [31:0] F;
    wire ZF, OF;

    ALU_FUN uut (
        .A(A),
        .B(B),
        .ALU_OP(ALU_OP),
        .F(F),
        .ZF(ZF),
        .OF(OF)
    );

    // 每组两个数据进行测试任务
    task run(input [31:0] a, input [31:0] b, input [3:0] op, input [40*8-1:0] des);
        begin
            A = a; B = b; ALU_OP = op;
            #10;
            // $display("=== %s ===\n", des);
            $display("[-%35s A=%h, B=%h, OP=%b => F=%h, ZF=%b, OF=%b\n",des, A, B, ALU_OP, F, ZF, OF);
        end
    endtask


    initial begin
        $display("⬇⬇⬇ ALU simulations\n");

        //  1. ADD 加法测试
        run(32'h0000_0001, 32'h0000_0002, 4'b0000, "Basic Addition");
        run(32'h7FFF_FFFF, 32'h0000_0001, 4'b0000, "overflow case");
        run(32'hFFFFFFFF, 32'h0000_0001, 4'b0000, "result in 0");

        //  2. SUB 减法测试
        run(32'h0000_0003, 32'h0000_0002, 4'b1000, "basic subtraction");
        run(32'h8000_0000, 32'h0000_0001, 4'b1000, "overflow case");
        run(32'h0000_0001, 32'h0000_0001, 4'b1000, "result in 0");

        //  3. SLT 有符号比较
        run(32'hFFFF_FFFF, 32'h0000_0001, 4'b0010, "STL Test: -1 < 1");
        run(32'h0000_0002, 32'hFFFFFFFE, 4'b0010, "STL Test: 2 > -2");

        // 4. SLTU 无符号比较
        run(32'h0000_0001, 32'h0000_0002, 4'b0011, "SLTU Test: 1 < 2");
        run(32'hFFFF_FFFF, 32'h0FFFFFFF, 4'b0011, "SLTU Test: 0xfffffff?");

        //  5. SLL 左移
        run(32'h0000_0001, 32'h0000_0004, 4'b0001, "SLL Test: 1 << 4");
        run(32'h0000_FF00, 32'h0000_0008, 4'b0001, "SLL Test: 0xFF00 << 8");

        //  6. SRL 逻辑右移
        run(32'h0000_0080, 32'h0000_0002, 4'b0101, "SRL Test: >> 2");
        run(32'h8000_0000, 32'h0000_0003, 4'b0101, "SRL Test: high bit mask's right shift");

        //  7. SRA 算术右移
        run(32'hFFFF_FF00, 32'h0000_0008, 4'b1101, "SRA Test: -256>> 8");
        run(32'h7FFF_FF00, 32'h0000_0008, 4'b1101, "SRA Test: positive number >> 8");

        //  8. XOR 异或
        run(32'h0000_FF00, 32'h0000_00FF, 4'b0100, "XOR Test: FF00 ^ 00FF");
        run(32'hAAAA_AAAA, 32'hAAAA_AAAA, 4'b0100, "XOR Test: the same number xor -> 0");

        //  9. OR 和 AND
        run(32'h1234_5678, 32'hFFFF_0000, 4'b0110, "OR Test: all 1");
        run(32'h1234_5678, 32'h0000_FFFF, 4'b0111, "AND Test: keep low bits");

        //  10. INCA / INCB / OUTA / OUT0
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1001, "INCA Test: A+1");
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1010, "OUTA Test: A");
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1011, "INCB Test: B+1");
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1100, "OUT0 Test: 0");

        //  11. 默认不动
        run(32'hDEAD_BEEF, 32'h1234_5678, 4'b1111, "DEFAULT Test: keep");

        $display("\n>>> 仿真结束");
        $finish;
    end

  
endmodule

这样的显示状态直接明了,也便于检测,我特地挑选了一些特殊的状态进行检测

仿真波形和结果

分析:

  1. 加法
  • 基本加法如 1 + 2 = 3 正确执行,F=0x00000003,未溢出(OF=0)。
  • 测试最大有符号数加 1(0x7FFFFFFF + 1)正确检测到溢出(OF=1),结果回绕为最小负数(F=0x80000000)表示溢出逻辑正确。
  • 测试 -1 + 1 = 0(即 0xFFFFFFFF + 1 = 0x00000000)无溢出,零标志(ZF=1)设置正确。
  1. 减法(SUB)
  • 基本减法如 3 - 2 = 1、1 - 1 = 0 等无符号溢出,溢出标志保持为 0(OF=0),零结果正确设置 ZF=1。
  • 特别测试最小有符号数 -1(0x80000000 - 1)正确检测到溢出(OF=1),结果回绕为最大正数,说明减法溢出判断逻辑有效。
  1. 有符号比较(SLT) 测试 -1 < 1 正确判为真,F=1;2 > -2 判为假,F=0。说明有符号比较功能正确

  2. 无符号比较(SLTU)

  • 测试 1 < 2 判为真,F=1;0xFFFFFFFF > 0x0FFFFFFF 判为假,F=0。验证无符号比较可以使用。
  1. 逻辑左移(SLL)
  • 测试 1 « 4 = 0x10,0xFF00 « 8 = 0x00FF0000,移位操作正确,未影响溢出标志位(OF=0)。
  1. 逻辑右移(SRL)
  • 测试 0x80 » 2 = 0x20;以及高位为 1 的数右移后不填充符号位,逻辑右移功能可以使用。
  1. 算术右移(SRA)
  • 测试 -256 » 8 = -1,保持符号位,验证算术右移左侧符号填充正确;正数右移结果也正确。
  1. 位运算(XOR / OR / AND)
  • XOR、OR、AND 运算结果匹配预期,例如相同数异或为 0,或全 1,可以正常使用,零标志设置正确。
  1. 特殊操作(INCA / INCB / OUTA / OUT0)
  • A+1 与 B+1 功能正确,输出当前 A、B、零值等操作符合预设功能规格。
  1. 默认操作(DEFAULT)
  • 默认 ALU_OP 0xF 情况下输出始终为 0,可以正常保存之前的状态。
  1. 状态位总结
  • 零标志(ZF)能在结果为0时准确置为1,否则为0。
  • 溢出标志(OF)仅在 ADD、SUB 的符号范围越界时置为1,其他操作保持为0

RTL电路图

顶层模块(直接用老师给的了)

RTL视图(ALU_TOP)

管脚约束

1.  **管脚约束说明(输入输出变量的I/O管脚需求分析,及板级硬件资源配置理由)

将button[2:0]部分约束到提供的八个按钮的左竖列上:R4 AB6 V8
左竖列最后一个按钮设置复位信号RESET: V9
3:8译码器以及数码管部分的输入输出参照辅助实验 数码管动态扫描实验

led部分选取板子左上32位led部分

实验分析

实验结论

可以正确实现ALU多路运算器的功能并在烧录的HDU-XL-01板上显示ABF、以及运算的结果和OF ZF符号,并为之后实现更加完善的RISC-V相关ALU运算器拓展做好准备

出现的问题和解决方案

在一开始进行实验仿真的时候出现了OF不符合预期的结果,并且将8000_0000-0000_0001应为溢出的情况(即负数0-1)判定为了无溢出的错误情况,同时sub减法出现了OF在未溢出也出现0的情况
assign OF = (ALU_OP == 4'b0000 || ALU_OP == 4'b1000) ? (A[31] ^ B[31] ^ F[31] ^ C32) : 1'b0;

经过测试发现这个逻辑在加法和减法下的使用是不同的,我们在判定补码规则时,A与B符号相异要再写一个判断逻辑,改为

1
2
3
4
5
6
7
assign OF = (ALU_OP == 4'b0000) ?  // ADD overflow

               ((A[31] == B[31]) && (F[31] != A[31])) :

             (ALU_OP == 4'b1000) ?  // SUB overflow

               ((A[31] != B[31]) && (F[31] != A[31])) :1'b0;

溢出符号可正常使用

思考与拓展部分

对于加法运算,当输入测试数据 A=0FFFFH,B=1H 时,该组数据相加产生什么结 果?请考虑,无符号加和有符号加,这两种情况下运算器硬件操作上有区别吗?无 符号数和有符号数是怎样识别的呢?

首先进行加法后会变为10000H;
在无符号加法角度是合法的,而有符号加法角度则因为符号位反转导致数字变为了范围外的负数,因此导致了溢出

在运算器硬件上操作时,加减法都采用统一的补码计算,而无符号和有符号所看的就是最高位C32,而通常我们会根据运算数标志位判断是否有符号

仔细研究 RV32I 的核心指令集,结合本实验所实现的多功能 ALU,分析该 ALU 能 否实现 RV32I 核心指令集的所有指令?如果不能,请分析它还需要哪些运算功能

RV32I指令可分以上几类:算术指令 逻辑指令 移位指令和比较指令;

我们已经实现了大部分的需求指令,但是还缺失一部分关键指令:

  1. 相等判断指令 如 EQ=(A==B)

  2. 分支指令BEQ BNE BLT等

  3. 内存访问指令,如load store指令等

 实验中的 ALU 实现了逻辑左移操作 sll,请考虑逻辑右移操作如何实现?考虑为何 RV32I 指令系统中没有算术左移指令

1
逻辑右移:F = A >> B[4:0];  // 无符号逻辑右移

因为我们使用的计算系统为补码系统,逻辑左移和算术左移并不会产生冲突,因为低位的数会补充到高位进行符号填充,左移只是位移位、不干涉符号处理,并不会出现符号位的填充需求(右移因为产生了符号位的空出,如果不确定算术右移还是符号右移便会产生空缺

80X86CPU 除了 ZF 和 OF,还有其他标志位,试理解 80X86 的 3 个标志位 SF、CF 和 PF 的作用和逻辑,将这 3 个标志位实现到 RV32I 的多功能 ALU 中,并完成板级调试。

(1) SF:符号标志,运算结果为负数,则 SF=1;结果为正数,则 SF=0。实际上, 在计算机中定点整数(integer)是使用补码表示并进行计算的,因此,符号位 SF 就 是结果的最高位,即 SF=F[31]。

(2) PF:奇偶标志,运算结果中有偶数个“1”,则 PF=1;有奇数个“1”,则 PF=0。

(3) CF:进位/借位标志,它对无符号数运算有效。当进行加法运算时,当做进位 标志,表明无符号运算发生溢出,此时 C32=1,则 CF=1;C32=0,则 CF=0;当进 行减法运算时,当做借位标志,表明不够减,此时 C32=1,则 CF=0;C32=0,则 CF=1。

在ALU_FUN模块中添加了SF PF CF的计算,先进行导入

1
2
3
output SF,  
output CF,  
output PF

然后添加三个的计算逻辑

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
// Sign flag
assign SF = F[31];        

// Carry Flag(CF),无符号m用于进位/借位判断:
assign CF = (ALU_OP == 4'b0000) ? C32 :            // 加法:直接用第33位进位判断
             (ALU_OP == 4'b1000) ? ~C32 :          // 减法:借位时进位位是0,因此取反
             1'b0;                                 // 无进位

// parity flag(PF): 1 的数量为偶数PF=1,否则=0
assign PF = ~(^F); // F自己从31到0每一位进行异或后,如果有偶数个1就会归为0,再取反为1

修改仿真文件进行测试

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
`timescale 1ns / 1ps

module ALU_Sim();
    reg [31:0] A, B;
    reg [3:0] ALU_OP;
    wire [31:0] F;
    wire ZF, OF,SF,CF,PF;

    ALU_FUN uut (
        .A(A),
        .B(B),
        .ALU_OP(ALU_OP),
        .F(F),
        .ZF(ZF),
        .OF(OF),
        .SF(SF),
        .CF(CF),
        .PF(PF)
    );

    // 每组两个数据进行测试任务
    task run(input [31:0] a, input [31:0] b, input [3:0] op, input [40*8-1:0] des);
        begin
            A = a; B = b; ALU_OP = op;
            #10;
            // $display("=== %s ===\n", des);
             $display("[-%35s A=%h, B=%h, OP=%b => F=%h | ZF=%b OF=%b SF=%b CF=%b PF=%b",
                     des, A, B, ALU_OP, F, ZF, OF, SF, CF, PF);
        end
    endtask


    initial begin
        $display("⬇⬇⬇ ALU simulations\n");

        //  1. ADD 加法测试
        run(32'h0000_0001, 32'h0000_0002, 4'b0000, "Basic Addition");
        run(32'h7FFF_FFFF, 32'h0000_0001, 4'b0000, "overflow case");
        run(32'hFFFFFFFF, 32'h0000_0001, 4'b0000, "result in 0");

        //  2. SUB 减法测试
        run(32'h0000_0003, 32'h0000_0002, 4'b1000, "basic subtraction");
        run(32'h8000_0000, 32'h0000_0001, 4'b1000, "overflow case");
        run(32'h0000_0001, 32'h0000_0001, 4'b1000, "result in 0");

        //  3. SLT 有符号比较
        run(32'hFFFF_FFFF, 32'h0000_0001, 4'b0010, "STL Test: -1 < 1");
        run(32'h0000_0002, 32'hFFFFFFFE, 4'b0010, "STL Test: 2 > -2");

        // 4. SLTU 无符号比较
        run(32'h0000_0001, 32'h0000_0002, 4'b0011, "SLTU Test: 1 < 2");
        run(32'hFFFF_FFFF, 32'h0FFFFFFF, 4'b0011, "SLTU Test: 0xfffffff?");

        //  5. SLL 左移
        run(32'h0000_0001, 32'h0000_0004, 4'b0001, "SLL Test: 1 << 4");
        run(32'h0000_FF00, 32'h0000_0008, 4'b0001, "SLL Test: 0xFF00 << 8");

        //  6. SRL 逻辑右移
        run(32'h0000_0080, 32'h0000_0002, 4'b0101, "SRL Test: >> 2");
        run(32'h8000_0000, 32'h0000_0003, 4'b0101, "SRL Test: high bit mask's right shift");

        //  7. SRA 算术右移
        run(32'hFFFF_FF00, 32'h0000_0008, 4'b1101, "SRA Test: -256>> 8");
        run(32'h7FFF_FF00, 32'h0000_0008, 4'b1101, "SRA Test: positive number >> 8");

        //  8. XOR 异或
        run(32'h0000_FF00, 32'h0000_00FF, 4'b0100, "XOR Test: FF00 ^ 00FF");
        run(32'hAAAA_AAAA, 32'hAAAA_AAAA, 4'b0100, "XOR Test: the same number xor 0");

        //  9. OR 和 AND
        run(32'h1234_5678, 32'hFFFF_0000, 4'b0110, "OR Test: all 1");
        run(32'h1234_5678, 32'h0000_FFFF, 4'b0111, "AND Test: keep low bits");

        //  10. INCA / INCB / OUTA / OUT0
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1001, "INCA Test: A+1");
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1010, "OUTA Test: A");
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1011, "INCB Test: B+1");
        run(32'hAAAA_AAAA, 32'h5555_5555, 4'b1100, "OUT0 Test: 0");

        //  11. 默认不动
        run(32'hDEAD_BEEF, 32'h1234_5678, 4'b1111, "DEFAULT Test: keep");

        $display("\n>>> 仿真结束");
        $finish;
    end

  
endmodule

波形检测和仿真都测试无误

本博客已稳定运行
发表了42篇文章 · 总计13万9千字

浙ICP备2024137952号 『网站统计』

𝓌𝒶𝒾𝓉 𝒻ℴ𝓇 𝒶 𝒹ℯ𝓁𝒾𝓋ℯ𝓇𝒶𝓃𝒸ℯ
使用 Hugo 构建
主题 StackJimmy 设计
⬆️该页面访问量Loading...