Skip to content

Commit 5977dfb

Browse files
committed
[AMDGPU][MC][NFC] Refactored custom operands handling
The original design of custom operands support assumed that most GPUs have the same or very similar operand names end encodings. This is no longer the case. As a result the support code becomes over-complicated and difficult to maintain. This change implements a different design with the following benefits: - support of aliases; - support of operands with overlapped encodings; - identification of defined but unsupported operands. Differential Revision: https://reviews.llvm.org/D121696
1 parent 0bc451e commit 5977dfb

File tree

6 files changed

+148
-133
lines changed

6 files changed

+148
-133
lines changed

llvm/lib/Target/AMDGPU/AsmParser/AMDGPUAsmParser.cpp

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1542,7 +1542,6 @@ class AMDGPUAsmParser : public MCTargetAsmParser {
15421542
int64_t Id;
15431543
bool IsSymbolic = false;
15441544
bool IsDefined = false;
1545-
StringRef Name;
15461545

15471546
OperandInfoTy(int64_t Id_) : Id(Id_) {}
15481547
};
@@ -6258,9 +6257,8 @@ AMDGPUAsmParser::parseHwregBody(OperandInfoTy &HwReg,
62586257
// The register may be specified by name or using a numeric code
62596258
HwReg.Loc = getLoc();
62606259
if (isToken(AsmToken::Identifier) &&
6261-
(HwReg.Id = getHwregId(getTokenStr(), getSTI())) >= 0) {
6260+
(HwReg.Id = getHwregId(getTokenStr(), getSTI())) != OPR_ID_UNKNOWN) {
62626261
HwReg.IsSymbolic = true;
6263-
HwReg.Name = getTokenStr();
62646262
lex(); // skip register name
62656263
} else if (!parseExpr(HwReg.Id, "a register name")) {
62666264
return false;
@@ -6292,16 +6290,18 @@ AMDGPUAsmParser::validateHwreg(const OperandInfoTy &HwReg,
62926290

62936291
using namespace llvm::AMDGPU::Hwreg;
62946292

6295-
if (HwReg.IsSymbolic &&
6296-
!isValidHwreg(HwReg.Id, getSTI(), HwReg.Name)) {
6297-
Error(HwReg.Loc,
6298-
"specified hardware register is not supported on this GPU");
6299-
return false;
6300-
}
6301-
if (!isValidHwreg(HwReg.Id)) {
6302-
Error(HwReg.Loc,
6303-
"invalid code of hardware register: only 6-bit values are legal");
6304-
return false;
6293+
if (HwReg.IsSymbolic) {
6294+
if (HwReg.Id == OPR_ID_UNSUPPORTED) {
6295+
Error(HwReg.Loc,
6296+
"specified hardware register is not supported on this GPU");
6297+
return false;
6298+
}
6299+
} else {
6300+
if (!isValidHwreg(HwReg.Id)) {
6301+
Error(HwReg.Loc,
6302+
"invalid code of hardware register: only 6-bit values are legal");
6303+
return false;
6304+
}
63056305
}
63066306
if (!isValidHwregOffset(Offset.Id)) {
63076307
Error(Offset.Loc, "invalid bit offset: only 5-bit values are legal");
@@ -6323,7 +6323,7 @@ AMDGPUAsmParser::parseHwreg(OperandVector &Operands) {
63236323
SMLoc Loc = getLoc();
63246324

63256325
if (trySkipId("hwreg", AsmToken::LParen)) {
6326-
OperandInfoTy HwReg(ID_UNKNOWN_);
6326+
OperandInfoTy HwReg(OPR_ID_UNKNOWN);
63276327
OperandInfoTy Offset(OFFSET_DEFAULT_);
63286328
OperandInfoTy Width(WIDTH_DEFAULT_);
63296329
if (parseHwregBody(HwReg, Offset, Width) &&

llvm/lib/Target/AMDGPU/SIDefines.h

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -363,8 +363,6 @@ enum StreamId : unsigned { // Stream ID, (2) [9:8].
363363
namespace Hwreg { // Encoding of SIMM16 used in s_setreg/getreg* insns.
364364

365365
enum Id { // HwRegCode, (6) [5:0]
366-
ID_UNKNOWN_ = -1,
367-
ID_SYMBOLIC_FIRST_ = 1, // There are corresponding symbolic names defined.
368366
ID_MODE = 1,
369367
ID_STATUS = 2,
370368
ID_TRAPSTS = 3,
@@ -373,28 +371,23 @@ enum Id { // HwRegCode, (6) [5:0]
373371
ID_LDS_ALLOC = 6,
374372
ID_IB_STS = 7,
375373
ID_MEM_BASES = 15,
376-
ID_SYMBOLIC_FIRST_GFX9_ = ID_MEM_BASES,
377374
ID_TBA_LO = 16,
378375
ID_TBA_HI = 17,
379376
ID_TMA_LO = 18,
380377
ID_TMA_HI = 19,
381378
ID_XCC_ID = 20,
382-
ID_SYMBOLIC_FIRST_GFX940_ = ID_XCC_ID,
383379
ID_SQ_PERF_SNAPSHOT_DATA = 21,
384380
ID_SQ_PERF_SNAPSHOT_DATA1 = 22,
385381
ID_SQ_PERF_SNAPSHOT_PC_LO = 23,
386382
ID_SQ_PERF_SNAPSHOT_PC_HI = 24,
387-
ID_SYMBOLIC_LAST_GFX940_ = ID_SQ_PERF_SNAPSHOT_PC_HI + 1,
388383
ID_FLAT_SCR_LO = 20,
389-
ID_SYMBOLIC_FIRST_GFX10_ = ID_FLAT_SCR_LO,
390384
ID_FLAT_SCR_HI = 21,
391385
ID_XNACK_MASK = 22,
392386
ID_HW_ID1 = 23,
393387
ID_HW_ID2 = 24,
394388
ID_POPS_PACKER = 25,
395389
ID_SHADER_CYCLES = 29,
396-
ID_SYMBOLIC_FIRST_GFX1030_ = ID_SHADER_CYCLES,
397-
ID_SYMBOLIC_LAST_ = 30,
390+
398391
ID_SHIFT_ = 0,
399392
ID_WIDTH_ = 6,
400393
ID_MASK_ = (((1 << ID_WIDTH_) - 1) << ID_SHIFT_)

llvm/lib/Target/AMDGPU/Utils/AMDGPUAsmUtils.cpp

Lines changed: 55 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,9 @@
66
//
77
//===----------------------------------------------------------------------===//
88
#include "AMDGPUAsmUtils.h"
9+
#include "AMDGPUBaseInfo.h"
910
#include "SIDefines.h"
1011

11-
#include "llvm/ADT/StringRef.h"
12-
1312
namespace llvm {
1413
namespace AMDGPU {
1514
namespace SendMsg {
@@ -54,49 +53,62 @@ const char *const OpGsSymbolic[OP_GS_LAST_] = {
5453

5554
namespace Hwreg {
5655

57-
// This must be in sync with llvm::AMDGPU::Hwreg::ID_SYMBOLIC_FIRST_/LAST_, see SIDefines.h.
58-
const char* const IdSymbolic[] = {
59-
nullptr,
60-
"HW_REG_MODE",
61-
"HW_REG_STATUS",
62-
"HW_REG_TRAPSTS",
63-
"HW_REG_HW_ID",
64-
"HW_REG_GPR_ALLOC",
65-
"HW_REG_LDS_ALLOC",
66-
"HW_REG_IB_STS",
67-
nullptr,
68-
nullptr,
69-
nullptr,
70-
nullptr,
71-
nullptr,
72-
nullptr,
73-
nullptr,
74-
"HW_REG_SH_MEM_BASES",
75-
"HW_REG_TBA_LO",
76-
"HW_REG_TBA_HI",
77-
"HW_REG_TMA_LO",
78-
"HW_REG_TMA_HI",
79-
"HW_REG_FLAT_SCR_LO",
80-
"HW_REG_FLAT_SCR_HI",
81-
"HW_REG_XNACK_MASK",
82-
"HW_REG_HW_ID1",
83-
"HW_REG_HW_ID2",
84-
"HW_REG_POPS_PACKER",
85-
nullptr,
86-
nullptr,
87-
nullptr,
88-
"HW_REG_SHADER_CYCLES"
56+
// Disable lint checking for this block since it makes the table unreadable.
57+
// NOLINTBEGIN
58+
const CustomOperand<const MCSubtargetInfo &> Opr[] = {
59+
{},
60+
{{"HW_REG_MODE"}, ID_MODE},
61+
{{"HW_REG_STATUS"}, ID_STATUS},
62+
{{"HW_REG_TRAPSTS"}, ID_TRAPSTS},
63+
{{"HW_REG_HW_ID"}, ID_HW_ID,
64+
[](const MCSubtargetInfo &STI) {
65+
return isSI(STI) || isCI(STI) ||
66+
isVI(STI) || isGFX9(STI);
67+
}},
68+
{{"HW_REG_GPR_ALLOC"}, ID_GPR_ALLOC},
69+
{{"HW_REG_LDS_ALLOC"}, ID_LDS_ALLOC},
70+
{{"HW_REG_IB_STS"}, ID_IB_STS},
71+
{},
72+
{},
73+
{},
74+
{},
75+
{},
76+
{},
77+
{},
78+
{{"HW_REG_SH_MEM_BASES"}, ID_MEM_BASES, isGFX9Plus},
79+
{{"HW_REG_TBA_LO"}, ID_TBA_LO, isGFX9_GFX10},
80+
{{"HW_REG_TBA_HI"}, ID_TBA_HI, isGFX9_GFX10},
81+
{{"HW_REG_TMA_LO"}, ID_TMA_LO, isGFX9_GFX10},
82+
{{"HW_REG_TMA_HI"}, ID_TMA_HI, isGFX9_GFX10},
83+
{{"HW_REG_FLAT_SCR_LO"}, ID_FLAT_SCR_LO, isGFX10Plus},
84+
{{"HW_REG_FLAT_SCR_HI"}, ID_FLAT_SCR_HI, isGFX10Plus},
85+
{{"HW_REG_XNACK_MASK"}, ID_XNACK_MASK,
86+
[](const MCSubtargetInfo &STI) {
87+
return isGFX10(STI) &&
88+
!AMDGPU::isGFX10_BEncoding(STI);
89+
}},
90+
{{"HW_REG_HW_ID1"}, ID_HW_ID1, isGFX10Plus},
91+
{{"HW_REG_HW_ID2"}, ID_HW_ID2, isGFX10Plus},
92+
{{"HW_REG_POPS_PACKER"}, ID_POPS_PACKER, isGFX10},
93+
{},
94+
{},
95+
{},
96+
{{"HW_REG_SHADER_CYCLES"}, ID_SHADER_CYCLES, isGFX10_BEncoding},
97+
98+
// GFX940 specific registers
99+
{{"HW_REG_XCC_ID"}, ID_XCC_ID, isGFX940},
100+
{{"HW_REG_SQ_PERF_SNAPSHOT_DATA"}, ID_SQ_PERF_SNAPSHOT_DATA, isGFX940},
101+
{{"HW_REG_SQ_PERF_SNAPSHOT_DATA1"}, ID_SQ_PERF_SNAPSHOT_DATA1, isGFX940},
102+
{{"HW_REG_SQ_PERF_SNAPSHOT_PC_LO"}, ID_SQ_PERF_SNAPSHOT_PC_LO, isGFX940},
103+
{{"HW_REG_SQ_PERF_SNAPSHOT_PC_HI"}, ID_SQ_PERF_SNAPSHOT_PC_HI, isGFX940},
104+
105+
// Aliases
106+
{{"HW_REG_HW_ID"}, ID_HW_ID1, isGFX10},
89107
};
108+
// NOLINTEND
90109

91-
// This is gfx940 specific portion from ID_SYMBOLIC_FIRST_GFX940_ to
92-
// ID_SYMBOLIC_LAST_GFX940_
93-
const char* const IdSymbolicGFX940Specific[] = {
94-
"HW_REG_XCC_ID",
95-
"HW_REG_SQ_PERF_SNAPSHOT_DATA",
96-
"HW_REG_SQ_PERF_SNAPSHOT_DATA1",
97-
"HW_REG_SQ_PERF_SNAPSHOT_PC_LO",
98-
"HW_REG_SQ_PERF_SNAPSHOT_PC_HI"
99-
};
110+
const int OPR_SIZE = static_cast<int>(
111+
sizeof(Opr) / sizeof(CustomOperand<const MCSubtargetInfo &>));
100112

101113
} // namespace Hwreg
102114

llvm/lib/Target/AMDGPU/Utils/AMDGPUAsmUtils.h

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,12 +11,24 @@
1111

1212
#include "SIDefines.h"
1313

14+
#include "llvm/ADT/StringRef.h"
15+
1416
namespace llvm {
1517

1618
class StringLiteral;
19+
class MCSubtargetInfo;
1720

1821
namespace AMDGPU {
1922

23+
const int OPR_ID_UNKNOWN = -1;
24+
const int OPR_ID_UNSUPPORTED = -2;
25+
26+
template <class T> struct CustomOperand {
27+
StringLiteral Name = "";
28+
int Encoding = 0;
29+
bool (*Cond)(T Context) = nullptr;
30+
};
31+
2032
namespace SendMsg { // Symbolic names for the sendmsg(...) syntax.
2133

2234
extern const char *const IdSymbolic[ID_GAPS_LAST_];
@@ -27,8 +39,8 @@ extern const char *const OpGsSymbolic[OP_GS_LAST_];
2739

2840
namespace Hwreg { // Symbolic names for the hwreg(...) syntax.
2941

30-
extern const char* const IdSymbolic[];
31-
extern const char* const IdSymbolicGFX940Specific[];
42+
extern const CustomOperand<const MCSubtargetInfo &> Opr[];
43+
extern const int OPR_SIZE;
3244

3345
} // namespace Hwreg
3446

0 commit comments

Comments
 (0)