comparison utils/TableGen/CodeEmitterGen.cpp @ 147:c2174574ed3a

LLVM 10
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Wed, 14 Aug 2019 16:55:33 +0900
parents 803732b1fca8
children
comparison
equal deleted inserted replaced
134:3a76565eade5 147:c2174574ed3a
1 //===- CodeEmitterGen.cpp - Code Emitter Generator ------------------------===// 1 //===- CodeEmitterGen.cpp - Code Emitter Generator ------------------------===//
2 // 2 //
3 // The LLVM Compiler Infrastructure 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // 4 // See https://llvm.org/LICENSE.txt for license information.
5 // This file is distributed under the University of Illinois Open Source 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 // License. See LICENSE.TXT for details.
7 // 6 //
8 //===----------------------------------------------------------------------===// 7 //===----------------------------------------------------------------------===//
9 // 8 //
10 // CodeEmitterGen uses the descriptions of instructions and their fields to 9 // CodeEmitterGen uses the descriptions of instructions and their fields to
11 // construct an automated code emitter: a function that, given a MachineInstr, 10 // construct an automated code emitter: a function that, given a MachineInstr,
14 //===----------------------------------------------------------------------===// 13 //===----------------------------------------------------------------------===//
15 14
16 #include "CodeGenInstruction.h" 15 #include "CodeGenInstruction.h"
17 #include "CodeGenTarget.h" 16 #include "CodeGenTarget.h"
18 #include "SubtargetFeatureInfo.h" 17 #include "SubtargetFeatureInfo.h"
18 #include "Types.h"
19 #include "llvm/ADT/ArrayRef.h" 19 #include "llvm/ADT/ArrayRef.h"
20 #include "llvm/ADT/StringExtras.h" 20 #include "llvm/ADT/StringExtras.h"
21 #include "llvm/Support/Casting.h" 21 #include "llvm/Support/Casting.h"
22 #include "llvm/Support/raw_ostream.h" 22 #include "llvm/Support/raw_ostream.h"
23 #include "llvm/TableGen/Record.h" 23 #include "llvm/TableGen/Record.h"
227 } 227 }
228 228
229 return Case; 229 return Case;
230 } 230 }
231 231
232 static std::string
233 getNameForFeatureBitset(const std::vector<Record *> &FeatureBitset) {
234 std::string Name = "CEFBS";
235 for (const auto &Feature : FeatureBitset)
236 Name += ("_" + Feature->getName()).str();
237 return Name;
238 }
239
232 void CodeEmitterGen::run(raw_ostream &o) { 240 void CodeEmitterGen::run(raw_ostream &o) {
233 CodeGenTarget Target(Records); 241 CodeGenTarget Target(Records);
234 std::vector<Record*> Insts = Records.getAllDerivedDefinitions("Instruction"); 242 std::vector<Record*> Insts = Records.getAllDerivedDefinitions("Instruction");
235 243
236 // For little-endian instruction bit encodings, reverse the bit order 244 // For little-endian instruction bit encodings, reverse the bit order
325 o << "#ifdef ENABLE_INSTR_PREDICATE_VERIFIER\n" 333 o << "#ifdef ENABLE_INSTR_PREDICATE_VERIFIER\n"
326 << "#undef ENABLE_INSTR_PREDICATE_VERIFIER\n" 334 << "#undef ENABLE_INSTR_PREDICATE_VERIFIER\n"
327 << "#include <sstream>\n\n"; 335 << "#include <sstream>\n\n";
328 336
329 // Emit the subtarget feature enumeration. 337 // Emit the subtarget feature enumeration.
330 SubtargetFeatureInfo::emitSubtargetFeatureFlagEnumeration(SubtargetFeatures, 338 SubtargetFeatureInfo::emitSubtargetFeatureBitEnumeration(SubtargetFeatures,
331 o); 339 o);
332 340
333 // Emit the name table for error messages. 341 // Emit the name table for error messages.
334 o << "#ifndef NDEBUG\n"; 342 o << "#ifndef NDEBUG\n";
335 SubtargetFeatureInfo::emitNameTable(SubtargetFeatures, o); 343 SubtargetFeatureInfo::emitNameTable(SubtargetFeatures, o);
336 o << "#endif // NDEBUG\n"; 344 o << "#endif // NDEBUG\n";
338 // Emit the available features compute function. 346 // Emit the available features compute function.
339 SubtargetFeatureInfo::emitComputeAssemblerAvailableFeatures( 347 SubtargetFeatureInfo::emitComputeAssemblerAvailableFeatures(
340 Target.getName(), "MCCodeEmitter", "computeAvailableFeatures", 348 Target.getName(), "MCCodeEmitter", "computeAvailableFeatures",
341 SubtargetFeatures, o); 349 SubtargetFeatures, o);
342 350
351 std::vector<std::vector<Record *>> FeatureBitsets;
352 for (const CodeGenInstruction *Inst : Target.getInstructionsByEnumValue()) {
353 FeatureBitsets.emplace_back();
354 for (Record *Predicate : Inst->TheDef->getValueAsListOfDefs("Predicates")) {
355 const auto &I = SubtargetFeatures.find(Predicate);
356 if (I != SubtargetFeatures.end())
357 FeatureBitsets.back().push_back(I->second.TheDef);
358 }
359 }
360
361 llvm::sort(FeatureBitsets, [&](const std::vector<Record *> &A,
362 const std::vector<Record *> &B) {
363 if (A.size() < B.size())
364 return true;
365 if (A.size() > B.size())
366 return false;
367 for (const auto &Pair : zip(A, B)) {
368 if (std::get<0>(Pair)->getName() < std::get<1>(Pair)->getName())
369 return true;
370 if (std::get<0>(Pair)->getName() > std::get<1>(Pair)->getName())
371 return false;
372 }
373 return false;
374 });
375 FeatureBitsets.erase(
376 std::unique(FeatureBitsets.begin(), FeatureBitsets.end()),
377 FeatureBitsets.end());
378 o << "#ifndef NDEBUG\n"
379 << "// Feature bitsets.\n"
380 << "enum : " << getMinimalTypeForRange(FeatureBitsets.size()) << " {\n"
381 << " CEFBS_None,\n";
382 for (const auto &FeatureBitset : FeatureBitsets) {
383 if (FeatureBitset.empty())
384 continue;
385 o << " " << getNameForFeatureBitset(FeatureBitset) << ",\n";
386 }
387 o << "};\n\n"
388 << "const static FeatureBitset FeatureBitsets[] {\n"
389 << " {}, // CEFBS_None\n";
390 for (const auto &FeatureBitset : FeatureBitsets) {
391 if (FeatureBitset.empty())
392 continue;
393 o << " {";
394 for (const auto &Feature : FeatureBitset) {
395 const auto &I = SubtargetFeatures.find(Feature);
396 assert(I != SubtargetFeatures.end() && "Didn't import predicate?");
397 o << I->second.getEnumBitName() << ", ";
398 }
399 o << "},\n";
400 }
401 o << "};\n"
402 << "#endif // NDEBUG\n\n";
403
404
343 // Emit the predicate verifier. 405 // Emit the predicate verifier.
344 o << "void " << Target.getName() 406 o << "void " << Target.getName()
345 << "MCCodeEmitter::verifyInstructionPredicates(\n" 407 << "MCCodeEmitter::verifyInstructionPredicates(\n"
346 << " const MCInst &Inst, uint64_t AvailableFeatures) const {\n" 408 << " const MCInst &Inst, const FeatureBitset &AvailableFeatures) const {\n"
347 << "#ifndef NDEBUG\n" 409 << "#ifndef NDEBUG\n"
348 << " static uint64_t RequiredFeatures[] = {\n"; 410 << " static " << getMinimalTypeForRange(FeatureBitsets.size())
411 << " RequiredFeaturesRefs[] = {\n";
349 unsigned InstIdx = 0; 412 unsigned InstIdx = 0;
350 for (const CodeGenInstruction *Inst : Target.getInstructionsByEnumValue()) { 413 for (const CodeGenInstruction *Inst : Target.getInstructionsByEnumValue()) {
351 o << " "; 414 o << " CEFBS";
415 unsigned NumPredicates = 0;
352 for (Record *Predicate : Inst->TheDef->getValueAsListOfDefs("Predicates")) { 416 for (Record *Predicate : Inst->TheDef->getValueAsListOfDefs("Predicates")) {
353 const auto &I = SubtargetFeatures.find(Predicate); 417 const auto &I = SubtargetFeatures.find(Predicate);
354 if (I != SubtargetFeatures.end()) 418 if (I != SubtargetFeatures.end()) {
355 o << I->second.getEnumName() << " | "; 419 o << '_' << I->second.TheDef->getName();
356 } 420 NumPredicates++;
357 o << "0, // " << Inst->TheDef->getName() << " = " << InstIdx << "\n"; 421 }
422 }
423 if (!NumPredicates)
424 o << "_None";
425 o << ", // " << Inst->TheDef->getName() << " = " << InstIdx << "\n";
358 InstIdx++; 426 InstIdx++;
359 } 427 }
360 o << " };\n\n"; 428 o << " };\n\n";
361 o << " assert(Inst.getOpcode() < " << InstIdx << ");\n"; 429 o << " assert(Inst.getOpcode() < " << InstIdx << ");\n";
362 o << " uint64_t MissingFeatures =\n" 430 o << " const FeatureBitset &RequiredFeatures = "
363 << " (AvailableFeatures & RequiredFeatures[Inst.getOpcode()]) ^\n" 431 "FeatureBitsets[RequiredFeaturesRefs[Inst.getOpcode()]];\n";
364 << " RequiredFeatures[Inst.getOpcode()];\n" 432 o << " FeatureBitset MissingFeatures =\n"
365 << " if (MissingFeatures) {\n" 433 << " (AvailableFeatures & RequiredFeatures) ^\n"
434 << " RequiredFeatures;\n"
435 << " if (MissingFeatures.any()) {\n"
366 << " std::ostringstream Msg;\n" 436 << " std::ostringstream Msg;\n"
367 << " Msg << \"Attempting to emit \" << " 437 << " Msg << \"Attempting to emit \" << "
368 "MCII.getName(Inst.getOpcode()).str()\n" 438 "MCII.getName(Inst.getOpcode()).str()\n"
369 << " << \" instruction but the \";\n" 439 << " << \" instruction but the \";\n"
370 << " for (unsigned i = 0; i < 8 * sizeof(MissingFeatures); ++i)\n" 440 << " for (unsigned i = 0, e = MissingFeatures.size(); i != e; ++i)\n"
371 << " if (MissingFeatures & (1ULL << i))\n" 441 << " if (MissingFeatures.test(i))\n"
372 << " Msg << SubtargetFeatureNames[i] << \" \";\n" 442 << " Msg << SubtargetFeatureNames[i] << \" \";\n"
373 << " Msg << \"predicate(s) are not met\";\n" 443 << " Msg << \"predicate(s) are not met\";\n"
374 << " report_fatal_error(Msg.str());\n" 444 << " report_fatal_error(Msg.str());\n"
375 << " }\n" 445 << " }\n"
376 << "#else\n" 446 << "#else\n"