Reapply 63765.  Patches for clang and llvm-gcc to follow.



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@63812 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/utils/TableGen/IntrinsicEmitter.cpp b/utils/TableGen/IntrinsicEmitter.cpp
index eda55e1..53081ff 100644
--- a/utils/TableGen/IntrinsicEmitter.cpp
+++ b/utils/TableGen/IntrinsicEmitter.cpp
@@ -25,7 +25,10 @@
 void IntrinsicEmitter::run(std::ostream &OS) {
   EmitSourceFileHeader("Intrinsic Function Source Fragment", OS);
   
-  std::vector<CodeGenIntrinsic> Ints = LoadIntrinsics(Records);
+  std::vector<CodeGenIntrinsic> Ints = LoadIntrinsics(Records, TargetOnly);
+  
+  if (TargetOnly && !Ints.empty())
+    TargetPrefix = Ints[0].TargetPrefix;
 
   // Emit the enum information.
   EmitEnumInfo(Ints, OS);
@@ -91,12 +94,12 @@
     if (Ints[I->second].isOverloaded)
       OS << "    if (Len > " << I->first.size()
        << " && !memcmp(Name, \"" << I->first << ".\", "
-       << (I->first.size() + 1) << ")) return Intrinsic::"
+       << (I->first.size() + 1) << ")) return " << TargetPrefix << "Intrinsic::"
        << Ints[I->second].EnumName << ";\n";
     else 
       OS << "    if (Len == " << I->first.size()
          << " && !memcmp(Name, \"" << I->first << "\", "
-         << I->first.size() << ")) return Intrinsic::"
+         << I->first.size() << ")) return " << TargetPrefix << "Intrinsic::"
          << Ints[I->second].EnumName << ";\n";
   }
   OS << "  }\n";
@@ -351,11 +354,13 @@
                              Ints[i].IS.ParamTypeDefs)].push_back(i);
 
   // Loop through the array, emitting one generator for each batch.
+  std::string IntrinsicStr = TargetPrefix + "Intrinsic::";
+  
   for (MapTy::iterator I = UniqueArgInfos.begin(),
        E = UniqueArgInfos.end(); I != E; ++I) {
     for (unsigned i = 0, e = I->second.size(); i != e; ++i)
-      OS << "  case Intrinsic::" << Ints[I->second[i]].EnumName << ":\t\t// "
-         << Ints[I->second[i]].Name << "\n";
+      OS << "  case " << IntrinsicStr << Ints[I->second[i]].EnumName 
+         << ":\t\t// " << Ints[I->second[i]].Name << "\n";
     
     const RecPair &ArgTypes = I->first;
     const std::vector<Record*> &RetTys = ArgTypes.first;
@@ -392,7 +397,11 @@
 EmitAttributes(const std::vector<CodeGenIntrinsic> &Ints, std::ostream &OS) {
   OS << "// Add parameter attributes that are not common to all intrinsics.\n";
   OS << "#ifdef GET_INTRINSIC_ATTRIBUTES\n";
-  OS << "AttrListPtr Intrinsic::getAttributes(ID id) {";
+  if (TargetOnly)
+    OS << "static AttrListPtr getAttributes(" << TargetPrefix 
+       << "Intrinsic::ID id) {";
+  else
+    OS << "AttrListPtr Intrinsic::getAttributes(ID id) {";
   OS << "  // No intrinsic can throw exceptions.\n";
   OS << "  Attributes Attr = Attribute::NoUnwind;\n";
   OS << "  switch (id) {\n";
@@ -404,7 +413,8 @@
     switch (Ints[i].ModRef) {
     default: break;
     case CodeGenIntrinsic::NoMem:
-      OS << "  case Intrinsic::" << Ints[i].EnumName << ":\n";
+      OS << "  case " << TargetPrefix << "Intrinsic::" << Ints[i].EnumName 
+         << ":\n";
       break;
     }
   }
@@ -415,7 +425,8 @@
     default: break;
     case CodeGenIntrinsic::ReadArgMem:
     case CodeGenIntrinsic::ReadMem:
-      OS << "  case Intrinsic::" << Ints[i].EnumName << ":\n";
+      OS << "  case " << TargetPrefix << "Intrinsic::" << Ints[i].EnumName 
+         << ":\n";
       break;
     }
   }
@@ -431,7 +442,8 @@
   for (unsigned i = 0, e = Ints.size(); i != e; ++i) {
     if (Ints[i].ArgumentAttributes.empty()) continue;
     
-    OS << "  case Intrinsic::" << Ints[i].EnumName << ":\n";
+    OS << "  case " << TargetPrefix << "Intrinsic::" << Ints[i].EnumName 
+       << ":\n";
 
     std::vector<std::pair<unsigned, CodeGenIntrinsic::ArgAttribute> > ArgAttrs =
       Ints[i].ArgumentAttributes;
@@ -495,7 +507,7 @@
 typedef std::map<std::string, std::string>::const_iterator StrMapIterator;
 static void EmitBuiltinComparisons(StrMapIterator Start, StrMapIterator End,
                                    unsigned CharStart, unsigned Indent,
-                                   std::ostream &OS) {
+                                   std::string TargetPrefix, std::ostream &OS) {
   if (Start == End) return; // empty range.
   
   // Determine what, if anything, is the same about all these strings.
@@ -522,7 +534,8 @@
       OS << CommonString.size() - CharStart << "))\n";
       ++Indent;
     }
-    OS << std::string(Indent*2, ' ') << "IntrinsicID = Intrinsic::";
+    OS << std::string(Indent*2, ' ') << "IntrinsicID = " << TargetPrefix
+       << "Intrinsic::";
     OS << Start->second << ";\n";
     return;
   }
@@ -535,7 +548,8 @@
     OS << ", \"" << (CommonString.c_str()+CharStart) << "\", ";
     OS << CommonString.size()-CharStart << ")) {\n";
     
-    EmitBuiltinComparisons(Start, End, CommonString.size(), Indent+1, OS);
+    EmitBuiltinComparisons(Start, End, CommonString.size(), Indent+1, 
+                           TargetPrefix, OS);
     OS << std::string(Indent*2, ' ') << "}\n";
     return;
   }
@@ -556,7 +570,7 @@
     for (++NextChar; NextChar != End && NextChar->first[CharStart] == ThisChar;
          ++NextChar)
       /*empty*/;
-    EmitBuiltinComparisons(I, NextChar, CharStart+1, Indent+1, OS);
+    EmitBuiltinComparisons(I, NextChar, CharStart+1, Indent+1, TargetPrefix,OS);
     OS << std::string(Indent*2, ' ') << "  break;\n";
     I = NextChar;
   }
@@ -566,6 +580,7 @@
 /// EmitTargetBuiltins - All of the builtins in the specified map are for the
 /// same target, and we already checked it.
 static void EmitTargetBuiltins(const std::map<std::string, std::string> &BIM,
+                               const std::string &TargetPrefix,
                                std::ostream &OS) {
   // Rearrange the builtins by length.
   std::vector<std::map<std::string, std::string> > BuiltinsByLen;
@@ -584,7 +599,7 @@
     if (BuiltinsByLen[i].empty()) continue;
     OS << "    case " << i << ":\n";
     EmitBuiltinComparisons(BuiltinsByLen[i].begin(), BuiltinsByLen[i].end(),
-                           0, 3, OS);
+                           0, 3, TargetPrefix, OS);
     OS << "      break;\n";
   }
   OS << "    }\n";
@@ -613,7 +628,22 @@
   OS << "// in as BuiltinName, and a target prefix (e.g. 'ppc') is passed\n";
   OS << "// in as TargetPrefix.  The result is assigned to 'IntrinsicID'.\n";
   OS << "#ifdef GET_LLVM_INTRINSIC_FOR_GCC_BUILTIN\n";
-  OS << "  IntrinsicID = Intrinsic::not_intrinsic;\n";
+  
+  if (TargetOnly) {
+    OS << "static " << TargetPrefix << "Intrinsic::ID "
+       << "getIntrinsicForGCCBuiltin(const char "
+       << "*TargetPrefix, const char *BuiltinName) {\n";
+    OS << "  " << TargetPrefix << "Intrinsic::ID IntrinsicID = ";
+  } else {
+    OS << "Intrinsic::ID Intrinsic::getIntrinsicForGCCBuiltin(const char "
+       << "*TargetPrefix, const char *BuiltinName) {\n";
+    OS << "  Intrinsic::ID IntrinsicID = ";
+  }
+  
+  if (TargetOnly)
+    OS << "(" << TargetPrefix<< "Intrinsic::ID)";
+
+  OS << "Intrinsic::not_intrinsic;\n";
   
   // Note: this could emit significantly better code if we cared.
   for (BIMTy::iterator I = BuiltinMap.begin(), E = BuiltinMap.end();I != E;++I){
@@ -625,8 +655,10 @@
     OS << "{\n";
 
     // Emit the comparisons for this target prefix.
-    EmitTargetBuiltins(I->second, OS);
+    EmitTargetBuiltins(I->second, TargetPrefix, OS);
     OS << "  }\n";
   }
+  OS << "  return IntrinsicID;\n";
+  OS << "}\n";
   OS << "#endif\n\n";
 }