From ef6fb8848f11f37d4fdeaa6e2732cc2f7a48af0d Mon Sep 17 00:00:00 2001 From: "colin.liang" Date: Mon, 16 Jan 2023 20:41:28 +0800 Subject: [PATCH] Remove irq support. --- Makefile | 4 +- firmware/firmware.h | 3 - firmware/irq.c | 140 -------------------- firmware/start.S | 309 -------------------------------------------- picorv32.v | 193 ++++----------------------- testbench_wb.v | 5 - 6 files changed, 25 insertions(+), 629 deletions(-) delete mode 100644 firmware/irq.c diff --git a/Makefile b/Makefile index 2bc6718..296fa52 100644 --- a/Makefile +++ b/Makefile @@ -12,7 +12,7 @@ IVERILOG = iverilog$(ICARUS_SUFFIX) VVP = vvp$(ICARUS_SUFFIX) TEST_OBJS = $(addsuffix .o,$(basename $(wildcard tests/*.S))) -FIRMWARE_OBJS = build/start.o build/irq.o build/print.o build/hello.o build/sieve.o build/multest.o build/stats.o +FIRMWARE_OBJS = build/start.o build/print.o build/hello.o build/sieve.o build/multest.o build/stats.o GCC_WARNS = -Werror -Wall -Wextra -Wshadow -Wundef -Wpointer-arith -Wcast-qual -Wcast-align -Wwrite-strings GCC_WARNS += -Wredundant-decls -Wstrict-prototypes -Wmissing-prototypes -pedantic # -Wconversion TOOLCHAIN_PREFIX = $(RISCV_GNU_TOOLCHAIN_INSTALL_PREFIX)/bin/riscv32-unknown-elf- @@ -25,7 +25,7 @@ test_verilator: build/testbench_verilator build/firmware.hex build/dhry.hex cd build && ./testbench_verilator firmware.hex cd build && ./testbench_verilator dhry.hex -firmware: build/testbench_verilator +firmware: build/testbench_verilator build/firmware.hex cd build && ./testbench_verilator firmware.hex dhry: build/firmware.hex build/dhry.hex diff --git a/firmware/firmware.h b/firmware/firmware.h index 59d3f11..df831df 100644 --- a/firmware/firmware.h +++ b/firmware/firmware.h @@ -11,9 +11,6 @@ #include #include -// irq.c -uint32_t *irq(uint32_t *regs, uint32_t irqs); - // print.c void print_chr(char ch); void print_str(const char *p); diff --git a/firmware/irq.c b/firmware/irq.c deleted file mode 100644 index 9fc1735..0000000 --- a/firmware/irq.c +++ /dev/null @@ -1,140 +0,0 @@ -// This is free and unencumbered software released into the public domain. -// -// Anyone is free to copy, modify, publish, use, compile, sell, or -// distribute this software, either in source code form or as a compiled -// binary, for any purpose, commercial or non-commercial, and by any -// means. - -#include "firmware.h" - -uint32_t *irq(uint32_t *regs, uint32_t irqs) -{ - static unsigned int ext_irq_4_count = 0; - static unsigned int ext_irq_5_count = 0; - static unsigned int timer_irq_count = 0; - - // checking compressed isa q0 reg handling - if ((irqs & 6) != 0) { - uint32_t pc = (regs[0] & 1) ? regs[0] - 3 : regs[0] - 4; - uint32_t instr = *(uint16_t*)pc; - - if ((instr & 3) == 3) - instr = instr | (*(uint16_t*)(pc + 2)) << 16; - - if (((instr & 3) != 3) != (regs[0] & 1)) { - print_str("Mismatch between q0 LSB and decoded instruction word! q0=0x"); - print_hex(regs[0], 8); - print_str(", instr=0x"); - if ((instr & 3) == 3) - print_hex(instr, 8); - else - print_hex(instr, 4); - print_str("\n"); - __asm__ volatile ("ebreak"); - } - } - - if ((irqs & (1<<4)) != 0) { - ext_irq_4_count++; - // print_str("[EXT-IRQ-4]"); - } - - if ((irqs & (1<<5)) != 0) { - ext_irq_5_count++; - // print_str("[EXT-IRQ-5]"); - } - - if ((irqs & 1) != 0) { - timer_irq_count++; - // print_str("[TIMER-IRQ]"); - } - - if ((irqs & 6) != 0) - { - uint32_t pc = (regs[0] & 1) ? regs[0] - 3 : regs[0] - 4; - uint32_t instr = *(uint16_t*)pc; - - if ((instr & 3) == 3) - instr = instr | (*(uint16_t*)(pc + 2)) << 16; - - print_str("\n"); - print_str("------------------------------------------------------------\n"); - - if ((irqs & 2) != 0) { - if (instr == 0x00100073 || instr == 0x9002) { - print_str("EBREAK instruction at 0x"); - print_hex(pc, 8); - print_str("\n"); - } else { - print_str("Illegal Instruction at 0x"); - print_hex(pc, 8); - print_str(": 0x"); - print_hex(instr, ((instr & 3) == 3) ? 8 : 4); - print_str("\n"); - } - } - - if ((irqs & 4) != 0) { - print_str("Bus error in Instruction at 0x"); - print_hex(pc, 8); - print_str(": 0x"); - print_hex(instr, ((instr & 3) == 3) ? 8 : 4); - print_str("\n"); - } - - for (int i = 0; i < 8; i++) - for (int k = 0; k < 4; k++) - { - int r = i + k*8; - - if (r == 0) { - print_str("pc "); - } else - if (r < 10) { - print_chr('x'); - print_chr('0' + r); - print_chr(' '); - print_chr(' '); - } else - if (r < 20) { - print_chr('x'); - print_chr('1'); - print_chr('0' + r - 10); - print_chr(' '); - } else - if (r < 30) { - print_chr('x'); - print_chr('2'); - print_chr('0' + r - 20); - print_chr(' '); - } else { - print_chr('x'); - print_chr('3'); - print_chr('0' + r - 30); - print_chr(' '); - } - - print_hex(regs[r], 8); - print_str(k == 3 ? "\n" : " "); - } - - print_str("------------------------------------------------------------\n"); - - print_str("Number of fast external IRQs counted: "); - print_dec(ext_irq_4_count); - print_str("\n"); - - print_str("Number of slow external IRQs counted: "); - print_dec(ext_irq_5_count); - print_str("\n"); - - print_str("Number of timer IRQs counted: "); - print_dec(timer_irq_count); - print_str("\n"); - - __asm__ volatile ("ebreak"); - } - - return regs; -} - diff --git a/firmware/start.S b/firmware/start.S index a0ff974..a84eeb5 100644 --- a/firmware/start.S +++ b/firmware/start.S @@ -5,26 +5,14 @@ // binary, for any purpose, commercial or non-commercial, and by any // means. -#define ENABLE_QREGS #define ENABLE_HELLO -#define ENABLE_RVTST #define ENABLE_SIEVE #define ENABLE_MULTST #define ENABLE_STATS -#ifndef ENABLE_QREGS -# undef ENABLE_RVTST -#endif - -// Only save registers in IRQ wrapper that are to be saved by the caller in -// the RISC-V ABI, with the excpetion of the stack pointer. The IRQ handler -// will save the rest if necessary. I.e. skip x3, x4, x8, x9, and x18-x27. -#undef ENABLE_FASTIRQ - #include "custom_ops.S" .section .text - .global irq .global hello .global sieve .global multest @@ -39,305 +27,8 @@ .global stats reset_vec: - // no more than 16 bytes here ! - picorv32_waitirq_insn(zero) - picorv32_maskirq_insn(zero, zero) j start - -/* Interrupt handler - **********************************/ - -.balign 16 -irq_vec: - /* save registers */ - -#ifdef ENABLE_QREGS - - picorv32_setq_insn(q2, x1) - picorv32_setq_insn(q3, x2) - - lui x1, %hi(irq_regs) - addi x1, x1, %lo(irq_regs) - - picorv32_getq_insn(x2, q0) - sw x2, 0*4(x1) - - picorv32_getq_insn(x2, q2) - sw x2, 1*4(x1) - - picorv32_getq_insn(x2, q3) - sw x2, 2*4(x1) - -#ifdef ENABLE_FASTIRQ - sw x5, 5*4(x1) - sw x6, 6*4(x1) - sw x7, 7*4(x1) - sw x10, 10*4(x1) - sw x11, 11*4(x1) - sw x12, 12*4(x1) - sw x13, 13*4(x1) - sw x14, 14*4(x1) - sw x15, 15*4(x1) - sw x16, 16*4(x1) - sw x17, 17*4(x1) - sw x28, 28*4(x1) - sw x29, 29*4(x1) - sw x30, 30*4(x1) - sw x31, 31*4(x1) -#else - sw x3, 3*4(x1) - sw x4, 4*4(x1) - sw x5, 5*4(x1) - sw x6, 6*4(x1) - sw x7, 7*4(x1) - sw x8, 8*4(x1) - sw x9, 9*4(x1) - sw x10, 10*4(x1) - sw x11, 11*4(x1) - sw x12, 12*4(x1) - sw x13, 13*4(x1) - sw x14, 14*4(x1) - sw x15, 15*4(x1) - sw x16, 16*4(x1) - sw x17, 17*4(x1) - sw x18, 18*4(x1) - sw x19, 19*4(x1) - sw x20, 20*4(x1) - sw x21, 21*4(x1) - sw x22, 22*4(x1) - sw x23, 23*4(x1) - sw x24, 24*4(x1) - sw x25, 25*4(x1) - sw x26, 26*4(x1) - sw x27, 27*4(x1) - sw x28, 28*4(x1) - sw x29, 29*4(x1) - sw x30, 30*4(x1) - sw x31, 31*4(x1) -#endif - -#else // ENABLE_QREGS - -#ifdef ENABLE_FASTIRQ - sw gp, 0*4+0x200(zero) - sw x1, 1*4+0x200(zero) - sw x2, 2*4+0x200(zero) - sw x5, 5*4+0x200(zero) - sw x6, 6*4+0x200(zero) - sw x7, 7*4+0x200(zero) - sw x10, 10*4+0x200(zero) - sw x11, 11*4+0x200(zero) - sw x12, 12*4+0x200(zero) - sw x13, 13*4+0x200(zero) - sw x14, 14*4+0x200(zero) - sw x15, 15*4+0x200(zero) - sw x16, 16*4+0x200(zero) - sw x17, 17*4+0x200(zero) - sw x28, 28*4+0x200(zero) - sw x29, 29*4+0x200(zero) - sw x30, 30*4+0x200(zero) - sw x31, 31*4+0x200(zero) -#else - sw gp, 0*4+0x200(zero) - sw x1, 1*4+0x200(zero) - sw x2, 2*4+0x200(zero) - sw x3, 3*4+0x200(zero) - sw x4, 4*4+0x200(zero) - sw x5, 5*4+0x200(zero) - sw x6, 6*4+0x200(zero) - sw x7, 7*4+0x200(zero) - sw x8, 8*4+0x200(zero) - sw x9, 9*4+0x200(zero) - sw x10, 10*4+0x200(zero) - sw x11, 11*4+0x200(zero) - sw x12, 12*4+0x200(zero) - sw x13, 13*4+0x200(zero) - sw x14, 14*4+0x200(zero) - sw x15, 15*4+0x200(zero) - sw x16, 16*4+0x200(zero) - sw x17, 17*4+0x200(zero) - sw x18, 18*4+0x200(zero) - sw x19, 19*4+0x200(zero) - sw x20, 20*4+0x200(zero) - sw x21, 21*4+0x200(zero) - sw x22, 22*4+0x200(zero) - sw x23, 23*4+0x200(zero) - sw x24, 24*4+0x200(zero) - sw x25, 25*4+0x200(zero) - sw x26, 26*4+0x200(zero) - sw x27, 27*4+0x200(zero) - sw x28, 28*4+0x200(zero) - sw x29, 29*4+0x200(zero) - sw x30, 30*4+0x200(zero) - sw x31, 31*4+0x200(zero) -#endif - -#endif // ENABLE_QREGS - - /* call interrupt handler C function */ - - lui sp, %hi(irq_stack) - addi sp, sp, %lo(irq_stack) - - // arg0 = address of regs - lui a0, %hi(irq_regs) - addi a0, a0, %lo(irq_regs) - - // arg1 = interrupt type -#ifdef ENABLE_QREGS - picorv32_getq_insn(a1, q1) -#else - addi a1, tp, 0 -#endif - - // call to C function - jal ra, irq - - /* restore registers */ - -#ifdef ENABLE_QREGS - - // new irq_regs address returned from C code in a0 - addi x1, a0, 0 - - lw x2, 0*4(x1) - picorv32_setq_insn(q0, x2) - - lw x2, 1*4(x1) - picorv32_setq_insn(q1, x2) - - lw x2, 2*4(x1) - picorv32_setq_insn(q2, x2) - -#ifdef ENABLE_FASTIRQ - lw x5, 5*4(x1) - lw x6, 6*4(x1) - lw x7, 7*4(x1) - lw x10, 10*4(x1) - lw x11, 11*4(x1) - lw x12, 12*4(x1) - lw x13, 13*4(x1) - lw x14, 14*4(x1) - lw x15, 15*4(x1) - lw x16, 16*4(x1) - lw x17, 17*4(x1) - lw x28, 28*4(x1) - lw x29, 29*4(x1) - lw x30, 30*4(x1) - lw x31, 31*4(x1) -#else - lw x3, 3*4(x1) - lw x4, 4*4(x1) - lw x5, 5*4(x1) - lw x6, 6*4(x1) - lw x7, 7*4(x1) - lw x8, 8*4(x1) - lw x9, 9*4(x1) - lw x10, 10*4(x1) - lw x11, 11*4(x1) - lw x12, 12*4(x1) - lw x13, 13*4(x1) - lw x14, 14*4(x1) - lw x15, 15*4(x1) - lw x16, 16*4(x1) - lw x17, 17*4(x1) - lw x18, 18*4(x1) - lw x19, 19*4(x1) - lw x20, 20*4(x1) - lw x21, 21*4(x1) - lw x22, 22*4(x1) - lw x23, 23*4(x1) - lw x24, 24*4(x1) - lw x25, 25*4(x1) - lw x26, 26*4(x1) - lw x27, 27*4(x1) - lw x28, 28*4(x1) - lw x29, 29*4(x1) - lw x30, 30*4(x1) - lw x31, 31*4(x1) -#endif - - picorv32_getq_insn(x1, q1) - picorv32_getq_insn(x2, q2) - -#else // ENABLE_QREGS - - // new irq_regs address returned from C code in a0 - addi a1, zero, 0x200 - beq a0, a1, 1f - ebreak -1: - -#ifdef ENABLE_FASTIRQ - lw gp, 0*4+0x200(zero) - lw x1, 1*4+0x200(zero) - lw x2, 2*4+0x200(zero) - lw x5, 5*4+0x200(zero) - lw x6, 6*4+0x200(zero) - lw x7, 7*4+0x200(zero) - lw x10, 10*4+0x200(zero) - lw x11, 11*4+0x200(zero) - lw x12, 12*4+0x200(zero) - lw x13, 13*4+0x200(zero) - lw x14, 14*4+0x200(zero) - lw x15, 15*4+0x200(zero) - lw x16, 16*4+0x200(zero) - lw x17, 17*4+0x200(zero) - lw x28, 28*4+0x200(zero) - lw x29, 29*4+0x200(zero) - lw x30, 30*4+0x200(zero) - lw x31, 31*4+0x200(zero) -#else - lw gp, 0*4+0x200(zero) - lw x1, 1*4+0x200(zero) - lw x2, 2*4+0x200(zero) - // do not restore x3 (gp) - lw x4, 4*4+0x200(zero) - lw x5, 5*4+0x200(zero) - lw x6, 6*4+0x200(zero) - lw x7, 7*4+0x200(zero) - lw x8, 8*4+0x200(zero) - lw x9, 9*4+0x200(zero) - lw x10, 10*4+0x200(zero) - lw x11, 11*4+0x200(zero) - lw x12, 12*4+0x200(zero) - lw x13, 13*4+0x200(zero) - lw x14, 14*4+0x200(zero) - lw x15, 15*4+0x200(zero) - lw x16, 16*4+0x200(zero) - lw x17, 17*4+0x200(zero) - lw x18, 18*4+0x200(zero) - lw x19, 19*4+0x200(zero) - lw x20, 20*4+0x200(zero) - lw x21, 21*4+0x200(zero) - lw x22, 22*4+0x200(zero) - lw x23, 23*4+0x200(zero) - lw x24, 24*4+0x200(zero) - lw x25, 25*4+0x200(zero) - lw x26, 26*4+0x200(zero) - lw x27, 27*4+0x200(zero) - lw x28, 28*4+0x200(zero) - lw x29, 29*4+0x200(zero) - lw x30, 30*4+0x200(zero) - lw x31, 31*4+0x200(zero) -#endif - -#endif // ENABLE_QREGS - - picorv32_retirq_insn() - -.balign 0x200 -irq_regs: - // registers are saved to this memory region during interrupt handling - // the program counter is saved as register 0 - .fill 32,4 - - // stack for the interrupt handler - .fill 128,4 -irq_stack: - - /* Main program **********************************/ diff --git a/picorv32.v b/picorv32.v index 7d631fe..4e944ad 100644 --- a/picorv32.v +++ b/picorv32.v @@ -24,6 +24,7 @@ `timescale 1 ns / 1 ps // `default_nettype none +// `define DEBUG `ifdef DEBUG `define debug(debug_command) debug_command @@ -40,10 +41,7 @@ module picorv32 #( parameter [0:0] ENABLE_TRACE = 0, - parameter [31:0] MASKED_IRQ = 32'h0000_0000, - parameter [31:0] LATCHED_IRQ = 32'hffff_ffff, parameter [31:0] PROGADDR_RESET = 32'h0000_0000, - parameter [31:0] PROGADDR_IRQ = 32'h0000_0010, parameter [31:0] STACKADDR = 32'hffff_ffff ) ( input clk, @@ -76,10 +74,6 @@ module picorv32 #( input pcpi_wait, input pcpi_ready, - // IRQ Interface - input [31:0] irq, - output reg [31:0] eoi, - // Trace Interface output reg trace_valid, output reg [35:0] trace_data, @@ -90,16 +84,11 @@ module picorv32 #( output reg [31:0] dbg_insn_addr, output reg [63:0] dbg_ascii_instr ); - localparam integer irq_timer = 0; - localparam integer irq_ebreak = 1; - localparam integer irq_buserror = 2; - localparam integer irqregs_offset = 32; - localparam integer regfile_size = 32 + 4; - localparam integer regindex_bits = 5 + 1; + localparam integer regfile_size = 32; + localparam integer regindex_bits = 5; localparam [35:0] TRACE_BRANCH = {4'b0001, 32'b0}; localparam [35:0] TRACE_ADDR = {4'b0010, 32'b0}; - localparam [35:0] TRACE_IRQ = {4'b1000, 32'b0}; reg [63:0] count_cycle, count_instr; reg [31:0] reg_pc, reg_next_pc, reg_op1, reg_op2, reg_out; @@ -120,12 +109,6 @@ module picorv32 #( wire [31:0] next_pc; - reg irq_delay; - reg irq_active; - reg [31:0] irq_mask; - reg [31:0] irq_pending; - reg [31:0] timer; - task empty_statement; // This task is used by the `assert directive in non-formal mode to // avoid empty statement (which are unsupported by plain Verilog syntax). @@ -362,7 +345,6 @@ module picorv32 #( reg instr_add, instr_sub, instr_sll, instr_slt, instr_sltu; reg instr_xor, instr_srl, instr_sra, instr_or, instr_and; reg instr_rdcycle, instr_rdcycleh, instr_rdinstr, instr_rdinstrh, instr_ecall_ebreak; - reg instr_getq, instr_setq, instr_retirq, instr_maskirq, instr_waitirq, instr_timer; wire instr_trap; reg [regindex_bits-1:0] decoded_rd, decoded_rs1, decoded_rs2; @@ -392,8 +374,7 @@ module picorv32 #( instr_lb, instr_lh, instr_lw, instr_lbu, instr_lhu, instr_sb, instr_sh, instr_sw, instr_addi, instr_slti, instr_sltiu, instr_xori, instr_ori, instr_andi, instr_slli, instr_srli, instr_srai, instr_add, instr_sub, instr_sll, instr_slt, instr_sltu, instr_xor, instr_srl, instr_sra, instr_or, instr_and, - instr_rdcycle, instr_rdcycleh, instr_rdinstr, instr_rdinstrh, - instr_getq, instr_setq, instr_retirq, instr_maskirq, instr_waitirq, instr_timer}; + instr_rdcycle, instr_rdcycleh, instr_rdinstr, instr_rdinstrh}; wire is_rdcycle_rdcycleh_rdinstr_rdinstrh; assign is_rdcycle_rdcycleh_rdinstr_rdinstrh = |{instr_rdcycle, instr_rdcycleh, instr_rdinstr, instr_rdinstrh}; @@ -461,12 +442,6 @@ module picorv32 #( if (instr_rdinstr) new_ascii_instr = "rdinstr"; if (instr_rdinstrh) new_ascii_instr = "rdinstrh"; - if (instr_getq) new_ascii_instr = "getq"; - if (instr_setq) new_ascii_instr = "setq"; - if (instr_retirq) new_ascii_instr = "retirq"; - if (instr_maskirq) new_ascii_instr = "maskirq"; - if (instr_waitirq) new_ascii_instr = "waitirq"; - if (instr_timer) new_ascii_instr = "timer"; end reg [63:0] q_ascii_instr; @@ -554,8 +529,6 @@ module picorv32 #( instr_auipc <= mem_rdata_latched[6:0] == 7'b0010111; instr_jal <= mem_rdata_latched[6:0] == 7'b1101111; instr_jalr <= mem_rdata_latched[6:0] == 7'b1100111 && mem_rdata_latched[14:12] == 3'b000; - instr_retirq <= mem_rdata_latched[6:0] == 7'b0001011 && mem_rdata_latched[31:25] == 7'b0000010; - instr_waitirq <= mem_rdata_latched[6:0] == 7'b0001011 && mem_rdata_latched[31:25] == 7'b0000100; is_beq_bne_blt_bge_bltu_bgeu <= mem_rdata_latched[6:0] == 7'b1100011; is_lb_lh_lw_lbu_lhu <= mem_rdata_latched[6:0] == 7'b0000011; @@ -570,12 +543,6 @@ module picorv32 #( decoded_rd <= mem_rdata_latched[11:7]; decoded_rs1 <= mem_rdata_latched[19:15]; decoded_rs2 <= mem_rdata_latched[24:20]; - - if (mem_rdata_latched[6:0] == 7'b0001011 && mem_rdata_latched[31:25] == 7'b0000000) - decoded_rs1[regindex_bits-1] <= 1; // instr_getq - - if (mem_rdata_latched[6:0] == 7'b0001011 && mem_rdata_latched[31:25] == 7'b0000010) - decoded_rs1 <= irqregs_offset; // instr_retirq end if (decoder_trigger && !decoder_pseudo_trigger) begin @@ -629,11 +596,6 @@ module picorv32 #( instr_ecall_ebreak <= (mem_rdata_q[6:0] == 7'b1110011 && !mem_rdata_q[31:21] && !mem_rdata_q[19:7]); - instr_getq <= mem_rdata_q[6:0] == 7'b0001011 && mem_rdata_q[31:25] == 7'b0000000; - instr_setq <= mem_rdata_q[6:0] == 7'b0001011 && mem_rdata_q[31:25] == 7'b0000001; - instr_maskirq <= mem_rdata_q[6:0] == 7'b0001011 && mem_rdata_q[31:25] == 7'b0000011; - instr_timer <= mem_rdata_q[6:0] == 7'b0001011 && mem_rdata_q[31:25] == 7'b0000101; - is_slli_srli_srai <= is_alu_reg_imm && |{ mem_rdata_q[14:12] == 3'b001 && mem_rdata_q[31:25] == 7'b0000000, mem_rdata_q[14:12] == 3'b101 && mem_rdata_q[31:25] == 7'b0000000, @@ -717,7 +679,6 @@ module picorv32 #( localparam cpu_state_ldmem = 8'b00000001; reg [7:0] cpu_state; - reg [1:0] irq_state; always @* begin dbg_ascii_state = ""; @@ -750,9 +711,6 @@ module picorv32 #( reg [3:0] pcpi_timeout_counter; reg pcpi_timeout; - reg [31:0] next_irq_pending; - reg do_waitirq; - reg [31:0] alu_out, alu_out_q; reg alu_out_0, alu_out_0_q; @@ -815,14 +773,6 @@ module picorv32 #( cpuregs_wrdata = latched_stalu ? alu_out_q : reg_out; cpuregs_write = 1; end - irq_state[0]: begin - cpuregs_wrdata = reg_next_pc; - cpuregs_write = 1; - end - irq_state[1]: begin - cpuregs_wrdata = irq_pending & ~irq_mask; - cpuregs_write = 1; - end endcase end end @@ -851,7 +801,7 @@ module picorv32 #( cpuregs_rs2 = decoded_rs2 ? cpuregs_rdata2 : 0; end - assign launch_next_insn = cpu_state == cpu_state_fetch && decoder_trigger && (irq_delay || irq_active || !(irq_pending & ~irq_mask)); + assign launch_next_insn = cpu_state == cpu_state_fetch && decoder_trigger; always @(posedge clk) begin trap <= 0; @@ -875,18 +825,12 @@ module picorv32 #( if (pcpi_timeout_counter) pcpi_timeout_counter <= pcpi_timeout_counter - 1; end else pcpi_timeout_counter <= ~0; pcpi_timeout <= !pcpi_timeout_counter; - count_cycle <= resetn ? count_cycle + 1 : 0; - next_irq_pending = irq_pending & LATCHED_IRQ; - - if (timer) begin - timer <= timer - 1; - end + count_cycle <= resetn ? count_cycle + 1 : 0; decoder_trigger <= mem_do_rinst && mem_done; decoder_trigger_q <= decoder_trigger; decoder_pseudo_trigger <= 0; decoder_pseudo_trigger_q <= decoder_pseudo_trigger; - do_waitirq <= 0; trace_valid <= 0; @@ -905,13 +849,6 @@ module picorv32 #( latched_is_lb <= 0; pcpi_valid <= 0; pcpi_timeout <= 0; - irq_active <= 0; - irq_delay <= 0; - irq_mask <= ~0; - next_irq_pending = 0; - irq_state <= 0; - eoi <= 0; - timer <= 0; if (~STACKADDR) begin latched_store <= 1; latched_rd <= 2; @@ -925,7 +862,7 @@ module picorv32 #( end cpu_state_fetch: begin - mem_do_rinst <= !decoder_trigger && !do_waitirq; + mem_do_rinst <= !decoder_trigger; mem_wordsize <= 0; current_pc = reg_next_pc; @@ -941,23 +878,13 @@ module picorv32 #( `debug($display("ST_RD: %2d 0x%08x", latched_rd, latched_stalu ? alu_out_q : reg_out );) end - irq_state[0]: begin - current_pc = PROGADDR_IRQ; - irq_active <= 1; - mem_do_rinst <= 1; - end - irq_state[1]: begin - eoi <= irq_pending & ~irq_mask; - next_irq_pending = next_irq_pending & irq_mask; - end endcase if (ENABLE_TRACE && latched_trace) begin latched_trace <= 0; trace_valid <= 1; - if (latched_branch) - trace_data <= (irq_active ? TRACE_IRQ : 0) | TRACE_BRANCH | (current_pc & 32'hfffffffe); - else trace_data <= (irq_active ? TRACE_IRQ : 0) | (latched_stalu ? alu_out_q : reg_out); + if (latched_branch) trace_data <= TRACE_BRANCH | (current_pc & 32'hfffffffe); + else trace_data <= latched_stalu ? alu_out_q : reg_out; end reg_pc <= current_pc; @@ -971,19 +898,8 @@ module picorv32 #( latched_is_lb <= 0; latched_rd <= decoded_rd; - if (((decoder_trigger && !irq_active && !irq_delay && |(irq_pending & ~irq_mask)) || irq_state)) begin - irq_state <= irq_state == 2'b00 ? 2'b01 : irq_state == 2'b01 ? 2'b10 : 2'b00; - latched_rd <= irqregs_offset | irq_state[0]; - end else if ((decoder_trigger || do_waitirq) && instr_waitirq) begin - if (irq_pending) begin - latched_store <= 1; - reg_out <= irq_pending; - reg_next_pc <= current_pc + 4; - mem_do_rinst <= 1; - end else do_waitirq <= 1; - end else if (decoder_trigger) begin + if (decoder_trigger) begin `debug($display("-- %-0t", $time);) - irq_delay <= irq_active; reg_next_pc <= current_pc + 4; if (ENABLE_TRACE) latched_trace <= 1; count_instr <= count_instr + 1; @@ -993,7 +909,7 @@ module picorv32 #( latched_branch <= 1; end else begin mem_do_rinst <= 0; - mem_do_prefetch <= !instr_jalr && !instr_retirq; + mem_do_prefetch <= !instr_jalr; cpu_state <= cpu_state_ld_rs1; end end @@ -1025,10 +941,7 @@ module picorv32 #( end else if (pcpi_timeout || instr_ecall_ebreak) begin pcpi_valid <= 0; `debug($display("EBREAK OR UNSUPPORTED INSN AT 0x%08x", reg_pc);) - if (!irq_mask[irq_ebreak] && !irq_active) begin - next_irq_pending[irq_ebreak] = 1; - cpu_state <= cpu_state_fetch; - end else cpu_state <= cpu_state_trap; + cpu_state <= cpu_state_trap; end end is_rdcycle_rdcycleh_rdinstr_rdinstrh: begin @@ -1048,52 +961,6 @@ module picorv32 #( mem_do_rinst <= mem_do_prefetch; cpu_state <= cpu_state_exec; end - instr_getq: begin - `debug($display("LD_RS1: %2d 0x%08x", decoded_rs1, cpuregs_rs1);) - reg_out <= cpuregs_rs1; - dbg_rs1val <= cpuregs_rs1; - dbg_rs1val_valid <= 1; - latched_store <= 1; - cpu_state <= cpu_state_fetch; - end - instr_setq: begin - `debug($display("LD_RS1: %2d 0x%08x", decoded_rs1, cpuregs_rs1);) - reg_out <= cpuregs_rs1; - dbg_rs1val <= cpuregs_rs1; - dbg_rs1val_valid <= 1; - latched_rd <= latched_rd | irqregs_offset; - latched_store <= 1; - cpu_state <= cpu_state_fetch; - end - instr_retirq: begin - eoi <= 0; - irq_active <= 0; - latched_branch <= 1; - latched_store <= 1; - `debug($display("LD_RS1: %2d 0x%08x", decoded_rs1, cpuregs_rs1);) - reg_out <= cpuregs_rs1 & 32'hfffffffe; - dbg_rs1val <= cpuregs_rs1; - dbg_rs1val_valid <= 1; - cpu_state <= cpu_state_fetch; - end - instr_maskirq: begin - latched_store <= 1; - reg_out <= irq_mask; - `debug($display("LD_RS1: %2d 0x%08x", decoded_rs1, cpuregs_rs1);) - irq_mask <= cpuregs_rs1 | MASKED_IRQ; - dbg_rs1val <= cpuregs_rs1; - dbg_rs1val_valid <= 1; - cpu_state <= cpu_state_fetch; - end - instr_timer: begin - latched_store <= 1; - reg_out <= timer; - `debug($display("LD_RS1: %2d 0x%08x", decoded_rs1, cpuregs_rs1);) - timer <= cpuregs_rs1; - dbg_rs1val <= cpuregs_rs1; - dbg_rs1val_valid <= 1; - cpu_state <= cpu_state_fetch; - end is_lb_lh_lw_lbu_lhu && !instr_trap: begin `debug($display("LD_RS1: %2d 0x%08x", decoded_rs1, cpuregs_rs1);) reg_op1 <= cpuregs_rs1; @@ -1167,10 +1034,7 @@ module picorv32 #( end else if (pcpi_timeout || instr_ecall_ebreak) begin pcpi_valid <= 0; `debug($display("EBREAK OR UNSUPPORTED INSN AT 0x%08x", reg_pc);) - if (!irq_mask[irq_ebreak] && !irq_active) begin - next_irq_pending[irq_ebreak] = 1; - cpu_state <= cpu_state_fetch; - end else cpu_state <= cpu_state_trap; + cpu_state <= cpu_state_trap; end end is_sb_sh_sw: begin @@ -1205,7 +1069,6 @@ module picorv32 #( cpu_state <= cpu_state_fetch; end end - cpu_state_shift: begin latched_store <= 1; if (reg_sh == 0) begin @@ -1243,7 +1106,7 @@ module picorv32 #( endcase if (ENABLE_TRACE) begin trace_valid <= 1; - trace_data <= (irq_active ? TRACE_IRQ : 0) | TRACE_ADDR | ((reg_op1 + decoded_imm) & 32'hffffffff); + trace_data <= TRACE_ADDR | ((reg_op1 + decoded_imm) & 32'hffffffff); end reg_op1 <= reg_op1 + decoded_imm; set_mem_do_wdata = 1; @@ -1271,7 +1134,7 @@ module picorv32 #( latched_is_lb <= instr_lb; if (ENABLE_TRACE) begin trace_valid <= 1; - trace_data <= (irq_active ? TRACE_IRQ : 0) | TRACE_ADDR | ((reg_op1 + decoded_imm) & 32'hffffffff); + trace_data <= TRACE_ADDR | ((reg_op1 + decoded_imm) & 32'hffffffff); end reg_op1 <= reg_op1 + decoded_imm; set_mem_do_rdata = 1; @@ -1291,28 +1154,19 @@ module picorv32 #( end endcase - next_irq_pending = next_irq_pending | irq; - if (timer) if (timer - 1 == 0) next_irq_pending[irq_timer] = 1; - if (resetn && (mem_do_rdata || mem_do_wdata)) begin if (mem_wordsize == 0 && reg_op1[1:0] != 0) begin `debug($display("MISALIGNED WORD: 0x%08x", reg_op1);) - if (!irq_mask[irq_buserror] && !irq_active) begin - next_irq_pending[irq_buserror] = 1; - end else cpu_state <= cpu_state_trap; + cpu_state <= cpu_state_trap; end if (mem_wordsize == 1 && reg_op1[0] != 0) begin `debug($display("MISALIGNED HALFWORD: 0x%08x", reg_op1);) - if (!irq_mask[irq_buserror] && !irq_active) begin - next_irq_pending[irq_buserror] = 1; - end else cpu_state <= cpu_state_trap; + cpu_state <= cpu_state_trap; end end if (resetn && mem_do_rinst && (|reg_pc[1:0])) begin `debug($display("MISALIGNED INSTRUCTION: 0x%08x", reg_pc);) - if (!irq_mask[irq_buserror] && !irq_active) begin - next_irq_pending[irq_buserror] = 1; - end else cpu_state <= cpu_state_trap; + cpu_state <= cpu_state_trap; end if (!resetn || mem_done) begin @@ -1326,7 +1180,6 @@ module picorv32 #( if (set_mem_do_rdata) mem_do_rdata <= 1; if (set_mem_do_wdata) mem_do_wdata <= 1; - irq_pending <= next_irq_pending & ~MASKED_IRQ; current_pc = 'bx; end endmodule @@ -1334,15 +1187,15 @@ endmodule module picorv32_regs ( input clk, wen, - input [5:0] waddr, - input [5:0] raddr1, - input [5:0] raddr2, + input [4:0] waddr, + input [4:0] raddr1, + input [4:0] raddr2, input [31:0] wdata, output [31:0] rdata1, output [31:0] rdata2 ); - reg [31:0] regs[0:35]; - always @(posedge clk) if (wen) regs[waddr[5:0]] <= wdata; + reg [31:0] regs[0:31]; + always @(posedge clk) if (wen) regs[waddr[4:0]] <= wdata; assign rdata1 = regs[raddr1]; assign rdata2 = regs[raddr2]; endmodule diff --git a/testbench_wb.v b/testbench_wb.v index 32c396b..8bfc180 100644 --- a/testbench_wb.v +++ b/testbench_wb.v @@ -113,10 +113,7 @@ module picorv32_wb #( picorv32 #( .ENABLE_TRACE(1), - .MASKED_IRQ(32'h0000_0000), - .LATCHED_IRQ(32'hffff_ffff), .PROGADDR_RESET(32'h0001_0000), - .PROGADDR_IRQ(32'h0001_0010), .STACKADDR(32'h0001_0000) ) picorv32_core ( .clk (clk), @@ -135,8 +132,6 @@ module picorv32_wb #( .mem_la_addr (mem_la_addr), .mem_la_wdata(mem_la_wdata), .mem_la_wstrb(mem_la_wstrb), - .irq (irq), - .eoi (eoi), .trace_valid(trace_valid), .trace_data (trace_data),