xref: /freebsd-src/contrib/llvm-project/clang/include/clang/Basic/AttributeCommonInfo.h (revision a7dea1671b87c07d2d266f836bfa8b58efc7c134)
1*a7dea167SDimitry Andric //======- AttributeCommonInfo.h - Base info about Attributes-----*- C++ -*-===//
2*a7dea167SDimitry Andric //
3*a7dea167SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4*a7dea167SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
5*a7dea167SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6*a7dea167SDimitry Andric //
7*a7dea167SDimitry Andric //===----------------------------------------------------------------------===//
8*a7dea167SDimitry Andric //
9*a7dea167SDimitry Andric // This file defines the AttributeCommonInfo type, which is the base for a
10*a7dea167SDimitry Andric // ParsedAttr and is used by Attr as a way to share info between the two.
11*a7dea167SDimitry Andric //
12*a7dea167SDimitry Andric //===----------------------------------------------------------------------===//
13*a7dea167SDimitry Andric 
14*a7dea167SDimitry Andric #ifndef LLVM_CLANG_BASIC_ATTRIBUTECOMMONINFO_H
15*a7dea167SDimitry Andric #define LLVM_CLANG_BASIC_ATTRIBUTECOMMONINFO_H
16*a7dea167SDimitry Andric #include "clang/Basic/SourceLocation.h"
17*a7dea167SDimitry Andric 
18*a7dea167SDimitry Andric namespace clang {
19*a7dea167SDimitry Andric class IdentifierInfo;
20*a7dea167SDimitry Andric class ASTRecordWriter;
21*a7dea167SDimitry Andric 
22*a7dea167SDimitry Andric class AttributeCommonInfo {
23*a7dea167SDimitry Andric public:
24*a7dea167SDimitry Andric   /// The style used to specify an attribute.
25*a7dea167SDimitry Andric   enum Syntax {
26*a7dea167SDimitry Andric     /// __attribute__((...))
27*a7dea167SDimitry Andric     AS_GNU,
28*a7dea167SDimitry Andric 
29*a7dea167SDimitry Andric     /// [[...]]
30*a7dea167SDimitry Andric     AS_CXX11,
31*a7dea167SDimitry Andric 
32*a7dea167SDimitry Andric     /// [[...]]
33*a7dea167SDimitry Andric     AS_C2x,
34*a7dea167SDimitry Andric 
35*a7dea167SDimitry Andric     /// __declspec(...)
36*a7dea167SDimitry Andric     AS_Declspec,
37*a7dea167SDimitry Andric 
38*a7dea167SDimitry Andric     /// [uuid("...")] class Foo
39*a7dea167SDimitry Andric     AS_Microsoft,
40*a7dea167SDimitry Andric 
41*a7dea167SDimitry Andric     /// __ptr16, alignas(...), etc.
42*a7dea167SDimitry Andric     AS_Keyword,
43*a7dea167SDimitry Andric 
44*a7dea167SDimitry Andric     /// #pragma ...
45*a7dea167SDimitry Andric     AS_Pragma,
46*a7dea167SDimitry Andric 
47*a7dea167SDimitry Andric     // Note TableGen depends on the order above.  Do not add or change the order
48*a7dea167SDimitry Andric     // without adding related code to TableGen/ClangAttrEmitter.cpp.
49*a7dea167SDimitry Andric     /// Context-sensitive version of a keyword attribute.
50*a7dea167SDimitry Andric     AS_ContextSensitiveKeyword,
51*a7dea167SDimitry Andric   };
52*a7dea167SDimitry Andric   enum Kind {
53*a7dea167SDimitry Andric #define PARSED_ATTR(NAME) AT_##NAME,
54*a7dea167SDimitry Andric #include "clang/Sema/AttrParsedAttrList.inc"
55*a7dea167SDimitry Andric #undef PARSED_ATTR
56*a7dea167SDimitry Andric     NoSemaHandlerAttribute,
57*a7dea167SDimitry Andric     IgnoredAttribute,
58*a7dea167SDimitry Andric     UnknownAttribute,
59*a7dea167SDimitry Andric   };
60*a7dea167SDimitry Andric 
61*a7dea167SDimitry Andric private:
62*a7dea167SDimitry Andric   const IdentifierInfo *AttrName = nullptr;
63*a7dea167SDimitry Andric   const IdentifierInfo *ScopeName = nullptr;
64*a7dea167SDimitry Andric   SourceRange AttrRange;
65*a7dea167SDimitry Andric   const SourceLocation ScopeLoc;
66*a7dea167SDimitry Andric   // Corresponds to the Kind enum.
67*a7dea167SDimitry Andric   unsigned AttrKind : 16;
68*a7dea167SDimitry Andric   /// Corresponds to the Syntax enum.
69*a7dea167SDimitry Andric   unsigned SyntaxUsed : 3;
70*a7dea167SDimitry Andric   unsigned SpellingIndex : 4;
71*a7dea167SDimitry Andric 
72*a7dea167SDimitry Andric protected:
73*a7dea167SDimitry Andric   static constexpr unsigned SpellingNotCalculated = 0xf;
74*a7dea167SDimitry Andric 
75*a7dea167SDimitry Andric public:
76*a7dea167SDimitry Andric   AttributeCommonInfo(SourceRange AttrRange)
77*a7dea167SDimitry Andric       : AttrRange(AttrRange), ScopeLoc(), AttrKind(0), SyntaxUsed(0),
78*a7dea167SDimitry Andric         SpellingIndex(SpellingNotCalculated) {}
79*a7dea167SDimitry Andric 
80*a7dea167SDimitry Andric   AttributeCommonInfo(SourceLocation AttrLoc)
81*a7dea167SDimitry Andric       : AttrRange(AttrLoc), ScopeLoc(), AttrKind(0), SyntaxUsed(0),
82*a7dea167SDimitry Andric         SpellingIndex(SpellingNotCalculated) {}
83*a7dea167SDimitry Andric 
84*a7dea167SDimitry Andric   AttributeCommonInfo(const IdentifierInfo *AttrName,
85*a7dea167SDimitry Andric                       const IdentifierInfo *ScopeName, SourceRange AttrRange,
86*a7dea167SDimitry Andric                       SourceLocation ScopeLoc, Syntax SyntaxUsed)
87*a7dea167SDimitry Andric       : AttrName(AttrName), ScopeName(ScopeName), AttrRange(AttrRange),
88*a7dea167SDimitry Andric         ScopeLoc(ScopeLoc),
89*a7dea167SDimitry Andric         AttrKind(getParsedKind(AttrName, ScopeName, SyntaxUsed)),
90*a7dea167SDimitry Andric         SyntaxUsed(SyntaxUsed), SpellingIndex(SpellingNotCalculated) {}
91*a7dea167SDimitry Andric 
92*a7dea167SDimitry Andric   AttributeCommonInfo(const IdentifierInfo *AttrName,
93*a7dea167SDimitry Andric                       const IdentifierInfo *ScopeName, SourceRange AttrRange,
94*a7dea167SDimitry Andric                       SourceLocation ScopeLoc, Kind AttrKind, Syntax SyntaxUsed)
95*a7dea167SDimitry Andric       : AttrName(AttrName), ScopeName(ScopeName), AttrRange(AttrRange),
96*a7dea167SDimitry Andric         ScopeLoc(ScopeLoc), AttrKind(AttrKind), SyntaxUsed(SyntaxUsed),
97*a7dea167SDimitry Andric         SpellingIndex(SpellingNotCalculated) {}
98*a7dea167SDimitry Andric 
99*a7dea167SDimitry Andric   AttributeCommonInfo(const IdentifierInfo *AttrName,
100*a7dea167SDimitry Andric                       const IdentifierInfo *ScopeName, SourceRange AttrRange,
101*a7dea167SDimitry Andric                       SourceLocation ScopeLoc, Kind AttrKind, Syntax SyntaxUsed,
102*a7dea167SDimitry Andric                       unsigned Spelling)
103*a7dea167SDimitry Andric       : AttrName(AttrName), ScopeName(ScopeName), AttrRange(AttrRange),
104*a7dea167SDimitry Andric         ScopeLoc(ScopeLoc), AttrKind(AttrKind), SyntaxUsed(SyntaxUsed),
105*a7dea167SDimitry Andric         SpellingIndex(Spelling) {}
106*a7dea167SDimitry Andric 
107*a7dea167SDimitry Andric   AttributeCommonInfo(const IdentifierInfo *AttrName, SourceRange AttrRange,
108*a7dea167SDimitry Andric                       Syntax SyntaxUsed)
109*a7dea167SDimitry Andric       : AttrName(AttrName), ScopeName(nullptr), AttrRange(AttrRange),
110*a7dea167SDimitry Andric         ScopeLoc(), AttrKind(getParsedKind(AttrName, ScopeName, SyntaxUsed)),
111*a7dea167SDimitry Andric         SyntaxUsed(SyntaxUsed), SpellingIndex(SpellingNotCalculated) {}
112*a7dea167SDimitry Andric 
113*a7dea167SDimitry Andric   AttributeCommonInfo(SourceRange AttrRange, Kind K, Syntax SyntaxUsed)
114*a7dea167SDimitry Andric       : AttrName(nullptr), ScopeName(nullptr), AttrRange(AttrRange), ScopeLoc(),
115*a7dea167SDimitry Andric         AttrKind(K), SyntaxUsed(SyntaxUsed),
116*a7dea167SDimitry Andric         SpellingIndex(SpellingNotCalculated) {}
117*a7dea167SDimitry Andric 
118*a7dea167SDimitry Andric   AttributeCommonInfo(SourceRange AttrRange, Kind K, Syntax SyntaxUsed,
119*a7dea167SDimitry Andric                       unsigned Spelling)
120*a7dea167SDimitry Andric       : AttrName(nullptr), ScopeName(nullptr), AttrRange(AttrRange), ScopeLoc(),
121*a7dea167SDimitry Andric         AttrKind(K), SyntaxUsed(SyntaxUsed), SpellingIndex(Spelling) {}
122*a7dea167SDimitry Andric 
123*a7dea167SDimitry Andric   AttributeCommonInfo(AttributeCommonInfo &&) = default;
124*a7dea167SDimitry Andric   AttributeCommonInfo(const AttributeCommonInfo &) = default;
125*a7dea167SDimitry Andric 
126*a7dea167SDimitry Andric   Kind getParsedKind() const { return Kind(AttrKind); }
127*a7dea167SDimitry Andric   Syntax getSyntax() const { return Syntax(SyntaxUsed); }
128*a7dea167SDimitry Andric   const IdentifierInfo *getAttrName() const { return AttrName; }
129*a7dea167SDimitry Andric   SourceLocation getLoc() const { return AttrRange.getBegin(); }
130*a7dea167SDimitry Andric   SourceRange getRange() const { return AttrRange; }
131*a7dea167SDimitry Andric   void setRange(SourceRange R) { AttrRange = R; }
132*a7dea167SDimitry Andric 
133*a7dea167SDimitry Andric   bool hasScope() const { return ScopeName; }
134*a7dea167SDimitry Andric   const IdentifierInfo *getScopeName() const { return ScopeName; }
135*a7dea167SDimitry Andric   SourceLocation getScopeLoc() const { return ScopeLoc; }
136*a7dea167SDimitry Andric 
137*a7dea167SDimitry Andric   bool isDeclspecAttribute() const { return SyntaxUsed == AS_Declspec; }
138*a7dea167SDimitry Andric   bool isMicrosoftAttribute() const { return SyntaxUsed == AS_Microsoft; }
139*a7dea167SDimitry Andric 
140*a7dea167SDimitry Andric   bool isGNUScope() const;
141*a7dea167SDimitry Andric 
142*a7dea167SDimitry Andric   bool isAlignasAttribute() const {
143*a7dea167SDimitry Andric     // FIXME: Use a better mechanism to determine this.
144*a7dea167SDimitry Andric     return getParsedKind() == AT_Aligned && isKeywordAttribute();
145*a7dea167SDimitry Andric   }
146*a7dea167SDimitry Andric 
147*a7dea167SDimitry Andric   bool isCXX11Attribute() const {
148*a7dea167SDimitry Andric     return SyntaxUsed == AS_CXX11 || isAlignasAttribute();
149*a7dea167SDimitry Andric   }
150*a7dea167SDimitry Andric 
151*a7dea167SDimitry Andric   bool isC2xAttribute() const { return SyntaxUsed == AS_C2x; }
152*a7dea167SDimitry Andric 
153*a7dea167SDimitry Andric   bool isKeywordAttribute() const {
154*a7dea167SDimitry Andric     return SyntaxUsed == AS_Keyword || SyntaxUsed == AS_ContextSensitiveKeyword;
155*a7dea167SDimitry Andric   }
156*a7dea167SDimitry Andric 
157*a7dea167SDimitry Andric   bool isContextSensitiveKeywordAttribute() const {
158*a7dea167SDimitry Andric     return SyntaxUsed == AS_ContextSensitiveKeyword;
159*a7dea167SDimitry Andric   }
160*a7dea167SDimitry Andric 
161*a7dea167SDimitry Andric   unsigned getAttributeSpellingListIndex() const {
162*a7dea167SDimitry Andric     assert((isAttributeSpellingListCalculated() || AttrName) &&
163*a7dea167SDimitry Andric            "Spelling cannot be found");
164*a7dea167SDimitry Andric     return isAttributeSpellingListCalculated()
165*a7dea167SDimitry Andric                ? SpellingIndex
166*a7dea167SDimitry Andric                : calculateAttributeSpellingListIndex();
167*a7dea167SDimitry Andric   }
168*a7dea167SDimitry Andric   void setAttributeSpellingListIndex(unsigned V) { SpellingIndex = V; }
169*a7dea167SDimitry Andric 
170*a7dea167SDimitry Andric   static Kind getParsedKind(const IdentifierInfo *Name,
171*a7dea167SDimitry Andric                             const IdentifierInfo *Scope, Syntax SyntaxUsed);
172*a7dea167SDimitry Andric 
173*a7dea167SDimitry Andric private:
174*a7dea167SDimitry Andric   /// Get an index into the attribute spelling list
175*a7dea167SDimitry Andric   /// defined in Attr.td. This index is used by an attribute
176*a7dea167SDimitry Andric   /// to pretty print itself.
177*a7dea167SDimitry Andric   unsigned calculateAttributeSpellingListIndex() const;
178*a7dea167SDimitry Andric 
179*a7dea167SDimitry Andric   friend class clang::ASTRecordWriter;
180*a7dea167SDimitry Andric   // Used exclusively by ASTDeclWriter to get the raw spelling list state.
181*a7dea167SDimitry Andric   unsigned getAttributeSpellingListIndexRaw() const { return SpellingIndex; }
182*a7dea167SDimitry Andric 
183*a7dea167SDimitry Andric protected:
184*a7dea167SDimitry Andric   bool isAttributeSpellingListCalculated() const {
185*a7dea167SDimitry Andric     return SpellingIndex != SpellingNotCalculated;
186*a7dea167SDimitry Andric   }
187*a7dea167SDimitry Andric };
188*a7dea167SDimitry Andric } // namespace clang
189*a7dea167SDimitry Andric 
190*a7dea167SDimitry Andric #endif // LLVM_CLANG_BASIC_ATTRIBUTECOMMONINFO_H
191