-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
51 changed files
with
38,634 additions
and
734 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,116 @@ | ||
# Decode stage | ||
|
||
The decode stage mainly do the following things: | ||
|
||
1. Decodes the instruction. | ||
2. Reads the value of source registers. | ||
|
||
It can be decomposed into combinators as follows ([code](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/decode.rs)): | ||
|
||
<p align="center"> | ||
<img src="../../figure/cpu-implementation-decode.svg" width=95% /> | ||
</p> | ||
|
||
## Input and Output | ||
|
||
The IO interface type of the decode stage is as follows: | ||
|
||
### Ingress | ||
|
||
It takes an ingress interface with type `I<VrH<FetEP, DecR>, { Dep::Demanding }>`. | ||
|
||
You can check the explanation of `FetEP` and `DecR` in [here](fetch.md#egress). | ||
|
||
### Egress | ||
|
||
It returns an egress interface with type `I<VrH<DecEP, ExeR>, { Dep::Demanding }>`. | ||
|
||
Each of `DecEP` and `ExeR` is defined as a struct with the following fields: | ||
|
||
**DecEP** (in [decode.rs](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/decode.rs)): | ||
|
||
- `wb_info`: Writeback information which contains the writeback address and selector. | ||
- `br_info`: Branch information which contains the branch type, target address' base and offset. | ||
- `alu_input`: ALU input. | ||
- `mem_info`: Memory information. | ||
- `csr_info`: CSR information. | ||
- `is_illegal`: Indicates that the instruction is illegal or not. | ||
- `pc`: PC. | ||
- `debug_inst`: Instruction (for debugging purpose). | ||
|
||
**ExeR** (in [exe.rs](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/exe.rs)): | ||
|
||
- `bypass_from_exe`: Bypassed data from the execute stage. | ||
- `bypass_from_mem`: Bypassed data from the memory stage. | ||
- `bypass_from_wb`: Bypassed data from the writeback stage. | ||
- `stall`: Destination register address of load or CSR instruction in the execute stage. | ||
- `redirect`: Redirection PC. | ||
- `rf`: Register file. | ||
|
||
## Behavior | ||
|
||
Each combinator do the following things: | ||
|
||
**M0** ([`map_resolver_inner`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map_resolver_inner)): | ||
|
||
- Constructs the ingress resolver of the decode stage. | ||
|
||
**M1** ([`reg_fwd`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.reg_fwd)): | ||
|
||
- Creates a pipelined stage before decoding the instruction. | ||
- Sends a ready signal which indicates it will be free in the next cycle. | ||
|
||
**M2** ([`map`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map-1)): | ||
|
||
- Decodes the instruction. | ||
|
||
**M3** ([`map_resolver_block`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map_resolver_block)): | ||
|
||
- Stalls until the value of source registers are visible. | ||
|
||
**M4** ([`filter_map_drop_with_r`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.filter_map_drop_with_r)): | ||
|
||
- Reads the value of source registers and attaches them to the payload. | ||
- Filters out the payload when the redirection happens. | ||
|
||
<!-- | ||
<p align="center"> | ||
<img src="../../figure/decode.drawio.svg" /> | ||
</p> | ||
**Calculate Ingress Resolver for Fetch Stage** | ||
* Calculate the resolver from decode stage to fetch stage. | ||
* Resolvers from later stages will be used here to calculate `pc_sel` and `if_kill` | ||
<p align="center"> | ||
<img src="../../figure/decode_gen_resolver.drawio.svg" /> | ||
</p> | ||
**Store The Instruction Memory Response and Decode The Instruction** | ||
* We store the `imem` response into the latch. | ||
* We decode the current `imem` response and calculate the instruction. | ||
<p align="center"> | ||
<img src="../../figure/store_decode.drawio.svg" /> | ||
</p> | ||
**Stall the Payload and Pass Back The Instruction** | ||
* We need to stall the payload if certain certain hazards happen. | ||
* We need to pass back the decoded instruction to previous combinators for calculating resolver. | ||
<p align="center"> | ||
<img src="../../figure/stall_pass_back.drawio.svg" /> | ||
</p> | ||
**Calculate the Egress Payload for Execution Stage** | ||
* Calculate the payload for execution stage. | ||
* Drop the payload if certain hazards happen. | ||
<p align="center"> | ||
<img src="../../figure/decode_ep.drawio.svg" /> | ||
</p> | ||
--> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,127 @@ | ||
# Execute stage | ||
|
||
The execute stage mainly do the following things: | ||
|
||
1. Executes the ALU. | ||
2. Resolves the branch misprediction. | ||
|
||
It can be decomposed into combinators as follows ([code](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/exe.rs)): | ||
|
||
<p align="center"> | ||
<img src="../../figure/cpu-implementation-exe.svg" width=95% /> | ||
</p> | ||
|
||
## Input and Output | ||
|
||
The IO interface type of the execute stage is as follows: | ||
|
||
### Ingress | ||
|
||
It takes an ingress interface with type `I<VrH<DecEP, ExeR>, { Dep::Demanding }>`. | ||
|
||
You can check the explanation of `DecEP` and `ExeR` in [here](decode.md#egress). | ||
|
||
### Egress | ||
|
||
It returns an egress interface with type `I<VrH<ExeEP, MemR>, { Dep::Demanding }>`. | ||
|
||
Each of `ExeEP` and `MemR` is defined as a struct with the following fields: | ||
|
||
**ExeEP** (in [exe.rs](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/exe.rs)): | ||
|
||
- `wb_info`: Writeback information which contains the writeback address and selector. | ||
- `alu_out`: ALU output. | ||
- `mem_info`: Memory information. | ||
- `csr_info`: CSR information. | ||
- `is_illegal`: Indicates that the instruction is illegal or not. | ||
- `pc`: PC. | ||
- `debug_inst`: Instruction (for debugging purpose). | ||
|
||
**MemR** (in [mem.rs](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/mem.rs)): | ||
|
||
- `bypass_from_mem`: Bypassed data from the memory stage. | ||
- `bypass_from_wb`: Bypassed data from the writeback stage. | ||
- `redirect`: Redirection PC. | ||
- `rf`: Register file. | ||
|
||
## Behavior | ||
|
||
Each combinator do the following things: | ||
|
||
**M0** ([`map_resolver_inner`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map_resolver_inner)): | ||
|
||
- Resolves the branch misprediction based on the branch type and ALU output. | ||
- Constructs the ingress resolver of the execute stage. | ||
+ Attaches the bypassed data, stall, and redirection PC for resolving data hazards. | ||
|
||
**M1** ([`reg_fwd`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.reg_fwd)): | ||
|
||
- Creates a pipelined stage before executing the ALU. | ||
- Sends a ready signal which indicates it will be free in the next cycle. | ||
|
||
**M2** ([`map`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map-1)): | ||
|
||
- Executes the ALU. | ||
|
||
**M3** ([`map_resolver_block_with_p`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map_resolver_block_with_p)): | ||
|
||
- Attaches the ALU output to the resolver signal for the redirection PC calculation. | ||
- Stalls until the data hazards have been resolved. | ||
|
||
**M4** ([`filter_map_drop_with_r_inner`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.filter_map_drop_with_r_inner)): | ||
|
||
- Attaches the ALU output to the payload. | ||
- Filters out the payload when the redirection happens. | ||
|
||
<!-- | ||
The execution stage executes instruction from the decode stage, | ||
calculates the payload passing to the memory stage, | ||
and also calculates the resolver passing to the decode stage. | ||
* The ingress payload is decode stage's egress payload `DecEP`. | ||
* The ingress resolver is the resolvers from execute stage and later stages `(exe_r, mem_r, wb_r)`. | ||
* The egress payload should contain necessary information for the memory stage `exe_ep`. | ||
* The egress resolver contains the resolver from memory stage and write-back stage `(mem_r, wb_r)`. | ||
**Calculate Ingress Resolver for Decode Stage** | ||
* Calculate the execution stage resolver and pass it with `mem_r` and `wb_r` to the decode stage. | ||
<p align="center"> | ||
<img src="../../figure/exe_resolver.drawio.svg" /> | ||
</p> | ||
**Store the Decode Stage Egress Payload** | ||
* Store the `dec_ep` into register for passing back to previous combinators for calculating `exe_r`. | ||
<p align="center"> | ||
<img src="../../figure/exe_latch.drawio.svg" /> | ||
</p> | ||
**Execute The Instruction** | ||
* Execute the instruction and pass the `alu_out` to the next combinator. | ||
<p align="center"> | ||
<img src="../../figure/exe_inst.drawio.svg" /> | ||
</p> | ||
**Stall The Payload and Pass Back The Result of ALU** | ||
* We need to stall the payload if certain certain hazards happen. | ||
* We need to pass back the result of ALU `alu_out` to previous combinators for calculating resolver. | ||
<p align="center"> | ||
<img src="../../figure/stall_exe.drawio.svg" /> | ||
</p> | ||
**Calculate The Payload For Memory Stage** | ||
* Calculate the payload for the memory stage. | ||
* Drop the payload if certain hazards happen. | ||
<p align="center"> | ||
<img src="../../figure/exe_ep.drawio.svg" /> | ||
</p> | ||
--> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,84 @@ | ||
# Fetch stage | ||
|
||
The fetch stage mainly do the following things: | ||
|
||
1. Calculates the next PC for the upcoming instruction. | ||
2. Accesses IMEM to retrieve the instruction bytecode. | ||
|
||
It can be decomposed into combinators as follows ([code](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/fetch.rs)): | ||
|
||
<p align="center"> | ||
<img src="../../figure/cpu-implementation-fetch.svg" width=95% /> | ||
</p> | ||
|
||
## Input and Output | ||
|
||
The IO interface type of the fetch stage is as follows: | ||
|
||
### Ingress | ||
|
||
This is the first stage, it does not take any ingress interface. | ||
|
||
### Egress | ||
|
||
It returns an egress interface with type `I<VrH<FetEP, DecR>, { Dep::Demanding }>`. | ||
|
||
Each of `FetEP` and `DecR` is defined as a struct with the following fields: | ||
|
||
**FetEP** (in [fetch.rs](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/fetch.rs)): | ||
|
||
- `imem_resp`: IMEM response which contains the address (PC) and the data (inst bytecode). | ||
|
||
**DecR** (in [decode.rs](https://github.com/kaist-cp/hazardflow/blob/main/hazardflow-designs/src/cpu/decode.rs)): | ||
|
||
- `redirect`: Represents the redirection PC when the control hazard occurs. | ||
|
||
## Behavior | ||
|
||
Each combinator do the following things: | ||
|
||
**M0** ([`source_drop`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.source_drop)): | ||
|
||
- Forwards the current IMEM response and the redirection PC from the resolver to the payload. | ||
|
||
**M1** ([`filter_map`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.filter_map-1)): | ||
|
||
- Calculates the next PC based on the incoming payload. | ||
+ If the redirection PC exists, go to it. | ||
+ Otherwise, go to the next sequential address (PC + 4). | ||
|
||
**M2** ([`reg_fwd_with_init`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.reg_fwd_with_init)): | ||
|
||
- Creates a pipelined stage before accessing IMEM by storing the next PC in a register. | ||
- When the circuit is reset, it is initialized with the designated start address (`START_ADDR`). | ||
|
||
**M3** ([`map`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map-1) + [`comb`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/interface/trait.Interface.html#method.comb) + [`map`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map-1)): | ||
|
||
- Constructs the IMEM request with `map` combinator. | ||
- Accesses the external IMEM module to fetch the instruction bytecode with `comb` combinator. | ||
+ We use an asynchronous memory for memory, it provide the response in the same cycle. | ||
+ We used [`attach_resolver`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/valid_ready/fn.attach_resolver.html) module combinator to attach additional resolver to the IMEM. | ||
- Deconstructs the IMEM response with `map` combinator. | ||
|
||
**M4** ([`map_resolver_drop_with_p`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.map_resolver_drop_with_p)): | ||
|
||
- Attaches the IMEM response to the resolver signal for the next PC calculation. | ||
- Turns on the ready signal when control hazard occurs to extract the payload from **M2**. | ||
|
||
**M5** ([`filter_map_drop_with_r_inner`](https://kaist-cp.github.io/hazardflow/docs/hazardflow_designs/std/hazard/struct.I.html#method.filter_map_drop_with_r_inner)): | ||
|
||
- Filters out the payload when the redirection happens. | ||
|
||
<!-- | ||
<p align="center"> | ||
<img src="../../figure/nextpc.drawio.svg" /> | ||
</p> | ||
<p align="center"> | ||
<img src="../../figure/store_extract_pc.drawio.svg" /> | ||
</p> | ||
<p align="center"> | ||
<img src="../../figure/req_imem.drawio.svg" /> | ||
</p> | ||
--> |
Oops, something went wrong.