diff --git a/CHANGELOG.md b/CHANGELOG.md index 77885d955..c7549bed6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -32,6 +32,7 @@ mimpid = 0x01040312 => 01.04.03.12 => Version 01.04.03.12 => v1.4.3.12 | Date (*dd.mm.yyyy*) | Version | Comment | |:-------------------:|:-------:|:--------| +| 03.09.2022 | 1.7.6.2 | cleanup hardware reset logic; [#405](https://github.com/stnolting/neorv32/pull/405) | | 02.09.2022 | 1.7.6.1 | :sparkles: add new processor module: **1-Wire Interface Controller** (ONEWIRE); [#402](https://github.com/stnolting/neorv32/pull/402) | | 28.08.2022 | [**:rocket:1.7.6**](https://github.com/stnolting/neorv32/releases/tag/v1.7.6) | **New release** | | 27.08.2022 | 1.7.5.9 | fix minor core rtl issues that were found while experimenting with a low-level netlist of the processor; [#398](https://github.com/stnolting/neorv32/pull/398) | diff --git a/docs/datasheet/cpu.adoc b/docs/datasheet/cpu.adoc index b157ee70a..ad7e24f76 100644 --- a/docs/datasheet/cpu.adoc +++ b/docs/datasheet/cpu.adoc @@ -1083,43 +1083,17 @@ memory system to perform the necessary operations (for example a cache flush/rel :sectnums: ==== CPU Hardware Reset -In order to reduce routing constraints (and by this the actual hardware requirements), most uncritical -registers of the NEORV32 CPU as well as most register of the whole NEORV32 Processor do not use **a -dedicated hardware reset**. "Uncritical registers" in this context means that the initial value of these registers -after power-up/reset is not relevant for a defined CPU boot process. +In order to reduce routing constraints (and by this the actual hardware requirements), most _uncritical registers_ +of the NEORV32 CPU as well as most registers of the whole NEORV32 Processor do not use **a dedicated hardware reset**. +"Uncritical registers" in this context means that the initial value of the according register(s) +after power-up/reset is not relevant for a defined CPU boot/start process. - -**Rationale** - -A good example to illustrate the concept of uncritical registers is a pipelined processing engine. Each stage -of the engine features an N-bit _data register_ and a 1-bit _status register_. The status register is set when the -data in the according data register is valid. At the end of the pipeline the status register might trigger a write-back -of the processing result to some kind of memory. The initial status of the data registers after power-up is -irrelevant as long as the status registers are all reset to a defined value that indicates there is no valid data in -the pipeline's data register. Therefore, the pipeline data register do no require a dedicated reset as they do not -control the actual operation (in contrast to the status register). This makes the pipeline data registers from -this example "uncritical registers". - - -**NEORV32 CPU Reset** +Many CPU-internal register do provide an asynchronous reset described in the VHDL code, but the "don't care" value +(VHDL `'-'`) is used for initialization of uncritical registers - effectively generating a flip-flop without a +reset input. In terms of the NEORV32 CPU, there are several pipeline registers, state machine registers and even some status and control registers (CSRs) that do not require a defined initial state to ensure a correct boot process. The pipeline register will get initialized by the CPU's internal state machines, which are initialized from the main -control engine that actually features a defined reset. - - -**Reset Configuration** - -Most CPU-internal register do provide an asynchronous reset in the VHDL code, but the "don't care" value -(VHDL `'-'`) is used for initialization of all uncritical registers - effectively generating a flip-flop without a -reset. However, certain applications or situations (like advanced gate-level / timing simulations) might -require a more deterministic reset state. For this case, a defined reset level (reset-to-low) of most CPU registers can -be configured by enabling a constant in the main VHDL package file (`rtl/core/neorv32_package.vhd`): +control engine that actually features a defined hardware reset. -[source,vhdl] ----- --- use dedicated hardware reset value for UNCRITICAL registers -- --- FALSE=reset value is irrelevant (might simplify HW), default; TRUE=defined LOW reset value -constant dedicated_reset_c : boolean := false; ----- diff --git a/docs/datasheet/cpu_csr.adoc b/docs/datasheet/cpu_csr.adoc index 77b8a7159..7b8a6b30b 100644 --- a/docs/datasheet/cpu_csr.adoc +++ b/docs/datasheet/cpu_csr.adoc @@ -560,6 +560,11 @@ the <<_mxisa>> CSR. + If _CPU_CNT_WIDTH_ is 0, the <<_cycleh>> and <<_instreth>> / <<_mcycleh>> and <<_minstreth>> CSRs are hardwired to zero and any write access to them is ignored. +.Counter Reset +[IMPORTANT] +The counter CSRs do **not** provide a hardware reset. Hence, the CSRs have to be explicitly initialized by software +before being used. + :sectnums!: ===== **`cycle[h]`** @@ -842,8 +847,7 @@ NEORV32-specific read-only CSR that helps machine-mode software to discover `Z*` | Bit | Name [C] | R/W | Function | 31 | _CSR_MXISA_FASTSHIFT_ | r/- | fast shifts available when set (via top's <<_fast_shift_en>> generic) | 30 | _CSR_MXISA_FASTMUL_ | r/- | fast multiplication available when set (via top's <<_fast_mul_en>> generic) -| 31:22 | - | r/- | _reserved_, read as zero -| 21 | _CSR_MXISA_HW_RESET_ | r/- | set if a dedicated hardware reset of all core registers is implemented (via package's `dedicated_reset_c` constant) +| 31:21 | - | r/- | _reserved_, read as zero | 20 | _CSR_MXISA_IS_SIM_ | r/- | set if CPU is being **simulated** (⚠️ not guaranteed) | 19:11 | - | r/- | _reserved_, read as zero | 10 | _CSR_MXISA_DEBUGMODE_ | r/- | RISC-V CPU `debug_mode` available when set (via top's <<_on_chip_debugger_en>> generic) diff --git a/docs/datasheet/soc_sysinfo.adoc b/docs/datasheet/soc_sysinfo.adoc index efe953dcb..b2e24d284 100644 --- a/docs/datasheet/soc_sysinfo.adoc +++ b/docs/datasheet/soc_sysinfo.adoc @@ -51,31 +51,32 @@ will signal a "DEVICE ERROR" in this case. [options="header",grid="all"] |======================= | Bit | Name [C] | Function -| `0` | _SYSINFO_SOC_BOOTLOADER_ | set if the processor-internal bootloader is implemented (via top's <<_int_bootloader_en>> generic) -| `1` | _SYSINFO_SOC_MEM_EXT_ | set if the external Wishbone bus interface is implemented (via top's <<_mem_ext_en>> generic) -| `2` | _SYSINFO_SOC_MEM_INT_IMEM_ | set if the processor-internal DMEM implemented (via top's <<_mem_int_dmem_en>> generic) -| `3` | _SYSINFO_SOC_MEM_INT_DMEM_ | set if the processor-internal IMEM is implemented (via top's <<_mem_int_imem_en>> generic) -| `4` | _SYSINFO_SOC_MEM_EXT_ENDIAN_ | set if external bus interface uses BIG-endian byte-order (via top's <<_mem_ext_big_endian>> generic) -| `5` | _SYSINFO_SOC_ICACHE_ | set if processor-internal instruction cache is implemented (via top's <<_icache_en>> generic) -| `13` | _SYSINFO_SOC_IS_SIM_ | set if processor is being **simulated** (⚠️ not guaranteed) -| `14` | _SYSINFO_SOC_OCD_ | set if on-chip debugger implemented (via top's <<_on_chip_debugger_en>> generic) -| `15` | _SYSINFO_SOC_HW_RESET_ | set if a dedicated hardware reset of all core registers is implemented (via package's `dedicated_reset_c` constant) -| `16` | _SYSINFO_SOC_IO_GPIO_ | set if the GPIO is implemented (via top's <<_io_gpio_en>> generic) -| `17` | _SYSINFO_SOC_IO_MTIME_ | set if the MTIME is implemented (via top's <<_io_mtime_en>> generic) -| `18` | _SYSINFO_SOC_IO_UART0_ | set if the primary UART0 is implemented (via top's <<_io_uart0_en>> generic) -| `19` | _SYSINFO_SOC_IO_SPI_ | set if the SPI is implemented (via top's <<_io_spi_en>> generic) -| `20` | _SYSINFO_SOC_IO_TWI_ | set if the TWI is implemented (via top's <<_io_twi_en>> generic) -| `21` | _SYSINFO_SOC_IO_PWM_ | set if the PWM is implemented (via top's <<_io_pwm_num_ch>> generic) -| `22` | _SYSINFO_SOC_IO_WDT_ | set if the WDT is implemented (via top's <<_io_wdt_en>> generic) -| `23` | _SYSINFO_SOC_IO_CFS_ | set if the custom functions subsystem is implemented (via top's <<_io_cfs_en>> generic) -| `24` | _SYSINFO_SOC_IO_TRNG_ | set if the TRNG is implemented (via top's _IO_TRNG_EN_ generic) -| `25` | _SYSINFO_SOC_IO_SLINK_ | set if the SLINK is implemented (via top's <<_slink_num_tx>> and/or <<_slink_num_rx>> generics) -| `26` | _SYSINFO_SOC_IO_UART1_ | set if the secondary UART1 is implemented (via top's <<_io_uart1_en>> generic) -| `27` | _SYSINFO_SOC_IO_NEOLED_ | set if the NEOLED is implemented (via top's <<_io_neoled_en>> generic) -| `28` | _SYSINFO_SOC_IO_XIRQ_ | set if the XIRQ is implemented (via top's <<_xirq_num_ch>> generic) -| `29` | _SYSINFO_SOC_IO_GPTMR_ | set if the GPTMR is implemented (via top's <<_io_gptmr_en>> generic) -| `30` | _SYSINFO_SOC_IO_XIP_ | set if the XIP module is implemented (via top's <<_io_xip_en>> generic) -| `31` | _SYSINFO_SOC_IO_ONEWIRE_ | set if the ONEWIRE interface is implemented (via top's <<_io_onewire_en>> generic) +| `0` | _SYSINFO_SOC_BOOTLOADER_ | set if the processor-internal bootloader is implemented (via top's <<_int_bootloader_en>> generic) +| `1` | _SYSINFO_SOC_MEM_EXT_ | set if the external Wishbone bus interface is implemented (via top's <<_mem_ext_en>> generic) +| `2` | _SYSINFO_SOC_MEM_INT_IMEM_ | set if the processor-internal DMEM implemented (via top's <<_mem_int_dmem_en>> generic) +| `3` | _SYSINFO_SOC_MEM_INT_DMEM_ | set if the processor-internal IMEM is implemented (via top's <<_mem_int_imem_en>> generic) +| `4` | _SYSINFO_SOC_MEM_EXT_ENDIAN_ | set if external bus interface uses BIG-endian byte-order (via top's <<_mem_ext_big_endian>> generic) +| `5` | _SYSINFO_SOC_ICACHE_ | set if processor-internal instruction cache is implemented (via top's <<_icache_en>> generic) +| `12:6` | - | _reserved_, read as zero +| `13` | _SYSINFO_SOC_IS_SIM_ | set if processor is being **simulated** (⚠️ not guaranteed) +| `14` | _SYSINFO_SOC_OCD_ | set if on-chip debugger implemented (via top's <<_on_chip_debugger_en>> generic) +| `15` | - | _reserved_, read as zero +| `16` | _SYSINFO_SOC_IO_GPIO_ | set if the GPIO is implemented (via top's <<_io_gpio_en>> generic) +| `17` | _SYSINFO_SOC_IO_MTIME_ | set if the MTIME is implemented (via top's <<_io_mtime_en>> generic) +| `18` | _SYSINFO_SOC_IO_UART0_ | set if the primary UART0 is implemented (via top's <<_io_uart0_en>> generic) +| `19` | _SYSINFO_SOC_IO_SPI_ | set if the SPI is implemented (via top's <<_io_spi_en>> generic) +| `20` | _SYSINFO_SOC_IO_TWI_ | set if the TWI is implemented (via top's <<_io_twi_en>> generic) +| `21` | _SYSINFO_SOC_IO_PWM_ | set if the PWM is implemented (via top's <<_io_pwm_num_ch>> generic) +| `22` | _SYSINFO_SOC_IO_WDT_ | set if the WDT is implemented (via top's <<_io_wdt_en>> generic) +| `23` | _SYSINFO_SOC_IO_CFS_ | set if the custom functions subsystem is implemented (via top's <<_io_cfs_en>> generic) +| `24` | _SYSINFO_SOC_IO_TRNG_ | set if the TRNG is implemented (via top's _IO_TRNG_EN_ generic) +| `25` | _SYSINFO_SOC_IO_SLINK_ | set if the SLINK is implemented (via top's <<_slink_num_tx>> and/or <<_slink_num_rx>> generics) +| `26` | _SYSINFO_SOC_IO_UART1_ | set if the secondary UART1 is implemented (via top's <<_io_uart1_en>> generic) +| `27` | _SYSINFO_SOC_IO_NEOLED_ | set if the NEOLED is implemented (via top's <<_io_neoled_en>> generic) +| `28` | _SYSINFO_SOC_IO_XIRQ_ | set if the XIRQ is implemented (via top's <<_xirq_num_ch>> generic) +| `29` | _SYSINFO_SOC_IO_GPTMR_ | set if the GPTMR is implemented (via top's <<_io_gptmr_en>> generic) +| `30` | _SYSINFO_SOC_IO_XIP_ | set if the XIP module is implemented (via top's <<_io_xip_en>> generic) +| `31` | _SYSINFO_SOC_IO_ONEWIRE_ | set if the ONEWIRE interface is implemented (via top's <<_io_onewire_en>> generic) |======================= diff --git a/docs/userguide/simulating_the_processor.adoc b/docs/userguide/simulating_the_processor.adoc index 8785fffc4..c201341fe 100644 --- a/docs/userguide/simulating_the_processor.adoc +++ b/docs/userguide/simulating_the_processor.adoc @@ -175,7 +175,6 @@ Using simulation runtime args: --stop-time=10ms <5> ../rtl/core/neorv32_top.vhd:370:3:@0ms:(assertion note): NEORV32 PROCESSOR CONFIG NOTE: Boot configuration: Direct boot from memory (processor-internal IMEM). ../rtl/core/neorv32_top.vhd:394:3:@0ms:(assertion note): NEORV32 PROCESSOR CONFIG NOTE: Implementing on-chip debugger (OCD). ../rtl/core/neorv32_cpu.vhd:169:3:@0ms:(assertion note): NEORV32 CPU ISA Configuration (MARCH): RV32IMCU_Zbb_Zicsr_Zifencei_Zfinx_Debug -../rtl/core/neorv32_cpu.vhd:189:3:@0ms:(assertion note): NEORV32 CPU CONFIG NOTE: Implementing NO dedicated hardware reset for uncritical registers (default, might reduce area). Set package constant = TRUE to configure a DEFINED reset value for all CPU registers. ../rtl/core/neorv32_imem.vhd:107:3:@0ms:(assertion note): NEORV32 PROCESSOR CONFIG NOTE: Implementing processor-internal IMEM as ROM (16384 bytes), pre-initialized with application (4612 bytes). ../rtl/core/neorv32_dmem.vhd:89:3:@0ms:(assertion note): NEORV32 PROCESSOR CONFIG NOTE: Implementing processor-internal DMEM (RAM, 8192 bytes). ../rtl/core/neorv32_wishbone.vhd:136:3:@0ms:(assertion note): NEORV32 PROCESSOR CONFIG NOTE: External Bus Interface - Implementing STANDARD Wishbone protocol. diff --git a/rtl/core/neorv32_cpu.vhd b/rtl/core/neorv32_cpu.vhd index 4625ac675..943d44466 100644 --- a/rtl/core/neorv32_cpu.vhd +++ b/rtl/core/neorv32_cpu.vhd @@ -1,21 +1,6 @@ -- ################################################################################################# -- # << NEORV32 - CPU Top Entity >> # -- # ********************************************************************************************* # --- # NEORV32 CPU: # --- # * neorv32_cpu.vhd - CPU top entity # --- # * neorv32_cpu_alu.vhd - Arithmetic/logic unit # --- # * neorv32_cpu_cp_bitmanip.vhd - Bit-manipulation co-processor # --- # * neorv32_cpu_cp_cfu.vhd - Custom instructions co-processor # --- # * neorv32_cpu_cp_fpu.vhd - Single-precision FPU co-processor # --- # * neorv32_cpu_cp_muldiv.vhd - Integer multiplier/divider co-processor # --- # * neorv32_cpu_cp_shifter.vhd - Base ISA shifter unit # --- # * neorv32_cpu_bus.vhd - Load/store unit & physical memory protection # --- # * neorv32_cpu_control.vhd - CPU control and CSR system # --- # * neorv32_cpu_decompressor.vhd - Compressed instructions decoder # --- # * neorv32_fifo.vhd - Instruction prefetch buffer # --- # * neorv32_cpu_regfile.vhd - Data register file # --- # * neorv32_package.vhd - Main CPU & Processor package file # --- # # -- # Check out the CPU's online documentation for more information: # -- # HQ: https://github.com/stnolting/neorv32 # -- # Data Sheet: https://stnolting.github.io/neorv32 # @@ -189,11 +174,6 @@ begin assert not (is_simulation_c = true) report "NEORV32 CPU WARNING! Assuming this is a simulation." severity warning; assert not (is_simulation_c = false) report "NEORV32 CPU NOTE: Assuming this is real hardware." severity note; - -- hardware reset notifier -- - assert not (dedicated_reset_c = false) report "NEORV32 CPU CONFIG NOTE: Implementing NO dedicated hardware reset for uncritical registers (default)." severity note; - assert not (dedicated_reset_c = true) report "NEORV32 CPU CONFIG NOTE: Implementing defined hardware reset for uncritical registers (non-default, reset-to-zero, might increase area)." severity note; - assert not ((def_rst_val_c /= '-') and (def_rst_val_c /= '0')) report "NEORV32 CPU CONFIG ERROR! Invalid configuration of package constant (has to be '-' or '0')." severity error; - -- CPU boot address -- assert not (CPU_BOOT_ADDR(1 downto 0) /= "00") report "NEORV32 CPU CONFIG ERROR! has to be 32-bit aligned." severity error; assert false report "NEORV32 CPU CONFIG NOTE: Boot from address 0x" & to_hstring32_f(CPU_BOOT_ADDR) & "." severity note; diff --git a/rtl/core/neorv32_cpu_bus.vhd b/rtl/core/neorv32_cpu_bus.vhd index cf5999014..937729432 100644 --- a/rtl/core/neorv32_cpu_bus.vhd +++ b/rtl/core/neorv32_cpu_bus.vhd @@ -137,7 +137,7 @@ begin mem_adr_reg: process(rstn_i, clk_i) begin if (rstn_i = '0') then - mar <= (others => def_rst_val_c); + mar <= (others => '0'); misaligned <= '0'; elsif rising_edge(clk_i) then if (ctrl_i(ctrl_bus_mo_we_c) = '1') then @@ -158,12 +158,9 @@ begin -- Write Data ----------------------------------------------------------------------------- -- ------------------------------------------------------------------------------------------- - mem_do_reg: process(rstn_i, clk_i) + mem_do_reg: process(clk_i) begin - if (rstn_i = '0') then - d_bus_wdata_o <= (others => def_rst_val_c); - d_bus_ben_o <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then if (ctrl_i(ctrl_bus_mo_we_c) = '1') then -- byte enable and data alignment -- case ctrl_i(ctrl_ir_funct3_1_c downto ctrl_ir_funct3_0_c) is -- data size @@ -197,11 +194,9 @@ begin -- Read Data ------------------------------------------------------------------------------ -- ------------------------------------------------------------------------------------------- - read_align: process(rstn_i, clk_i) + read_align: process(clk_i) begin - if (rstn_i = '0') then - rdata_o <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then -- input data alignment and sign extension -- case ctrl_i(ctrl_ir_funct3_1_c downto ctrl_ir_funct3_0_c) is when "00" => -- byte diff --git a/rtl/core/neorv32_cpu_control.vhd b/rtl/core/neorv32_cpu_control.vhd index 50936365c..737ebedf7 100644 --- a/rtl/core/neorv32_cpu_control.vhd +++ b/rtl/core/neorv32_cpu_control.vhd @@ -1747,7 +1747,7 @@ begin csr.mip_firq_nclr <= (others => '-'); -- csr.pmpcfg <= (others => (others => '0')); - csr.pmpaddr <= (others => (others => def_rst_val_c)); + csr.pmpaddr <= (others => (others => '-')); -- csr.mhpmevent <= (others => (others => '0')); -- @@ -2358,7 +2358,6 @@ begin csr.rdata(10) <= bool_to_ulogic_f(CPU_EXTENSION_RISCV_DEBUG); -- RISC-V debug mode -- misc -- csr.rdata(20) <= bool_to_ulogic_f(is_simulation_c); -- is this a simulation? - csr.rdata(21) <= bool_to_ulogic_f(dedicated_reset_c); -- dedicated hardware reset of all core registers? -- tuning options -- csr.rdata(30) <= bool_to_ulogic_f(FAST_MUL_EN); -- DSP-based multiplication (M extensions only) csr.rdata(31) <= bool_to_ulogic_f(FAST_SHIFT_EN); -- parallel logic for shifts (barrel shifters) @@ -2383,19 +2382,10 @@ begin -- Control and Status Registers - Counters ------------------------------------------------ -- ------------------------------------------------------------------------------------------- - csr_counters: process(rstn_i, clk_i) + csr_counters: process(clk_i) begin - if (rstn_i = '0') then - csr.mcycle <= (others => def_rst_val_c); - csr.mcycle_ovfl <= (others => def_rst_val_c); - csr.mcycleh <= (others => def_rst_val_c); - csr.minstret <= (others => def_rst_val_c); - csr.minstret_ovfl <= (others => def_rst_val_c); - csr.minstreth <= (others => def_rst_val_c); - csr.mhpmcounter <= (others => (others => def_rst_val_c)); - csr.mhpmcounter_ovfl <= (others => (others => def_rst_val_c)); - csr.mhpmcounterh <= (others => (others => def_rst_val_c)); - elsif rising_edge(clk_i) then + -- NOTE: the counter CSRs do NOT have a dedicated reset and need to be initialized by software before being used! + if rising_edge(clk_i) then -- [m]cycle -- if (cpu_cnt_lo_width_c > 0) and (CPU_EXTENSION_RISCV_Zicntr = true) then diff --git a/rtl/core/neorv32_cpu_cp_bitmanip.vhd b/rtl/core/neorv32_cpu_cp_bitmanip.vhd index be976a2c4..0289b4389 100644 --- a/rtl/core/neorv32_cpu_cp_bitmanip.vhd +++ b/rtl/core/neorv32_cpu_cp_bitmanip.vhd @@ -230,11 +230,11 @@ begin begin if (rstn_i = '0') then ctrl_state <= S_IDLE; - cmd_buf <= (others => def_rst_val_c); - rs1_reg <= (others => def_rst_val_c); - rs2_reg <= (others => def_rst_val_c); - sha_reg <= (others => def_rst_val_c); - less_reg <= def_rst_val_c; + cmd_buf <= (others => '-'); + rs1_reg <= (others => '-'); + rs2_reg <= (others => '-'); + sha_reg <= (others => '-'); + less_reg <= '-'; clmul.start <= '0'; shifter.start <= '0'; valid <= '0'; @@ -307,15 +307,10 @@ begin serial_shifter: if (FAST_SHIFT_EN = false) generate - shifter_unit: process(rstn_i, clk_i) + shifter_unit: process(clk_i) variable new_bit_v : std_ulogic; begin - if (rstn_i = '0') then - shifter.cnt <= (others => def_rst_val_c); - shifter.sreg <= (others => def_rst_val_c); - shifter.cnt_max <= (others => def_rst_val_c); - shifter.bcnt <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then if (shifter.start = '1') then -- trigger new shift shifter.cnt <= (others => '0'); -- shift operand -- @@ -429,12 +424,9 @@ begin -- Carry-Less Multiplication Core --------------------------------------------------------- -- ------------------------------------------------------------------------------------------- - clmul_core: process(rstn_i, clk_i) + clmul_core: process(clk_i) begin - if (rstn_i = '0') then - clmul.cnt <= (others => def_rst_val_c); - clmul.prod <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then if (clmul.start = '1') then -- start new multiplication clmul.cnt <= (others => '0'); clmul.cnt(clmul.cnt'left) <= '1'; diff --git a/rtl/core/neorv32_cpu_cp_fpu.vhd b/rtl/core/neorv32_cpu_cp_fpu.vhd index 295c34059..2bcf15675 100644 --- a/rtl/core/neorv32_cpu_cp_fpu.vhd +++ b/rtl/core/neorv32_cpu_cp_fpu.vhd @@ -354,13 +354,13 @@ begin ctrl_engine.state <= S_IDLE; ctrl_engine.valid <= '0'; ctrl_engine.start <= '0'; - fpu_operands.frm <= (others => def_rst_val_c); - fpu_operands.rs1 <= (others => def_rst_val_c); - fpu_operands.rs1_class <= (others => def_rst_val_c); - fpu_operands.rs2 <= (others => def_rst_val_c); - fpu_operands.rs2_class <= (others => def_rst_val_c); - funct_ff <= (others => def_rst_val_c); - cmp_ff <= (others => def_rst_val_c); + fpu_operands.frm <= (others => '-'); + fpu_operands.rs1 <= (others => '-'); + fpu_operands.rs1_class <= (others => '-'); + fpu_operands.rs2 <= (others => '-'); + fpu_operands.rs2_class <= (others => '-'); + funct_ff <= (others => '-'); + cmp_ff <= (others => '-'); elsif rising_edge(clk_i) then -- arbiter defaults -- ctrl_engine.valid <= '0'; @@ -437,15 +437,10 @@ begin -- Floating-Point Comparator -------------------------------------------------------------- -- ------------------------------------------------------------------------------------------- - float_comparator: process(rstn_i, clk_i) + float_comparator: process(clk_i) variable cond_v : std_ulogic_vector(1 downto 0); begin - if (rstn_i = '0') then - comp_equal_ff <= def_rst_val_c; - comp_less_ff <= def_rst_val_c; - fu_compare.done <= def_rst_val_c; - fu_min_max.done <= def_rst_val_c; - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then -- equal -- if ((fpu_operands.rs1_class(fp_class_pos_inf_c) = '1') and (fpu_operands.rs2_class(fp_class_pos_inf_c) = '1')) or -- +inf == +inf ((fpu_operands.rs1_class(fp_class_neg_inf_c) = '1') and (fpu_operands.rs2_class(fp_class_neg_inf_c) = '1')) or -- -inf == -inf @@ -589,14 +584,11 @@ begin -- Convert: [unsigned] Integer to Float (FCVT.W.S) ---------------------------------------- -- ------------------------------------------------------------------------------------------- - convert_i2f: process(rstn_i, clk_i) + convert_i2f: process(clk_i) begin -- this process only computes the absolute input value -- the actual conversion is done by the normalizer - if (rstn_i = '0') then - fu_conv_i2f.result <= (others => def_rst_val_c); - fu_conv_i2f.sign <= def_rst_val_c; - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then if (ctrl_i(ctrl_ir_funct12_0_c) = '0') and (rs1_i(31) = '1') then -- convert signed integer fu_conv_i2f.result <= std_ulogic_vector(0 - unsigned(rs1_i)); fu_conv_i2f.sign <= rs1_i(31); -- original sign @@ -611,20 +603,9 @@ begin -- Multiplier Core (FMUL) ----------------------------------------------------------------- -- ------------------------------------------------------------------------------------------- - multiplier_core: process(rstn_i, clk_i) + multiplier_core: process(clk_i) begin - if (rstn_i = '0') then - multiplier.opa <= (others => '-'); -- these might be DSP regs! - multiplier.opb <= (others => '-'); -- these might be DSP regs! - multiplier.buf_ff <= (others => '-'); -- these might be DSP regs! - multiplier.product <= (others => '-'); -- these might be DSP regs! - multiplier.sign <= def_rst_val_c; - multiplier.exp_res <= (others => def_rst_val_c); - multiplier.flags(fp_exc_of_c) <= def_rst_val_c; - multiplier.flags(fp_exc_uf_c) <= def_rst_val_c; - multiplier.flags(fp_exc_nv_c) <= def_rst_val_c; - multiplier.latency <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then -- multiplier core -- if (multiplier.start = '1') then -- FIXME / TODO remove buffer? multiplier.opa <= unsigned('1' & fpu_operands.rs1(22 downto 0)); -- append hidden one @@ -673,16 +654,14 @@ begin -- result class -- - multiplier_class_core: process(rstn_i, clk_i) + multiplier_class_core: process(clk_i) variable a_pos_norm_v, a_neg_norm_v, b_pos_norm_v, b_neg_norm_v : std_ulogic; variable a_pos_subn_v, a_neg_subn_v, b_pos_subn_v, b_neg_subn_v : std_ulogic; variable a_pos_zero_v, a_neg_zero_v, b_pos_zero_v, b_neg_zero_v : std_ulogic; variable a_pos_inf_v, a_neg_inf_v, b_pos_inf_v, b_neg_inf_v : std_ulogic; variable a_snan_v, a_qnan_v, b_snan_v, b_qnan_v : std_ulogic; begin - if (rstn_i = '0') then - multiplier.res_class <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then -- minions -- a_pos_norm_v := fpu_operands.rs1_class(fp_class_pos_norm_c); b_pos_norm_v := fpu_operands.rs2_class(fp_class_pos_norm_c); a_neg_norm_v := fpu_operands.rs1_class(fp_class_neg_norm_c); b_neg_norm_v := fpu_operands.rs2_class(fp_class_neg_norm_c); @@ -775,21 +754,9 @@ begin -- Adder/Subtractor Core (FADD, FSUB) ----------------------------------------------------- -- ------------------------------------------------------------------------------------------- - adder_subtractor_core: process(rstn_i, clk_i) + adder_subtractor_core: process(clk_i) begin - if (rstn_i = '0') then - addsub.latency <= (others => def_rst_val_c); - addsub.exp_comp <= (others => def_rst_val_c); - addsub.man_sreg <= (others => def_rst_val_c); - addsub.exp_cnt <= (others => def_rst_val_c); - addsub.man_g_ext <= def_rst_val_c; - addsub.man_r_ext <= def_rst_val_c; - addsub.man_s_ext <= def_rst_val_c; - addsub.man_comp <= def_rst_val_c; - addsub.add_stage <= (others => def_rst_val_c); - addsub.res_sign <= def_rst_val_c; - addsub.flags(fp_exc_nv_c) <= def_rst_val_c; - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then -- arbitration / latency -- if (ctrl_engine.state = S_IDLE) then -- hacky "reset" addsub.latency <= (others => '0'); @@ -907,16 +874,14 @@ begin -- result class -- - adder_subtractor_class_core: process(rstn_i, clk_i) + adder_subtractor_class_core: process(clk_i) variable a_pos_norm_v, a_neg_norm_v, b_pos_norm_v, b_neg_norm_v : std_ulogic; variable a_pos_subn_v, a_neg_subn_v, b_pos_subn_v, b_neg_subn_v : std_ulogic; variable a_pos_zero_v, a_neg_zero_v, b_pos_zero_v, b_neg_zero_v : std_ulogic; variable a_pos_inf_v, a_neg_inf_v, b_pos_inf_v, b_neg_inf_v : std_ulogic; variable a_snan_v, a_qnan_v, b_snan_v, b_qnan_v : std_ulogic; begin - if (rstn_i = '0') then - addsub.res_class <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then -- minions -- a_pos_norm_v := fpu_operands.rs1_class(fp_class_pos_norm_c); b_pos_norm_v := fpu_operands.rs2_class(fp_class_pos_norm_c); a_neg_norm_v := fpu_operands.rs1_class(fp_class_neg_norm_c); b_neg_norm_v := fpu_operands.rs2_class(fp_class_neg_norm_c); @@ -1123,12 +1088,9 @@ begin -- Result Output to CPU Pipeline ---------------------------------------------------------- -- ------------------------------------------------------------------------------------------- - output_gate: process(rstn_i, clk_i) + output_gate: process(clk_i) begin - if (rstn_i = '0') then - res_o <= (others => def_rst_val_c); - fflags_o <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then if (ctrl_engine.valid = '1') then case funct_ff is when op_class_c => @@ -1280,24 +1242,24 @@ begin begin if (rstn_i = '0') then ctrl.state <= S_IDLE; - ctrl.norm_r <= def_rst_val_c; - ctrl.cnt <= (others => def_rst_val_c); - ctrl.cnt_pre <= (others => def_rst_val_c); - ctrl.cnt_of <= def_rst_val_c; - ctrl.cnt_uf <= def_rst_val_c; - ctrl.rounded <= def_rst_val_c; - ctrl.res_exp <= (others => def_rst_val_c); - ctrl.res_man <= (others => def_rst_val_c); - ctrl.res_sgn <= def_rst_val_c; - ctrl.class <= (others => def_rst_val_c); - ctrl.flags <= (others => def_rst_val_c); + ctrl.norm_r <= '-'; + ctrl.cnt <= (others => '-'); + ctrl.cnt_pre <= (others => '-'); + ctrl.cnt_of <= '-'; + ctrl.cnt_uf <= '-'; + ctrl.rounded <= '-'; + ctrl.res_exp <= (others => '-'); + ctrl.res_man <= (others => '-'); + ctrl.res_sgn <= '-'; + ctrl.class <= (others => '-'); + ctrl.flags <= (others => '-'); -- - sreg.upper <= (others => def_rst_val_c); - sreg.lower <= (others => def_rst_val_c); - sreg.dir <= def_rst_val_c; - sreg.ext_g <= def_rst_val_c; - sreg.ext_r <= def_rst_val_c; - sreg.ext_s <= def_rst_val_c; + sreg.upper <= (others => '-'); + sreg.lower <= (others => '-'); + sreg.dir <= '-'; + sreg.ext_g <= '-'; + sreg.ext_r <= '-'; + sreg.ext_s <= '-'; -- done_o <= '0'; elsif rising_edge(clk_i) then @@ -1660,18 +1622,18 @@ begin begin if (rstn_i = '0') then ctrl.state <= S_IDLE; - ctrl.cnt <= (others => def_rst_val_c); - ctrl.sign <= def_rst_val_c; - ctrl.class <= (others => def_rst_val_c); - ctrl.rounded <= def_rst_val_c; - ctrl.over <= def_rst_val_c; - ctrl.under <= def_rst_val_c; - ctrl.unsign <= def_rst_val_c; - ctrl.result <= (others => def_rst_val_c); - ctrl.result_tmp <= (others => def_rst_val_c); - sreg.int <= (others => def_rst_val_c); - sreg.mant <= (others => def_rst_val_c); - sreg.ext_s <= def_rst_val_c; + ctrl.cnt <= (others => '-'); + ctrl.sign <= '-'; + ctrl.class <= (others => '-'); + ctrl.rounded <= '-'; + ctrl.over <= '-'; + ctrl.under <= '-'; + ctrl.unsign <= '-'; + ctrl.result <= (others => '-'); + ctrl.result_tmp <= (others => '-'); + sreg.int <= (others => '-'); + sreg.mant <= (others => '-'); + sreg.ext_s <= '-'; done_o <= '0'; elsif rising_edge(clk_i) then -- defaults -- diff --git a/rtl/core/neorv32_cpu_cp_muldiv.vhd b/rtl/core/neorv32_cpu_cp_muldiv.vhd index f2a067f9b..b7822d937 100644 --- a/rtl/core/neorv32_cpu_cp_muldiv.vhd +++ b/rtl/core/neorv32_cpu_cp_muldiv.vhd @@ -122,11 +122,11 @@ begin begin if (rstn_i = '0') then ctrl.state <= S_IDLE; - ctrl.rs2_abs <= (others => def_rst_val_c); - ctrl.cnt <= (others => def_rst_val_c); - ctrl.cp_op_ff <= (others => def_rst_val_c); + ctrl.rs2_abs <= (others => '-'); + ctrl.cnt <= (others => '-'); + ctrl.cp_op_ff <= (others => '-'); ctrl.out_en <= '0'; - div.sign_mod <= def_rst_val_c; + div.sign_mod <= '-'; elsif rising_edge(clk_i) then -- defaults -- ctrl.out_en <= '0'; @@ -234,11 +234,9 @@ begin if (FAST_MUL_EN = false) generate -- shift-and-add algorithm -- - multiplier_core: process(rstn_i, clk_i) + multiplier_core: process(clk_i) begin - if (rstn_i = '0') then - mul.prod <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then if (mul.start = '1') then -- start new multiplication mul.prod(63 downto 32) <= (others => '0'); mul.prod(31 downto 00) <= rs1_i; @@ -282,12 +280,9 @@ begin if (DIVISION_EN = true) generate -- restoring division algorithm -- - divider_core: process(rstn_i, clk_i) + divider_core: process(clk_i) begin - if (rstn_i = '0') then - div.quotient <= (others => def_rst_val_c); - div.remainder <= (others => def_rst_val_c); - elsif rising_edge(clk_i) then + if rising_edge(clk_i) then if (div.start = '1') then -- start new division if ((rs1_i(rs1_i'left) and ctrl.rs1_is_signed) = '1') then -- signed division? div.quotient <= std_ulogic_vector(0 - unsigned(rs1_i)); -- make positive diff --git a/rtl/core/neorv32_cpu_cp_shifter.vhd b/rtl/core/neorv32_cpu_cp_shifter.vhd index 14ba29838..265f31004 100644 --- a/rtl/core/neorv32_cpu_cp_shifter.vhd +++ b/rtl/core/neorv32_cpu_cp_shifter.vhd @@ -90,10 +90,10 @@ begin serial_shifter_core: process(rstn_i, clk_i) begin if (rstn_i = '0') then - shifter.busy_ff <= '-'; + shifter.busy_ff <= '0'; shifter.busy <= '0'; - shifter.cnt <= (others => def_rst_val_c); - shifter.sreg <= (others => def_rst_val_c); + shifter.cnt <= (others => '-'); -- no reset required + shifter.sreg <= (others => '-'); -- no reset required elsif rising_edge(clk_i) then shifter.busy_ff <= shifter.busy; if (start_i = '1') then diff --git a/rtl/core/neorv32_package.vhd b/rtl/core/neorv32_package.vhd index 14fdf0794..5a2eabbdc 100644 --- a/rtl/core/neorv32_package.vhd +++ b/rtl/core/neorv32_package.vhd @@ -47,10 +47,6 @@ package neorv32_package is -- if register x0 is implemented as actual physical register is has to be set to zero by the CPU hardware -- constant reset_x0_c : boolean := true; -- has to be 'true' for the default register file rtl description (BRAM-based) - -- use dedicated hardware reset value for UNCRITICAL CPU registers (like pipeline buffers) -- - -- FALSE = no hardware reset (might simplify HW), default; TRUE = reset to zero - constant dedicated_reset_c : boolean := false; - -- "response time window" for processor-internal modules -- -- = cycles after which an *unacknowledged* internal bus access will timeout and trigger a bus fault exception (min 2) constant max_proc_int_response_time_c : natural := 15; @@ -63,7 +59,7 @@ package neorv32_package is -- Architecture Constants (do not modify!) ------------------------------------------------ -- ------------------------------------------------------------------------------------------- constant data_width_c : natural := 32; -- native data path width - do not change! - constant hw_version_c : std_ulogic_vector(31 downto 0) := x"01070601"; -- NEORV32 version - no touchy! + constant hw_version_c : std_ulogic_vector(31 downto 0) := x"01070602"; -- NEORV32 version - no touchy! constant archid_c : natural := 19; -- official RISC-V architecture ID - hands off! -- Check if we're inside the Matrix ------------------------------------------------------- @@ -119,10 +115,6 @@ package neorv32_package is function leading_zeros_f(input : std_ulogic_vector) return natural; impure function mem32_init_f(init : mem32_t; depth : natural) return mem32_t; - -- Internal (auto-generated) Configurations ----------------------------------------------- - -- ------------------------------------------------------------------------------------------- - constant def_rst_val_c : std_ulogic; -- Use a deferred constant, prevents compile error with Questa, see IEEE 1076-2008 14.4.2.1 - -- Processor-Internal Address Space Layout ------------------------------------------------ -- ------------------------------------------------------------------------------------------- -- Internal Instruction Memory (IMEM) and Date Memory (DMEM) -- @@ -2537,11 +2529,6 @@ package body neorv32_package is end function mem32_init_f; - -- Finally set deferred constants, see IEEE 1076-2008 14.4.2.1 (NEORV32 Issue #242) ------- - -- ------------------------------------------------------------------------------------------- - constant def_rst_val_c : std_ulogic := cond_sel_stdulogic_f(dedicated_reset_c, '0', '-'); - - end neorv32_package; diff --git a/rtl/core/neorv32_sysinfo.vhd b/rtl/core/neorv32_sysinfo.vhd index e37ac44a9..6250cc5e6 100644 --- a/rtl/core/neorv32_sysinfo.vhd +++ b/rtl/core/neorv32_sysinfo.vhd @@ -143,7 +143,8 @@ begin -- Misc -- sysinfo_mem(2)(13) <= bool_to_ulogic_f(is_simulation_c); -- is this a simulation? sysinfo_mem(2)(14) <= bool_to_ulogic_f(ON_CHIP_DEBUGGER_EN); -- on-chip debugger implemented? - sysinfo_mem(2)(15) <= bool_to_ulogic_f(dedicated_reset_c); -- dedicated hardware reset of all core registers? + -- + sysinfo_mem(2)(15) <= '0'; -- reserved -- IO -- sysinfo_mem(2)(16) <= bool_to_ulogic_f(IO_GPIO_EN); -- general purpose input/output port unit (GPIO) implemented? sysinfo_mem(2)(17) <= bool_to_ulogic_f(IO_MTIME_EN); -- machine system timer (MTIME) implemented? diff --git a/sw/lib/include/neorv32.h b/sw/lib/include/neorv32.h index 40c5eb9af..b36e4645b 100644 --- a/sw/lib/include/neorv32.h +++ b/sw/lib/include/neorv32.h @@ -464,7 +464,6 @@ enum NEORV32_CSR_XISA_enum { // Misc CSR_MXISA_IS_SIM = 20, /**< CPU mxisa CSR (20): this might be a simulation when set (r/-)*/ - CSR_MXISA_HW_RESET = 21, /**< CPU mxisa CSR (21): set if a dedicated hardware reset of all core registers is implemented (r/-)*/ // Tuning options CSR_MXISA_FASTMUL = 30, /**< CPU mxisa CSR (30): DSP-based multiplication (M extensions only) (r/-)*/ @@ -1403,7 +1402,6 @@ enum NEORV32_SYSINFO_SOC_enum { SYSINFO_SOC_IS_SIM = 13, /**< SYSINFO_FEATURES (13) (r/-): Set during simulation (not guaranteed) */ SYSINFO_SOC_OCD = 14, /**< SYSINFO_FEATURES (14) (r/-): On-chip debugger implemented when 1 (via ON_CHIP_DEBUGGER_EN generic) */ - SYSINFO_SOC_HW_RESET = 15, /**< SYSINFO_FEATURES (15) (r/-): Dedicated hardware reset of core registers implemented when 1 (via package's dedicated_reset_c constant) */ SYSINFO_SOC_IO_GPIO = 16, /**< SYSINFO_FEATURES (16) (r/-): General purpose input/output port unit implemented when 1 (via IO_GPIO_EN generic) */ SYSINFO_SOC_IO_MTIME = 17, /**< SYSINFO_FEATURES (17) (r/-): Machine system timer implemented when 1 (via IO_MTIME_EN generic) */ diff --git a/sw/lib/source/neorv32_rte.c b/sw/lib/source/neorv32_rte.c index f571ae729..dfd65103a 100644 --- a/sw/lib/source/neorv32_rte.c +++ b/sw/lib/source/neorv32_rte.c @@ -301,7 +301,6 @@ void neorv32_rte_print_hw_config(void) { // general neorv32_uart0_printf("Is simulation: "); __neorv32_rte_print_true_false(neorv32_cpu_csr_read(CSR_MXISA) & (1 << CSR_MXISA_IS_SIM)); neorv32_uart0_printf("Clock speed: %u Hz\n", NEORV32_SYSINFO.CLK); - neorv32_uart0_printf("Full HW reset: "); __neorv32_rte_print_true_false(neorv32_cpu_csr_read(CSR_MXISA) & (1 << CSR_MXISA_HW_RESET)); neorv32_uart0_printf("On-chip debugger: "); __neorv32_rte_print_true_false(NEORV32_SYSINFO.SOC & (1 << SYSINFO_SOC_OCD)); // IDs diff --git a/sw/svd/neorv32.svd b/sw/svd/neorv32.svd index f9288ddcf..259a39f00 100644 --- a/sw/svd/neorv32.svd +++ b/sw/svd/neorv32.svd @@ -1304,7 +1304,6 @@ SYSINFO_SOC_ICACHE[5:5]Processor-internal instruction cache implemented SYSINFO_SOC_IS_SIM[13:13]Set if processor is being simulated SYSINFO_SOC_OCD[14:14]On-chip debugger implemented - SYSINFO_SOC_HW_RESET[15:15]Dedicated hardware reset of core registers implemented SYSINFO_SOC_IO_GPIO[16:16]General purpose input/output port unit implemented SYSINFO_SOC_IO_MTIME[17:17]Machine system timer implemented SYSINFO_SOC_IO_UART0[18:18]Primary universal asynchronous receiver/transmitter 0 implemented