Execute stage
The execute stage mainly do the following things:
- Executes the ALU.
- Resolves the branch misprediction.
It can be decomposed into combinators as follows (code):
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.
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):
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):
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):
- 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):
- Creates a pipelined stage before executing the ALU.
- Sends a ready signal which indicates it will be free in the next cycle.
M2 (map):
- Executes the ALU.
M3 (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):
- Attaches the ALU output to the payload.
- Filters out the payload when the redirection happens.