SemaDeclAttr.cpp revision 420efd83934ee78f04d73880e2ed1b7fdef3328c
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/DeclTemplate.h" 20#include "clang/AST/DeclObjC.h" 21#include "clang/AST/Expr.h" 22#include "clang/Basic/SourceManager.h" 23#include "clang/Basic/TargetInfo.h" 24#include "clang/Sema/DeclSpec.h" 25#include "clang/Sema/DelayedDiagnostic.h" 26#include "clang/Sema/Lookup.h" 27#include "llvm/ADT/StringExtras.h" 28using namespace clang; 29using namespace sema; 30 31/// These constants match the enumerated choices of 32/// warn_attribute_wrong_decl_type and err_attribute_wrong_decl_type. 33enum AttributeDeclKind { 34 ExpectedFunction, 35 ExpectedUnion, 36 ExpectedVariableOrFunction, 37 ExpectedFunctionOrMethod, 38 ExpectedParameter, 39 ExpectedFunctionMethodOrBlock, 40 ExpectedFunctionMethodOrParameter, 41 ExpectedClass, 42 ExpectedVariable, 43 ExpectedMethod, 44 ExpectedVariableFunctionOrLabel, 45 ExpectedFieldOrGlobalVar, 46 ExpectedStruct 47}; 48 49//===----------------------------------------------------------------------===// 50// Helper functions 51//===----------------------------------------------------------------------===// 52 53static const FunctionType *getFunctionType(const Decl *D, 54 bool blocksToo = true) { 55 QualType Ty; 56 if (const ValueDecl *decl = dyn_cast<ValueDecl>(D)) 57 Ty = decl->getType(); 58 else if (const FieldDecl *decl = dyn_cast<FieldDecl>(D)) 59 Ty = decl->getType(); 60 else if (const TypedefNameDecl* decl = dyn_cast<TypedefNameDecl>(D)) 61 Ty = decl->getUnderlyingType(); 62 else 63 return 0; 64 65 if (Ty->isFunctionPointerType()) 66 Ty = Ty->getAs<PointerType>()->getPointeeType(); 67 else if (blocksToo && Ty->isBlockPointerType()) 68 Ty = Ty->getAs<BlockPointerType>()->getPointeeType(); 69 70 return Ty->getAs<FunctionType>(); 71} 72 73// FIXME: We should provide an abstraction around a method or function 74// to provide the following bits of information. 75 76/// isFunction - Return true if the given decl has function 77/// type (function or function-typed variable). 78static bool isFunction(const Decl *D) { 79 return getFunctionType(D, false) != NULL; 80} 81 82/// isFunctionOrMethod - Return true if the given decl has function 83/// type (function or function-typed variable) or an Objective-C 84/// method. 85static bool isFunctionOrMethod(const Decl *D) { 86 return isFunction(D)|| isa<ObjCMethodDecl>(D); 87} 88 89/// isFunctionOrMethodOrBlock - Return true if the given decl has function 90/// type (function or function-typed variable) or an Objective-C 91/// method or a block. 92static bool isFunctionOrMethodOrBlock(const Decl *D) { 93 if (isFunctionOrMethod(D)) 94 return true; 95 // check for block is more involved. 96 if (const VarDecl *V = dyn_cast<VarDecl>(D)) { 97 QualType Ty = V->getType(); 98 return Ty->isBlockPointerType(); 99 } 100 return isa<BlockDecl>(D); 101} 102 103/// Return true if the given decl has a declarator that should have 104/// been processed by Sema::GetTypeForDeclarator. 105static bool hasDeclarator(const Decl *D) { 106 // In some sense, TypedefDecl really *ought* to be a DeclaratorDecl. 107 return isa<DeclaratorDecl>(D) || isa<BlockDecl>(D) || isa<TypedefNameDecl>(D) || 108 isa<ObjCPropertyDecl>(D); 109} 110 111/// hasFunctionProto - Return true if the given decl has a argument 112/// information. This decl should have already passed 113/// isFunctionOrMethod or isFunctionOrMethodOrBlock. 114static bool hasFunctionProto(const Decl *D) { 115 if (const FunctionType *FnTy = getFunctionType(D)) 116 return isa<FunctionProtoType>(FnTy); 117 else { 118 assert(isa<ObjCMethodDecl>(D) || isa<BlockDecl>(D)); 119 return true; 120 } 121} 122 123/// getFunctionOrMethodNumArgs - Return number of function or method 124/// arguments. It is an error to call this on a K&R function (use 125/// hasFunctionProto first). 126static unsigned getFunctionOrMethodNumArgs(const Decl *D) { 127 if (const FunctionType *FnTy = getFunctionType(D)) 128 return cast<FunctionProtoType>(FnTy)->getNumArgs(); 129 if (const BlockDecl *BD = dyn_cast<BlockDecl>(D)) 130 return BD->getNumParams(); 131 return cast<ObjCMethodDecl>(D)->param_size(); 132} 133 134static QualType getFunctionOrMethodArgType(const Decl *D, unsigned Idx) { 135 if (const FunctionType *FnTy = getFunctionType(D)) 136 return cast<FunctionProtoType>(FnTy)->getArgType(Idx); 137 if (const BlockDecl *BD = dyn_cast<BlockDecl>(D)) 138 return BD->getParamDecl(Idx)->getType(); 139 140 return cast<ObjCMethodDecl>(D)->param_begin()[Idx]->getType(); 141} 142 143static QualType getFunctionOrMethodResultType(const Decl *D) { 144 if (const FunctionType *FnTy = getFunctionType(D)) 145 return cast<FunctionProtoType>(FnTy)->getResultType(); 146 return cast<ObjCMethodDecl>(D)->getResultType(); 147} 148 149static bool isFunctionOrMethodVariadic(const Decl *D) { 150 if (const FunctionType *FnTy = getFunctionType(D)) { 151 const FunctionProtoType *proto = cast<FunctionProtoType>(FnTy); 152 return proto->isVariadic(); 153 } else if (const BlockDecl *BD = dyn_cast<BlockDecl>(D)) 154 return BD->isVariadic(); 155 else { 156 return cast<ObjCMethodDecl>(D)->isVariadic(); 157 } 158} 159 160static bool isInstanceMethod(const Decl *D) { 161 if (const CXXMethodDecl *MethodDecl = dyn_cast<CXXMethodDecl>(D)) 162 return MethodDecl->isInstance(); 163 return false; 164} 165 166static inline bool isNSStringType(QualType T, ASTContext &Ctx) { 167 const ObjCObjectPointerType *PT = T->getAs<ObjCObjectPointerType>(); 168 if (!PT) 169 return false; 170 171 ObjCInterfaceDecl *Cls = PT->getObjectType()->getInterface(); 172 if (!Cls) 173 return false; 174 175 IdentifierInfo* ClsName = Cls->getIdentifier(); 176 177 // FIXME: Should we walk the chain of classes? 178 return ClsName == &Ctx.Idents.get("NSString") || 179 ClsName == &Ctx.Idents.get("NSMutableString"); 180} 181 182static inline bool isCFStringType(QualType T, ASTContext &Ctx) { 183 const PointerType *PT = T->getAs<PointerType>(); 184 if (!PT) 185 return false; 186 187 const RecordType *RT = PT->getPointeeType()->getAs<RecordType>(); 188 if (!RT) 189 return false; 190 191 const RecordDecl *RD = RT->getDecl(); 192 if (RD->getTagKind() != TTK_Struct) 193 return false; 194 195 return RD->getIdentifier() == &Ctx.Idents.get("__CFString"); 196} 197 198/// \brief Check if the attribute has exactly as many args as Num. May 199/// output an error. 200static bool checkAttributeNumArgs(Sema &S, const AttributeList &Attr, 201 unsigned int Num) { 202 if (Attr.getNumArgs() != Num) { 203 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << Num; 204 return false; 205 } 206 207 return true; 208} 209 210 211/// \brief Check if the attribute has at least as many args as Num. May 212/// output an error. 213static bool checkAttributeAtLeastNumArgs(Sema &S, const AttributeList &Attr, 214 unsigned int Num) { 215 if (Attr.getNumArgs() < Num) { 216 S.Diag(Attr.getLoc(), diag::err_attribute_too_few_arguments) << Num; 217 return false; 218 } 219 220 return true; 221} 222 223/// 224/// \brief Check if passed in Decl is a field or potentially shared global var 225/// \return true if the Decl is a field or potentially shared global variable 226/// 227static bool mayBeSharedVariable(const Decl *D) { 228 if (isa<FieldDecl>(D)) 229 return true; 230 if (const VarDecl *vd = dyn_cast<VarDecl>(D)) 231 return (vd->hasGlobalStorage() && !(vd->isThreadSpecified())); 232 233 return false; 234} 235 236/// \brief Check if the passed-in expression is of type int or bool. 237static bool isIntOrBool(Expr *Exp) { 238 QualType QT = Exp->getType(); 239 return QT->isBooleanType() || QT->isIntegerType(); 240} 241 242 243// Check to see if the type is a smart pointer of some kind. We assume 244// it's a smart pointer if it defines both operator-> and operator*. 245static bool threadSafetyCheckIsSmartPointer(Sema &S, const RecordType* RT) { 246 DeclContextLookupConstResult Res1 = RT->getDecl()->lookup( 247 S.Context.DeclarationNames.getCXXOperatorName(OO_Star)); 248 if (Res1.first == Res1.second) 249 return false; 250 251 DeclContextLookupConstResult Res2 = RT->getDecl()->lookup( 252 S.Context.DeclarationNames.getCXXOperatorName(OO_Arrow)); 253 if (Res2.first == Res2.second) 254 return false; 255 256 return true; 257} 258 259/// \brief Check if passed in Decl is a pointer type. 260/// Note that this function may produce an error message. 261/// \return true if the Decl is a pointer type; false otherwise 262static bool threadSafetyCheckIsPointer(Sema &S, const Decl *D, 263 const AttributeList &Attr) { 264 if (const ValueDecl *vd = dyn_cast<ValueDecl>(D)) { 265 QualType QT = vd->getType(); 266 if (QT->isAnyPointerType()) 267 return true; 268 269 if (const RecordType *RT = QT->getAs<RecordType>()) { 270 // If it's an incomplete type, it could be a smart pointer; skip it. 271 // (We don't want to force template instantiation if we can avoid it, 272 // since that would alter the order in which templates are instantiated.) 273 if (RT->isIncompleteType()) 274 return true; 275 276 if (threadSafetyCheckIsSmartPointer(S, RT)) 277 return true; 278 } 279 280 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_decl_not_pointer) 281 << Attr.getName()->getName() << QT; 282 } else { 283 S.Diag(Attr.getLoc(), diag::err_attribute_can_be_applied_only_to_value_decl) 284 << Attr.getName(); 285 } 286 return false; 287} 288 289/// \brief Checks that the passed in QualType either is of RecordType or points 290/// to RecordType. Returns the relevant RecordType, null if it does not exit. 291static const RecordType *getRecordType(QualType QT) { 292 if (const RecordType *RT = QT->getAs<RecordType>()) 293 return RT; 294 295 // Now check if we point to record type. 296 if (const PointerType *PT = QT->getAs<PointerType>()) 297 return PT->getPointeeType()->getAs<RecordType>(); 298 299 return 0; 300} 301 302 303static bool checkBaseClassIsLockableCallback(const CXXBaseSpecifier *Specifier, 304 CXXBasePath &Path, void *Unused) { 305 const RecordType *RT = Specifier->getType()->getAs<RecordType>(); 306 if (RT->getDecl()->getAttr<LockableAttr>()) 307 return true; 308 return false; 309} 310 311 312/// \brief Thread Safety Analysis: Checks that the passed in RecordType 313/// resolves to a lockable object. 314static void checkForLockableRecord(Sema &S, Decl *D, const AttributeList &Attr, 315 QualType Ty) { 316 const RecordType *RT = getRecordType(Ty); 317 318 // Warn if could not get record type for this argument. 319 if (!RT) { 320 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_argument_not_class) 321 << Attr.getName() << Ty.getAsString(); 322 return; 323 } 324 325 // Don't check for lockable if the class hasn't been defined yet. 326 if (RT->isIncompleteType()) 327 return; 328 329 // Allow smart pointers to be used as lockable objects. 330 // FIXME -- Check the type that the smart pointer points to. 331 if (threadSafetyCheckIsSmartPointer(S, RT)) 332 return; 333 334 // Check if the type is lockable. 335 RecordDecl *RD = RT->getDecl(); 336 if (RD->getAttr<LockableAttr>()) 337 return; 338 339 // Else check if any base classes are lockable. 340 if (CXXRecordDecl *CRD = dyn_cast<CXXRecordDecl>(RD)) { 341 CXXBasePaths BPaths(false, false); 342 if (CRD->lookupInBases(checkBaseClassIsLockableCallback, 0, BPaths)) 343 return; 344 } 345 346 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_argument_not_lockable) 347 << Attr.getName() << Ty.getAsString(); 348} 349 350/// \brief Thread Safety Analysis: Checks that all attribute arguments, starting 351/// from Sidx, resolve to a lockable object. 352/// \param Sidx The attribute argument index to start checking with. 353/// \param ParamIdxOk Whether an argument can be indexing into a function 354/// parameter list. 355static void checkAttrArgsAreLockableObjs(Sema &S, Decl *D, 356 const AttributeList &Attr, 357 SmallVectorImpl<Expr*> &Args, 358 int Sidx = 0, 359 bool ParamIdxOk = false) { 360 for(unsigned Idx = Sidx; Idx < Attr.getNumArgs(); ++Idx) { 361 Expr *ArgExp = Attr.getArg(Idx); 362 363 if (ArgExp->isTypeDependent()) { 364 // FIXME -- need to check this again on template instantiation 365 Args.push_back(ArgExp); 366 continue; 367 } 368 369 if (StringLiteral *StrLit = dyn_cast<StringLiteral>(ArgExp)) { 370 // Ignore empty strings without warnings 371 if (StrLit->getLength() == 0) 372 continue; 373 374 // We allow constant strings to be used as a placeholder for expressions 375 // that are not valid C++ syntax, but warn that they are ignored. 376 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_ignored) << 377 Attr.getName(); 378 continue; 379 } 380 381 QualType ArgTy = ArgExp->getType(); 382 383 // A pointer to member expression of the form &MyClass::mu is treated 384 // specially -- we need to look at the type of the member. 385 if (UnaryOperator *UOp = dyn_cast<UnaryOperator>(ArgExp)) 386 if (UOp->getOpcode() == UO_AddrOf) 387 if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(UOp->getSubExpr())) 388 if (DRE->getDecl()->isCXXInstanceMember()) 389 ArgTy = DRE->getDecl()->getType(); 390 391 // First see if we can just cast to record type, or point to record type. 392 const RecordType *RT = getRecordType(ArgTy); 393 394 // Now check if we index into a record type function param. 395 if(!RT && ParamIdxOk) { 396 FunctionDecl *FD = dyn_cast<FunctionDecl>(D); 397 IntegerLiteral *IL = dyn_cast<IntegerLiteral>(ArgExp); 398 if(FD && IL) { 399 unsigned int NumParams = FD->getNumParams(); 400 llvm::APInt ArgValue = IL->getValue(); 401 uint64_t ParamIdxFromOne = ArgValue.getZExtValue(); 402 uint64_t ParamIdxFromZero = ParamIdxFromOne - 1; 403 if(!ArgValue.isStrictlyPositive() || ParamIdxFromOne > NumParams) { 404 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_range) 405 << Attr.getName() << Idx + 1 << NumParams; 406 continue; 407 } 408 ArgTy = FD->getParamDecl(ParamIdxFromZero)->getType(); 409 } 410 } 411 412 checkForLockableRecord(S, D, Attr, ArgTy); 413 414 Args.push_back(ArgExp); 415 } 416} 417 418//===----------------------------------------------------------------------===// 419// Attribute Implementations 420//===----------------------------------------------------------------------===// 421 422// FIXME: All this manual attribute parsing code is gross. At the 423// least add some helper functions to check most argument patterns (# 424// and types of args). 425 426static void handleGuardedVarAttr(Sema &S, Decl *D, const AttributeList &Attr, 427 bool pointer = false) { 428 assert(!Attr.isInvalid()); 429 430 if (!checkAttributeNumArgs(S, Attr, 0)) 431 return; 432 433 // D must be either a member field or global (potentially shared) variable. 434 if (!mayBeSharedVariable(D)) { 435 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 436 << Attr.getName() << ExpectedFieldOrGlobalVar; 437 return; 438 } 439 440 if (pointer && !threadSafetyCheckIsPointer(S, D, Attr)) 441 return; 442 443 if (pointer) 444 D->addAttr(::new (S.Context) PtGuardedVarAttr(Attr.getRange(), S.Context)); 445 else 446 D->addAttr(::new (S.Context) GuardedVarAttr(Attr.getRange(), S.Context)); 447} 448 449static void handleGuardedByAttr(Sema &S, Decl *D, const AttributeList &Attr, 450 bool pointer = false) { 451 assert(!Attr.isInvalid()); 452 453 if (!checkAttributeNumArgs(S, Attr, 1)) 454 return; 455 456 // D must be either a member field or global (potentially shared) variable. 457 if (!mayBeSharedVariable(D)) { 458 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 459 << Attr.getName() << ExpectedFieldOrGlobalVar; 460 return; 461 } 462 463 if (pointer && !threadSafetyCheckIsPointer(S, D, Attr)) 464 return; 465 466 SmallVector<Expr*, 1> Args; 467 // check that all arguments are lockable objects 468 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 469 unsigned Size = Args.size(); 470 if (Size != 1) 471 return; 472 Expr *Arg = Args[0]; 473 474 if (pointer) 475 D->addAttr(::new (S.Context) PtGuardedByAttr(Attr.getRange(), 476 S.Context, Arg)); 477 else 478 D->addAttr(::new (S.Context) GuardedByAttr(Attr.getRange(), S.Context, Arg)); 479} 480 481 482static void handleLockableAttr(Sema &S, Decl *D, const AttributeList &Attr, 483 bool scoped = false) { 484 assert(!Attr.isInvalid()); 485 486 if (!checkAttributeNumArgs(S, Attr, 0)) 487 return; 488 489 // FIXME: Lockable structs for C code. 490 if (!isa<CXXRecordDecl>(D)) { 491 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 492 << Attr.getName() << ExpectedClass; 493 return; 494 } 495 496 if (scoped) 497 D->addAttr(::new (S.Context) ScopedLockableAttr(Attr.getRange(), S.Context)); 498 else 499 D->addAttr(::new (S.Context) LockableAttr(Attr.getRange(), S.Context)); 500} 501 502static void handleNoThreadSafetyAttr(Sema &S, Decl *D, 503 const AttributeList &Attr) { 504 assert(!Attr.isInvalid()); 505 506 if (!checkAttributeNumArgs(S, Attr, 0)) 507 return; 508 509 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 510 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 511 << Attr.getName() << ExpectedFunctionOrMethod; 512 return; 513 } 514 515 D->addAttr(::new (S.Context) NoThreadSafetyAnalysisAttr(Attr.getRange(), 516 S.Context)); 517} 518 519static void handleNoAddressSafetyAttr(Sema &S, Decl *D, 520 const AttributeList &Attr) { 521 assert(!Attr.isInvalid()); 522 523 if (!checkAttributeNumArgs(S, Attr, 0)) 524 return; 525 526 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 527 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 528 << Attr.getName() << ExpectedFunctionOrMethod; 529 return; 530 } 531 532 D->addAttr(::new (S.Context) NoAddressSafetyAnalysisAttr(Attr.getRange(), 533 S.Context)); 534} 535 536static void handleAcquireOrderAttr(Sema &S, Decl *D, const AttributeList &Attr, 537 bool before) { 538 assert(!Attr.isInvalid()); 539 540 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 541 return; 542 543 // D must be either a member field or global (potentially shared) variable. 544 ValueDecl *VD = dyn_cast<ValueDecl>(D); 545 if (!VD || !mayBeSharedVariable(D)) { 546 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 547 << Attr.getName() << ExpectedFieldOrGlobalVar; 548 return; 549 } 550 551 // Check that this attribute only applies to lockable types. 552 QualType QT = VD->getType(); 553 if (!QT->isDependentType()) { 554 const RecordType *RT = getRecordType(QT); 555 if (!RT || !RT->getDecl()->getAttr<LockableAttr>()) { 556 S.Diag(Attr.getLoc(), diag::warn_thread_attribute_decl_not_lockable) 557 << Attr.getName(); 558 return; 559 } 560 } 561 562 SmallVector<Expr*, 1> Args; 563 // Check that all arguments are lockable objects. 564 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 565 unsigned Size = Args.size(); 566 if (Size == 0) 567 return; 568 Expr **StartArg = &Args[0]; 569 570 if (before) 571 D->addAttr(::new (S.Context) AcquiredBeforeAttr(Attr.getRange(), S.Context, 572 StartArg, Size)); 573 else 574 D->addAttr(::new (S.Context) AcquiredAfterAttr(Attr.getRange(), S.Context, 575 StartArg, Size)); 576} 577 578static void handleLockFunAttr(Sema &S, Decl *D, const AttributeList &Attr, 579 bool exclusive = false) { 580 assert(!Attr.isInvalid()); 581 582 // zero or more arguments ok 583 584 // check that the attribute is applied to a function 585 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 586 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 587 << Attr.getName() << ExpectedFunctionOrMethod; 588 return; 589 } 590 591 // check that all arguments are lockable objects 592 SmallVector<Expr*, 1> Args; 593 checkAttrArgsAreLockableObjs(S, D, Attr, Args, 0, /*ParamIdxOk=*/true); 594 unsigned Size = Args.size(); 595 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 596 597 if (exclusive) 598 D->addAttr(::new (S.Context) ExclusiveLockFunctionAttr(Attr.getRange(), 599 S.Context, StartArg, 600 Size)); 601 else 602 D->addAttr(::new (S.Context) SharedLockFunctionAttr(Attr.getRange(), 603 S.Context, StartArg, 604 Size)); 605} 606 607static void handleTrylockFunAttr(Sema &S, Decl *D, const AttributeList &Attr, 608 bool exclusive = false) { 609 assert(!Attr.isInvalid()); 610 611 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 612 return; 613 614 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 615 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 616 << Attr.getName() << ExpectedFunctionOrMethod; 617 return; 618 } 619 620 if (!isIntOrBool(Attr.getArg(0))) { 621 S.Diag(Attr.getLoc(), diag::err_attribute_first_argument_not_int_or_bool) 622 << Attr.getName(); 623 return; 624 } 625 626 SmallVector<Expr*, 2> Args; 627 // check that all arguments are lockable objects 628 checkAttrArgsAreLockableObjs(S, D, Attr, Args, 1); 629 unsigned Size = Args.size(); 630 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 631 632 if (exclusive) 633 D->addAttr(::new (S.Context) ExclusiveTrylockFunctionAttr(Attr.getRange(), 634 S.Context, 635 Attr.getArg(0), 636 StartArg, Size)); 637 else 638 D->addAttr(::new (S.Context) SharedTrylockFunctionAttr(Attr.getRange(), 639 S.Context, 640 Attr.getArg(0), 641 StartArg, Size)); 642} 643 644static void handleLocksRequiredAttr(Sema &S, Decl *D, const AttributeList &Attr, 645 bool exclusive = false) { 646 assert(!Attr.isInvalid()); 647 648 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 649 return; 650 651 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 652 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 653 << Attr.getName() << ExpectedFunctionOrMethod; 654 return; 655 } 656 657 // check that all arguments are lockable objects 658 SmallVector<Expr*, 1> Args; 659 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 660 unsigned Size = Args.size(); 661 if (Size == 0) 662 return; 663 Expr **StartArg = &Args[0]; 664 665 if (exclusive) 666 D->addAttr(::new (S.Context) ExclusiveLocksRequiredAttr(Attr.getRange(), 667 S.Context, StartArg, 668 Size)); 669 else 670 D->addAttr(::new (S.Context) SharedLocksRequiredAttr(Attr.getRange(), 671 S.Context, StartArg, 672 Size)); 673} 674 675static void handleUnlockFunAttr(Sema &S, Decl *D, 676 const AttributeList &Attr) { 677 assert(!Attr.isInvalid()); 678 679 // zero or more arguments ok 680 681 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 682 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 683 << Attr.getName() << ExpectedFunctionOrMethod; 684 return; 685 } 686 687 // check that all arguments are lockable objects 688 SmallVector<Expr*, 1> Args; 689 checkAttrArgsAreLockableObjs(S, D, Attr, Args, 0, /*ParamIdxOk=*/true); 690 unsigned Size = Args.size(); 691 Expr **StartArg = Size == 0 ? 0 : &Args[0]; 692 693 D->addAttr(::new (S.Context) UnlockFunctionAttr(Attr.getRange(), S.Context, 694 StartArg, Size)); 695} 696 697static void handleLockReturnedAttr(Sema &S, Decl *D, 698 const AttributeList &Attr) { 699 assert(!Attr.isInvalid()); 700 701 if (!checkAttributeNumArgs(S, Attr, 1)) 702 return; 703 Expr *Arg = Attr.getArg(0); 704 705 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 706 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 707 << Attr.getName() << ExpectedFunctionOrMethod; 708 return; 709 } 710 711 if (Arg->isTypeDependent()) 712 return; 713 714 // check that the argument is lockable object 715 SmallVector<Expr*, 1> Args; 716 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 717 unsigned Size = Args.size(); 718 if (Size == 0) 719 return; 720 721 D->addAttr(::new (S.Context) LockReturnedAttr(Attr.getRange(), S.Context, 722 Args[0])); 723} 724 725static void handleLocksExcludedAttr(Sema &S, Decl *D, 726 const AttributeList &Attr) { 727 assert(!Attr.isInvalid()); 728 729 if (!checkAttributeAtLeastNumArgs(S, Attr, 1)) 730 return; 731 732 if (!isa<FunctionDecl>(D) && !isa<FunctionTemplateDecl>(D)) { 733 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 734 << Attr.getName() << ExpectedFunctionOrMethod; 735 return; 736 } 737 738 // check that all arguments are lockable objects 739 SmallVector<Expr*, 1> Args; 740 checkAttrArgsAreLockableObjs(S, D, Attr, Args); 741 unsigned Size = Args.size(); 742 if (Size == 0) 743 return; 744 Expr **StartArg = &Args[0]; 745 746 D->addAttr(::new (S.Context) LocksExcludedAttr(Attr.getRange(), S.Context, 747 StartArg, Size)); 748} 749 750 751static void handleExtVectorTypeAttr(Sema &S, Scope *scope, Decl *D, 752 const AttributeList &Attr) { 753 TypedefNameDecl *tDecl = dyn_cast<TypedefNameDecl>(D); 754 if (tDecl == 0) { 755 S.Diag(Attr.getLoc(), diag::err_typecheck_ext_vector_not_typedef); 756 return; 757 } 758 759 QualType curType = tDecl->getUnderlyingType(); 760 761 Expr *sizeExpr; 762 763 // Special case where the argument is a template id. 764 if (Attr.getParameterName()) { 765 CXXScopeSpec SS; 766 SourceLocation TemplateKWLoc; 767 UnqualifiedId id; 768 id.setIdentifier(Attr.getParameterName(), Attr.getLoc()); 769 770 ExprResult Size = S.ActOnIdExpression(scope, SS, TemplateKWLoc, id, 771 false, false); 772 if (Size.isInvalid()) 773 return; 774 775 sizeExpr = Size.get(); 776 } else { 777 // check the attribute arguments. 778 if (!checkAttributeNumArgs(S, Attr, 1)) 779 return; 780 781 sizeExpr = Attr.getArg(0); 782 } 783 784 // Instantiate/Install the vector type, and let Sema build the type for us. 785 // This will run the reguired checks. 786 QualType T = S.BuildExtVectorType(curType, sizeExpr, Attr.getLoc()); 787 if (!T.isNull()) { 788 // FIXME: preserve the old source info. 789 tDecl->setTypeSourceInfo(S.Context.getTrivialTypeSourceInfo(T)); 790 791 // Remember this typedef decl, we will need it later for diagnostics. 792 S.ExtVectorDecls.push_back(tDecl); 793 } 794} 795 796static void handlePackedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 797 // check the attribute arguments. 798 if (!checkAttributeNumArgs(S, Attr, 0)) 799 return; 800 801 if (TagDecl *TD = dyn_cast<TagDecl>(D)) 802 TD->addAttr(::new (S.Context) PackedAttr(Attr.getRange(), S.Context)); 803 else if (FieldDecl *FD = dyn_cast<FieldDecl>(D)) { 804 // If the alignment is less than or equal to 8 bits, the packed attribute 805 // has no effect. 806 if (!FD->getType()->isIncompleteType() && 807 S.Context.getTypeAlign(FD->getType()) <= 8) 808 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored_for_field_of_type) 809 << Attr.getName() << FD->getType(); 810 else 811 FD->addAttr(::new (S.Context) PackedAttr(Attr.getRange(), S.Context)); 812 } else 813 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 814} 815 816static void handleMsStructAttr(Sema &S, Decl *D, const AttributeList &Attr) { 817 if (TagDecl *TD = dyn_cast<TagDecl>(D)) 818 TD->addAttr(::new (S.Context) MsStructAttr(Attr.getRange(), S.Context)); 819 else 820 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 821} 822 823static void handleIBAction(Sema &S, Decl *D, const AttributeList &Attr) { 824 // check the attribute arguments. 825 if (!checkAttributeNumArgs(S, Attr, 0)) 826 return; 827 828 // The IBAction attributes only apply to instance methods. 829 if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 830 if (MD->isInstanceMethod()) { 831 D->addAttr(::new (S.Context) IBActionAttr(Attr.getRange(), S.Context)); 832 return; 833 } 834 835 S.Diag(Attr.getLoc(), diag::warn_attribute_ibaction) << Attr.getName(); 836} 837 838static bool checkIBOutletCommon(Sema &S, Decl *D, const AttributeList &Attr) { 839 // The IBOutlet/IBOutletCollection attributes only apply to instance 840 // variables or properties of Objective-C classes. The outlet must also 841 // have an object reference type. 842 if (const ObjCIvarDecl *VD = dyn_cast<ObjCIvarDecl>(D)) { 843 if (!VD->getType()->getAs<ObjCObjectPointerType>()) { 844 S.Diag(Attr.getLoc(), diag::warn_iboutlet_object_type) 845 << Attr.getName() << VD->getType() << 0; 846 return false; 847 } 848 } 849 else if (const ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(D)) { 850 if (!PD->getType()->getAs<ObjCObjectPointerType>()) { 851 S.Diag(Attr.getLoc(), diag::warn_iboutlet_object_type) 852 << Attr.getName() << PD->getType() << 1; 853 return false; 854 } 855 } 856 else { 857 S.Diag(Attr.getLoc(), diag::warn_attribute_iboutlet) << Attr.getName(); 858 return false; 859 } 860 861 return true; 862} 863 864static void handleIBOutlet(Sema &S, Decl *D, const AttributeList &Attr) { 865 // check the attribute arguments. 866 if (!checkAttributeNumArgs(S, Attr, 0)) 867 return; 868 869 if (!checkIBOutletCommon(S, D, Attr)) 870 return; 871 872 D->addAttr(::new (S.Context) IBOutletAttr(Attr.getRange(), S.Context)); 873} 874 875static void handleIBOutletCollection(Sema &S, Decl *D, 876 const AttributeList &Attr) { 877 878 // The iboutletcollection attribute can have zero or one arguments. 879 if (Attr.getParameterName() && Attr.getNumArgs() > 0) { 880 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 881 return; 882 } 883 884 if (!checkIBOutletCommon(S, D, Attr)) 885 return; 886 887 IdentifierInfo *II = Attr.getParameterName(); 888 if (!II) 889 II = &S.Context.Idents.get("NSObject"); 890 891 ParsedType TypeRep = S.getTypeName(*II, Attr.getLoc(), 892 S.getScopeForContext(D->getDeclContext()->getParent())); 893 if (!TypeRep) { 894 S.Diag(Attr.getLoc(), diag::err_iboutletcollection_type) << II; 895 return; 896 } 897 QualType QT = TypeRep.get(); 898 // Diagnose use of non-object type in iboutletcollection attribute. 899 // FIXME. Gnu attribute extension ignores use of builtin types in 900 // attributes. So, __attribute__((iboutletcollection(char))) will be 901 // treated as __attribute__((iboutletcollection())). 902 if (!QT->isObjCIdType() && !QT->isObjCObjectType()) { 903 S.Diag(Attr.getLoc(), diag::err_iboutletcollection_type) << II; 904 return; 905 } 906 D->addAttr(::new (S.Context) IBOutletCollectionAttr(Attr.getRange(),S.Context, 907 QT, Attr.getParameterLoc())); 908} 909 910static void possibleTransparentUnionPointerType(QualType &T) { 911 if (const RecordType *UT = T->getAsUnionType()) 912 if (UT && UT->getDecl()->hasAttr<TransparentUnionAttr>()) { 913 RecordDecl *UD = UT->getDecl(); 914 for (RecordDecl::field_iterator it = UD->field_begin(), 915 itend = UD->field_end(); it != itend; ++it) { 916 QualType QT = it->getType(); 917 if (QT->isAnyPointerType() || QT->isBlockPointerType()) { 918 T = QT; 919 return; 920 } 921 } 922 } 923} 924 925static void handleNonNullAttr(Sema &S, Decl *D, const AttributeList &Attr) { 926 // GCC ignores the nonnull attribute on K&R style function prototypes, so we 927 // ignore it as well 928 if (!isFunctionOrMethod(D) || !hasFunctionProto(D)) { 929 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 930 << Attr.getName() << ExpectedFunction; 931 return; 932 } 933 934 // In C++ the implicit 'this' function parameter also counts, and they are 935 // counted from one. 936 bool HasImplicitThisParam = isInstanceMethod(D); 937 unsigned NumArgs = getFunctionOrMethodNumArgs(D) + HasImplicitThisParam; 938 939 // The nonnull attribute only applies to pointers. 940 SmallVector<unsigned, 10> NonNullArgs; 941 942 for (AttributeList::arg_iterator I=Attr.arg_begin(), 943 E=Attr.arg_end(); I!=E; ++I) { 944 945 946 // The argument must be an integer constant expression. 947 Expr *Ex = *I; 948 llvm::APSInt ArgNum(32); 949 if (Ex->isTypeDependent() || Ex->isValueDependent() || 950 !Ex->isIntegerConstantExpr(ArgNum, S.Context)) { 951 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 952 << "nonnull" << Ex->getSourceRange(); 953 return; 954 } 955 956 unsigned x = (unsigned) ArgNum.getZExtValue(); 957 958 if (x < 1 || x > NumArgs) { 959 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 960 << "nonnull" << I.getArgNum() << Ex->getSourceRange(); 961 return; 962 } 963 964 --x; 965 if (HasImplicitThisParam) { 966 if (x == 0) { 967 S.Diag(Attr.getLoc(), 968 diag::err_attribute_invalid_implicit_this_argument) 969 << "nonnull" << Ex->getSourceRange(); 970 return; 971 } 972 --x; 973 } 974 975 // Is the function argument a pointer type? 976 QualType T = getFunctionOrMethodArgType(D, x).getNonReferenceType(); 977 possibleTransparentUnionPointerType(T); 978 979 if (!T->isAnyPointerType() && !T->isBlockPointerType()) { 980 // FIXME: Should also highlight argument in decl. 981 S.Diag(Attr.getLoc(), diag::warn_nonnull_pointers_only) 982 << "nonnull" << Ex->getSourceRange(); 983 continue; 984 } 985 986 NonNullArgs.push_back(x); 987 } 988 989 // If no arguments were specified to __attribute__((nonnull)) then all pointer 990 // arguments have a nonnull attribute. 991 if (NonNullArgs.empty()) { 992 for (unsigned I = 0, E = getFunctionOrMethodNumArgs(D); I != E; ++I) { 993 QualType T = getFunctionOrMethodArgType(D, I).getNonReferenceType(); 994 possibleTransparentUnionPointerType(T); 995 if (T->isAnyPointerType() || T->isBlockPointerType()) 996 NonNullArgs.push_back(I); 997 } 998 999 // No pointer arguments? 1000 if (NonNullArgs.empty()) { 1001 // Warn the trivial case only if attribute is not coming from a 1002 // macro instantiation. 1003 if (Attr.getLoc().isFileID()) 1004 S.Diag(Attr.getLoc(), diag::warn_attribute_nonnull_no_pointers); 1005 return; 1006 } 1007 } 1008 1009 unsigned* start = &NonNullArgs[0]; 1010 unsigned size = NonNullArgs.size(); 1011 llvm::array_pod_sort(start, start + size); 1012 D->addAttr(::new (S.Context) NonNullAttr(Attr.getRange(), S.Context, start, 1013 size)); 1014} 1015 1016static void handleOwnershipAttr(Sema &S, Decl *D, const AttributeList &AL) { 1017 // This attribute must be applied to a function declaration. 1018 // The first argument to the attribute must be a string, 1019 // the name of the resource, for example "malloc". 1020 // The following arguments must be argument indexes, the arguments must be 1021 // of integer type for Returns, otherwise of pointer type. 1022 // The difference between Holds and Takes is that a pointer may still be used 1023 // after being held. free() should be __attribute((ownership_takes)), whereas 1024 // a list append function may well be __attribute((ownership_holds)). 1025 1026 if (!AL.getParameterName()) { 1027 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_not_string) 1028 << AL.getName()->getName() << 1; 1029 return; 1030 } 1031 // Figure out our Kind, and check arguments while we're at it. 1032 OwnershipAttr::OwnershipKind K; 1033 switch (AL.getKind()) { 1034 case AttributeList::AT_ownership_takes: 1035 K = OwnershipAttr::Takes; 1036 if (AL.getNumArgs() < 1) { 1037 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << 2; 1038 return; 1039 } 1040 break; 1041 case AttributeList::AT_ownership_holds: 1042 K = OwnershipAttr::Holds; 1043 if (AL.getNumArgs() < 1) { 1044 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << 2; 1045 return; 1046 } 1047 break; 1048 case AttributeList::AT_ownership_returns: 1049 K = OwnershipAttr::Returns; 1050 if (AL.getNumArgs() > 1) { 1051 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) 1052 << AL.getNumArgs() + 1; 1053 return; 1054 } 1055 break; 1056 default: 1057 // This should never happen given how we are called. 1058 llvm_unreachable("Unknown ownership attribute"); 1059 } 1060 1061 if (!isFunction(D) || !hasFunctionProto(D)) { 1062 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type) 1063 << AL.getName() << ExpectedFunction; 1064 return; 1065 } 1066 1067 // In C++ the implicit 'this' function parameter also counts, and they are 1068 // counted from one. 1069 bool HasImplicitThisParam = isInstanceMethod(D); 1070 unsigned NumArgs = getFunctionOrMethodNumArgs(D) + HasImplicitThisParam; 1071 1072 StringRef Module = AL.getParameterName()->getName(); 1073 1074 // Normalize the argument, __foo__ becomes foo. 1075 if (Module.startswith("__") && Module.endswith("__")) 1076 Module = Module.substr(2, Module.size() - 4); 1077 1078 SmallVector<unsigned, 10> OwnershipArgs; 1079 1080 for (AttributeList::arg_iterator I = AL.arg_begin(), E = AL.arg_end(); I != E; 1081 ++I) { 1082 1083 Expr *IdxExpr = *I; 1084 llvm::APSInt ArgNum(32); 1085 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() 1086 || !IdxExpr->isIntegerConstantExpr(ArgNum, S.Context)) { 1087 S.Diag(AL.getLoc(), diag::err_attribute_argument_not_int) 1088 << AL.getName()->getName() << IdxExpr->getSourceRange(); 1089 continue; 1090 } 1091 1092 unsigned x = (unsigned) ArgNum.getZExtValue(); 1093 1094 if (x > NumArgs || x < 1) { 1095 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds) 1096 << AL.getName()->getName() << x << IdxExpr->getSourceRange(); 1097 continue; 1098 } 1099 --x; 1100 if (HasImplicitThisParam) { 1101 if (x == 0) { 1102 S.Diag(AL.getLoc(), diag::err_attribute_invalid_implicit_this_argument) 1103 << "ownership" << IdxExpr->getSourceRange(); 1104 return; 1105 } 1106 --x; 1107 } 1108 1109 switch (K) { 1110 case OwnershipAttr::Takes: 1111 case OwnershipAttr::Holds: { 1112 // Is the function argument a pointer type? 1113 QualType T = getFunctionOrMethodArgType(D, x); 1114 if (!T->isAnyPointerType() && !T->isBlockPointerType()) { 1115 // FIXME: Should also highlight argument in decl. 1116 S.Diag(AL.getLoc(), diag::err_ownership_type) 1117 << ((K==OwnershipAttr::Takes)?"ownership_takes":"ownership_holds") 1118 << "pointer" 1119 << IdxExpr->getSourceRange(); 1120 continue; 1121 } 1122 break; 1123 } 1124 case OwnershipAttr::Returns: { 1125 if (AL.getNumArgs() > 1) { 1126 // Is the function argument an integer type? 1127 Expr *IdxExpr = AL.getArg(0); 1128 llvm::APSInt ArgNum(32); 1129 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() 1130 || !IdxExpr->isIntegerConstantExpr(ArgNum, S.Context)) { 1131 S.Diag(AL.getLoc(), diag::err_ownership_type) 1132 << "ownership_returns" << "integer" 1133 << IdxExpr->getSourceRange(); 1134 return; 1135 } 1136 } 1137 break; 1138 } 1139 } // switch 1140 1141 // Check we don't have a conflict with another ownership attribute. 1142 for (specific_attr_iterator<OwnershipAttr> 1143 i = D->specific_attr_begin<OwnershipAttr>(), 1144 e = D->specific_attr_end<OwnershipAttr>(); 1145 i != e; ++i) { 1146 if ((*i)->getOwnKind() != K) { 1147 for (const unsigned *I = (*i)->args_begin(), *E = (*i)->args_end(); 1148 I!=E; ++I) { 1149 if (x == *I) { 1150 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible) 1151 << AL.getName()->getName() << "ownership_*"; 1152 } 1153 } 1154 } 1155 } 1156 OwnershipArgs.push_back(x); 1157 } 1158 1159 unsigned* start = OwnershipArgs.data(); 1160 unsigned size = OwnershipArgs.size(); 1161 llvm::array_pod_sort(start, start + size); 1162 1163 if (K != OwnershipAttr::Returns && OwnershipArgs.empty()) { 1164 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << 2; 1165 return; 1166 } 1167 1168 D->addAttr(::new (S.Context) OwnershipAttr(AL.getLoc(), S.Context, K, Module, 1169 start, size)); 1170} 1171 1172/// Whether this declaration has internal linkage for the purposes of 1173/// things that want to complain about things not have internal linkage. 1174static bool hasEffectivelyInternalLinkage(NamedDecl *D) { 1175 switch (D->getLinkage()) { 1176 case NoLinkage: 1177 case InternalLinkage: 1178 return true; 1179 1180 // Template instantiations that go from external to unique-external 1181 // shouldn't get diagnosed. 1182 case UniqueExternalLinkage: 1183 return true; 1184 1185 case ExternalLinkage: 1186 return false; 1187 } 1188 llvm_unreachable("unknown linkage kind!"); 1189} 1190 1191static void handleWeakRefAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1192 // Check the attribute arguments. 1193 if (Attr.getNumArgs() > 1) { 1194 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1195 return; 1196 } 1197 1198 if (!isa<VarDecl>(D) && !isa<FunctionDecl>(D)) { 1199 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1200 << Attr.getName() << ExpectedVariableOrFunction; 1201 return; 1202 } 1203 1204 NamedDecl *nd = cast<NamedDecl>(D); 1205 1206 // gcc rejects 1207 // class c { 1208 // static int a __attribute__((weakref ("v2"))); 1209 // static int b() __attribute__((weakref ("f3"))); 1210 // }; 1211 // and ignores the attributes of 1212 // void f(void) { 1213 // static int a __attribute__((weakref ("v2"))); 1214 // } 1215 // we reject them 1216 const DeclContext *Ctx = D->getDeclContext()->getRedeclContext(); 1217 if (!Ctx->isFileContext()) { 1218 S.Diag(Attr.getLoc(), diag::err_attribute_weakref_not_global_context) << 1219 nd->getNameAsString(); 1220 return; 1221 } 1222 1223 // The GCC manual says 1224 // 1225 // At present, a declaration to which `weakref' is attached can only 1226 // be `static'. 1227 // 1228 // It also says 1229 // 1230 // Without a TARGET, 1231 // given as an argument to `weakref' or to `alias', `weakref' is 1232 // equivalent to `weak'. 1233 // 1234 // gcc 4.4.1 will accept 1235 // int a7 __attribute__((weakref)); 1236 // as 1237 // int a7 __attribute__((weak)); 1238 // This looks like a bug in gcc. We reject that for now. We should revisit 1239 // it if this behaviour is actually used. 1240 1241 if (!hasEffectivelyInternalLinkage(nd)) { 1242 S.Diag(Attr.getLoc(), diag::err_attribute_weakref_not_static); 1243 return; 1244 } 1245 1246 // GCC rejects 1247 // static ((alias ("y"), weakref)). 1248 // Should we? How to check that weakref is before or after alias? 1249 1250 if (Attr.getNumArgs() == 1) { 1251 Expr *Arg = Attr.getArg(0); 1252 Arg = Arg->IgnoreParenCasts(); 1253 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 1254 1255 if (!Str || !Str->isAscii()) { 1256 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1257 << "weakref" << 1; 1258 return; 1259 } 1260 // GCC will accept anything as the argument of weakref. Should we 1261 // check for an existing decl? 1262 D->addAttr(::new (S.Context) AliasAttr(Attr.getRange(), S.Context, 1263 Str->getString())); 1264 } 1265 1266 D->addAttr(::new (S.Context) WeakRefAttr(Attr.getRange(), S.Context)); 1267} 1268 1269static void handleAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1270 // check the attribute arguments. 1271 if (Attr.getNumArgs() != 1) { 1272 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1273 return; 1274 } 1275 1276 Expr *Arg = Attr.getArg(0); 1277 Arg = Arg->IgnoreParenCasts(); 1278 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 1279 1280 if (!Str || !Str->isAscii()) { 1281 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1282 << "alias" << 1; 1283 return; 1284 } 1285 1286 if (S.Context.getTargetInfo().getTriple().isOSDarwin()) { 1287 S.Diag(Attr.getLoc(), diag::err_alias_not_supported_on_darwin); 1288 return; 1289 } 1290 1291 // FIXME: check if target symbol exists in current file 1292 1293 D->addAttr(::new (S.Context) AliasAttr(Attr.getRange(), S.Context, 1294 Str->getString())); 1295} 1296 1297static void handleColdAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1298 // Check the attribute arguments. 1299 if (!checkAttributeNumArgs(S, Attr, 0)) 1300 return; 1301 1302 if (!isa<FunctionDecl>(D)) { 1303 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1304 << Attr.getName() << ExpectedFunction; 1305 return; 1306 } 1307 1308 if (D->hasAttr<HotAttr>()) { 1309 S.Diag(Attr.getLoc(), diag::err_attributes_are_not_compatible) 1310 << Attr.getName() << "hot"; 1311 return; 1312 } 1313 1314 D->addAttr(::new (S.Context) ColdAttr(Attr.getRange(), S.Context)); 1315} 1316 1317static void handleHotAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1318 // Check the attribute arguments. 1319 if (!checkAttributeNumArgs(S, Attr, 0)) 1320 return; 1321 1322 if (!isa<FunctionDecl>(D)) { 1323 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1324 << Attr.getName() << ExpectedFunction; 1325 return; 1326 } 1327 1328 if (D->hasAttr<ColdAttr>()) { 1329 S.Diag(Attr.getLoc(), diag::err_attributes_are_not_compatible) 1330 << Attr.getName() << "cold"; 1331 return; 1332 } 1333 1334 D->addAttr(::new (S.Context) HotAttr(Attr.getRange(), S.Context)); 1335} 1336 1337static void handleNakedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1338 // Check the attribute arguments. 1339 if (!checkAttributeNumArgs(S, Attr, 0)) 1340 return; 1341 1342 if (!isa<FunctionDecl>(D)) { 1343 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1344 << Attr.getName() << ExpectedFunction; 1345 return; 1346 } 1347 1348 D->addAttr(::new (S.Context) NakedAttr(Attr.getRange(), S.Context)); 1349} 1350 1351static void handleAlwaysInlineAttr(Sema &S, Decl *D, 1352 const AttributeList &Attr) { 1353 // Check the attribute arguments. 1354 if (Attr.hasParameterOrArguments()) { 1355 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1356 return; 1357 } 1358 1359 if (!isa<FunctionDecl>(D)) { 1360 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1361 << Attr.getName() << ExpectedFunction; 1362 return; 1363 } 1364 1365 D->addAttr(::new (S.Context) AlwaysInlineAttr(Attr.getRange(), S.Context)); 1366} 1367 1368static void handleMallocAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1369 // Check the attribute arguments. 1370 if (Attr.hasParameterOrArguments()) { 1371 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1372 return; 1373 } 1374 1375 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) { 1376 QualType RetTy = FD->getResultType(); 1377 if (RetTy->isAnyPointerType() || RetTy->isBlockPointerType()) { 1378 D->addAttr(::new (S.Context) MallocAttr(Attr.getRange(), S.Context)); 1379 return; 1380 } 1381 } 1382 1383 S.Diag(Attr.getLoc(), diag::warn_attribute_malloc_pointer_only); 1384} 1385 1386static void handleMayAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1387 // check the attribute arguments. 1388 if (!checkAttributeNumArgs(S, Attr, 0)) 1389 return; 1390 1391 D->addAttr(::new (S.Context) MayAliasAttr(Attr.getRange(), S.Context)); 1392} 1393 1394static void handleNoCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1395 assert(!Attr.isInvalid()); 1396 if (isa<VarDecl>(D)) 1397 D->addAttr(::new (S.Context) NoCommonAttr(Attr.getRange(), S.Context)); 1398 else 1399 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1400 << Attr.getName() << ExpectedVariable; 1401} 1402 1403static void handleCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1404 assert(!Attr.isInvalid()); 1405 if (isa<VarDecl>(D)) 1406 D->addAttr(::new (S.Context) CommonAttr(Attr.getRange(), S.Context)); 1407 else 1408 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1409 << Attr.getName() << ExpectedVariable; 1410} 1411 1412static void handleNoReturnAttr(Sema &S, Decl *D, const AttributeList &attr) { 1413 if (hasDeclarator(D)) return; 1414 1415 if (S.CheckNoReturnAttr(attr)) return; 1416 1417 if (!isa<ObjCMethodDecl>(D)) { 1418 S.Diag(attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1419 << attr.getName() << ExpectedFunctionOrMethod; 1420 return; 1421 } 1422 1423 D->addAttr(::new (S.Context) NoReturnAttr(attr.getRange(), S.Context)); 1424} 1425 1426bool Sema::CheckNoReturnAttr(const AttributeList &attr) { 1427 if (attr.hasParameterOrArguments()) { 1428 Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1429 attr.setInvalid(); 1430 return true; 1431 } 1432 1433 return false; 1434} 1435 1436static void handleAnalyzerNoReturnAttr(Sema &S, Decl *D, 1437 const AttributeList &Attr) { 1438 1439 // The checking path for 'noreturn' and 'analyzer_noreturn' are different 1440 // because 'analyzer_noreturn' does not impact the type. 1441 1442 if(!checkAttributeNumArgs(S, Attr, 0)) 1443 return; 1444 1445 if (!isFunctionOrMethod(D) && !isa<BlockDecl>(D)) { 1446 ValueDecl *VD = dyn_cast<ValueDecl>(D); 1447 if (VD == 0 || (!VD->getType()->isBlockPointerType() 1448 && !VD->getType()->isFunctionPointerType())) { 1449 S.Diag(Attr.getLoc(), 1450 Attr.isCXX0XAttribute() ? diag::err_attribute_wrong_decl_type 1451 : diag::warn_attribute_wrong_decl_type) 1452 << Attr.getName() << ExpectedFunctionMethodOrBlock; 1453 return; 1454 } 1455 } 1456 1457 D->addAttr(::new (S.Context) AnalyzerNoReturnAttr(Attr.getRange(), S.Context)); 1458} 1459 1460// PS3 PPU-specific. 1461static void handleVecReturnAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1462/* 1463 Returning a Vector Class in Registers 1464 1465 According to the PPU ABI specifications, a class with a single member of 1466 vector type is returned in memory when used as the return value of a function. 1467 This results in inefficient code when implementing vector classes. To return 1468 the value in a single vector register, add the vecreturn attribute to the 1469 class definition. This attribute is also applicable to struct types. 1470 1471 Example: 1472 1473 struct Vector 1474 { 1475 __vector float xyzw; 1476 } __attribute__((vecreturn)); 1477 1478 Vector Add(Vector lhs, Vector rhs) 1479 { 1480 Vector result; 1481 result.xyzw = vec_add(lhs.xyzw, rhs.xyzw); 1482 return result; // This will be returned in a register 1483 } 1484*/ 1485 if (!isa<RecordDecl>(D)) { 1486 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1487 << Attr.getName() << ExpectedClass; 1488 return; 1489 } 1490 1491 if (D->getAttr<VecReturnAttr>()) { 1492 S.Diag(Attr.getLoc(), diag::err_repeat_attribute) << "vecreturn"; 1493 return; 1494 } 1495 1496 RecordDecl *record = cast<RecordDecl>(D); 1497 int count = 0; 1498 1499 if (!isa<CXXRecordDecl>(record)) { 1500 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 1501 return; 1502 } 1503 1504 if (!cast<CXXRecordDecl>(record)->isPOD()) { 1505 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_pod_record); 1506 return; 1507 } 1508 1509 for (RecordDecl::field_iterator iter = record->field_begin(); 1510 iter != record->field_end(); iter++) { 1511 if ((count == 1) || !iter->getType()->isVectorType()) { 1512 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 1513 return; 1514 } 1515 count++; 1516 } 1517 1518 D->addAttr(::new (S.Context) VecReturnAttr(Attr.getRange(), S.Context)); 1519} 1520 1521static void handleDependencyAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1522 if (!isFunctionOrMethod(D) && !isa<ParmVarDecl>(D)) { 1523 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1524 << Attr.getName() << ExpectedFunctionMethodOrParameter; 1525 return; 1526 } 1527 // FIXME: Actually store the attribute on the declaration 1528} 1529 1530static void handleUnusedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1531 // check the attribute arguments. 1532 if (Attr.hasParameterOrArguments()) { 1533 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1534 return; 1535 } 1536 1537 if (!isa<VarDecl>(D) && !isa<ObjCIvarDecl>(D) && !isFunctionOrMethod(D) && 1538 !isa<TypeDecl>(D) && !isa<LabelDecl>(D)) { 1539 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1540 << Attr.getName() << ExpectedVariableFunctionOrLabel; 1541 return; 1542 } 1543 1544 D->addAttr(::new (S.Context) UnusedAttr(Attr.getRange(), S.Context)); 1545} 1546 1547static void handleReturnsTwiceAttr(Sema &S, Decl *D, 1548 const AttributeList &Attr) { 1549 // check the attribute arguments. 1550 if (Attr.hasParameterOrArguments()) { 1551 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1552 return; 1553 } 1554 1555 if (!isa<FunctionDecl>(D)) { 1556 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1557 << Attr.getName() << ExpectedFunction; 1558 return; 1559 } 1560 1561 D->addAttr(::new (S.Context) ReturnsTwiceAttr(Attr.getRange(), S.Context)); 1562} 1563 1564static void handleUsedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1565 // check the attribute arguments. 1566 if (Attr.hasParameterOrArguments()) { 1567 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1568 return; 1569 } 1570 1571 if (const VarDecl *VD = dyn_cast<VarDecl>(D)) { 1572 if (VD->hasLocalStorage() || VD->hasExternalStorage()) { 1573 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "used"; 1574 return; 1575 } 1576 } else if (!isFunctionOrMethod(D)) { 1577 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1578 << Attr.getName() << ExpectedVariableOrFunction; 1579 return; 1580 } 1581 1582 D->addAttr(::new (S.Context) UsedAttr(Attr.getRange(), S.Context)); 1583} 1584 1585static void handleConstructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1586 // check the attribute arguments. 1587 if (Attr.getNumArgs() > 1) { 1588 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1589 return; 1590 } 1591 1592 int priority = 65535; // FIXME: Do not hardcode such constants. 1593 if (Attr.getNumArgs() > 0) { 1594 Expr *E = Attr.getArg(0); 1595 llvm::APSInt Idx(32); 1596 if (E->isTypeDependent() || E->isValueDependent() || 1597 !E->isIntegerConstantExpr(Idx, S.Context)) { 1598 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1599 << "constructor" << 1 << E->getSourceRange(); 1600 return; 1601 } 1602 priority = Idx.getZExtValue(); 1603 } 1604 1605 if (!isa<FunctionDecl>(D)) { 1606 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1607 << Attr.getName() << ExpectedFunction; 1608 return; 1609 } 1610 1611 D->addAttr(::new (S.Context) ConstructorAttr(Attr.getRange(), S.Context, 1612 priority)); 1613} 1614 1615static void handleDestructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1616 // check the attribute arguments. 1617 if (Attr.getNumArgs() > 1) { 1618 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1619 return; 1620 } 1621 1622 int priority = 65535; // FIXME: Do not hardcode such constants. 1623 if (Attr.getNumArgs() > 0) { 1624 Expr *E = Attr.getArg(0); 1625 llvm::APSInt Idx(32); 1626 if (E->isTypeDependent() || E->isValueDependent() || 1627 !E->isIntegerConstantExpr(Idx, S.Context)) { 1628 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1629 << "destructor" << 1 << E->getSourceRange(); 1630 return; 1631 } 1632 priority = Idx.getZExtValue(); 1633 } 1634 1635 if (!isa<FunctionDecl>(D)) { 1636 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1637 << Attr.getName() << ExpectedFunction; 1638 return; 1639 } 1640 1641 D->addAttr(::new (S.Context) DestructorAttr(Attr.getRange(), S.Context, 1642 priority)); 1643} 1644 1645static void handleDeprecatedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1646 unsigned NumArgs = Attr.getNumArgs(); 1647 if (NumArgs > 1) { 1648 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1649 return; 1650 } 1651 1652 // Handle the case where deprecated attribute has a text message. 1653 StringRef Str; 1654 if (NumArgs == 1) { 1655 StringLiteral *SE = dyn_cast<StringLiteral>(Attr.getArg(0)); 1656 if (!SE) { 1657 S.Diag(Attr.getArg(0)->getLocStart(), diag::err_attribute_not_string) 1658 << "deprecated"; 1659 return; 1660 } 1661 Str = SE->getString(); 1662 } 1663 1664 D->addAttr(::new (S.Context) DeprecatedAttr(Attr.getRange(), S.Context, Str)); 1665} 1666 1667static void handleUnavailableAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1668 unsigned NumArgs = Attr.getNumArgs(); 1669 if (NumArgs > 1) { 1670 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1671 return; 1672 } 1673 1674 // Handle the case where unavailable attribute has a text message. 1675 StringRef Str; 1676 if (NumArgs == 1) { 1677 StringLiteral *SE = dyn_cast<StringLiteral>(Attr.getArg(0)); 1678 if (!SE) { 1679 S.Diag(Attr.getArg(0)->getLocStart(), 1680 diag::err_attribute_not_string) << "unavailable"; 1681 return; 1682 } 1683 Str = SE->getString(); 1684 } 1685 D->addAttr(::new (S.Context) UnavailableAttr(Attr.getRange(), S.Context, Str)); 1686} 1687 1688static void handleArcWeakrefUnavailableAttr(Sema &S, Decl *D, 1689 const AttributeList &Attr) { 1690 unsigned NumArgs = Attr.getNumArgs(); 1691 if (NumArgs > 0) { 1692 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 0; 1693 return; 1694 } 1695 1696 D->addAttr(::new (S.Context) ArcWeakrefUnavailableAttr( 1697 Attr.getRange(), S.Context)); 1698} 1699 1700static void handleObjCRootClassAttr(Sema &S, Decl *D, 1701 const AttributeList &Attr) { 1702 if (!isa<ObjCInterfaceDecl>(D)) { 1703 S.Diag(Attr.getLoc(), diag::err_attribute_requires_objc_interface); 1704 return; 1705 } 1706 1707 unsigned NumArgs = Attr.getNumArgs(); 1708 if (NumArgs > 0) { 1709 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 0; 1710 return; 1711 } 1712 1713 D->addAttr(::new (S.Context) ObjCRootClassAttr(Attr.getRange(), S.Context)); 1714} 1715 1716static void handleObjCRequiresPropertyDefsAttr(Sema &S, Decl *D, 1717 const AttributeList &Attr) { 1718 if (!isa<ObjCInterfaceDecl>(D)) { 1719 S.Diag(Attr.getLoc(), diag::err_suppress_autosynthesis); 1720 return; 1721 } 1722 1723 unsigned NumArgs = Attr.getNumArgs(); 1724 if (NumArgs > 0) { 1725 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 0; 1726 return; 1727 } 1728 1729 D->addAttr(::new (S.Context) ObjCRequiresPropertyDefsAttr( 1730 Attr.getRange(), S.Context)); 1731} 1732 1733static bool checkAvailabilityAttr(Sema &S, SourceRange Range, 1734 IdentifierInfo *Platform, 1735 VersionTuple Introduced, 1736 VersionTuple Deprecated, 1737 VersionTuple Obsoleted) { 1738 StringRef PlatformName 1739 = AvailabilityAttr::getPrettyPlatformName(Platform->getName()); 1740 if (PlatformName.empty()) 1741 PlatformName = Platform->getName(); 1742 1743 // Ensure that Introduced <= Deprecated <= Obsoleted (although not all 1744 // of these steps are needed). 1745 if (!Introduced.empty() && !Deprecated.empty() && 1746 !(Introduced <= Deprecated)) { 1747 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering) 1748 << 1 << PlatformName << Deprecated.getAsString() 1749 << 0 << Introduced.getAsString(); 1750 return true; 1751 } 1752 1753 if (!Introduced.empty() && !Obsoleted.empty() && 1754 !(Introduced <= Obsoleted)) { 1755 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering) 1756 << 2 << PlatformName << Obsoleted.getAsString() 1757 << 0 << Introduced.getAsString(); 1758 return true; 1759 } 1760 1761 if (!Deprecated.empty() && !Obsoleted.empty() && 1762 !(Deprecated <= Obsoleted)) { 1763 S.Diag(Range.getBegin(), diag::warn_availability_version_ordering) 1764 << 2 << PlatformName << Obsoleted.getAsString() 1765 << 1 << Deprecated.getAsString(); 1766 return true; 1767 } 1768 1769 return false; 1770} 1771 1772bool Sema::mergeAvailabilityAttr(Decl *D, SourceRange Range, 1773 bool Inherited, 1774 IdentifierInfo *Platform, 1775 VersionTuple Introduced, 1776 VersionTuple Deprecated, 1777 VersionTuple Obsoleted, 1778 bool IsUnavailable, 1779 StringRef Message) { 1780 VersionTuple MergedIntroduced = Introduced; 1781 VersionTuple MergedDeprecated = Deprecated; 1782 VersionTuple MergedObsoleted = Obsoleted; 1783 bool FoundAny = false; 1784 1785 if (D->hasAttrs()) { 1786 AttrVec &Attrs = D->getAttrs(); 1787 for (unsigned i = 0, e = Attrs.size(); i != e;) { 1788 const AvailabilityAttr *OldAA = dyn_cast<AvailabilityAttr>(Attrs[i]); 1789 if (!OldAA) { 1790 ++i; 1791 continue; 1792 } 1793 1794 IdentifierInfo *OldPlatform = OldAA->getPlatform(); 1795 if (OldPlatform != Platform) { 1796 ++i; 1797 continue; 1798 } 1799 1800 FoundAny = true; 1801 VersionTuple OldIntroduced = OldAA->getIntroduced(); 1802 VersionTuple OldDeprecated = OldAA->getDeprecated(); 1803 VersionTuple OldObsoleted = OldAA->getObsoleted(); 1804 bool OldIsUnavailable = OldAA->getUnavailable(); 1805 StringRef OldMessage = OldAA->getMessage(); 1806 1807 if ((!OldIntroduced.empty() && !Introduced.empty() && 1808 OldIntroduced != Introduced) || 1809 (!OldDeprecated.empty() && !Deprecated.empty() && 1810 OldDeprecated != Deprecated) || 1811 (!OldObsoleted.empty() && !Obsoleted.empty() && 1812 OldObsoleted != Obsoleted) || 1813 (OldIsUnavailable != IsUnavailable) || 1814 (OldMessage != Message)) { 1815 Diag(OldAA->getLocation(), diag::warn_mismatched_availability); 1816 Diag(Range.getBegin(), diag::note_previous_attribute); 1817 Attrs.erase(Attrs.begin() + i); 1818 --e; 1819 continue; 1820 } 1821 1822 VersionTuple MergedIntroduced2 = MergedIntroduced; 1823 VersionTuple MergedDeprecated2 = MergedDeprecated; 1824 VersionTuple MergedObsoleted2 = MergedObsoleted; 1825 1826 if (MergedIntroduced2.empty()) 1827 MergedIntroduced2 = OldIntroduced; 1828 if (MergedDeprecated2.empty()) 1829 MergedDeprecated2 = OldDeprecated; 1830 if (MergedObsoleted2.empty()) 1831 MergedObsoleted2 = OldObsoleted; 1832 1833 if (checkAvailabilityAttr(*this, OldAA->getRange(), Platform, 1834 MergedIntroduced2, MergedDeprecated2, 1835 MergedObsoleted2)) { 1836 Attrs.erase(Attrs.begin() + i); 1837 --e; 1838 continue; 1839 } 1840 1841 MergedIntroduced = MergedIntroduced2; 1842 MergedDeprecated = MergedDeprecated2; 1843 MergedObsoleted = MergedObsoleted2; 1844 ++i; 1845 } 1846 } 1847 1848 if (FoundAny && 1849 MergedIntroduced == Introduced && 1850 MergedDeprecated == Deprecated && 1851 MergedObsoleted == Obsoleted) 1852 return false; 1853 1854 if (!checkAvailabilityAttr(*this, Range, Platform, MergedIntroduced, 1855 MergedDeprecated, MergedObsoleted)) { 1856 AvailabilityAttr *Attr = 1857 ::new (Context) AvailabilityAttr(Range, Context, Platform, 1858 Introduced, Deprecated, 1859 Obsoleted, IsUnavailable, Message); 1860 1861 if (Inherited) 1862 Attr->setInherited(true); 1863 D->addAttr(Attr); 1864 return true; 1865 } 1866 return false; 1867} 1868 1869static void handleAvailabilityAttr(Sema &S, Decl *D, 1870 const AttributeList &Attr) { 1871 IdentifierInfo *Platform = Attr.getParameterName(); 1872 SourceLocation PlatformLoc = Attr.getParameterLoc(); 1873 1874 if (AvailabilityAttr::getPrettyPlatformName(Platform->getName()).empty()) 1875 S.Diag(PlatformLoc, diag::warn_availability_unknown_platform) 1876 << Platform; 1877 1878 AvailabilityChange Introduced = Attr.getAvailabilityIntroduced(); 1879 AvailabilityChange Deprecated = Attr.getAvailabilityDeprecated(); 1880 AvailabilityChange Obsoleted = Attr.getAvailabilityObsoleted(); 1881 bool IsUnavailable = Attr.getUnavailableLoc().isValid(); 1882 StringRef Str; 1883 const StringLiteral *SE = 1884 dyn_cast_or_null<const StringLiteral>(Attr.getMessageExpr()); 1885 if (SE) 1886 Str = SE->getString(); 1887 1888 S.mergeAvailabilityAttr(D, Attr.getRange(), 1889 false, Platform, 1890 Introduced.Version, 1891 Deprecated.Version, 1892 Obsoleted.Version, 1893 IsUnavailable, 1894 Str); 1895} 1896 1897bool Sema::mergeVisibilityAttr(Decl *D, SourceRange Range, 1898 bool Inherited, 1899 VisibilityAttr::VisibilityType Vis) { 1900 if (isa<TypedefNameDecl>(D)) { 1901 Diag(Range.getBegin(), diag::warn_attribute_ignored) << "visibility"; 1902 return false; 1903 } 1904 VisibilityAttr *ExistingAttr = D->getAttr<VisibilityAttr>(); 1905 if (ExistingAttr) { 1906 VisibilityAttr::VisibilityType ExistingVis = ExistingAttr->getVisibility(); 1907 if (ExistingVis == Vis) 1908 return false; 1909 Diag(ExistingAttr->getLocation(), diag::err_mismatched_visibility); 1910 Diag(Range.getBegin(), diag::note_previous_attribute); 1911 D->dropAttr<VisibilityAttr>(); 1912 } 1913 VisibilityAttr *Attr = ::new (Context) VisibilityAttr(Range, Context, Vis); 1914 if (Inherited) 1915 Attr->setInherited(true); 1916 D->addAttr(Attr); 1917 return true; 1918} 1919 1920static void handleVisibilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1921 // check the attribute arguments. 1922 if(!checkAttributeNumArgs(S, Attr, 1)) 1923 return; 1924 1925 Expr *Arg = Attr.getArg(0); 1926 Arg = Arg->IgnoreParenCasts(); 1927 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 1928 1929 if (!Str || !Str->isAscii()) { 1930 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1931 << "visibility" << 1; 1932 return; 1933 } 1934 1935 StringRef TypeStr = Str->getString(); 1936 VisibilityAttr::VisibilityType type; 1937 1938 if (TypeStr == "default") 1939 type = VisibilityAttr::Default; 1940 else if (TypeStr == "hidden") 1941 type = VisibilityAttr::Hidden; 1942 else if (TypeStr == "internal") 1943 type = VisibilityAttr::Hidden; // FIXME 1944 else if (TypeStr == "protected") { 1945 // Complain about attempts to use protected visibility on targets 1946 // (like Darwin) that don't support it. 1947 if (!S.Context.getTargetInfo().hasProtectedVisibility()) { 1948 S.Diag(Attr.getLoc(), diag::warn_attribute_protected_visibility); 1949 type = VisibilityAttr::Default; 1950 } else { 1951 type = VisibilityAttr::Protected; 1952 } 1953 } else { 1954 S.Diag(Attr.getLoc(), diag::warn_attribute_unknown_visibility) << TypeStr; 1955 return; 1956 } 1957 1958 S.mergeVisibilityAttr(D, Attr.getRange(), false, type); 1959} 1960 1961static void handleObjCMethodFamilyAttr(Sema &S, Decl *decl, 1962 const AttributeList &Attr) { 1963 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(decl); 1964 if (!method) { 1965 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1966 << ExpectedMethod; 1967 return; 1968 } 1969 1970 if (Attr.getNumArgs() != 0 || !Attr.getParameterName()) { 1971 if (!Attr.getParameterName() && Attr.getNumArgs() == 1) { 1972 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1973 << "objc_method_family" << 1; 1974 } else { 1975 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1976 } 1977 Attr.setInvalid(); 1978 return; 1979 } 1980 1981 StringRef param = Attr.getParameterName()->getName(); 1982 ObjCMethodFamilyAttr::FamilyKind family; 1983 if (param == "none") 1984 family = ObjCMethodFamilyAttr::OMF_None; 1985 else if (param == "alloc") 1986 family = ObjCMethodFamilyAttr::OMF_alloc; 1987 else if (param == "copy") 1988 family = ObjCMethodFamilyAttr::OMF_copy; 1989 else if (param == "init") 1990 family = ObjCMethodFamilyAttr::OMF_init; 1991 else if (param == "mutableCopy") 1992 family = ObjCMethodFamilyAttr::OMF_mutableCopy; 1993 else if (param == "new") 1994 family = ObjCMethodFamilyAttr::OMF_new; 1995 else { 1996 // Just warn and ignore it. This is future-proof against new 1997 // families being used in system headers. 1998 S.Diag(Attr.getParameterLoc(), diag::warn_unknown_method_family); 1999 return; 2000 } 2001 2002 if (family == ObjCMethodFamilyAttr::OMF_init && 2003 !method->getResultType()->isObjCObjectPointerType()) { 2004 S.Diag(method->getLocation(), diag::err_init_method_bad_return_type) 2005 << method->getResultType(); 2006 // Ignore the attribute. 2007 return; 2008 } 2009 2010 method->addAttr(new (S.Context) ObjCMethodFamilyAttr(Attr.getRange(), 2011 S.Context, family)); 2012} 2013 2014static void handleObjCExceptionAttr(Sema &S, Decl *D, 2015 const AttributeList &Attr) { 2016 if (!checkAttributeNumArgs(S, Attr, 0)) 2017 return; 2018 2019 ObjCInterfaceDecl *OCI = dyn_cast<ObjCInterfaceDecl>(D); 2020 if (OCI == 0) { 2021 S.Diag(Attr.getLoc(), diag::err_attribute_requires_objc_interface); 2022 return; 2023 } 2024 2025 D->addAttr(::new (S.Context) ObjCExceptionAttr(Attr.getRange(), S.Context)); 2026} 2027 2028static void handleObjCNSObject(Sema &S, Decl *D, const AttributeList &Attr) { 2029 if (Attr.getNumArgs() != 0) { 2030 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2031 return; 2032 } 2033 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) { 2034 QualType T = TD->getUnderlyingType(); 2035 if (!T->isPointerType() || 2036 !T->getAs<PointerType>()->getPointeeType()->isRecordType()) { 2037 S.Diag(TD->getLocation(), diag::err_nsobject_attribute); 2038 return; 2039 } 2040 } 2041 else if (!isa<ObjCPropertyDecl>(D)) { 2042 // It is okay to include this attribute on properties, e.g.: 2043 // 2044 // @property (retain, nonatomic) struct Bork *Q __attribute__((NSObject)); 2045 // 2046 // In this case it follows tradition and suppresses an error in the above 2047 // case. 2048 S.Diag(D->getLocation(), diag::warn_nsobject_attribute); 2049 } 2050 D->addAttr(::new (S.Context) ObjCNSObjectAttr(Attr.getRange(), S.Context)); 2051} 2052 2053static void 2054handleOverloadableAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2055 if (Attr.getNumArgs() != 0) { 2056 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2057 return; 2058 } 2059 2060 if (!isa<FunctionDecl>(D)) { 2061 S.Diag(Attr.getLoc(), diag::err_attribute_overloadable_not_function); 2062 return; 2063 } 2064 2065 D->addAttr(::new (S.Context) OverloadableAttr(Attr.getRange(), S.Context)); 2066} 2067 2068static void handleBlocksAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2069 if (!Attr.getParameterName()) { 2070 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 2071 << "blocks" << 1; 2072 return; 2073 } 2074 2075 if (Attr.getNumArgs() != 0) { 2076 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2077 return; 2078 } 2079 2080 BlocksAttr::BlockType type; 2081 if (Attr.getParameterName()->isStr("byref")) 2082 type = BlocksAttr::ByRef; 2083 else { 2084 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 2085 << "blocks" << Attr.getParameterName(); 2086 return; 2087 } 2088 2089 D->addAttr(::new (S.Context) BlocksAttr(Attr.getRange(), S.Context, type)); 2090} 2091 2092static void handleSentinelAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2093 // check the attribute arguments. 2094 if (Attr.getNumArgs() > 2) { 2095 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 2096 return; 2097 } 2098 2099 unsigned sentinel = 0; 2100 if (Attr.getNumArgs() > 0) { 2101 Expr *E = Attr.getArg(0); 2102 llvm::APSInt Idx(32); 2103 if (E->isTypeDependent() || E->isValueDependent() || 2104 !E->isIntegerConstantExpr(Idx, S.Context)) { 2105 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2106 << "sentinel" << 1 << E->getSourceRange(); 2107 return; 2108 } 2109 2110 if (Idx.isSigned() && Idx.isNegative()) { 2111 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_less_than_zero) 2112 << E->getSourceRange(); 2113 return; 2114 } 2115 2116 sentinel = Idx.getZExtValue(); 2117 } 2118 2119 unsigned nullPos = 0; 2120 if (Attr.getNumArgs() > 1) { 2121 Expr *E = Attr.getArg(1); 2122 llvm::APSInt Idx(32); 2123 if (E->isTypeDependent() || E->isValueDependent() || 2124 !E->isIntegerConstantExpr(Idx, S.Context)) { 2125 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2126 << "sentinel" << 2 << E->getSourceRange(); 2127 return; 2128 } 2129 nullPos = Idx.getZExtValue(); 2130 2131 if ((Idx.isSigned() && Idx.isNegative()) || nullPos > 1) { 2132 // FIXME: This error message could be improved, it would be nice 2133 // to say what the bounds actually are. 2134 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_not_zero_or_one) 2135 << E->getSourceRange(); 2136 return; 2137 } 2138 } 2139 2140 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) { 2141 const FunctionType *FT = FD->getType()->castAs<FunctionType>(); 2142 if (isa<FunctionNoProtoType>(FT)) { 2143 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_named_arguments); 2144 return; 2145 } 2146 2147 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 2148 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 2149 return; 2150 } 2151 } else if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) { 2152 if (!MD->isVariadic()) { 2153 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 2154 return; 2155 } 2156 } else if (BlockDecl *BD = dyn_cast<BlockDecl>(D)) { 2157 if (!BD->isVariadic()) { 2158 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 1; 2159 return; 2160 } 2161 } else if (const VarDecl *V = dyn_cast<VarDecl>(D)) { 2162 QualType Ty = V->getType(); 2163 if (Ty->isBlockPointerType() || Ty->isFunctionPointerType()) { 2164 const FunctionType *FT = Ty->isFunctionPointerType() ? getFunctionType(D) 2165 : Ty->getAs<BlockPointerType>()->getPointeeType()->getAs<FunctionType>(); 2166 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 2167 int m = Ty->isFunctionPointerType() ? 0 : 1; 2168 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << m; 2169 return; 2170 } 2171 } else { 2172 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2173 << Attr.getName() << ExpectedFunctionMethodOrBlock; 2174 return; 2175 } 2176 } else { 2177 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2178 << Attr.getName() << ExpectedFunctionMethodOrBlock; 2179 return; 2180 } 2181 D->addAttr(::new (S.Context) SentinelAttr(Attr.getRange(), S.Context, sentinel, 2182 nullPos)); 2183} 2184 2185static void handleWarnUnusedResult(Sema &S, Decl *D, const AttributeList &Attr) { 2186 // check the attribute arguments. 2187 if (!checkAttributeNumArgs(S, Attr, 0)) 2188 return; 2189 2190 if (!isFunction(D) && !isa<ObjCMethodDecl>(D)) { 2191 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2192 << Attr.getName() << ExpectedFunctionOrMethod; 2193 return; 2194 } 2195 2196 if (isFunction(D) && getFunctionType(D)->getResultType()->isVoidType()) { 2197 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 2198 << Attr.getName() << 0; 2199 return; 2200 } 2201 if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 2202 if (MD->getResultType()->isVoidType()) { 2203 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 2204 << Attr.getName() << 1; 2205 return; 2206 } 2207 2208 D->addAttr(::new (S.Context) WarnUnusedResultAttr(Attr.getRange(), S.Context)); 2209} 2210 2211static void handleWeakAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2212 // check the attribute arguments. 2213 if (Attr.hasParameterOrArguments()) { 2214 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2215 return; 2216 } 2217 2218 if (!isa<VarDecl>(D) && !isa<FunctionDecl>(D)) { 2219 if (isa<CXXRecordDecl>(D)) { 2220 D->addAttr(::new (S.Context) WeakAttr(Attr.getRange(), S.Context)); 2221 return; 2222 } 2223 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2224 << Attr.getName() << ExpectedVariableOrFunction; 2225 return; 2226 } 2227 2228 NamedDecl *nd = cast<NamedDecl>(D); 2229 2230 // 'weak' only applies to declarations with external linkage. 2231 if (hasEffectivelyInternalLinkage(nd)) { 2232 S.Diag(Attr.getLoc(), diag::err_attribute_weak_static); 2233 return; 2234 } 2235 2236 nd->addAttr(::new (S.Context) WeakAttr(Attr.getRange(), S.Context)); 2237} 2238 2239static void handleWeakImportAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2240 // check the attribute arguments. 2241 if (!checkAttributeNumArgs(S, Attr, 0)) 2242 return; 2243 2244 2245 // weak_import only applies to variable & function declarations. 2246 bool isDef = false; 2247 if (!D->canBeWeakImported(isDef)) { 2248 if (isDef) 2249 S.Diag(Attr.getLoc(), 2250 diag::warn_attribute_weak_import_invalid_on_definition) 2251 << "weak_import" << 2 /*variable and function*/; 2252 else if (isa<ObjCPropertyDecl>(D) || isa<ObjCMethodDecl>(D) || 2253 (S.Context.getTargetInfo().getTriple().isOSDarwin() && 2254 (isa<ObjCInterfaceDecl>(D) || isa<EnumDecl>(D)))) { 2255 // Nothing to warn about here. 2256 } else 2257 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2258 << Attr.getName() << ExpectedVariableOrFunction; 2259 2260 return; 2261 } 2262 2263 D->addAttr(::new (S.Context) WeakImportAttr(Attr.getRange(), S.Context)); 2264} 2265 2266static void handleReqdWorkGroupSize(Sema &S, Decl *D, 2267 const AttributeList &Attr) { 2268 // Attribute has 3 arguments. 2269 if (!checkAttributeNumArgs(S, Attr, 3)) 2270 return; 2271 2272 unsigned WGSize[3]; 2273 for (unsigned i = 0; i < 3; ++i) { 2274 Expr *E = Attr.getArg(i); 2275 llvm::APSInt ArgNum(32); 2276 if (E->isTypeDependent() || E->isValueDependent() || 2277 !E->isIntegerConstantExpr(ArgNum, S.Context)) { 2278 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 2279 << "reqd_work_group_size" << E->getSourceRange(); 2280 return; 2281 } 2282 WGSize[i] = (unsigned) ArgNum.getZExtValue(); 2283 } 2284 D->addAttr(::new (S.Context) ReqdWorkGroupSizeAttr(Attr.getRange(), S.Context, 2285 WGSize[0], WGSize[1], 2286 WGSize[2])); 2287} 2288 2289bool Sema::mergeSectionAttr(Decl *D, SourceRange Range, bool Inherited, 2290 StringRef Name) { 2291 if (SectionAttr *ExistingAttr = D->getAttr<SectionAttr>()) { 2292 if (ExistingAttr->getName() == Name) 2293 return false; 2294 Diag(ExistingAttr->getLocation(), diag::warn_mismatched_section); 2295 Diag(Range.getBegin(), diag::note_previous_attribute); 2296 return false; 2297 } 2298 SectionAttr *Attr = ::new (Context) SectionAttr(Range, Context, Name); 2299 if (Inherited) 2300 Attr->setInherited(true); 2301 D->addAttr(Attr); 2302 return true; 2303} 2304 2305static void handleSectionAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2306 // Attribute has no arguments. 2307 if (!checkAttributeNumArgs(S, Attr, 1)) 2308 return; 2309 2310 // Make sure that there is a string literal as the sections's single 2311 // argument. 2312 Expr *ArgExpr = Attr.getArg(0); 2313 StringLiteral *SE = dyn_cast<StringLiteral>(ArgExpr); 2314 if (!SE) { 2315 S.Diag(ArgExpr->getLocStart(), diag::err_attribute_not_string) << "section"; 2316 return; 2317 } 2318 2319 // If the target wants to validate the section specifier, make it happen. 2320 std::string Error = S.Context.getTargetInfo().isValidSectionSpecifier(SE->getString()); 2321 if (!Error.empty()) { 2322 S.Diag(SE->getLocStart(), diag::err_attribute_section_invalid_for_target) 2323 << Error; 2324 return; 2325 } 2326 2327 // This attribute cannot be applied to local variables. 2328 if (isa<VarDecl>(D) && cast<VarDecl>(D)->hasLocalStorage()) { 2329 S.Diag(SE->getLocStart(), diag::err_attribute_section_local_variable); 2330 return; 2331 } 2332 S.mergeSectionAttr(D, Attr.getRange(), false, SE->getString()); 2333} 2334 2335 2336static void handleNothrowAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2337 // check the attribute arguments. 2338 if (Attr.hasParameterOrArguments()) { 2339 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2340 return; 2341 } 2342 2343 if (NoThrowAttr *Existing = D->getAttr<NoThrowAttr>()) { 2344 if (Existing->getLocation().isInvalid()) 2345 Existing->setRange(Attr.getRange()); 2346 } else { 2347 D->addAttr(::new (S.Context) NoThrowAttr(Attr.getRange(), S.Context)); 2348 } 2349} 2350 2351static void handleConstAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2352 // check the attribute arguments. 2353 if (Attr.hasParameterOrArguments()) { 2354 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2355 return; 2356 } 2357 2358 if (ConstAttr *Existing = D->getAttr<ConstAttr>()) { 2359 if (Existing->getLocation().isInvalid()) 2360 Existing->setRange(Attr.getRange()); 2361 } else { 2362 D->addAttr(::new (S.Context) ConstAttr(Attr.getRange(), S.Context)); 2363 } 2364} 2365 2366static void handlePureAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2367 // check the attribute arguments. 2368 if (!checkAttributeNumArgs(S, Attr, 0)) 2369 return; 2370 2371 D->addAttr(::new (S.Context) PureAttr(Attr.getRange(), S.Context)); 2372} 2373 2374static void handleCleanupAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2375 if (!Attr.getParameterName()) { 2376 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2377 return; 2378 } 2379 2380 if (Attr.getNumArgs() != 0) { 2381 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2382 return; 2383 } 2384 2385 VarDecl *VD = dyn_cast<VarDecl>(D); 2386 2387 if (!VD || !VD->hasLocalStorage()) { 2388 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "cleanup"; 2389 return; 2390 } 2391 2392 // Look up the function 2393 // FIXME: Lookup probably isn't looking in the right place 2394 NamedDecl *CleanupDecl 2395 = S.LookupSingleName(S.TUScope, Attr.getParameterName(), 2396 Attr.getParameterLoc(), Sema::LookupOrdinaryName); 2397 if (!CleanupDecl) { 2398 S.Diag(Attr.getParameterLoc(), diag::err_attribute_cleanup_arg_not_found) << 2399 Attr.getParameterName(); 2400 return; 2401 } 2402 2403 FunctionDecl *FD = dyn_cast<FunctionDecl>(CleanupDecl); 2404 if (!FD) { 2405 S.Diag(Attr.getParameterLoc(), 2406 diag::err_attribute_cleanup_arg_not_function) 2407 << Attr.getParameterName(); 2408 return; 2409 } 2410 2411 if (FD->getNumParams() != 1) { 2412 S.Diag(Attr.getParameterLoc(), 2413 diag::err_attribute_cleanup_func_must_take_one_arg) 2414 << Attr.getParameterName(); 2415 return; 2416 } 2417 2418 // We're currently more strict than GCC about what function types we accept. 2419 // If this ever proves to be a problem it should be easy to fix. 2420 QualType Ty = S.Context.getPointerType(VD->getType()); 2421 QualType ParamTy = FD->getParamDecl(0)->getType(); 2422 if (S.CheckAssignmentConstraints(FD->getParamDecl(0)->getLocation(), 2423 ParamTy, Ty) != Sema::Compatible) { 2424 S.Diag(Attr.getParameterLoc(), 2425 diag::err_attribute_cleanup_func_arg_incompatible_type) << 2426 Attr.getParameterName() << ParamTy << Ty; 2427 return; 2428 } 2429 2430 D->addAttr(::new (S.Context) CleanupAttr(Attr.getRange(), S.Context, FD)); 2431 S.MarkFunctionReferenced(Attr.getParameterLoc(), FD); 2432} 2433 2434/// Handle __attribute__((format_arg((idx)))) attribute based on 2435/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 2436static void handleFormatArgAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2437 if (!checkAttributeNumArgs(S, Attr, 1)) 2438 return; 2439 2440 if (!isFunctionOrMethod(D) || !hasFunctionProto(D)) { 2441 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2442 << Attr.getName() << ExpectedFunction; 2443 return; 2444 } 2445 2446 // In C++ the implicit 'this' function parameter also counts, and they are 2447 // counted from one. 2448 bool HasImplicitThisParam = isInstanceMethod(D); 2449 unsigned NumArgs = getFunctionOrMethodNumArgs(D) + HasImplicitThisParam; 2450 unsigned FirstIdx = 1; 2451 2452 // checks for the 2nd argument 2453 Expr *IdxExpr = Attr.getArg(0); 2454 llvm::APSInt Idx(32); 2455 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 2456 !IdxExpr->isIntegerConstantExpr(Idx, S.Context)) { 2457 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2458 << "format" << 2 << IdxExpr->getSourceRange(); 2459 return; 2460 } 2461 2462 if (Idx.getZExtValue() < FirstIdx || Idx.getZExtValue() > NumArgs) { 2463 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 2464 << "format" << 2 << IdxExpr->getSourceRange(); 2465 return; 2466 } 2467 2468 unsigned ArgIdx = Idx.getZExtValue() - 1; 2469 2470 if (HasImplicitThisParam) { 2471 if (ArgIdx == 0) { 2472 S.Diag(Attr.getLoc(), diag::err_attribute_invalid_implicit_this_argument) 2473 << "format_arg" << IdxExpr->getSourceRange(); 2474 return; 2475 } 2476 ArgIdx--; 2477 } 2478 2479 // make sure the format string is really a string 2480 QualType Ty = getFunctionOrMethodArgType(D, ArgIdx); 2481 2482 bool not_nsstring_type = !isNSStringType(Ty, S.Context); 2483 if (not_nsstring_type && 2484 !isCFStringType(Ty, S.Context) && 2485 (!Ty->isPointerType() || 2486 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 2487 // FIXME: Should highlight the actual expression that has the wrong type. 2488 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2489 << (not_nsstring_type ? "a string type" : "an NSString") 2490 << IdxExpr->getSourceRange(); 2491 return; 2492 } 2493 Ty = getFunctionOrMethodResultType(D); 2494 if (!isNSStringType(Ty, S.Context) && 2495 !isCFStringType(Ty, S.Context) && 2496 (!Ty->isPointerType() || 2497 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 2498 // FIXME: Should highlight the actual expression that has the wrong type. 2499 S.Diag(Attr.getLoc(), diag::err_format_attribute_result_not) 2500 << (not_nsstring_type ? "string type" : "NSString") 2501 << IdxExpr->getSourceRange(); 2502 return; 2503 } 2504 2505 D->addAttr(::new (S.Context) FormatArgAttr(Attr.getRange(), S.Context, 2506 Idx.getZExtValue())); 2507} 2508 2509enum FormatAttrKind { 2510 CFStringFormat, 2511 NSStringFormat, 2512 StrftimeFormat, 2513 SupportedFormat, 2514 IgnoredFormat, 2515 InvalidFormat 2516}; 2517 2518/// getFormatAttrKind - Map from format attribute names to supported format 2519/// types. 2520static FormatAttrKind getFormatAttrKind(StringRef Format) { 2521 // Check for formats that get handled specially. 2522 if (Format == "NSString") 2523 return NSStringFormat; 2524 if (Format == "CFString") 2525 return CFStringFormat; 2526 if (Format == "strftime") 2527 return StrftimeFormat; 2528 2529 // Otherwise, check for supported formats. 2530 if (Format == "scanf" || Format == "printf" || Format == "printf0" || 2531 Format == "strfmon" || Format == "cmn_err" || Format == "vcmn_err" || 2532 Format == "zcmn_err" || 2533 Format == "kprintf") // OpenBSD. 2534 return SupportedFormat; 2535 2536 if (Format == "gcc_diag" || Format == "gcc_cdiag" || 2537 Format == "gcc_cxxdiag" || Format == "gcc_tdiag") 2538 return IgnoredFormat; 2539 2540 return InvalidFormat; 2541} 2542 2543/// Handle __attribute__((init_priority(priority))) attributes based on 2544/// http://gcc.gnu.org/onlinedocs/gcc/C_002b_002b-Attributes.html 2545static void handleInitPriorityAttr(Sema &S, Decl *D, 2546 const AttributeList &Attr) { 2547 if (!S.getLangOpts().CPlusPlus) { 2548 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 2549 return; 2550 } 2551 2552 if (!isa<VarDecl>(D) || S.getCurFunctionOrMethodDecl()) { 2553 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 2554 Attr.setInvalid(); 2555 return; 2556 } 2557 QualType T = dyn_cast<VarDecl>(D)->getType(); 2558 if (S.Context.getAsArrayType(T)) 2559 T = S.Context.getBaseElementType(T); 2560 if (!T->getAs<RecordType>()) { 2561 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 2562 Attr.setInvalid(); 2563 return; 2564 } 2565 2566 if (Attr.getNumArgs() != 1) { 2567 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2568 Attr.setInvalid(); 2569 return; 2570 } 2571 Expr *priorityExpr = Attr.getArg(0); 2572 2573 llvm::APSInt priority(32); 2574 if (priorityExpr->isTypeDependent() || priorityExpr->isValueDependent() || 2575 !priorityExpr->isIntegerConstantExpr(priority, S.Context)) { 2576 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 2577 << "init_priority" << priorityExpr->getSourceRange(); 2578 Attr.setInvalid(); 2579 return; 2580 } 2581 unsigned prioritynum = priority.getZExtValue(); 2582 if (prioritynum < 101 || prioritynum > 65535) { 2583 S.Diag(Attr.getLoc(), diag::err_attribute_argument_outof_range) 2584 << priorityExpr->getSourceRange(); 2585 Attr.setInvalid(); 2586 return; 2587 } 2588 D->addAttr(::new (S.Context) InitPriorityAttr(Attr.getRange(), S.Context, 2589 prioritynum)); 2590} 2591 2592bool Sema::mergeFormatAttr(Decl *D, SourceRange Range, bool Inherited, 2593 StringRef Format, int FormatIdx, int FirstArg) { 2594 // Check whether we already have an equivalent format attribute. 2595 for (specific_attr_iterator<FormatAttr> 2596 i = D->specific_attr_begin<FormatAttr>(), 2597 e = D->specific_attr_end<FormatAttr>(); 2598 i != e ; ++i) { 2599 FormatAttr *f = *i; 2600 if (f->getType() == Format && 2601 f->getFormatIdx() == FormatIdx && 2602 f->getFirstArg() == FirstArg) { 2603 // If we don't have a valid location for this attribute, adopt the 2604 // location. 2605 if (f->getLocation().isInvalid()) 2606 f->setRange(Range); 2607 return false; 2608 } 2609 } 2610 2611 FormatAttr *Attr = ::new (Context) FormatAttr(Range, Context, Format, 2612 FormatIdx, FirstArg); 2613 D->addAttr(Attr); 2614 return true; 2615} 2616 2617/// Handle __attribute__((format(type,idx,firstarg))) attributes based on 2618/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 2619static void handleFormatAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2620 2621 if (!Attr.getParameterName()) { 2622 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 2623 << "format" << 1; 2624 return; 2625 } 2626 2627 if (Attr.getNumArgs() != 2) { 2628 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 3; 2629 return; 2630 } 2631 2632 if (!isFunctionOrMethodOrBlock(D) || !hasFunctionProto(D)) { 2633 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2634 << Attr.getName() << ExpectedFunction; 2635 return; 2636 } 2637 2638 // In C++ the implicit 'this' function parameter also counts, and they are 2639 // counted from one. 2640 bool HasImplicitThisParam = isInstanceMethod(D); 2641 unsigned NumArgs = getFunctionOrMethodNumArgs(D) + HasImplicitThisParam; 2642 unsigned FirstIdx = 1; 2643 2644 StringRef Format = Attr.getParameterName()->getName(); 2645 2646 // Normalize the argument, __foo__ becomes foo. 2647 if (Format.startswith("__") && Format.endswith("__")) 2648 Format = Format.substr(2, Format.size() - 4); 2649 2650 // Check for supported formats. 2651 FormatAttrKind Kind = getFormatAttrKind(Format); 2652 2653 if (Kind == IgnoredFormat) 2654 return; 2655 2656 if (Kind == InvalidFormat) { 2657 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 2658 << "format" << Attr.getParameterName()->getName(); 2659 return; 2660 } 2661 2662 // checks for the 2nd argument 2663 Expr *IdxExpr = Attr.getArg(0); 2664 llvm::APSInt Idx(32); 2665 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 2666 !IdxExpr->isIntegerConstantExpr(Idx, S.Context)) { 2667 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2668 << "format" << 2 << IdxExpr->getSourceRange(); 2669 return; 2670 } 2671 2672 if (Idx.getZExtValue() < FirstIdx || Idx.getZExtValue() > NumArgs) { 2673 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 2674 << "format" << 2 << IdxExpr->getSourceRange(); 2675 return; 2676 } 2677 2678 // FIXME: Do we need to bounds check? 2679 unsigned ArgIdx = Idx.getZExtValue() - 1; 2680 2681 if (HasImplicitThisParam) { 2682 if (ArgIdx == 0) { 2683 S.Diag(Attr.getLoc(), 2684 diag::err_format_attribute_implicit_this_format_string) 2685 << IdxExpr->getSourceRange(); 2686 return; 2687 } 2688 ArgIdx--; 2689 } 2690 2691 // make sure the format string is really a string 2692 QualType Ty = getFunctionOrMethodArgType(D, ArgIdx); 2693 2694 if (Kind == CFStringFormat) { 2695 if (!isCFStringType(Ty, S.Context)) { 2696 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2697 << "a CFString" << IdxExpr->getSourceRange(); 2698 return; 2699 } 2700 } else if (Kind == NSStringFormat) { 2701 // FIXME: do we need to check if the type is NSString*? What are the 2702 // semantics? 2703 if (!isNSStringType(Ty, S.Context)) { 2704 // FIXME: Should highlight the actual expression that has the wrong type. 2705 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2706 << "an NSString" << IdxExpr->getSourceRange(); 2707 return; 2708 } 2709 } else if (!Ty->isPointerType() || 2710 !Ty->getAs<PointerType>()->getPointeeType()->isCharType()) { 2711 // FIXME: Should highlight the actual expression that has the wrong type. 2712 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2713 << "a string type" << IdxExpr->getSourceRange(); 2714 return; 2715 } 2716 2717 // check the 3rd argument 2718 Expr *FirstArgExpr = Attr.getArg(1); 2719 llvm::APSInt FirstArg(32); 2720 if (FirstArgExpr->isTypeDependent() || FirstArgExpr->isValueDependent() || 2721 !FirstArgExpr->isIntegerConstantExpr(FirstArg, S.Context)) { 2722 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2723 << "format" << 3 << FirstArgExpr->getSourceRange(); 2724 return; 2725 } 2726 2727 // check if the function is variadic if the 3rd argument non-zero 2728 if (FirstArg != 0) { 2729 if (isFunctionOrMethodVariadic(D)) { 2730 ++NumArgs; // +1 for ... 2731 } else { 2732 S.Diag(D->getLocation(), diag::err_format_attribute_requires_variadic); 2733 return; 2734 } 2735 } 2736 2737 // strftime requires FirstArg to be 0 because it doesn't read from any 2738 // variable the input is just the current time + the format string. 2739 if (Kind == StrftimeFormat) { 2740 if (FirstArg != 0) { 2741 S.Diag(Attr.getLoc(), diag::err_format_strftime_third_parameter) 2742 << FirstArgExpr->getSourceRange(); 2743 return; 2744 } 2745 // if 0 it disables parameter checking (to use with e.g. va_list) 2746 } else if (FirstArg != 0 && FirstArg != NumArgs) { 2747 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 2748 << "format" << 3 << FirstArgExpr->getSourceRange(); 2749 return; 2750 } 2751 2752 S.mergeFormatAttr(D, Attr.getRange(), false, Format, Idx.getZExtValue(), 2753 FirstArg.getZExtValue()); 2754} 2755 2756static void handleTransparentUnionAttr(Sema &S, Decl *D, 2757 const AttributeList &Attr) { 2758 // check the attribute arguments. 2759 if (!checkAttributeNumArgs(S, Attr, 0)) 2760 return; 2761 2762 2763 // Try to find the underlying union declaration. 2764 RecordDecl *RD = 0; 2765 TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D); 2766 if (TD && TD->getUnderlyingType()->isUnionType()) 2767 RD = TD->getUnderlyingType()->getAsUnionType()->getDecl(); 2768 else 2769 RD = dyn_cast<RecordDecl>(D); 2770 2771 if (!RD || !RD->isUnion()) { 2772 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2773 << Attr.getName() << ExpectedUnion; 2774 return; 2775 } 2776 2777 if (!RD->isCompleteDefinition()) { 2778 S.Diag(Attr.getLoc(), 2779 diag::warn_transparent_union_attribute_not_definition); 2780 return; 2781 } 2782 2783 RecordDecl::field_iterator Field = RD->field_begin(), 2784 FieldEnd = RD->field_end(); 2785 if (Field == FieldEnd) { 2786 S.Diag(Attr.getLoc(), diag::warn_transparent_union_attribute_zero_fields); 2787 return; 2788 } 2789 2790 FieldDecl *FirstField = &*Field; 2791 QualType FirstType = FirstField->getType(); 2792 if (FirstType->hasFloatingRepresentation() || FirstType->isVectorType()) { 2793 S.Diag(FirstField->getLocation(), 2794 diag::warn_transparent_union_attribute_floating) 2795 << FirstType->isVectorType() << FirstType; 2796 return; 2797 } 2798 2799 uint64_t FirstSize = S.Context.getTypeSize(FirstType); 2800 uint64_t FirstAlign = S.Context.getTypeAlign(FirstType); 2801 for (; Field != FieldEnd; ++Field) { 2802 QualType FieldType = Field->getType(); 2803 if (S.Context.getTypeSize(FieldType) != FirstSize || 2804 S.Context.getTypeAlign(FieldType) != FirstAlign) { 2805 // Warn if we drop the attribute. 2806 bool isSize = S.Context.getTypeSize(FieldType) != FirstSize; 2807 unsigned FieldBits = isSize? S.Context.getTypeSize(FieldType) 2808 : S.Context.getTypeAlign(FieldType); 2809 S.Diag(Field->getLocation(), 2810 diag::warn_transparent_union_attribute_field_size_align) 2811 << isSize << Field->getDeclName() << FieldBits; 2812 unsigned FirstBits = isSize? FirstSize : FirstAlign; 2813 S.Diag(FirstField->getLocation(), 2814 diag::note_transparent_union_first_field_size_align) 2815 << isSize << FirstBits; 2816 return; 2817 } 2818 } 2819 2820 RD->addAttr(::new (S.Context) TransparentUnionAttr(Attr.getRange(), S.Context)); 2821} 2822 2823static void handleAnnotateAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2824 // check the attribute arguments. 2825 if (!checkAttributeNumArgs(S, Attr, 1)) 2826 return; 2827 2828 Expr *ArgExpr = Attr.getArg(0); 2829 StringLiteral *SE = dyn_cast<StringLiteral>(ArgExpr); 2830 2831 // Make sure that there is a string literal as the annotation's single 2832 // argument. 2833 if (!SE) { 2834 S.Diag(ArgExpr->getLocStart(), diag::err_attribute_not_string) <<"annotate"; 2835 return; 2836 } 2837 2838 // Don't duplicate annotations that are already set. 2839 for (specific_attr_iterator<AnnotateAttr> 2840 i = D->specific_attr_begin<AnnotateAttr>(), 2841 e = D->specific_attr_end<AnnotateAttr>(); i != e; ++i) { 2842 if ((*i)->getAnnotation() == SE->getString()) 2843 return; 2844 } 2845 D->addAttr(::new (S.Context) AnnotateAttr(Attr.getRange(), S.Context, 2846 SE->getString())); 2847} 2848 2849static void handleAlignedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2850 // check the attribute arguments. 2851 if (Attr.getNumArgs() > 1) { 2852 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2853 return; 2854 } 2855 2856 //FIXME: The C++0x version of this attribute has more limited applicabilty 2857 // than GNU's, and should error out when it is used to specify a 2858 // weaker alignment, rather than being silently ignored. 2859 2860 if (Attr.getNumArgs() == 0) { 2861 D->addAttr(::new (S.Context) AlignedAttr(Attr.getRange(), S.Context, true, 0)); 2862 return; 2863 } 2864 2865 S.AddAlignedAttr(Attr.getRange(), D, Attr.getArg(0)); 2866} 2867 2868void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E) { 2869 // FIXME: Handle pack-expansions here. 2870 if (DiagnoseUnexpandedParameterPack(E)) 2871 return; 2872 2873 if (E->isTypeDependent() || E->isValueDependent()) { 2874 // Save dependent expressions in the AST to be instantiated. 2875 D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, E)); 2876 return; 2877 } 2878 2879 SourceLocation AttrLoc = AttrRange.getBegin(); 2880 // FIXME: Cache the number on the Attr object? 2881 llvm::APSInt Alignment(32); 2882 ExprResult ICE 2883 = VerifyIntegerConstantExpression(E, &Alignment, 2884 diag::err_aligned_attribute_argument_not_int, 2885 /*AllowFold*/ false); 2886 if (ICE.isInvalid()) 2887 return; 2888 if (!llvm::isPowerOf2_64(Alignment.getZExtValue())) { 2889 Diag(AttrLoc, diag::err_attribute_aligned_not_power_of_two) 2890 << E->getSourceRange(); 2891 return; 2892 } 2893 2894 D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, ICE.take())); 2895} 2896 2897void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *TS) { 2898 // FIXME: Cache the number on the Attr object if non-dependent? 2899 // FIXME: Perform checking of type validity 2900 D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, false, TS)); 2901 return; 2902} 2903 2904/// handleModeAttr - This attribute modifies the width of a decl with primitive 2905/// type. 2906/// 2907/// Despite what would be logical, the mode attribute is a decl attribute, not a 2908/// type attribute: 'int ** __attribute((mode(HI))) *G;' tries to make 'G' be 2909/// HImode, not an intermediate pointer. 2910static void handleModeAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2911 // This attribute isn't documented, but glibc uses it. It changes 2912 // the width of an int or unsigned int to the specified size. 2913 2914 // Check that there aren't any arguments 2915 if (!checkAttributeNumArgs(S, Attr, 0)) 2916 return; 2917 2918 2919 IdentifierInfo *Name = Attr.getParameterName(); 2920 if (!Name) { 2921 S.Diag(Attr.getLoc(), diag::err_attribute_missing_parameter_name); 2922 return; 2923 } 2924 2925 StringRef Str = Attr.getParameterName()->getName(); 2926 2927 // Normalize the attribute name, __foo__ becomes foo. 2928 if (Str.startswith("__") && Str.endswith("__")) 2929 Str = Str.substr(2, Str.size() - 4); 2930 2931 unsigned DestWidth = 0; 2932 bool IntegerMode = true; 2933 bool ComplexMode = false; 2934 switch (Str.size()) { 2935 case 2: 2936 switch (Str[0]) { 2937 case 'Q': DestWidth = 8; break; 2938 case 'H': DestWidth = 16; break; 2939 case 'S': DestWidth = 32; break; 2940 case 'D': DestWidth = 64; break; 2941 case 'X': DestWidth = 96; break; 2942 case 'T': DestWidth = 128; break; 2943 } 2944 if (Str[1] == 'F') { 2945 IntegerMode = false; 2946 } else if (Str[1] == 'C') { 2947 IntegerMode = false; 2948 ComplexMode = true; 2949 } else if (Str[1] != 'I') { 2950 DestWidth = 0; 2951 } 2952 break; 2953 case 4: 2954 // FIXME: glibc uses 'word' to define register_t; this is narrower than a 2955 // pointer on PIC16 and other embedded platforms. 2956 if (Str == "word") 2957 DestWidth = S.Context.getTargetInfo().getPointerWidth(0); 2958 else if (Str == "byte") 2959 DestWidth = S.Context.getTargetInfo().getCharWidth(); 2960 break; 2961 case 7: 2962 if (Str == "pointer") 2963 DestWidth = S.Context.getTargetInfo().getPointerWidth(0); 2964 break; 2965 } 2966 2967 QualType OldTy; 2968 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) 2969 OldTy = TD->getUnderlyingType(); 2970 else if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) 2971 OldTy = VD->getType(); 2972 else { 2973 S.Diag(D->getLocation(), diag::err_attr_wrong_decl) 2974 << "mode" << Attr.getRange(); 2975 return; 2976 } 2977 2978 if (!OldTy->getAs<BuiltinType>() && !OldTy->isComplexType()) 2979 S.Diag(Attr.getLoc(), diag::err_mode_not_primitive); 2980 else if (IntegerMode) { 2981 if (!OldTy->isIntegralOrEnumerationType()) 2982 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2983 } else if (ComplexMode) { 2984 if (!OldTy->isComplexType()) 2985 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2986 } else { 2987 if (!OldTy->isFloatingType()) 2988 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2989 } 2990 2991 // FIXME: Sync this with InitializePredefinedMacros; we need to match int8_t 2992 // and friends, at least with glibc. 2993 // FIXME: Make sure 32/64-bit integers don't get defined to types of the wrong 2994 // width on unusual platforms. 2995 // FIXME: Make sure floating-point mappings are accurate 2996 // FIXME: Support XF and TF types 2997 QualType NewTy; 2998 switch (DestWidth) { 2999 case 0: 3000 S.Diag(Attr.getLoc(), diag::err_unknown_machine_mode) << Name; 3001 return; 3002 default: 3003 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 3004 return; 3005 case 8: 3006 if (!IntegerMode) { 3007 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 3008 return; 3009 } 3010 if (OldTy->isSignedIntegerType()) 3011 NewTy = S.Context.SignedCharTy; 3012 else 3013 NewTy = S.Context.UnsignedCharTy; 3014 break; 3015 case 16: 3016 if (!IntegerMode) { 3017 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 3018 return; 3019 } 3020 if (OldTy->isSignedIntegerType()) 3021 NewTy = S.Context.ShortTy; 3022 else 3023 NewTy = S.Context.UnsignedShortTy; 3024 break; 3025 case 32: 3026 if (!IntegerMode) 3027 NewTy = S.Context.FloatTy; 3028 else if (OldTy->isSignedIntegerType()) 3029 NewTy = S.Context.IntTy; 3030 else 3031 NewTy = S.Context.UnsignedIntTy; 3032 break; 3033 case 64: 3034 if (!IntegerMode) 3035 NewTy = S.Context.DoubleTy; 3036 else if (OldTy->isSignedIntegerType()) 3037 if (S.Context.getTargetInfo().getLongWidth() == 64) 3038 NewTy = S.Context.LongTy; 3039 else 3040 NewTy = S.Context.LongLongTy; 3041 else 3042 if (S.Context.getTargetInfo().getLongWidth() == 64) 3043 NewTy = S.Context.UnsignedLongTy; 3044 else 3045 NewTy = S.Context.UnsignedLongLongTy; 3046 break; 3047 case 96: 3048 NewTy = S.Context.LongDoubleTy; 3049 break; 3050 case 128: 3051 if (!IntegerMode) { 3052 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 3053 return; 3054 } 3055 if (OldTy->isSignedIntegerType()) 3056 NewTy = S.Context.Int128Ty; 3057 else 3058 NewTy = S.Context.UnsignedInt128Ty; 3059 break; 3060 } 3061 3062 if (ComplexMode) { 3063 NewTy = S.Context.getComplexType(NewTy); 3064 } 3065 3066 // Install the new type. 3067 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) { 3068 // FIXME: preserve existing source info. 3069 TD->setTypeSourceInfo(S.Context.getTrivialTypeSourceInfo(NewTy)); 3070 } else 3071 cast<ValueDecl>(D)->setType(NewTy); 3072} 3073 3074static void handleNoDebugAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3075 // check the attribute arguments. 3076 if (!checkAttributeNumArgs(S, Attr, 0)) 3077 return; 3078 3079 if (!isFunctionOrMethod(D)) { 3080 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3081 << Attr.getName() << ExpectedFunction; 3082 return; 3083 } 3084 3085 D->addAttr(::new (S.Context) NoDebugAttr(Attr.getRange(), S.Context)); 3086} 3087 3088static void handleNoInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3089 // check the attribute arguments. 3090 if (!checkAttributeNumArgs(S, Attr, 0)) 3091 return; 3092 3093 3094 if (!isa<FunctionDecl>(D)) { 3095 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3096 << Attr.getName() << ExpectedFunction; 3097 return; 3098 } 3099 3100 D->addAttr(::new (S.Context) NoInlineAttr(Attr.getRange(), S.Context)); 3101} 3102 3103static void handleNoInstrumentFunctionAttr(Sema &S, Decl *D, 3104 const AttributeList &Attr) { 3105 // check the attribute arguments. 3106 if (!checkAttributeNumArgs(S, Attr, 0)) 3107 return; 3108 3109 3110 if (!isa<FunctionDecl>(D)) { 3111 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3112 << Attr.getName() << ExpectedFunction; 3113 return; 3114 } 3115 3116 D->addAttr(::new (S.Context) NoInstrumentFunctionAttr(Attr.getRange(), 3117 S.Context)); 3118} 3119 3120static void handleConstantAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3121 if (S.LangOpts.CUDA) { 3122 // check the attribute arguments. 3123 if (Attr.hasParameterOrArguments()) { 3124 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 3125 return; 3126 } 3127 3128 if (!isa<VarDecl>(D)) { 3129 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3130 << Attr.getName() << ExpectedVariable; 3131 return; 3132 } 3133 3134 D->addAttr(::new (S.Context) CUDAConstantAttr(Attr.getRange(), S.Context)); 3135 } else { 3136 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "constant"; 3137 } 3138} 3139 3140static void handleDeviceAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3141 if (S.LangOpts.CUDA) { 3142 // check the attribute arguments. 3143 if (Attr.getNumArgs() != 0) { 3144 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 3145 return; 3146 } 3147 3148 if (!isa<FunctionDecl>(D) && !isa<VarDecl>(D)) { 3149 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3150 << Attr.getName() << ExpectedVariableOrFunction; 3151 return; 3152 } 3153 3154 D->addAttr(::new (S.Context) CUDADeviceAttr(Attr.getRange(), S.Context)); 3155 } else { 3156 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "device"; 3157 } 3158} 3159 3160static void handleGlobalAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3161 if (S.LangOpts.CUDA) { 3162 // check the attribute arguments. 3163 if (!checkAttributeNumArgs(S, Attr, 0)) 3164 return; 3165 3166 if (!isa<FunctionDecl>(D)) { 3167 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3168 << Attr.getName() << ExpectedFunction; 3169 return; 3170 } 3171 3172 FunctionDecl *FD = cast<FunctionDecl>(D); 3173 if (!FD->getResultType()->isVoidType()) { 3174 TypeLoc TL = FD->getTypeSourceInfo()->getTypeLoc().IgnoreParens(); 3175 if (FunctionTypeLoc* FTL = dyn_cast<FunctionTypeLoc>(&TL)) { 3176 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 3177 << FD->getType() 3178 << FixItHint::CreateReplacement(FTL->getResultLoc().getSourceRange(), 3179 "void"); 3180 } else { 3181 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 3182 << FD->getType(); 3183 } 3184 return; 3185 } 3186 3187 D->addAttr(::new (S.Context) CUDAGlobalAttr(Attr.getRange(), S.Context)); 3188 } else { 3189 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "global"; 3190 } 3191} 3192 3193static void handleHostAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3194 if (S.LangOpts.CUDA) { 3195 // check the attribute arguments. 3196 if (!checkAttributeNumArgs(S, Attr, 0)) 3197 return; 3198 3199 3200 if (!isa<FunctionDecl>(D)) { 3201 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3202 << Attr.getName() << ExpectedFunction; 3203 return; 3204 } 3205 3206 D->addAttr(::new (S.Context) CUDAHostAttr(Attr.getRange(), S.Context)); 3207 } else { 3208 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "host"; 3209 } 3210} 3211 3212static void handleSharedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3213 if (S.LangOpts.CUDA) { 3214 // check the attribute arguments. 3215 if (!checkAttributeNumArgs(S, Attr, 0)) 3216 return; 3217 3218 3219 if (!isa<VarDecl>(D)) { 3220 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3221 << Attr.getName() << ExpectedVariable; 3222 return; 3223 } 3224 3225 D->addAttr(::new (S.Context) CUDASharedAttr(Attr.getRange(), S.Context)); 3226 } else { 3227 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "shared"; 3228 } 3229} 3230 3231static void handleGNUInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3232 // check the attribute arguments. 3233 if (!checkAttributeNumArgs(S, Attr, 0)) 3234 return; 3235 3236 FunctionDecl *Fn = dyn_cast<FunctionDecl>(D); 3237 if (Fn == 0) { 3238 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3239 << Attr.getName() << ExpectedFunction; 3240 return; 3241 } 3242 3243 if (!Fn->isInlineSpecified()) { 3244 S.Diag(Attr.getLoc(), diag::warn_gnu_inline_attribute_requires_inline); 3245 return; 3246 } 3247 3248 D->addAttr(::new (S.Context) GNUInlineAttr(Attr.getRange(), S.Context)); 3249} 3250 3251static void handleCallConvAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3252 if (hasDeclarator(D)) return; 3253 3254 // Diagnostic is emitted elsewhere: here we store the (valid) Attr 3255 // in the Decl node for syntactic reasoning, e.g., pretty-printing. 3256 CallingConv CC; 3257 if (S.CheckCallingConvAttr(Attr, CC)) 3258 return; 3259 3260 if (!isa<ObjCMethodDecl>(D)) { 3261 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3262 << Attr.getName() << ExpectedFunctionOrMethod; 3263 return; 3264 } 3265 3266 switch (Attr.getKind()) { 3267 case AttributeList::AT_fastcall: 3268 D->addAttr(::new (S.Context) FastCallAttr(Attr.getRange(), S.Context)); 3269 return; 3270 case AttributeList::AT_stdcall: 3271 D->addAttr(::new (S.Context) StdCallAttr(Attr.getRange(), S.Context)); 3272 return; 3273 case AttributeList::AT_thiscall: 3274 D->addAttr(::new (S.Context) ThisCallAttr(Attr.getRange(), S.Context)); 3275 return; 3276 case AttributeList::AT_cdecl: 3277 D->addAttr(::new (S.Context) CDeclAttr(Attr.getRange(), S.Context)); 3278 return; 3279 case AttributeList::AT_pascal: 3280 D->addAttr(::new (S.Context) PascalAttr(Attr.getRange(), S.Context)); 3281 return; 3282 case AttributeList::AT_pcs: { 3283 Expr *Arg = Attr.getArg(0); 3284 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 3285 if (!Str || !Str->isAscii()) { 3286 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 3287 << "pcs" << 1; 3288 Attr.setInvalid(); 3289 return; 3290 } 3291 3292 StringRef StrRef = Str->getString(); 3293 PcsAttr::PCSType PCS; 3294 if (StrRef == "aapcs") 3295 PCS = PcsAttr::AAPCS; 3296 else if (StrRef == "aapcs-vfp") 3297 PCS = PcsAttr::AAPCS_VFP; 3298 else { 3299 S.Diag(Attr.getLoc(), diag::err_invalid_pcs); 3300 Attr.setInvalid(); 3301 return; 3302 } 3303 3304 D->addAttr(::new (S.Context) PcsAttr(Attr.getRange(), S.Context, PCS)); 3305 } 3306 default: 3307 llvm_unreachable("unexpected attribute kind"); 3308 } 3309} 3310 3311static void handleOpenCLKernelAttr(Sema &S, Decl *D, const AttributeList &Attr){ 3312 assert(!Attr.isInvalid()); 3313 D->addAttr(::new (S.Context) OpenCLKernelAttr(Attr.getRange(), S.Context)); 3314} 3315 3316bool Sema::CheckCallingConvAttr(const AttributeList &attr, CallingConv &CC) { 3317 if (attr.isInvalid()) 3318 return true; 3319 3320 if ((attr.getNumArgs() != 0 && 3321 !(attr.getKind() == AttributeList::AT_pcs && attr.getNumArgs() == 1)) || 3322 attr.getParameterName()) { 3323 Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 3324 attr.setInvalid(); 3325 return true; 3326 } 3327 3328 // TODO: diagnose uses of these conventions on the wrong target. Or, better 3329 // move to TargetAttributesSema one day. 3330 switch (attr.getKind()) { 3331 case AttributeList::AT_cdecl: CC = CC_C; break; 3332 case AttributeList::AT_fastcall: CC = CC_X86FastCall; break; 3333 case AttributeList::AT_stdcall: CC = CC_X86StdCall; break; 3334 case AttributeList::AT_thiscall: CC = CC_X86ThisCall; break; 3335 case AttributeList::AT_pascal: CC = CC_X86Pascal; break; 3336 case AttributeList::AT_pcs: { 3337 Expr *Arg = attr.getArg(0); 3338 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 3339 if (!Str || !Str->isAscii()) { 3340 Diag(attr.getLoc(), diag::err_attribute_argument_n_not_string) 3341 << "pcs" << 1; 3342 attr.setInvalid(); 3343 return true; 3344 } 3345 3346 StringRef StrRef = Str->getString(); 3347 if (StrRef == "aapcs") { 3348 CC = CC_AAPCS; 3349 break; 3350 } else if (StrRef == "aapcs-vfp") { 3351 CC = CC_AAPCS_VFP; 3352 break; 3353 } 3354 // FALLS THROUGH 3355 } 3356 default: llvm_unreachable("unexpected attribute kind"); 3357 } 3358 3359 return false; 3360} 3361 3362static void handleRegparmAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3363 if (hasDeclarator(D)) return; 3364 3365 unsigned numParams; 3366 if (S.CheckRegparmAttr(Attr, numParams)) 3367 return; 3368 3369 if (!isa<ObjCMethodDecl>(D)) { 3370 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3371 << Attr.getName() << ExpectedFunctionOrMethod; 3372 return; 3373 } 3374 3375 D->addAttr(::new (S.Context) RegparmAttr(Attr.getRange(), S.Context, numParams)); 3376} 3377 3378/// Checks a regparm attribute, returning true if it is ill-formed and 3379/// otherwise setting numParams to the appropriate value. 3380bool Sema::CheckRegparmAttr(const AttributeList &Attr, unsigned &numParams) { 3381 if (Attr.isInvalid()) 3382 return true; 3383 3384 if (Attr.getNumArgs() != 1) { 3385 Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 3386 Attr.setInvalid(); 3387 return true; 3388 } 3389 3390 Expr *NumParamsExpr = Attr.getArg(0); 3391 llvm::APSInt NumParams(32); 3392 if (NumParamsExpr->isTypeDependent() || NumParamsExpr->isValueDependent() || 3393 !NumParamsExpr->isIntegerConstantExpr(NumParams, Context)) { 3394 Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 3395 << "regparm" << NumParamsExpr->getSourceRange(); 3396 Attr.setInvalid(); 3397 return true; 3398 } 3399 3400 if (Context.getTargetInfo().getRegParmMax() == 0) { 3401 Diag(Attr.getLoc(), diag::err_attribute_regparm_wrong_platform) 3402 << NumParamsExpr->getSourceRange(); 3403 Attr.setInvalid(); 3404 return true; 3405 } 3406 3407 numParams = NumParams.getZExtValue(); 3408 if (numParams > Context.getTargetInfo().getRegParmMax()) { 3409 Diag(Attr.getLoc(), diag::err_attribute_regparm_invalid_number) 3410 << Context.getTargetInfo().getRegParmMax() << NumParamsExpr->getSourceRange(); 3411 Attr.setInvalid(); 3412 return true; 3413 } 3414 3415 return false; 3416} 3417 3418static void handleLaunchBoundsAttr(Sema &S, Decl *D, const AttributeList &Attr){ 3419 if (S.LangOpts.CUDA) { 3420 // check the attribute arguments. 3421 if (Attr.getNumArgs() != 1 && Attr.getNumArgs() != 2) { 3422 // FIXME: 0 is not okay. 3423 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 3424 return; 3425 } 3426 3427 if (!isFunctionOrMethod(D)) { 3428 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3429 << Attr.getName() << ExpectedFunctionOrMethod; 3430 return; 3431 } 3432 3433 Expr *MaxThreadsExpr = Attr.getArg(0); 3434 llvm::APSInt MaxThreads(32); 3435 if (MaxThreadsExpr->isTypeDependent() || 3436 MaxThreadsExpr->isValueDependent() || 3437 !MaxThreadsExpr->isIntegerConstantExpr(MaxThreads, S.Context)) { 3438 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 3439 << "launch_bounds" << 1 << MaxThreadsExpr->getSourceRange(); 3440 return; 3441 } 3442 3443 llvm::APSInt MinBlocks(32); 3444 if (Attr.getNumArgs() > 1) { 3445 Expr *MinBlocksExpr = Attr.getArg(1); 3446 if (MinBlocksExpr->isTypeDependent() || 3447 MinBlocksExpr->isValueDependent() || 3448 !MinBlocksExpr->isIntegerConstantExpr(MinBlocks, S.Context)) { 3449 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 3450 << "launch_bounds" << 2 << MinBlocksExpr->getSourceRange(); 3451 return; 3452 } 3453 } 3454 3455 D->addAttr(::new (S.Context) CUDALaunchBoundsAttr(Attr.getRange(), S.Context, 3456 MaxThreads.getZExtValue(), 3457 MinBlocks.getZExtValue())); 3458 } else { 3459 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "launch_bounds"; 3460 } 3461} 3462 3463//===----------------------------------------------------------------------===// 3464// Checker-specific attribute handlers. 3465//===----------------------------------------------------------------------===// 3466 3467static bool isValidSubjectOfNSAttribute(Sema &S, QualType type) { 3468 return type->isDependentType() || 3469 type->isObjCObjectPointerType() || 3470 S.Context.isObjCNSObjectType(type); 3471} 3472static bool isValidSubjectOfCFAttribute(Sema &S, QualType type) { 3473 return type->isDependentType() || 3474 type->isPointerType() || 3475 isValidSubjectOfNSAttribute(S, type); 3476} 3477 3478static void handleNSConsumedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3479 ParmVarDecl *param = dyn_cast<ParmVarDecl>(D); 3480 if (!param) { 3481 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 3482 << Attr.getRange() << Attr.getName() << ExpectedParameter; 3483 return; 3484 } 3485 3486 bool typeOK, cf; 3487 if (Attr.getKind() == AttributeList::AT_ns_consumed) { 3488 typeOK = isValidSubjectOfNSAttribute(S, param->getType()); 3489 cf = false; 3490 } else { 3491 typeOK = isValidSubjectOfCFAttribute(S, param->getType()); 3492 cf = true; 3493 } 3494 3495 if (!typeOK) { 3496 S.Diag(D->getLocStart(), diag::warn_ns_attribute_wrong_parameter_type) 3497 << Attr.getRange() << Attr.getName() << cf; 3498 return; 3499 } 3500 3501 if (cf) 3502 param->addAttr(::new (S.Context) CFConsumedAttr(Attr.getRange(), S.Context)); 3503 else 3504 param->addAttr(::new (S.Context) NSConsumedAttr(Attr.getRange(), S.Context)); 3505} 3506 3507static void handleNSConsumesSelfAttr(Sema &S, Decl *D, 3508 const AttributeList &Attr) { 3509 if (!isa<ObjCMethodDecl>(D)) { 3510 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 3511 << Attr.getRange() << Attr.getName() << ExpectedMethod; 3512 return; 3513 } 3514 3515 D->addAttr(::new (S.Context) NSConsumesSelfAttr(Attr.getRange(), S.Context)); 3516} 3517 3518static void handleNSReturnsRetainedAttr(Sema &S, Decl *D, 3519 const AttributeList &Attr) { 3520 3521 QualType returnType; 3522 3523 if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 3524 returnType = MD->getResultType(); 3525 else if (ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(D)) 3526 returnType = PD->getType(); 3527 else if (S.getLangOpts().ObjCAutoRefCount && hasDeclarator(D) && 3528 (Attr.getKind() == AttributeList::AT_ns_returns_retained)) 3529 return; // ignore: was handled as a type attribute 3530 else if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) 3531 returnType = FD->getResultType(); 3532 else { 3533 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 3534 << Attr.getRange() << Attr.getName() 3535 << ExpectedFunctionOrMethod; 3536 return; 3537 } 3538 3539 bool typeOK; 3540 bool cf; 3541 switch (Attr.getKind()) { 3542 default: llvm_unreachable("invalid ownership attribute"); 3543 case AttributeList::AT_ns_returns_autoreleased: 3544 case AttributeList::AT_ns_returns_retained: 3545 case AttributeList::AT_ns_returns_not_retained: 3546 typeOK = isValidSubjectOfNSAttribute(S, returnType); 3547 cf = false; 3548 break; 3549 3550 case AttributeList::AT_cf_returns_retained: 3551 case AttributeList::AT_cf_returns_not_retained: 3552 typeOK = isValidSubjectOfCFAttribute(S, returnType); 3553 cf = true; 3554 break; 3555 } 3556 3557 if (!typeOK) { 3558 S.Diag(D->getLocStart(), diag::warn_ns_attribute_wrong_return_type) 3559 << Attr.getRange() << Attr.getName() << isa<ObjCMethodDecl>(D) << cf; 3560 return; 3561 } 3562 3563 switch (Attr.getKind()) { 3564 default: 3565 llvm_unreachable("invalid ownership attribute"); 3566 case AttributeList::AT_ns_returns_autoreleased: 3567 D->addAttr(::new (S.Context) NSReturnsAutoreleasedAttr(Attr.getRange(), 3568 S.Context)); 3569 return; 3570 case AttributeList::AT_cf_returns_not_retained: 3571 D->addAttr(::new (S.Context) CFReturnsNotRetainedAttr(Attr.getRange(), 3572 S.Context)); 3573 return; 3574 case AttributeList::AT_ns_returns_not_retained: 3575 D->addAttr(::new (S.Context) NSReturnsNotRetainedAttr(Attr.getRange(), 3576 S.Context)); 3577 return; 3578 case AttributeList::AT_cf_returns_retained: 3579 D->addAttr(::new (S.Context) CFReturnsRetainedAttr(Attr.getRange(), 3580 S.Context)); 3581 return; 3582 case AttributeList::AT_ns_returns_retained: 3583 D->addAttr(::new (S.Context) NSReturnsRetainedAttr(Attr.getRange(), 3584 S.Context)); 3585 return; 3586 }; 3587} 3588 3589static void handleObjCReturnsInnerPointerAttr(Sema &S, Decl *D, 3590 const AttributeList &attr) { 3591 SourceLocation loc = attr.getLoc(); 3592 3593 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(D); 3594 3595 if (!method) { 3596 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3597 << SourceRange(loc, loc) << attr.getName() << ExpectedMethod; 3598 return; 3599 } 3600 3601 // Check that the method returns a normal pointer. 3602 QualType resultType = method->getResultType(); 3603 3604 if (!resultType->isReferenceType() && 3605 (!resultType->isPointerType() || resultType->isObjCRetainableType())) { 3606 S.Diag(method->getLocStart(), diag::warn_ns_attribute_wrong_return_type) 3607 << SourceRange(loc) 3608 << attr.getName() << /*method*/ 1 << /*non-retainable pointer*/ 2; 3609 3610 // Drop the attribute. 3611 return; 3612 } 3613 3614 method->addAttr( 3615 ::new (S.Context) ObjCReturnsInnerPointerAttr(attr.getRange(), S.Context)); 3616} 3617 3618/// Handle cf_audited_transfer and cf_unknown_transfer. 3619static void handleCFTransferAttr(Sema &S, Decl *D, const AttributeList &A) { 3620 if (!isa<FunctionDecl>(D)) { 3621 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3622 << A.getRange() << A.getName() << ExpectedFunction; 3623 return; 3624 } 3625 3626 bool IsAudited = (A.getKind() == AttributeList::AT_cf_audited_transfer); 3627 3628 // Check whether there's a conflicting attribute already present. 3629 Attr *Existing; 3630 if (IsAudited) { 3631 Existing = D->getAttr<CFUnknownTransferAttr>(); 3632 } else { 3633 Existing = D->getAttr<CFAuditedTransferAttr>(); 3634 } 3635 if (Existing) { 3636 S.Diag(D->getLocStart(), diag::err_attributes_are_not_compatible) 3637 << A.getName() 3638 << (IsAudited ? "cf_unknown_transfer" : "cf_audited_transfer") 3639 << A.getRange() << Existing->getRange(); 3640 return; 3641 } 3642 3643 // All clear; add the attribute. 3644 if (IsAudited) { 3645 D->addAttr( 3646 ::new (S.Context) CFAuditedTransferAttr(A.getRange(), S.Context)); 3647 } else { 3648 D->addAttr( 3649 ::new (S.Context) CFUnknownTransferAttr(A.getRange(), S.Context)); 3650 } 3651} 3652 3653static void handleNSBridgedAttr(Sema &S, Scope *Sc, Decl *D, 3654 const AttributeList &Attr) { 3655 RecordDecl *RD = dyn_cast<RecordDecl>(D); 3656 if (!RD || RD->isUnion()) { 3657 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3658 << Attr.getRange() << Attr.getName() << ExpectedStruct; 3659 } 3660 3661 IdentifierInfo *ParmName = Attr.getParameterName(); 3662 3663 // In Objective-C, verify that the type names an Objective-C type. 3664 // We don't want to check this outside of ObjC because people sometimes 3665 // do crazy C declarations of Objective-C types. 3666 if (ParmName && S.getLangOpts().ObjC1) { 3667 // Check for an existing type with this name. 3668 LookupResult R(S, DeclarationName(ParmName), Attr.getParameterLoc(), 3669 Sema::LookupOrdinaryName); 3670 if (S.LookupName(R, Sc)) { 3671 NamedDecl *Target = R.getFoundDecl(); 3672 if (Target && !isa<ObjCInterfaceDecl>(Target)) { 3673 S.Diag(D->getLocStart(), diag::err_ns_bridged_not_interface); 3674 S.Diag(Target->getLocStart(), diag::note_declared_at); 3675 } 3676 } 3677 } 3678 3679 D->addAttr(::new (S.Context) NSBridgedAttr(Attr.getRange(), S.Context, 3680 ParmName)); 3681} 3682 3683static void handleObjCOwnershipAttr(Sema &S, Decl *D, 3684 const AttributeList &Attr) { 3685 if (hasDeclarator(D)) return; 3686 3687 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3688 << Attr.getRange() << Attr.getName() << ExpectedVariable; 3689} 3690 3691static void handleObjCPreciseLifetimeAttr(Sema &S, Decl *D, 3692 const AttributeList &Attr) { 3693 if (!isa<VarDecl>(D) && !isa<FieldDecl>(D)) { 3694 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3695 << Attr.getRange() << Attr.getName() << ExpectedVariable; 3696 return; 3697 } 3698 3699 ValueDecl *vd = cast<ValueDecl>(D); 3700 QualType type = vd->getType(); 3701 3702 if (!type->isDependentType() && 3703 !type->isObjCLifetimeType()) { 3704 S.Diag(Attr.getLoc(), diag::err_objc_precise_lifetime_bad_type) 3705 << type; 3706 return; 3707 } 3708 3709 Qualifiers::ObjCLifetime lifetime = type.getObjCLifetime(); 3710 3711 // If we have no lifetime yet, check the lifetime we're presumably 3712 // going to infer. 3713 if (lifetime == Qualifiers::OCL_None && !type->isDependentType()) 3714 lifetime = type->getObjCARCImplicitLifetime(); 3715 3716 switch (lifetime) { 3717 case Qualifiers::OCL_None: 3718 assert(type->isDependentType() && 3719 "didn't infer lifetime for non-dependent type?"); 3720 break; 3721 3722 case Qualifiers::OCL_Weak: // meaningful 3723 case Qualifiers::OCL_Strong: // meaningful 3724 break; 3725 3726 case Qualifiers::OCL_ExplicitNone: 3727 case Qualifiers::OCL_Autoreleasing: 3728 S.Diag(Attr.getLoc(), diag::warn_objc_precise_lifetime_meaningless) 3729 << (lifetime == Qualifiers::OCL_Autoreleasing); 3730 break; 3731 } 3732 3733 D->addAttr(::new (S.Context) 3734 ObjCPreciseLifetimeAttr(Attr.getRange(), S.Context)); 3735} 3736 3737static bool isKnownDeclSpecAttr(const AttributeList &Attr) { 3738 switch (Attr.getKind()) { 3739 default: 3740 return false; 3741 case AttributeList::AT_dllimport: 3742 case AttributeList::AT_dllexport: 3743 case AttributeList::AT_uuid: 3744 case AttributeList::AT_deprecated: 3745 case AttributeList::AT_noreturn: 3746 case AttributeList::AT_nothrow: 3747 case AttributeList::AT_naked: 3748 case AttributeList::AT_noinline: 3749 return true; 3750 } 3751} 3752 3753//===----------------------------------------------------------------------===// 3754// Microsoft specific attribute handlers. 3755//===----------------------------------------------------------------------===// 3756 3757static void handleUuidAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3758 if (S.LangOpts.MicrosoftExt || S.LangOpts.Borland) { 3759 // check the attribute arguments. 3760 if (!checkAttributeNumArgs(S, Attr, 1)) 3761 return; 3762 3763 Expr *Arg = Attr.getArg(0); 3764 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 3765 if (!Str || !Str->isAscii()) { 3766 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 3767 << "uuid" << 1; 3768 return; 3769 } 3770 3771 StringRef StrRef = Str->getString(); 3772 3773 bool IsCurly = StrRef.size() > 1 && StrRef.front() == '{' && 3774 StrRef.back() == '}'; 3775 3776 // Validate GUID length. 3777 if (IsCurly && StrRef.size() != 38) { 3778 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3779 return; 3780 } 3781 if (!IsCurly && StrRef.size() != 36) { 3782 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3783 return; 3784 } 3785 3786 // GUID format is "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX" or 3787 // "{XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX}" 3788 StringRef::iterator I = StrRef.begin(); 3789 if (IsCurly) // Skip the optional '{' 3790 ++I; 3791 3792 for (int i = 0; i < 36; ++i) { 3793 if (i == 8 || i == 13 || i == 18 || i == 23) { 3794 if (*I != '-') { 3795 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3796 return; 3797 } 3798 } else if (!isxdigit(*I)) { 3799 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3800 return; 3801 } 3802 I++; 3803 } 3804 3805 D->addAttr(::new (S.Context) UuidAttr(Attr.getRange(), S.Context, 3806 Str->getString())); 3807 } else 3808 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "uuid"; 3809} 3810 3811//===----------------------------------------------------------------------===// 3812// Top Level Sema Entry Points 3813//===----------------------------------------------------------------------===// 3814 3815static void ProcessNonInheritableDeclAttr(Sema &S, Scope *scope, Decl *D, 3816 const AttributeList &Attr) { 3817 switch (Attr.getKind()) { 3818 case AttributeList::AT_device: handleDeviceAttr (S, D, Attr); break; 3819 case AttributeList::AT_host: handleHostAttr (S, D, Attr); break; 3820 case AttributeList::AT_overloadable:handleOverloadableAttr(S, D, Attr); break; 3821 default: 3822 break; 3823 } 3824} 3825 3826static void ProcessInheritableDeclAttr(Sema &S, Scope *scope, Decl *D, 3827 const AttributeList &Attr) { 3828 switch (Attr.getKind()) { 3829 case AttributeList::AT_ibaction: handleIBAction(S, D, Attr); break; 3830 case AttributeList::AT_iboutlet: handleIBOutlet(S, D, Attr); break; 3831 case AttributeList::AT_iboutletcollection: 3832 handleIBOutletCollection(S, D, Attr); break; 3833 case AttributeList::AT_address_space: 3834 case AttributeList::AT_opencl_image_access: 3835 case AttributeList::AT_objc_gc: 3836 case AttributeList::AT_vector_size: 3837 case AttributeList::AT_neon_vector_type: 3838 case AttributeList::AT_neon_polyvector_type: 3839 // Ignore these, these are type attributes, handled by 3840 // ProcessTypeAttributes. 3841 break; 3842 case AttributeList::AT_device: 3843 case AttributeList::AT_host: 3844 case AttributeList::AT_overloadable: 3845 // Ignore, this is a non-inheritable attribute, handled 3846 // by ProcessNonInheritableDeclAttr. 3847 break; 3848 case AttributeList::AT_alias: handleAliasAttr (S, D, Attr); break; 3849 case AttributeList::AT_aligned: handleAlignedAttr (S, D, Attr); break; 3850 case AttributeList::AT_always_inline: 3851 handleAlwaysInlineAttr (S, D, Attr); break; 3852 case AttributeList::AT_analyzer_noreturn: 3853 handleAnalyzerNoReturnAttr (S, D, Attr); break; 3854 case AttributeList::AT_annotate: handleAnnotateAttr (S, D, Attr); break; 3855 case AttributeList::AT_availability:handleAvailabilityAttr(S, D, Attr); break; 3856 case AttributeList::AT_carries_dependency: 3857 handleDependencyAttr (S, D, Attr); break; 3858 case AttributeList::AT_common: handleCommonAttr (S, D, Attr); break; 3859 case AttributeList::AT_constant: handleConstantAttr (S, D, Attr); break; 3860 case AttributeList::AT_constructor: handleConstructorAttr (S, D, Attr); break; 3861 case AttributeList::AT_deprecated: handleDeprecatedAttr (S, D, Attr); break; 3862 case AttributeList::AT_destructor: handleDestructorAttr (S, D, Attr); break; 3863 case AttributeList::AT_ext_vector_type: 3864 handleExtVectorTypeAttr(S, scope, D, Attr); 3865 break; 3866 case AttributeList::AT_format: handleFormatAttr (S, D, Attr); break; 3867 case AttributeList::AT_format_arg: handleFormatArgAttr (S, D, Attr); break; 3868 case AttributeList::AT_global: handleGlobalAttr (S, D, Attr); break; 3869 case AttributeList::AT_gnu_inline: handleGNUInlineAttr (S, D, Attr); break; 3870 case AttributeList::AT_launch_bounds: 3871 handleLaunchBoundsAttr(S, D, Attr); 3872 break; 3873 case AttributeList::AT_mode: handleModeAttr (S, D, Attr); break; 3874 case AttributeList::AT_malloc: handleMallocAttr (S, D, Attr); break; 3875 case AttributeList::AT_may_alias: handleMayAliasAttr (S, D, Attr); break; 3876 case AttributeList::AT_nocommon: handleNoCommonAttr (S, D, Attr); break; 3877 case AttributeList::AT_nonnull: handleNonNullAttr (S, D, Attr); break; 3878 case AttributeList::AT_ownership_returns: 3879 case AttributeList::AT_ownership_takes: 3880 case AttributeList::AT_ownership_holds: 3881 handleOwnershipAttr (S, D, Attr); break; 3882 case AttributeList::AT_cold: handleColdAttr (S, D, Attr); break; 3883 case AttributeList::AT_hot: handleHotAttr (S, D, Attr); break; 3884 case AttributeList::AT_naked: handleNakedAttr (S, D, Attr); break; 3885 case AttributeList::AT_noreturn: handleNoReturnAttr (S, D, Attr); break; 3886 case AttributeList::AT_nothrow: handleNothrowAttr (S, D, Attr); break; 3887 case AttributeList::AT_shared: handleSharedAttr (S, D, Attr); break; 3888 case AttributeList::AT_vecreturn: handleVecReturnAttr (S, D, Attr); break; 3889 3890 case AttributeList::AT_objc_ownership: 3891 handleObjCOwnershipAttr(S, D, Attr); break; 3892 case AttributeList::AT_objc_precise_lifetime: 3893 handleObjCPreciseLifetimeAttr(S, D, Attr); break; 3894 3895 case AttributeList::AT_objc_returns_inner_pointer: 3896 handleObjCReturnsInnerPointerAttr(S, D, Attr); break; 3897 3898 case AttributeList::AT_ns_bridged: 3899 handleNSBridgedAttr(S, scope, D, Attr); break; 3900 3901 case AttributeList::AT_cf_audited_transfer: 3902 case AttributeList::AT_cf_unknown_transfer: 3903 handleCFTransferAttr(S, D, Attr); break; 3904 3905 // Checker-specific. 3906 case AttributeList::AT_cf_consumed: 3907 case AttributeList::AT_ns_consumed: handleNSConsumedAttr (S, D, Attr); break; 3908 case AttributeList::AT_ns_consumes_self: 3909 handleNSConsumesSelfAttr(S, D, Attr); break; 3910 3911 case AttributeList::AT_ns_returns_autoreleased: 3912 case AttributeList::AT_ns_returns_not_retained: 3913 case AttributeList::AT_cf_returns_not_retained: 3914 case AttributeList::AT_ns_returns_retained: 3915 case AttributeList::AT_cf_returns_retained: 3916 handleNSReturnsRetainedAttr(S, D, Attr); break; 3917 3918 case AttributeList::AT_reqd_work_group_size: 3919 handleReqdWorkGroupSize(S, D, Attr); break; 3920 3921 case AttributeList::AT_init_priority: 3922 handleInitPriorityAttr(S, D, Attr); break; 3923 3924 case AttributeList::AT_packed: handlePackedAttr (S, D, Attr); break; 3925 case AttributeList::AT_ms_struct: handleMsStructAttr (S, D, Attr); break; 3926 case AttributeList::AT_section: handleSectionAttr (S, D, Attr); break; 3927 case AttributeList::AT_unavailable: handleUnavailableAttr (S, D, Attr); break; 3928 case AttributeList::AT_objc_arc_weak_reference_unavailable: 3929 handleArcWeakrefUnavailableAttr (S, D, Attr); 3930 break; 3931 case AttributeList::AT_objc_root_class: 3932 handleObjCRootClassAttr(S, D, Attr); 3933 break; 3934 case AttributeList::AT_objc_requires_property_definitions: 3935 handleObjCRequiresPropertyDefsAttr (S, D, Attr); 3936 break; 3937 case AttributeList::AT_unused: handleUnusedAttr (S, D, Attr); break; 3938 case AttributeList::AT_returns_twice: 3939 handleReturnsTwiceAttr(S, D, Attr); 3940 break; 3941 case AttributeList::AT_used: handleUsedAttr (S, D, Attr); break; 3942 case AttributeList::AT_visibility: handleVisibilityAttr (S, D, Attr); break; 3943 case AttributeList::AT_warn_unused_result: handleWarnUnusedResult(S, D, Attr); 3944 break; 3945 case AttributeList::AT_weak: handleWeakAttr (S, D, Attr); break; 3946 case AttributeList::AT_weakref: handleWeakRefAttr (S, D, Attr); break; 3947 case AttributeList::AT_weak_import: handleWeakImportAttr (S, D, Attr); break; 3948 case AttributeList::AT_transparent_union: 3949 handleTransparentUnionAttr(S, D, Attr); 3950 break; 3951 case AttributeList::AT_objc_exception: 3952 handleObjCExceptionAttr(S, D, Attr); 3953 break; 3954 case AttributeList::AT_objc_method_family: 3955 handleObjCMethodFamilyAttr(S, D, Attr); 3956 break; 3957 case AttributeList::AT_NSObject: handleObjCNSObject (S, D, Attr); break; 3958 case AttributeList::AT_blocks: handleBlocksAttr (S, D, Attr); break; 3959 case AttributeList::AT_sentinel: handleSentinelAttr (S, D, Attr); break; 3960 case AttributeList::AT_const: handleConstAttr (S, D, Attr); break; 3961 case AttributeList::AT_pure: handlePureAttr (S, D, Attr); break; 3962 case AttributeList::AT_cleanup: handleCleanupAttr (S, D, Attr); break; 3963 case AttributeList::AT_nodebug: handleNoDebugAttr (S, D, Attr); break; 3964 case AttributeList::AT_noinline: handleNoInlineAttr (S, D, Attr); break; 3965 case AttributeList::AT_regparm: handleRegparmAttr (S, D, Attr); break; 3966 case AttributeList::IgnoredAttribute: 3967 // Just ignore 3968 break; 3969 case AttributeList::AT_no_instrument_function: // Interacts with -pg. 3970 handleNoInstrumentFunctionAttr(S, D, Attr); 3971 break; 3972 case AttributeList::AT_stdcall: 3973 case AttributeList::AT_cdecl: 3974 case AttributeList::AT_fastcall: 3975 case AttributeList::AT_thiscall: 3976 case AttributeList::AT_pascal: 3977 case AttributeList::AT_pcs: 3978 handleCallConvAttr(S, D, Attr); 3979 break; 3980 case AttributeList::AT_opencl_kernel_function: 3981 handleOpenCLKernelAttr(S, D, Attr); 3982 break; 3983 case AttributeList::AT_uuid: 3984 handleUuidAttr(S, D, Attr); 3985 break; 3986 3987 // Thread safety attributes: 3988 case AttributeList::AT_guarded_var: 3989 handleGuardedVarAttr(S, D, Attr); 3990 break; 3991 case AttributeList::AT_pt_guarded_var: 3992 handleGuardedVarAttr(S, D, Attr, /*pointer = */true); 3993 break; 3994 case AttributeList::AT_scoped_lockable: 3995 handleLockableAttr(S, D, Attr, /*scoped = */true); 3996 break; 3997 case AttributeList::AT_no_address_safety_analysis: 3998 handleNoAddressSafetyAttr(S, D, Attr); 3999 break; 4000 case AttributeList::AT_no_thread_safety_analysis: 4001 handleNoThreadSafetyAttr(S, D, Attr); 4002 break; 4003 case AttributeList::AT_lockable: 4004 handleLockableAttr(S, D, Attr); 4005 break; 4006 case AttributeList::AT_guarded_by: 4007 handleGuardedByAttr(S, D, Attr); 4008 break; 4009 case AttributeList::AT_pt_guarded_by: 4010 handleGuardedByAttr(S, D, Attr, /*pointer = */true); 4011 break; 4012 case AttributeList::AT_exclusive_lock_function: 4013 handleLockFunAttr(S, D, Attr, /*exclusive = */true); 4014 break; 4015 case AttributeList::AT_exclusive_locks_required: 4016 handleLocksRequiredAttr(S, D, Attr, /*exclusive = */true); 4017 break; 4018 case AttributeList::AT_exclusive_trylock_function: 4019 handleTrylockFunAttr(S, D, Attr, /*exclusive = */true); 4020 break; 4021 case AttributeList::AT_lock_returned: 4022 handleLockReturnedAttr(S, D, Attr); 4023 break; 4024 case AttributeList::AT_locks_excluded: 4025 handleLocksExcludedAttr(S, D, Attr); 4026 break; 4027 case AttributeList::AT_shared_lock_function: 4028 handleLockFunAttr(S, D, Attr); 4029 break; 4030 case AttributeList::AT_shared_locks_required: 4031 handleLocksRequiredAttr(S, D, Attr); 4032 break; 4033 case AttributeList::AT_shared_trylock_function: 4034 handleTrylockFunAttr(S, D, Attr); 4035 break; 4036 case AttributeList::AT_unlock_function: 4037 handleUnlockFunAttr(S, D, Attr); 4038 break; 4039 case AttributeList::AT_acquired_before: 4040 handleAcquireOrderAttr(S, D, Attr, /*before = */true); 4041 break; 4042 case AttributeList::AT_acquired_after: 4043 handleAcquireOrderAttr(S, D, Attr, /*before = */false); 4044 break; 4045 4046 default: 4047 // Ask target about the attribute. 4048 const TargetAttributesSema &TargetAttrs = S.getTargetAttributesSema(); 4049 if (!TargetAttrs.ProcessDeclAttribute(scope, D, Attr, S)) 4050 S.Diag(Attr.getLoc(), diag::warn_unknown_attribute_ignored) 4051 << Attr.getName(); 4052 break; 4053 } 4054} 4055 4056/// ProcessDeclAttribute - Apply the specific attribute to the specified decl if 4057/// the attribute applies to decls. If the attribute is a type attribute, just 4058/// silently ignore it if a GNU attribute. FIXME: Applying a C++0x attribute to 4059/// the wrong thing is illegal (C++0x [dcl.attr.grammar]/4). 4060static void ProcessDeclAttribute(Sema &S, Scope *scope, Decl *D, 4061 const AttributeList &Attr, 4062 bool NonInheritable, bool Inheritable) { 4063 if (Attr.isInvalid()) 4064 return; 4065 4066 if (Attr.isDeclspecAttribute() && !isKnownDeclSpecAttr(Attr)) 4067 // FIXME: Try to deal with other __declspec attributes! 4068 return; 4069 4070 if (NonInheritable) 4071 ProcessNonInheritableDeclAttr(S, scope, D, Attr); 4072 4073 if (Inheritable) 4074 ProcessInheritableDeclAttr(S, scope, D, Attr); 4075} 4076 4077/// ProcessDeclAttributeList - Apply all the decl attributes in the specified 4078/// attribute list to the specified decl, ignoring any type attributes. 4079void Sema::ProcessDeclAttributeList(Scope *S, Decl *D, 4080 const AttributeList *AttrList, 4081 bool NonInheritable, bool Inheritable) { 4082 for (const AttributeList* l = AttrList; l; l = l->getNext()) { 4083 ProcessDeclAttribute(*this, S, D, *l, NonInheritable, Inheritable); 4084 } 4085 4086 // GCC accepts 4087 // static int a9 __attribute__((weakref)); 4088 // but that looks really pointless. We reject it. 4089 if (Inheritable && D->hasAttr<WeakRefAttr>() && !D->hasAttr<AliasAttr>()) { 4090 Diag(AttrList->getLoc(), diag::err_attribute_weakref_without_alias) << 4091 dyn_cast<NamedDecl>(D)->getNameAsString(); 4092 return; 4093 } 4094} 4095 4096// Annotation attributes are the only attributes allowed after an access 4097// specifier. 4098bool Sema::ProcessAccessDeclAttributeList(AccessSpecDecl *ASDecl, 4099 const AttributeList *AttrList) { 4100 for (const AttributeList* l = AttrList; l; l = l->getNext()) { 4101 if (l->getKind() == AttributeList::AT_annotate) { 4102 handleAnnotateAttr(*this, ASDecl, *l); 4103 } else { 4104 Diag(l->getLoc(), diag::err_only_annotate_after_access_spec); 4105 return true; 4106 } 4107 } 4108 4109 return false; 4110} 4111 4112/// checkUnusedDeclAttributes - Check a list of attributes to see if it 4113/// contains any decl attributes that we should warn about. 4114static void checkUnusedDeclAttributes(Sema &S, const AttributeList *A) { 4115 for ( ; A; A = A->getNext()) { 4116 // Only warn if the attribute is an unignored, non-type attribute. 4117 if (A->isUsedAsTypeAttr()) continue; 4118 if (A->getKind() == AttributeList::IgnoredAttribute) continue; 4119 4120 if (A->getKind() == AttributeList::UnknownAttribute) { 4121 S.Diag(A->getLoc(), diag::warn_unknown_attribute_ignored) 4122 << A->getName() << A->getRange(); 4123 } else { 4124 S.Diag(A->getLoc(), diag::warn_attribute_not_on_decl) 4125 << A->getName() << A->getRange(); 4126 } 4127 } 4128} 4129 4130/// checkUnusedDeclAttributes - Given a declarator which is not being 4131/// used to build a declaration, complain about any decl attributes 4132/// which might be lying around on it. 4133void Sema::checkUnusedDeclAttributes(Declarator &D) { 4134 ::checkUnusedDeclAttributes(*this, D.getDeclSpec().getAttributes().getList()); 4135 ::checkUnusedDeclAttributes(*this, D.getAttributes()); 4136 for (unsigned i = 0, e = D.getNumTypeObjects(); i != e; ++i) 4137 ::checkUnusedDeclAttributes(*this, D.getTypeObject(i).getAttrs()); 4138} 4139 4140/// DeclClonePragmaWeak - clone existing decl (maybe definition), 4141/// #pragma weak needs a non-definition decl and source may not have one 4142NamedDecl * Sema::DeclClonePragmaWeak(NamedDecl *ND, IdentifierInfo *II, 4143 SourceLocation Loc) { 4144 assert(isa<FunctionDecl>(ND) || isa<VarDecl>(ND)); 4145 NamedDecl *NewD = 0; 4146 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(ND)) { 4147 FunctionDecl *NewFD; 4148 // FIXME: Missing call to CheckFunctionDeclaration(). 4149 // FIXME: Mangling? 4150 // FIXME: Is the qualifier info correct? 4151 // FIXME: Is the DeclContext correct? 4152 NewFD = FunctionDecl::Create(FD->getASTContext(), FD->getDeclContext(), 4153 Loc, Loc, DeclarationName(II), 4154 FD->getType(), FD->getTypeSourceInfo(), 4155 SC_None, SC_None, 4156 false/*isInlineSpecified*/, 4157 FD->hasPrototype(), 4158 false/*isConstexprSpecified*/); 4159 NewD = NewFD; 4160 4161 if (FD->getQualifier()) 4162 NewFD->setQualifierInfo(FD->getQualifierLoc()); 4163 4164 // Fake up parameter variables; they are declared as if this were 4165 // a typedef. 4166 QualType FDTy = FD->getType(); 4167 if (const FunctionProtoType *FT = FDTy->getAs<FunctionProtoType>()) { 4168 SmallVector<ParmVarDecl*, 16> Params; 4169 for (FunctionProtoType::arg_type_iterator AI = FT->arg_type_begin(), 4170 AE = FT->arg_type_end(); AI != AE; ++AI) { 4171 ParmVarDecl *Param = BuildParmVarDeclForTypedef(NewFD, Loc, *AI); 4172 Param->setScopeInfo(0, Params.size()); 4173 Params.push_back(Param); 4174 } 4175 NewFD->setParams(Params); 4176 } 4177 } else if (VarDecl *VD = dyn_cast<VarDecl>(ND)) { 4178 NewD = VarDecl::Create(VD->getASTContext(), VD->getDeclContext(), 4179 VD->getInnerLocStart(), VD->getLocation(), II, 4180 VD->getType(), VD->getTypeSourceInfo(), 4181 VD->getStorageClass(), 4182 VD->getStorageClassAsWritten()); 4183 if (VD->getQualifier()) { 4184 VarDecl *NewVD = cast<VarDecl>(NewD); 4185 NewVD->setQualifierInfo(VD->getQualifierLoc()); 4186 } 4187 } 4188 return NewD; 4189} 4190 4191/// DeclApplyPragmaWeak - A declaration (maybe definition) needs #pragma weak 4192/// applied to it, possibly with an alias. 4193void Sema::DeclApplyPragmaWeak(Scope *S, NamedDecl *ND, WeakInfo &W) { 4194 if (W.getUsed()) return; // only do this once 4195 W.setUsed(true); 4196 if (W.getAlias()) { // clone decl, impersonate __attribute(weak,alias(...)) 4197 IdentifierInfo *NDId = ND->getIdentifier(); 4198 NamedDecl *NewD = DeclClonePragmaWeak(ND, W.getAlias(), W.getLocation()); 4199 NewD->addAttr(::new (Context) AliasAttr(W.getLocation(), Context, 4200 NDId->getName())); 4201 NewD->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 4202 WeakTopLevelDecl.push_back(NewD); 4203 // FIXME: "hideous" code from Sema::LazilyCreateBuiltin 4204 // to insert Decl at TU scope, sorry. 4205 DeclContext *SavedContext = CurContext; 4206 CurContext = Context.getTranslationUnitDecl(); 4207 PushOnScopeChains(NewD, S); 4208 CurContext = SavedContext; 4209 } else { // just add weak to existing 4210 ND->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 4211 } 4212} 4213 4214/// ProcessDeclAttributes - Given a declarator (PD) with attributes indicated in 4215/// it, apply them to D. This is a bit tricky because PD can have attributes 4216/// specified in many different places, and we need to find and apply them all. 4217void Sema::ProcessDeclAttributes(Scope *S, Decl *D, const Declarator &PD, 4218 bool NonInheritable, bool Inheritable) { 4219 // It's valid to "forward-declare" #pragma weak, in which case we 4220 // have to do this. 4221 if (Inheritable) { 4222 LoadExternalWeakUndeclaredIdentifiers(); 4223 if (!WeakUndeclaredIdentifiers.empty()) { 4224 if (NamedDecl *ND = dyn_cast<NamedDecl>(D)) { 4225 if (IdentifierInfo *Id = ND->getIdentifier()) { 4226 llvm::DenseMap<IdentifierInfo*,WeakInfo>::iterator I 4227 = WeakUndeclaredIdentifiers.find(Id); 4228 if (I != WeakUndeclaredIdentifiers.end() && ND->hasLinkage()) { 4229 WeakInfo W = I->second; 4230 DeclApplyPragmaWeak(S, ND, W); 4231 WeakUndeclaredIdentifiers[Id] = W; 4232 } 4233 } 4234 } 4235 } 4236 } 4237 4238 // Apply decl attributes from the DeclSpec if present. 4239 if (const AttributeList *Attrs = PD.getDeclSpec().getAttributes().getList()) 4240 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 4241 4242 // Walk the declarator structure, applying decl attributes that were in a type 4243 // position to the decl itself. This handles cases like: 4244 // int *__attr__(x)** D; 4245 // when X is a decl attribute. 4246 for (unsigned i = 0, e = PD.getNumTypeObjects(); i != e; ++i) 4247 if (const AttributeList *Attrs = PD.getTypeObject(i).getAttrs()) 4248 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 4249 4250 // Finally, apply any attributes on the decl itself. 4251 if (const AttributeList *Attrs = PD.getAttributes()) 4252 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 4253} 4254 4255/// Is the given declaration allowed to use a forbidden type? 4256static bool isForbiddenTypeAllowed(Sema &S, Decl *decl) { 4257 // Private ivars are always okay. Unfortunately, people don't 4258 // always properly make their ivars private, even in system headers. 4259 // Plus we need to make fields okay, too. 4260 // Function declarations in sys headers will be marked unavailable. 4261 if (!isa<FieldDecl>(decl) && !isa<ObjCPropertyDecl>(decl) && 4262 !isa<FunctionDecl>(decl)) 4263 return false; 4264 4265 // Require it to be declared in a system header. 4266 return S.Context.getSourceManager().isInSystemHeader(decl->getLocation()); 4267} 4268 4269/// Handle a delayed forbidden-type diagnostic. 4270static void handleDelayedForbiddenType(Sema &S, DelayedDiagnostic &diag, 4271 Decl *decl) { 4272 if (decl && isForbiddenTypeAllowed(S, decl)) { 4273 decl->addAttr(new (S.Context) UnavailableAttr(diag.Loc, S.Context, 4274 "this system declaration uses an unsupported type")); 4275 return; 4276 } 4277 if (S.getLangOpts().ObjCAutoRefCount) 4278 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(decl)) { 4279 // FIXME. we may want to supress diagnostics for all 4280 // kind of forbidden type messages on unavailable functions. 4281 if (FD->hasAttr<UnavailableAttr>() && 4282 diag.getForbiddenTypeDiagnostic() == 4283 diag::err_arc_array_param_no_ownership) { 4284 diag.Triggered = true; 4285 return; 4286 } 4287 } 4288 4289 S.Diag(diag.Loc, diag.getForbiddenTypeDiagnostic()) 4290 << diag.getForbiddenTypeOperand() << diag.getForbiddenTypeArgument(); 4291 diag.Triggered = true; 4292} 4293 4294void Sema::PopParsingDeclaration(ParsingDeclState state, Decl *decl) { 4295 assert(DelayedDiagnostics.getCurrentPool()); 4296 DelayedDiagnosticPool &poppedPool = *DelayedDiagnostics.getCurrentPool(); 4297 DelayedDiagnostics.popWithoutEmitting(state); 4298 4299 // When delaying diagnostics to run in the context of a parsed 4300 // declaration, we only want to actually emit anything if parsing 4301 // succeeds. 4302 if (!decl) return; 4303 4304 // We emit all the active diagnostics in this pool or any of its 4305 // parents. In general, we'll get one pool for the decl spec 4306 // and a child pool for each declarator; in a decl group like: 4307 // deprecated_typedef foo, *bar, baz(); 4308 // only the declarator pops will be passed decls. This is correct; 4309 // we really do need to consider delayed diagnostics from the decl spec 4310 // for each of the different declarations. 4311 const DelayedDiagnosticPool *pool = &poppedPool; 4312 do { 4313 for (DelayedDiagnosticPool::pool_iterator 4314 i = pool->pool_begin(), e = pool->pool_end(); i != e; ++i) { 4315 // This const_cast is a bit lame. Really, Triggered should be mutable. 4316 DelayedDiagnostic &diag = const_cast<DelayedDiagnostic&>(*i); 4317 if (diag.Triggered) 4318 continue; 4319 4320 switch (diag.Kind) { 4321 case DelayedDiagnostic::Deprecation: 4322 // Don't bother giving deprecation diagnostics if the decl is invalid. 4323 if (!decl->isInvalidDecl()) 4324 HandleDelayedDeprecationCheck(diag, decl); 4325 break; 4326 4327 case DelayedDiagnostic::Access: 4328 HandleDelayedAccessCheck(diag, decl); 4329 break; 4330 4331 case DelayedDiagnostic::ForbiddenType: 4332 handleDelayedForbiddenType(*this, diag, decl); 4333 break; 4334 } 4335 } 4336 } while ((pool = pool->getParent())); 4337} 4338 4339/// Given a set of delayed diagnostics, re-emit them as if they had 4340/// been delayed in the current context instead of in the given pool. 4341/// Essentially, this just moves them to the current pool. 4342void Sema::redelayDiagnostics(DelayedDiagnosticPool &pool) { 4343 DelayedDiagnosticPool *curPool = DelayedDiagnostics.getCurrentPool(); 4344 assert(curPool && "re-emitting in undelayed context not supported"); 4345 curPool->steal(pool); 4346} 4347 4348static bool isDeclDeprecated(Decl *D) { 4349 do { 4350 if (D->isDeprecated()) 4351 return true; 4352 // A category implicitly has the availability of the interface. 4353 if (const ObjCCategoryDecl *CatD = dyn_cast<ObjCCategoryDecl>(D)) 4354 return CatD->getClassInterface()->isDeprecated(); 4355 } while ((D = cast_or_null<Decl>(D->getDeclContext()))); 4356 return false; 4357} 4358 4359void Sema::HandleDelayedDeprecationCheck(DelayedDiagnostic &DD, 4360 Decl *Ctx) { 4361 if (isDeclDeprecated(Ctx)) 4362 return; 4363 4364 DD.Triggered = true; 4365 if (!DD.getDeprecationMessage().empty()) 4366 Diag(DD.Loc, diag::warn_deprecated_message) 4367 << DD.getDeprecationDecl()->getDeclName() 4368 << DD.getDeprecationMessage(); 4369 else if (DD.getUnknownObjCClass()) { 4370 Diag(DD.Loc, diag::warn_deprecated_fwdclass_message) 4371 << DD.getDeprecationDecl()->getDeclName(); 4372 Diag(DD.getUnknownObjCClass()->getLocation(), diag::note_forward_class); 4373 } 4374 else 4375 Diag(DD.Loc, diag::warn_deprecated) 4376 << DD.getDeprecationDecl()->getDeclName(); 4377} 4378 4379void Sema::EmitDeprecationWarning(NamedDecl *D, StringRef Message, 4380 SourceLocation Loc, 4381 const ObjCInterfaceDecl *UnknownObjCClass) { 4382 // Delay if we're currently parsing a declaration. 4383 if (DelayedDiagnostics.shouldDelayDiagnostics()) { 4384 DelayedDiagnostics.add(DelayedDiagnostic::makeDeprecation(Loc, D, 4385 UnknownObjCClass, 4386 Message)); 4387 return; 4388 } 4389 4390 // Otherwise, don't warn if our current context is deprecated. 4391 if (isDeclDeprecated(cast<Decl>(getCurLexicalContext()))) 4392 return; 4393 if (!Message.empty()) { 4394 Diag(Loc, diag::warn_deprecated_message) << D->getDeclName() 4395 << Message; 4396 Diag(D->getLocation(), 4397 isa<ObjCMethodDecl>(D) ? diag::note_method_declared_at 4398 : diag::note_previous_decl) << D->getDeclName(); 4399 } 4400 else { 4401 if (!UnknownObjCClass) 4402 Diag(Loc, diag::warn_deprecated) << D->getDeclName(); 4403 else { 4404 Diag(Loc, diag::warn_deprecated_fwdclass_message) << D->getDeclName(); 4405 Diag(UnknownObjCClass->getLocation(), diag::note_forward_class); 4406 } 4407 } 4408} 4409