12
12
namespace llvm {
13
13
namespace AMDGPU {
14
14
15
+ // ===----------------------------------------------------------------------===//
16
+ // Custom Operands.
17
+ //
18
+ // A table of custom operands shall describe "primary" operand names first
19
+ // followed by aliases if any. It is not required but recommended to arrange
20
+ // operands so that operand encoding match operand position in the table. This
21
+ // will make getNameFromOperandTable() a bit more efficient. Unused slots in the
22
+ // table shall have an empty name.
23
+ //
24
+ // ===----------------------------------------------------------------------===//
25
+
26
+ // / Map from the encoding of a sendmsg/hwreg asm operand to it's name.
27
+ template <size_t N>
28
+ static StringRef getNameFromOperandTable (const CustomOperand (&Table)[N],
29
+ unsigned Encoding,
30
+ const MCSubtargetInfo &STI) {
31
+ auto isValidIndexForEncoding = [&](size_t Idx) {
32
+ return Idx < N && Table[Idx].Encoding == Encoding &&
33
+ !Table[Idx].Name .empty () &&
34
+ (!Table[Idx].Cond || Table[Idx].Cond (STI));
35
+ };
36
+
37
+ // This is an optimization that should work in most cases. As a side effect,
38
+ // it may cause selection of an alias instead of a primary operand name in
39
+ // case of sparse tables.
40
+ if (isValidIndexForEncoding (Encoding))
41
+ return Table[Encoding].Name ;
42
+
43
+ for (size_t Idx = 0 ; Idx != N; ++Idx)
44
+ if (isValidIndexForEncoding (Idx))
45
+ return Table[Idx].Name ;
46
+
47
+ return " " ;
48
+ }
49
+
50
+ // / Map from a symbolic name for a sendmsg/hwreg asm operand to it's encoding.
51
+ template <size_t N>
52
+ static int64_t getEncodingFromOperandTable (const CustomOperand (&Table)[N],
53
+ StringRef Name,
54
+ const MCSubtargetInfo &STI) {
55
+ int64_t InvalidEncoding = OPR_ID_UNKNOWN;
56
+ for (const CustomOperand &Entry : Table) {
57
+ if (Entry.Name != Name)
58
+ continue ;
59
+
60
+ if (!Entry.Cond || Entry.Cond (STI))
61
+ return Entry.Encoding ;
62
+
63
+ InvalidEncoding = OPR_ID_UNSUPPORTED;
64
+ }
65
+
66
+ return InvalidEncoding;
67
+ }
68
+
15
69
namespace DepCtr {
16
70
17
71
// NOLINTBEGIN
@@ -34,10 +88,11 @@ const int DEP_CTR_SIZE =
34
88
35
89
namespace SendMsg {
36
90
37
- // Disable lint checking for this block since it makes the table unreadable.
91
+ // Disable lint checking here since it makes these tables unreadable.
38
92
// NOLINTBEGIN
39
93
// clang-format off
40
- const CustomOperand<const MCSubtargetInfo &> Msg[] = {
94
+
95
+ static constexpr CustomOperand MsgOperands[] = {
41
96
{{" " }},
42
97
{{" MSG_INTERRUPT" }, ID_INTERRUPT},
43
98
{{" MSG_GS" }, ID_GS_PreGFX11, isNotGFX11Plus},
@@ -63,27 +118,47 @@ const CustomOperand<const MCSubtargetInfo &> Msg[] = {
63
118
{{" MSG_RTN_GET_TBA_TO_PC" }, ID_RTN_GET_TBA_TO_PC, isGFX11Plus},
64
119
{{" MSG_RTN_GET_SE_AID_ID" }, ID_RTN_GET_SE_AID_ID, isGFX12Plus},
65
120
};
121
+
122
+ static constexpr CustomOperand SysMsgOperands[] = {
123
+ {{" " }},
124
+ {{" SYSMSG_OP_ECC_ERR_INTERRUPT" }, OP_SYS_ECC_ERR_INTERRUPT},
125
+ {{" SYSMSG_OP_REG_RD" }, OP_SYS_REG_RD},
126
+ {{" SYSMSG_OP_HOST_TRAP_ACK" }, OP_SYS_HOST_TRAP_ACK, isNotGFX9Plus},
127
+ {{" SYSMSG_OP_TTRACE_PC" }, OP_SYS_TTRACE_PC},
128
+ };
129
+
130
+ static constexpr CustomOperand StreamMsgOperands[] = {
131
+ {{" GS_OP_NOP" }, OP_GS_NOP},
132
+ {{" GS_OP_CUT" }, OP_GS_CUT},
133
+ {{" GS_OP_EMIT" }, OP_GS_EMIT},
134
+ {{" GS_OP_EMIT_CUT" }, OP_GS_EMIT_CUT},
135
+ };
136
+
66
137
// clang-format on
67
138
// NOLINTEND
68
139
69
- const int MSG_SIZE = static_cast <int >(
70
- sizeof (Msg) / sizeof (CustomOperand<const MCSubtargetInfo &>));
140
+ int64_t getMsgId (StringRef Name, const MCSubtargetInfo &STI) {
141
+ return getEncodingFromOperandTable (MsgOperands, Name, STI);
142
+ }
71
143
72
- // These two must be in sync with llvm::AMDGPU::SendMsg::Op enum members, see SIDefines.h.
73
- const char *const OpSysSymbolic[OP_SYS_LAST_] = {
74
- nullptr ,
75
- " SYSMSG_OP_ECC_ERR_INTERRUPT" ,
76
- " SYSMSG_OP_REG_RD" ,
77
- " SYSMSG_OP_HOST_TRAP_ACK" ,
78
- " SYSMSG_OP_TTRACE_PC"
79
- };
144
+ StringRef getMsgName (uint64_t Encoding, const MCSubtargetInfo &STI) {
145
+ return getNameFromOperandTable (MsgOperands, Encoding, STI);
146
+ }
80
147
81
- const char *const OpGsSymbolic[OP_GS_LAST_] = {
82
- " GS_OP_NOP" ,
83
- " GS_OP_CUT" ,
84
- " GS_OP_EMIT" ,
85
- " GS_OP_EMIT_CUT"
86
- };
148
+ int64_t getMsgOpId (int64_t MsgId, StringRef Name, const MCSubtargetInfo &STI) {
149
+ if (MsgId == ID_SYSMSG)
150
+ return getEncodingFromOperandTable (SysMsgOperands, Name, STI);
151
+ return getEncodingFromOperandTable (StreamMsgOperands, Name, STI);
152
+ }
153
+
154
+ StringRef getMsgOpName (int64_t MsgId, uint64_t Encoding,
155
+ const MCSubtargetInfo &STI) {
156
+ assert (msgRequiresOp (MsgId, STI) && " must have an operand" );
157
+
158
+ if (MsgId == ID_SYSMSG)
159
+ return getNameFromOperandTable (SysMsgOperands, Encoding, STI);
160
+ return getNameFromOperandTable (StreamMsgOperands, Encoding, STI);
161
+ }
87
162
88
163
} // namespace SendMsg
89
164
@@ -92,7 +167,7 @@ namespace Hwreg {
92
167
// Disable lint checking for this block since it makes the table unreadable.
93
168
// NOLINTBEGIN
94
169
// clang-format off
95
- const CustomOperand< const MCSubtargetInfo &> Opr [] = {
170
+ static constexpr CustomOperand Operands [] = {
96
171
{{" " }},
97
172
{{" HW_REG_MODE" }, ID_MODE},
98
173
{{" HW_REG_STATUS" }, ID_STATUS},
@@ -155,8 +230,13 @@ const CustomOperand<const MCSubtargetInfo &> Opr[] = {
155
230
// clang-format on
156
231
// NOLINTEND
157
232
158
- const int OPR_SIZE = static_cast <int >(
159
- sizeof (Opr) / sizeof (CustomOperand<const MCSubtargetInfo &>));
233
+ int64_t getHwregId (StringRef Name, const MCSubtargetInfo &STI) {
234
+ return getEncodingFromOperandTable (Operands, Name, STI);
235
+ }
236
+
237
+ StringRef getHwreg (uint64_t Encoding, const MCSubtargetInfo &STI) {
238
+ return getNameFromOperandTable (Operands, Encoding, STI);
239
+ }
160
240
161
241
} // namespace Hwreg
162
242
0 commit comments