Added the notion of Type and TargetSpecific attributes to the clang tablegen.  In turn, this fixes a mistake with Ptr32, Ptr64, UPtr and SPtr attribtues generating AST nodes that are never actually used.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@187401 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/include/clang/Basic/Attr.td b/include/clang/Basic/Attr.td
index 405fea0..f592bcb 100644
--- a/include/clang/Basic/Attr.td
+++ b/include/clang/Basic/Attr.td
@@ -126,9 +126,19 @@
   code AdditionalMembers = [{}];
 }
 
+/// A type attribute is not processed on a declaration or a statement.
+class TypeAttr : Attr {
+  let ASTNode = 0;
+}
+
 /// An inheritable attribute is inherited by later redeclarations.
 class InheritableAttr : Attr;
 
+/// A target-specific attribute that is meant to be processed via
+/// TargetAttributesSema::ProcessDeclAttribute.  This class is meant to be used
+/// as a mixin with InheritableAttr or Attr depending on the attribute's needs.
+class TargetSpecificAttr;
+
 /// An inheritable parameter attribute is inherited by later
 /// redeclarations, even when it's written on a parameter.
 class InheritableParamAttr : InheritableAttr;
@@ -144,10 +154,9 @@
 // Attributes begin here
 //
 
-def AddressSpace : Attr {
+def AddressSpace : TypeAttr {
   let Spellings = [GNU<"address_space">];
   let Args = [IntArgument<"AddressSpace">];
-  let ASTNode = 0;
 }
 
 def Alias : InheritableAttr {
@@ -169,13 +178,13 @@
 
 def AlignMac68k : InheritableAttr {
   let Spellings = [];
-  let SemaHandler = 0;

-}

-

-def AllocSize : InheritableAttr {

-  let Spellings = [GNU<"alloc_size">, CXX11<"gnu", "alloc_size">];

-  let Args = [VariadicUnsignedArgument<"Args">];

-}

+  let SemaHandler = 0;
+}
+
+def AllocSize : InheritableAttr {
+  let Spellings = [GNU<"alloc_size">, CXX11<"gnu", "alloc_size">];
+  let Args = [VariadicUnsignedArgument<"Args">];
+}
 
 def AlwaysInline : InheritableAttr {
   let Spellings = [GNU<"always_inline">, CXX11<"gnu", "always_inline">];
@@ -323,17 +332,17 @@
 
 def CXX11NoReturn : InheritableAttr {
   let Spellings = [CXX11<"","noreturn">, CXX11<"std","noreturn">];
-  let Subjects = [Function];

-}

-

-def OpenCLKernel : InheritableAttr {

-  let Spellings = [Keyword<"__kernel">, Keyword<"kernel">];

-}

-

-def OpenCLImageAccess : Attr {

-  let Spellings = [GNU<"opencl_image_access">];

-  let Args = [IntArgument<"Access">];

-}

+  let Subjects = [Function];
+}
+
+def OpenCLKernel : InheritableAttr {
+  let Spellings = [Keyword<"__kernel">, Keyword<"kernel">];
+}
+
+def OpenCLImageAccess : Attr {
+  let Spellings = [GNU<"opencl_image_access">];
+  let Args = [IntArgument<"Access">];
+}
 
 def Deprecated : InheritableAttr {
   let Spellings = [GNU<"deprecated">, CXX11<"gnu", "deprecated">];
@@ -342,13 +351,13 @@
 
 def Destructor : InheritableAttr {
   let Spellings = [GNU<"destructor">, CXX11<"gnu", "destructor">];
-  let Args = [IntArgument<"Priority">];

-}

-

-def ExtVectorType : Attr {

-  let Spellings = [GNU<"ext_vector_type">];

-  let Args = [ExprArgument<"NumElements">];

-  let ASTNode = 0;

+  let Args = [IntArgument<"Priority">];
+}
+
+def ExtVectorType : Attr {
+  let Spellings = [GNU<"ext_vector_type">];
+  let Args = [ExprArgument<"NumElements">];
+  let ASTNode = 0;
 }
 
 def FallThrough : Attr {
@@ -417,36 +426,34 @@
   let Spellings = [GNU<"may_alias">, CXX11<"gnu", "may_alias">];
 }
 
-def MSP430Interrupt : InheritableAttr {
+def MSP430Interrupt : InheritableAttr, TargetSpecificAttr {
   let Spellings = [];
   let Args = [UnsignedArgument<"Number">];
   let SemaHandler = 0;
 }
 
-def Mips16 : InheritableAttr {
+def Mips16 : InheritableAttr, TargetSpecificAttr {
   let Spellings = [GNU<"mips16">, CXX11<"gnu", "mips16">];
-  let Subjects = [Function];

-}

-

-def Mode : Attr {

-  let Spellings = [GNU<"mode">, CXX11<"gnu", "mode">];

-  let Args = [IdentifierArgument<"Mode">];

-}

+  let Subjects = [Function];
+}
+
+def Mode : Attr {
+  let Spellings = [GNU<"mode">, CXX11<"gnu", "mode">];
+  let Args = [IdentifierArgument<"Mode">];
+}
 
 def Naked : InheritableAttr {
   let Spellings = [GNU<"naked">, CXX11<"gnu", "naked">];
 }
 
-def NeonPolyVectorType : Attr {
+def NeonPolyVectorType : TypeAttr {
   let Spellings = [GNU<"neon_polyvector_type">];
   let Args = [IntArgument<"NumElements">];
-  let ASTNode = 0;
 }
 
-def NeonVectorType : Attr {
+def NeonVectorType : TypeAttr {
   let Spellings = [GNU<"neon_vector_type">];
   let Args = [IntArgument<"NumElements">];
-  let ASTNode = 0;
 }
 
 def ReturnsTwice : InheritableAttr {
@@ -465,7 +472,7 @@
   let Spellings = [GNU<"noinline">, CXX11<"gnu", "noinline">];
 }
 
-def NoMips16 : InheritableAttr {
+def NoMips16 : InheritableAttr, TargetSpecificAttr {
   let Spellings = [GNU<"nomips16">, CXX11<"gnu", "nomips16">];
   let Subjects = [Function];
 }
@@ -544,28 +551,28 @@
 }
 
 def ObjCNSObject : InheritableAttr {
-  let Spellings = [GNU<"NSObject">];

-}

-

-def ObjCPreciseLifetime : InheritableAttr {

-  let Spellings = [GNU<"objc_precise_lifetime">];

-  let Subjects = [Var];

-}

-

-def ObjCReturnsInnerPointer : InheritableAttr {

-  let Spellings = [GNU<"objc_returns_inner_pointer">];

-  let Subjects = [ObjCMethod];

-}

+  let Spellings = [GNU<"NSObject">];
+}
+
+def ObjCPreciseLifetime : InheritableAttr {
+  let Spellings = [GNU<"objc_precise_lifetime">];
+  let Subjects = [Var];
+}
+
+def ObjCReturnsInnerPointer : InheritableAttr {
+  let Spellings = [GNU<"objc_returns_inner_pointer">];
+  let Subjects = [ObjCMethod];
+}
 
 def ObjCRequiresSuper : InheritableAttr {
   let Spellings = [GNU<"objc_requires_super">];
-  let Subjects = [ObjCMethod];

-}

-

-def ObjCRootClass : InheritableAttr {

-  let Spellings = [GNU<"objc_root_class">];

-  let Subjects = [ObjCInterface];

-}

+  let Subjects = [ObjCMethod];
+}
+
+def ObjCRootClass : InheritableAttr {
+  let Spellings = [GNU<"objc_root_class">];
+  let Subjects = [ObjCInterface];
+}
 
 def Overloadable : Attr {
   let Spellings = [GNU<"overloadable">];
@@ -676,16 +683,15 @@
   let Subjects = [ObjCInterface];
 }
 
-def ObjCGC : Attr {
+def ObjCGC : TypeAttr {
   let Spellings = [GNU<"objc_gc">];
   let Args = [IdentifierArgument<"Kind">];
-  let ASTNode = 0;

-}

-

-def ObjCOwnership : InheritableAttr {

-  let Spellings = [GNU<"objc_ownership">];

-  let Args = [IdentifierArgument<"Kind">];

-  let ASTNode = 0;

+}
+
+def ObjCOwnership : InheritableAttr {
+  let Spellings = [GNU<"objc_ownership">];
+  let Args = [IdentifierArgument<"Kind">];
+  let ASTNode = 0;
 }
 
 def ObjCRequiresPropertyDefs : InheritableAttr {
@@ -707,10 +713,9 @@
   let Subjects = [CXXRecord];
 }
 
-def VectorSize : Attr {
+def VectorSize : TypeAttr {
   let Spellings = [GNU<"vector_size">, CXX11<"gnu", "vector_size">];
   let Args = [ExprArgument<"NumBytes">];
-  let ASTNode = 0;
 }
 
 def VecTypeHint : InheritableAttr {
@@ -762,7 +767,7 @@
   let Spellings = [GNU<"weakref">, CXX11<"gnu", "weakref">];
 }
 
-def X86ForceAlignArgPointer : InheritableAttr {
+def X86ForceAlignArgPointer : InheritableAttr, TargetSpecificAttr {
   let Spellings = [];
 }
 
@@ -944,11 +949,11 @@
   let Spellings = [Declspec<"ms_struct">];
 }
 
-def DLLExport : InheritableAttr {
+def DLLExport : InheritableAttr, TargetSpecificAttr {
   let Spellings = [Declspec<"dllexport">];
 }
 
-def DLLImport : InheritableAttr {
+def DLLImport : InheritableAttr, TargetSpecificAttr {
   let Spellings = [Declspec<"dllimport">];
 }
 
@@ -964,19 +969,19 @@
   let Spellings = [Keyword<"__w64">];
 }
 
-def Ptr32 : InheritableAttr {
+def Ptr32 : TypeAttr {
   let Spellings = [Keyword<"__ptr32">];
 }
 
-def Ptr64 : InheritableAttr {
+def Ptr64 : TypeAttr {
   let Spellings = [Keyword<"__ptr64">];
 }
 
-def SPtr : InheritableAttr {
+def SPtr : TypeAttr {
   let Spellings = [Keyword<"__sptr">];
 }
 
-def UPtr : InheritableAttr {
+def UPtr : TypeAttr {
   let Spellings = [Keyword<"__uptr">];
 }
 
diff --git a/utils/TableGen/ClangAttrEmitter.cpp b/utils/TableGen/ClangAttrEmitter.cpp
index 3982fc3..4fad50e 100644
--- a/utils/TableGen/ClangAttrEmitter.cpp
+++ b/utils/TableGen/ClangAttrEmitter.cpp
@@ -892,7 +892,18 @@
     if (!R.getValueAsBit("ASTNode"))
       continue;
     
-    const std::string &SuperName = R.getSuperClasses().back()->getName();
+    const std::vector<Record *> Supers = R.getSuperClasses();
+    assert(!Supers.empty() && "Forgot to specify a superclass for the attr");
+    bool IsTargetSpecific = false;
+    std::string SuperName;
+    for (std::vector<Record *>::const_reverse_iterator I = Supers.rbegin(),
+         E = Supers.rend(); I != E; ++I) {
+      const Record &R = **I;
+      if (R.getName() == "TargetSpecificAttr")
+        IsTargetSpecific = true;
+      else if (SuperName.empty())
+        SuperName = R.getName();
+    }
 
     OS << "class " << R.getName() << "Attr : public " << SuperName << " {\n";