diff options
Diffstat (limited to 'contrib/llvm-project/clang/include/clang/Sema/DeclSpec.h')
-rw-r--r-- | contrib/llvm-project/clang/include/clang/Sema/DeclSpec.h | 166 |
1 files changed, 126 insertions, 40 deletions
diff --git a/contrib/llvm-project/clang/include/clang/Sema/DeclSpec.h b/contrib/llvm-project/clang/include/clang/Sema/DeclSpec.h index 2437be497de4..4561cca929c0 100644 --- a/contrib/llvm-project/clang/include/clang/Sema/DeclSpec.h +++ b/contrib/llvm-project/clang/include/clang/Sema/DeclSpec.h @@ -32,6 +32,7 @@ #include "clang/Lex/Token.h" #include "clang/Sema/Ownership.h" #include "clang/Sema/ParsedAttr.h" +#include "llvm/ADT/STLExtras.h" #include "llvm/ADT/SmallVector.h" #include "llvm/Support/Compiler.h" #include "llvm/Support/ErrorHandling.h" @@ -61,9 +62,18 @@ namespace clang { /// often used as if it meant "present". /// /// The actual scope is described by getScopeRep(). +/// +/// If the kind of getScopeRep() is TypeSpec then TemplateParamLists may be empty +/// or contain the template parameter lists attached to the current declaration. +/// Consider the following example: +/// template <class T> void SomeType<T>::some_method() {} +/// If CXXScopeSpec refers to SomeType<T> then TemplateParamLists will contain +/// a single element referring to template <class T>. + class CXXScopeSpec { SourceRange Range; NestedNameSpecifierLocBuilder Builder; + ArrayRef<TemplateParameterList *> TemplateParamLists; public: SourceRange getRange() const { return Range; } @@ -73,6 +83,13 @@ public: SourceLocation getBeginLoc() const { return Range.getBegin(); } SourceLocation getEndLoc() const { return Range.getEnd(); } + void setTemplateParamLists(ArrayRef<TemplateParameterList *> L) { + TemplateParamLists = L; + } + ArrayRef<TemplateParameterList *> getTemplateParamLists() const { + return TemplateParamLists; + } + /// Retrieve the representation of the nested-name-specifier. NestedNameSpecifier *getScopeRep() const { return Builder.getRepresentation(); @@ -288,9 +305,13 @@ public: static const TST TST_typename = clang::TST_typename; static const TST TST_typeofType = clang::TST_typeofType; static const TST TST_typeofExpr = clang::TST_typeofExpr; + static const TST TST_typeof_unqualType = clang::TST_typeof_unqualType; + static const TST TST_typeof_unqualExpr = clang::TST_typeof_unqualExpr; static const TST TST_decltype = clang::TST_decltype; static const TST TST_decltype_auto = clang::TST_decltype_auto; - static const TST TST_underlyingType = clang::TST_underlyingType; +#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) \ + static const TST TST_##Trait = clang::TST_##Trait; +#include "clang/Basic/TransformTypeTraits.def" static const TST TST_auto = clang::TST_auto; static const TST TST_auto_type = clang::TST_auto_type; static const TST TST_unknown_anytype = clang::TST_unknown_anytype; @@ -323,6 +344,11 @@ public: // FIXME: Attributes should be included here. }; + enum FriendSpecified : bool { + No, + Yes, + }; + private: // storage-class-specifier /*SCS*/unsigned StorageClassSpec : 3; @@ -333,7 +359,7 @@ private: /*TypeSpecifierWidth*/ unsigned TypeSpecWidth : 2; /*TSC*/unsigned TypeSpecComplex : 2; /*TSS*/unsigned TypeSpecSign : 2; - /*TST*/unsigned TypeSpecType : 6; + /*TST*/unsigned TypeSpecType : 7; unsigned TypeAltiVecVector : 1; unsigned TypeAltiVecPixel : 1; unsigned TypeAltiVecBool : 1; @@ -400,11 +426,12 @@ private: ObjCDeclSpec *ObjCQualifiers; static bool isTypeRep(TST T) { - return (T == TST_typename || T == TST_typeofType || - T == TST_underlyingType || T == TST_atomic); + return T == TST_atomic || T == TST_typename || T == TST_typeofType || + T == TST_typeof_unqualType || isTransformTypeTrait(T); } static bool isExprRep(TST T) { - return (T == TST_typeofExpr || T == TST_decltype || T == TST_bitint); + return T == TST_typeofExpr || T == TST_typeof_unqualExpr || + T == TST_decltype || T == TST_bitint; } static bool isTemplateIdRep(TST T) { return (T == TST_auto || T == TST_decltype_auto); @@ -418,6 +445,14 @@ public: T == TST_interface || T == TST_union || T == TST_class); } + static bool isTransformTypeTrait(TST T) { + constexpr std::array<TST, 16> Traits = { +#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) TST_##Trait, +#include "clang/Basic/TransformTypeTraits.def" + }; + + return T >= Traits.front() && T <= Traits.back(); + } DeclSpec(AttributeFactory &attrFactory) : StorageClassSpec(SCS_unspecified), @@ -516,12 +551,13 @@ public: SourceLocation getTypeSpecSatLoc() const { return TSSatLoc; } SourceLocation getTypeSpecTypeNameLoc() const { - assert(isDeclRep((TST) TypeSpecType) || TypeSpecType == TST_typename); + assert(isDeclRep((TST)TypeSpecType) || isTypeRep((TST)TypeSpecType) || + isExprRep((TST)TypeSpecType)); return TSTNameLoc; } SourceRange getTypeofParensRange() const { return TypeofParensRange; } - void setTypeofParensRange(SourceRange range) { TypeofParensRange = range; } + void setTypeArgumentRange(SourceRange range) { TypeofParensRange = range; } bool hasAutoTypeSpec() const { return (TypeSpecType == TST_auto || TypeSpecType == TST_auto_type || @@ -745,7 +781,10 @@ public: bool SetConstexprSpec(ConstexprSpecKind ConstexprKind, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID); - bool isFriendSpecified() const { return Friend_specified; } + FriendSpecified isFriendSpecified() const { + return static_cast<FriendSpecified>(Friend_specified); + } + SourceLocation getFriendSpecLoc() const { return FriendLoc; } bool isModulePrivateSpecified() const { return ModulePrivateLoc.isValid(); } @@ -786,7 +825,7 @@ public: /// int __attribute__((may_alias)) __attribute__((aligned(16))) var; /// \endcode /// - void addAttributes(ParsedAttributesView &AL) { + void addAttributes(const ParsedAttributesView &AL) { Attrs.addAll(AL.begin(), AL.end()); } @@ -952,10 +991,10 @@ private: UnqualifiedId(const UnqualifiedId &Other) = delete; const UnqualifiedId &operator=(const UnqualifiedId &) = delete; -public: /// Describes the kind of unqualified-id parsed. UnqualifiedIdKind Kind; +public: struct OFI { /// The kind of overloaded operator. OverloadedOperatorKind Operator; @@ -1342,7 +1381,7 @@ struct DeclaratorChunk { /// DeclSpec for the function with the qualifier related info. DeclSpec *MethodQualifiers; - /// AtttibuteFactory for the MethodQualifiers. + /// AttributeFactory for the MethodQualifiers. AttributeFactory *QualAttrFactory; union { @@ -1490,7 +1529,7 @@ struct DeclaratorChunk { /// prototype. Typically these are tag declarations. ArrayRef<NamedDecl *> getDeclsInPrototype() const { assert(ExceptionSpecType == EST_None); - return llvm::makeArrayRef(DeclsInPrototype, NumExceptionsOrDecls); + return llvm::ArrayRef(DeclsInPrototype, NumExceptionsOrDecls); } /// Determine whether this function declarator had a @@ -1737,7 +1776,7 @@ public: } ArrayRef<Binding> bindings() const { - return llvm::makeArrayRef(Bindings, NumBindings); + return llvm::ArrayRef(Bindings, NumBindings); } bool isSet() const { return LSquareLoc.isValid(); } @@ -1785,7 +1824,15 @@ enum class DeclaratorContext { TemplateTypeArg, // Template type argument (in default argument). AliasDecl, // C++11 alias-declaration. AliasTemplate, // C++11 alias-declaration template. - RequiresExpr // C++2a requires-expression. + RequiresExpr, // C++2a requires-expression. + Association // C11 _Generic selection expression association. +}; + +// Describes whether the current context is a context where an implicit +// typename is allowed (C++2a [temp.res]p5]). +enum class ImplicitTypenameContext { + No, + Yes, }; /// Information about one declarator, including the parsed type @@ -1850,9 +1897,13 @@ private: /// Indicates whether this declarator has an initializer. unsigned HasInitializer : 1; - /// Attrs - Attributes. + /// Attributes attached to the declarator. ParsedAttributes Attrs; + /// Attributes attached to the declaration. See also documentation for the + /// corresponding constructor parameter. + const ParsedAttributesView &DeclarationAttrs; + /// The asm label, if specified. Expr *AsmLabel; @@ -1891,16 +1942,41 @@ private: friend struct DeclaratorChunk; public: - Declarator(const DeclSpec &ds, DeclaratorContext C) - : DS(ds), Range(ds.getSourceRange()), Context(C), + /// `DS` and `DeclarationAttrs` must outlive the `Declarator`. In particular, + /// take care not to pass temporary objects for these parameters. + /// + /// `DeclarationAttrs` contains [[]] attributes from the + /// attribute-specifier-seq at the beginning of a declaration, which appertain + /// to the declared entity itself. Attributes with other syntax (e.g. GNU) + /// should not be placed in this attribute list; if they occur at the + /// beginning of a declaration, they apply to the `DeclSpec` and should be + /// attached to that instead. + /// + /// Here is an example of an attribute associated with a declaration: + /// + /// [[deprecated]] int x, y; + /// + /// This attribute appertains to all of the entities declared in the + /// declaration, i.e. `x` and `y` in this case. + Declarator(const DeclSpec &DS, const ParsedAttributesView &DeclarationAttrs, + DeclaratorContext C) + : DS(DS), Range(DS.getSourceRange()), Context(C), InvalidType(DS.getTypeSpecType() == DeclSpec::TST_error), GroupingParens(false), FunctionDefinition(static_cast<unsigned>( FunctionDefinitionKind::Declaration)), Redeclaration(false), Extension(false), ObjCIvar(false), ObjCWeakProperty(false), InlineStorageUsed(false), - HasInitializer(false), Attrs(ds.getAttributePool().getFactory()), - AsmLabel(nullptr), TrailingRequiresClause(nullptr), - InventedTemplateParameterList(nullptr) {} + HasInitializer(false), Attrs(DS.getAttributePool().getFactory()), + DeclarationAttrs(DeclarationAttrs), AsmLabel(nullptr), + TrailingRequiresClause(nullptr), + InventedTemplateParameterList(nullptr) { + assert(llvm::all_of(DeclarationAttrs, + [](const ParsedAttr &AL) { + return (AL.isStandardAttributeSyntax() || + AL.isRegularKeywordAttribute()); + }) && + "DeclarationAttrs may only contain [[]] and keyword attributes"); + } ~Declarator() { clear(); @@ -2023,6 +2099,7 @@ public: case DeclaratorContext::TrailingReturn: case DeclaratorContext::TrailingReturnVar: case DeclaratorContext::RequiresExpr: + case DeclaratorContext::Association: return true; } llvm_unreachable("unknown context kind!"); @@ -2062,6 +2139,7 @@ public: case DeclaratorContext::TemplateTypeArg: case DeclaratorContext::TrailingReturn: case DeclaratorContext::TrailingReturnVar: + case DeclaratorContext::Association: return false; } llvm_unreachable("unknown context kind!"); @@ -2105,6 +2183,7 @@ public: case DeclaratorContext::TemplateTypeArg: case DeclaratorContext::TrailingReturn: case DeclaratorContext::TrailingReturnVar: + case DeclaratorContext::Association: return false; } llvm_unreachable("unknown context kind!"); @@ -2161,6 +2240,7 @@ public: case DeclaratorContext::TemplateTypeArg: case DeclaratorContext::TrailingReturn: case DeclaratorContext::RequiresExpr: + case DeclaratorContext::Association: return false; } llvm_unreachable("unknown context kind!"); @@ -2383,6 +2463,7 @@ public: case DeclaratorContext::TrailingReturn: case DeclaratorContext::TrailingReturnVar: case DeclaratorContext::RequiresExpr: + case DeclaratorContext::Association: return false; } llvm_unreachable("unknown context kind!"); @@ -2417,6 +2498,7 @@ public: case DeclaratorContext::TrailingReturnVar: case DeclaratorContext::TemplateTypeArg: case DeclaratorContext::RequiresExpr: + case DeclaratorContext::Association: return false; case DeclaratorContext::Block: @@ -2513,19 +2595,24 @@ public: /// __attribute__((common,deprecated)); /// /// Also extends the range of the declarator. - void takeAttributes(ParsedAttributes &attrs, SourceLocation lastLoc) { + void takeAttributes(ParsedAttributes &attrs) { Attrs.takeAllFrom(attrs); - if (!lastLoc.isInvalid()) - SetRangeEnd(lastLoc); + if (attrs.Range.getEnd().isValid()) + SetRangeEnd(attrs.Range.getEnd()); } const ParsedAttributes &getAttributes() const { return Attrs; } ParsedAttributes &getAttributes() { return Attrs; } + const ParsedAttributesView &getDeclarationAttributes() const { + return DeclarationAttrs; + } + /// hasAttributes - do we contain any attributes? bool hasAttributes() const { - if (!getAttributes().empty() || getDeclSpec().hasAttributes()) + if (!getAttributes().empty() || !getDeclarationAttributes().empty() || + getDeclSpec().hasAttributes()) return true; for (unsigned i = 0, e = getNumTypeObjects(); i != e; ++i) if (!getTypeObject(i).getAttrs().empty()) @@ -2533,14 +2620,6 @@ public: return false; } - /// Return a source range list of C++11 attributes associated - /// with the declarator. - void getCXX11AttributeRanges(SmallVectorImpl<SourceRange> &Ranges) { - for (const ParsedAttr &AL : Attrs) - if (AL.isCXX11Attribute()) - Ranges.push_back(AL.getRange()); - } - void setAsmLabel(Expr *E) { AsmLabel = E; } Expr *getAsmLabel() const { return AsmLabel; } @@ -2595,6 +2674,8 @@ public: /// redeclaration time if the decl is static. bool isStaticMember(); + bool isExplicitObjectMemberFunction(); + /// Returns true if this declares a constructor or a destructor. bool isCtorOrDtor(); @@ -2607,8 +2688,10 @@ public: struct FieldDeclarator { Declarator D; Expr *BitfieldSize; - explicit FieldDeclarator(const DeclSpec &DS) - : D(DS, DeclaratorContext::Member), BitfieldSize(nullptr) {} + explicit FieldDeclarator(const DeclSpec &DS, + const ParsedAttributes &DeclarationAttrs) + : D(DS, DeclarationAttrs, DeclaratorContext::Member), + BitfieldSize(nullptr) {} }; /// Represents a C++11 virt-specifier-seq. @@ -2624,7 +2707,7 @@ public: VS_Abstract = 16 }; - VirtSpecifiers() : Specifiers(0), LastSpecifier(VS_None) { } + VirtSpecifiers() = default; bool SetSpecifier(Specifier VS, SourceLocation Loc, const char *&PrevSpec); @@ -2648,8 +2731,8 @@ public: Specifier getLastSpecifier() const { return LastSpecifier; } private: - unsigned Specifiers; - Specifier LastSpecifier; + unsigned Specifiers = 0; + Specifier LastSpecifier = VS_None; SourceLocation VS_overrideLoc, VS_finalLoc, VS_abstractLoc; SourceLocation FirstLocation; @@ -2688,11 +2771,14 @@ struct LambdaIntroducer { SourceRange Range; SourceLocation DefaultLoc; - LambdaCaptureDefault Default; + LambdaCaptureDefault Default = LCD_None; SmallVector<LambdaCapture, 4> Captures; - LambdaIntroducer() - : Default(LCD_None) {} + LambdaIntroducer() = default; + + bool hasLambdaCapture() const { + return Captures.size() > 0 || Default != LCD_None; + } /// Append a capture in a lambda introducer. void addCapture(LambdaCaptureKind Kind, |