1 //======- ParsedAttr.h - Parsed attribute sets ------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file defines the ParsedAttr class, which is used to collect
10 // parsed attributes.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #ifndef LLVM_CLANG_SEMA_PARSEDATTR_H
15 #define LLVM_CLANG_SEMA_PARSEDATTR_H
16 
17 #include "clang/Basic/AttrSubjectMatchRules.h"
18 #include "clang/Basic/AttributeCommonInfo.h"
19 #include "clang/Basic/Diagnostic.h"
20 #include "clang/Basic/ParsedAttrInfo.h"
21 #include "clang/Basic/SourceLocation.h"
22 #include "clang/Sema/Ownership.h"
23 #include "llvm/ADT/PointerUnion.h"
24 #include "llvm/ADT/SmallVector.h"
25 #include "llvm/Support/Allocator.h"
26 #include "llvm/Support/VersionTuple.h"
27 #include <bitset>
28 #include <cassert>
29 #include <cstddef>
30 #include <cstring>
31 #include <utility>
32 
33 namespace clang {
34 
35 class ASTContext;
36 class Decl;
37 class Expr;
38 class IdentifierInfo;
39 class LangOptions;
40 class Sema;
41 class Stmt;
42 class TargetInfo;
43 
44 /// Represents information about a change in availability for
45 /// an entity, which is part of the encoding of the 'availability'
46 /// attribute.
47 struct AvailabilityChange {
48   /// The location of the keyword indicating the kind of change.
49   SourceLocation KeywordLoc;
50 
51   /// The version number at which the change occurred.
52   VersionTuple Version;
53 
54   /// The source range covering the version number.
55   SourceRange VersionRange;
56 
57   /// Determine whether this availability change is valid.
58   bool isValid() const { return !Version.empty(); }
59 };
60 
61 namespace detail {
62 enum AvailabilitySlot {
63   IntroducedSlot, DeprecatedSlot, ObsoletedSlot, NumAvailabilitySlots
64 };
65 
66 /// Describes the trailing object for Availability attribute in ParsedAttr.
67 struct AvailabilityData {
68   AvailabilityChange Changes[NumAvailabilitySlots];
69   SourceLocation StrictLoc;
70   const Expr *Replacement;
71 
72   AvailabilityData(const AvailabilityChange &Introduced,
73                    const AvailabilityChange &Deprecated,
74                    const AvailabilityChange &Obsoleted,
75                    SourceLocation Strict, const Expr *ReplaceExpr)
76     : StrictLoc(Strict), Replacement(ReplaceExpr) {
77     Changes[IntroducedSlot] = Introduced;
78     Changes[DeprecatedSlot] = Deprecated;
79     Changes[ObsoletedSlot] = Obsoleted;
80   }
81 };
82 
83 struct TypeTagForDatatypeData {
84   ParsedType MatchingCType;
85   unsigned LayoutCompatible : 1;
86   unsigned MustBeNull : 1;
87 };
88 struct PropertyData {
89   IdentifierInfo *GetterId, *SetterId;
90 
91   PropertyData(IdentifierInfo *getterId, IdentifierInfo *setterId)
92       : GetterId(getterId), SetterId(setterId) {}
93 };
94 
95 } // namespace
96 
97 /// Wraps an identifier and optional source location for the identifier.
98 struct IdentifierLoc {
99   SourceLocation Loc;
100   IdentifierInfo *Ident;
101 
102   static IdentifierLoc *create(ASTContext &Ctx, SourceLocation Loc,
103                                IdentifierInfo *Ident);
104 };
105 
106 /// A union of the various pointer types that can be passed to an
107 /// ParsedAttr as an argument.
108 using ArgsUnion = llvm::PointerUnion<Expr *, IdentifierLoc *>;
109 using ArgsVector = llvm::SmallVector<ArgsUnion, 12U>;
110 
111 /// ParsedAttr - Represents a syntactic attribute.
112 ///
113 /// For a GNU attribute, there are four forms of this construct:
114 ///
115 /// 1: __attribute__(( const )). ParmName/Args/NumArgs will all be unused.
116 /// 2: __attribute__(( mode(byte) )). ParmName used, Args/NumArgs unused.
117 /// 3: __attribute__(( format(printf, 1, 2) )). ParmName/Args/NumArgs all used.
118 /// 4: __attribute__(( aligned(16) )). ParmName is unused, Args/Num used.
119 ///
120 class ParsedAttr final
121     : public AttributeCommonInfo,
122       private llvm::TrailingObjects<
123           ParsedAttr, ArgsUnion, detail::AvailabilityData,
124           detail::TypeTagForDatatypeData, ParsedType, detail::PropertyData> {
125   friend TrailingObjects;
126 
127   size_t numTrailingObjects(OverloadToken<ArgsUnion>) const { return NumArgs; }
128   size_t numTrailingObjects(OverloadToken<detail::AvailabilityData>) const {
129     return IsAvailability;
130   }
131   size_t
132       numTrailingObjects(OverloadToken<detail::TypeTagForDatatypeData>) const {
133     return IsTypeTagForDatatype;
134   }
135   size_t numTrailingObjects(OverloadToken<ParsedType>) const {
136     return HasParsedType;
137   }
138   size_t numTrailingObjects(OverloadToken<detail::PropertyData>) const {
139     return IsProperty;
140   }
141 
142 private:
143   IdentifierInfo *MacroII = nullptr;
144   SourceLocation MacroExpansionLoc;
145   SourceLocation EllipsisLoc;
146 
147   /// The number of expression arguments this attribute has.
148   /// The expressions themselves are stored after the object.
149   unsigned NumArgs : 16;
150 
151   /// True if already diagnosed as invalid.
152   mutable unsigned Invalid : 1;
153 
154   /// True if this attribute was used as a type attribute.
155   mutable unsigned UsedAsTypeAttr : 1;
156 
157   /// True if this has the extra information associated with an
158   /// availability attribute.
159   unsigned IsAvailability : 1;
160 
161   /// True if this has extra information associated with a
162   /// type_tag_for_datatype attribute.
163   unsigned IsTypeTagForDatatype : 1;
164 
165   /// True if this has extra information associated with a
166   /// Microsoft __delcspec(property) attribute.
167   unsigned IsProperty : 1;
168 
169   /// True if this has a ParsedType
170   unsigned HasParsedType : 1;
171 
172   /// True if the processing cache is valid.
173   mutable unsigned HasProcessingCache : 1;
174 
175   /// A cached value.
176   mutable unsigned ProcessingCache : 8;
177 
178   /// True if the attribute is specified using '#pragma clang attribute'.
179   mutable unsigned IsPragmaClangAttribute : 1;
180 
181   /// The location of the 'unavailable' keyword in an
182   /// availability attribute.
183   SourceLocation UnavailableLoc;
184 
185   const Expr *MessageExpr;
186 
187   const ParsedAttrInfo &Info;
188 
189   ArgsUnion *getArgsBuffer() { return getTrailingObjects<ArgsUnion>(); }
190   ArgsUnion const *getArgsBuffer() const {
191     return getTrailingObjects<ArgsUnion>();
192   }
193 
194   detail::AvailabilityData *getAvailabilityData() {
195     return getTrailingObjects<detail::AvailabilityData>();
196   }
197   const detail::AvailabilityData *getAvailabilityData() const {
198     return getTrailingObjects<detail::AvailabilityData>();
199   }
200 
201 private:
202   friend class AttributeFactory;
203   friend class AttributePool;
204 
205   /// Constructor for attributes with expression arguments.
206   ParsedAttr(IdentifierInfo *attrName, SourceRange attrRange,
207              IdentifierInfo *scopeName, SourceLocation scopeLoc,
208              ArgsUnion *args, unsigned numArgs, Form formUsed,
209              SourceLocation ellipsisLoc)
210       : AttributeCommonInfo(attrName, scopeName, attrRange, scopeLoc, formUsed),
211         EllipsisLoc(ellipsisLoc), NumArgs(numArgs), Invalid(false),
212         UsedAsTypeAttr(false), IsAvailability(false),
213         IsTypeTagForDatatype(false), IsProperty(false), HasParsedType(false),
214         HasProcessingCache(false), IsPragmaClangAttribute(false),
215         Info(ParsedAttrInfo::get(*this)) {
216     if (numArgs)
217       memcpy(getArgsBuffer(), args, numArgs * sizeof(ArgsUnion));
218   }
219 
220   /// Constructor for availability attributes.
221   ParsedAttr(IdentifierInfo *attrName, SourceRange attrRange,
222              IdentifierInfo *scopeName, SourceLocation scopeLoc,
223              IdentifierLoc *Parm, const AvailabilityChange &introduced,
224              const AvailabilityChange &deprecated,
225              const AvailabilityChange &obsoleted, SourceLocation unavailable,
226              const Expr *messageExpr, Form formUsed, SourceLocation strict,
227              const Expr *replacementExpr)
228       : AttributeCommonInfo(attrName, scopeName, attrRange, scopeLoc, formUsed),
229         NumArgs(1), Invalid(false), UsedAsTypeAttr(false), IsAvailability(true),
230         IsTypeTagForDatatype(false), IsProperty(false), HasParsedType(false),
231         HasProcessingCache(false), IsPragmaClangAttribute(false),
232         UnavailableLoc(unavailable), MessageExpr(messageExpr),
233         Info(ParsedAttrInfo::get(*this)) {
234     ArgsUnion PVal(Parm);
235     memcpy(getArgsBuffer(), &PVal, sizeof(ArgsUnion));
236     new (getAvailabilityData()) detail::AvailabilityData(
237         introduced, deprecated, obsoleted, strict, replacementExpr);
238   }
239 
240   /// Constructor for objc_bridge_related attributes.
241   ParsedAttr(IdentifierInfo *attrName, SourceRange attrRange,
242              IdentifierInfo *scopeName, SourceLocation scopeLoc,
243              IdentifierLoc *Parm1, IdentifierLoc *Parm2, IdentifierLoc *Parm3,
244              Form formUsed)
245       : AttributeCommonInfo(attrName, scopeName, attrRange, scopeLoc, formUsed),
246         NumArgs(3), Invalid(false), UsedAsTypeAttr(false),
247         IsAvailability(false), IsTypeTagForDatatype(false), IsProperty(false),
248         HasParsedType(false), HasProcessingCache(false),
249         IsPragmaClangAttribute(false), Info(ParsedAttrInfo::get(*this)) {
250     ArgsUnion *Args = getArgsBuffer();
251     Args[0] = Parm1;
252     Args[1] = Parm2;
253     Args[2] = Parm3;
254   }
255 
256   /// Constructor for type_tag_for_datatype attribute.
257   ParsedAttr(IdentifierInfo *attrName, SourceRange attrRange,
258              IdentifierInfo *scopeName, SourceLocation scopeLoc,
259              IdentifierLoc *ArgKind, ParsedType matchingCType,
260              bool layoutCompatible, bool mustBeNull, Form formUsed)
261       : AttributeCommonInfo(attrName, scopeName, attrRange, scopeLoc, formUsed),
262         NumArgs(1), Invalid(false), UsedAsTypeAttr(false),
263         IsAvailability(false), IsTypeTagForDatatype(true), IsProperty(false),
264         HasParsedType(false), HasProcessingCache(false),
265         IsPragmaClangAttribute(false), Info(ParsedAttrInfo::get(*this)) {
266     ArgsUnion PVal(ArgKind);
267     memcpy(getArgsBuffer(), &PVal, sizeof(ArgsUnion));
268     detail::TypeTagForDatatypeData &ExtraData = getTypeTagForDatatypeDataSlot();
269     new (&ExtraData.MatchingCType) ParsedType(matchingCType);
270     ExtraData.LayoutCompatible = layoutCompatible;
271     ExtraData.MustBeNull = mustBeNull;
272   }
273 
274   /// Constructor for attributes with a single type argument.
275   ParsedAttr(IdentifierInfo *attrName, SourceRange attrRange,
276              IdentifierInfo *scopeName, SourceLocation scopeLoc,
277              ParsedType typeArg, Form formUsed, SourceLocation ellipsisLoc)
278       : AttributeCommonInfo(attrName, scopeName, attrRange, scopeLoc, formUsed),
279         EllipsisLoc(ellipsisLoc), NumArgs(0), Invalid(false),
280         UsedAsTypeAttr(false), IsAvailability(false),
281         IsTypeTagForDatatype(false), IsProperty(false), HasParsedType(true),
282         HasProcessingCache(false), IsPragmaClangAttribute(false),
283         Info(ParsedAttrInfo::get(*this)) {
284     new (&getTypeBuffer()) ParsedType(typeArg);
285   }
286 
287   /// Constructor for microsoft __declspec(property) attribute.
288   ParsedAttr(IdentifierInfo *attrName, SourceRange attrRange,
289              IdentifierInfo *scopeName, SourceLocation scopeLoc,
290              IdentifierInfo *getterId, IdentifierInfo *setterId, Form formUsed)
291       : AttributeCommonInfo(attrName, scopeName, attrRange, scopeLoc, formUsed),
292         NumArgs(0), Invalid(false), UsedAsTypeAttr(false),
293         IsAvailability(false), IsTypeTagForDatatype(false), IsProperty(true),
294         HasParsedType(false), HasProcessingCache(false),
295         IsPragmaClangAttribute(false), Info(ParsedAttrInfo::get(*this)) {
296     new (&getPropertyDataBuffer()) detail::PropertyData(getterId, setterId);
297   }
298 
299   /// Type tag information is stored immediately following the arguments, if
300   /// any, at the end of the object.  They are mutually exclusive with
301   /// availability slots.
302   detail::TypeTagForDatatypeData &getTypeTagForDatatypeDataSlot() {
303     return *getTrailingObjects<detail::TypeTagForDatatypeData>();
304   }
305   const detail::TypeTagForDatatypeData &getTypeTagForDatatypeDataSlot() const {
306     return *getTrailingObjects<detail::TypeTagForDatatypeData>();
307   }
308 
309   /// The type buffer immediately follows the object and are mutually exclusive
310   /// with arguments.
311   ParsedType &getTypeBuffer() { return *getTrailingObjects<ParsedType>(); }
312   const ParsedType &getTypeBuffer() const {
313     return *getTrailingObjects<ParsedType>();
314   }
315 
316   /// The property data immediately follows the object is mutually exclusive
317   /// with arguments.
318   detail::PropertyData &getPropertyDataBuffer() {
319     assert(IsProperty);
320     return *getTrailingObjects<detail::PropertyData>();
321   }
322   const detail::PropertyData &getPropertyDataBuffer() const {
323     assert(IsProperty);
324     return *getTrailingObjects<detail::PropertyData>();
325   }
326 
327   size_t allocated_size() const;
328 
329 public:
330   ParsedAttr(const ParsedAttr &) = delete;
331   ParsedAttr(ParsedAttr &&) = delete;
332   ParsedAttr &operator=(const ParsedAttr &) = delete;
333   ParsedAttr &operator=(ParsedAttr &&) = delete;
334   ~ParsedAttr() = delete;
335 
336   void operator delete(void *) = delete;
337 
338   bool hasParsedType() const { return HasParsedType; }
339 
340   /// Is this the Microsoft __declspec(property) attribute?
341   bool isDeclspecPropertyAttribute() const  {
342     return IsProperty;
343   }
344 
345   bool isInvalid() const { return Invalid; }
346   void setInvalid(bool b = true) const { Invalid = b; }
347 
348   bool hasProcessingCache() const { return HasProcessingCache; }
349 
350   unsigned getProcessingCache() const {
351     assert(hasProcessingCache());
352     return ProcessingCache;
353   }
354 
355   void setProcessingCache(unsigned value) const {
356     ProcessingCache = value;
357     HasProcessingCache = true;
358   }
359 
360   bool isUsedAsTypeAttr() const { return UsedAsTypeAttr; }
361   void setUsedAsTypeAttr(bool Used = true) { UsedAsTypeAttr = Used; }
362 
363   /// True if the attribute is specified using '#pragma clang attribute'.
364   bool isPragmaClangAttribute() const { return IsPragmaClangAttribute; }
365 
366   void setIsPragmaClangAttribute() { IsPragmaClangAttribute = true; }
367 
368   bool isPackExpansion() const { return EllipsisLoc.isValid(); }
369   SourceLocation getEllipsisLoc() const { return EllipsisLoc; }
370 
371   /// getNumArgs - Return the number of actual arguments to this attribute.
372   unsigned getNumArgs() const { return NumArgs; }
373 
374   /// getArg - Return the specified argument.
375   ArgsUnion getArg(unsigned Arg) const {
376     assert(Arg < NumArgs && "Arg access out of range!");
377     return getArgsBuffer()[Arg];
378   }
379 
380   bool isArgExpr(unsigned Arg) const {
381     return Arg < NumArgs && getArg(Arg).is<Expr*>();
382   }
383 
384   Expr *getArgAsExpr(unsigned Arg) const {
385     return getArg(Arg).get<Expr*>();
386   }
387 
388   bool isArgIdent(unsigned Arg) const {
389     return Arg < NumArgs && getArg(Arg).is<IdentifierLoc*>();
390   }
391 
392   IdentifierLoc *getArgAsIdent(unsigned Arg) const {
393     return getArg(Arg).get<IdentifierLoc*>();
394   }
395 
396   const AvailabilityChange &getAvailabilityIntroduced() const {
397     assert(getParsedKind() == AT_Availability &&
398            "Not an availability attribute");
399     return getAvailabilityData()->Changes[detail::IntroducedSlot];
400   }
401 
402   const AvailabilityChange &getAvailabilityDeprecated() const {
403     assert(getParsedKind() == AT_Availability &&
404            "Not an availability attribute");
405     return getAvailabilityData()->Changes[detail::DeprecatedSlot];
406   }
407 
408   const AvailabilityChange &getAvailabilityObsoleted() const {
409     assert(getParsedKind() == AT_Availability &&
410            "Not an availability attribute");
411     return getAvailabilityData()->Changes[detail::ObsoletedSlot];
412   }
413 
414   SourceLocation getStrictLoc() const {
415     assert(getParsedKind() == AT_Availability &&
416            "Not an availability attribute");
417     return getAvailabilityData()->StrictLoc;
418   }
419 
420   SourceLocation getUnavailableLoc() const {
421     assert(getParsedKind() == AT_Availability &&
422            "Not an availability attribute");
423     return UnavailableLoc;
424   }
425 
426   const Expr * getMessageExpr() const {
427     assert(getParsedKind() == AT_Availability &&
428            "Not an availability attribute");
429     return MessageExpr;
430   }
431 
432   const Expr *getReplacementExpr() const {
433     assert(getParsedKind() == AT_Availability &&
434            "Not an availability attribute");
435     return getAvailabilityData()->Replacement;
436   }
437 
438   const ParsedType &getMatchingCType() const {
439     assert(getParsedKind() == AT_TypeTagForDatatype &&
440            "Not a type_tag_for_datatype attribute");
441     return getTypeTagForDatatypeDataSlot().MatchingCType;
442   }
443 
444   bool getLayoutCompatible() const {
445     assert(getParsedKind() == AT_TypeTagForDatatype &&
446            "Not a type_tag_for_datatype attribute");
447     return getTypeTagForDatatypeDataSlot().LayoutCompatible;
448   }
449 
450   bool getMustBeNull() const {
451     assert(getParsedKind() == AT_TypeTagForDatatype &&
452            "Not a type_tag_for_datatype attribute");
453     return getTypeTagForDatatypeDataSlot().MustBeNull;
454   }
455 
456   const ParsedType &getTypeArg() const {
457     assert(HasParsedType && "Not a type attribute");
458     return getTypeBuffer();
459   }
460 
461   IdentifierInfo *getPropertyDataGetter() const {
462     assert(isDeclspecPropertyAttribute() &&
463            "Not a __delcspec(property) attribute");
464     return getPropertyDataBuffer().GetterId;
465   }
466 
467   IdentifierInfo *getPropertyDataSetter() const {
468     assert(isDeclspecPropertyAttribute() &&
469            "Not a __delcspec(property) attribute");
470     return getPropertyDataBuffer().SetterId;
471   }
472 
473   /// Set the macro identifier info object that this parsed attribute was
474   /// declared in if it was declared in a macro. Also set the expansion location
475   /// of the macro.
476   void setMacroIdentifier(IdentifierInfo *MacroName, SourceLocation Loc) {
477     MacroII = MacroName;
478     MacroExpansionLoc = Loc;
479   }
480 
481   /// Returns true if this attribute was declared in a macro.
482   bool hasMacroIdentifier() const { return MacroII != nullptr; }
483 
484   /// Return the macro identifier if this attribute was declared in a macro.
485   /// nullptr is returned if it was not declared in a macro.
486   IdentifierInfo *getMacroIdentifier() const { return MacroII; }
487 
488   SourceLocation getMacroExpansionLoc() const {
489     assert(hasMacroIdentifier() && "Can only get the macro expansion location "
490                                    "if this attribute has a macro identifier.");
491     return MacroExpansionLoc;
492   }
493 
494   /// Check if the attribute has exactly as many args as Num. May output an
495   /// error. Returns false if a diagnostic is produced.
496   bool checkExactlyNumArgs(class Sema &S, unsigned Num) const;
497   /// Check if the attribute has at least as many args as Num. May output an
498   /// error. Returns false if a diagnostic is produced.
499   bool checkAtLeastNumArgs(class Sema &S, unsigned Num) const;
500   /// Check if the attribute has at most as many args as Num. May output an
501   /// error. Returns false if a diagnostic is produced.
502   bool checkAtMostNumArgs(class Sema &S, unsigned Num) const;
503 
504   bool isTargetSpecificAttr() const;
505   bool isTypeAttr() const;
506   bool isStmtAttr() const;
507 
508   bool hasCustomParsing() const;
509   bool acceptsExprPack() const;
510   bool isParamExpr(size_t N) const;
511   unsigned getMinArgs() const;
512   unsigned getMaxArgs() const;
513   unsigned getNumArgMembers() const;
514   bool hasVariadicArg() const;
515   void handleAttrWithDelayedArgs(Sema &S, Decl *D) const;
516   bool diagnoseAppertainsTo(class Sema &S, const Decl *D) const;
517   bool diagnoseAppertainsTo(class Sema &S, const Stmt *St) const;
518   bool diagnoseMutualExclusion(class Sema &S, const Decl *D) const;
519   // This function stub exists for parity with the declaration checking code so
520   // that checkCommonAttributeFeatures() can work generically on declarations
521   // or statements.
522   bool diagnoseMutualExclusion(class Sema &S, const Stmt *St) const {
523     return true;
524   }
525   bool appliesToDecl(const Decl *D, attr::SubjectMatchRule MatchRule) const;
526   void getMatchRules(const LangOptions &LangOpts,
527                      SmallVectorImpl<std::pair<attr::SubjectMatchRule, bool>>
528                          &MatchRules) const;
529   bool diagnoseLangOpts(class Sema &S) const;
530   bool existsInTarget(const TargetInfo &Target) const;
531   bool isKnownToGCC() const;
532   bool isSupportedByPragmaAttribute() const;
533 
534   /// Returns whether a [[]] attribute, if specified ahead of a declaration,
535   /// should be applied to the decl-specifier-seq instead (i.e. whether it
536   /// "slides" to the decl-specifier-seq).
537   ///
538   /// By the standard, attributes specified before the declaration always
539   /// appertain to the declaration, but historically we have allowed some of
540   /// these attributes to slide to the decl-specifier-seq, so we need to keep
541   /// supporting this behavior.
542   ///
543   /// This may only be called if isStandardAttributeSyntax() returns true.
544   bool slidesFromDeclToDeclSpecLegacyBehavior() const;
545 
546   /// If the parsed attribute has a semantic equivalent, and it would
547   /// have a semantic Spelling enumeration (due to having semantically-distinct
548   /// spelling variations), return the value of that semantic spelling. If the
549   /// parsed attribute does not have a semantic equivalent, or would not have
550   /// a Spelling enumeration, the value UINT_MAX is returned.
551   unsigned getSemanticSpelling() const;
552 
553   /// If this is an OpenCL address space attribute, returns its representation
554   /// in LangAS, otherwise returns default address space.
555   LangAS asOpenCLLangAS() const {
556     switch (getParsedKind()) {
557     case ParsedAttr::AT_OpenCLConstantAddressSpace:
558       return LangAS::opencl_constant;
559     case ParsedAttr::AT_OpenCLGlobalAddressSpace:
560       return LangAS::opencl_global;
561     case ParsedAttr::AT_OpenCLGlobalDeviceAddressSpace:
562       return LangAS::opencl_global_device;
563     case ParsedAttr::AT_OpenCLGlobalHostAddressSpace:
564       return LangAS::opencl_global_host;
565     case ParsedAttr::AT_OpenCLLocalAddressSpace:
566       return LangAS::opencl_local;
567     case ParsedAttr::AT_OpenCLPrivateAddressSpace:
568       return LangAS::opencl_private;
569     case ParsedAttr::AT_OpenCLGenericAddressSpace:
570       return LangAS::opencl_generic;
571     default:
572       return LangAS::Default;
573     }
574   }
575 
576   /// If this is an OpenCL address space attribute, returns its SYCL
577   /// representation in LangAS, otherwise returns default address space.
578   LangAS asSYCLLangAS() const {
579     switch (getKind()) {
580     case ParsedAttr::AT_OpenCLGlobalAddressSpace:
581       return LangAS::sycl_global;
582     case ParsedAttr::AT_OpenCLGlobalDeviceAddressSpace:
583       return LangAS::sycl_global_device;
584     case ParsedAttr::AT_OpenCLGlobalHostAddressSpace:
585       return LangAS::sycl_global_host;
586     case ParsedAttr::AT_OpenCLLocalAddressSpace:
587       return LangAS::sycl_local;
588     case ParsedAttr::AT_OpenCLPrivateAddressSpace:
589       return LangAS::sycl_private;
590     case ParsedAttr::AT_OpenCLGenericAddressSpace:
591     default:
592       return LangAS::Default;
593     }
594   }
595 
596   /// If this is an HLSL address space attribute, returns its representation
597   /// in LangAS, otherwise returns default address space.
598   LangAS asHLSLLangAS() const {
599     switch (getParsedKind()) {
600     case ParsedAttr::AT_HLSLGroupSharedAddressSpace:
601       return LangAS::hlsl_groupshared;
602     default:
603       return LangAS::Default;
604     }
605   }
606 
607   AttributeCommonInfo::Kind getKind() const {
608     return AttributeCommonInfo::Kind(Info.AttrKind);
609   }
610   const ParsedAttrInfo &getInfo() const { return Info; }
611 };
612 
613 class AttributePool;
614 /// A factory, from which one makes pools, from which one creates
615 /// individual attributes which are deallocated with the pool.
616 ///
617 /// Note that it's tolerably cheap to create and destroy one of
618 /// these as long as you don't actually allocate anything in it.
619 class AttributeFactory {
620 public:
621   enum {
622     AvailabilityAllocSize =
623         ParsedAttr::totalSizeToAlloc<ArgsUnion, detail::AvailabilityData,
624                                      detail::TypeTagForDatatypeData, ParsedType,
625                                      detail::PropertyData>(1, 1, 0, 0, 0),
626     TypeTagForDatatypeAllocSize =
627         ParsedAttr::totalSizeToAlloc<ArgsUnion, detail::AvailabilityData,
628                                      detail::TypeTagForDatatypeData, ParsedType,
629                                      detail::PropertyData>(1, 0, 1, 0, 0),
630     PropertyAllocSize =
631         ParsedAttr::totalSizeToAlloc<ArgsUnion, detail::AvailabilityData,
632                                      detail::TypeTagForDatatypeData, ParsedType,
633                                      detail::PropertyData>(0, 0, 0, 0, 1),
634   };
635 
636 private:
637   enum {
638     /// The number of free lists we want to be sure to support
639     /// inline.  This is just enough that availability attributes
640     /// don't surpass it.  It's actually very unlikely we'll see an
641     /// attribute that needs more than that; on x86-64 you'd need 10
642     /// expression arguments, and on i386 you'd need 19.
643     InlineFreeListsCapacity =
644         1 + (AvailabilityAllocSize - sizeof(ParsedAttr)) / sizeof(void *)
645   };
646 
647   llvm::BumpPtrAllocator Alloc;
648 
649   /// Free lists.  The index is determined by the following formula:
650   ///   (size - sizeof(ParsedAttr)) / sizeof(void*)
651   SmallVector<SmallVector<ParsedAttr *, 8>, InlineFreeListsCapacity> FreeLists;
652 
653   // The following are the private interface used by AttributePool.
654   friend class AttributePool;
655 
656   /// Allocate an attribute of the given size.
657   void *allocate(size_t size);
658 
659   void deallocate(ParsedAttr *AL);
660 
661   /// Reclaim all the attributes in the given pool chain, which is
662   /// non-empty.  Note that the current implementation is safe
663   /// against reclaiming things which were not actually allocated
664   /// with the allocator, although of course it's important to make
665   /// sure that their allocator lives at least as long as this one.
666   void reclaimPool(AttributePool &head);
667 
668 public:
669   AttributeFactory();
670   ~AttributeFactory();
671 };
672 
673 class AttributePool {
674   friend class AttributeFactory;
675   friend class ParsedAttributes;
676   AttributeFactory &Factory;
677   llvm::SmallVector<ParsedAttr *> Attrs;
678 
679   void *allocate(size_t size) {
680     return Factory.allocate(size);
681   }
682 
683   ParsedAttr *add(ParsedAttr *attr) {
684     Attrs.push_back(attr);
685     return attr;
686   }
687 
688   void remove(ParsedAttr *attr) {
689     assert(llvm::is_contained(Attrs, attr) &&
690            "Can't take attribute from a pool that doesn't own it!");
691     Attrs.erase(llvm::find(Attrs, attr));
692   }
693 
694   void takePool(AttributePool &pool);
695 
696 public:
697   /// Create a new pool for a factory.
698   AttributePool(AttributeFactory &factory) : Factory(factory) {}
699 
700   AttributePool(const AttributePool &) = delete;
701   // The copy assignment operator is defined as deleted pending further
702   // motivation.
703   AttributePool &operator=(const AttributePool &) = delete;
704 
705   ~AttributePool() { Factory.reclaimPool(*this); }
706 
707   /// Move the given pool's allocations to this pool.
708   AttributePool(AttributePool &&pool) = default;
709 
710   // The move assignment operator is defined as deleted pending further
711   // motivation.
712   AttributePool &operator=(AttributePool &&pool) = delete;
713 
714   AttributeFactory &getFactory() const { return Factory; }
715 
716   void clear() {
717     Factory.reclaimPool(*this);
718     Attrs.clear();
719   }
720 
721   /// Take the given pool's allocations and add them to this pool.
722   void takeAllFrom(AttributePool &pool) {
723     takePool(pool);
724     pool.Attrs.clear();
725   }
726 
727   ParsedAttr *create(IdentifierInfo *attrName, SourceRange attrRange,
728                      IdentifierInfo *scopeName, SourceLocation scopeLoc,
729                      ArgsUnion *args, unsigned numArgs, ParsedAttr::Form form,
730                      SourceLocation ellipsisLoc = SourceLocation()) {
731     size_t temp =
732         ParsedAttr::totalSizeToAlloc<ArgsUnion, detail::AvailabilityData,
733                                      detail::TypeTagForDatatypeData, ParsedType,
734                                      detail::PropertyData>(numArgs, 0, 0, 0, 0);
735     (void)temp;
736     void *memory = allocate(
737         ParsedAttr::totalSizeToAlloc<ArgsUnion, detail::AvailabilityData,
738                                      detail::TypeTagForDatatypeData, ParsedType,
739                                      detail::PropertyData>(numArgs, 0, 0, 0,
740                                                            0));
741     return add(new (memory) ParsedAttr(attrName, attrRange, scopeName, scopeLoc,
742                                        args, numArgs, form, ellipsisLoc));
743   }
744 
745   ParsedAttr *create(IdentifierInfo *attrName, SourceRange attrRange,
746                      IdentifierInfo *scopeName, SourceLocation scopeLoc,
747                      IdentifierLoc *Param, const AvailabilityChange &introduced,
748                      const AvailabilityChange &deprecated,
749                      const AvailabilityChange &obsoleted,
750                      SourceLocation unavailable, const Expr *MessageExpr,
751                      ParsedAttr::Form form, SourceLocation strict,
752                      const Expr *ReplacementExpr) {
753     void *memory = allocate(AttributeFactory::AvailabilityAllocSize);
754     return add(new (memory) ParsedAttr(
755         attrName, attrRange, scopeName, scopeLoc, Param, introduced, deprecated,
756         obsoleted, unavailable, MessageExpr, form, strict, ReplacementExpr));
757   }
758 
759   ParsedAttr *create(IdentifierInfo *attrName, SourceRange attrRange,
760                      IdentifierInfo *scopeName, SourceLocation scopeLoc,
761                      IdentifierLoc *Param1, IdentifierLoc *Param2,
762                      IdentifierLoc *Param3, ParsedAttr::Form form) {
763     void *memory = allocate(
764         ParsedAttr::totalSizeToAlloc<ArgsUnion, detail::AvailabilityData,
765                                      detail::TypeTagForDatatypeData, ParsedType,
766                                      detail::PropertyData>(3, 0, 0, 0, 0));
767     return add(new (memory) ParsedAttr(attrName, attrRange, scopeName, scopeLoc,
768                                        Param1, Param2, Param3, form));
769   }
770 
771   ParsedAttr *
772   createTypeTagForDatatype(IdentifierInfo *attrName, SourceRange attrRange,
773                            IdentifierInfo *scopeName, SourceLocation scopeLoc,
774                            IdentifierLoc *argumentKind,
775                            ParsedType matchingCType, bool layoutCompatible,
776                            bool mustBeNull, ParsedAttr::Form form) {
777     void *memory = allocate(AttributeFactory::TypeTagForDatatypeAllocSize);
778     return add(new (memory) ParsedAttr(attrName, attrRange, scopeName, scopeLoc,
779                                        argumentKind, matchingCType,
780                                        layoutCompatible, mustBeNull, form));
781   }
782 
783   ParsedAttr *createTypeAttribute(IdentifierInfo *attrName,
784                                   SourceRange attrRange,
785                                   IdentifierInfo *scopeName,
786                                   SourceLocation scopeLoc, ParsedType typeArg,
787                                   ParsedAttr::Form formUsed,
788                                   SourceLocation ellipsisLoc) {
789     void *memory = allocate(
790         ParsedAttr::totalSizeToAlloc<ArgsUnion, detail::AvailabilityData,
791                                      detail::TypeTagForDatatypeData, ParsedType,
792                                      detail::PropertyData>(0, 0, 0, 1, 0));
793     return add(new (memory) ParsedAttr(attrName, attrRange, scopeName, scopeLoc,
794                                        typeArg, formUsed, ellipsisLoc));
795   }
796 
797   ParsedAttr *
798   createPropertyAttribute(IdentifierInfo *attrName, SourceRange attrRange,
799                           IdentifierInfo *scopeName, SourceLocation scopeLoc,
800                           IdentifierInfo *getterId, IdentifierInfo *setterId,
801                           ParsedAttr::Form formUsed) {
802     void *memory = allocate(AttributeFactory::PropertyAllocSize);
803     return add(new (memory) ParsedAttr(attrName, attrRange, scopeName, scopeLoc,
804                                        getterId, setterId, formUsed));
805   }
806 };
807 
808 class ParsedAttributesView {
809   using VecTy = llvm::SmallVector<ParsedAttr *>;
810   using SizeType = decltype(std::declval<VecTy>().size());
811 
812 public:
813   SourceRange Range;
814 
815   static const ParsedAttributesView &none() {
816     static const ParsedAttributesView Attrs;
817     return Attrs;
818   }
819 
820   bool empty() const { return AttrList.empty(); }
821   SizeType size() const { return AttrList.size(); }
822   ParsedAttr &operator[](SizeType pos) { return *AttrList[pos]; }
823   const ParsedAttr &operator[](SizeType pos) const { return *AttrList[pos]; }
824 
825   void addAtEnd(ParsedAttr *newAttr) {
826     assert(newAttr);
827     AttrList.push_back(newAttr);
828   }
829 
830   void remove(ParsedAttr *ToBeRemoved) {
831     assert(is_contained(AttrList, ToBeRemoved) &&
832            "Cannot remove attribute that isn't in the list");
833     AttrList.erase(llvm::find(AttrList, ToBeRemoved));
834   }
835 
836   void clearListOnly() { AttrList.clear(); }
837 
838   struct iterator : llvm::iterator_adaptor_base<iterator, VecTy::iterator,
839                                                 std::random_access_iterator_tag,
840                                                 ParsedAttr> {
841     iterator() : iterator_adaptor_base(nullptr) {}
842     iterator(VecTy::iterator I) : iterator_adaptor_base(I) {}
843     reference operator*() const { return **I; }
844     friend class ParsedAttributesView;
845   };
846   struct const_iterator
847       : llvm::iterator_adaptor_base<const_iterator, VecTy::const_iterator,
848                                     std::random_access_iterator_tag,
849                                     ParsedAttr> {
850     const_iterator() : iterator_adaptor_base(nullptr) {}
851     const_iterator(VecTy::const_iterator I) : iterator_adaptor_base(I) {}
852 
853     reference operator*() const { return **I; }
854     friend class ParsedAttributesView;
855   };
856 
857   void addAll(iterator B, iterator E) {
858     AttrList.insert(AttrList.begin(), B.I, E.I);
859   }
860 
861   void addAll(const_iterator B, const_iterator E) {
862     AttrList.insert(AttrList.begin(), B.I, E.I);
863   }
864 
865   void addAllAtEnd(iterator B, iterator E) {
866     AttrList.insert(AttrList.end(), B.I, E.I);
867   }
868 
869   void addAllAtEnd(const_iterator B, const_iterator E) {
870     AttrList.insert(AttrList.end(), B.I, E.I);
871   }
872 
873   iterator begin() { return iterator(AttrList.begin()); }
874   const_iterator begin() const { return const_iterator(AttrList.begin()); }
875   iterator end() { return iterator(AttrList.end()); }
876   const_iterator end() const { return const_iterator(AttrList.end()); }
877 
878   ParsedAttr &front() {
879     assert(!empty());
880     return *AttrList.front();
881   }
882   const ParsedAttr &front() const {
883     assert(!empty());
884     return *AttrList.front();
885   }
886   ParsedAttr &back() {
887     assert(!empty());
888     return *AttrList.back();
889   }
890   const ParsedAttr &back() const {
891     assert(!empty());
892     return *AttrList.back();
893   }
894 
895   bool hasAttribute(ParsedAttr::Kind K) const {
896     return llvm::any_of(AttrList, [K](const ParsedAttr *AL) {
897       return AL->getParsedKind() == K;
898     });
899   }
900 
901   const ParsedAttr *getMSPropertyAttr() const {
902     auto It = llvm::find_if(AttrList, [](const ParsedAttr *AL) {
903       return AL->isDeclspecPropertyAttribute();
904     });
905     if (It != AttrList.end())
906       return *It;
907     return nullptr;
908   }
909   bool hasMSPropertyAttr() const { return getMSPropertyAttr(); }
910 
911 private:
912   VecTy AttrList;
913 };
914 
915 struct ParsedAttributeArgumentsProperties {
916   ParsedAttributeArgumentsProperties(uint32_t StringLiteralBits)
917       : StringLiterals(StringLiteralBits) {}
918   bool isStringLiteralArg(unsigned I) const {
919     // If the last bit is set, assume we have a variadic parameter
920     if (I >= StringLiterals.size())
921       return StringLiterals.test(StringLiterals.size() - 1);
922     return StringLiterals.test(I);
923   }
924 
925 private:
926   std::bitset<32> StringLiterals;
927 };
928 
929 /// ParsedAttributes - A collection of parsed attributes.  Currently
930 /// we don't differentiate between the various attribute syntaxes,
931 /// which is basically silly.
932 ///
933 /// Right now this is a very lightweight container, but the expectation
934 /// is that this will become significantly more serious.
935 class ParsedAttributes : public ParsedAttributesView {
936 public:
937   ParsedAttributes(AttributeFactory &factory) : pool(factory) {}
938   ParsedAttributes(const ParsedAttributes &) = delete;
939   ParsedAttributes &operator=(const ParsedAttributes &) = delete;
940 
941   AttributePool &getPool() const { return pool; }
942 
943   void takeAllFrom(ParsedAttributes &Other) {
944     assert(&Other != this &&
945            "ParsedAttributes can't take attributes from itself");
946     addAll(Other.begin(), Other.end());
947     Other.clearListOnly();
948     pool.takeAllFrom(Other.pool);
949   }
950 
951   void takeOneFrom(ParsedAttributes &Other, ParsedAttr *PA) {
952     assert(&Other != this &&
953            "ParsedAttributes can't take attribute from itself");
954     Other.getPool().remove(PA);
955     Other.remove(PA);
956     getPool().add(PA);
957     addAtEnd(PA);
958   }
959 
960   void clear() {
961     clearListOnly();
962     pool.clear();
963     Range = SourceRange();
964   }
965 
966   /// Add attribute with expression arguments.
967   ParsedAttr *addNew(IdentifierInfo *attrName, SourceRange attrRange,
968                      IdentifierInfo *scopeName, SourceLocation scopeLoc,
969                      ArgsUnion *args, unsigned numArgs, ParsedAttr::Form form,
970                      SourceLocation ellipsisLoc = SourceLocation()) {
971     ParsedAttr *attr = pool.create(attrName, attrRange, scopeName, scopeLoc,
972                                    args, numArgs, form, ellipsisLoc);
973     addAtEnd(attr);
974     return attr;
975   }
976 
977   /// Add availability attribute.
978   ParsedAttr *addNew(IdentifierInfo *attrName, SourceRange attrRange,
979                      IdentifierInfo *scopeName, SourceLocation scopeLoc,
980                      IdentifierLoc *Param, const AvailabilityChange &introduced,
981                      const AvailabilityChange &deprecated,
982                      const AvailabilityChange &obsoleted,
983                      SourceLocation unavailable, const Expr *MessageExpr,
984                      ParsedAttr::Form form, SourceLocation strict,
985                      const Expr *ReplacementExpr) {
986     ParsedAttr *attr = pool.create(
987         attrName, attrRange, scopeName, scopeLoc, Param, introduced, deprecated,
988         obsoleted, unavailable, MessageExpr, form, strict, ReplacementExpr);
989     addAtEnd(attr);
990     return attr;
991   }
992 
993   /// Add objc_bridge_related attribute.
994   ParsedAttr *addNew(IdentifierInfo *attrName, SourceRange attrRange,
995                      IdentifierInfo *scopeName, SourceLocation scopeLoc,
996                      IdentifierLoc *Param1, IdentifierLoc *Param2,
997                      IdentifierLoc *Param3, ParsedAttr::Form form) {
998     ParsedAttr *attr = pool.create(attrName, attrRange, scopeName, scopeLoc,
999                                    Param1, Param2, Param3, form);
1000     addAtEnd(attr);
1001     return attr;
1002   }
1003 
1004   /// Add type_tag_for_datatype attribute.
1005   ParsedAttr *
1006   addNewTypeTagForDatatype(IdentifierInfo *attrName, SourceRange attrRange,
1007                            IdentifierInfo *scopeName, SourceLocation scopeLoc,
1008                            IdentifierLoc *argumentKind,
1009                            ParsedType matchingCType, bool layoutCompatible,
1010                            bool mustBeNull, ParsedAttr::Form form) {
1011     ParsedAttr *attr = pool.createTypeTagForDatatype(
1012         attrName, attrRange, scopeName, scopeLoc, argumentKind, matchingCType,
1013         layoutCompatible, mustBeNull, form);
1014     addAtEnd(attr);
1015     return attr;
1016   }
1017 
1018   /// Add an attribute with a single type argument.
1019   ParsedAttr *addNewTypeAttr(IdentifierInfo *attrName, SourceRange attrRange,
1020                              IdentifierInfo *scopeName, SourceLocation scopeLoc,
1021                              ParsedType typeArg, ParsedAttr::Form formUsed,
1022                              SourceLocation ellipsisLoc = SourceLocation()) {
1023     ParsedAttr *attr =
1024         pool.createTypeAttribute(attrName, attrRange, scopeName, scopeLoc,
1025                                  typeArg, formUsed, ellipsisLoc);
1026     addAtEnd(attr);
1027     return attr;
1028   }
1029 
1030   /// Add microsoft __delspec(property) attribute.
1031   ParsedAttr *
1032   addNewPropertyAttr(IdentifierInfo *attrName, SourceRange attrRange,
1033                      IdentifierInfo *scopeName, SourceLocation scopeLoc,
1034                      IdentifierInfo *getterId, IdentifierInfo *setterId,
1035                      ParsedAttr::Form formUsed) {
1036     ParsedAttr *attr = pool.createPropertyAttribute(
1037         attrName, attrRange, scopeName, scopeLoc, getterId, setterId, formUsed);
1038     addAtEnd(attr);
1039     return attr;
1040   }
1041 
1042 private:
1043   mutable AttributePool pool;
1044 };
1045 
1046 /// Consumes the attributes from `First` and `Second` and concatenates them into
1047 /// `Result`. Sets `Result.Range` to the combined range of `First` and `Second`.
1048 void takeAndConcatenateAttrs(ParsedAttributes &First, ParsedAttributes &Second,
1049                              ParsedAttributes &Result);
1050 
1051 /// These constants match the enumerated choices of
1052 /// err_attribute_argument_n_type and err_attribute_argument_type.
1053 enum AttributeArgumentNType {
1054   AANT_ArgumentIntOrBool,
1055   AANT_ArgumentIntegerConstant,
1056   AANT_ArgumentString,
1057   AANT_ArgumentIdentifier,
1058   AANT_ArgumentConstantExpr,
1059   AANT_ArgumentBuiltinFunction,
1060 };
1061 
1062 /// These constants match the enumerated choices of
1063 /// warn_attribute_wrong_decl_type and err_attribute_wrong_decl_type.
1064 enum AttributeDeclKind {
1065   ExpectedFunction,
1066   ExpectedUnion,
1067   ExpectedVariableOrFunction,
1068   ExpectedFunctionOrMethod,
1069   ExpectedFunctionMethodOrBlock,
1070   ExpectedFunctionMethodOrParameter,
1071   ExpectedVariable,
1072   ExpectedVariableOrField,
1073   ExpectedVariableFieldOrTag,
1074   ExpectedTypeOrNamespace,
1075   ExpectedFunctionVariableOrClass,
1076   ExpectedKernelFunction,
1077   ExpectedFunctionWithProtoType,
1078 };
1079 
1080 inline const StreamingDiagnostic &operator<<(const StreamingDiagnostic &DB,
1081                                              const ParsedAttr &At) {
1082   DB.AddTaggedVal(reinterpret_cast<uint64_t>(At.getAttrName()),
1083                   DiagnosticsEngine::ak_identifierinfo);
1084   return DB;
1085 }
1086 
1087 inline const StreamingDiagnostic &operator<<(const StreamingDiagnostic &DB,
1088                                              const ParsedAttr *At) {
1089   DB.AddTaggedVal(reinterpret_cast<uint64_t>(At->getAttrName()),
1090                   DiagnosticsEngine::ak_identifierinfo);
1091   return DB;
1092 }
1093 
1094 /// AttributeCommonInfo has a non-explicit constructor which takes an
1095 /// SourceRange as its only argument, this constructor has many uses so making
1096 /// it explicit is hard. This constructor causes ambiguity with
1097 /// DiagnosticBuilder &operator<<(const DiagnosticBuilder &DB, SourceRange R).
1098 /// We use SFINAE to disable any conversion and remove any ambiguity.
1099 template <
1100     typename ACI,
1101     std::enable_if_t<std::is_same<ACI, AttributeCommonInfo>::value, int> = 0>
1102 inline const StreamingDiagnostic &operator<<(const StreamingDiagnostic &DB,
1103                                              const ACI &CI) {
1104   DB.AddTaggedVal(reinterpret_cast<uint64_t>(CI.getAttrName()),
1105                   DiagnosticsEngine::ak_identifierinfo);
1106   return DB;
1107 }
1108 
1109 template <
1110     typename ACI,
1111     std::enable_if_t<std::is_same<ACI, AttributeCommonInfo>::value, int> = 0>
1112 inline const StreamingDiagnostic &operator<<(const StreamingDiagnostic &DB,
1113                                              const ACI *CI) {
1114   DB.AddTaggedVal(reinterpret_cast<uint64_t>(CI->getAttrName()),
1115                   DiagnosticsEngine::ak_identifierinfo);
1116   return DB;
1117 }
1118 
1119 } // namespace clang
1120 
1121 #endif // LLVM_CLANG_SEMA_PARSEDATTR_H
1122