diff --git a/llvm/utils/TableGen/Common/CodeGenRegisters.cpp b/llvm/utils/TableGen/Common/CodeGenRegisters.cpp index 6b0b1ccba80fb..b65bb8fc27fc6 100644 --- a/llvm/utils/TableGen/Common/CodeGenRegisters.cpp +++ b/llvm/utils/TableGen/Common/CodeGenRegisters.cpp @@ -2623,6 +2623,55 @@ CodeGenRegBank::getMinimalPhysRegClass(const Record *RegRecord, return BestRC; } +const CodeGenRegisterClass * +CodeGenRegBank::getSuperRegForSubReg(const ValueTypeByHwMode &ValueTy, + const CodeGenSubRegIndex *SubIdx, + bool MustBeAllocatable) const { + std::vector Candidates; + auto &RegClasses = getRegClasses(); + + // Try to find a register class which supports ValueTy, and also contains + // SubIdx. + for (const CodeGenRegisterClass &RC : RegClasses) { + // Is there a subclass of this class which contains this subregister index? + const CodeGenRegisterClass *SubClassWithSubReg = + RC.getSubClassWithSubReg(SubIdx); + if (!SubClassWithSubReg) + continue; + + // We have a class. Check if it supports this value type. + if (!llvm::is_contained(SubClassWithSubReg->VTs, ValueTy)) + continue; + + // If necessary, check that it is allocatable. + if (MustBeAllocatable && !SubClassWithSubReg->Allocatable) + continue; + + // We have a register class which supports both the value type and + // subregister index. Remember it. + Candidates.push_back(SubClassWithSubReg); + } + + // If we didn't find anything, we're done. + if (Candidates.empty()) + return nullptr; + + // Find and return the largest of our candidate classes. + llvm::stable_sort(Candidates, [&](const CodeGenRegisterClass *A, + const CodeGenRegisterClass *B) { + if (A->getMembers().size() > B->getMembers().size()) + return true; + + if (A->getMembers().size() < B->getMembers().size()) + return false; + + // Order by name as a tie-breaker. + return StringRef(A->getName()) < B->getName(); + }); + + return Candidates[0]; +} + BitVector CodeGenRegBank::computeCoveredRegisters(ArrayRef Regs) { SetVector Set; diff --git a/llvm/utils/TableGen/Common/CodeGenRegisters.h b/llvm/utils/TableGen/Common/CodeGenRegisters.h index 75d9a3f7a2c0f..3f4c157fab69a 100644 --- a/llvm/utils/TableGen/Common/CodeGenRegisters.h +++ b/llvm/utils/TableGen/Common/CodeGenRegisters.h @@ -831,6 +831,13 @@ class CodeGenRegBank { getMinimalPhysRegClass(const Record *RegRecord, ValueTypeByHwMode *VT = nullptr); + /// Return the largest register class which supports \p Ty and covers \p + /// SubIdx if it exists. + const CodeGenRegisterClass * + getSuperRegForSubReg(const ValueTypeByHwMode &Ty, + const CodeGenSubRegIndex *SubIdx, + bool MustBeAllocatable = false) const; + // Get the sum of unit weights. unsigned getRegUnitSetWeight(const std::vector &Units) const { unsigned Weight = 0; diff --git a/llvm/utils/TableGen/Common/CodeGenTarget.cpp b/llvm/utils/TableGen/Common/CodeGenTarget.cpp index 303589d7a934a..f519582387db9 100644 --- a/llvm/utils/TableGen/Common/CodeGenTarget.cpp +++ b/llvm/utils/TableGen/Common/CodeGenTarget.cpp @@ -160,54 +160,6 @@ CodeGenRegBank &CodeGenTarget::getRegBank() const { return *RegBank; } -const CodeGenRegisterClass *CodeGenTarget::getSuperRegForSubReg( - const ValueTypeByHwMode &ValueTy, CodeGenRegBank &RegBank, - const CodeGenSubRegIndex *SubIdx, bool MustBeAllocatable) const { - std::vector Candidates; - auto &RegClasses = RegBank.getRegClasses(); - - // Try to find a register class which supports ValueTy, and also contains - // SubIdx. - for (const CodeGenRegisterClass &RC : RegClasses) { - // Is there a subclass of this class which contains this subregister index? - const CodeGenRegisterClass *SubClassWithSubReg = - RC.getSubClassWithSubReg(SubIdx); - if (!SubClassWithSubReg) - continue; - - // We have a class. Check if it supports this value type. - if (!llvm::is_contained(SubClassWithSubReg->VTs, ValueTy)) - continue; - - // If necessary, check that it is allocatable. - if (MustBeAllocatable && !SubClassWithSubReg->Allocatable) - continue; - - // We have a register class which supports both the value type and - // subregister index. Remember it. - Candidates.push_back(SubClassWithSubReg); - } - - // If we didn't find anything, we're done. - if (Candidates.empty()) - return nullptr; - - // Find and return the largest of our candidate classes. - llvm::stable_sort(Candidates, [&](const CodeGenRegisterClass *A, - const CodeGenRegisterClass *B) { - if (A->getMembers().size() > B->getMembers().size()) - return true; - - if (A->getMembers().size() < B->getMembers().size()) - return false; - - // Order by name as a tie-breaker. - return StringRef(A->getName()) < B->getName(); - }); - - return Candidates[0]; -} - /// getRegisterByName - If there is a register with the specific AsmName, /// return it. const CodeGenRegister *CodeGenTarget::getRegisterByName(StringRef Name) const { diff --git a/llvm/utils/TableGen/Common/CodeGenTarget.h b/llvm/utils/TableGen/Common/CodeGenTarget.h index da2f3e060591a..52871f33a301a 100644 --- a/llvm/utils/TableGen/Common/CodeGenTarget.h +++ b/llvm/utils/TableGen/Common/CodeGenTarget.h @@ -122,13 +122,6 @@ class CodeGenTarget { /// getRegBank - Return the register bank description. CodeGenRegBank &getRegBank() const; - /// Return the largest register class on \p RegBank which supports \p Ty and - /// covers \p SubIdx if it exists. - const CodeGenRegisterClass * - getSuperRegForSubReg(const ValueTypeByHwMode &Ty, CodeGenRegBank &RegBank, - const CodeGenSubRegIndex *SubIdx, - bool MustBeAllocatable = false) const; - /// getRegisterByName - If there is a register with the specific AsmName, /// return it. const CodeGenRegister *getRegisterByName(StringRef Name) const; diff --git a/llvm/utils/TableGen/GlobalISelEmitter.cpp b/llvm/utils/TableGen/GlobalISelEmitter.cpp index edaf5299efc39..3ed3509153a15 100644 --- a/llvm/utils/TableGen/GlobalISelEmitter.cpp +++ b/llvm/utils/TableGen/GlobalISelEmitter.cpp @@ -2008,7 +2008,7 @@ const CodeGenRegisterClass *GlobalISelEmitter::inferSuperRegisterClass( // Use the information we found above to find a minimal register class which // supports the subregister and type we want. - return Target.getSuperRegForSubReg(Ty.getValueTypeByHwMode(), CGRegs, SubIdx, + return CGRegs.getSuperRegForSubReg(Ty.getValueTypeByHwMode(), SubIdx, /*MustBeAllocatable=*/true); }