1 //===- InstrInfoEmitter.cpp - Generate a Instruction Set Desc. --*- C++ -*-===//
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 // This tablegen backend is responsible for emitting a description of the target
10 // instruction set for the code generator.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #include "Basic/SequenceToOffsetTable.h"
15 #include "Common/CodeGenDAGPatterns.h"
16 #include "Common/CodeGenInstruction.h"
17 #include "Common/CodeGenSchedule.h"
18 #include "Common/CodeGenTarget.h"
19 #include "Common/PredicateExpander.h"
20 #include "Common/SubtargetFeatureInfo.h"
21 #include "Common/Types.h"
22 #include "TableGenBackends.h"
23 #include "llvm/ADT/ArrayRef.h"
24 #include "llvm/ADT/STLExtras.h"
25 #include "llvm/ADT/SmallVector.h"
26 #include "llvm/ADT/StringExtras.h"
27 #include "llvm/Support/Casting.h"
28 #include "llvm/Support/raw_ostream.h"
29 #include "llvm/TableGen/Error.h"
30 #include "llvm/TableGen/Record.h"
31 #include "llvm/TableGen/TableGenBackend.h"
32 #include <cassert>
33 #include <cstdint>
34 #include <iterator>
35 #include <map>
36 #include <string>
37 #include <utility>
38 #include <vector>
39
40 using namespace llvm;
41
42 cl::OptionCategory InstrInfoEmitterCat("Options for -gen-instr-info");
43 static cl::opt<bool> ExpandMIOperandInfo(
44 "instr-info-expand-mi-operand-info",
45 cl::desc("Expand operand's MIOperandInfo DAG into suboperands"),
46 cl::cat(InstrInfoEmitterCat), cl::init(true));
47
48 namespace {
49
50 class InstrInfoEmitter {
51 RecordKeeper &Records;
52 CodeGenDAGPatterns CDP;
53 const CodeGenSchedModels &SchedModels;
54
55 public:
InstrInfoEmitter(RecordKeeper & R)56 InstrInfoEmitter(RecordKeeper &R)
57 : Records(R), CDP(R), SchedModels(CDP.getTargetInfo().getSchedModels()) {}
58
59 // run - Output the instruction set description.
60 void run(raw_ostream &OS);
61
62 private:
63 void emitEnums(raw_ostream &OS);
64
65 typedef std::vector<std::string> OperandInfoTy;
66 typedef std::vector<OperandInfoTy> OperandInfoListTy;
67 typedef std::map<OperandInfoTy, unsigned> OperandInfoMapTy;
68
69 /// The keys of this map are maps which have OpName enum values as their keys
70 /// and instruction operand indices as their values. The values of this map
71 /// are lists of instruction names.
72 typedef std::map<std::map<unsigned, unsigned>, std::vector<std::string>>
73 OpNameMapTy;
74 typedef std::map<std::string, unsigned>::iterator StrUintMapIter;
75
76 /// Generate member functions in the target-specific GenInstrInfo class.
77 ///
78 /// This method is used to custom expand TIIPredicate definitions.
79 /// See file llvm/Target/TargetInstPredicates.td for a description of what is
80 /// a TIIPredicate and how to use it.
81 void emitTIIHelperMethods(raw_ostream &OS, StringRef TargetName,
82 bool ExpandDefinition = true);
83
84 /// Expand TIIPredicate definitions to functions that accept a const MCInst
85 /// reference.
86 void emitMCIIHelperMethods(raw_ostream &OS, StringRef TargetName);
87
88 /// Write verifyInstructionPredicates methods.
89 void emitFeatureVerifier(raw_ostream &OS, const CodeGenTarget &Target);
90 void emitRecord(const CodeGenInstruction &Inst, unsigned Num,
91 Record *InstrInfo,
92 std::map<std::vector<Record *>, unsigned> &EL,
93 const OperandInfoMapTy &OperandInfo, raw_ostream &OS);
94 void emitOperandTypeMappings(
95 raw_ostream &OS, const CodeGenTarget &Target,
96 ArrayRef<const CodeGenInstruction *> NumberedInstructions);
97 void
98 initOperandMapData(ArrayRef<const CodeGenInstruction *> NumberedInstructions,
99 StringRef Namespace,
100 std::map<std::string, unsigned> &Operands,
101 OpNameMapTy &OperandMap);
102 void emitOperandNameMappings(
103 raw_ostream &OS, const CodeGenTarget &Target,
104 ArrayRef<const CodeGenInstruction *> NumberedInstructions);
105
106 void emitLogicalOperandSizeMappings(
107 raw_ostream &OS, StringRef Namespace,
108 ArrayRef<const CodeGenInstruction *> NumberedInstructions);
109 void emitLogicalOperandTypeMappings(
110 raw_ostream &OS, StringRef Namespace,
111 ArrayRef<const CodeGenInstruction *> NumberedInstructions);
112
113 // Operand information.
114 unsigned CollectOperandInfo(OperandInfoListTy &OperandInfoList,
115 OperandInfoMapTy &OperandInfoMap);
116 void EmitOperandInfo(raw_ostream &OS, OperandInfoListTy &OperandInfoList);
117 OperandInfoTy GetOperandInfo(const CodeGenInstruction &Inst);
118 };
119
120 } // end anonymous namespace
121
122 //===----------------------------------------------------------------------===//
123 // Operand Info Emission.
124 //===----------------------------------------------------------------------===//
125
126 InstrInfoEmitter::OperandInfoTy
GetOperandInfo(const CodeGenInstruction & Inst)127 InstrInfoEmitter::GetOperandInfo(const CodeGenInstruction &Inst) {
128 OperandInfoTy Result;
129
130 for (auto &Op : Inst.Operands) {
131 // Handle aggregate operands and normal operands the same way by expanding
132 // either case into a list of operands for this op.
133 std::vector<CGIOperandList::OperandInfo> OperandList;
134
135 // This might be a multiple operand thing. Targets like X86 have
136 // registers in their multi-operand operands. It may also be an anonymous
137 // operand, which has a single operand, but no declared class for the
138 // operand.
139 DagInit *MIOI = Op.MIOperandInfo;
140
141 if (!MIOI || MIOI->getNumArgs() == 0) {
142 // Single, anonymous, operand.
143 OperandList.push_back(Op);
144 } else {
145 for (unsigned j = 0, e = Op.MINumOperands; j != e; ++j) {
146 OperandList.push_back(Op);
147
148 auto *OpR = cast<DefInit>(MIOI->getArg(j))->getDef();
149 OperandList.back().Rec = OpR;
150 }
151 }
152
153 for (unsigned j = 0, e = OperandList.size(); j != e; ++j) {
154 Record *OpR = OperandList[j].Rec;
155 std::string Res;
156
157 if (OpR->isSubClassOf("RegisterOperand"))
158 OpR = OpR->getValueAsDef("RegClass");
159 if (OpR->isSubClassOf("RegisterClass"))
160 Res += getQualifiedName(OpR) + "RegClassID, ";
161 else if (OpR->isSubClassOf("PointerLikeRegClass"))
162 Res += utostr(OpR->getValueAsInt("RegClassKind")) + ", ";
163 else
164 // -1 means the operand does not have a fixed register class.
165 Res += "-1, ";
166
167 // Fill in applicable flags.
168 Res += "0";
169
170 // Ptr value whose register class is resolved via callback.
171 if (OpR->isSubClassOf("PointerLikeRegClass"))
172 Res += "|(1<<MCOI::LookupPtrRegClass)";
173
174 // Predicate operands. Check to see if the original unexpanded operand
175 // was of type PredicateOp.
176 if (Op.Rec->isSubClassOf("PredicateOp"))
177 Res += "|(1<<MCOI::Predicate)";
178
179 // Optional def operands. Check to see if the original unexpanded operand
180 // was of type OptionalDefOperand.
181 if (Op.Rec->isSubClassOf("OptionalDefOperand"))
182 Res += "|(1<<MCOI::OptionalDef)";
183
184 // Branch target operands. Check to see if the original unexpanded
185 // operand was of type BranchTargetOperand.
186 if (Op.Rec->isSubClassOf("BranchTargetOperand"))
187 Res += "|(1<<MCOI::BranchTarget)";
188
189 // Fill in operand type.
190 Res += ", ";
191 assert(!Op.OperandType.empty() && "Invalid operand type.");
192 Res += Op.OperandType;
193
194 // Fill in constraint info.
195 Res += ", ";
196
197 const CGIOperandList::ConstraintInfo &Constraint = Op.Constraints[j];
198 if (Constraint.isNone())
199 Res += "0";
200 else if (Constraint.isEarlyClobber())
201 Res += "MCOI_EARLY_CLOBBER";
202 else {
203 assert(Constraint.isTied());
204 Res += "MCOI_TIED_TO(" + utostr(Constraint.getTiedOperand()) + ")";
205 }
206
207 Result.push_back(Res);
208 }
209 }
210
211 return Result;
212 }
213
214 unsigned
CollectOperandInfo(OperandInfoListTy & OperandInfoList,OperandInfoMapTy & OperandInfoMap)215 InstrInfoEmitter::CollectOperandInfo(OperandInfoListTy &OperandInfoList,
216 OperandInfoMapTy &OperandInfoMap) {
217 const CodeGenTarget &Target = CDP.getTargetInfo();
218 unsigned Offset = 0;
219 for (const CodeGenInstruction *Inst : Target.getInstructionsByEnumValue()) {
220 OperandInfoTy OperandInfo = GetOperandInfo(*Inst);
221 if (OperandInfoMap.insert({OperandInfo, Offset}).second) {
222 OperandInfoList.push_back(OperandInfo);
223 Offset += OperandInfo.size();
224 }
225 }
226 return Offset;
227 }
228
EmitOperandInfo(raw_ostream & OS,OperandInfoListTy & OperandInfoList)229 void InstrInfoEmitter::EmitOperandInfo(raw_ostream &OS,
230 OperandInfoListTy &OperandInfoList) {
231 unsigned Offset = 0;
232 for (auto &OperandInfo : OperandInfoList) {
233 OS << " /* " << Offset << " */";
234 for (auto &Info : OperandInfo)
235 OS << " { " << Info << " },";
236 OS << '\n';
237 Offset += OperandInfo.size();
238 }
239 }
240
241 /// Initialize data structures for generating operand name mappings.
242 ///
243 /// \param Operands [out] A map used to generate the OpName enum with operand
244 /// names as its keys and operand enum values as its values.
245 /// \param OperandMap [out] A map for representing the operand name mappings for
246 /// each instructions. This is used to generate the OperandMap table as
247 /// well as the getNamedOperandIdx() function.
initOperandMapData(ArrayRef<const CodeGenInstruction * > NumberedInstructions,StringRef Namespace,std::map<std::string,unsigned> & Operands,OpNameMapTy & OperandMap)248 void InstrInfoEmitter::initOperandMapData(
249 ArrayRef<const CodeGenInstruction *> NumberedInstructions,
250 StringRef Namespace, std::map<std::string, unsigned> &Operands,
251 OpNameMapTy &OperandMap) {
252 unsigned NumOperands = 0;
253 for (const CodeGenInstruction *Inst : NumberedInstructions) {
254 if (!Inst->TheDef->getValueAsBit("UseNamedOperandTable"))
255 continue;
256 std::map<unsigned, unsigned> OpList;
257 for (const auto &Info : Inst->Operands) {
258 StrUintMapIter I = Operands.find(Info.Name);
259
260 if (I == Operands.end()) {
261 I = Operands.insert(Operands.begin(), std::pair<std::string, unsigned>(
262 Info.Name, NumOperands++));
263 }
264 OpList[I->second] = Info.MIOperandNo;
265 }
266 OperandMap[OpList].push_back(Namespace.str() +
267 "::" + Inst->TheDef->getName().str());
268 }
269 }
270
271 /// Generate a table and function for looking up the indices of operands by
272 /// name.
273 ///
274 /// This code generates:
275 /// - An enum in the llvm::TargetNamespace::OpName namespace, with one entry
276 /// for each operand name.
277 /// - A 2-dimensional table called OperandMap for mapping OpName enum values to
278 /// operand indices.
279 /// - A function called getNamedOperandIdx(uint16_t Opcode, uint16_t NamedIdx)
280 /// for looking up the operand index for an instruction, given a value from
281 /// OpName enum
emitOperandNameMappings(raw_ostream & OS,const CodeGenTarget & Target,ArrayRef<const CodeGenInstruction * > NumberedInstructions)282 void InstrInfoEmitter::emitOperandNameMappings(
283 raw_ostream &OS, const CodeGenTarget &Target,
284 ArrayRef<const CodeGenInstruction *> NumberedInstructions) {
285 StringRef Namespace = Target.getInstNamespace();
286 std::string OpNameNS = "OpName";
287 // Map of operand names to their enumeration value. This will be used to
288 // generate the OpName enum.
289 std::map<std::string, unsigned> Operands;
290 OpNameMapTy OperandMap;
291
292 initOperandMapData(NumberedInstructions, Namespace, Operands, OperandMap);
293
294 OS << "#ifdef GET_INSTRINFO_OPERAND_ENUM\n";
295 OS << "#undef GET_INSTRINFO_OPERAND_ENUM\n";
296 OS << "namespace llvm {\n";
297 OS << "namespace " << Namespace << " {\n";
298 OS << "namespace " << OpNameNS << " {\n";
299 OS << "enum {\n";
300 for (const auto &Op : Operands)
301 OS << " " << Op.first << " = " << Op.second << ",\n";
302
303 OS << " OPERAND_LAST";
304 OS << "\n};\n";
305 OS << "} // end namespace OpName\n";
306 OS << "} // end namespace " << Namespace << "\n";
307 OS << "} // end namespace llvm\n";
308 OS << "#endif //GET_INSTRINFO_OPERAND_ENUM\n\n";
309
310 OS << "#ifdef GET_INSTRINFO_NAMED_OPS\n";
311 OS << "#undef GET_INSTRINFO_NAMED_OPS\n";
312 OS << "namespace llvm {\n";
313 OS << "namespace " << Namespace << " {\n";
314 OS << "LLVM_READONLY\n";
315 OS << "int16_t getNamedOperandIdx(uint16_t Opcode, uint16_t NamedIdx) {\n";
316 if (!Operands.empty()) {
317 OS << " static const int16_t OperandMap [][" << Operands.size()
318 << "] = {\n";
319 for (const auto &Entry : OperandMap) {
320 const std::map<unsigned, unsigned> &OpList = Entry.first;
321 OS << "{";
322
323 // Emit a row of the OperandMap table
324 for (unsigned i = 0, e = Operands.size(); i != e; ++i)
325 OS << (OpList.count(i) == 0 ? -1 : (int)OpList.find(i)->second) << ", ";
326
327 OS << "},\n";
328 }
329 OS << "};\n";
330
331 OS << " switch(Opcode) {\n";
332 unsigned TableIndex = 0;
333 for (const auto &Entry : OperandMap) {
334 for (const std::string &Name : Entry.second)
335 OS << " case " << Name << ":\n";
336
337 OS << " return OperandMap[" << TableIndex++ << "][NamedIdx];\n";
338 }
339 OS << " default: return -1;\n";
340 OS << " }\n";
341 } else {
342 // There are no operands, so no need to emit anything
343 OS << " return -1;\n";
344 }
345 OS << "}\n";
346 OS << "} // end namespace " << Namespace << "\n";
347 OS << "} // end namespace llvm\n";
348 OS << "#endif //GET_INSTRINFO_NAMED_OPS\n\n";
349 }
350
351 /// Generate an enum for all the operand types for this target, under the
352 /// llvm::TargetNamespace::OpTypes namespace.
353 /// Operand types are all definitions derived of the Operand Target.td class.
emitOperandTypeMappings(raw_ostream & OS,const CodeGenTarget & Target,ArrayRef<const CodeGenInstruction * > NumberedInstructions)354 void InstrInfoEmitter::emitOperandTypeMappings(
355 raw_ostream &OS, const CodeGenTarget &Target,
356 ArrayRef<const CodeGenInstruction *> NumberedInstructions) {
357
358 StringRef Namespace = Target.getInstNamespace();
359 std::vector<Record *> Operands = Records.getAllDerivedDefinitions("Operand");
360 std::vector<Record *> RegisterOperands =
361 Records.getAllDerivedDefinitions("RegisterOperand");
362 std::vector<Record *> RegisterClasses =
363 Records.getAllDerivedDefinitions("RegisterClass");
364
365 OS << "#ifdef GET_INSTRINFO_OPERAND_TYPES_ENUM\n";
366 OS << "#undef GET_INSTRINFO_OPERAND_TYPES_ENUM\n";
367 OS << "namespace llvm {\n";
368 OS << "namespace " << Namespace << " {\n";
369 OS << "namespace OpTypes {\n";
370 OS << "enum OperandType {\n";
371
372 unsigned EnumVal = 0;
373 for (const std::vector<Record *> *RecordsToAdd :
374 {&Operands, &RegisterOperands, &RegisterClasses}) {
375 for (const Record *Op : *RecordsToAdd) {
376 if (!Op->isAnonymous())
377 OS << " " << Op->getName() << " = " << EnumVal << ",\n";
378 ++EnumVal;
379 }
380 }
381
382 OS << " OPERAND_TYPE_LIST_END"
383 << "\n};\n";
384 OS << "} // end namespace OpTypes\n";
385 OS << "} // end namespace " << Namespace << "\n";
386 OS << "} // end namespace llvm\n";
387 OS << "#endif // GET_INSTRINFO_OPERAND_TYPES_ENUM\n\n";
388
389 OS << "#ifdef GET_INSTRINFO_OPERAND_TYPE\n";
390 OS << "#undef GET_INSTRINFO_OPERAND_TYPE\n";
391 OS << "namespace llvm {\n";
392 OS << "namespace " << Namespace << " {\n";
393 OS << "LLVM_READONLY\n";
394 OS << "static int getOperandType(uint16_t Opcode, uint16_t OpIdx) {\n";
395 auto getInstrName = [&](int I) -> StringRef {
396 return NumberedInstructions[I]->TheDef->getName();
397 };
398 // TODO: Factor out duplicate operand lists to compress the tables.
399 if (!NumberedInstructions.empty()) {
400 std::vector<int> OperandOffsets;
401 std::vector<Record *> OperandRecords;
402 int CurrentOffset = 0;
403 for (const CodeGenInstruction *Inst : NumberedInstructions) {
404 OperandOffsets.push_back(CurrentOffset);
405 for (const auto &Op : Inst->Operands) {
406 const DagInit *MIOI = Op.MIOperandInfo;
407 if (!ExpandMIOperandInfo || !MIOI || MIOI->getNumArgs() == 0) {
408 // Single, anonymous, operand.
409 OperandRecords.push_back(Op.Rec);
410 ++CurrentOffset;
411 } else {
412 for (Init *Arg : MIOI->getArgs()) {
413 OperandRecords.push_back(cast<DefInit>(Arg)->getDef());
414 ++CurrentOffset;
415 }
416 }
417 }
418 }
419
420 // Emit the table of offsets (indexes) into the operand type table.
421 // Size the unsigned integer offset to save space.
422 assert(OperandRecords.size() <= UINT32_MAX &&
423 "Too many operands for offset table");
424 OS << " static const " << getMinimalTypeForRange(OperandRecords.size());
425 OS << " Offsets[] = {\n";
426 for (int I = 0, E = OperandOffsets.size(); I != E; ++I) {
427 OS << " /* " << getInstrName(I) << " */\n";
428 OS << " " << OperandOffsets[I] << ",\n";
429 }
430 OS << " };\n";
431
432 // Add an entry for the end so that we don't need to special case it below.
433 OperandOffsets.push_back(OperandRecords.size());
434
435 // Emit the actual operand types in a flat table.
436 // Size the signed integer operand type to save space.
437 assert(EnumVal <= INT16_MAX &&
438 "Too many operand types for operand types table");
439 OS << "\n using namespace OpTypes;\n";
440 OS << " static";
441 OS << ((EnumVal <= INT8_MAX) ? " const int8_t" : " const int16_t");
442 OS << " OpcodeOperandTypes[] = {\n ";
443 for (int I = 0, E = OperandRecords.size(), CurOffset = 0; I != E; ++I) {
444 // We print each Opcode's operands in its own row.
445 if (I == OperandOffsets[CurOffset]) {
446 OS << "\n /* " << getInstrName(CurOffset) << " */\n ";
447 while (OperandOffsets[++CurOffset] == I)
448 OS << "/* " << getInstrName(CurOffset) << " */\n ";
449 }
450 Record *OpR = OperandRecords[I];
451 if ((OpR->isSubClassOf("Operand") ||
452 OpR->isSubClassOf("RegisterOperand") ||
453 OpR->isSubClassOf("RegisterClass")) &&
454 !OpR->isAnonymous())
455 OS << OpR->getName();
456 else
457 OS << -1;
458 OS << ", ";
459 }
460 OS << "\n };\n";
461
462 OS << " return OpcodeOperandTypes[Offsets[Opcode] + OpIdx];\n";
463 } else {
464 OS << " llvm_unreachable(\"No instructions defined\");\n";
465 }
466 OS << "}\n";
467 OS << "} // end namespace " << Namespace << "\n";
468 OS << "} // end namespace llvm\n";
469 OS << "#endif // GET_INSTRINFO_OPERAND_TYPE\n\n";
470
471 OS << "#ifdef GET_INSTRINFO_MEM_OPERAND_SIZE\n";
472 OS << "#undef GET_INSTRINFO_MEM_OPERAND_SIZE\n";
473 OS << "namespace llvm {\n";
474 OS << "namespace " << Namespace << " {\n";
475 OS << "LLVM_READONLY\n";
476 OS << "static int getMemOperandSize(int OpType) {\n";
477 OS << " switch (OpType) {\n";
478 std::map<int, SmallVector<StringRef, 0>> SizeToOperandName;
479 for (const Record *Op : Operands) {
480 if (!Op->isSubClassOf("X86MemOperand"))
481 continue;
482 if (int Size = Op->getValueAsInt("Size"))
483 SizeToOperandName[Size].push_back(Op->getName());
484 }
485 OS << " default: return 0;\n";
486 for (const auto &KV : SizeToOperandName) {
487 for (const StringRef &OperandName : KV.second)
488 OS << " case OpTypes::" << OperandName << ":\n";
489 OS << " return " << KV.first << ";\n\n";
490 }
491 OS << " }\n}\n";
492 OS << "} // end namespace " << Namespace << "\n";
493 OS << "} // end namespace llvm\n";
494 OS << "#endif // GET_INSTRINFO_MEM_OPERAND_SIZE\n\n";
495 }
496
emitLogicalOperandSizeMappings(raw_ostream & OS,StringRef Namespace,ArrayRef<const CodeGenInstruction * > NumberedInstructions)497 void InstrInfoEmitter::emitLogicalOperandSizeMappings(
498 raw_ostream &OS, StringRef Namespace,
499 ArrayRef<const CodeGenInstruction *> NumberedInstructions) {
500 std::map<std::vector<unsigned>, unsigned> LogicalOpSizeMap;
501
502 std::map<unsigned, std::vector<std::string>> InstMap;
503
504 size_t LogicalOpListSize = 0U;
505 std::vector<unsigned> LogicalOpList;
506 for (const auto *Inst : NumberedInstructions) {
507 if (!Inst->TheDef->getValueAsBit("UseLogicalOperandMappings"))
508 continue;
509
510 LogicalOpList.clear();
511 llvm::transform(Inst->Operands, std::back_inserter(LogicalOpList),
512 [](const CGIOperandList::OperandInfo &Op) -> unsigned {
513 auto *MIOI = Op.MIOperandInfo;
514 if (!MIOI || MIOI->getNumArgs() == 0)
515 return 1;
516 return MIOI->getNumArgs();
517 });
518 LogicalOpListSize = std::max(LogicalOpList.size(), LogicalOpListSize);
519
520 auto I =
521 LogicalOpSizeMap.insert({LogicalOpList, LogicalOpSizeMap.size()}).first;
522 InstMap[I->second].push_back(
523 (Namespace + "::" + Inst->TheDef->getName()).str());
524 }
525
526 OS << "#ifdef GET_INSTRINFO_LOGICAL_OPERAND_SIZE_MAP\n";
527 OS << "#undef GET_INSTRINFO_LOGICAL_OPERAND_SIZE_MAP\n";
528 OS << "namespace llvm {\n";
529 OS << "namespace " << Namespace << " {\n";
530 OS << "LLVM_READONLY static unsigned\n";
531 OS << "getLogicalOperandSize(uint16_t Opcode, uint16_t LogicalOpIdx) {\n";
532 if (!InstMap.empty()) {
533 std::vector<const std::vector<unsigned> *> LogicalOpSizeList(
534 LogicalOpSizeMap.size());
535 for (auto &P : LogicalOpSizeMap) {
536 LogicalOpSizeList[P.second] = &P.first;
537 }
538 OS << " static const unsigned SizeMap[][" << LogicalOpListSize
539 << "] = {\n";
540 for (auto &R : LogicalOpSizeList) {
541 const auto &Row = *R;
542 OS << " {";
543 int i;
544 for (i = 0; i < static_cast<int>(Row.size()); ++i) {
545 OS << Row[i] << ", ";
546 }
547 for (; i < static_cast<int>(LogicalOpListSize); ++i) {
548 OS << "0, ";
549 }
550 OS << "}, ";
551 OS << "\n";
552 }
553 OS << " };\n";
554
555 OS << " switch (Opcode) {\n";
556 OS << " default: return LogicalOpIdx;\n";
557 for (auto &P : InstMap) {
558 auto OpMapIdx = P.first;
559 const auto &Insts = P.second;
560 for (const auto &Inst : Insts) {
561 OS << " case " << Inst << ":\n";
562 }
563 OS << " return SizeMap[" << OpMapIdx << "][LogicalOpIdx];\n";
564 }
565 OS << " }\n";
566 } else {
567 OS << " return LogicalOpIdx;\n";
568 }
569 OS << "}\n";
570
571 OS << "LLVM_READONLY static inline unsigned\n";
572 OS << "getLogicalOperandIdx(uint16_t Opcode, uint16_t LogicalOpIdx) {\n";
573 OS << " auto S = 0U;\n";
574 OS << " for (auto i = 0U; i < LogicalOpIdx; ++i)\n";
575 OS << " S += getLogicalOperandSize(Opcode, i);\n";
576 OS << " return S;\n";
577 OS << "}\n";
578
579 OS << "} // end namespace " << Namespace << "\n";
580 OS << "} // end namespace llvm\n";
581 OS << "#endif // GET_INSTRINFO_LOGICAL_OPERAND_SIZE_MAP\n\n";
582 }
583
emitLogicalOperandTypeMappings(raw_ostream & OS,StringRef Namespace,ArrayRef<const CodeGenInstruction * > NumberedInstructions)584 void InstrInfoEmitter::emitLogicalOperandTypeMappings(
585 raw_ostream &OS, StringRef Namespace,
586 ArrayRef<const CodeGenInstruction *> NumberedInstructions) {
587 std::map<std::vector<std::string>, unsigned> LogicalOpTypeMap;
588
589 std::map<unsigned, std::vector<std::string>> InstMap;
590
591 size_t OpTypeListSize = 0U;
592 std::vector<std::string> LogicalOpTypeList;
593 for (const auto *Inst : NumberedInstructions) {
594 if (!Inst->TheDef->getValueAsBit("UseLogicalOperandMappings"))
595 continue;
596
597 LogicalOpTypeList.clear();
598 for (const auto &Op : Inst->Operands) {
599 auto *OpR = Op.Rec;
600 if ((OpR->isSubClassOf("Operand") ||
601 OpR->isSubClassOf("RegisterOperand") ||
602 OpR->isSubClassOf("RegisterClass")) &&
603 !OpR->isAnonymous()) {
604 LogicalOpTypeList.push_back(
605 (Namespace + "::OpTypes::" + Op.Rec->getName()).str());
606 } else {
607 LogicalOpTypeList.push_back("-1");
608 }
609 }
610 OpTypeListSize = std::max(LogicalOpTypeList.size(), OpTypeListSize);
611
612 auto I =
613 LogicalOpTypeMap.insert({LogicalOpTypeList, LogicalOpTypeMap.size()})
614 .first;
615 InstMap[I->second].push_back(
616 (Namespace + "::" + Inst->TheDef->getName()).str());
617 }
618
619 OS << "#ifdef GET_INSTRINFO_LOGICAL_OPERAND_TYPE_MAP\n";
620 OS << "#undef GET_INSTRINFO_LOGICAL_OPERAND_TYPE_MAP\n";
621 OS << "namespace llvm {\n";
622 OS << "namespace " << Namespace << " {\n";
623 OS << "LLVM_READONLY static int\n";
624 OS << "getLogicalOperandType(uint16_t Opcode, uint16_t LogicalOpIdx) {\n";
625 if (!InstMap.empty()) {
626 std::vector<const std::vector<std::string> *> LogicalOpTypeList(
627 LogicalOpTypeMap.size());
628 for (auto &P : LogicalOpTypeMap) {
629 LogicalOpTypeList[P.second] = &P.first;
630 }
631 OS << " static const int TypeMap[][" << OpTypeListSize << "] = {\n";
632 for (int r = 0, rs = LogicalOpTypeList.size(); r < rs; ++r) {
633 const auto &Row = *LogicalOpTypeList[r];
634 OS << " {";
635 int i, s = Row.size();
636 for (i = 0; i < s; ++i) {
637 if (i > 0)
638 OS << ", ";
639 OS << Row[i];
640 }
641 for (; i < static_cast<int>(OpTypeListSize); ++i) {
642 if (i > 0)
643 OS << ", ";
644 OS << "-1";
645 }
646 OS << "}";
647 if (r != rs - 1)
648 OS << ",";
649 OS << "\n";
650 }
651 OS << " };\n";
652
653 OS << " switch (Opcode) {\n";
654 OS << " default: return -1;\n";
655 for (auto &P : InstMap) {
656 auto OpMapIdx = P.first;
657 const auto &Insts = P.second;
658 for (const auto &Inst : Insts) {
659 OS << " case " << Inst << ":\n";
660 }
661 OS << " return TypeMap[" << OpMapIdx << "][LogicalOpIdx];\n";
662 }
663 OS << " }\n";
664 } else {
665 OS << " return -1;\n";
666 }
667 OS << "}\n";
668 OS << "} // end namespace " << Namespace << "\n";
669 OS << "} // end namespace llvm\n";
670 OS << "#endif // GET_INSTRINFO_LOGICAL_OPERAND_TYPE_MAP\n\n";
671 }
672
emitMCIIHelperMethods(raw_ostream & OS,StringRef TargetName)673 void InstrInfoEmitter::emitMCIIHelperMethods(raw_ostream &OS,
674 StringRef TargetName) {
675 RecVec TIIPredicates = Records.getAllDerivedDefinitions("TIIPredicate");
676
677 OS << "#ifdef GET_INSTRINFO_MC_HELPER_DECLS\n";
678 OS << "#undef GET_INSTRINFO_MC_HELPER_DECLS\n\n";
679
680 OS << "namespace llvm {\n";
681 OS << "class MCInst;\n";
682 OS << "class FeatureBitset;\n\n";
683
684 OS << "namespace " << TargetName << "_MC {\n\n";
685
686 for (const Record *Rec : TIIPredicates) {
687 OS << "bool " << Rec->getValueAsString("FunctionName")
688 << "(const MCInst &MI);\n";
689 }
690
691 OS << "void verifyInstructionPredicates(unsigned Opcode, const FeatureBitset "
692 "&Features);\n";
693
694 OS << "\n} // end namespace " << TargetName << "_MC\n";
695 OS << "} // end namespace llvm\n\n";
696
697 OS << "#endif // GET_INSTRINFO_MC_HELPER_DECLS\n\n";
698
699 OS << "#ifdef GET_INSTRINFO_MC_HELPERS\n";
700 OS << "#undef GET_INSTRINFO_MC_HELPERS\n\n";
701
702 OS << "namespace llvm {\n";
703 OS << "namespace " << TargetName << "_MC {\n\n";
704
705 PredicateExpander PE(TargetName);
706 PE.setExpandForMC(true);
707
708 for (const Record *Rec : TIIPredicates) {
709 OS << "bool " << Rec->getValueAsString("FunctionName");
710 OS << "(const MCInst &MI) {\n";
711
712 OS.indent(PE.getIndentLevel() * 2);
713 PE.expandStatement(OS, Rec->getValueAsDef("Body"));
714 OS << "\n}\n\n";
715 }
716
717 OS << "} // end namespace " << TargetName << "_MC\n";
718 OS << "} // end namespace llvm\n\n";
719
720 OS << "#endif // GET_GENISTRINFO_MC_HELPERS\n\n";
721 }
722
723 static std::string
getNameForFeatureBitset(const std::vector<Record * > & FeatureBitset)724 getNameForFeatureBitset(const std::vector<Record *> &FeatureBitset) {
725 std::string Name = "CEFBS";
726 for (const auto &Feature : FeatureBitset)
727 Name += ("_" + Feature->getName()).str();
728 return Name;
729 }
730
emitFeatureVerifier(raw_ostream & OS,const CodeGenTarget & Target)731 void InstrInfoEmitter::emitFeatureVerifier(raw_ostream &OS,
732 const CodeGenTarget &Target) {
733 const auto &All = SubtargetFeatureInfo::getAll(Records);
734 std::map<Record *, SubtargetFeatureInfo, LessRecordByID> SubtargetFeatures;
735 SubtargetFeatures.insert(All.begin(), All.end());
736
737 OS << "#if (defined(ENABLE_INSTR_PREDICATE_VERIFIER) && !defined(NDEBUG)) "
738 << "||\\\n"
739 << " defined(GET_AVAILABLE_OPCODE_CHECKER)\n"
740 << "#define GET_COMPUTE_FEATURES\n"
741 << "#endif\n";
742 OS << "#ifdef GET_COMPUTE_FEATURES\n"
743 << "#undef GET_COMPUTE_FEATURES\n"
744 << "namespace llvm {\n"
745 << "namespace " << Target.getName() << "_MC {\n\n";
746
747 // Emit the subtarget feature enumeration.
748 SubtargetFeatureInfo::emitSubtargetFeatureBitEnumeration(SubtargetFeatures,
749 OS);
750 // Emit the available features compute function.
751 OS << "inline ";
752 SubtargetFeatureInfo::emitComputeAssemblerAvailableFeatures(
753 Target.getName(), "", "computeAvailableFeatures", SubtargetFeatures, OS);
754
755 std::vector<std::vector<Record *>> FeatureBitsets;
756 for (const CodeGenInstruction *Inst : Target.getInstructionsByEnumValue()) {
757 FeatureBitsets.emplace_back();
758 for (Record *Predicate : Inst->TheDef->getValueAsListOfDefs("Predicates")) {
759 const auto &I = SubtargetFeatures.find(Predicate);
760 if (I != SubtargetFeatures.end())
761 FeatureBitsets.back().push_back(I->second.TheDef);
762 }
763 }
764
765 llvm::sort(FeatureBitsets, [&](const std::vector<Record *> &A,
766 const std::vector<Record *> &B) {
767 if (A.size() < B.size())
768 return true;
769 if (A.size() > B.size())
770 return false;
771 for (auto Pair : zip(A, B)) {
772 if (std::get<0>(Pair)->getName() < std::get<1>(Pair)->getName())
773 return true;
774 if (std::get<0>(Pair)->getName() > std::get<1>(Pair)->getName())
775 return false;
776 }
777 return false;
778 });
779 FeatureBitsets.erase(llvm::unique(FeatureBitsets), FeatureBitsets.end());
780 OS << "inline FeatureBitset computeRequiredFeatures(unsigned Opcode) {\n"
781 << " enum : " << getMinimalTypeForRange(FeatureBitsets.size()) << " {\n"
782 << " CEFBS_None,\n";
783 for (const auto &FeatureBitset : FeatureBitsets) {
784 if (FeatureBitset.empty())
785 continue;
786 OS << " " << getNameForFeatureBitset(FeatureBitset) << ",\n";
787 }
788 OS << " };\n\n"
789 << " static constexpr FeatureBitset FeatureBitsets[] = {\n"
790 << " {}, // CEFBS_None\n";
791 for (const auto &FeatureBitset : FeatureBitsets) {
792 if (FeatureBitset.empty())
793 continue;
794 OS << " {";
795 for (const auto &Feature : FeatureBitset) {
796 const auto &I = SubtargetFeatures.find(Feature);
797 assert(I != SubtargetFeatures.end() && "Didn't import predicate?");
798 OS << I->second.getEnumBitName() << ", ";
799 }
800 OS << "},\n";
801 }
802 OS << " };\n"
803 << " static constexpr " << getMinimalTypeForRange(FeatureBitsets.size())
804 << " RequiredFeaturesRefs[] = {\n";
805 unsigned InstIdx = 0;
806 for (const CodeGenInstruction *Inst : Target.getInstructionsByEnumValue()) {
807 OS << " CEFBS";
808 unsigned NumPredicates = 0;
809 for (Record *Predicate : Inst->TheDef->getValueAsListOfDefs("Predicates")) {
810 const auto &I = SubtargetFeatures.find(Predicate);
811 if (I != SubtargetFeatures.end()) {
812 OS << '_' << I->second.TheDef->getName();
813 NumPredicates++;
814 }
815 }
816 if (!NumPredicates)
817 OS << "_None";
818 OS << ", // " << Inst->TheDef->getName() << " = " << InstIdx << "\n";
819 InstIdx++;
820 }
821 OS << " };\n\n"
822 << " assert(Opcode < " << InstIdx << ");\n"
823 << " return FeatureBitsets[RequiredFeaturesRefs[Opcode]];\n"
824 << "}\n\n";
825
826 OS << "} // end namespace " << Target.getName() << "_MC\n"
827 << "} // end namespace llvm\n"
828 << "#endif // GET_COMPUTE_FEATURES\n\n";
829
830 OS << "#ifdef GET_AVAILABLE_OPCODE_CHECKER\n"
831 << "#undef GET_AVAILABLE_OPCODE_CHECKER\n"
832 << "namespace llvm {\n"
833 << "namespace " << Target.getName() << "_MC {\n";
834 OS << "bool isOpcodeAvailable("
835 << "unsigned Opcode, const FeatureBitset &Features) {\n"
836 << " FeatureBitset AvailableFeatures = "
837 << "computeAvailableFeatures(Features);\n"
838 << " FeatureBitset RequiredFeatures = "
839 << "computeRequiredFeatures(Opcode);\n"
840 << " FeatureBitset MissingFeatures =\n"
841 << " (AvailableFeatures & RequiredFeatures) ^\n"
842 << " RequiredFeatures;\n"
843 << " return !MissingFeatures.any();\n"
844 << "}\n";
845 OS << "} // end namespace " << Target.getName() << "_MC\n"
846 << "} // end namespace llvm\n"
847 << "#endif // GET_AVAILABLE_OPCODE_CHECKER\n\n";
848
849 OS << "#ifdef ENABLE_INSTR_PREDICATE_VERIFIER\n"
850 << "#undef ENABLE_INSTR_PREDICATE_VERIFIER\n"
851 << "#include <sstream>\n\n";
852
853 OS << "namespace llvm {\n";
854 OS << "namespace " << Target.getName() << "_MC {\n\n";
855
856 // Emit the name table for error messages.
857 OS << "#ifndef NDEBUG\n";
858 SubtargetFeatureInfo::emitNameTable(SubtargetFeatures, OS);
859 OS << "#endif // NDEBUG\n\n";
860
861 // Emit the predicate verifier.
862 OS << "void verifyInstructionPredicates(\n"
863 << " unsigned Opcode, const FeatureBitset &Features) {\n"
864 << "#ifndef NDEBUG\n";
865 OS << " FeatureBitset AvailableFeatures = "
866 "computeAvailableFeatures(Features);\n";
867 OS << " FeatureBitset RequiredFeatures = "
868 << "computeRequiredFeatures(Opcode);\n";
869 OS << " FeatureBitset MissingFeatures =\n"
870 << " (AvailableFeatures & RequiredFeatures) ^\n"
871 << " RequiredFeatures;\n"
872 << " if (MissingFeatures.any()) {\n"
873 << " std::ostringstream Msg;\n"
874 << " Msg << \"Attempting to emit \" << &" << Target.getName()
875 << "InstrNameData[" << Target.getName() << "InstrNameIndices[Opcode]]\n"
876 << " << \" instruction but the \";\n"
877 << " for (unsigned i = 0, e = MissingFeatures.size(); i != e; ++i)\n"
878 << " if (MissingFeatures.test(i))\n"
879 << " Msg << SubtargetFeatureNames[i] << \" \";\n"
880 << " Msg << \"predicate(s) are not met\";\n"
881 << " report_fatal_error(Msg.str().c_str());\n"
882 << " }\n"
883 << "#endif // NDEBUG\n";
884 OS << "}\n";
885 OS << "} // end namespace " << Target.getName() << "_MC\n";
886 OS << "} // end namespace llvm\n";
887 OS << "#endif // ENABLE_INSTR_PREDICATE_VERIFIER\n\n";
888 }
889
emitTIIHelperMethods(raw_ostream & OS,StringRef TargetName,bool ExpandDefinition)890 void InstrInfoEmitter::emitTIIHelperMethods(raw_ostream &OS,
891 StringRef TargetName,
892 bool ExpandDefinition) {
893 RecVec TIIPredicates = Records.getAllDerivedDefinitions("TIIPredicate");
894 if (TIIPredicates.empty())
895 return;
896
897 PredicateExpander PE(TargetName);
898 PE.setExpandForMC(false);
899
900 for (const Record *Rec : TIIPredicates) {
901 OS << (ExpandDefinition ? "" : "static ") << "bool ";
902 if (ExpandDefinition)
903 OS << TargetName << "InstrInfo::";
904 OS << Rec->getValueAsString("FunctionName");
905 OS << "(const MachineInstr &MI)";
906 if (!ExpandDefinition) {
907 OS << ";\n";
908 continue;
909 }
910
911 OS << " {\n";
912 OS.indent(PE.getIndentLevel() * 2);
913 PE.expandStatement(OS, Rec->getValueAsDef("Body"));
914 OS << "\n}\n\n";
915 }
916 }
917
918 //===----------------------------------------------------------------------===//
919 // Main Output.
920 //===----------------------------------------------------------------------===//
921
922 // run - Emit the main instruction description records for the target...
run(raw_ostream & OS)923 void InstrInfoEmitter::run(raw_ostream &OS) {
924 emitSourceFileHeader("Target Instruction Enum Values and Descriptors", OS);
925 emitEnums(OS);
926
927 CodeGenTarget &Target = CDP.getTargetInfo();
928 const std::string &TargetName = std::string(Target.getName());
929 Record *InstrInfo = Target.getInstructionSet();
930
931 // Collect all of the operand info records.
932 Records.startTimer("Collect operand info");
933 OperandInfoListTy OperandInfoList;
934 OperandInfoMapTy OperandInfoMap;
935 unsigned OperandInfoSize =
936 CollectOperandInfo(OperandInfoList, OperandInfoMap);
937
938 // Collect all of the instruction's implicit uses and defs.
939 Records.startTimer("Collect uses/defs");
940 std::map<std::vector<Record *>, unsigned> EmittedLists;
941 std::vector<std::vector<Record *>> ImplicitLists;
942 unsigned ImplicitListSize = 0;
943 for (const CodeGenInstruction *II : Target.getInstructionsByEnumValue()) {
944 std::vector<Record *> ImplicitOps = II->ImplicitUses;
945 llvm::append_range(ImplicitOps, II->ImplicitDefs);
946 if (EmittedLists.insert({ImplicitOps, ImplicitListSize}).second) {
947 ImplicitLists.push_back(ImplicitOps);
948 ImplicitListSize += ImplicitOps.size();
949 }
950 }
951
952 ArrayRef<const CodeGenInstruction *> NumberedInstructions =
953 Target.getInstructionsByEnumValue();
954 OS << "#if defined(GET_INSTRINFO_MC_DESC) || "
955 "defined(GET_INSTRINFO_CTOR_DTOR)\n";
956 OS << "namespace llvm {\n\n";
957
958 OS << "struct " << TargetName << "InstrTable {\n";
959 OS << " MCInstrDesc Insts[" << NumberedInstructions.size() << "];\n";
960 OS << " static_assert(alignof(MCInstrDesc) >= alignof(MCOperandInfo), "
961 "\"Unwanted padding between Insts and OperandInfo\");\n";
962 OS << " MCOperandInfo OperandInfo[" << OperandInfoSize << "];\n";
963 OS << " static_assert(alignof(MCOperandInfo) >= alignof(MCPhysReg), "
964 "\"Unwanted padding between OperandInfo and ImplicitOps\");\n";
965 OS << " MCPhysReg ImplicitOps[" << std::max(ImplicitListSize, 1U) << "];\n";
966 OS << "};\n\n";
967
968 OS << "} // end namespace llvm\n";
969 OS << "#endif // defined(GET_INSTRINFO_MC_DESC) || "
970 "defined(GET_INSTRINFO_CTOR_DTOR)\n\n";
971
972 OS << "#ifdef GET_INSTRINFO_MC_DESC\n";
973 OS << "#undef GET_INSTRINFO_MC_DESC\n";
974 OS << "namespace llvm {\n\n";
975
976 // Emit all of the MCInstrDesc records in reverse ENUM ordering.
977 Records.startTimer("Emit InstrDesc records");
978 OS << "static_assert(sizeof(MCOperandInfo) % sizeof(MCPhysReg) == 0);\n";
979 OS << "static constexpr unsigned " << TargetName << "ImpOpBase = sizeof "
980 << TargetName << "InstrTable::OperandInfo / (sizeof(MCPhysReg));\n\n";
981
982 OS << "extern const " << TargetName << "InstrTable " << TargetName
983 << "Descs = {\n {\n";
984 SequenceToOffsetTable<std::string> InstrNames;
985 unsigned Num = NumberedInstructions.size();
986 for (const CodeGenInstruction *Inst : reverse(NumberedInstructions)) {
987 // Keep a list of the instruction names.
988 InstrNames.add(std::string(Inst->TheDef->getName()));
989 // Emit the record into the table.
990 emitRecord(*Inst, --Num, InstrInfo, EmittedLists, OperandInfoMap, OS);
991 }
992
993 OS << " }, {\n";
994
995 // Emit all of the operand info records.
996 Records.startTimer("Emit operand info");
997 EmitOperandInfo(OS, OperandInfoList);
998
999 OS << " }, {\n";
1000
1001 // Emit all of the instruction's implicit uses and defs.
1002 Records.startTimer("Emit uses/defs");
1003 for (auto &List : ImplicitLists) {
1004 OS << " /* " << EmittedLists[List] << " */";
1005 for (auto &Reg : List)
1006 OS << ' ' << getQualifiedName(Reg) << ',';
1007 OS << '\n';
1008 }
1009
1010 OS << " }\n};\n\n";
1011
1012 // Emit the array of instruction names.
1013 Records.startTimer("Emit instruction names");
1014 InstrNames.layout();
1015 InstrNames.emitStringLiteralDef(OS, Twine("extern const char ") + TargetName +
1016 "InstrNameData[]");
1017
1018 OS << "extern const unsigned " << TargetName << "InstrNameIndices[] = {";
1019 Num = 0;
1020 for (const CodeGenInstruction *Inst : NumberedInstructions) {
1021 // Newline every eight entries.
1022 if (Num % 8 == 0)
1023 OS << "\n ";
1024 OS << InstrNames.get(std::string(Inst->TheDef->getName())) << "U, ";
1025 ++Num;
1026 }
1027 OS << "\n};\n\n";
1028
1029 bool HasDeprecationFeatures =
1030 llvm::any_of(NumberedInstructions, [](const CodeGenInstruction *Inst) {
1031 return !Inst->HasComplexDeprecationPredicate &&
1032 !Inst->DeprecatedReason.empty();
1033 });
1034 if (HasDeprecationFeatures) {
1035 OS << "extern const uint8_t " << TargetName
1036 << "InstrDeprecationFeatures[] = {";
1037 Num = 0;
1038 for (const CodeGenInstruction *Inst : NumberedInstructions) {
1039 if (Num % 8 == 0)
1040 OS << "\n ";
1041 if (!Inst->HasComplexDeprecationPredicate &&
1042 !Inst->DeprecatedReason.empty())
1043 OS << Target.getInstNamespace() << "::" << Inst->DeprecatedReason
1044 << ", ";
1045 else
1046 OS << "uint8_t(-1), ";
1047 ++Num;
1048 }
1049 OS << "\n};\n\n";
1050 }
1051
1052 bool HasComplexDeprecationInfos =
1053 llvm::any_of(NumberedInstructions, [](const CodeGenInstruction *Inst) {
1054 return Inst->HasComplexDeprecationPredicate;
1055 });
1056 if (HasComplexDeprecationInfos) {
1057 OS << "extern const MCInstrInfo::ComplexDeprecationPredicate " << TargetName
1058 << "InstrComplexDeprecationInfos[] = {";
1059 Num = 0;
1060 for (const CodeGenInstruction *Inst : NumberedInstructions) {
1061 if (Num % 8 == 0)
1062 OS << "\n ";
1063 if (Inst->HasComplexDeprecationPredicate)
1064 // Emit a function pointer to the complex predicate method.
1065 OS << "&get" << Inst->DeprecatedReason << "DeprecationInfo, ";
1066 else
1067 OS << "nullptr, ";
1068 ++Num;
1069 }
1070 OS << "\n};\n\n";
1071 }
1072
1073 // MCInstrInfo initialization routine.
1074 Records.startTimer("Emit initialization routine");
1075 OS << "static inline void Init" << TargetName
1076 << "MCInstrInfo(MCInstrInfo *II) {\n";
1077 OS << " II->InitMCInstrInfo(" << TargetName << "Descs.Insts, " << TargetName
1078 << "InstrNameIndices, " << TargetName << "InstrNameData, ";
1079 if (HasDeprecationFeatures)
1080 OS << TargetName << "InstrDeprecationFeatures, ";
1081 else
1082 OS << "nullptr, ";
1083 if (HasComplexDeprecationInfos)
1084 OS << TargetName << "InstrComplexDeprecationInfos, ";
1085 else
1086 OS << "nullptr, ";
1087 OS << NumberedInstructions.size() << ");\n}\n\n";
1088
1089 OS << "} // end namespace llvm\n";
1090
1091 OS << "#endif // GET_INSTRINFO_MC_DESC\n\n";
1092
1093 // Create a TargetInstrInfo subclass to hide the MC layer initialization.
1094 OS << "#ifdef GET_INSTRINFO_HEADER\n";
1095 OS << "#undef GET_INSTRINFO_HEADER\n";
1096
1097 std::string ClassName = TargetName + "GenInstrInfo";
1098 OS << "namespace llvm {\n";
1099 OS << "struct " << ClassName << " : public TargetInstrInfo {\n"
1100 << " explicit " << ClassName
1101 << "(unsigned CFSetupOpcode = ~0u, unsigned CFDestroyOpcode = ~0u, "
1102 "unsigned CatchRetOpcode = ~0u, unsigned ReturnOpcode = ~0u);\n"
1103 << " ~" << ClassName << "() override = default;\n";
1104
1105 OS << "\n};\n} // end namespace llvm\n";
1106
1107 OS << "#endif // GET_INSTRINFO_HEADER\n\n";
1108
1109 OS << "#ifdef GET_INSTRINFO_HELPER_DECLS\n";
1110 OS << "#undef GET_INSTRINFO_HELPER_DECLS\n\n";
1111 emitTIIHelperMethods(OS, TargetName, /* ExpandDefinition = */ false);
1112 OS << "\n";
1113 OS << "#endif // GET_INSTRINFO_HELPER_DECLS\n\n";
1114
1115 OS << "#ifdef GET_INSTRINFO_HELPERS\n";
1116 OS << "#undef GET_INSTRINFO_HELPERS\n\n";
1117 emitTIIHelperMethods(OS, TargetName, /* ExpandDefinition = */ true);
1118 OS << "#endif // GET_INSTRINFO_HELPERS\n\n";
1119
1120 OS << "#ifdef GET_INSTRINFO_CTOR_DTOR\n";
1121 OS << "#undef GET_INSTRINFO_CTOR_DTOR\n";
1122
1123 OS << "namespace llvm {\n";
1124 OS << "extern const " << TargetName << "InstrTable " << TargetName
1125 << "Descs;\n";
1126 OS << "extern const unsigned " << TargetName << "InstrNameIndices[];\n";
1127 OS << "extern const char " << TargetName << "InstrNameData[];\n";
1128 if (HasDeprecationFeatures)
1129 OS << "extern const uint8_t " << TargetName
1130 << "InstrDeprecationFeatures[];\n";
1131 if (HasComplexDeprecationInfos)
1132 OS << "extern const MCInstrInfo::ComplexDeprecationPredicate " << TargetName
1133 << "InstrComplexDeprecationInfos[];\n";
1134 OS << ClassName << "::" << ClassName
1135 << "(unsigned CFSetupOpcode, unsigned CFDestroyOpcode, unsigned "
1136 "CatchRetOpcode, unsigned ReturnOpcode)\n"
1137 << " : TargetInstrInfo(CFSetupOpcode, CFDestroyOpcode, CatchRetOpcode, "
1138 "ReturnOpcode) {\n"
1139 << " InitMCInstrInfo(" << TargetName << "Descs.Insts, " << TargetName
1140 << "InstrNameIndices, " << TargetName << "InstrNameData, ";
1141 if (HasDeprecationFeatures)
1142 OS << TargetName << "InstrDeprecationFeatures, ";
1143 else
1144 OS << "nullptr, ";
1145 if (HasComplexDeprecationInfos)
1146 OS << TargetName << "InstrComplexDeprecationInfos, ";
1147 else
1148 OS << "nullptr, ";
1149 OS << NumberedInstructions.size() << ");\n}\n";
1150 OS << "} // end namespace llvm\n";
1151
1152 OS << "#endif // GET_INSTRINFO_CTOR_DTOR\n\n";
1153
1154 Records.startTimer("Emit operand name mappings");
1155 emitOperandNameMappings(OS, Target, NumberedInstructions);
1156
1157 Records.startTimer("Emit operand type mappings");
1158 emitOperandTypeMappings(OS, Target, NumberedInstructions);
1159
1160 Records.startTimer("Emit logical operand size mappings");
1161 emitLogicalOperandSizeMappings(OS, TargetName, NumberedInstructions);
1162
1163 Records.startTimer("Emit logical operand type mappings");
1164 emitLogicalOperandTypeMappings(OS, TargetName, NumberedInstructions);
1165
1166 Records.startTimer("Emit helper methods");
1167 emitMCIIHelperMethods(OS, TargetName);
1168
1169 Records.startTimer("Emit verifier methods");
1170 emitFeatureVerifier(OS, Target);
1171 }
1172
emitRecord(const CodeGenInstruction & Inst,unsigned Num,Record * InstrInfo,std::map<std::vector<Record * >,unsigned> & EmittedLists,const OperandInfoMapTy & OperandInfoMap,raw_ostream & OS)1173 void InstrInfoEmitter::emitRecord(
1174 const CodeGenInstruction &Inst, unsigned Num, Record *InstrInfo,
1175 std::map<std::vector<Record *>, unsigned> &EmittedLists,
1176 const OperandInfoMapTy &OperandInfoMap, raw_ostream &OS) {
1177 int MinOperands = 0;
1178 if (!Inst.Operands.empty())
1179 // Each logical operand can be multiple MI operands.
1180 MinOperands =
1181 Inst.Operands.back().MIOperandNo + Inst.Operands.back().MINumOperands;
1182 // Even the logical output operand may be multiple MI operands.
1183 int DefOperands = 0;
1184 if (Inst.Operands.NumDefs) {
1185 auto &Opnd = Inst.Operands[Inst.Operands.NumDefs - 1];
1186 DefOperands = Opnd.MIOperandNo + Opnd.MINumOperands;
1187 }
1188
1189 OS << " { ";
1190 OS << Num << ",\t" << MinOperands << ",\t" << DefOperands << ",\t"
1191 << Inst.TheDef->getValueAsInt("Size") << ",\t"
1192 << SchedModels.getSchedClassIdx(Inst) << ",\t";
1193
1194 CodeGenTarget &Target = CDP.getTargetInfo();
1195
1196 // Emit the implicit use/def list...
1197 OS << Inst.ImplicitUses.size() << ",\t" << Inst.ImplicitDefs.size() << ",\t";
1198 std::vector<Record *> ImplicitOps = Inst.ImplicitUses;
1199 llvm::append_range(ImplicitOps, Inst.ImplicitDefs);
1200 OS << Target.getName() << "ImpOpBase + " << EmittedLists[ImplicitOps]
1201 << ",\t";
1202
1203 // Emit the operand info offset.
1204 OperandInfoTy OperandInfo = GetOperandInfo(Inst);
1205 OS << OperandInfoMap.find(OperandInfo)->second << ",\t0";
1206
1207 // Emit all of the target independent flags...
1208 if (Inst.isPreISelOpcode)
1209 OS << "|(1ULL<<MCID::PreISelOpcode)";
1210 if (Inst.isPseudo)
1211 OS << "|(1ULL<<MCID::Pseudo)";
1212 if (Inst.isMeta)
1213 OS << "|(1ULL<<MCID::Meta)";
1214 if (Inst.isReturn)
1215 OS << "|(1ULL<<MCID::Return)";
1216 if (Inst.isEHScopeReturn)
1217 OS << "|(1ULL<<MCID::EHScopeReturn)";
1218 if (Inst.isBranch)
1219 OS << "|(1ULL<<MCID::Branch)";
1220 if (Inst.isIndirectBranch)
1221 OS << "|(1ULL<<MCID::IndirectBranch)";
1222 if (Inst.isCompare)
1223 OS << "|(1ULL<<MCID::Compare)";
1224 if (Inst.isMoveImm)
1225 OS << "|(1ULL<<MCID::MoveImm)";
1226 if (Inst.isMoveReg)
1227 OS << "|(1ULL<<MCID::MoveReg)";
1228 if (Inst.isBitcast)
1229 OS << "|(1ULL<<MCID::Bitcast)";
1230 if (Inst.isAdd)
1231 OS << "|(1ULL<<MCID::Add)";
1232 if (Inst.isTrap)
1233 OS << "|(1ULL<<MCID::Trap)";
1234 if (Inst.isSelect)
1235 OS << "|(1ULL<<MCID::Select)";
1236 if (Inst.isBarrier)
1237 OS << "|(1ULL<<MCID::Barrier)";
1238 if (Inst.hasDelaySlot)
1239 OS << "|(1ULL<<MCID::DelaySlot)";
1240 if (Inst.isCall)
1241 OS << "|(1ULL<<MCID::Call)";
1242 if (Inst.canFoldAsLoad)
1243 OS << "|(1ULL<<MCID::FoldableAsLoad)";
1244 if (Inst.mayLoad)
1245 OS << "|(1ULL<<MCID::MayLoad)";
1246 if (Inst.mayStore)
1247 OS << "|(1ULL<<MCID::MayStore)";
1248 if (Inst.mayRaiseFPException)
1249 OS << "|(1ULL<<MCID::MayRaiseFPException)";
1250 if (Inst.isPredicable)
1251 OS << "|(1ULL<<MCID::Predicable)";
1252 if (Inst.isConvertibleToThreeAddress)
1253 OS << "|(1ULL<<MCID::ConvertibleTo3Addr)";
1254 if (Inst.isCommutable)
1255 OS << "|(1ULL<<MCID::Commutable)";
1256 if (Inst.isTerminator)
1257 OS << "|(1ULL<<MCID::Terminator)";
1258 if (Inst.isReMaterializable)
1259 OS << "|(1ULL<<MCID::Rematerializable)";
1260 if (Inst.isNotDuplicable)
1261 OS << "|(1ULL<<MCID::NotDuplicable)";
1262 if (Inst.Operands.hasOptionalDef)
1263 OS << "|(1ULL<<MCID::HasOptionalDef)";
1264 if (Inst.usesCustomInserter)
1265 OS << "|(1ULL<<MCID::UsesCustomInserter)";
1266 if (Inst.hasPostISelHook)
1267 OS << "|(1ULL<<MCID::HasPostISelHook)";
1268 if (Inst.Operands.isVariadic)
1269 OS << "|(1ULL<<MCID::Variadic)";
1270 if (Inst.hasSideEffects)
1271 OS << "|(1ULL<<MCID::UnmodeledSideEffects)";
1272 if (Inst.isAsCheapAsAMove)
1273 OS << "|(1ULL<<MCID::CheapAsAMove)";
1274 if (!Target.getAllowRegisterRenaming() || Inst.hasExtraSrcRegAllocReq)
1275 OS << "|(1ULL<<MCID::ExtraSrcRegAllocReq)";
1276 if (!Target.getAllowRegisterRenaming() || Inst.hasExtraDefRegAllocReq)
1277 OS << "|(1ULL<<MCID::ExtraDefRegAllocReq)";
1278 if (Inst.isRegSequence)
1279 OS << "|(1ULL<<MCID::RegSequence)";
1280 if (Inst.isExtractSubreg)
1281 OS << "|(1ULL<<MCID::ExtractSubreg)";
1282 if (Inst.isInsertSubreg)
1283 OS << "|(1ULL<<MCID::InsertSubreg)";
1284 if (Inst.isConvergent)
1285 OS << "|(1ULL<<MCID::Convergent)";
1286 if (Inst.variadicOpsAreDefs)
1287 OS << "|(1ULL<<MCID::VariadicOpsAreDefs)";
1288 if (Inst.isAuthenticated)
1289 OS << "|(1ULL<<MCID::Authenticated)";
1290
1291 // Emit all of the target-specific flags...
1292 BitsInit *TSF = Inst.TheDef->getValueAsBitsInit("TSFlags");
1293 if (!TSF)
1294 PrintFatalError(Inst.TheDef->getLoc(), "no TSFlags?");
1295 uint64_t Value = 0;
1296 for (unsigned i = 0, e = TSF->getNumBits(); i != e; ++i) {
1297 if (const auto *Bit = dyn_cast<BitInit>(TSF->getBit(i)))
1298 Value |= uint64_t(Bit->getValue()) << i;
1299 else
1300 PrintFatalError(Inst.TheDef->getLoc(),
1301 "Invalid TSFlags bit in " + Inst.TheDef->getName());
1302 }
1303 OS << ", 0x";
1304 OS.write_hex(Value);
1305 OS << "ULL";
1306
1307 OS << " }, // Inst #" << Num << " = " << Inst.TheDef->getName() << "\n";
1308 }
1309
1310 // emitEnums - Print out enum values for all of the instructions.
emitEnums(raw_ostream & OS)1311 void InstrInfoEmitter::emitEnums(raw_ostream &OS) {
1312 OS << "#ifdef GET_INSTRINFO_ENUM\n";
1313 OS << "#undef GET_INSTRINFO_ENUM\n";
1314
1315 OS << "namespace llvm {\n\n";
1316
1317 const CodeGenTarget &Target = CDP.getTargetInfo();
1318
1319 // We must emit the PHI opcode first...
1320 StringRef Namespace = Target.getInstNamespace();
1321
1322 if (Namespace.empty())
1323 PrintFatalError("No instructions defined!");
1324
1325 OS << "namespace " << Namespace << " {\n";
1326 OS << " enum {\n";
1327 unsigned Num = 0;
1328 for (const CodeGenInstruction *Inst : Target.getInstructionsByEnumValue())
1329 OS << " " << Inst->TheDef->getName()
1330 << "\t= " << (Num = Target.getInstrIntValue(Inst->TheDef)) << ",\n";
1331 OS << " INSTRUCTION_LIST_END = " << Num + 1 << "\n";
1332 OS << " };\n\n";
1333 OS << "} // end namespace " << Namespace << "\n";
1334 OS << "} // end namespace llvm\n";
1335 OS << "#endif // GET_INSTRINFO_ENUM\n\n";
1336
1337 OS << "#ifdef GET_INSTRINFO_SCHED_ENUM\n";
1338 OS << "#undef GET_INSTRINFO_SCHED_ENUM\n";
1339 OS << "namespace llvm {\n\n";
1340 OS << "namespace " << Namespace << " {\n";
1341 OS << "namespace Sched {\n";
1342 OS << " enum {\n";
1343 Num = 0;
1344 for (const auto &Class : SchedModels.explicit_classes())
1345 OS << " " << Class.Name << "\t= " << Num++ << ",\n";
1346 OS << " SCHED_LIST_END = " << Num << "\n";
1347 OS << " };\n";
1348 OS << "} // end namespace Sched\n";
1349 OS << "} // end namespace " << Namespace << "\n";
1350 OS << "} // end namespace llvm\n";
1351
1352 OS << "#endif // GET_INSTRINFO_SCHED_ENUM\n\n";
1353 }
1354
EmitInstrInfo(RecordKeeper & RK,raw_ostream & OS)1355 static void EmitInstrInfo(RecordKeeper &RK, raw_ostream &OS) {
1356 RK.startTimer("Analyze DAG patterns");
1357 InstrInfoEmitter(RK).run(OS);
1358 RK.startTimer("Emit map table");
1359 EmitMapTable(RK, OS);
1360 }
1361
1362 static TableGen::Emitter::Opt X("gen-instr-info", EmitInstrInfo,
1363 "Generate instruction descriptions");
1364