bpred_unit.cc (11432:4209ec56e923) | bpred_unit.cc (11433:72b075cdc336) |
---|---|
1/* 2 * Copyright (c) 2011-2012, 2014 ARM Limited 3 * Copyright (c) 2010 The University of Edinburgh 4 * Copyright (c) 2012 Mark D. Hill and David A. Wood 5 * All rights reserved 6 * 7 * The license below extends only to copyright in the software and shall 8 * not be construed as granting a license to any other intellectual --- 48 unchanged lines hidden (view full) --- 57 : SimObject(params), 58 numThreads(params->numThreads), 59 predHist(numThreads), 60 BTB(params->BTBEntries, 61 params->BTBTagSize, 62 params->instShiftAmt, 63 params->numThreads), 64 RAS(numThreads), | 1/* 2 * Copyright (c) 2011-2012, 2014 ARM Limited 3 * Copyright (c) 2010 The University of Edinburgh 4 * Copyright (c) 2012 Mark D. Hill and David A. Wood 5 * All rights reserved 6 * 7 * The license below extends only to copyright in the software and shall 8 * not be construed as granting a license to any other intellectual --- 48 unchanged lines hidden (view full) --- 57 : SimObject(params), 58 numThreads(params->numThreads), 59 predHist(numThreads), 60 BTB(params->BTBEntries, 61 params->BTBTagSize, 62 params->instShiftAmt, 63 params->numThreads), 64 RAS(numThreads), |
65 useIndirect(params->useIndirect), 66 iPred(params->indirectHashGHR, 67 params->indirectHashTargets, 68 params->indirectSets, 69 params->indirectWays, 70 params->indirectTagSize, 71 params->indirectPathLength, 72 params->instShiftAmt, 73 params->numThreads), |
|
65 instShiftAmt(params->instShiftAmt) 66{ 67 for (auto& r : RAS) 68 r.init(params->RASSize); 69} 70 71void 72BPredUnit::regStats() --- 39 unchanged lines hidden (view full) --- 112 .name(name() + ".usedRAS") 113 .desc("Number of times the RAS was used to get a target.") 114 ; 115 116 RASIncorrect 117 .name(name() + ".RASInCorrect") 118 .desc("Number of incorrect RAS predictions.") 119 ; | 74 instShiftAmt(params->instShiftAmt) 75{ 76 for (auto& r : RAS) 77 r.init(params->RASSize); 78} 79 80void 81BPredUnit::regStats() --- 39 unchanged lines hidden (view full) --- 121 .name(name() + ".usedRAS") 122 .desc("Number of times the RAS was used to get a target.") 123 ; 124 125 RASIncorrect 126 .name(name() + ".RASInCorrect") 127 .desc("Number of incorrect RAS predictions.") 128 ; |
129 130 indirectLookups 131 .name(name() + ".indirectLookups") 132 .desc("Number of indirect predictor lookups.") 133 ; 134 135 indirectHits 136 .name(name() + ".indirectHits") 137 .desc("Number of indirect target hits.") 138 ; 139 140 indirectMisses 141 .name(name() + ".indirectMisses") 142 .desc("Number of indirect misses.") 143 ; 144 145 indirectMispredicted 146 .name(name() + "indirectMispredicted") 147 .desc("Number of mispredicted indirect branches.") 148 ; 149 |
|
120} 121 122ProbePoints::PMUUPtr 123BPredUnit::pmuProbePoint(const char *name) 124{ 125 ProbePoints::PMUUPtr ptr; 126 ptr.reset(new ProbePoints::PMU(getProbeManager(), name)); 127 --- 83 unchanged lines hidden (view full) --- 211 // be popped off if the speculation is incorrect. 212 predict_record.wasCall = true; 213 214 DPRINTF(Branch, "[tid:%i]: Instruction %s was a " 215 "call, adding %s to the RAS index: %i.\n", 216 tid, pc, pc, RAS[tid].topIdx()); 217 } 218 | 150} 151 152ProbePoints::PMUUPtr 153BPredUnit::pmuProbePoint(const char *name) 154{ 155 ProbePoints::PMUUPtr ptr; 156 ptr.reset(new ProbePoints::PMU(getProbeManager(), name)); 157 --- 83 unchanged lines hidden (view full) --- 241 // be popped off if the speculation is incorrect. 242 predict_record.wasCall = true; 243 244 DPRINTF(Branch, "[tid:%i]: Instruction %s was a " 245 "call, adding %s to the RAS index: %i.\n", 246 tid, pc, pc, RAS[tid].topIdx()); 247 } 248 |
219 if (BTB.valid(pc.instAddr(), tid)) { 220 ++BTBHits; | 249 if (inst->isDirectCtrl() || !useIndirect) { 250 // Check BTB on direct branches 251 if (BTB.valid(pc.instAddr(), tid)) { 252 ++BTBHits; |
221 | 253 |
222 // If it's not a return, use the BTB to get the target addr. 223 target = BTB.lookup(pc.instAddr(), tid); | 254 // If it's not a return, use the BTB to get target addr. 255 target = BTB.lookup(pc.instAddr(), tid); |
224 | 256 |
225 DPRINTF(Branch, "[tid:%i]: Instruction %s predicted" 226 " target is %s.\n", tid, pc, target); | 257 DPRINTF(Branch, "[tid:%i]: Instruction %s predicted" 258 " target is %s.\n", tid, pc, target); |
227 | 259 |
260 } else { 261 DPRINTF(Branch, "[tid:%i]: BTB doesn't have a " 262 "valid entry.\n",tid); 263 pred_taken = false; 264 // The Direction of the branch predictor is altered 265 // because the BTB did not have an entry 266 // The predictor needs to be updated accordingly 267 if (!inst->isCall() && !inst->isReturn()) { 268 btbUpdate(pc.instAddr(), bp_history); 269 DPRINTF(Branch, "[tid:%i]:[sn:%i] btbUpdate" 270 " called for %s\n", tid, seqNum, pc); 271 } else if (inst->isCall() && !inst->isUncondCtrl()) { 272 RAS[tid].pop(); 273 predict_record.pushedRAS = false; 274 } 275 TheISA::advancePC(target, inst); 276 } |
|
228 } else { | 277 } else { |
229 DPRINTF(Branch, "[tid:%i]: BTB doesn't have a " 230 "valid entry.\n",tid); 231 pred_taken = false; 232 // The Direction of the branch predictor is altered because the 233 // BTB did not have an entry 234 // The predictor needs to be updated accordingly 235 if (!inst->isCall() && !inst->isReturn()) { 236 btbUpdate(pc.instAddr(), bp_history); 237 DPRINTF(Branch, "[tid:%i]:[sn:%i] btbUpdate" 238 " called for %s\n", tid, seqNum, pc); 239 } else if (inst->isCall() && !inst->isUncondCtrl()) { 240 RAS[tid].pop(); 241 predict_record.pushedRAS = false; | 278 predict_record.wasIndirect = true; 279 ++indirectLookups; 280 //Consult indirect predictor on indirect control 281 if (iPred.lookup(pc.instAddr(), getGHR(bp_history), target, 282 tid)) { 283 // Indirect predictor hit 284 ++indirectHits; 285 DPRINTF(Branch, "[tid:%i]: Instruction %s predicted " 286 "indirect target is %s.\n", tid, pc, target); 287 } else { 288 ++indirectMisses; 289 pred_taken = false; 290 DPRINTF(Branch, "[tid:%i]: Instruction %s no indirect " 291 "target.\n", tid, pc); 292 if (!inst->isCall() && !inst->isReturn()) { 293 294 } else if (inst->isCall() && !inst->isUncondCtrl()) { 295 RAS[tid].pop(); 296 predict_record.pushedRAS = false; 297 } 298 TheISA::advancePC(target, inst); |
242 } | 299 } |
243 TheISA::advancePC(target, inst); | 300 iPred.recordIndirect(pc.instAddr(), target.instAddr(), seqNum, 301 tid); |
244 } 245 } 246 } else { 247 if (inst->isReturn()) { 248 predict_record.wasReturn = true; 249 } 250 TheISA::advancePC(target, inst); 251 } --- 131 unchanged lines hidden (view full) --- 383} 384 385void 386BPredUnit::update(const InstSeqNum &done_sn, ThreadID tid) 387{ 388 DPRINTF(Branch, "[tid:%i]: Committing branches until " 389 "[sn:%lli].\n", tid, done_sn); 390 | 302 } 303 } 304 } else { 305 if (inst->isReturn()) { 306 predict_record.wasReturn = true; 307 } 308 TheISA::advancePC(target, inst); 309 } --- 131 unchanged lines hidden (view full) --- 441} 442 443void 444BPredUnit::update(const InstSeqNum &done_sn, ThreadID tid) 445{ 446 DPRINTF(Branch, "[tid:%i]: Committing branches until " 447 "[sn:%lli].\n", tid, done_sn); 448 |
449 iPred.commit(done_sn, tid); |
|
391 while (!predHist[tid].empty() && 392 predHist[tid].back().seqNum <= done_sn) { 393 // Update the branch predictor with the correct results. 394 if (!predHist[tid].back().wasSquashed) { 395 update(predHist[tid].back().pc, predHist[tid].back().predTaken, 396 predHist[tid].back().bpHistory, false); 397 } else { 398 retireSquashed(predHist[tid].back().bpHistory); 399 } 400 401 predHist[tid].pop_back(); 402 } 403} 404 405void 406BPredUnit::squash(const InstSeqNum &squashed_sn, ThreadID tid) 407{ 408 History &pred_hist = predHist[tid]; 409 | 450 while (!predHist[tid].empty() && 451 predHist[tid].back().seqNum <= done_sn) { 452 // Update the branch predictor with the correct results. 453 if (!predHist[tid].back().wasSquashed) { 454 update(predHist[tid].back().pc, predHist[tid].back().predTaken, 455 predHist[tid].back().bpHistory, false); 456 } else { 457 retireSquashed(predHist[tid].back().bpHistory); 458 } 459 460 predHist[tid].pop_back(); 461 } 462} 463 464void 465BPredUnit::squash(const InstSeqNum &squashed_sn, ThreadID tid) 466{ 467 History &pred_hist = predHist[tid]; 468 |
469 iPred.squash(squashed_sn, tid); |
|
410 while (!pred_hist.empty() && 411 pred_hist.front().seqNum > squashed_sn) { 412 if (pred_hist.front().usedRAS) { 413 DPRINTF(Branch, "[tid:%i]: Restoring top of RAS to: %i," 414 " target: %s.\n", tid, 415 pred_hist.front().RASIndex, pred_hist.front().RASTarget); 416 417 RAS[tid].restore(pred_hist.front().RASIndex, --- 62 unchanged lines hidden (view full) --- 480 pred_hist.front().seqNum, squashed_sn); 481 482 assert(pred_hist.front().seqNum == squashed_sn); 483 } 484 485 486 if ((*hist_it).usedRAS) { 487 ++RASIncorrect; | 470 while (!pred_hist.empty() && 471 pred_hist.front().seqNum > squashed_sn) { 472 if (pred_hist.front().usedRAS) { 473 DPRINTF(Branch, "[tid:%i]: Restoring top of RAS to: %i," 474 " target: %s.\n", tid, 475 pred_hist.front().RASIndex, pred_hist.front().RASTarget); 476 477 RAS[tid].restore(pred_hist.front().RASIndex, --- 62 unchanged lines hidden (view full) --- 540 pred_hist.front().seqNum, squashed_sn); 541 542 assert(pred_hist.front().seqNum == squashed_sn); 543 } 544 545 546 if ((*hist_it).usedRAS) { 547 ++RASIncorrect; |
548 DPRINTF(Branch, "[tid:%i]: Incorrect RAS [sn:%i]\n", 549 tid, hist_it->seqNum); |
|
488 } 489 | 550 } 551 |
552 // Have to get GHR here because the update deletes bpHistory 553 unsigned ghr = getGHR(hist_it->bpHistory); 554 |
|
490 update((*hist_it).pc, actually_taken, 491 pred_hist.front().bpHistory, true); 492 hist_it->wasSquashed = true; 493 494 if (actually_taken) { 495 if (hist_it->wasReturn && !hist_it->usedRAS) { 496 DPRINTF(Branch, "[tid: %i] Incorrectly predicted" 497 " return [sn:%i] PC: %s\n", tid, hist_it->seqNum, 498 hist_it->pc); 499 RAS[tid].pop(); 500 hist_it->usedRAS = true; 501 } | 555 update((*hist_it).pc, actually_taken, 556 pred_hist.front().bpHistory, true); 557 hist_it->wasSquashed = true; 558 559 if (actually_taken) { 560 if (hist_it->wasReturn && !hist_it->usedRAS) { 561 DPRINTF(Branch, "[tid: %i] Incorrectly predicted" 562 " return [sn:%i] PC: %s\n", tid, hist_it->seqNum, 563 hist_it->pc); 564 RAS[tid].pop(); 565 hist_it->usedRAS = true; 566 } |
567 if (hist_it->wasIndirect) { 568 ++indirectMispredicted; 569 iPred.recordTarget(hist_it->seqNum, ghr, corrTarget, tid); 570 } else { 571 DPRINTF(Branch,"[tid: %i] BTB Update called for [sn:%i]" 572 " PC: %s\n", tid,hist_it->seqNum, hist_it->pc); |
|
502 | 573 |
503 DPRINTF(Branch,"[tid: %i] BTB Update called for [sn:%i]" 504 " PC: %s\n", tid,hist_it->seqNum, hist_it->pc); 505 506 BTB.update((*hist_it).pc, corrTarget, tid); 507 | 574 BTB.update((*hist_it).pc, corrTarget, tid); 575 } |
508 } else { 509 //Actually not Taken 510 if (hist_it->usedRAS) { 511 DPRINTF(Branch,"[tid: %i] Incorrectly predicted" 512 " return [sn:%i] PC: %s Restoring RAS\n", tid, 513 hist_it->seqNum, hist_it->pc); 514 DPRINTF(Branch, "[tid:%i]: Restoring top of RAS" 515 " to: %i, target: %s.\n", tid, --- 42 unchanged lines hidden --- | 576 } else { 577 //Actually not Taken 578 if (hist_it->usedRAS) { 579 DPRINTF(Branch,"[tid: %i] Incorrectly predicted" 580 " return [sn:%i] PC: %s Restoring RAS\n", tid, 581 hist_it->seqNum, hist_it->pc); 582 DPRINTF(Branch, "[tid:%i]: Restoring top of RAS" 583 " to: %i, target: %s.\n", tid, --- 42 unchanged lines hidden --- |