aboutsummaryrefslogtreecommitdiff
path: root/backend/lib/CodeGen
diff options
context:
space:
mode:
Diffstat (limited to 'backend/lib/CodeGen')
-rw-r--r--backend/lib/CodeGen/TargetDescription.cpp17
-rw-r--r--backend/lib/CodeGen/TargetRegisterInfo.cpp30
2 files changed, 40 insertions, 7 deletions
diff --git a/backend/lib/CodeGen/TargetDescription.cpp b/backend/lib/CodeGen/TargetDescription.cpp
index b9f7606..e2bbe8a 100644
--- a/backend/lib/CodeGen/TargetDescription.cpp
+++ b/backend/lib/CodeGen/TargetDescription.cpp
@@ -175,10 +175,10 @@ Expected<void> TargetDescription::validateVirtualRegister(Register Reg,
return makeUnexpected(ErrorCode::VerificationError,
"virtual register allocation hint names an unknown physical register");
}
- if (HintDesc->IsConstant || HintDesc->IsArtificial) {
+ if (HintDesc->IsConstant || HintDesc->IsArtificial || HintDesc->IsReserved) {
return makeUnexpected(
ErrorCode::VerificationError,
- "virtual register allocation hint names a constant or artificial register");
+ "virtual register allocation hint names a constant, artificial, or reserved register");
}
if (Info.RegClass && !Registers.registerClassContains(*Info.RegClass, Hint)) {
return makeUnexpected(ErrorCode::VerificationError,
@@ -283,7 +283,8 @@ Expected<void> TargetDescription::validateTargetOperand(const OperandDescriptor
return Registers.regsOverlap(Reserved, PhysRegValue);
});
if (Operand.registerFlags().has(RegisterOperandFlag::Renamable) &&
- (IsReservedOrAlias || PhysRegDesc->IsConstant || PhysRegDesc->IsArtificial)) {
+ (IsReservedOrAlias || PhysRegDesc->IsConstant || PhysRegDesc->IsArtificial ||
+ PhysRegDesc->IsReserved)) {
return makeUnexpected(ErrorCode::VerificationError,
"fixed physical register operand cannot be renamable");
}
@@ -718,9 +719,15 @@ Expected<void> TargetDescription::validateRegisterInfo(const MachineRegisterInfo
if (!Validation)
return std::unexpected(Validation.error());
for (const PhysicalRegister Hint : Info.AllocationHints) {
- if (std::ranges::any_of(RegInfo.reservedRegisters(), [this, Hint](PhysicalRegister Reserved) {
+ const bool IsStaticReservedOrAlias = std::ranges::any_of(
+ Registers.physicalRegisters(), [this, Hint](const PhysicalRegisterDesc &Register) {
+ return Register.IsReserved && Registers.regsOverlap(Register.Reg, Hint);
+ });
+ const bool IsFunctionReservedOrAlias =
+ std::ranges::any_of(RegInfo.reservedRegisters(), [this, Hint](PhysicalRegister Reserved) {
return Registers.regsOverlap(Reserved, Hint);
- })) {
+ });
+ if (IsStaticReservedOrAlias || IsFunctionReservedOrAlias) {
return makeUnexpected(
ErrorCode::VerificationError,
"virtual register allocation hint overlaps a reserved physical register");
diff --git a/backend/lib/CodeGen/TargetRegisterInfo.cpp b/backend/lib/CodeGen/TargetRegisterInfo.cpp
index 3ece639..42ae935 100644
--- a/backend/lib/CodeGen/TargetRegisterInfo.cpp
+++ b/backend/lib/CodeGen/TargetRegisterInfo.cpp
@@ -75,10 +75,19 @@ Expected<TargetRegisterInfo> TargetRegisterInfo::create(TargetRegisterInfoDesc D
}
std::string MIRName = lowerASCII(Register.Name);
if (!Result.RegisterToIndex.emplace(Register.Reg, Index).second ||
+ Result.AlternativeRegisterNameToIndex.contains(MIRName) ||
!Result.RegisterNameToIndex.emplace(MIRName, Index).second) {
return invalidDescription(
"physical register numbers and names must be unique case-insensitively");
}
+ for (const std::string &AlternativeName : Register.AlternativeNames) {
+ const std::string NormalizedName = lowerASCII(AlternativeName);
+ if (AlternativeName.empty() || Result.RegisterNameToIndex.contains(NormalizedName) ||
+ !Result.AlternativeRegisterNameToIndex.emplace(NormalizedName, Index).second) {
+ return invalidDescription(
+ "physical register alternative names must be nonempty and unique case-insensitively");
+ }
+ }
Result.RegisterMIRNames.push_back(std::move(MIRName));
}
@@ -275,9 +284,13 @@ Expected<TargetRegisterInfo> TargetRegisterInfo::create(TargetRegisterInfoDesc D
std::unordered_set<PhysicalRegister> AllocationRegisters;
for (const PhysicalRegister Reg : Class.AllocationOrder) {
- if (!Members.contains(Reg) || !AllocationRegisters.insert(Reg).second) {
+ const PhysicalRegisterDesc *Register = Result.physicalRegister(Reg);
+ const bool IsUnavailable =
+ Register != nullptr &&
+ (Register->IsConstant || Register->IsArtificial || Register->IsReserved);
+ if (!Members.contains(Reg) || IsUnavailable || !AllocationRegisters.insert(Reg).second) {
return invalidDescription(
- "register class allocation order must contain unique class members");
+ "register class allocation order must contain unique allocatable class members");
}
}
if ((Class.Allocatable && Class.AllocationOrder.empty()) ||
@@ -453,6 +466,19 @@ TargetRegisterInfo::physicalRegister(std::string_view Name) const noexcept {
: &Description.PhysicalRegisters[Position->second];
}
+const PhysicalRegisterDesc *
+TargetRegisterInfo::physicalRegisterByAlternativeName(std::string_view Name) const noexcept {
+ const auto Position = AlternativeRegisterNameToIndex.find(lowerASCII(Name));
+ return Position == AlternativeRegisterNameToIndex.end()
+ ? nullptr
+ : &Description.PhysicalRegisters[Position->second];
+}
+
+bool TargetRegisterInfo::isReservedRegister(PhysicalRegister Reg) const noexcept {
+ const PhysicalRegisterDesc *Register = physicalRegister(Reg);
+ return Register != nullptr && Register->IsReserved;
+}
+
const SubRegIndexDesc *TargetRegisterInfo::subRegIndex(SubRegIndex Index) const noexcept {
const auto Position = SubRegIndexToIndex.find(Index);
return Position == SubRegIndexToIndex.end() ? nullptr