1//===- offload-tblgen/RecordTypes.cpp - Offload record type wrappers -----===-//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#pragma once
10
11#include <string>
12
13#include "llvm/TableGen/Record.h"
14
15namespace llvm {
16namespace offload {
17namespace tblgen {
18
19class HandleRec {
20public:
21 explicit HandleRec(const Record *rec) : rec(rec) {}
22 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
23 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
24
25private:
26 const Record *rec;
27};
28
29class MacroRec {
30public:
31 explicit MacroRec(const Record *rec) : rec(rec) {
32 auto Name = rec->getValueAsString(FieldName: "name");
33 auto OpenBrace = Name.find_first_of(Chars: "(");
34 nameWithoutArgs = Name.substr(Start: 0, N: OpenBrace);
35 }
36 StringRef getName() const { return nameWithoutArgs; }
37 StringRef getNameWithArgs() const { return rec->getValueAsString(FieldName: "name"); }
38 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
39
40 std::optional<StringRef> getCondition() const {
41 return rec->getValueAsOptionalString(FieldName: "condition");
42 }
43 StringRef getValue() const { return rec->getValueAsString(FieldName: "value"); }
44 std::optional<StringRef> getAltValue() const {
45 return rec->getValueAsOptionalString(FieldName: "alt_value");
46 }
47
48private:
49 const Record *rec;
50 std::string nameWithoutArgs;
51};
52
53class TypedefRec {
54public:
55 explicit TypedefRec(const Record *rec) : rec(rec) {}
56 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
57 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
58 StringRef getValue() const { return rec->getValueAsString(FieldName: "value"); }
59
60private:
61 const Record *rec;
62};
63
64class EnumValueRec {
65public:
66 explicit EnumValueRec(const Record *rec) : rec(rec) {}
67 std::string getName() const { return rec->getValueAsString(FieldName: "name").upper(); }
68 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
69 StringRef getTaggedType() const {
70 return rec->getValueAsString(FieldName: "tagged_type");
71 }
72
73private:
74 const Record *rec;
75};
76
77class EnumRec {
78public:
79 explicit EnumRec(const Record *rec) : rec(rec) {
80 for (const auto *Val : rec->getValueAsListOfDefs(FieldName: "etors")) {
81 vals.emplace_back(args: EnumValueRec{Val});
82 }
83 }
84 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
85 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
86 const std::vector<EnumValueRec> &getValues() const { return vals; }
87
88 std::string getEnumValNamePrefix() const {
89 return StringRef(getName().str().substr(pos: 0, n: getName().str().length() - 2))
90 .upper();
91 }
92
93 bool isTyped() const { return rec->getValueAsBit(FieldName: "is_typed"); }
94
95private:
96 const Record *rec;
97 std::vector<EnumValueRec> vals;
98};
99
100class StructMemberRec {
101public:
102 explicit StructMemberRec(const Record *rec) : rec(rec) {}
103 StringRef getType() const { return rec->getValueAsString(FieldName: "type"); }
104 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
105 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
106 bool isPointerType() const { return getType().ends_with(Suffix: '*'); }
107 bool isHandleType() const { return getType().ends_with(Suffix: "_handle_t"); }
108
109private:
110 const Record *rec;
111};
112
113class StructRec {
114public:
115 explicit StructRec(const Record *rec) : rec(rec) {
116 for (auto *Member : rec->getValueAsListOfDefs(FieldName: "all_members")) {
117 members.emplace_back(args: StructMemberRec(Member));
118 }
119 }
120 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
121 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
122 std::optional<StringRef> getBaseClass() const {
123 return rec->getValueAsOptionalString(FieldName: "base_class");
124 }
125 const std::vector<StructMemberRec> &getMembers() const { return members; }
126
127private:
128 const Record *rec;
129 std::vector<StructMemberRec> members;
130};
131
132class ParamRec {
133public:
134 explicit ParamRec(const Record *rec) : rec(rec) {
135 flags = rec->getValueAsBitsInit(FieldName: "flags");
136 auto *Range = rec->getValueAsDef(FieldName: "range");
137 auto RangeBegin = Range->getValueAsString(FieldName: "begin");
138 auto RangeEnd = Range->getValueAsString(FieldName: "end");
139 if (RangeBegin != "" && RangeEnd != "") {
140 range = {RangeBegin, RangeEnd};
141 } else {
142 range = std::nullopt;
143 }
144
145 auto *TypeInfo = rec->getValueAsDef(FieldName: "type_info");
146 auto TypeInfoEnum = TypeInfo->getValueAsString(FieldName: "enum");
147 auto TypeInfoSize = TypeInfo->getValueAsString(FieldName: "size");
148 if (TypeInfoEnum != "" && TypeInfoSize != "") {
149 typeinfo = {TypeInfoEnum, TypeInfoSize};
150 } else {
151 typeinfo = std::nullopt;
152 }
153 }
154 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
155 StringRef getType() const { return rec->getValueAsString(FieldName: "type"); }
156 bool isPointerType() const { return getType().ends_with(Suffix: '*'); }
157 bool isHandleType() const { return getType().ends_with(Suffix: "_handle_t"); }
158 bool isFptrType() const { return getType().ends_with(Suffix: "_cb_t"); }
159 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
160 bool getFlagBit(unsigned int Bit) const {
161 if (auto *BitValue = dyn_cast<BitInit>(Val: flags->getBit(Bit)))
162 return BitValue->getValue();
163 assert(false && "Parameter flags has no default or set value");
164 return false;
165 }
166 bool isIn() const { return getFlagBit(Bit: 0); }
167 bool isOut() const { return getFlagBit(Bit: 1); }
168 bool isOpt() const { return getFlagBit(Bit: 2); }
169
170 const Record *getRec() const { return rec; }
171 std::optional<std::pair<StringRef, StringRef>> getRange() const {
172 return range;
173 }
174
175 std::optional<std::pair<StringRef, StringRef>> getTypeInfo() const {
176 return typeinfo;
177 }
178
179 // Needed to check whether we're at the back of a vector of params
180 bool operator!=(const ParamRec &p) const { return rec != p.getRec(); }
181
182private:
183 const Record *rec;
184 const BitsInit *flags;
185 std::optional<std::pair<StringRef, StringRef>> range;
186 std::optional<std::pair<StringRef, StringRef>> typeinfo;
187};
188
189class ReturnRec {
190public:
191 ReturnRec(const Record *rec) : rec(rec) {}
192 StringRef getValue() const { return rec->getValueAsString(FieldName: "value"); }
193 // Strip the "OL_ERRC_" from the value, resulting in just "FOO" from
194 // "OL_ERRC_FOO"
195 StringRef getUnprefixedValue() const {
196 constexpr const char *ERRC = "ERRC_";
197 auto Start = getValue().find(Str: ERRC) + strlen(s: ERRC);
198 return getValue().substr(Start);
199 }
200 std::vector<StringRef> getConditions() const {
201 return rec->getValueAsListOfStrings(FieldName: "conditions");
202 }
203
204private:
205 const Record *rec;
206};
207
208class FunctionRec {
209public:
210 FunctionRec(const Record *rec) : rec(rec) {
211 for (auto &Ret : rec->getValueAsListOfDefs(FieldName: "all_returns"))
212 rets.emplace_back(args&: Ret);
213 for (auto &Param : rec->getValueAsListOfDefs(FieldName: "params"))
214 params.emplace_back(args&: Param);
215 }
216
217 std::string getParamStructName() const {
218 return llvm::formatv(Fmt: "{0}_params_t",
219 Vals: llvm::convertToSnakeFromCamelCase(input: getName()));
220 }
221
222 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
223 StringRef getClass() const { return rec->getValueAsString(FieldName: "api_class"); }
224 const std::vector<ReturnRec> &getReturns() const { return rets; }
225 const std::vector<ParamRec> &getParams() const { return params; }
226 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
227 std::vector<StringRef> getDetails() const {
228 return rec->getValueAsListOfStrings(FieldName: "details");
229 }
230 std::vector<StringRef> getAnalogues() const {
231 return rec->getValueAsListOfStrings(FieldName: "analogues");
232 }
233
234private:
235 std::vector<ReturnRec> rets;
236 std::vector<ParamRec> params;
237
238 const Record *rec;
239};
240
241class FptrTypedefRec {
242public:
243 explicit FptrTypedefRec(const Record *rec) : rec(rec) {
244 for (auto &Param : rec->getValueAsListOfDefs(FieldName: "params"))
245 params.emplace_back(args&: Param);
246 }
247 StringRef getName() const { return rec->getValueAsString(FieldName: "name"); }
248 StringRef getDesc() const { return rec->getValueAsString(FieldName: "desc"); }
249 StringRef getReturn() const { return rec->getValueAsString(FieldName: "return"); }
250 const std::vector<ParamRec> &getParams() const { return params; }
251
252private:
253 std::vector<ParamRec> params;
254
255 const Record *rec;
256};
257
258} // namespace tblgen
259} // namespace offload
260} // namespace llvm
261

source code of offload/tools/offload-tblgen/RecordTypes.hpp