| OLD | NEW |
| 1 //===- subzero/src/IceRegAlloc.cpp - Linear-scan implementation -----------===// | 1 //===- subzero/src/IceRegAlloc.cpp - Linear-scan implementation -----------===// |
| 2 // | 2 // |
| 3 // The Subzero Code Generator | 3 // The Subzero Code Generator |
| 4 // | 4 // |
| 5 // This file is distributed under the University of Illinois Open Source | 5 // This file is distributed under the University of Illinois Open Source |
| 6 // License. See LICENSE.TXT for details. | 6 // License. See LICENSE.TXT for details. |
| 7 // | 7 // |
| 8 //===----------------------------------------------------------------------===// | 8 //===----------------------------------------------------------------------===// |
| 9 /// | 9 /// |
| 10 /// \file | 10 /// \file |
| (...skipping 484 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 495 // the current Variable has an unambiguous "first" definition. The preference is | 495 // the current Variable has an unambiguous "first" definition. The preference is |
| 496 // some source Variable of the defining instruction that either is assigned a | 496 // some source Variable of the defining instruction that either is assigned a |
| 497 // register that is currently free, or that is assigned a register that is not | 497 // register that is currently free, or that is assigned a register that is not |
| 498 // free but overlap is allowed. Overlap is allowed when the Variable under | 498 // free but overlap is allowed. Overlap is allowed when the Variable under |
| 499 // consideration is single-definition, and its definition is a simple assignment | 499 // consideration is single-definition, and its definition is a simple assignment |
| 500 // - i.e., the register gets copied/aliased but is never modified. Furthermore, | 500 // - i.e., the register gets copied/aliased but is never modified. Furthermore, |
| 501 // overlap is only allowed when preferred Variable definition instructions do | 501 // overlap is only allowed when preferred Variable definition instructions do |
| 502 // not appear within the current Variable's live range. | 502 // not appear within the current Variable's live range. |
| 503 void LinearScan::findRegisterPreference(IterationState &Iter) { | 503 void LinearScan::findRegisterPreference(IterationState &Iter) { |
| 504 Iter.Prefer = nullptr; | 504 Iter.Prefer = nullptr; |
| 505 Iter.PreferReg = RegNumT::NoRegister; | 505 Iter.PreferReg = RegNumT(); |
| 506 Iter.AllowOverlap = false; | 506 Iter.AllowOverlap = false; |
| 507 | 507 |
| 508 if (!FindPreference) | 508 if (!FindPreference) |
| 509 return; | 509 return; |
| 510 | 510 |
| 511 VariablesMetadata *VMetadata = Func->getVMetadata(); | 511 VariablesMetadata *VMetadata = Func->getVMetadata(); |
| 512 const Inst *DefInst = VMetadata->getFirstDefinitionSingleBlock(Iter.Cur); | 512 const Inst *DefInst = VMetadata->getFirstDefinitionSingleBlock(Iter.Cur); |
| 513 if (DefInst == nullptr) | 513 if (DefInst == nullptr) |
| 514 return; | 514 return; |
| 515 | 515 |
| (...skipping 215 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 731 const SizeT Index = I - 1; | 731 const SizeT Index = I - 1; |
| 732 Variable *Item = Active[Index]; | 732 Variable *Item = Active[Index]; |
| 733 const auto RegNum = Item->getRegNumTmp(); | 733 const auto RegNum = Item->getRegNumTmp(); |
| 734 if (Aliases[RegNum]) { | 734 if (Aliases[RegNum]) { |
| 735 dumpLiveRangeTrace("Evicting A ", Item); | 735 dumpLiveRangeTrace("Evicting A ", Item); |
| 736 const llvm::SmallBitVector &Aliases = *RegAliases[RegNum]; | 736 const llvm::SmallBitVector &Aliases = *RegAliases[RegNum]; |
| 737 for (RegNumT RegAlias : RegNumBVIter(Aliases)) { | 737 for (RegNumT RegAlias : RegNumBVIter(Aliases)) { |
| 738 --RegUses[RegAlias]; | 738 --RegUses[RegAlias]; |
| 739 assert(RegUses[RegAlias] >= 0); | 739 assert(RegUses[RegAlias] >= 0); |
| 740 } | 740 } |
| 741 Item->setRegNumTmp(RegNumT::NoRegister); | 741 Item->setRegNumTmp(RegNumT()); |
| 742 moveItem(Active, Index, Handled); | 742 moveItem(Active, Index, Handled); |
| 743 Evicted.push_back(Item); | 743 Evicted.push_back(Item); |
| 744 } | 744 } |
| 745 } | 745 } |
| 746 // Do the same for Inactive. | 746 // Do the same for Inactive. |
| 747 for (SizeT I = Inactive.size(); I > 0; --I) { | 747 for (SizeT I = Inactive.size(); I > 0; --I) { |
| 748 const SizeT Index = I - 1; | 748 const SizeT Index = I - 1; |
| 749 Variable *Item = Inactive[Index]; | 749 Variable *Item = Inactive[Index]; |
| 750 // Note: The Item->rangeOverlaps(Cur) clause is not part of the description | 750 // Note: The Item->rangeOverlaps(Cur) clause is not part of the description |
| 751 // of AssignMemLoc() in the original paper. But there doesn't seem to be any | 751 // of AssignMemLoc() in the original paper. But there doesn't seem to be any |
| 752 // need to evict an inactive live range that doesn't overlap with the live | 752 // need to evict an inactive live range that doesn't overlap with the live |
| 753 // range currently being considered. It's especially bad if we would end up | 753 // range currently being considered. It's especially bad if we would end up |
| 754 // evicting an infinite-weight but currently-inactive live range. The most | 754 // evicting an infinite-weight but currently-inactive live range. The most |
| 755 // common situation for this would be a scratch register kill set for call | 755 // common situation for this would be a scratch register kill set for call |
| 756 // instructions. | 756 // instructions. |
| 757 if (Aliases[Item->getRegNumTmp()] && Item->rangeOverlaps(Iter.Cur)) { | 757 if (Aliases[Item->getRegNumTmp()] && Item->rangeOverlaps(Iter.Cur)) { |
| 758 dumpLiveRangeTrace("Evicting I ", Item); | 758 dumpLiveRangeTrace("Evicting I ", Item); |
| 759 Item->setRegNumTmp(RegNumT::NoRegister); | 759 Item->setRegNumTmp(RegNumT()); |
| 760 moveItem(Inactive, Index, Handled); | 760 moveItem(Inactive, Index, Handled); |
| 761 Evicted.push_back(Item); | 761 Evicted.push_back(Item); |
| 762 } | 762 } |
| 763 } | 763 } |
| 764 // Assign the register to Cur. | 764 // Assign the register to Cur. |
| 765 Iter.Cur->setRegNumTmp(RegNumT::fromInt(MinWeightIndex)); | 765 Iter.Cur->setRegNumTmp(RegNumT::fromInt(MinWeightIndex)); |
| 766 for (RegNumT RegAlias : RegNumBVIter(Aliases)) { | 766 for (RegNumT RegAlias : RegNumBVIter(Aliases)) { |
| 767 assert(RegUses[RegAlias] >= 0); | 767 assert(RegUses[RegAlias] >= 0); |
| 768 ++RegUses[RegAlias]; | 768 ++RegUses[RegAlias]; |
| 769 } | 769 } |
| (...skipping 241 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1011 Str << "\n"; | 1011 Str << "\n"; |
| 1012 } | 1012 } |
| 1013 Str << "++++++ Inactive:\n"; | 1013 Str << "++++++ Inactive:\n"; |
| 1014 for (const Variable *Item : Inactive) { | 1014 for (const Variable *Item : Inactive) { |
| 1015 dumpLiveRange(Item, Func); | 1015 dumpLiveRange(Item, Func); |
| 1016 Str << "\n"; | 1016 Str << "\n"; |
| 1017 } | 1017 } |
| 1018 } | 1018 } |
| 1019 | 1019 |
| 1020 } // end of namespace Ice | 1020 } // end of namespace Ice |
| OLD | NEW |