diff options
-rw-r--r-- | include/clang/AST/Attr.h | 22 | ||||
-rw-r--r-- | include/clang/Sema/AttributeList.h | 5 | ||||
-rw-r--r-- | include/clang/Sema/CMakeLists.txt | 7 | ||||
-rw-r--r-- | include/clang/Sema/Makefile | 9 | ||||
-rw-r--r-- | include/clang/Sema/Sema.h | 20 | ||||
-rw-r--r-- | lib/Sema/AttributeList.cpp | 11 | ||||
-rw-r--r-- | lib/Sema/CMakeLists.txt | 1 | ||||
-rw-r--r-- | lib/Sema/SemaDecl.cpp | 19 | ||||
-rw-r--r-- | lib/Sema/SemaDeclAttr.cpp | 565 | ||||
-rw-r--r-- | lib/Sema/TargetAttributesSema.cpp | 25 | ||||
-rw-r--r-- | test/Sema/attr-print.c | 16 | ||||
-rw-r--r-- | test/SemaCXX/attr-print.cpp | 15 | ||||
-rw-r--r-- | test/SemaCXX/cxx11-attr-print.cpp | 50 | ||||
-rw-r--r-- | utils/TableGen/ClangAttrEmitter.cpp | 161 | ||||
-rw-r--r-- | utils/TableGen/TableGen.cpp | 7 | ||||
-rw-r--r-- | utils/TableGen/TableGenBackends.h | 1 |
16 files changed, 690 insertions, 244 deletions
diff --git a/include/clang/AST/Attr.h b/include/clang/AST/Attr.h index aad2fb8577..fbb097011f 100644 --- a/include/clang/AST/Attr.h +++ b/include/clang/AST/Attr.h @@ -44,10 +44,14 @@ private: unsigned AttrKind : 16; protected: + /// An index into the spelling list of an + /// attribute defined in Attr.td file. + unsigned SpellingListIndex : 4; + bool Inherited : 1; virtual ~Attr(); - + void* operator new(size_t bytes) throw() { llvm_unreachable("Attrs cannot be allocated with regular 'new'."); } @@ -67,14 +71,17 @@ public: } protected: - Attr(attr::Kind AK, SourceRange R) - : Range(R), AttrKind(AK), Inherited(false) {} + Attr(attr::Kind AK, SourceRange R, unsigned SpellingListIndex = 0) + : Range(R), AttrKind(AK), SpellingListIndex(SpellingListIndex), + Inherited(false) {} public: attr::Kind getKind() const { return static_cast<attr::Kind>(AttrKind); } + + unsigned getSpellingListIndex() const { return SpellingListIndex; } SourceLocation getLocation() const { return Range.getBegin(); } SourceRange getRange() const { return Range; } @@ -95,8 +102,8 @@ public: class InheritableAttr : public Attr { virtual void anchor(); protected: - InheritableAttr(attr::Kind AK, SourceRange R) - : Attr(AK, R) {} + InheritableAttr(attr::Kind AK, SourceRange R, unsigned SpellingListIndex = 0) + : Attr(AK, R, SpellingListIndex) {} public: void setInherited(bool I) { Inherited = I; } @@ -110,8 +117,9 @@ public: class InheritableParamAttr : public InheritableAttr { virtual void anchor(); protected: - InheritableParamAttr(attr::Kind AK, SourceRange R) - : InheritableAttr(AK, R) {} + InheritableParamAttr(attr::Kind AK, SourceRange R, + unsigned SpellingListIndex = 0) + : InheritableAttr(AK, R, SpellingListIndex) {} public: // Implement isa/cast/dyncast/etc. diff --git a/include/clang/Sema/AttributeList.h b/include/clang/Sema/AttributeList.h index 3055df65eb..65a959526c 100644 --- a/include/clang/Sema/AttributeList.h +++ b/include/clang/Sema/AttributeList.h @@ -340,6 +340,11 @@ public: "Not a type_tag_for_datatype attribute"); return getTypeTagForDatatypeDataSlot().MustBeNull; } + + /// \brief Get an index into the attribute spelling list + /// defined in Attr.td. This index is used by an attribute + /// to pretty print itself. + unsigned getAttributeSpellingListIndex() const; }; /// A factory, from which one makes pools, from which one creates diff --git a/include/clang/Sema/CMakeLists.txt b/include/clang/Sema/CMakeLists.txt index 03f99a3630..6b5d222b5d 100644 --- a/include/clang/Sema/CMakeLists.txt +++ b/include/clang/Sema/CMakeLists.txt @@ -11,4 +11,9 @@ clang_tablegen(AttrParsedAttrList.inc -gen-clang-attr-parsed-attr-list clang_tablegen(AttrParsedAttrKinds.inc -gen-clang-attr-parsed-attr-kinds -I ${CMAKE_CURRENT_SOURCE_DIR}/../../ SOURCE ../Basic/Attr.td - TARGET ClangAttrParsedAttrKinds)
\ No newline at end of file + TARGET ClangAttrParsedAttrKinds) + +clang_tablegen(AttrSpellingListIndex.inc -gen-clang-attr-spelling-index + -I ${CMAKE_CURRENT_SOURCE_DIR}/../../ + SOURCE ../Basic/Attr.td + TARGET ClangAttrSpellingListIndex) diff --git a/include/clang/Sema/Makefile b/include/clang/Sema/Makefile index f6662d6b08..7d658a7c11 100644 --- a/include/clang/Sema/Makefile +++ b/include/clang/Sema/Makefile @@ -1,6 +1,7 @@ CLANG_LEVEL := ../../.. TD_SRC_DIR = $(PROJ_SRC_DIR)/../Basic -BUILT_SOURCES = AttrTemplateInstantiate.inc AttrParsedAttrList.inc AttrParsedAttrKinds.inc +BUILT_SOURCES = AttrTemplateInstantiate.inc AttrParsedAttrList.inc AttrParsedAttrKinds.inc \ + AttrSpellingListIndex.inc TABLEGEN_INC_FILES_COMMON = 1 @@ -24,4 +25,10 @@ $(ObjDir)/AttrParsedAttrKinds.inc.tmp : $(TD_SRC_DIR)/Attr.td \ $(Verb) $(ClangTableGen) -gen-clang-attr-parsed-attr-kinds -o \ $(call SYSPATH, $@) -I $(PROJ_SRC_DIR)/../../ $< +$(ObjDir)/AttrSpellingListIndex.inc.tmp : $(TD_SRC_DIR)/Attr.td \ + $(CLANG_TBLGEN) $(ObjDir)/.dir + $(Echo) "Building Clang attribute spelling list index with tablegen" + $(Verb) $(ClangTableGen) -gen-clang-attr-spelling-index -o \ + $(call SYSPATH, $@) -I $(PROJ_SRC_DIR)/../../ $< + diff --git a/include/clang/Sema/Sema.h b/include/clang/Sema/Sema.h index f649e1a48a..8b826ad350 100644 --- a/include/clang/Sema/Sema.h +++ b/include/clang/Sema/Sema.h @@ -1681,14 +1681,20 @@ public: VersionTuple Obsoleted, bool IsUnavailable, StringRef Message, - bool Override); + bool Override, + unsigned AttrSpellingListIndex); VisibilityAttr *mergeVisibilityAttr(Decl *D, SourceRange Range, - VisibilityAttr::VisibilityType Vis); - DLLImportAttr *mergeDLLImportAttr(Decl *D, SourceRange Range); - DLLExportAttr *mergeDLLExportAttr(Decl *D, SourceRange Range); + VisibilityAttr::VisibilityType Vis, + unsigned AttrSpellingListIndex); + DLLImportAttr *mergeDLLImportAttr(Decl *D, SourceRange Range, + unsigned AttrSpellingListIndex); + DLLExportAttr *mergeDLLExportAttr(Decl *D, SourceRange Range, + unsigned AttrSpellingListIndex); FormatAttr *mergeFormatAttr(Decl *D, SourceRange Range, StringRef Format, - int FormatIdx, int FirstArg); - SectionAttr *mergeSectionAttr(Decl *D, SourceRange Range, StringRef Name); + int FormatIdx, int FirstArg, + unsigned AttrSpellingListIndex); + SectionAttr *mergeSectionAttr(Decl *D, SourceRange Range, StringRef Name, + unsigned AttrSpellingListIndex); bool mergeDeclAttribute(NamedDecl *New, InheritableAttr *Attr, bool Override); @@ -6520,7 +6526,7 @@ public: /// AddAlignedAttr - Adds an aligned attribute to a particular declaration. void AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E, - bool isDeclSpec); + bool isDeclSpec, unsigned SpellingListIndex = 0); void AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *T, bool isDeclSpec); diff --git a/lib/Sema/AttributeList.cpp b/lib/Sema/AttributeList.cpp index 99479267a6..e227d4e840 100644 --- a/lib/Sema/AttributeList.cpp +++ b/lib/Sema/AttributeList.cpp @@ -125,3 +125,14 @@ AttributeList::Kind AttributeList::getKind(const IdentifierInfo *Name, return ::getAttrKind(Buf); } + +unsigned AttributeList::getAttributeSpellingListIndex() const { + // Both variables will be used in tablegen generated + // attribute spell list index matching code. + StringRef Name = AttrName->getName(); + StringRef Scope = ScopeName ? ScopeName->getName() : ""; + +#include "clang/Sema/AttrSpellingListIndex.inc" + +} + diff --git a/lib/Sema/CMakeLists.txt b/lib/Sema/CMakeLists.txt index 7cfe3ae846..4636a097fd 100644 --- a/lib/Sema/CMakeLists.txt +++ b/lib/Sema/CMakeLists.txt @@ -58,6 +58,7 @@ add_dependencies(clangSema ClangAttrList ClangAttrParsedAttrList ClangAttrParsedAttrKinds + ClangAttrSpellingListIndex ClangAttrTemplateInstantiate ClangCommentNodes ClangDeclNodes diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp index 2a1894674a..ca9610b7d7 100644 --- a/lib/Sema/SemaDecl.cpp +++ b/lib/Sema/SemaDecl.cpp @@ -1825,22 +1825,29 @@ DeclHasAttr(const Decl *D, const Attr *A) { bool Sema::mergeDeclAttribute(NamedDecl *D, InheritableAttr *Attr, bool Override) { InheritableAttr *NewAttr = NULL; + unsigned AttrSpellingListIndex = Attr->getSpellingListIndex(); if (AvailabilityAttr *AA = dyn_cast<AvailabilityAttr>(Attr)) NewAttr = mergeAvailabilityAttr(D, AA->getRange(), AA->getPlatform(), AA->getIntroduced(), AA->getDeprecated(), AA->getObsoleted(), AA->getUnavailable(), - AA->getMessage(), Override); + AA->getMessage(), Override, + AttrSpellingListIndex); else if (VisibilityAttr *VA = dyn_cast<VisibilityAttr>(Attr)) - NewAttr = mergeVisibilityAttr(D, VA->getRange(), VA->getVisibility()); + NewAttr = mergeVisibilityAttr(D, VA->getRange(), VA->getVisibility(), + AttrSpellingListIndex); else if (DLLImportAttr *ImportA = dyn_cast<DLLImportAttr>(Attr)) - NewAttr = mergeDLLImportAttr(D, ImportA->getRange()); + NewAttr = mergeDLLImportAttr(D, ImportA->getRange(), + AttrSpellingListIndex); else if (DLLExportAttr *ExportA = dyn_cast<DLLExportAttr>(Attr)) - NewAttr = mergeDLLExportAttr(D, ExportA->getRange()); + NewAttr = mergeDLLExportAttr(D, ExportA->getRange(), + AttrSpellingListIndex); else if (FormatAttr *FA = dyn_cast<FormatAttr>(Attr)) NewAttr = mergeFormatAttr(D, FA->getRange(), FA->getType(), - FA->getFormatIdx(), FA->getFirstArg()); + FA->getFormatIdx(), FA->getFirstArg(), + AttrSpellingListIndex); else if (SectionAttr *SA = dyn_cast<SectionAttr>(Attr)) - NewAttr = mergeSectionAttr(D, SA->getRange(), SA->getName()); + NewAttr = mergeSectionAttr(D, SA->getRange(), SA->getName(), + AttrSpellingListIndex); else if (!DeclHasAttr(D, Attr)) NewAttr = cast<InheritableAttr>(Attr->clone(Context)); diff --git a/lib/Sema/SemaDeclAttr.cpp b/lib/Sema/SemaDeclAttr.cpp index beea474a7e..ea35330129 100644 --- a/lib/Sema/SemaDeclAttr.cpp +++ b/lib/Sema/SemaDeclAttr.cpp @@ -505,18 +505,22 @@ static void handleGuardedVarAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (!checkGuardedVarAttrCommon(S, D, Attr)) return; - D->addAttr(::new (S.Context) GuardedVarAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + GuardedVarAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handlePtGuardedVarAttr(Sema &S, Decl *D, - const AttributeList &Attr) { + const AttributeList &Attr) { if (!checkGuardedVarAttrCommon(S, D, Attr)) return; if (!threadSafetyCheckIsPointer(S, D, Attr)) return; - D->addAttr(::new (S.Context) PtGuardedVarAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + PtGuardedVarAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static bool checkGuardedByAttrCommon(Sema &S, Decl *D, @@ -596,7 +600,9 @@ static void handleScopedLockableAttr(Sema &S, Decl *D, if (!checkLockableAttrCommon(S, D, Attr)) return; - D->addAttr(::new (S.Context) ScopedLockableAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ScopedLockableAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleNoThreadSafetyAttr(Sema &S, Decl *D, @@ -629,8 +635,9 @@ static void handleNoAddressSafetyAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) NoAddressSafetyAnalysisAttr(Attr.getRange(), - S.Context)); + D->addAttr(::new (S.Context) + NoAddressSafetyAnalysisAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static bool checkAcquireOrderAttrCommon(Sema &S, Decl *D, @@ -675,8 +682,10 @@ static void handleAcquiredAfterAttr(Sema &S, Decl *D, return; Expr **StartArg = &Args[0]; - D->addAttr(::new (S.Context) AcquiredAfterAttr(Attr.getRange(), S.Context, - StartArg, Args.size())); + D->addAttr(::new (S.Context) + AcquiredAfterAttr(Attr.getRange(), S.Context, + StartArg, Args.size(), + Attr.getAttributeSpellingListIndex())); } static void handleAcquiredBeforeAttr(Sema &S, Decl *D, @@ -686,8 +695,10 @@ static void handleAcquiredBeforeAttr(Sema &S, Decl *D, return; Expr **StartArg = &Args[0]; - D->addAttr(::new (S.Context) AcquiredBeforeAttr(Attr.getRange(), S.Context, - StartArg, Args.size())); + D->addAttr(::new (S.Context) + AcquiredBeforeAttr(Attr.getRange(), S.Context, + StartArg, Args.size(), + Attr.getAttributeSpellingListIndex())); } static bool checkLockFunAttrCommon(Sema &S, Decl *D, @@ -718,9 +729,9 @@ static void handleSharedLockFunctionAttr(Sema &S, Decl *D, unsigned Size = Args.size(); Expr **StartArg = Size == 0 ? 0 : &Args[0]; - D->addAttr(::new (S.Context) SharedLockFunctionAttr(Attr.getRange(), - S.Context, - StartArg, Size)); + D->addAttr(::new (S.Context) + SharedLockFunctionAttr(Attr.getRange(), S.Context, StartArg, Size, + Attr.getAttributeSpellingListIndex())); } static void handleExclusiveLockFunctionAttr(Sema &S, Decl *D, @@ -731,9 +742,10 @@ static void handleExclusiveLockFunctionAttr(Sema &S, Decl *D, unsigned Size = Args.size(); Expr **StartArg = Size == 0 ? 0 : &Args[0]; - D->addAttr(::new (S.Context) ExclusiveLockFunctionAttr(Attr.getRange(), - S.Context, - StartArg, Size)); + D->addAttr(::new (S.Context) + ExclusiveLockFunctionAttr(Attr.getRange(), S.Context, + StartArg, Size, + Attr.getAttributeSpellingListIndex())); } static bool checkTryLockFunAttrCommon(Sema &S, Decl *D, @@ -770,10 +782,10 @@ static void handleSharedTrylockFunctionAttr(Sema &S, Decl *D, unsigned Size = Args.size(); Expr **StartArg = Size == 0 ? 0 : &Args[0]; - D->addAttr(::new (S.Context) SharedTrylockFunctionAttr(Attr.getRange(), - S.Context, - Attr.getArg(0), - StartArg, Size)); + D->addAttr(::new (S.Context) + SharedTrylockFunctionAttr(Attr.getRange(), S.Context, + Attr.getArg(0), StartArg, Size, + Attr.getAttributeSpellingListIndex())); } static void handleExclusiveTrylockFunctionAttr(Sema &S, Decl *D, @@ -784,10 +796,10 @@ static void handleExclusiveTrylockFunctionAttr(Sema &S, Decl *D, unsigned Size = Args.size(); Expr **StartArg = Size == 0 ? 0 : &Args[0]; - D->addAttr(::new (S.Context) ExclusiveTrylockFunctionAttr(Attr.getRange(), - S.Context, - Attr.getArg(0), - StartArg, Size)); + D->addAttr(::new (S.Context) + ExclusiveTrylockFunctionAttr(Attr.getRange(), S.Context, + Attr.getArg(0), StartArg, Size, + Attr.getAttributeSpellingListIndex())); } static bool checkLocksRequiredCommon(Sema &S, Decl *D, @@ -819,10 +831,10 @@ static void handleExclusiveLocksRequiredAttr(Sema &S, Decl *D, return; Expr **StartArg = &Args[0]; - D->addAttr(::new (S.Context) ExclusiveLocksRequiredAttr(Attr.getRange(), - S.Context, - StartArg, - Args.size())); + D->addAttr(::new (S.Context) + ExclusiveLocksRequiredAttr(Attr.getRange(), S.Context, + StartArg, Args.size(), + Attr.getAttributeSpellingListIndex())); } static void handleSharedLocksRequiredAttr(Sema &S, Decl *D, @@ -832,10 +844,10 @@ static void handleSharedLocksRequiredAttr(Sema &S, Decl *D, return; Expr **StartArg = &Args[0]; - D->addAttr(::new (S.Context) SharedLocksRequiredAttr(Attr.getRange(), - S.Context, - StartArg, - Args.size())); + D->addAttr(::new (S.Context) + SharedLocksRequiredAttr(Attr.getRange(), S.Context, + StartArg, Args.size(), + Attr.getAttributeSpellingListIndex())); } static void handleUnlockFunAttr(Sema &S, Decl *D, @@ -856,8 +868,9 @@ static void handleUnlockFunAttr(Sema &S, Decl *D, unsigned Size = Args.size(); Expr **StartArg = Size == 0 ? 0 : &Args[0]; - D->addAttr(::new (S.Context) UnlockFunctionAttr(Attr.getRange(), S.Context, - StartArg, Size)); + D->addAttr(::new (S.Context) + UnlockFunctionAttr(Attr.getRange(), S.Context, StartArg, Size, + Attr.getAttributeSpellingListIndex())); } static void handleLockReturnedAttr(Sema &S, Decl *D, @@ -880,8 +893,9 @@ static void handleLockReturnedAttr(Sema &S, Decl *D, if (Size == 0) return; - D->addAttr(::new (S.Context) LockReturnedAttr(Attr.getRange(), S.Context, - Args[0])); + D->addAttr(::new (S.Context) + LockReturnedAttr(Attr.getRange(), S.Context, Args[0], + Attr.getAttributeSpellingListIndex())); } static void handleLocksExcludedAttr(Sema &S, Decl *D, @@ -905,8 +919,9 @@ static void handleLocksExcludedAttr(Sema &S, Decl *D, return; Expr **StartArg = &Args[0]; - D->addAttr(::new (S.Context) LocksExcludedAttr(Attr.getRange(), S.Context, - StartArg, Size)); + D->addAttr(::new (S.Context) + LocksExcludedAttr(Attr.getRange(), S.Context, StartArg, Size, + Attr.getAttributeSpellingListIndex())); } @@ -940,14 +955,18 @@ static void handlePackedAttr(Sema &S, Decl *D, const AttributeList &Attr) { S.Diag(Attr.getLoc(), diag::warn_attribute_ignored_for_field_of_type) << Attr.getName() << FD->getType(); else - FD->addAttr(::new (S.Context) PackedAttr(Attr.getRange(), S.Context)); + FD->addAttr(::new (S.Context) + PackedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } else S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); } static void handleMsStructAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (RecordDecl *RD = dyn_cast<RecordDecl>(D)) - RD->addAttr(::new (S.Context) MsStructAttr(Attr.getRange(), S.Context)); + RD->addAttr(::new (S.Context) + MsStructAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); } @@ -960,7 +979,9 @@ static void handleIBAction(Sema &S, Decl *D, const AttributeList &Attr) { // The IBAction attributes only apply to instance methods. if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) if (MD->isInstanceMethod()) { - D->addAttr(::new (S.Context) IBActionAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + IBActionAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; } @@ -1001,7 +1022,9 @@ static void handleIBOutlet(Sema &S, Decl *D, const AttributeList &Attr) { if (!checkIBOutletCommon(S, D, Attr)) return; - D->addAttr(::new (S.Context) IBOutletAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + IBOutletAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleIBOutletCollection(Sema &S, Decl *D, @@ -1035,8 +1058,10 @@ static void handleIBOutletCollection(Sema &S, Decl *D, S.Diag(Attr.getLoc(), diag::err_iboutletcollection_type) << II; return; } - D->addAttr(::new (S.Context) IBOutletCollectionAttr(Attr.getRange(),S.Context, - QT, Attr.getParameterLoc())); + D->addAttr(::new (S.Context) + IBOutletCollectionAttr(Attr.getRange(),S.Context, + QT, Attr.getParameterLoc(), + Attr.getAttributeSpellingListIndex())); } static void possibleTransparentUnionPointerType(QualType &T) { @@ -1119,8 +1144,10 @@ static void handleAllocSizeAttr(Sema &S, Decl *D, const AttributeList &Attr) { << "alloc_size" << 0 /*function*/<< 1 /*pointer*/ << D->getSourceRange(); } - D->addAttr(::new (S.Context) AllocSizeAttr(Attr.getRange(), S.Context, - SizeArgs.data(), SizeArgs.size())); + D->addAttr(::new (S.Context) + AllocSizeAttr(Attr.getRange(), S.Context, + SizeArgs.data(), SizeArgs.size(), + Attr.getAttributeSpellingListIndex())); } static void handleNonNullAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1208,8 +1235,9 @@ static void handleNonNullAttr(Sema &S, Decl *D, const AttributeList &Attr) { unsigned *start = &NonNullArgs[0]; unsigned size = NonNullArgs.size(); llvm::array_pod_sort(start, start + size); - D->addAttr(::new (S.Context) NonNullAttr(Attr.getRange(), S.Context, start, - size)); + D->addAttr(::new (S.Context) + NonNullAttr(Attr.getRange(), S.Context, start, size, + Attr.getAttributeSpellingListIndex())); } static void handleOwnershipAttr(Sema &S, Decl *D, const AttributeList &AL) { @@ -1364,8 +1392,9 @@ static void handleOwnershipAttr(Sema &S, Decl *D, const AttributeList &AL) { return; } - D->addAttr(::new (S.Context) OwnershipAttr(AL.getLoc(), S.Context, K, Module, - start, size)); + D->addAttr(::new (S.Context) + OwnershipAttr(AL.getLoc(), S.Context, K, Module, start, size, + AL.getAttributeSpellingListIndex())); } static void handleWeakRefAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1438,7 +1467,9 @@ static void handleWeakRefAttr(Sema &S, Decl *D, const AttributeList &Attr) { Str->getString())); } - D->addAttr(::new (S.Context) WeakRefAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + WeakRefAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1466,7 +1497,8 @@ static void handleAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { // FIXME: check if target symbol exists in current file D->addAttr(::new (S.Context) AliasAttr(Attr.getRange(), S.Context, - Str->getString())); + Str->getString(), + Attr.getAttributeSpellingListIndex())); } static void handleMinSizeAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1480,7 +1512,9 @@ static void handleMinSizeAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) MinSizeAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + MinSizeAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleColdAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1500,7 +1534,8 @@ static void handleColdAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) ColdAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) ColdAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleHotAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1520,7 +1555,8 @@ static void handleHotAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) HotAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) HotAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleNakedAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1534,7 +1570,9 @@ static void handleNakedAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) NakedAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NakedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleAlwaysInlineAttr(Sema &S, Decl *D, @@ -1551,7 +1589,9 @@ static void handleAlwaysInlineAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) AlwaysInlineAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + AlwaysInlineAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleTLSModelAttr(Sema &S, Decl *D, @@ -1586,8 +1626,9 @@ static void handleTLSModelAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) TLSModelAttr(Attr.getRange(), S.Context, - Model)); + D->addAttr(::new (S.Context) + TLSModelAttr(Attr.getRange(), S.Context, Model, + Attr.getAttributeSpellingListIndex())); } static void handleMallocAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1600,7 +1641,9 @@ static void handleMallocAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) { QualType RetTy = FD->getResultType(); if (RetTy->isAnyPointerType() || RetTy->isBlockPointerType()) { - D->addAttr(::new (S.Context) MallocAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + MallocAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; } } @@ -1613,13 +1656,17 @@ static void handleMayAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (!checkAttributeNumArgs(S, Attr, 0)) return; - D->addAttr(::new (S.Context) MayAliasAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + MayAliasAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleNoCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { assert(!Attr.isInvalid()); if (isa<VarDecl>(D)) - D->addAttr(::new (S.Context) NoCommonAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NoCommonAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << Attr.getName() << ExpectedVariable; @@ -1628,7 +1675,9 @@ static void handleNoCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { static void handleCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { assert(!Attr.isInvalid()); if (isa<VarDecl>(D)) - D->addAttr(::new (S.Context) CommonAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CommonAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << Attr.getName() << ExpectedVariable; @@ -1645,7 +1694,9 @@ static void handleNoReturnAttr(Sema &S, Decl *D, const AttributeList &attr) { return; } - D->addAttr(::new (S.Context) NoReturnAttr(attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NoReturnAttr(attr.getRange(), S.Context, + attr.getAttributeSpellingListIndex())); } bool Sema::CheckNoReturnAttr(const AttributeList &attr) { @@ -1679,7 +1730,9 @@ static void handleAnalyzerNoReturnAttr(Sema &S, Decl *D, } } - D->addAttr(::new (S.Context) AnalyzerNoReturnAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + AnalyzerNoReturnAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleCXX11NoReturnAttr(Sema &S, Decl *D, @@ -1694,7 +1747,9 @@ static void handleCXX11NoReturnAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) CXX11NoReturnAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CXX11NoReturnAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } // PS3 PPU-specific. @@ -1755,7 +1810,9 @@ static void handleVecReturnAttr(Sema &S, Decl *D, const AttributeList &Attr) { count++; } - D->addAttr(::new (S.Context) VecReturnAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + VecReturnAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleDependencyAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1781,7 +1838,9 @@ static void handleUnusedAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) UnusedAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + UnusedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleReturnsTwiceAttr(Sema &S, Decl *D, @@ -1798,7 +1857,9 @@ static void handleReturnsTwiceAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) ReturnsTwiceAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ReturnsTwiceAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleUsedAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1819,7 +1880,9 @@ static void handleUsedAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) UsedAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + UsedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleConstructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1848,8 +1911,9 @@ static void handleConstructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) ConstructorAttr(Attr.getRange(), S.Context, - priority)); + D->addAttr(::new (S.Context) + ConstructorAttr(Attr.getRange(), S.Context, priority, + Attr.getAttributeSpellingListIndex())); } static void handleDestructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -1878,8 +1942,9 @@ static void handleDestructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) DestructorAttr(Attr.getRange(), S.Context, - priority)); + D->addAttr(::new (S.Context) + DestructorAttr(Attr.getRange(), S.Context, priority, + Attr.getAttributeSpellingListIndex())); } template <typename AttrTy> @@ -1903,7 +1968,8 @@ static void handleAttrWithMessage(Sema &S, Decl *D, const AttributeList &Attr, Str = SE->getString(); } - D->addAttr(::new (S.Context) AttrTy(Attr.getRange(), S.Context, Str)); + D->addAttr(::new (S.Context) AttrTy(Attr.getRange(), S.Context, Str, + Attr.getAttributeSpellingListIndex())); } static void handleArcWeakrefUnavailableAttr(Sema &S, Decl *D, @@ -1914,8 +1980,9 @@ static void handleArcWeakrefUnavailableAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) ArcWeakrefUnavailableAttr( - Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ArcWeakrefUnavailableAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleObjCRootClassAttr(Sema &S, Decl *D, @@ -1931,11 +1998,13 @@ static void handleObjCRootClassAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) ObjCRootClassAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ObjCRootClassAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } -static void handleObjCRequiresPropertyDefsAttr(Sema &S, Decl *D, - const AttributeList &Attr) { +static void handleObjCRequiresPropertyDefsAttr(Sema &S, Decl *D, + const AttributeList &Attr) { if (!isa<ObjCInterfaceDecl>(D)) { S.Diag(Attr.getLoc(), diag::err_suppress_autosynthesis); return; @@ -1947,8 +2016,9 @@ static void handleObjCRequiresPropertyDefsAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) ObjCRequiresPropertyDefsAttr( - Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ObjCRequiresPropertyDefsAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static bool checkAvailabilityAttr(Sema &S, SourceRange Range, @@ -2015,7 +2085,8 @@ AvailabilityAttr *Sema::mergeAvailabilityAttr(NamedDecl *D, SourceRange Range, VersionTuple Obsoleted, bool IsUnavailable, StringRef Message, - bool Override) { + bool Override, + unsigned AttrSpellingListIndex) { VersionTuple MergedIntroduced = Introduced; VersionTuple MergedDeprecated = Deprecated; VersionTuple MergedObsoleted = Obsoleted; @@ -2123,7 +2194,8 @@ AvailabilityAttr *Sema::mergeAvailabilityAttr(NamedDecl *D, SourceRange Range, MergedDeprecated, MergedObsoleted)) { return ::new (Context) AvailabilityAttr(Range, Context, Platform, Introduced, Deprecated, - Obsoleted, IsUnavailable, Message); + Obsoleted, IsUnavailable, Message, + AttrSpellingListIndex); } return NULL; } @@ -2132,7 +2204,8 @@ static void handleAvailabilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { IdentifierInfo *Platform = Attr.getParameterName(); SourceLocation PlatformLoc = Attr.getParameterLoc(); - + unsigned Index = Attr.getAttributeSpellingListIndex(); + if (AvailabilityAttr::getPrettyPlatformName(Platform->getName()).empty()) S.Diag(PlatformLoc, diag::warn_availability_unknown_platform) << Platform; @@ -2159,13 +2232,15 @@ static void handleAvailabilityAttr(Sema &S, Decl *D, Deprecated.Version, Obsoleted.Version, IsUnavailable, Str, - /*Override=*/false); + /*Override=*/false, + Index); if (NewAttr) D->addAttr(NewAttr); } VisibilityAttr *Sema::mergeVisibilityAttr(Decl *D, SourceRange Range, - VisibilityAttr::VisibilityType Vis) { + VisibilityAttr::VisibilityType Vis, + unsigned AttrSpellingListIndex) { if (isa<TypedefNameDecl>(D)) { Diag(Range.getBegin(), diag::warn_attribute_ignored) << "visibility"; return NULL; @@ -2179,7 +2254,8 @@ VisibilityAttr *Sema::mergeVisibilityAttr(Decl *D, SourceRange Range, Diag(Range.getBegin(), diag::note_previous_attribute); D->dropAttr<VisibilityAttr>(); } - return ::new (Context) VisibilityAttr(Range, Context, Vis); + return ::new (Context) VisibilityAttr(Range, Context, Vis, + AttrSpellingListIndex); } static void handleVisibilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2199,7 +2275,7 @@ static void handleVisibilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { StringRef TypeStr = Str->getString(); VisibilityAttr::VisibilityType type; - + if (TypeStr == "default") type = VisibilityAttr::Default; else if (TypeStr == "hidden") @@ -2220,7 +2296,9 @@ static void handleVisibilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - VisibilityAttr *NewAttr = S.mergeVisibilityAttr(D, Attr.getRange(), type); + unsigned Index = Attr.getAttributeSpellingListIndex(); + VisibilityAttr *NewAttr = S.mergeVisibilityAttr(D, Attr.getRange(), type, + Index); if (NewAttr) D->addAttr(NewAttr); } @@ -2289,7 +2367,9 @@ static void handleObjCExceptionAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) ObjCExceptionAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ObjCExceptionAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleObjCNSObject(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2320,7 +2400,9 @@ static void handleObjCNSObject(Sema &S, Decl *D, const AttributeList &Attr) { // case. S.Diag(D->getLocation(), diag::warn_nsobject_attribute); } - D->addAttr(::new (S.Context) ObjCNSObjectAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ObjCNSObjectAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void @@ -2335,7 +2417,9 @@ handleOverloadableAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) OverloadableAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + OverloadableAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleBlocksAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2359,7 +2443,9 @@ static void handleBlocksAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) BlocksAttr(Attr.getRange(), S.Context, type)); + D->addAttr(::new (S.Context) + BlocksAttr(Attr.getRange(), S.Context, type, + Attr.getAttributeSpellingListIndex())); } static void handleSentinelAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2451,8 +2537,9 @@ static void handleSentinelAttr(Sema &S, Decl *D, const AttributeList &Attr) { << Attr.getName() << ExpectedFunctionMethodOrBlock; return; } - D->addAttr(::new (S.Context) SentinelAttr(Attr.getRange(), S.Context, sentinel, - nullPos)); + D->addAttr(::new (S.Context) + SentinelAttr(Attr.getRange(), S.Context, sentinel, nullPos, + Attr.getAttributeSpellingListIndex())); } static void handleWarnUnusedResult(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2478,7 +2565,9 @@ static void handleWarnUnusedResult(Sema &S, Decl *D, const AttributeList &Attr) return; } - D->addAttr(::new (S.Context) WarnUnusedResultAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + WarnUnusedResultAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleWeakAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2500,7 +2589,9 @@ static void handleWeakAttr(Sema &S, Decl *D, const AttributeList &Attr) { NamedDecl *nd = cast<NamedDecl>(D); - nd->addAttr(::new (S.Context) WeakAttr(Attr.getRange(), S.Context)); + nd->addAttr(::new (S.Context) + WeakAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleWeakImportAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2527,7 +2618,9 @@ static void handleWeakImportAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) WeakImportAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + WeakImportAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } // Handles reqd_work_group_size and work_group_size_hint. @@ -2577,15 +2670,18 @@ static void handleWorkGroupSize(Sema &S, Decl *D, if (Attr.getKind() == AttributeList::AT_ReqdWorkGroupSize) D->addAttr(::new (S.Context) ReqdWorkGroupSizeAttr(Attr.getRange(), S.Context, - WGSize[0], WGSize[1], WGSize[2])); + WGSize[0], WGSize[1], WGSize[2], + Attr.getAttributeSpellingListIndex())); else D->addAttr(::new (S.Context) WorkGroupSizeHintAttr(Attr.getRange(), S.Context, - WGSize[0], WGSize[1], WGSize[2])); + WGSize[0], WGSize[1], WGSize[2], + Attr.getAttributeSpellingListIndex())); } SectionAttr *Sema::mergeSectionAttr(Decl *D, SourceRange Range, - StringRef Name) { + StringRef Name, + unsigned AttrSpellingListIndex) { if (SectionAttr *ExistingAttr = D->getAttr<SectionAttr>()) { if (ExistingAttr->getName() == Name) return NULL; @@ -2593,7 +2689,8 @@ SectionAttr *Sema::mergeSectionAttr(Decl *D, SourceRange Range, Diag(Range.getBegin(), diag::note_previous_attribute); return NULL; } - return ::new (Context) SectionAttr(Range, Context, Name); + return ::new (Context) SectionAttr(Range, Context, Name, + AttrSpellingListIndex); } static void handleSectionAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2623,8 +2720,10 @@ static void handleSectionAttr(Sema &S, Decl *D, const AttributeList &Attr) { S.Diag(SE->getLocStart(), diag::err_attribute_section_local_variable); return; } + + unsigned Index = Attr.getAttributeSpellingListIndex(); SectionAttr *NewAttr = S.mergeSectionAttr(D, Attr.getRange(), - SE->getString()); + SE->getString(), Index); if (NewAttr) D->addAttr(NewAttr); } @@ -2641,7 +2740,9 @@ static void handleNothrowAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (Existing->getLocation().isInvalid()) Existing->setRange(Attr.getRange()); } else { - D->addAttr(::new (S.Context) NoThrowAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NoThrowAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } } @@ -2656,7 +2757,9 @@ static void handleConstAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (Existing->getLocation().isInvalid()) Existing->setRange(Attr.getRange()); } else { - D->addAttr(::new (S.Context) ConstAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ConstAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex() )); } } @@ -2665,7 +2768,9 @@ static void handlePureAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (!checkAttributeNumArgs(S, Attr, 0)) return; - D->addAttr(::new (S.Context) PureAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + PureAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleCleanupAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -2724,7 +2829,9 @@ static void handleCleanupAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) CleanupAttr(Attr.getRange(), S.Context, FD)); + D->addAttr(::new (S.Context) + CleanupAttr(Attr.getRange(), S.Context, FD, + Attr.getAttributeSpellingListIndex())); S.MarkFunctionReferenced(Attr.getParameterLoc(), FD); } @@ -2799,8 +2906,9 @@ static void handleFormatArgAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) FormatArgAttr(Attr.getRange(), S.Context, - Idx.getZExtValue())); + D->addAttr(::new (S.Context) + FormatArgAttr(Attr.getRange(), S.Context, Idx.getZExtValue(), + Attr.getAttributeSpellingListIndex())); } enum FormatAttrKind { @@ -2875,12 +2983,14 @@ static void handleInitPriorityAttr(Sema &S, Decl *D, Attr.setInvalid(); return; } - D->addAttr(::new (S.Context) InitPriorityAttr(Attr.getRange(), S.Context, - prioritynum)); + D->addAttr(::new (S.Context) + InitPriorityAttr(Attr.getRange(), S.Context, prioritynum, + Attr.getAttributeSpellingListIndex())); } FormatAttr *Sema::mergeFormatAttr(Decl *D, SourceRange Range, StringRef Format, - int FormatIdx, int FirstArg) { + int FormatIdx, int FirstArg, + unsigned AttrSpellingListIndex) { // Check whether we already have an equivalent format attribute. for (specific_attr_iterator<FormatAttr> i = D->specific_attr_begin<FormatAttr>(), @@ -2898,8 +3008,8 @@ FormatAttr *Sema::mergeFormatAttr(Decl *D, SourceRange Range, StringRef Format, } } - return ::new (Context) FormatAttr(Range, Context, Format, FormatIdx, - FirstArg); + return ::new (Context) FormatAttr(Range, Context, Format, FormatIdx, FirstArg, + AttrSpellingListIndex); } /// Handle __attribute__((format(type,idx,firstarg))) attributes based on @@ -3039,7 +3149,8 @@ static void handleFormatAttr(Sema &S, Decl *D, const AttributeList &Attr) { FormatAttr *NewAttr = S.mergeFormatAttr(D, Attr.getRange(), Format, Idx.getZExtValue(), - FirstArg.getZExtValue()); + FirstArg.getZExtValue(), + Attr.getAttributeSpellingListIndex()); if (NewAttr) D->addAttr(NewAttr); } @@ -3108,7 +3219,9 @@ static void handleTransparentUnionAttr(Sema &S, Decl *D, } } - RD->addAttr(::new (S.Context) TransparentUnionAttr(Attr.getRange(), S.Context)); + RD->addAttr(::new (S.Context) + TransparentUnionAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleAnnotateAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -3133,8 +3246,10 @@ static void handleAnnotateAttr(Sema &S, Decl *D, const AttributeList &Attr) { if ((*i)->getAnnotation() == SE->getString()) return; } - D->addAttr(::new (S.Context) AnnotateAttr(Attr.getRange(), S.Context, - SE->getString())); + + D->addAttr(::new (S.Context) + AnnotateAttr(Attr.getRange(), S.Context, SE->getString(), + Attr.getAttributeSpellingListIndex())); } static void handleAlignedAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -3150,16 +3265,18 @@ static void handleAlignedAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (Attr.getNumArgs() == 0) { D->addAttr(::new (S.Context) AlignedAttr(Attr.getRange(), S.Context, - true, 0, Attr.isDeclspecAttribute())); + true, 0, Attr.isDeclspecAttribute(), + Attr.getAttributeSpellingListIndex())); return; } S.AddAlignedAttr(Attr.getRange(), D, Attr.getArg(0), - Attr.isDeclspecAttribute()); + Attr.isDeclspecAttribute(), + Attr.getAttributeSpellingListIndex()); } void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E, - bool isDeclSpec) { + bool isDeclSpec, unsigned SpellingListIndex) { // FIXME: Handle pack-expansions here. if (DiagnoseUnexpandedParameterPack(E)) return; @@ -3167,7 +3284,7 @@ void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E, if (E->isTypeDependent() || E->isValueDependent()) { // Save dependent expressions in the AST to be instantiated. D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, E, - isDeclSpec)); + isDeclSpec, SpellingListIndex)); return; } @@ -3196,7 +3313,7 @@ void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E, } D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, ICE.take(), - isDeclSpec)); + isDeclSpec, SpellingListIndex)); } void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *TS, @@ -3399,7 +3516,9 @@ static void handleNoDebugAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) NoDebugAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NoDebugAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleNoInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -3414,7 +3533,9 @@ static void handleNoInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) NoInlineAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NoInlineAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleNoInstrumentFunctionAttr(Sema &S, Decl *D, @@ -3430,8 +3551,9 @@ static void handleNoInstrumentFunctionAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) NoInstrumentFunctionAttr(Attr.getRange(), - S.Context)); + D->addAttr(::new (S.Context) + NoInstrumentFunctionAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleConstantAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -3448,7 +3570,9 @@ static void handleConstantAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) CUDAConstantAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CUDAConstantAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } else { S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "constant"; } @@ -3468,7 +3592,9 @@ static void handleDeviceAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) CUDADeviceAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CUDADeviceAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } else { S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "device"; } @@ -3501,7 +3627,9 @@ static void handleGlobalAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) CUDAGlobalAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CUDAGlobalAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } else { S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "global"; } @@ -3520,7 +3648,9 @@ static void handleHostAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) CUDAHostAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CUDAHostAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } else { S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "host"; } @@ -3532,14 +3662,15 @@ static void handleSharedAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (!checkAttributeNumArgs(S, Attr, 0)) return; - if (!isa<VarDecl>(D)) { S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << Attr.getName() << ExpectedVariable; return; } - D->addAttr(::new (S.Context) CUDASharedAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CUDASharedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } else { S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "shared"; } @@ -3562,7 +3693,9 @@ static void handleGNUInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) GNUInlineAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + GNUInlineAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleCallConvAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -3583,19 +3716,29 @@ static void handleCallConvAttr(Sema &S, Decl *D, const AttributeList &Attr) { switch (Attr.getKind()) { case AttributeList::AT_FastCall: - D->addAttr(::new (S.Context) FastCallAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + FastCallAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_StdCall: - D->addAttr(::new (S.Context) StdCallAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + StdCallAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_ThisCall: - D->addAttr(::new (S.Context) ThisCallAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ThisCallAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_CDecl: - D->addAttr(::new (S.Context) CDeclAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CDeclAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_Pascal: - D->addAttr(::new (S.Context) PascalAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + PascalAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_Pcs: { PcsAttr::PCSType PCS; @@ -3610,14 +3753,20 @@ static void handleCallConvAttr(Sema &S, Decl *D, const AttributeList &Attr) { llvm_unreachable("unexpected calling convention in pcs attribute"); } - D->addAttr(::new (S.Context) PcsAttr(Attr.getRange(), S.Context, PCS)); + D->addAttr(::new (S.Context) + PcsAttr(Attr.getRange(), S.Context, PCS, + Attr.getAttributeSpellingListIndex())); return; } case AttributeList::AT_PnaclCall: - D->addAttr(::new (S.Context) PnaclCallAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + PnaclCallAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_IntelOclBicc: - D->addAttr(::new (S.Context) IntelOclBiccAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + IntelOclBiccAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; default: @@ -3706,7 +3855,9 @@ static void handleRegparmAttr(Sema &S, Decl *D, const AttributeList &Attr) { return; } - D->addAttr(::new (S.Context) RegparmAttr(Attr.getRange(), S.Context, numParams)); + D->addAttr(::new (S.Context) + RegparmAttr(Attr.getRange(), S.Context, numParams, + Attr.getAttributeSpellingListIndex())); } /// Checks a regparm attribute, returning true if it is ill-formed and @@ -3786,9 +3937,11 @@ static void handleLaunchBoundsAttr(Sema &S, Decl *D, const AttributeList &Attr){ } } - D->addAttr(::new (S.Context) CUDALaunchBoundsAttr(Attr.getRange(), S.Context, - MaxThreads.getZExtValue(), - MinBlocks.getZExtValue())); + D->addAttr(::new (S.Context) + CUDALaunchBoundsAttr(Attr.getRange(), S.Context, + MaxThreads.getZExtValue(), + MinBlocks.getZExtValue(), + Attr.getAttributeSpellingListIndex())); } else { S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "launch_bounds"; } @@ -3839,12 +3992,10 @@ static void handleArgumentWithTypeTagAttr(Sema &S, Decl *D, } } - D->addAttr(::new (S.Context) ArgumentWithTypeTagAttr(Attr.getRange(), - S.Context, - ArgumentKind, - ArgumentIdx, - TypeTagIdx, - IsPointer)); + D->addAttr(::new (S.Context) + ArgumentWithTypeTagAttr(Attr.getRange(), S.Context, ArgumentKind, + ArgumentIdx, TypeTagIdx, IsPointer, + Attr.getAttributeSpellingListIndex())); } static void handleTypeTagForDatatypeAttr(Sema &S, Decl *D, @@ -3858,13 +4009,12 @@ static void handleTypeTagForDatatypeAttr(Sema &S, Decl *D, QualType MatchingCType = S.GetTypeFromParser(Attr.getMatchingCType(), NULL); - D->addAttr(::new (S.Context) TypeTagForDatatypeAttr( - Attr.getRange(), - S.Context, - PointerKind, - MatchingCType, - Attr.getLayoutCompatible(), - Attr.getMustBeNull())); + D->addAttr(::new (S.Context) + TypeTagForDatatypeAttr(Attr.getRange(), S.Context, PointerKind, + MatchingCType, + Attr.getLayoutCompatible(), + Attr.getMustBeNull(), + Attr.getAttributeSpellingListIndex())); } //===----------------------------------------------------------------------===// @@ -3906,9 +4056,13 @@ static void handleNSConsumedAttr(Sema &S, Decl *D, const AttributeList &Attr) { } if (cf) - param->addAttr(::new (S.Context) CFConsumedAttr(Attr.getRange(), S.Context)); + param->addAttr(::new (S.Context) + CFConsumedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else - param->addAttr(::new (S.Context) NSConsumedAttr(Attr.getRange(), S.Context)); + param->addAttr(::new (S.Context) + NSConsumedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleNSConsumesSelfAttr(Sema &S, Decl *D, @@ -3919,7 +4073,9 @@ static void handleNSConsumesSelfAttr(Sema &S, Decl *D, return; } - D->addAttr(::new (S.Context) NSConsumesSelfAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NSConsumesSelfAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handleNSReturnsRetainedAttr(Sema &S, Decl *D, @@ -3971,24 +4127,29 @@ static void handleNSReturnsRetainedAttr(Sema &S, Decl *D, default: llvm_unreachable("invalid ownership attribute"); case AttributeList::AT_NSReturnsAutoreleased: - D->addAttr(::new (S.Context) NSReturnsAutoreleasedAttr(Attr.getRange(), - S.Context)); + D->addAttr(::new (S.Context) + NSReturnsAutoreleasedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_CFReturnsNotRetained: - D->addAttr(::new (S.Context) CFReturnsNotRetainedAttr(Attr.getRange(), - S.Context)); + D->addAttr(::new (S.Context) + CFReturnsNotRetainedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_NSReturnsNotRetained: - D->addAttr(::new (S.Context) NSReturnsNotRetainedAttr(Attr.getRange(), - S.Context)); + D->addAttr(::new (S.Context) + NSReturnsNotRetainedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_CFReturnsRetained: - D->addAttr(::new (S.Context) CFReturnsRetainedAttr(Attr.getRange(), - S.Context)); + D->addAttr(::new (S.Context) + CFReturnsRetainedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; case AttributeList::AT_NSReturnsRetained: - D->addAttr(::new (S.Context) NSReturnsRetainedAttr(Attr.getRange(), - S.Context)); + D->addAttr(::new (S.Context) + NSReturnsRetainedAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); return; }; } @@ -4018,8 +4179,9 @@ static void handleObjCReturnsInnerPointerAttr(Sema &S, Decl *D, return; } - method->addAttr( - ::new (S.Context) ObjCReturnsInnerPointerAttr(attr.getRange(), S.Context)); + method->addAttr(::new (S.Context) + ObjCReturnsInnerPointerAttr(attr.getRange(), S.Context, + attr.getAttributeSpellingListIndex())); } static void handleObjCRequiresSuperAttr(Sema &S, Decl *D, @@ -4045,8 +4207,9 @@ static void handleObjCRequiresSuperAttr(Sema &S, Decl *D, return; } - method->addAttr( - ::new (S.Context) ObjCRequiresSuperAttr(attr.getRange(), S.Context)); + method->addAttr(::new (S.Context) + ObjCRequiresSuperAttr(attr.getRange(), S.Context, + attr.getAttributeSpellingListIndex())); } /// Handle cf_audited_transfer and cf_unknown_transfer. @@ -4076,11 +4239,13 @@ static void handleCFTransferAttr(Sema &S, Decl *D, const AttributeList &A) { // All clear; add the attribute. if (IsAudited) { - D->addAttr( - ::new (S.Context) CFAuditedTransferAttr(A.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CFAuditedTransferAttr(A.getRange(), S.Context, + A.getAttributeSpellingListIndex())); } else { - D->addAttr( - ::new (S.Context) CFUnknownTransferAttr(A.getRange(), S.Context)); + D->addAttr(::new (S.Context) + CFUnknownTransferAttr(A.getRange(), S.Context, + A.getAttributeSpellingListIndex())); } } @@ -4110,8 +4275,9 @@ static void handleNSBridgedAttr(Sema &S, Scope *Sc, Decl *D, } } - D->addAttr(::new (S.Context) NSBridgedAttr(Attr.getRange(), S.Context, - ParmName)); + D->addAttr(::new (S.Context) + NSBridgedAttr(Attr.getRange(), S.Context, ParmName, + Attr.getAttributeSpellingListIndex())); } static void handleObjCOwnershipAttr(Sema &S, Decl *D, @@ -4165,7 +4331,8 @@ static void handleObjCPreciseLifetimeAttr(Sema &S, Decl *D, } D->addAttr(::new (S.Context) - ObjCPreciseLifetimeAttr(Attr.getRange(), S.Context)); + ObjCPreciseLifetimeAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } //===----------------------------------------------------------------------===// @@ -4220,8 +4387,9 @@ static void handleUuidAttr(Sema &S, Decl *D, const AttributeList &Attr) { I++; } - D->addAttr(::new (S.Context) UuidAttr(Attr.getRange(), S.Context, - Str->getString())); + D->addAttr(::new (S.Context) + UuidAttr(Attr.getRange(), S.Context, Str->getString(), + Attr.getAttributeSpellingListIndex())); } else S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "uuid"; } @@ -4235,13 +4403,19 @@ static void handleInheritanceAttr(Sema &S, Decl *D, const AttributeList &Attr) { AttributeList::Kind Kind = Attr.getKind(); if (Kind == AttributeList::AT_SingleInheritance) D->addAttr( - ::new (S.Context) SingleInheritanceAttr(Attr.getRange(), S.Context)); + ::new (S.Context) + SingleInheritanceAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else if (Kind == AttributeList::AT_MultipleInheritance) D->addAttr( - ::new (S.Context) MultipleInheritanceAttr(Attr.getRange(), S.Context)); + ::new (S.Context) + MultipleInheritanceAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else if (Kind == AttributeList::AT_VirtualInheritance) D->addAttr( - ::new (S.Context) VirtualInheritanceAttr(Attr.getRange(), S.Context)); + ::new (S.Context) + VirtualInheritanceAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void handlePortabilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { @@ -4249,20 +4423,25 @@ static void handlePortabilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { AttributeList::Kind Kind = Attr.getKind(); if (Kind == AttributeList::AT_Ptr32) D->addAttr( - ::new (S.Context) Ptr32Attr(Attr.getRange(), S.Context)); + ::new (S.Context) Ptr32Attr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else if (Kind == AttributeList::AT_Ptr64) D->addAttr( - ::new (S.Context) Ptr64Attr(Attr.getRange(), S.Context)); + ::new (S.Context) Ptr64Attr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else if (Kind == AttributeList::AT_Win64) D->addAttr( - ::new (S.Context) Win64Attr(Attr.getRange(), S.Context)); + ::new (S.Context) Win64Attr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } else S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); } static void handleForceInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { if (S.LangOpts.MicrosoftExt) - D->addAttr(::new (S.Context) ForceInlineAttr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + ForceInlineAttr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); else S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); } diff --git a/lib/Sema/TargetAttributesSema.cpp b/lib/Sema/TargetAttributesSema.cpp index 1b8889de82..2f7701227d 100644 --- a/lib/Sema/TargetAttributesSema.cpp +++ b/lib/Sema/TargetAttributesSema.cpp @@ -151,7 +151,8 @@ static void HandleX86ForceAlignArgPointerAttr(Decl *D, S.Context)); } -DLLImportAttr *Sema::mergeDLLImportAttr(Decl *D, SourceRange Range) { +DLLImportAttr *Sema::mergeDLLImportAttr(Decl *D, SourceRange Range, + unsigned AttrSpellingListIndex) { if (D->hasAttr<DLLExportAttr>()) { Diag(Range.getBegin(), diag::warn_attribute_ignored) << "dllimport"; return NULL; @@ -160,7 +161,8 @@ DLLImportAttr *Sema::mergeDLLImportAttr(Decl *D, SourceRange Range) { if (D->hasAttr<DLLImportAttr>()) return NULL; - return ::new (Context) DLLImportAttr(Range, Context); + return ::new (Context) DLLImportAttr(Range, Context, + AttrSpellingListIndex); } static void HandleDLLImportAttr(Decl *D, const AttributeList &Attr, Sema &S) { @@ -189,12 +191,14 @@ static void HandleDLLImportAttr(Decl *D, const AttributeList &Attr, Sema &S) { return; } - DLLImportAttr *NewAttr = S.mergeDLLImportAttr(D, Attr.getRange()); + unsigned Index = Attr.getAttributeSpellingListIndex(); + DLLImportAttr *NewAttr = S.mergeDLLImportAttr(D, Attr.getRange(), Index); if (NewAttr) D->addAttr(NewAttr); } -DLLExportAttr *Sema::mergeDLLExportAttr(Decl *D, SourceRange Range) { +DLLExportAttr *Sema::mergeDLLExportAttr(Decl *D, SourceRange Range, + unsigned AttrSpellingListIndex) { if (DLLImportAttr *Import = D->getAttr<DLLImportAttr>()) { Diag(Import->getLocation(), diag::warn_attribute_ignored) << "dllimport"; D->dropAttr<DLLImportAttr>(); @@ -203,7 +207,8 @@ DLLExportAttr *Sema::mergeDLLExportAttr(Decl *D, SourceRange Range) { if (D->hasAttr<DLLExportAttr>()) return NULL; - return ::new (Context) DLLExportAttr(Range, Context); + return ::new (Context) DLLExportAttr(Range, Context, + AttrSpellingListIndex); } static void HandleDLLExportAttr(Decl *D, const AttributeList &Attr, Sema &S) { @@ -229,7 +234,8 @@ static void HandleDLLExportAttr(Decl *D, const AttributeList &Attr, Sema &S) { return; } - DLLExportAttr *NewAttr = S.mergeDLLExportAttr(D, Attr.getRange()); + unsigned Index = Attr.getAttributeSpellingListIndex(); + DLLExportAttr *NewAttr = S.mergeDLLExportAttr(D, Attr.getRange(), Index); if (NewAttr) D->addAttr(NewAttr); } @@ -274,7 +280,8 @@ static void HandleMips16Attr(Decl *D, const AttributeList &Attr, Sema &S) { << Attr.getName() << /* function */0; return; } - D->addAttr(::new (S.Context) Mips16Attr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) Mips16Attr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } static void HandleNoMips16Attr(Decl *D, const AttributeList &Attr, Sema &S) { @@ -289,7 +296,9 @@ static void HandleNoMips16Attr(Decl *D, const AttributeList &Attr, Sema &S) { << Attr.getName() << /* function */0; return; } - D->addAttr(::new (S.Context) NoMips16Attr(Attr.getRange(), S.Context)); + D->addAttr(::new (S.Context) + NoMips16Attr(Attr.getRange(), S.Context, + Attr.getAttributeSpellingListIndex())); } namespace { diff --git a/test/Sema/attr-print.c b/test/Sema/attr-print.c new file mode 100644 index 0000000000..f952e4b410 --- /dev/null +++ b/test/Sema/attr-print.c @@ -0,0 +1,16 @@ +// RUN: %clang_cc1 %s -ast-print | FileCheck %s + +// FIXME: we need to fix the "BoolArgument<"IsMSDeclSpec">" +// hack in Attr.td for attribute "Aligned". + +// CHECK: int x __attribute__((aligned(4, 0))); +int x __attribute__((aligned(4))); + +// CHECK: int y __attribute__((align(4, 0))); +int y __attribute__((align(4))); + +// CHECK: void foo() __attribute__((const)); +void foo() __attribute__((const)); + +// CHECK: void bar() __attribute__((__const)); +void bar() __attribute__((__const)); diff --git a/test/SemaCXX/attr-print.cpp b/test/SemaCXX/attr-print.cpp new file mode 100644 index 0000000000..317ba4d157 --- /dev/null +++ b/test/SemaCXX/attr-print.cpp @@ -0,0 +1,15 @@ +// RUN: %clang_cc1 %s -ast-print | FileCheck %s + +// FIXME: align attribute print + +// CHECK: int x __attribute__((aligned(4, 0))); +int x __attribute__((aligned(4))); + +// CHECK: int y __attribute__((align(4, 0))); +int y __attribute__((align(4))); + +// CHECK: void foo() __attribute__((const)); +void foo() __attribute__((const)); + +// CHECK: void bar() __attribute__((__const)); +void bar() __attribute__((__const)); diff --git a/test/SemaCXX/cxx11-attr-print.cpp b/test/SemaCXX/cxx11-attr-print.cpp new file mode 100644 index 0000000000..985d9a44fe --- /dev/null +++ b/test/SemaCXX/cxx11-attr-print.cpp @@ -0,0 +1,50 @@ +// RUN: %clang_cc1 -std=c++11 -ast-print %s | FileCheck %s +// FIXME: align attribute print + +// CHECK: int x __attribute__((aligned(4, 0))); +int x __attribute__((aligned(4))); + +// CHECK: int y __attribute__((align(4, 0))); +int y __attribute__((align(4))); + +// CHECK: gnu::aligned(4, 0)]]; +int z [[gnu::aligned(4)]]; + +// CHECK: __attribute__((deprecated("warning"))); +int a __attribute__((deprecated("warning"))); + +// CHECK: gnu::deprecated("warning")]]; +int b [[gnu::deprecated("warning")]]; + +// CHECK: void foo() __attribute__((const)); +void foo() __attribute__((const)); + +// CHECK: void bar() __attribute__((__const)); +void bar() __attribute__((__const)); + +// CHECK: int f1() __attribute__((warn_unused_result)); +int f1() __attribute__((warn_unused_result)); + +// CHECK: clang::warn_unused_result]]; +int f2 [[clang::warn_unused_result]] (); + +// CHECK: gnu::warn_unused_result]]; +int f3 [[gnu::warn_unused_result]] (); + +// FIXME: ast-print need to print C++11 +// attribute after function declare-id. +// CHECK: noreturn]]; +void f4 [[noreturn]] (); + +// CHECK: std::noreturn]]; +void f5 [[std::noreturn]] (); + +// CHECK: __attribute__((gnu_inline)); +inline void f6() __attribute__((gnu_inline)); + +// CHECK: gnu::gnu_inline]]; +inline void f7 [[gnu::gnu_inline]] (); + +// arguments printing +// CHECK: __attribute__((format("printf", 2, 3))); +void f8 (void *, const char *, ...) __attribute__ ((format (printf, 2, 3))); diff --git a/utils/TableGen/ClangAttrEmitter.cpp b/utils/TableGen/ClangAttrEmitter.cpp index ef618cea4e..b873636b4a 100644 --- a/utils/TableGen/ClangAttrEmitter.cpp +++ b/utils/TableGen/ClangAttrEmitter.cpp @@ -735,6 +735,82 @@ static void writeAvailabilityValue(raw_ostream &OS) { << " OS << \""; } +static void writePrettyPrintFunction(Record &R, std::vector<Argument*> &Args, + raw_ostream &OS) { + std::vector<Record*> Spellings = R.getValueAsListOfDefs("Spellings"); + + OS << "void " << R.getName() << "Attr::printPretty(" + << "raw_ostream &OS, const PrintingPolicy &Policy) const {\n"; + + if (Spellings.size() == 0) { + OS << "}\n\n"; + return; + } + + OS << + " switch (SpellingListIndex) {\n" + " default:\n" + " llvm_unreachable(\"Unknown attribute spelling!\");\n" + " break;\n"; + + for (unsigned I = 0; I < Spellings.size(); ++ I) { + llvm::SmallString<16> Prefix; + llvm::SmallString<8> Suffix; + // The actual spelling of the name and namespace (if applicable) + // of an attribute without considering prefix and suffix. + llvm::SmallString<64> Spelling; + std::string Name = Spellings[I]->getValueAsString("Name"); + std::string Variety = Spellings[I]->getValueAsString("Variety"); + + if (Variety == "GNU") { + Prefix = " __attribute__(("; + Suffix = "))"; + } else if (Variety == "CXX11") { + Prefix = " [["; + Suffix = "]]"; + std::string Namespace = Spellings[I]->getValueAsString("Namespace"); + if (Namespace != "") { + Spelling += Namespace; + Spelling += "::"; + } + } else if (Variety == "Declspec") { + Prefix = " __declspec("; + Suffix = ")"; + } else { + llvm_unreachable("Unkown attribute syntax variety!"); + } + + Spelling += Name; + + OS << + " case " << I << " : {\n" + " OS << \"" + Prefix.str() + Spelling.str(); + + if (Args.size()) OS << "("; + if (Spelling == "availability") { + writeAvailabilityValue(OS); + } else { + for (std::vector<Argument*>::const_iterator I = Args.begin(), + E = Args.end(); I != E; ++ I) { + if (I != Args.begin()) OS << ", "; + (*I)->writeValue(OS); + } + } + + if (Args.size()) OS << ")"; + OS << Suffix.str() + "\";\n"; + + OS << + " break;\n" + " }\n"; + } + + // End of the switch statement. + OS << "}\n"; + // End of the print function. + OS << "}\n\n"; +} + namespace clang { // Emits the class definitions for attributes. @@ -783,9 +859,12 @@ void EmitClangAttrClass(RecordKeeper &Records, raw_ostream &OS) { (*ai)->writeCtorParameters(OS); OS << "\n"; } - + + OS << " , "; + OS << "unsigned SI = 0\n"; + OS << " )\n"; - OS << " : " << SuperName << "(attr::" << R.getName() << ", R)\n"; + OS << " : " << SuperName << "(attr::" << R.getName() << ", R, SI)\n"; for (ai = Args.begin(); ai != ae; ++ai) { OS << " , "; @@ -841,7 +920,6 @@ void EmitClangAttrImpl(RecordKeeper &Records, raw_ostream &OS) { continue; std::vector<Record*> ArgRecords = R.getValueAsListOfDefs("Args"); - std::vector<Record*> Spellings = R.getValueAsListOfDefs("Spellings"); std::vector<Argument*> Args; for (ri = ArgRecords.begin(), re = ArgRecords.end(); ri != re; ++ri) Args.push_back(createArgument(**ri, R.getName())); @@ -858,24 +936,7 @@ void EmitClangAttrImpl(RecordKeeper &Records, raw_ostream &OS) { } OS << ");\n}\n\n"; - OS << "void " << R.getName() << "Attr::printPretty(" - << "raw_ostream &OS, const PrintingPolicy &Policy) const {\n"; - if (Spellings.begin() != Spellings.end()) { - std::string Spelling = (*Spellings.begin())->getValueAsString("Name"); - OS << " OS << \" __attribute__((" << Spelling; - if (Args.size()) OS << "("; - if (Spelling == "availability") { - writeAvailabilityValue(OS); - } else { - for (ai = Args.begin(); ai != ae; ++ai) { - if (ai!=Args.begin()) OS <<", "; - (*ai)->writeValue(OS); - } - } - if (Args.size()) OS << ")"; - OS << "))\";\n"; - } - OS << "}\n\n"; + writePrettyPrintFunction(R, Args, OS); } } @@ -1044,6 +1105,64 @@ void EmitClangAttrSpellingList(RecordKeeper &Records, raw_ostream &OS) { } +void EmitClangAttrSpellingListIndex(RecordKeeper &Records, raw_ostream &OS) { + OS << "// This file is generated by TableGen. Do not edit it. \n\n"; + + OS << + " unsigned Index = 0;\n" + " switch (AttrKind) {\n" + " default:\n" + " llvm_unreachable(\"Unknown attribute kind!\");\n" + " break;\n"; + + std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr"); + for (std::vector<Record*>::const_iterator I = Attrs.begin(), E = Attrs.end(); + I != E; ++I) { + Record &R = **I; + // We only care about attributes that participate in Sema checking, so + // skip those attributes that are not able to make their way to Sema. + if (!R.getValueAsBit("SemaHandler")) + continue; + + std::vector<Record*> Spellings = R.getValueAsListOfDefs("Spellings"); + // Each distinct spelling yields an attribute kind. + if (R.getValueAsBit("DistinctSpellings")) { + for (unsigned I = 0; I < Spellings.size(); ++ I) { + OS << + " case AT_" << Spellings[I]->getValueAsString("Name") << ": \n" + " Index = " << I << ";\n" + " break;\n"; + } + } else { + OS << " case AT_" << R.getName() << " : {\n"; + for (unsigned I = 0; I < Spellings.size(); ++ I) { + SmallString<16> Namespace; + if (Spellings[I]->getValueAsString("Variety") == "CXX11") + Namespace = Spellings[I]->getValueAsString("Namespace"); + else + Namespace = ""; + + OS << " if (Name == \"" + << Spellings[I]->getValueAsString("Name") << "\" && " + << "SyntaxUsed == " + << StringSwitch<unsigned>(Spellings[I]->getValueAsString("Variety")) + .Case("GNU", 0) + .Case("CXX11", 1) + .Case("Declspec", 2) + .Default(0) + << " && Scope == \"" << Namespace << "\")\n" + << " return " << I << ";\n"; + } + + OS << " break;\n"; + OS << " }\n"; + } + } + + OS << " }\n"; + OS << " return Index;\n"; +} + // Emits the LateParsed property for attributes. void EmitClangAttrLateParsedList(RecordKeeper &Records, raw_ostream &OS) { OS << "// This file is generated by TableGen. Do not edit.\n\n"; diff --git a/utils/TableGen/TableGen.cpp b/utils/TableGen/TableGen.cpp index 7e9076f7b3..8af6598cd0 100644 --- a/utils/TableGen/TableGen.cpp +++ b/utils/TableGen/TableGen.cpp @@ -29,6 +29,7 @@ enum ActionType { GenClangAttrPCHRead, GenClangAttrPCHWrite, GenClangAttrSpellingList, + GenClangAttrSpellingListIndex, GenClangAttrLateParsedList, GenClangAttrTemplateInstantiate, GenClangAttrParsedAttrList, @@ -70,6 +71,9 @@ namespace { clEnumValN(GenClangAttrSpellingList, "gen-clang-attr-spelling-list", "Generate a clang attribute spelling list"), + clEnumValN(GenClangAttrSpellingListIndex, + "gen-clang-attr-spelling-index", + "Generate a clang attribute spelling index"), clEnumValN(GenClangAttrLateParsedList, "gen-clang-attr-late-parsed-list", "Generate a clang attribute LateParsed list"), @@ -144,6 +148,9 @@ bool ClangTableGenMain(raw_ostream &OS, RecordKeeper &Records) { case GenClangAttrSpellingList: EmitClangAttrSpellingList(Records, OS); break; + case GenClangAttrSpellingListIndex: + EmitClangAttrSpellingListIndex(Records, OS); + break; case GenClangAttrLateParsedList: EmitClangAttrLateParsedList(Records, OS); break; diff --git a/utils/TableGen/TableGenBackends.h b/utils/TableGen/TableGenBackends.h index 54e76fdd5e..637e54c01b 100644 --- a/utils/TableGen/TableGenBackends.h +++ b/utils/TableGen/TableGenBackends.h @@ -35,6 +35,7 @@ void EmitClangAttrList(RecordKeeper &Records, raw_ostream &OS); void EmitClangAttrPCHRead(RecordKeeper &Records, raw_ostream &OS); void EmitClangAttrPCHWrite(RecordKeeper &Records, raw_ostream &OS); void EmitClangAttrSpellingList(RecordKeeper &Records, raw_ostream &OS); +void EmitClangAttrSpellingListIndex(RecordKeeper &Records, raw_ostream &OS); void EmitClangAttrLateParsedList(RecordKeeper &Records, raw_ostream &OS); void EmitClangAttrTemplateInstantiate(RecordKeeper &Records, raw_ostream &OS); void EmitClangAttrParsedAttrList(RecordKeeper &Records, raw_ostream &OS); |