SemaDeclAttr.cpp revision d386fef64f1fd00fc9a97efb963d8ec393fd1ace
1//===--- SemaDeclAttr.cpp - Declaration Attribute Handling ----------------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file implements decl-related attribute processing. 11// 12//===----------------------------------------------------------------------===// 13 14#include "clang/Sema/SemaInternal.h" 15#include "TargetAttributesSema.h" 16#include "clang/AST/ASTContext.h" 17#include "clang/AST/CXXInheritance.h" 18#include "clang/AST/DeclCXX.h" 19#include "clang/AST/DeclObjC.h" 20#include "clang/AST/DeclTemplate.h" 21#include "clang/AST/Expr.h" 22#include "clang/AST/Mangle.h" 23#include "clang/Basic/CharInfo.h" 24#include "clang/Basic/SourceManager.h" 25#include "clang/Basic/TargetInfo.h" 26#include "clang/Lex/Preprocessor.h" 27#include "clang/Sema/DeclSpec.h" 28#include "clang/Sema/DelayedDiagnostic.h" 29#include "clang/Sema/Lookup.h" 30#include "clang/Sema/Scope.h" 31#include "llvm/ADT/StringExtras.h" 32using namespace clang; 33using namespace sema; 34 35/// These constants match the enumerated choices of 36/// warn_attribute_wrong_decl_type and err_attribute_wrong_decl_type. 37enum AttributeDeclKind { 38 ExpectedFunction, 39 ExpectedUnion, 40 ExpectedVariableOrFunction, 41 ExpectedFunctionOrMethod, 42 ExpectedParameter, 43 ExpectedFunctionMethodOrBlock, 44 ExpectedFunctionMethodOrClass, 45 ExpectedFunctionMethodOrParameter, 46 ExpectedClass, 47 ExpectedVariable, 48 ExpectedMethod, 49 ExpectedVariableFunctionOrLabel, 50 ExpectedFieldOrGlobalVar, 51 ExpectedStruct, 52 ExpectedVariableFunctionOrTag, 53 ExpectedTLSVar, 54 ExpectedVariableOrField, 55 ExpectedVariableFieldOrTag, 56 ExpectedTypeOrNamespace, 57 ExpectedObjectiveCInterface, 58 ExpectedMethodOrProperty 59}; 60 61//===----------------------------------------------------------------------===// 62// Helper functions 63//===----------------------------------------------------------------------===// 64 65static const FunctionType *getFunctionType(const Decl *D, 66 bool blocksToo = true) { 67 QualType Ty; 68 if (const ValueDecl *decl = dyn_cast<ValueDecl>(D)) 69 Ty = decl->getType(); 70 else if (const FieldDecl *decl = dyn_cast<FieldDecl>(D)) 71 Ty = decl->getType(); 72 else if (const TypedefNameDecl* decl = dyn_cast<TypedefNameDecl>(D)) 73 Ty = decl->getUnderlyingType(); 74 else 75 return 0; 76 77 if (Ty->isFunctionPointerType()) 78 Ty = Ty->getAs<PointerType>()->getPointeeType(); 79 else if (blocksToo && Ty->isBlockPointerType()) 80 Ty = Ty->getAs<BlockPointerType>()->getPointeeType(); 81 82 return Ty->getAs<FunctionType>(); 83} 84 85// FIXME: We should provide an abstraction around a method or function 86// to provide the following bits of information. 87 88/// isFunction - Return true if the given decl has function 89/// type (function or function-typed variable). 90static bool isFunction(const Decl *D) { 91 return getFunctionType(D, false) != NULL; 92} 93 94/// isFunctionOrMethod - Return true if the given decl has function 95/// type (function or function-typed variable) or an Objective-C 96/// method. 97static bool isFunctionOrMethod(const Decl *D) { 98 return isFunction(D) || isa<ObjCMethodDecl>(D); 99} 100 101/// isFunctionOrMethodOrBlock - Return true if the given decl has function 102/// type (function or function-typed variable) or an Objective-C 103/// method or a block. 104static bool isFunctionOrMethodOrBlock(const Decl *D) { 105 if (isFunctionOrMethod(D)) 106 return true; 107 // check for block is more involved. 108 if (const VarDecl *V = dyn_cast<VarDecl>(D)) { 109 QualType Ty = V->getType(); 110 return Ty->isBlockPointerType(); 111 } 112 return isa<BlockDecl>(D); 113} 114 115/// Return true if the given decl has a declarator that should have 116/// been processed by Sema::GetTypeForDeclarator. 117static bool hasDeclarator(const Decl *D) { 118 // In some sense, TypedefDecl really *ought* to be a DeclaratorDecl. 119 return isa<DeclaratorDecl>(D) || isa<BlockDecl>(D) || isa<TypedefNameDecl>(D) || 120 isa<ObjCPropertyDecl>(D); 121} 122 123/// hasFunctionProto - Return true if the given decl has a argument 124/// information. This decl should have already passed 125/// isFunctionOrMethod or isFunctionOrMethodOrBlock. 126static bool hasFunctionProto(const Decl *D) { 127 if (const FunctionType *FnTy = getFunctionType(D)) 128 return isa<FunctionProtoType>(FnTy); 129 else { 130 assert(isa<ObjCMethodDecl>(D) || isa<BlockDecl>(D)); 131 return true; 132 } 133} 134 135/// getFunctionOrMethodNumArgs - Return number of function or method 136/// arguments. It is an error to call this on a K&R function (use 137/// hasFunctionProto first). 138static unsigned getFunctionOrMethodNumArgs(const Decl *D) { 139 if (const FunctionType *FnTy = getFunctionType(D)) 140 return cast<FunctionProtoType>(FnTy)->getNumArgs(); 141 if (const BlockDecl *BD = dyn_cast<BlockDecl>(D)) 142 return BD->getNumParams(); 143 return cast<ObjCMethodDecl>(D)->param_size(); 144} 145 146static QualType getFunctionOrMethodArgType(const Decl *D, unsigned Idx) { 147 if (const FunctionType *FnTy = getFunctionType(D)) 148 return cast<FunctionProtoType>(FnTy)->getArgType(Idx); 149 if (const BlockDecl *BD = dyn_cast<BlockDecl>(D)) 150 return BD->getParamDecl(Idx)->getType(); 151 152 return cast<ObjCMethodDecl>(D)->param_begin()[Idx]->getType(); 153} 154 155static QualType getFunctionOrMethodResultType(const Decl *D) { 156 if (const FunctionType *FnTy = getFunctionType(D)) 157 return cast<FunctionProtoType>(FnTy)->getResultType(); 158 return cast<ObjCMethodDecl>(D)->getResultType(); 159} 160 161static bool isFunctionOrMethodVariadic(const Decl *D) { 162 if (const FunctionType *FnTy = getFunctionType(D)) { 163 const FunctionProtoType *proto = cast<FunctionProtoType>(FnTy); 164 return proto->isVariadic(); 165 } else if (const BlockDecl *BD = dyn_cast<BlockDecl>(D)) 166 return BD->isVariadic(); 167 else { 168 return cast<ObjCMethodDecl>(D)->isVariadic(); 169 } 170} 171 172static bool isInstanceMethod(const Decl *D) { 173 if (const CXXMethodDecl *MethodDecl = dyn_cast<CXXMethodDecl>(D)) 174 return MethodDecl->isInstance(); 175 return false; 176} 177 178static inline bool isNSStringType(QualType T, ASTContext &Ctx) { 179 const ObjCObjectPointerType *PT = T->getAs<ObjCObjectPointerType>(); 180 if (!PT) 181 return false; 182 183 ObjCInterfaceDecl *Cls = PT->getObjectType()->getInterface(); 184 if (!Cls) 185 return false; 186 187 IdentifierInfo* ClsName = Cls->getIdentifier(); 188 189 // FIXME: Should we walk the chain of classes? 190 return ClsName == &Ctx.Idents.get("NSString") || 191 ClsName == &Ctx.Idents.get("NSMutableString"); 192} 193 194static inline bool isCFStringType(QualType T, ASTContext &Ctx) { 195 const PointerType *PT = T->getAs<PointerType>(); 196 if (!PT) 197 return false; 198 199 const RecordType *RT = PT->getPointeeType()->getAs<RecordType>(); 200 if (!RT) 201 return false; 202 203 const RecordDecl *RD = RT->getDecl(); 204 if (RD->getTagKind() != TTK_Struct) 205 return false; 206 207 return RD->getIdentifier() == &Ctx.Idents.get("__CFString"); 208} 209 210/// \brief Check if the attribute has exactly as many args as Num. May 211/// output an error. 212static bool checkAttributeNumArgs(Sema &S, const AttributeList &Attr, 213 unsigned int Num) { 214 if (Attr.getNumArgs() != Num) { 215 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) 216 << Attr.getName() << Num; 217 return false; 218 } 219 220 return true; 221} 222 223 224/// \brief Check if the attribute has at least as many args as Num. May 225/// output an error. 226static bool checkAttributeAtLeastNumArgs(Sema &S, const AttributeList &Attr, 227 unsigned int Num) { 228 if (Attr.getNumArgs() < Num) { 229 S.Diag(Attr.getLoc(), diag::err_attribute_too_few_arguments) << Num; 230 return false; 231 } 232 233 return true; 234} 235 236/// \brief Check if IdxExpr is a valid argument index for a function or 237/// instance method D. May output an error. 238/// 239/// \returns true if IdxExpr is a valid index. 240static bool checkFunctionOrMethodArgumentIndex(Sema &S, const Decl *D, 241 StringRef AttrName, 242 SourceLocation AttrLoc, 243 unsigned AttrArgNum, 244 const Expr *IdxExpr, 245 uint64_t &Idx) 246{ 247 assert(isFunctionOrMethod(D)); 248 249 // In C++ the implicit 'this' function parameter also counts. 250 // Parameters are counted from one. 251 bool HP = hasFunctionProto(D); 252 bool HasImplicitThisParam = isInstanceMethod(D); 253 bool IV = HP && isFunctionOrMethodVariadic(D); 254 unsigned NumArgs = (HP ? getFunctionOrMethodNumArgs(D) : 0) + 255 HasImplicitThisParam; 256 257 llvm::APSInt IdxInt; 258 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 259 !IdxExpr->isIntegerConstantExpr(IdxInt, S.Context)) { 260 std::string Name = std::string("'") + AttrName.str() + std::string("'"); 261 S.Diag(AttrLoc, diag::err_attribute_argument_n_type) << Name.c_str() 262 << AttrArgNum << AANT_ArgumentIntegerConstant << IdxExpr->getSourceRange(); 263 return false; 264 } 265 266 Idx = IdxInt.getLimitedValue(); 267 if (Idx < 1 || (!IV && Idx > NumArgs)) { 268 S.Diag(AttrLoc, diag::err_attribute_argument_out_of_bounds) 269 << AttrName << AttrArgNum << IdxExpr->getSourceRange(); 270 return false; 271 } 272 Idx--; // Convert to zero-based. 273 if (HasImplicitThisParam) { 274 if (Idx == 0) { 275 S.Diag(AttrLoc, 276 diag::err_attribute_invalid_implicit_this_argument) 277 << AttrName << IdxExpr->getSourceRange(); 278 return false; 279 } 280 --Idx; 281 } 282 283 return true; 284} 285 286/// \brief Check if the argument \p ArgNum of \p Attr is a ASCII string literal. 287/// If not emit an error and return false. If the argument is an identifier it 288/// will emit an error with a fixit hint and treat it as if it was a string 289/// literal. 290bool Sema::checkStringLiteralArgumentAttr(const AttributeList &Attr, 291 unsigned ArgNum, StringRef &Str, 292 SourceLocation *ArgLocation) { 293 // Look for identifiers. If we have one emit a hint to fix it to a literal. 294 if (Attr.isArgIdent(ArgNum)) { 295 IdentifierLoc *Loc = Attr.getArgAsIdent(ArgNum); 296 Diag(Loc->Loc, diag::err_attribute_argument_type) 297 << Attr.getName() << AANT_ArgumentString 298 << FixItHint::CreateInsertion(Loc->Loc, "\"") 299 << FixItHint::CreateInsertion(PP.getLocForEndOfToken(Loc->Loc), "\""); 300 Str = Loc->Ident->getName(); 301 if (ArgLocation) 302 *ArgLocation = Loc->Loc; 303 return true; 304 } 305 306 // Now check for an actual string literal. 307 Expr *ArgExpr = Attr.getArgAsExpr(ArgNum); 308 StringLiteral *Literal = dyn_cast<StringLiteral>(ArgExpr->IgnoreParenCasts()); 309 if (ArgLocation) 310 *ArgLocation = ArgExpr->getLocStart(); 311 312 if (!Literal || !Literal->isAscii()) { 313 Diag(ArgExpr->getLocStart(), diag::err_attribute_argument_type) 314 << Attr.getName() << AANT_ArgumentString; 315 return false; 316 } 317 318 Str = Literal->getString(); 319 return true; 320} 321 322/// 323/// \brief Check if passed in Decl is a field or potentially shared global var 324/// \return true if the Decl is a field or potentially shared global variable 325/// 326static bool mayBeSharedVariable(const Decl *D) { 327 if (isa<FieldDecl>(D)) 328 return true; 329 if (const VarDecl *vd = dyn_cast<VarDecl>(D)) 330 return vd->hasGlobalStorage() && !vd->getTLSKind(); 331 332 return false; 333} 334 335/// \brief Check if the passed-in expression is of type int or bool. 336static bool isIntOrBool(Expr *Exp) { 337 QualType QT = Exp->getType(); 338 return QT->isBooleanType() || QT->isIntegerType(); 339} 340 341 342// Check to see if the type is a smart pointer of some kind. We assume 343// it's a smart pointer if it defines both operator-> and operator*. 344static bool threadSafetyCheckIsSmartPointer(Sema &S, const RecordType* RT) { 345 DeclContextLookupConstResult Res1 = RT->getDecl()->lookup( 346 S.Context.DeclarationNames.getCXXOperatorName(OO_Star)); 347 if (Res1.empty()) 348 return false; 349 350 DeclContextLookupConstResult Res2 = RT->getDecl()->lookup( 351 S.Context.DeclarationNames.getCXXOperatorName(OO_Arrow)); 352 if (Res2.empty()) 353 return false; 354 355 return true; 356} 357 358/// \brief Check if passed in Decl is a pointer type. 359/// Note that this function may produce an error message. 360/// \return true if the Decl is a pointer type; false otherwise 361static bool threadSafetyCheckIsPointer(Sema &S, const Decl *D, 362 const AttributeList &Attr) { 363 if (const ValueDecl *vd = dyn_cast<ValueDecl>(D)) { 364 QualType QT = vd->getType(); 365 if (QT->isAnyPointerType()) 366 return true; 367 368 if (const RecordType *RT = QT->getAs<RecordType>()) { 369 // If it's an incomplete type, it could be a smart pointer; skip it. 370 // (We don't want to force template instantiation if we can avoid it, 371 // since that would alter the order in which templates are instantiated.) 372 if (RT->isIncompleteType()) 373 return true; 374 375 if (threadSafetyCheckIsSmartPointer(S, RT)) 376 return true; 377 } 378 379 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_decl_not_pointer) 380 << Attr.getName()->getName() << QT; 381 } else { 382 S.Diag(Attr.getLoc(), diag::err_attribute_can_be_applied_only_to_value_decl) 383 << Attr.getName(); 384 } 385 return false; 386} 387 388/// \brief Checks that the passed in QualType either is of RecordType or points 389/// to RecordType. Returns the relevant RecordType, null if it does not exit. 390static const RecordType *getRecordType(QualType QT) { 391 if (const RecordType *RT = QT->getAs<RecordType>()) 392 return RT; 393 394 // Now check if we point to record type. 395 if (const PointerType *PT = QT->getAs<PointerType>()) 396 return PT->getPointeeType()->getAs<RecordType>(); 397 398 return 0; 399} 400 401 402static bool checkBaseClassIsLockableCallback(const CXXBaseSpecifier *Specifier, 403 CXXBasePath &Path, void *Unused) { 404 const RecordType *RT = Specifier->getType()->getAs<RecordType>(); 405 if (RT->getDecl()->getAttr<LockableAttr>()) 406 return true; 407 return false; 408} 409 410 411/// \brief Thread Safety Analysis: Checks that the passed in RecordType 412/// resolves to a lockable object. 413static void checkForLockableRecord(Sema &S, Decl *D, const AttributeList &Attr, 414 QualType Ty) { 415 const RecordType *RT = getRecordType(Ty); 416 417 // Warn if could not get record type for this argument. 418 if (!RT) { 419 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_argument_not_class) 420 << Attr.getName() << Ty.getAsString(); 421 return; 422 } 423 424 // Don't check for lockable if the class hasn't been defined yet. 425 if (RT->isIncompleteType()) 426 return; 427 428 // Allow smart pointers to be used as lockable objects. 429 // FIXME -- Check the type that the smart pointer points to. 430 if (threadSafetyCheckIsSmartPointer(S, RT)) 431 return; 432 433 // Check if the type is lockable. 434 RecordDecl *RD = RT->getDecl(); 435 if (RD->getAttr<LockableAttr>()) 436 return; 437 438 // Else check if any base classes are lockable. 439 if (CXXRecordDecl *CRD = dyn_cast<CXXRecordDecl>(RD)) { 440 CXXBasePaths BPaths(false, false); 441 if (CRD->lookupInBases(checkBaseClassIsLockableCallback, 0, BPaths)) 442 return; 443 } 444 445 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_argument_not_lockable) 446 << Attr.getName() << Ty.getAsString(); 447} 448 449/// \brief Thread Safety Analysis: Checks that all attribute arguments, starting 450/// from Sidx, resolve to a lockable object. 451/// \param Sidx The attribute argument index to start checking with. 452/// \param ParamIdxOk Whether an argument can be indexing into a function 453/// parameter list. 454static void checkAttrArgsAreLockableObjs(Sema &S, Decl *D, 455 const AttributeList &Attr, 456 SmallVectorImpl<Expr*> &Args, 457 int Sidx = 0, 458 bool ParamIdxOk = false) { 459 for(unsigned Idx = Sidx; Idx < Attr.getNumArgs(); ++Idx) { 460 Expr *ArgExp = Attr.getArgAsExpr(Idx); 461 462 if (ArgExp->isTypeDependent()) { 463 // FIXME -- need to check this again on template instantiation 464 Args.push_back(ArgExp); 465 continue; 466 } 467 468 if (StringLiteral *StrLit = dyn_cast<StringLiteral>(ArgExp)) { 469 if (StrLit->getLength() == 0 || 470 (StrLit->isAscii() && StrLit->getString() == StringRef("*"))) { 471 // Pass empty strings to the analyzer without warnings. 472 // Treat "*" as the universal lock. 473 Args.push_back(ArgExp); 474 continue; 475 } 476 477 // We allow constant strings to be used as a placeholder for expressions 478 // that are not valid C++ syntax, but warn that they are ignored. 479 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_ignored) << 480 Attr.getName(); 481 Args.push_back(ArgExp); 482 continue; 483 } 484 485 QualType ArgTy = ArgExp->getType(); 486 487 // A pointer to member expression of the form &MyClass::mu is treated 488 // specially -- we need to look at the type of the member. 489 if (UnaryOperator *UOp = dyn_cast<UnaryOperator>(ArgExp)) 490 if (UOp->getOpcode() == UO_AddrOf) 491 if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(UOp->getSubExpr())) 492 if (DRE->getDecl()->isCXXInstanceMember()) 493 ArgTy = DRE->getDecl()->getType(); 494 495 // First see if we can just cast to record type, or point to record type. 496 const RecordType *RT = getRecordType(ArgTy); 497 498 // Now check if we index into a record type function param. 499 if(!RT && ParamIdxOk) { 500 FunctionDecl *FD = dyn_cast<FunctionDecl>(D); 501 IntegerLiteral *IL = dyn_cast<IntegerLiteral>(ArgExp); 502 if(FD && IL) { 503 unsigned int NumParams = FD->getNumParams(); 504 llvm::APInt ArgValue = IL->getValue(); 505 uint64_t ParamIdxFromOne = ArgValue.getZExtValue(); 506 uint64_t ParamIdxFromZero = ParamIdxFromOne - 1; 507 if(!ArgValue.isStrictlyPositive() || ParamIdxFromOne > NumParams) { 508 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_range) 509 << Attr.getName() << Idx + 1 << NumParams; 510 continue; 511 } 512 ArgTy = FD->getParamDecl(ParamIdxFromZero)->getType(); 513 } 514 } 515 516 checkForLockableRecord(S, D, Attr, ArgTy); 517 518 Args.push_back(ArgExp); 519 } 520} 521 522//===----------------------------------------------------------------------===// 523// Attribute Implementations 524//===----------------------------------------------------------------------===// 525 526// FIXME: All this manual attribute parsing code is gross. At the 527// least add some helper functions to check most argument patterns (# 528// and types of args). 529 530enum ThreadAttributeDeclKind { 531 ThreadExpectedFieldOrGlobalVar, 532 ThreadExpectedFunctionOrMethod, 533 ThreadExpectedClassOrStruct 534}; 535 536static bool checkGuardedVarAttrCommon(Sema &S, Decl *D, 537 const AttributeList &Attr) { 538 // D must be either a member field or global (potentially shared) variable. 539 if (!mayBeSharedVariable(D)) { 540 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 541 << Attr.getName() << ThreadExpectedFieldOrGlobalVar; 542 return false; 543 } 544 545 return true; 546} 547 548static void handleGuardedVarAttr(Sema &S, Decl *D, const AttributeList &Attr) { 549 if (!checkGuardedVarAttrCommon(S, D, Attr)) 550 return; 551 552 D->addAttr(::new (S.Context) 553 GuardedVarAttr(Attr.getRange(), S.Context, 554 Attr.getAttributeSpellingListIndex())); 555} 556 557static void handlePtGuardedVarAttr(Sema &S, Decl *D, 558 const AttributeList &Attr) { 559 if (!checkGuardedVarAttrCommon(S, D, Attr)) 560 return; 561 562 if (!threadSafetyCheckIsPointer(S, D, Attr)) 563 return; 564 565 D->addAttr(::new (S.Context) 566 PtGuardedVarAttr(Attr.getRange(), S.Context, 567 Attr.getAttributeSpellingListIndex())); 568} 569 570static bool checkGuardedByAttrCommon(Sema &S, Decl *D, 571 const AttributeList &Attr, 572 Expr* &Arg) { 573 // D must be either a member field or global (potentially shared) variable. 574 if (!mayBeSharedVariable(D)) { 575 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 576 << Attr.getName() << ThreadExpectedFieldOrGlobalVar; 577 return false; 578 } 579 580 SmallVector<Expr*, 1> Args; 581 // check that all arguments are lockable objects 582 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 583 unsigned Size = Args.size(); 584 if (Size != 1) 585 return false; 586 587 Arg = Args[0]; 588 589 return true; 590} 591 592static void handleGuardedByAttr(Sema &S, Decl *D, const AttributeList &Attr) { 593 Expr *Arg = 0; 594 if (!checkGuardedByAttrCommon(S, D, Attr, Arg)) 595 return; 596 597 D->addAttr(::new (S.Context) GuardedByAttr(Attr.getRange(), S.Context, Arg)); 598} 599 600static void handlePtGuardedByAttr(Sema &S, Decl *D, 601 const AttributeList &Attr) { 602 Expr *Arg = 0; 603 if (!checkGuardedByAttrCommon(S, D, Attr, Arg)) 604 return; 605 606 if (!threadSafetyCheckIsPointer(S, D, Attr)) 607 return; 608 609 D->addAttr(::new (S.Context) PtGuardedByAttr(Attr.getRange(), 610 S.Context, Arg)); 611} 612 613static bool checkLockableAttrCommon(Sema &S, Decl *D, 614 const AttributeList &Attr) { 615 // FIXME: Lockable structs for C code. 616 if (!isa<RecordDecl>(D)) { 617 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 618 << Attr.getName() << ThreadExpectedClassOrStruct; 619 return false; 620 } 621 622 return true; 623} 624 625static void handleLockableAttr(Sema &S, Decl *D, const AttributeList &Attr) { 626 if (!checkLockableAttrCommon(S, D, Attr)) 627 return; 628 629 D->addAttr(::new (S.Context) LockableAttr(Attr.getRange(), S.Context)); 630} 631 632static void handleScopedLockableAttr(Sema &S, Decl *D, 633 const AttributeList &Attr) { 634 if (!checkLockableAttrCommon(S, D, Attr)) 635 return; 636 637 D->addAttr(::new (S.Context) 638 ScopedLockableAttr(Attr.getRange(), S.Context, 639 Attr.getAttributeSpellingListIndex())); 640} 641 642static void handleNoThreadSafetyAnalysis(Sema &S, Decl *D, 643 const AttributeList &Attr) { 644 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 645 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 646 << Attr.getName() << ThreadExpectedFunctionOrMethod; 647 return; 648 } 649 650 D->addAttr(::new (S.Context) NoThreadSafetyAnalysisAttr(Attr.getRange(), 651 S.Context)); 652} 653 654static void handleNoSanitizeAddressAttr(Sema &S, Decl *D, 655 const AttributeList &Attr) { 656 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 657 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 658 << Attr.getName() << ExpectedFunctionOrMethod; 659 return; 660 } 661 662 D->addAttr(::new (S.Context) 663 NoSanitizeAddressAttr(Attr.getRange(), S.Context, 664 Attr.getAttributeSpellingListIndex())); 665} 666 667static void handleNoSanitizeMemory(Sema &S, Decl *D, 668 const AttributeList &Attr) { 669 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 670 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 671 << Attr.getName() << ExpectedFunctionOrMethod; 672 return; 673 } 674 675 D->addAttr(::new (S.Context) NoSanitizeMemoryAttr(Attr.getRange(), 676 S.Context)); 677} 678 679static void handleNoSanitizeThread(Sema &S, Decl *D, 680 const AttributeList &Attr) { 681 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 682 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 683 << Attr.getName() << ExpectedFunctionOrMethod; 684 return; 685 } 686 687 D->addAttr(::new (S.Context) NoSanitizeThreadAttr(Attr.getRange(), 688 S.Context)); 689} 690 691static bool checkAcquireOrderAttrCommon(Sema &S, Decl *D, 692 const AttributeList &Attr, 693 SmallVectorImpl<Expr *> &Args) { 694 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 695 return false; 696 697 // D must be either a member field or global (potentially shared) variable. 698 ValueDecl *VD = dyn_cast<ValueDecl>(D); 699 if (!VD || !mayBeSharedVariable(D)) { 700 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 701 << Attr.getName() << ThreadExpectedFieldOrGlobalVar; 702 return false; 703 } 704 705 // Check that this attribute only applies to lockable types. 706 QualType QT = VD->getType(); 707 if (!QT->isDependentType()) { 708 const RecordType *RT = getRecordType(QT); 709 if (!RT || !RT->getDecl()->getAttr<LockableAttr>()) { 710 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_decl_not_lockable) 711 << Attr.getName(); 712 return false; 713 } 714 } 715 716 // Check that all arguments are lockable objects. 717 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 718 if (Args.empty()) 719 return false; 720 721 return true; 722} 723 724static void handleAcquiredAfterAttr(Sema &S, Decl *D, 725 const AttributeList &Attr) { 726 SmallVector<Expr*, 1> Args; 727 if (!checkAcquireOrderAttrCommon(S, D, Attr, Args)) 728 return; 729 730 Expr **StartArg = &Args[0]; 731 D->addAttr(::new (S.Context) 732 AcquiredAfterAttr(Attr.getRange(), S.Context, 733 StartArg, Args.size(), 734 Attr.getAttributeSpellingListIndex())); 735} 736 737static void handleAcquiredBeforeAttr(Sema &S, Decl *D, 738 const AttributeList &Attr) { 739 SmallVector<Expr*, 1> Args; 740 if (!checkAcquireOrderAttrCommon(S, D, Attr, Args)) 741 return; 742 743 Expr **StartArg = &Args[0]; 744 D->addAttr(::new (S.Context) 745 AcquiredBeforeAttr(Attr.getRange(), S.Context, 746 StartArg, Args.size(), 747 Attr.getAttributeSpellingListIndex())); 748} 749 750static bool checkLockFunAttrCommon(Sema &S, Decl *D, 751 const AttributeList &Attr, 752 SmallVectorImpl<Expr *> &Args) { 753 // zero or more arguments ok 754 755 // check that the attribute is applied to a function 756 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 757 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 758 << Attr.getName() << ThreadExpectedFunctionOrMethod; 759 return false; 760 } 761 762 // check that all arguments are lockable objects 763 checkAttrArgsAreLockableObjs(S, D, Attr, Args, 0, /*ParamIdxOk=*/true); 764 765 return true; 766} 767 768static void handleSharedLockFunctionAttr(Sema &S, Decl *D, 769 const AttributeList &Attr) { 770 SmallVector<Expr*, 1> Args; 771 if (!checkLockFunAttrCommon(S, D, Attr, Args)) 772 return; 773 774 unsigned Size = Args.size(); 775 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 776 D->addAttr(::new (S.Context) 777 SharedLockFunctionAttr(Attr.getRange(), S.Context, StartArg, Size, 778 Attr.getAttributeSpellingListIndex())); 779} 780 781static void handleExclusiveLockFunctionAttr(Sema &S, Decl *D, 782 const AttributeList &Attr) { 783 SmallVector<Expr*, 1> Args; 784 if (!checkLockFunAttrCommon(S, D, Attr, Args)) 785 return; 786 787 unsigned Size = Args.size(); 788 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 789 D->addAttr(::new (S.Context) 790 ExclusiveLockFunctionAttr(Attr.getRange(), S.Context, 791 StartArg, Size, 792 Attr.getAttributeSpellingListIndex())); 793} 794 795static void handleAssertSharedLockAttr(Sema &S, Decl *D, 796 const AttributeList &Attr) { 797 SmallVector<Expr*, 1> Args; 798 if (!checkLockFunAttrCommon(S, D, Attr, Args)) 799 return; 800 801 unsigned Size = Args.size(); 802 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 803 D->addAttr(::new (S.Context) 804 AssertSharedLockAttr(Attr.getRange(), S.Context, StartArg, Size, 805 Attr.getAttributeSpellingListIndex())); 806} 807 808static void handleAssertExclusiveLockAttr(Sema &S, Decl *D, 809 const AttributeList &Attr) { 810 SmallVector<Expr*, 1> Args; 811 if (!checkLockFunAttrCommon(S, D, Attr, Args)) 812 return; 813 814 unsigned Size = Args.size(); 815 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 816 D->addAttr(::new (S.Context) 817 AssertExclusiveLockAttr(Attr.getRange(), S.Context, 818 StartArg, Size, 819 Attr.getAttributeSpellingListIndex())); 820} 821 822 823static bool checkTryLockFunAttrCommon(Sema &S, Decl *D, 824 const AttributeList &Attr, 825 SmallVectorImpl<Expr *> &Args) { 826 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 827 return false; 828 829 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 830 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 831 << Attr.getName() << ThreadExpectedFunctionOrMethod; 832 return false; 833 } 834 835 if (!isIntOrBool(Attr.getArgAsExpr(0))) { 836 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 837 << Attr.getName() << 1 << AANT_ArgumentIntOrBool; 838 return false; 839 } 840 841 // check that all arguments are lockable objects 842 checkAttrArgsAreLockableObjs(S, D, Attr, Args, 1); 843 844 return true; 845} 846 847static void handleSharedTrylockFunctionAttr(Sema &S, Decl *D, 848 const AttributeList &Attr) { 849 SmallVector<Expr*, 2> Args; 850 if (!checkTryLockFunAttrCommon(S, D, Attr, Args)) 851 return; 852 853 D->addAttr(::new (S.Context) 854 SharedTrylockFunctionAttr(Attr.getRange(), S.Context, 855 Attr.getArgAsExpr(0), 856 Args.data(), Args.size(), 857 Attr.getAttributeSpellingListIndex())); 858} 859 860static void handleExclusiveTrylockFunctionAttr(Sema &S, Decl *D, 861 const AttributeList &Attr) { 862 SmallVector<Expr*, 2> Args; 863 if (!checkTryLockFunAttrCommon(S, D, Attr, Args)) 864 return; 865 866 D->addAttr(::new (S.Context) 867 ExclusiveTrylockFunctionAttr(Attr.getRange(), S.Context, 868 Attr.getArgAsExpr(0), 869 Args.data(), Args.size(), 870 Attr.getAttributeSpellingListIndex())); 871} 872 873static bool checkLocksRequiredCommon(Sema &S, Decl *D, 874 const AttributeList &Attr, 875 SmallVectorImpl<Expr *> &Args) { 876 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 877 return false; 878 879 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 880 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 881 << Attr.getName() << ThreadExpectedFunctionOrMethod; 882 return false; 883 } 884 885 // check that all arguments are lockable objects 886 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 887 if (Args.empty()) 888 return false; 889 890 return true; 891} 892 893static void handleExclusiveLocksRequiredAttr(Sema &S, Decl *D, 894 const AttributeList &Attr) { 895 SmallVector<Expr*, 1> Args; 896 if (!checkLocksRequiredCommon(S, D, Attr, Args)) 897 return; 898 899 Expr **StartArg = &Args[0]; 900 D->addAttr(::new (S.Context) 901 ExclusiveLocksRequiredAttr(Attr.getRange(), S.Context, 902 StartArg, Args.size(), 903 Attr.getAttributeSpellingListIndex())); 904} 905 906static void handleSharedLocksRequiredAttr(Sema &S, Decl *D, 907 const AttributeList &Attr) { 908 SmallVector<Expr*, 1> Args; 909 if (!checkLocksRequiredCommon(S, D, Attr, Args)) 910 return; 911 912 Expr **StartArg = &Args[0]; 913 D->addAttr(::new (S.Context) 914 SharedLocksRequiredAttr(Attr.getRange(), S.Context, 915 StartArg, Args.size(), 916 Attr.getAttributeSpellingListIndex())); 917} 918 919static void handleUnlockFunAttr(Sema &S, Decl *D, 920 const AttributeList &Attr) { 921 // zero or more arguments ok 922 923 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 924 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 925 << Attr.getName() << ThreadExpectedFunctionOrMethod; 926 return; 927 } 928 929 // check that all arguments are lockable objects 930 SmallVector<Expr*, 1> Args; 931 checkAttrArgsAreLockableObjs(S, D, Attr, Args, 0, /*ParamIdxOk=*/true); 932 unsigned Size = Args.size(); 933 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 934 935 D->addAttr(::new (S.Context) 936 UnlockFunctionAttr(Attr.getRange(), S.Context, StartArg, Size, 937 Attr.getAttributeSpellingListIndex())); 938} 939 940static void handleLockReturnedAttr(Sema &S, Decl *D, 941 const AttributeList &Attr) { 942 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 943 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 944 << Attr.getName() << ThreadExpectedFunctionOrMethod; 945 return; 946 } 947 948 // check that the argument is lockable object 949 SmallVector<Expr*, 1> Args; 950 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 951 unsigned Size = Args.size(); 952 if (Size == 0) 953 return; 954 955 D->addAttr(::new (S.Context) 956 LockReturnedAttr(Attr.getRange(), S.Context, Args[0], 957 Attr.getAttributeSpellingListIndex())); 958} 959 960static void handleLocksExcludedAttr(Sema &S, Decl *D, 961 const AttributeList &Attr) { 962 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 963 return; 964 965 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 966 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_wrong_decl_type) 967 << Attr.getName() << ThreadExpectedFunctionOrMethod; 968 return; 969 } 970 971 // check that all arguments are lockable objects 972 SmallVector<Expr*, 1> Args; 973 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 974 unsigned Size = Args.size(); 975 if (Size == 0) 976 return; 977 Expr **StartArg = &Args[0]; 978 979 D->addAttr(::new (S.Context) 980 LocksExcludedAttr(Attr.getRange(), S.Context, StartArg, Size, 981 Attr.getAttributeSpellingListIndex())); 982} 983 984static void handleConsumableAttr(Sema &S, Decl *D, const AttributeList &Attr) { 985 ConsumableAttr::ConsumedState DefaultState; 986 987 if (Attr.isArgIdent(0)) { 988 IdentifierLoc *IL = Attr.getArgAsIdent(0); 989 if (!ConsumableAttr::ConvertStrToConsumedState(IL->Ident->getName(), 990 DefaultState)) { 991 S.Diag(IL->Loc, diag::warn_attribute_type_not_supported) 992 << Attr.getName() << IL->Ident; 993 return; 994 } 995 } else { 996 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) 997 << Attr.getName() << AANT_ArgumentIdentifier; 998 return; 999 } 1000 1001 if (!isa<CXXRecordDecl>(D)) { 1002 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << 1003 Attr.getName() << ExpectedClass; 1004 return; 1005 } 1006 1007 D->addAttr(::new (S.Context) 1008 ConsumableAttr(Attr.getRange(), S.Context, DefaultState, 1009 Attr.getAttributeSpellingListIndex())); 1010} 1011 1012static bool checkForConsumableClass(Sema &S, const CXXMethodDecl *MD, 1013 const AttributeList &Attr) { 1014 ASTContext &CurrContext = S.getASTContext(); 1015 QualType ThisType = MD->getThisType(CurrContext)->getPointeeType(); 1016 1017 if (const CXXRecordDecl *RD = ThisType->getAsCXXRecordDecl()) { 1018 if (!RD->hasAttr<ConsumableAttr>()) { 1019 S.Diag(Attr.getLoc(), diag::warn_attr_on_unconsumable_class) << 1020 RD->getNameAsString(); 1021 1022 return false; 1023 } 1024 } 1025 1026 return true; 1027} 1028 1029 1030static void handleCallableWhenAttr(Sema &S, Decl *D, 1031 const AttributeList &Attr) { 1032 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 1033 return; 1034 1035 if (!isa<CXXMethodDecl>(D)) { 1036 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << 1037 Attr.getName() << ExpectedMethod; 1038 return; 1039 } 1040 1041 if (!checkForConsumableClass(S, cast<CXXMethodDecl>(D), Attr)) 1042 return; 1043 1044 SmallVector<CallableWhenAttr::ConsumedState, 3> States; 1045 for (unsigned ArgIndex = 0; ArgIndex < Attr.getNumArgs(); ++ArgIndex) { 1046 CallableWhenAttr::ConsumedState CallableState; 1047 1048 StringRef StateString; 1049 SourceLocation Loc; 1050 if (!S.checkStringLiteralArgumentAttr(Attr, ArgIndex, StateString, &Loc)) 1051 return; 1052 1053 if (!CallableWhenAttr::ConvertStrToConsumedState(StateString, 1054 CallableState)) { 1055 S.Diag(Loc, diag::warn_attribute_type_not_supported) 1056 << Attr.getName() << StateString; 1057 return; 1058 } 1059 1060 States.push_back(CallableState); 1061 } 1062 1063 D->addAttr(::new (S.Context) 1064 CallableWhenAttr(Attr.getRange(), S.Context, States.data(), 1065 States.size(), Attr.getAttributeSpellingListIndex())); 1066} 1067 1068 1069static void handleParamTypestateAttr(Sema &S, Decl *D, 1070 const AttributeList &Attr) { 1071 if (!checkAttributeNumArgs(S, Attr, 1)) return; 1072 1073 if (!isa<ParmVarDecl>(D)) { 1074 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << 1075 Attr.getName() << ExpectedParameter; 1076 return; 1077 } 1078 1079 ParamTypestateAttr::ConsumedState ParamState; 1080 1081 if (Attr.isArgIdent(0)) { 1082 IdentifierLoc *Ident = Attr.getArgAsIdent(0); 1083 StringRef StateString = Ident->Ident->getName(); 1084 1085 if (!ParamTypestateAttr::ConvertStrToConsumedState(StateString, 1086 ParamState)) { 1087 S.Diag(Ident->Loc, diag::warn_attribute_type_not_supported) 1088 << Attr.getName() << StateString; 1089 return; 1090 } 1091 } else { 1092 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) << 1093 Attr.getName() << AANT_ArgumentIdentifier; 1094 return; 1095 } 1096 1097 // FIXME: This check is currently being done in the analysis. It can be 1098 // enabled here only after the parser propagates attributes at 1099 // template specialization definition, not declaration. 1100 //QualType ReturnType = cast<ParmVarDecl>(D)->getType(); 1101 //const CXXRecordDecl *RD = ReturnType->getAsCXXRecordDecl(); 1102 // 1103 //if (!RD || !RD->hasAttr<ConsumableAttr>()) { 1104 // S.Diag(Attr.getLoc(), diag::warn_return_state_for_unconsumable_type) << 1105 // ReturnType.getAsString(); 1106 // return; 1107 //} 1108 1109 D->addAttr(::new (S.Context) 1110 ParamTypestateAttr(Attr.getRange(), S.Context, ParamState, 1111 Attr.getAttributeSpellingListIndex())); 1112} 1113 1114 1115static void handleReturnTypestateAttr(Sema &S, Decl *D, 1116 const AttributeList &Attr) { 1117 if (!checkAttributeNumArgs(S, Attr, 1)) return; 1118 1119 if (!(isa<FunctionDecl>(D) || isa<ParmVarDecl>(D))) { 1120 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << 1121 Attr.getName() << ExpectedFunctionMethodOrParameter; 1122 return; 1123 } 1124 1125 ReturnTypestateAttr::ConsumedState ReturnState; 1126 1127 if (Attr.isArgIdent(0)) { 1128 IdentifierLoc *IL = Attr.getArgAsIdent(0); 1129 if (!ReturnTypestateAttr::ConvertStrToConsumedState(IL->Ident->getName(), 1130 ReturnState)) { 1131 S.Diag(IL->Loc, diag::warn_attribute_type_not_supported) 1132 << Attr.getName() << IL->Ident; 1133 return; 1134 } 1135 } else { 1136 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) << 1137 Attr.getName() << AANT_ArgumentIdentifier; 1138 return; 1139 } 1140 1141 // FIXME: This check is currently being done in the analysis. It can be 1142 // enabled here only after the parser propagates attributes at 1143 // template specialization definition, not declaration. 1144 //QualType ReturnType; 1145 // 1146 //if (const ParmVarDecl *Param = dyn_cast<ParmVarDecl>(D)) { 1147 // ReturnType = Param->getType(); 1148 // 1149 //} else if (const CXXConstructorDecl *Constructor = 1150 // dyn_cast<CXXConstructorDecl>(D)) { 1151 // ReturnType = Constructor->getThisType(S.getASTContext())->getPointeeType(); 1152 // 1153 //} else { 1154 // 1155 // ReturnType = cast<FunctionDecl>(D)->getCallResultType(); 1156 //} 1157 // 1158 //const CXXRecordDecl *RD = ReturnType->getAsCXXRecordDecl(); 1159 // 1160 //if (!RD || !RD->hasAttr<ConsumableAttr>()) { 1161 // S.Diag(Attr.getLoc(), diag::warn_return_state_for_unconsumable_type) << 1162 // ReturnType.getAsString(); 1163 // return; 1164 //} 1165 1166 D->addAttr(::new (S.Context) 1167 ReturnTypestateAttr(Attr.getRange(), S.Context, ReturnState, 1168 Attr.getAttributeSpellingListIndex())); 1169} 1170 1171 1172static void handleSetTypestateAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1173 if (!checkAttributeNumArgs(S, Attr, 1)) 1174 return; 1175 1176 if (!isa<CXXMethodDecl>(D)) { 1177 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << 1178 Attr.getName() << ExpectedMethod; 1179 return; 1180 } 1181 1182 if (!checkForConsumableClass(S, cast<CXXMethodDecl>(D), Attr)) 1183 return; 1184 1185 SetTypestateAttr::ConsumedState NewState; 1186 if (Attr.isArgIdent(0)) { 1187 IdentifierLoc *Ident = Attr.getArgAsIdent(0); 1188 StringRef Param = Ident->Ident->getName(); 1189 if (!SetTypestateAttr::ConvertStrToConsumedState(Param, NewState)) { 1190 S.Diag(Ident->Loc, diag::warn_attribute_type_not_supported) 1191 << Attr.getName() << Param; 1192 return; 1193 } 1194 } else { 1195 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) << 1196 Attr.getName() << AANT_ArgumentIdentifier; 1197 return; 1198 } 1199 1200 D->addAttr(::new (S.Context) 1201 SetTypestateAttr(Attr.getRange(), S.Context, NewState, 1202 Attr.getAttributeSpellingListIndex())); 1203} 1204 1205static void handleTestTypestateAttr(Sema &S, Decl *D, 1206 const AttributeList &Attr) { 1207 if (!checkAttributeNumArgs(S, Attr, 1)) 1208 return; 1209 1210 if (!isa<CXXMethodDecl>(D)) { 1211 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) << 1212 Attr.getName() << ExpectedMethod; 1213 return; 1214 } 1215 1216 if (!checkForConsumableClass(S, cast<CXXMethodDecl>(D), Attr)) 1217 return; 1218 1219 TestTypestateAttr::ConsumedState TestState; 1220 if (Attr.isArgIdent(0)) { 1221 IdentifierLoc *Ident = Attr.getArgAsIdent(0); 1222 StringRef Param = Ident->Ident->getName(); 1223 if (!TestTypestateAttr::ConvertStrToConsumedState(Param, TestState)) { 1224 S.Diag(Ident->Loc, diag::warn_attribute_type_not_supported) 1225 << Attr.getName() << Param; 1226 return; 1227 } 1228 } else { 1229 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) << 1230 Attr.getName() << AANT_ArgumentIdentifier; 1231 return; 1232 } 1233 1234 D->addAttr(::new (S.Context) 1235 TestTypestateAttr(Attr.getRange(), S.Context, TestState, 1236 Attr.getAttributeSpellingListIndex())); 1237} 1238 1239static void handleExtVectorTypeAttr(Sema &S, Scope *scope, Decl *D, 1240 const AttributeList &Attr) { 1241 TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D); 1242 if (TD == 0) { 1243 // __attribute__((ext_vector_type(N))) can only be applied to typedefs 1244 // and type-ids. 1245 S.Diag(Attr.getLoc(), diag::err_typecheck_ext_vector_not_typedef); 1246 return; 1247 } 1248 1249 // Remember this typedef decl, we will need it later for diagnostics. 1250 S.ExtVectorDecls.push_back(TD); 1251} 1252 1253static void handlePackedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1254 if (TagDecl *TD = dyn_cast<TagDecl>(D)) 1255 TD->addAttr(::new (S.Context) PackedAttr(Attr.getRange(), S.Context)); 1256 else if (FieldDecl *FD = dyn_cast<FieldDecl>(D)) { 1257 // If the alignment is less than or equal to 8 bits, the packed attribute 1258 // has no effect. 1259 if (!FD->getType()->isDependentType() && 1260 !FD->getType()->isIncompleteType() && 1261 S.Context.getTypeAlign(FD->getType()) <= 8) 1262 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored_for_field_of_type) 1263 << Attr.getName() << FD->getType(); 1264 else 1265 FD->addAttr(::new (S.Context) 1266 PackedAttr(Attr.getRange(), S.Context, 1267 Attr.getAttributeSpellingListIndex())); 1268 } else 1269 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 1270} 1271 1272static void handleMsStructAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1273 if (RecordDecl *RD = dyn_cast<RecordDecl>(D)) 1274 RD->addAttr(::new (S.Context) 1275 MsStructAttr(Attr.getRange(), S.Context, 1276 Attr.getAttributeSpellingListIndex())); 1277 else 1278 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 1279} 1280 1281static void handleIBAction(Sema &S, Decl *D, const AttributeList &Attr) { 1282 // The IBAction attributes only apply to instance methods. 1283 if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 1284 if (MD->isInstanceMethod()) { 1285 D->addAttr(::new (S.Context) 1286 IBActionAttr(Attr.getRange(), S.Context, 1287 Attr.getAttributeSpellingListIndex())); 1288 return; 1289 } 1290 1291 S.Diag(Attr.getLoc(), diag::warn_attribute_ibaction) << Attr.getName(); 1292} 1293 1294static bool checkIBOutletCommon(Sema &S, Decl *D, const AttributeList &Attr) { 1295 // The IBOutlet/IBOutletCollection attributes only apply to instance 1296 // variables or properties of Objective-C classes. The outlet must also 1297 // have an object reference type. 1298 if (const ObjCIvarDecl *VD = dyn_cast<ObjCIvarDecl>(D)) { 1299 if (!VD->getType()->getAs<ObjCObjectPointerType>()) { 1300 S.Diag(Attr.getLoc(), diag::warn_iboutlet_object_type) 1301 << Attr.getName() << VD->getType() << 0; 1302 return false; 1303 } 1304 } 1305 else if (const ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(D)) { 1306 if (!PD->getType()->getAs<ObjCObjectPointerType>()) { 1307 S.Diag(Attr.getLoc(), diag::warn_iboutlet_object_type) 1308 << Attr.getName() << PD->getType() << 1; 1309 return false; 1310 } 1311 } 1312 else { 1313 S.Diag(Attr.getLoc(), diag::warn_attribute_iboutlet) << Attr.getName(); 1314 return false; 1315 } 1316 1317 return true; 1318} 1319 1320static void handleIBOutlet(Sema &S, Decl *D, const AttributeList &Attr) { 1321 if (!checkIBOutletCommon(S, D, Attr)) 1322 return; 1323 1324 D->addAttr(::new (S.Context) 1325 IBOutletAttr(Attr.getRange(), S.Context, 1326 Attr.getAttributeSpellingListIndex())); 1327} 1328 1329static void handleIBOutletCollection(Sema &S, Decl *D, 1330 const AttributeList &Attr) { 1331 1332 // The iboutletcollection attribute can have zero or one arguments. 1333 if (Attr.getNumArgs() > 1) { 1334 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) 1335 << Attr.getName() << 1; 1336 return; 1337 } 1338 1339 if (!checkIBOutletCommon(S, D, Attr)) 1340 return; 1341 1342 ParsedType PT; 1343 1344 if (Attr.hasParsedType()) 1345 PT = Attr.getTypeArg(); 1346 else { 1347 PT = S.getTypeName(S.Context.Idents.get("NSObject"), Attr.getLoc(), 1348 S.getScopeForContext(D->getDeclContext()->getParent())); 1349 if (!PT) { 1350 S.Diag(Attr.getLoc(), diag::err_iboutletcollection_type) << "NSObject"; 1351 return; 1352 } 1353 } 1354 1355 TypeSourceInfo *TSI = 0; 1356 QualType QT = S.GetTypeFromParser(PT, &TSI); 1357 SourceLocation QTLoc = 1358 TSI ? TSI->getTypeLoc().getLocStart() : SourceLocation(); 1359 1360 // Diagnose use of non-object type in iboutletcollection attribute. 1361 // FIXME. Gnu attribute extension ignores use of builtin types in 1362 // attributes. So, __attribute__((iboutletcollection(char))) will be 1363 // treated as __attribute__((iboutletcollection())). 1364 if (!QT->isObjCIdType() && !QT->isObjCObjectType()) { 1365 S.Diag(Attr.getLoc(), 1366 QT->isBuiltinType() ? diag::err_iboutletcollection_builtintype 1367 : diag::err_iboutletcollection_type) << QT; 1368 return; 1369 } 1370 1371 D->addAttr(::new (S.Context) 1372 IBOutletCollectionAttr(Attr.getRange(), S.Context, QT, QTLoc, 1373 Attr.getAttributeSpellingListIndex())); 1374} 1375 1376static void possibleTransparentUnionPointerType(QualType &T) { 1377 if (const RecordType *UT = T->getAsUnionType()) 1378 if (UT && UT->getDecl()->hasAttr<TransparentUnionAttr>()) { 1379 RecordDecl *UD = UT->getDecl(); 1380 for (RecordDecl::field_iterator it = UD->field_begin(), 1381 itend = UD->field_end(); it != itend; ++it) { 1382 QualType QT = it->getType(); 1383 if (QT->isAnyPointerType() || QT->isBlockPointerType()) { 1384 T = QT; 1385 return; 1386 } 1387 } 1388 } 1389} 1390 1391static void handleAllocSizeAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1392 if (!isFunctionOrMethod(D)) { 1393 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1394 << Attr.getName() << ExpectedFunctionOrMethod; 1395 return; 1396 } 1397 1398 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 1399 return; 1400 1401 SmallVector<unsigned, 8> SizeArgs; 1402 for (unsigned i = 0; i < Attr.getNumArgs(); ++i) { 1403 Expr *Ex = Attr.getArgAsExpr(i); 1404 uint64_t Idx; 1405 if (!checkFunctionOrMethodArgumentIndex(S, D, Attr.getName()->getName(), 1406 Attr.getLoc(), i + 1, Ex, Idx)) 1407 return; 1408 1409 // check if the function argument is of an integer type 1410 QualType T = getFunctionOrMethodArgType(D, Idx).getNonReferenceType(); 1411 if (!T->isIntegerType()) { 1412 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) 1413 << Attr.getName() << AANT_ArgumentIntegerConstant 1414 << Ex->getSourceRange(); 1415 return; 1416 } 1417 SizeArgs.push_back(Idx); 1418 } 1419 1420 // check if the function returns a pointer 1421 if (!getFunctionType(D)->getResultType()->isAnyPointerType()) { 1422 S.Diag(Attr.getLoc(), diag::warn_ns_attribute_wrong_return_type) 1423 << Attr.getName() << 0 /*function*/<< 1 /*pointer*/ << D->getSourceRange(); 1424 } 1425 1426 D->addAttr(::new (S.Context) 1427 AllocSizeAttr(Attr.getRange(), S.Context, 1428 SizeArgs.data(), SizeArgs.size(), 1429 Attr.getAttributeSpellingListIndex())); 1430} 1431 1432static void handleNonNullAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1433 // GCC ignores the nonnull attribute on K&R style function prototypes, so we 1434 // ignore it as well 1435 if (!isFunctionOrMethod(D) || !hasFunctionProto(D)) { 1436 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1437 << Attr.getName() << ExpectedFunction; 1438 return; 1439 } 1440 1441 SmallVector<unsigned, 8> NonNullArgs; 1442 for (unsigned i = 0; i < Attr.getNumArgs(); ++i) { 1443 Expr *Ex = Attr.getArgAsExpr(i); 1444 uint64_t Idx; 1445 if (!checkFunctionOrMethodArgumentIndex(S, D, Attr.getName()->getName(), 1446 Attr.getLoc(), i + 1, Ex, Idx)) 1447 return; 1448 1449 // Is the function argument a pointer type? 1450 QualType T = getFunctionOrMethodArgType(D, Idx).getNonReferenceType(); 1451 possibleTransparentUnionPointerType(T); 1452 1453 if (!T->isAnyPointerType() && !T->isBlockPointerType()) { 1454 // FIXME: Should also highlight argument in decl. 1455 S.Diag(Attr.getLoc(), diag::warn_nonnull_pointers_only) 1456 << "nonnull" << Ex->getSourceRange(); 1457 continue; 1458 } 1459 1460 NonNullArgs.push_back(Idx); 1461 } 1462 1463 // If no arguments were specified to __attribute__((nonnull)) then all pointer 1464 // arguments have a nonnull attribute. 1465 if (NonNullArgs.empty()) { 1466 for (unsigned i = 0, e = getFunctionOrMethodNumArgs(D); i != e; ++i) { 1467 QualType T = getFunctionOrMethodArgType(D, i).getNonReferenceType(); 1468 possibleTransparentUnionPointerType(T); 1469 if (T->isAnyPointerType() || T->isBlockPointerType()) 1470 NonNullArgs.push_back(i); 1471 } 1472 1473 // No pointer arguments? 1474 if (NonNullArgs.empty()) { 1475 // Warn the trivial case only if attribute is not coming from a 1476 // macro instantiation. 1477 if (Attr.getLoc().isFileID()) 1478 S.Diag(Attr.getLoc(), diag::warn_attribute_nonnull_no_pointers); 1479 return; 1480 } 1481 } 1482 1483 unsigned *start = &NonNullArgs[0]; 1484 unsigned size = NonNullArgs.size(); 1485 llvm::array_pod_sort(start, start + size); 1486 D->addAttr(::new (S.Context) 1487 NonNullAttr(Attr.getRange(), S.Context, start, size, 1488 Attr.getAttributeSpellingListIndex())); 1489} 1490 1491static const char *ownershipKindToDiagName(OwnershipAttr::OwnershipKind K) { 1492 switch (K) { 1493 case OwnershipAttr::Holds: return "'ownership_holds'"; 1494 case OwnershipAttr::Takes: return "'ownership_takes'"; 1495 case OwnershipAttr::Returns: return "'ownership_returns'"; 1496 } 1497 llvm_unreachable("unknown ownership"); 1498} 1499 1500static void handleOwnershipAttr(Sema &S, Decl *D, const AttributeList &AL) { 1501 // This attribute must be applied to a function declaration. The first 1502 // argument to the attribute must be an identifier, the name of the resource, 1503 // for example: malloc. The following arguments must be argument indexes, the 1504 // arguments must be of integer type for Returns, otherwise of pointer type. 1505 // The difference between Holds and Takes is that a pointer may still be used 1506 // after being held. free() should be __attribute((ownership_takes)), whereas 1507 // a list append function may well be __attribute((ownership_holds)). 1508 1509 if (!AL.isArgIdent(0)) { 1510 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_type) 1511 << AL.getName() << 1 << AANT_ArgumentIdentifier; 1512 return; 1513 } 1514 1515 // Figure out our Kind, and check arguments while we're at it. 1516 OwnershipAttr::OwnershipKind K; 1517 switch (AL.getKind()) { 1518 case AttributeList::AT_ownership_takes: 1519 K = OwnershipAttr::Takes; 1520 if (AL.getNumArgs() < 2) { 1521 S.Diag(AL.getLoc(), diag::err_attribute_too_few_arguments) << 2; 1522 return; 1523 } 1524 break; 1525 case AttributeList::AT_ownership_holds: 1526 K = OwnershipAttr::Holds; 1527 if (AL.getNumArgs() < 2) { 1528 S.Diag(AL.getLoc(), diag::err_attribute_too_few_arguments) << 2; 1529 return; 1530 } 1531 break; 1532 case AttributeList::AT_ownership_returns: 1533 K = OwnershipAttr::Returns; 1534 1535 if (AL.getNumArgs() > 2) { 1536 S.Diag(AL.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1537 return; 1538 } 1539 break; 1540 default: 1541 // This should never happen given how we are called. 1542 llvm_unreachable("Unknown ownership attribute"); 1543 } 1544 1545 if (!isFunction(D) || !hasFunctionProto(D)) { 1546 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type) 1547 << AL.getName() << ExpectedFunction; 1548 return; 1549 } 1550 1551 StringRef Module = AL.getArgAsIdent(0)->Ident->getName(); 1552 1553 // Normalize the argument, __foo__ becomes foo. 1554 if (Module.startswith("__") && Module.endswith("__")) 1555 Module = Module.substr(2, Module.size() - 4); 1556 1557 SmallVector<unsigned, 8> OwnershipArgs; 1558 for (unsigned i = 1; i < AL.getNumArgs(); ++i) { 1559 Expr *Ex = AL.getArgAsExpr(i); 1560 uint64_t Idx; 1561 if (!checkFunctionOrMethodArgumentIndex(S, D, AL.getName()->getName(), 1562 AL.getLoc(), i, Ex, Idx)) 1563 return; 1564 1565 // Is the function argument a pointer type? 1566 QualType T = getFunctionOrMethodArgType(D, Idx); 1567 int Err = -1; // No error 1568 switch (K) { 1569 case OwnershipAttr::Takes: 1570 case OwnershipAttr::Holds: 1571 if (!T->isAnyPointerType() && !T->isBlockPointerType()) 1572 Err = 0; 1573 break; 1574 case OwnershipAttr::Returns: 1575 if (!T->isIntegerType()) 1576 Err = 1; 1577 break; 1578 } 1579 if (-1 != Err) { 1580 S.Diag(AL.getLoc(), diag::err_ownership_type) << AL.getName() << Err 1581 << Ex->getSourceRange(); 1582 return; 1583 } 1584 1585 // Check we don't have a conflict with another ownership attribute. 1586 for (specific_attr_iterator<OwnershipAttr> 1587 i = D->specific_attr_begin<OwnershipAttr>(), 1588 e = D->specific_attr_end<OwnershipAttr>(); i != e; ++i) { 1589 if ((*i)->getOwnKind() != K && (*i)->args_end() != 1590 std::find((*i)->args_begin(), (*i)->args_end(), Idx)) { 1591 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible) 1592 << AL.getName() << ownershipKindToDiagName((*i)->getOwnKind()); 1593 return; 1594 } 1595 } 1596 OwnershipArgs.push_back(Idx); 1597 } 1598 1599 unsigned* start = OwnershipArgs.data(); 1600 unsigned size = OwnershipArgs.size(); 1601 llvm::array_pod_sort(start, start + size); 1602 1603 D->addAttr(::new (S.Context) 1604 OwnershipAttr(AL.getLoc(), S.Context, K, Module, start, size, 1605 AL.getAttributeSpellingListIndex())); 1606} 1607 1608static void handleWeakRefAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1609 // Check the attribute arguments. 1610 if (Attr.getNumArgs() > 1) { 1611 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) 1612 << Attr.getName() << 1; 1613 return; 1614 } 1615 1616 if (!isa<VarDecl>(D) && !isa<FunctionDecl>(D)) { 1617 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1618 << Attr.getName() << ExpectedVariableOrFunction; 1619 return; 1620 } 1621 1622 NamedDecl *nd = cast<NamedDecl>(D); 1623 1624 // gcc rejects 1625 // class c { 1626 // static int a __attribute__((weakref ("v2"))); 1627 // static int b() __attribute__((weakref ("f3"))); 1628 // }; 1629 // and ignores the attributes of 1630 // void f(void) { 1631 // static int a __attribute__((weakref ("v2"))); 1632 // } 1633 // we reject them 1634 const DeclContext *Ctx = D->getDeclContext()->getRedeclContext(); 1635 if (!Ctx->isFileContext()) { 1636 S.Diag(Attr.getLoc(), diag::err_attribute_weakref_not_global_context) << 1637 nd->getNameAsString(); 1638 return; 1639 } 1640 1641 // The GCC manual says 1642 // 1643 // At present, a declaration to which `weakref' is attached can only 1644 // be `static'. 1645 // 1646 // It also says 1647 // 1648 // Without a TARGET, 1649 // given as an argument to `weakref' or to `alias', `weakref' is 1650 // equivalent to `weak'. 1651 // 1652 // gcc 4.4.1 will accept 1653 // int a7 __attribute__((weakref)); 1654 // as 1655 // int a7 __attribute__((weak)); 1656 // This looks like a bug in gcc. We reject that for now. We should revisit 1657 // it if this behaviour is actually used. 1658 1659 // GCC rejects 1660 // static ((alias ("y"), weakref)). 1661 // Should we? How to check that weakref is before or after alias? 1662 1663 // FIXME: it would be good for us to keep the WeakRefAttr as-written instead 1664 // of transforming it into an AliasAttr. The WeakRefAttr never uses the 1665 // StringRef parameter it was given anyway. 1666 StringRef Str; 1667 if (Attr.getNumArgs() && S.checkStringLiteralArgumentAttr(Attr, 0, Str)) 1668 // GCC will accept anything as the argument of weakref. Should we 1669 // check for an existing decl? 1670 D->addAttr(::new (S.Context) AliasAttr(Attr.getRange(), S.Context, Str, 1671 Attr.getAttributeSpellingListIndex())); 1672 1673 D->addAttr(::new (S.Context) 1674 WeakRefAttr(Attr.getRange(), S.Context, 1675 Attr.getAttributeSpellingListIndex())); 1676} 1677 1678static void handleAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1679 StringRef Str; 1680 if (!S.checkStringLiteralArgumentAttr(Attr, 0, Str)) 1681 return; 1682 1683 if (S.Context.getTargetInfo().getTriple().isOSDarwin()) { 1684 S.Diag(Attr.getLoc(), diag::err_alias_not_supported_on_darwin); 1685 return; 1686 } 1687 1688 // FIXME: check if target symbol exists in current file 1689 1690 D->addAttr(::new (S.Context) AliasAttr(Attr.getRange(), S.Context, Str, 1691 Attr.getAttributeSpellingListIndex())); 1692} 1693 1694static void handleMinSizeAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1695 if (!isa<FunctionDecl>(D) && !isa<ObjCMethodDecl>(D)) { 1696 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1697 << Attr.getName() << ExpectedFunctionOrMethod; 1698 return; 1699 } 1700 1701 D->addAttr(::new (S.Context) 1702 MinSizeAttr(Attr.getRange(), S.Context, 1703 Attr.getAttributeSpellingListIndex())); 1704} 1705 1706static void handleColdAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1707 if (!isa<FunctionDecl>(D)) { 1708 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1709 << Attr.getName() << ExpectedFunction; 1710 return; 1711 } 1712 1713 if (D->hasAttr<HotAttr>()) { 1714 S.Diag(Attr.getLoc(), diag::err_attributes_are_not_compatible) 1715 << Attr.getName() << "hot"; 1716 return; 1717 } 1718 1719 D->addAttr(::new (S.Context) ColdAttr(Attr.getRange(), S.Context, 1720 Attr.getAttributeSpellingListIndex())); 1721} 1722 1723static void handleHotAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1724 if (!isa<FunctionDecl>(D)) { 1725 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1726 << Attr.getName() << ExpectedFunction; 1727 return; 1728 } 1729 1730 if (D->hasAttr<ColdAttr>()) { 1731 S.Diag(Attr.getLoc(), diag::err_attributes_are_not_compatible) 1732 << Attr.getName() << "cold"; 1733 return; 1734 } 1735 1736 D->addAttr(::new (S.Context) HotAttr(Attr.getRange(), S.Context, 1737 Attr.getAttributeSpellingListIndex())); 1738} 1739 1740static void handleNakedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1741 if (!isa<FunctionDecl>(D)) { 1742 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1743 << Attr.getName() << ExpectedFunction; 1744 return; 1745 } 1746 1747 D->addAttr(::new (S.Context) 1748 NakedAttr(Attr.getRange(), S.Context, 1749 Attr.getAttributeSpellingListIndex())); 1750} 1751 1752static void handleAlwaysInlineAttr(Sema &S, Decl *D, 1753 const AttributeList &Attr) { 1754 if (!isa<FunctionDecl>(D)) { 1755 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1756 << Attr.getName() << ExpectedFunction; 1757 return; 1758 } 1759 1760 D->addAttr(::new (S.Context) 1761 AlwaysInlineAttr(Attr.getRange(), S.Context, 1762 Attr.getAttributeSpellingListIndex())); 1763} 1764 1765static void handleTLSModelAttr(Sema &S, Decl *D, 1766 const AttributeList &Attr) { 1767 StringRef Model; 1768 SourceLocation LiteralLoc; 1769 // Check that it is a string. 1770 if (!S.checkStringLiteralArgumentAttr(Attr, 0, Model, &LiteralLoc)) 1771 return; 1772 1773 if (!isa<VarDecl>(D) || !cast<VarDecl>(D)->getTLSKind()) { 1774 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1775 << Attr.getName() << ExpectedTLSVar; 1776 return; 1777 } 1778 1779 // Check that the value. 1780 if (Model != "global-dynamic" && Model != "local-dynamic" 1781 && Model != "initial-exec" && Model != "local-exec") { 1782 S.Diag(LiteralLoc, diag::err_attr_tlsmodel_arg); 1783 return; 1784 } 1785 1786 D->addAttr(::new (S.Context) 1787 TLSModelAttr(Attr.getRange(), S.Context, Model, 1788 Attr.getAttributeSpellingListIndex())); 1789} 1790 1791static void handleMallocAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1792 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) { 1793 QualType RetTy = FD->getResultType(); 1794 if (RetTy->isAnyPointerType() || RetTy->isBlockPointerType()) { 1795 D->addAttr(::new (S.Context) 1796 MallocAttr(Attr.getRange(), S.Context, 1797 Attr.getAttributeSpellingListIndex())); 1798 return; 1799 } 1800 } 1801 1802 S.Diag(Attr.getLoc(), diag::warn_attribute_malloc_pointer_only); 1803} 1804 1805static void handleMayAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1806 D->addAttr(::new (S.Context) 1807 MayAliasAttr(Attr.getRange(), S.Context, 1808 Attr.getAttributeSpellingListIndex())); 1809} 1810 1811static void handleNoCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1812 if (isa<VarDecl>(D)) 1813 D->addAttr(::new (S.Context) 1814 NoCommonAttr(Attr.getRange(), S.Context, 1815 Attr.getAttributeSpellingListIndex())); 1816 else 1817 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1818 << Attr.getName() << ExpectedVariable; 1819} 1820 1821static void handleCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1822 if (S.LangOpts.CPlusPlus) { 1823 S.Diag(Attr.getLoc(), diag::err_common_not_supported_cplusplus); 1824 return; 1825 } 1826 1827 if (isa<VarDecl>(D)) 1828 D->addAttr(::new (S.Context) 1829 CommonAttr(Attr.getRange(), S.Context, 1830 Attr.getAttributeSpellingListIndex())); 1831 else 1832 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1833 << Attr.getName() << ExpectedVariable; 1834} 1835 1836static void handleNoReturnAttr(Sema &S, Decl *D, const AttributeList &attr) { 1837 if (hasDeclarator(D)) return; 1838 1839 if (S.CheckNoReturnAttr(attr)) return; 1840 1841 if (!isa<ObjCMethodDecl>(D)) { 1842 S.Diag(attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1843 << attr.getName() << ExpectedFunctionOrMethod; 1844 return; 1845 } 1846 1847 D->addAttr(::new (S.Context) 1848 NoReturnAttr(attr.getRange(), S.Context, 1849 attr.getAttributeSpellingListIndex())); 1850} 1851 1852bool Sema::CheckNoReturnAttr(const AttributeList &attr) { 1853 if (!checkAttributeNumArgs(*this, attr, 0)) { 1854 attr.setInvalid(); 1855 return true; 1856 } 1857 1858 return false; 1859} 1860 1861static void handleAnalyzerNoReturnAttr(Sema &S, Decl *D, 1862 const AttributeList &Attr) { 1863 1864 // The checking path for 'noreturn' and 'analyzer_noreturn' are different 1865 // because 'analyzer_noreturn' does not impact the type. 1866 if (!isFunctionOrMethod(D) && !isa<BlockDecl>(D)) { 1867 ValueDecl *VD = dyn_cast<ValueDecl>(D); 1868 if (VD == 0 || (!VD->getType()->isBlockPointerType() 1869 && !VD->getType()->isFunctionPointerType())) { 1870 S.Diag(Attr.getLoc(), 1871 Attr.isCXX11Attribute() ? diag::err_attribute_wrong_decl_type 1872 : diag::warn_attribute_wrong_decl_type) 1873 << Attr.getName() << ExpectedFunctionMethodOrBlock; 1874 return; 1875 } 1876 } 1877 1878 D->addAttr(::new (S.Context) 1879 AnalyzerNoReturnAttr(Attr.getRange(), S.Context, 1880 Attr.getAttributeSpellingListIndex())); 1881} 1882 1883static void handleCXX11NoReturnAttr(Sema &S, Decl *D, 1884 const AttributeList &Attr) { 1885 // C++11 [dcl.attr.noreturn]p1: 1886 // The attribute may be applied to the declarator-id in a function 1887 // declaration. 1888 FunctionDecl *FD = dyn_cast<FunctionDecl>(D); 1889 if (!FD) { 1890 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1891 << Attr.getName() << ExpectedFunctionOrMethod; 1892 return; 1893 } 1894 1895 D->addAttr(::new (S.Context) 1896 CXX11NoReturnAttr(Attr.getRange(), S.Context, 1897 Attr.getAttributeSpellingListIndex())); 1898} 1899 1900// PS3 PPU-specific. 1901static void handleVecReturnAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1902/* 1903 Returning a Vector Class in Registers 1904 1905 According to the PPU ABI specifications, a class with a single member of 1906 vector type is returned in memory when used as the return value of a function. 1907 This results in inefficient code when implementing vector classes. To return 1908 the value in a single vector register, add the vecreturn attribute to the 1909 class definition. This attribute is also applicable to struct types. 1910 1911 Example: 1912 1913 struct Vector 1914 { 1915 __vector float xyzw; 1916 } __attribute__((vecreturn)); 1917 1918 Vector Add(Vector lhs, Vector rhs) 1919 { 1920 Vector result; 1921 result.xyzw = vec_add(lhs.xyzw, rhs.xyzw); 1922 return result; // This will be returned in a register 1923 } 1924*/ 1925 if (!isa<RecordDecl>(D)) { 1926 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1927 << Attr.getName() << ExpectedClass; 1928 return; 1929 } 1930 1931 if (D->getAttr<VecReturnAttr>()) { 1932 S.Diag(Attr.getLoc(), diag::err_repeat_attribute) << "vecreturn"; 1933 return; 1934 } 1935 1936 RecordDecl *record = cast<RecordDecl>(D); 1937 int count = 0; 1938 1939 if (!isa<CXXRecordDecl>(record)) { 1940 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 1941 return; 1942 } 1943 1944 if (!cast<CXXRecordDecl>(record)->isPOD()) { 1945 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_pod_record); 1946 return; 1947 } 1948 1949 for (RecordDecl::field_iterator iter = record->field_begin(); 1950 iter != record->field_end(); iter++) { 1951 if ((count == 1) || !iter->getType()->isVectorType()) { 1952 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 1953 return; 1954 } 1955 count++; 1956 } 1957 1958 D->addAttr(::new (S.Context) 1959 VecReturnAttr(Attr.getRange(), S.Context, 1960 Attr.getAttributeSpellingListIndex())); 1961} 1962 1963static void handleDependencyAttr(Sema &S, Scope *Scope, Decl *D, 1964 const AttributeList &Attr) { 1965 if (isa<ParmVarDecl>(D)) { 1966 // [[carries_dependency]] can only be applied to a parameter if it is a 1967 // parameter of a function declaration or lambda. 1968 if (!(Scope->getFlags() & clang::Scope::FunctionDeclarationScope)) { 1969 S.Diag(Attr.getLoc(), 1970 diag::err_carries_dependency_param_not_function_decl); 1971 return; 1972 } 1973 } else if (!isa<FunctionDecl>(D)) { 1974 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1975 << Attr.getName() << ExpectedFunctionMethodOrParameter; 1976 return; 1977 } 1978 1979 D->addAttr(::new (S.Context) CarriesDependencyAttr( 1980 Attr.getRange(), S.Context, 1981 Attr.getAttributeSpellingListIndex())); 1982} 1983 1984static void handleUnusedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1985 if (!isa<VarDecl>(D) && !isa<ObjCIvarDecl>(D) && !isFunctionOrMethod(D) && 1986 !isa<TypeDecl>(D) && !isa<LabelDecl>(D) && !isa<FieldDecl>(D)) { 1987 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1988 << Attr.getName() << ExpectedVariableFunctionOrLabel; 1989 return; 1990 } 1991 1992 D->addAttr(::new (S.Context) 1993 UnusedAttr(Attr.getRange(), S.Context, 1994 Attr.getAttributeSpellingListIndex())); 1995} 1996 1997static void handleReturnsTwiceAttr(Sema &S, Decl *D, 1998 const AttributeList &Attr) { 1999 if (!isa<FunctionDecl>(D)) { 2000 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2001 << Attr.getName() << ExpectedFunction; 2002 return; 2003 } 2004 2005 D->addAttr(::new (S.Context) 2006 ReturnsTwiceAttr(Attr.getRange(), S.Context, 2007 Attr.getAttributeSpellingListIndex())); 2008} 2009 2010static void handleUsedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2011 if (const VarDecl *VD = dyn_cast<VarDecl>(D)) { 2012 if (VD->hasLocalStorage()) { 2013 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "used"; 2014 return; 2015 } 2016 } else if (!isFunctionOrMethod(D)) { 2017 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2018 << Attr.getName() << ExpectedVariableOrFunction; 2019 return; 2020 } 2021 2022 D->addAttr(::new (S.Context) 2023 UsedAttr(Attr.getRange(), S.Context, 2024 Attr.getAttributeSpellingListIndex())); 2025} 2026 2027static void handleConstructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2028 // check the attribute arguments. 2029 if (Attr.getNumArgs() > 1) { 2030 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 2031 return; 2032 } 2033 2034 int priority = 65535; // FIXME: Do not hardcode such constants. 2035 if (Attr.getNumArgs() > 0) { 2036 Expr *E = Attr.getArgAsExpr(0); 2037 llvm::APSInt Idx(32); 2038 if (E->isTypeDependent() || E->isValueDependent() || 2039 !E->isIntegerConstantExpr(Idx, S.Context)) { 2040 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 2041 << Attr.getName() << 1 << AANT_ArgumentIntegerConstant 2042 << E->getSourceRange(); 2043 return; 2044 } 2045 priority = Idx.getZExtValue(); 2046 } 2047 2048 if (!isa<FunctionDecl>(D)) { 2049 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2050 << Attr.getName() << ExpectedFunction; 2051 return; 2052 } 2053 2054 D->addAttr(::new (S.Context) 2055 ConstructorAttr(Attr.getRange(), S.Context, priority, 2056 Attr.getAttributeSpellingListIndex())); 2057} 2058 2059static void handleDestructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2060 // check the attribute arguments. 2061 if (Attr.getNumArgs() > 1) { 2062 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 2063 return; 2064 } 2065 2066 int priority = 65535; // FIXME: Do not hardcode such constants. 2067 if (Attr.getNumArgs() > 0) { 2068 Expr *E = Attr.getArgAsExpr(0); 2069 llvm::APSInt Idx(32); 2070 if (E->isTypeDependent() || E->isValueDependent() || 2071 !E->isIntegerConstantExpr(Idx, S.Context)) { 2072 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 2073 << Attr.getName() << 1 << AANT_ArgumentIntegerConstant 2074 << E->getSourceRange(); 2075 return; 2076 } 2077 priority = Idx.getZExtValue(); 2078 } 2079 2080 if (!isa<FunctionDecl>(D)) { 2081 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2082 << Attr.getName() << ExpectedFunction; 2083 return; 2084 } 2085 2086 D->addAttr(::new (S.Context) 2087 DestructorAttr(Attr.getRange(), S.Context, priority, 2088 Attr.getAttributeSpellingListIndex())); 2089} 2090 2091template <typename AttrTy> 2092static void handleAttrWithMessage(Sema &S, Decl *D, 2093 const AttributeList &Attr) { 2094 unsigned NumArgs = Attr.getNumArgs(); 2095 if (NumArgs > 1) { 2096 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 2097 return; 2098 } 2099 2100 // Handle the case where the attribute has a text message. 2101 StringRef Str; 2102 if (NumArgs == 1 && !S.checkStringLiteralArgumentAttr(Attr, 0, Str)) 2103 return; 2104 2105 D->addAttr(::new (S.Context) AttrTy(Attr.getRange(), S.Context, Str, 2106 Attr.getAttributeSpellingListIndex())); 2107} 2108 2109static void handleArcWeakrefUnavailableAttr(Sema &S, Decl *D, 2110 const AttributeList &Attr) { 2111 D->addAttr(::new (S.Context) 2112 ArcWeakrefUnavailableAttr(Attr.getRange(), S.Context, 2113 Attr.getAttributeSpellingListIndex())); 2114} 2115 2116static void handleObjCRootClassAttr(Sema &S, Decl *D, 2117 const AttributeList &Attr) { 2118 if (!isa<ObjCInterfaceDecl>(D)) { 2119 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 2120 << Attr.getName() << ExpectedObjectiveCInterface; 2121 return; 2122 } 2123 2124 D->addAttr(::new (S.Context) 2125 ObjCRootClassAttr(Attr.getRange(), S.Context, 2126 Attr.getAttributeSpellingListIndex())); 2127} 2128 2129static void handleObjCRequiresPropertyDefsAttr(Sema &S, Decl *D, 2130 const AttributeList &Attr) { 2131 if (!isa<ObjCInterfaceDecl>(D)) { 2132 S.Diag(Attr.getLoc(), diag::err_suppress_autosynthesis); 2133 return; 2134 } 2135 2136 D->addAttr(::new (S.Context) 2137 ObjCRequiresPropertyDefsAttr(Attr.getRange(), S.Context, 2138 Attr.getAttributeSpellingListIndex())); 2139} 2140 2141static bool checkAvailabilityAttr(Sema &S, SourceRange Range, 2142 IdentifierInfo *Platform, 2143 VersionTuple Introduced, 2144 VersionTuple Deprecated, 2145 VersionTuple Obsoleted) { 2146 StringRef PlatformName 2147 = AvailabilityAttr::getPrettyPlatformName(Platform->getName()); 2148 if (PlatformName.empty()) 2149 PlatformName = Platform->getName(); 2150 2151 // Ensure that Introduced <= Deprecated <= Obsoleted (although not all 2152 // of these steps are needed). 2153 if (!Introduced.empty() && !Deprecated.empty() && 2154 !(Introduced <= Deprecated)) { 2155 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering) 2156 << 1 << PlatformName << Deprecated.getAsString() 2157 << 0 << Introduced.getAsString(); 2158 return true; 2159 } 2160 2161 if (!Introduced.empty() && !Obsoleted.empty() && 2162 !(Introduced <= Obsoleted)) { 2163 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering) 2164 << 2 << PlatformName << Obsoleted.getAsString() 2165 << 0 << Introduced.getAsString(); 2166 return true; 2167 } 2168 2169 if (!Deprecated.empty() && !Obsoleted.empty() && 2170 !(Deprecated <= Obsoleted)) { 2171 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering) 2172 << 2 << PlatformName << Obsoleted.getAsString() 2173 << 1 << Deprecated.getAsString(); 2174 return true; 2175 } 2176 2177 return false; 2178} 2179 2180/// \brief Check whether the two versions match. 2181/// 2182/// If either version tuple is empty, then they are assumed to match. If 2183/// \p BeforeIsOkay is true, then \p X can be less than or equal to \p Y. 2184static bool versionsMatch(const VersionTuple &X, const VersionTuple &Y, 2185 bool BeforeIsOkay) { 2186 if (X.empty() || Y.empty()) 2187 return true; 2188 2189 if (X == Y) 2190 return true; 2191 2192 if (BeforeIsOkay && X < Y) 2193 return true; 2194 2195 return false; 2196} 2197 2198AvailabilityAttr *Sema::mergeAvailabilityAttr(NamedDecl *D, SourceRange Range, 2199 IdentifierInfo *Platform, 2200 VersionTuple Introduced, 2201 VersionTuple Deprecated, 2202 VersionTuple Obsoleted, 2203 bool IsUnavailable, 2204 StringRef Message, 2205 bool Override, 2206 unsigned AttrSpellingListIndex) { 2207 VersionTuple MergedIntroduced = Introduced; 2208 VersionTuple MergedDeprecated = Deprecated; 2209 VersionTuple MergedObsoleted = Obsoleted; 2210 bool FoundAny = false; 2211 2212 if (D->hasAttrs()) { 2213 AttrVec &Attrs = D->getAttrs(); 2214 for (unsigned i = 0, e = Attrs.size(); i != e;) { 2215 const AvailabilityAttr *OldAA = dyn_cast<AvailabilityAttr>(Attrs[i]); 2216 if (!OldAA) { 2217 ++i; 2218 continue; 2219 } 2220 2221 IdentifierInfo *OldPlatform = OldAA->getPlatform(); 2222 if (OldPlatform != Platform) { 2223 ++i; 2224 continue; 2225 } 2226 2227 FoundAny = true; 2228 VersionTuple OldIntroduced = OldAA->getIntroduced(); 2229 VersionTuple OldDeprecated = OldAA->getDeprecated(); 2230 VersionTuple OldObsoleted = OldAA->getObsoleted(); 2231 bool OldIsUnavailable = OldAA->getUnavailable(); 2232 2233 if (!versionsMatch(OldIntroduced, Introduced, Override) || 2234 !versionsMatch(Deprecated, OldDeprecated, Override) || 2235 !versionsMatch(Obsoleted, OldObsoleted, Override) || 2236 !(OldIsUnavailable == IsUnavailable || 2237 (Override && !OldIsUnavailable && IsUnavailable))) { 2238 if (Override) { 2239 int Which = -1; 2240 VersionTuple FirstVersion; 2241 VersionTuple SecondVersion; 2242 if (!versionsMatch(OldIntroduced, Introduced, Override)) { 2243 Which = 0; 2244 FirstVersion = OldIntroduced; 2245 SecondVersion = Introduced; 2246 } else if (!versionsMatch(Deprecated, OldDeprecated, Override)) { 2247 Which = 1; 2248 FirstVersion = Deprecated; 2249 SecondVersion = OldDeprecated; 2250 } else if (!versionsMatch(Obsoleted, OldObsoleted, Override)) { 2251 Which = 2; 2252 FirstVersion = Obsoleted; 2253 SecondVersion = OldObsoleted; 2254 } 2255 2256 if (Which == -1) { 2257 Diag(OldAA->getLocation(), 2258 diag::warn_mismatched_availability_override_unavail) 2259 << AvailabilityAttr::getPrettyPlatformName(Platform->getName()); 2260 } else { 2261 Diag(OldAA->getLocation(), 2262 diag::warn_mismatched_availability_override) 2263 << Which 2264 << AvailabilityAttr::getPrettyPlatformName(Platform->getName()) 2265 << FirstVersion.getAsString() << SecondVersion.getAsString(); 2266 } 2267 Diag(Range.getBegin(), diag::note_overridden_method); 2268 } else { 2269 Diag(OldAA->getLocation(), diag::warn_mismatched_availability); 2270 Diag(Range.getBegin(), diag::note_previous_attribute); 2271 } 2272 2273 Attrs.erase(Attrs.begin() + i); 2274 --e; 2275 continue; 2276 } 2277 2278 VersionTuple MergedIntroduced2 = MergedIntroduced; 2279 VersionTuple MergedDeprecated2 = MergedDeprecated; 2280 VersionTuple MergedObsoleted2 = MergedObsoleted; 2281 2282 if (MergedIntroduced2.empty()) 2283 MergedIntroduced2 = OldIntroduced; 2284 if (MergedDeprecated2.empty()) 2285 MergedDeprecated2 = OldDeprecated; 2286 if (MergedObsoleted2.empty()) 2287 MergedObsoleted2 = OldObsoleted; 2288 2289 if (checkAvailabilityAttr(*this, OldAA->getRange(), Platform, 2290 MergedIntroduced2, MergedDeprecated2, 2291 MergedObsoleted2)) { 2292 Attrs.erase(Attrs.begin() + i); 2293 --e; 2294 continue; 2295 } 2296 2297 MergedIntroduced = MergedIntroduced2; 2298 MergedDeprecated = MergedDeprecated2; 2299 MergedObsoleted = MergedObsoleted2; 2300 ++i; 2301 } 2302 } 2303 2304 if (FoundAny && 2305 MergedIntroduced == Introduced && 2306 MergedDeprecated == Deprecated && 2307 MergedObsoleted == Obsoleted) 2308 return NULL; 2309 2310 // Only create a new attribute if !Override, but we want to do 2311 // the checking. 2312 if (!checkAvailabilityAttr(*this, Range, Platform, MergedIntroduced, 2313 MergedDeprecated, MergedObsoleted) && 2314 !Override) { 2315 return ::new (Context) AvailabilityAttr(Range, Context, Platform, 2316 Introduced, Deprecated, 2317 Obsoleted, IsUnavailable, Message, 2318 AttrSpellingListIndex); 2319 } 2320 return NULL; 2321} 2322 2323static void handleAvailabilityAttr(Sema &S, Decl *D, 2324 const AttributeList &Attr) { 2325 if (!checkAttributeNumArgs(S, Attr, 1)) 2326 return; 2327 IdentifierLoc *Platform = Attr.getArgAsIdent(0); 2328 unsigned Index = Attr.getAttributeSpellingListIndex(); 2329 2330 IdentifierInfo *II = Platform->Ident; 2331 if (AvailabilityAttr::getPrettyPlatformName(II->getName()).empty()) 2332 S.Diag(Platform->Loc, diag::warn_availability_unknown_platform) 2333 << Platform->Ident; 2334 2335 NamedDecl *ND = dyn_cast<NamedDecl>(D); 2336 if (!ND) { 2337 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 2338 return; 2339 } 2340 2341 AvailabilityChange Introduced = Attr.getAvailabilityIntroduced(); 2342 AvailabilityChange Deprecated = Attr.getAvailabilityDeprecated(); 2343 AvailabilityChange Obsoleted = Attr.getAvailabilityObsoleted(); 2344 bool IsUnavailable = Attr.getUnavailableLoc().isValid(); 2345 StringRef Str; 2346 if (const StringLiteral *SE = 2347 dyn_cast_or_null<StringLiteral>(Attr.getMessageExpr())) 2348 Str = SE->getString(); 2349 2350 AvailabilityAttr *NewAttr = S.mergeAvailabilityAttr(ND, Attr.getRange(), II, 2351 Introduced.Version, 2352 Deprecated.Version, 2353 Obsoleted.Version, 2354 IsUnavailable, Str, 2355 /*Override=*/false, 2356 Index); 2357 if (NewAttr) 2358 D->addAttr(NewAttr); 2359} 2360 2361template <class T> 2362static T *mergeVisibilityAttr(Sema &S, Decl *D, SourceRange range, 2363 typename T::VisibilityType value, 2364 unsigned attrSpellingListIndex) { 2365 T *existingAttr = D->getAttr<T>(); 2366 if (existingAttr) { 2367 typename T::VisibilityType existingValue = existingAttr->getVisibility(); 2368 if (existingValue == value) 2369 return NULL; 2370 S.Diag(existingAttr->getLocation(), diag::err_mismatched_visibility); 2371 S.Diag(range.getBegin(), diag::note_previous_attribute); 2372 D->dropAttr<T>(); 2373 } 2374 return ::new (S.Context) T(range, S.Context, value, attrSpellingListIndex); 2375} 2376 2377VisibilityAttr *Sema::mergeVisibilityAttr(Decl *D, SourceRange Range, 2378 VisibilityAttr::VisibilityType Vis, 2379 unsigned AttrSpellingListIndex) { 2380 return ::mergeVisibilityAttr<VisibilityAttr>(*this, D, Range, Vis, 2381 AttrSpellingListIndex); 2382} 2383 2384TypeVisibilityAttr *Sema::mergeTypeVisibilityAttr(Decl *D, SourceRange Range, 2385 TypeVisibilityAttr::VisibilityType Vis, 2386 unsigned AttrSpellingListIndex) { 2387 return ::mergeVisibilityAttr<TypeVisibilityAttr>(*this, D, Range, Vis, 2388 AttrSpellingListIndex); 2389} 2390 2391static void handleVisibilityAttr(Sema &S, Decl *D, const AttributeList &Attr, 2392 bool isTypeVisibility) { 2393 // Visibility attributes don't mean anything on a typedef. 2394 if (isa<TypedefNameDecl>(D)) { 2395 S.Diag(Attr.getRange().getBegin(), diag::warn_attribute_ignored) 2396 << Attr.getName(); 2397 return; 2398 } 2399 2400 // 'type_visibility' can only go on a type or namespace. 2401 if (isTypeVisibility && 2402 !(isa<TagDecl>(D) || 2403 isa<ObjCInterfaceDecl>(D) || 2404 isa<NamespaceDecl>(D))) { 2405 S.Diag(Attr.getRange().getBegin(), diag::err_attribute_wrong_decl_type) 2406 << Attr.getName() << ExpectedTypeOrNamespace; 2407 return; 2408 } 2409 2410 // Check that the argument is a string literal. 2411 StringRef TypeStr; 2412 SourceLocation LiteralLoc; 2413 if (!S.checkStringLiteralArgumentAttr(Attr, 0, TypeStr, &LiteralLoc)) 2414 return; 2415 2416 VisibilityAttr::VisibilityType type; 2417 if (!VisibilityAttr::ConvertStrToVisibilityType(TypeStr, type)) { 2418 S.Diag(LiteralLoc, diag::warn_attribute_type_not_supported) 2419 << Attr.getName() << TypeStr; 2420 return; 2421 } 2422 2423 // Complain about attempts to use protected visibility on targets 2424 // (like Darwin) that don't support it. 2425 if (type == VisibilityAttr::Protected && 2426 !S.Context.getTargetInfo().hasProtectedVisibility()) { 2427 S.Diag(Attr.getLoc(), diag::warn_attribute_protected_visibility); 2428 type = VisibilityAttr::Default; 2429 } 2430 2431 unsigned Index = Attr.getAttributeSpellingListIndex(); 2432 clang::Attr *newAttr; 2433 if (isTypeVisibility) { 2434 newAttr = S.mergeTypeVisibilityAttr(D, Attr.getRange(), 2435 (TypeVisibilityAttr::VisibilityType) type, 2436 Index); 2437 } else { 2438 newAttr = S.mergeVisibilityAttr(D, Attr.getRange(), type, Index); 2439 } 2440 if (newAttr) 2441 D->addAttr(newAttr); 2442} 2443 2444static void handleObjCMethodFamilyAttr(Sema &S, Decl *decl, 2445 const AttributeList &Attr) { 2446 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(decl); 2447 if (!method) { 2448 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 2449 << ExpectedMethod; 2450 return; 2451 } 2452 2453 if (!Attr.isArgIdent(0)) { 2454 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 2455 << Attr.getName() << 1 << AANT_ArgumentIdentifier; 2456 return; 2457 } 2458 2459 IdentifierLoc *IL = Attr.getArgAsIdent(0); 2460 ObjCMethodFamilyAttr::FamilyKind F; 2461 if (!ObjCMethodFamilyAttr::ConvertStrToFamilyKind(IL->Ident->getName(), F)) { 2462 S.Diag(IL->Loc, diag::warn_attribute_type_not_supported) << Attr.getName() 2463 << IL->Ident; 2464 return; 2465 } 2466 2467 if (F == ObjCMethodFamilyAttr::OMF_init && 2468 !method->getResultType()->isObjCObjectPointerType()) { 2469 S.Diag(method->getLocation(), diag::err_init_method_bad_return_type) 2470 << method->getResultType(); 2471 // Ignore the attribute. 2472 return; 2473 } 2474 2475 method->addAttr(new (S.Context) ObjCMethodFamilyAttr(Attr.getRange(), 2476 S.Context, F)); 2477} 2478 2479static void handleObjCExceptionAttr(Sema &S, Decl *D, 2480 const AttributeList &Attr) { 2481 ObjCInterfaceDecl *OCI = dyn_cast<ObjCInterfaceDecl>(D); 2482 if (OCI == 0) { 2483 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 2484 << Attr.getName() << ExpectedObjectiveCInterface; 2485 return; 2486 } 2487 2488 D->addAttr(::new (S.Context) 2489 ObjCExceptionAttr(Attr.getRange(), S.Context, 2490 Attr.getAttributeSpellingListIndex())); 2491} 2492 2493static void handleObjCNSObject(Sema &S, Decl *D, const AttributeList &Attr) { 2494 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) { 2495 QualType T = TD->getUnderlyingType(); 2496 if (!T->isCARCBridgableType()) { 2497 S.Diag(TD->getLocation(), diag::err_nsobject_attribute); 2498 return; 2499 } 2500 } 2501 else if (ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(D)) { 2502 QualType T = PD->getType(); 2503 if (!T->isCARCBridgableType()) { 2504 S.Diag(PD->getLocation(), diag::err_nsobject_attribute); 2505 return; 2506 } 2507 } 2508 else { 2509 // It is okay to include this attribute on properties, e.g.: 2510 // 2511 // @property (retain, nonatomic) struct Bork *Q __attribute__((NSObject)); 2512 // 2513 // In this case it follows tradition and suppresses an error in the above 2514 // case. 2515 S.Diag(D->getLocation(), diag::warn_nsobject_attribute); 2516 } 2517 D->addAttr(::new (S.Context) 2518 ObjCNSObjectAttr(Attr.getRange(), S.Context, 2519 Attr.getAttributeSpellingListIndex())); 2520} 2521 2522static void 2523handleOverloadableAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2524 if (!isa<FunctionDecl>(D)) { 2525 S.Diag(Attr.getLoc(), diag::err_attribute_overloadable_not_function); 2526 return; 2527 } 2528 2529 D->addAttr(::new (S.Context) 2530 OverloadableAttr(Attr.getRange(), S.Context, 2531 Attr.getAttributeSpellingListIndex())); 2532} 2533 2534static void handleBlocksAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2535 if (!Attr.isArgIdent(0)) { 2536 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 2537 << Attr.getName() << 1 << AANT_ArgumentIdentifier; 2538 return; 2539 } 2540 2541 IdentifierInfo *II = Attr.getArgAsIdent(0)->Ident; 2542 BlocksAttr::BlockType type; 2543 if (!BlocksAttr::ConvertStrToBlockType(II->getName(), type)) { 2544 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 2545 << Attr.getName() << II; 2546 return; 2547 } 2548 2549 D->addAttr(::new (S.Context) 2550 BlocksAttr(Attr.getRange(), S.Context, type, 2551 Attr.getAttributeSpellingListIndex())); 2552} 2553 2554static void handleSentinelAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2555 // check the attribute arguments. 2556 if (Attr.getNumArgs() > 2) { 2557 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 2558 return; 2559 } 2560 2561 unsigned sentinel = 0; 2562 if (Attr.getNumArgs() > 0) { 2563 Expr *E = Attr.getArgAsExpr(0); 2564 llvm::APSInt Idx(32); 2565 if (E->isTypeDependent() || E->isValueDependent() || 2566 !E->isIntegerConstantExpr(Idx, S.Context)) { 2567 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 2568 << Attr.getName() << 1 << AANT_ArgumentIntegerConstant 2569 << E->getSourceRange(); 2570 return; 2571 } 2572 2573 if (Idx.isSigned() && Idx.isNegative()) { 2574 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_less_than_zero) 2575 << E->getSourceRange(); 2576 return; 2577 } 2578 2579 sentinel = Idx.getZExtValue(); 2580 } 2581 2582 unsigned nullPos = 0; 2583 if (Attr.getNumArgs() > 1) { 2584 Expr *E = Attr.getArgAsExpr(1); 2585 llvm::APSInt Idx(32); 2586 if (E->isTypeDependent() || E->isValueDependent() || 2587 !E->isIntegerConstantExpr(Idx, S.Context)) { 2588 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 2589 << Attr.getName() << 2 << AANT_ArgumentIntegerConstant 2590 << E->getSourceRange(); 2591 return; 2592 } 2593 nullPos = Idx.getZExtValue(); 2594 2595 if ((Idx.isSigned() && Idx.isNegative()) || nullPos > 1) { 2596 // FIXME: This error message could be improved, it would be nice 2597 // to say what the bounds actually are. 2598 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_not_zero_or_one) 2599 << E->getSourceRange(); 2600 return; 2601 } 2602 } 2603 2604 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) { 2605 const FunctionType *FT = FD->getType()->castAs<FunctionType>(); 2606 if (isa<FunctionNoProtoType>(FT)) { 2607 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_named_arguments); 2608 return; 2609 } 2610 2611 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 2612 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 2613 return; 2614 } 2615 } else if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) { 2616 if (!MD->isVariadic()) { 2617 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 2618 return; 2619 } 2620 } else if (BlockDecl *BD = dyn_cast<BlockDecl>(D)) { 2621 if (!BD->isVariadic()) { 2622 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 1; 2623 return; 2624 } 2625 } else if (const VarDecl *V = dyn_cast<VarDecl>(D)) { 2626 QualType Ty = V->getType(); 2627 if (Ty->isBlockPointerType() || Ty->isFunctionPointerType()) { 2628 const FunctionType *FT = Ty->isFunctionPointerType() ? getFunctionType(D) 2629 : Ty->getAs<BlockPointerType>()->getPointeeType()->getAs<FunctionType>(); 2630 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 2631 int m = Ty->isFunctionPointerType() ? 0 : 1; 2632 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << m; 2633 return; 2634 } 2635 } else { 2636 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2637 << Attr.getName() << ExpectedFunctionMethodOrBlock; 2638 return; 2639 } 2640 } else { 2641 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2642 << Attr.getName() << ExpectedFunctionMethodOrBlock; 2643 return; 2644 } 2645 D->addAttr(::new (S.Context) 2646 SentinelAttr(Attr.getRange(), S.Context, sentinel, nullPos, 2647 Attr.getAttributeSpellingListIndex())); 2648} 2649 2650static void handleWarnUnusedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2651 if (RecordDecl *RD = dyn_cast<RecordDecl>(D)) 2652 RD->addAttr(::new (S.Context) WarnUnusedAttr(Attr.getRange(), S.Context)); 2653 else 2654 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 2655} 2656 2657static void handleWarnUnusedResult(Sema &S, Decl *D, const AttributeList &Attr) { 2658 if (!isFunction(D) && !isa<ObjCMethodDecl>(D) && !isa<CXXRecordDecl>(D)) { 2659 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2660 << Attr.getName() << ExpectedFunctionMethodOrClass; 2661 return; 2662 } 2663 2664 if (isFunction(D) && getFunctionType(D)->getResultType()->isVoidType()) { 2665 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 2666 << Attr.getName() << 0; 2667 return; 2668 } 2669 if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 2670 if (MD->getResultType()->isVoidType()) { 2671 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 2672 << Attr.getName() << 1; 2673 return; 2674 } 2675 2676 D->addAttr(::new (S.Context) 2677 WarnUnusedResultAttr(Attr.getRange(), S.Context, 2678 Attr.getAttributeSpellingListIndex())); 2679} 2680 2681static void handleWeakAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2682 if (!isa<VarDecl>(D) && !isa<FunctionDecl>(D)) { 2683 if (isa<CXXRecordDecl>(D)) { 2684 D->addAttr(::new (S.Context) WeakAttr(Attr.getRange(), S.Context)); 2685 return; 2686 } 2687 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2688 << Attr.getName() << ExpectedVariableOrFunction; 2689 return; 2690 } 2691 2692 NamedDecl *nd = cast<NamedDecl>(D); 2693 2694 nd->addAttr(::new (S.Context) 2695 WeakAttr(Attr.getRange(), S.Context, 2696 Attr.getAttributeSpellingListIndex())); 2697} 2698 2699static void handleWeakImportAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2700 // weak_import only applies to variable & function declarations. 2701 bool isDef = false; 2702 if (!D->canBeWeakImported(isDef)) { 2703 if (isDef) 2704 S.Diag(Attr.getLoc(), diag::warn_attribute_invalid_on_definition) 2705 << "weak_import"; 2706 else if (isa<ObjCPropertyDecl>(D) || isa<ObjCMethodDecl>(D) || 2707 (S.Context.getTargetInfo().getTriple().isOSDarwin() && 2708 (isa<ObjCInterfaceDecl>(D) || isa<EnumDecl>(D)))) { 2709 // Nothing to warn about here. 2710 } else 2711 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2712 << Attr.getName() << ExpectedVariableOrFunction; 2713 2714 return; 2715 } 2716 2717 D->addAttr(::new (S.Context) 2718 WeakImportAttr(Attr.getRange(), S.Context, 2719 Attr.getAttributeSpellingListIndex())); 2720} 2721 2722// Handles reqd_work_group_size and work_group_size_hint. 2723static void handleWorkGroupSize(Sema &S, Decl *D, 2724 const AttributeList &Attr) { 2725 unsigned WGSize[3]; 2726 for (unsigned i = 0; i < 3; ++i) { 2727 Expr *E = Attr.getArgAsExpr(i); 2728 llvm::APSInt ArgNum(32); 2729 if (E->isTypeDependent() || E->isValueDependent() || 2730 !E->isIntegerConstantExpr(ArgNum, S.Context)) { 2731 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) 2732 << Attr.getName() << AANT_ArgumentIntegerConstant 2733 << E->getSourceRange(); 2734 return; 2735 } 2736 WGSize[i] = (unsigned) ArgNum.getZExtValue(); 2737 } 2738 2739 if (Attr.getKind() == AttributeList::AT_ReqdWorkGroupSize 2740 && D->hasAttr<ReqdWorkGroupSizeAttr>()) { 2741 ReqdWorkGroupSizeAttr *A = D->getAttr<ReqdWorkGroupSizeAttr>(); 2742 if (!(A->getXDim() == WGSize[0] && 2743 A->getYDim() == WGSize[1] && 2744 A->getZDim() == WGSize[2])) { 2745 S.Diag(Attr.getLoc(), diag::warn_duplicate_attribute) << 2746 Attr.getName(); 2747 } 2748 } 2749 2750 if (Attr.getKind() == AttributeList::AT_WorkGroupSizeHint 2751 && D->hasAttr<WorkGroupSizeHintAttr>()) { 2752 WorkGroupSizeHintAttr *A = D->getAttr<WorkGroupSizeHintAttr>(); 2753 if (!(A->getXDim() == WGSize[0] && 2754 A->getYDim() == WGSize[1] && 2755 A->getZDim() == WGSize[2])) { 2756 S.Diag(Attr.getLoc(), diag::warn_duplicate_attribute) << 2757 Attr.getName(); 2758 } 2759 } 2760 2761 if (Attr.getKind() == AttributeList::AT_ReqdWorkGroupSize) 2762 D->addAttr(::new (S.Context) 2763 ReqdWorkGroupSizeAttr(Attr.getRange(), S.Context, 2764 WGSize[0], WGSize[1], WGSize[2], 2765 Attr.getAttributeSpellingListIndex())); 2766 else 2767 D->addAttr(::new (S.Context) 2768 WorkGroupSizeHintAttr(Attr.getRange(), S.Context, 2769 WGSize[0], WGSize[1], WGSize[2], 2770 Attr.getAttributeSpellingListIndex())); 2771} 2772 2773static void handleVecTypeHint(Sema &S, Decl *D, const AttributeList &Attr) { 2774 assert(Attr.getKind() == AttributeList::AT_VecTypeHint); 2775 2776 if (!checkAttributeNumArgs(S, Attr, 0)) 2777 return; 2778 2779 if (!Attr.hasParsedType()) { 2780 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) 2781 << Attr.getName() << 1; 2782 return; 2783 } 2784 2785 QualType ParmType = S.GetTypeFromParser(Attr.getTypeArg()); 2786 2787 if (!ParmType->isExtVectorType() && !ParmType->isFloatingType() && 2788 (ParmType->isBooleanType() || 2789 !ParmType->isIntegralType(S.getASTContext()))) { 2790 S.Diag(Attr.getLoc(), diag::err_attribute_argument_vec_type_hint) 2791 << ParmType; 2792 return; 2793 } 2794 2795 if (Attr.getKind() == AttributeList::AT_VecTypeHint && 2796 D->hasAttr<VecTypeHintAttr>()) { 2797 VecTypeHintAttr *A = D->getAttr<VecTypeHintAttr>(); 2798 if (A->getTypeHint() != ParmType) { 2799 S.Diag(Attr.getLoc(), diag::warn_duplicate_attribute) << Attr.getName(); 2800 return; 2801 } 2802 } 2803 2804 D->addAttr(::new (S.Context) VecTypeHintAttr(Attr.getLoc(), S.Context, 2805 ParmType, Attr.getLoc())); 2806} 2807 2808SectionAttr *Sema::mergeSectionAttr(Decl *D, SourceRange Range, 2809 StringRef Name, 2810 unsigned AttrSpellingListIndex) { 2811 if (SectionAttr *ExistingAttr = D->getAttr<SectionAttr>()) { 2812 if (ExistingAttr->getName() == Name) 2813 return NULL; 2814 Diag(ExistingAttr->getLocation(), diag::warn_mismatched_section); 2815 Diag(Range.getBegin(), diag::note_previous_attribute); 2816 return NULL; 2817 } 2818 return ::new (Context) SectionAttr(Range, Context, Name, 2819 AttrSpellingListIndex); 2820} 2821 2822static void handleSectionAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2823 // Make sure that there is a string literal as the sections's single 2824 // argument. 2825 StringRef Str; 2826 SourceLocation LiteralLoc; 2827 if (!S.checkStringLiteralArgumentAttr(Attr, 0, Str, &LiteralLoc)) 2828 return; 2829 2830 // If the target wants to validate the section specifier, make it happen. 2831 std::string Error = S.Context.getTargetInfo().isValidSectionSpecifier(Str); 2832 if (!Error.empty()) { 2833 S.Diag(LiteralLoc, diag::err_attribute_section_invalid_for_target) 2834 << Error; 2835 return; 2836 } 2837 2838 // This attribute cannot be applied to local variables. 2839 if (isa<VarDecl>(D) && cast<VarDecl>(D)->hasLocalStorage()) { 2840 S.Diag(LiteralLoc, diag::err_attribute_section_local_variable); 2841 return; 2842 } 2843 2844 unsigned Index = Attr.getAttributeSpellingListIndex(); 2845 SectionAttr *NewAttr = S.mergeSectionAttr(D, Attr.getRange(), Str, Index); 2846 if (NewAttr) 2847 D->addAttr(NewAttr); 2848} 2849 2850 2851static void handleNothrowAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2852 if (NoThrowAttr *Existing = D->getAttr<NoThrowAttr>()) { 2853 if (Existing->getLocation().isInvalid()) 2854 Existing->setRange(Attr.getRange()); 2855 } else { 2856 D->addAttr(::new (S.Context) 2857 NoThrowAttr(Attr.getRange(), S.Context, 2858 Attr.getAttributeSpellingListIndex())); 2859 } 2860} 2861 2862static void handleConstAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2863 if (ConstAttr *Existing = D->getAttr<ConstAttr>()) { 2864 if (Existing->getLocation().isInvalid()) 2865 Existing->setRange(Attr.getRange()); 2866 } else { 2867 D->addAttr(::new (S.Context) 2868 ConstAttr(Attr.getRange(), S.Context, 2869 Attr.getAttributeSpellingListIndex() )); 2870 } 2871} 2872 2873static void handlePureAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2874 D->addAttr(::new (S.Context) 2875 PureAttr(Attr.getRange(), S.Context, 2876 Attr.getAttributeSpellingListIndex())); 2877} 2878 2879static void handleCleanupAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2880 VarDecl *VD = dyn_cast<VarDecl>(D); 2881 if (!VD || !VD->hasLocalStorage()) { 2882 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 2883 return; 2884 } 2885 2886 Expr *E = Attr.getArgAsExpr(0); 2887 SourceLocation Loc = E->getExprLoc(); 2888 FunctionDecl *FD = 0; 2889 DeclarationNameInfo NI; 2890 2891 // gcc only allows for simple identifiers. Since we support more than gcc, we 2892 // will warn the user. 2893 if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) { 2894 if (DRE->hasQualifier()) 2895 S.Diag(Loc, diag::warn_cleanup_ext); 2896 FD = dyn_cast<FunctionDecl>(DRE->getDecl()); 2897 NI = DRE->getNameInfo(); 2898 if (!FD) { 2899 S.Diag(Loc, diag::err_attribute_cleanup_arg_not_function) << 1 2900 << NI.getName(); 2901 return; 2902 } 2903 } else if (UnresolvedLookupExpr *ULE = dyn_cast<UnresolvedLookupExpr>(E)) { 2904 if (ULE->hasExplicitTemplateArgs()) 2905 S.Diag(Loc, diag::warn_cleanup_ext); 2906 FD = S.ResolveSingleFunctionTemplateSpecialization(ULE, true); 2907 NI = ULE->getNameInfo(); 2908 if (!FD) { 2909 S.Diag(Loc, diag::err_attribute_cleanup_arg_not_function) << 2 2910 << NI.getName(); 2911 if (ULE->getType() == S.Context.OverloadTy) 2912 S.NoteAllOverloadCandidates(ULE); 2913 return; 2914 } 2915 } else { 2916 S.Diag(Loc, diag::err_attribute_cleanup_arg_not_function) << 0; 2917 return; 2918 } 2919 2920 if (FD->getNumParams() != 1) { 2921 S.Diag(Loc, diag::err_attribute_cleanup_func_must_take_one_arg) 2922 << NI.getName(); 2923 return; 2924 } 2925 2926 // We're currently more strict than GCC about what function types we accept. 2927 // If this ever proves to be a problem it should be easy to fix. 2928 QualType Ty = S.Context.getPointerType(VD->getType()); 2929 QualType ParamTy = FD->getParamDecl(0)->getType(); 2930 if (S.CheckAssignmentConstraints(FD->getParamDecl(0)->getLocation(), 2931 ParamTy, Ty) != Sema::Compatible) { 2932 S.Diag(Loc, diag::err_attribute_cleanup_func_arg_incompatible_type) 2933 << NI.getName() << ParamTy << Ty; 2934 return; 2935 } 2936 2937 D->addAttr(::new (S.Context) 2938 CleanupAttr(Attr.getRange(), S.Context, FD, 2939 Attr.getAttributeSpellingListIndex())); 2940} 2941 2942/// Handle __attribute__((format_arg((idx)))) attribute based on 2943/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 2944static void handleFormatArgAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2945 if (!isFunctionOrMethod(D) || !hasFunctionProto(D)) { 2946 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2947 << Attr.getName() << ExpectedFunction; 2948 return; 2949 } 2950 2951 Expr *IdxExpr = Attr.getArgAsExpr(0); 2952 uint64_t ArgIdx; 2953 if (!checkFunctionOrMethodArgumentIndex(S, D, Attr.getName()->getName(), 2954 Attr.getLoc(), 1, IdxExpr, ArgIdx)) 2955 return; 2956 2957 // make sure the format string is really a string 2958 QualType Ty = getFunctionOrMethodArgType(D, ArgIdx); 2959 2960 bool not_nsstring_type = !isNSStringType(Ty, S.Context); 2961 if (not_nsstring_type && 2962 !isCFStringType(Ty, S.Context) && 2963 (!Ty->isPointerType() || 2964 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 2965 // FIXME: Should highlight the actual expression that has the wrong type. 2966 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2967 << (not_nsstring_type ? "a string type" : "an NSString") 2968 << IdxExpr->getSourceRange(); 2969 return; 2970 } 2971 Ty = getFunctionOrMethodResultType(D); 2972 if (!isNSStringType(Ty, S.Context) && 2973 !isCFStringType(Ty, S.Context) && 2974 (!Ty->isPointerType() || 2975 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 2976 // FIXME: Should highlight the actual expression that has the wrong type. 2977 S.Diag(Attr.getLoc(), diag::err_format_attribute_result_not) 2978 << (not_nsstring_type ? "string type" : "NSString") 2979 << IdxExpr->getSourceRange(); 2980 return; 2981 } 2982 2983 // We cannot use the ArgIdx returned from checkFunctionOrMethodArgumentIndex 2984 // because that has corrected for the implicit this parameter, and is zero- 2985 // based. The attribute expects what the user wrote explicitly. 2986 llvm::APSInt Val; 2987 IdxExpr->EvaluateAsInt(Val, S.Context); 2988 2989 D->addAttr(::new (S.Context) 2990 FormatArgAttr(Attr.getRange(), S.Context, Val.getZExtValue(), 2991 Attr.getAttributeSpellingListIndex())); 2992} 2993 2994enum FormatAttrKind { 2995 CFStringFormat, 2996 NSStringFormat, 2997 StrftimeFormat, 2998 SupportedFormat, 2999 IgnoredFormat, 3000 InvalidFormat 3001}; 3002 3003/// getFormatAttrKind - Map from format attribute names to supported format 3004/// types. 3005static FormatAttrKind getFormatAttrKind(StringRef Format) { 3006 return llvm::StringSwitch<FormatAttrKind>(Format) 3007 // Check for formats that get handled specially. 3008 .Case("NSString", NSStringFormat) 3009 .Case("CFString", CFStringFormat) 3010 .Case("strftime", StrftimeFormat) 3011 3012 // Otherwise, check for supported formats. 3013 .Cases("scanf", "printf", "printf0", "strfmon", SupportedFormat) 3014 .Cases("cmn_err", "vcmn_err", "zcmn_err", SupportedFormat) 3015 .Case("kprintf", SupportedFormat) // OpenBSD. 3016 3017 .Cases("gcc_diag", "gcc_cdiag", "gcc_cxxdiag", "gcc_tdiag", IgnoredFormat) 3018 .Default(InvalidFormat); 3019} 3020 3021/// Handle __attribute__((init_priority(priority))) attributes based on 3022/// http://gcc.gnu.org/onlinedocs/gcc/C_002b_002b-Attributes.html 3023static void handleInitPriorityAttr(Sema &S, Decl *D, 3024 const AttributeList &Attr) { 3025 if (!S.getLangOpts().CPlusPlus) { 3026 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 3027 return; 3028 } 3029 3030 if (!isa<VarDecl>(D) || S.getCurFunctionOrMethodDecl()) { 3031 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 3032 Attr.setInvalid(); 3033 return; 3034 } 3035 QualType T = dyn_cast<VarDecl>(D)->getType(); 3036 if (S.Context.getAsArrayType(T)) 3037 T = S.Context.getBaseElementType(T); 3038 if (!T->getAs<RecordType>()) { 3039 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 3040 Attr.setInvalid(); 3041 return; 3042 } 3043 3044 Expr *priorityExpr = Attr.getArgAsExpr(0); 3045 3046 llvm::APSInt priority(32); 3047 if (priorityExpr->isTypeDependent() || priorityExpr->isValueDependent() || 3048 !priorityExpr->isIntegerConstantExpr(priority, S.Context)) { 3049 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) 3050 << Attr.getName() << AANT_ArgumentIntegerConstant 3051 << priorityExpr->getSourceRange(); 3052 Attr.setInvalid(); 3053 return; 3054 } 3055 unsigned prioritynum = priority.getZExtValue(); 3056 if (prioritynum < 101 || prioritynum > 65535) { 3057 S.Diag(Attr.getLoc(), diag::err_attribute_argument_outof_range) 3058 << priorityExpr->getSourceRange(); 3059 Attr.setInvalid(); 3060 return; 3061 } 3062 D->addAttr(::new (S.Context) 3063 InitPriorityAttr(Attr.getRange(), S.Context, prioritynum, 3064 Attr.getAttributeSpellingListIndex())); 3065} 3066 3067FormatAttr *Sema::mergeFormatAttr(Decl *D, SourceRange Range, 3068 IdentifierInfo *Format, int FormatIdx, 3069 int FirstArg, 3070 unsigned AttrSpellingListIndex) { 3071 // Check whether we already have an equivalent format attribute. 3072 for (specific_attr_iterator<FormatAttr> 3073 i = D->specific_attr_begin<FormatAttr>(), 3074 e = D->specific_attr_end<FormatAttr>(); 3075 i != e ; ++i) { 3076 FormatAttr *f = *i; 3077 if (f->getType() == Format && 3078 f->getFormatIdx() == FormatIdx && 3079 f->getFirstArg() == FirstArg) { 3080 // If we don't have a valid location for this attribute, adopt the 3081 // location. 3082 if (f->getLocation().isInvalid()) 3083 f->setRange(Range); 3084 return NULL; 3085 } 3086 } 3087 3088 return ::new (Context) FormatAttr(Range, Context, Format, FormatIdx, 3089 FirstArg, AttrSpellingListIndex); 3090} 3091 3092/// Handle __attribute__((format(type,idx,firstarg))) attributes based on 3093/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 3094static void handleFormatAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3095 if (!Attr.isArgIdent(0)) { 3096 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 3097 << Attr.getName() << 1 << AANT_ArgumentIdentifier; 3098 return; 3099 } 3100 3101 if (!isFunctionOrMethodOrBlock(D) || !hasFunctionProto(D)) { 3102 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3103 << Attr.getName() << ExpectedFunction; 3104 return; 3105 } 3106 3107 // In C++ the implicit 'this' function parameter also counts, and they are 3108 // counted from one. 3109 bool HasImplicitThisParam = isInstanceMethod(D); 3110 unsigned NumArgs = getFunctionOrMethodNumArgs(D) + HasImplicitThisParam; 3111 unsigned FirstIdx = 1; 3112 3113 IdentifierInfo *II = Attr.getArgAsIdent(0)->Ident; 3114 StringRef Format = II->getName(); 3115 3116 // Normalize the argument, __foo__ becomes foo. 3117 if (Format.startswith("__") && Format.endswith("__")) { 3118 Format = Format.substr(2, Format.size() - 4); 3119 // If we've modified the string name, we need a new identifier for it. 3120 II = &S.Context.Idents.get(Format); 3121 } 3122 3123 // Check for supported formats. 3124 FormatAttrKind Kind = getFormatAttrKind(Format); 3125 3126 if (Kind == IgnoredFormat) 3127 return; 3128 3129 if (Kind == InvalidFormat) { 3130 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 3131 << "format" << II->getName(); 3132 return; 3133 } 3134 3135 // checks for the 2nd argument 3136 Expr *IdxExpr = Attr.getArgAsExpr(1); 3137 llvm::APSInt Idx(32); 3138 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 3139 !IdxExpr->isIntegerConstantExpr(Idx, S.Context)) { 3140 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 3141 << Attr.getName() << 2 << AANT_ArgumentIntegerConstant 3142 << IdxExpr->getSourceRange(); 3143 return; 3144 } 3145 3146 if (Idx.getZExtValue() < FirstIdx || Idx.getZExtValue() > NumArgs) { 3147 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 3148 << "format" << 2 << IdxExpr->getSourceRange(); 3149 return; 3150 } 3151 3152 // FIXME: Do we need to bounds check? 3153 unsigned ArgIdx = Idx.getZExtValue() - 1; 3154 3155 if (HasImplicitThisParam) { 3156 if (ArgIdx == 0) { 3157 S.Diag(Attr.getLoc(), 3158 diag::err_format_attribute_implicit_this_format_string) 3159 << IdxExpr->getSourceRange(); 3160 return; 3161 } 3162 ArgIdx--; 3163 } 3164 3165 // make sure the format string is really a string 3166 QualType Ty = getFunctionOrMethodArgType(D, ArgIdx); 3167 3168 if (Kind == CFStringFormat) { 3169 if (!isCFStringType(Ty, S.Context)) { 3170 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 3171 << "a CFString" << IdxExpr->getSourceRange(); 3172 return; 3173 } 3174 } else if (Kind == NSStringFormat) { 3175 // FIXME: do we need to check if the type is NSString*? What are the 3176 // semantics? 3177 if (!isNSStringType(Ty, S.Context)) { 3178 // FIXME: Should highlight the actual expression that has the wrong type. 3179 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 3180 << "an NSString" << IdxExpr->getSourceRange(); 3181 return; 3182 } 3183 } else if (!Ty->isPointerType() || 3184 !Ty->getAs<PointerType>()->getPointeeType()->isCharType()) { 3185 // FIXME: Should highlight the actual expression that has the wrong type. 3186 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 3187 << "a string type" << IdxExpr->getSourceRange(); 3188 return; 3189 } 3190 3191 // check the 3rd argument 3192 Expr *FirstArgExpr = Attr.getArgAsExpr(2); 3193 llvm::APSInt FirstArg(32); 3194 if (FirstArgExpr->isTypeDependent() || FirstArgExpr->isValueDependent() || 3195 !FirstArgExpr->isIntegerConstantExpr(FirstArg, S.Context)) { 3196 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 3197 << Attr.getName() << 3 << AANT_ArgumentIntegerConstant 3198 << FirstArgExpr->getSourceRange(); 3199 return; 3200 } 3201 3202 // check if the function is variadic if the 3rd argument non-zero 3203 if (FirstArg != 0) { 3204 if (isFunctionOrMethodVariadic(D)) { 3205 ++NumArgs; // +1 for ... 3206 } else { 3207 S.Diag(D->getLocation(), diag::err_format_attribute_requires_variadic); 3208 return; 3209 } 3210 } 3211 3212 // strftime requires FirstArg to be 0 because it doesn't read from any 3213 // variable the input is just the current time + the format string. 3214 if (Kind == StrftimeFormat) { 3215 if (FirstArg != 0) { 3216 S.Diag(Attr.getLoc(), diag::err_format_strftime_third_parameter) 3217 << FirstArgExpr->getSourceRange(); 3218 return; 3219 } 3220 // if 0 it disables parameter checking (to use with e.g. va_list) 3221 } else if (FirstArg != 0 && FirstArg != NumArgs) { 3222 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 3223 << "format" << 3 << FirstArgExpr->getSourceRange(); 3224 return; 3225 } 3226 3227 FormatAttr *NewAttr = S.mergeFormatAttr(D, Attr.getRange(), II, 3228 Idx.getZExtValue(), 3229 FirstArg.getZExtValue(), 3230 Attr.getAttributeSpellingListIndex()); 3231 if (NewAttr) 3232 D->addAttr(NewAttr); 3233} 3234 3235static void handleTransparentUnionAttr(Sema &S, Decl *D, 3236 const AttributeList &Attr) { 3237 // Try to find the underlying union declaration. 3238 RecordDecl *RD = 0; 3239 TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D); 3240 if (TD && TD->getUnderlyingType()->isUnionType()) 3241 RD = TD->getUnderlyingType()->getAsUnionType()->getDecl(); 3242 else 3243 RD = dyn_cast<RecordDecl>(D); 3244 3245 if (!RD || !RD->isUnion()) { 3246 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3247 << Attr.getName() << ExpectedUnion; 3248 return; 3249 } 3250 3251 if (!RD->isCompleteDefinition()) { 3252 S.Diag(Attr.getLoc(), 3253 diag::warn_transparent_union_attribute_not_definition); 3254 return; 3255 } 3256 3257 RecordDecl::field_iterator Field = RD->field_begin(), 3258 FieldEnd = RD->field_end(); 3259 if (Field == FieldEnd) { 3260 S.Diag(Attr.getLoc(), diag::warn_transparent_union_attribute_zero_fields); 3261 return; 3262 } 3263 3264 FieldDecl *FirstField = *Field; 3265 QualType FirstType = FirstField->getType(); 3266 if (FirstType->hasFloatingRepresentation() || FirstType->isVectorType()) { 3267 S.Diag(FirstField->getLocation(), 3268 diag::warn_transparent_union_attribute_floating) 3269 << FirstType->isVectorType() << FirstType; 3270 return; 3271 } 3272 3273 uint64_t FirstSize = S.Context.getTypeSize(FirstType); 3274 uint64_t FirstAlign = S.Context.getTypeAlign(FirstType); 3275 for (; Field != FieldEnd; ++Field) { 3276 QualType FieldType = Field->getType(); 3277 if (S.Context.getTypeSize(FieldType) != FirstSize || 3278 S.Context.getTypeAlign(FieldType) != FirstAlign) { 3279 // Warn if we drop the attribute. 3280 bool isSize = S.Context.getTypeSize(FieldType) != FirstSize; 3281 unsigned FieldBits = isSize? S.Context.getTypeSize(FieldType) 3282 : S.Context.getTypeAlign(FieldType); 3283 S.Diag(Field->getLocation(), 3284 diag::warn_transparent_union_attribute_field_size_align) 3285 << isSize << Field->getDeclName() << FieldBits; 3286 unsigned FirstBits = isSize? FirstSize : FirstAlign; 3287 S.Diag(FirstField->getLocation(), 3288 diag::note_transparent_union_first_field_size_align) 3289 << isSize << FirstBits; 3290 return; 3291 } 3292 } 3293 3294 RD->addAttr(::new (S.Context) 3295 TransparentUnionAttr(Attr.getRange(), S.Context, 3296 Attr.getAttributeSpellingListIndex())); 3297} 3298 3299static void handleAnnotateAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3300 // Make sure that there is a string literal as the annotation's single 3301 // argument. 3302 StringRef Str; 3303 if (!S.checkStringLiteralArgumentAttr(Attr, 0, Str)) 3304 return; 3305 3306 // Don't duplicate annotations that are already set. 3307 for (specific_attr_iterator<AnnotateAttr> 3308 i = D->specific_attr_begin<AnnotateAttr>(), 3309 e = D->specific_attr_end<AnnotateAttr>(); i != e; ++i) { 3310 if ((*i)->getAnnotation() == Str) 3311 return; 3312 } 3313 3314 D->addAttr(::new (S.Context) 3315 AnnotateAttr(Attr.getRange(), S.Context, Str, 3316 Attr.getAttributeSpellingListIndex())); 3317} 3318 3319static void handleAlignedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3320 // check the attribute arguments. 3321 if (Attr.getNumArgs() > 1) { 3322 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) 3323 << Attr.getName() << 1; 3324 return; 3325 } 3326 3327 if (Attr.getNumArgs() == 0) { 3328 D->addAttr(::new (S.Context) AlignedAttr(Attr.getRange(), S.Context, 3329 true, 0, Attr.getAttributeSpellingListIndex())); 3330 return; 3331 } 3332 3333 Expr *E = Attr.getArgAsExpr(0); 3334 if (Attr.isPackExpansion() && !E->containsUnexpandedParameterPack()) { 3335 S.Diag(Attr.getEllipsisLoc(), 3336 diag::err_pack_expansion_without_parameter_packs); 3337 return; 3338 } 3339 3340 if (!Attr.isPackExpansion() && S.DiagnoseUnexpandedParameterPack(E)) 3341 return; 3342 3343 S.AddAlignedAttr(Attr.getRange(), D, E, Attr.getAttributeSpellingListIndex(), 3344 Attr.isPackExpansion()); 3345} 3346 3347void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E, 3348 unsigned SpellingListIndex, bool IsPackExpansion) { 3349 AlignedAttr TmpAttr(AttrRange, Context, true, E, SpellingListIndex); 3350 SourceLocation AttrLoc = AttrRange.getBegin(); 3351 3352 // C++11 alignas(...) and C11 _Alignas(...) have additional requirements. 3353 if (TmpAttr.isAlignas()) { 3354 // C++11 [dcl.align]p1: 3355 // An alignment-specifier may be applied to a variable or to a class 3356 // data member, but it shall not be applied to a bit-field, a function 3357 // parameter, the formal parameter of a catch clause, or a variable 3358 // declared with the register storage class specifier. An 3359 // alignment-specifier may also be applied to the declaration of a class 3360 // or enumeration type. 3361 // C11 6.7.5/2: 3362 // An alignment attribute shall not be specified in a declaration of 3363 // a typedef, or a bit-field, or a function, or a parameter, or an 3364 // object declared with the register storage-class specifier. 3365 int DiagKind = -1; 3366 if (isa<ParmVarDecl>(D)) { 3367 DiagKind = 0; 3368 } else if (VarDecl *VD = dyn_cast<VarDecl>(D)) { 3369 if (VD->getStorageClass() == SC_Register) 3370 DiagKind = 1; 3371 if (VD->isExceptionVariable()) 3372 DiagKind = 2; 3373 } else if (FieldDecl *FD = dyn_cast<FieldDecl>(D)) { 3374 if (FD->isBitField()) 3375 DiagKind = 3; 3376 } else if (!isa<TagDecl>(D)) { 3377 Diag(AttrLoc, diag::err_attribute_wrong_decl_type) 3378 << (TmpAttr.isC11() ? "'_Alignas'" : "'alignas'") 3379 << (TmpAttr.isC11() ? ExpectedVariableOrField 3380 : ExpectedVariableFieldOrTag); 3381 return; 3382 } 3383 if (DiagKind != -1) { 3384 Diag(AttrLoc, diag::err_alignas_attribute_wrong_decl_type) 3385 << TmpAttr.isC11() << DiagKind; 3386 return; 3387 } 3388 } 3389 3390 if (E->isTypeDependent() || E->isValueDependent()) { 3391 // Save dependent expressions in the AST to be instantiated. 3392 AlignedAttr *AA = ::new (Context) AlignedAttr(TmpAttr); 3393 AA->setPackExpansion(IsPackExpansion); 3394 D->addAttr(AA); 3395 return; 3396 } 3397 3398 // FIXME: Cache the number on the Attr object? 3399 llvm::APSInt Alignment(32); 3400 ExprResult ICE 3401 = VerifyIntegerConstantExpression(E, &Alignment, 3402 diag::err_aligned_attribute_argument_not_int, 3403 /*AllowFold*/ false); 3404 if (ICE.isInvalid()) 3405 return; 3406 3407 // C++11 [dcl.align]p2: 3408 // -- if the constant expression evaluates to zero, the alignment 3409 // specifier shall have no effect 3410 // C11 6.7.5p6: 3411 // An alignment specification of zero has no effect. 3412 if (!(TmpAttr.isAlignas() && !Alignment) && 3413 !llvm::isPowerOf2_64(Alignment.getZExtValue())) { 3414 Diag(AttrLoc, diag::err_attribute_aligned_not_power_of_two) 3415 << E->getSourceRange(); 3416 return; 3417 } 3418 3419 if (TmpAttr.isDeclspec()) { 3420 // We've already verified it's a power of 2, now let's make sure it's 3421 // 8192 or less. 3422 if (Alignment.getZExtValue() > 8192) { 3423 Diag(AttrLoc, diag::err_attribute_aligned_greater_than_8192) 3424 << E->getSourceRange(); 3425 return; 3426 } 3427 } 3428 3429 AlignedAttr *AA = ::new (Context) AlignedAttr(AttrRange, Context, true, 3430 ICE.take(), SpellingListIndex); 3431 AA->setPackExpansion(IsPackExpansion); 3432 D->addAttr(AA); 3433} 3434 3435void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *TS, 3436 unsigned SpellingListIndex, bool IsPackExpansion) { 3437 // FIXME: Cache the number on the Attr object if non-dependent? 3438 // FIXME: Perform checking of type validity 3439 AlignedAttr *AA = ::new (Context) AlignedAttr(AttrRange, Context, false, TS, 3440 SpellingListIndex); 3441 AA->setPackExpansion(IsPackExpansion); 3442 D->addAttr(AA); 3443} 3444 3445void Sema::CheckAlignasUnderalignment(Decl *D) { 3446 assert(D->hasAttrs() && "no attributes on decl"); 3447 3448 QualType Ty; 3449 if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) 3450 Ty = VD->getType(); 3451 else 3452 Ty = Context.getTagDeclType(cast<TagDecl>(D)); 3453 if (Ty->isDependentType() || Ty->isIncompleteType()) 3454 return; 3455 3456 // C++11 [dcl.align]p5, C11 6.7.5/4: 3457 // The combined effect of all alignment attributes in a declaration shall 3458 // not specify an alignment that is less strict than the alignment that 3459 // would otherwise be required for the entity being declared. 3460 AlignedAttr *AlignasAttr = 0; 3461 unsigned Align = 0; 3462 for (specific_attr_iterator<AlignedAttr> 3463 I = D->specific_attr_begin<AlignedAttr>(), 3464 E = D->specific_attr_end<AlignedAttr>(); I != E; ++I) { 3465 if (I->isAlignmentDependent()) 3466 return; 3467 if (I->isAlignas()) 3468 AlignasAttr = *I; 3469 Align = std::max(Align, I->getAlignment(Context)); 3470 } 3471 3472 if (AlignasAttr && Align) { 3473 CharUnits RequestedAlign = Context.toCharUnitsFromBits(Align); 3474 CharUnits NaturalAlign = Context.getTypeAlignInChars(Ty); 3475 if (NaturalAlign > RequestedAlign) 3476 Diag(AlignasAttr->getLocation(), diag::err_alignas_underaligned) 3477 << Ty << (unsigned)NaturalAlign.getQuantity(); 3478 } 3479} 3480 3481/// handleModeAttr - This attribute modifies the width of a decl with primitive 3482/// type. 3483/// 3484/// Despite what would be logical, the mode attribute is a decl attribute, not a 3485/// type attribute: 'int ** __attribute((mode(HI))) *G;' tries to make 'G' be 3486/// HImode, not an intermediate pointer. 3487static void handleModeAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3488 // This attribute isn't documented, but glibc uses it. It changes 3489 // the width of an int or unsigned int to the specified size. 3490 if (!Attr.isArgIdent(0)) { 3491 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) << Attr.getName() 3492 << AANT_ArgumentIdentifier; 3493 return; 3494 } 3495 3496 IdentifierInfo *Name = Attr.getArgAsIdent(0)->Ident; 3497 StringRef Str = Name->getName(); 3498 3499 // Normalize the attribute name, __foo__ becomes foo. 3500 if (Str.startswith("__") && Str.endswith("__")) 3501 Str = Str.substr(2, Str.size() - 4); 3502 3503 unsigned DestWidth = 0; 3504 bool IntegerMode = true; 3505 bool ComplexMode = false; 3506 switch (Str.size()) { 3507 case 2: 3508 switch (Str[0]) { 3509 case 'Q': DestWidth = 8; break; 3510 case 'H': DestWidth = 16; break; 3511 case 'S': DestWidth = 32; break; 3512 case 'D': DestWidth = 64; break; 3513 case 'X': DestWidth = 96; break; 3514 case 'T': DestWidth = 128; break; 3515 } 3516 if (Str[1] == 'F') { 3517 IntegerMode = false; 3518 } else if (Str[1] == 'C') { 3519 IntegerMode = false; 3520 ComplexMode = true; 3521 } else if (Str[1] != 'I') { 3522 DestWidth = 0; 3523 } 3524 break; 3525 case 4: 3526 // FIXME: glibc uses 'word' to define register_t; this is narrower than a 3527 // pointer on PIC16 and other embedded platforms. 3528 if (Str == "word") 3529 DestWidth = S.Context.getTargetInfo().getPointerWidth(0); 3530 else if (Str == "byte") 3531 DestWidth = S.Context.getTargetInfo().getCharWidth(); 3532 break; 3533 case 7: 3534 if (Str == "pointer") 3535 DestWidth = S.Context.getTargetInfo().getPointerWidth(0); 3536 break; 3537 case 11: 3538 if (Str == "unwind_word") 3539 DestWidth = S.Context.getTargetInfo().getUnwindWordWidth(); 3540 break; 3541 } 3542 3543 QualType OldTy; 3544 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) 3545 OldTy = TD->getUnderlyingType(); 3546 else if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) 3547 OldTy = VD->getType(); 3548 else { 3549 S.Diag(D->getLocation(), diag::err_attr_wrong_decl) 3550 << "mode" << Attr.getRange(); 3551 return; 3552 } 3553 3554 if (!OldTy->getAs<BuiltinType>() && !OldTy->isComplexType()) 3555 S.Diag(Attr.getLoc(), diag::err_mode_not_primitive); 3556 else if (IntegerMode) { 3557 if (!OldTy->isIntegralOrEnumerationType()) 3558 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 3559 } else if (ComplexMode) { 3560 if (!OldTy->isComplexType()) 3561 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 3562 } else { 3563 if (!OldTy->isFloatingType()) 3564 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 3565 } 3566 3567 // FIXME: Sync this with InitializePredefinedMacros; we need to match int8_t 3568 // and friends, at least with glibc. 3569 // FIXME: Make sure floating-point mappings are accurate 3570 // FIXME: Support XF and TF types 3571 if (!DestWidth) { 3572 S.Diag(Attr.getLoc(), diag::err_unknown_machine_mode) << Name; 3573 return; 3574 } 3575 3576 QualType NewTy; 3577 3578 if (IntegerMode) 3579 NewTy = S.Context.getIntTypeForBitwidth(DestWidth, 3580 OldTy->isSignedIntegerType()); 3581 else 3582 NewTy = S.Context.getRealTypeForBitwidth(DestWidth); 3583 3584 if (NewTy.isNull()) { 3585 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 3586 return; 3587 } 3588 3589 if (ComplexMode) { 3590 NewTy = S.Context.getComplexType(NewTy); 3591 } 3592 3593 // Install the new type. 3594 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) 3595 TD->setModedTypeSourceInfo(TD->getTypeSourceInfo(), NewTy); 3596 else 3597 cast<ValueDecl>(D)->setType(NewTy); 3598 3599 D->addAttr(::new (S.Context) 3600 ModeAttr(Attr.getRange(), S.Context, Name, 3601 Attr.getAttributeSpellingListIndex())); 3602} 3603 3604static void handleNoDebugAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3605 if (const VarDecl *VD = dyn_cast<VarDecl>(D)) { 3606 if (!VD->hasGlobalStorage()) 3607 S.Diag(Attr.getLoc(), 3608 diag::warn_attribute_requires_functions_or_static_globals) 3609 << Attr.getName(); 3610 } else if (!isFunctionOrMethod(D)) { 3611 S.Diag(Attr.getLoc(), 3612 diag::warn_attribute_requires_functions_or_static_globals) 3613 << Attr.getName(); 3614 return; 3615 } 3616 3617 D->addAttr(::new (S.Context) 3618 NoDebugAttr(Attr.getRange(), S.Context, 3619 Attr.getAttributeSpellingListIndex())); 3620} 3621 3622static void handleNoInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3623 if (!isa<FunctionDecl>(D)) { 3624 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3625 << Attr.getName() << ExpectedFunction; 3626 return; 3627 } 3628 3629 D->addAttr(::new (S.Context) 3630 NoInlineAttr(Attr.getRange(), S.Context, 3631 Attr.getAttributeSpellingListIndex())); 3632} 3633 3634static void handleNoInstrumentFunctionAttr(Sema &S, Decl *D, 3635 const AttributeList &Attr) { 3636 if (!isa<FunctionDecl>(D)) { 3637 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3638 << Attr.getName() << ExpectedFunction; 3639 return; 3640 } 3641 3642 D->addAttr(::new (S.Context) 3643 NoInstrumentFunctionAttr(Attr.getRange(), S.Context, 3644 Attr.getAttributeSpellingListIndex())); 3645} 3646 3647static void handleConstantAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3648 if (S.LangOpts.CUDA) { 3649 if (!isa<VarDecl>(D)) { 3650 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3651 << Attr.getName() << ExpectedVariable; 3652 return; 3653 } 3654 3655 D->addAttr(::new (S.Context) 3656 CUDAConstantAttr(Attr.getRange(), S.Context, 3657 Attr.getAttributeSpellingListIndex())); 3658 } else { 3659 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "constant"; 3660 } 3661} 3662 3663static void handleDeviceAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3664 if (S.LangOpts.CUDA) { 3665 // check the attribute arguments. 3666 if (Attr.getNumArgs() != 0) { 3667 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) 3668 << Attr.getName() << 0; 3669 return; 3670 } 3671 3672 if (!isa<FunctionDecl>(D) && !isa<VarDecl>(D)) { 3673 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3674 << Attr.getName() << ExpectedVariableOrFunction; 3675 return; 3676 } 3677 3678 D->addAttr(::new (S.Context) 3679 CUDADeviceAttr(Attr.getRange(), S.Context, 3680 Attr.getAttributeSpellingListIndex())); 3681 } else { 3682 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "device"; 3683 } 3684} 3685 3686static void handleGlobalAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3687 if (S.LangOpts.CUDA) { 3688 if (!isa<FunctionDecl>(D)) { 3689 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3690 << Attr.getName() << ExpectedFunction; 3691 return; 3692 } 3693 3694 FunctionDecl *FD = cast<FunctionDecl>(D); 3695 if (!FD->getResultType()->isVoidType()) { 3696 TypeLoc TL = FD->getTypeSourceInfo()->getTypeLoc().IgnoreParens(); 3697 if (FunctionTypeLoc FTL = TL.getAs<FunctionTypeLoc>()) { 3698 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 3699 << FD->getType() 3700 << FixItHint::CreateReplacement(FTL.getResultLoc().getSourceRange(), 3701 "void"); 3702 } else { 3703 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 3704 << FD->getType(); 3705 } 3706 return; 3707 } 3708 3709 D->addAttr(::new (S.Context) 3710 CUDAGlobalAttr(Attr.getRange(), S.Context, 3711 Attr.getAttributeSpellingListIndex())); 3712 } else { 3713 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "global"; 3714 } 3715} 3716 3717static void handleHostAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3718 if (S.LangOpts.CUDA) { 3719 if (!isa<FunctionDecl>(D)) { 3720 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3721 << Attr.getName() << ExpectedFunction; 3722 return; 3723 } 3724 3725 D->addAttr(::new (S.Context) 3726 CUDAHostAttr(Attr.getRange(), S.Context, 3727 Attr.getAttributeSpellingListIndex())); 3728 } else { 3729 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "host"; 3730 } 3731} 3732 3733static void handleSharedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3734 if (S.LangOpts.CUDA) { 3735 if (!isa<VarDecl>(D)) { 3736 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3737 << Attr.getName() << ExpectedVariable; 3738 return; 3739 } 3740 3741 D->addAttr(::new (S.Context) 3742 CUDASharedAttr(Attr.getRange(), S.Context, 3743 Attr.getAttributeSpellingListIndex())); 3744 } else { 3745 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "shared"; 3746 } 3747} 3748 3749static void handleGNUInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3750 FunctionDecl *Fn = dyn_cast<FunctionDecl>(D); 3751 if (Fn == 0) { 3752 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3753 << Attr.getName() << ExpectedFunction; 3754 return; 3755 } 3756 3757 if (!Fn->isInlineSpecified()) { 3758 S.Diag(Attr.getLoc(), diag::warn_gnu_inline_attribute_requires_inline); 3759 return; 3760 } 3761 3762 D->addAttr(::new (S.Context) 3763 GNUInlineAttr(Attr.getRange(), S.Context, 3764 Attr.getAttributeSpellingListIndex())); 3765} 3766 3767static void handleCallConvAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3768 if (hasDeclarator(D)) return; 3769 3770 const FunctionDecl *FD = dyn_cast<FunctionDecl>(D); 3771 // Diagnostic is emitted elsewhere: here we store the (valid) Attr 3772 // in the Decl node for syntactic reasoning, e.g., pretty-printing. 3773 CallingConv CC; 3774 if (S.CheckCallingConvAttr(Attr, CC, FD)) 3775 return; 3776 3777 if (!isa<ObjCMethodDecl>(D)) { 3778 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3779 << Attr.getName() << ExpectedFunctionOrMethod; 3780 return; 3781 } 3782 3783 switch (Attr.getKind()) { 3784 case AttributeList::AT_FastCall: 3785 D->addAttr(::new (S.Context) 3786 FastCallAttr(Attr.getRange(), S.Context, 3787 Attr.getAttributeSpellingListIndex())); 3788 return; 3789 case AttributeList::AT_StdCall: 3790 D->addAttr(::new (S.Context) 3791 StdCallAttr(Attr.getRange(), S.Context, 3792 Attr.getAttributeSpellingListIndex())); 3793 return; 3794 case AttributeList::AT_ThisCall: 3795 D->addAttr(::new (S.Context) 3796 ThisCallAttr(Attr.getRange(), S.Context, 3797 Attr.getAttributeSpellingListIndex())); 3798 return; 3799 case AttributeList::AT_CDecl: 3800 D->addAttr(::new (S.Context) 3801 CDeclAttr(Attr.getRange(), S.Context, 3802 Attr.getAttributeSpellingListIndex())); 3803 return; 3804 case AttributeList::AT_Pascal: 3805 D->addAttr(::new (S.Context) 3806 PascalAttr(Attr.getRange(), S.Context, 3807 Attr.getAttributeSpellingListIndex())); 3808 return; 3809 case AttributeList::AT_MSABI: 3810 D->addAttr(::new (S.Context) 3811 MSABIAttr(Attr.getRange(), S.Context, 3812 Attr.getAttributeSpellingListIndex())); 3813 return; 3814 case AttributeList::AT_SysVABI: 3815 D->addAttr(::new (S.Context) 3816 SysVABIAttr(Attr.getRange(), S.Context, 3817 Attr.getAttributeSpellingListIndex())); 3818 return; 3819 case AttributeList::AT_Pcs: { 3820 PcsAttr::PCSType PCS; 3821 switch (CC) { 3822 case CC_AAPCS: 3823 PCS = PcsAttr::AAPCS; 3824 break; 3825 case CC_AAPCS_VFP: 3826 PCS = PcsAttr::AAPCS_VFP; 3827 break; 3828 default: 3829 llvm_unreachable("unexpected calling convention in pcs attribute"); 3830 } 3831 3832 D->addAttr(::new (S.Context) 3833 PcsAttr(Attr.getRange(), S.Context, PCS, 3834 Attr.getAttributeSpellingListIndex())); 3835 return; 3836 } 3837 case AttributeList::AT_PnaclCall: 3838 D->addAttr(::new (S.Context) 3839 PnaclCallAttr(Attr.getRange(), S.Context, 3840 Attr.getAttributeSpellingListIndex())); 3841 return; 3842 case AttributeList::AT_IntelOclBicc: 3843 D->addAttr(::new (S.Context) 3844 IntelOclBiccAttr(Attr.getRange(), S.Context, 3845 Attr.getAttributeSpellingListIndex())); 3846 return; 3847 3848 default: 3849 llvm_unreachable("unexpected attribute kind"); 3850 } 3851} 3852 3853static void handleOpenCLKernelAttr(Sema &S, Decl *D, const AttributeList &Attr){ 3854 D->addAttr(::new (S.Context) OpenCLKernelAttr(Attr.getRange(), S.Context)); 3855} 3856 3857static void handleOpenCLImageAccessAttr(Sema &S, Decl *D, const AttributeList &Attr){ 3858 Expr *E = Attr.getArgAsExpr(0); 3859 llvm::APSInt ArgNum(32); 3860 if (E->isTypeDependent() || E->isValueDependent() || 3861 !E->isIntegerConstantExpr(ArgNum, S.Context)) { 3862 S.Diag(Attr.getLoc(), diag::err_attribute_argument_type) 3863 << Attr.getName() << AANT_ArgumentIntegerConstant 3864 << E->getSourceRange(); 3865 return; 3866 } 3867 3868 D->addAttr(::new (S.Context) OpenCLImageAccessAttr( 3869 Attr.getRange(), S.Context, ArgNum.getZExtValue())); 3870} 3871 3872bool Sema::CheckCallingConvAttr(const AttributeList &attr, CallingConv &CC, 3873 const FunctionDecl *FD) { 3874 if (attr.isInvalid()) 3875 return true; 3876 3877 unsigned ReqArgs = attr.getKind() == AttributeList::AT_Pcs ? 1 : 0; 3878 if (!checkAttributeNumArgs(*this, attr, ReqArgs)) { 3879 attr.setInvalid(); 3880 return true; 3881 } 3882 3883 // TODO: diagnose uses of these conventions on the wrong target. Or, better 3884 // move to TargetAttributesSema one day. 3885 switch (attr.getKind()) { 3886 case AttributeList::AT_CDecl: CC = CC_C; break; 3887 case AttributeList::AT_FastCall: CC = CC_X86FastCall; break; 3888 case AttributeList::AT_StdCall: CC = CC_X86StdCall; break; 3889 case AttributeList::AT_ThisCall: CC = CC_X86ThisCall; break; 3890 case AttributeList::AT_Pascal: CC = CC_X86Pascal; break; 3891 case AttributeList::AT_MSABI: 3892 CC = Context.getTargetInfo().getTriple().isOSWindows() ? CC_C : 3893 CC_X86_64Win64; 3894 break; 3895 case AttributeList::AT_SysVABI: 3896 CC = Context.getTargetInfo().getTriple().isOSWindows() ? CC_X86_64SysV : 3897 CC_C; 3898 break; 3899 case AttributeList::AT_Pcs: { 3900 StringRef StrRef; 3901 if (!checkStringLiteralArgumentAttr(attr, 0, StrRef)) { 3902 attr.setInvalid(); 3903 return true; 3904 } 3905 if (StrRef == "aapcs") { 3906 CC = CC_AAPCS; 3907 break; 3908 } else if (StrRef == "aapcs-vfp") { 3909 CC = CC_AAPCS_VFP; 3910 break; 3911 } 3912 3913 attr.setInvalid(); 3914 Diag(attr.getLoc(), diag::err_invalid_pcs); 3915 return true; 3916 } 3917 case AttributeList::AT_PnaclCall: CC = CC_PnaclCall; break; 3918 case AttributeList::AT_IntelOclBicc: CC = CC_IntelOclBicc; break; 3919 default: llvm_unreachable("unexpected attribute kind"); 3920 } 3921 3922 const TargetInfo &TI = Context.getTargetInfo(); 3923 TargetInfo::CallingConvCheckResult A = TI.checkCallingConvention(CC); 3924 if (A == TargetInfo::CCCR_Warning) { 3925 Diag(attr.getLoc(), diag::warn_cconv_ignored) << attr.getName(); 3926 3927 TargetInfo::CallingConvMethodType MT = TargetInfo::CCMT_Unknown; 3928 if (FD) 3929 MT = FD->isCXXInstanceMember() ? TargetInfo::CCMT_Member : 3930 TargetInfo::CCMT_NonMember; 3931 CC = TI.getDefaultCallingConv(MT); 3932 } 3933 3934 return false; 3935} 3936 3937static void handleRegparmAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3938 if (hasDeclarator(D)) return; 3939 3940 unsigned numParams; 3941 if (S.CheckRegparmAttr(Attr, numParams)) 3942 return; 3943 3944 if (!isa<ObjCMethodDecl>(D)) { 3945 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3946 << Attr.getName() << ExpectedFunctionOrMethod; 3947 return; 3948 } 3949 3950 D->addAttr(::new (S.Context) 3951 RegparmAttr(Attr.getRange(), S.Context, numParams, 3952 Attr.getAttributeSpellingListIndex())); 3953} 3954 3955/// Checks a regparm attribute, returning true if it is ill-formed and 3956/// otherwise setting numParams to the appropriate value. 3957bool Sema::CheckRegparmAttr(const AttributeList &Attr, unsigned &numParams) { 3958 if (Attr.isInvalid()) 3959 return true; 3960 3961 if (!checkAttributeNumArgs(*this, Attr, 1)) { 3962 Attr.setInvalid(); 3963 return true; 3964 } 3965 3966 Expr *NumParamsExpr = Attr.getArgAsExpr(0); 3967 llvm::APSInt NumParams(32); 3968 if (NumParamsExpr->isTypeDependent() || NumParamsExpr->isValueDependent() || 3969 !NumParamsExpr->isIntegerConstantExpr(NumParams, Context)) { 3970 Diag(Attr.getLoc(), diag::err_attribute_argument_type) 3971 << Attr.getName() << AANT_ArgumentIntegerConstant 3972 << NumParamsExpr->getSourceRange(); 3973 Attr.setInvalid(); 3974 return true; 3975 } 3976 3977 if (Context.getTargetInfo().getRegParmMax() == 0) { 3978 Diag(Attr.getLoc(), diag::err_attribute_regparm_wrong_platform) 3979 << NumParamsExpr->getSourceRange(); 3980 Attr.setInvalid(); 3981 return true; 3982 } 3983 3984 numParams = NumParams.getZExtValue(); 3985 if (numParams > Context.getTargetInfo().getRegParmMax()) { 3986 Diag(Attr.getLoc(), diag::err_attribute_regparm_invalid_number) 3987 << Context.getTargetInfo().getRegParmMax() << NumParamsExpr->getSourceRange(); 3988 Attr.setInvalid(); 3989 return true; 3990 } 3991 3992 return false; 3993} 3994 3995static void handleLaunchBoundsAttr(Sema &S, Decl *D, const AttributeList &Attr){ 3996 if (S.LangOpts.CUDA) { 3997 // check the attribute arguments. 3998 if (Attr.getNumArgs() != 1 && Attr.getNumArgs() != 2) { 3999 // FIXME: 0 is not okay. 4000 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 4001 return; 4002 } 4003 4004 if (!isFunctionOrMethod(D)) { 4005 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 4006 << Attr.getName() << ExpectedFunctionOrMethod; 4007 return; 4008 } 4009 4010 Expr *MaxThreadsExpr = Attr.getArgAsExpr(0); 4011 llvm::APSInt MaxThreads(32); 4012 if (MaxThreadsExpr->isTypeDependent() || 4013 MaxThreadsExpr->isValueDependent() || 4014 !MaxThreadsExpr->isIntegerConstantExpr(MaxThreads, S.Context)) { 4015 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 4016 << Attr.getName() << 1 << AANT_ArgumentIntegerConstant 4017 << MaxThreadsExpr->getSourceRange(); 4018 return; 4019 } 4020 4021 llvm::APSInt MinBlocks(32); 4022 if (Attr.getNumArgs() > 1) { 4023 Expr *MinBlocksExpr = Attr.getArgAsExpr(1); 4024 if (MinBlocksExpr->isTypeDependent() || 4025 MinBlocksExpr->isValueDependent() || 4026 !MinBlocksExpr->isIntegerConstantExpr(MinBlocks, S.Context)) { 4027 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 4028 << Attr.getName() << 2 << AANT_ArgumentIntegerConstant 4029 << MinBlocksExpr->getSourceRange(); 4030 return; 4031 } 4032 } 4033 4034 D->addAttr(::new (S.Context) 4035 CUDALaunchBoundsAttr(Attr.getRange(), S.Context, 4036 MaxThreads.getZExtValue(), 4037 MinBlocks.getZExtValue(), 4038 Attr.getAttributeSpellingListIndex())); 4039 } else { 4040 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "launch_bounds"; 4041 } 4042} 4043 4044static void handleArgumentWithTypeTagAttr(Sema &S, Decl *D, 4045 const AttributeList &Attr) { 4046 if (!Attr.isArgIdent(0)) { 4047 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 4048 << Attr.getName() << /* arg num = */ 1 << AANT_ArgumentIdentifier; 4049 return; 4050 } 4051 4052 if (!checkAttributeNumArgs(S, Attr, 3)) 4053 return; 4054 4055 StringRef AttrName = Attr.getName()->getName(); 4056 IdentifierInfo *ArgumentKind = Attr.getArgAsIdent(0)->Ident; 4057 4058 if (!isFunctionOrMethod(D) || !hasFunctionProto(D)) { 4059 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 4060 << Attr.getName() << ExpectedFunctionOrMethod; 4061 return; 4062 } 4063 4064 uint64_t ArgumentIdx; 4065 if (!checkFunctionOrMethodArgumentIndex(S, D, AttrName, 4066 Attr.getLoc(), 2, 4067 Attr.getArgAsExpr(1), ArgumentIdx)) 4068 return; 4069 4070 uint64_t TypeTagIdx; 4071 if (!checkFunctionOrMethodArgumentIndex(S, D, AttrName, 4072 Attr.getLoc(), 3, 4073 Attr.getArgAsExpr(2), TypeTagIdx)) 4074 return; 4075 4076 bool IsPointer = (AttrName == "pointer_with_type_tag"); 4077 if (IsPointer) { 4078 // Ensure that buffer has a pointer type. 4079 QualType BufferTy = getFunctionOrMethodArgType(D, ArgumentIdx); 4080 if (!BufferTy->isPointerType()) { 4081 S.Diag(Attr.getLoc(), diag::err_attribute_pointers_only) 4082 << Attr.getName(); 4083 } 4084 } 4085 4086 D->addAttr(::new (S.Context) 4087 ArgumentWithTypeTagAttr(Attr.getRange(), S.Context, ArgumentKind, 4088 ArgumentIdx, TypeTagIdx, IsPointer, 4089 Attr.getAttributeSpellingListIndex())); 4090} 4091 4092static void handleTypeTagForDatatypeAttr(Sema &S, Decl *D, 4093 const AttributeList &Attr) { 4094 if (!Attr.isArgIdent(0)) { 4095 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_type) 4096 << Attr.getName() << 1 << AANT_ArgumentIdentifier; 4097 return; 4098 } 4099 4100 if (!checkAttributeNumArgs(S, Attr, 1)) 4101 return; 4102 4103 IdentifierInfo *PointerKind = Attr.getArgAsIdent(0)->Ident; 4104 QualType MatchingCType = S.GetTypeFromParser(Attr.getMatchingCType(), NULL); 4105 4106 D->addAttr(::new (S.Context) 4107 TypeTagForDatatypeAttr(Attr.getRange(), S.Context, PointerKind, 4108 MatchingCType, 4109 Attr.getLayoutCompatible(), 4110 Attr.getMustBeNull(), 4111 Attr.getAttributeSpellingListIndex())); 4112} 4113 4114//===----------------------------------------------------------------------===// 4115// Checker-specific attribute handlers. 4116//===----------------------------------------------------------------------===// 4117 4118static bool isValidSubjectOfNSAttribute(Sema &S, QualType type) { 4119 return type->isDependentType() || 4120 type->isObjCObjectPointerType() || 4121 S.Context.isObjCNSObjectType(type); 4122} 4123static bool isValidSubjectOfCFAttribute(Sema &S, QualType type) { 4124 return type->isDependentType() || 4125 type->isPointerType() || 4126 isValidSubjectOfNSAttribute(S, type); 4127} 4128 4129static void handleNSConsumedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 4130 ParmVarDecl *param = dyn_cast<ParmVarDecl>(D); 4131 if (!param) { 4132 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 4133 << Attr.getRange() << Attr.getName() << ExpectedParameter; 4134 return; 4135 } 4136 4137 bool typeOK, cf; 4138 if (Attr.getKind() == AttributeList::AT_NSConsumed) { 4139 typeOK = isValidSubjectOfNSAttribute(S, param->getType()); 4140 cf = false; 4141 } else { 4142 typeOK = isValidSubjectOfCFAttribute(S, param->getType()); 4143 cf = true; 4144 } 4145 4146 if (!typeOK) { 4147 S.Diag(D->getLocStart(), diag::warn_ns_attribute_wrong_parameter_type) 4148 << Attr.getRange() << Attr.getName() << cf; 4149 return; 4150 } 4151 4152 if (cf) 4153 param->addAttr(::new (S.Context) 4154 CFConsumedAttr(Attr.getRange(), S.Context, 4155 Attr.getAttributeSpellingListIndex())); 4156 else 4157 param->addAttr(::new (S.Context) 4158 NSConsumedAttr(Attr.getRange(), S.Context, 4159 Attr.getAttributeSpellingListIndex())); 4160} 4161 4162static void handleNSConsumesSelfAttr(Sema &S, Decl *D, 4163 const AttributeList &Attr) { 4164 if (!isa<ObjCMethodDecl>(D)) { 4165 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 4166 << Attr.getRange() << Attr.getName() << ExpectedMethod; 4167 return; 4168 } 4169 4170 D->addAttr(::new (S.Context) 4171 NSConsumesSelfAttr(Attr.getRange(), S.Context, 4172 Attr.getAttributeSpellingListIndex())); 4173} 4174 4175static void handleNSReturnsRetainedAttr(Sema &S, Decl *D, 4176 const AttributeList &Attr) { 4177 4178 QualType returnType; 4179 4180 if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 4181 returnType = MD->getResultType(); 4182 else if (S.getLangOpts().ObjCAutoRefCount && hasDeclarator(D) && 4183 (Attr.getKind() == AttributeList::AT_NSReturnsRetained)) 4184 return; // ignore: was handled as a type attribute 4185 else if (ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(D)) 4186 returnType = PD->getType(); 4187 else if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) 4188 returnType = FD->getResultType(); 4189 else { 4190 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 4191 << Attr.getRange() << Attr.getName() 4192 << ExpectedFunctionOrMethod; 4193 return; 4194 } 4195 4196 bool typeOK; 4197 bool cf; 4198 switch (Attr.getKind()) { 4199 default: llvm_unreachable("invalid ownership attribute"); 4200 case AttributeList::AT_NSReturnsAutoreleased: 4201 case AttributeList::AT_NSReturnsRetained: 4202 case AttributeList::AT_NSReturnsNotRetained: 4203 typeOK = isValidSubjectOfNSAttribute(S, returnType); 4204 cf = false; 4205 break; 4206 4207 case AttributeList::AT_CFReturnsRetained: 4208 case AttributeList::AT_CFReturnsNotRetained: 4209 typeOK = isValidSubjectOfCFAttribute(S, returnType); 4210 cf = true; 4211 break; 4212 } 4213 4214 if (!typeOK) { 4215 S.Diag(D->getLocStart(), diag::warn_ns_attribute_wrong_return_type) 4216 << Attr.getRange() << Attr.getName() << isa<ObjCMethodDecl>(D) << cf; 4217 return; 4218 } 4219 4220 switch (Attr.getKind()) { 4221 default: 4222 llvm_unreachable("invalid ownership attribute"); 4223 case AttributeList::AT_NSReturnsAutoreleased: 4224 D->addAttr(::new (S.Context) 4225 NSReturnsAutoreleasedAttr(Attr.getRange(), S.Context, 4226 Attr.getAttributeSpellingListIndex())); 4227 return; 4228 case AttributeList::AT_CFReturnsNotRetained: 4229 D->addAttr(::new (S.Context) 4230 CFReturnsNotRetainedAttr(Attr.getRange(), S.Context, 4231 Attr.getAttributeSpellingListIndex())); 4232 return; 4233 case AttributeList::AT_NSReturnsNotRetained: 4234 D->addAttr(::new (S.Context) 4235 NSReturnsNotRetainedAttr(Attr.getRange(), S.Context, 4236 Attr.getAttributeSpellingListIndex())); 4237 return; 4238 case AttributeList::AT_CFReturnsRetained: 4239 D->addAttr(::new (S.Context) 4240 CFReturnsRetainedAttr(Attr.getRange(), S.Context, 4241 Attr.getAttributeSpellingListIndex())); 4242 return; 4243 case AttributeList::AT_NSReturnsRetained: 4244 D->addAttr(::new (S.Context) 4245 NSReturnsRetainedAttr(Attr.getRange(), S.Context, 4246 Attr.getAttributeSpellingListIndex())); 4247 return; 4248 }; 4249} 4250 4251static void handleObjCReturnsInnerPointerAttr(Sema &S, Decl *D, 4252 const AttributeList &attr) { 4253 const int EP_ObjCMethod = 1; 4254 const int EP_ObjCProperty = 2; 4255 4256 SourceLocation loc = attr.getLoc(); 4257 QualType resultType; 4258 4259 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(D); 4260 4261 if (!method) { 4262 ObjCPropertyDecl *property = dyn_cast<ObjCPropertyDecl>(D); 4263 if (!property) { 4264 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 4265 << SourceRange(loc, loc) << attr.getName() << ExpectedMethodOrProperty; 4266 return; 4267 } 4268 resultType = property->getType(); 4269 } 4270 else 4271 // Check that the method returns a normal pointer. 4272 resultType = method->getResultType(); 4273 4274 if (!resultType->isReferenceType() && 4275 (!resultType->isPointerType() || resultType->isObjCRetainableType())) { 4276 S.Diag(D->getLocStart(), diag::warn_ns_attribute_wrong_return_type) 4277 << SourceRange(loc) 4278 << attr.getName() << (method ? EP_ObjCMethod : EP_ObjCProperty) 4279 << /*non-retainable pointer*/ 2; 4280 4281 // Drop the attribute. 4282 return; 4283 } 4284 4285 D->addAttr(::new (S.Context) 4286 ObjCReturnsInnerPointerAttr(attr.getRange(), S.Context, 4287 attr.getAttributeSpellingListIndex())); 4288} 4289 4290static void handleObjCRequiresSuperAttr(Sema &S, Decl *D, 4291 const AttributeList &attr) { 4292 SourceLocation loc = attr.getLoc(); 4293 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(D); 4294 4295 if (!method) { 4296 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 4297 << SourceRange(loc, loc) << attr.getName() << ExpectedMethod; 4298 return; 4299 } 4300 DeclContext *DC = method->getDeclContext(); 4301 if (const ObjCProtocolDecl *PDecl = dyn_cast_or_null<ObjCProtocolDecl>(DC)) { 4302 S.Diag(D->getLocStart(), diag::warn_objc_requires_super_protocol) 4303 << attr.getName() << 0; 4304 S.Diag(PDecl->getLocation(), diag::note_protocol_decl); 4305 return; 4306 } 4307 if (method->getMethodFamily() == OMF_dealloc) { 4308 S.Diag(D->getLocStart(), diag::warn_objc_requires_super_protocol) 4309 << attr.getName() << 1; 4310 return; 4311 } 4312 4313 method->addAttr(::new (S.Context) 4314 ObjCRequiresSuperAttr(attr.getRange(), S.Context, 4315 attr.getAttributeSpellingListIndex())); 4316} 4317 4318/// Handle cf_audited_transfer and cf_unknown_transfer. 4319static void handleCFTransferAttr(Sema &S, Decl *D, const AttributeList &A) { 4320 if (!isa<FunctionDecl>(D)) { 4321 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 4322 << A.getRange() << A.getName() << ExpectedFunction; 4323 return; 4324 } 4325 4326 bool IsAudited = (A.getKind() == AttributeList::AT_CFAuditedTransfer); 4327 4328 // Check whether there's a conflicting attribute already present. 4329 Attr *Existing; 4330 if (IsAudited) { 4331 Existing = D->getAttr<CFUnknownTransferAttr>(); 4332 } else { 4333 Existing = D->getAttr<CFAuditedTransferAttr>(); 4334 } 4335 if (Existing) { 4336 S.Diag(D->getLocStart(), diag::err_attributes_are_not_compatible) 4337 << A.getName() 4338 << (IsAudited ? "cf_unknown_transfer" : "cf_audited_transfer") 4339 << A.getRange() << Existing->getRange(); 4340 return; 4341 } 4342 4343 // All clear; add the attribute. 4344 if (IsAudited) { 4345 D->addAttr(::new (S.Context) 4346 CFAuditedTransferAttr(A.getRange(), S.Context, 4347 A.getAttributeSpellingListIndex())); 4348 } else { 4349 D->addAttr(::new (S.Context) 4350 CFUnknownTransferAttr(A.getRange(), S.Context, 4351 A.getAttributeSpellingListIndex())); 4352 } 4353} 4354 4355static void handleNSBridgedAttr(Sema &S, Scope *Sc, Decl *D, 4356 const AttributeList &Attr) { 4357 RecordDecl *RD = dyn_cast<RecordDecl>(D); 4358 if (!RD || RD->isUnion()) { 4359 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 4360 << Attr.getRange() << Attr.getName() << ExpectedStruct; 4361 } 4362 4363 IdentifierLoc *Parm = Attr.isArgIdent(0) ? Attr.getArgAsIdent(0) : 0; 4364 4365 // In Objective-C, verify that the type names an Objective-C type. 4366 // We don't want to check this outside of ObjC because people sometimes 4367 // do crazy C declarations of Objective-C types. 4368 if (Parm && S.getLangOpts().ObjC1) { 4369 // Check for an existing type with this name. 4370 LookupResult R(S, DeclarationName(Parm->Ident), Parm->Loc, 4371 Sema::LookupOrdinaryName); 4372 if (S.LookupName(R, Sc)) { 4373 NamedDecl *Target = R.getFoundDecl(); 4374 if (Target && !isa<ObjCInterfaceDecl>(Target)) { 4375 S.Diag(D->getLocStart(), diag::err_ns_bridged_not_interface); 4376 S.Diag(Target->getLocStart(), diag::note_declared_at); 4377 } 4378 } 4379 } 4380 4381 D->addAttr(::new (S.Context) 4382 NSBridgedAttr(Attr.getRange(), S.Context, Parm ? Parm->Ident : 0, 4383 Attr.getAttributeSpellingListIndex())); 4384} 4385 4386static void handleObjCOwnershipAttr(Sema &S, Decl *D, 4387 const AttributeList &Attr) { 4388 if (hasDeclarator(D)) return; 4389 4390 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 4391 << Attr.getRange() << Attr.getName() << ExpectedVariable; 4392} 4393 4394static void handleObjCPreciseLifetimeAttr(Sema &S, Decl *D, 4395 const AttributeList &Attr) { 4396 if (!isa<VarDecl>(D) && !isa<FieldDecl>(D)) { 4397 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 4398 << Attr.getRange() << Attr.getName() << ExpectedVariable; 4399 return; 4400 } 4401 4402 ValueDecl *vd = cast<ValueDecl>(D); 4403 QualType type = vd->getType(); 4404 4405 if (!type->isDependentType() && 4406 !type->isObjCLifetimeType()) { 4407 S.Diag(Attr.getLoc(), diag::err_objc_precise_lifetime_bad_type) 4408 << type; 4409 return; 4410 } 4411 4412 Qualifiers::ObjCLifetime lifetime = type.getObjCLifetime(); 4413 4414 // If we have no lifetime yet, check the lifetime we're presumably 4415 // going to infer. 4416 if (lifetime == Qualifiers::OCL_None && !type->isDependentType()) 4417 lifetime = type->getObjCARCImplicitLifetime(); 4418 4419 switch (lifetime) { 4420 case Qualifiers::OCL_None: 4421 assert(type->isDependentType() && 4422 "didn't infer lifetime for non-dependent type?"); 4423 break; 4424 4425 case Qualifiers::OCL_Weak: // meaningful 4426 case Qualifiers::OCL_Strong: // meaningful 4427 break; 4428 4429 case Qualifiers::OCL_ExplicitNone: 4430 case Qualifiers::OCL_Autoreleasing: 4431 S.Diag(Attr.getLoc(), diag::warn_objc_precise_lifetime_meaningless) 4432 << (lifetime == Qualifiers::OCL_Autoreleasing); 4433 break; 4434 } 4435 4436 D->addAttr(::new (S.Context) 4437 ObjCPreciseLifetimeAttr(Attr.getRange(), S.Context, 4438 Attr.getAttributeSpellingListIndex())); 4439} 4440 4441//===----------------------------------------------------------------------===// 4442// Microsoft specific attribute handlers. 4443//===----------------------------------------------------------------------===// 4444 4445// Check if MS extensions or some other language extensions are enabled. If 4446// not, issue a diagnostic that the given attribute is unused. 4447static bool checkMicrosoftExt(Sema &S, const AttributeList &Attr, 4448 bool OtherExtension = false) { 4449 if (S.LangOpts.MicrosoftExt || OtherExtension) 4450 return true; 4451 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 4452 return false; 4453} 4454 4455static void handleUuidAttr(Sema &S, Decl *D, const AttributeList &Attr) { 4456 if (!checkMicrosoftExt(S, Attr, S.LangOpts.Borland)) 4457 return; 4458 4459 StringRef StrRef; 4460 SourceLocation LiteralLoc; 4461 if (!S.checkStringLiteralArgumentAttr(Attr, 0, StrRef, &LiteralLoc)) 4462 return; 4463 4464 // GUID format is "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX" or 4465 // "{XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX}", normalize to the former. 4466 if (StrRef.size() == 38 && StrRef.front() == '{' && StrRef.back() == '}') 4467 StrRef = StrRef.drop_front().drop_back(); 4468 4469 // Validate GUID length. 4470 if (StrRef.size() != 36) { 4471 S.Diag(LiteralLoc, diag::err_attribute_uuid_malformed_guid); 4472 return; 4473 } 4474 4475 for (unsigned i = 0; i < 36; ++i) { 4476 if (i == 8 || i == 13 || i == 18 || i == 23) { 4477 if (StrRef[i] != '-') { 4478 S.Diag(LiteralLoc, diag::err_attribute_uuid_malformed_guid); 4479 return; 4480 } 4481 } else if (!isHexDigit(StrRef[i])) { 4482 S.Diag(LiteralLoc, diag::err_attribute_uuid_malformed_guid); 4483 return; 4484 } 4485 } 4486 4487 D->addAttr(::new (S.Context) UuidAttr(Attr.getRange(), S.Context, StrRef, 4488 Attr.getAttributeSpellingListIndex())); 4489} 4490 4491static void handleInheritanceAttr(Sema &S, Decl *D, const AttributeList &Attr) { 4492 if (!checkMicrosoftExt(S, Attr)) 4493 return; 4494 4495 AttributeList::Kind Kind = Attr.getKind(); 4496 if (Kind == AttributeList::AT_SingleInheritance) 4497 D->addAttr( 4498 ::new (S.Context) 4499 SingleInheritanceAttr(Attr.getRange(), S.Context, 4500 Attr.getAttributeSpellingListIndex())); 4501 else if (Kind == AttributeList::AT_MultipleInheritance) 4502 D->addAttr( 4503 ::new (S.Context) 4504 MultipleInheritanceAttr(Attr.getRange(), S.Context, 4505 Attr.getAttributeSpellingListIndex())); 4506 else if (Kind == AttributeList::AT_VirtualInheritance) 4507 D->addAttr( 4508 ::new (S.Context) 4509 VirtualInheritanceAttr(Attr.getRange(), S.Context, 4510 Attr.getAttributeSpellingListIndex())); 4511} 4512 4513static void handlePortabilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { 4514 if (!checkMicrosoftExt(S, Attr)) 4515 return; 4516 4517 AttributeList::Kind Kind = Attr.getKind(); 4518 if (Kind == AttributeList::AT_Win64) 4519 D->addAttr( 4520 ::new (S.Context) Win64Attr(Attr.getRange(), S.Context, 4521 Attr.getAttributeSpellingListIndex())); 4522} 4523 4524static void handleForceInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { 4525 if (!checkMicrosoftExt(S, Attr)) 4526 return; 4527 D->addAttr(::new (S.Context) 4528 ForceInlineAttr(Attr.getRange(), S.Context, 4529 Attr.getAttributeSpellingListIndex())); 4530} 4531 4532static void handleSelectAnyAttr(Sema &S, Decl *D, const AttributeList &Attr) { 4533 if (!checkMicrosoftExt(S, Attr)) 4534 return; 4535 // Check linkage after possibly merging declaratinos. See 4536 // checkAttributesAfterMerging(). 4537 D->addAttr(::new (S.Context) 4538 SelectAnyAttr(Attr.getRange(), S.Context, 4539 Attr.getAttributeSpellingListIndex())); 4540} 4541 4542/// Handles semantic checking for features that are common to all attributes, 4543/// such as checking whether a parameter was properly specified, or the correct 4544/// number of arguments were passed, etc. 4545static bool handleCommonAttributeFeatures(Sema &S, Scope *scope, Decl *D, 4546 const AttributeList &Attr) { 4547 // Several attributes carry different semantics than the parsing requires, so 4548 // those are opted out of the common handling. 4549 // 4550 // We also bail on unknown and ignored attributes because those are handled 4551 // as part of the target-specific handling logic. 4552 if (Attr.hasCustomParsing() || 4553 Attr.getKind() == AttributeList::UnknownAttribute || 4554 Attr.getKind() == AttributeList::IgnoredAttribute) 4555 return false; 4556 4557 // If there are no optional arguments, then checking for the argument count 4558 // is trivial. 4559 if (Attr.getMinArgs() == Attr.getMaxArgs() && 4560 !checkAttributeNumArgs(S, Attr, Attr.getMinArgs())) 4561 return true; 4562 return false; 4563} 4564 4565//===----------------------------------------------------------------------===// 4566// Top Level Sema Entry Points 4567//===----------------------------------------------------------------------===// 4568 4569/// ProcessDeclAttribute - Apply the specific attribute to the specified decl if 4570/// the attribute applies to decls. If the attribute is a type attribute, just 4571/// silently ignore it if a GNU attribute. 4572static void ProcessDeclAttribute(Sema &S, Scope *scope, Decl *D, 4573 const AttributeList &Attr, 4574 bool IncludeCXX11Attributes) { 4575 if (Attr.isInvalid()) 4576 return; 4577 4578 // Ignore C++11 attributes on declarator chunks: they appertain to the type 4579 // instead. 4580 if (Attr.isCXX11Attribute() && !IncludeCXX11Attributes) 4581 return; 4582 4583 if (handleCommonAttributeFeatures(S, scope, D, Attr)) 4584 return; 4585 4586 switch (Attr.getKind()) { 4587 case AttributeList::AT_IBAction: handleIBAction(S, D, Attr); break; 4588 case AttributeList::AT_IBOutlet: handleIBOutlet(S, D, Attr); break; 4589 case AttributeList::AT_IBOutletCollection: 4590 handleIBOutletCollection(S, D, Attr); break; 4591 case AttributeList::AT_AddressSpace: 4592 case AttributeList::AT_ObjCGC: 4593 case AttributeList::AT_VectorSize: 4594 case AttributeList::AT_NeonVectorType: 4595 case AttributeList::AT_NeonPolyVectorType: 4596 case AttributeList::AT_Ptr32: 4597 case AttributeList::AT_Ptr64: 4598 case AttributeList::AT_SPtr: 4599 case AttributeList::AT_UPtr: 4600 // Ignore these, these are type attributes, handled by 4601 // ProcessTypeAttributes. 4602 break; 4603 case AttributeList::AT_Alias: handleAliasAttr (S, D, Attr); break; 4604 case AttributeList::AT_Aligned: handleAlignedAttr (S, D, Attr); break; 4605 case AttributeList::AT_AllocSize: handleAllocSizeAttr (S, D, Attr); break; 4606 case AttributeList::AT_AlwaysInline: 4607 handleAlwaysInlineAttr (S, D, Attr); break; 4608 case AttributeList::AT_AnalyzerNoReturn: 4609 handleAnalyzerNoReturnAttr (S, D, Attr); break; 4610 case AttributeList::AT_TLSModel: handleTLSModelAttr (S, D, Attr); break; 4611 case AttributeList::AT_Annotate: handleAnnotateAttr (S, D, Attr); break; 4612 case AttributeList::AT_Availability:handleAvailabilityAttr(S, D, Attr); break; 4613 case AttributeList::AT_CarriesDependency: 4614 handleDependencyAttr(S, scope, D, Attr); 4615 break; 4616 case AttributeList::AT_Common: handleCommonAttr (S, D, Attr); break; 4617 case AttributeList::AT_CUDAConstant:handleConstantAttr (S, D, Attr); break; 4618 case AttributeList::AT_Constructor: handleConstructorAttr (S, D, Attr); break; 4619 case AttributeList::AT_CXX11NoReturn: 4620 handleCXX11NoReturnAttr(S, D, Attr); 4621 break; 4622 case AttributeList::AT_Deprecated: 4623 handleAttrWithMessage<DeprecatedAttr>(S, D, Attr); 4624 break; 4625 case AttributeList::AT_Destructor: handleDestructorAttr (S, D, Attr); break; 4626 case AttributeList::AT_ExtVectorType: 4627 handleExtVectorTypeAttr(S, scope, D, Attr); 4628 break; 4629 case AttributeList::AT_MinSize: 4630 handleMinSizeAttr(S, D, Attr); 4631 break; 4632 case AttributeList::AT_Format: handleFormatAttr (S, D, Attr); break; 4633 case AttributeList::AT_FormatArg: handleFormatArgAttr (S, D, Attr); break; 4634 case AttributeList::AT_CUDAGlobal: handleGlobalAttr (S, D, Attr); break; 4635 case AttributeList::AT_CUDADevice: handleDeviceAttr (S, D, Attr); break; 4636 case AttributeList::AT_CUDAHost: handleHostAttr (S, D, Attr); break; 4637 case AttributeList::AT_GNUInline: handleGNUInlineAttr (S, D, Attr); break; 4638 case AttributeList::AT_CUDALaunchBounds: 4639 handleLaunchBoundsAttr(S, D, Attr); 4640 break; 4641 case AttributeList::AT_Malloc: handleMallocAttr (S, D, Attr); break; 4642 case AttributeList::AT_MayAlias: handleMayAliasAttr (S, D, Attr); break; 4643 case AttributeList::AT_Mode: handleModeAttr (S, D, Attr); break; 4644 case AttributeList::AT_NoCommon: handleNoCommonAttr (S, D, Attr); break; 4645 case AttributeList::AT_NonNull: handleNonNullAttr (S, D, Attr); break; 4646 case AttributeList::AT_Overloadable:handleOverloadableAttr(S, D, Attr); break; 4647 case AttributeList::AT_ownership_returns: 4648 case AttributeList::AT_ownership_takes: 4649 case AttributeList::AT_ownership_holds: 4650 handleOwnershipAttr (S, D, Attr); break; 4651 case AttributeList::AT_Cold: handleColdAttr (S, D, Attr); break; 4652 case AttributeList::AT_Hot: handleHotAttr (S, D, Attr); break; 4653 case AttributeList::AT_Naked: handleNakedAttr (S, D, Attr); break; 4654 case AttributeList::AT_NoReturn: handleNoReturnAttr (S, D, Attr); break; 4655 case AttributeList::AT_NoThrow: handleNothrowAttr (S, D, Attr); break; 4656 case AttributeList::AT_CUDAShared: handleSharedAttr (S, D, Attr); break; 4657 case AttributeList::AT_VecReturn: handleVecReturnAttr (S, D, Attr); break; 4658 4659 case AttributeList::AT_ObjCOwnership: 4660 handleObjCOwnershipAttr(S, D, Attr); break; 4661 case AttributeList::AT_ObjCPreciseLifetime: 4662 handleObjCPreciseLifetimeAttr(S, D, Attr); break; 4663 4664 case AttributeList::AT_ObjCReturnsInnerPointer: 4665 handleObjCReturnsInnerPointerAttr(S, D, Attr); break; 4666 4667 case AttributeList::AT_ObjCRequiresSuper: 4668 handleObjCRequiresSuperAttr(S, D, Attr); break; 4669 4670 case AttributeList::AT_NSBridged: 4671 handleNSBridgedAttr(S, scope, D, Attr); break; 4672 4673 case AttributeList::AT_CFAuditedTransfer: 4674 case AttributeList::AT_CFUnknownTransfer: 4675 handleCFTransferAttr(S, D, Attr); break; 4676 4677 // Checker-specific. 4678 case AttributeList::AT_CFConsumed: 4679 case AttributeList::AT_NSConsumed: handleNSConsumedAttr (S, D, Attr); break; 4680 case AttributeList::AT_NSConsumesSelf: 4681 handleNSConsumesSelfAttr(S, D, Attr); break; 4682 4683 case AttributeList::AT_NSReturnsAutoreleased: 4684 case AttributeList::AT_NSReturnsNotRetained: 4685 case AttributeList::AT_CFReturnsNotRetained: 4686 case AttributeList::AT_NSReturnsRetained: 4687 case AttributeList::AT_CFReturnsRetained: 4688 handleNSReturnsRetainedAttr(S, D, Attr); break; 4689 4690 case AttributeList::AT_WorkGroupSizeHint: 4691 case AttributeList::AT_ReqdWorkGroupSize: 4692 handleWorkGroupSize(S, D, Attr); break; 4693 4694 case AttributeList::AT_VecTypeHint: 4695 handleVecTypeHint(S, D, Attr); break; 4696 4697 case AttributeList::AT_InitPriority: 4698 handleInitPriorityAttr(S, D, Attr); break; 4699 4700 case AttributeList::AT_Packed: handlePackedAttr (S, D, Attr); break; 4701 case AttributeList::AT_Section: handleSectionAttr (S, D, Attr); break; 4702 case AttributeList::AT_Unavailable: 4703 handleAttrWithMessage<UnavailableAttr>(S, D, Attr); 4704 break; 4705 case AttributeList::AT_ArcWeakrefUnavailable: 4706 handleArcWeakrefUnavailableAttr (S, D, Attr); 4707 break; 4708 case AttributeList::AT_ObjCRootClass: 4709 handleObjCRootClassAttr(S, D, Attr); 4710 break; 4711 case AttributeList::AT_ObjCRequiresPropertyDefs: 4712 handleObjCRequiresPropertyDefsAttr (S, D, Attr); 4713 break; 4714 case AttributeList::AT_Unused: handleUnusedAttr (S, D, Attr); break; 4715 case AttributeList::AT_ReturnsTwice: 4716 handleReturnsTwiceAttr(S, D, Attr); 4717 break; 4718 case AttributeList::AT_Used: handleUsedAttr (S, D, Attr); break; 4719 case AttributeList::AT_Visibility: 4720 handleVisibilityAttr(S, D, Attr, false); 4721 break; 4722 case AttributeList::AT_TypeVisibility: 4723 handleVisibilityAttr(S, D, Attr, true); 4724 break; 4725 case AttributeList::AT_WarnUnused: 4726 handleWarnUnusedAttr(S, D, Attr); 4727 break; 4728 case AttributeList::AT_WarnUnusedResult: handleWarnUnusedResult(S, D, Attr); 4729 break; 4730 case AttributeList::AT_Weak: handleWeakAttr (S, D, Attr); break; 4731 case AttributeList::AT_WeakRef: handleWeakRefAttr (S, D, Attr); break; 4732 case AttributeList::AT_WeakImport: handleWeakImportAttr (S, D, Attr); break; 4733 case AttributeList::AT_TransparentUnion: 4734 handleTransparentUnionAttr(S, D, Attr); 4735 break; 4736 case AttributeList::AT_ObjCException: 4737 handleObjCExceptionAttr(S, D, Attr); 4738 break; 4739 case AttributeList::AT_ObjCMethodFamily: 4740 handleObjCMethodFamilyAttr(S, D, Attr); 4741 break; 4742 case AttributeList::AT_ObjCNSObject:handleObjCNSObject (S, D, Attr); break; 4743 case AttributeList::AT_Blocks: handleBlocksAttr (S, D, Attr); break; 4744 case AttributeList::AT_Sentinel: handleSentinelAttr (S, D, Attr); break; 4745 case AttributeList::AT_Const: handleConstAttr (S, D, Attr); break; 4746 case AttributeList::AT_Pure: handlePureAttr (S, D, Attr); break; 4747 case AttributeList::AT_Cleanup: handleCleanupAttr (S, D, Attr); break; 4748 case AttributeList::AT_NoDebug: handleNoDebugAttr (S, D, Attr); break; 4749 case AttributeList::AT_NoInline: handleNoInlineAttr (S, D, Attr); break; 4750 case AttributeList::AT_Regparm: handleRegparmAttr (S, D, Attr); break; 4751 case AttributeList::IgnoredAttribute: 4752 // Just ignore 4753 break; 4754 case AttributeList::AT_NoInstrumentFunction: // Interacts with -pg. 4755 handleNoInstrumentFunctionAttr(S, D, Attr); 4756 break; 4757 case AttributeList::AT_StdCall: 4758 case AttributeList::AT_CDecl: 4759 case AttributeList::AT_FastCall: 4760 case AttributeList::AT_ThisCall: 4761 case AttributeList::AT_Pascal: 4762 case AttributeList::AT_MSABI: 4763 case AttributeList::AT_SysVABI: 4764 case AttributeList::AT_Pcs: 4765 case AttributeList::AT_PnaclCall: 4766 case AttributeList::AT_IntelOclBicc: 4767 handleCallConvAttr(S, D, Attr); 4768 break; 4769 case AttributeList::AT_OpenCLKernel: 4770 handleOpenCLKernelAttr(S, D, Attr); 4771 break; 4772 case AttributeList::AT_OpenCLImageAccess: 4773 handleOpenCLImageAccessAttr(S, D, Attr); 4774 break; 4775 4776 // Microsoft attributes: 4777 case AttributeList::AT_MsStruct: 4778 handleMsStructAttr(S, D, Attr); 4779 break; 4780 case AttributeList::AT_Uuid: 4781 handleUuidAttr(S, D, Attr); 4782 break; 4783 case AttributeList::AT_SingleInheritance: 4784 case AttributeList::AT_MultipleInheritance: 4785 case AttributeList::AT_VirtualInheritance: 4786 handleInheritanceAttr(S, D, Attr); 4787 break; 4788 case AttributeList::AT_Win64: 4789 handlePortabilityAttr(S, D, Attr); 4790 break; 4791 case AttributeList::AT_ForceInline: 4792 handleForceInlineAttr(S, D, Attr); 4793 break; 4794 case AttributeList::AT_SelectAny: 4795 handleSelectAnyAttr(S, D, Attr); 4796 break; 4797 4798 // Thread safety attributes: 4799 case AttributeList::AT_AssertExclusiveLock: 4800 handleAssertExclusiveLockAttr(S, D, Attr); 4801 break; 4802 case AttributeList::AT_AssertSharedLock: 4803 handleAssertSharedLockAttr(S, D, Attr); 4804 break; 4805 case AttributeList::AT_GuardedVar: 4806 handleGuardedVarAttr(S, D, Attr); 4807 break; 4808 case AttributeList::AT_PtGuardedVar: 4809 handlePtGuardedVarAttr(S, D, Attr); 4810 break; 4811 case AttributeList::AT_ScopedLockable: 4812 handleScopedLockableAttr(S, D, Attr); 4813 break; 4814 case AttributeList::AT_NoSanitizeAddress: 4815 handleNoSanitizeAddressAttr(S, D, Attr); 4816 break; 4817 case AttributeList::AT_NoThreadSafetyAnalysis: 4818 handleNoThreadSafetyAnalysis(S, D, Attr); 4819 break; 4820 case AttributeList::AT_NoSanitizeThread: 4821 handleNoSanitizeThread(S, D, Attr); 4822 break; 4823 case AttributeList::AT_NoSanitizeMemory: 4824 handleNoSanitizeMemory(S, D, Attr); 4825 break; 4826 case AttributeList::AT_Lockable: 4827 handleLockableAttr(S, D, Attr); 4828 break; 4829 case AttributeList::AT_GuardedBy: 4830 handleGuardedByAttr(S, D, Attr); 4831 break; 4832 case AttributeList::AT_PtGuardedBy: 4833 handlePtGuardedByAttr(S, D, Attr); 4834 break; 4835 case AttributeList::AT_ExclusiveLockFunction: 4836 handleExclusiveLockFunctionAttr(S, D, Attr); 4837 break; 4838 case AttributeList::AT_ExclusiveLocksRequired: 4839 handleExclusiveLocksRequiredAttr(S, D, Attr); 4840 break; 4841 case AttributeList::AT_ExclusiveTrylockFunction: 4842 handleExclusiveTrylockFunctionAttr(S, D, Attr); 4843 break; 4844 case AttributeList::AT_LockReturned: 4845 handleLockReturnedAttr(S, D, Attr); 4846 break; 4847 case AttributeList::AT_LocksExcluded: 4848 handleLocksExcludedAttr(S, D, Attr); 4849 break; 4850 case AttributeList::AT_SharedLockFunction: 4851 handleSharedLockFunctionAttr(S, D, Attr); 4852 break; 4853 case AttributeList::AT_SharedLocksRequired: 4854 handleSharedLocksRequiredAttr(S, D, Attr); 4855 break; 4856 case AttributeList::AT_SharedTrylockFunction: 4857 handleSharedTrylockFunctionAttr(S, D, Attr); 4858 break; 4859 case AttributeList::AT_UnlockFunction: 4860 handleUnlockFunAttr(S, D, Attr); 4861 break; 4862 case AttributeList::AT_AcquiredBefore: 4863 handleAcquiredBeforeAttr(S, D, Attr); 4864 break; 4865 case AttributeList::AT_AcquiredAfter: 4866 handleAcquiredAfterAttr(S, D, Attr); 4867 break; 4868 4869 // Consumed analysis attributes. 4870 case AttributeList::AT_Consumable: 4871 handleConsumableAttr(S, D, Attr); 4872 break; 4873 case AttributeList::AT_CallableWhen: 4874 handleCallableWhenAttr(S, D, Attr); 4875 break; 4876 case AttributeList::AT_ParamTypestate: 4877 handleParamTypestateAttr(S, D, Attr); 4878 break; 4879 case AttributeList::AT_ReturnTypestate: 4880 handleReturnTypestateAttr(S, D, Attr); 4881 break; 4882 case AttributeList::AT_SetTypestate: 4883 handleSetTypestateAttr(S, D, Attr); 4884 break; 4885 case AttributeList::AT_TestTypestate: 4886 handleTestTypestateAttr(S, D, Attr); 4887 break; 4888 4889 // Type safety attributes. 4890 case AttributeList::AT_ArgumentWithTypeTag: 4891 handleArgumentWithTypeTagAttr(S, D, Attr); 4892 break; 4893 case AttributeList::AT_TypeTagForDatatype: 4894 handleTypeTagForDatatypeAttr(S, D, Attr); 4895 break; 4896 4897 default: 4898 // Ask target about the attribute. 4899 const TargetAttributesSema &TargetAttrs = S.getTargetAttributesSema(); 4900 if (!TargetAttrs.ProcessDeclAttribute(scope, D, Attr, S)) 4901 S.Diag(Attr.getLoc(), Attr.isDeclspecAttribute() ? 4902 diag::warn_unhandled_ms_attribute_ignored : 4903 diag::warn_unknown_attribute_ignored) << Attr.getName(); 4904 break; 4905 } 4906} 4907 4908/// ProcessDeclAttributeList - Apply all the decl attributes in the specified 4909/// attribute list to the specified decl, ignoring any type attributes. 4910void Sema::ProcessDeclAttributeList(Scope *S, Decl *D, 4911 const AttributeList *AttrList, 4912 bool IncludeCXX11Attributes) { 4913 for (const AttributeList* l = AttrList; l; l = l->getNext()) 4914 ProcessDeclAttribute(*this, S, D, *l, IncludeCXX11Attributes); 4915 4916 // GCC accepts 4917 // static int a9 __attribute__((weakref)); 4918 // but that looks really pointless. We reject it. 4919 if (D->hasAttr<WeakRefAttr>() && !D->hasAttr<AliasAttr>()) { 4920 Diag(AttrList->getLoc(), diag::err_attribute_weakref_without_alias) << 4921 cast<NamedDecl>(D)->getNameAsString(); 4922 D->dropAttr<WeakRefAttr>(); 4923 return; 4924 } 4925} 4926 4927// Annotation attributes are the only attributes allowed after an access 4928// specifier. 4929bool Sema::ProcessAccessDeclAttributeList(AccessSpecDecl *ASDecl, 4930 const AttributeList *AttrList) { 4931 for (const AttributeList* l = AttrList; l; l = l->getNext()) { 4932 if (l->getKind() == AttributeList::AT_Annotate) { 4933 handleAnnotateAttr(*this, ASDecl, *l); 4934 } else { 4935 Diag(l->getLoc(), diag::err_only_annotate_after_access_spec); 4936 return true; 4937 } 4938 } 4939 4940 return false; 4941} 4942 4943/// checkUnusedDeclAttributes - Check a list of attributes to see if it 4944/// contains any decl attributes that we should warn about. 4945static void checkUnusedDeclAttributes(Sema &S, const AttributeList *A) { 4946 for ( ; A; A = A->getNext()) { 4947 // Only warn if the attribute is an unignored, non-type attribute. 4948 if (A->isUsedAsTypeAttr() || A->isInvalid()) continue; 4949 if (A->getKind() == AttributeList::IgnoredAttribute) continue; 4950 4951 if (A->getKind() == AttributeList::UnknownAttribute) { 4952 S.Diag(A->getLoc(), diag::warn_unknown_attribute_ignored) 4953 << A->getName() << A->getRange(); 4954 } else { 4955 S.Diag(A->getLoc(), diag::warn_attribute_not_on_decl) 4956 << A->getName() << A->getRange(); 4957 } 4958 } 4959} 4960 4961/// checkUnusedDeclAttributes - Given a declarator which is not being 4962/// used to build a declaration, complain about any decl attributes 4963/// which might be lying around on it. 4964void Sema::checkUnusedDeclAttributes(Declarator &D) { 4965 ::checkUnusedDeclAttributes(*this, D.getDeclSpec().getAttributes().getList()); 4966 ::checkUnusedDeclAttributes(*this, D.getAttributes()); 4967 for (unsigned i = 0, e = D.getNumTypeObjects(); i != e; ++i) 4968 ::checkUnusedDeclAttributes(*this, D.getTypeObject(i).getAttrs()); 4969} 4970 4971/// DeclClonePragmaWeak - clone existing decl (maybe definition), 4972/// \#pragma weak needs a non-definition decl and source may not have one. 4973NamedDecl * Sema::DeclClonePragmaWeak(NamedDecl *ND, IdentifierInfo *II, 4974 SourceLocation Loc) { 4975 assert(isa<FunctionDecl>(ND) || isa<VarDecl>(ND)); 4976 NamedDecl *NewD = 0; 4977 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(ND)) { 4978 FunctionDecl *NewFD; 4979 // FIXME: Missing call to CheckFunctionDeclaration(). 4980 // FIXME: Mangling? 4981 // FIXME: Is the qualifier info correct? 4982 // FIXME: Is the DeclContext correct? 4983 NewFD = FunctionDecl::Create(FD->getASTContext(), FD->getDeclContext(), 4984 Loc, Loc, DeclarationName(II), 4985 FD->getType(), FD->getTypeSourceInfo(), 4986 SC_None, false/*isInlineSpecified*/, 4987 FD->hasPrototype(), 4988 false/*isConstexprSpecified*/); 4989 NewD = NewFD; 4990 4991 if (FD->getQualifier()) 4992 NewFD->setQualifierInfo(FD->getQualifierLoc()); 4993 4994 // Fake up parameter variables; they are declared as if this were 4995 // a typedef. 4996 QualType FDTy = FD->getType(); 4997 if (const FunctionProtoType *FT = FDTy->getAs<FunctionProtoType>()) { 4998 SmallVector<ParmVarDecl*, 16> Params; 4999 for (FunctionProtoType::arg_type_iterator AI = FT->arg_type_begin(), 5000 AE = FT->arg_type_end(); AI != AE; ++AI) { 5001 ParmVarDecl *Param = BuildParmVarDeclForTypedef(NewFD, Loc, *AI); 5002 Param->setScopeInfo(0, Params.size()); 5003 Params.push_back(Param); 5004 } 5005 NewFD->setParams(Params); 5006 } 5007 } else if (VarDecl *VD = dyn_cast<VarDecl>(ND)) { 5008 NewD = VarDecl::Create(VD->getASTContext(), VD->getDeclContext(), 5009 VD->getInnerLocStart(), VD->getLocation(), II, 5010 VD->getType(), VD->getTypeSourceInfo(), 5011 VD->getStorageClass()); 5012 if (VD->getQualifier()) { 5013 VarDecl *NewVD = cast<VarDecl>(NewD); 5014 NewVD->setQualifierInfo(VD->getQualifierLoc()); 5015 } 5016 } 5017 return NewD; 5018} 5019 5020/// DeclApplyPragmaWeak - A declaration (maybe definition) needs \#pragma weak 5021/// applied to it, possibly with an alias. 5022void Sema::DeclApplyPragmaWeak(Scope *S, NamedDecl *ND, WeakInfo &W) { 5023 if (W.getUsed()) return; // only do this once 5024 W.setUsed(true); 5025 if (W.getAlias()) { // clone decl, impersonate __attribute(weak,alias(...)) 5026 IdentifierInfo *NDId = ND->getIdentifier(); 5027 NamedDecl *NewD = DeclClonePragmaWeak(ND, W.getAlias(), W.getLocation()); 5028 NewD->addAttr(::new (Context) AliasAttr(W.getLocation(), Context, 5029 NDId->getName())); 5030 NewD->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 5031 WeakTopLevelDecl.push_back(NewD); 5032 // FIXME: "hideous" code from Sema::LazilyCreateBuiltin 5033 // to insert Decl at TU scope, sorry. 5034 DeclContext *SavedContext = CurContext; 5035 CurContext = Context.getTranslationUnitDecl(); 5036 PushOnScopeChains(NewD, S); 5037 CurContext = SavedContext; 5038 } else { // just add weak to existing 5039 ND->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 5040 } 5041} 5042 5043void Sema::ProcessPragmaWeak(Scope *S, Decl *D) { 5044 // It's valid to "forward-declare" #pragma weak, in which case we 5045 // have to do this. 5046 LoadExternalWeakUndeclaredIdentifiers(); 5047 if (!WeakUndeclaredIdentifiers.empty()) { 5048 NamedDecl *ND = NULL; 5049 if (VarDecl *VD = dyn_cast<VarDecl>(D)) 5050 if (VD->isExternC()) 5051 ND = VD; 5052 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) 5053 if (FD->isExternC()) 5054 ND = FD; 5055 if (ND) { 5056 if (IdentifierInfo *Id = ND->getIdentifier()) { 5057 llvm::DenseMap<IdentifierInfo*,WeakInfo>::iterator I 5058 = WeakUndeclaredIdentifiers.find(Id); 5059 if (I != WeakUndeclaredIdentifiers.end()) { 5060 WeakInfo W = I->second; 5061 DeclApplyPragmaWeak(S, ND, W); 5062 WeakUndeclaredIdentifiers[Id] = W; 5063 } 5064 } 5065 } 5066 } 5067} 5068 5069/// ProcessDeclAttributes - Given a declarator (PD) with attributes indicated in 5070/// it, apply them to D. This is a bit tricky because PD can have attributes 5071/// specified in many different places, and we need to find and apply them all. 5072void Sema::ProcessDeclAttributes(Scope *S, Decl *D, const Declarator &PD) { 5073 // Apply decl attributes from the DeclSpec if present. 5074 if (const AttributeList *Attrs = PD.getDeclSpec().getAttributes().getList()) 5075 ProcessDeclAttributeList(S, D, Attrs); 5076 5077 // Walk the declarator structure, applying decl attributes that were in a type 5078 // position to the decl itself. This handles cases like: 5079 // int *__attr__(x)** D; 5080 // when X is a decl attribute. 5081 for (unsigned i = 0, e = PD.getNumTypeObjects(); i != e; ++i) 5082 if (const AttributeList *Attrs = PD.getTypeObject(i).getAttrs()) 5083 ProcessDeclAttributeList(S, D, Attrs, /*IncludeCXX11Attributes=*/false); 5084 5085 // Finally, apply any attributes on the decl itself. 5086 if (const AttributeList *Attrs = PD.getAttributes()) 5087 ProcessDeclAttributeList(S, D, Attrs); 5088} 5089 5090/// Is the given declaration allowed to use a forbidden type? 5091static bool isForbiddenTypeAllowed(Sema &S, Decl *decl) { 5092 // Private ivars are always okay. Unfortunately, people don't 5093 // always properly make their ivars private, even in system headers. 5094 // Plus we need to make fields okay, too. 5095 // Function declarations in sys headers will be marked unavailable. 5096 if (!isa<FieldDecl>(decl) && !isa<ObjCPropertyDecl>(decl) && 5097 !isa<FunctionDecl>(decl)) 5098 return false; 5099 5100 // Require it to be declared in a system header. 5101 return S.Context.getSourceManager().isInSystemHeader(decl->getLocation()); 5102} 5103 5104/// Handle a delayed forbidden-type diagnostic. 5105static void handleDelayedForbiddenType(Sema &S, DelayedDiagnostic &diag, 5106 Decl *decl) { 5107 if (decl && isForbiddenTypeAllowed(S, decl)) { 5108 decl->addAttr(new (S.Context) UnavailableAttr(diag.Loc, S.Context, 5109 "this system declaration uses an unsupported type")); 5110 return; 5111 } 5112 if (S.getLangOpts().ObjCAutoRefCount) 5113 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(decl)) { 5114 // FIXME: we may want to suppress diagnostics for all 5115 // kind of forbidden type messages on unavailable functions. 5116 if (FD->hasAttr<UnavailableAttr>() && 5117 diag.getForbiddenTypeDiagnostic() == 5118 diag::err_arc_array_param_no_ownership) { 5119 diag.Triggered = true; 5120 return; 5121 } 5122 } 5123 5124 S.Diag(diag.Loc, diag.getForbiddenTypeDiagnostic()) 5125 << diag.getForbiddenTypeOperand() << diag.getForbiddenTypeArgument(); 5126 diag.Triggered = true; 5127} 5128 5129void Sema::PopParsingDeclaration(ParsingDeclState state, Decl *decl) { 5130 assert(DelayedDiagnostics.getCurrentPool()); 5131 DelayedDiagnosticPool &poppedPool = *DelayedDiagnostics.getCurrentPool(); 5132 DelayedDiagnostics.popWithoutEmitting(state); 5133 5134 // When delaying diagnostics to run in the context of a parsed 5135 // declaration, we only want to actually emit anything if parsing 5136 // succeeds. 5137 if (!decl) return; 5138 5139 // We emit all the active diagnostics in this pool or any of its 5140 // parents. In general, we'll get one pool for the decl spec 5141 // and a child pool for each declarator; in a decl group like: 5142 // deprecated_typedef foo, *bar, baz(); 5143 // only the declarator pops will be passed decls. This is correct; 5144 // we really do need to consider delayed diagnostics from the decl spec 5145 // for each of the different declarations. 5146 const DelayedDiagnosticPool *pool = &poppedPool; 5147 do { 5148 for (DelayedDiagnosticPool::pool_iterator 5149 i = pool->pool_begin(), e = pool->pool_end(); i != e; ++i) { 5150 // This const_cast is a bit lame. Really, Triggered should be mutable. 5151 DelayedDiagnostic &diag = const_cast<DelayedDiagnostic&>(*i); 5152 if (diag.Triggered) 5153 continue; 5154 5155 switch (diag.Kind) { 5156 case DelayedDiagnostic::Deprecation: 5157 // Don't bother giving deprecation diagnostics if the decl is invalid. 5158 if (!decl->isInvalidDecl()) 5159 HandleDelayedDeprecationCheck(diag, decl); 5160 break; 5161 5162 case DelayedDiagnostic::Access: 5163 HandleDelayedAccessCheck(diag, decl); 5164 break; 5165 5166 case DelayedDiagnostic::ForbiddenType: 5167 handleDelayedForbiddenType(*this, diag, decl); 5168 break; 5169 } 5170 } 5171 } while ((pool = pool->getParent())); 5172} 5173 5174/// Given a set of delayed diagnostics, re-emit them as if they had 5175/// been delayed in the current context instead of in the given pool. 5176/// Essentially, this just moves them to the current pool. 5177void Sema::redelayDiagnostics(DelayedDiagnosticPool &pool) { 5178 DelayedDiagnosticPool *curPool = DelayedDiagnostics.getCurrentPool(); 5179 assert(curPool && "re-emitting in undelayed context not supported"); 5180 curPool->steal(pool); 5181} 5182 5183static bool isDeclDeprecated(Decl *D) { 5184 do { 5185 if (D->isDeprecated()) 5186 return true; 5187 // A category implicitly has the availability of the interface. 5188 if (const ObjCCategoryDecl *CatD = dyn_cast<ObjCCategoryDecl>(D)) 5189 return CatD->getClassInterface()->isDeprecated(); 5190 } while ((D = cast_or_null<Decl>(D->getDeclContext()))); 5191 return false; 5192} 5193 5194static void 5195DoEmitDeprecationWarning(Sema &S, const NamedDecl *D, StringRef Message, 5196 SourceLocation Loc, 5197 const ObjCInterfaceDecl *UnknownObjCClass, 5198 const ObjCPropertyDecl *ObjCPropery) { 5199 DeclarationName Name = D->getDeclName(); 5200 if (!Message.empty()) { 5201 S.Diag(Loc, diag::warn_deprecated_message) << Name << Message; 5202 S.Diag(D->getLocation(), 5203 isa<ObjCMethodDecl>(D) ? diag::note_method_declared_at 5204 : diag::note_previous_decl) << Name; 5205 if (ObjCPropery) 5206 S.Diag(ObjCPropery->getLocation(), diag::note_property_attribute) 5207 << ObjCPropery->getDeclName() << 0; 5208 } else if (!UnknownObjCClass) { 5209 S.Diag(Loc, diag::warn_deprecated) << D->getDeclName(); 5210 S.Diag(D->getLocation(), 5211 isa<ObjCMethodDecl>(D) ? diag::note_method_declared_at 5212 : diag::note_previous_decl) << Name; 5213 if (ObjCPropery) 5214 S.Diag(ObjCPropery->getLocation(), diag::note_property_attribute) 5215 << ObjCPropery->getDeclName() << 0; 5216 } else { 5217 S.Diag(Loc, diag::warn_deprecated_fwdclass_message) << Name; 5218 S.Diag(UnknownObjCClass->getLocation(), diag::note_forward_class); 5219 } 5220} 5221 5222void Sema::HandleDelayedDeprecationCheck(DelayedDiagnostic &DD, 5223 Decl *Ctx) { 5224 if (isDeclDeprecated(Ctx)) 5225 return; 5226 5227 DD.Triggered = true; 5228 DoEmitDeprecationWarning(*this, DD.getDeprecationDecl(), 5229 DD.getDeprecationMessage(), DD.Loc, 5230 DD.getUnknownObjCClass(), 5231 DD.getObjCProperty()); 5232} 5233 5234void Sema::EmitDeprecationWarning(NamedDecl *D, StringRef Message, 5235 SourceLocation Loc, 5236 const ObjCInterfaceDecl *UnknownObjCClass, 5237 const ObjCPropertyDecl *ObjCProperty) { 5238 // Delay if we're currently parsing a declaration. 5239 if (DelayedDiagnostics.shouldDelayDiagnostics()) { 5240 DelayedDiagnostics.add(DelayedDiagnostic::makeDeprecation(Loc, D, 5241 UnknownObjCClass, 5242 ObjCProperty, 5243 Message)); 5244 return; 5245 } 5246 5247 // Otherwise, don't warn if our current context is deprecated. 5248 if (isDeclDeprecated(cast<Decl>(getCurLexicalContext()))) 5249 return; 5250 DoEmitDeprecationWarning(*this, D, Message, Loc, UnknownObjCClass, ObjCProperty); 5251} 5252