clang 19.0.0git
SemaDeclAttr.cpp
Go to the documentation of this file.
1//===--- SemaDeclAttr.cpp - Declaration Attribute Handling ----------------===//
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 implements decl-related attribute processing.
10//
11//===----------------------------------------------------------------------===//
12
17#include "clang/AST/DeclCXX.h"
18#include "clang/AST/DeclObjC.h"
20#include "clang/AST/Expr.h"
21#include "clang/AST/ExprCXX.h"
22#include "clang/AST/Mangle.h"
24#include "clang/AST/Type.h"
26#include "clang/Basic/Cuda.h"
36#include "clang/Sema/DeclSpec.h"
39#include "clang/Sema/Lookup.h"
41#include "clang/Sema/Scope.h"
43#include "clang/Sema/SemaCUDA.h"
44#include "clang/Sema/SemaHLSL.h"
46#include "clang/Sema/SemaObjC.h"
47#include "llvm/ADT/STLExtras.h"
48#include "llvm/ADT/STLForwardCompat.h"
49#include "llvm/ADT/StringExtras.h"
50#include "llvm/Demangle/Demangle.h"
51#include "llvm/IR/Assumptions.h"
52#include "llvm/MC/MCSectionMachO.h"
53#include "llvm/Support/Error.h"
54#include "llvm/Support/MathExtras.h"
55#include "llvm/Support/raw_ostream.h"
56#include "llvm/TargetParser/Triple.h"
57#include <optional>
58
59using namespace clang;
60using namespace sema;
61
63 enum LANG {
66 ObjC
67 };
68} // end namespace AttributeLangSupport
69
70//===----------------------------------------------------------------------===//
71// Helper functions
72//===----------------------------------------------------------------------===//
73
74/// isFunctionOrMethod - Return true if the given decl has function
75/// type (function or function-typed variable) or an Objective-C
76/// method.
77static bool isFunctionOrMethod(const Decl *D) {
78 return (D->getFunctionType() != nullptr) || isa<ObjCMethodDecl>(D);
79}
80
81/// Return true if the given decl has function type (function or
82/// function-typed variable) or an Objective-C method or a block.
83static bool isFunctionOrMethodOrBlock(const Decl *D) {
84 return isFunctionOrMethod(D) || isa<BlockDecl>(D);
85}
86
87/// Return true if the given decl has a declarator that should have
88/// been processed by Sema::GetTypeForDeclarator.
89static bool hasDeclarator(const Decl *D) {
90 // In some sense, TypedefDecl really *ought* to be a DeclaratorDecl.
91 return isa<DeclaratorDecl>(D) || isa<BlockDecl>(D) || isa<TypedefNameDecl>(D) ||
92 isa<ObjCPropertyDecl>(D);
93}
94
95/// hasFunctionProto - Return true if the given decl has a argument
96/// information. This decl should have already passed
97/// isFunctionOrMethod or isFunctionOrMethodOrBlock.
98static bool hasFunctionProto(const Decl *D) {
99 if (const FunctionType *FnTy = D->getFunctionType())
100 return isa<FunctionProtoType>(FnTy);
101 return isa<ObjCMethodDecl>(D) || isa<BlockDecl>(D);
102}
103
104/// getFunctionOrMethodNumParams - Return number of function or method
105/// parameters. It is an error to call this on a K&R function (use
106/// hasFunctionProto first).
107static unsigned getFunctionOrMethodNumParams(const Decl *D) {
108 if (const FunctionType *FnTy = D->getFunctionType())
109 return cast<FunctionProtoType>(FnTy)->getNumParams();
110 if (const auto *BD = dyn_cast<BlockDecl>(D))
111 return BD->getNumParams();
112 return cast<ObjCMethodDecl>(D)->param_size();
113}
114
116 unsigned Idx) {
117 if (const auto *FD = dyn_cast<FunctionDecl>(D))
118 return FD->getParamDecl(Idx);
119 if (const auto *MD = dyn_cast<ObjCMethodDecl>(D))
120 return MD->getParamDecl(Idx);
121 if (const auto *BD = dyn_cast<BlockDecl>(D))
122 return BD->getParamDecl(Idx);
123 return nullptr;
124}
125
126static QualType getFunctionOrMethodParamType(const Decl *D, unsigned Idx) {
127 if (const FunctionType *FnTy = D->getFunctionType())
128 return cast<FunctionProtoType>(FnTy)->getParamType(Idx);
129 if (const auto *BD = dyn_cast<BlockDecl>(D))
130 return BD->getParamDecl(Idx)->getType();
131
132 return cast<ObjCMethodDecl>(D)->parameters()[Idx]->getType();
133}
134
135static SourceRange getFunctionOrMethodParamRange(const Decl *D, unsigned Idx) {
136 if (auto *PVD = getFunctionOrMethodParam(D, Idx))
137 return PVD->getSourceRange();
138 return SourceRange();
139}
140
142 if (const FunctionType *FnTy = D->getFunctionType())
143 return FnTy->getReturnType();
144 return cast<ObjCMethodDecl>(D)->getReturnType();
145}
146
148 if (const auto *FD = dyn_cast<FunctionDecl>(D))
149 return FD->getReturnTypeSourceRange();
150 if (const auto *MD = dyn_cast<ObjCMethodDecl>(D))
151 return MD->getReturnTypeSourceRange();
152 return SourceRange();
153}
154
155static bool isFunctionOrMethodVariadic(const Decl *D) {
156 if (const FunctionType *FnTy = D->getFunctionType())
157 return cast<FunctionProtoType>(FnTy)->isVariadic();
158 if (const auto *BD = dyn_cast<BlockDecl>(D))
159 return BD->isVariadic();
160 return cast<ObjCMethodDecl>(D)->isVariadic();
161}
162
163static bool isInstanceMethod(const Decl *D) {
164 if (const auto *MethodDecl = dyn_cast<CXXMethodDecl>(D))
165 return MethodDecl->isInstance();
166 return false;
167}
168
169static inline bool isNSStringType(QualType T, ASTContext &Ctx,
170 bool AllowNSAttributedString = false) {
171 const auto *PT = T->getAs<ObjCObjectPointerType>();
172 if (!PT)
173 return false;
174
175 ObjCInterfaceDecl *Cls = PT->getObjectType()->getInterface();
176 if (!Cls)
177 return false;
178
179 IdentifierInfo* ClsName = Cls->getIdentifier();
180
181 if (AllowNSAttributedString &&
182 ClsName == &Ctx.Idents.get("NSAttributedString"))
183 return true;
184 // FIXME: Should we walk the chain of classes?
185 return ClsName == &Ctx.Idents.get("NSString") ||
186 ClsName == &Ctx.Idents.get("NSMutableString");
187}
188
189static inline bool isCFStringType(QualType T, ASTContext &Ctx) {
190 const auto *PT = T->getAs<PointerType>();
191 if (!PT)
192 return false;
193
194 const auto *RT = PT->getPointeeType()->getAs<RecordType>();
195 if (!RT)
196 return false;
197
198 const RecordDecl *RD = RT->getDecl();
199 if (RD->getTagKind() != TagTypeKind::Struct)
200 return false;
201
202 return RD->getIdentifier() == &Ctx.Idents.get("__CFString");
203}
204
205static unsigned getNumAttributeArgs(const ParsedAttr &AL) {
206 // FIXME: Include the type in the argument list.
207 return AL.getNumArgs() + AL.hasParsedType();
208}
209
210/// A helper function to provide Attribute Location for the Attr types
211/// AND the ParsedAttr.
212template <typename AttrInfo>
213static std::enable_if_t<std::is_base_of_v<Attr, AttrInfo>, SourceLocation>
214getAttrLoc(const AttrInfo &AL) {
215 return AL.getLocation();
216}
217static SourceLocation getAttrLoc(const ParsedAttr &AL) { return AL.getLoc(); }
218
219/// If Expr is a valid integer constant, get the value of the integer
220/// expression and return success or failure. May output an error.
221///
222/// Negative argument is implicitly converted to unsigned, unless
223/// \p StrictlyUnsigned is true.
224template <typename AttrInfo>
225static bool checkUInt32Argument(Sema &S, const AttrInfo &AI, const Expr *Expr,
226 uint32_t &Val, unsigned Idx = UINT_MAX,
227 bool StrictlyUnsigned = false) {
228 std::optional<llvm::APSInt> I = llvm::APSInt(32);
229 if (Expr->isTypeDependent() ||
231 if (Idx != UINT_MAX)
232 S.Diag(getAttrLoc(AI), diag::err_attribute_argument_n_type)
233 << &AI << Idx << AANT_ArgumentIntegerConstant
234 << Expr->getSourceRange();
235 else
236 S.Diag(getAttrLoc(AI), diag::err_attribute_argument_type)
238 return false;
239 }
240
241 if (!I->isIntN(32)) {
242 S.Diag(Expr->getExprLoc(), diag::err_ice_too_large)
243 << toString(*I, 10, false) << 32 << /* Unsigned */ 1;
244 return false;
245 }
246
247 if (StrictlyUnsigned && I->isSigned() && I->isNegative()) {
248 S.Diag(getAttrLoc(AI), diag::err_attribute_requires_positive_integer)
249 << &AI << /*non-negative*/ 1;
250 return false;
251 }
252
253 Val = (uint32_t)I->getZExtValue();
254 return true;
255}
256
257/// Wrapper around checkUInt32Argument, with an extra check to be sure
258/// that the result will fit into a regular (signed) int. All args have the same
259/// purpose as they do in checkUInt32Argument.
260template <typename AttrInfo>
261static bool checkPositiveIntArgument(Sema &S, const AttrInfo &AI, const Expr *Expr,
262 int &Val, unsigned Idx = UINT_MAX) {
263 uint32_t UVal;
264 if (!checkUInt32Argument(S, AI, Expr, UVal, Idx))
265 return false;
266
267 if (UVal > (uint32_t)std::numeric_limits<int>::max()) {
268 llvm::APSInt I(32); // for toString
269 I = UVal;
270 S.Diag(Expr->getExprLoc(), diag::err_ice_too_large)
271 << toString(I, 10, false) << 32 << /* Unsigned */ 0;
272 return false;
273 }
274
275 Val = UVal;
276 return true;
277}
278
279/// Diagnose mutually exclusive attributes when present on a given
280/// declaration. Returns true if diagnosed.
281template <typename AttrTy>
282static bool checkAttrMutualExclusion(Sema &S, Decl *D, const ParsedAttr &AL) {
283 if (const auto *A = D->getAttr<AttrTy>()) {
284 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible)
285 << AL << A
286 << (AL.isRegularKeywordAttribute() || A->isRegularKeywordAttribute());
287 S.Diag(A->getLocation(), diag::note_conflicting_attribute);
288 return true;
289 }
290 return false;
291}
292
293template <typename AttrTy>
294static bool checkAttrMutualExclusion(Sema &S, Decl *D, const Attr &AL) {
295 if (const auto *A = D->getAttr<AttrTy>()) {
296 S.Diag(AL.getLocation(), diag::err_attributes_are_not_compatible)
297 << &AL << A
298 << (AL.isRegularKeywordAttribute() || A->isRegularKeywordAttribute());
299 S.Diag(A->getLocation(), diag::note_conflicting_attribute);
300 return true;
301 }
302 return false;
303}
304
305/// Check if IdxExpr is a valid parameter index for a function or
306/// instance method D. May output an error.
307///
308/// \returns true if IdxExpr is a valid index.
309template <typename AttrInfo>
311 Sema &S, const Decl *D, const AttrInfo &AI, unsigned AttrArgNum,
312 const Expr *IdxExpr, ParamIdx &Idx, bool CanIndexImplicitThis = false) {
313 assert(isFunctionOrMethodOrBlock(D));
314
315 // In C++ the implicit 'this' function parameter also counts.
316 // Parameters are counted from one.
317 bool HP = hasFunctionProto(D);
318 bool HasImplicitThisParam = isInstanceMethod(D);
319 bool IV = HP && isFunctionOrMethodVariadic(D);
320 unsigned NumParams =
321 (HP ? getFunctionOrMethodNumParams(D) : 0) + HasImplicitThisParam;
322
323 std::optional<llvm::APSInt> IdxInt;
324 if (IdxExpr->isTypeDependent() ||
325 !(IdxInt = IdxExpr->getIntegerConstantExpr(S.Context))) {
326 S.Diag(getAttrLoc(AI), diag::err_attribute_argument_n_type)
327 << &AI << AttrArgNum << AANT_ArgumentIntegerConstant
328 << IdxExpr->getSourceRange();
329 return false;
330 }
331
332 unsigned IdxSource = IdxInt->getLimitedValue(UINT_MAX);
333 if (IdxSource < 1 || (!IV && IdxSource > NumParams)) {
334 S.Diag(getAttrLoc(AI), diag::err_attribute_argument_out_of_bounds)
335 << &AI << AttrArgNum << IdxExpr->getSourceRange();
336 return false;
337 }
338 if (HasImplicitThisParam && !CanIndexImplicitThis) {
339 if (IdxSource == 1) {
340 S.Diag(getAttrLoc(AI), diag::err_attribute_invalid_implicit_this_argument)
341 << &AI << IdxExpr->getSourceRange();
342 return false;
343 }
344 }
345
346 Idx = ParamIdx(IdxSource, D);
347 return true;
348}
349
350/// Check if the argument \p E is a ASCII string literal. If not emit an error
351/// and return false, otherwise set \p Str to the value of the string literal
352/// and return true.
354 const Expr *E, StringRef &Str,
355 SourceLocation *ArgLocation) {
356 const auto *Literal = dyn_cast<StringLiteral>(E->IgnoreParenCasts());
357 if (ArgLocation)
358 *ArgLocation = E->getBeginLoc();
359
360 if (!Literal || (!Literal->isUnevaluated() && !Literal->isOrdinary())) {
361 Diag(E->getBeginLoc(), diag::err_attribute_argument_type)
362 << CI << AANT_ArgumentString;
363 return false;
364 }
365
366 Str = Literal->getString();
367 return true;
368}
369
370/// Check if the argument \p ArgNum of \p Attr is a ASCII string literal.
371/// If not emit an error and return false. If the argument is an identifier it
372/// will emit an error with a fixit hint and treat it as if it was a string
373/// literal.
374bool Sema::checkStringLiteralArgumentAttr(const ParsedAttr &AL, unsigned ArgNum,
375 StringRef &Str,
376 SourceLocation *ArgLocation) {
377 // Look for identifiers. If we have one emit a hint to fix it to a literal.
378 if (AL.isArgIdent(ArgNum)) {
379 IdentifierLoc *Loc = AL.getArgAsIdent(ArgNum);
380 Diag(Loc->Loc, diag::err_attribute_argument_type)
381 << AL << AANT_ArgumentString
382 << FixItHint::CreateInsertion(Loc->Loc, "\"")
384 Str = Loc->Ident->getName();
385 if (ArgLocation)
386 *ArgLocation = Loc->Loc;
387 return true;
388 }
389
390 // Now check for an actual string literal.
391 Expr *ArgExpr = AL.getArgAsExpr(ArgNum);
392 const auto *Literal = dyn_cast<StringLiteral>(ArgExpr->IgnoreParenCasts());
393 if (ArgLocation)
394 *ArgLocation = ArgExpr->getBeginLoc();
395
396 if (!Literal || (!Literal->isUnevaluated() && !Literal->isOrdinary())) {
397 Diag(ArgExpr->getBeginLoc(), diag::err_attribute_argument_type)
398 << AL << AANT_ArgumentString;
399 return false;
400 }
401 Str = Literal->getString();
402 return checkStringLiteralArgumentAttr(AL, ArgExpr, Str, ArgLocation);
403}
404
405/// Applies the given attribute to the Decl without performing any
406/// additional semantic checking.
407template <typename AttrType>
408static void handleSimpleAttribute(Sema &S, Decl *D,
409 const AttributeCommonInfo &CI) {
410 D->addAttr(::new (S.Context) AttrType(S.Context, CI));
411}
412
413template <typename... DiagnosticArgs>
414static const Sema::SemaDiagnosticBuilder&
416 return Bldr;
417}
418
419template <typename T, typename... DiagnosticArgs>
420static const Sema::SemaDiagnosticBuilder&
422 DiagnosticArgs &&... ExtraArgs) {
423 return appendDiagnostics(Bldr << std::forward<T>(ExtraArg),
424 std::forward<DiagnosticArgs>(ExtraArgs)...);
425}
426
427/// Add an attribute @c AttrType to declaration @c D, provided that
428/// @c PassesCheck is true.
429/// Otherwise, emit diagnostic @c DiagID, passing in all parameters
430/// specified in @c ExtraArgs.
431template <typename AttrType, typename... DiagnosticArgs>
433 const AttributeCommonInfo &CI,
434 bool PassesCheck, unsigned DiagID,
435 DiagnosticArgs &&... ExtraArgs) {
436 if (!PassesCheck) {
437 Sema::SemaDiagnosticBuilder DB = S.Diag(D->getBeginLoc(), DiagID);
438 appendDiagnostics(DB, std::forward<DiagnosticArgs>(ExtraArgs)...);
439 return;
440 }
441 handleSimpleAttribute<AttrType>(S, D, CI);
442}
443
444/// Check if the passed-in expression is of type int or bool.
445static bool isIntOrBool(Expr *Exp) {
446 QualType QT = Exp->getType();
447 return QT->isBooleanType() || QT->isIntegerType();
448}
449
450
451// Check to see if the type is a smart pointer of some kind. We assume
452// it's a smart pointer if it defines both operator-> and operator*.
454 auto IsOverloadedOperatorPresent = [&S](const RecordDecl *Record,
458 return !Result.empty();
459 };
460
461 const RecordDecl *Record = RT->getDecl();
462 bool foundStarOperator = IsOverloadedOperatorPresent(Record, OO_Star);
463 bool foundArrowOperator = IsOverloadedOperatorPresent(Record, OO_Arrow);
464 if (foundStarOperator && foundArrowOperator)
465 return true;
466
467 const CXXRecordDecl *CXXRecord = dyn_cast<CXXRecordDecl>(Record);
468 if (!CXXRecord)
469 return false;
470
471 for (const auto &BaseSpecifier : CXXRecord->bases()) {
472 if (!foundStarOperator)
473 foundStarOperator = IsOverloadedOperatorPresent(
474 BaseSpecifier.getType()->getAsRecordDecl(), OO_Star);
475 if (!foundArrowOperator)
476 foundArrowOperator = IsOverloadedOperatorPresent(
477 BaseSpecifier.getType()->getAsRecordDecl(), OO_Arrow);
478 }
479
480 if (foundStarOperator && foundArrowOperator)
481 return true;
482
483 return false;
484}
485
486/// Check if passed in Decl is a pointer type.
487/// Note that this function may produce an error message.
488/// \return true if the Decl is a pointer type; false otherwise
489static bool threadSafetyCheckIsPointer(Sema &S, const Decl *D,
490 const ParsedAttr &AL) {
491 const auto *VD = cast<ValueDecl>(D);
492 QualType QT = VD->getType();
493 if (QT->isAnyPointerType())
494 return true;
495
496 if (const auto *RT = QT->getAs<RecordType>()) {
497 // If it's an incomplete type, it could be a smart pointer; skip it.
498 // (We don't want to force template instantiation if we can avoid it,
499 // since that would alter the order in which templates are instantiated.)
500 if (RT->isIncompleteType())
501 return true;
502
504 return true;
505 }
506
507 S.Diag(AL.getLoc(), diag::warn_thread_attribute_decl_not_pointer) << AL << QT;
508 return false;
509}
510
511/// Checks that the passed in QualType either is of RecordType or points
512/// to RecordType. Returns the relevant RecordType, null if it does not exit.
514 if (const auto *RT = QT->getAs<RecordType>())
515 return RT;
516
517 // Now check if we point to record type.
518 if (const auto *PT = QT->getAs<PointerType>())
519 return PT->getPointeeType()->getAs<RecordType>();
520
521 return nullptr;
522}
523
524template <typename AttrType>
525static bool checkRecordDeclForAttr(const RecordDecl *RD) {
526 // Check if the record itself has the attribute.
527 if (RD->hasAttr<AttrType>())
528 return true;
529
530 // Else check if any base classes have the attribute.
531 if (const auto *CRD = dyn_cast<CXXRecordDecl>(RD)) {
532 if (!CRD->forallBases([](const CXXRecordDecl *Base) {
533 return !Base->hasAttr<AttrType>();
534 }))
535 return true;
536 }
537 return false;
538}
539
541 const RecordType *RT = getRecordType(Ty);
542
543 if (!RT)
544 return false;
545
546 // Don't check for the capability if the class hasn't been defined yet.
547 if (RT->isIncompleteType())
548 return true;
549
550 // Allow smart pointers to be used as capability objects.
551 // FIXME -- Check the type that the smart pointer points to.
553 return true;
554
555 return checkRecordDeclForAttr<CapabilityAttr>(RT->getDecl());
556}
557
559 const auto *TD = Ty->getAs<TypedefType>();
560 if (!TD)
561 return false;
562
563 TypedefNameDecl *TN = TD->getDecl();
564 if (!TN)
565 return false;
566
567 return TN->hasAttr<CapabilityAttr>();
568}
569
570static bool typeHasCapability(Sema &S, QualType Ty) {
572 return true;
573
575 return true;
576
577 return false;
578}
579
580static bool isCapabilityExpr(Sema &S, const Expr *Ex) {
581 // Capability expressions are simple expressions involving the boolean logic
582 // operators &&, || or !, a simple DeclRefExpr, CastExpr or a ParenExpr. Once
583 // a DeclRefExpr is found, its type should be checked to determine whether it
584 // is a capability or not.
585
586 if (const auto *E = dyn_cast<CastExpr>(Ex))
587 return isCapabilityExpr(S, E->getSubExpr());
588 else if (const auto *E = dyn_cast<ParenExpr>(Ex))
589 return isCapabilityExpr(S, E->getSubExpr());
590 else if (const auto *E = dyn_cast<UnaryOperator>(Ex)) {
591 if (E->getOpcode() == UO_LNot || E->getOpcode() == UO_AddrOf ||
592 E->getOpcode() == UO_Deref)
593 return isCapabilityExpr(S, E->getSubExpr());
594 return false;
595 } else if (const auto *E = dyn_cast<BinaryOperator>(Ex)) {
596 if (E->getOpcode() == BO_LAnd || E->getOpcode() == BO_LOr)
597 return isCapabilityExpr(S, E->getLHS()) &&
598 isCapabilityExpr(S, E->getRHS());
599 return false;
600 }
601
602 return typeHasCapability(S, Ex->getType());
603}
604
605/// Checks that all attribute arguments, starting from Sidx, resolve to
606/// a capability object.
607/// \param Sidx The attribute argument index to start checking with.
608/// \param ParamIdxOk Whether an argument can be indexing into a function
609/// parameter list.
611 const ParsedAttr &AL,
613 unsigned Sidx = 0,
614 bool ParamIdxOk = false) {
615 if (Sidx == AL.getNumArgs()) {
616 // If we don't have any capability arguments, the attribute implicitly
617 // refers to 'this'. So we need to make sure that 'this' exists, i.e. we're
618 // a non-static method, and that the class is a (scoped) capability.
619 const auto *MD = dyn_cast<const CXXMethodDecl>(D);
620 if (MD && !MD->isStatic()) {
621 const CXXRecordDecl *RD = MD->getParent();
622 // FIXME -- need to check this again on template instantiation
623 if (!checkRecordDeclForAttr<CapabilityAttr>(RD) &&
624 !checkRecordDeclForAttr<ScopedLockableAttr>(RD))
625 S.Diag(AL.getLoc(),
626 diag::warn_thread_attribute_not_on_capability_member)
627 << AL << MD->getParent();
628 } else {
629 S.Diag(AL.getLoc(), diag::warn_thread_attribute_not_on_non_static_member)
630 << AL;
631 }
632 }
633
634 for (unsigned Idx = Sidx; Idx < AL.getNumArgs(); ++Idx) {
635 Expr *ArgExp = AL.getArgAsExpr(Idx);
636
637 if (ArgExp->isTypeDependent()) {
638 // FIXME -- need to check this again on template instantiation
639 Args.push_back(ArgExp);
640 continue;
641 }
642
643 if (const auto *StrLit = dyn_cast<StringLiteral>(ArgExp)) {
644 if (StrLit->getLength() == 0 ||
645 (StrLit->isOrdinary() && StrLit->getString() == "*")) {
646 // Pass empty strings to the analyzer without warnings.
647 // Treat "*" as the universal lock.
648 Args.push_back(ArgExp);
649 continue;
650 }
651
652 // We allow constant strings to be used as a placeholder for expressions
653 // that are not valid C++ syntax, but warn that they are ignored.
654 S.Diag(AL.getLoc(), diag::warn_thread_attribute_ignored) << AL;
655 Args.push_back(ArgExp);
656 continue;
657 }
658
659 QualType ArgTy = ArgExp->getType();
660
661 // A pointer to member expression of the form &MyClass::mu is treated
662 // specially -- we need to look at the type of the member.
663 if (const auto *UOp = dyn_cast<UnaryOperator>(ArgExp))
664 if (UOp->getOpcode() == UO_AddrOf)
665 if (const auto *DRE = dyn_cast<DeclRefExpr>(UOp->getSubExpr()))
666 if (DRE->getDecl()->isCXXInstanceMember())
667 ArgTy = DRE->getDecl()->getType();
668
669 // First see if we can just cast to record type, or pointer to record type.
670 const RecordType *RT = getRecordType(ArgTy);
671
672 // Now check if we index into a record type function param.
673 if(!RT && ParamIdxOk) {
674 const auto *FD = dyn_cast<FunctionDecl>(D);
675 const auto *IL = dyn_cast<IntegerLiteral>(ArgExp);
676 if(FD && IL) {
677 unsigned int NumParams = FD->getNumParams();
678 llvm::APInt ArgValue = IL->getValue();
679 uint64_t ParamIdxFromOne = ArgValue.getZExtValue();
680 uint64_t ParamIdxFromZero = ParamIdxFromOne - 1;
681 if (!ArgValue.isStrictlyPositive() || ParamIdxFromOne > NumParams) {
682 S.Diag(AL.getLoc(),
683 diag::err_attribute_argument_out_of_bounds_extra_info)
684 << AL << Idx + 1 << NumParams;
685 continue;
686 }
687 ArgTy = FD->getParamDecl(ParamIdxFromZero)->getType();
688 }
689 }
690
691 // If the type does not have a capability, see if the components of the
692 // expression have capabilities. This allows for writing C code where the
693 // capability may be on the type, and the expression is a capability
694 // boolean logic expression. Eg) requires_capability(A || B && !C)
695 if (!typeHasCapability(S, ArgTy) && !isCapabilityExpr(S, ArgExp))
696 S.Diag(AL.getLoc(), diag::warn_thread_attribute_argument_not_lockable)
697 << AL << ArgTy;
698
699 Args.push_back(ArgExp);
700 }
701}
702
703//===----------------------------------------------------------------------===//
704// Attribute Implementations
705//===----------------------------------------------------------------------===//
706
707static void handlePtGuardedVarAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
708 if (!threadSafetyCheckIsPointer(S, D, AL))
709 return;
710
711 D->addAttr(::new (S.Context) PtGuardedVarAttr(S.Context, AL));
712}
713
714static bool checkGuardedByAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL,
715 Expr *&Arg) {
717 // check that all arguments are lockable objects
718 checkAttrArgsAreCapabilityObjs(S, D, AL, Args);
719 unsigned Size = Args.size();
720 if (Size != 1)
721 return false;
722
723 Arg = Args[0];
724
725 return true;
726}
727
728static void handleGuardedByAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
729 Expr *Arg = nullptr;
730 if (!checkGuardedByAttrCommon(S, D, AL, Arg))
731 return;
732
733 D->addAttr(::new (S.Context) GuardedByAttr(S.Context, AL, Arg));
734}
735
736static void handlePtGuardedByAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
737 Expr *Arg = nullptr;
738 if (!checkGuardedByAttrCommon(S, D, AL, Arg))
739 return;
740
741 if (!threadSafetyCheckIsPointer(S, D, AL))
742 return;
743
744 D->addAttr(::new (S.Context) PtGuardedByAttr(S.Context, AL, Arg));
745}
746
747static bool checkAcquireOrderAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL,
749 if (!AL.checkAtLeastNumArgs(S, 1))
750 return false;
751
752 // Check that this attribute only applies to lockable types.
753 QualType QT = cast<ValueDecl>(D)->getType();
754 if (!QT->isDependentType() && !typeHasCapability(S, QT)) {
755 S.Diag(AL.getLoc(), diag::warn_thread_attribute_decl_not_lockable) << AL;
756 return false;
757 }
758
759 // Check that all arguments are lockable objects.
760 checkAttrArgsAreCapabilityObjs(S, D, AL, Args);
761 if (Args.empty())
762 return false;
763
764 return true;
765}
766
767static void handleAcquiredAfterAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
769 if (!checkAcquireOrderAttrCommon(S, D, AL, Args))
770 return;
771
772 Expr **StartArg = &Args[0];
773 D->addAttr(::new (S.Context)
774 AcquiredAfterAttr(S.Context, AL, StartArg, Args.size()));
775}
776
777static void handleAcquiredBeforeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
779 if (!checkAcquireOrderAttrCommon(S, D, AL, Args))
780 return;
781
782 Expr **StartArg = &Args[0];
783 D->addAttr(::new (S.Context)
784 AcquiredBeforeAttr(S.Context, AL, StartArg, Args.size()));
785}
786
787static bool checkLockFunAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL,
789 // zero or more arguments ok
790 // check that all arguments are lockable objects
791 checkAttrArgsAreCapabilityObjs(S, D, AL, Args, 0, /*ParamIdxOk=*/true);
792
793 return true;
794}
795
796static void handleAssertSharedLockAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
798 if (!checkLockFunAttrCommon(S, D, AL, Args))
799 return;
800
801 unsigned Size = Args.size();
802 Expr **StartArg = Size == 0 ? nullptr : &Args[0];
803 D->addAttr(::new (S.Context)
804 AssertSharedLockAttr(S.Context, AL, StartArg, Size));
805}
806
808 const ParsedAttr &AL) {
810 if (!checkLockFunAttrCommon(S, D, AL, Args))
811 return;
812
813 unsigned Size = Args.size();
814 Expr **StartArg = Size == 0 ? nullptr : &Args[0];
815 D->addAttr(::new (S.Context)
816 AssertExclusiveLockAttr(S.Context, AL, StartArg, Size));
817}
818
819/// Checks to be sure that the given parameter number is in bounds, and
820/// is an integral type. Will emit appropriate diagnostics if this returns
821/// false.
822///
823/// AttrArgNo is used to actually retrieve the argument, so it's base-0.
824template <typename AttrInfo>
825static bool checkParamIsIntegerType(Sema &S, const Decl *D, const AttrInfo &AI,
826 unsigned AttrArgNo) {
827 assert(AI.isArgExpr(AttrArgNo) && "Expected expression argument");
828 Expr *AttrArg = AI.getArgAsExpr(AttrArgNo);
829 ParamIdx Idx;
830 if (!checkFunctionOrMethodParameterIndex(S, D, AI, AttrArgNo + 1, AttrArg,
831 Idx))
832 return false;
833
835 if (!ParamTy->isIntegerType() && !ParamTy->isCharType()) {
836 SourceLocation SrcLoc = AttrArg->getBeginLoc();
837 S.Diag(SrcLoc, diag::err_attribute_integers_only)
839 return false;
840 }
841 return true;
842}
843
844static void handleAllocSizeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
845 if (!AL.checkAtLeastNumArgs(S, 1) || !AL.checkAtMostNumArgs(S, 2))
846 return;
847
848 assert(isFunctionOrMethod(D) && hasFunctionProto(D));
849
851 if (!RetTy->isPointerType()) {
852 S.Diag(AL.getLoc(), diag::warn_attribute_return_pointers_only) << AL;
853 return;
854 }
855
856 const Expr *SizeExpr = AL.getArgAsExpr(0);
857 int SizeArgNoVal;
858 // Parameter indices are 1-indexed, hence Index=1
859 if (!checkPositiveIntArgument(S, AL, SizeExpr, SizeArgNoVal, /*Idx=*/1))
860 return;
861 if (!checkParamIsIntegerType(S, D, AL, /*AttrArgNo=*/0))
862 return;
863 ParamIdx SizeArgNo(SizeArgNoVal, D);
864
865 ParamIdx NumberArgNo;
866 if (AL.getNumArgs() == 2) {
867 const Expr *NumberExpr = AL.getArgAsExpr(1);
868 int Val;
869 // Parameter indices are 1-based, hence Index=2
870 if (!checkPositiveIntArgument(S, AL, NumberExpr, Val, /*Idx=*/2))
871 return;
872 if (!checkParamIsIntegerType(S, D, AL, /*AttrArgNo=*/1))
873 return;
874 NumberArgNo = ParamIdx(Val, D);
875 }
876
877 D->addAttr(::new (S.Context)
878 AllocSizeAttr(S.Context, AL, SizeArgNo, NumberArgNo));
879}
880
881static bool checkTryLockFunAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL,
883 if (!AL.checkAtLeastNumArgs(S, 1))
884 return false;
885
886 if (!isIntOrBool(AL.getArgAsExpr(0))) {
887 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
888 << AL << 1 << AANT_ArgumentIntOrBool;
889 return false;
890 }
891
892 // check that all arguments are lockable objects
893 checkAttrArgsAreCapabilityObjs(S, D, AL, Args, 1);
894
895 return true;
896}
897
899 const ParsedAttr &AL) {
901 if (!checkTryLockFunAttrCommon(S, D, AL, Args))
902 return;
903
904 D->addAttr(::new (S.Context) SharedTrylockFunctionAttr(
905 S.Context, AL, AL.getArgAsExpr(0), Args.data(), Args.size()));
906}
907
909 const ParsedAttr &AL) {
911 if (!checkTryLockFunAttrCommon(S, D, AL, Args))
912 return;
913
914 D->addAttr(::new (S.Context) ExclusiveTrylockFunctionAttr(
915 S.Context, AL, AL.getArgAsExpr(0), Args.data(), Args.size()));
916}
917
918static void handleLockReturnedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
919 // check that the argument is lockable object
921 checkAttrArgsAreCapabilityObjs(S, D, AL, Args);
922 unsigned Size = Args.size();
923 if (Size == 0)
924 return;
925
926 D->addAttr(::new (S.Context) LockReturnedAttr(S.Context, AL, Args[0]));
927}
928
929static void handleLocksExcludedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
930 if (!AL.checkAtLeastNumArgs(S, 1))
931 return;
932
933 // check that all arguments are lockable objects
935 checkAttrArgsAreCapabilityObjs(S, D, AL, Args);
936 unsigned Size = Args.size();
937 if (Size == 0)
938 return;
939 Expr **StartArg = &Args[0];
940
941 D->addAttr(::new (S.Context)
942 LocksExcludedAttr(S.Context, AL, StartArg, Size));
943}
944
945static bool checkFunctionConditionAttr(Sema &S, Decl *D, const ParsedAttr &AL,
946 Expr *&Cond, StringRef &Msg) {
947 Cond = AL.getArgAsExpr(0);
948 if (!Cond->isTypeDependent()) {
950 if (Converted.isInvalid())
951 return false;
952 Cond = Converted.get();
953 }
954
955 if (!S.checkStringLiteralArgumentAttr(AL, 1, Msg))
956 return false;
957
958 if (Msg.empty())
959 Msg = "<no message provided>";
960
962 if (isa<FunctionDecl>(D) && !Cond->isValueDependent() &&
963 !Expr::isPotentialConstantExprUnevaluated(Cond, cast<FunctionDecl>(D),
964 Diags)) {
965 S.Diag(AL.getLoc(), diag::err_attr_cond_never_constant_expr) << AL;
966 for (const PartialDiagnosticAt &PDiag : Diags)
967 S.Diag(PDiag.first, PDiag.second);
968 return false;
969 }
970 return true;
971}
972
973static void handleEnableIfAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
974 S.Diag(AL.getLoc(), diag::ext_clang_enable_if);
975
976 Expr *Cond;
977 StringRef Msg;
978 if (checkFunctionConditionAttr(S, D, AL, Cond, Msg))
979 D->addAttr(::new (S.Context) EnableIfAttr(S.Context, AL, Cond, Msg));
980}
981
982static void handleErrorAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
983 StringRef NewUserDiagnostic;
984 if (!S.checkStringLiteralArgumentAttr(AL, 0, NewUserDiagnostic))
985 return;
986 if (ErrorAttr *EA = S.mergeErrorAttr(D, AL, NewUserDiagnostic))
987 D->addAttr(EA);
988}
989
991 const ParsedAttr &AL) {
992 const auto *PD = isa<CXXRecordDecl>(D)
993 ? cast<DeclContext>(D)
995 if (const auto *RD = dyn_cast<CXXRecordDecl>(PD); RD && RD->isLocalClass()) {
996 S.Diag(AL.getLoc(),
997 diag::warn_attribute_exclude_from_explicit_instantiation_local_class)
998 << AL << /*IsMember=*/!isa<CXXRecordDecl>(D);
999 return;
1000 }
1001 D->addAttr(::new (S.Context)
1002 ExcludeFromExplicitInstantiationAttr(S.Context, AL));
1003}
1004
1005namespace {
1006/// Determines if a given Expr references any of the given function's
1007/// ParmVarDecls, or the function's implicit `this` parameter (if applicable).
1008class ArgumentDependenceChecker
1009 : public RecursiveASTVisitor<ArgumentDependenceChecker> {
1010#ifndef NDEBUG
1011 const CXXRecordDecl *ClassType;
1012#endif
1014 bool Result;
1015
1016public:
1017 ArgumentDependenceChecker(const FunctionDecl *FD) {
1018#ifndef NDEBUG
1019 if (const auto *MD = dyn_cast<CXXMethodDecl>(FD))
1020 ClassType = MD->getParent();
1021 else
1022 ClassType = nullptr;
1023#endif
1024 Parms.insert(FD->param_begin(), FD->param_end());
1025 }
1026
1027 bool referencesArgs(Expr *E) {
1028 Result = false;
1029 TraverseStmt(E);
1030 return Result;
1031 }
1032
1033 bool VisitCXXThisExpr(CXXThisExpr *E) {
1034 assert(E->getType()->getPointeeCXXRecordDecl() == ClassType &&
1035 "`this` doesn't refer to the enclosing class?");
1036 Result = true;
1037 return false;
1038 }
1039
1040 bool VisitDeclRefExpr(DeclRefExpr *DRE) {
1041 if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl()))
1042 if (Parms.count(PVD)) {
1043 Result = true;
1044 return false;
1045 }
1046 return true;
1047 }
1048};
1049}
1050
1052 const ParsedAttr &AL) {
1053 const auto *DeclFD = cast<FunctionDecl>(D);
1054
1055 if (const auto *MethodDecl = dyn_cast<CXXMethodDecl>(DeclFD))
1056 if (!MethodDecl->isStatic()) {
1057 S.Diag(AL.getLoc(), diag::err_attribute_no_member_function) << AL;
1058 return;
1059 }
1060
1061 auto DiagnoseType = [&](unsigned Index, AttributeArgumentNType T) {
1062 SourceLocation Loc = [&]() {
1063 auto Union = AL.getArg(Index - 1);
1064 if (Union.is<Expr *>())
1065 return Union.get<Expr *>()->getBeginLoc();
1066 return Union.get<IdentifierLoc *>()->Loc;
1067 }();
1068
1069 S.Diag(Loc, diag::err_attribute_argument_n_type) << AL << Index << T;
1070 };
1071
1072 FunctionDecl *AttrFD = [&]() -> FunctionDecl * {
1073 if (!AL.isArgExpr(0))
1074 return nullptr;
1075 auto *F = dyn_cast_if_present<DeclRefExpr>(AL.getArgAsExpr(0));
1076 if (!F)
1077 return nullptr;
1078 return dyn_cast_if_present<FunctionDecl>(F->getFoundDecl());
1079 }();
1080
1081 if (!AttrFD || !AttrFD->getBuiltinID(true)) {
1082 DiagnoseType(1, AANT_ArgumentBuiltinFunction);
1083 return;
1084 }
1085
1086 if (AttrFD->getNumParams() != AL.getNumArgs() - 1) {
1087 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments_for)
1088 << AL << AttrFD << AttrFD->getNumParams();
1089 return;
1090 }
1091
1093
1094 for (unsigned I = 1; I < AL.getNumArgs(); ++I) {
1095 if (!AL.isArgExpr(I)) {
1096 DiagnoseType(I + 1, AANT_ArgumentIntegerConstant);
1097 return;
1098 }
1099
1100 const Expr *IndexExpr = AL.getArgAsExpr(I);
1101 uint32_t Index;
1102
1103 if (!checkUInt32Argument(S, AL, IndexExpr, Index, I + 1, false))
1104 return;
1105
1106 if (Index > DeclFD->getNumParams()) {
1107 S.Diag(AL.getLoc(), diag::err_attribute_bounds_for_function)
1108 << AL << Index << DeclFD << DeclFD->getNumParams();
1109 return;
1110 }
1111
1112 QualType T1 = AttrFD->getParamDecl(I - 1)->getType();
1113 QualType T2 = DeclFD->getParamDecl(Index - 1)->getType();
1114
1117 S.Diag(IndexExpr->getBeginLoc(), diag::err_attribute_parameter_types)
1118 << AL << Index << DeclFD << T2 << I << AttrFD << T1;
1119 return;
1120 }
1121
1122 Indices.push_back(Index - 1);
1123 }
1124
1125 D->addAttr(::new (S.Context) DiagnoseAsBuiltinAttr(
1126 S.Context, AL, AttrFD, Indices.data(), Indices.size()));
1127}
1128
1129static void handleDiagnoseIfAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1130 S.Diag(AL.getLoc(), diag::ext_clang_diagnose_if);
1131
1132 Expr *Cond;
1133 StringRef Msg;
1134 if (!checkFunctionConditionAttr(S, D, AL, Cond, Msg))
1135 return;
1136
1137 StringRef DiagTypeStr;
1138 if (!S.checkStringLiteralArgumentAttr(AL, 2, DiagTypeStr))
1139 return;
1140
1141 DiagnoseIfAttr::DiagnosticType DiagType;
1142 if (!DiagnoseIfAttr::ConvertStrToDiagnosticType(DiagTypeStr, DiagType)) {
1143 S.Diag(AL.getArgAsExpr(2)->getBeginLoc(),
1144 diag::err_diagnose_if_invalid_diagnostic_type);
1145 return;
1146 }
1147
1148 bool ArgDependent = false;
1149 if (const auto *FD = dyn_cast<FunctionDecl>(D))
1150 ArgDependent = ArgumentDependenceChecker(FD).referencesArgs(Cond);
1151 D->addAttr(::new (S.Context) DiagnoseIfAttr(
1152 S.Context, AL, Cond, Msg, DiagType, ArgDependent, cast<NamedDecl>(D)));
1153}
1154
1155static void handleNoBuiltinAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1156 static constexpr const StringRef kWildcard = "*";
1157
1159 bool HasWildcard = false;
1160
1161 const auto AddBuiltinName = [&Names, &HasWildcard](StringRef Name) {
1162 if (Name == kWildcard)
1163 HasWildcard = true;
1164 Names.push_back(Name);
1165 };
1166
1167 // Add previously defined attributes.
1168 if (const auto *NBA = D->getAttr<NoBuiltinAttr>())
1169 for (StringRef BuiltinName : NBA->builtinNames())
1170 AddBuiltinName(BuiltinName);
1171
1172 // Add current attributes.
1173 if (AL.getNumArgs() == 0)
1174 AddBuiltinName(kWildcard);
1175 else
1176 for (unsigned I = 0, E = AL.getNumArgs(); I != E; ++I) {
1177 StringRef BuiltinName;
1178 SourceLocation LiteralLoc;
1179 if (!S.checkStringLiteralArgumentAttr(AL, I, BuiltinName, &LiteralLoc))
1180 return;
1181
1182 if (Builtin::Context::isBuiltinFunc(BuiltinName))
1183 AddBuiltinName(BuiltinName);
1184 else
1185 S.Diag(LiteralLoc, diag::warn_attribute_no_builtin_invalid_builtin_name)
1186 << BuiltinName << AL;
1187 }
1188
1189 // Repeating the same attribute is fine.
1190 llvm::sort(Names);
1191 Names.erase(std::unique(Names.begin(), Names.end()), Names.end());
1192
1193 // Empty no_builtin must be on its own.
1194 if (HasWildcard && Names.size() > 1)
1195 S.Diag(D->getLocation(),
1196 diag::err_attribute_no_builtin_wildcard_or_builtin_name)
1197 << AL;
1198
1199 if (D->hasAttr<NoBuiltinAttr>())
1200 D->dropAttr<NoBuiltinAttr>();
1201 D->addAttr(::new (S.Context)
1202 NoBuiltinAttr(S.Context, AL, Names.data(), Names.size()));
1203}
1204
1205static void handlePassObjectSizeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1206 if (D->hasAttr<PassObjectSizeAttr>()) {
1207 S.Diag(D->getBeginLoc(), diag::err_attribute_only_once_per_parameter) << AL;
1208 return;
1209 }
1210
1211 Expr *E = AL.getArgAsExpr(0);
1212 uint32_t Type;
1213 if (!checkUInt32Argument(S, AL, E, Type, /*Idx=*/1))
1214 return;
1215
1216 // pass_object_size's argument is passed in as the second argument of
1217 // __builtin_object_size. So, it has the same constraints as that second
1218 // argument; namely, it must be in the range [0, 3].
1219 if (Type > 3) {
1220 S.Diag(E->getBeginLoc(), diag::err_attribute_argument_out_of_range)
1221 << AL << 0 << 3 << E->getSourceRange();
1222 return;
1223 }
1224
1225 // pass_object_size is only supported on constant pointer parameters; as a
1226 // kindness to users, we allow the parameter to be non-const for declarations.
1227 // At this point, we have no clue if `D` belongs to a function declaration or
1228 // definition, so we defer the constness check until later.
1229 if (!cast<ParmVarDecl>(D)->getType()->isPointerType()) {
1230 S.Diag(D->getBeginLoc(), diag::err_attribute_pointers_only) << AL << 1;
1231 return;
1232 }
1233
1234 D->addAttr(::new (S.Context) PassObjectSizeAttr(S.Context, AL, (int)Type));
1235}
1236
1237static void handleConsumableAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1238 ConsumableAttr::ConsumedState DefaultState;
1239
1240 if (AL.isArgIdent(0)) {
1241 IdentifierLoc *IL = AL.getArgAsIdent(0);
1242 if (!ConsumableAttr::ConvertStrToConsumedState(IL->Ident->getName(),
1243 DefaultState)) {
1244 S.Diag(IL->Loc, diag::warn_attribute_type_not_supported) << AL
1245 << IL->Ident;
1246 return;
1247 }
1248 } else {
1249 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
1250 << AL << AANT_ArgumentIdentifier;
1251 return;
1252 }
1253
1254 D->addAttr(::new (S.Context) ConsumableAttr(S.Context, AL, DefaultState));
1255}
1256
1258 const ParsedAttr &AL) {
1260
1261 if (const CXXRecordDecl *RD = ThisType->getAsCXXRecordDecl()) {
1262 if (!RD->hasAttr<ConsumableAttr>()) {
1263 S.Diag(AL.getLoc(), diag::warn_attr_on_unconsumable_class) << RD;
1264
1265 return false;
1266 }
1267 }
1268
1269 return true;
1270}
1271
1272static void handleCallableWhenAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1273 if (!AL.checkAtLeastNumArgs(S, 1))
1274 return;
1275
1276 if (!checkForConsumableClass(S, cast<CXXMethodDecl>(D), AL))
1277 return;
1278
1280 for (unsigned ArgIndex = 0; ArgIndex < AL.getNumArgs(); ++ArgIndex) {
1281 CallableWhenAttr::ConsumedState CallableState;
1282
1283 StringRef StateString;
1285 if (AL.isArgIdent(ArgIndex)) {
1286 IdentifierLoc *Ident = AL.getArgAsIdent(ArgIndex);
1287 StateString = Ident->Ident->getName();
1288 Loc = Ident->Loc;
1289 } else {
1290 if (!S.checkStringLiteralArgumentAttr(AL, ArgIndex, StateString, &Loc))
1291 return;
1292 }
1293
1294 if (!CallableWhenAttr::ConvertStrToConsumedState(StateString,
1295 CallableState)) {
1296 S.Diag(Loc, diag::warn_attribute_type_not_supported) << AL << StateString;
1297 return;
1298 }
1299
1300 States.push_back(CallableState);
1301 }
1302
1303 D->addAttr(::new (S.Context)
1304 CallableWhenAttr(S.Context, AL, States.data(), States.size()));
1305}
1306
1307static void handleParamTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1308 ParamTypestateAttr::ConsumedState ParamState;
1309
1310 if (AL.isArgIdent(0)) {
1311 IdentifierLoc *Ident = AL.getArgAsIdent(0);
1312 StringRef StateString = Ident->Ident->getName();
1313
1314 if (!ParamTypestateAttr::ConvertStrToConsumedState(StateString,
1315 ParamState)) {
1316 S.Diag(Ident->Loc, diag::warn_attribute_type_not_supported)
1317 << AL << StateString;
1318 return;
1319 }
1320 } else {
1321 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
1322 << AL << AANT_ArgumentIdentifier;
1323 return;
1324 }
1325
1326 // FIXME: This check is currently being done in the analysis. It can be
1327 // enabled here only after the parser propagates attributes at
1328 // template specialization definition, not declaration.
1329 //QualType ReturnType = cast<ParmVarDecl>(D)->getType();
1330 //const CXXRecordDecl *RD = ReturnType->getAsCXXRecordDecl();
1331 //
1332 //if (!RD || !RD->hasAttr<ConsumableAttr>()) {
1333 // S.Diag(AL.getLoc(), diag::warn_return_state_for_unconsumable_type) <<
1334 // ReturnType.getAsString();
1335 // return;
1336 //}
1337
1338 D->addAttr(::new (S.Context) ParamTypestateAttr(S.Context, AL, ParamState));
1339}
1340
1341static void handleReturnTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1342 ReturnTypestateAttr::ConsumedState ReturnState;
1343
1344 if (AL.isArgIdent(0)) {
1345 IdentifierLoc *IL = AL.getArgAsIdent(0);
1346 if (!ReturnTypestateAttr::ConvertStrToConsumedState(IL->Ident->getName(),
1347 ReturnState)) {
1348 S.Diag(IL->Loc, diag::warn_attribute_type_not_supported) << AL
1349 << IL->Ident;
1350 return;
1351 }
1352 } else {
1353 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
1354 << AL << AANT_ArgumentIdentifier;
1355 return;
1356 }
1357
1358 // FIXME: This check is currently being done in the analysis. It can be
1359 // enabled here only after the parser propagates attributes at
1360 // template specialization definition, not declaration.
1361 // QualType ReturnType;
1362 //
1363 // if (const ParmVarDecl *Param = dyn_cast<ParmVarDecl>(D)) {
1364 // ReturnType = Param->getType();
1365 //
1366 //} else if (const CXXConstructorDecl *Constructor =
1367 // dyn_cast<CXXConstructorDecl>(D)) {
1368 // ReturnType = Constructor->getFunctionObjectParameterType();
1369 //
1370 //} else {
1371 //
1372 // ReturnType = cast<FunctionDecl>(D)->getCallResultType();
1373 //}
1374 //
1375 // const CXXRecordDecl *RD = ReturnType->getAsCXXRecordDecl();
1376 //
1377 // if (!RD || !RD->hasAttr<ConsumableAttr>()) {
1378 // S.Diag(Attr.getLoc(), diag::warn_return_state_for_unconsumable_type) <<
1379 // ReturnType.getAsString();
1380 // return;
1381 //}
1382
1383 D->addAttr(::new (S.Context) ReturnTypestateAttr(S.Context, AL, ReturnState));
1384}
1385
1386static void handleSetTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1387 if (!checkForConsumableClass(S, cast<CXXMethodDecl>(D), AL))
1388 return;
1389
1390 SetTypestateAttr::ConsumedState NewState;
1391 if (AL.isArgIdent(0)) {
1392 IdentifierLoc *Ident = AL.getArgAsIdent(0);
1393 StringRef Param = Ident->Ident->getName();
1394 if (!SetTypestateAttr::ConvertStrToConsumedState(Param, NewState)) {
1395 S.Diag(Ident->Loc, diag::warn_attribute_type_not_supported) << AL
1396 << Param;
1397 return;
1398 }
1399 } else {
1400 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
1401 << AL << AANT_ArgumentIdentifier;
1402 return;
1403 }
1404
1405 D->addAttr(::new (S.Context) SetTypestateAttr(S.Context, AL, NewState));
1406}
1407
1408static void handleTestTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1409 if (!checkForConsumableClass(S, cast<CXXMethodDecl>(D), AL))
1410 return;
1411
1412 TestTypestateAttr::ConsumedState TestState;
1413 if (AL.isArgIdent(0)) {
1414 IdentifierLoc *Ident = AL.getArgAsIdent(0);
1415 StringRef Param = Ident->Ident->getName();
1416 if (!TestTypestateAttr::ConvertStrToConsumedState(Param, TestState)) {
1417 S.Diag(Ident->Loc, diag::warn_attribute_type_not_supported) << AL
1418 << Param;
1419 return;
1420 }
1421 } else {
1422 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
1423 << AL << AANT_ArgumentIdentifier;
1424 return;
1425 }
1426
1427 D->addAttr(::new (S.Context) TestTypestateAttr(S.Context, AL, TestState));
1428}
1429
1430static void handleExtVectorTypeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1431 // Remember this typedef decl, we will need it later for diagnostics.
1432 S.ExtVectorDecls.push_back(cast<TypedefNameDecl>(D));
1433}
1434
1435static void handlePackedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1436 if (auto *TD = dyn_cast<TagDecl>(D))
1437 TD->addAttr(::new (S.Context) PackedAttr(S.Context, AL));
1438 else if (auto *FD = dyn_cast<FieldDecl>(D)) {
1439 bool BitfieldByteAligned = (!FD->getType()->isDependentType() &&
1440 !FD->getType()->isIncompleteType() &&
1441 FD->isBitField() &&
1442 S.Context.getTypeAlign(FD->getType()) <= 8);
1443
1444 if (S.getASTContext().getTargetInfo().getTriple().isPS()) {
1445 if (BitfieldByteAligned)
1446 // The PS4/PS5 targets need to maintain ABI backwards compatibility.
1447 S.Diag(AL.getLoc(), diag::warn_attribute_ignored_for_field_of_type)
1448 << AL << FD->getType();
1449 else
1450 FD->addAttr(::new (S.Context) PackedAttr(S.Context, AL));
1451 } else {
1452 // Report warning about changed offset in the newer compiler versions.
1453 if (BitfieldByteAligned)
1454 S.Diag(AL.getLoc(), diag::warn_attribute_packed_for_bitfield);
1455
1456 FD->addAttr(::new (S.Context) PackedAttr(S.Context, AL));
1457 }
1458
1459 } else
1460 S.Diag(AL.getLoc(), diag::warn_attribute_ignored) << AL;
1461}
1462
1463static void handlePreferredName(Sema &S, Decl *D, const ParsedAttr &AL) {
1464 auto *RD = cast<CXXRecordDecl>(D);
1465 ClassTemplateDecl *CTD = RD->getDescribedClassTemplate();
1466 assert(CTD && "attribute does not appertain to this declaration");
1467
1468 ParsedType PT = AL.getTypeArg();
1469 TypeSourceInfo *TSI = nullptr;
1470 QualType T = S.GetTypeFromParser(PT, &TSI);
1471 if (!TSI)
1473
1474 if (!T.hasQualifiers() && T->isTypedefNameType()) {
1475 // Find the template name, if this type names a template specialization.
1476 const TemplateDecl *Template = nullptr;
1477 if (const auto *CTSD = dyn_cast_if_present<ClassTemplateSpecializationDecl>(
1478 T->getAsCXXRecordDecl())) {
1479 Template = CTSD->getSpecializedTemplate();
1480 } else if (const auto *TST = T->getAs<TemplateSpecializationType>()) {
1481 while (TST && TST->isTypeAlias())
1482 TST = TST->getAliasedType()->getAs<TemplateSpecializationType>();
1483 if (TST)
1484 Template = TST->getTemplateName().getAsTemplateDecl();
1485 }
1486
1487 if (Template && declaresSameEntity(Template, CTD)) {
1488 D->addAttr(::new (S.Context) PreferredNameAttr(S.Context, AL, TSI));
1489 return;
1490 }
1491 }
1492
1493 S.Diag(AL.getLoc(), diag::err_attribute_preferred_name_arg_invalid)
1494 << T << CTD;
1495 if (const auto *TT = T->getAs<TypedefType>())
1496 S.Diag(TT->getDecl()->getLocation(), diag::note_entity_declared_at)
1497 << TT->getDecl();
1498}
1499
1500static bool checkIBOutletCommon(Sema &S, Decl *D, const ParsedAttr &AL) {
1501 // The IBOutlet/IBOutletCollection attributes only apply to instance
1502 // variables or properties of Objective-C classes. The outlet must also
1503 // have an object reference type.
1504 if (const auto *VD = dyn_cast<ObjCIvarDecl>(D)) {
1505 if (!VD->getType()->getAs<ObjCObjectPointerType>()) {
1506 S.Diag(AL.getLoc(), diag::warn_iboutlet_object_type)
1507 << AL << VD->getType() << 0;
1508 return false;
1509 }
1510 }
1511 else if (const auto *PD = dyn_cast<ObjCPropertyDecl>(D)) {
1512 if (!PD->getType()->getAs<ObjCObjectPointerType>()) {
1513 S.Diag(AL.getLoc(), diag::warn_iboutlet_object_type)
1514 << AL << PD->getType() << 1;
1515 return false;
1516 }
1517 }
1518 else {
1519 S.Diag(AL.getLoc(), diag::warn_attribute_iboutlet) << AL;
1520 return false;
1521 }
1522
1523 return true;
1524}
1525
1526static void handleIBOutlet(Sema &S, Decl *D, const ParsedAttr &AL) {
1527 if (!checkIBOutletCommon(S, D, AL))
1528 return;
1529
1530 D->addAttr(::new (S.Context) IBOutletAttr(S.Context, AL));
1531}
1532
1533static void handleIBOutletCollection(Sema &S, Decl *D, const ParsedAttr &AL) {
1534
1535 // The iboutletcollection attribute can have zero or one arguments.
1536 if (AL.getNumArgs() > 1) {
1537 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << AL << 1;
1538 return;
1539 }
1540
1541 if (!checkIBOutletCommon(S, D, AL))
1542 return;
1543
1544 ParsedType PT;
1545
1546 if (AL.hasParsedType())
1547 PT = AL.getTypeArg();
1548 else {
1549 PT = S.getTypeName(S.Context.Idents.get("NSObject"), AL.getLoc(),
1551 if (!PT) {
1552 S.Diag(AL.getLoc(), diag::err_iboutletcollection_type) << "NSObject";
1553 return;
1554 }
1555 }
1556
1557 TypeSourceInfo *QTLoc = nullptr;
1558 QualType QT = S.GetTypeFromParser(PT, &QTLoc);
1559 if (!QTLoc)
1560 QTLoc = S.Context.getTrivialTypeSourceInfo(QT, AL.getLoc());
1561
1562 // Diagnose use of non-object type in iboutletcollection attribute.
1563 // FIXME. Gnu attribute extension ignores use of builtin types in
1564 // attributes. So, __attribute__((iboutletcollection(char))) will be
1565 // treated as __attribute__((iboutletcollection())).
1566 if (!QT->isObjCIdType() && !QT->isObjCObjectType()) {
1567 S.Diag(AL.getLoc(),
1568 QT->isBuiltinType() ? diag::err_iboutletcollection_builtintype
1569 : diag::err_iboutletcollection_type) << QT;
1570 return;
1571 }
1572
1573 D->addAttr(::new (S.Context) IBOutletCollectionAttr(S.Context, AL, QTLoc));
1574}
1575
1577 if (RefOkay) {
1578 if (T->isReferenceType())
1579 return true;
1580 } else {
1581 T = T.getNonReferenceType();
1582 }
1583
1584 // The nonnull attribute, and other similar attributes, can be applied to a
1585 // transparent union that contains a pointer type.
1586 if (const RecordType *UT = T->getAsUnionType()) {
1587 if (UT && UT->getDecl()->hasAttr<TransparentUnionAttr>()) {
1588 RecordDecl *UD = UT->getDecl();
1589 for (const auto *I : UD->fields()) {
1590 QualType QT = I->getType();
1591 if (QT->isAnyPointerType() || QT->isBlockPointerType())
1592 return true;
1593 }
1594 }
1595 }
1596
1597 return T->isAnyPointerType() || T->isBlockPointerType();
1598}
1599
1600static bool attrNonNullArgCheck(Sema &S, QualType T, const ParsedAttr &AL,
1601 SourceRange AttrParmRange,
1602 SourceRange TypeRange,
1603 bool isReturnValue = false) {
1604 if (!S.isValidPointerAttrType(T)) {
1605 if (isReturnValue)
1606 S.Diag(AL.getLoc(), diag::warn_attribute_return_pointers_only)
1607 << AL << AttrParmRange << TypeRange;
1608 else
1609 S.Diag(AL.getLoc(), diag::warn_attribute_pointers_only)
1610 << AL << AttrParmRange << TypeRange << 0;
1611 return false;
1612 }
1613 return true;
1614}
1615
1616static void handleNonNullAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1617 SmallVector<ParamIdx, 8> NonNullArgs;
1618 for (unsigned I = 0; I < AL.getNumArgs(); ++I) {
1619 Expr *Ex = AL.getArgAsExpr(I);
1620 ParamIdx Idx;
1621 if (!checkFunctionOrMethodParameterIndex(S, D, AL, I + 1, Ex, Idx))
1622 return;
1623
1624 // Is the function argument a pointer type?
1628 Ex->getSourceRange(),
1630 continue;
1631
1632 NonNullArgs.push_back(Idx);
1633 }
1634
1635 // If no arguments were specified to __attribute__((nonnull)) then all pointer
1636 // arguments have a nonnull attribute; warn if there aren't any. Skip this
1637 // check if the attribute came from a macro expansion or a template
1638 // instantiation.
1639 if (NonNullArgs.empty() && AL.getLoc().isFileID() &&
1641 bool AnyPointers = isFunctionOrMethodVariadic(D);
1642 for (unsigned I = 0, E = getFunctionOrMethodNumParams(D);
1643 I != E && !AnyPointers; ++I) {
1646 AnyPointers = true;
1647 }
1648
1649 if (!AnyPointers)
1650 S.Diag(AL.getLoc(), diag::warn_attribute_nonnull_no_pointers);
1651 }
1652
1653 ParamIdx *Start = NonNullArgs.data();
1654 unsigned Size = NonNullArgs.size();
1655 llvm::array_pod_sort(Start, Start + Size);
1656 D->addAttr(::new (S.Context) NonNullAttr(S.Context, AL, Start, Size));
1657}
1658
1660 const ParsedAttr &AL) {
1661 if (AL.getNumArgs() > 0) {
1662 if (D->getFunctionType()) {
1663 handleNonNullAttr(S, D, AL);
1664 } else {
1665 S.Diag(AL.getLoc(), diag::warn_attribute_nonnull_parm_no_args)
1666 << D->getSourceRange();
1667 }
1668 return;
1669 }
1670
1671 // Is the argument a pointer type?
1672 if (!attrNonNullArgCheck(S, D->getType(), AL, SourceRange(),
1673 D->getSourceRange()))
1674 return;
1675
1676 D->addAttr(::new (S.Context) NonNullAttr(S.Context, AL, nullptr, 0));
1677}
1678
1679static void handleReturnsNonNullAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1682 if (!attrNonNullArgCheck(S, ResultType, AL, SourceRange(), SR,
1683 /* isReturnValue */ true))
1684 return;
1685
1686 D->addAttr(::new (S.Context) ReturnsNonNullAttr(S.Context, AL));
1687}
1688
1689static void handleNoEscapeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1690 if (D->isInvalidDecl())
1691 return;
1692
1693 // noescape only applies to pointer types.
1694 QualType T = cast<ParmVarDecl>(D)->getType();
1695 if (!S.isValidPointerAttrType(T, /* RefOkay */ true)) {
1696 S.Diag(AL.getLoc(), diag::warn_attribute_pointers_only)
1697 << AL << AL.getRange() << 0;
1698 return;
1699 }
1700
1701 D->addAttr(::new (S.Context) NoEscapeAttr(S.Context, AL));
1702}
1703
1704static void handleAssumeAlignedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1705 Expr *E = AL.getArgAsExpr(0),
1706 *OE = AL.getNumArgs() > 1 ? AL.getArgAsExpr(1) : nullptr;
1707 S.AddAssumeAlignedAttr(D, AL, E, OE);
1708}
1709
1710static void handleAllocAlignAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1711 S.AddAllocAlignAttr(D, AL, AL.getArgAsExpr(0));
1712}
1713
1715 Expr *OE) {
1718
1719 AssumeAlignedAttr TmpAttr(Context, CI, E, OE);
1720 SourceLocation AttrLoc = TmpAttr.getLocation();
1721
1722 if (!isValidPointerAttrType(ResultType, /* RefOkay */ true)) {
1723 Diag(AttrLoc, diag::warn_attribute_return_pointers_refs_only)
1724 << &TmpAttr << TmpAttr.getRange() << SR;
1725 return;
1726 }
1727
1728 if (!E->isValueDependent()) {
1729 std::optional<llvm::APSInt> I = llvm::APSInt(64);
1730 if (!(I = E->getIntegerConstantExpr(Context))) {
1731 if (OE)
1732 Diag(AttrLoc, diag::err_attribute_argument_n_type)
1733 << &TmpAttr << 1 << AANT_ArgumentIntegerConstant
1734 << E->getSourceRange();
1735 else
1736 Diag(AttrLoc, diag::err_attribute_argument_type)
1737 << &TmpAttr << AANT_ArgumentIntegerConstant
1738 << E->getSourceRange();
1739 return;
1740 }
1741
1742 if (!I->isPowerOf2()) {
1743 Diag(AttrLoc, diag::err_alignment_not_power_of_two)
1744 << E->getSourceRange();
1745 return;
1746 }
1747
1748 if (*I > Sema::MaximumAlignment)
1749 Diag(CI.getLoc(), diag::warn_assume_aligned_too_great)
1751 }
1752
1753 if (OE && !OE->isValueDependent() && !OE->isIntegerConstantExpr(Context)) {
1754 Diag(AttrLoc, diag::err_attribute_argument_n_type)
1755 << &TmpAttr << 2 << AANT_ArgumentIntegerConstant
1756 << OE->getSourceRange();
1757 return;
1758 }
1759
1760 D->addAttr(::new (Context) AssumeAlignedAttr(Context, CI, E, OE));
1761}
1762
1764 Expr *ParamExpr) {
1766
1767 AllocAlignAttr TmpAttr(Context, CI, ParamIdx());
1768 SourceLocation AttrLoc = CI.getLoc();
1769
1770 if (!ResultType->isDependentType() &&
1771 !isValidPointerAttrType(ResultType, /* RefOkay */ true)) {
1772 Diag(AttrLoc, diag::warn_attribute_return_pointers_refs_only)
1773 << &TmpAttr << CI.getRange() << getFunctionOrMethodResultSourceRange(D);
1774 return;
1775 }
1776
1777 ParamIdx Idx;
1778 const auto *FuncDecl = cast<FunctionDecl>(D);
1779 if (!checkFunctionOrMethodParameterIndex(*this, FuncDecl, TmpAttr,
1780 /*AttrArgNum=*/1, ParamExpr, Idx))
1781 return;
1782
1784 if (!Ty->isDependentType() && !Ty->isIntegralType(Context) &&
1785 !Ty->isAlignValT()) {
1786 Diag(ParamExpr->getBeginLoc(), diag::err_attribute_integers_only)
1787 << &TmpAttr
1788 << FuncDecl->getParamDecl(Idx.getASTIndex())->getSourceRange();
1789 return;
1790 }
1791
1792 D->addAttr(::new (Context) AllocAlignAttr(Context, CI, Idx));
1793}
1794
1795/// Check if \p AssumptionStr is a known assumption and warn if not.
1797 StringRef AssumptionStr) {
1798 if (llvm::KnownAssumptionStrings.count(AssumptionStr))
1799 return;
1800
1801 unsigned BestEditDistance = 3;
1802 StringRef Suggestion;
1803 for (const auto &KnownAssumptionIt : llvm::KnownAssumptionStrings) {
1804 unsigned EditDistance =
1805 AssumptionStr.edit_distance(KnownAssumptionIt.getKey());
1806 if (EditDistance < BestEditDistance) {
1807 Suggestion = KnownAssumptionIt.getKey();
1808 BestEditDistance = EditDistance;
1809 }
1810 }
1811
1812 if (!Suggestion.empty())
1813 S.Diag(Loc, diag::warn_omp_assume_attribute_string_unknown_suggested)
1814 << AssumptionStr << Suggestion;
1815 else
1816 S.Diag(Loc, diag::warn_omp_assume_attribute_string_unknown)
1817 << AssumptionStr;
1818}
1819
1820static void handleOMPAssumeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1821 // Handle the case where the attribute has a text message.
1822 StringRef Str;
1823 SourceLocation AttrStrLoc;
1824 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &AttrStrLoc))
1825 return;
1826
1827 checkOMPAssumeAttr(S, AttrStrLoc, Str);
1828
1829 D->addAttr(::new (S.Context) OMPAssumeAttr(S.Context, AL, Str));
1830}
1831
1832/// Normalize the attribute, __foo__ becomes foo.
1833/// Returns true if normalization was applied.
1834static bool normalizeName(StringRef &AttrName) {
1835 if (AttrName.size() > 4 && AttrName.starts_with("__") &&
1836 AttrName.ends_with("__")) {
1837 AttrName = AttrName.drop_front(2).drop_back(2);
1838 return true;
1839 }
1840 return false;
1841}
1842
1843static void handleOwnershipAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1844 // This attribute must be applied to a function declaration. The first
1845 // argument to the attribute must be an identifier, the name of the resource,
1846 // for example: malloc. The following arguments must be argument indexes, the
1847 // arguments must be of integer type for Returns, otherwise of pointer type.
1848 // The difference between Holds and Takes is that a pointer may still be used
1849 // after being held. free() should be __attribute((ownership_takes)), whereas
1850 // a list append function may well be __attribute((ownership_holds)).
1851
1852 if (!AL.isArgIdent(0)) {
1853 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
1854 << AL << 1 << AANT_ArgumentIdentifier;
1855 return;
1856 }
1857
1858 // Figure out our Kind.
1859 OwnershipAttr::OwnershipKind K =
1860 OwnershipAttr(S.Context, AL, nullptr, nullptr, 0).getOwnKind();
1861
1862 // Check arguments.
1863 switch (K) {
1864 case OwnershipAttr::Takes:
1865 case OwnershipAttr::Holds:
1866 if (AL.getNumArgs() < 2) {
1867 S.Diag(AL.getLoc(), diag::err_attribute_too_few_arguments) << AL << 2;
1868 return;
1869 }
1870 break;
1871 case OwnershipAttr::Returns:
1872 if (AL.getNumArgs() > 2) {
1873 S.Diag(AL.getLoc(), diag::err_attribute_too_many_arguments) << AL << 1;
1874 return;
1875 }
1876 break;
1877 }
1878
1880
1881 StringRef ModuleName = Module->getName();
1882 if (normalizeName(ModuleName)) {
1883 Module = &S.PP.getIdentifierTable().get(ModuleName);
1884 }
1885
1886 SmallVector<ParamIdx, 8> OwnershipArgs;
1887 for (unsigned i = 1; i < AL.getNumArgs(); ++i) {
1888 Expr *Ex = AL.getArgAsExpr(i);
1889 ParamIdx Idx;
1890 if (!checkFunctionOrMethodParameterIndex(S, D, AL, i, Ex, Idx))
1891 return;
1892
1893 // Is the function argument a pointer type?
1895 int Err = -1; // No error
1896 switch (K) {
1897 case OwnershipAttr::Takes:
1898 case OwnershipAttr::Holds:
1899 if (!T->isAnyPointerType() && !T->isBlockPointerType())
1900 Err = 0;
1901 break;
1902 case OwnershipAttr::Returns:
1903 if (!T->isIntegerType())
1904 Err = 1;
1905 break;
1906 }
1907 if (-1 != Err) {
1908 S.Diag(AL.getLoc(), diag::err_ownership_type) << AL << Err
1909 << Ex->getSourceRange();
1910 return;
1911 }
1912
1913 // Check we don't have a conflict with another ownership attribute.
1914 for (const auto *I : D->specific_attrs<OwnershipAttr>()) {
1915 // Cannot have two ownership attributes of different kinds for the same
1916 // index.
1917 if (I->getOwnKind() != K && llvm::is_contained(I->args(), Idx)) {
1918 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible)
1919 << AL << I
1920 << (AL.isRegularKeywordAttribute() ||
1921 I->isRegularKeywordAttribute());
1922 return;
1923 } else if (K == OwnershipAttr::Returns &&
1924 I->getOwnKind() == OwnershipAttr::Returns) {
1925 // A returns attribute conflicts with any other returns attribute using
1926 // a different index.
1927 if (!llvm::is_contained(I->args(), Idx)) {
1928 S.Diag(I->getLocation(), diag::err_ownership_returns_index_mismatch)
1929 << I->args_begin()->getSourceIndex();
1930 if (I->args_size())
1931 S.Diag(AL.getLoc(), diag::note_ownership_returns_index_mismatch)
1932 << Idx.getSourceIndex() << Ex->getSourceRange();
1933 return;
1934 }
1935 }
1936 }
1937 OwnershipArgs.push_back(Idx);
1938 }
1939
1940 ParamIdx *Start = OwnershipArgs.data();
1941 unsigned Size = OwnershipArgs.size();
1942 llvm::array_pod_sort(Start, Start + Size);
1943 D->addAttr(::new (S.Context)
1944 OwnershipAttr(S.Context, AL, Module, Start, Size));
1945}
1946
1947static void handleWeakRefAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
1948 // Check the attribute arguments.
1949 if (AL.getNumArgs() > 1) {
1950 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << AL << 1;
1951 return;
1952 }
1953
1954 // gcc rejects
1955 // class c {
1956 // static int a __attribute__((weakref ("v2")));
1957 // static int b() __attribute__((weakref ("f3")));
1958 // };
1959 // and ignores the attributes of
1960 // void f(void) {
1961 // static int a __attribute__((weakref ("v2")));
1962 // }
1963 // we reject them
1964 const DeclContext *Ctx = D->getDeclContext()->getRedeclContext();
1965 if (!Ctx->isFileContext()) {
1966 S.Diag(AL.getLoc(), diag::err_attribute_weakref_not_global_context)
1967 << cast<NamedDecl>(D);
1968 return;
1969 }
1970
1971 // The GCC manual says
1972 //
1973 // At present, a declaration to which `weakref' is attached can only
1974 // be `static'.
1975 //
1976 // It also says
1977 //
1978 // Without a TARGET,
1979 // given as an argument to `weakref' or to `alias', `weakref' is
1980 // equivalent to `weak'.
1981 //
1982 // gcc 4.4.1 will accept
1983 // int a7 __attribute__((weakref));
1984 // as
1985 // int a7 __attribute__((weak));
1986 // This looks like a bug in gcc. We reject that for now. We should revisit
1987 // it if this behaviour is actually used.
1988
1989 // GCC rejects
1990 // static ((alias ("y"), weakref)).
1991 // Should we? How to check that weakref is before or after alias?
1992
1993 // FIXME: it would be good for us to keep the WeakRefAttr as-written instead
1994 // of transforming it into an AliasAttr. The WeakRefAttr never uses the
1995 // StringRef parameter it was given anyway.
1996 StringRef Str;
1997 if (AL.getNumArgs() && S.checkStringLiteralArgumentAttr(AL, 0, Str))
1998 // GCC will accept anything as the argument of weakref. Should we
1999 // check for an existing decl?
2000 D->addAttr(::new (S.Context) AliasAttr(S.Context, AL, Str));
2001
2002 D->addAttr(::new (S.Context) WeakRefAttr(S.Context, AL));
2003}
2004
2005// Mark alias/ifunc target as used. Due to name mangling, we look up the
2006// demangled name ignoring parameters (not supported by microsoftDemangle
2007// https://github.com/llvm/llvm-project/issues/88825). This should handle the
2008// majority of use cases while leaving namespace scope names unmarked.
2009static void markUsedForAliasOrIfunc(Sema &S, Decl *D, const ParsedAttr &AL,
2010 StringRef Str) {
2011 std::unique_ptr<char, llvm::FreeDeleter> Demangled;
2012 if (S.getASTContext().getCXXABIKind() != TargetCXXABI::Microsoft)
2013 Demangled.reset(llvm::itaniumDemangle(Str, /*ParseParams=*/false));
2014 std::unique_ptr<MangleContext> MC(S.Context.createMangleContext());
2015 SmallString<256> Name;
2016
2018 &S.Context.Idents.get(Demangled ? Demangled.get() : Str), AL.getLoc());
2020 if (S.LookupName(LR, S.TUScope)) {
2021 for (NamedDecl *ND : LR) {
2022 if (!isa<FunctionDecl>(ND) && !isa<VarDecl>(ND))
2023 continue;
2024 if (MC->shouldMangleDeclName(ND)) {
2025 llvm::raw_svector_ostream Out(Name);
2026 Name.clear();
2027 MC->mangleName(GlobalDecl(ND), Out);
2028 } else {
2029 Name = ND->getIdentifier()->getName();
2030 }
2031 if (Name == Str)
2032 ND->markUsed(S.Context);
2033 }
2034 }
2035}
2036
2037static void handleIFuncAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2038 StringRef Str;
2039 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str))
2040 return;
2041
2042 // Aliases should be on declarations, not definitions.
2043 const auto *FD = cast<FunctionDecl>(D);
2044 if (FD->isThisDeclarationADefinition()) {
2045 S.Diag(AL.getLoc(), diag::err_alias_is_definition) << FD << 1;
2046 return;
2047 }
2048
2049 markUsedForAliasOrIfunc(S, D, AL, Str);
2050 D->addAttr(::new (S.Context) IFuncAttr(S.Context, AL, Str));
2051}
2052
2053static void handleAliasAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2054 StringRef Str;
2055 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str))
2056 return;
2057
2058 if (S.Context.getTargetInfo().getTriple().isOSDarwin()) {
2059 S.Diag(AL.getLoc(), diag::err_alias_not_supported_on_darwin);
2060 return;
2061 }
2062
2063 if (S.Context.getTargetInfo().getTriple().isNVPTX()) {
2064 CudaVersion Version =
2066 if (Version != CudaVersion::UNKNOWN && Version < CudaVersion::CUDA_100)
2067 S.Diag(AL.getLoc(), diag::err_alias_not_supported_on_nvptx);
2068 }
2069
2070 // Aliases should be on declarations, not definitions.
2071 if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
2072 if (FD->isThisDeclarationADefinition()) {
2073 S.Diag(AL.getLoc(), diag::err_alias_is_definition) << FD << 0;
2074 return;
2075 }
2076 } else {
2077 const auto *VD = cast<VarDecl>(D);
2078 if (VD->isThisDeclarationADefinition() && VD->isExternallyVisible()) {
2079 S.Diag(AL.getLoc(), diag::err_alias_is_definition) << VD << 0;
2080 return;
2081 }
2082 }
2083
2084 markUsedForAliasOrIfunc(S, D, AL, Str);
2085 D->addAttr(::new (S.Context) AliasAttr(S.Context, AL, Str));
2086}
2087
2088static void handleTLSModelAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2089 StringRef Model;
2090 SourceLocation LiteralLoc;
2091 // Check that it is a string.
2092 if (!S.checkStringLiteralArgumentAttr(AL, 0, Model, &LiteralLoc))
2093 return;
2094
2095 // Check that the value.
2096 if (Model != "global-dynamic" && Model != "local-dynamic"
2097 && Model != "initial-exec" && Model != "local-exec") {
2098 S.Diag(LiteralLoc, diag::err_attr_tlsmodel_arg);
2099 return;
2100 }
2101
2102 D->addAttr(::new (S.Context) TLSModelAttr(S.Context, AL, Model));
2103}
2104
2105static void handleRestrictAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2107 if (ResultType->isAnyPointerType() || ResultType->isBlockPointerType()) {
2108 D->addAttr(::new (S.Context) RestrictAttr(S.Context, AL));
2109 return;
2110 }
2111
2112 S.Diag(AL.getLoc(), diag::warn_attribute_return_pointers_only)
2114}
2115
2116static void handleCPUSpecificAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2117 // Ensure we don't combine these with themselves, since that causes some
2118 // confusing behavior.
2119 if (AL.getParsedKind() == ParsedAttr::AT_CPUDispatch) {
2120 if (checkAttrMutualExclusion<CPUSpecificAttr>(S, D, AL))
2121 return;
2122
2123 if (const auto *Other = D->getAttr<CPUDispatchAttr>()) {
2124 S.Diag(AL.getLoc(), diag::err_disallowed_duplicate_attribute) << AL;
2125 S.Diag(Other->getLocation(), diag::note_conflicting_attribute);
2126 return;
2127 }
2128 } else if (AL.getParsedKind() == ParsedAttr::AT_CPUSpecific) {
2129 if (checkAttrMutualExclusion<CPUDispatchAttr>(S, D, AL))
2130 return;
2131
2132 if (const auto *Other = D->getAttr<CPUSpecificAttr>()) {
2133 S.Diag(AL.getLoc(), diag::err_disallowed_duplicate_attribute) << AL;
2134 S.Diag(Other->getLocation(), diag::note_conflicting_attribute);
2135 return;
2136 }
2137 }
2138
2139 FunctionDecl *FD = cast<FunctionDecl>(D);
2140
2141 if (const auto *MD = dyn_cast<CXXMethodDecl>(D)) {
2142 if (MD->getParent()->isLambda()) {
2143 S.Diag(AL.getLoc(), diag::err_attribute_dll_lambda) << AL;
2144 return;
2145 }
2146 }
2147
2148 if (!AL.checkAtLeastNumArgs(S, 1))
2149 return;
2150
2152 for (unsigned ArgNo = 0; ArgNo < getNumAttributeArgs(AL); ++ArgNo) {
2153 if (!AL.isArgIdent(ArgNo)) {
2154 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
2155 << AL << AANT_ArgumentIdentifier;
2156 return;
2157 }
2158
2159 IdentifierLoc *CPUArg = AL.getArgAsIdent(ArgNo);
2160 StringRef CPUName = CPUArg->Ident->getName().trim();
2161
2163 S.Diag(CPUArg->Loc, diag::err_invalid_cpu_specific_dispatch_value)
2164 << CPUName << (AL.getKind() == ParsedAttr::AT_CPUDispatch);
2165 return;
2166 }
2167
2169 if (llvm::any_of(CPUs, [CPUName, &Target](const IdentifierInfo *Cur) {
2170 return Target.CPUSpecificManglingCharacter(CPUName) ==
2171 Target.CPUSpecificManglingCharacter(Cur->getName());
2172 })) {
2173 S.Diag(AL.getLoc(), diag::warn_multiversion_duplicate_entries);
2174 return;
2175 }
2176 CPUs.push_back(CPUArg->Ident);
2177 }
2178
2179 FD->setIsMultiVersion(true);
2180 if (AL.getKind() == ParsedAttr::AT_CPUSpecific)
2181 D->addAttr(::new (S.Context)
2182 CPUSpecificAttr(S.Context, AL, CPUs.data(), CPUs.size()));
2183 else
2184 D->addAttr(::new (S.Context)
2185 CPUDispatchAttr(S.Context, AL, CPUs.data(), CPUs.size()));
2186}
2187
2188static void handleCommonAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2189 if (S.LangOpts.CPlusPlus) {
2190 S.Diag(AL.getLoc(), diag::err_attribute_not_supported_in_lang)
2192 return;
2193 }
2194
2195 D->addAttr(::new (S.Context) CommonAttr(S.Context, AL));
2196}
2197
2198static void handleCmseNSEntryAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2199 if (S.LangOpts.CPlusPlus && !D->getDeclContext()->isExternCContext()) {
2200 S.Diag(AL.getLoc(), diag::err_attribute_not_clinkage) << AL;
2201 return;
2202 }
2203
2204 const auto *FD = cast<FunctionDecl>(D);
2205 if (!FD->isExternallyVisible()) {
2206 S.Diag(AL.getLoc(), diag::warn_attribute_cmse_entry_static);
2207 return;
2208 }
2209
2210 D->addAttr(::new (S.Context) CmseNSEntryAttr(S.Context, AL));
2211}
2212
2213static void handleNakedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2214 if (AL.isDeclspecAttribute()) {
2215 const auto &Triple = S.getASTContext().getTargetInfo().getTriple();
2216 const auto &Arch = Triple.getArch();
2217 if (Arch != llvm::Triple::x86 &&
2218 (Arch != llvm::Triple::arm && Arch != llvm::Triple::thumb)) {
2219 S.Diag(AL.getLoc(), diag::err_attribute_not_supported_on_arch)
2220 << AL << Triple.getArchName();
2221 return;
2222 }
2223
2224 // This form is not allowed to be written on a member function (static or
2225 // nonstatic) when in Microsoft compatibility mode.
2226 if (S.getLangOpts().MSVCCompat && isa<CXXMethodDecl>(D)) {
2227 S.Diag(AL.getLoc(), diag::err_attribute_wrong_decl_type_str)
2228 << AL << AL.isRegularKeywordAttribute() << "non-member functions";
2229 return;
2230 }
2231 }
2232
2233 D->addAttr(::new (S.Context) NakedAttr(S.Context, AL));
2234}
2235
2236static void handleNoReturnAttr(Sema &S, Decl *D, const ParsedAttr &Attrs) {
2237 if (hasDeclarator(D)) return;
2238
2239 if (!isa<ObjCMethodDecl>(D)) {
2240 S.Diag(Attrs.getLoc(), diag::warn_attribute_wrong_decl_type)
2241 << Attrs << Attrs.isRegularKeywordAttribute()
2243 return;
2244 }
2245
2246 D->addAttr(::new (S.Context) NoReturnAttr(S.Context, Attrs));
2247}
2248
2249static void handleStandardNoReturnAttr(Sema &S, Decl *D, const ParsedAttr &A) {
2250 // The [[_Noreturn]] spelling is deprecated in C23, so if that was used,
2251 // issue an appropriate diagnostic. However, don't issue a diagnostic if the
2252 // attribute name comes from a macro expansion. We don't want to punish users
2253 // who write [[noreturn]] after including <stdnoreturn.h> (where 'noreturn'
2254 // is defined as a macro which expands to '_Noreturn').
2255 if (!S.getLangOpts().CPlusPlus &&
2256 A.getSemanticSpelling() == CXX11NoReturnAttr::C23_Noreturn &&
2257 !(A.getLoc().isMacroID() &&
2259 S.Diag(A.getLoc(), diag::warn_deprecated_noreturn_spelling) << A.getRange();
2260
2261 D->addAttr(::new (S.Context) CXX11NoReturnAttr(S.Context, A));
2262}
2263
2264static void handleNoCfCheckAttr(Sema &S, Decl *D, const ParsedAttr &Attrs) {
2265 if (!S.getLangOpts().CFProtectionBranch)
2266 S.Diag(Attrs.getLoc(), diag::warn_nocf_check_attribute_ignored);
2267 else
2268 handleSimpleAttribute<AnyX86NoCfCheckAttr>(S, D, Attrs);
2269}
2270
2272 if (!Attrs.checkExactlyNumArgs(*this, 0)) {
2273 Attrs.setInvalid();
2274 return true;
2275 }
2276
2277 return false;
2278}
2279
2281 // Check whether the attribute is valid on the current target.
2284 ? diag::err_keyword_not_supported_on_target
2285 : diag::warn_unknown_attribute_ignored)
2286 << AL << AL.getRange();
2287 AL.setInvalid();
2288 return true;
2289 }
2290
2291 return false;
2292}
2293
2294static void handleAnalyzerNoReturnAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2295
2296 // The checking path for 'noreturn' and 'analyzer_noreturn' are different
2297 // because 'analyzer_noreturn' does not impact the type.
2298 if (!isFunctionOrMethodOrBlock(D)) {
2299 ValueDecl *VD = dyn_cast<ValueDecl>(D);
2300 if (!VD || (!VD->getType()->isBlockPointerType() &&
2301 !VD->getType()->isFunctionPointerType())) {
2303 ? diag::err_attribute_wrong_decl_type
2304 : diag::warn_attribute_wrong_decl_type)
2305 << AL << AL.isRegularKeywordAttribute()
2307 return;
2308 }
2309 }
2310
2311 D->addAttr(::new (S.Context) AnalyzerNoReturnAttr(S.Context, AL));
2312}
2313
2314// PS3 PPU-specific.
2315static void handleVecReturnAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2316 /*
2317 Returning a Vector Class in Registers
2318
2319 According to the PPU ABI specifications, a class with a single member of
2320 vector type is returned in memory when used as the return value of a
2321 function.
2322 This results in inefficient code when implementing vector classes. To return
2323 the value in a single vector register, add the vecreturn attribute to the
2324 class definition. This attribute is also applicable to struct types.
2325
2326 Example:
2327
2328 struct Vector
2329 {
2330 __vector float xyzw;
2331 } __attribute__((vecreturn));
2332
2333 Vector Add(Vector lhs, Vector rhs)
2334 {
2335 Vector result;
2336 result.xyzw = vec_add(lhs.xyzw, rhs.xyzw);
2337 return result; // This will be returned in a register
2338 }
2339 */
2340 if (VecReturnAttr *A = D->getAttr<VecReturnAttr>()) {
2341 S.Diag(AL.getLoc(), diag::err_repeat_attribute) << A;
2342 return;
2343 }
2344
2345 const auto *R = cast<RecordDecl>(D);
2346 int count = 0;
2347
2348 if (!isa<CXXRecordDecl>(R)) {
2349 S.Diag(AL.getLoc(), diag::err_attribute_vecreturn_only_vector_member);
2350 return;
2351 }
2352
2353 if (!cast<CXXRecordDecl>(R)->isPOD()) {
2354 S.Diag(AL.getLoc(), diag::err_attribute_vecreturn_only_pod_record);
2355 return;
2356 }
2357
2358 for (const auto *I : R->fields()) {
2359 if ((count == 1) || !I->getType()->isVectorType()) {
2360 S.Diag(AL.getLoc(), diag::err_attribute_vecreturn_only_vector_member);
2361 return;
2362 }
2363 count++;
2364 }
2365
2366 D->addAttr(::new (S.Context) VecReturnAttr(S.Context, AL));
2367}
2368
2370 const ParsedAttr &AL) {
2371 if (isa<ParmVarDecl>(D)) {
2372 // [[carries_dependency]] can only be applied to a parameter if it is a
2373 // parameter of a function declaration or lambda.
2375 S.Diag(AL.getLoc(),
2376 diag::err_carries_dependency_param_not_function_decl);
2377 return;
2378 }
2379 }
2380
2381 D->addAttr(::new (S.Context) CarriesDependencyAttr(S.Context, AL));
2382}
2383
2384static void handleUnusedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2385 bool IsCXX17Attr = AL.isCXX11Attribute() && !AL.getScopeName();
2386
2387 // If this is spelled as the standard C++17 attribute, but not in C++17, warn
2388 // about using it as an extension.
2389 if (!S.getLangOpts().CPlusPlus17 && IsCXX17Attr)
2390 S.Diag(AL.getLoc(), diag::ext_cxx17_attr) << AL;
2391
2392 D->addAttr(::new (S.Context) UnusedAttr(S.Context, AL));
2393}
2394
2395static void handleConstructorAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2396 uint32_t priority = ConstructorAttr::DefaultPriority;
2397 if (S.getLangOpts().HLSL && AL.getNumArgs()) {
2398 S.Diag(AL.getLoc(), diag::err_hlsl_init_priority_unsupported);
2399 return;
2400 }
2401 if (AL.getNumArgs() &&
2402 !checkUInt32Argument(S, AL, AL.getArgAsExpr(0), priority))
2403 return;
2404
2405 D->addAttr(::new (S.Context) ConstructorAttr(S.Context, AL, priority));
2406}
2407
2408static void handleDestructorAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2409 uint32_t priority = DestructorAttr::DefaultPriority;
2410 if (AL.getNumArgs() &&
2411 !checkUInt32Argument(S, AL, AL.getArgAsExpr(0), priority))
2412 return;
2413
2414 D->addAttr(::new (S.Context) DestructorAttr(S.Context, AL, priority));
2415}
2416
2417template <typename AttrTy>
2418static void handleAttrWithMessage(Sema &S, Decl *D, const ParsedAttr &AL) {
2419 // Handle the case where the attribute has a text message.
2420 StringRef Str;
2421 if (AL.getNumArgs() == 1 && !S.checkStringLiteralArgumentAttr(AL, 0, Str))
2422 return;
2423
2424 D->addAttr(::new (S.Context) AttrTy(S.Context, AL, Str));
2425}
2426
2428 const ParsedAttr &AL) {
2429 if (!cast<ObjCProtocolDecl>(D)->isThisDeclarationADefinition()) {
2430 S.Diag(AL.getLoc(), diag::err_objc_attr_protocol_requires_definition)
2431 << AL << AL.getRange();
2432 return;
2433 }
2434
2435 D->addAttr(::new (S.Context) ObjCExplicitProtocolImplAttr(S.Context, AL));
2436}
2437
2439 IdentifierInfo *Platform,
2440 VersionTuple Introduced,
2441 VersionTuple Deprecated,
2442 VersionTuple Obsoleted) {
2443 StringRef PlatformName
2444 = AvailabilityAttr::getPrettyPlatformName(Platform->getName());
2445 if (PlatformName.empty())
2446 PlatformName = Platform->getName();
2447
2448 // Ensure that Introduced <= Deprecated <= Obsoleted (although not all
2449 // of these steps are needed).
2450 if (!Introduced.empty() && !Deprecated.empty() &&
2451 !(Introduced <= Deprecated)) {
2452 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering)
2453 << 1 << PlatformName << Deprecated.getAsString()
2454 << 0 << Introduced.getAsString();
2455 return true;
2456 }
2457
2458 if (!Introduced.empty() && !Obsoleted.empty() &&
2459 !(Introduced <= Obsoleted)) {
2460 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering)
2461 << 2 << PlatformName << Obsoleted.getAsString()
2462 << 0 << Introduced.getAsString();
2463 return true;
2464 }
2465
2466 if (!Deprecated.empty() && !Obsoleted.empty() &&
2467 !(Deprecated <= Obsoleted)) {
2468 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering)
2469 << 2 << PlatformName << Obsoleted.getAsString()
2470 << 1 << Deprecated.getAsString();
2471 return true;
2472 }
2473
2474 return false;
2475}
2476
2477/// Check whether the two versions match.
2478///
2479/// If either version tuple is empty, then they are assumed to match. If
2480/// \p BeforeIsOkay is true, then \p X can be less than or equal to \p Y.
2481static bool versionsMatch(const VersionTuple &X, const VersionTuple &Y,
2482 bool BeforeIsOkay) {
2483 if (X.empty() || Y.empty())
2484 return true;
2485
2486 if (X == Y)
2487 return true;
2488
2489 if (BeforeIsOkay && X < Y)
2490 return true;
2491
2492 return false;
2493}
2494
2496 NamedDecl *D, const AttributeCommonInfo &CI, IdentifierInfo *Platform,
2497 bool Implicit, VersionTuple Introduced, VersionTuple Deprecated,
2498 VersionTuple Obsoleted, bool IsUnavailable, StringRef Message,
2499 bool IsStrict, StringRef Replacement, AvailabilityMergeKind AMK,
2500 int Priority, IdentifierInfo *Environment) {
2501 VersionTuple MergedIntroduced = Introduced;
2502 VersionTuple MergedDeprecated = Deprecated;
2503 VersionTuple MergedObsoleted = Obsoleted;
2504 bool FoundAny = false;
2505 bool OverrideOrImpl = false;
2506 switch (AMK) {
2507 case AMK_None:
2508 case AMK_Redeclaration:
2509 OverrideOrImpl = false;
2510 break;
2511
2512 case AMK_Override:
2515 OverrideOrImpl = true;
2516 break;
2517 }
2518
2519 if (D->hasAttrs()) {
2520 AttrVec &Attrs = D->getAttrs();
2521 for (unsigned i = 0, e = Attrs.size(); i != e;) {
2522 const auto *OldAA = dyn_cast<AvailabilityAttr>(Attrs[i]);
2523 if (!OldAA) {
2524 ++i;
2525 continue;
2526 }
2527
2528 IdentifierInfo *OldPlatform = OldAA->getPlatform();
2529 if (OldPlatform != Platform) {
2530 ++i;
2531 continue;
2532 }
2533
2534 IdentifierInfo *OldEnvironment = OldAA->getEnvironment();
2535 if (OldEnvironment != Environment) {
2536 ++i;
2537 continue;
2538 }
2539
2540 // If there is an existing availability attribute for this platform that
2541 // has a lower priority use the existing one and discard the new
2542 // attribute.
2543 if (OldAA->getPriority() < Priority)
2544 return nullptr;
2545
2546 // If there is an existing attribute for this platform that has a higher
2547 // priority than the new attribute then erase the old one and continue
2548 // processing the attributes.
2549 if (OldAA->getPriority() > Priority) {
2550 Attrs.erase(Attrs.begin() + i);
2551 --e;
2552 continue;
2553 }
2554
2555 FoundAny = true;
2556 VersionTuple OldIntroduced = OldAA->getIntroduced();
2557 VersionTuple OldDeprecated = OldAA->getDeprecated();
2558 VersionTuple OldObsoleted = OldAA->getObsoleted();
2559 bool OldIsUnavailable = OldAA->getUnavailable();
2560
2561 if (!versionsMatch(OldIntroduced, Introduced, OverrideOrImpl) ||
2562 !versionsMatch(Deprecated, OldDeprecated, OverrideOrImpl) ||
2563 !versionsMatch(Obsoleted, OldObsoleted, OverrideOrImpl) ||
2564 !(OldIsUnavailable == IsUnavailable ||
2565 (OverrideOrImpl && !OldIsUnavailable && IsUnavailable))) {
2566 if (OverrideOrImpl) {
2567 int Which = -1;
2568 VersionTuple FirstVersion;
2569 VersionTuple SecondVersion;
2570 if (!versionsMatch(OldIntroduced, Introduced, OverrideOrImpl)) {
2571 Which = 0;
2572 FirstVersion = OldIntroduced;
2573 SecondVersion = Introduced;
2574 } else if (!versionsMatch(Deprecated, OldDeprecated, OverrideOrImpl)) {
2575 Which = 1;
2576 FirstVersion = Deprecated;
2577 SecondVersion = OldDeprecated;
2578 } else if (!versionsMatch(Obsoleted, OldObsoleted, OverrideOrImpl)) {
2579 Which = 2;
2580 FirstVersion = Obsoleted;
2581 SecondVersion = OldObsoleted;
2582 }
2583
2584 if (Which == -1) {
2585 Diag(OldAA->getLocation(),
2586 diag::warn_mismatched_availability_override_unavail)
2587 << AvailabilityAttr::getPrettyPlatformName(Platform->getName())
2588 << (AMK == AMK_Override);
2589 } else if (Which != 1 && AMK == AMK_OptionalProtocolImplementation) {
2590 // Allow different 'introduced' / 'obsoleted' availability versions
2591 // on a method that implements an optional protocol requirement. It
2592 // makes less sense to allow this for 'deprecated' as the user can't
2593 // see if the method is 'deprecated' as 'respondsToSelector' will
2594 // still return true when the method is deprecated.
2595 ++i;
2596 continue;
2597 } else {
2598 Diag(OldAA->getLocation(),
2599 diag::warn_mismatched_availability_override)
2600 << Which
2601 << AvailabilityAttr::getPrettyPlatformName(Platform->getName())
2602 << FirstVersion.getAsString() << SecondVersion.getAsString()
2603 << (AMK == AMK_Override);
2604 }
2605 if (AMK == AMK_Override)
2606 Diag(CI.getLoc(), diag::note_overridden_method);
2607 else
2608 Diag(CI.getLoc(), diag::note_protocol_method);
2609 } else {
2610 Diag(OldAA->getLocation(), diag::warn_mismatched_availability);
2611 Diag(CI.getLoc(), diag::note_previous_attribute);
2612 }
2613
2614 Attrs.erase(Attrs.begin() + i);
2615 --e;
2616 continue;
2617 }
2618
2619 VersionTuple MergedIntroduced2 = MergedIntroduced;
2620 VersionTuple MergedDeprecated2 = MergedDeprecated;
2621 VersionTuple MergedObsoleted2 = MergedObsoleted;
2622
2623 if (MergedIntroduced2.empty())
2624 MergedIntroduced2 = OldIntroduced;
2625 if (MergedDeprecated2.empty())
2626 MergedDeprecated2 = OldDeprecated;
2627 if (MergedObsoleted2.empty())
2628 MergedObsoleted2 = OldObsoleted;
2629
2630 if (checkAvailabilityAttr(*this, OldAA->getRange(), Platform,
2631 MergedIntroduced2, MergedDeprecated2,
2632 MergedObsoleted2)) {
2633 Attrs.erase(Attrs.begin() + i);
2634 --e;
2635 continue;
2636 }
2637
2638 MergedIntroduced = MergedIntroduced2;
2639 MergedDeprecated = MergedDeprecated2;
2640 MergedObsoleted = MergedObsoleted2;
2641 ++i;
2642 }
2643 }
2644
2645 if (FoundAny &&
2646 MergedIntroduced == Introduced &&
2647 MergedDeprecated == Deprecated &&
2648 MergedObsoleted == Obsoleted)
2649 return nullptr;
2650
2651 // Only create a new attribute if !OverrideOrImpl, but we want to do
2652 // the checking.
2653 if (!checkAvailabilityAttr(*this, CI.getRange(), Platform, MergedIntroduced,
2654 MergedDeprecated, MergedObsoleted) &&
2655 !OverrideOrImpl) {
2656 auto *Avail = ::new (Context) AvailabilityAttr(
2657 Context, CI, Platform, Introduced, Deprecated, Obsoleted, IsUnavailable,
2658 Message, IsStrict, Replacement, Priority, Environment);
2659 Avail->setImplicit(Implicit);
2660 return Avail;
2661 }
2662 return nullptr;
2663}
2664
2665static void handleAvailabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
2666 if (isa<UsingDecl, UnresolvedUsingTypenameDecl, UnresolvedUsingValueDecl>(
2667 D)) {
2668 S.Diag(AL.getRange().getBegin(), diag::warn_deprecated_ignored_on_using)
2669 << AL;
2670 return;
2671 }
2672
2673 if (!AL.checkExactlyNumArgs(S, 1))
2674 return;
2675 IdentifierLoc *Platform = AL.getArgAsIdent(0);
2676
2677 IdentifierInfo *II = Platform->Ident;
2678 if (AvailabilityAttr::getPrettyPlatformName(II->getName()).empty())
2679 S.Diag(Platform->Loc, diag::warn_availability_unknown_platform)
2680 << Platform->Ident;
2681
2682 auto *ND = dyn_cast<NamedDecl>(D);
2683 if (!ND) // We warned about this already, so just return.
2684 return;
2685
2689 bool IsUnavailable = AL.getUnavailableLoc().isValid();
2690 bool IsStrict = AL.getStrictLoc().isValid();
2691 StringRef Str;
2692 if (const auto *SE = dyn_cast_if_present<StringLiteral>(AL.getMessageExpr()))
2693 Str = SE->getString();
2694 StringRef Replacement;
2695 if (const auto *SE =
2696 dyn_cast_if_present<StringLiteral>(AL.getReplacementExpr()))
2697 Replacement = SE->getString();
2698
2699 if (II->isStr("swift")) {
2700 if (Introduced.isValid() || Obsoleted.isValid() ||
2701 (!IsUnavailable && !Deprecated.isValid())) {
2702 S.Diag(AL.getLoc(),
2703 diag::warn_availability_swift_unavailable_deprecated_only);
2704 return;
2705 }
2706 }
2707
2708 if (II->isStr("fuchsia")) {
2709 std::optional<unsigned> Min, Sub;
2710 if ((Min = Introduced.Version.getMinor()) ||
2711 (Sub = Introduced.Version.getSubminor())) {
2712 S.Diag(AL.getLoc(), diag::warn_availability_fuchsia_unavailable_minor);
2713 return;
2714 }
2715 }
2716
2717 if (S.getLangOpts().HLSL && IsStrict)
2718 S.Diag(AL.getStrictLoc(), diag::err_availability_unexpected_parameter)
2719 << "strict" << /* HLSL */ 0;
2720
2721 int PriorityModifier = AL.isPragmaClangAttribute()
2724
2725 const IdentifierLoc *EnvironmentLoc = AL.getEnvironment();
2726 IdentifierInfo *IIEnvironment = nullptr;
2727 if (EnvironmentLoc) {
2728 if (S.getLangOpts().HLSL) {
2729 IIEnvironment = EnvironmentLoc->Ident;
2730 if (AvailabilityAttr::getEnvironmentType(
2731 EnvironmentLoc->Ident->getName()) ==
2732 llvm::Triple::EnvironmentType::UnknownEnvironment)
2733 S.Diag(EnvironmentLoc->Loc, diag::warn_availability_unknown_environment)
2734 << EnvironmentLoc->Ident;
2735 } else {
2736 S.Diag(EnvironmentLoc->Loc, diag::err_availability_unexpected_parameter)
2737 << "environment" << /* C/C++ */ 1;
2738 }
2739 }
2740
2741 AvailabilityAttr *NewAttr = S.mergeAvailabilityAttr(
2742 ND, AL, II, false /*Implicit*/, Introduced.Version, Deprecated.Version,
2743 Obsoleted.Version, IsUnavailable, Str, IsStrict, Replacement,
2744 Sema::AMK_None, PriorityModifier, IIEnvironment);
2745 if (NewAttr)
2746 D->addAttr(NewAttr);
2747
2748 // Transcribe "ios" to "watchos" (and add a new attribute) if the versioning
2749 // matches before the start of the watchOS platform.
2750 if (S.Context.getTargetInfo().getTriple().isWatchOS()) {
2751 IdentifierInfo *NewII = nullptr;
2752 if (II->getName() == "ios")
2753 NewII = &S.Context.Idents.get("watchos");
2754 else if (II->getName() == "ios_app_extension")
2755 NewII = &S.Context.Idents.get("watchos_app_extension");
2756
2757 if (NewII) {
2758 const auto *SDKInfo = S.getDarwinSDKInfoForAvailabilityChecking();
2759 const auto *IOSToWatchOSMapping =
2760 SDKInfo ? SDKInfo->getVersionMapping(
2762 : nullptr;
2763
2764 auto adjustWatchOSVersion =
2765 [IOSToWatchOSMapping](VersionTuple Version) -> VersionTuple {
2766 if (Version.empty())
2767 return Version;
2768 auto MinimumWatchOSVersion = VersionTuple(2, 0);
2769
2770 if (IOSToWatchOSMapping) {
2771 if (auto MappedVersion = IOSToWatchOSMapping->map(
2772 Version, MinimumWatchOSVersion, std::nullopt)) {
2773 return *MappedVersion;
2774 }
2775 }
2776
2777 auto Major = Version.getMajor();
2778 auto NewMajor = Major >= 9 ? Major - 7 : 0;
2779 if (NewMajor >= 2) {
2780 if (Version.getMinor()) {
2781 if (Version.getSubminor())
2782 return VersionTuple(NewMajor, *Version.getMinor(),
2783 *Version.getSubminor());
2784 else
2785 return VersionTuple(NewMajor, *Version.getMinor());
2786 }
2787 return VersionTuple(NewMajor);
2788 }
2789
2790 return MinimumWatchOSVersion;
2791 };
2792
2793 auto NewIntroduced = adjustWatchOSVersion(Introduced.Version);
2794 auto NewDeprecated = adjustWatchOSVersion(Deprecated.Version);
2795 auto NewObsoleted = adjustWatchOSVersion(Obsoleted.Version);
2796
2797 AvailabilityAttr *NewAttr = S.mergeAvailabilityAttr(
2798 ND, AL, NewII, true /*Implicit*/, NewIntroduced, NewDeprecated,
2799 NewObsoleted, IsUnavailable, Str, IsStrict, Replacement,
2801 IIEnvironment);
2802 if (NewAttr)
2803 D->addAttr(NewAttr);
2804 }
2805 } else if (S.Context.getTargetInfo().getTriple().isTvOS()) {
2806 // Transcribe "ios" to "tvos" (and add a new attribute) if the versioning
2807 // matches before the start of the tvOS platform.
2808 IdentifierInfo *NewII = nullptr;
2809 if (II->getName() == "ios")
2810 NewII = &S.Context.Idents.get("tvos");
2811 else if (II->getName() == "ios_app_extension")
2812 NewII = &S.Context.Idents.get("tvos_app_extension");
2813
2814 if (NewII) {
2815 const auto *SDKInfo = S.getDarwinSDKInfoForAvailabilityChecking();
2816 const auto *IOSToTvOSMapping =
2817 SDKInfo ? SDKInfo->getVersionMapping(
2819 : nullptr;
2820
2821 auto AdjustTvOSVersion =
2822 [IOSToTvOSMapping](VersionTuple Version) -> VersionTuple {
2823 if (Version.empty())
2824 return Version;
2825
2826 if (IOSToTvOSMapping) {
2827 if (auto MappedVersion = IOSToTvOSMapping->map(
2828 Version, VersionTuple(0, 0), std::nullopt)) {
2829 return *MappedVersion;
2830 }
2831 }
2832 return Version;
2833 };
2834
2835 auto NewIntroduced = AdjustTvOSVersion(Introduced.Version);
2836 auto NewDeprecated = AdjustTvOSVersion(Deprecated.Version);
2837 auto NewObsoleted = AdjustTvOSVersion(Obsoleted.Version);
2838
2839 AvailabilityAttr *NewAttr = S.mergeAvailabilityAttr(
2840 ND, AL, NewII, true /*Implicit*/, NewIntroduced, NewDeprecated,
2841 NewObsoleted, IsUnavailable, Str, IsStrict, Replacement,
2843 IIEnvironment);
2844 if (NewAttr)
2845 D->addAttr(NewAttr);
2846 }
2847 } else if (S.Context.getTargetInfo().getTriple().getOS() ==
2848 llvm::Triple::IOS &&
2849 S.Context.getTargetInfo().getTriple().isMacCatalystEnvironment()) {
2850 auto GetSDKInfo = [&]() {
2852 "macOS");
2853 };
2854
2855 // Transcribe "ios" to "maccatalyst" (and add a new attribute).
2856 IdentifierInfo *NewII = nullptr;
2857 if (II->getName() == "ios")
2858 NewII = &S.Context.Idents.get("maccatalyst");
2859 else if (II->getName() == "ios_app_extension")
2860 NewII = &S.Context.Idents.get("maccatalyst_app_extension");
2861 if (NewII) {
2862 auto MinMacCatalystVersion = [](const VersionTuple &V) {
2863 if (V.empty())
2864 return V;
2865 if (V.getMajor() < 13 ||
2866 (V.getMajor() == 13 && V.getMinor() && *V.getMinor() < 1))
2867 return VersionTuple(13, 1); // The min Mac Catalyst version is 13.1.
2868 return V;
2869 };
2870 AvailabilityAttr *NewAttr = S.mergeAvailabilityAttr(
2871 ND, AL, NewII, true /*Implicit*/,
2872 MinMacCatalystVersion(Introduced.Version),
2873 MinMacCatalystVersion(Deprecated.Version),
2874 MinMacCatalystVersion(Obsoleted.Version), IsUnavailable, Str,
2875 IsStrict, Replacement, Sema::AMK_None,
2876 PriorityModifier + Sema::AP_InferredFromOtherPlatform, IIEnvironment);
2877 if (NewAttr)
2878 D->addAttr(NewAttr);
2879 } else if (II->getName() == "macos" && GetSDKInfo() &&
2880 (!Introduced.Version.empty() || !Deprecated.Version.empty() ||
2881 !Obsoleted.Version.empty())) {
2882 if (const auto *MacOStoMacCatalystMapping =
2883 GetSDKInfo()->getVersionMapping(
2885 // Infer Mac Catalyst availability from the macOS availability attribute
2886 // if it has versioned availability. Don't infer 'unavailable'. This
2887 // inferred availability has lower priority than the other availability
2888 // attributes that are inferred from 'ios'.
2889 NewII = &S.Context.Idents.get("maccatalyst");
2890 auto RemapMacOSVersion =
2891 [&](const VersionTuple &V) -> std::optional<VersionTuple> {
2892 if (V.empty())
2893 return std::nullopt;
2894 // API_TO_BE_DEPRECATED is 100000.
2895 if (V.getMajor() == 100000)
2896 return VersionTuple(100000);
2897 // The minimum iosmac version is 13.1
2898 return MacOStoMacCatalystMapping->map(V, VersionTuple(13, 1),
2899 std::nullopt);
2900 };
2901 std::optional<VersionTuple> NewIntroduced =
2902 RemapMacOSVersion(Introduced.Version),
2903 NewDeprecated =
2904 RemapMacOSVersion(Deprecated.Version),
2905 NewObsoleted =
2906 RemapMacOSVersion(Obsoleted.Version);
2907 if (NewIntroduced || NewDeprecated || NewObsoleted) {
2908 auto VersionOrEmptyVersion =
2909 [](const std::optional<VersionTuple> &V) -> VersionTuple {
2910 return V ? *V : VersionTuple();
2911 };
2912 AvailabilityAttr *NewAttr = S.mergeAvailabilityAttr(
2913 ND, AL, NewII, true /*Implicit*/,
2914 VersionOrEmptyVersion(NewIntroduced),
2915 VersionOrEmptyVersion(NewDeprecated),
2916 VersionOrEmptyVersion(NewObsoleted), /*IsUnavailable=*/false, Str,
2917 IsStrict, Replacement, Sema::AMK_None,
2918 PriorityModifier + Sema::AP_InferredFromOtherPlatform +
2920 IIEnvironment);
2921 if (NewAttr)
2922 D->addAttr(NewAttr);
2923 }
2924 }
2925 }
2926 }
2927}
2928
2930 const ParsedAttr &AL) {
2931 if (!AL.checkAtLeastNumArgs(S, 1) || !AL.checkAtMostNumArgs(S, 4))
2932 return;
2933
2934 StringRef Language;
2935 if (const auto *SE = dyn_cast_if_present<StringLiteral>(AL.getArgAsExpr(0)))
2936 Language = SE->getString();
2937 StringRef DefinedIn;
2938 if (const auto *SE = dyn_cast_if_present<StringLiteral>(AL.getArgAsExpr(1)))
2939 DefinedIn = SE->getString();
2940 bool IsGeneratedDeclaration = AL.getArgAsIdent(2) != nullptr;
2941 StringRef USR;
2942 if (const auto *SE = dyn_cast_if_present<StringLiteral>(AL.getArgAsExpr(3)))
2943 USR = SE->getString();
2944
2945 D->addAttr(::new (S.Context) ExternalSourceSymbolAttr(
2946 S.Context, AL, Language, DefinedIn, IsGeneratedDeclaration, USR));
2947}
2948
2949template <class T>
2951 typename T::VisibilityType value) {
2952 T *existingAttr = D->getAttr<T>();
2953 if (existingAttr) {
2954 typename T::VisibilityType existingValue = existingAttr->getVisibility();
2955 if (existingValue == value)
2956 return nullptr;
2957 S.Diag(existingAttr->getLocation(), diag::err_mismatched_visibility);
2958 S.Diag(CI.getLoc(), diag::note_previous_attribute);
2959 D->dropAttr<T>();
2960 }
2961 return ::new (S.Context) T(S.Context, CI, value);
2962}
2963
2965 const AttributeCommonInfo &CI,
2966 VisibilityAttr::VisibilityType Vis) {
2967 return ::mergeVisibilityAttr<VisibilityAttr>(*this, D, CI, Vis);
2968}
2969
2970TypeVisibilityAttr *
2972 TypeVisibilityAttr::VisibilityType Vis) {
2973 return ::mergeVisibilityAttr<TypeVisibilityAttr>(*this, D, CI, Vis);
2974}
2975
2976static void handleVisibilityAttr(Sema &S, Decl *D, const ParsedAttr &AL,
2977 bool isTypeVisibility) {
2978 // Visibility attributes don't mean anything on a typedef.
2979 if (isa<TypedefNameDecl>(D)) {
2980 S.Diag(AL.getRange().getBegin(), diag::warn_attribute_ignored) << AL;
2981 return;
2982 }
2983
2984 // 'type_visibility' can only go on a type or namespace.
2985 if (isTypeVisibility && !(isa<TagDecl>(D) || isa<ObjCInterfaceDecl>(D) ||
2986 isa<NamespaceDecl>(D))) {
2987 S.Diag(AL.getRange().getBegin(), diag::err_attribute_wrong_decl_type)
2989 return;
2990 }
2991
2992 // Check that the argument is a string literal.
2993 StringRef TypeStr;
2994 SourceLocation LiteralLoc;
2995 if (!S.checkStringLiteralArgumentAttr(AL, 0, TypeStr, &LiteralLoc))
2996 return;
2997
2998 VisibilityAttr::VisibilityType type;
2999 if (!VisibilityAttr::ConvertStrToVisibilityType(TypeStr, type)) {
3000 S.Diag(LiteralLoc, diag::warn_attribute_type_not_supported) << AL
3001 << TypeStr;
3002 return;
3003 }
3004
3005 // Complain about attempts to use protected visibility on targets
3006 // (like Darwin) that don't support it.
3007 if (type == VisibilityAttr::Protected &&
3009 S.Diag(AL.getLoc(), diag::warn_attribute_protected_visibility);
3010 type = VisibilityAttr::Default;
3011 }
3012
3013 Attr *newAttr;
3014 if (isTypeVisibility) {
3015 newAttr = S.mergeTypeVisibilityAttr(
3016 D, AL, (TypeVisibilityAttr::VisibilityType)type);
3017 } else {
3018 newAttr = S.mergeVisibilityAttr(D, AL, type);
3019 }
3020 if (newAttr)
3021 D->addAttr(newAttr);
3022}
3023
3024static void handleObjCDirectAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3025 // objc_direct cannot be set on methods declared in the context of a protocol
3026 if (isa<ObjCProtocolDecl>(D->getDeclContext())) {
3027 S.Diag(AL.getLoc(), diag::err_objc_direct_on_protocol) << false;
3028 return;
3029 }
3030
3032 handleSimpleAttribute<ObjCDirectAttr>(S, D, AL);
3033 } else {
3034 S.Diag(AL.getLoc(), diag::warn_objc_direct_ignored) << AL;
3035 }
3036}
3037
3039 const ParsedAttr &AL) {
3041 handleSimpleAttribute<ObjCDirectMembersAttr>(S, D, AL);
3042 } else {
3043 S.Diag(AL.getLoc(), diag::warn_objc_direct_ignored) << AL;
3044 }
3045}
3046
3047static void handleObjCMethodFamilyAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3048 const auto *M = cast<ObjCMethodDecl>(D);
3049 if (!AL.isArgIdent(0)) {
3050 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
3051 << AL << 1 << AANT_ArgumentIdentifier;
3052 return;
3053 }
3054
3055 IdentifierLoc *IL = AL.getArgAsIdent(0);
3056 ObjCMethodFamilyAttr::FamilyKind F;
3057 if (!ObjCMethodFamilyAttr::ConvertStrToFamilyKind(IL->Ident->getName(), F)) {
3058 S.Diag(IL->Loc, diag::warn_attribute_type_not_supported) << AL << IL->Ident;
3059 return;
3060 }
3061
3062 if (F == ObjCMethodFamilyAttr::OMF_init &&
3063 !M->getReturnType()->isObjCObjectPointerType()) {
3064 S.Diag(M->getLocation(), diag::err_init_method_bad_return_type)
3065 << M->getReturnType();
3066 // Ignore the attribute.
3067 return;
3068 }
3069
3070 D->addAttr(new (S.Context) ObjCMethodFamilyAttr(S.Context, AL, F));
3071}
3072
3073static void handleObjCNSObject(Sema &S, Decl *D, const ParsedAttr &AL) {
3074 if (const auto *TD = dyn_cast<TypedefNameDecl>(D)) {
3075 QualType T = TD->getUnderlyingType();
3076 if (!T->isCARCBridgableType()) {
3077 S.Diag(TD->getLocation(), diag::err_nsobject_attribute);
3078 return;
3079 }
3080 }
3081 else if (const auto *PD = dyn_cast<ObjCPropertyDecl>(D)) {
3082 QualType T = PD->getType();
3083 if (!T->isCARCBridgableType()) {
3084 S.Diag(PD->getLocation(), diag::err_nsobject_attribute);
3085 return;
3086 }
3087 }
3088 else {
3089 // It is okay to include this attribute on properties, e.g.:
3090 //
3091 // @property (retain, nonatomic) struct Bork *Q __attribute__((NSObject));
3092 //
3093 // In this case it follows tradition and suppresses an error in the above
3094 // case.
3095 S.Diag(D->getLocation(), diag::warn_nsobject_attribute);
3096 }
3097 D->addAttr(::new (S.Context) ObjCNSObjectAttr(S.Context, AL));
3098}
3099
3100static void handleObjCIndependentClass(Sema &S, Decl *D, const ParsedAttr &AL) {
3101 if (const auto *TD = dyn_cast<TypedefNameDecl>(D)) {
3102 QualType T = TD->getUnderlyingType();
3103 if (!T->isObjCObjectPointerType()) {
3104 S.Diag(TD->getLocation(), diag::warn_ptr_independentclass_attribute);
3105 return;
3106 }
3107 } else {
3108 S.Diag(D->getLocation(), diag::warn_independentclass_attribute);
3109 return;
3110 }
3111 D->addAttr(::new (S.Context) ObjCIndependentClassAttr(S.Context, AL));
3112}
3113
3114static void handleBlocksAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3115 if (!AL.isArgIdent(0)) {
3116 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
3117 << AL << 1 << AANT_ArgumentIdentifier;
3118 return;
3119 }
3120
3121 IdentifierInfo *II = AL.getArgAsIdent(0)->Ident;
3122 BlocksAttr::BlockType type;
3123 if (!BlocksAttr::ConvertStrToBlockType(II->getName(), type)) {
3124 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported) << AL << II;
3125 return;
3126 }
3127
3128 D->addAttr(::new (S.Context) BlocksAttr(S.Context, AL, type));
3129}
3130
3131static void handleSentinelAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3132 unsigned sentinel = (unsigned)SentinelAttr::DefaultSentinel;
3133 if (AL.getNumArgs() > 0) {
3134 Expr *E = AL.getArgAsExpr(0);
3135 std::optional<llvm::APSInt> Idx = llvm::APSInt(32);
3136 if (E->isTypeDependent() || !(Idx = E->getIntegerConstantExpr(S.Context))) {
3137 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
3138 << AL << 1 << AANT_ArgumentIntegerConstant << E->getSourceRange();
3139 return;
3140 }
3141
3142 if (Idx->isSigned() && Idx->isNegative()) {
3143 S.Diag(AL.getLoc(), diag::err_attribute_sentinel_less_than_zero)
3144 << E->getSourceRange();
3145 return;
3146 }
3147
3148 sentinel = Idx->getZExtValue();
3149 }
3150
3151 unsigned nullPos = (unsigned)SentinelAttr::DefaultNullPos;
3152 if (AL.getNumArgs() > 1) {
3153 Expr *E = AL.getArgAsExpr(1);
3154 std::optional<llvm::APSInt> Idx = llvm::APSInt(32);
3155 if (E->isTypeDependent() || !(Idx = E->getIntegerConstantExpr(S.Context))) {
3156 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
3157 << AL << 2 << AANT_ArgumentIntegerConstant << E->getSourceRange();
3158 return;
3159 }
3160 nullPos = Idx->getZExtValue();
3161
3162 if ((Idx->isSigned() && Idx->isNegative()) || nullPos > 1) {
3163 // FIXME: This error message could be improved, it would be nice
3164 // to say what the bounds actually are.
3165 S.Diag(AL.getLoc(), diag::err_attribute_sentinel_not_zero_or_one)
3166 << E->getSourceRange();
3167 return;
3168 }
3169 }
3170
3171 if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
3172 const FunctionType *FT = FD->getType()->castAs<FunctionType>();
3173 if (isa<FunctionNoProtoType>(FT)) {
3174 S.Diag(AL.getLoc(), diag::warn_attribute_sentinel_named_arguments);
3175 return;
3176 }
3177
3178 if (!cast<FunctionProtoType>(FT)->isVariadic()) {
3179 S.Diag(AL.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0;
3180 return;
3181 }
3182 } else if (const auto *MD = dyn_cast<ObjCMethodDecl>(D)) {
3183 if (!MD->isVariadic()) {
3184 S.Diag(AL.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0;
3185 return;
3186 }
3187 } else if (const auto *BD = dyn_cast<BlockDecl>(D)) {
3188 if (!BD->isVariadic()) {
3189 S.Diag(AL.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 1;
3190 return;
3191 }
3192 } else if (const auto *V = dyn_cast<VarDecl>(D)) {
3193 QualType Ty = V->getType();
3194 if (Ty->isBlockPointerType() || Ty->isFunctionPointerType()) {
3195 const FunctionType *FT = Ty->isFunctionPointerType()
3196 ? D->getFunctionType()
3197 : Ty->castAs<BlockPointerType>()
3198 ->getPointeeType()
3199 ->castAs<FunctionType>();
3200 if (!cast<FunctionProtoType>(FT)->isVariadic()) {
3201 int m = Ty->isFunctionPointerType() ? 0 : 1;
3202 S.Diag(AL.getLoc(), diag::warn_attribute_sentinel_not_variadic) << m;
3203 return;
3204 }
3205 } else {
3206 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
3207 << AL << AL.isRegularKeywordAttribute()
3209 return;
3210 }
3211 } else {
3212 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
3213 << AL << AL.isRegularKeywordAttribute()
3215 return;
3216 }
3217 D->addAttr(::new (S.Context) SentinelAttr(S.Context, AL, sentinel, nullPos));
3218}
3219
3220static void handleWarnUnusedResult(Sema &S, Decl *D, const ParsedAttr &AL) {
3221 if (D->getFunctionType() &&
3223 !isa<CXXConstructorDecl>(D)) {
3224 S.Diag(AL.getLoc(), diag::warn_attribute_void_function_method) << AL << 0;
3225 return;
3226 }
3227 if (const auto *MD = dyn_cast<ObjCMethodDecl>(D))
3228 if (MD->getReturnType()->isVoidType()) {
3229 S.Diag(AL.getLoc(), diag::warn_attribute_void_function_method) << AL << 1;
3230 return;
3231 }
3232
3233 StringRef Str;
3234 if (AL.isStandardAttributeSyntax() && !AL.getScopeName()) {
3235 // The standard attribute cannot be applied to variable declarations such
3236 // as a function pointer.
3237 if (isa<VarDecl>(D))
3238 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type_str)
3239 << AL << AL.isRegularKeywordAttribute()
3240 << "functions, classes, or enumerations";
3241
3242 // If this is spelled as the standard C++17 attribute, but not in C++17,
3243 // warn about using it as an extension. If there are attribute arguments,
3244 // then claim it's a C++20 extension instead.
3245 // FIXME: If WG14 does not seem likely to adopt the same feature, add an
3246 // extension warning for C23 mode.
3247 const LangOptions &LO = S.getLangOpts();
3248 if (AL.getNumArgs() == 1) {
3249 if (LO.CPlusPlus && !LO.CPlusPlus20)
3250 S.Diag(AL.getLoc(), diag::ext_cxx20_attr) << AL;
3251
3252 // Since this is spelled [[nodiscard]], get the optional string
3253 // literal. If in C++ mode, but not in C++20 mode, diagnose as an
3254 // extension.
3255 // FIXME: C23 should support this feature as well, even as an extension.
3256 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, nullptr))
3257 return;
3258 } else if (LO.CPlusPlus && !LO.CPlusPlus17)
3259 S.Diag(AL.getLoc(), diag::ext_cxx17_attr) << AL;
3260 }
3261
3262 if ((!AL.isGNUAttribute() &&
3263 !(AL.isStandardAttributeSyntax() && AL.isClangScope())) &&
3264 isa<TypedefNameDecl>(D)) {
3265 S.Diag(AL.getLoc(), diag::warn_unused_result_typedef_unsupported_spelling)
3266 << AL.isGNUScope();
3267 return;
3268 }
3269
3270 D->addAttr(::new (S.Context) WarnUnusedResultAttr(S.Context, AL, Str));
3271}
3272
3273static void handleWeakImportAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3274 // weak_import only applies to variable & function declarations.
3275 bool isDef = false;
3276 if (!D->canBeWeakImported(isDef)) {
3277 if (isDef)
3278 S.Diag(AL.getLoc(), diag::warn_attribute_invalid_on_definition)
3279 << "weak_import";
3280 else if (isa<ObjCPropertyDecl>(D) || isa<ObjCMethodDecl>(D) ||
3281 (S.Context.getTargetInfo().getTriple().isOSDarwin() &&
3282 (isa<ObjCInterfaceDecl>(D) || isa<EnumDecl>(D)))) {
3283 // Nothing to warn about here.
3284 } else
3285 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
3287
3288 return;
3289 }
3290
3291 D->addAttr(::new (S.Context) WeakImportAttr(S.Context, AL));
3292}
3293
3294// Handles reqd_work_group_size and work_group_size_hint.
3295template <typename WorkGroupAttr>
3296static void handleWorkGroupSize(Sema &S, Decl *D, const ParsedAttr &AL) {
3297 uint32_t WGSize[3];
3298 for (unsigned i = 0; i < 3; ++i) {
3299 const Expr *E = AL.getArgAsExpr(i);
3300 if (!checkUInt32Argument(S, AL, E, WGSize[i], i,
3301 /*StrictlyUnsigned=*/true))
3302 return;
3303 if (WGSize[i] == 0) {
3304 S.Diag(AL.getLoc(), diag::err_attribute_argument_is_zero)
3305 << AL << E->getSourceRange();
3306 return;
3307 }
3308 }
3309
3310 WorkGroupAttr *Existing = D->getAttr<WorkGroupAttr>();
3311 if (Existing && !(Existing->getXDim() == WGSize[0] &&
3312 Existing->getYDim() == WGSize[1] &&
3313 Existing->getZDim() == WGSize[2]))
3314 S.Diag(AL.getLoc(), diag::warn_duplicate_attribute) << AL;
3315
3316 D->addAttr(::new (S.Context)
3317 WorkGroupAttr(S.Context, AL, WGSize[0], WGSize[1], WGSize[2]));
3318}
3319
3320// Handles intel_reqd_sub_group_size.
3321static void handleSubGroupSize(Sema &S, Decl *D, const ParsedAttr &AL) {
3322 uint32_t SGSize;
3323 const Expr *E = AL.getArgAsExpr(0);
3324 if (!checkUInt32Argument(S, AL, E, SGSize))
3325 return;
3326 if (SGSize == 0) {
3327 S.Diag(AL.getLoc(), diag::err_attribute_argument_is_zero)
3328 << AL << E->getSourceRange();
3329 return;
3330 }
3331
3332 OpenCLIntelReqdSubGroupSizeAttr *Existing =
3333 D->getAttr<OpenCLIntelReqdSubGroupSizeAttr>();
3334 if (Existing && Existing->getSubGroupSize() != SGSize)
3335 S.Diag(AL.getLoc(), diag::warn_duplicate_attribute) << AL;
3336
3337 D->addAttr(::new (S.Context)
3338 OpenCLIntelReqdSubGroupSizeAttr(S.Context, AL, SGSize));
3339}
3340
3341static void handleVecTypeHint(Sema &S, Decl *D, const ParsedAttr &AL) {
3342 if (!AL.hasParsedType()) {
3343 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << AL << 1;
3344 return;
3345 }
3346
3347 TypeSourceInfo *ParmTSI = nullptr;
3348 QualType ParmType = S.GetTypeFromParser(AL.getTypeArg(), &ParmTSI);
3349 assert(ParmTSI && "no type source info for attribute argument");
3350
3351 if (!ParmType->isExtVectorType() && !ParmType->isFloatingType() &&
3352 (ParmType->isBooleanType() ||
3353 !ParmType->isIntegralType(S.getASTContext()))) {
3354 S.Diag(AL.getLoc(), diag::err_attribute_invalid_argument) << 2 << AL;
3355 return;
3356 }
3357
3358 if (VecTypeHintAttr *A = D->getAttr<VecTypeHintAttr>()) {
3359 if (!S.Context.hasSameType(A->getTypeHint(), ParmType)) {
3360 S.Diag(AL.getLoc(), diag::warn_duplicate_attribute) << AL;
3361 return;
3362 }
3363 }
3364
3365 D->addAttr(::new (S.Context) VecTypeHintAttr(S.Context, AL, ParmTSI));
3366}
3367
3369 StringRef Name) {
3370 // Explicit or partial specializations do not inherit
3371 // the section attribute from the primary template.
3372 if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
3373 if (CI.getAttributeSpellingListIndex() == SectionAttr::Declspec_allocate &&
3375 return nullptr;
3376 }
3377 if (SectionAttr *ExistingAttr = D->getAttr<SectionAttr>()) {
3378 if (ExistingAttr->getName() == Name)
3379 return nullptr;
3380 Diag(ExistingAttr->getLocation(), diag::warn_mismatched_section)
3381 << 1 /*section*/;
3382 Diag(CI.getLoc(), diag::note_previous_attribute);
3383 return nullptr;
3384 }
3385 return ::new (Context) SectionAttr(Context, CI, Name);
3386}
3387
3388/// Used to implement to perform semantic checking on
3389/// attribute((section("foo"))) specifiers.
3390///
3391/// In this case, "foo" is passed in to be checked. If the section
3392/// specifier is invalid, return an Error that indicates the problem.
3393///
3394/// This is a simple quality of implementation feature to catch errors
3395/// and give good diagnostics in cases when the assembler or code generator
3396/// would otherwise reject the section specifier.
3397llvm::Error Sema::isValidSectionSpecifier(StringRef SecName) {
3398 if (!Context.getTargetInfo().getTriple().isOSDarwin())
3399 return llvm::Error::success();
3400
3401 // Let MCSectionMachO validate this.
3402 StringRef Segment, Section;
3403 unsigned TAA, StubSize;
3404 bool HasTAA;
3405 return llvm::MCSectionMachO::ParseSectionSpecifier(SecName, Segment, Section,
3406 TAA, HasTAA, StubSize);
3407}
3408
3409bool Sema::checkSectionName(SourceLocation LiteralLoc, StringRef SecName) {
3410 if (llvm::Error E = isValidSectionSpecifier(SecName)) {
3411 Diag(LiteralLoc, diag::err_attribute_section_invalid_for_target)
3412 << toString(std::move(E)) << 1 /*'section'*/;
3413 return false;
3414 }
3415 return true;
3416}
3417
3418static void handleSectionAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3419 // Make sure that there is a string literal as the sections's single
3420 // argument.
3421 StringRef Str;
3422 SourceLocation LiteralLoc;
3423 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &LiteralLoc))
3424 return;
3425
3426 if (!S.checkSectionName(LiteralLoc, Str))
3427 return;
3428
3429 SectionAttr *NewAttr = S.mergeSectionAttr(D, AL, Str);
3430 if (NewAttr) {
3431 D->addAttr(NewAttr);
3433 ObjCPropertyDecl>(D))
3434 S.UnifySection(NewAttr->getName(),
3436 cast<NamedDecl>(D));
3437 }
3438}
3439
3440static void handleCodeModelAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3441 StringRef Str;
3442 SourceLocation LiteralLoc;
3443 // Check that it is a string.
3444 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &LiteralLoc))
3445 return;
3446
3447 llvm::CodeModel::Model CM;
3448 if (!CodeModelAttr::ConvertStrToModel(Str, CM)) {
3449 S.Diag(LiteralLoc, diag::err_attr_codemodel_arg) << Str;
3450 return;
3451 }
3452
3453 D->addAttr(::new (S.Context) CodeModelAttr(S.Context, AL, CM));
3454}
3455
3456// This is used for `__declspec(code_seg("segname"))` on a decl.
3457// `#pragma code_seg("segname")` uses checkSectionName() instead.
3458static bool checkCodeSegName(Sema &S, SourceLocation LiteralLoc,
3459 StringRef CodeSegName) {
3460 if (llvm::Error E = S.isValidSectionSpecifier(CodeSegName)) {
3461 S.Diag(LiteralLoc, diag::err_attribute_section_invalid_for_target)
3462 << toString(std::move(E)) << 0 /*'code-seg'*/;
3463 return false;
3464 }
3465
3466 return true;
3467}
3468
3470 StringRef Name) {
3471 // Explicit or partial specializations do not inherit
3472 // the code_seg attribute from the primary template.
3473 if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
3475 return nullptr;
3476 }
3477 if (const auto *ExistingAttr = D->getAttr<CodeSegAttr>()) {
3478 if (ExistingAttr->getName() == Name)
3479 return nullptr;
3480 Diag(ExistingAttr->getLocation(), diag::warn_mismatched_section)
3481 << 0 /*codeseg*/;
3482 Diag(CI.getLoc(), diag::note_previous_attribute);
3483 return nullptr;
3484 }
3485 return ::new (Context) CodeSegAttr(Context, CI, Name);
3486}
3487
3488static void handleCodeSegAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3489 StringRef Str;
3490 SourceLocation LiteralLoc;
3491 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &LiteralLoc))
3492 return;
3493 if (!checkCodeSegName(S, LiteralLoc, Str))
3494 return;
3495 if (const auto *ExistingAttr = D->getAttr<CodeSegAttr>()) {
3496 if (!ExistingAttr->isImplicit()) {
3497 S.Diag(AL.getLoc(),
3498 ExistingAttr->getName() == Str
3499 ? diag::warn_duplicate_codeseg_attribute
3500 : diag::err_conflicting_codeseg_attribute);
3501 return;
3502 }
3503 D->dropAttr<CodeSegAttr>();
3504 }
3505 if (CodeSegAttr *CSA = S.mergeCodeSegAttr(D, AL, Str))
3506 D->addAttr(CSA);
3507}
3508
3509// Check for things we'd like to warn about. Multiversioning issues are
3510// handled later in the process, once we know how many exist.
3511bool Sema::checkTargetAttr(SourceLocation LiteralLoc, StringRef AttrStr) {
3512 enum FirstParam { Unsupported, Duplicate, Unknown };
3513 enum SecondParam { None, CPU, Tune };
3514 enum ThirdParam { Target, TargetClones };
3515 if (AttrStr.contains("fpmath="))
3516 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3517 << Unsupported << None << "fpmath=" << Target;
3518
3519 // Diagnose use of tune if target doesn't support it.
3521 AttrStr.contains("tune="))
3522 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3523 << Unsupported << None << "tune=" << Target;
3524
3525 ParsedTargetAttr ParsedAttrs =
3527
3528 if (!ParsedAttrs.CPU.empty() &&
3529 !Context.getTargetInfo().isValidCPUName(ParsedAttrs.CPU))
3530 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3531 << Unknown << CPU << ParsedAttrs.CPU << Target;
3532
3533 if (!ParsedAttrs.Tune.empty() &&
3534 !Context.getTargetInfo().isValidCPUName(ParsedAttrs.Tune))
3535 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3536 << Unknown << Tune << ParsedAttrs.Tune << Target;
3537
3538 if (Context.getTargetInfo().getTriple().isRISCV() &&
3539 ParsedAttrs.Duplicate != "")
3540 return Diag(LiteralLoc, diag::err_duplicate_target_attribute)
3541 << Duplicate << None << ParsedAttrs.Duplicate << Target;
3542
3543 if (ParsedAttrs.Duplicate != "")
3544 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3545 << Duplicate << None << ParsedAttrs.Duplicate << Target;
3546
3547 for (const auto &Feature : ParsedAttrs.Features) {
3548 auto CurFeature = StringRef(Feature).drop_front(); // remove + or -.
3549 if (!Context.getTargetInfo().isValidFeatureName(CurFeature))
3550 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3551 << Unsupported << None << CurFeature << Target;
3552 }
3553
3555 StringRef DiagMsg;
3556 if (ParsedAttrs.BranchProtection.empty())
3557 return false;
3559 ParsedAttrs.BranchProtection, ParsedAttrs.CPU, BPI, DiagMsg)) {
3560 if (DiagMsg.empty())
3561 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3562 << Unsupported << None << "branch-protection" << Target;
3563 return Diag(LiteralLoc, diag::err_invalid_branch_protection_spec)
3564 << DiagMsg;
3565 }
3566 if (!DiagMsg.empty())
3567 Diag(LiteralLoc, diag::warn_unsupported_branch_protection_spec) << DiagMsg;
3568
3569 return false;
3570}
3571
3572// Check Target Version attrs
3574 StringRef &AttrStr, bool &isDefault) {
3575 enum FirstParam { Unsupported };
3576 enum SecondParam { None };
3577 enum ThirdParam { Target, TargetClones, TargetVersion };
3578 if (AttrStr.trim() == "default")
3579 isDefault = true;
3581 AttrStr.split(Features, "+");
3582 for (auto &CurFeature : Features) {
3583 CurFeature = CurFeature.trim();
3584 if (CurFeature == "default")
3585 continue;
3586 if (!Context.getTargetInfo().validateCpuSupports(CurFeature))
3587 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3588 << Unsupported << None << CurFeature << TargetVersion;
3589 }
3590 if (IsArmStreamingFunction(cast<FunctionDecl>(D),
3591 /*IncludeLocallyStreaming=*/false))
3592 return Diag(LiteralLoc, diag::err_sme_streaming_cannot_be_multiversioned);
3593 return false;
3594}
3595
3596static void handleTargetVersionAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3597 StringRef Str;
3598 SourceLocation LiteralLoc;
3599 bool isDefault = false;
3600 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &LiteralLoc) ||
3601 S.checkTargetVersionAttr(LiteralLoc, D, Str, isDefault))
3602 return;
3603 // Do not create default only target_version attribute
3604 if (!isDefault) {
3605 TargetVersionAttr *NewAttr =
3606 ::new (S.Context) TargetVersionAttr(S.Context, AL, Str);
3607 D->addAttr(NewAttr);
3608 }
3609}
3610
3611static void handleTargetAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3612 StringRef Str;
3613 SourceLocation LiteralLoc;
3614 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &LiteralLoc) ||
3615 S.checkTargetAttr(LiteralLoc, Str))
3616 return;
3617
3618 TargetAttr *NewAttr = ::new (S.Context) TargetAttr(S.Context, AL, Str);
3619 D->addAttr(NewAttr);
3620}
3621
3623 SourceLocation LiteralLoc, StringRef Str, const StringLiteral *Literal,
3624 Decl *D, bool &HasDefault, bool &HasCommas, bool &HasNotDefault,
3625 SmallVectorImpl<SmallString<64>> &StringsBuffer) {
3626 enum FirstParam { Unsupported, Duplicate, Unknown };
3627 enum SecondParam { None, CPU, Tune };
3628 enum ThirdParam { Target, TargetClones };
3629 HasCommas = HasCommas || Str.contains(',');
3630 const TargetInfo &TInfo = Context.getTargetInfo();
3631 // Warn on empty at the beginning of a string.
3632 if (Str.size() == 0)
3633 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3634 << Unsupported << None << "" << TargetClones;
3635
3636 std::pair<StringRef, StringRef> Parts = {{}, Str};
3637 while (!Parts.second.empty()) {
3638 Parts = Parts.second.split(',');
3639 StringRef Cur = Parts.first.trim();
3640 SourceLocation CurLoc =
3641 Literal->getLocationOfByte(Cur.data() - Literal->getString().data(),
3642 getSourceManager(), getLangOpts(), TInfo);
3643
3644 bool DefaultIsDupe = false;
3645 bool HasCodeGenImpact = false;
3646 if (Cur.empty())
3647 return Diag(CurLoc, diag::warn_unsupported_target_attribute)
3648 << Unsupported << None << "" << TargetClones;
3649
3650 if (TInfo.getTriple().isAArch64()) {
3651 // AArch64 target clones specific
3652 if (Cur == "default") {
3653 DefaultIsDupe = HasDefault;
3654 HasDefault = true;
3655 if (llvm::is_contained(StringsBuffer, Cur) || DefaultIsDupe)
3656 Diag(CurLoc, diag::warn_target_clone_duplicate_options);
3657 else
3658 StringsBuffer.push_back(Cur);
3659 } else {
3660 std::pair<StringRef, StringRef> CurParts = {{}, Cur};
3662 while (!CurParts.second.empty()) {
3663 CurParts = CurParts.second.split('+');
3664 StringRef CurFeature = CurParts.first.trim();
3665 if (!TInfo.validateCpuSupports(CurFeature)) {
3666 Diag(CurLoc, diag::warn_unsupported_target_attribute)
3667 << Unsupported << None << CurFeature << TargetClones;
3668 continue;
3669 }
3670 if (TInfo.doesFeatureAffectCodeGen(CurFeature))
3671 HasCodeGenImpact = true;
3672 CurFeatures.push_back(CurFeature);
3673 }
3674 // Canonize TargetClones Attributes
3675 llvm::sort(CurFeatures);
3676 SmallString<64> Res;
3677 for (auto &CurFeat : CurFeatures) {
3678 if (!Res.empty())
3679 Res.append("+");
3680 Res.append(CurFeat);
3681 }
3682 if (llvm::is_contained(StringsBuffer, Res) || DefaultIsDupe)
3683 Diag(CurLoc, diag::warn_target_clone_duplicate_options);
3684 else if (!HasCodeGenImpact)
3685 // Ignore features in target_clone attribute that don't impact
3686 // code generation
3687 Diag(CurLoc, diag::warn_target_clone_no_impact_options);
3688 else if (!Res.empty()) {
3689 StringsBuffer.push_back(Res);
3690 HasNotDefault = true;
3691 }
3692 }
3693 if (IsArmStreamingFunction(cast<FunctionDecl>(D),
3694 /*IncludeLocallyStreaming=*/false))
3695 return Diag(LiteralLoc,
3696 diag::err_sme_streaming_cannot_be_multiversioned);
3697 } else {
3698 // Other targets ( currently X86 )
3699 if (Cur.starts_with("arch=")) {
3701 Cur.drop_front(sizeof("arch=") - 1)))
3702 return Diag(CurLoc, diag::warn_unsupported_target_attribute)
3703 << Unsupported << CPU << Cur.drop_front(sizeof("arch=") - 1)
3704 << TargetClones;
3705 } else if (Cur == "default") {
3706 DefaultIsDupe = HasDefault;
3707 HasDefault = true;
3708 } else if (!Context.getTargetInfo().isValidFeatureName(Cur))
3709 return Diag(CurLoc, diag::warn_unsupported_target_attribute)
3710 << Unsupported << None << Cur << TargetClones;
3711 if (llvm::is_contained(StringsBuffer, Cur) || DefaultIsDupe)
3712 Diag(CurLoc, diag::warn_target_clone_duplicate_options);
3713 // Note: Add even if there are duplicates, since it changes name mangling.
3714 StringsBuffer.push_back(Cur);
3715 }
3716 }
3717 if (Str.rtrim().ends_with(","))
3718 return Diag(LiteralLoc, diag::warn_unsupported_target_attribute)
3719 << Unsupported << None << "" << TargetClones;
3720 return false;
3721}
3722
3723static void handleTargetClonesAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3724 if (S.Context.getTargetInfo().getTriple().isAArch64() &&
3725 !S.Context.getTargetInfo().hasFeature("fmv"))
3726 return;
3727
3728 // Ensure we don't combine these with themselves, since that causes some
3729 // confusing behavior.
3730 if (const auto *Other = D->getAttr<TargetClonesAttr>()) {
3731 S.Diag(AL.getLoc(), diag::err_disallowed_duplicate_attribute) << AL;
3732 S.Diag(Other->getLocation(), diag::note_conflicting_attribute);
3733 return;
3734 }
3735 if (checkAttrMutualExclusion<TargetClonesAttr>(S, D, AL))
3736 return;
3737
3739 SmallVector<SmallString<64>, 2> StringsBuffer;
3740 bool HasCommas = false, HasDefault = false, HasNotDefault = false;
3741
3742 for (unsigned I = 0, E = AL.getNumArgs(); I != E; ++I) {
3743 StringRef CurStr;
3744 SourceLocation LiteralLoc;
3745 if (!S.checkStringLiteralArgumentAttr(AL, I, CurStr, &LiteralLoc) ||
3747 LiteralLoc, CurStr,
3748 cast<StringLiteral>(AL.getArgAsExpr(I)->IgnoreParenCasts()), D,
3749 HasDefault, HasCommas, HasNotDefault, StringsBuffer))
3750 return;
3751 }
3752 for (auto &SmallStr : StringsBuffer)
3753 Strings.push_back(SmallStr.str());
3754
3755 if (HasCommas && AL.getNumArgs() > 1)
3756 S.Diag(AL.getLoc(), diag::warn_target_clone_mixed_values);
3757
3758 if (S.Context.getTargetInfo().getTriple().isAArch64() && !HasDefault) {
3759 // Add default attribute if there is no one
3760 HasDefault = true;
3761 Strings.push_back("default");
3762 }
3763
3764 if (!HasDefault) {
3765 S.Diag(AL.getLoc(), diag::err_target_clone_must_have_default);
3766 return;
3767 }
3768
3769 // FIXME: We could probably figure out how to get this to work for lambdas
3770 // someday.
3771 if (const auto *MD = dyn_cast<CXXMethodDecl>(D)) {
3772 if (MD->getParent()->isLambda()) {
3773 S.Diag(D->getLocation(), diag::err_multiversion_doesnt_support)
3774 << static_cast<unsigned>(MultiVersionKind::TargetClones)
3775 << /*Lambda*/ 9;
3776 return;
3777 }
3778 }
3779
3780 // No multiversion if we have default version only.
3781 if (S.Context.getTargetInfo().getTriple().isAArch64() && !HasNotDefault)
3782 return;
3783
3784 cast<FunctionDecl>(D)->setIsMultiVersion();
3785 TargetClonesAttr *NewAttr = ::new (S.Context)
3786 TargetClonesAttr(S.Context, AL, Strings.data(), Strings.size());
3787 D->addAttr(NewAttr);
3788}
3789
3790static void handleMinVectorWidthAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3791 Expr *E = AL.getArgAsExpr(0);
3792 uint32_t VecWidth;
3793 if (!checkUInt32Argument(S, AL, E, VecWidth)) {
3794 AL.setInvalid();
3795 return;
3796 }
3797
3798 MinVectorWidthAttr *Existing = D->getAttr<MinVectorWidthAttr>();
3799 if (Existing && Existing->getVectorWidth() != VecWidth) {
3800 S.Diag(AL.getLoc(), diag::warn_duplicate_attribute) << AL;
3801 return;
3802 }
3803
3804 D->addAttr(::new (S.Context) MinVectorWidthAttr(S.Context, AL, VecWidth));
3805}
3806
3807static void handleCleanupAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3808 Expr *E = AL.getArgAsExpr(0);
3810 FunctionDecl *FD = nullptr;
3812
3813 // gcc only allows for simple identifiers. Since we support more than gcc, we
3814 // will warn the user.
3815 if (auto *DRE = dyn_cast<DeclRefExpr>(E)) {
3816 if (DRE->hasQualifier())
3817 S.Diag(Loc, diag::warn_cleanup_ext);
3818 FD = dyn_cast<FunctionDecl>(DRE->getDecl());
3819 NI = DRE->getNameInfo();
3820 if (!FD) {
3821 S.Diag(Loc, diag::err_attribute_cleanup_arg_not_function) << 1
3822 << NI.getName();
3823 return;
3824 }
3825 } else if (auto *ULE = dyn_cast<UnresolvedLookupExpr>(E)) {
3826 if (ULE->hasExplicitTemplateArgs())
3827 S.Diag(Loc, diag::warn_cleanup_ext);
3829 NI = ULE->getNameInfo();
3830 if (!FD) {
3831 S.Diag(Loc, diag::err_attribute_cleanup_arg_not_function) << 2
3832 << NI.getName();
3833 if (ULE->getType() == S.Context.OverloadTy)
3835 return;
3836 }
3837 } else {
3838 S.Diag(Loc, diag::err_attribute_cleanup_arg_not_function) << 0;
3839 return;
3840 }
3841
3842 if (FD->getNumParams() != 1) {
3843 S.Diag(Loc, diag::err_attribute_cleanup_func_must_take_one_arg)
3844 << NI.getName();
3845 return;
3846 }
3847
3848 // We're currently more strict than GCC about what function types we accept.
3849 // If this ever proves to be a problem it should be easy to fix.
3850 QualType Ty = S.Context.getPointerType(cast<VarDecl>(D)->getType());
3851 QualType ParamTy = FD->getParamDecl(0)->getType();
3853 ParamTy, Ty) != Sema::Compatible) {
3854 S.Diag(Loc, diag::err_attribute_cleanup_func_arg_incompatible_type)
3855 << NI.getName() << ParamTy << Ty;
3856 return;
3857 }
3858 VarDecl *VD = cast<VarDecl>(D);
3859 // Create a reference to the variable declaration. This is a fake/dummy
3860 // reference.
3861 DeclRefExpr *VariableReference = DeclRefExpr::Create(
3862 S.Context, NestedNameSpecifierLoc{}, FD->getLocation(), VD, false,
3863 DeclarationNameInfo{VD->getDeclName(), VD->getLocation()}, VD->getType(),
3864 VK_LValue);
3865
3866 // Create a unary operator expression that represents taking the address of
3867 // the variable. This is a fake/dummy expression.
3868 Expr *AddressOfVariable = UnaryOperator::Create(
3869 S.Context, VariableReference, UnaryOperatorKind::UO_AddrOf,
3871 +false, FPOptionsOverride{});
3872
3873 // Create a function call expression. This is a fake/dummy call expression.
3874 CallExpr *FunctionCallExpression =
3875 CallExpr::Create(S.Context, E, ArrayRef{AddressOfVariable},
3877
3878 if (S.CheckFunctionCall(FD, FunctionCallExpression,
3879 FD->getType()->getAs<FunctionProtoType>())) {
3880 return;
3881 }
3882
3883 D->addAttr(::new (S.Context) CleanupAttr(S.Context, AL, FD));
3884}
3885
3887 const ParsedAttr &AL) {
3888 if (!AL.isArgIdent(0)) {
3889 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
3890 << AL << 0 << AANT_ArgumentIdentifier;
3891 return;
3892 }
3893
3894 EnumExtensibilityAttr::Kind ExtensibilityKind;
3895 IdentifierInfo *II = AL.getArgAsIdent(0)->Ident;
3896 if (!EnumExtensibilityAttr::ConvertStrToKind(II->getName(),
3897 ExtensibilityKind)) {
3898 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported) << AL << II;
3899 return;
3900 }
3901
3902 D->addAttr(::new (S.Context)
3903 EnumExtensibilityAttr(S.Context, AL, ExtensibilityKind));
3904}
3905
3906/// Handle __attribute__((format_arg((idx)))) attribute based on
3907/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html
3908static void handleFormatArgAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3909 const Expr *IdxExpr = AL.getArgAsExpr(0);
3910 ParamIdx Idx;
3911 if (!checkFunctionOrMethodParameterIndex(S, D, AL, 1, IdxExpr, Idx))
3912 return;
3913
3914 // Make sure the format string is really a string.
3916
3917 bool NotNSStringTy = !isNSStringType(Ty, S.Context);
3918 if (NotNSStringTy &&
3919 !isCFStringType(Ty, S.Context) &&
3920 (!Ty->isPointerType() ||
3922 S.Diag(AL.getLoc(), diag::err_format_attribute_not)
3923 << IdxExpr->getSourceRange() << getFunctionOrMethodParamRange(D, 0);
3924 return;
3925 }
3927 // replace instancetype with the class type
3928 auto Instancetype = S.Context.getObjCInstanceTypeDecl()->getTypeForDecl();
3929 if (Ty->getAs<TypedefType>() == Instancetype)
3930 if (auto *OMD = dyn_cast<ObjCMethodDecl>(D))
3931 if (auto *Interface = OMD->getClassInterface())
3933 QualType(Interface->getTypeForDecl(), 0));
3934 if (!isNSStringType(Ty, S.Context, /*AllowNSAttributedString=*/true) &&
3935 !isCFStringType(Ty, S.Context) &&
3936 (!Ty->isPointerType() ||
3938 S.Diag(AL.getLoc(), diag::err_format_attribute_result_not)
3939 << (NotNSStringTy ? "string type" : "NSString")
3940 << IdxExpr->getSourceRange() << getFunctionOrMethodParamRange(D, 0);
3941 return;
3942 }
3943
3944 D->addAttr(::new (S.Context) FormatArgAttr(S.Context, AL, Idx));
3945}
3946
3955
3956/// getFormatAttrKind - Map from format attribute names to supported format
3957/// types.
3958static FormatAttrKind getFormatAttrKind(StringRef Format) {
3959 return llvm::StringSwitch<FormatAttrKind>(Format)
3960 // Check for formats that get handled specially.
3961 .Case("NSString", NSStringFormat)
3962 .Case("CFString", CFStringFormat)
3963 .Case("strftime", StrftimeFormat)
3964
3965 // Otherwise, check for supported formats.
3966 .Cases("scanf", "printf", "printf0", "strfmon", SupportedFormat)
3967 .Cases("cmn_err", "vcmn_err", "zcmn_err", SupportedFormat)
3968 .Case("kprintf", SupportedFormat) // OpenBSD.
3969 .Case("freebsd_kprintf", SupportedFormat) // FreeBSD.
3970 .Case("os_trace", SupportedFormat)
3971 .Case("os_log", SupportedFormat)
3972
3973 .Cases("gcc_diag", "gcc_cdiag", "gcc_cxxdiag", "gcc_tdiag", IgnoredFormat)
3974 .Default(InvalidFormat);
3975}
3976
3977/// Handle __attribute__((init_priority(priority))) attributes based on
3978/// http://gcc.gnu.org/onlinedocs/gcc/C_002b_002b-Attributes.html
3979static void handleInitPriorityAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
3980 if (!S.getLangOpts().CPlusPlus) {
3981 S.Diag(AL.getLoc(), diag::warn_attribute_ignored) << AL;
3982 return;
3983 }
3984
3985 if (S.getLangOpts().HLSL) {
3986 S.Diag(AL.getLoc(), diag::err_hlsl_init_priority_unsupported);
3987 return;
3988 }
3989
3991 S.Diag(AL.getLoc(), diag::err_init_priority_object_attr);
3992 AL.setInvalid();
3993 return;
3994 }
3995 QualType T = cast<VarDecl>(D)->getType();
3996 if (S.Context.getAsArrayType(T))
3998 if (!T->getAs<RecordType>()) {
3999 S.Diag(AL.getLoc(), diag::err_init_priority_object_attr);
4000 AL.setInvalid();
4001 return;
4002 }
4003
4004 Expr *E = AL.getArgAsExpr(0);
4005 uint32_t prioritynum;
4006 if (!checkUInt32Argument(S, AL, E, prioritynum)) {
4007 AL.setInvalid();
4008 return;
4009 }
4010
4011 // Only perform the priority check if the attribute is outside of a system
4012 // header. Values <= 100 are reserved for the implementation, and libc++
4013 // benefits from being able to specify values in that range.
4014 if ((prioritynum < 101 || prioritynum > 65535) &&
4016 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_range)
4017 << E->getSourceRange() << AL << 101 << 65535;
4018 AL.setInvalid();
4019 return;
4020 }
4021 D->addAttr(::new (S.Context) InitPriorityAttr(S.Context, AL, prioritynum));
4022}
4023
4025 StringRef NewUserDiagnostic) {
4026 if (const auto *EA = D->getAttr<ErrorAttr>()) {
4027 std::string NewAttr = CI.getNormalizedFullName();
4028 assert((NewAttr == "error" || NewAttr == "warning") &&
4029 "unexpected normalized full name");
4030 bool Match = (EA->isError() && NewAttr == "error") ||
4031 (EA->isWarning() && NewAttr == "warning");
4032 if (!Match) {
4033 Diag(EA->getLocation(), diag::err_attributes_are_not_compatible)
4034 << CI << EA
4035 << (CI.isRegularKeywordAttribute() ||
4036 EA->isRegularKeywordAttribute());
4037 Diag(CI.getLoc(), diag::note_conflicting_attribute);
4038 return nullptr;
4039 }
4040 if (EA->getUserDiagnostic() != NewUserDiagnostic) {
4041 Diag(CI.getLoc(), diag::warn_duplicate_attribute) << EA;
4042 Diag(EA->getLoc(), diag::note_previous_attribute);
4043 }
4044 D->dropAttr<ErrorAttr>();
4045 }
4046 return ::new (Context) ErrorAttr(Context, CI, NewUserDiagnostic);
4047}
4048
4050 IdentifierInfo *Format, int FormatIdx,
4051 int FirstArg) {
4052 // Check whether we already have an equivalent format attribute.
4053 for (auto *F : D->specific_attrs<FormatAttr>()) {
4054 if (F->getType() == Format &&
4055 F->getFormatIdx() == FormatIdx &&
4056 F->getFirstArg() == FirstArg) {
4057 // If we don't have a valid location for this attribute, adopt the
4058 // location.
4059 if (F->getLocation().isInvalid())
4060 F->setRange(CI.getRange());
4061 return nullptr;
4062 }
4063 }
4064
4065 return ::new (Context) FormatAttr(Context, CI, Format, FormatIdx, FirstArg);
4066}
4067
4068/// Handle __attribute__((format(type,idx,firstarg))) attributes based on
4069/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html
4070static void handleFormatAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4071 if (!AL.isArgIdent(0)) {
4072 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
4073 << AL << 1 << AANT_ArgumentIdentifier;
4074 return;
4075 }
4076
4077 // In C++ the implicit 'this' function parameter also counts, and they are
4078 // counted from one.
4079 bool HasImplicitThisParam = isInstanceMethod(D);
4080 unsigned NumArgs = getFunctionOrMethodNumParams(D) + HasImplicitThisParam;
4081
4082 IdentifierInfo *II = AL.getArgAsIdent(0)->Ident;
4083 StringRef Format = II->getName();
4084
4085 if (normalizeName(Format)) {
4086 // If we've modified the string name, we need a new identifier for it.
4087 II = &S.Context.Idents.get(Format);
4088 }
4089
4090 // Check for supported formats.
4091 FormatAttrKind Kind = getFormatAttrKind(Format);
4092
4093 if (Kind == IgnoredFormat)
4094 return;
4095
4096 if (Kind == InvalidFormat) {
4097 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported)
4098 << AL << II->getName();
4099 return;
4100 }
4101
4102 // checks for the 2nd argument
4103 Expr *IdxExpr = AL.getArgAsExpr(1);
4104 uint32_t Idx;
4105 if (!checkUInt32Argument(S, AL, IdxExpr, Idx, 2))
4106 return;
4107
4108 if (Idx < 1 || Idx > NumArgs) {
4109 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
4110 << AL << 2 << IdxExpr->getSourceRange();
4111 return;
4112 }
4113
4114 // FIXME: Do we need to bounds check?
4115 unsigned ArgIdx = Idx - 1;
4116
4117 if (HasImplicitThisParam) {
4118 if (ArgIdx == 0) {
4119 S.Diag(AL.getLoc(),
4120 diag::err_format_attribute_implicit_this_format_string)
4121 << IdxExpr->getSourceRange();
4122 return;
4123 }
4124 ArgIdx--;
4125 }
4126
4127 // make sure the format string is really a string
4128 QualType Ty = getFunctionOrMethodParamType(D, ArgIdx);
4129
4130 if (!isNSStringType(Ty, S.Context, true) &&
4131 !isCFStringType(Ty, S.Context) &&
4132 (!Ty->isPointerType() ||
4134 S.Diag(AL.getLoc(), diag::err_format_attribute_not)
4135 << IdxExpr->getSourceRange() << getFunctionOrMethodParamRange(D, ArgIdx);
4136 return;
4137 }
4138
4139 // check the 3rd argument
4140 Expr *FirstArgExpr = AL.getArgAsExpr(2);
4141 uint32_t FirstArg;
4142 if (!checkUInt32Argument(S, AL, FirstArgExpr, FirstArg, 3))
4143 return;
4144
4145 // FirstArg == 0 is is always valid.
4146 if (FirstArg != 0) {
4147 if (Kind == StrftimeFormat) {
4148 // If the kind is strftime, FirstArg must be 0 because strftime does not
4149 // use any variadic arguments.
4150 S.Diag(AL.getLoc(), diag::err_format_strftime_third_parameter)
4151 << FirstArgExpr->getSourceRange()
4152 << FixItHint::CreateReplacement(FirstArgExpr->getSourceRange(), "0");
4153 return;
4154 } else if (isFunctionOrMethodVariadic(D)) {
4155 // Else, if the function is variadic, then FirstArg must be 0 or the
4156 // "position" of the ... parameter. It's unusual to use 0 with variadic
4157 // functions, so the fixit proposes the latter.
4158 if (FirstArg != NumArgs + 1) {
4159 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
4160 << AL << 3 << FirstArgExpr->getSourceRange()
4162 std::to_string(NumArgs + 1));
4163 return;
4164 }
4165 } else {
4166 // Inescapable GCC compatibility diagnostic.
4167 S.Diag(D->getLocation(), diag::warn_gcc_requires_variadic_function) << AL;
4168 if (FirstArg <= Idx) {
4169 // Else, the function is not variadic, and FirstArg must be 0 or any
4170 // parameter after the format parameter. We don't offer a fixit because
4171 // there are too many possible good values.
4172 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
4173 << AL << 3 << FirstArgExpr->getSourceRange();
4174 return;
4175 }
4176 }
4177 }
4178
4179 FormatAttr *NewAttr = S.mergeFormatAttr(D, AL, II, Idx, FirstArg);
4180 if (NewAttr)
4181 D->addAttr(NewAttr);
4182}
4183
4184/// Handle __attribute__((callback(CalleeIdx, PayloadIdx0, ...))) attributes.
4185static void handleCallbackAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4186 // The index that identifies the callback callee is mandatory.
4187 if (AL.getNumArgs() == 0) {
4188 S.Diag(AL.getLoc(), diag::err_callback_attribute_no_callee)
4189 << AL.getRange();
4190 return;
4191 }
4192
4193 bool HasImplicitThisParam = isInstanceMethod(D);
4194 int32_t NumArgs = getFunctionOrMethodNumParams(D);
4195
4196 FunctionDecl *FD = D->getAsFunction();
4197 assert(FD && "Expected a function declaration!");
4198
4199 llvm::StringMap<int> NameIdxMapping;
4200 NameIdxMapping["__"] = -1;
4201
4202 NameIdxMapping["this"] = 0;
4203
4204 int Idx = 1;
4205 for (const ParmVarDecl *PVD : FD->parameters())
4206 NameIdxMapping[PVD->getName()] = Idx++;
4207
4208 auto UnknownName = NameIdxMapping.end();
4209
4210 SmallVector<int, 8> EncodingIndices;
4211 for (unsigned I = 0, E = AL.getNumArgs(); I < E; ++I) {
4212 SourceRange SR;
4213 int32_t ArgIdx;
4214
4215 if (AL.isArgIdent(I)) {
4216 IdentifierLoc *IdLoc = AL.getArgAsIdent(I);
4217 auto It = NameIdxMapping.find(IdLoc->Ident->getName());
4218 if (It == UnknownName) {
4219 S.Diag(AL.getLoc(), diag::err_callback_attribute_argument_unknown)
4220 << IdLoc->Ident << IdLoc->Loc;
4221 return;
4222 }
4223
4224 SR = SourceRange(IdLoc->Loc);
4225 ArgIdx = It->second;
4226 } else if (AL.isArgExpr(I)) {
4227 Expr *IdxExpr = AL.getArgAsExpr(I);
4228
4229 // If the expression is not parseable as an int32_t we have a problem.
4230 if (!checkUInt32Argument(S, AL, IdxExpr, (uint32_t &)ArgIdx, I + 1,
4231 false)) {
4232 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
4233 << AL << (I + 1) << IdxExpr->getSourceRange();
4234 return;
4235 }
4236
4237 // Check oob, excluding the special values, 0 and -1.
4238 if (ArgIdx < -1 || ArgIdx > NumArgs) {
4239 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
4240 << AL << (I + 1) << IdxExpr->getSourceRange();
4241 return;
4242 }
4243
4244 SR = IdxExpr->getSourceRange();
4245 } else {
4246 llvm_unreachable("Unexpected ParsedAttr argument type!");
4247 }
4248
4249 if (ArgIdx == 0 && !HasImplicitThisParam) {
4250 S.Diag(AL.getLoc(), diag::err_callback_implicit_this_not_available)
4251 << (I + 1) << SR;
4252 return;
4253 }
4254
4255 // Adjust for the case we do not have an implicit "this" parameter. In this
4256 // case we decrease all positive values by 1 to get LLVM argument indices.
4257 if (!HasImplicitThisParam && ArgIdx > 0)
4258 ArgIdx -= 1;
4259
4260 EncodingIndices.push_back(ArgIdx);
4261 }
4262
4263 int CalleeIdx = EncodingIndices.front();
4264 // Check if the callee index is proper, thus not "this" and not "unknown".
4265 // This means the "CalleeIdx" has to be non-negative if "HasImplicitThisParam"
4266 // is false and positive if "HasImplicitThisParam" is true.
4267 if (CalleeIdx < (int)HasImplicitThisParam) {
4268 S.Diag(AL.getLoc(), diag::err_callback_attribute_invalid_callee)
4269 << AL.getRange();
4270 return;
4271 }
4272
4273 // Get the callee type, note the index adjustment as the AST doesn't contain
4274 // the this type (which the callee cannot reference anyway!).
4275 const Type *CalleeType =
4276 getFunctionOrMethodParamType(D, CalleeIdx - HasImplicitThisParam)
4277 .getTypePtr();
4278 if (!CalleeType || !CalleeType->isFunctionPointerType()) {
4279 S.Diag(AL.getLoc(), diag::err_callback_callee_no_function_type)
4280 << AL.getRange();
4281 return;
4282 }
4283
4284 const Type *CalleeFnType =
4286
4287 // TODO: Check the type of the callee arguments.
4288
4289 const auto *CalleeFnProtoType = dyn_cast<FunctionProtoType>(CalleeFnType);
4290 if (!CalleeFnProtoType) {
4291 S.Diag(AL.getLoc(), diag::err_callback_callee_no_function_type)
4292 << AL.getRange();
4293 return;
4294 }
4295
4296 if (CalleeFnProtoType->getNumParams() > EncodingIndices.size() - 1) {
4297 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments)
4298 << AL << (unsigned)(EncodingIndices.size() - 1);
4299 return;
4300 }
4301
4302 if (CalleeFnProtoType->getNumParams() < EncodingIndices.size() - 1) {
4303 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments)
4304 << AL << (unsigned)(EncodingIndices.size() - 1);
4305 return;
4306 }
4307
4308 if (CalleeFnProtoType->isVariadic()) {
4309 S.Diag(AL.getLoc(), diag::err_callback_callee_is_variadic) << AL.getRange();
4310 return;
4311 }
4312
4313 // Do not allow multiple callback attributes.
4314 if (D->hasAttr<CallbackAttr>()) {
4315 S.Diag(AL.getLoc(), diag::err_callback_attribute_multiple) << AL.getRange();
4316 return;
4317 }
4318
4319 D->addAttr(::new (S.Context) CallbackAttr(
4320 S.Context, AL, EncodingIndices.data(), EncodingIndices.size()));
4321}
4322
4323static bool isFunctionLike(const Type &T) {
4324 // Check for explicit function types.
4325 // 'called_once' is only supported in Objective-C and it has
4326 // function pointers and block pointers.
4328}
4329
4330/// Handle 'called_once' attribute.
4331static void handleCalledOnceAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4332 // 'called_once' only applies to parameters representing functions.
4333 QualType T = cast<ParmVarDecl>(D)->getType();
4334
4335 if (!isFunctionLike(*T)) {
4336 S.Diag(AL.getLoc(), diag::err_called_once_attribute_wrong_type);
4337 return;
4338 }
4339
4340 D->addAttr(::new (S.Context) CalledOnceAttr(S.Context, AL));
4341}
4342
4343static void handleTransparentUnionAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4344 // Try to find the underlying union declaration.
4345 RecordDecl *RD = nullptr;
4346 const auto *TD = dyn_cast<TypedefNameDecl>(D);
4347 if (TD && TD->getUnderlyingType()->isUnionType())
4348 RD = TD->getUnderlyingType()->getAsUnionType()->getDecl();
4349 else
4350 RD = dyn_cast<RecordDecl>(D);
4351
4352 if (!RD || !RD->isUnion()) {
4353 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
4355 return;
4356 }
4357
4358 if (!RD->isCompleteDefinition()) {
4359 if (!RD->isBeingDefined())
4360 S.Diag(AL.getLoc(),
4361 diag::warn_transparent_union_attribute_not_definition);
4362 return;
4363 }
4364
4366 FieldEnd = RD->field_end();
4367 if (Field == FieldEnd) {
4368 S.Diag(AL.getLoc(), diag::warn_transparent_union_attribute_zero_fields);
4369 return;
4370 }
4371
4372 FieldDecl *FirstField = *Field;
4373 QualType FirstType = FirstField->getType();
4374 if (FirstType->hasFloatingRepresentation() || FirstType->isVectorType()) {
4375 S.Diag(FirstField->getLocation(),
4376 diag::warn_transparent_union_attribute_floating)
4377 << FirstType->isVectorType() << FirstType;
4378 return;
4379 }
4380
4381 if (FirstType->isIncompleteType())
4382 return;
4383 uint64_t FirstSize = S.Context.getTypeSize(FirstType);
4384 uint64_t FirstAlign = S.Context.getTypeAlign(FirstType);
4385 for (; Field != FieldEnd; ++Field) {
4386 QualType FieldType = Field->getType();
4387 if (FieldType->isIncompleteType())
4388 return;
4389 // FIXME: this isn't fully correct; we also need to test whether the
4390 // members of the union would all have the same calling convention as the
4391 // first member of the union. Checking just the size and alignment isn't
4392 // sufficient (consider structs passed on the stack instead of in registers
4393 // as an example).
4394 if (S.Context.getTypeSize(FieldType) != FirstSize ||
4395 S.Context.getTypeAlign(FieldType) > FirstAlign) {
4396 // Warn if we drop the attribute.
4397 bool isSize = S.Context.getTypeSize(FieldType) != FirstSize;
4398 unsigned FieldBits = isSize ? S.Context.getTypeSize(FieldType)
4399 : S.Context.getTypeAlign(FieldType);
4400 S.Diag(Field->getLocation(),
4401 diag::warn_transparent_union_attribute_field_size_align)
4402 << isSize << *Field << FieldBits;
4403 unsigned FirstBits = isSize ? FirstSize : FirstAlign;
4404 S.Diag(FirstField->getLocation(),
4405 diag::note_transparent_union_first_field_size_align)
4406 << isSize << FirstBits;
4407 return;
4408 }
4409 }
4410
4411 RD->addAttr(::new (S.Context) TransparentUnionAttr(S.Context, AL));
4412}
4413
4415 StringRef Str, MutableArrayRef<Expr *> Args) {
4416 auto *Attr = AnnotateAttr::Create(Context, Str, Args.data(), Args.size(), CI);
4418 CI, MutableArrayRef<Expr *>(Attr->args_begin(), Attr->args_end()))) {
4419 D->addAttr(Attr);
4420 }
4421}
4422
4423static void handleAnnotateAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4424 // Make sure that there is a string literal as the annotation's first
4425 // argument.
4426 StringRef Str;
4427 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str))
4428 return;
4429
4431 Args.reserve(AL.getNumArgs() - 1);
4432 for (unsigned Idx = 1; Idx < AL.getNumArgs(); Idx++) {
4433 assert(!AL.isArgIdent(Idx));
4434 Args.push_back(AL.getArgAsExpr(Idx));
4435 }
4436
4437 S.AddAnnotationAttr(D, AL, Str, Args);
4438}
4439
4440static void handleAlignValueAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4441 S.AddAlignValueAttr(D, AL, AL.getArgAsExpr(0));
4442}
4443
4445 AlignValueAttr TmpAttr(Context, CI, E);
4446 SourceLocation AttrLoc = CI.getLoc();
4447
4448 QualType T;
4449 if (const auto *TD = dyn_cast<TypedefNameDecl>(D))
4450 T = TD->getUnderlyingType();
4451 else if (const auto *VD = dyn_cast<ValueDecl>(D))
4452 T = VD->getType();
4453 else
4454 llvm_unreachable("Unknown decl type for align_value");
4455
4456 if (!T->isDependentType() && !T->isAnyPointerType() &&
4458 Diag(AttrLoc, diag::warn_attribute_pointer_or_reference_only)
4459 << &TmpAttr << T << D->getSourceRange();
4460 return;
4461 }
4462
4463 if (!E->isValueDependent()) {
4464 llvm::APSInt Alignment;
4466 E, &Alignment, diag::err_align_value_attribute_argument_not_int);
4467 if (ICE.isInvalid())
4468 return;
4469
4470 if (!Alignment.isPowerOf2()) {
4471 Diag(AttrLoc, diag::err_alignment_not_power_of_two)
4472 << E->getSourceRange();
4473 return;
4474 }
4475
4476 D->addAttr(::new (Context) AlignValueAttr(Context, CI, ICE.get()));
4477 return;
4478 }
4479
4480 // Save dependent expressions in the AST to be instantiated.
4481 D->addAttr(::new (Context) AlignValueAttr(Context, CI, E));
4482}
4483
4484static void handleAlignedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4485 if (AL.hasParsedType()) {
4486 const ParsedType &TypeArg = AL.getTypeArg();
4487 TypeSourceInfo *TInfo;
4488 (void)S.GetTypeFromParser(
4489 ParsedType::getFromOpaquePtr(TypeArg.getAsOpaquePtr()), &TInfo);
4490 if (AL.isPackExpansion() &&
4492 S.Diag(AL.getEllipsisLoc(),
4493 diag::err_pack_expansion_without_parameter_packs);
4494 return;
4495 }
4496
4497 if (!AL.isPackExpansion() &&
4499 TInfo, Sema::UPPC_Expression))
4500 return;
4501
4502 S.AddAlignedAttr(D, AL, TInfo, AL.isPackExpansion());
4503 return;
4504 }
4505
4506 // check the attribute arguments.
4507 if (AL.getNumArgs() > 1) {
4508 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << AL << 1;
4509 return;
4510 }
4511
4512 if (AL.getNumArgs() == 0) {
4513 D->addAttr(::new (S.Context) AlignedAttr(S.Context, AL, true, nullptr));
4514 return;
4515 }
4516
4517 Expr *E = AL.getArgAsExpr(0);
4519 S.Diag(AL.getEllipsisLoc(),
4520 diag::err_pack_expansion_without_parameter_packs);
4521 return;
4522 }
4523
4525 return;
4526
4527 S.AddAlignedAttr(D, AL, E, AL.isPackExpansion());
4528}
4529
4530/// Perform checking of type validity
4531///
4532/// C++11 [dcl.align]p1:
4533/// An alignment-specifier may be applied to a variable or to a class
4534/// data member, but it shall not be applied to a bit-field, a function
4535/// parameter, the formal parameter of a catch clause, or a variable
4536/// declared with the register storage class specifier. An
4537/// alignment-specifier may also be applied to the declaration of a class
4538/// or enumeration type.
4539/// CWG 2354:
4540/// CWG agreed to remove permission for alignas to be applied to
4541/// enumerations.
4542/// C11 6.7.5/2:
4543/// An alignment attribute shall not be specified in a declaration of
4544/// a typedef, or a bit-field, or a function, or a parameter, or an
4545/// object declared with the register storage-class specifier.
4547 const AlignedAttr &Attr,
4548 SourceLocation AttrLoc) {
4549 int DiagKind = -1;
4550 if (isa<ParmVarDecl>(D)) {
4551 DiagKind = 0;
4552 } else if (const auto *VD = dyn_cast<VarDecl>(D)) {
4553 if (VD->getStorageClass() == SC_Register)
4554 DiagKind = 1;
4555 if (VD->isExceptionVariable())
4556 DiagKind = 2;
4557 } else if (const auto *FD = dyn_cast<FieldDecl>(D)) {
4558 if (FD->isBitField())
4559 DiagKind = 3;
4560 } else if (const auto *ED = dyn_cast<EnumDecl>(D)) {
4561 if (ED->getLangOpts().CPlusPlus)
4562 DiagKind = 4;
4563 } else if (!isa<TagDecl>(D)) {
4564 return S.Diag(AttrLoc, diag::err_attribute_wrong_decl_type)
4566 << (Attr.isC11() ? ExpectedVariableOrField
4568 }
4569 if (DiagKind != -1) {
4570 return S.Diag(AttrLoc, diag::err_alignas_attribute_wrong_decl_type)
4571 << &Attr << DiagKind;
4572 }
4573 return false;
4574}
4575
4577 bool IsPackExpansion) {
4578 AlignedAttr TmpAttr(Context, CI, true, E);
4579 SourceLocation AttrLoc = CI.getLoc();
4580
4581 // C++11 alignas(...) and C11 _Alignas(...) have additional requirements.
4582 if (TmpAttr.isAlignas() &&
4583 validateAlignasAppliedType(*this, D, TmpAttr, AttrLoc))
4584 return;
4585
4586 if (E->isValueDependent()) {
4587 // We can't support a dependent alignment on a non-dependent type,
4588 // because we have no way to model that a type is "alignment-dependent"
4589 // but not dependent in any other way.
4590 if (const auto *TND = dyn_cast<TypedefNameDecl>(D)) {
4591 if (!TND->getUnderlyingType()->isDependentType()) {
4592 Diag(AttrLoc, diag::err_alignment_dependent_typedef_name)
4593 << E->getSourceRange();
4594 return;
4595 }
4596 }
4597
4598 // Save dependent expressions in the AST to be instantiated.
4599 AlignedAttr *AA = ::new (Context) AlignedAttr(Context, CI, true, E);
4600 AA->setPackExpansion(IsPackExpansion);
4601 D->addAttr(AA);
4602 return;
4603 }
4604
4605 // FIXME: Cache the number on the AL object?
4606 llvm::APSInt Alignment;
4608 E, &Alignment, diag::err_aligned_attribute_argument_not_int);
4609 if (ICE.isInvalid())
4610 return;
4611
4613 if (Context.getTargetInfo().getTriple().isOSBinFormatCOFF())
4614 MaximumAlignment = std::min(MaximumAlignment, uint64_t(8192));
4615 if (Alignment > MaximumAlignment) {
4616 Diag(AttrLoc, diag::err_attribute_aligned_too_great)
4618 return;
4619 }
4620
4621 uint64_t AlignVal = Alignment.getZExtValue();
4622 // C++11 [dcl.align]p2:
4623 // -- if the constant expression evaluates to zero, the alignment
4624 // specifier shall have no effect
4625 // C11 6.7.5p6:
4626 // An alignment specification of zero has no effect.
4627 if (!(TmpAttr.isAlignas() && !Alignment)) {
4628 if (!llvm::isPowerOf2_64(AlignVal)) {
4629 Diag(AttrLoc, diag::err_alignment_not_power_of_two)
4630 << E->getSourceRange();
4631 return;
4632 }
4633 }
4634
4635 const auto *VD = dyn_cast<VarDecl>(D);
4636 if (VD) {
4637 unsigned MaxTLSAlign =
4639 .getQuantity();
4640 if (MaxTLSAlign && AlignVal > MaxTLSAlign &&
4641 VD->getTLSKind() != VarDecl::TLS_None) {
4642 Diag(VD->getLocation(), diag::err_tls_var_aligned_over_maximum)
4643 << (unsigned)AlignVal << VD << MaxTLSAlign;
4644 return;
4645 }
4646 }
4647
4648 // On AIX, an aligned attribute can not decrease the alignment when applied
4649 // to a variable declaration with vector type.
4650 if (VD && Context.getTargetInfo().getTriple().isOSAIX()) {
4651 const Type *Ty = VD->getType().getTypePtr();
4652 if (Ty->isVectorType() && AlignVal < 16) {
4653 Diag(VD->getLocation(), diag::warn_aligned_attr_underaligned)
4654 << VD->getType() << 16;
4655 return;
4656 }
4657 }
4658
4659 AlignedAttr *AA = ::new (Context) AlignedAttr(Context, CI, true, ICE.get());
4660 AA->setPackExpansion(IsPackExpansion);
4661 AA->setCachedAlignmentValue(
4662 static_cast<unsigned>(AlignVal * Context.getCharWidth()));
4663 D->addAttr(AA);
4664}
4665
4667 TypeSourceInfo *TS, bool IsPackExpansion) {
4668 AlignedAttr TmpAttr(Context, CI, false, TS);
4669 SourceLocation AttrLoc = CI.getLoc();
4670
4671 // C++11 alignas(...) and C11 _Alignas(...) have additional requirements.
4672 if (TmpAttr.isAlignas() &&
4673 validateAlignasAppliedType(*this, D, TmpAttr, AttrLoc))
4674 return;
4675
4676 if (TS->getType()->isDependentType()) {
4677 // We can't support a dependent alignment on a non-dependent type,
4678 // because we have no way to model that a type is "type-dependent"
4679 // but not dependent in any other way.
4680 if (const auto *TND = dyn_cast<TypedefNameDecl>(D)) {
4681 if (!TND->getUnderlyingType()->isDependentType()) {
4682 Diag(AttrLoc, diag::err_alignment_dependent_typedef_name)
4683 << TS->getTypeLoc().getSourceRange();
4684 return;
4685 }
4686 }
4687
4688 AlignedAttr *AA = ::new (Context) AlignedAttr(Context, CI, false, TS);
4689 AA->setPackExpansion(IsPackExpansion);
4690 D->addAttr(AA);
4691 return;
4692 }
4693
4694 const auto *VD = dyn_cast<VarDecl>(D);
4695 unsigned AlignVal = TmpAttr.getAlignment(Context);
4696 // On AIX, an aligned attribute can not decrease the alignment when applied
4697 // to a variable declaration with vector type.
4698 if (VD && Context.getTargetInfo().getTriple().isOSAIX()) {
4699 const Type *Ty = VD->getType().getTypePtr();
4700 if (Ty->isVectorType() &&
4701 Context.toCharUnitsFromBits(AlignVal).getQuantity() < 16) {
4702 Diag(VD->getLocation(), diag::warn_aligned_attr_underaligned)
4703 << VD->getType() << 16;
4704 return;
4705 }
4706 }
4707
4708 AlignedAttr *AA = ::new (Context) AlignedAttr(Context, CI, false, TS);
4709 AA->setPackExpansion(IsPackExpansion);
4710 AA->setCachedAlignmentValue(AlignVal);
4711 D->addAttr(AA);
4712}
4713
4715 assert(D->hasAttrs() && "no attributes on decl");
4716
4717 QualType UnderlyingTy, DiagTy;
4718 if (const auto *VD = dyn_cast<ValueDecl>(D)) {
4719 UnderlyingTy = DiagTy = VD->getType();
4720 } else {
4721 UnderlyingTy = DiagTy = Context.getTagDeclType(cast<TagDecl>(D));
4722 if (const auto *ED = dyn_cast<EnumDecl>(D))
4723 UnderlyingTy = ED->getIntegerType();
4724 }
4725 if (DiagTy->isDependentType() || DiagTy->isIncompleteType())
4726 return;
4727
4728 // C++11 [dcl.align]p5, C11 6.7.5/4:
4729 // The combined effect of all alignment attributes in a declaration shall
4730 // not specify an alignment that is less strict than the alignment that
4731 // would otherwise be required for the entity being declared.
4732 AlignedAttr *AlignasAttr = nullptr;
4733 AlignedAttr *LastAlignedAttr = nullptr;
4734 unsigned Align = 0;
4735 for (auto *I : D->specific_attrs<AlignedAttr>()) {
4736 if (I->isAlignmentDependent())
4737 return;
4738 if (I->isAlignas())
4739 AlignasAttr = I;
4740 Align = std::max(Align, I->getAlignment(Context));
4741 LastAlignedAttr = I;
4742 }
4743
4744 if (Align && DiagTy->isSizelessType()) {
4745 Diag(LastAlignedAttr->getLocation(), diag::err_attribute_sizeless_type)
4746 << LastAlignedAttr << DiagTy;
4747 } else if (AlignasAttr && Align) {
4748 CharUnits RequestedAlign = Context.toCharUnitsFromBits(Align);
4749 CharUnits NaturalAlign = Context.getTypeAlignInChars(UnderlyingTy);
4750 if (NaturalAlign > RequestedAlign)
4751 Diag(AlignasAttr->getLocation(), diag::err_alignas_underaligned)
4752 << DiagTy << (unsigned)NaturalAlign.getQuantity();
4753 }
4754}
4755
4757 CXXRecordDecl *RD, SourceRange Range, bool BestCase,
4758 MSInheritanceModel ExplicitModel) {
4759 assert(RD->hasDefinition() && "RD has no definition!");
4760
4761 // We may not have seen base specifiers or any virtual methods yet. We will
4762 // have to wait until the record is defined to catch any mismatches.
4763 if (!RD->getDefinition()->isCompleteDefinition())
4764 return false;
4765
4766 // The unspecified model never matches what a definition could need.
4767 if (ExplicitModel == MSInheritanceModel::Unspecified)
4768 return false;
4769
4770 if (BestCase) {
4771 if (RD->calculateInheritanceModel() == ExplicitModel)
4772 return false;
4773 } else {
4774 if (RD->calculateInheritanceModel() <= ExplicitModel)
4775 return false;
4776 }
4777
4778 Diag(Range.getBegin(), diag::err_mismatched_ms_inheritance)
4779 << 0 /*definition*/;
4780 Diag(RD->getDefinition()->getLocation(), diag::note_defined_here) << RD;
4781 return true;
4782}
4783
4784/// parseModeAttrArg - Parses attribute mode string and returns parsed type
4785/// attribute.
4786static void parseModeAttrArg(Sema &S, StringRef Str, unsigned &DestWidth,
4787 bool &IntegerMode, bool &ComplexMode,
4788 FloatModeKind &ExplicitType) {
4789 IntegerMode = true;
4790 ComplexMode = false;
4791 ExplicitType = FloatModeKind::NoFloat;
4792 switch (Str.size()) {
4793 case 2:
4794 switch (Str[0]) {
4795 case 'Q':
4796 DestWidth = 8;
4797 break;
4798 case 'H':
4799 DestWidth = 16;
4800 break;
4801 case 'S':
4802 DestWidth = 32;
4803 break;
4804 case 'D':
4805 DestWidth = 64;
4806 break;
4807 case 'X':
4808 DestWidth = 96;
4809 break;
4810 case 'K': // KFmode - IEEE quad precision (__float128)
4811 ExplicitType = FloatModeKind::Float128;
4812 DestWidth = Str[1] == 'I' ? 0 : 128;
4813 break;
4814 case 'T':
4815 ExplicitType = FloatModeKind::LongDouble;
4816 DestWidth = 128;
4817 break;
4818 case 'I':
4819 ExplicitType = FloatModeKind::Ibm128;
4820 DestWidth = Str[1] == 'I' ? 0 : 128;
4821 break;
4822 }
4823 if (Str[1] == 'F') {
4824 IntegerMode = false;
4825 } else if (Str[1] == 'C') {
4826 IntegerMode = false;
4827 ComplexMode = true;
4828 } else if (Str[1] != 'I') {
4829 DestWidth = 0;
4830 }
4831 break;
4832 case 4:
4833 // FIXME: glibc uses 'word' to define register_t; this is narrower than a
4834 // pointer on PIC16 and other embedded platforms.
4835 if (Str == "word")
4836 DestWidth = S.Context.getTargetInfo().getRegisterWidth();
4837 else if (Str == "byte")
4838 DestWidth = S.Context.getTargetInfo().getCharWidth();
4839 break;
4840 case 7:
4841 if (Str == "pointer")
4843 break;
4844 case 11:
4845 if (Str == "unwind_word")
4846 DestWidth = S.Context.getTargetInfo().getUnwindWordWidth();
4847 break;
4848 }
4849}
4850
4851/// handleModeAttr - This attribute modifies the width of a decl with primitive
4852/// type.
4853///
4854/// Despite what would be logical, the mode attribute is a decl attribute, not a
4855/// type attribute: 'int ** __attribute((mode(HI))) *G;' tries to make 'G' be
4856/// HImode, not an intermediate pointer.
4857static void handleModeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
4858 // This attribute isn't documented, but glibc uses it. It changes
4859 // the width of an int or unsigned int to the specified size.
4860 if (!AL.isArgIdent(0)) {
4861 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
4862 << AL << AANT_ArgumentIdentifier;
4863 return;
4864 }
4865
4866 IdentifierInfo *Name = AL.getArgAsIdent(0)->Ident;
4867
4868 S.AddModeAttr(D, AL, Name);
4869}
4870
4872 IdentifierInfo *Name, bool InInstantiation) {
4873 StringRef Str = Name->getName();
4874 normalizeName(Str);
4875 SourceLocation AttrLoc = CI.getLoc();
4876
4877 unsigned DestWidth = 0;
4878 bool IntegerMode = true;
4879 bool ComplexMode = false;
4881 llvm::APInt VectorSize(64, 0);
4882 if (Str.size() >= 4 && Str[0] == 'V') {
4883 // Minimal length of vector mode is 4: 'V' + NUMBER(>=1) + TYPE(>=2).
4884 size_t StrSize = Str.size();
4885 size_t VectorStringLength = 0;
4886 while ((VectorStringLength + 1) < StrSize &&
4887 isdigit(Str[VectorStringLength + 1]))
4888 ++VectorStringLength;
4889 if (VectorStringLength &&
4890 !Str.substr(1, VectorStringLength).getAsInteger(10, VectorSize) &&
4891 VectorSize.isPowerOf2()) {
4892 parseModeAttrArg(*this, Str.substr(VectorStringLength + 1), DestWidth,
4893 IntegerMode, ComplexMode, ExplicitType);
4894 // Avoid duplicate warning from template instantiation.
4895 if (!InInstantiation)
4896 Diag(AttrLoc, diag::warn_vector_mode_deprecated);
4897 } else {
4898 VectorSize = 0;
4899 }
4900 }
4901
4902 if (!VectorSize)
4903 parseModeAttrArg(*this, Str, DestWidth, IntegerMode, ComplexMode,
4904 ExplicitType);
4905
4906 // FIXME: Sync this with InitializePredefinedMacros; we need to match int8_t
4907 // and friends, at least with glibc.
4908 // FIXME: Make sure floating-point mappings are accurate
4909 // FIXME: Support XF and TF types
4910 if (!DestWidth) {
4911 Diag(AttrLoc, diag::err_machine_mode) << 0 /*Unknown*/ << Name;
4912 return;
4913 }
4914
4915 QualType OldTy;
4916 if (const auto *TD = dyn_cast<TypedefNameDecl>(D))
4917 OldTy = TD->getUnderlyingType();
4918 else if (const auto *ED = dyn_cast<EnumDecl>(D)) {
4919 // Something like 'typedef enum { X } __attribute__((mode(XX))) T;'.
4920 // Try to get type from enum declaration, default to int.
4921 OldTy = ED->getIntegerType();
4922 if (OldTy.isNull())
4923 OldTy = Context.IntTy;
4924 } else
4925 OldTy = cast<ValueDecl>(D)->getType();
4926
4927 if (OldTy->isDependentType()) {
4928 D->addAttr(::new (Context) ModeAttr(Context, CI, Name));
4929 return;
4930 }
4931
4932 // Base type can also be a vector type (see PR17453).
4933 // Distinguish between base type and base element type.
4934 QualType OldElemTy = OldTy;
4935 if (const auto *VT = OldTy->getAs<VectorType>())
4936 OldElemTy = VT->getElementType();
4937
4938 // GCC allows 'mode' attribute on enumeration types (even incomplete), except
4939 // for vector modes. So, 'enum X __attribute__((mode(QI)));' forms a complete
4940 // type, 'enum { A } __attribute__((mode(V4SI)))' is rejected.
4941 if ((isa<EnumDecl>(D) || OldElemTy->getAs<EnumType>()) &&
4942 VectorSize.getBoolValue()) {
4943 Diag(AttrLoc, diag::err_enum_mode_vector_type) << Name << CI.getRange();
4944 return;
4945 }
4946 bool IntegralOrAnyEnumType = (OldElemTy->isIntegralOrEnumerationType() &&
4947 !OldElemTy->isBitIntType()) ||
4948 OldElemTy->getAs<EnumType>();
4949
4950 if (!OldElemTy->getAs<BuiltinType>() && !OldElemTy->isComplexType() &&
4951 !IntegralOrAnyEnumType)
4952 Diag(AttrLoc, diag::err_mode_not_primitive);
4953 else if (IntegerMode) {
4954 if (!IntegralOrAnyEnumType)
4955 Diag(AttrLoc, diag::err_mode_wrong_type);
4956 } else if (ComplexMode) {
4957 if (!OldElemTy->isComplexType())
4958 Diag(AttrLoc, diag::err_mode_wrong_type);
4959 } else {
4960 if (!OldElemTy->isFloatingType())
4961 Diag(AttrLoc, diag::err_mode_wrong_type);
4962 }
4963
4964 QualType NewElemTy;
4965
4966 if (IntegerMode)
4967 NewElemTy = Context.getIntTypeForBitwidth(DestWidth,
4968 OldElemTy->isSignedIntegerType());
4969 else
4970 NewElemTy = Context.getRealTypeForBitwidth(DestWidth, ExplicitType);
4971
4972 if (NewElemTy.isNull()) {
4973 // Only emit diagnostic on host for 128-bit mode attribute
4974 if (!(DestWidth == 128 && getLangOpts().CUDAIsDevice))
4975 Diag(AttrLoc, diag::err_machine_mode) << 1 /*Unsupported*/ << Name;
4976 return;
4977 }
4978
4979 if (ComplexMode) {
4980 NewElemTy = Context.getComplexType(NewElemTy);
4981 }
4982
4983 QualType NewTy = NewElemTy;
4984 if (VectorSize.getBoolValue()) {
4985 NewTy = Context.getVectorType(NewTy, VectorSize.getZExtValue(),
4987 } else if (const auto *OldVT = OldTy->getAs<VectorType>()) {
4988 // Complex machine mode does not support base vector types.
4989 if (ComplexMode) {
4990 Diag(AttrLoc, diag::err_complex_mode_vector_type);
4991 return;
4992 }
4993 unsigned NumElements = Context.getTypeSize(OldElemTy) *
4994 OldVT->getNumElements() /
4995 Context.getTypeSize(NewElemTy);
4996 NewTy =
4997 Context.getVectorType(NewElemTy, NumElements, OldVT->getVectorKind());
4998 }
4999
5000 if (NewTy.isNull()) {
5001 Diag(AttrLoc, diag::err_mode_wrong_type);
5002 return;
5003 }
5004
5005 // Install the new type.
5006 if (auto *TD = dyn_cast<TypedefNameDecl>(D))
5007 TD->setModedTypeSourceInfo(TD->getTypeSourceInfo(), NewTy);
5008 else if (auto *ED = dyn_cast<EnumDecl>(D))
5009 ED->setIntegerType(NewTy);
5010 else
5011 cast<ValueDecl>(D)->setType(NewTy);
5012
5013 D->addAttr(::new (Context) ModeAttr(Context, CI, Name));
5014}
5015
5016static void handleNoDebugAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5017 D->addAttr(::new (S.Context) NoDebugAttr(S.Context, AL));
5018}
5019
5021 const AttributeCommonInfo &CI,
5022 const IdentifierInfo *Ident) {
5023 if (OptimizeNoneAttr *Optnone = D->getAttr<OptimizeNoneAttr>()) {
5024 Diag(CI.getLoc(), diag::warn_attribute_ignored) << Ident;
5025 Diag(Optnone->getLocation(), diag::note_conflicting_attribute);
5026 return nullptr;
5027 }
5028
5029 if (D->hasAttr<AlwaysInlineAttr>())
5030 return nullptr;
5031
5032 return ::new (Context) AlwaysInlineAttr(Context, CI);
5033}
5034
5035InternalLinkageAttr *Sema::mergeInternalLinkageAttr(Decl *D,
5036 const ParsedAttr &AL) {
5037 if (const auto *VD = dyn_cast<VarDecl>(D)) {
5038 // Attribute applies to Var but not any subclass of it (like ParmVar,
5039 // ImplicitParm or VarTemplateSpecialization).
5040 if (VD->getKind() != Decl::Var) {
5041 Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
5042 << AL << AL.isRegularKeywordAttribute()
5045 return nullptr;
5046 }
5047 // Attribute does not apply to non-static local variables.
5048 if (VD->hasLocalStorage()) {
5049 Diag(VD->getLocation(), diag::warn_internal_linkage_local_storage);
5050 return nullptr;
5051 }
5052 }
5053
5054 return ::new (Context) InternalLinkageAttr(Context, AL);
5055}
5056InternalLinkageAttr *
5057Sema::mergeInternalLinkageAttr(Decl *D, const InternalLinkageAttr &AL) {
5058 if (const auto *VD = dyn_cast<VarDecl>(D)) {
5059 // Attribute applies to Var but not any subclass of it (like ParmVar,
5060 // ImplicitParm or VarTemplateSpecialization).
5061 if (VD->getKind() != Decl::Var) {
5062 Diag(AL.getLocation(), diag::warn_attribute_wrong_decl_type)
5063 << &AL << AL.isRegularKeywordAttribute()
5066 return nullptr;
5067 }
5068 // Attribute does not apply to non-static local variables.
5069 if (VD->hasLocalStorage()) {
5070 Diag(VD->getLocation(), diag::warn_internal_linkage_local_storage);
5071 return nullptr;
5072 }
5073 }
5074
5075 return ::new (Context) InternalLinkageAttr(Context, AL);
5076}
5077
5079 if (OptimizeNoneAttr *Optnone = D->getAttr<OptimizeNoneAttr>()) {
5080 Diag(CI.getLoc(), diag::warn_attribute_ignored) << "'minsize'";
5081 Diag(Optnone->getLocation(), diag::note_conflicting_attribute);
5082 return nullptr;
5083 }
5084
5085 if (D->hasAttr<MinSizeAttr>())
5086 return nullptr;
5087
5088 return ::new (Context) MinSizeAttr(Context, CI);
5089}
5090
5091SwiftNameAttr *Sema::mergeSwiftNameAttr(Decl *D, const SwiftNameAttr &SNA,
5092 StringRef Name) {
5093 if (const auto *PrevSNA = D->getAttr<SwiftNameAttr>()) {
5094 if (PrevSNA->getName() != Name && !PrevSNA->isImplicit()) {
5095 Diag(PrevSNA->getLocation(), diag::err_attributes_are_not_compatible)
5096 << PrevSNA << &SNA
5097 << (PrevSNA->isRegularKeywordAttribute() ||
5098 SNA.isRegularKeywordAttribute());
5099 Diag(SNA.getLoc(), diag::note_conflicting_attribute);
5100 }
5101
5102 D->dropAttr<SwiftNameAttr>();
5103 }
5104 return ::new (Context) SwiftNameAttr(Context, SNA, Name);
5105}
5106
5108 const AttributeCommonInfo &CI) {
5109 if (AlwaysInlineAttr *Inline = D->getAttr<AlwaysInlineAttr>()) {
5110 Diag(Inline->getLocation(), diag::warn_attribute_ignored) << Inline;
5111 Diag(CI.getLoc(), diag::note_conflicting_attribute);
5112 D->dropAttr<AlwaysInlineAttr>();
5113 }
5114 if (MinSizeAttr *MinSize = D->getAttr<MinSizeAttr>()) {
5115 Diag(MinSize->getLocation(), diag::warn_attribute_ignored) << MinSize;
5116 Diag(CI.getLoc(), diag::note_conflicting_attribute);
5117 D->dropAttr<MinSizeAttr>();
5118 }
5119
5120 if (D->hasAttr<OptimizeNoneAttr>())
5121 return nullptr;
5122
5123 return ::new (Context) OptimizeNoneAttr(Context, CI);
5124}
5125
5126static void handleAlwaysInlineAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5127 if (AlwaysInlineAttr *Inline =
5128 S.mergeAlwaysInlineAttr(D, AL, AL.getAttrName()))
5129 D->addAttr(Inline);
5130}
5131
5132static void handleMinSizeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5133 if (MinSizeAttr *MinSize = S.mergeMinSizeAttr(D, AL))
5134 D->addAttr(MinSize);
5135}
5136
5137static void handleOptimizeNoneAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5138 if (OptimizeNoneAttr *Optnone = S.mergeOptimizeNoneAttr(D, AL))
5139 D->addAttr(Optnone);
5140}
5141
5142static void handleConstantAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5143 const auto *VD = cast<VarDecl>(D);
5144 if (VD->hasLocalStorage()) {
5145 S.Diag(AL.getLoc(), diag::err_cuda_nonstatic_constdev);
5146 return;
5147 }
5148 // constexpr variable may already get an implicit constant attr, which should
5149 // be replaced by the explicit constant attr.
5150 if (auto *A = D->getAttr<CUDAConstantAttr>()) {
5151 if (!A->isImplicit())
5152 return;
5153 D->dropAttr<CUDAConstantAttr>();
5154 }
5155 D->addAttr(::new (S.Context) CUDAConstantAttr(S.Context, AL));
5156}
5157
5158static void handleSharedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5159 const auto *VD = cast<VarDecl>(D);
5160 // extern __shared__ is only allowed on arrays with no length (e.g.
5161 // "int x[]").
5162 if (!S.getLangOpts().GPURelocatableDeviceCode && VD->hasExternalStorage() &&
5163 !isa<IncompleteArrayType>(VD->getType())) {
5164 S.Diag(AL.getLoc(), diag::err_cuda_extern_shared) << VD;
5165 return;
5166 }
5167 if (S.getLangOpts().CUDA && VD->hasLocalStorage() &&
5168 S.CUDA().DiagIfHostCode(AL.getLoc(), diag::err_cuda_host_shared)
5169 << llvm::to_underlying(S.CUDA().CurrentTarget()))
5170 return;
5171 D->addAttr(::new (S.Context) CUDASharedAttr(S.Context, AL));
5172}
5173
5174static void handleGlobalAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5175 const auto *FD = cast<FunctionDecl>(D);
5176 if (!FD->getReturnType()->isVoidType() &&
5177 !FD->getReturnType()->getAs<AutoType>() &&
5179 SourceRange RTRange = FD->getReturnTypeSourceRange();
5180 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return)
5181 << FD->getType()
5182 << (RTRange.isValid() ? FixItHint::CreateReplacement(RTRange, "void")
5183 : FixItHint());
5184 return;
5185 }
5186 if (const auto *Method = dyn_cast<CXXMethodDecl>(FD)) {
5187 if (Method->isInstance()) {
5188 S.Diag(Method->getBeginLoc(), diag::err_kern_is_nonstatic_method)
5189 << Method;
5190 return;
5191 }
5192 S.Diag(Method->getBeginLoc(), diag::warn_kern_is_method) << Method;
5193 }
5194 // Only warn for "inline" when compiling for host, to cut down on noise.
5195 if (FD->isInlineSpecified() && !S.getLangOpts().CUDAIsDevice)
5196 S.Diag(FD->getBeginLoc(), diag::warn_kern_is_inline) << FD;
5197
5198 if (AL.getKind() == ParsedAttr::AT_NVPTXKernel)
5199 D->addAttr(::new (S.Context) NVPTXKernelAttr(S.Context, AL));
5200 else
5201 D->addAttr(::new (S.Context) CUDAGlobalAttr(S.Context, AL));
5202 // In host compilation the kernel is emitted as a stub function, which is
5203 // a helper function for launching the kernel. The instructions in the helper
5204 // function has nothing to do with the source code of the kernel. Do not emit
5205 // debug info for the stub function to avoid confusing the debugger.
5206 if (S.LangOpts.HIP && !S.LangOpts.CUDAIsDevice)
5207 D->addAttr(NoDebugAttr::CreateImplicit(S.Context));
5208}
5209
5210static void handleDeviceAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5211 if (const auto *VD = dyn_cast<VarDecl>(D)) {
5212 if (VD->hasLocalStorage()) {
5213 S.Diag(AL.getLoc(), diag::err_cuda_nonstatic_constdev);
5214 return;
5215 }
5216 }
5217
5218 if (auto *A = D->getAttr<CUDADeviceAttr>()) {
5219 if (!A->isImplicit())
5220 return;
5221 D->dropAttr<CUDADeviceAttr>();
5222 }
5223 D->addAttr(::new (S.Context) CUDADeviceAttr(S.Context, AL));
5224}
5225
5226static void handleManagedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5227 if (const auto *VD = dyn_cast<VarDecl>(D)) {
5228 if (VD->hasLocalStorage()) {
5229 S.Diag(AL.getLoc(), diag::err_cuda_nonstatic_constdev);
5230 return;
5231 }
5232 }
5233 if (!D->hasAttr<HIPManagedAttr>())
5234 D->addAttr(::new (S.Context) HIPManagedAttr(S.Context, AL));
5235 if (!D->hasAttr<CUDADeviceAttr>())
5236 D->addAttr(CUDADeviceAttr::CreateImplicit(S.Context));
5237}
5238
5239static void handleGNUInlineAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5240 const auto *Fn = cast<FunctionDecl>(D);
5241 if (!Fn->isInlineSpecified()) {
5242 S.Diag(AL.getLoc(), diag::warn_gnu_inline_attribute_requires_inline);
5243 return;
5244 }
5245
5246 if (S.LangOpts.CPlusPlus && Fn->getStorageClass() != SC_Extern)
5247 S.Diag(AL.getLoc(), diag::warn_gnu_inline_cplusplus_without_extern);
5248
5249 D->addAttr(::new (S.Context) GNUInlineAttr(S.Context, AL));
5250}
5251
5252static void handleCallConvAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5253 if (hasDeclarator(D)) return;
5254
5255 // Diagnostic is emitted elsewhere: here we store the (valid) AL
5256 // in the Decl node for syntactic reasoning, e.g., pretty-printing.
5257 CallingConv CC;
5259 AL, CC, /*FD*/ nullptr,
5260 S.CUDA().IdentifyTarget(dyn_cast<FunctionDecl>(D))))
5261 return;
5262
5263 if (!isa<ObjCMethodDecl>(D)) {
5264 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
5266 return;
5267 }
5268
5269 switch (AL.getKind()) {
5270 case ParsedAttr::AT_FastCall:
5271 D->addAttr(::new (S.Context) FastCallAttr(S.Context, AL));
5272 return;
5273 case ParsedAttr::AT_StdCall:
5274 D->addAttr(::new (S.Context) StdCallAttr(S.Context, AL));
5275 return;
5276 case ParsedAttr::AT_ThisCall:
5277 D->addAttr(::new (S.Context) ThisCallAttr(S.Context, AL));
5278 return;
5279 case ParsedAttr::AT_CDecl:
5280 D->addAttr(::new (S.Context) CDeclAttr(S.Context, AL));
5281 return;
5282 case ParsedAttr::AT_Pascal:
5283 D->addAttr(::new (S.Context) PascalAttr(S.Context, AL));
5284 return;
5285 case ParsedAttr::AT_SwiftCall:
5286 D->addAttr(::new (S.Context) SwiftCallAttr(S.Context, AL));
5287 return;
5288 case ParsedAttr::AT_SwiftAsyncCall:
5289 D->addAttr(::new (S.Context) SwiftAsyncCallAttr(S.Context, AL));
5290 return;
5291 case ParsedAttr::AT_VectorCall:
5292 D->addAttr(::new (S.Context) VectorCallAttr(S.Context, AL));
5293 return;
5294 case ParsedAttr::AT_MSABI:
5295 D->addAttr(::new (S.Context) MSABIAttr(S.Context, AL));
5296 return;
5297 case ParsedAttr::AT_SysVABI:
5298 D->addAttr(::new (S.Context) SysVABIAttr(S.Context, AL));
5299 return;
5300 case ParsedAttr::AT_RegCall:
5301 D->addAttr(::new (S.Context) RegCallAttr(S.Context, AL));
5302 return;
5303 case ParsedAttr::AT_Pcs: {
5304 PcsAttr::PCSType PCS;
5305 switch (CC) {
5306 case CC_AAPCS:
5307 PCS = PcsAttr::AAPCS;
5308 break;
5309 case CC_AAPCS_VFP:
5310 PCS = PcsAttr::AAPCS_VFP;
5311 break;
5312 default:
5313 llvm_unreachable("unexpected calling convention in pcs attribute");
5314 }
5315
5316 D->addAttr(::new (S.Context) PcsAttr(S.Context, AL, PCS));
5317 return;
5318 }
5319 case ParsedAttr::AT_AArch64VectorPcs:
5320 D->addAttr(::new (S.Context) AArch64VectorPcsAttr(S.Context, AL));
5321 return;
5322 case ParsedAttr::AT_AArch64SVEPcs:
5323 D->addAttr(::new (S.Context) AArch64SVEPcsAttr(S.Context, AL));
5324 return;
5325 case ParsedAttr::AT_AMDGPUKernelCall:
5326 D->addAttr(::new (S.Context) AMDGPUKernelCallAttr(S.Context, AL));
5327 return;
5328 case ParsedAttr::AT_IntelOclBicc:
5329 D->addAttr(::new (S.Context) IntelOclBiccAttr(S.Context, AL));
5330 return;
5331 case ParsedAttr::AT_PreserveMost:
5332 D->addAttr(::new (S.Context) PreserveMostAttr(S.Context, AL));
5333 return;
5334 case ParsedAttr::AT_PreserveAll:
5335 D->addAttr(::new (S.Context) PreserveAllAttr(S.Context, AL));
5336 return;
5337 case ParsedAttr::AT_M68kRTD:
5338 D->addAttr(::new (S.Context) M68kRTDAttr(S.Context, AL));
5339 return;
5340 case ParsedAttr::AT_PreserveNone:
5341 D->addAttr(::new (S.Context) PreserveNoneAttr(S.Context, AL));
5342 return;
5343 case ParsedAttr::AT_RISCVVectorCC:
5344 D->addAttr(::new (S.Context) RISCVVectorCCAttr(S.Context, AL));
5345 return;
5346 default:
5347 llvm_unreachable("unexpected attribute kind");
5348 }
5349}
5350
5351static void handleSuppressAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5352 if (AL.getAttributeSpellingListIndex() == SuppressAttr::CXX11_gsl_suppress) {
5353 // Suppression attribute with GSL spelling requires at least 1 argument.
5354 if (!AL.checkAtLeastNumArgs(S, 1))
5355 return;
5356 }
5357
5358 std::vector<StringRef> DiagnosticIdentifiers;
5359 for (unsigned I = 0, E = AL.getNumArgs(); I != E; ++I) {
5360 StringRef RuleName;
5361
5362 if (!S.checkStringLiteralArgumentAttr(AL, I, RuleName, nullptr))
5363 return;
5364
5365 DiagnosticIdentifiers.push_back(RuleName);
5366 }
5367 D->addAttr(::new (S.Context)
5368 SuppressAttr(S.Context, AL, DiagnosticIdentifiers.data(),
5369 DiagnosticIdentifiers.size()));
5370}
5371
5372static void handleLifetimeCategoryAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5373 TypeSourceInfo *DerefTypeLoc = nullptr;
5374 QualType ParmType;
5375 if (AL.hasParsedType()) {
5376 ParmType = S.GetTypeFromParser(AL.getTypeArg(), &DerefTypeLoc);
5377
5378 unsigned SelectIdx = ~0U;
5379 if (ParmType->isReferenceType())
5380 SelectIdx = 0;
5381 else if (ParmType->isArrayType())
5382 SelectIdx = 1;
5383
5384 if (SelectIdx != ~0U) {
5385 S.Diag(AL.getLoc(), diag::err_attribute_invalid_argument)
5386 << SelectIdx << AL;
5387 return;
5388 }
5389 }
5390
5391 // To check if earlier decl attributes do not conflict the newly parsed ones
5392 // we always add (and check) the attribute to the canonical decl. We need
5393 // to repeat the check for attribute mutual exclusion because we're attaching
5394 // all of the attributes to the canonical declaration rather than the current
5395 // declaration.
5396 D = D->getCanonicalDecl();
5397 if (AL.getKind() == ParsedAttr::AT_Owner) {
5398 if (checkAttrMutualExclusion<PointerAttr>(S, D, AL))
5399 return;
5400 if (const auto *OAttr = D->getAttr<OwnerAttr>()) {
5401 const Type *ExistingDerefType = OAttr->getDerefTypeLoc()
5402 ? OAttr->getDerefType().getTypePtr()
5403 : nullptr;
5404 if (ExistingDerefType != ParmType.getTypePtrOrNull()) {
5405 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible)
5406 << AL << OAttr
5407 << (AL.isRegularKeywordAttribute() ||
5408 OAttr->isRegularKeywordAttribute());
5409 S.Diag(OAttr->getLocation(), diag::note_conflicting_attribute);
5410 }
5411 return;
5412 }
5413 for (Decl *Redecl : D->redecls()) {
5414 Redecl->addAttr(::new (S.Context) OwnerAttr(S.Context, AL, DerefTypeLoc));
5415 }
5416 } else {
5417 if (checkAttrMutualExclusion<OwnerAttr>(S, D, AL))
5418 return;
5419 if (const auto *PAttr = D->getAttr<PointerAttr>()) {
5420 const Type *ExistingDerefType = PAttr->getDerefTypeLoc()
5421 ? PAttr->getDerefType().getTypePtr()
5422 : nullptr;
5423 if (ExistingDerefType != ParmType.getTypePtrOrNull()) {
5424 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible)
5425 << AL << PAttr
5426 << (AL.isRegularKeywordAttribute() ||
5427 PAttr->isRegularKeywordAttribute());
5428 S.Diag(PAttr->getLocation(), diag::note_conflicting_attribute);
5429 }
5430 return;
5431 }
5432 for (Decl *Redecl : D->redecls()) {
5433 Redecl->addAttr(::new (S.Context)
5434 PointerAttr(S.Context, AL, DerefTypeLoc));
5435 }
5436 }
5437}
5438
5439static void handleRandomizeLayoutAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5440 if (checkAttrMutualExclusion<NoRandomizeLayoutAttr>(S, D, AL))
5441 return;
5442 if (!D->hasAttr<RandomizeLayoutAttr>())
5443 D->addAttr(::new (S.Context) RandomizeLayoutAttr(S.Context, AL));
5444}
5445
5447 const ParsedAttr &AL) {
5448 if (checkAttrMutualExclusion<RandomizeLayoutAttr>(S, D, AL))
5449 return;
5450 if (!D->hasAttr<NoRandomizeLayoutAttr>())
5451 D->addAttr(::new (S.Context) NoRandomizeLayoutAttr(S.Context, AL));
5452}
5453
5455 const FunctionDecl *FD,
5456 CUDAFunctionTarget CFT) {
5457 if (Attrs.isInvalid())
5458 return true;
5459
5460 if (Attrs.hasProcessingCache()) {
5461 CC = (CallingConv) Attrs.getProcessingCache();
5462 return false;
5463 }
5464
5465 unsigned ReqArgs = Attrs.getKind() == ParsedAttr::AT_Pcs ? 1 : 0;
5466 if (!Attrs.checkExactlyNumArgs(*this, ReqArgs)) {
5467 Attrs.setInvalid();
5468 return true;
5469 }
5470
5471 // TODO: diagnose uses of these conventions on the wrong target.
5472 switch (Attrs.getKind()) {
5473 case ParsedAttr::AT_CDecl:
5474 CC = CC_C;
5475 break;
5476 case ParsedAttr::AT_FastCall:
5477 CC = CC_X86FastCall;
5478 break;
5479 case ParsedAttr::AT_StdCall:
5480 CC = CC_X86StdCall;
5481 break;
5482 case ParsedAttr::AT_ThisCall:
5483 CC = CC_X86ThisCall;
5484 break;
5485 case ParsedAttr::AT_Pascal:
5486 CC = CC_X86Pascal;
5487 break;
5488 case ParsedAttr::AT_SwiftCall:
5489 CC = CC_Swift;
5490 break;
5491 case ParsedAttr::AT_SwiftAsyncCall:
5492 CC = CC_SwiftAsync;
5493 break;
5494 case ParsedAttr::AT_VectorCall:
5495 CC = CC_X86VectorCall;
5496 break;
5497 case ParsedAttr::AT_AArch64VectorPcs:
5499 break;
5500 case ParsedAttr::AT_AArch64SVEPcs:
5501 CC = CC_AArch64SVEPCS;
5502 break;
5503 case ParsedAttr::AT_AMDGPUKernelCall:
5505 break;
5506 case ParsedAttr::AT_RegCall:
5507 CC = CC_X86RegCall;
5508 break;
5509 case ParsedAttr::AT_MSABI:
5510 CC = Context.getTargetInfo().getTriple().isOSWindows() ? CC_C :
5511 CC_Win64;
5512 break;
5513 case ParsedAttr::AT_SysVABI:
5514 CC = Context.getTargetInfo().getTriple().isOSWindows() ? CC_X86_64SysV :
5515 CC_C;
5516 break;
5517 case ParsedAttr::AT_Pcs: {
5518 StringRef StrRef;
5519 if (!checkStringLiteralArgumentAttr(Attrs, 0, StrRef)) {
5520 Attrs.setInvalid();
5521 return true;
5522 }
5523 if (StrRef == "aapcs") {
5524 CC = CC_AAPCS;
5525 break;
5526 } else if (StrRef == "aapcs-vfp") {
5527 CC = CC_AAPCS_VFP;
5528 break;
5529 }
5530
5531 Attrs.setInvalid();
5532 Diag(Attrs.getLoc(), diag::err_invalid_pcs);
5533 return true;
5534 }
5535 case ParsedAttr::AT_IntelOclBicc:
5536 CC = CC_IntelOclBicc;
5537 break;
5538 case ParsedAttr::AT_PreserveMost:
5539 CC = CC_PreserveMost;
5540 break;
5541 case ParsedAttr::AT_PreserveAll:
5542 CC = CC_PreserveAll;
5543 break;
5544 case ParsedAttr::AT_M68kRTD:
5545 CC = CC_M68kRTD;
5546 break;
5547 case ParsedAttr::AT_PreserveNone:
5548 CC = CC_PreserveNone;
5549 break;
5550 case ParsedAttr::AT_RISCVVectorCC:
5551 CC = CC_RISCVVectorCall;
5552 break;
5553 default: llvm_unreachable("unexpected attribute kind");
5554 }
5555
5557 const TargetInfo &TI = Context.getTargetInfo();
5558 // CUDA functions may have host and/or device attributes which indicate
5559 // their targeted execution environment, therefore the calling convention
5560 // of functions in CUDA should be checked against the target deduced based
5561 // on their host/device attributes.
5562 if (LangOpts.CUDA) {
5563 auto *Aux = Context.getAuxTargetInfo();
5564 assert(FD || CFT != CUDAFunctionTarget::InvalidTarget);
5565 auto CudaTarget = FD ? CUDA().IdentifyTarget(FD) : CFT;
5566 bool CheckHost = false, CheckDevice = false;
5567 switch (CudaTarget) {
5569 CheckHost = true;
5570 CheckDevice = true;
5571 break;
5573 CheckHost = true;
5574 break;
5577 CheckDevice = true;
5578 break;
5580 llvm_unreachable("unexpected cuda target");
5581 }
5582 auto *HostTI = LangOpts.CUDAIsDevice ? Aux : &TI;
5583 auto *DeviceTI = LangOpts.CUDAIsDevice ? &TI : Aux;
5584 if (CheckHost && HostTI)
5585 A = HostTI->checkCallingConvention(CC);
5586 if (A == TargetInfo::CCCR_OK && CheckDevice && DeviceTI)
5587 A = DeviceTI->checkCallingConvention(CC);
5588 } else {
5589 A = TI.checkCallingConvention(CC);
5590 }
5591
5592 switch (A) {
5594 break;
5595
5597 // Treat an ignored convention as if it was an explicit C calling convention
5598 // attribute. For example, __stdcall on Win x64 functions as __cdecl, so
5599 // that command line flags that change the default convention to
5600 // __vectorcall don't affect declarations marked __stdcall.
5601 CC = CC_C;
5602 break;
5603
5605 Diag(Attrs.getLoc(), diag::error_cconv_unsupported)
5607 break;
5608
5610 Diag(Attrs.getLoc(), diag::warn_cconv_unsupported)
5612
5613 // This convention is not valid for the target. Use the default function or
5614 // method calling convention.
5615 bool IsCXXMethod = false, IsVariadic = false;
5616 if (FD) {
5617 IsCXXMethod = FD->isCXXInstanceMember();
5618 IsVariadic = FD->isVariadic();
5619 }
5620 CC = Context.getDefaultCallingConvention(IsVariadic, IsCXXMethod);
5621 break;
5622 }
5623 }
5624
5625 Attrs.setProcessingCache((unsigned) CC);
5626 return false;
5627}
5628
5629/// Pointer-like types in the default address space.
5631 if (!Ty->hasPointerRepresentation())
5632 return Ty->isDependentType();
5634}
5635
5636/// Pointers and references in the default address space.
5638 if (const auto *PtrType = Ty->getAs<PointerType>()) {
5639 Ty = PtrType->getPointeeType();
5640 } else if (const auto *RefType = Ty->getAs<ReferenceType>()) {
5641 Ty = RefType->getPointeeType();
5642 } else {
5643 return Ty->isDependentType();
5644 }
5645 return Ty.getAddressSpace() == LangAS::Default;
5646}
5647
5648/// Pointers and references to pointers in the default address space.
5650 if (const auto *PtrType = Ty->getAs<PointerType>()) {
5651 Ty = PtrType->getPointeeType();
5652 } else if (const auto *RefType = Ty->getAs<ReferenceType>()) {
5653 Ty = RefType->getPointeeType();
5654 } else {
5655 return Ty->isDependentType();
5656 }
5657 if (!Ty.getQualifiers().empty())
5658 return false;
5659 return isValidSwiftContextType(Ty);
5660}
5661
5663 ParameterABI abi) {
5664
5665 QualType type = cast<ParmVarDecl>(D)->getType();
5666
5667 if (auto existingAttr = D->getAttr<ParameterABIAttr>()) {
5668 if (existingAttr->getABI() != abi) {
5669 Diag(CI.getLoc(), diag::err_attributes_are_not_compatible)
5670 << getParameterABISpelling(abi) << existingAttr
5671 << (CI.isRegularKeywordAttribute() ||
5672 existingAttr->isRegularKeywordAttribute());
5673 Diag(existingAttr->getLocation(), diag::note_conflicting_attribute);
5674 return;
5675 }
5676 }
5677
5678 switch (abi) {
5680 llvm_unreachable("explicit attribute for ordinary parameter ABI?");
5681
5684 Diag(CI.getLoc(), diag::err_swift_abi_parameter_wrong_type)
5685 << getParameterABISpelling(abi) << /*pointer to pointer */ 0 << type;
5686 }
5687 D->addAttr(::new (Context) SwiftContextAttr(Context, CI));
5688 return;
5689
5692 Diag(CI.getLoc(), diag::err_swift_abi_parameter_wrong_type)
5693 << getParameterABISpelling(abi) << /*pointer to pointer */ 0 << type;
5694 }
5695 D->addAttr(::new (Context) SwiftAsyncContextAttr(Context, CI));
5696 return;
5697
5700 Diag(CI.getLoc(), diag::err_swift_abi_parameter_wrong_type)
5701 << getParameterABISpelling(abi) << /*pointer to pointer */ 1 << type;
5702 }
5703 D->addAttr(::new (Context) SwiftErrorResultAttr(Context, CI));
5704 return;
5705
5708 Diag(CI.getLoc(), diag::err_swift_abi_parameter_wrong_type)
5709 << getParameterABISpelling(abi) << /*pointer*/ 0 << type;
5710 }
5711 D->addAttr(::new (Context) SwiftIndirectResultAttr(Context, CI));
5712 return;
5713 }
5714 llvm_unreachable("bad parameter ABI attribute");
5715}
5716
5717/// Checks a regparm attribute, returning true if it is ill-formed and
5718/// otherwise setting numParams to the appropriate value.
5719bool Sema::CheckRegparmAttr(const ParsedAttr &AL, unsigned &numParams) {
5720 if (AL.isInvalid())
5721 return true;
5722
5723 if (!AL.checkExactlyNumArgs(*this, 1)) {
5724 AL.setInvalid();
5725 return true;
5726 }
5727
5728 uint32_t NP;
5729 Expr *NumParamsExpr = AL.getArgAsExpr(0);
5730 if (!checkUInt32Argument(*this, AL, NumParamsExpr, NP)) {
5731 AL.setInvalid();
5732 return true;
5733 }
5734
5735 if (Context.getTargetInfo().getRegParmMax() == 0) {
5736 Diag(AL.getLoc(), diag::err_attribute_regparm_wrong_platform)
5737 << NumParamsExpr->getSourceRange();
5738 AL.setInvalid();
5739 return true;
5740 }
5741
5742 numParams = NP;
5743 if (numParams > Context.getTargetInfo().getRegParmMax()) {
5744 Diag(AL.getLoc(), diag::err_attribute_regparm_invalid_number)
5745 << Context.getTargetInfo().getRegParmMax() << NumParamsExpr->getSourceRange();
5746 AL.setInvalid();
5747 return true;
5748 }
5749
5750 return false;
5751}
5752
5753// Helper to get CudaArch.
5755 if (!TI.getTriple().isNVPTX())
5756 llvm_unreachable("getCudaArch is only valid for NVPTX triple");
5757 auto &TO = TI.getTargetOpts();
5758 return StringToCudaArch(TO.CPU);
5759}
5760
5761// Checks whether an argument of launch_bounds attribute is
5762// acceptable, performs implicit conversion to Rvalue, and returns
5763// non-nullptr Expr result on success. Otherwise, it returns nullptr
5764// and may output an error.
5766 const CUDALaunchBoundsAttr &AL,
5767 const unsigned Idx) {
5769 return nullptr;
5770
5771 // Accept template arguments for now as they depend on something else.
5772 // We'll get to check them when they eventually get instantiated.
5773 if (E->isValueDependent())
5774 return E;
5775
5776 std::optional<llvm::APSInt> I = llvm::APSInt(64);
5777 if (!(I = E->getIntegerConstantExpr(S.Context))) {
5778 S.Diag(E->getExprLoc(), diag::err_attribute_argument_n_type)
5779 << &AL << Idx << AANT_ArgumentIntegerConstant << E->getSourceRange();
5780 return nullptr;
5781 }
5782 // Make sure we can fit it in 32 bits.
5783 if (!I->isIntN(32)) {
5784 S.Diag(E->getExprLoc(), diag::err_ice_too_large)
5785 << toString(*I, 10, false) << 32 << /* Unsigned */ 1;
5786 return nullptr;
5787 }
5788 if (*I < 0)
5789 S.Diag(E->getExprLoc(), diag::warn_attribute_argument_n_negative)
5790 << &AL << Idx << E->getSourceRange();
5791
5792 // We may need to perform implicit conversion of the argument.
5794 S.Context, S.Context.getConstType(S.Context.IntTy), /*consume*/ false);
5795 ExprResult ValArg = S.PerformCopyInitialization(Entity, SourceLocation(), E);
5796 assert(!ValArg.isInvalid() &&
5797 "Unexpected PerformCopyInitialization() failure.");
5798
5799 return ValArg.getAs<Expr>();
5800}
5801
5802CUDALaunchBoundsAttr *
5804 Expr *MinBlocks, Expr *MaxBlocks) {
5805 CUDALaunchBoundsAttr TmpAttr(Context, CI, MaxThreads, MinBlocks, MaxBlocks);
5806 MaxThreads = makeLaunchBoundsArgExpr(*this, MaxThreads, TmpAttr, 0);
5807 if (!MaxThreads)
5808 return nullptr;
5809
5810 if (MinBlocks) {
5811 MinBlocks = makeLaunchBoundsArgExpr(*this, MinBlocks, TmpAttr, 1);
5812 if (!MinBlocks)
5813 return nullptr;
5814 }
5815
5816 if (MaxBlocks) {
5817 // '.maxclusterrank' ptx directive requires .target sm_90 or higher.
5819 if (SM == CudaArch::UNKNOWN || SM < CudaArch::SM_90) {
5820 Diag(MaxBlocks->getBeginLoc(), diag::warn_cuda_maxclusterrank_sm_90)
5821 << CudaArchToString(SM) << CI << MaxBlocks->getSourceRange();
5822 // Ignore it by setting MaxBlocks to null;
5823 MaxBlocks = nullptr;
5824 } else {
5825 MaxBlocks = makeLaunchBoundsArgExpr(*this, MaxBlocks, TmpAttr, 2);
5826 if (!MaxBlocks)
5827 return nullptr;
5828 }
5829 }
5830
5831 return ::new (Context)
5832 CUDALaunchBoundsAttr(Context, CI, MaxThreads, MinBlocks, MaxBlocks);
5833}
5834
5836 Expr *MaxThreads, Expr *MinBlocks,
5837 Expr *MaxBlocks) {
5838 if (auto *Attr = CreateLaunchBoundsAttr(CI, MaxThreads, MinBlocks, MaxBlocks))
5839 D->addAttr(Attr);
5840}
5841
5842static void handleLaunchBoundsAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5843 if (!AL.checkAtLeastNumArgs(S, 1) || !AL.checkAtMostNumArgs(S, 3))
5844 return;
5845
5846 S.AddLaunchBoundsAttr(D, AL, AL.getArgAsExpr(0),
5847 AL.getNumArgs() > 1 ? AL.getArgAsExpr(1) : nullptr,
5848 AL.getNumArgs() > 2 ? AL.getArgAsExpr(2) : nullptr);
5849}
5850
5852 const ParsedAttr &AL) {
5853 if (!AL.isArgIdent(0)) {
5854 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
5855 << AL << /* arg num = */ 1 << AANT_ArgumentIdentifier;
5856 return;
5857 }
5858
5859 ParamIdx ArgumentIdx;
5860 if (!checkFunctionOrMethodParameterIndex(S, D, AL, 2, AL.getArgAsExpr(1),
5861 ArgumentIdx))
5862 return;
5863
5864 ParamIdx TypeTagIdx;
5865 if (!checkFunctionOrMethodParameterIndex(S, D, AL, 3, AL.getArgAsExpr(2),
5866 TypeTagIdx))
5867 return;
5868
5869 bool IsPointer = AL.getAttrName()->getName() == "pointer_with_type_tag";
5870 if (IsPointer) {
5871 // Ensure that buffer has a pointer type.
5872 unsigned ArgumentIdxAST = ArgumentIdx.getASTIndex();
5873 if (ArgumentIdxAST >= getFunctionOrMethodNumParams(D) ||
5874 !getFunctionOrMethodParamType(D, ArgumentIdxAST)->isPointerType())
5875 S.Diag(AL.getLoc(), diag::err_attribute_pointers_only) << AL << 0;
5876 }
5877
5878 D->addAttr(::new (S.Context) ArgumentWithTypeTagAttr(
5879 S.Context, AL, AL.getArgAsIdent(0)->Ident, ArgumentIdx, TypeTagIdx,
5880 IsPointer));
5881}
5882
5884 const ParsedAttr &AL) {
5885 if (!AL.isArgIdent(0)) {
5886 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
5887 << AL << 1 << AANT_ArgumentIdentifier;
5888 return;
5889 }
5890
5891 if (!AL.checkExactlyNumArgs(S, 1))
5892 return;
5893
5894 if (!isa<VarDecl>(D)) {
5895 S.Diag(AL.getLoc(), diag::err_attribute_wrong_decl_type)
5897 return;
5898 }
5899
5900 IdentifierInfo *PointerKind = AL.getArgAsIdent(0)->Ident;
5901 TypeSourceInfo *MatchingCTypeLoc = nullptr;
5902 S.GetTypeFromParser(AL.getMatchingCType(), &MatchingCTypeLoc);
5903 assert(MatchingCTypeLoc && "no type source info for attribute argument");
5904
5905 D->addAttr(::new (S.Context) TypeTagForDatatypeAttr(
5906 S.Context, AL, PointerKind, MatchingCTypeLoc, AL.getLayoutCompatible(),
5907 AL.getMustBeNull()));
5908}
5909
5910static void handleXRayLogArgsAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5911 ParamIdx ArgCount;
5912
5913 if (!checkFunctionOrMethodParameterIndex(S, D, AL, 1, AL.getArgAsExpr(0),
5914 ArgCount,
5915 true /* CanIndexImplicitThis */))
5916 return;
5917
5918 // ArgCount isn't a parameter index [0;n), it's a count [1;n]
5919 D->addAttr(::new (S.Context)
5920 XRayLogArgsAttr(S.Context, AL, ArgCount.getSourceIndex()));
5921}
5922
5924 const ParsedAttr &AL) {
5925 uint32_t Count = 0, Offset = 0;
5926 if (!checkUInt32Argument(S, AL, AL.getArgAsExpr(0), Count, 0, true))
5927 return;
5928 if (AL.getNumArgs() == 2) {
5929 Expr *Arg = AL.getArgAsExpr(1);
5930 if (!checkUInt32Argument(S, AL, Arg, Offset, 1, true))
5931 return;
5932 if (Count < Offset) {
5933 S.Diag(getAttrLoc(AL), diag::err_attribute_argument_out_of_range)
5934 << &AL << 0 << Count << Arg->getBeginLoc();
5935 return;
5936 }
5937 }
5938 D->addAttr(::new (S.Context)
5939 PatchableFunctionEntryAttr(S.Context, AL, Count, Offset));
5940}
5941
5942namespace {
5943struct IntrinToName {
5944 uint32_t Id;
5945 int32_t FullName;
5946 int32_t ShortName;
5947};
5948} // unnamed namespace
5949
5950static bool ArmBuiltinAliasValid(unsigned BuiltinID, StringRef AliasName,
5952 const char *IntrinNames) {
5953 AliasName.consume_front("__arm_");
5954 const IntrinToName *It =
5955 llvm::lower_bound(Map, BuiltinID, [](const IntrinToName &L, unsigned Id) {
5956 return L.Id < Id;
5957 });
5958 if (It == Map.end() || It->Id != BuiltinID)
5959 return false;
5960 StringRef FullName(&IntrinNames[It->FullName]);
5961 if (AliasName == FullName)
5962 return true;
5963 if (It->ShortName == -1)
5964 return false;
5965 StringRef ShortName(&IntrinNames[It->ShortName]);
5966 return AliasName == ShortName;
5967}
5968
5969static bool ArmMveAliasValid(unsigned BuiltinID, StringRef AliasName) {
5970#include "clang/Basic/arm_mve_builtin_aliases.inc"
5971 // The included file defines:
5972 // - ArrayRef<IntrinToName> Map
5973 // - const char IntrinNames[]
5974 return ArmBuiltinAliasValid(BuiltinID, AliasName, Map, IntrinNames);
5975}
5976
5977static bool ArmCdeAliasValid(unsigned BuiltinID, StringRef AliasName) {
5978#include "clang/Basic/arm_cde_builtin_aliases.inc"
5979 return ArmBuiltinAliasValid(BuiltinID, AliasName, Map, IntrinNames);
5980}
5981
5982static bool ArmSveAliasValid(ASTContext &Context, unsigned BuiltinID,
5983 StringRef AliasName) {
5984 if (Context.BuiltinInfo.isAuxBuiltinID(BuiltinID))
5985 BuiltinID = Context.BuiltinInfo.getAuxBuiltinID(BuiltinID);
5986 return BuiltinID >= AArch64::FirstSVEBuiltin &&
5987 BuiltinID <= AArch64::LastSVEBuiltin;
5988}
5989
5990static bool ArmSmeAliasValid(ASTContext &Context, unsigned BuiltinID,
5991 StringRef AliasName) {
5992 if (Context.BuiltinInfo.isAuxBuiltinID(BuiltinID))
5993 BuiltinID = Context.BuiltinInfo.getAuxBuiltinID(BuiltinID);
5994 return BuiltinID >= AArch64::FirstSMEBuiltin &&
5995 BuiltinID <= AArch64::LastSMEBuiltin;
5996}
5997
5998static void handleArmBuiltinAliasAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
5999 if (!AL.isArgIdent(0)) {
6000 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
6001 << AL << 1 << AANT_ArgumentIdentifier;
6002 return;
6003 }
6004
6005 IdentifierInfo *Ident = AL.getArgAsIdent(0)->Ident;
6006 unsigned BuiltinID = Ident->getBuiltinID();
6007 StringRef AliasName = cast<FunctionDecl>(D)->getIdentifier()->getName();
6008
6009 bool IsAArch64 = S.Context.getTargetInfo().getTriple().isAArch64();
6010 if ((IsAArch64 && !ArmSveAliasValid(S.Context, BuiltinID, AliasName) &&
6011 !ArmSmeAliasValid(S.Context, BuiltinID, AliasName)) ||
6012 (!IsAArch64 && !ArmMveAliasValid(BuiltinID, AliasName) &&
6013 !ArmCdeAliasValid(BuiltinID, AliasName))) {
6014 S.Diag(AL.getLoc(), diag::err_attribute_arm_builtin_alias);
6015 return;
6016 }
6017
6018 D->addAttr(::new (S.Context) ArmBuiltinAliasAttr(S.Context, AL, Ident));
6019}
6020
6021static bool RISCVAliasValid(unsigned BuiltinID, StringRef AliasName) {
6022 return BuiltinID >= RISCV::FirstRVVBuiltin &&
6023 BuiltinID <= RISCV::LastRVVBuiltin;
6024}
6025
6027 const ParsedAttr &AL) {
6028 if (!AL.isArgIdent(0)) {
6029 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
6030 << AL << 1 << AANT_ArgumentIdentifier;
6031 return;
6032 }
6033
6034 IdentifierInfo *Ident = AL.getArgAsIdent(0)->Ident;
6035 unsigned BuiltinID = Ident->getBuiltinID();
6036 StringRef AliasName = cast<FunctionDecl>(D)->getIdentifier()->getName();
6037
6038 bool IsAArch64 = S.Context.getTargetInfo().getTriple().isAArch64();
6039 bool IsARM = S.Context.getTargetInfo().getTriple().isARM();
6040 bool IsRISCV = S.Context.getTargetInfo().getTriple().isRISCV();
6041 bool IsHLSL = S.Context.getLangOpts().HLSL;
6042 if ((IsAArch64 && !ArmSveAliasValid(S.Context, BuiltinID, AliasName)) ||
6043 (IsARM && !ArmMveAliasValid(BuiltinID, AliasName) &&
6044 !ArmCdeAliasValid(BuiltinID, AliasName)) ||
6045 (IsRISCV && !RISCVAliasValid(BuiltinID, AliasName)) ||
6046 (!IsAArch64 && !IsARM && !IsRISCV && !IsHLSL)) {
6047 S.Diag(AL.getLoc(), diag::err_attribute_builtin_alias) << AL;
6048 return;
6049 }
6050
6051 D->addAttr(::new (S.Context) BuiltinAliasAttr(S.Context, AL, Ident));
6052}
6053
6054static void handleNullableTypeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
6055 if (AL.isUsedAsTypeAttr())
6056 return;
6057
6058 if (auto *CRD = dyn_cast<CXXRecordDecl>(D);
6059 !CRD || !(CRD->isClass() || CRD->isStruct())) {
6060 S.Diag(AL.getRange().getBegin(), diag::err_attribute_wrong_decl_type_str)
6061 << AL << AL.isRegularKeywordAttribute() << "classes";
6062 return;
6063 }
6064
6065 handleSimpleAttribute<TypeNullableAttr>(S, D, AL);
6066}
6067
6068static void handlePreferredTypeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
6069 if (!AL.hasParsedType()) {
6070 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << AL << 1;
6071 return;
6072 }
6073
6074 TypeSourceInfo *ParmTSI = nullptr;
6075 QualType QT = S.GetTypeFromParser(AL.getTypeArg(), &ParmTSI);
6076 assert(ParmTSI && "no type source info for attribute argument");
6077 S.RequireCompleteType(ParmTSI->getTypeLoc().getBeginLoc(), QT,
6078 diag::err_incomplete_type);
6079
6080 D->addAttr(::new (S.Context) PreferredTypeAttr(S.Context, AL, ParmTSI));
6081}
6082
6083//===----------------------------------------------------------------------===//
6084// Checker-specific attribute handlers.
6085//===----------------------------------------------------------------------===//
6087 return QT->isDependentType() || QT->isObjCRetainableType();
6088}
6089
6091 return QT->isDependentType() || QT->isObjCObjectPointerType() ||
6092 QT->isObjCNSObjectType();
6093}
6094
6096 return QT->isDependentType() || QT->isPointerType() ||
6098}
6099
6101 if (QT->isDependentType())
6102 return true;
6103 QualType PT = QT->getPointeeType();
6104 return !PT.isNull() && PT->getAsCXXRecordDecl() != nullptr;
6105}
6106
6109 bool IsTemplateInstantiation) {
6110 ValueDecl *VD = cast<ValueDecl>(D);
6111 switch (K) {
6113 handleSimpleAttributeOrDiagnose<OSConsumedAttr>(
6114 *this, VD, CI, isValidSubjectOfOSAttribute(VD->getType()),
6115 diag::warn_ns_attribute_wrong_parameter_type,
6116 /*ExtraArgs=*/CI.getRange(), "os_consumed", /*pointers*/ 1);
6117 return;
6119 handleSimpleAttributeOrDiagnose<NSConsumedAttr>(
6120 *this, VD, CI, isValidSubjectOfNSAttribute(VD->getType()),
6121
6122 // These attributes are normally just advisory, but in ARC, ns_consumed
6123 // is significant. Allow non-dependent code to contain inappropriate
6124 // attributes even in ARC, but require template instantiations to be
6125 // set up correctly.
6126 ((IsTemplateInstantiation && getLangOpts().ObjCAutoRefCount)
6127 ? diag::err_ns_attribute_wrong_parameter_type
6128 : diag::warn_ns_attribute_wrong_parameter_type),
6129 /*ExtraArgs=*/CI.getRange(), "ns_consumed", /*objc pointers*/ 0);
6130 return;
6132 handleSimpleAttributeOrDiagnose<CFConsumedAttr>(
6133 *this, VD, CI, isValidSubjectOfCFAttribute(VD->getType()),
6134 diag::warn_ns_attribute_wrong_parameter_type,
6135 /*ExtraArgs=*/CI.getRange(), "cf_consumed", /*pointers*/ 1);
6136 return;
6137 }
6138}
6139
6142 switch (AL.getKind()) {
6143 case ParsedAttr::AT_CFConsumed:
6144 case ParsedAttr::AT_CFReturnsRetained:
6145 case ParsedAttr::AT_CFReturnsNotRetained:
6147 case ParsedAttr::AT_OSConsumesThis:
6148 case ParsedAttr::AT_OSConsumed:
6149 case ParsedAttr::AT_OSReturnsRetained:
6150 case ParsedAttr::AT_OSReturnsNotRetained:
6151 case ParsedAttr::AT_OSReturnsRetainedOnZero:
6152 case ParsedAttr::AT_OSReturnsRetainedOnNonZero:
6154 case ParsedAttr::AT_NSConsumesSelf:
6155 case ParsedAttr::AT_NSConsumed:
6156 case ParsedAttr::AT_NSReturnsRetained:
6157 case ParsedAttr::AT_NSReturnsNotRetained:
6158 case ParsedAttr::AT_NSReturnsAutoreleased:
6160 default:
6161 llvm_unreachable("Wrong argument supplied");
6162 }
6163}
6164
6167 return false;
6168
6169 Diag(Loc, diag::warn_ns_attribute_wrong_return_type)
6170 << "'ns_returns_retained'" << 0 << 0;
6171 return true;
6172}
6173
6174/// \return whether the parameter is a pointer to OSObject pointer.
6175static bool isValidOSObjectOutParameter(const Decl *D) {
6176 const auto *PVD = dyn_cast<ParmVarDecl>(D);
6177 if (!PVD)
6178 return false;
6179 QualType QT = PVD->getType();
6180 QualType PT = QT->getPointeeType();
6181 return !PT.isNull() && isValidSubjectOfOSAttribute(PT);
6182}
6183
6185 const ParsedAttr &AL) {
6186 QualType ReturnType;
6188
6189 if (const auto *MD = dyn_cast<ObjCMethodDecl>(D)) {
6190 ReturnType = MD->getReturnType();
6191 } else if (S.getLangOpts().ObjCAutoRefCount && hasDeclarator(D) &&
6192 (AL.getKind() == ParsedAttr::AT_NSReturnsRetained)) {
6193 return; // ignore: was handled as a type attribute
6194 } else if (const auto *PD = dyn_cast<ObjCPropertyDecl>(D)) {
6195 ReturnType = PD->getType();
6196 } else if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
6197 ReturnType = FD->getReturnType();
6198 } else if (const auto *Param = dyn_cast<ParmVarDecl>(D)) {
6199 // Attributes on parameters are used for out-parameters,
6200 // passed as pointers-to-pointers.
6201 unsigned DiagID = K == Sema::RetainOwnershipKind::CF
6202 ? /*pointer-to-CF-pointer*/2
6203 : /*pointer-to-OSObject-pointer*/3;
6204 ReturnType = Param->getType()->getPointeeType();
6205 if (ReturnType.isNull()) {
6206 S.Diag(D->getBeginLoc(), diag::warn_ns_attribute_wrong_parameter_type)
6207 << AL << DiagID << AL.getRange();
6208 return;
6209 }
6210 } else if (AL.isUsedAsTypeAttr()) {
6211 return;
6212 } else {
6213 AttributeDeclKind ExpectedDeclKind;
6214 switch (AL.getKind()) {
6215 default: llvm_unreachable("invalid ownership attribute");
6216 case ParsedAttr::AT_NSReturnsRetained:
6217 case ParsedAttr::AT_NSReturnsAutoreleased:
6218 case ParsedAttr::AT_NSReturnsNotRetained:
6219 ExpectedDeclKind = ExpectedFunctionOrMethod;
6220 break;
6221
6222 case ParsedAttr::AT_OSReturnsRetained:
6223 case ParsedAttr::AT_OSReturnsNotRetained:
6224 case ParsedAttr::AT_CFReturnsRetained:
6225 case ParsedAttr::AT_CFReturnsNotRetained:
6226 ExpectedDeclKind = ExpectedFunctionMethodOrParameter;
6227 break;
6228 }
6229 S.Diag(D->getBeginLoc(), diag::warn_attribute_wrong_decl_type)
6230 << AL.getRange() << AL << AL.isRegularKeywordAttribute()
6231 << ExpectedDeclKind;
6232 return;
6233 }
6234
6235 bool TypeOK;
6236 bool Cf;
6237 unsigned ParmDiagID = 2; // Pointer-to-CF-pointer
6238 switch (AL.getKind()) {
6239 default: llvm_unreachable("invalid ownership attribute");
6240 case ParsedAttr::AT_NSReturnsRetained:
6241 TypeOK = isValidSubjectOfNSReturnsRetainedAttribute(ReturnType);
6242 Cf = false;
6243 break;
6244
6245 case ParsedAttr::AT_NSReturnsAutoreleased:
6246 case ParsedAttr::AT_NSReturnsNotRetained:
6247 TypeOK = isValidSubjectOfNSAttribute(ReturnType);
6248 Cf = false;
6249 break;
6250
6251 case ParsedAttr::AT_CFReturnsRetained:
6252 case ParsedAttr::AT_CFReturnsNotRetained:
6253 TypeOK = isValidSubjectOfCFAttribute(ReturnType);
6254 Cf = true;
6255 break;
6256
6257 case ParsedAttr::AT_OSReturnsRetained:
6258 case ParsedAttr::AT_OSReturnsNotRetained:
6259 TypeOK = isValidSubjectOfOSAttribute(ReturnType);
6260 Cf = true;
6261 ParmDiagID = 3; // Pointer-to-OSObject-pointer
6262 break;
6263 }
6264
6265 if (!TypeOK) {
6266 if (AL.isUsedAsTypeAttr())
6267 return;
6268
6269 if (isa<ParmVarDecl>(D)) {
6270 S.Diag(D->getBeginLoc(), diag::warn_ns_attribute_wrong_parameter_type)
6271 << AL << ParmDiagID << AL.getRange();
6272 } else {
6273 // Needs to be kept in sync with warn_ns_attribute_wrong_return_type.
6274 enum : unsigned {
6275 Function,
6276 Method,
6277 Property
6278 } SubjectKind = Function;
6279 if (isa<ObjCMethodDecl>(D))
6280 SubjectKind = Method;
6281 else if (isa<ObjCPropertyDecl>(D))
6282 SubjectKind = Property;
6283 S.Diag(D->getBeginLoc(), diag::warn_ns_attribute_wrong_return_type)
6284 << AL << SubjectKind << Cf << AL.getRange();
6285 }
6286 return;
6287 }
6288
6289 switch (AL.getKind()) {
6290 default:
6291 llvm_unreachable("invalid ownership attribute");
6292 case ParsedAttr::AT_NSReturnsAutoreleased:
6293 handleSimpleAttribute<NSReturnsAutoreleasedAttr>(S, D, AL);
6294 return;
6295 case ParsedAttr::AT_CFReturnsNotRetained:
6296 handleSimpleAttribute<CFReturnsNotRetainedAttr>(S, D, AL);
6297 return;
6298 case ParsedAttr::AT_NSReturnsNotRetained:
6299 handleSimpleAttribute<NSReturnsNotRetainedAttr>(S, D, AL);
6300 return;
6301 case ParsedAttr::AT_CFReturnsRetained:
6302 handleSimpleAttribute<CFReturnsRetainedAttr>(S, D, AL);
6303 return;
6304 case ParsedAttr::AT_NSReturnsRetained:
6305 handleSimpleAttribute<NSReturnsRetainedAttr>(S, D, AL);
6306 return;
6307 case ParsedAttr::AT_OSReturnsRetained:
6308 handleSimpleAttribute<OSReturnsRetainedAttr>(S, D, AL);
6309 return;
6310 case ParsedAttr::AT_OSReturnsNotRetained:
6311 handleSimpleAttribute<OSReturnsNotRetainedAttr>(S, D, AL);
6312 return;
6313 };
6314}
6315
6317 const ParsedAttr &Attrs) {
6318 const int EP_ObjCMethod = 1;
6319 const int EP_ObjCProperty = 2;
6320
6321 SourceLocation loc = Attrs.getLoc();
6322 QualType resultType;
6323 if (isa<ObjCMethodDecl>(D))
6324 resultType = cast<ObjCMethodDecl>(D)->getReturnType();
6325 else
6326 resultType = cast<ObjCPropertyDecl>(D)->getType();
6327
6328 if (!resultType->isReferenceType() &&
6329 (!resultType->isPointerType() || resultType->isObjCRetainableType())) {
6330 S.Diag(D->getBeginLoc(), diag::warn_ns_attribute_wrong_return_type)
6331 << SourceRange(loc) << Attrs
6332 << (isa<ObjCMethodDecl>(D) ? EP_ObjCMethod : EP_ObjCProperty)
6333 << /*non-retainable pointer*/ 2;
6334
6335 // Drop the attribute.
6336 return;
6337 }
6338
6339 D->addAttr(::new (S.Context) ObjCReturnsInnerPointerAttr(S.Context, Attrs));
6340}
6341
6343 const ParsedAttr &Attrs) {
6344 const auto *Method = cast<ObjCMethodDecl>(D);
6345
6346 const DeclContext *DC = Method->getDeclContext();
6347 if (const auto *PDecl = dyn_cast_if_present<ObjCProtocolDecl>(DC)) {
6348 S.Diag(D->getBeginLoc(), diag::warn_objc_requires_super_protocol) << Attrs
6349 << 0;
6350 S.Diag(PDecl->getLocation(), diag::note_protocol_decl);
6351 return;
6352 }
6353 if (Method->getMethodFamily() == OMF_dealloc) {
6354 S.Diag(D->getBeginLoc(), diag::warn_objc_requires_super_protocol) << Attrs
6355 << 1;
6356 return;
6357 }
6358
6359 D->addAttr(::new (S.Context) ObjCRequiresSuperAttr(S.Context, Attrs));
6360}
6361
6362static void handleNSErrorDomain(Sema &S, Decl *D, const ParsedAttr &Attr) {
6363 if (!isa<TagDecl>(D)) {
6364 S.Diag(D->getBeginLoc(), diag::err_nserrordomain_invalid_decl) << 0;
6365 return;
6366 }
6367
6368 IdentifierLoc *IdentLoc =
6369 Attr.isArgIdent(0) ? Attr.getArgAsIdent(0) : nullptr;
6370 if (!IdentLoc || !IdentLoc->Ident) {
6371 // Try to locate the argument directly.
6373 if (Attr.isArgExpr(0) && Attr.getArgAsExpr(0))
6374 Loc = Attr.getArgAsExpr(0)->getBeginLoc();
6375
6376 S.Diag(Loc, diag::err_nserrordomain_invalid_decl) << 0;
6377 return;
6378 }
6379
6380 // Verify that the identifier is a valid decl in the C decl namespace.
6383 if (!S.LookupName(Result, S.TUScope) || !Result.getAsSingle<VarDecl>()) {
6384 S.Diag(IdentLoc->Loc, diag::err_nserrordomain_invalid_decl)
6385 << 1 << IdentLoc->Ident;
6386 return;
6387 }
6388
6389 D->addAttr(::new (S.Context)
6390 NSErrorDomainAttr(S.Context, Attr, IdentLoc->Ident));
6391}
6392
6393static void handleObjCBridgeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
6394 IdentifierLoc *Parm = AL.isArgIdent(0) ? AL.getArgAsIdent(0) : nullptr;
6395
6396 if (!Parm) {
6397 S.Diag(D->getBeginLoc(), diag::err_objc_attr_not_id) << AL << 0;
6398 return;
6399 }
6400
6401 // Typedefs only allow objc_bridge(id) and have some additional checking.
6402 if (const auto *TD = dyn_cast<TypedefNameDecl>(D)) {
6403 if (!Parm->Ident->isStr("id")) {
6404 S.Diag(AL.getLoc(), diag::err_objc_attr_typedef_not_id) << AL;
6405 return;
6406 }
6407
6408 // Only allow 'cv void *'.
6409 QualType T = TD->getUnderlyingType();
6410 if (!T->isVoidPointerType()) {
6411 S.Diag(AL.getLoc(), diag::err_objc_attr_typedef_not_void_pointer);
6412 return;
6413 }
6414 }
6415
6416 D->addAttr(::new (S.Context) ObjCBridgeAttr(S.Context, AL, Parm->Ident));
6417}
6418
6420 const ParsedAttr &AL) {
6421 IdentifierLoc *Parm = AL.isArgIdent(0) ? AL.getArgAsIdent(0) : nullptr;
6422
6423 if (!Parm) {
6424 S.Diag(D->getBeginLoc(), diag::err_objc_attr_not_id) << AL << 0;
6425 return;
6426 }
6427
6428 D->addAttr(::new (S.Context)
6429 ObjCBridgeMutableAttr(S.Context, AL, Parm->Ident));
6430}
6431
6433 const ParsedAttr &AL) {
6434 IdentifierInfo *RelatedClass =
6435 AL.isArgIdent(0) ? AL.getArgAsIdent(0)->Ident : nullptr;
6436 if (!RelatedClass) {
6437 S.Diag(D->getBeginLoc(), diag::err_objc_attr_not_id) << AL << 0;
6438 return;
6439 }
6440 IdentifierInfo *ClassMethod =
6441 AL.getArgAsIdent(1) ? AL.getArgAsIdent(1)->Ident : nullptr;
6442 IdentifierInfo *InstanceMethod =
6443 AL.getArgAsIdent(2) ? AL.getArgAsIdent(2)->Ident : nullptr;
6444 D->addAttr(::new (S.Context) ObjCBridgeRelatedAttr(
6445 S.Context, AL, RelatedClass, ClassMethod, InstanceMethod));
6446}
6447
6449 const ParsedAttr &AL) {
6450 DeclContext *Ctx = D->getDeclContext();
6451
6452 // This attribute can only be applied to methods in interfaces or class
6453 // extensions.
6454 if (!isa<ObjCInterfaceDecl>(Ctx) &&
6455 !(isa<ObjCCategoryDecl>(Ctx) &&
6456 cast<ObjCCategoryDecl>(Ctx)->IsClassExtension())) {
6457 S.Diag(D->getLocation(), diag::err_designated_init_attr_non_init);
6458 return;
6459 }
6460
6461 ObjCInterfaceDecl *IFace;
6462 if (auto *CatDecl = dyn_cast<ObjCCategoryDecl>(Ctx))
6463 IFace = CatDecl->getClassInterface();
6464 else
6465 IFace = cast<ObjCInterfaceDecl>(Ctx);
6466
6467 if (!IFace)
6468 return;
6469
6471 D->addAttr(::new (S.Context) ObjCDesignatedInitializerAttr(S.Context, AL));
6472}
6473
6474static void handleObjCRuntimeName(Sema &S, Decl *D, const ParsedAttr &AL) {
6475 StringRef MetaDataName;
6476 if (!S.checkStringLiteralArgumentAttr(AL, 0, MetaDataName))
6477 return;
6478 D->addAttr(::new (S.Context)
6479 ObjCRuntimeNameAttr(S.Context, AL, MetaDataName));
6480}
6481
6482// When a user wants to use objc_boxable with a union or struct
6483// but they don't have access to the declaration (legacy/third-party code)
6484// then they can 'enable' this feature with a typedef:
6485// typedef struct __attribute((objc_boxable)) legacy_struct legacy_struct;
6486static void handleObjCBoxable(Sema &S, Decl *D, const ParsedAttr &AL) {
6487 bool notify = false;
6488
6489 auto *RD = dyn_cast<RecordDecl>(D);
6490 if (RD && RD->getDefinition()) {
6491 RD = RD->getDefinition();
6492 notify = true;
6493 }
6494
6495 if (RD) {
6496 ObjCBoxableAttr *BoxableAttr =
6497 ::new (S.Context) ObjCBoxableAttr(S.Context, AL);
6498 RD->addAttr(BoxableAttr);
6499 if (notify) {
6500 // we need to notify ASTReader/ASTWriter about
6501 // modification of existing declaration
6503 L->AddedAttributeToRecord(BoxableAttr, RD);
6504 }
6505 }
6506}
6507
6508static void handleObjCOwnershipAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
6509 if (hasDeclarator(D))
6510 return;
6511
6512 S.Diag(D->getBeginLoc(), diag::err_attribute_wrong_decl_type)
6513 << AL.getRange() << AL << AL.isRegularKeywordAttribute()
6515}
6516
6518 const ParsedAttr &AL) {
6519 const auto *VD = cast<ValueDecl>(D);
6520 QualType QT = VD->getType();
6521
6522 if (!QT->isDependentType() &&
6523 !QT->isObjCLifetimeType()) {
6524 S.Diag(AL.getLoc(), diag::err_objc_precise_lifetime_bad_type)
6525 << QT;
6526 return;
6527 }
6528
6530
6531 // If we have no lifetime yet, check the lifetime we're presumably
6532 // going to infer.
6533 if (Lifetime == Qualifiers::OCL_None && !QT->isDependentType())
6534 Lifetime = QT->getObjCARCImplicitLifetime();
6535
6536 switch (Lifetime) {
6538 assert(QT->isDependentType() &&
6539 "didn't infer lifetime for non-dependent type?");
6540 break;
6541
6542 case Qualifiers::OCL_Weak: // meaningful
6543 case Qualifiers::OCL_Strong: // meaningful
6544 break;
6545
6548 S.Diag(AL.getLoc(), diag::warn_objc_precise_lifetime_meaningless)
6549 << (Lifetime == Qualifiers::OCL_Autoreleasing);
6550 break;
6551 }
6552
6553 D->addAttr(::new (S.Context) ObjCPreciseLifetimeAttr(S.Context, AL));
6554}
6555
6556static void handleSwiftAttrAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
6557 // Make sure that there is a string literal as the annotation's single
6558 // argument.
6559 StringRef Str;
6560 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str))
6561 return;
6562
6563 D->addAttr(::new (S.Context) SwiftAttrAttr(S.Context, AL, Str));
6564}
6565
6566static void handleSwiftBridge(Sema &S, Decl *D, const ParsedAttr &AL) {
6567 // Make sure that there is a string literal as the annotation's single
6568 // argument.
6569 StringRef BT;
6570 if (!S.checkStringLiteralArgumentAttr(AL, 0, BT))
6571 return;
6572
6573 // Warn about duplicate attributes if they have different arguments, but drop
6574 // any duplicate attributes regardless.
6575 if (const auto *Other = D->getAttr<SwiftBridgeAttr>()) {
6576 if (Other->getSwiftType() != BT)
6577 S.Diag(AL.getLoc(), diag::warn_duplicate_attribute) << AL;
6578 return;
6579 }
6580
6581 D->addAttr(::new (S.Context) SwiftBridgeAttr(S.Context, AL, BT));
6582}
6583
6584static bool isErrorParameter(Sema &S, QualType QT) {
6585 const auto *PT = QT->getAs<PointerType>();
6586 if (!PT)
6587 return false;
6588
6589 QualType Pointee = PT->getPointeeType();
6590
6591 // Check for NSError**.
6592 if (const auto *OPT = Pointee->getAs<ObjCObjectPointerType>())
6593 if (const auto *ID = OPT->getInterfaceDecl())
6594 if (ID->getIdentifier() == S.ObjC().getNSErrorIdent())
6595 return true;
6596
6597 // Check for CFError**.
6598 if (const auto *PT = Pointee->getAs<PointerType>())
6599 if (const auto *RT = PT->getPointeeType()->getAs<RecordType>())
6600 if (S.ObjC().isCFError(RT->getDecl()))
6601 return true;
6602
6603 return false;
6604}
6605
6606static void handleSwiftError(Sema &S, Decl *D, const ParsedAttr &AL) {
6607 auto hasErrorParameter = [](Sema &S, Decl *D, const ParsedAttr &AL) -> bool {
6608 for (unsigned I = 0, E = getFunctionOrMethodNumParams(D); I != E; ++I) {
6610 return true;
6611 }
6612
6613 S.Diag(AL.getLoc(), diag::err_attr_swift_error_no_error_parameter)
6614 << AL << isa<ObjCMethodDecl>(D);
6615 return false;
6616 };
6617
6618 auto hasPointerResult = [](Sema &S, Decl *D, const ParsedAttr &AL) -> bool {
6619 // - C, ObjC, and block pointers are definitely okay.
6620 // - References are definitely not okay.
6621 // - nullptr_t is weird, but acceptable.
6623 if (RT->hasPointerRepresentation() && !RT->isReferenceType())
6624 return true;
6625
6626 S.Diag(AL.getLoc(), diag::err_attr_swift_error_return_type)
6627 << AL << AL.getArgAsIdent(0)->Ident->getName() << isa<ObjCMethodDecl>(D)
6628 << /*pointer*/ 1;
6629 return false;
6630 };
6631
6632 auto hasIntegerResult = [](Sema &S, Decl *D, const ParsedAttr &AL) -> bool {
6634 if (RT->isIntegralType(S.Context))
6635 return true;
6636
6637 S.Diag(AL.getLoc(), diag::err_attr_swift_error_return_type)
6638 << AL << AL.getArgAsIdent(0)->Ident->getName() << isa<ObjCMethodDecl>(D)
6639 << /*integral*/ 0;
6640 return false;
6641 };
6642
6643 if (D->isInvalidDecl())
6644 return;
6645
6647 SwiftErrorAttr::ConventionKind Convention;
6648 if (!SwiftErrorAttr::ConvertStrToConventionKind(Loc->Ident->getName(),
6649 Convention)) {
6650 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported)
6651 << AL << Loc->Ident;
6652 return;
6653 }
6654
6655 switch (Convention) {
6656 case SwiftErrorAttr::None:
6657 // No additional validation required.
6658 break;
6659
6660 case SwiftErrorAttr::NonNullError:
6661 if (!hasErrorParameter(S, D, AL))
6662 return;
6663 break;
6664
6665 case SwiftErrorAttr::NullResult:
6666 if (!hasErrorParameter(S, D, AL) || !hasPointerResult(S, D, AL))
6667 return;
6668 break;
6669
6670 case SwiftErrorAttr::NonZeroResult:
6671 case SwiftErrorAttr::ZeroResult:
6672 if (!hasErrorParameter(S, D, AL) || !hasIntegerResult(S, D, AL))
6673 return;
6674 break;
6675 }
6676
6677 D->addAttr(::new (S.Context) SwiftErrorAttr(S.Context, AL, Convention));
6678}
6679
6681 const SwiftAsyncErrorAttr *ErrorAttr,
6682 const SwiftAsyncAttr *AsyncAttr) {
6683 if (AsyncAttr->getKind() == SwiftAsyncAttr::None) {
6684 if (ErrorAttr->getConvention() != SwiftAsyncErrorAttr::None) {
6685 S.Diag(AsyncAttr->getLocation(),
6686 diag::err_swift_async_error_without_swift_async)
6687 << AsyncAttr << isa<ObjCMethodDecl>(D);
6688 }
6689 return;
6690 }
6691
6692 const ParmVarDecl *HandlerParam = getFunctionOrMethodParam(
6693 D, AsyncAttr->getCompletionHandlerIndex().getASTIndex());
6694 // handleSwiftAsyncAttr already verified the type is correct, so no need to
6695 // double-check it here.
6696 const auto *FuncTy = HandlerParam->getType()
6698 ->getPointeeType()
6700 ArrayRef<QualType> BlockParams;
6701 if (FuncTy)
6702 BlockParams = FuncTy->getParamTypes();
6703
6704 switch (ErrorAttr->getConvention()) {
6705 case SwiftAsyncErrorAttr::ZeroArgument:
6706 case SwiftAsyncErrorAttr::NonZeroArgument: {
6707 uint32_t ParamIdx = ErrorAttr->getHandlerParamIdx();
6708 if (ParamIdx == 0 || ParamIdx > BlockParams.size()) {
6709 S.Diag(ErrorAttr->getLocation(),
6710 diag::err_attribute_argument_out_of_bounds) << ErrorAttr << 2;
6711 return;
6712 }
6713 QualType ErrorParam = BlockParams[ParamIdx - 1];
6714 if (!ErrorParam->isIntegralType(S.Context)) {
6715 StringRef ConvStr =
6716 ErrorAttr->getConvention() == SwiftAsyncErrorAttr::ZeroArgument
6717 ? "zero_argument"
6718 : "nonzero_argument";
6719 S.Diag(ErrorAttr->getLocation(), diag::err_swift_async_error_non_integral)
6720 << ErrorAttr << ConvStr << ParamIdx << ErrorParam;
6721 return;
6722 }
6723 break;
6724 }
6725 case SwiftAsyncErrorAttr::NonNullError: {
6726 bool AnyErrorParams = false;
6727 for (QualType Param : BlockParams) {
6728 // Check for NSError *.
6729 if (const auto *ObjCPtrTy = Param->getAs<ObjCObjectPointerType>()) {
6730 if (const auto *ID = ObjCPtrTy->getInterfaceDecl()) {
6731 if (ID->getIdentifier() == S.ObjC().getNSErrorIdent()) {
6732 AnyErrorParams = true;
6733 break;
6734 }
6735 }
6736 }
6737 // Check for CFError *.
6738 if (const auto *PtrTy = Param->getAs<PointerType>()) {
6739 if (const auto *RT = PtrTy->getPointeeType()->getAs<RecordType>()) {
6740 if (S.ObjC().isCFError(RT->getDecl())) {
6741 AnyErrorParams = true;
6742 break;
6743 }
6744 }
6745 }
6746 }
6747
6748 if (!AnyErrorParams) {
6749 S.Diag(ErrorAttr->getLocation(),
6750 diag::err_swift_async_error_no_error_parameter)
6751 << ErrorAttr << isa<ObjCMethodDecl>(D);
6752 return;
6753 }
6754 break;
6755 }
6756 case SwiftAsyncErrorAttr::None:
6757 break;
6758 }
6759}
6760
6761static void handleSwiftAsyncError(Sema &S, Decl *D, const ParsedAttr &AL) {
6762 IdentifierLoc *IDLoc = AL.getArgAsIdent(0);
6763 SwiftAsyncErrorAttr::ConventionKind ConvKind;
6764 if (!SwiftAsyncErrorAttr::ConvertStrToConventionKind(IDLoc->Ident->getName(),
6765 ConvKind)) {
6766 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported)
6767 << AL << IDLoc->Ident;
6768 return;
6769 }
6770
6771 uint32_t ParamIdx = 0;
6772 switch (ConvKind) {
6773 case SwiftAsyncErrorAttr::ZeroArgument:
6774 case SwiftAsyncErrorAttr::NonZeroArgument: {
6775 if (!AL.checkExactlyNumArgs(S, 2))
6776 return;
6777
6778 Expr *IdxExpr = AL.getArgAsExpr(1);
6779 if (!checkUInt32Argument(S, AL, IdxExpr, ParamIdx))
6780 return;
6781 break;
6782 }
6783 case SwiftAsyncErrorAttr::NonNullError:
6784 case SwiftAsyncErrorAttr::None: {
6785 if (!AL.checkExactlyNumArgs(S, 1))
6786 return;
6787 break;
6788 }
6789 }
6790
6791 auto *ErrorAttr =
6792 ::new (S.Context) SwiftAsyncErrorAttr(S.Context, AL, ConvKind, ParamIdx);
6793 D->addAttr(ErrorAttr);
6794
6795 if (auto *AsyncAttr = D->getAttr<SwiftAsyncAttr>())
6796 checkSwiftAsyncErrorBlock(S, D, ErrorAttr, AsyncAttr);
6797}
6798
6799// For a function, this will validate a compound Swift name, e.g.
6800// <code>init(foo:bar:baz:)</code> or <code>controllerForName(_:)</code>, and
6801// the function will output the number of parameter names, and whether this is a
6802// single-arg initializer.
6803//
6804// For a type, enum constant, property, or variable declaration, this will
6805// validate either a simple identifier, or a qualified
6806// <code>context.identifier</code> name.
6807static bool
6809 StringRef Name, unsigned &SwiftParamCount,
6810 bool &IsSingleParamInit) {
6811 SwiftParamCount = 0;
6812 IsSingleParamInit = false;
6813
6814 // Check whether this will be mapped to a getter or setter of a property.
6815 bool IsGetter = false, IsSetter = false;
6816 if (Name.consume_front("getter:"))
6817 IsGetter = true;
6818 else if (Name.consume_front("setter:"))
6819 IsSetter = true;
6820
6821 if (Name.back() != ')') {
6822 S.Diag(Loc, diag::warn_attr_swift_name_function) << AL;
6823 return false;
6824 }
6825
6826 bool IsMember = false;
6827 StringRef ContextName, BaseName, Parameters;
6828
6829 std::tie(BaseName, Parameters) = Name.split('(');
6830
6831 // Split at the first '.', if it exists, which separates the context name
6832 // from the base name.
6833 std::tie(ContextName, BaseName) = BaseName.split('.');
6834 if (BaseName.empty()) {
6835 BaseName = ContextName;
6836 ContextName = StringRef();
6837 } else if (ContextName.empty() || !isValidAsciiIdentifier(ContextName)) {
6838 S.Diag(Loc, diag::warn_attr_swift_name_invalid_identifier)
6839 << AL << /*context*/ 1;
6840 return false;
6841 } else {
6842 IsMember = true;
6843 }
6844
6845 if (!isValidAsciiIdentifier(BaseName) || BaseName == "_") {
6846 S.Diag(Loc, diag::warn_attr_swift_name_invalid_identifier)
6847 << AL << /*basename*/ 0;
6848 return false;
6849 }
6850
6851 bool IsSubscript = BaseName == "subscript";
6852 // A subscript accessor must be a getter or setter.
6853 if (IsSubscript && !IsGetter && !IsSetter) {
6854 S.Diag(Loc, diag::warn_attr_swift_name_subscript_invalid_parameter)
6855 << AL << /* getter or setter */ 0;
6856 return false;
6857 }
6858
6859 if (Parameters.empty()) {
6860 S.Diag(Loc, diag::warn_attr_swift_name_missing_parameters) << AL;
6861 return false;
6862 }
6863
6864 assert(Parameters.back() == ')' && "expected ')'");
6865 Parameters = Parameters.drop_back(); // ')'
6866
6867 if (Parameters.empty()) {
6868 // Setters and subscripts must have at least one parameter.
6869 if (IsSubscript) {
6870 S.Diag(Loc, diag::warn_attr_swift_name_subscript_invalid_parameter)
6871 << AL << /* have at least one parameter */1;
6872 return false;
6873 }
6874
6875 if (IsSetter) {
6876 S.Diag(Loc, diag::warn_attr_swift_name_setter_parameters) << AL;
6877 return false;
6878 }
6879
6880 return true;
6881 }
6882
6883 if (Parameters.back() != ':') {
6884 S.Diag(Loc, diag::warn_attr_swift_name_function) << AL;
6885 return false;
6886 }
6887
6888 StringRef CurrentParam;
6889 std::optional<unsigned> SelfLocation;
6890 unsigned NewValueCount = 0;
6891 std::optional<unsigned> NewValueLocation;
6892 do {
6893 std::tie(CurrentParam, Parameters) = Parameters.split(':');
6894
6895 if (!isValidAsciiIdentifier(CurrentParam)) {
6896 S.Diag(Loc, diag::warn_attr_swift_name_invalid_identifier)
6897 << AL << /*parameter*/2;
6898 return false;
6899 }
6900
6901 if (IsMember && CurrentParam == "self") {
6902 // "self" indicates the "self" argument for a member.
6903
6904 // More than one "self"?
6905 if (SelfLocation) {
6906 S.Diag(Loc, diag::warn_attr_swift_name_multiple_selfs) << AL;
6907 return false;
6908 }
6909
6910 // The "self" location is the current parameter.
6911 SelfLocation = SwiftParamCount;
6912 } else if (CurrentParam == "newValue") {
6913 // "newValue" indicates the "newValue" argument for a setter.
6914
6915 // There should only be one 'newValue', but it's only significant for
6916 // subscript accessors, so don't error right away.
6917 ++NewValueCount;
6918
6919 NewValueLocation = SwiftParamCount;
6920 }
6921
6922 ++SwiftParamCount;
6923 } while (!Parameters.empty());
6924
6925 // Only instance subscripts are currently supported.
6926 if (IsSubscript && !SelfLocation) {
6927 S.Diag(Loc, diag::warn_attr_swift_name_subscript_invalid_parameter)
6928 << AL << /*have a 'self:' parameter*/2;
6929 return false;
6930 }
6931
6932 IsSingleParamInit =
6933 SwiftParamCount == 1 && BaseName == "init" && CurrentParam != "_";
6934
6935 // Check the number of parameters for a getter/setter.
6936 if (IsGetter || IsSetter) {
6937 // Setters have one parameter for the new value.
6938 unsigned NumExpectedParams = IsGetter ? 0 : 1;
6939 unsigned ParamDiag =
6940 IsGetter ? diag::warn_attr_swift_name_getter_parameters
6941 : diag::warn_attr_swift_name_setter_parameters;
6942
6943 // Instance methods have one parameter for "self".
6944 if (SelfLocation)
6945 ++NumExpectedParams;
6946
6947 // Subscripts may have additional parameters beyond the expected params for
6948 // the index.
6949 if (IsSubscript) {
6950 if (SwiftParamCount < NumExpectedParams) {
6951 S.Diag(Loc, ParamDiag) << AL;
6952 return false;
6953 }
6954
6955 // A subscript setter must explicitly label its newValue parameter to
6956 // distinguish it from index parameters.
6957 if (IsSetter) {
6958 if (!NewValueLocation) {
6959 S.Diag(Loc, diag::warn_attr_swift_name_subscript_setter_no_newValue)
6960 << AL;
6961 return false;
6962 }
6963 if (NewValueCount > 1) {
6964 S.Diag(Loc, diag::warn_attr_swift_name_subscript_setter_multiple_newValues)
6965 << AL;
6966 return false;
6967 }
6968 } else {
6969 // Subscript getters should have no 'newValue:' parameter.
6970 if (NewValueLocation) {
6971 S.Diag(Loc, diag::warn_attr_swift_name_subscript_getter_newValue)
6972 << AL;
6973 return false;
6974 }
6975 }
6976 } else {
6977 // Property accessors must have exactly the number of expected params.
6978 if (SwiftParamCount != NumExpectedParams) {
6979 S.Diag(Loc, ParamDiag) << AL;
6980 return false;
6981 }
6982 }
6983 }
6984
6985 return true;
6986}
6987
6989 const ParsedAttr &AL, bool IsAsync) {
6990 if (isa<ObjCMethodDecl>(D) || isa<FunctionDecl>(D)) {
6992 unsigned ParamCount;
6993
6994 if (const auto *Method = dyn_cast<ObjCMethodDecl>(D)) {
6995 ParamCount = Method->getSelector().getNumArgs();
6996 Params = Method->parameters().slice(0, ParamCount);
6997 } else {
6998 const auto *F = cast<FunctionDecl>(D);
6999
7000 ParamCount = F->getNumParams();
7001 Params = F->parameters();
7002
7003 if (!F->hasWrittenPrototype()) {
7004 Diag(Loc, diag::warn_attribute_wrong_decl_type)
7005 << AL << AL.isRegularKeywordAttribute()
7007 return false;
7008 }
7009 }
7010
7011 // The async name drops the last callback parameter.
7012 if (IsAsync) {
7013 if (ParamCount == 0) {
7014 Diag(Loc, diag::warn_attr_swift_name_decl_missing_params)
7015 << AL << isa<ObjCMethodDecl>(D);
7016 return false;
7017 }
7018 ParamCount -= 1;
7019 }
7020
7021 unsigned SwiftParamCount;
7022 bool IsSingleParamInit;
7023 if (!validateSwiftFunctionName(*this, AL, Loc, Name,
7024 SwiftParamCount, IsSingleParamInit))
7025 return false;
7026
7027 bool ParamCountValid;
7028 if (SwiftParamCount == ParamCount) {
7029 ParamCountValid = true;
7030 } else if (SwiftParamCount > ParamCount) {
7031 ParamCountValid = IsSingleParamInit && ParamCount == 0;
7032 } else {
7033 // We have fewer Swift parameters than Objective-C parameters, but that
7034 // might be because we've transformed some of them. Check for potential
7035 // "out" parameters and err on the side of not warning.
7036 unsigned MaybeOutParamCount =
7037 llvm::count_if(Params, [](const ParmVarDecl *Param) -> bool {
7038 QualType ParamTy = Param->getType();
7039 if (ParamTy->isReferenceType() || ParamTy->isPointerType())
7040 return !ParamTy->getPointeeType().isConstQualified();
7041 return false;
7042 });
7043
7044 ParamCountValid = SwiftParamCount + MaybeOutParamCount >= ParamCount;
7045 }
7046
7047 if (!ParamCountValid) {
7048 Diag(Loc, diag::warn_attr_swift_name_num_params)
7049 << (SwiftParamCount > ParamCount) << AL << ParamCount
7050 << SwiftParamCount;
7051 return false;
7052 }
7053 } else if ((isa<EnumConstantDecl>(D) || isa<ObjCProtocolDecl>(D) ||
7054 isa<ObjCInterfaceDecl>(D) || isa<ObjCPropertyDecl>(D) ||
7055 isa<VarDecl>(D) || isa<TypedefNameDecl>(D) || isa<TagDecl>(D) ||
7056 isa<IndirectFieldDecl>(D) || isa<FieldDecl>(D)) &&
7057 !IsAsync) {
7058 StringRef ContextName, BaseName;
7059
7060 std::tie(ContextName, BaseName) = Name.split('.');
7061 if (BaseName.empty()) {
7062 BaseName = ContextName;
7063 ContextName = StringRef();
7064 } else if (!isValidAsciiIdentifier(ContextName)) {
7065 Diag(Loc, diag::warn_attr_swift_name_invalid_identifier) << AL
7066 << /*context*/1;
7067 return false;
7068 }
7069
7070 if (!isValidAsciiIdentifier(BaseName)) {
7071 Diag(Loc, diag::warn_attr_swift_name_invalid_identifier) << AL
7072 << /*basename*/0;
7073 return false;
7074 }
7075 } else {
7076 Diag(Loc, diag::warn_attr_swift_name_decl_kind) << AL;
7077 return false;
7078 }
7079 return true;
7080}
7081
7082static void handleSwiftName(Sema &S, Decl *D, const ParsedAttr &AL) {
7083 StringRef Name;
7085 if (!S.checkStringLiteralArgumentAttr(AL, 0, Name, &Loc))
7086 return;
7087
7088 if (!S.DiagnoseSwiftName(D, Name, Loc, AL, /*IsAsync=*/false))
7089 return;
7090
7091 D->addAttr(::new (S.Context) SwiftNameAttr(S.Context, AL, Name));
7092}
7093
7094static void handleSwiftAsyncName(Sema &S, Decl *D, const ParsedAttr &AL) {
7095 StringRef Name;
7097 if (!S.checkStringLiteralArgumentAttr(AL, 0, Name, &Loc))
7098 return;
7099
7100 if (!S.DiagnoseSwiftName(D, Name, Loc, AL, /*IsAsync=*/true))
7101 return;
7102
7103 D->addAttr(::new (S.Context) SwiftAsyncNameAttr(S.Context, AL, Name));
7104}
7105
7106static void handleSwiftNewType(Sema &S, Decl *D, const ParsedAttr &AL) {
7107 // Make sure that there is an identifier as the annotation's single argument.
7108 if (!AL.checkExactlyNumArgs(S, 1))
7109 return;
7110
7111 if (!AL.isArgIdent(0)) {
7112 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
7113 << AL << AANT_ArgumentIdentifier;
7114 return;
7115 }
7116
7117 SwiftNewTypeAttr::NewtypeKind Kind;
7118 IdentifierInfo *II = AL.getArgAsIdent(0)->Ident;
7119 if (!SwiftNewTypeAttr::ConvertStrToNewtypeKind(II->getName(), Kind)) {
7120 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported) << AL << II;
7121 return;
7122 }
7123
7124 if (!isa<TypedefNameDecl>(D)) {
7125 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type_str)
7126 << AL << AL.isRegularKeywordAttribute() << "typedefs";
7127 return;
7128 }
7129
7130 D->addAttr(::new (S.Context) SwiftNewTypeAttr(S.Context, AL, Kind));
7131}
7132
7133static void handleSwiftAsyncAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7134 if (!AL.isArgIdent(0)) {
7135 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type)
7136 << AL << 1 << AANT_ArgumentIdentifier;
7137 return;
7138 }
7139
7140 SwiftAsyncAttr::Kind Kind;
7141 IdentifierInfo *II = AL.getArgAsIdent(0)->Ident;
7142 if (!SwiftAsyncAttr::ConvertStrToKind(II->getName(), Kind)) {
7143 S.Diag(AL.getLoc(), diag::err_swift_async_no_access) << AL << II;
7144 return;
7145 }
7146
7147 ParamIdx Idx;
7148 if (Kind == SwiftAsyncAttr::None) {
7149 // If this is 'none', then there shouldn't be any additional arguments.
7150 if (!AL.checkExactlyNumArgs(S, 1))
7151 return;
7152 } else {
7153 // Non-none swift_async requires a completion handler index argument.
7154 if (!AL.checkExactlyNumArgs(S, 2))
7155 return;
7156
7157 Expr *HandlerIdx = AL.getArgAsExpr(1);
7158 if (!checkFunctionOrMethodParameterIndex(S, D, AL, 2, HandlerIdx, Idx))
7159 return;
7160
7161 const ParmVarDecl *CompletionBlock =
7163 QualType CompletionBlockType = CompletionBlock->getType();
7164 if (!CompletionBlockType->isBlockPointerType()) {
7165 S.Diag(CompletionBlock->getLocation(),
7166 diag::err_swift_async_bad_block_type)
7167 << CompletionBlock->getType();
7168 return;
7169 }
7170 QualType BlockTy =
7171 CompletionBlockType->castAs<BlockPointerType>()->getPointeeType();
7172 if (!BlockTy->castAs<FunctionType>()->getReturnType()->isVoidType()) {
7173 S.Diag(CompletionBlock->getLocation(),
7174 diag::err_swift_async_bad_block_type)
7175 << CompletionBlock->getType();
7176 return;
7177 }
7178 }
7179
7180 auto *AsyncAttr =
7181 ::new (S.Context) SwiftAsyncAttr(S.Context, AL, Kind, Idx);
7182 D->addAttr(AsyncAttr);
7183
7184 if (auto *ErrorAttr = D->getAttr<SwiftAsyncErrorAttr>())
7185 checkSwiftAsyncErrorBlock(S, D, ErrorAttr, AsyncAttr);
7186}
7187
7188//===----------------------------------------------------------------------===//
7189// Microsoft specific attribute handlers.
7190//===----------------------------------------------------------------------===//
7191
7193 StringRef UuidAsWritten, MSGuidDecl *GuidDecl) {
7194 if (const auto *UA = D->getAttr<UuidAttr>()) {
7195 if (declaresSameEntity(UA->getGuidDecl(), GuidDecl))
7196 return nullptr;
7197 if (!UA->getGuid().empty()) {
7198 Diag(UA->getLocation(), diag::err_mismatched_uuid);
7199 Diag(CI.getLoc(), diag::note_previous_uuid);
7200 D->dropAttr<UuidAttr>();
7201 }
7202 }
7203
7204 return ::new (Context) UuidAttr(Context, CI, UuidAsWritten, GuidDecl);
7205}
7206
7207static void handleUuidAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7208 if (!S.LangOpts.CPlusPlus) {
7209 S.Diag(AL.getLoc(), diag::err_attribute_not_supported_in_lang)
7210 << AL << AttributeLangSupport::C;
7211 return;
7212 }
7213
7214 StringRef OrigStrRef;
7215 SourceLocation LiteralLoc;
7216 if (!S.checkStringLiteralArgumentAttr(AL, 0, OrigStrRef, &LiteralLoc))
7217 return;
7218
7219 // GUID format is "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX" or
7220 // "{XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX}", normalize to the former.
7221 StringRef StrRef = OrigStrRef;
7222 if (StrRef.size() == 38 && StrRef.front() == '{' && StrRef.back() == '}')
7223 StrRef = StrRef.drop_front().drop_back();
7224
7225 // Validate GUID length.
7226 if (StrRef.size() != 36) {
7227 S.Diag(LiteralLoc, diag::err_attribute_uuid_malformed_guid);
7228 return;
7229 }
7230
7231 for (unsigned i = 0; i < 36; ++i) {
7232 if (i == 8 || i == 13 || i == 18 || i == 23) {
7233 if (StrRef[i] != '-') {
7234 S.Diag(LiteralLoc, diag::err_attribute_uuid_malformed_guid);
7235 return;
7236 }
7237 } else if (!isHexDigit(StrRef[i])) {
7238 S.Diag(LiteralLoc, diag::err_attribute_uuid_malformed_guid);
7239 return;
7240 }
7241 }
7242
7243 // Convert to our parsed format and canonicalize.
7244 MSGuidDecl::Parts Parsed;
7245 StrRef.substr(0, 8).getAsInteger(16, Parsed.Part1);
7246 StrRef.substr(9, 4).getAsInteger(16, Parsed.Part2);
7247 StrRef.substr(14, 4).getAsInteger(16, Parsed.Part3);
7248 for (unsigned i = 0; i != 8; ++i)
7249 StrRef.substr(19 + 2 * i + (i >= 2 ? 1 : 0), 2)
7250 .getAsInteger(16, Parsed.Part4And5[i]);
7251 MSGuidDecl *Guid = S.Context.getMSGuidDecl(Parsed);
7252
7253 // FIXME: It'd be nice to also emit a fixit removing uuid(...) (and, if it's
7254 // the only thing in the [] list, the [] too), and add an insertion of
7255 // __declspec(uuid(...)). But sadly, neither the SourceLocs of the commas
7256 // separating attributes nor of the [ and the ] are in the AST.
7257 // Cf "SourceLocations of attribute list delimiters - [[ ... , ... ]] etc"
7258 // on cfe-dev.
7259 if (AL.isMicrosoftAttribute()) // Check for [uuid(...)] spelling.
7260 S.Diag(AL.getLoc(), diag::warn_atl_uuid_deprecated);
7261
7262 UuidAttr *UA = S.mergeUuidAttr(D, AL, OrigStrRef, Guid);
7263 if (UA)
7264 D->addAttr(UA);
7265}
7266
7267static void handleHLSLNumThreadsAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7268 llvm::VersionTuple SMVersion =
7269 S.Context.getTargetInfo().getTriple().getOSVersion();
7270 uint32_t ZMax = 1024;
7271 uint32_t ThreadMax = 1024;
7272 if (SMVersion.getMajor() <= 4) {
7273 ZMax = 1;
7274 ThreadMax = 768;
7275 } else if (SMVersion.getMajor() == 5) {
7276 ZMax = 64;
7277 ThreadMax = 1024;
7278 }
7279
7280 uint32_t X;
7281 if (!checkUInt32Argument(S, AL, AL.getArgAsExpr(0), X))
7282 return;
7283 if (X > 1024) {
7284 S.Diag(AL.getArgAsExpr(0)->getExprLoc(),
7285 diag::err_hlsl_numthreads_argument_oor) << 0 << 1024;
7286 return;
7287 }
7288 uint32_t Y;
7289 if (!checkUInt32Argument(S, AL, AL.getArgAsExpr(1), Y))
7290 return;
7291 if (Y > 1024) {
7292 S.Diag(AL.getArgAsExpr(1)->getExprLoc(),
7293 diag::err_hlsl_numthreads_argument_oor) << 1 << 1024;
7294 return;
7295 }
7296 uint32_t Z;
7297 if (!checkUInt32Argument(S, AL, AL.getArgAsExpr(2), Z))
7298 return;
7299 if (Z > ZMax) {
7300 S.Diag(AL.getArgAsExpr(2)->getExprLoc(),
7301 diag::err_hlsl_numthreads_argument_oor) << 2 << ZMax;
7302 return;
7303 }
7304
7305 if (X * Y * Z > ThreadMax) {
7306 S.Diag(AL.getLoc(), diag::err_hlsl_numthreads_invalid) << ThreadMax;
7307 return;
7308 }
7309
7310 HLSLNumThreadsAttr *NewAttr = S.HLSL().mergeNumThreadsAttr(D, AL, X, Y, Z);
7311 if (NewAttr)
7312 D->addAttr(NewAttr);
7313}
7314
7317 return false;
7318 if (const auto *VT = T->getAs<VectorType>())
7319 return VT->getNumElements() <= 3;
7320 return true;
7321}
7322
7324 const ParsedAttr &AL) {
7325 // FIXME: support semantic on field.
7326 // See https://github.com/llvm/llvm-project/issues/57889.
7327 if (isa<FieldDecl>(D)) {
7328 S.Diag(AL.getLoc(), diag::err_hlsl_attr_invalid_ast_node)
7329 << AL << "parameter";
7330 return;
7331 }
7332
7333 auto *VD = cast<ValueDecl>(D);
7334 if (!isLegalTypeForHLSLSV_DispatchThreadID(VD->getType())) {
7335 S.Diag(AL.getLoc(), diag::err_hlsl_attr_invalid_type)
7336 << AL << "uint/uint2/uint3";
7337 return;
7338 }
7339
7340 D->addAttr(::new (S.Context) HLSLSV_DispatchThreadIDAttr(S.Context, AL));
7341}
7342
7343static void handleHLSLPackOffsetAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7344 if (!isa<VarDecl>(D) || !isa<HLSLBufferDecl>(D->getDeclContext())) {
7345 S.Diag(AL.getLoc(), diag::err_hlsl_attr_invalid_ast_node)
7346 << AL << "shader constant in a constant buffer";
7347 return;
7348 }
7349
7350 uint32_t SubComponent;
7351 if (!checkUInt32Argument(S, AL, AL.getArgAsExpr(0), SubComponent))
7352 return;
7353 uint32_t Component;
7354 if (!checkUInt32Argument(S, AL, AL.getArgAsExpr(1), Component))
7355 return;
7356
7357 QualType T = cast<VarDecl>(D)->getType().getCanonicalType();
7358 // Check if T is an array or struct type.
7359 // TODO: mark matrix type as aggregate type.
7360 bool IsAggregateTy = (T->isArrayType() || T->isStructureType());
7361
7362 // Check Component is valid for T.
7363 if (Component) {
7364 unsigned Size = S.getASTContext().getTypeSize(T);
7365 if (IsAggregateTy || Size > 128) {
7366 S.Diag(AL.getLoc(), diag::err_hlsl_packoffset_cross_reg_boundary);
7367 return;
7368 } else {
7369 // Make sure Component + sizeof(T) <= 4.
7370 if ((Component * 32 + Size) > 128) {
7371 S.Diag(AL.getLoc(), diag::err_hlsl_packoffset_cross_reg_boundary);
7372 return;
7373 }
7374 QualType EltTy = T;
7375 if (const auto *VT = T->getAs<VectorType>())
7376 EltTy = VT->getElementType();
7377 unsigned Align = S.getASTContext().getTypeAlign(EltTy);
7378 if (Align > 32 && Component == 1) {
7379 // NOTE: Component 3 will hit err_hlsl_packoffset_cross_reg_boundary.
7380 // So we only need to check Component 1 here.
7381 S.Diag(AL.getLoc(), diag::err_hlsl_packoffset_alignment_mismatch)
7382 << Align << EltTy;
7383 return;
7384 }
7385 }
7386 }
7387
7388 D->addAttr(::new (S.Context)
7389 HLSLPackOffsetAttr(S.Context, AL, SubComponent, Component));
7390}
7391
7392static void handleHLSLShaderAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7393 StringRef Str;
7394 SourceLocation ArgLoc;
7395 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &ArgLoc))
7396 return;
7397
7398 HLSLShaderAttr::ShaderType ShaderType;
7399 if (!HLSLShaderAttr::ConvertStrToShaderType(Str, ShaderType)) {
7400 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported)
7401 << AL << Str << ArgLoc;
7402 return;
7403 }
7404
7405 // FIXME: check function match the shader stage.
7406
7407 HLSLShaderAttr *NewAttr = S.HLSL().mergeShaderAttr(D, AL, ShaderType);
7408 if (NewAttr)
7409 D->addAttr(NewAttr);
7410}
7411
7413 const ParsedAttr &AL) {
7414 StringRef Space = "space0";
7415 StringRef Slot = "";
7416
7417 if (!AL.isArgIdent(0)) {
7418 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
7419 << AL << AANT_ArgumentIdentifier;
7420 return;
7421 }
7422
7424 StringRef Str = Loc->Ident->getName();
7425 SourceLocation ArgLoc = Loc->Loc;
7426
7427 SourceLocation SpaceArgLoc;
7428 if (AL.getNumArgs() == 2) {
7429 Slot = Str;
7430 if (!AL.isArgIdent(1)) {
7431 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
7432 << AL << AANT_ArgumentIdentifier;
7433 return;
7434 }
7435
7437 Space = Loc->Ident->getName();
7438 SpaceArgLoc = Loc->Loc;
7439 } else {
7440 Slot = Str;
7441 }
7442
7443 // Validate.
7444 if (!Slot.empty()) {
7445 switch (Slot[0]) {
7446 case 'u':
7447 case 'b':
7448 case 's':
7449 case 't':
7450 break;
7451 default:
7452 S.Diag(ArgLoc, diag::err_hlsl_unsupported_register_type)
7453 << Slot.substr(0, 1);
7454 return;
7455 }
7456
7457 StringRef SlotNum = Slot.substr(1);
7458 unsigned Num = 0;
7459 if (SlotNum.getAsInteger(10, Num)) {
7460 S.Diag(ArgLoc, diag::err_hlsl_unsupported_register_number);
7461 return;
7462 }
7463 }
7464
7465 if (!Space.starts_with("space")) {
7466 S.Diag(SpaceArgLoc, diag::err_hlsl_expected_space) << Space;
7467 return;
7468 }
7469 StringRef SpaceNum = Space.substr(5);
7470 unsigned Num = 0;
7471 if (SpaceNum.getAsInteger(10, Num)) {
7472 S.Diag(SpaceArgLoc, diag::err_hlsl_expected_space) << Space;
7473 return;
7474 }
7475
7476 // FIXME: check reg type match decl. Issue
7477 // https://github.com/llvm/llvm-project/issues/57886.
7478 HLSLResourceBindingAttr *NewAttr =
7479 HLSLResourceBindingAttr::Create(S.getASTContext(), Slot, Space, AL);
7480 if (NewAttr)
7481 D->addAttr(NewAttr);
7482}
7483
7485 const ParsedAttr &AL) {
7486 HLSLParamModifierAttr *NewAttr = S.HLSL().mergeParamModifierAttr(
7487 D, AL,
7488 static_cast<HLSLParamModifierAttr::Spelling>(AL.getSemanticSpelling()));
7489 if (NewAttr)
7490 D->addAttr(NewAttr);
7491}
7492
7493static void handleMSInheritanceAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7494 if (!S.LangOpts.CPlusPlus) {
7495 S.Diag(AL.getLoc(), diag::err_attribute_not_supported_in_lang)
7496 << AL << AttributeLangSupport::C;
7497 return;
7498 }
7499 MSInheritanceAttr *IA = S.mergeMSInheritanceAttr(
7500 D, AL, /*BestCase=*/true, (MSInheritanceModel)AL.getSemanticSpelling());
7501 if (IA) {
7502 D->addAttr(IA);
7503 S.Consumer.AssignInheritanceModel(cast<CXXRecordDecl>(D));
7504 }
7505}
7506
7507static void handleDeclspecThreadAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7508 const auto *VD = cast<VarDecl>(D);
7510 S.Diag(AL.getLoc(), diag::err_thread_unsupported);
7511 return;
7512 }
7513 if (VD->getTSCSpec() != TSCS_unspecified) {
7514 S.Diag(AL.getLoc(), diag::err_declspec_thread_on_thread_variable);
7515 return;
7516 }
7517 if (VD->hasLocalStorage()) {
7518 S.Diag(AL.getLoc(), diag::err_thread_non_global) << "__declspec(thread)";
7519 return;
7520 }
7521 D->addAttr(::new (S.Context) ThreadAttr(S.Context, AL));
7522}
7523
7524static void handleMSConstexprAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7526 S.Diag(AL.getLoc(), diag::warn_unknown_attribute_ignored)
7527 << AL << AL.getRange();
7528 return;
7529 }
7530 auto *FD = cast<FunctionDecl>(D);
7531 if (FD->isConstexprSpecified() || FD->isConsteval()) {
7532 S.Diag(AL.getLoc(), diag::err_ms_constexpr_cannot_be_applied)
7533 << FD->isConsteval() << FD;
7534 return;
7535 }
7536 if (auto *MD = dyn_cast<CXXMethodDecl>(FD)) {
7537 if (!S.getLangOpts().CPlusPlus20 && MD->isVirtual()) {
7538 S.Diag(AL.getLoc(), diag::err_ms_constexpr_cannot_be_applied)
7539 << /*virtual*/ 2 << MD;
7540 return;
7541 }
7542 }
7543 D->addAttr(::new (S.Context) MSConstexprAttr(S.Context, AL));
7544}
7545
7546static void handleAbiTagAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7548 for (unsigned I = 0, E = AL.getNumArgs(); I != E; ++I) {
7549 StringRef Tag;
7550 if (!S.checkStringLiteralArgumentAttr(AL, I, Tag))
7551 return;
7552 Tags.push_back(Tag);
7553 }
7554
7555 if (const auto *NS = dyn_cast<NamespaceDecl>(D)) {
7556 if (!NS->isInline()) {
7557 S.Diag(AL.getLoc(), diag::warn_attr_abi_tag_namespace) << 0;
7558 return;
7559 }
7560 if (NS->isAnonymousNamespace()) {
7561 S.Diag(AL.getLoc(), diag::warn_attr_abi_tag_namespace) << 1;
7562 return;
7563 }
7564 if (AL.getNumArgs() == 0)
7565 Tags.push_back(NS->getName());
7566 } else if (!AL.checkAtLeastNumArgs(S, 1))
7567 return;
7568
7569 // Store tags sorted and without duplicates.
7570 llvm::sort(Tags);
7571 Tags.erase(std::unique(Tags.begin(), Tags.end()), Tags.end());
7572
7573 D->addAttr(::new (S.Context)
7574 AbiTagAttr(S.Context, AL, Tags.data(), Tags.size()));
7575}
7576
7577static void handleARMInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7578 // Check the attribute arguments.
7579 if (AL.getNumArgs() > 1) {
7580 S.Diag(AL.getLoc(), diag::err_attribute_too_many_arguments) << AL << 1;
7581 return;
7582 }
7583
7584 StringRef Str;
7585 SourceLocation ArgLoc;
7586
7587 if (AL.getNumArgs() == 0)
7588 Str = "";
7589 else if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &ArgLoc))
7590 return;
7591
7592 ARMInterruptAttr::InterruptType Kind;
7593 if (!ARMInterruptAttr::ConvertStrToInterruptType(Str, Kind)) {
7594 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported) << AL << Str
7595 << ArgLoc;
7596 return;
7597 }
7598
7599 D->addAttr(::new (S.Context) ARMInterruptAttr(S.Context, AL, Kind));
7600}
7601
7602static void handleMSP430InterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7603 // MSP430 'interrupt' attribute is applied to
7604 // a function with no parameters and void return type.
7605 if (!isFunctionOrMethod(D)) {
7606 S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
7608 return;
7609 }
7610
7612 S.Diag(D->getLocation(), diag::warn_interrupt_attribute_invalid)
7613 << /*MSP430*/ 1 << 0;
7614 return;
7615 }
7616
7617 if (!getFunctionOrMethodResultType(D)->isVoidType()) {
7618 S.Diag(D->getLocation(), diag::warn_interrupt_attribute_invalid)
7619 << /*MSP430*/ 1 << 1;
7620 return;
7621 }
7622
7623 // The attribute takes one integer argument.
7624 if (!AL.checkExactlyNumArgs(S, 1))
7625 return;
7626
7627 if (!AL.isArgExpr(0)) {
7628 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
7630 return;
7631 }
7632
7633 Expr *NumParamsExpr = static_cast<Expr *>(AL.getArgAsExpr(0));
7634 std::optional<llvm::APSInt> NumParams = llvm::APSInt(32);
7635 if (!(NumParams = NumParamsExpr->getIntegerConstantExpr(S.Context))) {
7636 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
7638 << NumParamsExpr->getSourceRange();
7639 return;
7640 }
7641 // The argument should be in range 0..63.
7642 unsigned Num = NumParams->getLimitedValue(255);
7643 if (Num > 63) {
7644 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
7645 << AL << (int)NumParams->getSExtValue()
7646 << NumParamsExpr->getSourceRange();
7647 return;
7648 }
7649
7650 D->addAttr(::new (S.Context) MSP430InterruptAttr(S.Context, AL, Num));
7651 D->addAttr(UsedAttr::CreateImplicit(S.Context));
7652}
7653
7654static void handleMipsInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7655 // Only one optional argument permitted.
7656 if (AL.getNumArgs() > 1) {
7657 S.Diag(AL.getLoc(), diag::err_attribute_too_many_arguments) << AL << 1;
7658 return;
7659 }
7660
7661 StringRef Str;
7662 SourceLocation ArgLoc;
7663
7664 if (AL.getNumArgs() == 0)
7665 Str = "";
7666 else if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &ArgLoc))
7667 return;
7668
7669 // Semantic checks for a function with the 'interrupt' attribute for MIPS:
7670 // a) Must be a function.
7671 // b) Must have no parameters.
7672 // c) Must have the 'void' return type.
7673 // d) Cannot have the 'mips16' attribute, as that instruction set
7674 // lacks the 'eret' instruction.
7675 // e) The attribute itself must either have no argument or one of the
7676 // valid interrupt types, see [MipsInterruptDocs].
7677
7678 if (!isFunctionOrMethod(D)) {
7679 S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
7681 return;
7682 }
7683
7685 S.Diag(D->getLocation(), diag::warn_interrupt_attribute_invalid)
7686 << /*MIPS*/ 0 << 0;
7687 return;
7688 }
7689
7690 if (!getFunctionOrMethodResultType(D)->isVoidType()) {
7691 S.Diag(D->getLocation(), diag::warn_interrupt_attribute_invalid)
7692 << /*MIPS*/ 0 << 1;
7693 return;
7694 }
7695
7696 // We still have to do this manually because the Interrupt attributes are
7697 // a bit special due to sharing their spellings across targets.
7698 if (checkAttrMutualExclusion<Mips16Attr>(S, D, AL))
7699 return;
7700
7701 MipsInterruptAttr::InterruptType Kind;
7702 if (!MipsInterruptAttr::ConvertStrToInterruptType(Str, Kind)) {
7703 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported)
7704 << AL << "'" + std::string(Str) + "'";
7705 return;
7706 }
7707
7708 D->addAttr(::new (S.Context) MipsInterruptAttr(S.Context, AL, Kind));
7709}
7710
7711static void handleM68kInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7712 if (!AL.checkExactlyNumArgs(S, 1))
7713 return;
7714
7715 if (!AL.isArgExpr(0)) {
7716 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
7718 return;
7719 }
7720
7721 // FIXME: Check for decl - it should be void ()(void).
7722
7723 Expr *NumParamsExpr = static_cast<Expr *>(AL.getArgAsExpr(0));
7724 auto MaybeNumParams = NumParamsExpr->getIntegerConstantExpr(S.Context);
7725 if (!MaybeNumParams) {
7726 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
7728 << NumParamsExpr->getSourceRange();
7729 return;
7730 }
7731
7732 unsigned Num = MaybeNumParams->getLimitedValue(255);
7733 if ((Num & 1) || Num > 30) {
7734 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
7735 << AL << (int)MaybeNumParams->getSExtValue()
7736 << NumParamsExpr->getSourceRange();
7737 return;
7738 }
7739
7740 D->addAttr(::new (S.Context) M68kInterruptAttr(S.Context, AL, Num));
7741 D->addAttr(UsedAttr::CreateImplicit(S.Context));
7742}
7743
7744static void handleAnyX86InterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7745 // Semantic checks for a function with the 'interrupt' attribute.
7746 // a) Must be a function.
7747 // b) Must have the 'void' return type.
7748 // c) Must take 1 or 2 arguments.
7749 // d) The 1st argument must be a pointer.
7750 // e) The 2nd argument (if any) must be an unsigned integer.
7753 cast<NamedDecl>(D)->getDeclName().getCXXOverloadedOperator())) {
7754 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
7755 << AL << AL.isRegularKeywordAttribute()
7757 return;
7758 }
7759 // Interrupt handler must have void return type.
7760 if (!getFunctionOrMethodResultType(D)->isVoidType()) {
7762 diag::err_anyx86_interrupt_attribute)
7763 << (S.Context.getTargetInfo().getTriple().getArch() == llvm::Triple::x86
7764 ? 0
7765 : 1)
7766 << 0;
7767 return;
7768 }
7769 // Interrupt handler must have 1 or 2 parameters.
7770 unsigned NumParams = getFunctionOrMethodNumParams(D);
7771 if (NumParams < 1 || NumParams > 2) {
7772 S.Diag(D->getBeginLoc(), diag::err_anyx86_interrupt_attribute)
7773 << (S.Context.getTargetInfo().getTriple().getArch() == llvm::Triple::x86
7774 ? 0
7775 : 1)
7776 << 1;
7777 return;
7778 }
7779 // The first argument must be a pointer.
7782 diag::err_anyx86_interrupt_attribute)
7783 << (S.Context.getTargetInfo().getTriple().getArch() == llvm::Triple::x86
7784 ? 0
7785 : 1)
7786 << 2;
7787 return;
7788 }
7789 // The second argument, if present, must be an unsigned integer.
7790 unsigned TypeSize =
7791 S.Context.getTargetInfo().getTriple().getArch() == llvm::Triple::x86_64
7792 ? 64
7793 : 32;
7794 if (NumParams == 2 &&
7795 (!getFunctionOrMethodParamType(D, 1)->isUnsignedIntegerType() ||
7796 S.Context.getTypeSize(getFunctionOrMethodParamType(D, 1)) != TypeSize)) {
7798 diag::err_anyx86_interrupt_attribute)
7799 << (S.Context.getTargetInfo().getTriple().getArch() == llvm::Triple::x86
7800 ? 0
7801 : 1)
7802 << 3 << S.Context.getIntTypeForBitwidth(TypeSize, /*Signed=*/false);
7803 return;
7804 }
7805 D->addAttr(::new (S.Context) AnyX86InterruptAttr(S.Context, AL));
7806 D->addAttr(UsedAttr::CreateImplicit(S.Context));
7807}
7808
7809static void handleAVRInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7810 if (!isFunctionOrMethod(D)) {
7811 S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
7813 return;
7814 }
7815
7816 if (!AL.checkExactlyNumArgs(S, 0))
7817 return;
7818
7819 handleSimpleAttribute<AVRInterruptAttr>(S, D, AL);
7820}
7821
7822static void handleAVRSignalAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7823 if (!isFunctionOrMethod(D)) {
7824 S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
7826 return;
7827 }
7828
7829 if (!AL.checkExactlyNumArgs(S, 0))
7830 return;
7831
7832 handleSimpleAttribute<AVRSignalAttr>(S, D, AL);
7833}
7834
7836 // Add preserve_access_index attribute to all fields and inner records.
7837 for (auto *D : RD->decls()) {
7838 if (D->hasAttr<BPFPreserveAccessIndexAttr>())
7839 continue;
7840
7841 D->addAttr(BPFPreserveAccessIndexAttr::CreateImplicit(S.Context));
7842 if (auto *Rec = dyn_cast<RecordDecl>(D))
7844 }
7845}
7846
7848 const ParsedAttr &AL) {
7849 auto *Rec = cast<RecordDecl>(D);
7851 Rec->addAttr(::new (S.Context) BPFPreserveAccessIndexAttr(S.Context, AL));
7852}
7853
7854static bool hasBTFDeclTagAttr(Decl *D, StringRef Tag) {
7855 for (const auto *I : D->specific_attrs<BTFDeclTagAttr>()) {
7856 if (I->getBTFDeclTag() == Tag)
7857 return true;
7858 }
7859 return false;
7860}
7861
7862static void handleBTFDeclTagAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
7863 StringRef Str;
7864 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str))
7865 return;
7866 if (hasBTFDeclTagAttr(D, Str))
7867 return;
7868
7869 D->addAttr(::new (S.Context) BTFDeclTagAttr(S.Context, AL, Str));
7870}
7871
7872BTFDeclTagAttr *Sema::mergeBTFDeclTagAttr(Decl *D, const BTFDeclTagAttr &AL) {
7873 if (hasBTFDeclTagAttr(D, AL.getBTFDeclTag()))
7874 return nullptr;
7875 return ::new (Context) BTFDeclTagAttr(Context, AL, AL.getBTFDeclTag());
7876}
7877
7879 const ParsedAttr &AL) {
7880 if (!isFunctionOrMethod(D)) {
7881 S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
7883 return;
7884 }
7885
7886 auto *FD = cast<FunctionDecl>(D);
7887 if (FD->isThisDeclarationADefinition()) {
7888 S.Diag(D->getLocation(), diag::err_alias_is_definition) << FD << 0;
7889 return;
7890 }
7891
7892 StringRef Str;
7893 SourceLocation ArgLoc;
7894 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &ArgLoc))
7895 return;
7896
7897 D->addAttr(::new (S.Context) WebAssemblyExportNameAttr(S.Context, AL, Str));
7898 D->addAttr(UsedAttr::CreateImplicit(S.Context));
7899}
7900
7901WebAssemblyImportModuleAttr *
7902Sema::mergeImportModuleAttr(Decl *D, const WebAssemblyImportModuleAttr &AL) {
7903 auto *FD = cast<FunctionDecl>(D);
7904
7905 if (const auto *ExistingAttr = FD->getAttr<WebAssemblyImportModuleAttr>()) {
7906 if (ExistingAttr->getImportModule() == AL.getImportModule())
7907 return nullptr;
7908 Diag(ExistingAttr->getLocation(), diag::warn_mismatched_import) << 0
7909 << ExistingAttr->getImportModule() << AL.getImportModule();
7910 Diag(AL.getLoc(), diag::note_previous_attribute);
7911 return nullptr;
7912 }
7913 if (FD->hasBody()) {
7914 Diag(AL.getLoc(), diag::warn_import_on_definition) << 0;
7915 return nullptr;
7916 }
7917 return ::new (Context) WebAssemblyImportModuleAttr(Context, AL,
7918 AL.getImportModule());
7919}
7920
7921WebAssemblyImportNameAttr *
7922Sema::mergeImportNameAttr(Decl *D, const WebAssemblyImportNameAttr &AL) {
7923 auto *FD = cast<FunctionDecl>(D);
7924
7925 if (const auto *ExistingAttr = FD->getAttr<WebAssemblyImportNameAttr>()) {
7926 if (ExistingAttr->getImportName() == AL.getImportName())
7927 return nullptr;
7928 Diag(ExistingAttr->getLocation(), diag::warn_mismatched_import) << 1
7929 << ExistingAttr->getImportName() << AL.getImportName();
7930 Diag(AL.getLoc(), diag::note_previous_attribute);
7931 return nullptr;
7932 }
7933 if (FD->hasBody()) {
7934 Diag(AL.getLoc(), diag::warn_import_on_definition) << 1;
7935 return nullptr;
7936 }
7937 return ::new (Context) WebAssemblyImportNameAttr(Context, AL,
7938 AL.getImportName());
7939}
7940
7941static void
7943 auto *FD = cast<FunctionDecl>(D);
7944
7945 StringRef Str;
7946 SourceLocation ArgLoc;
7947 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &ArgLoc))
7948 return;
7949 if (FD->hasBody()) {
7950 S.Diag(AL.getLoc(), diag::warn_import_on_definition) << 0;
7951 return;
7952 }
7953
7954 FD->addAttr(::new (S.Context)
7955 WebAssemblyImportModuleAttr(S.Context, AL, Str));
7956}
7957
7958static void
7960 auto *FD = cast<FunctionDecl>(D);
7961
7962 StringRef Str;
7963 SourceLocation ArgLoc;
7964 if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &ArgLoc))
7965 return;
7966 if (FD->hasBody()) {
7967 S.Diag(AL.getLoc(), diag::warn_import_on_definition) << 1;
7968 return;
7969 }
7970
7971 FD->addAttr(::new (S.Context) WebAssemblyImportNameAttr(S.Context, AL, Str));
7972}
7973
7975 const ParsedAttr &AL) {
7976 // Warn about repeated attributes.
7977 if (const auto *A = D->getAttr<RISCVInterruptAttr>()) {
7978 S.Diag(AL.getRange().getBegin(),
7979 diag::warn_riscv_repeated_interrupt_attribute);
7980 S.Diag(A->getLocation(), diag::note_riscv_repeated_interrupt_attribute);
7981 return;
7982 }
7983
7984 // Check the attribute argument. Argument is optional.
7985 if (!AL.checkAtMostNumArgs(S, 1))
7986 return;
7987
7988 StringRef Str;
7989 SourceLocation ArgLoc;
7990
7991 // 'machine'is the default interrupt mode.
7992 if (AL.getNumArgs() == 0)
7993 Str = "machine";
7994 else if (!S.checkStringLiteralArgumentAttr(AL, 0, Str, &ArgLoc))
7995 return;
7996
7997 // Semantic checks for a function with the 'interrupt' attribute:
7998 // - Must be a function.
7999 // - Must have no parameters.
8000 // - Must have the 'void' return type.
8001 // - The attribute itself must either have no argument or one of the
8002 // valid interrupt types, see [RISCVInterruptDocs].
8003
8004 if (D->getFunctionType() == nullptr) {
8005 S.Diag(D->getLocation(), diag::warn_attribute_wrong_decl_type)
8007 return;
8008 }
8009
8011 S.Diag(D->getLocation(), diag::warn_interrupt_attribute_invalid)
8012 << /*RISC-V*/ 2 << 0;
8013 return;
8014 }
8015
8016 if (!getFunctionOrMethodResultType(D)->isVoidType()) {
8017 S.Diag(D->getLocation(), diag::warn_interrupt_attribute_invalid)
8018 << /*RISC-V*/ 2 << 1;
8019 return;
8020 }
8021
8022 RISCVInterruptAttr::InterruptType Kind;
8023 if (!RISCVInterruptAttr::ConvertStrToInterruptType(Str, Kind)) {
8024 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported) << AL << Str
8025 << ArgLoc;
8026 return;
8027 }
8028
8029 D->addAttr(::new (S.Context) RISCVInterruptAttr(S.Context, AL, Kind));
8030}
8031
8032static void handleInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8033 // Dispatch the interrupt attribute based on the current target.
8034 switch (S.Context.getTargetInfo().getTriple().getArch()) {
8035 case llvm::Triple::msp430:
8036 handleMSP430InterruptAttr(S, D, AL);
8037 break;
8038 case llvm::Triple::mipsel:
8039 case llvm::Triple::mips:
8040 handleMipsInterruptAttr(S, D, AL);
8041 break;
8042 case llvm::Triple::m68k:
8043 handleM68kInterruptAttr(S, D, AL);
8044 break;
8045 case llvm::Triple::x86:
8046 case llvm::Triple::x86_64:
8047 handleAnyX86InterruptAttr(S, D, AL);
8048 break;
8049 case llvm::Triple::avr:
8050 handleAVRInterruptAttr(S, D, AL);
8051 break;
8052 case llvm::Triple::riscv32:
8053 case llvm::Triple::riscv64:
8054 handleRISCVInterruptAttr(S, D, AL);
8055 break;
8056 default:
8057 handleARMInterruptAttr(S, D, AL);
8058 break;
8059 }
8060}
8061
8062static bool
8064 const AMDGPUFlatWorkGroupSizeAttr &Attr) {
8065 // Accept template arguments for now as they depend on something else.
8066 // We'll get to check them when they eventually get instantiated.
8067 if (MinExpr->isValueDependent() || MaxExpr->isValueDependent())
8068 return false;
8069
8070 uint32_t Min = 0;
8071 if (!checkUInt32Argument(S, Attr, MinExpr, Min, 0))
8072 return true;
8073
8074 uint32_t Max = 0;
8075 if (!checkUInt32Argument(S, Attr, MaxExpr, Max, 1))
8076 return true;
8077
8078 if (Min == 0 && Max != 0) {
8079 S.Diag(Attr.getLocation(), diag::err_attribute_argument_invalid)
8080 << &Attr << 0;
8081 return true;
8082 }
8083 if (Min > Max) {
8084 S.Diag(Attr.getLocation(), diag::err_attribute_argument_invalid)
8085 << &Attr << 1;
8086 return true;
8087 }
8088
8089 return false;
8090}
8091
8092AMDGPUFlatWorkGroupSizeAttr *
8094 Expr *MinExpr, Expr *MaxExpr) {
8095 AMDGPUFlatWorkGroupSizeAttr TmpAttr(Context, CI, MinExpr, MaxExpr);
8096
8097 if (checkAMDGPUFlatWorkGroupSizeArguments(*this, MinExpr, MaxExpr, TmpAttr))
8098 return nullptr;
8099 return ::new (Context)
8100 AMDGPUFlatWorkGroupSizeAttr(Context, CI, MinExpr, MaxExpr);
8101}
8102
8104 const AttributeCommonInfo &CI,
8105 Expr *MinExpr, Expr *MaxExpr) {
8106 if (auto *Attr = CreateAMDGPUFlatWorkGroupSizeAttr(CI, MinExpr, MaxExpr))
8107 D->addAttr(Attr);
8108}
8109
8111 const ParsedAttr &AL) {
8112 Expr *MinExpr = AL.getArgAsExpr(0);
8113 Expr *MaxExpr = AL.getArgAsExpr(1);
8114
8115 S.addAMDGPUFlatWorkGroupSizeAttr(D, AL, MinExpr, MaxExpr);
8116}
8117
8119 Expr *MaxExpr,
8120 const AMDGPUWavesPerEUAttr &Attr) {
8121 if (S.DiagnoseUnexpandedParameterPack(MinExpr) ||
8122 (MaxExpr && S.DiagnoseUnexpandedParameterPack(MaxExpr)))
8123 return true;
8124
8125 // Accept template arguments for now as they depend on something else.
8126 // We'll get to check them when they eventually get instantiated.
8127 if (MinExpr->isValueDependent() || (MaxExpr && MaxExpr->isValueDependent()))
8128 return false;
8129
8130 uint32_t Min = 0;
8131 if (!checkUInt32Argument(S, Attr, MinExpr, Min, 0))
8132 return true;
8133
8134 uint32_t Max = 0;
8135 if (MaxExpr && !checkUInt32Argument(S, Attr, MaxExpr, Max, 1))
8136 return true;
8137
8138 if (Min == 0 && Max != 0) {
8139 S.Diag(Attr.getLocation(), diag::err_attribute_argument_invalid)
8140 << &Attr << 0;
8141 return true;
8142 }
8143 if (Max != 0 && Min > Max) {
8144 S.Diag(Attr.getLocation(), diag::err_attribute_argument_invalid)
8145 << &Attr << 1;
8146 return true;
8147 }
8148
8149 return false;
8150}
8151
8152AMDGPUWavesPerEUAttr *
8154 Expr *MaxExpr) {
8155 AMDGPUWavesPerEUAttr TmpAttr(Context, CI, MinExpr, MaxExpr);
8156
8157 if (checkAMDGPUWavesPerEUArguments(*this, MinExpr, MaxExpr, TmpAttr))
8158 return nullptr;
8159
8160 return ::new (Context) AMDGPUWavesPerEUAttr(Context, CI, MinExpr, MaxExpr);
8161}
8162
8164 Expr *MinExpr, Expr *MaxExpr) {
8165 if (auto *Attr = CreateAMDGPUWavesPerEUAttr(CI, MinExpr, MaxExpr))
8166 D->addAttr(Attr);
8167}
8168
8169static void handleAMDGPUWavesPerEUAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8170 if (!AL.checkAtLeastNumArgs(S, 1) || !AL.checkAtMostNumArgs(S, 2))
8171 return;
8172
8173 Expr *MinExpr = AL.getArgAsExpr(0);
8174 Expr *MaxExpr = (AL.getNumArgs() > 1) ? AL.getArgAsExpr(1) : nullptr;
8175
8176 S.addAMDGPUWavesPerEUAttr(D, AL, MinExpr, MaxExpr);
8177}
8178
8179static void handleAMDGPUNumSGPRAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8180 uint32_t NumSGPR = 0;
8181 Expr *NumSGPRExpr = AL.getArgAsExpr(0);
8182 if (!checkUInt32Argument(S, AL, NumSGPRExpr, NumSGPR))
8183 return;
8184
8185 D->addAttr(::new (S.Context) AMDGPUNumSGPRAttr(S.Context, AL, NumSGPR));
8186}
8187
8188static void handleAMDGPUNumVGPRAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8189 uint32_t NumVGPR = 0;
8190 Expr *NumVGPRExpr = AL.getArgAsExpr(0);
8191 if (!checkUInt32Argument(S, AL, NumVGPRExpr, NumVGPR))
8192 return;
8193
8194 D->addAttr(::new (S.Context) AMDGPUNumVGPRAttr(S.Context, AL, NumVGPR));
8195}
8196
8197static bool
8199 Expr *ZExpr,
8200 const AMDGPUMaxNumWorkGroupsAttr &Attr) {
8201 if (S.DiagnoseUnexpandedParameterPack(XExpr) ||
8202 (YExpr && S.DiagnoseUnexpandedParameterPack(YExpr)) ||
8203 (ZExpr && S.DiagnoseUnexpandedParameterPack(ZExpr)))
8204 return true;
8205
8206 // Accept template arguments for now as they depend on something else.
8207 // We'll get to check them when they eventually get instantiated.
8208 if (XExpr->isValueDependent() || (YExpr && YExpr->isValueDependent()) ||
8209 (ZExpr && ZExpr->isValueDependent()))
8210 return false;
8211
8212 uint32_t NumWG = 0;
8213 Expr *Exprs[3] = {XExpr, YExpr, ZExpr};
8214 for (int i = 0; i < 3; i++) {
8215 if (Exprs[i]) {
8216 if (!checkUInt32Argument(S, Attr, Exprs[i], NumWG, i,
8217 /*StrictlyUnsigned=*/true))
8218 return true;
8219 if (NumWG == 0) {
8220 S.Diag(Attr.getLoc(), diag::err_attribute_argument_is_zero)
8221 << &Attr << Exprs[i]->getSourceRange();
8222 return true;
8223 }
8224 }
8225 }
8226
8227 return false;
8228}
8229
8230AMDGPUMaxNumWorkGroupsAttr *
8232 Expr *XExpr, Expr *YExpr, Expr *ZExpr) {
8233 AMDGPUMaxNumWorkGroupsAttr TmpAttr(Context, CI, XExpr, YExpr, ZExpr);
8234
8235 if (checkAMDGPUMaxNumWorkGroupsArguments(*this, XExpr, YExpr, ZExpr, TmpAttr))
8236 return nullptr;
8237
8238 return ::new (Context)
8239 AMDGPUMaxNumWorkGroupsAttr(Context, CI, XExpr, YExpr, ZExpr);
8240}
8241
8243 Expr *XExpr, Expr *YExpr,
8244 Expr *ZExpr) {
8245 if (auto *Attr = CreateAMDGPUMaxNumWorkGroupsAttr(CI, XExpr, YExpr, ZExpr))
8246 D->addAttr(Attr);
8247}
8248
8250 const ParsedAttr &AL) {
8251 Expr *YExpr = (AL.getNumArgs() > 1) ? AL.getArgAsExpr(1) : nullptr;
8252 Expr *ZExpr = (AL.getNumArgs() > 2) ? AL.getArgAsExpr(2) : nullptr;
8253 S.addAMDGPUMaxNumWorkGroupsAttr(D, AL, AL.getArgAsExpr(0), YExpr, ZExpr);
8254}
8255
8257 const ParsedAttr &AL) {
8258 // If we try to apply it to a function pointer, don't warn, but don't
8259 // do anything, either. It doesn't matter anyway, because there's nothing
8260 // special about calling a force_align_arg_pointer function.
8261 const auto *VD = dyn_cast<ValueDecl>(D);
8262 if (VD && VD->getType()->isFunctionPointerType())
8263 return;
8264 // Also don't warn on function pointer typedefs.
8265 const auto *TD = dyn_cast<TypedefNameDecl>(D);
8266 if (TD && (TD->getUnderlyingType()->isFunctionPointerType() ||
8267 TD->getUnderlyingType()->isFunctionType()))
8268 return;
8269 // Attribute can only be applied to function types.
8270 if (!isa<FunctionDecl>(D)) {
8271 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type)
8273 return;
8274 }
8275
8276 D->addAttr(::new (S.Context) X86ForceAlignArgPointerAttr(S.Context, AL));
8277}
8278
8279static void handleLayoutVersion(Sema &S, Decl *D, const ParsedAttr &AL) {
8280 uint32_t Version;
8281 Expr *VersionExpr = static_cast<Expr *>(AL.getArgAsExpr(0));
8282 if (!checkUInt32Argument(S, AL, AL.getArgAsExpr(0), Version))
8283 return;
8284
8285 // TODO: Investigate what happens with the next major version of MSVC.
8286 if (Version != LangOptions::MSVC2015 / 100) {
8287 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds)
8288 << AL << Version << VersionExpr->getSourceRange();
8289 return;
8290 }
8291
8292 // The attribute expects a "major" version number like 19, but new versions of
8293 // MSVC have moved to updating the "minor", or less significant numbers, so we
8294 // have to multiply by 100 now.
8295 Version *= 100;
8296
8297 D->addAttr(::new (S.Context) LayoutVersionAttr(S.Context, AL, Version));
8298}
8299
8301 const AttributeCommonInfo &CI) {
8302 if (D->hasAttr<DLLExportAttr>()) {
8303 Diag(CI.getLoc(), diag::warn_attribute_ignored) << "'dllimport'";
8304 return nullptr;
8305 }
8306
8307 if (D->hasAttr<DLLImportAttr>())
8308 return nullptr;
8309
8310 return ::new (Context) DLLImportAttr(Context, CI);
8311}
8312
8314 const AttributeCommonInfo &CI) {
8315 if (DLLImportAttr *Import = D->getAttr<DLLImportAttr>()) {
8316 Diag(Import->getLocation(), diag::warn_attribute_ignored) << Import;
8317 D->dropAttr<DLLImportAttr>();
8318 }
8319
8320 if (D->hasAttr<DLLExportAttr>())
8321 return nullptr;
8322
8323 return ::new (Context) DLLExportAttr(Context, CI);
8324}
8325
8326static void handleDLLAttr(Sema &S, Decl *D, const ParsedAttr &A) {
8327 if (isa<ClassTemplatePartialSpecializationDecl>(D) &&
8329 S.Diag(A.getRange().getBegin(), diag::warn_attribute_ignored) << A;
8330 return;
8331 }
8332
8333 if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
8334 if (FD->isInlined() && A.getKind() == ParsedAttr::AT_DLLImport &&
8336 // MinGW doesn't allow dllimport on inline functions.
8337 S.Diag(A.getRange().getBegin(), diag::warn_attribute_ignored_on_inline)
8338 << A;
8339 return;
8340 }
8341 }
8342
8343 if (const auto *MD = dyn_cast<CXXMethodDecl>(D)) {
8345 MD->getParent()->isLambda()) {
8346 S.Diag(A.getRange().getBegin(), diag::err_attribute_dll_lambda) << A;
8347 return;
8348 }
8349 }
8350
8351 Attr *NewAttr = A.getKind() == ParsedAttr::AT_DLLExport
8352 ? (Attr *)S.mergeDLLExportAttr(D, A)
8353 : (Attr *)S.mergeDLLImportAttr(D, A);
8354 if (NewAttr)
8355 D->addAttr(NewAttr);
8356}
8357
8358MSInheritanceAttr *
8360 bool BestCase,
8361 MSInheritanceModel Model) {
8362 if (MSInheritanceAttr *IA = D->getAttr<MSInheritanceAttr>()) {
8363 if (IA->getInheritanceModel() == Model)
8364 return nullptr;
8365 Diag(IA->getLocation(), diag::err_mismatched_ms_inheritance)
8366 << 1 /*previous declaration*/;
8367 Diag(CI.getLoc(), diag::note_previous_ms_inheritance);
8368 D->dropAttr<MSInheritanceAttr>();
8369 }
8370
8371 auto *RD = cast<CXXRecordDecl>(D);
8372 if (RD->hasDefinition()) {
8373 if (checkMSInheritanceAttrOnDefinition(RD, CI.getRange(), BestCase,
8374 Model)) {
8375 return nullptr;
8376 }
8377 } else {
8378 if (isa<ClassTemplatePartialSpecializationDecl>(RD)) {
8379 Diag(CI.getLoc(), diag::warn_ignored_ms_inheritance)
8380 << 1 /*partial specialization*/;
8381 return nullptr;
8382 }
8383 if (RD->getDescribedClassTemplate()) {
8384 Diag(CI.getLoc(), diag::warn_ignored_ms_inheritance)
8385 << 0 /*primary template*/;
8386 return nullptr;
8387 }
8388 }
8389
8390 return ::new (Context) MSInheritanceAttr(Context, CI, BestCase);
8391}
8392
8393static void handleCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8394 // The capability attributes take a single string parameter for the name of
8395 // the capability they represent. The lockable attribute does not take any
8396 // parameters. However, semantically, both attributes represent the same
8397 // concept, and so they use the same semantic attribute. Eventually, the
8398 // lockable attribute will be removed.
8399 //
8400 // For backward compatibility, any capability which has no specified string
8401 // literal will be considered a "mutex."
8402 StringRef N("mutex");
8403 SourceLocation LiteralLoc;
8404 if (AL.getKind() == ParsedAttr::AT_Capability &&
8405 !S.checkStringLiteralArgumentAttr(AL, 0, N, &LiteralLoc))
8406 return;
8407
8408 D->addAttr(::new (S.Context) CapabilityAttr(S.Context, AL, N));
8409}
8410
8411static void handleAssertCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8413 if (!checkLockFunAttrCommon(S, D, AL, Args))
8414 return;
8415
8416 D->addAttr(::new (S.Context)
8417 AssertCapabilityAttr(S.Context, AL, Args.data(), Args.size()));
8418}
8419
8421 const ParsedAttr &AL) {
8423 if (!checkLockFunAttrCommon(S, D, AL, Args))
8424 return;
8425
8426 D->addAttr(::new (S.Context) AcquireCapabilityAttr(S.Context, AL, Args.data(),
8427 Args.size()));
8428}
8429
8431 const ParsedAttr &AL) {
8433 if (!checkTryLockFunAttrCommon(S, D, AL, Args))
8434 return;
8435
8436 D->addAttr(::new (S.Context) TryAcquireCapabilityAttr(
8437 S.Context, AL, AL.getArgAsExpr(0), Args.data(), Args.size()));
8438}
8439
8441 const ParsedAttr &AL) {
8442 // Check that all arguments are lockable objects.
8444 checkAttrArgsAreCapabilityObjs(S, D, AL, Args, 0, true);
8445
8446 D->addAttr(::new (S.Context) ReleaseCapabilityAttr(S.Context, AL, Args.data(),
8447 Args.size()));
8448}
8449
8451 const ParsedAttr &AL) {
8452 if (!AL.checkAtLeastNumArgs(S, 1))
8453 return;
8454
8455 // check that all arguments are lockable objects
8457 checkAttrArgsAreCapabilityObjs(S, D, AL, Args);
8458 if (Args.empty())
8459 return;
8460
8461 RequiresCapabilityAttr *RCA = ::new (S.Context)
8462 RequiresCapabilityAttr(S.Context, AL, Args.data(), Args.size());
8463
8464 D->addAttr(RCA);
8465}
8466
8467static void handleDeprecatedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8468 if (const auto *NSD = dyn_cast<NamespaceDecl>(D)) {
8469 if (NSD->isAnonymousNamespace()) {
8470 S.Diag(AL.getLoc(), diag::warn_deprecated_anonymous_namespace);
8471 // Do not want to attach the attribute to the namespace because that will
8472 // cause confusing diagnostic reports for uses of declarations within the
8473 // namespace.
8474 return;
8475 }
8478 S.Diag(AL.getRange().getBegin(), diag::warn_deprecated_ignored_on_using)
8479 << AL;
8480 return;
8481 }
8482
8483 // Handle the cases where the attribute has a text message.
8484 StringRef Str, Replacement;
8485 if (AL.isArgExpr(0) && AL.getArgAsExpr(0) &&
8486 !S.checkStringLiteralArgumentAttr(AL, 0, Str))
8487 return;
8488
8489 // Support a single optional message only for Declspec and [[]] spellings.
8491 AL.checkAtMostNumArgs(S, 1);
8492 else if (AL.isArgExpr(1) && AL.getArgAsExpr(1) &&
8493 !S.checkStringLiteralArgumentAttr(AL, 1, Replacement))
8494 return;
8495
8496 if (!S.getLangOpts().CPlusPlus14 && AL.isCXX11Attribute() && !AL.isGNUScope())
8497 S.Diag(AL.getLoc(), diag::ext_cxx14_attr) << AL;
8498
8499 D->addAttr(::new (S.Context) DeprecatedAttr(S.Context, AL, Str, Replacement));
8500}
8501
8502static bool isGlobalVar(const Decl *D) {
8503 if (const auto *S = dyn_cast<VarDecl>(D))
8504 return S->hasGlobalStorage();
8505 return false;
8506}
8507
8508static bool isSanitizerAttributeAllowedOnGlobals(StringRef Sanitizer) {
8509 return Sanitizer == "address" || Sanitizer == "hwaddress" ||
8510 Sanitizer == "memtag";
8511}
8512
8513static void handleNoSanitizeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8514 if (!AL.checkAtLeastNumArgs(S, 1))
8515 return;
8516
8517 std::vector<StringRef> Sanitizers;
8518
8519 for (unsigned I = 0, E = AL.getNumArgs(); I != E; ++I) {
8520 StringRef SanitizerName;
8521 SourceLocation LiteralLoc;
8522
8523 if (!S.checkStringLiteralArgumentAttr(AL, I, SanitizerName, &LiteralLoc))
8524 return;
8525
8526 if (parseSanitizerValue(SanitizerName, /*AllowGroups=*/true) ==
8527 SanitizerMask() &&
8528 SanitizerName != "coverage")
8529 S.Diag(LiteralLoc, diag::warn_unknown_sanitizer_ignored) << SanitizerName;
8530 else if (isGlobalVar(D) && !isSanitizerAttributeAllowedOnGlobals(SanitizerName))
8531 S.Diag(D->getLocation(), diag::warn_attribute_type_not_supported_global)
8532 << AL << SanitizerName;
8533 Sanitizers.push_back(SanitizerName);
8534 }
8535
8536 D->addAttr(::new (S.Context) NoSanitizeAttr(S.Context, AL, Sanitizers.data(),
8537 Sanitizers.size()));
8538}
8539
8541 const ParsedAttr &AL) {
8542 StringRef AttrName = AL.getAttrName()->getName();
8543 normalizeName(AttrName);
8544 StringRef SanitizerName = llvm::StringSwitch<StringRef>(AttrName)
8545 .Case("no_address_safety_analysis", "address")
8546 .Case("no_sanitize_address", "address")
8547 .Case("no_sanitize_thread", "thread")
8548 .Case("no_sanitize_memory", "memory");
8549 if (isGlobalVar(D) && SanitizerName != "address")
8550 S.Diag(D->getLocation(), diag::err_attribute_wrong_decl_type)
8552
8553 // FIXME: Rather than create a NoSanitizeSpecificAttr, this creates a
8554 // NoSanitizeAttr object; but we need to calculate the correct spelling list
8555 // index rather than incorrectly assume the index for NoSanitizeSpecificAttr
8556 // has the same spellings as the index for NoSanitizeAttr. We don't have a
8557 // general way to "translate" between the two, so this hack attempts to work
8558 // around the issue with hard-coded indices. This is critical for calling
8559 // getSpelling() or prettyPrint() on the resulting semantic attribute object
8560 // without failing assertions.
8561 unsigned TranslatedSpellingIndex = 0;
8563 TranslatedSpellingIndex = 1;
8564
8565 AttributeCommonInfo Info = AL;
8566 Info.setAttributeSpellingListIndex(TranslatedSpellingIndex);
8567 D->addAttr(::new (S.Context)
8568 NoSanitizeAttr(S.Context, Info, &SanitizerName, 1));
8569}
8570
8571static void handleInternalLinkageAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8572 if (InternalLinkageAttr *Internal = S.mergeInternalLinkageAttr(D, AL))
8573 D->addAttr(Internal);
8574}
8575
8576static void handleOpenCLNoSVMAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8578 S.Diag(AL.getLoc(), diag::err_attribute_requires_opencl_version)
8579 << AL << "2.0" << 1;
8580 else
8581 S.Diag(AL.getLoc(), diag::warn_opencl_attr_deprecated_ignored)
8582 << AL << S.LangOpts.getOpenCLVersionString();
8583}
8584
8585static void handleOpenCLAccessAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8586 if (D->isInvalidDecl())
8587 return;
8588
8589 // Check if there is only one access qualifier.
8590 if (D->hasAttr<OpenCLAccessAttr>()) {
8591 if (D->getAttr<OpenCLAccessAttr>()->getSemanticSpelling() ==
8592 AL.getSemanticSpelling()) {
8593 S.Diag(AL.getLoc(), diag::warn_duplicate_declspec)
8594 << AL.getAttrName()->getName() << AL.getRange();
8595 } else {
8596 S.Diag(AL.getLoc(), diag::err_opencl_multiple_access_qualifiers)
8597 << D->getSourceRange();
8598 D->setInvalidDecl(true);
8599 return;
8600 }
8601 }
8602
8603 // OpenCL v2.0 s6.6 - read_write can be used for image types to specify that
8604 // an image object can be read and written. OpenCL v2.0 s6.13.6 - A kernel
8605 // cannot read from and write to the same pipe object. Using the read_write
8606 // (or __read_write) qualifier with the pipe qualifier is a compilation error.
8607 // OpenCL v3.0 s6.8 - For OpenCL C 2.0, or with the
8608 // __opencl_c_read_write_images feature, image objects specified as arguments
8609 // to a kernel can additionally be declared to be read-write.
8610 // C++ for OpenCL 1.0 inherits rule from OpenCL C v2.0.
8611 // C++ for OpenCL 2021 inherits rule from OpenCL C v3.0.
8612 if (const auto *PDecl = dyn_cast<ParmVarDecl>(D)) {
8613 const Type *DeclTy = PDecl->getType().getCanonicalType().getTypePtr();
8614 if (AL.getAttrName()->getName().contains("read_write")) {
8615 bool ReadWriteImagesUnsupported =
8618 !S.getOpenCLOptions().isSupported("__opencl_c_read_write_images",
8619 S.getLangOpts()));
8620 if (ReadWriteImagesUnsupported || DeclTy->isPipeType()) {
8621 S.Diag(AL.getLoc(), diag::err_opencl_invalid_read_write)
8622 << AL << PDecl->getType() << DeclTy->isImageType();
8623 D->setInvalidDecl(true);
8624 return;
8625 }
8626 }
8627 }
8628
8629 D->addAttr(::new (S.Context) OpenCLAccessAttr(S.Context, AL));
8630}
8631
8632static void handleZeroCallUsedRegsAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8633 // Check that the argument is a string literal.
8634 StringRef KindStr;
8635 SourceLocation LiteralLoc;
8636 if (!S.checkStringLiteralArgumentAttr(AL, 0, KindStr, &LiteralLoc))
8637 return;
8638
8639 ZeroCallUsedRegsAttr::ZeroCallUsedRegsKind Kind;
8640 if (!ZeroCallUsedRegsAttr::ConvertStrToZeroCallUsedRegsKind(KindStr, Kind)) {
8641 S.Diag(LiteralLoc, diag::warn_attribute_type_not_supported)
8642 << AL << KindStr;
8643 return;
8644 }
8645
8646 D->dropAttr<ZeroCallUsedRegsAttr>();
8647 D->addAttr(ZeroCallUsedRegsAttr::Create(S.Context, Kind, AL));
8648}
8649
8651 const auto *RD = FD->getParent();
8652 // An unnamed struct is anonymous struct only if it's not instantiated.
8653 // However, the struct may not be fully processed yet to determine
8654 // whether it's anonymous or not. In that case, this function treats it as
8655 // an anonymous struct and tries to find a named parent.
8656 while (RD && (RD->isAnonymousStructOrUnion() ||
8657 (!RD->isCompleteDefinition() && RD->getName().empty()))) {
8658 const auto *Parent = dyn_cast<RecordDecl>(RD->getParent());
8659 if (!Parent)
8660 break;
8661 RD = Parent;
8662 }
8663 return RD;
8664}
8665
8666static bool
8669 if (FD->getParent()->isUnion()) {
8670 S.Diag(FD->getBeginLoc(), diag::err_counted_by_attr_in_union)
8671 << FD->getSourceRange();
8672 return true;
8673 }
8674
8675 if (!E->getType()->isIntegerType() || E->getType()->isBooleanType()) {
8676 S.Diag(E->getBeginLoc(), diag::err_counted_by_attr_argument_not_integer)
8677 << E->getSourceRange();
8678 return true;
8679 }
8680
8681 LangOptions::StrictFlexArraysLevelKind StrictFlexArraysLevel =
8683
8685 StrictFlexArraysLevel, true)) {
8686 // The "counted_by" attribute must be on a flexible array member.
8687 SourceRange SR = FD->getLocation();
8688 S.Diag(SR.getBegin(),
8689 diag::err_counted_by_attr_not_on_flexible_array_member)
8690 << SR;
8691 return true;
8692 }
8693
8694 auto *DRE = dyn_cast<DeclRefExpr>(E);
8695 if (!DRE) {
8696 S.Diag(E->getBeginLoc(),
8697 diag::err_counted_by_attr_only_support_simple_decl_reference)
8698 << E->getSourceRange();
8699 return true;
8700 }
8701
8702 auto *CountDecl = DRE->getDecl();
8703 FieldDecl *CountFD = dyn_cast<FieldDecl>(CountDecl);
8704 if (auto *IFD = dyn_cast<IndirectFieldDecl>(CountDecl)) {
8705 CountFD = IFD->getAnonField();
8706 }
8707 if (!CountFD) {
8708 S.Diag(E->getBeginLoc(), diag::err_counted_by_must_be_in_structure)
8709 << CountDecl << E->getSourceRange();
8710
8711 S.Diag(CountDecl->getBeginLoc(),
8712 diag::note_flexible_array_counted_by_attr_field)
8713 << CountDecl << CountDecl->getSourceRange();
8714 return true;
8715 }
8716
8717 if (FD->getParent() != CountFD->getParent()) {
8718 if (CountFD->getParent()->isUnion()) {
8719 S.Diag(CountFD->getBeginLoc(), diag::err_counted_by_attr_refer_to_union)
8720 << CountFD->getSourceRange();
8721 return true;
8722 }
8723 // Whether CountRD is an anonymous struct is not determined at this
8724 // point. Thus, an additional diagnostic in case it's not anonymous struct
8725 // is done later in `Parser::ParseStructDeclaration`.
8726 auto *RD = GetEnclosingNamedOrTopAnonRecord(FD);
8727 auto *CountRD = GetEnclosingNamedOrTopAnonRecord(CountFD);
8728
8729 if (RD != CountRD) {
8730 S.Diag(E->getBeginLoc(),
8731 diag::err_flexible_array_count_not_in_same_struct)
8732 << CountFD << E->getSourceRange();
8733 S.Diag(CountFD->getBeginLoc(),
8734 diag::note_flexible_array_counted_by_attr_field)
8735 << CountFD << CountFD->getSourceRange();
8736 return true;
8737 }
8738 }
8739
8740 Decls.push_back(TypeCoupledDeclRefInfo(CountFD, /*IsDref*/ false));
8741 return false;
8742}
8743
8744static void handleCountedByAttrField(Sema &S, Decl *D, const ParsedAttr &AL) {
8745 auto *FD = dyn_cast<FieldDecl>(D);
8746 assert(FD);
8747
8748 auto *CountExpr = AL.getArgAsExpr(0);
8749 if (!CountExpr)
8750 return;
8751
8753 if (CheckCountExpr(S, FD, CountExpr, Decls))
8754 return;
8755
8756 QualType CAT = S.BuildCountAttributedArrayType(FD->getType(), CountExpr);
8757 FD->setType(CAT);
8758}
8759
8761 const ParsedAttr &AL) {
8762 StringRef KindStr;
8763 SourceLocation LiteralLoc;
8764 if (!S.checkStringLiteralArgumentAttr(AL, 0, KindStr, &LiteralLoc))
8765 return;
8766
8767 FunctionReturnThunksAttr::Kind Kind;
8768 if (!FunctionReturnThunksAttr::ConvertStrToKind(KindStr, Kind)) {
8769 S.Diag(LiteralLoc, diag::warn_attribute_type_not_supported)
8770 << AL << KindStr;
8771 return;
8772 }
8773 // FIXME: it would be good to better handle attribute merging rather than
8774 // silently replacing the existing attribute, so long as it does not break
8775 // the expected codegen tests.
8776 D->dropAttr<FunctionReturnThunksAttr>();
8777 D->addAttr(FunctionReturnThunksAttr::Create(S.Context, Kind, AL));
8778}
8779
8781 const ParsedAttr &AL) {
8782 assert(isa<TypedefNameDecl>(D) && "This attribute only applies to a typedef");
8783 handleSimpleAttribute<AvailableOnlyInDefaultEvalMethodAttr>(S, D, AL);
8784}
8785
8786static void handleNoMergeAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8787 auto *VDecl = dyn_cast<VarDecl>(D);
8788 if (VDecl && !VDecl->isFunctionPointerType()) {
8789 S.Diag(AL.getLoc(), diag::warn_attribute_ignored_non_function_pointer)
8790 << AL << VDecl;
8791 return;
8792 }
8793 D->addAttr(NoMergeAttr::Create(S.Context, AL));
8794}
8795
8796static void handleNoUniqueAddressAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8797 D->addAttr(NoUniqueAddressAttr::Create(S.Context, AL));
8798}
8799
8800static void handleSYCLKernelAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8801 // The 'sycl_kernel' attribute applies only to function templates.
8802 const auto *FD = cast<FunctionDecl>(D);
8804 assert(FT && "Function template is expected");
8805
8806 // Function template must have at least two template parameters.
8808 if (TL->size() < 2) {
8809 S.Diag(FT->getLocation(), diag::warn_sycl_kernel_num_of_template_params);
8810 return;
8811 }
8812
8813 // Template parameters must be typenames.
8814 for (unsigned I = 0; I < 2; ++I) {
8815 const NamedDecl *TParam = TL->getParam(I);
8816 if (isa<NonTypeTemplateParmDecl>(TParam)) {
8817 S.Diag(FT->getLocation(),
8818 diag::warn_sycl_kernel_invalid_template_param_type);
8819 return;
8820 }
8821 }
8822
8823 // Function must have at least one argument.
8824 if (getFunctionOrMethodNumParams(D) != 1) {
8825 S.Diag(FT->getLocation(), diag::warn_sycl_kernel_num_of_function_params);
8826 return;
8827 }
8828
8829 // Function must return void.
8831 if (!RetTy->isVoidType()) {
8832 S.Diag(FT->getLocation(), diag::warn_sycl_kernel_return_type);
8833 return;
8834 }
8835
8836 handleSimpleAttribute<SYCLKernelAttr>(S, D, AL);
8837}
8838
8839static void handleDestroyAttr(Sema &S, Decl *D, const ParsedAttr &A) {
8840 if (!cast<VarDecl>(D)->hasGlobalStorage()) {
8841 S.Diag(D->getLocation(), diag::err_destroy_attr_on_non_static_var)
8842 << (A.getKind() == ParsedAttr::AT_AlwaysDestroy);
8843 return;
8844 }
8845
8846 if (A.getKind() == ParsedAttr::AT_AlwaysDestroy)
8847 handleSimpleAttribute<AlwaysDestroyAttr>(S, D, A);
8848 else
8849 handleSimpleAttribute<NoDestroyAttr>(S, D, A);
8850}
8851
8852static void handleUninitializedAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8853 assert(cast<VarDecl>(D)->getStorageDuration() == SD_Automatic &&
8854 "uninitialized is only valid on automatic duration variables");
8855 D->addAttr(::new (S.Context) UninitializedAttr(S.Context, AL));
8856}
8857
8859 bool DiagnoseFailure) {
8860 QualType Ty = VD->getType();
8861 if (!Ty->isObjCRetainableType()) {
8862 if (DiagnoseFailure) {
8863 S.Diag(VD->getBeginLoc(), diag::warn_ignored_objc_externally_retained)
8864 << 0;
8865 }
8866 return false;
8867 }
8868
8870
8871 // SemaObjC::inferObjCARCLifetime must run after processing decl attributes
8872 // (because __block lowers to an attribute), so if the lifetime hasn't been
8873 // explicitly specified, infer it locally now.
8874 if (LifetimeQual == Qualifiers::OCL_None)
8875 LifetimeQual = Ty->getObjCARCImplicitLifetime();
8876
8877 // The attributes only really makes sense for __strong variables; ignore any
8878 // attempts to annotate a parameter with any other lifetime qualifier.
8879 if (LifetimeQual != Qualifiers::OCL_Strong) {
8880 if (DiagnoseFailure) {
8881 S.Diag(VD->getBeginLoc(), diag::warn_ignored_objc_externally_retained)
8882 << 1;
8883 }
8884 return false;
8885 }
8886
8887 // Tampering with the type of a VarDecl here is a bit of a hack, but we need
8888 // to ensure that the variable is 'const' so that we can error on
8889 // modification, which can otherwise over-release.
8890 VD->setType(Ty.withConst());
8891 VD->setARCPseudoStrong(true);
8892 return true;
8893}
8894
8896 const ParsedAttr &AL) {
8897 if (auto *VD = dyn_cast<VarDecl>(D)) {
8898 assert(!isa<ParmVarDecl>(VD) && "should be diagnosed automatically");
8899 if (!VD->hasLocalStorage()) {
8900 S.Diag(D->getBeginLoc(), diag::warn_ignored_objc_externally_retained)
8901 << 0;
8902 return;
8903 }
8904
8905 if (!tryMakeVariablePseudoStrong(S, VD, /*DiagnoseFailure=*/true))
8906 return;
8907
8908 handleSimpleAttribute<ObjCExternallyRetainedAttr>(S, D, AL);
8909 return;
8910 }
8911
8912 // If D is a function-like declaration (method, block, or function), then we
8913 // make every parameter psuedo-strong.
8914 unsigned NumParams =
8916 for (unsigned I = 0; I != NumParams; ++I) {
8917 auto *PVD = const_cast<ParmVarDecl *>(getFunctionOrMethodParam(D, I));
8918 QualType Ty = PVD->getType();
8919
8920 // If a user wrote a parameter with __strong explicitly, then assume they
8921 // want "real" strong semantics for that parameter. This works because if
8922 // the parameter was written with __strong, then the strong qualifier will
8923 // be non-local.
8926 continue;
8927
8928 tryMakeVariablePseudoStrong(S, PVD, /*DiagnoseFailure=*/false);
8929 }
8930 handleSimpleAttribute<ObjCExternallyRetainedAttr>(S, D, AL);
8931}
8932
8933static void handleMIGServerRoutineAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8934 // Check that the return type is a `typedef int kern_return_t` or a typedef
8935 // around it, because otherwise MIG convention checks make no sense.
8936 // BlockDecl doesn't store a return type, so it's annoying to check,
8937 // so let's skip it for now.
8938 if (!isa<BlockDecl>(D)) {
8940 bool IsKernReturnT = false;
8941 while (const auto *TT = T->getAs<TypedefType>()) {
8942 IsKernReturnT = (TT->getDecl()->getName() == "kern_return_t");
8943 T = TT->desugar();
8944 }
8945 if (!IsKernReturnT || T.getCanonicalType() != S.getASTContext().IntTy) {
8946 S.Diag(D->getBeginLoc(),
8947 diag::warn_mig_server_routine_does_not_return_kern_return_t);
8948 return;
8949 }
8950 }
8951
8952 handleSimpleAttribute<MIGServerRoutineAttr>(S, D, AL);
8953}
8954
8955static void handleMSAllocatorAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8956 // Warn if the return type is not a pointer or reference type.
8957 if (auto *FD = dyn_cast<FunctionDecl>(D)) {
8958 QualType RetTy = FD->getReturnType();
8959 if (!RetTy->isPointerType() && !RetTy->isReferenceType()) {
8960 S.Diag(AL.getLoc(), diag::warn_declspec_allocator_nonpointer)
8961 << AL.getRange() << RetTy;
8962 return;
8963 }
8964 }
8965
8966 handleSimpleAttribute<MSAllocatorAttr>(S, D, AL);
8967}
8968
8969static void handleAcquireHandleAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8970 if (AL.isUsedAsTypeAttr())
8971 return;
8972 // Warn if the parameter is definitely not an output parameter.
8973 if (const auto *PVD = dyn_cast<ParmVarDecl>(D)) {
8974 if (PVD->getType()->isIntegerType()) {
8975 S.Diag(AL.getLoc(), diag::err_attribute_output_parameter)
8976 << AL.getRange();
8977 return;
8978 }
8979 }
8980 StringRef Argument;
8981 if (!S.checkStringLiteralArgumentAttr(AL, 0, Argument))
8982 return;
8983 D->addAttr(AcquireHandleAttr::Create(S.Context, Argument, AL));
8984}
8985
8986template<typename Attr>
8987static void handleHandleAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
8988 StringRef Argument;
8989 if (!S.checkStringLiteralArgumentAttr(AL, 0, Argument))
8990 return;
8991 D->addAttr(Attr::Create(S.Context, Argument, AL));
8992}
8993
8994template<typename Attr>
8995static void handleUnsafeBufferUsage(Sema &S, Decl *D, const ParsedAttr &AL) {
8996 D->addAttr(Attr::Create(S.Context, AL));
8997}
8998
8999static void handleCFGuardAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
9000 // The guard attribute takes a single identifier argument.
9001
9002 if (!AL.isArgIdent(0)) {
9003 S.Diag(AL.getLoc(), diag::err_attribute_argument_type)
9004 << AL << AANT_ArgumentIdentifier;
9005 return;
9006 }
9007
9008 CFGuardAttr::GuardArg Arg;
9009 IdentifierInfo *II = AL.getArgAsIdent(0)->Ident;
9010 if (!CFGuardAttr::ConvertStrToGuardArg(II->getName(), Arg)) {
9011 S.Diag(AL.getLoc(), diag::warn_attribute_type_not_supported) << AL << II;
9012 return;
9013 }
9014
9015 D->addAttr(::new (S.Context) CFGuardAttr(S.Context, AL, Arg));
9016}
9017
9018
9019template <typename AttrTy>
9020static const AttrTy *findEnforceTCBAttrByName(Decl *D, StringRef Name) {
9021 auto Attrs = D->specific_attrs<AttrTy>();
9022 auto I = llvm::find_if(Attrs,
9023 [Name](const AttrTy *A) {
9024 return A->getTCBName() == Name;
9025 });
9026 return I == Attrs.end() ? nullptr : *I;
9027}
9028
9029template <typename AttrTy, typename ConflictingAttrTy>
9030static void handleEnforceTCBAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
9031 StringRef Argument;
9032 if (!S.checkStringLiteralArgumentAttr(AL, 0, Argument))
9033 return;
9034
9035 // A function cannot be have both regular and leaf membership in the same TCB.
9036 if (const ConflictingAttrTy *ConflictingAttr =
9037 findEnforceTCBAttrByName<ConflictingAttrTy>(D, Argument)) {
9038 // We could attach a note to the other attribute but in this case
9039 // there's no need given how the two are very close to each other.
9040 S.Diag(AL.getLoc(), diag::err_tcb_conflicting_attributes)
9041 << AL.getAttrName()->getName() << ConflictingAttr->getAttrName()->getName()
9042 << Argument;
9043
9044 // Error recovery: drop the non-leaf attribute so that to suppress
9045 // all future warnings caused by erroneous attributes. The leaf attribute
9046 // needs to be kept because it can only suppresses warnings, not cause them.
9047 D->dropAttr<EnforceTCBAttr>();
9048 return;
9049 }
9050
9051 D->addAttr(AttrTy::Create(S.Context, Argument, AL));
9052}
9053
9054template <typename AttrTy, typename ConflictingAttrTy>
9055static AttrTy *mergeEnforceTCBAttrImpl(Sema &S, Decl *D, const AttrTy &AL) {
9056 // Check if the new redeclaration has different leaf-ness in the same TCB.
9057 StringRef TCBName = AL.getTCBName();
9058 if (const ConflictingAttrTy *ConflictingAttr =
9059 findEnforceTCBAttrByName<ConflictingAttrTy>(D, TCBName)) {
9060 S.Diag(ConflictingAttr->getLoc(), diag::err_tcb_conflicting_attributes)
9061 << ConflictingAttr->getAttrName()->getName()
9062 << AL.getAttrName()->getName() << TCBName;
9063
9064 // Add a note so that the user could easily find the conflicting attribute.
9065 S.Diag(AL.getLoc(), diag::note_conflicting_attribute);
9066
9067 // More error recovery.
9068 D->dropAttr<EnforceTCBAttr>();
9069 return nullptr;
9070 }
9071
9072 ASTContext &Context = S.getASTContext();
9073 return ::new(Context) AttrTy(Context, AL, AL.getTCBName());
9074}
9075
9076EnforceTCBAttr *Sema::mergeEnforceTCBAttr(Decl *D, const EnforceTCBAttr &AL) {
9077 return mergeEnforceTCBAttrImpl<EnforceTCBAttr, EnforceTCBLeafAttr>(
9078 *this, D, AL);
9079}
9080
9082 Decl *D, const EnforceTCBLeafAttr &AL) {
9083 return mergeEnforceTCBAttrImpl<EnforceTCBLeafAttr, EnforceTCBAttr>(
9084 *this, D, AL);
9085}
9086
9087//===----------------------------------------------------------------------===//
9088// Top Level Sema Entry Points
9089//===----------------------------------------------------------------------===//
9090
9091// Returns true if the attribute must delay setting its arguments until after
9092// template instantiation, and false otherwise.
9094 // Only attributes that accept expression parameter packs can delay arguments.
9095 if (!AL.acceptsExprPack())
9096 return false;
9097
9098 bool AttrHasVariadicArg = AL.hasVariadicArg();
9099 unsigned AttrNumArgs = AL.getNumArgMembers();
9100 for (size_t I = 0; I < std::min(AL.getNumArgs(), AttrNumArgs); ++I) {
9101 bool IsLastAttrArg = I == (AttrNumArgs - 1);
9102 // If the argument is the last argument and it is variadic it can contain
9103 // any expression.
9104 if (IsLastAttrArg && AttrHasVariadicArg)
9105 return false;
9106 Expr *E = AL.getArgAsExpr(I);
9107 bool ArgMemberCanHoldExpr = AL.isParamExpr(I);
9108 // If the expression is a pack expansion then arguments must be delayed
9109 // unless the argument is an expression and it is the last argument of the
9110 // attribute.
9111 if (isa<PackExpansionExpr>(E))
9112 return !(IsLastAttrArg && ArgMemberCanHoldExpr);
9113 // Last case is if the expression is value dependent then it must delay
9114 // arguments unless the corresponding argument is able to hold the
9115 // expression.
9116 if (E->isValueDependent() && !ArgMemberCanHoldExpr)
9117 return true;
9118 }
9119 return false;
9120}
9121
9123 Sema &S, const ParsedAttr &AL, const FunctionProtoType *FPT,
9124 FunctionType::ArmStateValue CurrentState, StringRef StateName) {
9125 auto CheckForIncompatibleAttr =
9126 [&](FunctionType::ArmStateValue IncompatibleState,
9127 StringRef IncompatibleStateName) {
9128 if (CurrentState == IncompatibleState) {
9129 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible)
9130 << (std::string("'__arm_new(\"") + StateName.str() + "\")'")
9131 << (std::string("'") + IncompatibleStateName.str() + "(\"" +
9132 StateName.str() + "\")'")
9133 << true;
9134 AL.setInvalid();
9135 }
9136 };
9137
9138 CheckForIncompatibleAttr(FunctionType::ARM_In, "__arm_in");
9139 CheckForIncompatibleAttr(FunctionType::ARM_Out, "__arm_out");
9140 CheckForIncompatibleAttr(FunctionType::ARM_InOut, "__arm_inout");
9141 CheckForIncompatibleAttr(FunctionType::ARM_Preserves, "__arm_preserves");
9142 return AL.isInvalid();
9143}
9144
9145static void handleArmNewAttr(Sema &S, Decl *D, const ParsedAttr &AL) {
9146 if (!AL.getNumArgs()) {
9147 S.Diag(AL.getLoc(), diag::err_missing_arm_state) << AL;
9148 AL.setInvalid();
9149 return;
9150 }
9151
9152 std::vector<StringRef> NewState;
9153 if (const auto *ExistingAttr = D->getAttr<ArmNewAttr>()) {
9154 for (StringRef S : ExistingAttr->newArgs())
9155 NewState.push_back(S);
9156 }
9157
9158 bool HasZA = false;
9159 bool HasZT0 = false;
9160 for (unsigned I = 0, E = AL.getNumArgs(); I != E; ++I) {
9161 StringRef StateName;
9162 SourceLocation LiteralLoc;
9163 if (!S.checkStringLiteralArgumentAttr(AL, I, StateName, &LiteralLoc))
9164 return;
9165
9166 if (StateName == "za")
9167 HasZA = true;
9168 else if (StateName == "zt0")
9169 HasZT0 = true;
9170 else {
9171 S.Diag(LiteralLoc, diag::err_unknown_arm_state) << StateName;
9172 AL.setInvalid();
9173 return;
9174 }
9175
9176 if (!llvm::is_contained(NewState, StateName)) // Avoid adding duplicates.
9177 NewState.push_back(StateName);
9178 }
9179
9180 if (auto *FPT = dyn_cast<FunctionProtoType>(D->getFunctionType())) {
9182 FunctionType::getArmZAState(FPT->getAArch64SMEAttributes());
9183 if (HasZA && ZAState != FunctionType::ARM_None &&
9184 checkArmNewAttrMutualExclusion(S, AL, FPT, ZAState, "za"))
9185 return;
9187 FunctionType::getArmZT0State(FPT->getAArch64SMEAttributes());
9188 if (HasZT0 && ZT0State != FunctionType::ARM_None &&
9189 checkArmNewAttrMutualExclusion(S, AL, FPT, ZT0State, "zt0"))
9190 return;
9191 }
9192
9193 D->dropAttr<ArmNewAttr>();
9194 D->addAttr(::new (S.Context)
9195 ArmNewAttr(S.Context, AL, NewState.data(), NewState.size()));
9196}
9197
9198/// ProcessDeclAttribute - Apply the specific attribute to the specified decl if
9199/// the attribute applies to decls. If the attribute is a type attribute, just
9200/// silently ignore it if a GNU attribute.
9201static void
9203 const Sema::ProcessDeclAttributeOptions &Options) {
9205 return;
9206
9207 // Ignore C++11 attributes on declarator chunks: they appertain to the type
9208 // instead.
9209 if (AL.isCXX11Attribute() && !Options.IncludeCXX11Attributes)
9210 return;
9211
9212 // Unknown attributes are automatically warned on. Target-specific attributes
9213 // which do not apply to the current target architecture are treated as
9214 // though they were unknown attributes.
9217 S.Diag(AL.getLoc(),
9219 ? (unsigned)diag::err_keyword_not_supported_on_target
9220 : AL.isDeclspecAttribute()
9221 ? (unsigned)diag::warn_unhandled_ms_attribute_ignored
9222 : (unsigned)diag::warn_unknown_attribute_ignored)
9223 << AL << AL.getRange();
9224 return;
9225 }
9226
9227 // Check if argument population must delayed to after template instantiation.
9228 bool MustDelayArgs = MustDelayAttributeArguments(AL);
9229
9230 // Argument number check must be skipped if arguments are delayed.
9231 if (S.checkCommonAttributeFeatures(D, AL, MustDelayArgs))
9232 return;
9233
9234 if (MustDelayArgs) {
9236 return;
9237 }
9238
9239 switch (AL.getKind()) {
9240 default:
9242 break;
9243 if (!AL.isStmtAttr()) {
9244 assert(AL.isTypeAttr() && "Non-type attribute not handled");
9245 }
9246 if (AL.isTypeAttr()) {
9247 if (Options.IgnoreTypeAttributes)
9248 break;
9250 // Non-[[]] type attributes are handled in processTypeAttrs(); silently
9251 // move on.
9252 break;
9253 }
9254
9255 // According to the C and C++ standards, we should never see a
9256 // [[]] type attribute on a declaration. However, we have in the past
9257 // allowed some type attributes to "slide" to the `DeclSpec`, so we need
9258 // to continue to support this legacy behavior. We only do this, however,
9259 // if
9260 // - we actually have a `DeclSpec`, i.e. if we're looking at a
9261 // `DeclaratorDecl`, or
9262 // - we are looking at an alias-declaration, where historically we have
9263 // allowed type attributes after the identifier to slide to the type.
9265 isa<DeclaratorDecl, TypeAliasDecl>(D)) {
9266 // Suggest moving the attribute to the type instead, but only for our
9267 // own vendor attributes; moving other vendors' attributes might hurt
9268 // portability.
9269 if (AL.isClangScope()) {
9270 S.Diag(AL.getLoc(), diag::warn_type_attribute_deprecated_on_decl)
9271 << AL << D->getLocation();
9272 }
9273
9274 // Allow this type attribute to be handled in processTypeAttrs();
9275 // silently move on.
9276 break;
9277 }
9278
9279 if (AL.getKind() == ParsedAttr::AT_Regparm) {
9280 // `regparm` is a special case: It's a type attribute but we still want
9281 // to treat it as if it had been written on the declaration because that
9282 // way we'll be able to handle it directly in `processTypeAttr()`.
9283 // If we treated `regparm` it as if it had been written on the
9284 // `DeclSpec`, the logic in `distributeFunctionTypeAttrFromDeclSepc()`
9285 // would try to move it to the declarator, but that doesn't work: We
9286 // can't remove the attribute from the list of declaration attributes
9287 // because it might be needed by other declarators in the same
9288 // declaration.
9289 break;
9290 }
9291
9292 if (AL.getKind() == ParsedAttr::AT_VectorSize) {
9293 // `vector_size` is a special case: It's a type attribute semantically,
9294 // but GCC expects the [[]] syntax to be written on the declaration (and
9295 // warns that the attribute has no effect if it is placed on the
9296 // decl-specifier-seq).
9297 // Silently move on and allow the attribute to be handled in
9298 // processTypeAttr().
9299 break;
9300 }
9301
9302 if (AL.getKind() == ParsedAttr::AT_NoDeref) {
9303 // FIXME: `noderef` currently doesn't work correctly in [[]] syntax.
9304 // See https://github.com/llvm/llvm-project/issues/55790 for details.
9305 // We allow processTypeAttrs() to emit a warning and silently move on.
9306 break;
9307 }
9308 }
9309 // N.B., ClangAttrEmitter.cpp emits a diagnostic helper that ensures a
9310 // statement attribute is not written on a declaration, but this code is
9311 // needed for type attributes as well as statement attributes in Attr.td
9312 // that do not list any subjects.
9313 S.Diag(AL.getLoc(), diag::err_attribute_invalid_on_decl)
9314 << AL << AL.isRegularKeywordAttribute() << D->getLocation();
9315 break;
9316 case ParsedAttr::AT_Interrupt:
9317 handleInterruptAttr(S, D, AL);
9318 break;
9319 case ParsedAttr::AT_X86ForceAlignArgPointer:
9321 break;
9322 case ParsedAttr::AT_ReadOnlyPlacement:
9323 handleSimpleAttribute<ReadOnlyPlacementAttr>(S, D, AL);
9324 break;
9325 case ParsedAttr::AT_DLLExport:
9326 case ParsedAttr::AT_DLLImport:
9327 handleDLLAttr(S, D, AL);
9328 break;
9329 case ParsedAttr::AT_AMDGPUFlatWorkGroupSize:
9331 break;
9332 case ParsedAttr::AT_AMDGPUWavesPerEU:
9334 break;
9335 case ParsedAttr::AT_AMDGPUNumSGPR:
9336 handleAMDGPUNumSGPRAttr(S, D, AL);
9337 break;
9338 case ParsedAttr::AT_AMDGPUNumVGPR:
9339 handleAMDGPUNumVGPRAttr(S, D, AL);
9340 break;
9341 case ParsedAttr::AT_AMDGPUMaxNumWorkGroups:
9343 break;
9344 case ParsedAttr::AT_AVRSignal:
9345 handleAVRSignalAttr(S, D, AL);
9346 break;
9347 case ParsedAttr::AT_BPFPreserveAccessIndex:
9349 break;
9350 case ParsedAttr::AT_BPFPreserveStaticOffset:
9351 handleSimpleAttribute<BPFPreserveStaticOffsetAttr>(S, D, AL);
9352 break;
9353 case ParsedAttr::AT_BTFDeclTag:
9354 handleBTFDeclTagAttr(S, D, AL);
9355 break;
9356 case ParsedAttr::AT_WebAssemblyExportName:
9358 break;
9359 case ParsedAttr::AT_WebAssemblyImportModule:
9361 break;
9362 case ParsedAttr::AT_WebAssemblyImportName:
9364 break;
9365 case ParsedAttr::AT_IBOutlet:
9366 handleIBOutlet(S, D, AL);
9367 break;
9368 case ParsedAttr::AT_IBOutletCollection:
9369 handleIBOutletCollection(S, D, AL);
9370 break;
9371 case ParsedAttr::AT_IFunc:
9372 handleIFuncAttr(S, D, AL);
9373 break;
9374 case ParsedAttr::AT_Alias:
9375 handleAliasAttr(S, D, AL);
9376 break;
9377 case ParsedAttr::AT_Aligned:
9378 handleAlignedAttr(S, D, AL);
9379 break;
9380 case ParsedAttr::AT_AlignValue:
9381 handleAlignValueAttr(S, D, AL);
9382 break;
9383 case ParsedAttr::AT_AllocSize:
9384 handleAllocSizeAttr(S, D, AL);
9385 break;
9386 case ParsedAttr::AT_AlwaysInline:
9387 handleAlwaysInlineAttr(S, D, AL);
9388 break;
9389 case ParsedAttr::AT_AnalyzerNoReturn:
9391 break;
9392 case ParsedAttr::AT_TLSModel:
9393 handleTLSModelAttr(S, D, AL);
9394 break;
9395 case ParsedAttr::AT_Annotate:
9396 handleAnnotateAttr(S, D, AL);
9397 break;
9398 case ParsedAttr::AT_Availability:
9399 handleAvailabilityAttr(S, D, AL);
9400 break;
9401 case ParsedAttr::AT_CarriesDependency:
9402 handleDependencyAttr(S, scope, D, AL);
9403 break;
9404 case ParsedAttr::AT_CPUDispatch:
9405 case ParsedAttr::AT_CPUSpecific:
9406 handleCPUSpecificAttr(S, D, AL);
9407 break;
9408 case ParsedAttr::AT_Common:
9409 handleCommonAttr(S, D, AL);
9410 break;
9411 case ParsedAttr::AT_CUDAConstant:
9412 handleConstantAttr(S, D, AL);
9413 break;
9414 case ParsedAttr::AT_PassObjectSize:
9415 handlePassObjectSizeAttr(S, D, AL);
9416 break;
9417 case ParsedAttr::AT_Constructor:
9418 handleConstructorAttr(S, D, AL);
9419 break;
9420 case ParsedAttr::AT_Deprecated:
9421 handleDeprecatedAttr(S, D, AL);
9422 break;
9423 case ParsedAttr::AT_Destructor:
9424 handleDestructorAttr(S, D, AL);
9425 break;
9426 case ParsedAttr::AT_EnableIf:
9427 handleEnableIfAttr(S, D, AL);
9428 break;
9429 case ParsedAttr::AT_Error:
9430 handleErrorAttr(S, D, AL);
9431 break;
9432 case ParsedAttr::AT_ExcludeFromExplicitInstantiation:
9434 break;
9435 case ParsedAttr::AT_DiagnoseIf:
9436 handleDiagnoseIfAttr(S, D, AL);
9437 break;
9438 case ParsedAttr::AT_DiagnoseAsBuiltin:
9440 break;
9441 case ParsedAttr::AT_NoBuiltin:
9442 handleNoBuiltinAttr(S, D, AL);
9443 break;
9444 case ParsedAttr::AT_ExtVectorType:
9445 handleExtVectorTypeAttr(S, D, AL);
9446 break;
9447 case ParsedAttr::AT_ExternalSourceSymbol:
9449 break;
9450 case ParsedAttr::AT_MinSize:
9451 handleMinSizeAttr(S, D, AL);
9452 break;
9453 case ParsedAttr::AT_OptimizeNone:
9454 handleOptimizeNoneAttr(S, D, AL);
9455 break;
9456 case ParsedAttr::AT_EnumExtensibility:
9458 break;
9459 case ParsedAttr::AT_SYCLKernel:
9460 handleSYCLKernelAttr(S, D, AL);
9461 break;
9462 case ParsedAttr::AT_SYCLSpecialClass:
9463 handleSimpleAttribute<SYCLSpecialClassAttr>(S, D, AL);
9464 break;
9465 case ParsedAttr::AT_Format:
9466 handleFormatAttr(S, D, AL);
9467 break;
9468 case ParsedAttr::AT_FormatArg:
9469 handleFormatArgAttr(S, D, AL);
9470 break;
9471 case ParsedAttr::AT_Callback:
9472 handleCallbackAttr(S, D, AL);
9473 break;
9474 case ParsedAttr::AT_CalledOnce:
9475 handleCalledOnceAttr(S, D, AL);
9476 break;
9477 case ParsedAttr::AT_NVPTXKernel:
9478 case ParsedAttr::AT_CUDAGlobal:
9479 handleGlobalAttr(S, D, AL);
9480 break;
9481 case ParsedAttr::AT_CUDADevice:
9482 handleDeviceAttr(S, D, AL);
9483 break;
9484 case ParsedAttr::AT_HIPManaged:
9485 handleManagedAttr(S, D, AL);
9486 break;
9487 case ParsedAttr::AT_GNUInline:
9488 handleGNUInlineAttr(S, D, AL);
9489 break;
9490 case ParsedAttr::AT_CUDALaunchBounds:
9491 handleLaunchBoundsAttr(S, D, AL);
9492 break;
9493 case ParsedAttr::AT_Restrict:
9494 handleRestrictAttr(S, D, AL);
9495 break;
9496 case ParsedAttr::AT_Mode:
9497 handleModeAttr(S, D, AL);
9498 break;
9499 case ParsedAttr::AT_NonNull:
9500 if (auto *PVD = dyn_cast<ParmVarDecl>(D))
9501 handleNonNullAttrParameter(S, PVD, AL);
9502 else
9503 handleNonNullAttr(S, D, AL);
9504 break;
9505 case ParsedAttr::AT_ReturnsNonNull:
9506 handleReturnsNonNullAttr(S, D, AL);
9507 break;
9508 case ParsedAttr::AT_NoEscape:
9509 handleNoEscapeAttr(S, D, AL);
9510 break;
9511 case ParsedAttr::AT_MaybeUndef:
9512 handleSimpleAttribute<MaybeUndefAttr>(S, D, AL);
9513 break;
9514 case ParsedAttr::AT_AssumeAligned:
9515 handleAssumeAlignedAttr(S, D, AL);
9516 break;
9517 case ParsedAttr::AT_AllocAlign:
9518 handleAllocAlignAttr(S, D, AL);
9519 break;
9520 case ParsedAttr::AT_Ownership:
9521 handleOwnershipAttr(S, D, AL);
9522 break;
9523 case ParsedAttr::AT_Naked:
9524 handleNakedAttr(S, D, AL);
9525 break;
9526 case ParsedAttr::AT_NoReturn:
9527 handleNoReturnAttr(S, D, AL);
9528 break;
9529 case ParsedAttr::AT_CXX11NoReturn:
9531 break;
9532 case ParsedAttr::AT_AnyX86NoCfCheck:
9533 handleNoCfCheckAttr(S, D, AL);
9534 break;
9535 case ParsedAttr::AT_NoThrow:
9536 if (!AL.isUsedAsTypeAttr())
9537 handleSimpleAttribute<NoThrowAttr>(S, D, AL);
9538 break;
9539 case ParsedAttr::AT_CUDAShared:
9540 handleSharedAttr(S, D, AL);
9541 break;
9542 case ParsedAttr::AT_VecReturn:
9543 handleVecReturnAttr(S, D, AL);
9544 break;
9545 case ParsedAttr::AT_ObjCOwnership:
9546 handleObjCOwnershipAttr(S, D, AL);
9547 break;
9548 case ParsedAttr::AT_ObjCPreciseLifetime:
9550 break;
9551 case ParsedAttr::AT_ObjCReturnsInnerPointer:
9553 break;
9554 case ParsedAttr::AT_ObjCRequiresSuper:
9556 break;
9557 case ParsedAttr::AT_ObjCBridge:
9558 handleObjCBridgeAttr(S, D, AL);
9559 break;
9560 case ParsedAttr::AT_ObjCBridgeMutable:
9562 break;
9563 case ParsedAttr::AT_ObjCBridgeRelated:
9565 break;
9566 case ParsedAttr::AT_ObjCDesignatedInitializer:
9568 break;
9569 case ParsedAttr::AT_ObjCRuntimeName:
9570 handleObjCRuntimeName(S, D, AL);
9571 break;
9572 case ParsedAttr::AT_ObjCBoxable:
9573 handleObjCBoxable(S, D, AL);
9574 break;
9575 case ParsedAttr::AT_NSErrorDomain:
9576 handleNSErrorDomain(S, D, AL);
9577 break;
9578 case ParsedAttr::AT_CFConsumed:
9579 case ParsedAttr::AT_NSConsumed:
9580 case ParsedAttr::AT_OSConsumed:
9582 /*IsTemplateInstantiation=*/false);
9583 break;
9584 case ParsedAttr::AT_OSReturnsRetainedOnZero:
9585 handleSimpleAttributeOrDiagnose<OSReturnsRetainedOnZeroAttr>(
9586 S, D, AL, isValidOSObjectOutParameter(D),
9587 diag::warn_ns_attribute_wrong_parameter_type,
9588 /*Extra Args=*/AL, /*pointer-to-OSObject-pointer*/ 3, AL.getRange());
9589 break;
9590 case ParsedAttr::AT_OSReturnsRetainedOnNonZero:
9591 handleSimpleAttributeOrDiagnose<OSReturnsRetainedOnNonZeroAttr>(
9592 S, D, AL, isValidOSObjectOutParameter(D),
9593 diag::warn_ns_attribute_wrong_parameter_type,
9594 /*Extra Args=*/AL, /*pointer-to-OSObject-poointer*/ 3, AL.getRange());
9595 break;
9596 case ParsedAttr::AT_NSReturnsAutoreleased:
9597 case ParsedAttr::AT_NSReturnsNotRetained:
9598 case ParsedAttr::AT_NSReturnsRetained:
9599 case ParsedAttr::AT_CFReturnsNotRetained:
9600 case ParsedAttr::AT_CFReturnsRetained:
9601 case ParsedAttr::AT_OSReturnsNotRetained:
9602 case ParsedAttr::AT_OSReturnsRetained:
9604 break;
9605 case ParsedAttr::AT_WorkGroupSizeHint:
9606 handleWorkGroupSize<WorkGroupSizeHintAttr>(S, D, AL);
9607 break;
9608 case ParsedAttr::AT_ReqdWorkGroupSize:
9609 handleWorkGroupSize<ReqdWorkGroupSizeAttr>(S, D, AL);
9610 break;
9611 case ParsedAttr::AT_OpenCLIntelReqdSubGroupSize:
9612 handleSubGroupSize(S, D, AL);
9613 break;
9614 case ParsedAttr::AT_VecTypeHint:
9615 handleVecTypeHint(S, D, AL);
9616 break;
9617 case ParsedAttr::AT_InitPriority:
9618 handleInitPriorityAttr(S, D, AL);
9619 break;
9620 case ParsedAttr::AT_Packed:
9621 handlePackedAttr(S, D, AL);
9622 break;
9623 case ParsedAttr::AT_PreferredName:
9624 handlePreferredName(S, D, AL);
9625 break;
9626 case ParsedAttr::AT_Section:
9627 handleSectionAttr(S, D, AL);
9628 break;
9629 case ParsedAttr::AT_CodeModel:
9630 handleCodeModelAttr(S, D, AL);
9631 break;
9632 case ParsedAttr::AT_RandomizeLayout:
9633 handleRandomizeLayoutAttr(S, D, AL);
9634 break;
9635 case ParsedAttr::AT_NoRandomizeLayout:
9637 break;
9638 case ParsedAttr::AT_CodeSeg:
9639 handleCodeSegAttr(S, D, AL);
9640 break;
9641 case ParsedAttr::AT_Target:
9642 handleTargetAttr(S, D, AL);
9643 break;
9644 case ParsedAttr::AT_TargetVersion:
9645 handleTargetVersionAttr(S, D, AL);
9646 break;
9647 case ParsedAttr::AT_TargetClones:
9648 handleTargetClonesAttr(S, D, AL);
9649 break;
9650 case ParsedAttr::AT_MinVectorWidth:
9651 handleMinVectorWidthAttr(S, D, AL);
9652 break;
9653 case ParsedAttr::AT_Unavailable:
9654 handleAttrWithMessage<UnavailableAttr>(S, D, AL);
9655 break;
9656 case ParsedAttr::AT_OMPAssume:
9657 handleOMPAssumeAttr(S, D, AL);
9658 break;
9659 case ParsedAttr::AT_ObjCDirect:
9660 handleObjCDirectAttr(S, D, AL);
9661 break;
9662 case ParsedAttr::AT_ObjCDirectMembers:
9664 handleSimpleAttribute<ObjCDirectMembersAttr>(S, D, AL);
9665 break;
9666 case ParsedAttr::AT_ObjCExplicitProtocolImpl:
9668 break;
9669 case ParsedAttr::AT_Unused:
9670 handleUnusedAttr(S, D, AL);
9671 break;
9672 case ParsedAttr::AT_Visibility:
9673 handleVisibilityAttr(S, D, AL, false);
9674 break;
9675 case ParsedAttr::AT_TypeVisibility:
9676 handleVisibilityAttr(S, D, AL, true);
9677 break;
9678 case ParsedAttr::AT_WarnUnusedResult:
9679 handleWarnUnusedResult(S, D, AL);
9680 break;
9681 case ParsedAttr::AT_WeakRef:
9682 handleWeakRefAttr(S, D, AL);
9683 break;
9684 case ParsedAttr::AT_WeakImport:
9685 handleWeakImportAttr(S, D, AL);
9686 break;
9687 case ParsedAttr::AT_TransparentUnion:
9689 break;
9690 case ParsedAttr::AT_ObjCMethodFamily:
9692 break;
9693 case ParsedAttr::AT_ObjCNSObject:
9694 handleObjCNSObject(S, D, AL);
9695 break;
9696 case ParsedAttr::AT_ObjCIndependentClass:
9698 break;
9699 case ParsedAttr::AT_Blocks:
9700 handleBlocksAttr(S, D, AL);
9701 break;
9702 case ParsedAttr::AT_Sentinel:
9703 handleSentinelAttr(S, D, AL);
9704 break;
9705 case ParsedAttr::AT_Cleanup:
9706 handleCleanupAttr(S, D, AL);
9707 break;
9708 case ParsedAttr::AT_NoDebug:
9709 handleNoDebugAttr(S, D, AL);
9710 break;
9711 case ParsedAttr::AT_CmseNSEntry:
9712 handleCmseNSEntryAttr(S, D, AL);
9713 break;
9714 case ParsedAttr::AT_StdCall:
9715 case ParsedAttr::AT_CDecl:
9716 case ParsedAttr::AT_FastCall:
9717 case ParsedAttr::AT_ThisCall:
9718 case ParsedAttr::AT_Pascal:
9719 case ParsedAttr::AT_RegCall:
9720 case ParsedAttr::AT_SwiftCall:
9721 case ParsedAttr::AT_SwiftAsyncCall:
9722 case ParsedAttr::AT_VectorCall:
9723 case ParsedAttr::AT_MSABI:
9724 case ParsedAttr::AT_SysVABI:
9725 case ParsedAttr::AT_Pcs:
9726 case ParsedAttr::AT_IntelOclBicc:
9727 case ParsedAttr::AT_PreserveMost:
9728 case ParsedAttr::AT_PreserveAll:
9729 case ParsedAttr::AT_AArch64VectorPcs:
9730 case ParsedAttr::AT_AArch64SVEPcs:
9731 case ParsedAttr::AT_AMDGPUKernelCall:
9732 case ParsedAttr::AT_M68kRTD:
9733 case ParsedAttr::AT_PreserveNone:
9734 case ParsedAttr::AT_RISCVVectorCC:
9735 handleCallConvAttr(S, D, AL);
9736 break;
9737 case ParsedAttr::AT_Suppress:
9738 handleSuppressAttr(S, D, AL);
9739 break;
9740 case ParsedAttr::AT_Owner:
9741 case ParsedAttr::AT_Pointer:
9743 break;
9744 case ParsedAttr::AT_OpenCLAccess:
9745 handleOpenCLAccessAttr(S, D, AL);
9746 break;
9747 case ParsedAttr::AT_OpenCLNoSVM:
9748 handleOpenCLNoSVMAttr(S, D, AL);
9749 break;
9750 case ParsedAttr::AT_SwiftContext:
9752 break;
9753 case ParsedAttr::AT_SwiftAsyncContext:
9755 break;
9756 case ParsedAttr::AT_SwiftErrorResult:
9758 break;
9759 case ParsedAttr::AT_SwiftIndirectResult:
9761 break;
9762 case ParsedAttr::AT_InternalLinkage:
9763 handleInternalLinkageAttr(S, D, AL);
9764 break;
9765 case ParsedAttr::AT_ZeroCallUsedRegs:
9767 break;
9768 case ParsedAttr::AT_FunctionReturnThunks:
9770 break;
9771 case ParsedAttr::AT_NoMerge:
9772 handleNoMergeAttr(S, D, AL);
9773 break;
9774 case ParsedAttr::AT_NoUniqueAddress:
9775 handleNoUniqueAddressAttr(S, D, AL);
9776 break;
9777
9778 case ParsedAttr::AT_AvailableOnlyInDefaultEvalMethod:
9780 break;
9781
9782 case ParsedAttr::AT_CountedBy:
9783 handleCountedByAttrField(S, D, AL);
9784 break;
9785
9786 // Microsoft attributes:
9787 case ParsedAttr::AT_LayoutVersion:
9788 handleLayoutVersion(S, D, AL);
9789 break;
9790 case ParsedAttr::AT_Uuid:
9791 handleUuidAttr(S, D, AL);
9792 break;
9793 case ParsedAttr::AT_MSInheritance:
9794 handleMSInheritanceAttr(S, D, AL);
9795 break;
9796 case ParsedAttr::AT_Thread:
9797 handleDeclspecThreadAttr(S, D, AL);
9798 break;
9799 case ParsedAttr::AT_MSConstexpr:
9800 handleMSConstexprAttr(S, D, AL);
9801 break;
9802
9803 // HLSL attributes:
9804 case ParsedAttr::AT_HLSLNumThreads:
9805 handleHLSLNumThreadsAttr(S, D, AL);
9806 break;
9807 case ParsedAttr::AT_HLSLSV_GroupIndex:
9808 handleSimpleAttribute<HLSLSV_GroupIndexAttr>(S, D, AL);
9809 break;
9810 case ParsedAttr::AT_HLSLSV_DispatchThreadID:
9812 break;
9813 case ParsedAttr::AT_HLSLPackOffset:
9814 handleHLSLPackOffsetAttr(S, D, AL);
9815 break;
9816 case ParsedAttr::AT_HLSLShader:
9817 handleHLSLShaderAttr(S, D, AL);
9818 break;
9819 case ParsedAttr::AT_HLSLResourceBinding:
9821 break;
9822 case ParsedAttr::AT_HLSLParamModifier:
9824 break;
9825
9826 case ParsedAttr::AT_AbiTag:
9827 handleAbiTagAttr(S, D, AL);
9828 break;
9829 case ParsedAttr::AT_CFGuard:
9830 handleCFGuardAttr(S, D, AL);
9831 break;
9832
9833 // Thread safety attributes:
9834 case ParsedAttr::AT_AssertExclusiveLock:
9836 break;
9837 case ParsedAttr::AT_AssertSharedLock:
9839 break;
9840 case ParsedAttr::AT_PtGuardedVar:
9841 handlePtGuardedVarAttr(S, D, AL);
9842 break;
9843 case ParsedAttr::AT_NoSanitize:
9844 handleNoSanitizeAttr(S, D, AL);
9845 break;
9846 case ParsedAttr::AT_NoSanitizeSpecific:
9848 break;
9849 case ParsedAttr::AT_GuardedBy:
9850 handleGuardedByAttr(S, D, AL);
9851 break;
9852 case ParsedAttr::AT_PtGuardedBy:
9853 handlePtGuardedByAttr(S, D, AL);
9854 break;
9855 case ParsedAttr::AT_ExclusiveTrylockFunction:
9857 break;
9858 case ParsedAttr::AT_LockReturned:
9859 handleLockReturnedAttr(S, D, AL);
9860 break;
9861 case ParsedAttr::AT_LocksExcluded:
9862 handleLocksExcludedAttr(S, D, AL);
9863 break;
9864 case ParsedAttr::AT_SharedTrylockFunction:
9866 break;
9867 case ParsedAttr::AT_AcquiredBefore:
9868 handleAcquiredBeforeAttr(S, D, AL);
9869 break;
9870 case ParsedAttr::AT_AcquiredAfter:
9871 handleAcquiredAfterAttr(S, D, AL);
9872 break;
9873
9874 // Capability analysis attributes.
9875 case ParsedAttr::AT_Capability:
9876 case ParsedAttr::AT_Lockable:
9877 handleCapabilityAttr(S, D, AL);
9878 break;
9879 case ParsedAttr::AT_RequiresCapability:
9881 break;
9882
9883 case ParsedAttr::AT_AssertCapability:
9885 break;
9886 case ParsedAttr::AT_AcquireCapability:
9888 break;
9889 case ParsedAttr::AT_ReleaseCapability:
9891 break;
9892 case ParsedAttr::AT_TryAcquireCapability:
9894 break;
9895
9896 // Consumed analysis attributes.
9897 case ParsedAttr::AT_Consumable:
9898 handleConsumableAttr(S, D, AL);
9899 break;
9900 case ParsedAttr::AT_CallableWhen:
9901 handleCallableWhenAttr(S, D, AL);
9902 break;
9903 case ParsedAttr::AT_ParamTypestate:
9904 handleParamTypestateAttr(S, D, AL);
9905 break;
9906 case ParsedAttr::AT_ReturnTypestate:
9907 handleReturnTypestateAttr(S, D, AL);
9908 break;
9909 case ParsedAttr::AT_SetTypestate:
9910 handleSetTypestateAttr(S, D, AL);
9911 break;
9912 case ParsedAttr::AT_TestTypestate:
9913 handleTestTypestateAttr(S, D, AL);
9914 break;
9915
9916 // Type safety attributes.
9917 case ParsedAttr::AT_ArgumentWithTypeTag:
9919 break;
9920 case ParsedAttr::AT_TypeTagForDatatype:
9922 break;
9923
9924 // Swift attributes.
9925 case ParsedAttr::AT_SwiftAsyncName:
9926 handleSwiftAsyncName(S, D, AL);
9927 break;
9928 case ParsedAttr::AT_SwiftAttr:
9929 handleSwiftAttrAttr(S, D, AL);
9930 break;
9931 case ParsedAttr::AT_SwiftBridge:
9932 handleSwiftBridge(S, D, AL);
9933 break;
9934 case ParsedAttr::AT_SwiftError:
9935 handleSwiftError(S, D, AL);
9936 break;
9937 case ParsedAttr::AT_SwiftName:
9938 handleSwiftName(S, D, AL);
9939 break;
9940 case ParsedAttr::AT_SwiftNewType:
9941 handleSwiftNewType(S, D, AL);
9942 break;
9943 case ParsedAttr::AT_SwiftAsync:
9944 handleSwiftAsyncAttr(S, D, AL);
9945 break;
9946 case ParsedAttr::AT_SwiftAsyncError:
9947 handleSwiftAsyncError(S, D, AL);
9948 break;
9949
9950 // XRay attributes.
9951 case ParsedAttr::AT_XRayLogArgs:
9952 handleXRayLogArgsAttr(S, D, AL);
9953 break;
9954
9955 case ParsedAttr::AT_PatchableFunctionEntry:
9957 break;
9958
9959 case ParsedAttr::AT_AlwaysDestroy:
9960 case ParsedAttr::AT_NoDestroy:
9961 handleDestroyAttr(S, D, AL);
9962 break;
9963
9964 case ParsedAttr::AT_Uninitialized:
9965 handleUninitializedAttr(S, D, AL);
9966 break;
9967
9968 case ParsedAttr::AT_ObjCExternallyRetained:
9970 break;
9971
9972 case ParsedAttr::AT_MIGServerRoutine:
9974 break;
9975
9976 case ParsedAttr::AT_MSAllocator:
9977 handleMSAllocatorAttr(S, D, AL);
9978 break;
9979
9980 case ParsedAttr::AT_ArmBuiltinAlias:
9981 handleArmBuiltinAliasAttr(S, D, AL);
9982 break;
9983
9984 case ParsedAttr::AT_ArmLocallyStreaming:
9985 handleSimpleAttribute<ArmLocallyStreamingAttr>(S, D, AL);
9986 break;
9987
9988 case ParsedAttr::AT_ArmNew:
9989 handleArmNewAttr(S, D, AL);
9990 break;
9991
9992 case ParsedAttr::AT_AcquireHandle:
9993 handleAcquireHandleAttr(S, D, AL);
9994 break;
9995
9996 case ParsedAttr::AT_ReleaseHandle:
9997 handleHandleAttr<ReleaseHandleAttr>(S, D, AL);
9998 break;
9999
10000 case ParsedAttr::AT_UnsafeBufferUsage:
10001 handleUnsafeBufferUsage<UnsafeBufferUsageAttr>(S, D, AL);
10002 break;
10003
10004 case ParsedAttr::AT_UseHandle:
10005 handleHandleAttr<UseHandleAttr>(S, D, AL);
10006 break;
10007
10008 case ParsedAttr::AT_EnforceTCB:
10009 handleEnforceTCBAttr<EnforceTCBAttr, EnforceTCBLeafAttr>(S, D, AL);
10010 break;
10011
10012 case ParsedAttr::AT_EnforceTCBLeaf:
10013 handleEnforceTCBAttr<EnforceTCBLeafAttr, EnforceTCBAttr>(S, D, AL);
10014 break;
10015
10016 case ParsedAttr::AT_BuiltinAlias:
10017 handleBuiltinAliasAttr(S, D, AL);
10018 break;
10019
10020 case ParsedAttr::AT_PreferredType:
10021 handlePreferredTypeAttr(S, D, AL);
10022 break;
10023
10024 case ParsedAttr::AT_UsingIfExists:
10025 handleSimpleAttribute<UsingIfExistsAttr>(S, D, AL);
10026 break;
10027
10028 case ParsedAttr::AT_TypeNullable:
10029 handleNullableTypeAttr(S, D, AL);
10030 break;
10031 }
10032}
10033
10034/// ProcessDeclAttributeList - Apply all the decl attributes in the specified
10035/// attribute list to the specified decl, ignoring any type attributes.
10037 Scope *S, Decl *D, const ParsedAttributesView &AttrList,
10038 const ProcessDeclAttributeOptions &Options) {
10039 if (AttrList.empty())
10040 return;
10041
10042 for (const ParsedAttr &AL : AttrList)
10043 ProcessDeclAttribute(*this, S, D, AL, Options);
10044
10045 // FIXME: We should be able to handle these cases in TableGen.
10046 // GCC accepts
10047 // static int a9 __attribute__((weakref));
10048 // but that looks really pointless. We reject it.
10049 if (D->hasAttr<WeakRefAttr>() && !D->hasAttr<AliasAttr>()) {
10050 Diag(AttrList.begin()->getLoc(), diag::err_attribute_weakref_without_alias)
10051 << cast<NamedDecl>(D);
10052 D->dropAttr<WeakRefAttr>();
10053 return;
10054 }
10055
10056 // FIXME: We should be able to handle this in TableGen as well. It would be
10057 // good to have a way to specify "these attributes must appear as a group",
10058 // for these. Additionally, it would be good to have a way to specify "these
10059 // attribute must never appear as a group" for attributes like cold and hot.
10060 if (!D->hasAttr<OpenCLKernelAttr>()) {
10061 // These attributes cannot be applied to a non-kernel function.
10062 if (const auto *A = D->getAttr<ReqdWorkGroupSizeAttr>()) {
10063 // FIXME: This emits a different error message than
10064 // diag::err_attribute_wrong_decl_type + ExpectedKernelFunction.
10065 Diag(D->getLocation(), diag::err_opencl_kernel_attr) << A;
10066 D->setInvalidDecl();
10067 } else if (const auto *A = D->getAttr<WorkGroupSizeHintAttr>()) {
10068 Diag(D->getLocation(), diag::err_opencl_kernel_attr) << A;
10069 D->setInvalidDecl();
10070 } else if (const auto *A = D->getAttr<VecTypeHintAttr>()) {
10071 Diag(D->getLocation(), diag::err_opencl_kernel_attr) << A;
10072 D->setInvalidDecl();
10073 } else if (const auto *A = D->getAttr<OpenCLIntelReqdSubGroupSizeAttr>()) {
10074 Diag(D->getLocation(), diag::err_opencl_kernel_attr) << A;
10075 D->setInvalidDecl();
10076 } else if (!D->hasAttr<CUDAGlobalAttr>()) {
10077 if (const auto *A = D->getAttr<AMDGPUFlatWorkGroupSizeAttr>()) {
10078 Diag(D->getLocation(), diag::err_attribute_wrong_decl_type)
10079 << A << A->isRegularKeywordAttribute() << ExpectedKernelFunction;
10080 D->setInvalidDecl();
10081 } else if (const auto *A = D->getAttr<AMDGPUWavesPerEUAttr>()) {
10082 Diag(D->getLocation(), diag::err_attribute_wrong_decl_type)
10083 << A << A->isRegularKeywordAttribute() << ExpectedKernelFunction;
10084 D->setInvalidDecl();
10085 } else if (const auto *A = D->getAttr<AMDGPUNumSGPRAttr>()) {
10086 Diag(D->getLocation(), diag::err_attribute_wrong_decl_type)
10087 << A << A->isRegularKeywordAttribute() << ExpectedKernelFunction;
10088 D->setInvalidDecl();
10089 } else if (const auto *A = D->getAttr<AMDGPUNumVGPRAttr>()) {
10090 Diag(D->getLocation(), diag::err_attribute_wrong_decl_type)
10091 << A << A->isRegularKeywordAttribute() << ExpectedKernelFunction;
10092 D->setInvalidDecl();
10093 }
10094 }
10095 }
10096
10097 // Do this check after processing D's attributes because the attribute
10098 // objc_method_family can change whether the given method is in the init
10099 // family, and it can be applied after objc_designated_initializer. This is a
10100 // bit of a hack, but we need it to be compatible with versions of clang that
10101 // processed the attribute list in the wrong order.
10102 if (D->hasAttr<ObjCDesignatedInitializerAttr>() &&
10103 cast<ObjCMethodDecl>(D)->getMethodFamily() != OMF_init) {
10104 Diag(D->getLocation(), diag::err_designated_init_attr_non_init);
10105 D->dropAttr<ObjCDesignatedInitializerAttr>();
10106 }
10107}
10108
10109// Helper for delayed processing TransparentUnion or BPFPreserveAccessIndexAttr
10110// attribute.
10112 const ParsedAttributesView &AttrList) {
10113 for (const ParsedAttr &AL : AttrList)
10114 if (AL.getKind() == ParsedAttr::AT_TransparentUnion) {
10115 handleTransparentUnionAttr(*this, D, AL);
10116 break;
10117 }
10118
10119 // For BPFPreserveAccessIndexAttr, we want to populate the attributes
10120 // to fields and inner records as well.
10121 if (D && D->hasAttr<BPFPreserveAccessIndexAttr>())
10122 handleBPFPreserveAIRecord(*this, cast<RecordDecl>(D));
10123}
10124
10125// Annotation attributes are the only attributes allowed after an access
10126// specifier.
10128 AccessSpecDecl *ASDecl, const ParsedAttributesView &AttrList) {
10129 for (const ParsedAttr &AL : AttrList) {
10130 if (AL.getKind() == ParsedAttr::AT_Annotate) {
10131 ProcessDeclAttribute(*this, nullptr, ASDecl, AL,
10133 } else {
10134 Diag(AL.getLoc(), diag::err_only_annotate_after_access_spec);
10135 return true;
10136 }
10137 }
10138 return false;
10139}
10140
10141/// checkUnusedDeclAttributes - Check a list of attributes to see if it
10142/// contains any decl attributes that we should warn about.
10144 for (const ParsedAttr &AL : A) {
10145 // Only warn if the attribute is an unignored, non-type attribute.
10146 if (AL.isUsedAsTypeAttr() || AL.isInvalid())
10147 continue;
10148 if (AL.getKind() == ParsedAttr::IgnoredAttribute)
10149 continue;
10150
10151 if (AL.getKind() == ParsedAttr::UnknownAttribute) {
10152 S.Diag(AL.getLoc(), diag::warn_unknown_attribute_ignored)
10153 << AL << AL.getRange();
10154 } else {
10155 S.Diag(AL.getLoc(), diag::warn_attribute_not_on_decl) << AL
10156 << AL.getRange();
10157 }
10158 }
10159}
10160
10161/// checkUnusedDeclAttributes - Given a declarator which is not being
10162/// used to build a declaration, complain about any decl attributes
10163/// which might be lying around on it.
10168 for (unsigned i = 0, e = D.getNumTypeObjects(); i != e; ++i)
10170}
10171
10172/// DeclClonePragmaWeak - clone existing decl (maybe definition),
10173/// \#pragma weak needs a non-definition decl and source may not have one.
10176 assert(isa<FunctionDecl>(ND) || isa<VarDecl>(ND));
10177 NamedDecl *NewD = nullptr;
10178 if (auto *FD = dyn_cast<FunctionDecl>(ND)) {
10179 FunctionDecl *NewFD;
10180 // FIXME: Missing call to CheckFunctionDeclaration().
10181 // FIXME: Mangling?
10182 // FIXME: Is the qualifier info correct?
10183 // FIXME: Is the DeclContext correct?
10184 NewFD = FunctionDecl::Create(
10185 FD->getASTContext(), FD->getDeclContext(), Loc, Loc,
10187 getCurFPFeatures().isFPConstrained(), false /*isInlineSpecified*/,
10190 NewD = NewFD;
10191
10192 if (FD->getQualifier())
10193 NewFD->setQualifierInfo(FD->getQualifierLoc());
10194
10195 // Fake up parameter variables; they are declared as if this were
10196 // a typedef.
10197 QualType FDTy = FD->getType();
10198 if (const auto *FT = FDTy->getAs<FunctionProtoType>()) {
10200 for (const auto &AI : FT->param_types()) {
10201 ParmVarDecl *Param = BuildParmVarDeclForTypedef(NewFD, Loc, AI);
10202 Param->setScopeInfo(0, Params.size());
10203 Params.push_back(Param);
10204 }
10205 NewFD->setParams(Params);
10206 }
10207 } else if (auto *VD = dyn_cast<VarDecl>(ND)) {
10208 NewD = VarDecl::Create(VD->getASTContext(), VD->getDeclContext(),
10209 VD->getInnerLocStart(), VD->getLocation(), II,
10210 VD->getType(), VD->getTypeSourceInfo(),
10211 VD->getStorageClass());
10212 if (VD->getQualifier())
10213 cast<VarDecl>(NewD)->setQualifierInfo(VD->getQualifierLoc());
10214 }
10215 return NewD;
10216}
10217
10218/// DeclApplyPragmaWeak - A declaration (maybe definition) needs \#pragma weak
10219/// applied to it, possibly with an alias.
10221 if (W.getAlias()) { // clone decl, impersonate __attribute(weak,alias(...))
10222 IdentifierInfo *NDId = ND->getIdentifier();
10223 NamedDecl *NewD = DeclClonePragmaWeak(ND, W.getAlias(), W.getLocation());
10224 NewD->addAttr(
10225 AliasAttr::CreateImplicit(Context, NDId->getName(), W.getLocation()));
10226 NewD->addAttr(WeakAttr::CreateImplicit(Context, W.getLocation()));
10227 WeakTopLevelDecl.push_back(NewD);
10228 // FIXME: "hideous" code from Sema::LazilyCreateBuiltin
10229 // to insert Decl at TU scope, sorry.
10230 DeclContext *SavedContext = CurContext;
10234 PushOnScopeChains(NewD, S);
10235 CurContext = SavedContext;
10236 } else { // just add weak to existing
10237 ND->addAttr(WeakAttr::CreateImplicit(Context, W.getLocation()));
10238 }
10239}
10240
10242 // It's valid to "forward-declare" #pragma weak, in which case we
10243 // have to do this.
10245 if (WeakUndeclaredIdentifiers.empty())
10246 return;
10247 NamedDecl *ND = nullptr;
10248 if (auto *VD = dyn_cast<VarDecl>(D))
10249 if (VD->isExternC())
10250 ND = VD;
10251 if (auto *FD = dyn_cast<FunctionDecl>(D))
10252 if (FD->isExternC())
10253 ND = FD;
10254 if (!ND)
10255 return;
10256 if (IdentifierInfo *Id = ND->getIdentifier()) {
10257 auto I = WeakUndeclaredIdentifiers.find(Id);
10258 if (I != WeakUndeclaredIdentifiers.end()) {
10259 auto &WeakInfos = I->second;
10260 for (const auto &W : WeakInfos)
10261 DeclApplyPragmaWeak(S, ND, W);
10262 std::remove_reference_t<decltype(WeakInfos)> EmptyWeakInfos;
10263 WeakInfos.swap(EmptyWeakInfos);
10264 }
10265 }
10266}
10267
10268/// ProcessDeclAttributes - Given a declarator (PD) with attributes indicated in
10269/// it, apply them to D. This is a bit tricky because PD can have attributes
10270/// specified in many different places, and we need to find and apply them all.
10272 // Ordering of attributes can be important, so we take care to process
10273 // attributes in the order in which they appeared in the source code.
10274
10275 // First, process attributes that appeared on the declaration itself (but
10276 // only if they don't have the legacy behavior of "sliding" to the DeclSepc).
10277 ParsedAttributesView NonSlidingAttrs;
10278 for (ParsedAttr &AL : PD.getDeclarationAttributes()) {
10279 if (AL.slidesFromDeclToDeclSpecLegacyBehavior()) {
10280 // Skip processing the attribute, but do check if it appertains to the
10281 // declaration. This is needed for the `MatrixType` attribute, which,
10282 // despite being a type attribute, defines a `SubjectList` that only
10283 // allows it to be used on typedef declarations.
10284 AL.diagnoseAppertainsTo(*this, D);
10285 } else {
10286 NonSlidingAttrs.addAtEnd(&AL);
10287 }
10288 }
10289 ProcessDeclAttributeList(S, D, NonSlidingAttrs);
10290
10291 // Apply decl attributes from the DeclSpec if present.
10292 if (!PD.getDeclSpec().getAttributes().empty()) {
10295 .WithIncludeCXX11Attributes(false)
10296 .WithIgnoreTypeAttributes(true));
10297 }
10298
10299 // Walk the declarator structure, applying decl attributes that were in a type
10300 // position to the decl itself. This handles cases like:
10301 // int *__attr__(x)** D;
10302 // when X is a decl attribute.
10303 for (unsigned i = 0, e = PD.getNumTypeObjects(); i != e; ++i) {
10306 .WithIncludeCXX11Attributes(false)
10307 .WithIgnoreTypeAttributes(true));
10308 }
10309
10310 // Finally, apply any attributes on the decl itself.
10312
10313 // Apply additional attributes specified by '#pragma clang attribute'.
10314 AddPragmaAttributes(S, D);
10315
10316 // Look for API notes that map to attributes.
10317 ProcessAPINotes(D);
10318}
10319
10320/// Is the given declaration allowed to use a forbidden type?
10321/// If so, it'll still be annotated with an attribute that makes it
10322/// illegal to actually use.
10324 const DelayedDiagnostic &diag,
10325 UnavailableAttr::ImplicitReason &reason) {
10326 // Private ivars are always okay. Unfortunately, people don't
10327 // always properly make their ivars private, even in system headers.
10328 // Plus we need to make fields okay, too.
10329 if (!isa<FieldDecl>(D) && !isa<ObjCPropertyDecl>(D) &&
10330 !isa<FunctionDecl>(D))
10331 return false;
10332
10333 // Silently accept unsupported uses of __weak in both user and system
10334 // declarations when it's been disabled, for ease of integration with
10335 // -fno-objc-arc files. We do have to take some care against attempts
10336 // to define such things; for now, we've only done that for ivars
10337 // and properties.
10338 if ((isa<ObjCIvarDecl>(D) || isa<ObjCPropertyDecl>(D))) {
10339 if (diag.getForbiddenTypeDiagnostic() == diag::err_arc_weak_disabled ||
10340 diag.getForbiddenTypeDiagnostic() == diag::err_arc_weak_no_runtime) {
10341 reason = UnavailableAttr::IR_ForbiddenWeak;
10342 return true;
10343 }
10344 }
10345
10346 // Allow all sorts of things in system headers.
10348 // Currently, all the failures dealt with this way are due to ARC
10349 // restrictions.
10350 reason = UnavailableAttr::IR_ARCForbiddenType;
10351 return true;
10352 }
10353
10354 return false;
10355}
10356
10357/// Handle a delayed forbidden-type diagnostic.
10359 Decl *D) {
10360 auto Reason = UnavailableAttr::IR_None;
10361 if (D && isForbiddenTypeAllowed(S, D, DD, Reason)) {
10362 assert(Reason && "didn't set reason?");
10363 D->addAttr(UnavailableAttr::CreateImplicit(S.Context, "", Reason, DD.Loc));
10364 return;
10365 }
10366 if (S.getLangOpts().ObjCAutoRefCount)
10367 if (const auto *FD = dyn_cast<FunctionDecl>(D)) {
10368 // FIXME: we may want to suppress diagnostics for all
10369 // kind of forbidden type messages on unavailable functions.
10370 if (FD->hasAttr<UnavailableAttr>() &&
10372 diag::err_arc_array_param_no_ownership) {
10373 DD.Triggered = true;
10374 return;
10375 }
10376 }
10377
10380 DD.Triggered = true;
10381}
10382
10383
10388
10389 // When delaying diagnostics to run in the context of a parsed
10390 // declaration, we only want to actually emit anything if parsing
10391 // succeeds.
10392 if (!decl) return;
10393
10394 // We emit all the active diagnostics in this pool or any of its
10395 // parents. In general, we'll get one pool for the decl spec
10396 // and a child pool for each declarator; in a decl group like:
10397 // deprecated_typedef foo, *bar, baz();
10398 // only the declarator pops will be passed decls. This is correct;
10399 // we really do need to consider delayed diagnostics from the decl spec
10400 // for each of the different declarations.
10401 const DelayedDiagnosticPool *pool = &poppedPool;
10402 do {
10403 bool AnyAccessFailures = false;
10405 i = pool->pool_begin(), e = pool->pool_end(); i != e; ++i) {
10406 // This const_cast is a bit lame. Really, Triggered should be mutable.
10407 DelayedDiagnostic &diag = const_cast<DelayedDiagnostic&>(*i);
10408 if (diag.Triggered)
10409 continue;
10410
10411 switch (diag.Kind) {
10413 // Don't bother giving deprecation/unavailable diagnostics if
10414 // the decl is invalid.
10415 if (!decl->isInvalidDecl())
10417 break;
10418
10420 // Only produce one access control diagnostic for a structured binding
10421 // declaration: we don't need to tell the user that all the fields are
10422 // inaccessible one at a time.
10423 if (AnyAccessFailures && isa<DecompositionDecl>(decl))
10424 continue;
10426 if (diag.Triggered)
10427 AnyAccessFailures = true;
10428 break;
10429
10431 handleDelayedForbiddenType(*this, diag, decl);
10432 break;
10433 }
10434 }
10435 } while ((pool = pool->getParent()));
10436}
10437
10438/// Given a set of delayed diagnostics, re-emit them as if they had
10439/// been delayed in the current context instead of in the given pool.
10440/// Essentially, this just moves them to the current pool.
10443 assert(curPool && "re-emitting in undelayed context not supported");
10444 curPool->steal(pool);
10445}
Defines the clang::ASTContext interface.
#define V(N, I)
Definition: ASTContext.h:3285
NodeId Parent
Definition: ASTDiff.cpp:191
int Id
Definition: ASTDiff.cpp:190
static SmallString< 64 > normalizeName(const IdentifierInfo *Name, const IdentifierInfo *Scope, AttributeCommonInfo::Syntax SyntaxUsed)
Definition: Attributes.cpp:127
#define SM(sm)
Definition: Cuda.cpp:83
static CudaArch getCudaArch(CodeGenModule &CGM)
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....
Defines the C++ template declaration subclasses.
Defines the classes clang::DelayedDiagnostic and clang::AccessedEntity.
Defines the clang::Expr interface and subclasses for C++ expressions.
int Priority
Definition: Format.cpp:2979
Defines helper utilities for supporting the HLSL runtime environment.
Defines the clang::IdentifierInfo, clang::IdentifierTable, and clang::Selector interfaces.
#define X(type, name)
Definition: Value.h:143
Defines the clang::LangOptions interface.
llvm::MachO::Target Target
Definition: MachO.h:50
llvm::MachO::Record Record
Definition: MachO.h:31
static bool versionsMatch(const VersionTuple &X, const VersionTuple &Y)
Check whether the two versions match.
Definition: ObjCMT.cpp:1068
static unsigned getNumAttributeArgs(const ParsedAttr &AL)
Definition: ParsedAttr.cpp:282
Defines the clang::Preprocessor interface.
static std::string toString(const clang::SanitizerSet &Sanitizers)
Produce a string containing comma-separated names of sanitizers in Sanitizers set.
This file declares semantic analysis for CUDA constructs.
static bool isCFStringType(QualType T, ASTContext &Ctx)
static void handleObjCBoxable(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleBPFPreserveAccessIndexAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCleanupAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAlignedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleWeakImportAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleHandleAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleHLSLShaderAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkGuardedByAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL, Expr *&Arg)
static void handleCodeSegAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handlePatchableFunctionEntryAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCountedByAttrField(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAMDGPUNumVGPRAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleOpenCLAccessAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleFormatAttr(Sema &S, Decl *D, const ParsedAttr &AL)
Handle attribute((format(type,idx,firstarg))) attributes based on http://gcc.gnu.org/onlinedocs/gcc/F...
static void handleUninitializedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isNSStringType(QualType T, ASTContext &Ctx, bool AllowNSAttributedString=false)
static void handleRequiresCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleBTFDeclTagAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleOptimizeNoneAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleEnableIfAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isFunctionOrMethodVariadic(const Decl *D)
static void handleSwiftError(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSectionAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleStandardNoReturnAttr(Sema &S, Decl *D, const ParsedAttr &A)
static void handleMIGServerRoutineAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleGuardedByAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleZeroCallUsedRegsAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static const RecordDecl * GetEnclosingNamedOrTopAnonRecord(const FieldDecl *FD)
static void handleDiagnoseAsBuiltinAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleEnumExtensibilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static T * mergeVisibilityAttr(Sema &S, Decl *D, const AttributeCommonInfo &CI, typename T::VisibilityType value)
static bool CheckCountExpr(Sema &S, FieldDecl *FD, Expr *E, llvm::SmallVectorImpl< TypeCoupledDeclRefInfo > &Decls)
static void handleLayoutVersion(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAMDGPUWavesPerEUAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkForConsumableClass(Sema &S, const CXXMethodDecl *MD, const ParsedAttr &AL)
static void handleDLLAttr(Sema &S, Decl *D, const ParsedAttr &A)
static void handleConstantAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAlignValueAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleHLSLSV_DispatchThreadIDAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSubGroupSize(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNoCfCheckAttr(Sema &S, Decl *D, const ParsedAttr &Attrs)
static void handleArmBuiltinAliasAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCmseNSEntryAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleOpenCLNoSVMAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleReturnsNonNullAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void checkUnusedDeclAttributes(Sema &S, const ParsedAttributesView &A)
checkUnusedDeclAttributes - Check a list of attributes to see if it contains any decl attributes that...
static void handleGNUInlineAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkArmNewAttrMutualExclusion(Sema &S, const ParsedAttr &AL, const FunctionProtoType *FPT, FunctionType::ArmStateValue CurrentState, StringRef StateName)
static void handleWorkGroupSize(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleBuiltinAliasAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleTransparentUnionAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isErrorParameter(Sema &S, QualType QT)
static void handleEnforceTCBAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void checkAttrArgsAreCapabilityObjs(Sema &S, Decl *D, const ParsedAttr &AL, SmallVectorImpl< Expr * > &Args, unsigned Sidx=0, bool ParamIdxOk=false)
Checks that all attribute arguments, starting from Sidx, resolve to a capability object.
static QualType getFunctionOrMethodParamType(const Decl *D, unsigned Idx)
static bool isLegalTypeForHLSLSV_DispatchThreadID(QualType T)
static void handleSwiftNewType(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCIndependentClass(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleXReturnsXRetainedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleErrorAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkCodeSegName(Sema &S, SourceLocation LiteralLoc, StringRef CodeSegName)
static void handleAvailabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSwiftAsyncName(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleTryAcquireCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleRISCVInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSetTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleFormatArgAttr(Sema &S, Decl *D, const ParsedAttr &AL)
Handle attribute((format_arg((idx)))) attribute based on http://gcc.gnu.org/onlinedocs/gcc/Function-A...
static void ProcessDeclAttribute(Sema &S, Scope *scope, Decl *D, const ParsedAttr &AL, const Sema::ProcessDeclAttributeOptions &Options)
ProcessDeclAttribute - Apply the specific attribute to the specified decl if the attribute applies to...
static void handleTargetAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleXRayLogArgsAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCOwnershipAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static const Sema::SemaDiagnosticBuilder & appendDiagnostics(const Sema::SemaDiagnosticBuilder &Bldr)
static void handlePassObjectSizeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static const ParmVarDecl * getFunctionOrMethodParam(const Decl *D, unsigned Idx)
static bool ArmCdeAliasValid(unsigned BuiltinID, StringRef AliasName)
static void handleAMDGPUMaxNumWorkGroupsAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNoMergeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleArmNewAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCPreciseLifetimeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkUInt32Argument(Sema &S, const AttrInfo &AI, const Expr *Expr, uint32_t &Val, unsigned Idx=UINT_MAX, bool StrictlyUnsigned=false)
If Expr is a valid integer constant, get the value of the integer expression and return success or fa...
static void handleAnyX86InterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCDirectMembersAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleManagedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSwiftAttrAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAVRInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSwiftAsyncAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleParamTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleUnsafeBufferUsage(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isValidSubjectOfNSReturnsRetainedAttribute(QualType QT)
static bool attrNonNullArgCheck(Sema &S, QualType T, const ParsedAttr &AL, SourceRange AttrParmRange, SourceRange TypeRange, bool isReturnValue=false)
static void handleAcquireCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static std::enable_if_t< std::is_base_of_v< Attr, AttrInfo >, SourceLocation > getAttrLoc(const AttrInfo &AL)
A helper function to provide Attribute Location for the Attr types AND the ParsedAttr.
static void handleCPUSpecificAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCRuntimeName(Sema &S, Decl *D, const ParsedAttr &AL)
static void handlePackedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleIFuncAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkFunctionOrMethodParameterIndex(Sema &S, const Decl *D, const AttrInfo &AI, unsigned AttrArgNum, const Expr *IdxExpr, ParamIdx &Idx, bool CanIndexImplicitThis=false)
Check if IdxExpr is a valid parameter index for a function or instance method D.
static void handleAbiTagAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isFunctionOrMethod(const Decl *D)
isFunctionOrMethod - Return true if the given decl has function type (function or function-typed vari...
static void handleObjCMethodFamilyAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAttrWithMessage(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleWeakRefAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleExtVectorTypeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleX86ForceAlignArgPointerAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCalledOnceAttr(Sema &S, Decl *D, const ParsedAttr &AL)
Handle 'called_once' attribute.
static void handleLockReturnedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkFunctionConditionAttr(Sema &S, Decl *D, const ParsedAttr &AL, Expr *&Cond, StringRef &Msg)
static void handleAcquiredAfterAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleExternalSourceSymbolAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNonNullAttrParameter(Sema &S, ParmVarDecl *D, const ParsedAttr &AL)
static bool checkParamIsIntegerType(Sema &S, const Decl *D, const AttrInfo &AI, unsigned AttrArgNo)
Checks to be sure that the given parameter number is in bounds, and is an integral type.
static void handleObjCReturnsInnerPointerAttr(Sema &S, Decl *D, const ParsedAttr &Attrs)
static bool checkRecordTypeForCapability(Sema &S, QualType Ty)
static void handleArgumentWithTypeTagAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkIBOutletCommon(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkAcquireOrderAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL, SmallVectorImpl< Expr * > &Args)
static void handleWebAssemblyImportModuleAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleLocksExcludedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleMSAllocatorAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static AttrTy * mergeEnforceTCBAttrImpl(Sema &S, Decl *D, const AttrTy &AL)
static bool isValidSubjectOfOSAttribute(QualType QT)
static bool hasDeclarator(const Decl *D)
Return true if the given decl has a declarator that should have been processed by Sema::GetTypeForDec...
static bool ArmMveAliasValid(unsigned BuiltinID, StringRef AliasName)
static void handleConstructorAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAllocSizeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleConsumableAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static const RecordType * getRecordType(QualType QT)
Checks that the passed in QualType either is of RecordType or points to RecordType.
static void handleObjCExternallyRetainedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNoSanitizeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleReturnTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isValidSubjectOfNSAttribute(QualType QT)
static void handleTargetClonesAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAllocAlignAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleM68kInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleIBOutlet(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleHLSLResourceBindingAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCSuppresProtocolAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkAMDGPUFlatWorkGroupSizeArguments(Sema &S, Expr *MinExpr, Expr *MaxExpr, const AMDGPUFlatWorkGroupSizeAttr &Attr)
static void handleSwiftBridge(Sema &S, Decl *D, const ParsedAttr &AL)
FormatAttrKind
@ CFStringFormat
@ IgnoredFormat
@ InvalidFormat
@ StrftimeFormat
@ SupportedFormat
@ NSStringFormat
static void handleBPFPreserveAIRecord(Sema &S, RecordDecl *RD)
static bool isFunctionOrMethodOrBlock(const Decl *D)
Return true if the given decl has function type (function or function-typed variable) or an Objective...
static void handlePreferredTypeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isValidSubjectOfCFAttribute(QualType QT)
static void checkOMPAssumeAttr(Sema &S, SourceLocation Loc, StringRef AssumptionStr)
Check if AssumptionStr is a known assumption and warn if not.
static void handleDeviceAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleHLSLPackOffsetAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handlePtGuardedByAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAlwaysInlineAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAssertCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleVisibilityAttr(Sema &S, Decl *D, const ParsedAttr &AL, bool isTypeVisibility)
static void handleAnnotateAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static FormatAttrKind getFormatAttrKind(StringRef Format)
getFormatAttrKind - Map from format attribute names to supported format types.
static void handleNullableTypeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleUuidAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAcquireHandleAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isValidSwiftIndirectResultType(QualType Ty)
Pointers and references in the default address space.
static void handleWebAssemblyImportNameAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool tryMakeVariablePseudoStrong(Sema &S, VarDecl *VD, bool DiagnoseFailure)
static void handleMSConstexprAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void checkSwiftAsyncErrorBlock(Sema &S, Decl *D, const SwiftAsyncErrorAttr *ErrorAttr, const SwiftAsyncAttr *AsyncAttr)
static void handleCommonAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleTestTypestateAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkTryLockFunAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL, SmallVectorImpl< Expr * > &Args)
static bool ArmBuiltinAliasValid(unsigned BuiltinID, StringRef AliasName, ArrayRef< IntrinToName > Map, const char *IntrinNames)
static void parseModeAttrArg(Sema &S, StringRef Str, unsigned &DestWidth, bool &IntegerMode, bool &ComplexMode, FloatModeKind &ExplicitType)
parseModeAttrArg - Parses attribute mode string and returns parsed type attribute.
static void handleSimpleAttribute(Sema &S, Decl *D, const AttributeCommonInfo &CI)
Applies the given attribute to the Decl without performing any additional semantic checking.
static void handleExcludeFromExplicitInstantiationAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleHLSLNumThreadsAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSharedTrylockFunctionAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleLaunchBoundsAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkAvailabilityAttr(Sema &S, SourceRange Range, IdentifierInfo *Platform, VersionTuple Introduced, VersionTuple Deprecated, VersionTuple Obsoleted)
static void handleObjCBridgeMutableAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleDependencyAttr(Sema &S, Scope *Scope, Decl *D, const ParsedAttr &AL)
static void handleARMInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNoBuiltinAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleLifetimeCategoryAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNoUniqueAddressAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool validateAlignasAppliedType(Sema &S, Decl *D, const AlignedAttr &Attr, SourceLocation AttrLoc)
Perform checking of type validity.
static void handleNakedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleFunctionReturnThunksAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleDeprecatedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static SourceRange getFunctionOrMethodResultSourceRange(const Decl *D)
static Sema::RetainOwnershipKind parsedAttrToRetainOwnershipKind(const ParsedAttr &AL)
static unsigned getNumAttributeArgs(const ParsedAttr &AL)
static void handleGlobalAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSentinelAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCodeModelAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleHLSLParamModifierAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCallableWhenAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool hasBTFDeclTagAttr(Decl *D, StringRef Tag)
static void handleDelayedForbiddenType(Sema &S, DelayedDiagnostic &DD, Decl *D)
Handle a delayed forbidden-type diagnostic.
static void handleAssertSharedLockAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkLockFunAttrCommon(Sema &S, Decl *D, const ParsedAttr &AL, SmallVectorImpl< Expr * > &Args)
static bool RISCVAliasValid(unsigned BuiltinID, StringRef AliasName)
static void handleAssumeAlignedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSharedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleMSInheritanceAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkAMDGPUMaxNumWorkGroupsArguments(Sema &S, Expr *XExpr, Expr *YExpr, Expr *ZExpr, const AMDGPUMaxNumWorkGroupsAttr &Attr)
static void handleVecTypeHint(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleRestrictAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleMinVectorWidthAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleUnusedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static Expr * makeLaunchBoundsArgExpr(Sema &S, Expr *E, const CUDALaunchBoundsAttr &AL, const unsigned Idx)
static bool ArmSmeAliasValid(ASTContext &Context, unsigned BuiltinID, StringRef AliasName)
static void handleMipsInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleDeclspecThreadAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSYCLKernelAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAMDGPUNumSGPRAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool ArmSveAliasValid(ASTContext &Context, unsigned BuiltinID, StringRef AliasName)
static void handleInterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleExclusiveTrylockFunctionAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCallbackAttr(Sema &S, Decl *D, const ParsedAttr &AL)
Handle attribute((callback(CalleeIdx, PayloadIdx0, ...))) attributes.
static void handleInitPriorityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
Handle attribute((init_priority(priority))) attributes based on http://gcc.gnu.org/onlinedocs/gcc/C_0...
static void handlePtGuardedVarAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool hasFunctionProto(const Decl *D)
hasFunctionProto - Return true if the given decl has a argument information.
static bool checkRecordDeclForAttr(const RecordDecl *RD)
static void handleDestroyAttr(Sema &S, Decl *D, const ParsedAttr &A)
static void handleTypeTagForDatatypeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static unsigned getFunctionOrMethodNumParams(const Decl *D)
getFunctionOrMethodNumParams - Return number of function or method parameters.
static void handleRandomizeLayoutAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void markUsedForAliasOrIfunc(Sema &S, Decl *D, const ParsedAttr &AL, StringRef Str)
static bool isCapabilityExpr(Sema &S, const Expr *Ex)
static bool isValidOSObjectOutParameter(const Decl *D)
static bool isValidSwiftContextType(QualType Ty)
Pointer-like types in the default address space.
static void handleNoDebugAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSuppressAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleSwiftName(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCRequiresSuperAttr(Sema &S, Decl *D, const ParsedAttr &Attrs)
static void handleObjCDesignatedInitializer(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNoReturnAttr(Sema &S, Decl *D, const ParsedAttr &Attrs)
static const AttrTy * findEnforceTCBAttrByName(Decl *D, StringRef Name)
static void handleWebAssemblyExportNameAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNoEscapeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAvailableOnlyInDefaultEvalMethod(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkAttrMutualExclusion(Sema &S, Decl *D, const ParsedAttr &AL)
Diagnose mutually exclusive attributes when present on a given declaration.
static bool MustDelayAttributeArguments(const ParsedAttr &AL)
static void handleNoRandomizeLayoutAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isInstanceMethod(const Decl *D)
static void handleTargetVersionAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static SourceRange getFunctionOrMethodParamRange(const Decl *D, unsigned Idx)
static void handleAVRSignalAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static QualType getFunctionOrMethodResultType(const Decl *D)
static void handleWarnUnusedResult(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleBlocksAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAssertExclusiveLockAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isIntOrBool(Expr *Exp)
Check if the passed-in expression is of type int or bool.
static void handleSimpleAttributeOrDiagnose(Sema &S, Decl *D, const AttributeCommonInfo &CI, bool PassesCheck, unsigned DiagID, DiagnosticArgs &&... ExtraArgs)
Add an attribute AttrType to declaration D, provided that PassesCheck is true.
static bool isSanitizerAttributeAllowedOnGlobals(StringRef Sanitizer)
static void handleObjCBridgeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCBridgeRelatedAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isValidSwiftErrorResultType(QualType Ty)
Pointers and references to pointers in the default address space.
static void handleCallConvAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkAMDGPUWavesPerEUArguments(Sema &S, Expr *MinExpr, Expr *MaxExpr, const AMDGPUWavesPerEUAttr &Attr)
static void handleMinSizeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool validateSwiftFunctionName(Sema &S, const ParsedAttr &AL, SourceLocation Loc, StringRef Name, unsigned &SwiftParamCount, bool &IsSingleParamInit)
static void handleOwnershipAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkTypedefTypeForCapability(QualType Ty)
static void handleAcquiredBeforeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleReleaseCapabilityAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleMSP430InterruptAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool typeHasCapability(Sema &S, QualType Ty)
static void handleAnalyzerNoReturnAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleIBOutletCollection(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCNSObject(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleObjCDirectAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNSErrorDomain(Sema &S, Decl *D, const ParsedAttr &Attr)
static bool threadSafetyCheckIsSmartPointer(Sema &S, const RecordType *RT)
static bool isFunctionLike(const Type &T)
static void handleOMPAssumeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleDiagnoseIfAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleCFGuardAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleNonNullAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool threadSafetyCheckIsPointer(Sema &S, const Decl *D, const ParsedAttr &AL)
Check if passed in Decl is a pointer type.
static bool isForbiddenTypeAllowed(Sema &S, Decl *D, const DelayedDiagnostic &diag, UnavailableAttr::ImplicitReason &reason)
Is the given declaration allowed to use a forbidden type? If so, it'll still be annotated with an att...
static void handleInternalLinkageAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAMDGPUFlatWorkGroupSizeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleModeAttr(Sema &S, Decl *D, const ParsedAttr &AL)
handleModeAttr - This attribute modifies the width of a decl with primitive type.
static void handleDestructorAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handlePreferredName(Sema &S, Decl *D, const ParsedAttr &AL)
static bool checkPositiveIntArgument(Sema &S, const AttrInfo &AI, const Expr *Expr, int &Val, unsigned Idx=UINT_MAX)
Wrapper around checkUInt32Argument, with an extra check to be sure that the result will fit into a re...
static void handleNoSanitizeSpecificAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleVecReturnAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static bool isGlobalVar(const Decl *D)
static void handleSwiftAsyncError(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleTLSModelAttr(Sema &S, Decl *D, const ParsedAttr &AL)
static void handleAliasAttr(Sema &S, Decl *D, const ParsedAttr &AL)
This file declares semantic analysis for HLSL constructs.
SourceRange Range
Definition: SemaObjC.cpp:754
SourceLocation Loc
Definition: SemaObjC.cpp:755
This file declares semantic analysis for Objective-C.
Defines the clang::SourceLocation class and associated facilities.
Defines the SourceManager interface.
Enumerates target-specific builtins in their own namespaces within namespace clang.
C Language Family Type Representation.
__device__ int
virtual void AssignInheritanceModel(CXXRecordDecl *RD)
Callback invoked when an MSInheritanceAttr has been attached to a CXXRecordDecl.
Definition: ASTConsumer.h:112
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition: ASTContext.h:182
MSGuidDecl * getMSGuidDecl(MSGuidDeclParts Parts) const
Return a declaration for the global GUID object representing the given GUID value.
SourceManager & getSourceManager()
Definition: ASTContext.h:705
TranslationUnitDecl * getTranslationUnitDecl() const
Definition: ASTContext.h:1073
CharUnits getTypeAlignInChars(QualType T) const
Return the ABI-specified alignment of a (complete) type T, in characters.
TypedefDecl * getObjCInstanceTypeDecl()
Retrieve the typedef declaration corresponding to the Objective-C "instancetype" type.
QualType getTagDeclType(const TagDecl *Decl) const
Return the unique reference to the type for the specified TagDecl (struct/union/class/enum) decl.
DeclarationNameTable DeclarationNames
Definition: ASTContext.h:648
MangleContext * createMangleContext(const TargetInfo *T=nullptr)
If T is null pointer, assume the target in ASTContext.
QualType getRealTypeForBitwidth(unsigned DestWidth, FloatModeKind ExplicitType) const
getRealTypeForBitwidth - sets floating point QualTy according to specified bitwidth.
bool hasSameType(QualType T1, QualType T2) const
Determine whether the given types T1 and T2 are equivalent.
Definition: ASTContext.h:2591
QualType getVectorType(QualType VectorType, unsigned NumElts, VectorKind VecKind) const
Return the unique reference to a vector type of the specified element type and size.
CallingConv getDefaultCallingConvention(bool IsVariadic, bool IsCXXMethod, bool IsBuiltin=false) const
Retrieves the default calling convention for the current target.
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
IdentifierTable & Idents
Definition: ASTContext.h:644
Builtin::Context & BuiltinInfo
Definition: ASTContext.h:646
const LangOptions & getLangOpts() const
Definition: ASTContext.h:775
QualType getConstType(QualType T) const
Return the uniqued reference to the type for a const qualified type.
Definition: ASTContext.h:1299
QualType getBaseElementType(const ArrayType *VAT) const
Return the innermost element type of an array type.
QualType getIntTypeForBitwidth(unsigned DestWidth, unsigned Signed) const
getIntTypeForBitwidth - sets integer QualTy according to specified details: bitwidth,...
const TargetInfo * getAuxTargetInfo() const
Definition: ASTContext.h:758
TypeSourceInfo * getTrivialTypeSourceInfo(QualType T, SourceLocation Loc=SourceLocation()) const
Allocate a TypeSourceInfo where all locations have been initialized to a given location,...
CanQualType IntTy
Definition: ASTContext.h:1100
QualType getObjCObjectPointerType(QualType OIT) const
Return a ObjCObjectPointerType type for the given ObjCObjectType.
CanQualType OverloadTy
Definition: ASTContext.h:1119
const ArrayType * getAsArrayType(QualType T) const
Type Query functions.
uint64_t getTypeSize(QualType T) const
Return the size of the specified (complete) type T, in bits.
Definition: ASTContext.h:2341
CanQualType VoidTy
Definition: ASTContext.h:1091
QualType getComplexType(QualType T) const
Return the uniqued reference to the type for a complex number with the specified element type.
const TargetInfo & getTargetInfo() const
Definition: ASTContext.h:757
CharUnits toCharUnitsFromBits(int64_t BitSize) const
Convert a size in bits to a size in characters.
TargetCXXABI::Kind getCXXABIKind() const
Return the C++ ABI kind that should be used.
Definition: ASTContext.cpp:818
unsigned getTypeAlign(QualType T) const
Return the ABI-specified alignment of a (complete) type T, in bits.
Definition: ASTContext.h:2372
uint64_t getCharWidth() const
Return the size of the character type, in bits.
Definition: ASTContext.h:2345
An abstract interface that should be implemented by listeners that want to be notified when an AST en...
Represents an access specifier followed by colon ':'.
Definition: DeclCXX.h:86
PtrTy get() const
Definition: Ownership.h:170
bool isInvalid() const
Definition: Ownership.h:166
Attr - This represents one attribute.
Definition: Attr.h:42
SourceLocation getLocation() const
Definition: Attr.h:95
void setAttributeSpellingListIndex(unsigned V)
std::string getNormalizedFullName() const
Gets the normalized full name, which consists of both scope and name and with surrounding underscores...
Definition: Attributes.cpp:151
unsigned getAttributeSpellingListIndex() const
const IdentifierInfo * getScopeName() const
SourceLocation getLoc() const
const IdentifierInfo * getAttrName() const
bool isStandardAttributeSyntax() const
The attribute is spelled [[]] in either C or C++ mode, including standard attributes spelled with a k...
Represents a C++11 auto or C++14 decltype(auto) type, possibly constrained by a type-constraint.
Definition: Type.h:5981
Pointer to a block type.
Definition: Type.h:3349
This class is used for builtin types like 'int'.
Definition: Type.h:2981
bool isAuxBuiltinID(unsigned ID) const
Return true if builtin ID belongs to AuxTarget.
Definition: Builtins.h:262
static bool isBuiltinFunc(llvm::StringRef Name)
Returns true if this is a libc/libm function without the '__builtin_' prefix.
Definition: Builtins.cpp:63
unsigned getAuxBuiltinID(unsigned ID) const
Return real builtin ID (i.e.
Definition: Builtins.h:268
Represents a static or instance method of a struct/union/class.
Definition: DeclCXX.h:2060
QualType getFunctionObjectParameterType() const
Definition: DeclCXX.h:2210
static bool isStaticOverloadedOperator(OverloadedOperatorKind OOK)
Returns true if the given operator is implicitly static in a record context.
Definition: DeclCXX.h:2102
Represents a C++ struct/union/class.
Definition: DeclCXX.h:258
CXXRecordDecl * getDefinition() const
Definition: DeclCXX.h:564
bool hasDefinition() const
Definition: DeclCXX.h:571
MSInheritanceModel calculateInheritanceModel() const
Calculate what the inheritance model would be for this class.
Represents the this expression in C++.
Definition: ExprCXX.h:1148
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
Definition: Expr.h:2820
static CallExpr * Create(const ASTContext &Ctx, Expr *Fn, ArrayRef< Expr * > Args, QualType Ty, ExprValueKind VK, SourceLocation RParenLoc, FPOptionsOverride FPFeatures, unsigned MinNumArgs=0, ADLCallKind UsesADL=NotADL)
Create a call expression.
Definition: Expr.cpp:1494
CharUnits - This is an opaque type for sizes expressed in character units.
Definition: CharUnits.h:38
QuantityType getQuantity() const
getQuantity - Get the raw integer representation of this quantity.
Definition: CharUnits.h:185
Declaration of a class template.
const RelatedTargetVersionMapping * getVersionMapping(OSEnvPair Kind) const
The results of name lookup within a DeclContext.
Definition: DeclBase.h:1369
specific_decl_iterator - Iterates over a subrange of declarations stored in a DeclContext,...
Definition: DeclBase.h:2342
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
Definition: DeclBase.h:1436
DeclContext * getParent()
getParent - Returns the containing DeclContext.
Definition: DeclBase.h:2066
bool isFileContext() const
Definition: DeclBase.h:2137
DeclContext * getRedeclContext()
getRedeclContext - Retrieve the context in which an entity conflicts with other entities of the same ...
Definition: DeclBase.cpp:1938
decl_range decls() const
decls_begin/decls_end - Iterate over the declarations stored in this context.
Definition: DeclBase.h:2322
bool isExternCContext() const
Determines whether this context or some of its ancestors is a linkage specification context that spec...
Definition: DeclBase.cpp:1333
A reference to a declared variable, function, enum, etc.
Definition: Expr.h:1260
DeclarationNameInfo getNameInfo() const
Definition: Expr.h:1332
static DeclRefExpr * Create(const ASTContext &Context, NestedNameSpecifierLoc QualifierLoc, SourceLocation TemplateKWLoc, ValueDecl *D, bool RefersToEnclosingVariableOrCapture, SourceLocation NameLoc, QualType T, ExprValueKind VK, NamedDecl *FoundD=nullptr, const TemplateArgumentListInfo *TemplateArgs=nullptr, NonOdrUseReason NOUR=NOUR_None)
Definition: Expr.cpp:488
bool hasQualifier() const
Determine whether this declaration reference was preceded by a C++ nested-name-specifier,...
Definition: Expr.h:1343
ValueDecl * getDecl()
Definition: Expr.h:1328
ParsedAttributes & getAttributes()
Definition: DeclSpec.h:870
Decl - This represents one declaration (or definition), e.g.
Definition: DeclBase.h:86
T * getAttr() const
Definition: DeclBase.h:579
bool hasAttrs() const
Definition: DeclBase.h:524
ASTContext & getASTContext() const LLVM_READONLY
Definition: DeclBase.cpp:501
void addAttr(Attr *A)
Definition: DeclBase.cpp:991
void setInvalidDecl(bool Invalid=true)
setInvalidDecl - Indicates the Decl had a semantic error.
Definition: DeclBase.cpp:132
const FunctionType * getFunctionType(bool BlocksToo=true) const
Looks through the Decl's underlying type to extract a FunctionType when possible.
Definition: DeclBase.cpp:1132
FunctionDecl * getAsFunction() LLVM_READONLY
Returns the function itself, or the templated function if this is a function template.
Definition: DeclBase.cpp:227
bool canBeWeakImported(bool &IsDefinition) const
Determines whether this symbol can be weak-imported, e.g., whether it would be well-formed to add the...
Definition: DeclBase.cpp:791
bool isInvalidDecl() const
Definition: DeclBase.h:594
llvm::iterator_range< specific_attr_iterator< T > > specific_attrs() const
Definition: DeclBase.h:565
SourceLocation getLocation() const
Definition: DeclBase.h:445
redecl_range redecls() const
Returns an iterator range for all the redeclarations of the same decl.
Definition: DeclBase.h:1039
DeclContext * getDeclContext()
Definition: DeclBase.h:454
SourceLocation getBeginLoc() const LLVM_READONLY
Definition: DeclBase.h:437
void dropAttr()
Definition: DeclBase.h:562
AttrVec & getAttrs()
Definition: DeclBase.h:530
static bool isFlexibleArrayMemberLike(ASTContext &Context, const Decl *D, QualType Ty, LangOptions::StrictFlexArraysLevelKind StrictFlexArraysLevel, bool IgnoreTemplateOrMacroSubstitution)
Whether it resembles a flexible array member.
Definition: DeclBase.cpp:413
void setDeclContext(DeclContext *DC)
setDeclContext - Set both the semantic and lexical DeclContext to DC.
Definition: DeclBase.cpp:336
bool hasAttr() const
Definition: DeclBase.h:583
void setLexicalDeclContext(DeclContext *DC)
Definition: DeclBase.cpp:340
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
Definition: DeclBase.h:968
virtual SourceRange getSourceRange() const LLVM_READONLY
Source range that this declaration covers.
Definition: DeclBase.h:433
DeclarationName getCXXOperatorName(OverloadedOperatorKind Op)
Get the name of the overloadable C++ operator corresponding to Op.
The name of a declaration.
NestedNameSpecifier * getQualifier() const
Retrieve the nested-name-specifier that qualifies the name of this declaration, if it was present in ...
Definition: Decl.h:828
SourceLocation getTypeSpecStartLoc() const
Definition: Decl.cpp:1985
SourceLocation getBeginLoc() const LLVM_READONLY
Definition: Decl.h:822
void setQualifierInfo(NestedNameSpecifierLoc QualifierLoc)
Definition: Decl.cpp:1997
NestedNameSpecifierLoc getQualifierLoc() const
Retrieve the nested-name-specifier (with source-location information) that qualifies the name of this...
Definition: Decl.h:836
Expr * getTrailingRequiresClause()
Get the constraint-expression introduced by the trailing requires-clause in the function/member decla...
Definition: Decl.h:846
TypeSourceInfo * getTypeSourceInfo() const
Definition: Decl.h:799
Information about one declarator, including the parsed type information and the identifier.
Definition: DeclSpec.h:1900
const DeclaratorChunk & getTypeObject(unsigned i) const
Return the specified TypeInfo from this declarator.
Definition: DeclSpec.h:2398
const DeclSpec & getDeclSpec() const
getDeclSpec - Return the declaration-specifier that this declarator was declared with.
Definition: DeclSpec.h:2047
const ParsedAttributes & getAttributes() const
Definition: DeclSpec.h:2683
unsigned getNumTypeObjects() const
Return the number of types applied to this declarator.
Definition: DeclSpec.h:2394
const ParsedAttributesView & getDeclarationAttributes() const
Definition: DeclSpec.h:2686
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of enums.
Definition: Type.h:5575
This represents one expression.
Definition: Expr.h:110
static bool isPotentialConstantExprUnevaluated(Expr *E, const FunctionDecl *FD, SmallVectorImpl< PartialDiagnosticAt > &Diags)
isPotentialConstantExprUnevaluated - Return true if this expression might be usable in a constant exp...
Expr * IgnoreParenCasts() LLVM_READONLY
Skip past any parentheses and casts which might surround this expression until reaching a fixed point...
Definition: Expr.cpp:3064
bool isValueDependent() const
Determines whether the value of this expression depends on.
Definition: Expr.h:175
bool isTypeDependent() const
Determines whether the type of this expression depends on.
Definition: Expr.h:192
bool containsUnexpandedParameterPack() const
Whether this expression contains an unexpanded parameter pack (for C++11 variadic templates).
Definition: Expr.h:239
bool isIntegerConstantExpr(const ASTContext &Ctx, SourceLocation *Loc=nullptr) const
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
Definition: Expr.cpp:277
std::optional< llvm::APSInt > getIntegerConstantExpr(const ASTContext &Ctx, SourceLocation *Loc=nullptr) const
isIntegerConstantExpr - Return the value if this expression is a valid integer constant expression.
QualType getType() const
Definition: Expr.h:142
Represents difference between two FPOptions values.
Definition: LangOptions.h:915
Represents a member of a struct/union/class.
Definition: Decl.h:3057
SourceRange getSourceRange() const override LLVM_READONLY
Source range that this declaration covers.
Definition: Decl.cpp:4666
const RecordDecl * getParent() const
Returns the parent of this field declaration, which is the struct in which this field is defined.
Definition: Decl.h:3270
Annotates a diagnostic with some code that should be inserted, removed, or replaced to fix the proble...
Definition: Diagnostic.h:71
static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)
Create a code modification hint that replaces the given source range with the given code string.
Definition: Diagnostic.h:134
static FixItHint CreateInsertion(SourceLocation InsertionLoc, StringRef Code, bool BeforePreviousInsertions=false)
Create a code modification hint that inserts the given code string at a specific location.
Definition: Diagnostic.h:97
Represents a function declaration or definition.
Definition: Decl.h:1971
const ParmVarDecl * getParamDecl(unsigned i) const
Definition: Decl.h:2706
bool isFunctionTemplateSpecialization() const
Determine whether this function is a function template specialization.
Definition: Decl.cpp:4054
FunctionTemplateDecl * getDescribedFunctionTemplate() const
Retrieves the function template that is described by this function declaration.
Definition: Decl.cpp:4042
bool isThisDeclarationADefinition() const
Returns whether this specific declaration of the function is also a definition that does not contain ...
Definition: Decl.h:2283
SourceRange getReturnTypeSourceRange() const
Attempt to compute an informative source range covering the function return type.
Definition: Decl.cpp:3873
unsigned getBuiltinID(bool ConsiderWrapperFunctions=false) const
Returns a value indicating whether this function corresponds to a builtin function.
Definition: Decl.cpp:3632
param_iterator param_end()
Definition: Decl.h:2696
bool isInlined() const
Determine whether this function should be inlined, because it is either marked "inline" or "constexpr...
Definition: Decl.h:2830
void setIsMultiVersion(bool V=true)
Sets the multiversion state for this declaration and all of its redeclarations.
Definition: Decl.h:2605
QualType getReturnType() const
Definition: Decl.h:2754
ArrayRef< ParmVarDecl * > parameters() const
Definition: Decl.h:2683
bool hasPrototype() const
Whether this function has a prototype, either because one was explicitly written or because it was "i...
Definition: Decl.h:2405
param_iterator param_begin()
Definition: Decl.h:2695
bool isVariadic() const
Whether this function is variadic.
Definition: Decl.cpp:3089
bool isConstexprSpecified() const
Definition: Decl.h:2441
bool isExternC() const
Determines whether this function is a function with external, C linkage.
Definition: Decl.cpp:3492
static FunctionDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation NLoc, DeclarationName N, QualType T, TypeSourceInfo *TInfo, StorageClass SC, bool UsesFPIntrin=false, bool isInlineSpecified=false, bool hasWrittenPrototype=true, ConstexprSpecKind ConstexprKind=ConstexprSpecKind::Unspecified, Expr *TrailingRequiresClause=nullptr)
Definition: Decl.h:2160
bool isConsteval() const
Definition: Decl.h:2444
unsigned getNumParams() const
Return the number of parameters this function must have based on its FunctionType.
Definition: Decl.cpp:3692
bool hasBody(const FunctionDecl *&Definition) const
Returns true if the function has a body.
Definition: Decl.cpp:3156
bool isInlineSpecified() const
Determine whether the "inline" keyword was specified for this function.
Definition: Decl.h:2808
Represents a prototype with parameter type info, e.g.
Definition: Type.h:4656
QualType desugar() const
Definition: Type.h:5123
Declaration of a template function.
Definition: DeclTemplate.h:957
FunctionType - C99 6.7.5.3 - Function Declarators.
Definition: Type.h:4256
static ArmStateValue getArmZT0State(unsigned AttrBits)
Definition: Type.h:4543
static ArmStateValue getArmZAState(unsigned AttrBits)
Definition: Type.h:4539
QualType getReturnType() const
Definition: Type.h:4573
GlobalDecl - represents a global declaration.
Definition: GlobalDecl.h:56
One of these records is kept for each identifier that is lexed.
unsigned getBuiltinID() const
Return a value indicating whether this is a builtin function.
bool isStr(const char(&Str)[StrLen]) const
Return true if this is the identifier for the specified string.
StringRef getName() const
Return the actual identifier string.
IdentifierInfo & get(StringRef Name)
Return the identifier token info for the specified named identifier.
Describes an entity that is being initialized.
static InitializedEntity InitializeParameter(ASTContext &Context, ParmVarDecl *Parm)
Create the initialization entity for a parameter.
@ IncompleteOnly
Any trailing array member of undefined size is a FAM.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
Definition: LangOptions.h:461
bool isCompatibleWithMSVC(MSVCMajorVersion MajorVersion) const
Definition: LangOptions.h:625
clang::ObjCRuntime ObjCRuntime
Definition: LangOptions.h:496
std::string getOpenCLVersionString() const
Return the OpenCL C or C++ for OpenCL language name and version as a string.
Definition: LangOptions.cpp:79
unsigned getOpenCLCompatibleVersion() const
Return the OpenCL version that kernel language is compatible with.
Definition: LangOptions.cpp:63
void push_back(const T &LocalValue)
Represents the results of name lookup.
Definition: Lookup.h:46
A global _GUID constant.
Definition: DeclCXX.h:4289
Describes a module or submodule.
Definition: Module.h:105
This represents a decl that may have a name.
Definition: Decl.h:249
IdentifierInfo * getIdentifier() const
Get the identifier that names this declaration, if there is one.
Definition: Decl.h:270
bool isCXXInstanceMember() const
Determine whether the given declaration is an instance member of a C++ class.
Definition: Decl.cpp:1959
bool isExternallyVisible() const
Definition: Decl.h:408
A C++ nested-name-specifier augmented with source location information.
Represents an ObjC class declaration.
Definition: DeclObjC.h:1153
void setHasDesignatedInitializers()
Indicate that this interface decl contains at least one initializer marked with the 'objc_designated_...
Definition: DeclObjC.cpp:1595
ObjCMethodDecl - Represents an instance or class method declaration.
Definition: DeclObjC.h:140
Represents a pointer to an Objective C object.
Definition: Type.h:7008
Represents one property declaration in an Objective-C interface.
Definition: DeclObjC.h:730
bool allowsDirectDispatch() const
Does this runtime supports direct dispatch.
Definition: ObjCRuntime.h:467
void * getAsOpaquePtr() const
Definition: Ownership.h:90
static OpaquePtr getFromOpaquePtr(void *P)
Definition: Ownership.h:91
bool isSupported(llvm::StringRef Ext, const LangOptions &LO) const
A single parameter index whose accessors require each use to make explicit the parameter index encodi...
Definition: Attr.h:250
unsigned getSourceIndex() const
Get the parameter index as it would normally be encoded for attributes at the source level of represe...
Definition: Attr.h:318
unsigned getASTIndex() const
Get the parameter index as it would normally be encoded at the AST level of representation: zero-orig...
Definition: Attr.h:329
A parameter attribute which changes the argument-passing ABI rule for the parameter.
Definition: Attr.h:218
Represents a parameter to a function.
Definition: Decl.h:1761
void setScopeInfo(unsigned scopeDepth, unsigned parameterIndex)
Definition: Decl.h:1794
SourceRange getSourceRange() const override LLVM_READONLY
Source range that this declaration covers.
Definition: Decl.cpp:2938
ParsedAttr - Represents a syntactic attribute.
Definition: ParsedAttr.h:129
bool isPackExpansion() const
Definition: ParsedAttr.h:382
const AvailabilityChange & getAvailabilityDeprecated() const
Definition: ParsedAttr.h:416
unsigned getSemanticSpelling() const
If the parsed attribute has a semantic equivalent, and it would have a semantic Spelling enumeration ...
Definition: ParsedAttr.cpp:262
bool existsInTarget(const TargetInfo &Target) const
Definition: ParsedAttr.cpp:201
bool checkExactlyNumArgs(class Sema &S, unsigned Num) const
Check if the attribute has exactly as many args as Num.
Definition: ParsedAttr.cpp:298
IdentifierLoc * getArgAsIdent(unsigned Arg) const
Definition: ParsedAttr.h:406
bool hasParsedType() const
Definition: ParsedAttr.h:352
const AvailabilityChange & getAvailabilityIntroduced() const
Definition: ParsedAttr.h:410
void setInvalid(bool b=true) const
Definition: ParsedAttr.h:360
bool hasVariadicArg() const
Definition: ParsedAttr.cpp:266
const ParsedAttrInfo & getInfo() const
Definition: ParsedAttr.h:630
void handleAttrWithDelayedArgs(Sema &S, Decl *D) const
Definition: ParsedAttr.cpp:278
const Expr * getReplacementExpr() const
Definition: ParsedAttr.h:446
bool hasProcessingCache() const
Definition: ParsedAttr.h:362
SourceLocation getUnavailableLoc() const
Definition: ParsedAttr.h:434
unsigned getProcessingCache() const
Definition: ParsedAttr.h:364
const IdentifierLoc * getEnvironment() const
Definition: ParsedAttr.h:452
bool acceptsExprPack() const
Definition: ParsedAttr.cpp:260
const Expr * getMessageExpr() const
Definition: ParsedAttr.h:440
const ParsedType & getMatchingCType() const
Definition: ParsedAttr.h:458
const ParsedType & getTypeArg() const
Definition: ParsedAttr.h:476
SourceLocation getStrictLoc() const
Definition: ParsedAttr.h:428
bool isTypeAttr() const
Definition: ParsedAttr.cpp:197
unsigned getNumArgs() const
getNumArgs - Return the number of actual arguments to this attribute.
Definition: ParsedAttr.h:386
bool isArgIdent(unsigned Arg) const
Definition: ParsedAttr.h:402
Expr * getArgAsExpr(unsigned Arg) const
Definition: ParsedAttr.h:398
bool getMustBeNull() const
Definition: ParsedAttr.h:470
bool checkAtLeastNumArgs(class Sema &S, unsigned Num) const
Check if the attribute has at least as many args as Num.
Definition: ParsedAttr.cpp:303
bool isUsedAsTypeAttr() const
Definition: ParsedAttr.h:374
unsigned getNumArgMembers() const
Definition: ParsedAttr.cpp:154
bool isStmtAttr() const
Definition: ParsedAttr.cpp:199
bool isPragmaClangAttribute() const
True if the attribute is specified using '#pragma clang attribute'.
Definition: ParsedAttr.h:378
bool slidesFromDeclToDeclSpecLegacyBehavior() const
Returns whether a [[]] attribute, if specified ahead of a declaration, should be applied to the decl-...
Definition: ParsedAttr.cpp:222
AttributeCommonInfo::Kind getKind() const
Definition: ParsedAttr.h:627
void setProcessingCache(unsigned value) const
Definition: ParsedAttr.h:369
bool isParamExpr(size_t N) const
Definition: ParsedAttr.cpp:274
bool isArgExpr(unsigned Arg) const
Definition: ParsedAttr.h:394
bool getLayoutCompatible() const
Definition: ParsedAttr.h:464
ArgsUnion getArg(unsigned Arg) const
getArg - Return the specified argument.
Definition: ParsedAttr.h:389
SourceLocation getEllipsisLoc() const
Definition: ParsedAttr.h:383
bool isInvalid() const
Definition: ParsedAttr.h:359
bool checkAtMostNumArgs(class Sema &S, unsigned Num) const
Check if the attribute has at most as many args as Num.
Definition: ParsedAttr.cpp:308
const AvailabilityChange & getAvailabilityObsoleted() const
Definition: ParsedAttr.h:422
void addAtEnd(ParsedAttr *newAttr)
Definition: ParsedAttr.h:848
PointerType - C99 6.7.5.1 - Pointer Declarators.
Definition: Type.h:3139
QualType getPointeeType() const
Definition: Type.h:3149
IdentifierTable & getIdentifierTable()
A (possibly-)qualified type.
Definition: Type.h:940
QualType withConst() const
Definition: Type.h:1154
QualType getLocalUnqualifiedType() const
Return this type with all of the instance-specific qualifiers removed, but without removing any quali...
Definition: Type.h:1220
bool isNull() const
Return true if this QualType doesn't point to a type yet.
Definition: Type.h:1007
const Type * getTypePtr() const
Retrieves a pointer to the underlying (unqualified) type.
Definition: Type.h:7359
LangAS getAddressSpace() const
Return the address space of this type.
Definition: Type.h:7485
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
Definition: Type.h:7399
Qualifiers::ObjCLifetime getObjCLifetime() const
Returns lifetime attribute of this type.
Definition: Type.h:1432
QualType getCanonicalType() const
Definition: Type.h:7411
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
Definition: Type.h:7453
bool isConstQualified() const
Determine whether this type is const-qualified.
Definition: Type.h:7432
const Type * getTypePtrOrNull() const
Definition: Type.h:7363
@ OCL_Strong
Assigning into this object requires the old value to be released and the new value to be retained.
Definition: Type.h:347
@ OCL_ExplicitNone
This object can be modified without requiring retains or releases.
Definition: Type.h:340
@ OCL_None
There is no lifetime qualification on this type.
Definition: Type.h:336
@ OCL_Weak
Reading or writing from this object requires a barrier call.
Definition: Type.h:350
@ OCL_Autoreleasing
Assigning into this object requires a lifetime extension.
Definition: Type.h:353
ObjCLifetime getObjCLifetime() const
Definition: Type.h:531
bool empty() const
Definition: Type.h:633
Represents a struct/union/class.
Definition: Decl.h:4168
field_iterator field_end() const
Definition: Decl.h:4377
field_range fields() const
Definition: Decl.h:4374
field_iterator field_begin() const
Definition: Decl.cpp:5069
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
Definition: Type.h:5549
RecordDecl * getDecl() const
Definition: Type.h:5559
A class that does preorder or postorder depth-first traversal on the entire Clang AST and visits each...
Base for LValueReferenceType and RValueReferenceType.
Definition: Type.h:3380
Scope - A scope is a transient data structure that is used while parsing the program.
Definition: Scope.h:41
unsigned getFlags() const
getFlags - Return the flags for this scope.
Definition: Scope.h:262
@ FunctionDeclarationScope
This is a scope that corresponds to the parameters within a function prototype for a function declara...
Definition: Scope.h:91
A generic diagnostic builder for errors which may or may not be deferred.
Definition: SemaBase.h:110
SemaDiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID, bool DeferHint=false)
Emit a diagnostic.
Definition: SemaBase.cpp:56
CUDAFunctionTarget IdentifyTarget(const FunctionDecl *D, bool IgnoreImplicitHDAttr=false)
Determines whether the given function is a CUDA device/host/kernel/etc.
Definition: SemaCUDA.cpp:136
CUDAFunctionTarget CurrentTarget()
Gets the CUDA target for the current context.
Definition: SemaCUDA.h:142
SemaDiagnosticBuilder DiagIfHostCode(SourceLocation Loc, unsigned DiagID)
Creates a SemaDiagnosticBuilder that emits the diagnostic if the current context is "used as host cod...
Definition: SemaCUDA.cpp:851
HLSLNumThreadsAttr * mergeNumThreadsAttr(Decl *D, const AttributeCommonInfo &AL, int X, int Y, int Z)
Definition: SemaHLSL.cpp:128
HLSLShaderAttr * mergeShaderAttr(Decl *D, const AttributeCommonInfo &AL, HLSLShaderAttr::ShaderType ShaderType)
Definition: SemaHLSL.cpp:143
HLSLParamModifierAttr * mergeParamModifierAttr(Decl *D, const AttributeCommonInfo &AL, HLSLParamModifierAttr::Spelling Spelling)
Definition: SemaHLSL.cpp:156
bool isCFError(RecordDecl *D)
Definition: SemaObjC.cpp:1461
IdentifierInfo * getNSErrorIdent()
Retrieve the identifier "NSError".
Definition: SemaObjC.cpp:1265
A class which encapsulates the logic for delaying diagnostics during parsing and other processing.
Definition: Sema.h:927
sema::DelayedDiagnosticPool * getCurrentPool() const
Returns the current delayed-diagnostics pool.
Definition: Sema.h:942
void popWithoutEmitting(DelayedDiagnosticsState state)
Leave a delayed-diagnostic state that was previously pushed.
Definition: Sema.h:956
Sema - This implements semantic analysis and AST building for C.
Definition: Sema.h:451
bool ConstantFoldAttrArgs(const AttributeCommonInfo &CI, MutableArrayRef< Expr * > Args)
ConstantFoldAttrArgs - Folds attribute arguments into ConstantExprs (unless they are value dependent ...
Definition: SemaAttr.cpp:400
BTFDeclTagAttr * mergeBTFDeclTagAttr(Decl *D, const BTFDeclTagAttr &AL)
void LoadExternalWeakUndeclaredIdentifiers()
Load weak undeclared identifiers from the external source.
Definition: Sema.cpp:939
@ LookupOrdinaryName
Ordinary name lookup, which finds ordinary names (functions, variables, typedefs, etc....
Definition: Sema.h:7289
EnforceTCBAttr * mergeEnforceTCBAttr(Decl *D, const EnforceTCBAttr &AL)
bool checkTargetVersionAttr(SourceLocation LiteralLoc, Decl *D, StringRef &Str, bool &isDefault)
bool isValidPointerAttrType(QualType T, bool RefOkay=false)
Determine if type T is a valid subject for a nonnull and similar attributes.
RetainOwnershipKind
Definition: Sema.h:3675
TypeVisibilityAttr * mergeTypeVisibilityAttr(Decl *D, const AttributeCommonInfo &CI, TypeVisibilityAttr::VisibilityType Vis)
void AddAlignedAttr(Decl *D, const AttributeCommonInfo &CI, Expr *E, bool IsPackExpansion)
AddAlignedAttr - Adds an aligned attribute to a particular declaration.
void AddAssumeAlignedAttr(Decl *D, const AttributeCommonInfo &CI, Expr *E, Expr *OE)
AddAssumeAlignedAttr - Adds an assume_aligned attribute to a particular declaration.
bool checkSectionName(SourceLocation LiteralLoc, StringRef Str)
void AddPragmaAttributes(Scope *S, Decl *D)
Adds the attributes that have been specified using the '#pragma clang attribute push' directives to t...
Definition: SemaAttr.cpp:1093
SemaCUDA & CUDA()
Definition: Sema.h:993
bool checkCommonAttributeFeatures(const Decl *D, const ParsedAttr &A, bool SkipArgCountCheck=false)
Handles semantic checking for features that are common to all attributes, such as checking whether a ...
Definition: SemaAttr.cpp:1454
void addAMDGPUWavesPerEUAttr(Decl *D, const AttributeCommonInfo &CI, Expr *Min, Expr *Max)
addAMDGPUWavePersEUAttr - Adds an amdgpu_waves_per_eu attribute to a particular declaration.
WebAssemblyImportNameAttr * mergeImportNameAttr(Decl *D, const WebAssemblyImportNameAttr &AL)
void addAMDGPUMaxNumWorkGroupsAttr(Decl *D, const AttributeCommonInfo &CI, Expr *XExpr, Expr *YExpr, Expr *ZExpr)
addAMDGPUMaxNumWorkGroupsAttr - Adds an amdgpu_max_num_work_groups attribute to a particular declarat...
Scope * getScopeForContext(DeclContext *Ctx)
Determines the active Scope associated with the given declaration context.
Definition: Sema.cpp:2113
bool ProcessAccessDeclAttributeList(AccessSpecDecl *ASDecl, const ParsedAttributesView &AttrList)
AMDGPUFlatWorkGroupSizeAttr * CreateAMDGPUFlatWorkGroupSizeAttr(const AttributeCommonInfo &CI, Expr *Min, Expr *Max)
Create an AMDGPUWavesPerEUAttr attribute.
DLLImportAttr * mergeDLLImportAttr(Decl *D, const AttributeCommonInfo &CI)
ExtVectorDeclsType ExtVectorDecls
ExtVectorDecls - This is a list all the extended vector types.
Definition: Sema.h:3556
ExprResult VerifyIntegerConstantExpression(Expr *E, llvm::APSInt *Result, VerifyICEDiagnoser &Diagnoser, AllowFoldKind CanFold=NoFold)
VerifyIntegerConstantExpression - Verifies that an expression is an ICE, and reports the appropriate ...
Definition: SemaExpr.cpp:17081
void PopParsingDeclaration(ParsingDeclState state, Decl *decl)
ErrorAttr * mergeErrorAttr(Decl *D, const AttributeCommonInfo &CI, StringRef NewUserDiagnostic)
void redelayDiagnostics(sema::DelayedDiagnosticPool &pool)
Given a set of delayed diagnostics, re-emit them as if they had been delayed in the current context i...
VisibilityAttr * mergeVisibilityAttr(Decl *D, const AttributeCommonInfo &CI, VisibilityAttr::VisibilityType Vis)
ParmVarDecl * BuildParmVarDeclForTypedef(DeclContext *DC, SourceLocation Loc, QualType T)
Synthesizes a variable for a parameter arising from a typedef.
Definition: SemaDecl.cpp:15217
ASTContext & Context
Definition: Sema.h:848
AMDGPUWavesPerEUAttr * CreateAMDGPUWavesPerEUAttr(const AttributeCommonInfo &CI, Expr *Min, Expr *Max)
Create an AMDGPUWavesPerEUAttr attribute.
SemaObjC & ObjC()
Definition: Sema.h:1003
void PushOnScopeChains(NamedDecl *D, Scope *S, bool AddToContext=true)
Add this decl to the scope shadowed decl chains.
Definition: SemaDecl.cpp:1523
ASTContext & getASTContext() const
Definition: Sema.h:517
@ None
This is not a defaultable comparison operator.
bool CheckCallingConvAttr(const ParsedAttr &attr, CallingConv &CC, const FunctionDecl *FD=nullptr, CUDAFunctionTarget CFT=CUDAFunctionTarget::InvalidTarget)
Check validaty of calling convention attribute attr.
FunctionDecl * ResolveSingleFunctionTemplateSpecialization(OverloadExpr *ovl, bool Complain=false, DeclAccessPair *Found=nullptr, TemplateSpecCandidateSet *FailedTSC=nullptr)
Given an expression that refers to an overloaded function, try to resolve that overloaded function ex...
void ProcessPragmaWeak(Scope *S, Decl *D)
void AddXConsumedAttr(Decl *D, const AttributeCommonInfo &CI, RetainOwnershipKind K, bool IsTemplateInstantiation)
bool CheckAttrNoArgs(const ParsedAttr &CurrAttr)
bool UnifySection(StringRef SectionName, int SectionFlags, NamedDecl *TheDecl)
Definition: SemaAttr.cpp:693
FPOptions & getCurFPFeatures()
Definition: Sema.h:512
SourceLocation getLocForEndOfToken(SourceLocation Loc, unsigned Offset=0)
Calls Lexer::getLocForEndOfToken()
Definition: Sema.cpp:65
@ UPPC_Expression
An arbitrary expression.
Definition: Sema.h:10709
const LangOptions & getLangOpts() const
Definition: Sema.h:510
void AddModeAttr(Decl *D, const AttributeCommonInfo &CI, IdentifierInfo *Name, bool InInstantiation=false)
AddModeAttr - Adds a mode attribute to a particular declaration.
bool checkNSReturnsRetainedReturnType(SourceLocation loc, QualType type)
Preprocessor & PP
Definition: Sema.h:847
bool DiagnoseUnexpandedParameterPack(SourceLocation Loc, TypeSourceInfo *T, UnexpandedParameterPackContext UPPC)
If the given type contains an unexpanded parameter pack, diagnose the error.
MinSizeAttr * mergeMinSizeAttr(Decl *D, const AttributeCommonInfo &CI)
const LangOptions & LangOpts
Definition: Sema.h:846
static const uint64_t MaximumAlignment
Definition: Sema.h:788
SemaHLSL & HLSL()
Definition: Sema.h:998
AlwaysInlineAttr * mergeAlwaysInlineAttr(Decl *D, const AttributeCommonInfo &CI, const IdentifierInfo *Ident)
void ProcessDeclAttributeList(Scope *S, Decl *D, const ParsedAttributesView &AttrList, const ProcessDeclAttributeOptions &Options=ProcessDeclAttributeOptions())
ProcessDeclAttributeList - Apply all the decl attributes in the specified attribute list to the speci...
WebAssemblyImportModuleAttr * mergeImportModuleAttr(Decl *D, const WebAssemblyImportModuleAttr &AL)
NamedDecl * getCurFunctionOrMethodDecl() const
getCurFunctionOrMethodDecl - Return the Decl for the current ObjC method or C function we're in,...
Definition: Sema.cpp:1511
void AddAllocAlignAttr(Decl *D, const AttributeCommonInfo &CI, Expr *ParamExpr)
AddAllocAlignAttr - Adds an alloc_align attribute to a particular declaration.
bool CheckRegparmAttr(const ParsedAttr &attr, unsigned &value)
Checks a regparm attribute, returning true if it is ill-formed and otherwise setting numParams to the...
void AddAnnotationAttr(Decl *D, const AttributeCommonInfo &CI, StringRef Annot, MutableArrayRef< Expr * > Args)
AddAnnotationAttr - Adds an annotation Annot with Args arguments to D.
void ProcessDeclAttributeDelayed(Decl *D, const ParsedAttributesView &AttrList)
MSInheritanceAttr * mergeMSInheritanceAttr(Decl *D, const AttributeCommonInfo &CI, bool BestCase, MSInheritanceModel Model)
InternalLinkageAttr * mergeInternalLinkageAttr(Decl *D, const ParsedAttr &AL)
DeclContext * CurContext
CurContext - This is the current declaration context of parsing.
Definition: Sema.h:986
ExprResult PerformContextuallyConvertToBool(Expr *From)
PerformContextuallyConvertToBool - Perform a contextual conversion of the expression From to bool (C+...
@ Compatible
Compatible - the types are compatible according to the standard.
Definition: Sema.h:6022
NamedDecl * DeclClonePragmaWeak(NamedDecl *ND, const IdentifierInfo *II, SourceLocation Loc)
DeclClonePragmaWeak - clone existing decl (maybe definition), #pragma weak needs a non-definition dec...
DLLExportAttr * mergeDLLExportAttr(Decl *D, const AttributeCommonInfo &CI)
AMDGPUMaxNumWorkGroupsAttr * CreateAMDGPUMaxNumWorkGroupsAttr(const AttributeCommonInfo &CI, Expr *XExpr, Expr *YExpr, Expr *ZExpr)
Create an AMDGPUMaxNumWorkGroupsAttr attribute.
CodeSegAttr * mergeCodeSegAttr(Decl *D, const AttributeCommonInfo &CI, StringRef Name)
SectionAttr * mergeSectionAttr(Decl *D, const AttributeCommonInfo &CI, StringRef Name)
bool inTemplateInstantiation() const
Determine whether we are currently performing template instantiation.
Definition: Sema.h:10402
SourceManager & getSourceManager() const
Definition: Sema.h:515
bool checkTargetAttr(SourceLocation LiteralLoc, StringRef Str)
llvm::Error isValidSectionSpecifier(StringRef Str)
Used to implement to perform semantic checking on attribute((section("foo"))) specifiers.
void AddLaunchBoundsAttr(Decl *D, const AttributeCommonInfo &CI, Expr *MaxThreads, Expr *MinBlocks, Expr *MaxBlocks)
AddLaunchBoundsAttr - Adds a launch_bounds attribute to a particular declaration.
OptimizeNoneAttr * mergeOptimizeNoneAttr(Decl *D, const AttributeCommonInfo &CI)
void checkUnusedDeclAttributes(Declarator &D)
checkUnusedDeclAttributes - Given a declarator which is not being used to build a declaration,...
bool CheckAttrTarget(const ParsedAttr &CurrAttr)
EnforceTCBLeafAttr * mergeEnforceTCBLeafAttr(Decl *D, const EnforceTCBLeafAttr &AL)
ParsedType getTypeName(const IdentifierInfo &II, SourceLocation NameLoc, Scope *S, CXXScopeSpec *SS=nullptr, bool isClassName=false, bool HasTrailingDot=false, ParsedType ObjectType=nullptr, bool IsCtorOrDtorName=false, bool WantNontrivialTypeSourceInfo=false, bool IsClassTemplateDeductionContext=true, ImplicitTypenameContext AllowImplicitTypename=ImplicitTypenameContext::No, IdentifierInfo **CorrectedII=nullptr)
If the identifier refers to a type name within this scope, return the declaration of that type.
Definition: SemaDecl.cpp:291
ASTConsumer & Consumer
Definition: Sema.h:849
void NoteAllOverloadCandidates(Expr *E, QualType DestType=QualType(), bool TakingAddress=false)
FormatAttr * mergeFormatAttr(Decl *D, const AttributeCommonInfo &CI, IdentifierInfo *Format, int FormatIdx, int FirstArg)
@ AP_PragmaClangAttribute
The availability attribute was applied using '#pragma clang attribute'.
Definition: Sema.h:3523
@ AP_InferredFromOtherPlatform
The availability attribute for a specific platform was inferred from an availability attribute for an...
Definition: Sema.h:3527
@ AP_Explicit
The availability attribute was specified explicitly next to the declaration.
Definition: Sema.h:3520
AvailabilityMergeKind
Describes the kind of merge to perform for availability attributes (including "deprecated",...
Definition: Sema.h:3317
@ AMK_None
Don't merge availability attributes at all.
Definition: Sema.h:3319
@ AMK_Override
Merge availability attributes for an override, which requires an exact match or a weakening of constr...
Definition: Sema.h:3325
@ AMK_ProtocolImplementation
Merge availability attributes for an implementation of a protocol requirement.
Definition: Sema.h:3328
@ AMK_OptionalProtocolImplementation
Merge availability attributes for an implementation of an optional protocol requirement.
Definition: Sema.h:3331
@ AMK_Redeclaration
Merge availability attributes for a redeclaration, which requires an exact match.
Definition: Sema.h:3322
SmallVector< Decl *, 2 > WeakTopLevelDecl
WeakTopLevelDecl - Translation-unit scoped declarations generated by #pragma weak during processing o...
Definition: Sema.h:3544
bool RequireCompleteType(SourceLocation Loc, QualType T, CompleteTypeKind Kind, TypeDiagnoser &Diagnoser)
Ensure that the type T is a complete type.
Definition: SemaType.cpp:8831
Scope * TUScope
Translation Unit Scope - useful to Objective-C actions that need to lookup file scope declarations in...
Definition: Sema.h:820
UuidAttr * mergeUuidAttr(Decl *D, const AttributeCommonInfo &CI, StringRef UuidAsWritten, MSGuidDecl *GuidDecl)
void addAMDGPUFlatWorkGroupSizeAttr(Decl *D, const AttributeCommonInfo &CI, Expr *Min, Expr *Max)
addAMDGPUFlatWorkGroupSizeAttr - Adds an amdgpu_flat_work_group_size attribute to a particular declar...
OpenCLOptions & getOpenCLOptions()
Definition: Sema.h:511
void AddParameterABIAttr(Decl *D, const AttributeCommonInfo &CI, ParameterABI ABI)
ExprResult PerformCopyInitialization(const InitializedEntity &Entity, SourceLocation EqualLoc, ExprResult Init, bool TopLevelOfInitList=false, bool AllowExplicit=false)
Definition: SemaInit.cpp:10684
bool checkTargetClonesAttrString(SourceLocation LiteralLoc, StringRef Str, const StringLiteral *Literal, Decl *D, bool &HasDefault, bool &HasCommas, bool &HasNotDefault, SmallVectorImpl< SmallString< 64 > > &StringsBuffer)
void handleDelayedAvailabilityCheck(sema::DelayedDiagnostic &DD, Decl *Ctx)
void ProcessDeclAttributes(Scope *S, Decl *D, const Declarator &PD)
ProcessDeclAttributes - Given a declarator (PD) with attributes indicated in it, apply them to D.
void DeclApplyPragmaWeak(Scope *S, NamedDecl *ND, const WeakInfo &W)
DeclApplyPragmaWeak - A declaration (maybe definition) needs #pragma weak applied to it,...
AvailabilityAttr * mergeAvailabilityAttr(NamedDecl *D, const AttributeCommonInfo &CI, IdentifierInfo *Platform, bool Implicit, VersionTuple Introduced, VersionTuple Deprecated, VersionTuple Obsoleted, bool IsUnavailable, StringRef Message, bool IsStrict, StringRef Replacement, AvailabilityMergeKind AMK, int Priority, IdentifierInfo *IIEnvironment)
bool DiagnoseSwiftName(Decl *D, StringRef Name, SourceLocation Loc, const ParsedAttr &AL, bool IsAsync)
Do a check to make sure Name looks like a legal argument for the swift_name attribute applied to decl...
llvm::MapVector< IdentifierInfo *, llvm::SetVector< WeakInfo, llvm::SmallVector< WeakInfo, 1u >, llvm::SmallDenseSet< WeakInfo, 2u, WeakInfo::DenseMapInfoByAliasOnly > > > WeakUndeclaredIdentifiers
WeakUndeclaredIdentifiers - Identifiers contained in #pragma weak before declared.
Definition: Sema.h:2595
void ProcessAPINotes(Decl *D)
Map any API notes provided for this declaration to attributes on the declaration.
void CheckAlignasUnderalignment(Decl *D)
void HandleDelayedAccessCheck(sema::DelayedDiagnostic &DD, Decl *Ctx)
DarwinSDKInfo * getDarwinSDKInfoForAvailabilityChecking(SourceLocation Loc, StringRef Platform)
Definition: Sema.cpp:72
AssignConvertType CheckAssignmentConstraints(SourceLocation Loc, QualType LHSType, QualType RHSType)
CheckAssignmentConstraints - Perform type checking for assignment, argument passing,...
Definition: SemaExpr.cpp:9251
SwiftNameAttr * mergeSwiftNameAttr(Decl *D, const SwiftNameAttr &SNA, StringRef Name)
CUDALaunchBoundsAttr * CreateLaunchBoundsAttr(const AttributeCommonInfo &CI, Expr *MaxThreads, Expr *MinBlocks, Expr *MaxBlocks)
Create an CUDALaunchBoundsAttr attribute.
bool LookupName(LookupResult &R, Scope *S, bool AllowBuiltinCreation=false, bool ForceNoCPlusPlus=false)
Perform unqualified name lookup starting from a given scope.
static QualType GetTypeFromParser(ParsedType Ty, TypeSourceInfo **TInfo=nullptr)
Definition: SemaType.cpp:2805
void AddAlignValueAttr(Decl *D, const AttributeCommonInfo &CI, Expr *E)
AddAlignValueAttr - Adds an align_value attribute to a particular declaration.
QualType BuildCountAttributedArrayType(QualType WrappedTy, Expr *CountExpr)
Definition: SemaType.cpp:9348
bool checkMSInheritanceAttrOnDefinition(CXXRecordDecl *RD, SourceRange Range, bool BestCase, MSInheritanceModel SemanticSpelling)
bool checkStringLiteralArgumentAttr(const AttributeCommonInfo &CI, const Expr *E, StringRef &Str, SourceLocation *ArgLocation=nullptr)
Check if the argument E is a ASCII string literal.
bool CheckFunctionCall(FunctionDecl *FDecl, CallExpr *TheCall, const FunctionProtoType *Proto)
CheckFunctionCall - Check a direct function call for various correctness and safety properties not st...
ASTMutationListener * getASTMutationListener() const
Definition: Sema.cpp:550
Encodes a location in the source.
bool isValid() const
Return true if this is a valid SourceLocation object.
bool isInSystemMacro(SourceLocation loc) const
Returns whether Loc is expanded from a macro in a system header.
bool isInSystemHeader(SourceLocation Loc) const
Returns if a SourceLocation is in a system header.
A trivial tuple used to represent a source range.
SourceLocation getBegin() const
bool isValid() const
SourceRange getSourceRange() const LLVM_READONLY
SourceLocation tokens are not useful in isolation - they are low level value objects created/interpre...
Definition: Stmt.cpp:326
SourceLocation getBeginLoc() const LLVM_READONLY
Definition: Stmt.cpp:338
StringLiteral - This represents a string literal expression, e.g.
Definition: Expr.h:1773
bool isBeingDefined() const
Return true if this decl is currently being defined.
Definition: Decl.h:3707
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
Definition: Decl.h:3687
bool isUnion() const
Definition: Decl.h:3790
TagKind getTagKind() const
Definition: Decl.h:3779
Exposes information about the current target.
Definition: TargetInfo.h:218
TargetOptions & getTargetOpts() const
Retrieve the target options.
Definition: TargetInfo.h:312
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
Definition: TargetInfo.h:1256
uint64_t getPointerWidth(LangAS AddrSpace) const
Return the width of pointers on this target, for the specified address space.
Definition: TargetInfo.h:472
virtual CallingConvCheckResult checkCallingConvention(CallingConv CC) const
Determines whether a given calling convention is valid for the target.
Definition: TargetInfo.h:1679
bool isTLSSupported() const
Whether the target supports thread-local storage.
Definition: TargetInfo.h:1561
unsigned getMaxTLSAlign() const
Return the maximum alignment (in bits) of a TLS variable.
Definition: TargetInfo.h:1569
virtual unsigned getRegisterWidth() const
Return the "preferred" register width on this target.
Definition: TargetInfo.h:879
virtual bool validateCpuSupports(StringRef Name) const
Definition: TargetInfo.h:1504
virtual bool doesFeatureAffectCodeGen(StringRef Feature) const
Returns true if feature has an impact on target code generation.
Definition: TargetInfo.h:1399
virtual bool validateCPUSpecificCPUDispatch(StringRef Name) const
Definition: TargetInfo.h:1522
virtual bool hasProtectedVisibility() const
Does this target support "protected" visibility?
Definition: TargetInfo.h:1290
unsigned getRegParmMax() const
Definition: TargetInfo.h:1555
virtual unsigned getUnwindWordWidth() const
Definition: TargetInfo.h:874
virtual bool isValidFeatureName(StringRef Feature) const
Determine whether this TargetInfo supports the given feature.
Definition: TargetInfo.h:1393
unsigned getCharWidth() const
Definition: TargetInfo.h:496
virtual ParsedTargetAttr parseTargetAttr(StringRef Str) const
Definition: TargetInfo.cpp:548
virtual bool supportsTargetAttributeTune() const
Determine whether this TargetInfo supports tune in target attribute.
Definition: TargetInfo.h:1360
virtual bool shouldDLLImportComdatSymbols() const
Does this target aim for semantic compatibility with Microsoft C++ code using dllimport/export attrib...
Definition: TargetInfo.h:1294
virtual bool hasFeature(StringRef Feature) const
Determine whether the given target has the given feature.
Definition: TargetInfo.h:1472
virtual bool isValidCPUName(StringRef Name) const
Determine whether this TargetInfo supports the given CPU name.
Definition: TargetInfo.h:1347
const llvm::VersionTuple & getSDKVersion() const
Definition: TargetInfo.h:1780
virtual bool validateBranchProtection(StringRef Spec, StringRef Arch, BranchProtectionInfo &BPI, StringRef &Err) const
Determine if this TargetInfo supports the given branch protection specification.
Definition: TargetInfo.h:1448
The base class of all kinds of template declarations (e.g., class, function, etc.).
Definition: DeclTemplate.h:394
TemplateParameterList * getTemplateParameters() const
Get the list of template parameters.
Definition: DeclTemplate.h:413
Stores a list of template parameters for a TemplateDecl and its derived classes.
Definition: DeclTemplate.h:73
NamedDecl * getParam(unsigned Idx)
Definition: DeclTemplate.h:144
Represents a type template specialization; the template must be a class template, a type alias templa...
Definition: Type.h:6089
[BoundsSafety] Represents information of declarations referenced by the arguments of the counted_by a...
Definition: Type.h:3167
const Type * getTypeForDecl() const
Definition: Decl.h:3414
SourceRange getSourceRange() const LLVM_READONLY
Get the full source range.
Definition: TypeLoc.h:153
SourceLocation getBeginLoc() const
Get the begin source location.
Definition: TypeLoc.cpp:192
A container of type source information.
Definition: Type.h:7330
TypeLoc getTypeLoc() const
Return the TypeLoc wrapper for the type source info.
Definition: TypeLoc.h:256
QualType getType() const
Return the type wrapped by this type source info.
Definition: Type.h:7341
The base class of the type hierarchy.
Definition: Type.h:1813
bool isSizelessType() const
As an extension, we classify types as one of "sized" or "sizeless"; every type is one or the other.
Definition: Type.cpp:2455
bool isStructureType() const
Definition: Type.cpp:629
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
Definition: Type.cpp:1871
bool isBlockPointerType() const
Definition: Type.h:7620
bool isVoidType() const
Definition: Type.h:7905
bool isBooleanType() const
Definition: Type.h:8033
const RecordType * getAsUnionType() const
NOTE: getAs*ArrayType are methods on ASTContext.
Definition: Type.cpp:730
bool isSignedIntegerType() const
Return true if this is an integer type that is signed, according to C99 6.2.5p4 [char,...
Definition: Type.cpp:2135
bool isComplexType() const
isComplexType() does not include complex integers (a GCC extension).
Definition: Type.cpp:667
bool isVoidPointerType() const
Definition: Type.cpp:655
bool isArrayType() const
Definition: Type.h:7678
bool isCharType() const
Definition: Type.cpp:2078
bool isFunctionPointerType() const
Definition: Type.h:7646
bool isPointerType() const
Definition: Type.h:7612
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
Definition: Type.h:7945
const T * castAs() const
Member-template castAs<specific type>.
Definition: Type.h:8193
bool isReferenceType() const
Definition: Type.h:7624
bool isObjCNSObjectType() const
Definition: Type.cpp:4866
const CXXRecordDecl * getPointeeCXXRecordDecl() const
If this is a pointer or reference to a RecordType, return the CXXRecordDecl that the type refers to.
Definition: Type.cpp:1856
bool isIntegralType(const ASTContext &Ctx) const
Determine whether this type is an integral type.
Definition: Type.cpp:2047
bool isAlignValT() const
Definition: Type.cpp:3071
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
Definition: Type.cpp:695
bool isIntegralOrEnumerationType() const
Determine whether this type is an integral or enumeration type.
Definition: Type.h:8020
bool hasUnsignedIntegerRepresentation() const
Determine whether this type has an unsigned integer representation of some sort, e....
Definition: Type.cpp:2225
bool isExtVectorType() const
Definition: Type.h:7722
bool isInstantiationDependentType() const
Determine whether this type is an instantiation-dependent type, meaning that the type involves a temp...
Definition: Type.h:2661
bool isBitIntType() const
Definition: Type.h:7840
bool isBuiltinType() const
Helper methods to distinguish type categories.
Definition: Type.h:7702
bool isDependentType() const
Whether this type is a dependent type, meaning that its definition somehow depends on a template para...
Definition: Type.h:2653
bool isCARCBridgableType() const
Determine whether the given type T is a "bridgeable" C type.
Definition: Type.cpp:4912
bool containsUnexpandedParameterPack() const
Whether this type is or contains an unexpanded parameter pack, used to support C++0x variadic templat...
Definition: Type.h:2320
bool isMemberPointerType() const
Definition: Type.h:7660
bool isObjCIdType() const
Definition: Type.h:7777
bool isObjCObjectType() const
Definition: Type.h:7748
bool isObjCLifetimeType() const
Returns true if objects of this type have lifetime semantics under ARC.
Definition: Type.cpp:4898
Qualifiers::ObjCLifetime getObjCARCImplicitLifetime() const
Return the implicit lifetime for this type, which must not be dependent.
Definition: Type.cpp:4841
bool isIncompleteType(NamedDecl **Def=nullptr) const
Types are partitioned into 3 broad categories (C99 6.2.5p1): object types, function types,...
Definition: Type.cpp:2351
bool isObjCObjectPointerType() const
Definition: Type.h:7744
Visibility getVisibility() const
Determine the visibility of this type.
Definition: Type.h:2882
bool hasFloatingRepresentation() const
Determine whether this type has a floating-point representation of some sort, e.g....
Definition: Type.cpp:2247
bool isVectorType() const
Definition: Type.h:7718
bool isFloatingType() const
Definition: Type.cpp:2238
bool isAnyPointerType() const
Definition: Type.h:7616
const T * getAs() const
Member-template getAs<specific type>'.
Definition: Type.h:8126
const Type * getUnqualifiedDesugaredType() const
Return the specified type with any "sugar" removed from the type, removing any typedefs,...
Definition: Type.cpp:605
bool isObjCRetainableType() const
Definition: Type.cpp:4878
bool isTypedefNameType() const
Determines whether this type is written as a typedef-name.
Definition: Type.h:8054
bool hasPointerRepresentation() const
Whether this type is represented natively as a pointer.
Definition: Type.h:8067
Base class for declarations which introduce a typedef-name.
Definition: Decl.h:3432
static UnaryOperator * Create(const ASTContext &C, Expr *input, Opcode opc, QualType type, ExprValueKind VK, ExprObjectKind OK, SourceLocation l, bool CanOverflow, FPOptionsOverride FPFeatures)
Definition: Expr.cpp:4843
Represents a dependent using declaration which was marked with typename.
Definition: DeclCXX.h:3959
Represents a dependent using declaration which was not marked with typename.
Definition: DeclCXX.h:3862
Represents a C++ using-declaration.
Definition: DeclCXX.h:3512
Represent the declaration of a variable (in which case it is an lvalue) a function (in which case it ...
Definition: Decl.h:706
void setType(QualType newType)
Definition: Decl.h:718
QualType getType() const
Definition: Decl.h:717
Represents a variable declaration or definition.
Definition: Decl.h:918
static VarDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, const IdentifierInfo *Id, QualType T, TypeSourceInfo *TInfo, StorageClass S)
Definition: Decl.cpp:2148
void setARCPseudoStrong(bool PS)
Definition: Decl.h:1528
@ TLS_None
Not a TLS variable.
Definition: Decl.h:938
Represents a GCC generic vector type.
Definition: Type.h:3969
Captures information about a #pragma weak directive.
Definition: Weak.h:25
const IdentifierInfo * getAlias() const
Definition: Weak.h:32
SourceLocation getLocation() const
Definition: Weak.h:33
A collection of diagnostics which were delayed.
const DelayedDiagnosticPool * getParent() const
void steal(DelayedDiagnosticPool &pool)
Steal the diagnostics from the given pool.
SmallVectorImpl< DelayedDiagnostic >::const_iterator pool_iterator
A diagnostic message which has been conditionally emitted pending the complete parsing of the current...
QualType getForbiddenTypeOperand() const
unsigned getForbiddenTypeDiagnostic() const
The diagnostic ID to emit.
unsigned getForbiddenTypeArgument() const
Defines the clang::TargetInfo interface.
#define UINT_MAX
Definition: limits.h:64
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
const internal::VariadicAllOfMatcher< Decl > decl
Matches declarations.
The JSON file list parser is used to communicate input to InstallAPI.
OverloadedOperatorKind
Enumeration specifying the different kinds of C++ overloaded operators.
Definition: OperatorKinds.h:21
bool isa(CodeGen::Address addr)
Definition: Address.h:294
AttributeDeclKind
These constants match the enumerated choices of warn_attribute_wrong_decl_type and err_attribute_wron...
Definition: ParsedAttr.h:1090
@ ExpectedFunctionMethodOrParameter
Definition: ParsedAttr.h:1096
@ ExpectedFunctionWithProtoType
Definition: ParsedAttr.h:1103
@ ExpectedFunctionMethodOrBlock
Definition: ParsedAttr.h:1095
@ ExpectedTypeOrNamespace
Definition: ParsedAttr.h:1100
@ ExpectedVariableFieldOrTag
Definition: ParsedAttr.h:1099
@ ExpectedVariableOrField
Definition: ParsedAttr.h:1098
@ ExpectedUnion
Definition: ParsedAttr.h:1092
@ ExpectedFunctionOrMethod
Definition: ParsedAttr.h:1094
@ ExpectedVariable
Definition: ParsedAttr.h:1097
@ ExpectedVariableOrFunction
Definition: ParsedAttr.h:1093
@ ExpectedKernelFunction
Definition: ParsedAttr.h:1102
@ ExpectedFunctionVariableOrClass
Definition: ParsedAttr.h:1101
@ ExpectedFunction
Definition: ParsedAttr.h:1091
CudaArch
Definition: Cuda.h:54
llvm::StringRef getParameterABISpelling(ParameterABI kind)
CUDAFunctionTarget
Definition: Cuda.h:132
@ OK_Ordinary
An ordinary object is located at an address in memory.
Definition: Specifiers.h:148
CudaVersion ToCudaVersion(llvm::VersionTuple)
Definition: Cuda.cpp:66
LLVM_READONLY bool isValidAsciiIdentifier(StringRef S, bool AllowDollar=false)
Return true if this is a valid ASCII identifier.
Definition: CharInfo.h:244
CudaArch StringToCudaArch(llvm::StringRef S)
Definition: Cuda.cpp:169
@ SC_Extern
Definition: Specifiers.h:248
@ SC_Register
Definition: Specifiers.h:254
@ SC_None
Definition: Specifiers.h:247
@ TSCS_unspecified
Definition: Specifiers.h:233
@ Internal
Internal linkage, which indicates that the entity can be referred to from within the translation unit...
Language
The language for the input, used to select and validate the language standard and possible actions.
Definition: LangStandard.h:23
AttributeArgumentNType
These constants match the enumerated choices of err_attribute_argument_n_type and err_attribute_argum...
Definition: ParsedAttr.h:1079
@ AANT_ArgumentIntegerConstant
Definition: ParsedAttr.h:1081
@ AANT_ArgumentBuiltinFunction
Definition: ParsedAttr.h:1085
@ AANT_ArgumentIntOrBool
Definition: ParsedAttr.h:1080
@ AANT_ArgumentIdentifier
Definition: ParsedAttr.h:1083
@ AANT_ArgumentString
Definition: ParsedAttr.h:1082
@ SD_Automatic
Automatic storage duration (most local variables).
Definition: Specifiers.h:326
@ Property
The type of a property.
@ Result
The result type of a method or function.
ParameterABI
Kinds of parameter ABI.
Definition: Specifiers.h:363
@ SwiftAsyncContext
This parameter (which must have pointer type) uses the special Swift asynchronous context-pointer ABI...
@ SwiftErrorResult
This parameter (which must have pointer-to-pointer type) uses the special Swift error-result ABI trea...
@ Ordinary
This parameter uses ordinary ABI rules for its type.
@ SwiftIndirectResult
This parameter (which must have pointer type) is a Swift indirect result parameter.
@ SwiftContext
This parameter (which must have pointer type) uses the special Swift context-pointer ABI treatment.
CudaVersion
Definition: Cuda.h:20
LLVM_READONLY bool isHexDigit(unsigned char c)
Return true if this character is an ASCII hex digit: [0-9a-fA-F].
Definition: CharInfo.h:145
SanitizerMask parseSanitizerValue(StringRef Value, bool AllowGroups)
Parse a single value from a -fsanitize= or -fno-sanitize= value list.
Definition: Sanitizers.cpp:29
FloatModeKind
Definition: TargetInfo.h:72
@ VK_PRValue
A pr-value expression (in the C++11 taxonomy) produces a temporary value.
Definition: Specifiers.h:132
@ VK_LValue
An l-value expression is a reference to an object with independent storage.
Definition: Specifiers.h:136
const FunctionProtoType * T
MSInheritanceModel
Assigned inheritance model for a class in the MS C++ ABI.
Definition: Specifiers.h:389
bool declaresSameEntity(const Decl *D1, const Decl *D2)
Determine whether two declarations declare the same entity.
Definition: DeclBase.h:1275
std::pair< SourceLocation, PartialDiagnostic > PartialDiagnosticAt
A partial diagnostic along with the source location where this diagnostic occurs.
CallingConv
CallingConv - Specifies the calling convention that a function uses.
Definition: Specifiers.h:275
@ CC_X86Pascal
Definition: Specifiers.h:281
@ CC_Swift
Definition: Specifiers.h:290
@ CC_IntelOclBicc
Definition: Specifiers.h:287
@ CC_PreserveMost
Definition: Specifiers.h:292
@ CC_Win64
Definition: Specifiers.h:282
@ CC_X86ThisCall
Definition: Specifiers.h:279
@ CC_AArch64VectorCall
Definition: Specifiers.h:294
@ CC_AAPCS
Definition: Specifiers.h:285
@ CC_PreserveNone
Definition: Specifiers.h:298
@ CC_C
Definition: Specifiers.h:276
@ CC_AMDGPUKernelCall
Definition: Specifiers.h:296
@ CC_M68kRTD
Definition: Specifiers.h:297
@ CC_SwiftAsync
Definition: Specifiers.h:291
@ CC_X86RegCall
Definition: Specifiers.h:284
@ CC_RISCVVectorCall
Definition: Specifiers.h:299
@ CC_X86VectorCall
Definition: Specifiers.h:280
@ CC_AArch64SVEPCS
Definition: Specifiers.h:295
@ CC_X86StdCall
Definition: Specifiers.h:277
@ CC_X86_64SysV
Definition: Specifiers.h:283
@ CC_PreserveAll
Definition: Specifiers.h:293
@ CC_X86FastCall
Definition: Specifiers.h:278
@ CC_AAPCS_VFP
Definition: Specifiers.h:286
@ Generic
not a target-specific vector type
@ Interface
The "__interface" keyword introduces the elaborated-type-specifier.
@ Union
The "union" keyword introduces the elaborated-type-specifier.
bool IsArmStreamingFunction(const FunctionDecl *FD, bool IncludeLocallyStreaming)
Returns whether the given FunctionDecl has an __arm[_locally]_streaming attribute.
Definition: Decl.cpp:5760
@ Other
Other implicit parameter.
@ Implicit
An implicit conversion.
const char * CudaArchToString(CudaArch A)
Definition: Cuda.cpp:151
Represents information about a change in availability for an entity, which is part of the encoding of...
Definition: ParsedAttr.h:48
VersionTuple Version
The version number at which the change occurred.
Definition: ParsedAttr.h:53
bool isValid() const
Determine whether this availability change is valid.
Definition: ParsedAttr.h:59
static constexpr OSEnvPair macOStoMacCatalystPair()
Returns the os-environment mapping pair that's used to represent the macOS -> Mac Catalyst version ma...
Definition: DarwinSDKInfo.h:49
static constexpr OSEnvPair iOStoWatchOSPair()
Returns the os-environment mapping pair that's used to represent the iOS -> watchOS version mapping.
Definition: DarwinSDKInfo.h:63
static constexpr OSEnvPair iOStoTvOSPair()
Returns the os-environment mapping pair that's used to represent the iOS -> tvOS version mapping.
Definition: DarwinSDKInfo.h:70
DeclarationNameInfo - A collector data type for bundling together a DeclarationName and the correspon...
DeclarationName getName() const
getName - Returns the embedded declaration name.
const ParsedAttributesView & getAttrs() const
If there are attributes applied to this declaratorchunk, return them.
Definition: DeclSpec.h:1660
Wraps an identifier and optional source location for the identifier.
Definition: ParsedAttr.h:103
SourceLocation Loc
Definition: ParsedAttr.h:104
IdentifierInfo * Ident
Definition: ParsedAttr.h:105
Parts of a decomposed MSGuidDecl.
Definition: DeclCXX.h:4264
uint16_t Part2
...-89ab-...
Definition: DeclCXX.h:4268
uint32_t Part1
{01234567-...
Definition: DeclCXX.h:4266
uint16_t Part3
...-cdef-...
Definition: DeclCXX.h:4270
uint8_t Part4And5[8]
...-0123-456789abcdef}
Definition: DeclCXX.h:4272
virtual AttrHandling handleDeclAttribute(Sema &S, Decl *D, const ParsedAttr &Attr) const
If this ParsedAttrInfo knows how to handle this ParsedAttr applied to this Decl then do so and return...
Contains information gathered from parsing the contents of TargetAttr.
Definition: TargetInfo.h:57
std::vector< std::string > Features
Definition: TargetInfo.h:58
StringRef BranchProtection
Definition: TargetInfo.h:61