forked from Github_Repos/cvw
Create module for instruction class prediction and decoding.
This commit is contained in:
parent
86f611577f
commit
3804626166
@ -33,11 +33,11 @@ module RASPredictor #(parameter int StackSize = 16 )(
|
|||||||
input logic clk,
|
input logic clk,
|
||||||
input logic reset,
|
input logic reset,
|
||||||
input logic StallF, StallD, StallE, StallM, FlushD, FlushE, FlushM,
|
input logic StallF, StallD, StallE, StallM, FlushD, FlushE, FlushM,
|
||||||
input logic WrongBPRetD, // Prediction class is wrong
|
input logic WrongBPReturnD, // Prediction class is wrong
|
||||||
input logic RetD,
|
input logic ReturnD,
|
||||||
input logic RetE, JalE, // Instr class
|
input logic ReturnE, CallE, // Instr class
|
||||||
input logic BPRetF,
|
input logic BPReturnF,
|
||||||
input logic [`XLEN-1:0] PCLinkE, // PC of instruction after a jal
|
input logic [`XLEN-1:0] PCLinkE, // PC of instruction after a call
|
||||||
output logic [`XLEN-1:0] RASPCF // Top of the stack
|
output logic [`XLEN-1:0] RASPCF // Top of the stack
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -54,21 +54,21 @@ module RASPredictor #(parameter int StackSize = 16 )(
|
|||||||
logic IncrRepairD, DecRepairD;
|
logic IncrRepairD, DecRepairD;
|
||||||
|
|
||||||
logic DecrementPtr;
|
logic DecrementPtr;
|
||||||
logic FlushedRetDE;
|
logic FlushedReturnDE;
|
||||||
logic WrongPredRetD;
|
logic WrongPredReturnD;
|
||||||
|
|
||||||
|
|
||||||
assign PopF = BPRetF & ~StallD & ~FlushD;
|
assign PopF = BPReturnF & ~StallD & ~FlushD;
|
||||||
assign PushE = JalE & ~StallM & ~FlushM;
|
assign PushE = CallE & ~StallM & ~FlushM;
|
||||||
|
|
||||||
assign WrongPredRetD = (WrongBPRetD) & ~StallE & ~FlushE;
|
assign WrongPredReturnD = (WrongBPReturnD) & ~StallE & ~FlushE;
|
||||||
assign FlushedRetDE = (~StallE & FlushE & RetD) | (~StallM & FlushM & RetE); // flushed ret
|
assign FlushedReturnDE = (~StallE & FlushE & ReturnD) | (~StallM & FlushM & ReturnE); // flushed return
|
||||||
|
|
||||||
assign RepairD = WrongPredRetD | FlushedRetDE ;
|
assign RepairD = WrongPredReturnD | FlushedReturnDE ;
|
||||||
|
|
||||||
assign IncrRepairD = FlushedRetDE | (WrongPredRetD & ~RetD); // Guessed it was a ret, but its not
|
assign IncrRepairD = FlushedReturnDE | (WrongPredReturnD & ~ReturnD); // Guessed it was a return, but its not
|
||||||
|
|
||||||
assign DecRepairD = WrongPredRetD & RetD; // Guessed non ret but is a ret.
|
assign DecRepairD = WrongPredReturnD & ReturnD; // Guessed non return but is a return.
|
||||||
|
|
||||||
assign CounterEn = PopF | PushE | RepairD;
|
assign CounterEn = PopF | PushE | RepairD;
|
||||||
|
|
||||||
|
@ -58,8 +58,8 @@ module bpred (
|
|||||||
input logic [`XLEN-1:0] IEUAdrE, // The branch/jump target address
|
input logic [`XLEN-1:0] IEUAdrE, // The branch/jump target address
|
||||||
input logic [`XLEN-1:0] IEUAdrM, // The branch/jump target address
|
input logic [`XLEN-1:0] IEUAdrM, // The branch/jump target address
|
||||||
input logic [`XLEN-1:0] PCLinkE, // The address following the branch instruction. (AKA Fall through address)
|
input logic [`XLEN-1:0] PCLinkE, // The address following the branch instruction. (AKA Fall through address)
|
||||||
output logic [3:0] InstrClassM, // The valid instruction class. 1-hot encoded as jalr, ret, jr (not ret), j, br
|
output logic [3:0] InstrClassM, // The valid instruction class. 1-hot encoded as call, return, jr (not return), j, br
|
||||||
output logic JumpOrTakenBranchM, // The valid instruction class. 1-hot encoded as jalr, ret, jr (not ret), j, br
|
output logic JumpOrTakenBranchM, // The valid instruction class. 1-hot encoded as call, return, jr (not return), j, br
|
||||||
|
|
||||||
// Report branch prediction status
|
// Report branch prediction status
|
||||||
output logic BPPredWrongE, // Prediction is wrong
|
output logic BPPredWrongE, // Prediction is wrong
|
||||||
@ -88,14 +88,14 @@ module bpred (
|
|||||||
|
|
||||||
logic [`XLEN-1:0] BTAD;
|
logic [`XLEN-1:0] BTAD;
|
||||||
|
|
||||||
logic BTBJalF, BTBRetF, BTBJumpF, BTBBranchF;
|
logic BTBCallF, BTBReturnF, BTBJumpF, BTBBranchF;
|
||||||
logic BPBranchF, BPJumpF, BPRetF, BPJalF;
|
logic BPBranchF, BPJumpF, BPReturnF, BPCallF;
|
||||||
logic BPBranchD, BPJumpD, BPRetD, BPJalD;
|
logic BPBranchD, BPJumpD, BPReturnD, BPCallD;
|
||||||
logic RetD, JalD;
|
logic ReturnD, CallD;
|
||||||
logic RetE, JalE;
|
logic ReturnE, CallE;
|
||||||
logic BranchM, JumpM, RetM, JalM;
|
logic BranchM, JumpM, ReturnM, CallM;
|
||||||
logic BranchW, JumpW, RetW, JalW;
|
logic BranchW, JumpW, ReturnW, CallW;
|
||||||
logic WrongBPRetD;
|
logic WrongBPReturnD;
|
||||||
logic [`XLEN-1:0] PCW, IEUAdrW;
|
logic [`XLEN-1:0] PCW, IEUAdrW;
|
||||||
|
|
||||||
// Part 1 branch direction prediction
|
// Part 1 branch direction prediction
|
||||||
@ -150,71 +150,27 @@ module bpred (
|
|||||||
TargetPredictor(.clk, .reset, .StallF, .StallD, .StallE, .StallM, .StallW, .FlushD, .FlushE, .FlushM, .FlushW,
|
TargetPredictor(.clk, .reset, .StallF, .StallD, .StallE, .StallM, .StallW, .FlushD, .FlushE, .FlushM, .FlushW,
|
||||||
.PCNextF, .PCF, .PCD, .PCE, .PCM, .PCW,
|
.PCNextF, .PCF, .PCD, .PCE, .PCM, .PCW,
|
||||||
.BTAF, .BTAD,
|
.BTAF, .BTAD,
|
||||||
.BTBIClassF({BTBJalF, BTBRetF, BTBJumpF, BTBBranchF}),
|
.BTBIClassF({BTBCallF, BTBReturnF, BTBJumpF, BTBBranchF}),
|
||||||
.PredictionInstrClassWrongM,
|
.PredictionInstrClassWrongM,
|
||||||
.IEUAdrE, .IEUAdrM, .IEUAdrW,
|
.IEUAdrE, .IEUAdrM, .IEUAdrW,
|
||||||
.InstrClassD({JalD, RetD, JumpD, BranchD}), .InstrClassE({JalE, RetE, JumpE, BranchE}), .InstrClassM({JalM, RetM, JumpM, BranchM}),
|
.InstrClassD({CallD, ReturnD, JumpD, BranchD}), .InstrClassE({CallE, ReturnE, JumpE, BranchE}), .InstrClassM({CallM, ReturnM, JumpM, BranchM}),
|
||||||
.InstrClassW({JalW, RetW, JumpW, BranchW}));
|
.InstrClassW({CallW, ReturnW, JumpW, BranchW}));
|
||||||
|
|
||||||
if (!`INSTR_CLASS_PRED) begin : DirectClassDecode
|
|
||||||
// This section is mainly for testing, verification, and PPA comparison.
|
|
||||||
// An alternative to using the BTB to store the instruction class is to partially decode
|
|
||||||
// the instructions in the Fetch stage into, Jal, Ret, Jump, and Branch instructions.
|
|
||||||
// This logic is not described in the text book as of 23 February 2023.
|
|
||||||
logic cjal, cj, cjr, cjalr, CJumpF, CBranchF;
|
|
||||||
logic NCJumpF, NCBranchF;
|
|
||||||
|
|
||||||
if(`C_SUPPORTED) begin
|
icpred icpred(.clk, .reset, .StallF, .StallD, .StallE, .StallM, .StallW, .FlushD, .FlushE, .FlushM, .FlushW,
|
||||||
logic [4:0] CompressedOpcF;
|
.PostSpillInstrRawF, .InstrD, .BranchD, .BranchE, .JumpD, .JumpE, .BranchM, .BranchW, .JumpM, .JumpW,
|
||||||
assign CompressedOpcF = {PostSpillInstrRawF[1:0], PostSpillInstrRawF[15:13]};
|
.CallD, .CallE, .CallM, .CallW, .ReturnD, .ReturnE, .ReturnM, .ReturnW, .BTBCallF, .BTBReturnF, .BTBJumpF, .BTBBranchF,
|
||||||
assign cjal = CompressedOpcF == 5'h09 & `XLEN == 32;
|
.BPCallF, .BPReturnF, .BPJumpF, .BPBranchF, .PredictionInstrClassWrongM, .WrongBPReturnD);
|
||||||
assign cj = CompressedOpcF == 5'h0d;
|
|
||||||
assign cjr = CompressedOpcF == 5'h14 & ~PostSpillInstrRawF[12] & PostSpillInstrRawF[6:2] == 5'b0 & PostSpillInstrRawF[11:7] != 5'b0;
|
|
||||||
assign cjalr = CompressedOpcF == 5'h14 & PostSpillInstrRawF[12] & PostSpillInstrRawF[6:2] == 5'b0 & PostSpillInstrRawF[11:7] != 5'b0;
|
|
||||||
assign CJumpF = cjal | cj | cjr | cjalr;
|
|
||||||
assign CBranchF = CompressedOpcF[4:1] == 4'h7;
|
|
||||||
end else begin
|
|
||||||
assign {cjal, cj, cjr, cjalr, CJumpF, CBranchF} = '0;
|
|
||||||
end
|
|
||||||
|
|
||||||
assign NCJumpF = PostSpillInstrRawF[6:0] == 7'h67 | PostSpillInstrRawF[6:0] == 7'h6F;
|
|
||||||
assign NCBranchF = PostSpillInstrRawF[6:0] == 7'h63;
|
|
||||||
|
|
||||||
assign BPBranchF = NCBranchF | (`C_SUPPORTED & CBranchF);
|
|
||||||
assign BPJumpF = NCJumpF | (`C_SUPPORTED & (CJumpF));
|
|
||||||
assign BPRetF = (NCJumpF & (PostSpillInstrRawF[19:15] & 5'h1B) == 5'h01) | // return must return to ra or r5
|
|
||||||
(`C_SUPPORTED & (cjalr | cjr) & ((PostSpillInstrRawF[11:7] & 5'h1B) == 5'h01));
|
|
||||||
|
|
||||||
assign BPJalF = (NCJumpF & (PostSpillInstrRawF[11:07] & 5'h1B) == 5'h01) | // jal(r) must link to ra or x5
|
|
||||||
(`C_SUPPORTED & (cjal | (cjalr & (PostSpillInstrRawF[11:7] & 5'h1b) == 5'h01)));
|
|
||||||
|
|
||||||
end else begin
|
|
||||||
// This section connects the BTB's instruction class prediction.
|
|
||||||
assign {BPJalF, BPRetF, BPJumpF, BPBranchF} = {BTBJalF, BTBRetF, BTBJumpF, BTBBranchF};
|
|
||||||
end
|
|
||||||
assign BPPCSrcF = (BPBranchF & BPDirPredF[1]) | BPJumpF;
|
assign BPPCSrcF = (BPBranchF & BPDirPredF[1]) | BPJumpF;
|
||||||
|
flopenrc #(1) BPPredWrongMReg(clk, reset, FlushM, ~StallM, BPPredWrongE, BPPredWrongM);
|
||||||
|
|
||||||
// Part 3 RAS
|
// Part 3 RAS
|
||||||
RASPredictor RASPredictor(.clk, .reset, .StallF, .StallD, .StallE, .StallM, .FlushD, .FlushE, .FlushM,
|
RASPredictor RASPredictor(.clk, .reset, .StallF, .StallD, .StallE, .StallM, .FlushD, .FlushE, .FlushM,
|
||||||
.BPRetF, .RetD, .RetE, .JalE,
|
.BPReturnF, .ReturnD, .ReturnE, .CallE,
|
||||||
.WrongBPRetD, .RASPCF, .PCLinkE);
|
.WrongBPReturnD, .RASPCF, .PCLinkE);
|
||||||
|
|
||||||
assign BPPredPCF = BPRetF ? RASPCF : BTAF;
|
assign BPPredPCF = BPReturnF ? RASPCF : BTAF;
|
||||||
|
|
||||||
assign RetD = JumpD & (InstrD[19:15] & 5'h1B) == 5'h01; // return must return to ra or x5
|
|
||||||
assign JalD = JumpD & (InstrD[11:7] & 5'h1B) == 5'h01; // jal(r) must link to ra or x5
|
|
||||||
|
|
||||||
flopenrc #(2) InstrClassRegE(clk, reset, FlushE, ~StallE, {JalD, RetD}, {JalE, RetE});
|
|
||||||
flopenrc #(4) InstrClassRegM(clk, reset, FlushM, ~StallM, {JalE, RetE, JumpE, BranchE}, {JalM, RetM, JumpM, BranchM});
|
|
||||||
flopenrc #(4) InstrClassRegW(clk, reset, FlushM, ~StallW, {JalM, RetM, JumpM, BranchM}, {JalW, RetW, JumpW, BranchW});
|
|
||||||
flopenrc #(1) BPPredWrongMReg(clk, reset, FlushM, ~StallM, BPPredWrongE, BPPredWrongM);
|
|
||||||
|
|
||||||
// branch predictor
|
|
||||||
flopenrc #(1) BPClassWrongRegM(clk, reset, FlushM, ~StallM, AnyWrongPredInstrClassE, PredictionInstrClassWrongM);
|
|
||||||
flopenrc #(1) WrongInstrClassRegE(clk, reset, FlushE, ~StallE, AnyWrongPredInstrClassD, AnyWrongPredInstrClassE);
|
|
||||||
|
|
||||||
// pipeline the predicted class
|
|
||||||
flopenrc #(4) PredInstrClassRegD(clk, reset, FlushD, ~StallD, {BPJalF, BPRetF, BPJumpF, BPBranchF}, {BPJalD, BPRetD, BPJumpD, BPBranchD});
|
|
||||||
|
|
||||||
// Check the prediction
|
// Check the prediction
|
||||||
// if it is a CFI then check if the next instruction address (PCD) matches the branch's target or fallthrough address.
|
// if it is a CFI then check if the next instruction address (PCD) matches the branch's target or fallthrough address.
|
||||||
@ -224,16 +180,13 @@ module bpred (
|
|||||||
// also flush the branch. This will change in a superscaler cpu.
|
// also flush the branch. This will change in a superscaler cpu.
|
||||||
assign PredictionPCWrongE = PCCorrectE != PCD;
|
assign PredictionPCWrongE = PCCorrectE != PCD;
|
||||||
|
|
||||||
// branch class prediction wrong.
|
|
||||||
assign AnyWrongPredInstrClassD = |({BPJalD, BPRetD, BPJumpD, BPBranchD} ^ {JalD, RetD, JumpD, BranchD});
|
|
||||||
assign WrongBPRetD = BPRetD ^ RetD;
|
|
||||||
|
|
||||||
// branch is wrong only if the PC does not match and both the Decode and Fetch stages have valid instructions.
|
// branch is wrong only if the PC does not match and both the Decode and Fetch stages have valid instructions.
|
||||||
assign BPPredWrongE = PredictionPCWrongE & InstrValidE & InstrValidD;
|
assign BPPredWrongE = PredictionPCWrongE & InstrValidE & InstrValidD;
|
||||||
|
|
||||||
|
// *** clean up old signal names for testing.
|
||||||
logic BPPredWrongEAlt;
|
logic BPPredWrongEAlt;
|
||||||
logic NotMatch;
|
logic NotMatch;
|
||||||
assign BPPredWrongEAlt = PredictionPCWrongE & InstrValidE & InstrValidD; // this does not work for cubic benchmark
|
assign BPPredWrongEAlt = PredictionPCWrongE & InstrValidE & InstrValidD;
|
||||||
assign NotMatch = BPPredWrongE != BPPredWrongEAlt;
|
assign NotMatch = BPPredWrongE != BPPredWrongEAlt;
|
||||||
|
|
||||||
// Output the predicted PC or corrected PC on miss-predict.
|
// Output the predicted PC or corrected PC on miss-predict.
|
||||||
@ -263,8 +216,8 @@ module bpred (
|
|||||||
// could be wrong or the fall through address selected for branch predict not taken.
|
// could be wrong or the fall through address selected for branch predict not taken.
|
||||||
// By pipeline the BTB's PC and RAS address through the pipeline we can measure the accuracy of
|
// By pipeline the BTB's PC and RAS address through the pipeline we can measure the accuracy of
|
||||||
// both without the above inaccuracies.
|
// both without the above inaccuracies.
|
||||||
assign BTBPredPCWrongE = (BTAE != IEUAdrE) & (BranchE | JumpE & ~RetE) & PCSrcE;
|
assign BTBPredPCWrongE = (BTAE != IEUAdrE) & (BranchE | JumpE & ~ReturnE) & PCSrcE;
|
||||||
assign RASPredPCWrongE = (RASPCE != IEUAdrE) & RetE & PCSrcE;
|
assign RASPredPCWrongE = (RASPCE != IEUAdrE) & ReturnE & PCSrcE;
|
||||||
|
|
||||||
assign JumpOrTakenBranchE = (BranchE & PCSrcE) | JumpE;
|
assign JumpOrTakenBranchE = (BranchE & PCSrcE) | JumpE;
|
||||||
|
|
||||||
@ -283,7 +236,7 @@ module bpred (
|
|||||||
end
|
end
|
||||||
|
|
||||||
// **** Fix me
|
// **** Fix me
|
||||||
assign InstrClassM = {JalM, RetM, JumpM, BranchM};
|
assign InstrClassM = {CallM, ReturnM, JumpM, BranchM};
|
||||||
flopenr #(`XLEN) PCWReg(clk, reset, ~StallW, PCM, PCW);
|
flopenr #(`XLEN) PCWReg(clk, reset, ~StallW, PCM, PCW);
|
||||||
flopenr #(`XLEN) IEUAdrWReg(clk, reset, ~StallW, IEUAdrM, IEUAdrW);
|
flopenr #(`XLEN) IEUAdrWReg(clk, reset, ~StallW, IEUAdrM, IEUAdrW);
|
||||||
|
|
||||||
|
107
src/ifu/bpred/icpred.sv
Normal file
107
src/ifu/bpred/icpred.sv
Normal file
@ -0,0 +1,107 @@
|
|||||||
|
///////////////////////////////////////////
|
||||||
|
// icpred.sv
|
||||||
|
//
|
||||||
|
// Written: Ross Thomposn ross1728@gmail.com
|
||||||
|
// Created: February 26, 2023
|
||||||
|
// Modified: February 26, 2023
|
||||||
|
//
|
||||||
|
// Purpose: Partial decode of instructions into control flow instructions (cfi)P
|
||||||
|
// Call, Return, Jump, and Branch
|
||||||
|
//
|
||||||
|
// A component of the CORE-V-WALLY configurable RISC-V project.
|
||||||
|
//
|
||||||
|
// Copyright (C) 2021-23 Harvey Mudd College & Oklahoma State University
|
||||||
|
//
|
||||||
|
// SPDX-License-Identifier: Apache-2.0 WITH SHL-2.1
|
||||||
|
//
|
||||||
|
// Licensed under the Solderpad Hardware License v 2.1 (the “License”); you may not use this file
|
||||||
|
// except in compliance with the License, or, at your option, the Apache License version 2.0. You
|
||||||
|
// may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// https://solderpad.org/licenses/SHL-2.1/
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, any work distributed under the
|
||||||
|
// License is distributed on an “AS IS” BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
|
||||||
|
// either express or implied. See the License for the specific language governing permissions
|
||||||
|
// and limitations under the License.
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
`include "wally-config.vh"
|
||||||
|
|
||||||
|
`define INSTR_CLASS_PRED 1
|
||||||
|
|
||||||
|
module icpred (
|
||||||
|
input logic clk, reset,
|
||||||
|
input logic StallF, StallD, StallE, StallM, StallW,
|
||||||
|
input logic FlushD, FlushE, FlushM, FlushW,
|
||||||
|
input logic [31:0] PostSpillInstrRawF, InstrD, // Instruction
|
||||||
|
input logic BranchD, BranchE,
|
||||||
|
input logic JumpD, JumpE,
|
||||||
|
output logic BranchM, BranchW,
|
||||||
|
output logic JumpM, JumpW,
|
||||||
|
output logic CallD, CallE, CallM, CallW,
|
||||||
|
output logic ReturnD, ReturnE, ReturnM, ReturnW,
|
||||||
|
input logic BTBCallF, BTBReturnF, BTBJumpF, BTBBranchF,
|
||||||
|
output logic BPCallF, BPReturnF, BPJumpF, BPBranchF,
|
||||||
|
output logic PredictionInstrClassWrongM, WrongBPReturnD
|
||||||
|
);
|
||||||
|
|
||||||
|
logic AnyWrongPredInstrClassD, AnyWrongPredInstrClassE;
|
||||||
|
logic BPBranchD, BPJumpD, BPReturnD, BPCallD;
|
||||||
|
|
||||||
|
if (!`INSTR_CLASS_PRED) begin : DirectClassDecode
|
||||||
|
// This section is mainly for testing, verification, and PPA comparison.
|
||||||
|
// An alternative to using the BTB to store the instruction class is to partially decode
|
||||||
|
// the instructions in the Fetch stage into, Call, Return, Jump, and Branch instructions.
|
||||||
|
// This logic is not described in the text book as of 23 February 2023.
|
||||||
|
logic ccall, cj, cjr, ccallr, CJumpF, CBranchF;
|
||||||
|
logic NCJumpF, NCBranchF;
|
||||||
|
|
||||||
|
if(`C_SUPPORTED) begin
|
||||||
|
logic [4:0] CompressedOpcF;
|
||||||
|
assign CompressedOpcF = {PostSpillInstrRawF[1:0], PostSpillInstrRawF[15:13]};
|
||||||
|
assign ccall = CompressedOpcF == 5'h09 & `XLEN == 32;
|
||||||
|
assign cj = CompressedOpcF == 5'h0d;
|
||||||
|
assign cjr = CompressedOpcF == 5'h14 & ~PostSpillInstrRawF[12] & PostSpillInstrRawF[6:2] == 5'b0 & PostSpillInstrRawF[11:7] != 5'b0;
|
||||||
|
assign ccallr = CompressedOpcF == 5'h14 & PostSpillInstrRawF[12] & PostSpillInstrRawF[6:2] == 5'b0 & PostSpillInstrRawF[11:7] != 5'b0;
|
||||||
|
assign CJumpF = ccall | cj | cjr | ccallr;
|
||||||
|
assign CBranchF = CompressedOpcF[4:1] == 4'h7;
|
||||||
|
end else begin
|
||||||
|
assign {ccall, cj, cjr, ccallr, CJumpF, CBranchF} = '0;
|
||||||
|
end
|
||||||
|
|
||||||
|
assign NCJumpF = PostSpillInstrRawF[6:0] == 7'h67 | PostSpillInstrRawF[6:0] == 7'h6F;
|
||||||
|
assign NCBranchF = PostSpillInstrRawF[6:0] == 7'h63;
|
||||||
|
|
||||||
|
assign BPBranchF = NCBranchF | (`C_SUPPORTED & CBranchF);
|
||||||
|
assign BPJumpF = NCJumpF | (`C_SUPPORTED & (CJumpF));
|
||||||
|
assign BPReturnF = (NCJumpF & (PostSpillInstrRawF[19:15] & 5'h1B) == 5'h01) | // returnurn must returnurn to ra or r5
|
||||||
|
(`C_SUPPORTED & (ccallr | cjr) & ((PostSpillInstrRawF[11:7] & 5'h1B) == 5'h01));
|
||||||
|
|
||||||
|
assign BPCallF = (NCJumpF & (PostSpillInstrRawF[11:07] & 5'h1B) == 5'h01) | // call(r) must link to ra or x5
|
||||||
|
(`C_SUPPORTED & (ccall | (ccallr & (PostSpillInstrRawF[11:7] & 5'h1b) == 5'h01)));
|
||||||
|
|
||||||
|
end else begin
|
||||||
|
// This section connects the BTB's instruction class prediction.
|
||||||
|
assign {BPCallF, BPReturnF, BPJumpF, BPBranchF} = {BTBCallF, BTBReturnF, BTBJumpF, BTBBranchF};
|
||||||
|
end
|
||||||
|
|
||||||
|
assign ReturnD = JumpD & (InstrD[19:15] & 5'h1B) == 5'h01; // returnurn must returnurn to ra or x5
|
||||||
|
assign CallD = JumpD & (InstrD[11:7] & 5'h1B) == 5'h01; // call(r) must link to ra or x5
|
||||||
|
|
||||||
|
flopenrc #(2) InstrClassRegE(clk, reset, FlushE, ~StallE, {CallD, ReturnD}, {CallE, ReturnE});
|
||||||
|
flopenrc #(4) InstrClassRegM(clk, reset, FlushM, ~StallM, {CallE, ReturnE, JumpE, BranchE}, {CallM, ReturnM, JumpM, BranchM});
|
||||||
|
flopenrc #(4) InstrClassRegW(clk, reset, FlushM, ~StallW, {CallM, ReturnM, JumpM, BranchM}, {CallW, ReturnW, JumpW, BranchW});
|
||||||
|
|
||||||
|
// branch predictor
|
||||||
|
flopenrc #(1) BPClassWrongRegM(clk, reset, FlushM, ~StallM, AnyWrongPredInstrClassE, PredictionInstrClassWrongM);
|
||||||
|
flopenrc #(1) WrongInstrClassRegE(clk, reset, FlushE, ~StallE, AnyWrongPredInstrClassD, AnyWrongPredInstrClassE);
|
||||||
|
|
||||||
|
// pipeline the predicted class
|
||||||
|
flopenrc #(4) PredInstrClassRegD(clk, reset, FlushD, ~StallD, {BPCallF, BPReturnF, BPJumpF, BPBranchF}, {BPCallD, BPReturnD, BPJumpD, BPBranchD});
|
||||||
|
|
||||||
|
// branch class prediction wrong.
|
||||||
|
assign AnyWrongPredInstrClassD = |({BPCallD, BPReturnD, BPJumpD, BPBranchD} ^ {CallD, ReturnD, JumpD, BranchD});
|
||||||
|
assign WrongBPReturnD = BPReturnD ^ ReturnD;
|
||||||
|
|
||||||
|
endmodule
|
Loading…
Reference in New Issue
Block a user