Ana içeriğe geç

Simulation (sim/) - Teknik Dokümantasyon

İçindekiler

  1. Genel Bakış
  2. Testbench'ler (tb/)
  3. DO Scripts (do/)
  4. Test Programları (test/)

Genel Bakış

Dizin Yapısı

sim/
├── README.md              # Simulation guide
├── tb/                    # Testbench'ler
│   ├── tb_wrapper.sv      # SystemVerilog top-level testbench
│   ├── tb_wrapper.cpp     # Verilator C++ testbench
│   ├── mmu/               # MMU unit testleri
│   └── stage01_fetch/     # Fetch stage testleri
├── do/                    # ModelSim/Questa DO scripts
│   ├── pipeline.do        # Full pipeline debug waveform
│   ├── questa.do          # Questa simulation script
│   ├── minimal.do         # Minimal debug view
│   ├── cache_debug.do     # Cache debugging
│   ├── hazard_debug.do    # Hazard unit debugging
│   ├── branch_debug.do    # Branch predictor debugging
│   ├── exception_debug.do # Exception handling debug
│   └── memory_debug.do    # Memory system debugging
└── test/                  # Test programları ve listeler
    ├── riscv_test_list.flist     # ISA test listesi
    ├── arch_test.flist           # Architecture test listesi
    ├── imperas_test_list.flist   # Imperas test listesi
    ├── custom/                   # Custom C testleri
    │   ├── uart_hello_test.c
    │   ├── gpio_test.c
    │   └── ...
    └── coremark/                 # CoreMark benchmark

Simülasyon Akışı

┌─────────────────────────────────────────────────────────────────┐
│                      SIMULATION FLOW                             │
├─────────────────────────────────────────────────────────────────┤
│                                                                  │
│  ┌──────────┐    ┌──────────┐    ┌──────────┐    ┌──────────┐  │
│  │  Test    │    │  ELF →   │    │Testbench │    │  Results │  │
│  │ Program  │───▶│  MEM     │───▶│ Execute  │───▶│ Analysis │  │
│  └──────────┘    └──────────┘    └──────────┘    └──────────┘  │
│       │                               │                          │
│       │         ┌─────────────────────┼─────────────────────┐   │
│       │         │                     │                     │   │
│       ▼         ▼                     ▼                     ▼   │
│  ┌──────────┐ ┌──────────┐      ┌──────────┐          ┌──────────┐
│  │ C/ASM    │ │Verilator │      │ Waveform │          │ Pass/Fail│
│  │ Source   │ │tb_wrapper│      │   .vcd   │          │  Report  │
│  └──────────┘ │   .cpp   │      │   .fst   │          └──────────┘
│               └──────────┘      │   .wlf   │                     │
│                     │           └──────────┘                     │
│                     ▼                                            │
│               ┌──────────┐                                       │
│               │ModelSim  │                                       │
│               │tb_wrapper│                                       │
│               │   .sv    │                                       │
│               └──────────┘                                       │
│                                                                  │
└─────────────────────────────────────────────────────────────────┘

Testbench'ler (tb/)

tb_wrapper.sv - SystemVerilog Testbench

Dosya: sim/tb/tb_wrapper.sv

ModelSim/Questa için ana testbench.

Kod Yapısı

`timescale 1ns / 1ps
module tb_wrapper;
  // ═══════════════════════════════════════════════════════════════
  // Signal Declarations
  // ═══════════════════════════════════════════════════════════════
  logic        clk_i = 0;
  logic        rst_ni = 0;
  logic        program_rx_i = 1;
  logic        uart_rx_i = 1;
  logic        prog_mode_led_o;
  logic        uart_tx_o;

  // SPI Interface
  logic        spi0_sclk_o;
  logic        spi0_mosi_o;
  logic        spi0_miso_i;
  logic [ 3:0] spi0_ss_o;

  // I2C Interface
  wire         i2c0_sda_io;
  wire         i2c0_scl_io;

  // GPIO Interface
  logic [31:0] gpio_i;
  logic [31:0] gpio_o;
  logic [31:0] gpio_oe_o;

  // External Interrupts
  logic [ 7:0] ext_irq_i;
  logic [ 3:0] status_led_o;

  // ═══════════════════════════════════════════════════════════════
  // DUT Instantiation
  // ═══════════════════════════════════════════════════════════════
  ceres_wrapper ceres_wrapper (
      .clk_i          (clk_i),
      .rst_ni         (rst_ni),
      .program_rx_i   (program_rx_i),
      .prog_mode_led_o(prog_mode_led_o),
      .uart_tx_o      (uart_tx_o),
      .uart_rx_i      (uart_rx_i),
      .spi0_sclk_o    (spi0_sclk_o),
      .spi0_mosi_o    (spi0_mosi_o),
      .spi0_miso_i    (spi0_miso_i),
      .spi0_ss_o      (spi0_ss_o),
      .i2c0_sda_io    (i2c0_sda_io),
      .i2c0_scl_io    (i2c0_scl_io),
      .gpio_i         (gpio_i),
      .gpio_o         (gpio_o),
      .gpio_oe_o      (gpio_oe_o),
      .ext_irq_i      (ext_irq_i),
      .status_led_o   (status_led_o)
  );

  // ═══════════════════════════════════════════════════════════════
  // Peripheral Loopbacks
  // ═══════════════════════════════════════════════════════════════
  // SPI Loopback: MOSI → MISO
  assign spi0_miso_i = spi0_mosi_o;

  // ═══════════════════════════════════════════════════════════════
  // Reset & Clock Generation
  // ═══════════════════════════════════════════════════════════════
  initial begin
    rst_ni       <= 0;
    program_rx_i <= 1;
    uart_rx_i    <= 1;
    #10;
    rst_ni <= 1;
  end

  // 100 MHz clock (10ns period)
  always #5 clk_i = !clk_i;

endmodule

Port Açıklamaları

Port Yön Genişlik Açıklama
clk_i input 1 System clock
rst_ni input 1 Active-low reset
program_rx_i input 1 Programming UART RX
uart_rx_i input 1 Console UART RX
uart_tx_o output 1 Console UART TX
spi0_* mixed - SPI interface
i2c0_* inout - I2C interface
gpio_* mixed 32 GPIO interface
ext_irq_i input 8 External interrupts
status_led_o output 4 Status LEDs

tb_wrapper.cpp - Verilator C++ Testbench

Dosya: sim/tb/tb_wrapper.cpp

Verilator için C++ testbench driver.

Özellikler

  • Trace Support: FST veya VCD format
  • Coverage: Line/toggle coverage
  • Progress Reporting: %10 interval'lerle ilerleme
  • Configurable: Command-line arguments

Kod Yapısı

#include "Vceres_wrapper.h"
#include "verilated.h"

#if defined(VM_TRACE_FST)
#include "verilated_fst_c.h"
#elif defined(VM_TRACE)
#include "verilated_vcd_c.h"
#endif

#if VM_COVERAGE
#include "verilated_cov.h"
#endif

static vluint64_t main_time = 0;
double sc_time_stamp() { return main_time; }

int main(int argc, char **argv) {
    // Create Verilator context
    VerilatedContext* contextp = new VerilatedContext;
    contextp->commandArgs(argc, argv);

    // Enable tracing
#if defined(VM_TRACE_FST) || defined(VM_TRACE)
    Verilated::traceEverOn(true);
#endif

    // Instantiate DUT
    Vceres_wrapper* top = new Vceres_wrapper{contextp};

    // Setup trace file
#if defined(VM_TRACE_FST)
    VerilatedFstC* tfp = new VerilatedFstC;
    top->trace(tfp, 99);
    const char* dump_file = "waveform.fst";
#elif defined(VM_TRACE)
    VerilatedVcdC* tfp = new VerilatedVcdC;
    top->trace(tfp, 99);
    const char* dump_file = "waveform.vcd";
#endif

    // Parse dump file argument
#if defined(VM_TRACE_FST) || defined(VM_TRACE)
    for (int i = 1; i < argc; ++i) {
        if (strncmp(argv[i], "+DUMP_FILE=", 11) == 0)
            dump_file = argv[i] + 11;
    }
    tfp->open(dump_file);
#endif

    // Initialize signals
    top->clk_i     = 0;
    top->rst_ni    = 0;
    top->uart_rx_i = 1;

    // Reset phase (10 cycles)
    for (int i = 0; i < 10; ++i) {
        top->clk_i = 0; top->eval();
#if defined(VM_TRACE_FST) || defined(VM_TRACE)
        tfp->dump(main_time++);
#endif
        top->clk_i = 1; top->eval();
#if defined(VM_TRACE_FST) || defined(VM_TRACE)
        tfp->dump(main_time++);
#endif
    }

    top->rst_ni = 1;

    // Get max cycles from command line
    uint64_t MAX_CYCLES = (argc > 1) ? 
        std::strtoull(argv[1], nullptr, 10) : 100000ULL;

    uint64_t progress_interval = (MAX_CYCLES > 10000) ? 
        (MAX_CYCLES / 10) : 1000;

    // Main simulation loop
    while (!contextp->gotFinish() && (main_time / 2) < MAX_CYCLES) {
        // Progress reporting
        if (((main_time / 2) % progress_interval) == 0 && (main_time / 2) > 0) {
            std::cout << "[CYCLE] " << (main_time / 2) << "/" 
                      << MAX_CYCLES << std::endl;
        }

        // Clock toggle
        top->clk_i = 0; top->eval();
#if defined(VM_TRACE_FST) || defined(VM_TRACE)
        tfp->dump(main_time++);
#endif
        top->clk_i = 1; top->eval();
#if defined(VM_TRACE_FST) || defined(VM_TRACE)
        tfp->dump(main_time++);
#endif
    }

    // Cleanup
#if defined(VM_TRACE_FST) || defined(VM_TRACE)
    tfp->close();
    delete tfp;
#endif

    top->final();

#if VM_COVERAGE
    const char* coverage_file = "coverage.dat";
    VerilatedCov::write(coverage_file);
#endif

    std::cout << "[INFO] Simulation finished after " 
              << (main_time / 2) << " cycles." << std::endl;

    delete top;
    delete contextp;
    return 0;
}

Command Line Arguments

Argument Format Açıklama
<cycles> integer Maximum simulation cycles
+DUMP_FILE= path Waveform output file
+COVERAGE_FILE= path Coverage output file

DO Scripts (do/)

pipeline.do - Full Pipeline Debug

Dosya: sim/do/pipeline.do

Kapsamlı pipeline debug waveform script'i.

Özellikler

##################################################################################
#                     CERES RISC-V — Advanced Debug Waveform                     #
##################################################################################
# Features:
#   - Hierarchical grouping by pipeline stage
#   - Color-coded signal categories
#   - Automatic radix selection (hex/decimal/binary)
#   - Collapsible groups for easy navigation
#   - Critical path signals highlighted
#   - Exception/Interrupt debugging section
#   - Performance counter monitoring
#   - Memory transaction tracking
##################################################################################

Hierarchy Paths

set TB        "sim:/tb_wrapper"
set WRAPPER   "$TB/ceres_wrapper"
set SOC       "$WRAPPER/i_soc"
set FETCH     "$SOC/i_fetch"
set DECODE    "$SOC/i_decode"
set EXECUTE   "$SOC/i_execution"
set MEMORY    "$SOC/i_memory"
set WRITEBACK "$SOC/i_writeback"
set HAZARD    "$SOC/i_hazard_unit"
set ARBITER   "$SOC/i_memory_arbiter"

Signal Groups

Group Renk İçerik
⏱️ CLK/RST Gold/Orange Clock ve reset
🔄 PIPELINE Gradient PC ve instruction per stage
⚠️ STALL/FLUSH Red/Orange Stall ve flush sinyalleri
🎯 FETCH Cyan Fetch stage sinyalleri
📖 DECODE Green Decode stage sinyalleri
⚡ EXECUTE Yellow ALU ve execution
💾 MEMORY Magenta Load/store operations
✅ WRITEBACK Blue Register writeback
🔀 HAZARD Red Forwarding ve hazard
🌿 BRANCH Cyan Branch predictor
💥 EXCEPTION Red Exception handling

Diğer DO Scripts

Script Açıklama
questa.do Questa simulation runner
minimal.do Minimal debug view
cache_debug.do Cache hit/miss debugging
hazard_debug.do Hazard unit detailed view
branch_debug.do Branch predictor analysis
exception_debug.do Exception/interrupt flow
memory_debug.do Memory transaction debug

Test Programları (test/)

Test Listeleri

Dosya İçerik
riscv_test_list.flist riscv-tests ISA testleri
arch_test.flist riscv-arch-test compliance
imperas_test_list.flist Imperas extended tests
custom_tests.flist Custom C testleri
all_tests.flist Tüm testler (combined)
branch_test.flist Branch predictor testleri
exception_test.flist Exception testleri
machine_csr_test.flist CSR testleri

Custom Test Programları (custom/)

Dosya Listesi

Dosya Açıklama
startup.s Assembly startup code
ceres_test.h Common test header
uart_hello_test.c UART basic test
gpio_test.c GPIO functionality
timer_test.c Timer peripheral
spi_test.c SPI controller
i2c_test.c I2C controller
plic_test.c Interrupt controller
pwm_test.c PWM output
dma_test.c DMA controller
wdt_test.c Watchdog timer
vga_test.c VGA controller
clint_test.c Core-local interruptor
exception_test.c Exception handling
csr_test.c CSR read/write
memory_test.c Memory operations
cache_test.c Cache behavior
branch_test.c Branch operations
arithmetic_test.c ALU operations
fibonacci_test.c Fibonacci benchmark
loop_test.c Loop performance
interrupt_test.c Interrupt handling

startup.s

.section .text._start
.globl _start

_start:
    /* Set stack pointer */
    la sp, __stack_end

    /* Jump to main */
    jal ra, main

    /* Infinite loop on return */
    j _start

.section .bss
.align 4
__stack_start:
    .space 0x4000    # 16KB stack
__stack_end:

uart_hello_test.c Örneği

/**
 * UART Hello Test - Ceres-V RV32IMC_Zicsr
 */

#include <stdint.h>

/* Hardware Definitions */
#define CPU_CLK          50000000   /* 50 MHz */
#define BAUD_RATE        115200

/* UART MMIO Map */
#define UART_CTRL        (*(volatile uint32_t*)0x20000000)
#define UART_STATUS      (*(volatile uint32_t*)0x20000004)
#define UART_RDATA       (*(volatile uint32_t*)0x20000008)
#define UART_WDATA       (*(volatile uint32_t*)0x2000000c)

/* Status Register Bits */
#define UART_STATUS_TX_FULL   0x1
#define UART_STATUS_RX_FULL   0x2

/* Control Register Bits */
#define UART_CTRL_TX_EN   0x1
#define UART_CTRL_RX_EN   0x2

void uart_init(void) {
    uint32_t baud_div = CPU_CLK / BAUD_RATE;
    UART_CTRL = (baud_div << 16) | UART_CTRL_TX_EN | UART_CTRL_RX_EN;
}

void uart_putc(char c) {
    while (UART_STATUS & UART_STATUS_TX_FULL);
    UART_WDATA = (uint32_t)c;
}

void uart_puts(const char *s) {
    while (*s) {
        if (*s == '\n') uart_putc('\r');
        uart_putc(*s++);
    }
}

int main(void) {
    uart_init();
    uart_puts("Hello from Ceres!\n");
    while (1);
    return 0;
}

Kullanım Örnekleri

Verilator ile Simülasyon

# Build
make verilate

# Run ISA test
make run T=rv32ui-p-add

# Run with trace
make run T=rv32ui-p-add TRACE=1

# Run CoreMark
make cm SIM_FAST=1 SIM_UART_MONITOR=1

ModelSim ile Simülasyon

# Compile
make compile

# GUI simulation
make simulate_gui

# Batch simulation
make simulate

Custom Test Build

# Build custom test
./script/shell/build_custom_test.sh uart_hello_test

# Run custom test
make run T=uart_hello_test TEST_TYPE=custom

Özet

Simulation dizini:

  1. tb/: SystemVerilog ve C++ testbench'ler
  2. do/: ModelSim/Questa debug waveform scripts
  3. test/: Test programları ve listeler
  4. Dual Simulator: Verilator ve ModelSim desteği
  5. Comprehensive Debug: Color-coded, grouped waveforms
  6. Custom Tests: Peripheral test suite