Skip to content

Commit

Permalink
add(Branch_Predictor.sv, branch_predictor.cpp) (#111)
Browse files Browse the repository at this point in the history
  • Loading branch information
ShinyMiraidon authored Nov 7, 2023
1 parent 9b59f7d commit 678a487
Show file tree
Hide file tree
Showing 5 changed files with 153 additions and 10 deletions.
16 changes: 9 additions & 7 deletions Documentation/01_Module_Docs/16_Branch_Predictor.md
Original file line number Diff line number Diff line change
@@ -1,12 +1,15 @@
# Branch Predictor #

## Contents
* [Inputs](#inputs)
* [Outputs](#outputs)
* [Functionality](#functionality)
* [Registers](#registers)
* [Clk](#on-posedge-clk)
* [Active low reset](#asynchronous-active-low-reset)
- [Branch Predictor](#branch-predictor)
- [Contents](#contents)
- [Inputs](#inputs)
- [Outputs](#outputs)
- [Functionality](#functionality)
- [Registers](#registers)
- [Combinational](#combinational)
- [On posedge clk](#on-posedge-clk)
- [Asynchronous active low reset on rstn\_h](#asynchronous-active-low-reset-on-rstn_h)

## Inputs
|Name|Bits wide|
Expand Down Expand Up @@ -35,7 +38,6 @@
|```branch_occr[1] == 0```|```branch_taken = branch_occr[0]```|
|```branch_occr[1] == 1```|```branch_taken = curr_pred```|
### On posedge clk
- Use a table when necessary if statements are used:
- ```branch_cond```, ```pred_taken```, ```act_taken```
|```condition```|```curr_pred```|```incorrect_pred```|
|---|---|---|
Expand Down
4 changes: 2 additions & 2 deletions dv/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,11 @@ find_package(nyu-util REQUIRED CONFIG)

add_executable(tests)
target_sources(tests PRIVATE
alu.cpp branch_eval.cpp pc.cpp ifid.cpp memwb.cpp gpr.cpp exmem.cpp branch_addr_calc.cpp idex.cpp
alu.cpp branch_eval.cpp pc.cpp ifid.cpp memwb.cpp gpr.cpp exmem.cpp branch_addr_calc.cpp idex.cpp branch_predictor.cpp
)
nyu_link_sv(tests PRIVATE core)
nyu_target_verilate(tests
TOP_MODULES Alu Branch_Eval PC IFID MEMWB GPR EXMEM Branch_Addr_Calc IDEX
TOP_MODULES Alu Branch_Eval PC IFID MEMWB GPR EXMEM Branch_Addr_Calc IDEX Branch_Predictor
ARGS COVERAGE
)
target_link_libraries(tests PRIVATE Catch2::Catch2WithMain nyu::covrecorder)
Expand Down
102 changes: 102 additions & 0 deletions dv/branch_predictor.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
#include <catch2/catch_test_macros.hpp>
#include <VBranch_Predictor.h>
#include <cstdint>
#include <stdlib.h>
#include <math.h>


TEST_CASE("Non Prediction Instruction") {

VBranch_Predictor model;

uint8_t branch_occr;
bool act_taken;
bool pred_taken;
uint8_t branch_cond;

//Initialize Module
model.rstn_h = 1;
model.clk = 0;
model.eval();
model.rstn_h = 0;
model.eval();



//Test Module
for (int i = 0; i < 1000; i++) {
branch_occr = rand() % (int) (pow(2, 1) - 1);
act_taken = rand() % (int) (pow(2, 1) - 1);
pred_taken = rand() % (int) (pow(2, 1) - 1);
branch_cond = rand() % (int) (pow(2, 2) - 1);

model.clk = 0;
model.eval();

model.clk = 1;
model.rstn_h = 1;
model.branch_occr = branch_occr;
model.act_taken = act_taken;
model.pred_taken = pred_taken;
model.branch_cond = branch_cond;
model.eval();
REQUIRE ((bool) model.branch_taken == (bool) branch_occr);
}
}

TEST_CASE("Prediction Instruction") {

VBranch_Predictor model;

uint8_t branch_occr;
bool act_taken;
bool pred_taken;
uint8_t branch_cond;

//Initialize Module
model.rstn_h = 1;
model.clk = 0;
model.eval();
model.rstn_h = 0;
model.eval();

//Initialize Register Tracker Variables
bool curr_pred = 0;
bool incorrect_pred = 0;

//Test Module
for (int i = 0; i < 1000; i++) {
branch_occr = 2 + rand() % (int) (pow(2, 1) - 1);
act_taken = rand() % (int) (pow(2, 1) - 1);
pred_taken = rand() % (int) (pow(2, 1) - 1);
branch_cond = rand() % (int) (pow(2, 2) - 1);

model.clk = 0;
model.eval();

model.clk = 1;
model.rstn_h = 1;
model.branch_occr = branch_occr;
model.act_taken = act_taken;
model.pred_taken = pred_taken;
model.branch_cond = branch_cond;

if (__builtin_parity(branch_cond) == 0) {
break;
}
else if ((act_taken ^ pred_taken) == 0) {
incorrect_pred = 0;
}
else if (incorrect_pred == 1) {
curr_pred = ~curr_pred;
incorrect_pred = 1;
}
else {
incorrect_pred = 1;
}

model.eval();

REQUIRE ((bool) model.branch_taken == (bool) curr_pred);
}
}
39 changes: 39 additions & 0 deletions rtl/Branch_Predictor.sv
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
module Branch_Predictor (
input clk, rstn_h, act_taken, pred_taken,
input [1:0] branch_occr, branch_cond,
output logic branch_taken
);
logic curr_pred, incorrect_pred;

always @ (posedge clk or negedge rstn_h) begin
if (!rstn_h) begin
curr_pred <= 0;
incorrect_pred <= 0;
end
else begin
if (^branch_cond == 0) begin
curr_pred <= curr_pred;
incorrect_pred <= incorrect_pred;
end
else if (act_taken ^ pred_taken == 0) begin
curr_pred <= curr_pred;
incorrect_pred <= 0;
end
else if (incorrect_pred) begin
curr_pred <= ~curr_pred;
incorrect_pred <= 1;
end
else begin
curr_pred <= curr_pred;
incorrect_pred <= 1;
end
end
end
always_comb begin
case(branch_occr[1])
0: branch_taken = branch_occr[0];
1: branch_taken = curr_pred;
default branch_taken = 0;
endcase
end
endmodule
2 changes: 1 addition & 1 deletion rtl/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
nyu_add_sv(core
Alu.sv Branch_Eval.sv PC.sv IFID.sv MEMWB.sv GPR.sv EXMEM.sv Branch_Addr_Calc.sv IDEX.sv
Alu.sv Branch_Eval.sv PC.sv IFID.sv MEMWB.sv GPR.sv EXMEM.sv Branch_Addr_Calc.sv IDEX.sv Branch_Predictor.sv
)

0 comments on commit 678a487

Please sign in to comment.