mirror of
https://github.com/stnolting/neorv32.git
synced 2025-04-24 22:27:21 -04:00
[docs] fixing #181 (em dash vs. en dash)
This commit is contained in:
parent
9e18b2eb6f
commit
a31a24e940
11 changed files with 46 additions and 46 deletions
|
@ -21,7 +21,7 @@ image::riscv_logo.png[width=350,align=center]
|
|||
** `PMP` - physical memory protection
|
||||
** `HPM` - hardware performance monitors
|
||||
** `DB` - debug mode
|
||||
* Compatible to the RISC-V user specifications and a subset of the RISC-V privileged architecture specifications – passes the official RISC-V Architecture Tests (v2+)
|
||||
* Compatible to the RISC-V user specifications and a subset of the RISC-V privileged architecture specifications - passes the official RISC-V Architecture Tests (v2+)
|
||||
* Official RISC-V open-source architecture ID
|
||||
* Standard RISC-V interrupts (_external_, _timer_, _software_) plus 16 _fast_ interrupts
|
||||
* Supports most of the traps from the RISC-V specifications (including bus access exceptions) and traps on all unimplemented/illegal/malformed instructions
|
||||
|
@ -31,7 +31,7 @@ image::riscv_logo.png[width=350,align=center]
|
|||
the NEORV32 processor)
|
||||
* little-endian byte order
|
||||
* Configurable hardware reset
|
||||
* No hardware support of unaligned data/instruction accesses – they will trigger an exception.
|
||||
* No hardware support of unaligned data/instruction accesses - they will trigger an exception.
|
||||
|
||||
[NOTE]
|
||||
It is recommended to use the **NEORV32 Processor** as default top instance even if you only want to use the actual
|
||||
|
@ -53,11 +53,11 @@ specifications. The following figure shows the simplified architecture of the CP
|
|||
|
||||
image::neorv32_cpu.png[align=center]
|
||||
|
||||
The CPU uses a pipelined architecture with basically two main stages. The first stage (IF – instruction fetch)
|
||||
The CPU uses a pipelined architecture with basically two main stages. The first stage (IF - instruction fetch)
|
||||
is responsible for fetching new instruction data from memory via the fetch engine. The instruction data is
|
||||
stored to a FIFO – the instruction prefetch buffer. The issue engine takes this data and assembles 32-bit
|
||||
instruction words for the next pipeline stage. Compressed instructions – if enabled – are also decompressed
|
||||
in this stage. The second stage (EX – execution) is responsible for actually executing the fetched instructions
|
||||
stored to a FIFO - the instruction prefetch buffer. The issue engine takes this data and assembles 32-bit
|
||||
instruction words for the next pipeline stage. Compressed instructions - if enabled - are also decompressed
|
||||
in this stage. The second stage (EX - execution) is responsible for actually executing the fetched instructions
|
||||
via the execute engine.
|
||||
|
||||
These two pipeline stages are based on a multi-cycle processing engine. So the processing of each stage for a
|
||||
|
@ -341,7 +341,7 @@ of the debugger memory. See section <<_on_chip_debugger_ocd>> for more informati
|
|||
|
||||
The basic NEORV32 is a RISC-V `rv32i` architecture that provides several _optional_ RISC-V CPU and ISA
|
||||
(instruction set architecture) extensions. For more information regarding the RISC-V ISA extensions please
|
||||
see the the _RISC-V Instruction Set Manual – Volume I: Unprivileged ISA_ and _The RISC-V Instruction Set Manual
|
||||
see the the _RISC-V Instruction Set Manual - Volume I: Unprivileged ISA_ and _The RISC-V Instruction Set Manual
|
||||
Volume II: Privileged Architecture_, which are available in the projects `docs/references` folder.
|
||||
|
||||
[TIP]
|
||||
|
@ -656,7 +656,7 @@ internal (iterative) computations before the configuration becomes valid.
|
|||
|
||||
[NOTE]
|
||||
For more information regarding RISC-V physical memory protection see the official _The RISC-V
|
||||
Instruction Set Manual – Volume II: Privileged Architecture_ specifications.
|
||||
Instruction Set Manual - Volume II: Privileged Architecture_ specifications.
|
||||
|
||||
|
||||
==== **`HPM`** Hardware Performance Monitors
|
||||
|
@ -753,7 +753,7 @@ configurations are presented in <<_cpu_performance>>.
|
|||
|=======================
|
||||
|
||||
[NOTE]
|
||||
The presented values of the *floating-point execution cycles* are average values – obtained from
|
||||
The presented values of the *floating-point execution cycles* are average values - obtained from
|
||||
4096 instruction executions using pseudo-random input values. The execution time for emulating the
|
||||
instructions (using pure-software libraries) is ~17..140 times higher.
|
||||
|
||||
|
@ -818,7 +818,7 @@ until it is explicitly acknowledged by the CPU software (for example by writing
|
|||
|
||||
.Instruction Atomicity
|
||||
[NOTE]
|
||||
All instructions execute as atomic operations – interrupts can only trigger between two instructions.
|
||||
All instructions execute as atomic operations - interrupts can only trigger between two instructions.
|
||||
So if there is a permanent interrupt request, exactly one instruction from the interrupt program will be executed before
|
||||
a new interrupt handler can start.
|
||||
|
||||
|
@ -912,7 +912,7 @@ accessing data (`d_bus_*`) via load and store operations. Both interfaces use th
|
|||
The CPU is a 32-bit architecture with separated instruction and data interfaces making it a Harvard
|
||||
Architecture. Each of this interfaces can access an address space of up to 2^32^ bytes (4GB). The memory
|
||||
system is based on 32-bit words with a minimal granularity of 1 byte. Please note, that the NEORV32 CPU
|
||||
does not support unaligned memory accesses _in hardware_ – however, a software-based handling can be
|
||||
does not support unaligned memory accesses _in hardware_ - however, a software-based handling can be
|
||||
implemented as any unaligned memory access will trigger an according exception.
|
||||
|
||||
:sectnums:
|
||||
|
|
|
@ -502,7 +502,7 @@ first PMP configuration entry) are implemented (all remaining bits are always ze
|
|||
[options="header",grid="rows"]
|
||||
|=======================
|
||||
| Bit | RISC-V name | R/W | Function
|
||||
| 7 | _L_ | r/w | lock bit, can be set – but not be cleared again (only via CPU reset)
|
||||
| 7 | _L_ | r/w | lock bit, can be set - but not be cleared again (only via CPU reset)
|
||||
| 6:5 | - | r/- | reserved, read as zero
|
||||
| 4:3 | _A_ | r/w | mode configuration; only OFF (`00`) and NAPOT (`11`) are supported
|
||||
| 2 | _X_ | r/w | execute permission
|
||||
|
|
|
@ -11,7 +11,7 @@ memories, NoCs and other peripherals. On-line and in-system debugging is support
|
|||
compatible on-chip debugger accessible via JTAG.
|
||||
|
||||
The software framework of the processor comes with application makefiles, software libraries for all CPU
|
||||
and processor features, a bootloader, a runtime environment and several example programs – including a port
|
||||
and processor features, a bootloader, a runtime environment and several example programs - including a port
|
||||
of the CoreMark MCU benchmark and the official RISC-V architecture test suite. RISC-V GCC is used as
|
||||
default toolchain (https://github.com/stnolting/riscv-gcc-prebuilt[prebuilt toolchains are also provided]).
|
||||
|
||||
|
|
|
@ -995,7 +995,7 @@ _fast interrupt request_ (see below).
|
|||
==== NEORV32-Specific Fast Interrupt Requests
|
||||
|
||||
As part of the custom/NEORV32-specific CPU extensions, the CPU features 16 fast interrupt request signals
|
||||
(`FIRQ0` – `FIRQ15`). These are reserved for _processor-internal_ modules only (for example for the communication
|
||||
(`FIRQ0` - `FIRQ15`). These are reserved for _processor-internal_ modules only (for example for the communication
|
||||
interfaces to signal "available incoming data" or "ready to send new data").
|
||||
|
||||
The mapping of the 16 FIRQ channels is shown in the following table (the channel number also corresponds to
|
||||
|
@ -1015,9 +1015,9 @@ the according FIRQ priority; 0 = highest, 15 = lowest):
|
|||
| 6 | <<_serial_peripheral_interface_controller_spi,SPI>> | SPI transmission done interrupt
|
||||
| 7 | <<_two_wire_serial_interface_controller_twi,TWI>> | TWI transmission done interrupt
|
||||
| 8 | <<_external_interrupt_controller_xirq,XIRQ>> | External interrupt controller interrupt
|
||||
| 9 | <<_smart_led_interface_neoled,NEOLED>> | NEOLED buffer TX empty / not full interrupt
|
||||
| 10 | <<_stream_link_interface_slink,SLINK>> | RX data received
|
||||
| 11 | <<_stream_link_interface_slink,SLINK>> | TX data send
|
||||
| 9 | <<_smart_led_interface_neoled,NEOLED>> | NEOLED TX buffer interrupt
|
||||
| 10 | <<_stream_link_interface_slink,SLINK>> | RX data buffer interrupt
|
||||
| 11 | <<_stream_link_interface_slink,SLINK>> | TX data buffer interrupt
|
||||
| 12:15 | - | _reserved_, will never fire
|
||||
|=======================
|
||||
|
||||
|
@ -1037,9 +1037,9 @@ as long as the interrupt-causing device's state fulfills it's interrupt conditio
|
|||
The NEORV32 Processor provides a 32-bit / 4GB (physical) address space
|
||||
By default, this address space is divided into five main regions:
|
||||
|
||||
1. **Instruction address space** – memory address space for instructions (=code) and constants.
|
||||
1. **Instruction address space** - memory address space for instructions (=code) and constants.
|
||||
A configurable section of this address space is used by the internal/external _instruction memory_ (<<_mem_int_imem_size>> for the internal IMEM).
|
||||
2. **Data address space** – memory address space for application runtime data (heap, stack, etc.).
|
||||
2. **Data address space** - memory address space for application runtime data (heap, stack, etc.).
|
||||
A configurable section of this address space is used by the internal/external _data memory_ (<<_mem_int_dmem_size>> for the internal DMEM).
|
||||
3. **Bootloader address space**. A _fixed_ section of this address space is used by the
|
||||
internal _bootloader memory_ (BOOTLDROM).
|
||||
|
@ -1102,7 +1102,7 @@ are _aligned_ to a 4-byte boundary.
|
|||
[NOTE]
|
||||
The base address of the internal bootloader (at _0xFFFF0000_) and the internal IO region (at _0xFFFFFE00_) for
|
||||
peripheral devices are also defined in the package and are fixed. These address regions cannot not be used for other
|
||||
applications – even if the bootloader or all IO devices are not implemented - without modifying the core's
|
||||
applications - even if the bootloader or all IO devices are not implemented - without modifying the core's
|
||||
hardware sources.
|
||||
|
||||
|
||||
|
@ -1113,13 +1113,13 @@ The processor setup defines fixed attributes for the four processor-internal add
|
|||
Accessing a memory region in a way that violates any of these attributes will raise an according
|
||||
access exception..
|
||||
|
||||
* `r` – read access (from CPU data access interface, "loads")
|
||||
* `w` – write access (from CPU data access interface, "stores")
|
||||
* `x` – execute access (from CPU instruction fetch interface)
|
||||
* `a` – atomic access (from CPU data access interface)
|
||||
* `8` – byte (8-bit)-accessible (when writing)
|
||||
* `16` – half-word (16-bit)-accessible (when writing)
|
||||
* `32` – word (32-bit)-accessible (when writing)
|
||||
* `r` - read access (from CPU data access interface, "loads")
|
||||
* `w` - write access (from CPU data access interface, "stores")
|
||||
* `x` - execute access (from CPU instruction fetch interface)
|
||||
* `a` - atomic access (from CPU data access interface)
|
||||
* `8` - byte (8-bit)-accessible (when writing)
|
||||
* `16` - half-word (16-bit)-accessible (when writing)
|
||||
* `32` - word (32-bit)-accessible (when writing)
|
||||
|
||||
[NOTE]
|
||||
Read accesses (loads and instruction fetches) can always access data in
|
||||
|
@ -1267,7 +1267,7 @@ system implements an internal reset generator and a global clock generator/divid
|
|||
|
||||
**Internal Reset Generator**
|
||||
|
||||
Most processor-internal modules – except for the CPU and the watchdog timer – do not have a dedicated
|
||||
Most processor-internal modules - except for the CPU and the watchdog timer - do not have a dedicated
|
||||
reset signal. However, all devices can be reset by software by clearing the corresponding unit's control
|
||||
register. The automatically included application start-up code (`crt0.S`) will perform a software-reset of all
|
||||
modules to ensure a clean system reset state.
|
||||
|
|
|
@ -29,8 +29,8 @@ beginning of the instruction memory space (default `ispace_base_c` = 0x00000000)
|
|||
|
||||
By default, the IMEM is implemented as RAM, so the content can be modified during run time. This is
|
||||
required when using a bootloader that can update the content of the IMEM at any time. If you do not need
|
||||
the bootloader anymore – since your application development has completed and you want the program to
|
||||
permanently reside in the internal instruction memory – the IMEM is automatically implemented as _pre-intialized_
|
||||
the bootloader anymore - since your application development has completed and you want the program to
|
||||
permanently reside in the internal instruction memory - the IMEM is automatically implemented as _pre-intialized_
|
||||
ROM when the processor-internal bootloader is disabled (_INT_BOOTLOADER_EN_ = _false_).
|
||||
|
||||
When the IMEM is implemented as ROM, it will be initialized during synthesis with the actual application
|
||||
|
|
|
@ -26,8 +26,8 @@ If the processor-internal **MTIME unit is NOT implemented**, the top's `mtime_i`
|
|||
and the `MTI` machine timer CPU interrupt (`MTI`) is directly connected to the top's `mtime_irq_i` input.
|
||||
|
||||
The 64-bit system time can be accessed via the `TIME_LO` and `TIME_HI` memory-mapped registers (read/write) and also via
|
||||
the CPU's `time[h]` CSRs (read-only). A 64-bit time compare register – accessible via memory-mapped `TIMECMP_LO` and `TIMECMP_HI`
|
||||
registers – is used to configure an interrupt to the CPU. The interrupt is triggered
|
||||
the CPU's `time[h]` CSRs (read-only). A 64-bit time compare register - accessible via memory-mapped `TIMECMP_LO` and `TIMECMP_HI`
|
||||
registers - is used to configure an interrupt to the CPU. The interrupt is triggered
|
||||
whenever `TIME` (high & low part) >= `TIMECMP` (high & low part) and is directly forwarded to the CPU's `MTI` interrupt.
|
||||
The interrupt remain active (=pending) until `TIME` < `TIMECMP` (either by modifying `TIME` or `TIMECMP`).
|
||||
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
The SYSINFO allows the application software to determine the setting of most of the processor's top entity
|
||||
generics that are related to processor/SoC configuration. All registers of this unit are read-only.
|
||||
|
||||
This device is always implemented – regardless of the actual hardware configuration. The bootloader as well
|
||||
This device is always implemented - regardless of the actual hardware configuration. The bootloader as well
|
||||
as the NEORV32 software runtime environment require information from this device (like memory layout
|
||||
and default clock speed) for correct operation.
|
||||
|
||||
|
|
|
@ -16,9 +16,9 @@
|
|||
|
||||
**Theory of Operation**
|
||||
|
||||
The two wire interface – also called "I²C" – is a quite famous interface for connecting several on-board
|
||||
The two wire interface - also called "I²C" - is a quite famous interface for connecting several on-board
|
||||
components. Since this interface only needs two signals (the serial data line `twi_sda_io` and the serial
|
||||
clock line `twi_scl_io`) – despite of the number of connected devices – it allows easy interconnections of
|
||||
clock line `twi_scl_io`) - despite of the number of connected devices - it allows easy interconnections of
|
||||
several peripheral nodes.
|
||||
|
||||
The NEORV32 TWI implements a **TWI controller**. It features "clock stretching" (if enabled via the control
|
||||
|
|
|
@ -64,7 +64,7 @@ received data are indicated via the _UART_DATA_PERR_ flag in the _UART_DATA_ reg
|
|||
received character. A frame error in the received data (i.e. stop bit is not set) is indicated via the
|
||||
_UART_DATA_FERR_ flag in the `DATA`. This flag is also updated with each new received character
|
||||
|
||||
**Hardware Flow Control – RTS/CTS**
|
||||
**Hardware Flow Control - RTS/CTS**
|
||||
|
||||
The UART supports hardware flow control using the standard CTS (clear to send) and/or RTS (ready to send
|
||||
/ ready to receive "RTR") signals. Both hardware control flow mechanisms can be individually enabled.
|
||||
|
@ -92,7 +92,7 @@ Signal changes on `uart0_cts_i` during an active transmission are ignored. Appli
|
|||
the current state of the `uart0_cts_o` input signal via the _UART_CTRL_CTS_ control register flag.
|
||||
|
||||
[TIP]
|
||||
Please note that – just like the RXD and TXD signals – the RTS and CTS signals have to be **cross**-coupled
|
||||
Please note that - just like the RXD and TXD signals - the RTS and CTS signals have to be **cross**-coupled
|
||||
between devices.
|
||||
|
||||
**Interrupts**
|
||||
|
@ -106,7 +106,7 @@ request is cleared by fetching the available data or by disabling the UART.
|
|||
If the UART0 is not implemented, the UART0 interrupts are permanently tied to zero.
|
||||
|
||||
[NOTE]
|
||||
The UART's RX interrupt is always triggered when a new data word has arrived – regardless of the
|
||||
The UART's RX interrupt is always triggered when a new data word has arrived - regardless of the
|
||||
state of the RX double-buffer.
|
||||
|
||||
**Simulation Mode**
|
||||
|
@ -183,7 +183,7 @@ section https://stnolting.github.io/neorv32/ug/#_simulating_the_processor[Simula
|
|||
|
||||
The secondary UART (UART1) is functional identical to the primary UART (<<_primary_universal_asynchronous_receiver_and_transmitter_uart0>>).
|
||||
Obviously, UART1 has different addresses for
|
||||
the control register (`CTRL`) and the data register (`DATA`) – see the register map below. However, the
|
||||
the control register (`CTRL`) and the data register (`DATA`) - see the register map below. However, the
|
||||
register bits/flags use the same bit positions and naming. Furthermore, the "RX done" and "TX done" interrupts are
|
||||
mapped to different CPU fast interrupt channels.
|
||||
|
||||
|
|
|
@ -64,7 +64,7 @@ a| image::wishbone_pipelined_write.png[700,300]
|
|||
|
||||
[TOP]
|
||||
A detailed description of the implemented Wishbone bus protocol and the according interface signals
|
||||
can be found in the data sheet "Wishbone B4 – WISHBONE System-on-Chip (SoC) Interconnection
|
||||
can be found in the data sheet "Wishbone B4 - WISHBONE System-on-Chip (SoC) Interconnection
|
||||
Architecture for Portable IP Cores". A copy of this document can be found in the docs folder of this
|
||||
project.
|
||||
|
||||
|
|
|
@ -38,12 +38,12 @@ toolchains for several target ISAs.
|
|||
.Configuring GCC build for `rv32i` (minimal ISA)
|
||||
[source,bash]
|
||||
----
|
||||
riscv-gnu-toolchain$ ./configure --prefix=/opt/riscv --with-arch=rv32i –-with-abi=ilp32
|
||||
riscv-gnu-toolchain$ ./configure --prefix=/opt/riscv --with-arch=rv32i --with-abi=ilp32
|
||||
riscv-gnu-toolchain$ make
|
||||
----
|
||||
|
||||
[IMPORTANT]
|
||||
Keep in mind that – for instance – a toolchain build with `--with-arch=rv32imc` only provides library code compiled with
|
||||
Keep in mind that - for instance - a toolchain build with `--with-arch=rv32imc` only provides library code compiled with
|
||||
compressed (`C`) and `mul`/`div` instructions (`M`)! Hence, this code cannot be executed (without
|
||||
emulation) on an architecture without these extensions!
|
||||
|
||||
|
@ -196,8 +196,8 @@ provide a minimal set of configuration generics, that might have to be adapted t
|
|||
<3> Default size of internal data memory: 8kB
|
||||
|
||||
[start=7]
|
||||
. If you feel like it – or if your FPGA does not provide sufficient resources – you can modify the
|
||||
_memory sizes_ (`MEM_INT_IMEM_SIZE` and `MEM_INT_DMEM_SIZE` – marked with notes "2" and "3"). But as mentioned
|
||||
. If you feel like it - or if your FPGA does not provide sufficient resources - you can modify the
|
||||
_memory sizes_ (`MEM_INT_IMEM_SIZE` and `MEM_INT_DMEM_SIZE` - marked with notes "2" and "3"). But as mentioned
|
||||
above, let's keep things simple at first and use the standard configuration for now.
|
||||
. There is one generic that _has to be set according to your FPGA board_ setup: the actual clock frequency
|
||||
of the top's clock input signal (`clk_i`). Use the `CLOCK_FREQUENCY` generic to specify your clock source's
|
||||
|
@ -205,7 +205,7 @@ frequency in Hertz (Hz).
|
|||
|
||||
[NOTE]
|
||||
If you have changed the default memory configuration (`MEM_INT_IMEM_SIZE` and `MEM_INT_DMEM_SIZE` generics)
|
||||
keep those new sizes in mind – these values are required for setting
|
||||
keep those new sizes in mind - these values are required for setting
|
||||
up the software framework in the next section <<_general_software_framework_setup>>.
|
||||
|
||||
[start=9]
|
||||
|
@ -249,7 +249,7 @@ or _inside_ the test setup if this is your top entity (low-active LEDs example:
|
|||
|
||||
[start=10]
|
||||
. Attach the clock input `clk_i` to your clock source and connect the reset line `rstn_i` to a button of
|
||||
your FPGA board. Check whether it is low-active or high-active – the reset signal of the processor is
|
||||
your FPGA board. Check whether it is low-active or high-active - the reset signal of the processor is
|
||||
**low-active**, so maybe you need to invert the input signal.
|
||||
. If possible, connected _at least_ bit `0` of the GPIO output port `gpio_o` to a LED (see "Signal Polarity" note above).
|
||||
. Finally, if your are using the UART-based test setup (`neorv32_testsetup_bootloader.vhd`)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue