Hi rsmith,

This is the updated patch that fixes alignment attribute printing by removing 
"IsMSDeclSpec" argument from alignment attribute and using attribute syntax 
accessor generated by TableGen to decide if an alignment attribute is a MS 
declspec attribute.

http://llvm-reviews.chandlerc.com/D360

Files:
  utils/TableGen/ClangAttrEmitter.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Sema/SemaTemplateInstantiateDecl.cpp
  test/SemaCXX/attr-print.cpp
  test/SemaCXX/cxx11-attr-print.cpp
  test/Sema/attr-print.c
  include/clang/Basic/Attr.td
  include/clang/Sema/Sema.h
Index: utils/TableGen/ClangAttrEmitter.cpp
===================================================================
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -829,6 +829,51 @@
   OS << "}\n\n";
 }
 
+/// \brief Return the index of a spelling in a spelling list.
+static unsigned getSpellingListIndex(const std::vector<Record*> &SpellingList,
+                                     const Record &Spelling) {
+  assert(SpellingList.size() && "Spelling list is empty!");
+
+  for (unsigned Index = 0; Index < SpellingList.size(); ++ Index) {
+    Record *S = SpellingList[Index];
+    if (S->getValueAsString("Variety") != Spelling.getValueAsString("Variety"))
+      continue;
+    if ((S->getValueAsString("Variety") == "CXX11") &&
+        (S->getValueAsString("Namespace") !=
+         Spelling.getValueAsString("Namespace")))
+      continue;
+    if (S->getValueAsString("Name") != Spelling.getValueAsString("Name"))
+      continue;
+
+    return Index;
+  }
+
+  llvm_unreachable("Unknown spelling!");
+}
+
+static void writeAttrAccessorDefinition(Record &R, raw_ostream &OS) {
+  std::vector<Record*> Accessors = R.getValueAsListOfDefs("Accessors");
+  for (std::vector<Record*>::const_iterator I = Accessors.begin(),
+       E = Accessors.end(); I != E; ++ I) {
+    Record *Accessor = *I;
+    std::string Name = Accessor->getValueAsString("Name");
+    std::vector<Record*> Spellings = Accessor->getValueAsListOfDefs(
+      "Spellings");
+    std::vector<Record*> SpellingList = R.getValueAsListOfDefs("Spellings");
+    assert(SpellingList.size() &&
+           "Attribute with empty spelling list can't have accessors!");
+
+    OS << "  bool " << Name << "() const { return SpellingListIndex == ";
+    for (unsigned Index = 0; Index < Spellings.size(); ++ Index) {
+      OS << getSpellingListIndex(SpellingList, *Spellings[Index]);
+      if (Index != Spellings.size() -1)
+        OS << " ||\n    SpellingListIndex == ";
+      else
+        OS << "; }\n";
+    }
+  }
+}
+
 namespace clang {
 
 // Emits the class definitions for attributes.
@@ -903,6 +948,8 @@
     OS << "  virtual void printPretty(raw_ostream &OS,\n"
        << "                           const PrintingPolicy &Policy) const;\n";
 
+    writeAttrAccessorDefinition(R, OS);
+
     for (ai = Args.begin(); ai != ae; ++ai) {
       (*ai)->writeAccessors(OS);
       OS << "\n\n";
Index: lib/Sema/SemaDeclAttr.cpp
===================================================================
--- lib/Sema/SemaDeclAttr.cpp
+++ lib/Sema/SemaDeclAttr.cpp
@@ -3316,12 +3316,11 @@
 
   if (Attr.getNumArgs() == 0) {
     D->addAttr(::new (S.Context) AlignedAttr(Attr.getRange(), S.Context, 
-               true, 0, Attr.isDeclspecAttribute(),
-               Attr.getAttributeSpellingListIndex()));
+               true, 0, Attr.getAttributeSpellingListIndex()));
     return;
   }
 
-  S.AddAlignedAttr(Attr.getRange(), D, Attr.getArg(0), 
+  S.AddAlignedAttr(Attr.getRange(), D, Attr.getArg(0),
                    Attr.isDeclspecAttribute(),
                    Attr.getAttributeSpellingListIndex());
 }
@@ -3334,8 +3333,8 @@
 
   if (E->isTypeDependent() || E->isValueDependent()) {
     // Save dependent expressions in the AST to be instantiated.
-    D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, E, 
-                                           isDeclSpec, SpellingListIndex));
+    D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, E,
+                                           SpellingListIndex));
     return;
   }
   
@@ -3357,22 +3356,22 @@
     // We've already verified it's a power of 2, now let's make sure it's
     // 8192 or less.
     if (Alignment.getZExtValue() > 8192) {
-      Diag(AttrLoc, diag::err_attribute_aligned_greater_than_8192) 
+      Diag(AttrLoc, diag::err_attribute_aligned_greater_than_8192)
         << E->getSourceRange();
       return;
     }
   }
 
-  D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, ICE.take(), 
-                                         isDeclSpec, SpellingListIndex));
+  D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, ICE.take(),
+                                         SpellingListIndex));
 }
 
-void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *TS, 
-                          bool isDeclSpec, unsigned SpellingListIndex) {
+void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *TS,
+                          unsigned SpellingListIndex) {
   // FIXME: Cache the number on the Attr object if non-dependent?
   // FIXME: Perform checking of type validity
-  D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, false, TS, 
-                                         isDeclSpec, SpellingListIndex));
+  D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, false, TS,
+                                         SpellingListIndex));
   return;
 }
 
Index: lib/Sema/SemaTemplateInstantiateDecl.cpp
===================================================================
--- lib/Sema/SemaTemplateInstantiateDecl.cpp
+++ lib/Sema/SemaTemplateInstantiateDecl.cpp
@@ -79,8 +79,8 @@
           ExprResult Result = SubstExpr(Aligned->getAlignmentExpr(),
                                         TemplateArgs);
           if (!Result.isInvalid())
-            AddAlignedAttr(Aligned->getLocation(), New, Result.takeAs<Expr>(), 
-                           Aligned->getIsMSDeclSpec(),
+            AddAlignedAttr(Aligned->getLocation(), New, Result.takeAs<Expr>(),
+                           Aligned->isDeclspec(),
                            Aligned->getSpellingListIndex());
         } else {
           TypeSourceInfo *Result = SubstType(Aligned->getAlignmentType(),
@@ -89,7 +89,6 @@
                                              DeclarationName());
           if (Result)
             AddAlignedAttr(Aligned->getLocation(), New, Result,
-                           Aligned->getIsMSDeclSpec(),
                            Aligned->getSpellingListIndex());
         }
         continue;
Index: test/SemaCXX/attr-print.cpp
===================================================================
--- test/SemaCXX/attr-print.cpp
+++ test/SemaCXX/attr-print.cpp
@@ -1,12 +1,10 @@
 // RUN: %clang_cc1 %s -ast-print -fms-extensions | FileCheck %s
 
-// FIXME: align attribute print
-
-// CHECK: int x __attribute__((aligned(4, 0)));
+// CHECK: int x __attribute__((aligned(4)));
 int x __attribute__((aligned(4)));
 
 // FIXME: Print this at a valid location for a __declspec attr.
-// CHECK: int y __declspec(align(4, 1));
+// CHECK: int y __declspec(align(4));
 __declspec(align(4)) int y;
 
 // CHECK: void foo() __attribute__((const));
Index: test/SemaCXX/cxx11-attr-print.cpp
===================================================================
--- test/SemaCXX/cxx11-attr-print.cpp
+++ test/SemaCXX/cxx11-attr-print.cpp
@@ -1,14 +1,13 @@
 // RUN: %clang_cc1 -std=c++11 -ast-print -fms-extensions %s | FileCheck %s
-// FIXME: align attribute print
-
-// CHECK: int x __attribute__((aligned(4, 0)));
+//
+// CHECK: int x __attribute__((aligned(4)));
 int x __attribute__((aligned(4)));
 
 // FIXME: Print this at a valid location for a __declspec attr.
-// CHECK: int y __declspec(align(4, 1));
+// CHECK: int y __declspec(align(4));
 __declspec(align(4)) int y;
 
-// CHECK: gnu::aligned(4, 0)]];
+// CHECK: gnu::aligned(4)]];
 int z [[gnu::aligned(4)]];
 
 // CHECK: __attribute__((deprecated("warning")));
@@ -17,10 +16,10 @@
 // CHECK: gnu::deprecated("warning")]];
 int b [[gnu::deprecated("warning")]];
 
-// CHECK: int cxx11_alignas alignas(4, 0);
+// CHECK: int cxx11_alignas alignas(4);
 alignas(4) int cxx11_alignas;
 
-// CHECK: int c11_alignas _Alignas(alignof(int), 0);
+// CHECK: int c11_alignas _Alignas(alignof(int));
 _Alignas(int) int c11_alignas;
 
 // CHECK: void foo() __attribute__((const));
Index: test/Sema/attr-print.c
===================================================================
--- test/Sema/attr-print.c
+++ test/Sema/attr-print.c
@@ -1,13 +1,10 @@
 // RUN: %clang_cc1 %s -ast-print -fms-extensions | FileCheck %s
 
-// FIXME: we need to fix the "BoolArgument<"IsMSDeclSpec">"
-// hack in Attr.td for attribute "Aligned".
-
-// CHECK: int x __attribute__((aligned(4, 0)));
+// CHECK: int x __attribute__((aligned(4)));
 int x __attribute__((aligned(4)));
 
 // FIXME: Print this at a valid location for a __declspec attr.
-// CHECK: int y __declspec(align(4, 1));
+// CHECK: int y __declspec(align(4));
 __declspec(align(4)) int y;
 
 // CHECK: void foo() __attribute__((const));
Index: include/clang/Basic/Attr.td
===================================================================
--- include/clang/Basic/Attr.td
+++ include/clang/Basic/Attr.td
@@ -93,6 +93,11 @@
 }
 class Keyword<string name> : Spelling<name, "Keyword">;
 
+class Accessor<string name, list<Spelling> spellings> {
+  string Name = name;
+  list<Spelling> Spellings = spellings;
+}
+
 class Attr {
   // The various ways in which an attribute can be spelled in source
   list<Spelling> Spellings;
@@ -100,8 +105,10 @@
   list<AttrSubject> Subjects;
   // The arguments allowed on an attribute
   list<Argument> Args = [];
-  // Set to true for attributes with arguments which require delayed parsing. 
-  bit LateParsed = 0;  
+  // Accessors which should be generated for the attribute.
+  list<Accessor> Accessors = [];
+  // Set to true for attributes with arguments which require delayed parsing.
+  bit LateParsed = 0;
   // Set to false to prevent an attribute from being propagated from a template
   // to the instantiation.
   bit Clone = 1;
@@ -115,7 +122,7 @@
   bit Ignored = 0;
   // Set to true if each of the spellings is a distinct attribute.
   bit DistinctSpellings = 0;
-  // Any additional text that should be included verbatim in the class.  
+  // Any additional text that should be included verbatim in the class.
   code AdditionalMembers = [{}];
 }
 
@@ -140,7 +147,7 @@
 def AddressSpace : Attr {
   let Spellings = [GNU<"address_space">];
   let Args = [IntArgument<"AddressSpace">];
-  let ASTNode = 0;  
+  let ASTNode = 0;
 }
 
 def Alias : InheritableAttr {
@@ -152,7 +159,11 @@
   let Spellings = [GNU<"aligned">, Declspec<"align">, CXX11<"gnu", "aligned">,
                    Keyword<"alignas">, Keyword<"_Alignas">];
   let Subjects = [NonBitField, NormalVar, Tag];
-  let Args = [AlignedArgument<"Alignment">, BoolArgument<"IsMSDeclSpec">];
+  let Args = [AlignedArgument<"Alignment">];
+  let Accessors = [Accessor<"isGNU", [GNU<"aligned">, CXX11<"gnu","aligned">]>,
+                   Accessor<"isAlignas",
+                   [Keyword<"alignas">, Keyword<"_Alignas">]>,
+                   Accessor<"isDeclspec",[Declspec<"align">]>];
 }
 
 def AlignMac68k : InheritableAttr {
Index: include/clang/Sema/Sema.h
===================================================================
--- include/clang/Sema/Sema.h
+++ include/clang/Sema/Sema.h
@@ -6533,7 +6533,7 @@
   void AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E,
                       bool isDeclSpec, unsigned SpellingListIndex);
   void AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *T,
-                      bool isDeclSpec, unsigned SpellingListIndex);
+                      unsigned SpellingListIndex);
 
   /// \brief The kind of conversion being performed.
   enum CheckedConversionKind {
_______________________________________________
cfe-commits mailing list
[email protected]
http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits

Reply via email to