indirect.cc (13654:dc3878f03a0c) indirect.cc (13810:f50e3b82df73)
1/*
2 * Copyright (c) 2014 ARM Limited
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;

--- 22 unchanged lines hidden (view full) ---

31#include "cpu/pred/indirect.hh"
32
33#include "base/intmath.hh"
34#include "debug/Indirect.hh"
35
36IndirectPredictor::IndirectPredictor(bool hash_ghr, bool hash_targets,
37 unsigned num_sets, unsigned num_ways,
38 unsigned tag_bits, unsigned path_len, unsigned inst_shift,
1/*
2 * Copyright (c) 2014 ARM Limited
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;

--- 22 unchanged lines hidden (view full) ---

31#include "cpu/pred/indirect.hh"
32
33#include "base/intmath.hh"
34#include "debug/Indirect.hh"
35
36IndirectPredictor::IndirectPredictor(bool hash_ghr, bool hash_targets,
37 unsigned num_sets, unsigned num_ways,
38 unsigned tag_bits, unsigned path_len, unsigned inst_shift,
39 unsigned num_threads)
39 unsigned num_threads, unsigned ghr_size)
40 : hashGHR(hash_ghr), hashTargets(hash_targets),
41 numSets(num_sets), numWays(num_ways), tagBits(tag_bits),
40 : hashGHR(hash_ghr), hashTargets(hash_targets),
41 numSets(num_sets), numWays(num_ways), tagBits(tag_bits),
42 pathLength(path_len), instShift(inst_shift)
42 pathLength(path_len), instShift(inst_shift),
43 ghrNumBits(ghr_size), ghrMask((1 << ghr_size)-1)
43{
44 if (!isPowerOf2(numSets)) {
45 panic("Indirect predictor requires power of 2 number of sets");
46 }
47
48 threadInfo.resize(num_threads);
49
50 targetCache.resize(numSets);
51 for (unsigned i = 0; i < numSets; i++) {
52 targetCache[i].resize(numWays);
53 }
44{
45 if (!isPowerOf2(numSets)) {
46 panic("Indirect predictor requires power of 2 number of sets");
47 }
48
49 threadInfo.resize(num_threads);
50
51 targetCache.resize(numSets);
52 for (unsigned i = 0; i < numSets; i++) {
53 targetCache[i].resize(numWays);
54 }
55
56 fatal_if(ghrNumBits > (sizeof(ThreadInfo::ghr)*8), "ghr_size is too big");
54}
55
56void
57}
58
59void
57IndirectPredictor::updateDirectionInfo(ThreadID tid, bool taken,
58 void* & indirect_history)
60IndirectPredictor::genIndirectInfo(ThreadID tid, void* & indirect_history)
59{
60 // record the GHR as it was before this prediction
61 // It will be used to recover the history in case this prediction is
62 // wrong or belongs to bad path
63 indirect_history = new unsigned(threadInfo[tid].ghr);
61{
62 // record the GHR as it was before this prediction
63 // It will be used to recover the history in case this prediction is
64 // wrong or belongs to bad path
65 indirect_history = new unsigned(threadInfo[tid].ghr);
66}
64
67
65 threadInfo[tid].ghr <<= taken;
68void
69IndirectPredictor::updateDirectionInfo(
70 ThreadID tid, bool actually_taken)
71{
72 threadInfo[tid].ghr <<= 1;
73 threadInfo[tid].ghr |= actually_taken;
74 threadInfo[tid].ghr &= ghrMask;
66}
67
68void
69IndirectPredictor::changeDirectionPrediction(ThreadID tid,
70 void * indirect_history, bool actually_taken)
71{
72 unsigned * previousGhr = static_cast<unsigned *>(indirect_history);
73 threadInfo[tid].ghr = ((*previousGhr) << 1) + actually_taken;
75}
76
77void
78IndirectPredictor::changeDirectionPrediction(ThreadID tid,
79 void * indirect_history, bool actually_taken)
80{
81 unsigned * previousGhr = static_cast<unsigned *>(indirect_history);
82 threadInfo[tid].ghr = ((*previousGhr) << 1) + actually_taken;
83 threadInfo[tid].ghr &= ghrMask;
74}
75
76bool
77IndirectPredictor::lookup(Addr br_addr, TheISA::PCState& target,
78 ThreadID tid)
79{
80 Addr set_index = getSetIndex(br_addr, threadInfo[tid].ghr, tid);
81 Addr tag = getTag(br_addr);

--- 60 unchanged lines hidden (view full) ---

142 if (squash_itr != t_info.pathHist.end()) {
143 DPRINTF(Indirect, "Squashing series starting with sn:%d\n",
144 squash_itr->seqNum);
145 }
146 t_info.pathHist.erase(squash_itr, t_info.pathHist.end());
147}
148
149void
84}
85
86bool
87IndirectPredictor::lookup(Addr br_addr, TheISA::PCState& target,
88 ThreadID tid)
89{
90 Addr set_index = getSetIndex(br_addr, threadInfo[tid].ghr, tid);
91 Addr tag = getTag(br_addr);

--- 60 unchanged lines hidden (view full) ---

152 if (squash_itr != t_info.pathHist.end()) {
153 DPRINTF(Indirect, "Squashing series starting with sn:%d\n",
154 squash_itr->seqNum);
155 }
156 t_info.pathHist.erase(squash_itr, t_info.pathHist.end());
157}
158
159void
150IndirectPredictor::deleteDirectionInfo(ThreadID tid, void * indirect_history)
160IndirectPredictor::deleteIndirectInfo(ThreadID tid, void * indirect_history)
151{
152 unsigned * previousGhr = static_cast<unsigned *>(indirect_history);
153 threadInfo[tid].ghr = *previousGhr;
154
155 delete previousGhr;
156}
157
158void
161{
162 unsigned * previousGhr = static_cast<unsigned *>(indirect_history);
163 threadInfo[tid].ghr = *previousGhr;
164
165 delete previousGhr;
166}
167
168void
159IndirectPredictor::recordTarget(InstSeqNum seq_num,
160 const TheISA::PCState& target, ThreadID tid)
169IndirectPredictor::recordTarget(
170 InstSeqNum seq_num, void * indirect_history, const TheISA::PCState& target,
171 ThreadID tid)
161{
162 ThreadInfo &t_info = threadInfo[tid];
163
172{
173 ThreadInfo &t_info = threadInfo[tid];
174
175 unsigned * ghr = static_cast<unsigned *>(indirect_history);
176
164 // Should have just squashed so this branch should be the oldest
165 auto hist_entry = *(t_info.pathHist.rbegin());
166 // Temporarily pop it off the history so we can calculate the set
167 t_info.pathHist.pop_back();
177 // Should have just squashed so this branch should be the oldest
178 auto hist_entry = *(t_info.pathHist.rbegin());
179 // Temporarily pop it off the history so we can calculate the set
180 t_info.pathHist.pop_back();
168 Addr set_index = getSetIndex(hist_entry.pcAddr, t_info.ghr, tid);
181 Addr set_index = getSetIndex(hist_entry.pcAddr, *ghr, tid);
169 Addr tag = getTag(hist_entry.pcAddr);
170 hist_entry.targetAddr = target.instAddr();
171 t_info.pathHist.push_back(hist_entry);
172
173 assert(set_index < numSets);
174
175 auto &iset = targetCache[set_index];
176 for (auto way = iset.begin(); way != iset.end(); ++way) {

--- 42 unchanged lines hidden ---
182 Addr tag = getTag(hist_entry.pcAddr);
183 hist_entry.targetAddr = target.instAddr();
184 t_info.pathHist.push_back(hist_entry);
185
186 assert(set_index < numSets);
187
188 auto &iset = targetCache[set_index];
189 for (auto way = iset.begin(); way != iset.end(); ++way) {

--- 42 unchanged lines hidden ---