Skip to content

Commit 40ddde5

Browse files
committed
[TableGen] Allow targets to entirely ignore Psets for registers
Tablegen currently expects targets to have at least one pressure set for every broader register category. AMDGPU's VGPR or AGPR, for instance, seemed to work correctly without any pset, though we have forced one for each type to avoid the assertion in computeRegUnitSets. However, psets can not be entirely empty. At least one set is mandatory for every target. This patch bypasses the assertion for the classes when GeneratePressureSet is zero while ensuring the RegUnitSets are not empty. Reviewed By: arsenm, rampitec Differential Revision: https://reviews.llvm.org/D110305
1 parent 58d9ed2 commit 40ddde5

File tree

3 files changed

+87
-1
lines changed

3 files changed

+87
-1
lines changed
Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
// RUN: llvm-tblgen -gen-register-info -I %p/../../include -I %p/Common %s | FileCheck %s
2+
3+
// Test to check the bare minimum pressure sets.
4+
// At least one register pressure set is required for the target.
5+
// Allowed the pset only for D_32 regclass and ignored it for all
6+
// other classes including the tuples.
7+
include "llvm/Target/Target.td"
8+
9+
class MyClass<int size, list<ValueType> types, dag registers>
10+
: RegisterClass<"MyTarget", types, size, registers> {
11+
let Size = size;
12+
}
13+
14+
def sub0 : SubRegIndex<32>;
15+
def sub1 : SubRegIndex<32, 32>;
16+
17+
let Namespace = "MyTarget" in {
18+
def D : Register<"d">;
19+
foreach Index = 0-7 in {
20+
def S#Index : Register <"s"#Index>;
21+
}
22+
}
23+
24+
// Should generate psets for D_32
25+
def D_32 : MyClass<32, [i32], (add D)>;
26+
27+
let GeneratePressureSet = 0 in {
28+
def S_32 : MyClass<32, [i32], (sequence "S%u", 0, 7)>;
29+
def SD_32 : MyClass<32, [i32], (add S_32, D_32)>;
30+
}
31+
32+
def S_64 : RegisterTuples<[sub0, sub1],
33+
[(decimate (shl S_32, 0), 1),
34+
(decimate (shl S_32, 1), 1)
35+
]>;
36+
37+
def SReg_64 : MyClass<64, [i64], (add S_64)> {
38+
let GeneratePressureSet = 0;
39+
}
40+
41+
def MyTarget : Target;
42+
43+
// CHECK-LABEL: // Register pressure sets enum.
44+
// CHECK-NEXT: namespace MyTarget {
45+
// CHECK-NEXT: enum RegisterPressureSets {
46+
// CHECK-NEXT: D_32 = 0,
47+
// CHECK-NEXT: };
48+
// NAMESPACE-NEXT: } // end namespace TestNamespace
49+
50+
// CHECK-LABEL: getRegPressureSetName(unsigned Idx) const {
51+
// CHECK-NEXT: static const char *const PressureNameTable[] = {
52+
// CHECK-NEXT: "D_32",
53+
// CHECK-NEXT: };
54+
// CHECK-NEXT: return PressureNameTable[Idx];
55+
// CHECK-NEXT: }
56+
57+
// CHECK: unsigned MyTargetGenRegisterInfo::
58+
// CHECK-NEXT: getRegPressureSetLimit(const MachineFunction &MF, unsigned Idx) const {
59+
// CHECK-NEXT: static const uint8_t PressureLimitTable[] = {
60+
// CHECK-NEXT: {{[0-9]+}}, // 0: D_32
61+
// CHECK-NEXT: };
62+
// CHECK-NEXT: return PressureLimitTable[Idx];
63+
// CHECK-NEXT:}
64+
65+
// CHECK: static const int RCSetsTable[] = {
66+
// CHECK-NEXT: /* 0 */ 0, -1,
67+
// CHECK-NEXT: };

llvm/test/TableGen/empty-psets.td

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
// RUN: not llvm-tblgen -gen-register-info -I %p/../../include -I %p/Common %s 2>&1 | FileCheck %s
2+
3+
// Negative test to check empty Psets for a target.
4+
5+
include "llvm/Target/Target.td"
6+
7+
def R : Register<"r">;
8+
9+
def R_32 : RegisterClass<"MyTarget", [i32], 32, (add R)> {
10+
let GeneratePressureSet = 0;
11+
}
12+
13+
def MyTarget : Target;
14+
15+
// CHECK: error: RegUnitSets cannot be empty!

llvm/utils/TableGen/CodeGenRegisters.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1915,6 +1915,9 @@ void CodeGenRegBank::computeRegUnitSets() {
19151915
RegUnitSets.pop_back();
19161916
}
19171917

1918+
if (RegUnitSets.empty())
1919+
PrintFatalError("RegUnitSets cannot be empty!");
1920+
19181921
LLVM_DEBUG(dbgs() << "\nBefore pruning:\n"; for (unsigned USIdx = 0,
19191922
USEnd = RegUnitSets.size();
19201923
USIdx < USEnd; ++USIdx) {
@@ -2025,7 +2028,8 @@ void CodeGenRegBank::computeRegUnitSets() {
20252028
}
20262029
}
20272030
LLVM_DEBUG(dbgs() << "\n");
2028-
assert(!RegClassUnitSets[RCIdx].empty() && "missing unit set for regclass");
2031+
assert((!RegClassUnitSets[RCIdx].empty() || !RC.GeneratePressureSet) &&
2032+
"missing unit set for regclass");
20292033
}
20302034

20312035
// For each register unit, ensure that we have the list of UnitSets that

0 commit comments

Comments
 (0)