Drop a RecordKeeper reference that wasn't necessary.
[oota-llvm.git] / utils / TableGen / ClangAttrEmitter.cpp
index db10d7906e238304ebdadbb1141640273c682859..26bd8786a49cedfff9b634420b10acd891a2f754 100644 (file)
@@ -45,6 +45,8 @@ std::string ReadPCHRecord(StringRef type) {
     .EndsWith("Decl *", "cast_or_null<" + std::string(type, 0, type.size()-1) +
               ">(GetDecl(Record[Idx++]))")
     .Case("QualType", "GetType(Record[Idx++])")
+    .Case("Expr *", "ReadSubExpr()")
+    .Case("IdentifierInfo *", "GetIdentifierInfo(Record, Idx)")
     .Default("Record[Idx++]");
 }
 
@@ -54,6 +56,9 @@ std::string WritePCHRecord(StringRef type, StringRef name) {
     .EndsWith("Decl *", "AddDeclRef(" + std::string(name) +
                         ", Record);\n")
     .Case("QualType", "AddTypeRef(" + std::string(name) + ", Record);\n")
+    .Case("Expr *", "AddStmt(" + std::string(name) + ");\n")
+    .Case("IdentifierInfo *", 
+          "AddIdentifierRef(" + std::string(name) + ", Record);\n")
     .Default("Record.push_back(" + std::string(name) + ");\n");
 }
 
@@ -413,6 +418,47 @@ namespace {
       OS << "Record.push_back(SA->get" << getUpperName() << "());\n";
     }
   };
+
+  class VersionArgument : public Argument {
+  public:
+    VersionArgument(Record &Arg, StringRef Attr)
+      : Argument(Arg, Attr)
+    {}
+
+    void writeAccessors(raw_ostream &OS) const {
+      OS << "  VersionTuple get" << getUpperName() << "() const {\n";
+      OS << "    return " << getLowerName() << ";\n";
+      OS << "  }\n";
+      OS << "  void set" << getUpperName() 
+         << "(ASTContext &C, VersionTuple V) {\n";
+      OS << "    " << getLowerName() << " = V;\n";
+      OS << "  }";
+    }
+    void writeCloneArgs(raw_ostream &OS) const {
+      OS << "get" << getUpperName() << "()";
+    }
+    void writeCtorBody(raw_ostream &OS) const {
+    }
+    void writeCtorInitializers(raw_ostream &OS) const {
+      OS << getLowerName() << "(" << getUpperName() << ")";
+    }
+    void writeCtorParameters(raw_ostream &OS) const {
+      OS << "VersionTuple " << getUpperName();
+    }
+    void writeDeclarations(raw_ostream &OS) const {
+      OS << "VersionTuple " << getLowerName() << ";\n";
+    }
+    void writePCHReadDecls(raw_ostream &OS) const {
+      OS << "    VersionTuple " << getLowerName()
+         << "= ReadVersionTuple(Record, Idx);\n";
+    }
+    void writePCHReadArgs(raw_ostream &OS) const {
+      OS << getLowerName();
+    }
+    void writePCHWrite(raw_ostream &OS) const {
+      OS << "    AddVersionTuple(SA->get" << getUpperName() << "(), Record);\n";
+    }
+  };
 }
 
 static Argument *createArgument(Record &Arg, StringRef Attr,
@@ -431,6 +477,8 @@ static Argument *createArgument(Record &Arg, StringRef Attr,
     Ptr = new SimpleArgument(Arg, Attr, "FunctionDecl *");
   else if (ArgName == "IdentifierArgument")
     Ptr = new SimpleArgument(Arg, Attr, "IdentifierInfo *");
+  else if (ArgName == "BoolArgument") Ptr = new SimpleArgument(Arg, Attr, 
+                                                               "bool");
   else if (ArgName == "IntArgument") Ptr = new SimpleArgument(Arg, Attr, "int");
   else if (ArgName == "StringArgument") Ptr = new StringArgument(Arg, Attr);
   else if (ArgName == "TypeArgument")
@@ -439,6 +487,8 @@ static Argument *createArgument(Record &Arg, StringRef Attr,
     Ptr = new SimpleArgument(Arg, Attr, "unsigned");
   else if (ArgName == "VariadicUnsignedArgument")
     Ptr = new VariadicArgument(Arg, Attr, "unsigned");
+  else if (ArgName == "VersionArgument")
+    Ptr = new VersionArgument(Arg, Attr);
 
   if (!Ptr) {
     std::vector<Record*> Bases = Search->getSuperClasses();
@@ -462,8 +512,9 @@ void ClangAttrClassEmitter::run(raw_ostream &OS) {
   for (std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end();
        i != e; ++i) {
     Record &R = **i;
+    const std::string &SuperName = R.getSuperClasses().back()->getName();
 
-    OS << "class " << R.getName() << "Attr : public Attr {\n";
+    OS << "class " << R.getName() << "Attr : public " << SuperName << " {\n";
 
     std::vector<Record*> ArgRecords = R.getValueAsListOfDefs("Args");
     std::vector<Argument*> Args;
@@ -494,7 +545,7 @@ void ClangAttrClassEmitter::run(raw_ostream &OS) {
     }
     
     OS << "             )\n";
-    OS << "    : Attr(attr::" << R.getName() << ", L)\n";
+    OS << "    : " << SuperName << "(attr::" << R.getName() << ", L)\n";
 
     for (ai = Args.begin(); ai != ae; ++ai) {
       OS << "              , ";
@@ -558,31 +609,72 @@ void ClangAttrImplEmitter::run(raw_ostream &OS) {
   }
 }
 
+static void EmitAttrList(raw_ostream &OS, StringRef Class,
+                         const std::vector<Record*> &AttrList) {
+  std::vector<Record*>::const_iterator i = AttrList.begin(), e = AttrList.end();
+
+  if (i != e) {
+    // Move the end iterator back to emit the last attribute.
+    for(--e; i != e; ++i)
+      OS << Class << "(" << (*i)->getName() << ")\n";
+    
+    OS << "LAST_" << Class << "(" << (*i)->getName() << ")\n\n";
+  }
+}
+
 void ClangAttrListEmitter::run(raw_ostream &OS) {
   OS << "// This file is generated by TableGen. Do not edit.\n\n";
 
   OS << "#ifndef LAST_ATTR\n";
   OS << "#define LAST_ATTR(NAME) ATTR(NAME)\n";
   OS << "#endif\n\n";
-   
-  std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr");
-  std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end();
 
-  if (i != e) {
-    // Move the end iterator back to emit the last attribute.
-    for(--e; i != e; ++i)
-      OS << "ATTR(" << (*i)->getName() << ")\n";
-    
-    OS << "LAST_ATTR(" << (*i)->getName() << ")\n\n";
+  OS << "#ifndef INHERITABLE_ATTR\n";
+  OS << "#define INHERITABLE_ATTR(NAME) ATTR(NAME)\n";
+  OS << "#endif\n\n";
+
+  OS << "#ifndef LAST_INHERITABLE_ATTR\n";
+  OS << "#define LAST_INHERITABLE_ATTR(NAME) INHERITABLE_ATTR(NAME)\n";
+  OS << "#endif\n\n";
+
+  OS << "#ifndef INHERITABLE_PARAM_ATTR\n";
+  OS << "#define INHERITABLE_PARAM_ATTR(NAME) ATTR(NAME)\n";
+  OS << "#endif\n\n";
+
+  OS << "#ifndef LAST_INHERITABLE_PARAM_ATTR\n";
+  OS << "#define LAST_INHERITABLE_PARAM_ATTR(NAME)"
+        " INHERITABLE_PARAM_ATTR(NAME)\n";
+  OS << "#endif\n\n";
+
+  Record *InhClass = Records.getClass("InheritableAttr");
+  Record *InhParamClass = Records.getClass("InheritableParamAttr");
+  std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr"),
+                       NonInhAttrs, InhAttrs, InhParamAttrs;
+  for (std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end();
+       i != e; ++i) {
+    if ((*i)->isSubClassOf(InhParamClass))
+      InhParamAttrs.push_back(*i);
+    else if ((*i)->isSubClassOf(InhClass))
+      InhAttrs.push_back(*i);
+    else
+      NonInhAttrs.push_back(*i);
   }
 
+  EmitAttrList(OS, "INHERITABLE_PARAM_ATTR", InhParamAttrs);
+  EmitAttrList(OS, "INHERITABLE_ATTR", InhAttrs);
+  EmitAttrList(OS, "ATTR", NonInhAttrs);
+
   OS << "#undef LAST_ATTR\n";
+  OS << "#undef INHERITABLE_ATTR\n";
+  OS << "#undef LAST_INHERITABLE_ATTR\n";
+  OS << "#undef LAST_INHERITABLE_PARAM_ATTR\n";
   OS << "#undef ATTR\n";
 }
 
 void ClangAttrPCHReadEmitter::run(raw_ostream &OS) {
   OS << "// This file is generated by TableGen. Do not edit.\n\n";
 
+  Record *InhClass = Records.getClass("InheritableAttr");
   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr"),
                        ArgRecords;
   std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end(), ai, ae;
@@ -596,6 +688,8 @@ void ClangAttrPCHReadEmitter::run(raw_ostream &OS) {
   for (; i != e; ++i) {
     Record &R = **i;
     OS << "  case attr::" << R.getName() << ": {\n";
+    if (R.isSubClassOf(InhClass))
+      OS << "    bool isInherited = Record[Idx++];\n";
     ArgRecords = R.getValueAsListOfDefs("Args");
     Args.clear();
     for (ai = ArgRecords.begin(), ae = ArgRecords.end(); ai != ae; ++ai) {
@@ -609,6 +703,8 @@ void ClangAttrPCHReadEmitter::run(raw_ostream &OS) {
       (*ri)->writePCHReadArgs(OS);
     }
     OS << ");\n";
+    if (R.isSubClassOf(InhClass))
+      OS << "    cast<InheritableAttr>(New)->setInherited(isInherited);\n";
     OS << "    break;\n";
     OS << "  }\n";
   }
@@ -616,6 +712,7 @@ void ClangAttrPCHReadEmitter::run(raw_ostream &OS) {
 }
 
 void ClangAttrPCHWriteEmitter::run(raw_ostream &OS) {
+  Record *InhClass = Records.getClass("InheritableAttr");
   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr"), Args;
   std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end(), ai, ae;
 
@@ -627,9 +724,11 @@ void ClangAttrPCHWriteEmitter::run(raw_ostream &OS) {
     Record &R = **i;
     OS << "  case attr::" << R.getName() << ": {\n";
     Args = R.getValueAsListOfDefs("Args");
-    if (!Args.empty())
+    if (R.isSubClassOf(InhClass) || !Args.empty())
       OS << "    const " << R.getName() << "Attr *SA = cast<" << R.getName()
          << "Attr>(A);\n";
+    if (R.isSubClassOf(InhClass))
+      OS << "    Record.push_back(SA->isInherited());\n";
     for (ai = Args.begin(), ae = Args.end(); ai != ae; ++ai)
       createArgument(**ai, R.getName())->writePCHWrite(OS);
     OS << "    break;\n";