OpenCores
URL https://opencores.org/ocsvn/steelcore/steelcore/trunk

Subversion Repositories steelcore

[/] [docs/] [details.md] - Blame information for rev 11

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 11 rafaelcalc
# Implementation details
2
 
3
This section contains information on implementation details. It is intended for those who want to know more about how Steel works.
4
 
5
## Implemented CSRs
6
 
7
The control and status registers implemented in Steel are shown in table 1, below. Other M-mode registers not shown in the table return the hardwired value defined by the RISC-V specifications when read.
8
 
9

10
Table 1. Implemented CSRs
11

12
 
13
| **CSR**            | **Name**                             | **Address** |
14
| :----------------- | :----------------------------------- | ----------: |
15
| cycle              | *Cycle Counter*                      | 0xC00       |
16
| time               | *System Timer*                       | 0xC01       |
17
| instret            | *Instructions Retired*               | 0xC02       |
18
| mstatus            | *Machine Status*                     | 0x300       |
19
| misa               | *Machine ISA*                        | 0x301       |
20
| mie                | *Machine Interrupt Enable*           | 0x304       |
21
| mtvec              | *Machine Trap Vector*                | 0x305       |
22
| mscratch           | *Machine Scratch*                    | 0x340       |
23
| mepc               | *Machine Exception Program Counter*  | 0x341       |
24
| mcause             | *Machine Cause*                      | 0x342       |
25
| mtval              | *Machine Trap Value*                 | 0x343       |
26
| mip                | *Machine Interrupt Pending*          | 0x344       |
27
| mcycle             | *Machine Cycle Counter*              | 0xB00       |
28
| minstret           | *Machine Instructions Retired*       | 0xB01       |
29
| mcountinhibit      | *Machine Counter Inhibit*            | 0x320       |
30
 
31
## Modules
32
 
33
### Decoder
34
 
35
The Decoder (**decoder.v**) decodes the instruction and generates the signals that control the memory, the Load Unit, the Store Unit, the ALU, the two register files (Integer and CSR), the Immediate Generator and the Writeback Multiplexer. The description of its input and output signals are shown in table 2, below.
36
 
37

38
Table 2. Decoder input/output signals
39

40
 
41
| **Signal name**                       | **Width**  | **Direction**  | **Description**                                                                                                       |
42
| :------------------------------------ | :--------- | :------------- | :-------------------------------------------------------------------------------------------------------------------- |
43
| **OPCODE\_6\_TO\_2**                     | 5 bits     | Input          | Connected to the instruction *opcode* field.                                                                          |
44
| **FUNCT7\_5**                          | 1 bit      | Input          | Connected to the instruction *funct7* field.                                                                          |
45
| **FUNCT3**                            | 3 bits     | Input          | Connected to the instruction *funct3* field.                                                                          |
46
| **IADDER\_OUT\_1\_TO\_0**                 | 2 bits     | Input          | Used to verify the alignment of loads and stores.                                                                     |
47
| **TRAP\_TAKEN**                        | 1 bit      | Input          | When set high indicates that a trap will be taken in the next clock cycle. Connected to the Machine Control module.       |
48
| **ALU\_OPCODE**                        | 4 bits     | Output         | Selects the operation to be performed by the ALU.                                     |
49
| **MEM\_WR\_REQ**                        | 1 bit      | Output         | When set high indicates a request to write to memory.                                                                     |
50
| **LOAD\_SIZE**                         | 2 bits     | Output         | Indicates the word size of load instruction. |
51
| **LOAD\_UNSIGNED**                     | 1 bit      | Output         | Indicates the type of load instruction (signed or unsigned).  |
52
| **ALU\_SRC**                           | 1 bit      | Output         | Selects the ALU 2nd operand.                                                                                          |
53
| **IADDER\_SRC**                        | 1 bit      | Output         | Selects the Immediate Adder 2nd operand.                                                                              |
54
| **CSR\_WR\_EN**                         | 1 bit      | Output         | Controls the WR\_EN input of CSR Register File.                                                                        |
55
| **RF\_WR\_EN**                          | 1          | Output         | Controls the WR\_EN input of Integer Register File.  |
56
| **WB\_MUX\_SEL**                        | 3          | Output         | Selects the data to be written in the Integer Register File.                                                          |
57
| **IMM\_TYPE**                          | 3          | Output         | Selects the immediate based on the type of the instruction.                                                           |
58
| **CSR\_OP**                            | 3          | Output         | Selects the operation to be performed by the CSR Register File (read/write, set or clear).                            |
59
| **ILLEGAL\_INSTR**                     | 1 bit      | Output         | When set high indicates that an invalid or not implemented instruction was fetched from memory.                           |
60
| **MISALIGNED\_LOAD**                   | 1 bit      | Output         | When set high indicates an attempt to read data in disagreement with the memory alignment rules.  |
61
| **MISALIGNED\_STORE**                  | 1 bit      | Output         | When set high indicates an attempt to write data to memory in disagreement with the memory alignment rules.  |
62
 
63
### ALU
64
 
65
The ALU (**alu.v**) applies ten distinct logical and arithmetic operations in parallel to two 32-bit operands, outputting the result selected by **OPCODE**. The ALU input/output signals and the opcodes are shown in tables 3 and 4, below.
66
 
67
The opcode values were assigned to facilitate instruction decoding. The most significant bit of **OPCODE** matches with the second most significant bit in the instruction **funct7** field. The remaining three bits match with the instruction **funct3** field.
68
 
69

70
Table 3. ALU input/output signals
71

72
 
73
| **Signal name**            | **Width**  | **Direction**  | **Description**                                                                                                    |
74
| :------------------------- | :--------- | :------------- | :----------------------------------------------------------------------------------------------------------------- |
75
| **OP\_1**                   | 32 bits    | Input          | Operation first operand.                                                                                           |
76
| **OP\_2**                   | 32 bits    | Input          | Operation second operand.                                                                                          |
77
| **OPCODE**                 | 4 bits     | Input          | Operation code. This signal is driven by *funct7* and *funct3* instruction fields.                                 |
78
| **RESULT**                 | 32 bits    | Output         | Result of the requested operation.                                                                                 |
79
 
80

81
Table 4. ALU opcodes
82

83
 
84
| **Opcode**          | **Operation**             |  **Binary value** |
85
| :------------------ | :------------------------ | :---------------- |
86
| **ALU\_ADD**         | Addition                  | 4'b0000           |
87
| **ALU\_SUB**         | Subtraction               | 4'b1000           |
88
| **ALU\_SLT**         | Set on less than          | 4'b0010           |
89
| **ALU\_SLTU**        | Set on less than unsigned | 4'b0011           |
90
| **ALU\_AND**         | Bitwise logical AND       | 4'b0111           |
91
| **ALU\_OR**          | Bitwise logical OR        | 4'b0110           |
92
| **ALU\_XOR**         | Bitwise logical XOR       | 4'b0100           |
93
| **ALU\_SLL**         | Logical left shift        | 4'b0001           |
94
| **ALU\_SRL**         | Logical right shift       | 4'b0101           |
95
| **ALU\_SRA**         | Arithmetic right shift    | 4'b1101           |
96
 
97
### Integer Register File
98
 
99
The Integer Register File (**integer\_file.v**) has 32 general-purpose registers and supports read and write operations. Reads are requested by pipeline stage 2 and provide data from one or two registers. Writes are requested by stage 3 and put the data coming from the Writeback Multiplexer into the selected register. If stage 3 requests to write to a register being read by stage 2, the data to be written is immediately forwarded to stage 2. Each operation is driven by a distinct set of signals, shown in the tables 5 and 6, below.
100
 
101

102
Table 5. Integer Register File signals for read
103

104
 
105
| **Signal name**        | **Width**  | **Direction**  | **Description**                                                                                                                                                         |
106
| :--------------------- | :--------- | :------------- | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
107
| **RS\_1\_ADDR**          | 5 bits     | Input          | *Register source 1 address*. The data is placed at **RS_1** immediately after an address change.                                                                            |
108
| **RS\_2\_ADDR**          | 5 bits     | Input          | *Register source 2 address*. The data is placed at **RS_2** immediately after an address change.                                                                            |
109
| **RS\_1**               | 32 bits    | Output         | Data read (source 1).                                                                                                                                                   |
110
| **RS\_2**               | 32 bits    | Output         | Data read (source 2).                                                                                                                                                   |
111
 
112

113
Table 6. Integer Register File signals for write
114

115
 
116
| **Signal name**        | **Width**  | **Direction**  | **Description**                                                                                                                                                          |
117
| :--------------------- | :--------- | :------------- | :----------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
118
| **RD\_ADDR**            | 5 bits     | Input          | *Destination register address*.                                                                                                                                          |
119
| **RD**                 | 32 bits    | Input          | Data to be written in the destination register.                                                                                                                          |
120
| **WR\_EN**              | 1 bit      | Input          | *Write enable*. When set high, the data placed on RD is written in the destination register at the next clock rising edge.                                                   |
121
 
122
### Branch Unit
123
 
124
The Branch Unit (**branch\_unit.v**) decides if a branch instruction must be taken or not. It receives two operands from the Integer Register File and, based on the value of *opcode* and *funct3* instruction fields, decides the branch. Jump instructions are interpreted as branches that must always be taken. Internally, the unit realizes just two comparisions, deriving other four from them. Table 7 (below) shows the module input and output signals.
125
 
126

127
Table 7. Branch Unit input/output signals
128

129
 
130
| **Signal name**       | **Width**  | **Direction**  | **Description**                                          |
131
| :-------------------- | :--------- | :------------- | :------------------------------------------------------- |
132
| **OPCODE\_6\_TO\_2**     | 5 bits     | Input          | Connected to the *opcode* instruction field.             |
133
| **FUNCT3**            | 3 bits     | Input          | Connected to the *funct3* instruction field.             |
134
| **RS1**               | 32 bits    | Input          | Connected to the Integer Register File 1st operand source.       |
135
| **RS2**               | 32 bits    | Input          | Connected to the Integer Register File 2nd operand source.       |
136
| **BRANCH\_TAKEN**      | 1 bit      | Output         | High if the branch must be taken, low otherwise.         |
137
 
138
### Load Unit
139
 
140
The Load Unit (**load\_unit.v**) reads the **DATA_IN** input signal and forms a 32-bit value based on the load instruction type (encoded in the *funct3* field). The formed value (placed on **OUTPUT**) can then be written in the Integer Register File. The module input and output signals are shown in table 8. The value of **OUTPUT** is formed as shown in table 9.
141
 
142

143
Table 8. Load Unit input/output signals
144

145
 
146
| **Signal name**              | **Width**  | **Direction**  | **Description**                                                                                                                                            |
147
| :--------------------------- | :--------- | :------------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------- |
148
| **LOAD\_SIZE**                | 2 bits     | Input          | Connected to the two least significant bits of the *funct3* instruction field.                                                                             |
149
| **LOAD\_UNSIGNED**            | 1 bit      | Input          | Connected to the most significant bit of the *funct3* instruction field.                                                                                   |
150
| **DATA\_IN**                  | 32 bits    | Input          | 32-bit word read from memory.                                                                                                                              |
151
| **IADDER\_OUT\_1\_TO\_0**        | 2 bits     | Input          | Indicates the byte/halfword position in **DATA_IN**. Used only with load byte/halfword instructions.                                                           |
152
| **OUTPUT**                   | 32 bits    | Output         | 32-bit value to be written in the Integer Register File.                                                                                                   |
153
 
154

155
Table 9. Load Unit output generation
156

157
 
158
| **LOAD\_SIZE**               | **Effect on OUTPUT**                                                                                                                                                                   |
159
| :-------------------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
160
| **2'b00**                   | The byte in the position indicated by **IADDER_OUT_1_TO_0** is placed on the least significant byte of **OUTPUT**. The upper 24 bits are filled according to the **LOAD_UNSIGNED** signal.         |
161
| **2'b01**                   | The halfword in the position indicated by **IADDER_OUT_1_TO_0** is placed on the least significant halfword of **OUTPUT**. The upper 16 bits are filled according to the **LOAD_UNSIGNED** signal. |
162
| **2'b10**                   | All bits of **DATA_IN** are placed on OUTPUT.                                                                                                                                              |
163
| **2'b11**                   | All bits of **DATA_IN** are placed on OUTPUT.                                                                                                                                              |
164
| **LOAD\_UNSIGNED**           | **Effect on OUTPUT**                                                                                                                                                                   |
165
| **1'b0**                    | The remaining bits of **OUTPUT** are filled with the sign bit.                                                                                                                             |
166
| **1'b1**                    | The remaining bits of **OUTPUT** are filled with zeros.                                                                                                                                    |
167
 
168
### Store Unit
169
 
170
The Store Unit (**store\_unit.v**) drives the signals that interface with memory. It places the data to be written (which can be a byte, halfword or word) in the right position in **DATA_OUT** and sets the value of **WR_MASK** in an appropriate way. Table 10 (below) shows the unit input and output signals.
171
 
172

173
Table 10. Store Unit input/output signals
174

175
 
176
| **Signal name**       | **Width**  | **Direction**  | **Description**                                                                                                                                                           |
177
| :-------------------- | :--------- | :------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
178
| **FUNCT3**            | 3 bits     | Input          | Connected to the *funct3* instruction field. Indicates the data size (byte, halfword or word).                                                                            |
179
| **IADDER\_OUT**        | 32 bits    | Input          | Contains the address (possibly unaligned) where the data must be written.                                                                                                 |
180
| **RS2**               | 32 bits    | Input          | Connected to Integer Register File source 2. Contains the data to be written (possibly in the wrong position).                                                           |
181
| **MEM\_WR\_REQ**        | 1 bit      | Input          | Control signal generated by the Control Unit. When set high indicates a request to write to memory.                                                                           |
182
| **DATA\_OUT**          | 32 bits    | Output         | Contains the data to be written in the right position.                                                                                                                    |
183
| **D\_ADDR**            | 32 bits    | Output         | Contains the address (aligned) where the data must be written.                                                                                                            |
184
| **WR\_MASK**           | 4 bits     | Output         | A bitmask that indicates which bytes of **DATA_OUT** must be written.   |
185
| **WR\_REQ**            | 1 bit      | Output         | When set high indicates a request to write to memory. |
186
 
187
### Immediate Generator
188
 
189
The Immediate Generator (**imm\_generator.v**) rearranges the immediate bits contained in the instruction and, if necessary, sign-extends it to form a 32-bit value. The unit is controlled by the **IMM_TYPE** signal, generated by the Control Unit. Table 11 shows the unit input and output signals.
190
 
191

192
Table 11. Immediate Generator input/output signals
193

194
 
195
| **Signal name**     | **Width**  | **Direction**  | **Description**                                                                                                                                    |
196
| :------------------ | :--------- | :------------- | :------------------------------------------------------------------------------------------------------------------------------------------------- |
197
| **INSTR**           | 25 bits    | Input          | Connected to the instruction bits (32 to 7).                                                                                                       |
198
| **IMM\_TYPE**        | 2 bits     | Input          | Control signal generated by the Control Unit that indicates the type of immediate that must be generated.                                          |
199
| **IMM**             | 32 bits    | Output         | 32-bit generated immediate.                                                                                                                        |
200
 
201
### CSR Register File
202
 
203
The CSR Register File (**csr_file.v**) has the control and status registers required for the implementation of M-mode. Read/write, set and clear operations can be applied to the registers. Table 12 shows the unit input and output signals, except those used for communication with the Machine Control module, which are shown in table 13.
204
 
205

206
Table 12. CSR Register File input/output signals
207

208
 
209
| **Signal name**                | **Width**  | **Direction**  | **Description**                                                                                                                                |
210
| :----------------------------- | :--------- | :------------- | :--------------------------------------------------------------------------------------------------------------------------------------------- |
211
| **WR\_EN**                      | 1 bit      | Input          | *Write enable*. When set high, updates the CSR addressed by **CSR_ADDR** at the next clock rising edge according to the operation selected by **CSR_OP**.  |
212
| **CSR\_ADDR**                   | 12 bits    | Input          | Address of the CSR to read/write/modify.                                                                                                       |
213
| **CSR\_OP**                     | 3 bits     | Input          | Control signal generated by the Control Unit. Selects the operation to be performed (read/write, set, clear or no operation).                  |
214
| **CSR\_UIMM**                   | 5 bits     | Input          | *Unsigned immediate*. Connected to the five least significant bits from the Immediate Generator output.                                        |
215
| **CSR\_DATA\_IN**                | 32 bits    | Input          | In write operations, contains the data to be written. In set or clear operations, contains a bit mask.                                         |
216
| **PC**                         | 32 bits    | Input          | *Program counter* value. Used to update the **mepc** CSR.                                                                                          |
217
| **E\_IRQ**                      | 1 bit      | Input          | *External interrupt request*. Used to update the MEIP bit of **mip** CSR.                                                                          |
218
| **T\_IRQ**                      | 1 bit      | Input          | *Timer interrupt request*. Used to update the MTIP bit of **mip** CSR.                                                                             |
219
| **S\_IRQ**                      | 1 bit      | Input          | *Software interrupt request*. Used to update the MSIP bit of **mip** CSR.                                                                          |
220
| **REAL\_TIME**                  | 64 bits    | Input          | Current value of the real time counter. Used to update the **time** and **timeh** CSRs.                                                                |
221
| **CSR\_DATA\_OUT**               | 32 bits    | Output         | Contains the data read from the CSR addressed by **CSR_ADDR**.                                                                                     |
222
| **EPC\_OUT**                    | 32 bits    | Output         | Current value of the **mepc** CSR.                                                                                                                 |
223
| **TRAP\_ADDRESS**               | 32 bits    | Output         | Address of the trap handler first instruction.                                                                                                 |
224
 
225

226
Table 13. CSR Register File and Machine Control module interface signals
227

228
 
229
| **Signal name**                                                                                                    | **Width**  | **Direction**  | **Description**                                                                                                                                            |
230
| :----------------------------------------------------------------------------------------------------------------- | :--------- | :----------------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------- |
231
| **I\_OR\_E**                                                                                                         | 1 bit      | Input              | *Interrupt or exception*. When set high indicates an interrupt, otherwise indicates an exception. Used to update the most significant bit of **mcause** register.  |
232
| **CAUSE\_IN**                                                                                                       | 4 bits     | Input              | Contains the exception code. Used to update the **mcause** register.                                                                               |
233
| **SET\_CAUSE**                                                                                                      | 1 bit      | Input              | When set high updates the **mcause** register with the values of **I_OR_E** and **CAUSE_IN**.                                                                              |
234
| **SET\_EPC**                                                                                                        | 1 bit      | Input              | When set high, updates the **mepc** register with the value of PC.                                                                                                 |
235
| **INSTRET\_INC**                                                                                                    | 1 bit      | Input              | When set high enables the instructions retired counting.                                                                                                       |
236
| **MIE\_CLEAR**                                                                                                      | 1 bit      | Input              | When set high sets the MIE bit of **mstatus** to zero (which globally disables interrupts). The old value of MIE is saved in the **mstatus** MPIE field.               |
237
| **MIE\_SET**                                                                                                        | 1 bit      | Input              | When set high sets the MPIE bit of **mstatus** to one. The old value of MPIE is saved in the **mstatus** MIE field.                                                    |
238
| **MIE**                                                                                                            | 1 bit      | Output             | Current value of MIE bit of **mstatus** CSR.                                                                                                                   |
239
| **MEIE\_OUT**                                                                                                       | 1 bit      | Output             | Current value of MEIE bit of **mie** CSR.                                                                                                                      |
240
| **MTIE\_OUT**                                                                                                       | 1 bit      | Output             | Current value of MTIE bit of **mie** CSR.                                                                                                                      |
241
| **MSIE\_OUT**                                                                                                       | 1 bit      | Output             | Current value of MSIE bit of **mie** CSR.                                                                                                                      |
242
| **MEIP\_OUT**                                                                                                       | 1 bit      | Output             | Current value of MEIP bit of **mip** CSR.                                                                                                                      |
243
| **MTIP\_OUT**                                                                                                       | 1 bit      | Output             | Current value of MTIP bit of **mip** CSR.                                                                                                                      |
244
| **MSIP\_OUT**                                                                                                       | 1 bit      | Output             | Current value of MSIP bit of **mip** CSR.                                                                                                                      |
245
 
246
### Machine Control
247
 
248
The Machine Control module (**machine_control.v**) implements the M-mode, controlling the the program counter generation and updating several CSRs. It has a special communication interface with the CSR Register File, already shown in table 13 (above). Its input and output signals are shown in table 14 (below).
249
 
250
Internally, the module implements the finite state machine shown in figure 1 (below).
251
 
252

253
Table 14. Machine Control input/output signals
254

255
 
256
| **Signal name**                      | **Width**  | **Direction**  | **Description**                                                                                                                                                   |
257
| :----------------------------------- | :--------- | :------------- | :---------------------------------------------------------------------------------------------------------------------------------------------------------------- |
258
| **ILLEGAL\_INSTR**                    | 1 bit      | Input          | *Illegal instruction*. When set high indicates that an invalid or not implemented instruction was fetched from memory.                                                |
259
| **MISALIGNED\_INSTR**                 | 1 bit      | Input          | *Misaligned instruction*. When set high indicates an attempt to fetch an instruction which address is in disagreement with the memory alignment rules.  |
260
| **MISALIGNED\_LOAD**                  | 1 bit      | Input          | *Misaligned load*. When set high indicates an attempt to read data in disagreement with the memory alignment rules.                                    |
261
| **MISALIGNED\_STORE**                 | 1 bit      | Input          | *Misaligned store*. When set high indicates an attempt to write data to memory in disagreement with the memory alignment rules.                        |
262
| **OPCODE\_6\_TO\_2**                    | 5 bits     | Input          | Value of the *opcode* instruction field.                                                                                                                          |
263
| **FUNCT3**                           | 3 bits     | Input          | Value of the *funct3* instruction field.                                                                                                                          |
264
| **FUNCT7**                           | 7 bits     | Input          | Value of the *funct7* instruction field.                                                                                                                          |
265
| **RS1\_ADDR**                         | 5 bits     | Input          | Value of the *rs1* instruction field.                                                                                                                             |
266
| **RS2\_ADDR**                         | 5 bits     | Input          | Value of the *rs2* instruction field.                                                                                                                             |
267
| **RD\_ADDR**                          | 5 bits     | Input          | Value of the *rd* instruction field.                                                                                                                              |
268
| **E\_IRQ**                            | 1 bit      | Input          | *External interrupt request*.                                                                                                                                     |
269
| **T\_IRQ**                            | 1 bit      | Input          | *Timer interrupt request*.                                                                                                                                        |
270
| **S\_IRQ**                            | 1 bit      | Input          | *Software interrupt request*.                                                                                                                                     |
271
| **PC\_SRC**                           | 2 bit      | Output         | Selects the program counter source.                                                                                                                               |
272
| **FLUSH**                            | 1 bit      | Output         | Flushes the pipeline when set.                                                                                                                                    |
273
| **TRAP\_TAKEN**                       | 1 bit      | Output         | When set high indicates that a trap will be taken in the next clock cycle.                                                                                            |
274
 
275

276
277

278

279
Fig. 1: Machine Control finite state machine
280

281
![Machine Control FSM]()

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.