rename_map.cc (2632:1bb2f91485ea) | rename_map.cc (2654:9559cfa91b9d) |
---|---|
1/* 2 * Copyright (c) 2004-2005 The Regents of The University of Michigan 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; --- 18 unchanged lines hidden (view full) --- 27 */ 28 29#include <vector> 30 31#include "cpu/o3/rename_map.hh" 32 33using namespace std; 34 | 1/* 2 * Copyright (c) 2004-2005 The Regents of The University of Michigan 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; --- 18 unchanged lines hidden (view full) --- 27 */ 28 29#include <vector> 30 31#include "cpu/o3/rename_map.hh" 32 33using namespace std; 34 |
35// Todo: Consider making functions inline. Avoid having things that are 36// using the zero register or misc registers from adding on the registers 37// to the free list. Possibly remove the direct communication between 38// this and the freelist. Considering making inline bool functions that 39// determine if the register is a logical int, logical fp, physical int, 40// physical fp, etc. | 35// @todo: Consider making inline bool functions that determine if the 36// register is a logical int, logical fp, physical int, physical fp, 37// etc. |
41 | 38 |
42SimpleRenameMap::SimpleRenameMap(unsigned _numLogicalIntRegs, 43 unsigned _numPhysicalIntRegs, 44 unsigned _numLogicalFloatRegs, 45 unsigned _numPhysicalFloatRegs, 46 unsigned _numMiscRegs, 47 RegIndex _intZeroReg, 48 RegIndex _floatZeroReg) 49 : numLogicalIntRegs(_numLogicalIntRegs), 50 numPhysicalIntRegs(_numPhysicalIntRegs), 51 numLogicalFloatRegs(_numLogicalFloatRegs), 52 numPhysicalFloatRegs(_numPhysicalFloatRegs), 53 numMiscRegs(_numMiscRegs), 54 intZeroReg(_intZeroReg), 55 floatZeroReg(_floatZeroReg) | 39SimpleRenameMap::~SimpleRenameMap() |
56{ | 40{ |
57 DPRINTF(Rename, "Rename: Creating rename map. Phys: %i / %i, Float: " 58 "%i / %i.\n", numLogicalIntRegs, numPhysicalIntRegs, | 41} 42 43void 44SimpleRenameMap::init(unsigned _numLogicalIntRegs, 45 unsigned _numPhysicalIntRegs, 46 PhysRegIndex &ireg_idx, 47 48 unsigned _numLogicalFloatRegs, 49 unsigned _numPhysicalFloatRegs, 50 PhysRegIndex &freg_idx, 51 52 unsigned _numMiscRegs, 53 54 RegIndex _intZeroReg, 55 RegIndex _floatZeroReg, 56 57 int map_id, 58 bool bindRegs) 59{ 60 id = map_id; 61 62 numLogicalIntRegs = _numLogicalIntRegs; 63 64 numLogicalFloatRegs = _numLogicalFloatRegs; 65 66 numPhysicalIntRegs = _numPhysicalIntRegs; 67 68 numPhysicalFloatRegs = _numPhysicalFloatRegs; 69 70 numMiscRegs = _numMiscRegs; 71 72 intZeroReg = _intZeroReg; 73 floatZeroReg = _floatZeroReg; 74 75 DPRINTF(Rename, "Creating rename map %i. Phys: %i / %i, Float: " 76 "%i / %i.\n", id, numLogicalIntRegs, numPhysicalIntRegs, |
59 numLogicalFloatRegs, numPhysicalFloatRegs); 60 61 numLogicalRegs = numLogicalIntRegs + numLogicalFloatRegs; 62 63 numPhysicalRegs = numPhysicalIntRegs + numPhysicalFloatRegs; 64 | 77 numLogicalFloatRegs, numPhysicalFloatRegs); 78 79 numLogicalRegs = numLogicalIntRegs + numLogicalFloatRegs; 80 81 numPhysicalRegs = numPhysicalIntRegs + numPhysicalFloatRegs; 82 |
65 //Create the rename maps, and their scoreboards. 66 intRenameMap = new RenameEntry[numLogicalIntRegs]; 67 floatRenameMap = new RenameEntry[numLogicalRegs]; | 83 //Create the rename maps 84 intRenameMap.resize(numLogicalIntRegs); 85 floatRenameMap.resize(numLogicalRegs); |
68 | 86 |
69 // Should combine this into one scoreboard. 70 intScoreboard.resize(numPhysicalIntRegs); 71 floatScoreboard.resize(numPhysicalRegs); 72 miscScoreboard.resize(numPhysicalRegs + numMiscRegs); | 87 if (bindRegs) { 88 DPRINTF(Rename, "Binding registers into rename map %i",id); |
73 | 89 |
74 // Initialize the entries in the integer rename map to point to the 75 // physical registers of the same index, and consider each register 76 // ready until the first rename occurs. 77 for (RegIndex index = 0; index < numLogicalIntRegs; ++index) 78 { 79 intRenameMap[index].physical_reg = index; 80 intScoreboard[index] = 1; 81 } | 90 // Initialize the entries in the integer rename map to point to the 91 // physical registers of the same index 92 for (RegIndex index = 0; index < numLogicalIntRegs; ++index) 93 { 94 intRenameMap[index].physical_reg = ireg_idx++; 95 } |
82 | 96 |
83 // Initialize the rest of the physical registers (the ones that don't 84 // directly map to a logical register) as unready. 85 for (PhysRegIndex index = numLogicalIntRegs; 86 index < numPhysicalIntRegs; 87 ++index) 88 { 89 intScoreboard[index] = 0; 90 } | 97 // Initialize the entries in the floating point rename map to point to 98 // the physical registers of the same index 99 // Although the index refers purely to architected registers, because 100 // the floating reg indices come after the integer reg indices, they 101 // may exceed the size of a normal RegIndex (short). 102 for (PhysRegIndex index = numLogicalIntRegs; 103 index < numLogicalRegs; ++index) 104 { 105 floatRenameMap[index].physical_reg = freg_idx++; 106 } 107 } else { 108 DPRINTF(Rename, "Binding registers into rename map %i",id); |
91 | 109 |
92 int float_reg_idx = numPhysicalIntRegs; | 110 PhysRegIndex temp_ireg = ireg_idx; |
93 | 111 |
94 // Initialize the entries in the floating point rename map to point to 95 // the physical registers of the same index, and consider each register 96 // ready until the first rename occurs. 97 // Although the index refers purely to architected registers, because 98 // the floating reg indices come after the integer reg indices, they 99 // may exceed the size of a normal RegIndex (short). 100 for (PhysRegIndex index = numLogicalIntRegs; 101 index < numLogicalRegs; ++index) 102 { 103 floatRenameMap[index].physical_reg = float_reg_idx++; 104 } | 112 for (RegIndex index = 0; index < numLogicalIntRegs; ++index) 113 { 114 intRenameMap[index].physical_reg = temp_ireg++; 115 } |
105 | 116 |
106 for (PhysRegIndex index = numPhysicalIntRegs; 107 index < numPhysicalIntRegs + numLogicalFloatRegs; ++index) 108 { 109 floatScoreboard[index] = 1; 110 } | 117 PhysRegIndex temp_freg = freg_idx; |
111 | 118 |
112 // Initialize the rest of the physical registers (the ones that don't 113 // directly map to a logical register) as unready. 114 for (PhysRegIndex index = numPhysicalIntRegs + numLogicalFloatRegs; 115 index < numPhysicalRegs; 116 ++index) 117 { 118 floatScoreboard[index] = 0; | 119 for (PhysRegIndex index = numLogicalIntRegs; 120 index < numLogicalRegs; ++index) 121 { 122 floatRenameMap[index].physical_reg = temp_freg++; 123 } |
119 } | 124 } |
120 121 // Initialize the entries in the misc register scoreboard to be ready. 122 for (PhysRegIndex index = numPhysicalRegs; 123 index < numPhysicalRegs + numMiscRegs; ++index) 124 { 125 miscScoreboard[index] = 1; 126 } | |
127} 128 | 125} 126 |
129SimpleRenameMap::~SimpleRenameMap() 130{ 131 // Delete the rename maps as they were allocated with new. 132 delete [] intRenameMap; 133 delete [] floatRenameMap; 134} 135 | |
136void 137SimpleRenameMap::setFreeList(SimpleFreeList *fl_ptr) 138{ | 127void 128SimpleRenameMap::setFreeList(SimpleFreeList *fl_ptr) 129{ |
139 //Setup the interface to the freelist. | |
140 freeList = fl_ptr; 141} 142 143 | 130 freeList = fl_ptr; 131} 132 133 |
144// Don't allow this stage to fault; force that check to the rename stage. 145// Simply ask to rename a logical register and get back a new physical 146// register index. | |
147SimpleRenameMap::RenameInfo 148SimpleRenameMap::rename(RegIndex arch_reg) 149{ 150 PhysRegIndex renamed_reg; 151 PhysRegIndex prev_reg; 152 153 if (arch_reg < numLogicalIntRegs) { 154 155 // Record the current physical register that is renamed to the 156 // requested architected register. 157 prev_reg = intRenameMap[arch_reg].physical_reg; 158 | 134SimpleRenameMap::RenameInfo 135SimpleRenameMap::rename(RegIndex arch_reg) 136{ 137 PhysRegIndex renamed_reg; 138 PhysRegIndex prev_reg; 139 140 if (arch_reg < numLogicalIntRegs) { 141 142 // Record the current physical register that is renamed to the 143 // requested architected register. 144 prev_reg = intRenameMap[arch_reg].physical_reg; 145 |
159 // If it's not referencing the zero register, then mark the register 160 // as not ready. | 146 // If it's not referencing the zero register, then rename the 147 // register. |
161 if (arch_reg != intZeroReg) { | 148 if (arch_reg != intZeroReg) { |
162 // Get a free physical register to rename to. | |
163 renamed_reg = freeList->getIntReg(); 164 | 149 renamed_reg = freeList->getIntReg(); 150 |
165 // Update the integer rename map. | |
166 intRenameMap[arch_reg].physical_reg = renamed_reg; 167 168 assert(renamed_reg >= 0 && renamed_reg < numPhysicalIntRegs); 169 | 151 intRenameMap[arch_reg].physical_reg = renamed_reg; 152 153 assert(renamed_reg >= 0 && renamed_reg < numPhysicalIntRegs); 154 |
170 // Mark register as not ready. 171 intScoreboard[renamed_reg] = false; | |
172 } else { 173 // Otherwise return the zero register so nothing bad happens. 174 renamed_reg = intZeroReg; 175 } 176 } else if (arch_reg < numLogicalRegs) { | 155 } else { 156 // Otherwise return the zero register so nothing bad happens. 157 renamed_reg = intZeroReg; 158 } 159 } else if (arch_reg < numLogicalRegs) { |
177 // Subtract off the base offset for floating point registers. 178// arch_reg = arch_reg - numLogicalIntRegs; 179 | |
180 // Record the current physical register that is renamed to the 181 // requested architected register. 182 prev_reg = floatRenameMap[arch_reg].physical_reg; 183 | 160 // Record the current physical register that is renamed to the 161 // requested architected register. 162 prev_reg = floatRenameMap[arch_reg].physical_reg; 163 |
184 // If it's not referencing the zero register, then mark the register 185 // as not ready. | 164 // If it's not referencing the zero register, then rename the 165 // register. |
186 if (arch_reg != floatZeroReg) { | 166 if (arch_reg != floatZeroReg) { |
187 // Get a free floating point register to rename to. | |
188 renamed_reg = freeList->getFloatReg(); 189 | 167 renamed_reg = freeList->getFloatReg(); 168 |
190 // Update the floating point rename map. | |
191 floatRenameMap[arch_reg].physical_reg = renamed_reg; 192 193 assert(renamed_reg < numPhysicalRegs && 194 renamed_reg >= numPhysicalIntRegs); | 169 floatRenameMap[arch_reg].physical_reg = renamed_reg; 170 171 assert(renamed_reg < numPhysicalRegs && 172 renamed_reg >= numPhysicalIntRegs); |
195 196 // Mark register as not ready. 197 floatScoreboard[renamed_reg] = false; | |
198 } else { 199 // Otherwise return the zero register so nothing bad happens. 200 renamed_reg = floatZeroReg; 201 } 202 } else { 203 // Subtract off the base offset for miscellaneous registers. 204 arch_reg = arch_reg - numLogicalRegs; 205 | 173 } else { 174 // Otherwise return the zero register so nothing bad happens. 175 renamed_reg = floatZeroReg; 176 } 177 } else { 178 // Subtract off the base offset for miscellaneous registers. 179 arch_reg = arch_reg - numLogicalRegs; 180 |
206 // No renaming happens to the misc. registers. They are simply the 207 // registers that come after all the physical registers; thus 208 // take the base architected register and add the physical registers 209 // to it. | 181 // No renaming happens to the misc. registers. They are 182 // simply the registers that come after all the physical 183 // registers; thus take the base architected register and add 184 // the physical registers to it. |
210 renamed_reg = arch_reg + numPhysicalRegs; 211 212 // Set the previous register to the same register; mainly it must be 213 // known that the prev reg was outside the range of normal registers 214 // so the free list can avoid adding it. 215 prev_reg = renamed_reg; 216 217 assert(renamed_reg < numPhysicalRegs + numMiscRegs); | 185 renamed_reg = arch_reg + numPhysicalRegs; 186 187 // Set the previous register to the same register; mainly it must be 188 // known that the prev reg was outside the range of normal registers 189 // so the free list can avoid adding it. 190 prev_reg = renamed_reg; 191 192 assert(renamed_reg < numPhysicalRegs + numMiscRegs); |
218 219 miscScoreboard[renamed_reg] = false; | |
220 } 221 222 return RenameInfo(renamed_reg, prev_reg); 223} 224 | 193 } 194 195 return RenameInfo(renamed_reg, prev_reg); 196} 197 |
225//Perhaps give this a pair as a return value, of the physical register 226//and whether or not it's ready. | |
227PhysRegIndex 228SimpleRenameMap::lookup(RegIndex arch_reg) 229{ 230 if (arch_reg < numLogicalIntRegs) { 231 return intRenameMap[arch_reg].physical_reg; 232 } else if (arch_reg < numLogicalRegs) { | 198PhysRegIndex 199SimpleRenameMap::lookup(RegIndex arch_reg) 200{ 201 if (arch_reg < numLogicalIntRegs) { 202 return intRenameMap[arch_reg].physical_reg; 203 } else if (arch_reg < numLogicalRegs) { |
233 // Subtract off the base FP offset. 234// arch_reg = arch_reg - numLogicalIntRegs; 235 | |
236 return floatRenameMap[arch_reg].physical_reg; 237 } else { 238 // Subtract off the misc registers offset. 239 arch_reg = arch_reg - numLogicalRegs; 240 241 // Misc. regs don't rename, so simply add the base arch reg to 242 // the number of physical registers. 243 return numPhysicalRegs + arch_reg; 244 } 245} 246 | 204 return floatRenameMap[arch_reg].physical_reg; 205 } else { 206 // Subtract off the misc registers offset. 207 arch_reg = arch_reg - numLogicalRegs; 208 209 // Misc. regs don't rename, so simply add the base arch reg to 210 // the number of physical registers. 211 return numPhysicalRegs + arch_reg; 212 } 213} 214 |
247bool 248SimpleRenameMap::isReady(PhysRegIndex phys_reg) 249{ 250 if (phys_reg < numPhysicalIntRegs) { 251 return intScoreboard[phys_reg]; 252 } else if (phys_reg < numPhysicalRegs) { 253 254 // Subtract off the base FP offset. 255// phys_reg = phys_reg - numPhysicalIntRegs; 256 257 return floatScoreboard[phys_reg]; 258 } else { 259 // Subtract off the misc registers offset. 260// phys_reg = phys_reg - numPhysicalRegs; 261 262 return miscScoreboard[phys_reg]; 263 } 264} 265 266// In this implementation the miscellaneous registers do not actually rename, 267// so this function does not allow you to try to change their mappings. | |
268void 269SimpleRenameMap::setEntry(RegIndex arch_reg, PhysRegIndex renamed_reg) 270{ | 215void 216SimpleRenameMap::setEntry(RegIndex arch_reg, PhysRegIndex renamed_reg) 217{ |
218 // In this implementation the miscellaneous registers do not 219 // actually rename, so this function does not allow you to try to 220 // change their mappings. |
|
271 if (arch_reg < numLogicalIntRegs) { 272 DPRINTF(Rename, "Rename Map: Integer register %i being set to %i.\n", 273 (int)arch_reg, renamed_reg); 274 275 intRenameMap[arch_reg].physical_reg = renamed_reg; | 221 if (arch_reg < numLogicalIntRegs) { 222 DPRINTF(Rename, "Rename Map: Integer register %i being set to %i.\n", 223 (int)arch_reg, renamed_reg); 224 225 intRenameMap[arch_reg].physical_reg = renamed_reg; |
276 } else { 277 assert(arch_reg < (numLogicalIntRegs + numLogicalFloatRegs)); 278 | 226 } else if (arch_reg < numLogicalIntRegs + numLogicalFloatRegs) { |
279 DPRINTF(Rename, "Rename Map: Float register %i being set to %i.\n", 280 (int)arch_reg - numLogicalIntRegs, renamed_reg); 281 282 floatRenameMap[arch_reg].physical_reg = renamed_reg; 283 } 284} 285 | 227 DPRINTF(Rename, "Rename Map: Float register %i being set to %i.\n", 228 (int)arch_reg - numLogicalIntRegs, renamed_reg); 229 230 floatRenameMap[arch_reg].physical_reg = renamed_reg; 231 } 232} 233 |
286void 287SimpleRenameMap::squash(vector<RegIndex> freed_regs, 288 vector<UnmapInfo> unmaps) 289{ 290 panic("Not sure this function should be called."); 291 292 // Not sure the rename map should be able to access the free list 293 // like this. 294 while (!freed_regs.empty()) { 295 RegIndex free_register = freed_regs.back(); 296 297 if (free_register < numPhysicalIntRegs) { 298 freeList->addIntReg(free_register); 299 } else { 300 // Subtract off the base FP dependence tag. 301 free_register = free_register - numPhysicalIntRegs; 302 freeList->addFloatReg(free_register); 303 } 304 305 freed_regs.pop_back(); 306 } 307 308 // Take unmap info and roll back the rename map. 309} 310 311void 312SimpleRenameMap::markAsReady(PhysRegIndex ready_reg) 313{ 314 DPRINTF(Rename, "Rename map: Marking register %i as ready.\n", 315 (int)ready_reg); 316 317 if (ready_reg < numPhysicalIntRegs) { 318 assert(ready_reg >= 0); 319 320 intScoreboard[ready_reg] = 1; 321 } else if (ready_reg < numPhysicalRegs) { 322 323 // Subtract off the base FP offset. 324// ready_reg = ready_reg - numPhysicalIntRegs; 325 326 floatScoreboard[ready_reg] = 1; 327 } else { 328 //Subtract off the misc registers offset. 329// ready_reg = ready_reg - numPhysicalRegs; 330 331 miscScoreboard[ready_reg] = 1; 332 } 333} 334 | |
335int 336SimpleRenameMap::numFreeEntries() 337{ 338 int free_int_regs = freeList->numFreeIntRegs(); 339 int free_float_regs = freeList->numFreeFloatRegs(); 340 341 if (free_int_regs < free_float_regs) { 342 return free_int_regs; 343 } else { 344 return free_float_regs; 345 } 346} | 234int 235SimpleRenameMap::numFreeEntries() 236{ 237 int free_int_regs = freeList->numFreeIntRegs(); 238 int free_float_regs = freeList->numFreeFloatRegs(); 239 240 if (free_int_regs < free_float_regs) { 241 return free_int_regs; 242 } else { 243 return free_float_regs; 244 } 245} |