-void InstrInfoEmitter::InferFromPattern(const CodeGenInstruction &Inst,
- bool &mayStore, bool &mayLoad,
- bool &NeverHasSideEffects) {
- mayStore = mayLoad = NeverHasSideEffects = false;
-
- InstAnalyzer(CDP, mayStore, mayLoad,NeverHasSideEffects).Analyze(Inst.TheDef);
-
- // InstAnalyzer only correctly analyzes mayStore/mayLoad so far.
- if (Inst.mayStore) { // If the .td file explicitly sets mayStore, use it.
- // If we decided that this is a store from the pattern, then the .td file
- // entry is redundant.
- if (mayStore)
- fprintf(stderr,
- "Warning: mayStore flag explicitly set on instruction '%s'"
- " but flag already inferred from pattern.\n",
- Inst.TheDef->getName().c_str());
- mayStore = true;
+/// Generate a table and function for looking up the indices of operands by
+/// name.
+///
+/// This code generates:
+/// - An enum in the llvm::TargetNamespace::OpName namespace, with one entry
+/// for each operand name.
+/// - A 2-dimensional table called OperandMap for mapping OpName enum values to
+/// operand indices.
+/// - A function called getNamedOperandIdx(uint16_t Opcode, uint16_t NamedIdx)
+/// for looking up the operand index for an instruction, given a value from
+/// OpName enum
+void InstrInfoEmitter::emitOperandNameMappings(raw_ostream &OS,
+ const CodeGenTarget &Target,
+ const std::vector<const CodeGenInstruction*> &NumberedInstructions) {
+
+ const std::string &Namespace = Target.getInstNamespace();
+ std::string OpNameNS = "OpName";
+ // Map of operand names to their enumeration value. This will be used to
+ // generate the OpName enum.
+ std::map<std::string, unsigned> Operands;
+ OpNameMapTy OperandMap;
+
+ initOperandMapData(NumberedInstructions, Namespace, Operands, OperandMap);
+
+ OS << "#ifdef GET_INSTRINFO_OPERAND_ENUM\n";
+ OS << "#undef GET_INSTRINFO_OPERAND_ENUM\n";
+ OS << "namespace llvm {";
+ OS << "namespace " << Namespace << " {\n";
+ OS << "namespace " << OpNameNS << " { \n";
+ OS << "enum {\n";
+ for (StrUintMapIter i = Operands.begin(), e = Operands.end(); i != e; ++i)
+ OS << " " << i->first << " = " << i->second << ",\n";
+
+ OS << "OPERAND_LAST";
+ OS << "\n};\n";
+ OS << "} // End namespace OpName\n";
+ OS << "} // End namespace " << Namespace << "\n";
+ OS << "} // End namespace llvm\n";
+ OS << "#endif //GET_INSTRINFO_OPERAND_ENUM\n";
+
+ OS << "#ifdef GET_INSTRINFO_NAMED_OPS\n";
+ OS << "#undef GET_INSTRINFO_NAMED_OPS\n";
+ OS << "namespace llvm {";
+ OS << "namespace " << Namespace << " {\n";
+ OS << "int16_t getNamedOperandIdx(uint16_t Opcode, uint16_t NamedIdx) {\n";
+ OS << " static const int16_t OperandMap []["<< Operands.size() << "] = {\n";
+ for (OpNameMapTy::iterator i = OperandMap.begin(), e = OperandMap.end();
+ i != e; ++i) {
+ const std::map<unsigned, unsigned> &OpList = i->first;
+ OS << "{";
+
+ // Emit a row of the OperandMap table
+ for (unsigned ii = 0, ie = Operands.size(); ii != ie; ++ii)
+ OS << (OpList.count(ii) == 0 ? -1 : (int)OpList.find(ii)->second) << ", ";
+
+ OS << "},\n";