SemaDeclAttr.cpp revision ab41fe914f63bb470dfa7e400876ada72f57a931
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 303bool checkBaseClassIsLockableCallback(const CXXBaseSpecifier *Specifier, 304 CXXBasePath &Path, void *UserData) { 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 handleNakedAttr(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 D->addAttr(::new (S.Context) NakedAttr(Attr.getRange(), S.Context)); 1309} 1310 1311static void handleAlwaysInlineAttr(Sema &S, Decl *D, 1312 const AttributeList &Attr) { 1313 // Check the attribute arguments. 1314 if (Attr.hasParameterOrArguments()) { 1315 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1316 return; 1317 } 1318 1319 if (!isa<FunctionDecl>(D)) { 1320 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1321 << Attr.getName() << ExpectedFunction; 1322 return; 1323 } 1324 1325 D->addAttr(::new (S.Context) AlwaysInlineAttr(Attr.getRange(), S.Context)); 1326} 1327 1328static void handleMallocAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1329 // Check the attribute arguments. 1330 if (Attr.hasParameterOrArguments()) { 1331 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1332 return; 1333 } 1334 1335 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) { 1336 QualType RetTy = FD->getResultType(); 1337 if (RetTy->isAnyPointerType() || RetTy->isBlockPointerType()) { 1338 D->addAttr(::new (S.Context) MallocAttr(Attr.getRange(), S.Context)); 1339 return; 1340 } 1341 } 1342 1343 S.Diag(Attr.getLoc(), diag::warn_attribute_malloc_pointer_only); 1344} 1345 1346static void handleMayAliasAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1347 // check the attribute arguments. 1348 if (!checkAttributeNumArgs(S, Attr, 0)) 1349 return; 1350 1351 D->addAttr(::new (S.Context) MayAliasAttr(Attr.getRange(), S.Context)); 1352} 1353 1354static void handleNoCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1355 assert(!Attr.isInvalid()); 1356 if (isa<VarDecl>(D)) 1357 D->addAttr(::new (S.Context) NoCommonAttr(Attr.getRange(), S.Context)); 1358 else 1359 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1360 << Attr.getName() << ExpectedVariable; 1361} 1362 1363static void handleCommonAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1364 assert(!Attr.isInvalid()); 1365 if (isa<VarDecl>(D)) 1366 D->addAttr(::new (S.Context) CommonAttr(Attr.getRange(), S.Context)); 1367 else 1368 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1369 << Attr.getName() << ExpectedVariable; 1370} 1371 1372static void handleNoReturnAttr(Sema &S, Decl *D, const AttributeList &attr) { 1373 if (hasDeclarator(D)) return; 1374 1375 if (S.CheckNoReturnAttr(attr)) return; 1376 1377 if (!isa<ObjCMethodDecl>(D)) { 1378 S.Diag(attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1379 << attr.getName() << ExpectedFunctionOrMethod; 1380 return; 1381 } 1382 1383 D->addAttr(::new (S.Context) NoReturnAttr(attr.getRange(), S.Context)); 1384} 1385 1386bool Sema::CheckNoReturnAttr(const AttributeList &attr) { 1387 if (attr.hasParameterOrArguments()) { 1388 Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1389 attr.setInvalid(); 1390 return true; 1391 } 1392 1393 return false; 1394} 1395 1396static void handleAnalyzerNoReturnAttr(Sema &S, Decl *D, 1397 const AttributeList &Attr) { 1398 1399 // The checking path for 'noreturn' and 'analyzer_noreturn' are different 1400 // because 'analyzer_noreturn' does not impact the type. 1401 1402 if(!checkAttributeNumArgs(S, Attr, 0)) 1403 return; 1404 1405 if (!isFunctionOrMethod(D) && !isa<BlockDecl>(D)) { 1406 ValueDecl *VD = dyn_cast<ValueDecl>(D); 1407 if (VD == 0 || (!VD->getType()->isBlockPointerType() 1408 && !VD->getType()->isFunctionPointerType())) { 1409 S.Diag(Attr.getLoc(), 1410 Attr.isCXX0XAttribute() ? diag::err_attribute_wrong_decl_type 1411 : diag::warn_attribute_wrong_decl_type) 1412 << Attr.getName() << ExpectedFunctionMethodOrBlock; 1413 return; 1414 } 1415 } 1416 1417 D->addAttr(::new (S.Context) AnalyzerNoReturnAttr(Attr.getRange(), S.Context)); 1418} 1419 1420// PS3 PPU-specific. 1421static void handleVecReturnAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1422/* 1423 Returning a Vector Class in Registers 1424 1425 According to the PPU ABI specifications, a class with a single member of 1426 vector type is returned in memory when used as the return value of a function. 1427 This results in inefficient code when implementing vector classes. To return 1428 the value in a single vector register, add the vecreturn attribute to the 1429 class definition. This attribute is also applicable to struct types. 1430 1431 Example: 1432 1433 struct Vector 1434 { 1435 __vector float xyzw; 1436 } __attribute__((vecreturn)); 1437 1438 Vector Add(Vector lhs, Vector rhs) 1439 { 1440 Vector result; 1441 result.xyzw = vec_add(lhs.xyzw, rhs.xyzw); 1442 return result; // This will be returned in a register 1443 } 1444*/ 1445 if (!isa<RecordDecl>(D)) { 1446 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1447 << Attr.getName() << ExpectedClass; 1448 return; 1449 } 1450 1451 if (D->getAttr<VecReturnAttr>()) { 1452 S.Diag(Attr.getLoc(), diag::err_repeat_attribute) << "vecreturn"; 1453 return; 1454 } 1455 1456 RecordDecl *record = cast<RecordDecl>(D); 1457 int count = 0; 1458 1459 if (!isa<CXXRecordDecl>(record)) { 1460 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 1461 return; 1462 } 1463 1464 if (!cast<CXXRecordDecl>(record)->isPOD()) { 1465 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_pod_record); 1466 return; 1467 } 1468 1469 for (RecordDecl::field_iterator iter = record->field_begin(); 1470 iter != record->field_end(); iter++) { 1471 if ((count == 1) || !iter->getType()->isVectorType()) { 1472 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 1473 return; 1474 } 1475 count++; 1476 } 1477 1478 D->addAttr(::new (S.Context) VecReturnAttr(Attr.getRange(), S.Context)); 1479} 1480 1481static void handleDependencyAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1482 if (!isFunctionOrMethod(D) && !isa<ParmVarDecl>(D)) { 1483 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1484 << Attr.getName() << ExpectedFunctionMethodOrParameter; 1485 return; 1486 } 1487 // FIXME: Actually store the attribute on the declaration 1488} 1489 1490static void handleUnusedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1491 // check the attribute arguments. 1492 if (Attr.hasParameterOrArguments()) { 1493 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1494 return; 1495 } 1496 1497 if (!isa<VarDecl>(D) && !isa<ObjCIvarDecl>(D) && !isFunctionOrMethod(D) && 1498 !isa<TypeDecl>(D) && !isa<LabelDecl>(D)) { 1499 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1500 << Attr.getName() << ExpectedVariableFunctionOrLabel; 1501 return; 1502 } 1503 1504 D->addAttr(::new (S.Context) UnusedAttr(Attr.getRange(), S.Context)); 1505} 1506 1507static void handleReturnsTwiceAttr(Sema &S, Decl *D, 1508 const AttributeList &Attr) { 1509 // check the attribute arguments. 1510 if (Attr.hasParameterOrArguments()) { 1511 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1512 return; 1513 } 1514 1515 if (!isa<FunctionDecl>(D)) { 1516 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1517 << Attr.getName() << ExpectedFunction; 1518 return; 1519 } 1520 1521 D->addAttr(::new (S.Context) ReturnsTwiceAttr(Attr.getRange(), S.Context)); 1522} 1523 1524static void handleUsedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1525 // check the attribute arguments. 1526 if (Attr.hasParameterOrArguments()) { 1527 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1528 return; 1529 } 1530 1531 if (const VarDecl *VD = dyn_cast<VarDecl>(D)) { 1532 if (VD->hasLocalStorage() || VD->hasExternalStorage()) { 1533 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "used"; 1534 return; 1535 } 1536 } else if (!isFunctionOrMethod(D)) { 1537 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1538 << Attr.getName() << ExpectedVariableOrFunction; 1539 return; 1540 } 1541 1542 D->addAttr(::new (S.Context) UsedAttr(Attr.getRange(), S.Context)); 1543} 1544 1545static void handleConstructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1546 // check the attribute arguments. 1547 if (Attr.getNumArgs() > 1) { 1548 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1549 return; 1550 } 1551 1552 int priority = 65535; // FIXME: Do not hardcode such constants. 1553 if (Attr.getNumArgs() > 0) { 1554 Expr *E = Attr.getArg(0); 1555 llvm::APSInt Idx(32); 1556 if (E->isTypeDependent() || E->isValueDependent() || 1557 !E->isIntegerConstantExpr(Idx, S.Context)) { 1558 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1559 << "constructor" << 1 << E->getSourceRange(); 1560 return; 1561 } 1562 priority = Idx.getZExtValue(); 1563 } 1564 1565 if (!isa<FunctionDecl>(D)) { 1566 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1567 << Attr.getName() << ExpectedFunction; 1568 return; 1569 } 1570 1571 D->addAttr(::new (S.Context) ConstructorAttr(Attr.getRange(), S.Context, 1572 priority)); 1573} 1574 1575static void handleDestructorAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1576 // check the attribute arguments. 1577 if (Attr.getNumArgs() > 1) { 1578 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1579 return; 1580 } 1581 1582 int priority = 65535; // FIXME: Do not hardcode such constants. 1583 if (Attr.getNumArgs() > 0) { 1584 Expr *E = Attr.getArg(0); 1585 llvm::APSInt Idx(32); 1586 if (E->isTypeDependent() || E->isValueDependent() || 1587 !E->isIntegerConstantExpr(Idx, S.Context)) { 1588 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1589 << "destructor" << 1 << E->getSourceRange(); 1590 return; 1591 } 1592 priority = Idx.getZExtValue(); 1593 } 1594 1595 if (!isa<FunctionDecl>(D)) { 1596 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1597 << Attr.getName() << ExpectedFunction; 1598 return; 1599 } 1600 1601 D->addAttr(::new (S.Context) DestructorAttr(Attr.getRange(), S.Context, 1602 priority)); 1603} 1604 1605static void handleDeprecatedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1606 unsigned NumArgs = Attr.getNumArgs(); 1607 if (NumArgs > 1) { 1608 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1609 return; 1610 } 1611 1612 // Handle the case where deprecated attribute has a text message. 1613 StringRef Str; 1614 if (NumArgs == 1) { 1615 StringLiteral *SE = dyn_cast<StringLiteral>(Attr.getArg(0)); 1616 if (!SE) { 1617 S.Diag(Attr.getArg(0)->getLocStart(), diag::err_attribute_not_string) 1618 << "deprecated"; 1619 return; 1620 } 1621 Str = SE->getString(); 1622 } 1623 1624 D->addAttr(::new (S.Context) DeprecatedAttr(Attr.getRange(), S.Context, Str)); 1625} 1626 1627static void handleUnavailableAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1628 unsigned NumArgs = Attr.getNumArgs(); 1629 if (NumArgs > 1) { 1630 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1631 return; 1632 } 1633 1634 // Handle the case where unavailable attribute has a text message. 1635 StringRef Str; 1636 if (NumArgs == 1) { 1637 StringLiteral *SE = dyn_cast<StringLiteral>(Attr.getArg(0)); 1638 if (!SE) { 1639 S.Diag(Attr.getArg(0)->getLocStart(), 1640 diag::err_attribute_not_string) << "unavailable"; 1641 return; 1642 } 1643 Str = SE->getString(); 1644 } 1645 D->addAttr(::new (S.Context) UnavailableAttr(Attr.getRange(), S.Context, Str)); 1646} 1647 1648static void handleArcWeakrefUnavailableAttr(Sema &S, Decl *D, 1649 const AttributeList &Attr) { 1650 unsigned NumArgs = Attr.getNumArgs(); 1651 if (NumArgs > 0) { 1652 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 0; 1653 return; 1654 } 1655 1656 D->addAttr(::new (S.Context) ArcWeakrefUnavailableAttr( 1657 Attr.getRange(), S.Context)); 1658} 1659 1660static void handleObjCRootClassAttr(Sema &S, Decl *D, 1661 const AttributeList &Attr) { 1662 if (!isa<ObjCInterfaceDecl>(D)) { 1663 S.Diag(Attr.getLoc(), diag::err_attribute_requires_objc_interface); 1664 return; 1665 } 1666 1667 unsigned NumArgs = Attr.getNumArgs(); 1668 if (NumArgs > 0) { 1669 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 0; 1670 return; 1671 } 1672 1673 D->addAttr(::new (S.Context) ObjCRootClassAttr(Attr.getRange(), S.Context)); 1674} 1675 1676static void handleObjCRequiresPropertyDefsAttr(Sema &S, Decl *D, 1677 const AttributeList &Attr) { 1678 if (!isa<ObjCInterfaceDecl>(D)) { 1679 S.Diag(Attr.getLoc(), diag::err_suppress_autosynthesis); 1680 return; 1681 } 1682 1683 unsigned NumArgs = Attr.getNumArgs(); 1684 if (NumArgs > 0) { 1685 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 0; 1686 return; 1687 } 1688 1689 D->addAttr(::new (S.Context) ObjCRequiresPropertyDefsAttr( 1690 Attr.getRange(), S.Context)); 1691} 1692 1693static void handleAvailabilityAttr(Sema &S, Decl *D, 1694 const AttributeList &Attr) { 1695 IdentifierInfo *Platform = Attr.getParameterName(); 1696 SourceLocation PlatformLoc = Attr.getParameterLoc(); 1697 1698 StringRef PlatformName 1699 = AvailabilityAttr::getPrettyPlatformName(Platform->getName()); 1700 if (PlatformName.empty()) { 1701 S.Diag(PlatformLoc, diag::warn_availability_unknown_platform) 1702 << Platform; 1703 1704 PlatformName = Platform->getName(); 1705 } 1706 1707 AvailabilityChange Introduced = Attr.getAvailabilityIntroduced(); 1708 AvailabilityChange Deprecated = Attr.getAvailabilityDeprecated(); 1709 AvailabilityChange Obsoleted = Attr.getAvailabilityObsoleted(); 1710 bool IsUnavailable = Attr.getUnavailableLoc().isValid(); 1711 1712 // Ensure that Introduced <= Deprecated <= Obsoleted (although not all 1713 // of these steps are needed). 1714 if (Introduced.isValid() && Deprecated.isValid() && 1715 !(Introduced.Version <= Deprecated.Version)) { 1716 S.Diag(Introduced.KeywordLoc, diag::warn_availability_version_ordering) 1717 << 1 << PlatformName << Deprecated.Version.getAsString() 1718 << 0 << Introduced.Version.getAsString(); 1719 return; 1720 } 1721 1722 if (Introduced.isValid() && Obsoleted.isValid() && 1723 !(Introduced.Version <= Obsoleted.Version)) { 1724 S.Diag(Introduced.KeywordLoc, diag::warn_availability_version_ordering) 1725 << 2 << PlatformName << Obsoleted.Version.getAsString() 1726 << 0 << Introduced.Version.getAsString(); 1727 return; 1728 } 1729 1730 if (Deprecated.isValid() && Obsoleted.isValid() && 1731 !(Deprecated.Version <= Obsoleted.Version)) { 1732 S.Diag(Deprecated.KeywordLoc, diag::warn_availability_version_ordering) 1733 << 2 << PlatformName << Obsoleted.Version.getAsString() 1734 << 1 << Deprecated.Version.getAsString(); 1735 return; 1736 } 1737 1738 StringRef Str; 1739 const StringLiteral *SE = 1740 dyn_cast_or_null<const StringLiteral>(Attr.getMessageExpr()); 1741 if (SE) 1742 Str = SE->getString(); 1743 1744 D->addAttr(::new (S.Context) AvailabilityAttr(Attr.getRange(), S.Context, 1745 Platform, 1746 Introduced.Version, 1747 Deprecated.Version, 1748 Obsoleted.Version, 1749 IsUnavailable, 1750 Str)); 1751} 1752 1753static void handleVisibilityAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1754 // check the attribute arguments. 1755 if(!checkAttributeNumArgs(S, Attr, 1)) 1756 return; 1757 1758 Expr *Arg = Attr.getArg(0); 1759 Arg = Arg->IgnoreParenCasts(); 1760 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 1761 1762 if (!Str || !Str->isAscii()) { 1763 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1764 << "visibility" << 1; 1765 return; 1766 } 1767 1768 StringRef TypeStr = Str->getString(); 1769 VisibilityAttr::VisibilityType type; 1770 1771 if (TypeStr == "default") 1772 type = VisibilityAttr::Default; 1773 else if (TypeStr == "hidden") 1774 type = VisibilityAttr::Hidden; 1775 else if (TypeStr == "internal") 1776 type = VisibilityAttr::Hidden; // FIXME 1777 else if (TypeStr == "protected") { 1778 // Complain about attempts to use protected visibility on targets 1779 // (like Darwin) that don't support it. 1780 if (!S.Context.getTargetInfo().hasProtectedVisibility()) { 1781 S.Diag(Attr.getLoc(), diag::warn_attribute_protected_visibility); 1782 type = VisibilityAttr::Default; 1783 } else { 1784 type = VisibilityAttr::Protected; 1785 } 1786 } else { 1787 S.Diag(Attr.getLoc(), diag::warn_attribute_unknown_visibility) << TypeStr; 1788 return; 1789 } 1790 1791 // Find the last Decl that has an attribute. 1792 VisibilityAttr *PrevAttr; 1793 assert(D->redecls_begin() == D); 1794 for (Decl::redecl_iterator I = D->redecls_begin(), E = D->redecls_end(); 1795 I != E; ++I) { 1796 PrevAttr = I->getAttr<VisibilityAttr>() ; 1797 if (PrevAttr) 1798 break; 1799 } 1800 1801 if (PrevAttr) { 1802 VisibilityAttr::VisibilityType PrevVisibility = PrevAttr->getVisibility(); 1803 if (PrevVisibility != type) { 1804 S.Diag(Attr.getLoc(), diag::err_mismatched_visibilit); 1805 S.Diag(PrevAttr->getLocation(), diag::note_previous_attribute); 1806 return; 1807 } 1808 } 1809 D->addAttr(::new (S.Context) VisibilityAttr(Attr.getRange(), S.Context, type)); 1810} 1811 1812static void handleObjCMethodFamilyAttr(Sema &S, Decl *decl, 1813 const AttributeList &Attr) { 1814 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(decl); 1815 if (!method) { 1816 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 1817 << ExpectedMethod; 1818 return; 1819 } 1820 1821 if (Attr.getNumArgs() != 0 || !Attr.getParameterName()) { 1822 if (!Attr.getParameterName() && Attr.getNumArgs() == 1) { 1823 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1824 << "objc_method_family" << 1; 1825 } else { 1826 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1827 } 1828 Attr.setInvalid(); 1829 return; 1830 } 1831 1832 StringRef param = Attr.getParameterName()->getName(); 1833 ObjCMethodFamilyAttr::FamilyKind family; 1834 if (param == "none") 1835 family = ObjCMethodFamilyAttr::OMF_None; 1836 else if (param == "alloc") 1837 family = ObjCMethodFamilyAttr::OMF_alloc; 1838 else if (param == "copy") 1839 family = ObjCMethodFamilyAttr::OMF_copy; 1840 else if (param == "init") 1841 family = ObjCMethodFamilyAttr::OMF_init; 1842 else if (param == "mutableCopy") 1843 family = ObjCMethodFamilyAttr::OMF_mutableCopy; 1844 else if (param == "new") 1845 family = ObjCMethodFamilyAttr::OMF_new; 1846 else { 1847 // Just warn and ignore it. This is future-proof against new 1848 // families being used in system headers. 1849 S.Diag(Attr.getParameterLoc(), diag::warn_unknown_method_family); 1850 return; 1851 } 1852 1853 if (family == ObjCMethodFamilyAttr::OMF_init && 1854 !method->getResultType()->isObjCObjectPointerType()) { 1855 S.Diag(method->getLocation(), diag::err_init_method_bad_return_type) 1856 << method->getResultType(); 1857 // Ignore the attribute. 1858 return; 1859 } 1860 1861 method->addAttr(new (S.Context) ObjCMethodFamilyAttr(Attr.getRange(), 1862 S.Context, family)); 1863} 1864 1865static void handleObjCExceptionAttr(Sema &S, Decl *D, 1866 const AttributeList &Attr) { 1867 if (!checkAttributeNumArgs(S, Attr, 0)) 1868 return; 1869 1870 ObjCInterfaceDecl *OCI = dyn_cast<ObjCInterfaceDecl>(D); 1871 if (OCI == 0) { 1872 S.Diag(Attr.getLoc(), diag::err_attribute_requires_objc_interface); 1873 return; 1874 } 1875 1876 D->addAttr(::new (S.Context) ObjCExceptionAttr(Attr.getRange(), S.Context)); 1877} 1878 1879static void handleObjCNSObject(Sema &S, Decl *D, const AttributeList &Attr) { 1880 if (Attr.getNumArgs() != 0) { 1881 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1882 return; 1883 } 1884 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) { 1885 QualType T = TD->getUnderlyingType(); 1886 if (!T->isPointerType() || 1887 !T->getAs<PointerType>()->getPointeeType()->isRecordType()) { 1888 S.Diag(TD->getLocation(), diag::err_nsobject_attribute); 1889 return; 1890 } 1891 } 1892 else if (!isa<ObjCPropertyDecl>(D)) { 1893 // It is okay to include this attribute on properties, e.g.: 1894 // 1895 // @property (retain, nonatomic) struct Bork *Q __attribute__((NSObject)); 1896 // 1897 // In this case it follows tradition and suppresses an error in the above 1898 // case. 1899 S.Diag(D->getLocation(), diag::warn_nsobject_attribute); 1900 } 1901 D->addAttr(::new (S.Context) ObjCNSObjectAttr(Attr.getRange(), S.Context)); 1902} 1903 1904static void 1905handleOverloadableAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1906 if (Attr.getNumArgs() != 0) { 1907 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1908 return; 1909 } 1910 1911 if (!isa<FunctionDecl>(D)) { 1912 S.Diag(Attr.getLoc(), diag::err_attribute_overloadable_not_function); 1913 return; 1914 } 1915 1916 D->addAttr(::new (S.Context) OverloadableAttr(Attr.getRange(), S.Context)); 1917} 1918 1919static void handleBlocksAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1920 if (!Attr.getParameterName()) { 1921 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1922 << "blocks" << 1; 1923 return; 1924 } 1925 1926 if (Attr.getNumArgs() != 0) { 1927 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1928 return; 1929 } 1930 1931 BlocksAttr::BlockType type; 1932 if (Attr.getParameterName()->isStr("byref")) 1933 type = BlocksAttr::ByRef; 1934 else { 1935 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 1936 << "blocks" << Attr.getParameterName(); 1937 return; 1938 } 1939 1940 D->addAttr(::new (S.Context) BlocksAttr(Attr.getRange(), S.Context, type)); 1941} 1942 1943static void handleSentinelAttr(Sema &S, Decl *D, const AttributeList &Attr) { 1944 // check the attribute arguments. 1945 if (Attr.getNumArgs() > 2) { 1946 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 1947 return; 1948 } 1949 1950 unsigned sentinel = 0; 1951 if (Attr.getNumArgs() > 0) { 1952 Expr *E = Attr.getArg(0); 1953 llvm::APSInt Idx(32); 1954 if (E->isTypeDependent() || E->isValueDependent() || 1955 !E->isIntegerConstantExpr(Idx, S.Context)) { 1956 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1957 << "sentinel" << 1 << E->getSourceRange(); 1958 return; 1959 } 1960 1961 if (Idx.isSigned() && Idx.isNegative()) { 1962 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_less_than_zero) 1963 << E->getSourceRange(); 1964 return; 1965 } 1966 1967 sentinel = Idx.getZExtValue(); 1968 } 1969 1970 unsigned nullPos = 0; 1971 if (Attr.getNumArgs() > 1) { 1972 Expr *E = Attr.getArg(1); 1973 llvm::APSInt Idx(32); 1974 if (E->isTypeDependent() || E->isValueDependent() || 1975 !E->isIntegerConstantExpr(Idx, S.Context)) { 1976 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1977 << "sentinel" << 2 << E->getSourceRange(); 1978 return; 1979 } 1980 nullPos = Idx.getZExtValue(); 1981 1982 if ((Idx.isSigned() && Idx.isNegative()) || nullPos > 1) { 1983 // FIXME: This error message could be improved, it would be nice 1984 // to say what the bounds actually are. 1985 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_not_zero_or_one) 1986 << E->getSourceRange(); 1987 return; 1988 } 1989 } 1990 1991 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) { 1992 const FunctionType *FT = FD->getType()->castAs<FunctionType>(); 1993 if (isa<FunctionNoProtoType>(FT)) { 1994 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_named_arguments); 1995 return; 1996 } 1997 1998 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 1999 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 2000 return; 2001 } 2002 } else if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) { 2003 if (!MD->isVariadic()) { 2004 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 2005 return; 2006 } 2007 } else if (BlockDecl *BD = dyn_cast<BlockDecl>(D)) { 2008 if (!BD->isVariadic()) { 2009 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 1; 2010 return; 2011 } 2012 } else if (const VarDecl *V = dyn_cast<VarDecl>(D)) { 2013 QualType Ty = V->getType(); 2014 if (Ty->isBlockPointerType() || Ty->isFunctionPointerType()) { 2015 const FunctionType *FT = Ty->isFunctionPointerType() ? getFunctionType(D) 2016 : Ty->getAs<BlockPointerType>()->getPointeeType()->getAs<FunctionType>(); 2017 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 2018 int m = Ty->isFunctionPointerType() ? 0 : 1; 2019 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << m; 2020 return; 2021 } 2022 } else { 2023 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2024 << Attr.getName() << ExpectedFunctionMethodOrBlock; 2025 return; 2026 } 2027 } else { 2028 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2029 << Attr.getName() << ExpectedFunctionMethodOrBlock; 2030 return; 2031 } 2032 D->addAttr(::new (S.Context) SentinelAttr(Attr.getRange(), S.Context, sentinel, 2033 nullPos)); 2034} 2035 2036static void handleWarnUnusedResult(Sema &S, Decl *D, const AttributeList &Attr) { 2037 // check the attribute arguments. 2038 if (!checkAttributeNumArgs(S, Attr, 0)) 2039 return; 2040 2041 if (!isFunction(D) && !isa<ObjCMethodDecl>(D)) { 2042 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2043 << Attr.getName() << ExpectedFunctionOrMethod; 2044 return; 2045 } 2046 2047 if (isFunction(D) && getFunctionType(D)->getResultType()->isVoidType()) { 2048 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 2049 << Attr.getName() << 0; 2050 return; 2051 } 2052 if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 2053 if (MD->getResultType()->isVoidType()) { 2054 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 2055 << Attr.getName() << 1; 2056 return; 2057 } 2058 2059 D->addAttr(::new (S.Context) WarnUnusedResultAttr(Attr.getRange(), S.Context)); 2060} 2061 2062static void handleWeakAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2063 // check the attribute arguments. 2064 if (Attr.hasParameterOrArguments()) { 2065 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2066 return; 2067 } 2068 2069 if (!isa<VarDecl>(D) && !isa<FunctionDecl>(D)) { 2070 if (isa<CXXRecordDecl>(D)) { 2071 D->addAttr(::new (S.Context) WeakAttr(Attr.getRange(), S.Context)); 2072 return; 2073 } 2074 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2075 << Attr.getName() << ExpectedVariableOrFunction; 2076 return; 2077 } 2078 2079 NamedDecl *nd = cast<NamedDecl>(D); 2080 2081 // 'weak' only applies to declarations with external linkage. 2082 if (hasEffectivelyInternalLinkage(nd)) { 2083 S.Diag(Attr.getLoc(), diag::err_attribute_weak_static); 2084 return; 2085 } 2086 2087 nd->addAttr(::new (S.Context) WeakAttr(Attr.getRange(), S.Context)); 2088} 2089 2090static void handleWeakImportAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2091 // check the attribute arguments. 2092 if (!checkAttributeNumArgs(S, Attr, 0)) 2093 return; 2094 2095 2096 // weak_import only applies to variable & function declarations. 2097 bool isDef = false; 2098 if (!D->canBeWeakImported(isDef)) { 2099 if (isDef) 2100 S.Diag(Attr.getLoc(), 2101 diag::warn_attribute_weak_import_invalid_on_definition) 2102 << "weak_import" << 2 /*variable and function*/; 2103 else if (isa<ObjCPropertyDecl>(D) || isa<ObjCMethodDecl>(D) || 2104 (S.Context.getTargetInfo().getTriple().isOSDarwin() && 2105 (isa<ObjCInterfaceDecl>(D) || isa<EnumDecl>(D)))) { 2106 // Nothing to warn about here. 2107 } else 2108 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2109 << Attr.getName() << ExpectedVariableOrFunction; 2110 2111 return; 2112 } 2113 2114 D->addAttr(::new (S.Context) WeakImportAttr(Attr.getRange(), S.Context)); 2115} 2116 2117static void handleReqdWorkGroupSize(Sema &S, Decl *D, 2118 const AttributeList &Attr) { 2119 // Attribute has 3 arguments. 2120 if (!checkAttributeNumArgs(S, Attr, 3)) 2121 return; 2122 2123 unsigned WGSize[3]; 2124 for (unsigned i = 0; i < 3; ++i) { 2125 Expr *E = Attr.getArg(i); 2126 llvm::APSInt ArgNum(32); 2127 if (E->isTypeDependent() || E->isValueDependent() || 2128 !E->isIntegerConstantExpr(ArgNum, S.Context)) { 2129 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 2130 << "reqd_work_group_size" << E->getSourceRange(); 2131 return; 2132 } 2133 WGSize[i] = (unsigned) ArgNum.getZExtValue(); 2134 } 2135 D->addAttr(::new (S.Context) ReqdWorkGroupSizeAttr(Attr.getRange(), S.Context, 2136 WGSize[0], WGSize[1], 2137 WGSize[2])); 2138} 2139 2140static void handleSectionAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2141 // Attribute has no arguments. 2142 if (!checkAttributeNumArgs(S, Attr, 1)) 2143 return; 2144 2145 // Make sure that there is a string literal as the sections's single 2146 // argument. 2147 Expr *ArgExpr = Attr.getArg(0); 2148 StringLiteral *SE = dyn_cast<StringLiteral>(ArgExpr); 2149 if (!SE) { 2150 S.Diag(ArgExpr->getLocStart(), diag::err_attribute_not_string) << "section"; 2151 return; 2152 } 2153 2154 // If the target wants to validate the section specifier, make it happen. 2155 std::string Error = S.Context.getTargetInfo().isValidSectionSpecifier(SE->getString()); 2156 if (!Error.empty()) { 2157 S.Diag(SE->getLocStart(), diag::err_attribute_section_invalid_for_target) 2158 << Error; 2159 return; 2160 } 2161 2162 // This attribute cannot be applied to local variables. 2163 if (isa<VarDecl>(D) && cast<VarDecl>(D)->hasLocalStorage()) { 2164 S.Diag(SE->getLocStart(), diag::err_attribute_section_local_variable); 2165 return; 2166 } 2167 2168 D->addAttr(::new (S.Context) SectionAttr(Attr.getRange(), S.Context, 2169 SE->getString())); 2170} 2171 2172 2173static void handleNothrowAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2174 // check the attribute arguments. 2175 if (Attr.hasParameterOrArguments()) { 2176 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2177 return; 2178 } 2179 2180 if (NoThrowAttr *Existing = D->getAttr<NoThrowAttr>()) { 2181 if (Existing->getLocation().isInvalid()) 2182 Existing->setRange(Attr.getRange()); 2183 } else { 2184 D->addAttr(::new (S.Context) NoThrowAttr(Attr.getRange(), S.Context)); 2185 } 2186} 2187 2188static void handleConstAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2189 // check the attribute arguments. 2190 if (Attr.hasParameterOrArguments()) { 2191 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2192 return; 2193 } 2194 2195 if (ConstAttr *Existing = D->getAttr<ConstAttr>()) { 2196 if (Existing->getLocation().isInvalid()) 2197 Existing->setRange(Attr.getRange()); 2198 } else { 2199 D->addAttr(::new (S.Context) ConstAttr(Attr.getRange(), S.Context)); 2200 } 2201} 2202 2203static void handlePureAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2204 // check the attribute arguments. 2205 if (!checkAttributeNumArgs(S, Attr, 0)) 2206 return; 2207 2208 D->addAttr(::new (S.Context) PureAttr(Attr.getRange(), S.Context)); 2209} 2210 2211static void handleCleanupAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2212 if (!Attr.getParameterName()) { 2213 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2214 return; 2215 } 2216 2217 if (Attr.getNumArgs() != 0) { 2218 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2219 return; 2220 } 2221 2222 VarDecl *VD = dyn_cast<VarDecl>(D); 2223 2224 if (!VD || !VD->hasLocalStorage()) { 2225 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "cleanup"; 2226 return; 2227 } 2228 2229 // Look up the function 2230 // FIXME: Lookup probably isn't looking in the right place 2231 NamedDecl *CleanupDecl 2232 = S.LookupSingleName(S.TUScope, Attr.getParameterName(), 2233 Attr.getParameterLoc(), Sema::LookupOrdinaryName); 2234 if (!CleanupDecl) { 2235 S.Diag(Attr.getParameterLoc(), diag::err_attribute_cleanup_arg_not_found) << 2236 Attr.getParameterName(); 2237 return; 2238 } 2239 2240 FunctionDecl *FD = dyn_cast<FunctionDecl>(CleanupDecl); 2241 if (!FD) { 2242 S.Diag(Attr.getParameterLoc(), 2243 diag::err_attribute_cleanup_arg_not_function) 2244 << Attr.getParameterName(); 2245 return; 2246 } 2247 2248 if (FD->getNumParams() != 1) { 2249 S.Diag(Attr.getParameterLoc(), 2250 diag::err_attribute_cleanup_func_must_take_one_arg) 2251 << Attr.getParameterName(); 2252 return; 2253 } 2254 2255 // We're currently more strict than GCC about what function types we accept. 2256 // If this ever proves to be a problem it should be easy to fix. 2257 QualType Ty = S.Context.getPointerType(VD->getType()); 2258 QualType ParamTy = FD->getParamDecl(0)->getType(); 2259 if (S.CheckAssignmentConstraints(FD->getParamDecl(0)->getLocation(), 2260 ParamTy, Ty) != Sema::Compatible) { 2261 S.Diag(Attr.getParameterLoc(), 2262 diag::err_attribute_cleanup_func_arg_incompatible_type) << 2263 Attr.getParameterName() << ParamTy << Ty; 2264 return; 2265 } 2266 2267 D->addAttr(::new (S.Context) CleanupAttr(Attr.getRange(), S.Context, FD)); 2268 S.MarkFunctionReferenced(Attr.getParameterLoc(), FD); 2269} 2270 2271/// Handle __attribute__((format_arg((idx)))) attribute based on 2272/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 2273static void handleFormatArgAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2274 if (!checkAttributeNumArgs(S, Attr, 1)) 2275 return; 2276 2277 if (!isFunctionOrMethod(D) || !hasFunctionProto(D)) { 2278 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2279 << Attr.getName() << ExpectedFunction; 2280 return; 2281 } 2282 2283 // In C++ the implicit 'this' function parameter also counts, and they are 2284 // counted from one. 2285 bool HasImplicitThisParam = isInstanceMethod(D); 2286 unsigned NumArgs = getFunctionOrMethodNumArgs(D) + HasImplicitThisParam; 2287 unsigned FirstIdx = 1; 2288 2289 // checks for the 2nd argument 2290 Expr *IdxExpr = Attr.getArg(0); 2291 llvm::APSInt Idx(32); 2292 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 2293 !IdxExpr->isIntegerConstantExpr(Idx, S.Context)) { 2294 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2295 << "format" << 2 << IdxExpr->getSourceRange(); 2296 return; 2297 } 2298 2299 if (Idx.getZExtValue() < FirstIdx || Idx.getZExtValue() > NumArgs) { 2300 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 2301 << "format" << 2 << IdxExpr->getSourceRange(); 2302 return; 2303 } 2304 2305 unsigned ArgIdx = Idx.getZExtValue() - 1; 2306 2307 if (HasImplicitThisParam) { 2308 if (ArgIdx == 0) { 2309 S.Diag(Attr.getLoc(), diag::err_attribute_invalid_implicit_this_argument) 2310 << "format_arg" << IdxExpr->getSourceRange(); 2311 return; 2312 } 2313 ArgIdx--; 2314 } 2315 2316 // make sure the format string is really a string 2317 QualType Ty = getFunctionOrMethodArgType(D, ArgIdx); 2318 2319 bool not_nsstring_type = !isNSStringType(Ty, S.Context); 2320 if (not_nsstring_type && 2321 !isCFStringType(Ty, S.Context) && 2322 (!Ty->isPointerType() || 2323 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 2324 // FIXME: Should highlight the actual expression that has the wrong type. 2325 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2326 << (not_nsstring_type ? "a string type" : "an NSString") 2327 << IdxExpr->getSourceRange(); 2328 return; 2329 } 2330 Ty = getFunctionOrMethodResultType(D); 2331 if (!isNSStringType(Ty, S.Context) && 2332 !isCFStringType(Ty, S.Context) && 2333 (!Ty->isPointerType() || 2334 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 2335 // FIXME: Should highlight the actual expression that has the wrong type. 2336 S.Diag(Attr.getLoc(), diag::err_format_attribute_result_not) 2337 << (not_nsstring_type ? "string type" : "NSString") 2338 << IdxExpr->getSourceRange(); 2339 return; 2340 } 2341 2342 D->addAttr(::new (S.Context) FormatArgAttr(Attr.getRange(), S.Context, 2343 Idx.getZExtValue())); 2344} 2345 2346enum FormatAttrKind { 2347 CFStringFormat, 2348 NSStringFormat, 2349 StrftimeFormat, 2350 SupportedFormat, 2351 IgnoredFormat, 2352 InvalidFormat 2353}; 2354 2355/// getFormatAttrKind - Map from format attribute names to supported format 2356/// types. 2357static FormatAttrKind getFormatAttrKind(StringRef Format) { 2358 // Check for formats that get handled specially. 2359 if (Format == "NSString") 2360 return NSStringFormat; 2361 if (Format == "CFString") 2362 return CFStringFormat; 2363 if (Format == "strftime") 2364 return StrftimeFormat; 2365 2366 // Otherwise, check for supported formats. 2367 if (Format == "scanf" || Format == "printf" || Format == "printf0" || 2368 Format == "strfmon" || Format == "cmn_err" || Format == "vcmn_err" || 2369 Format == "zcmn_err" || 2370 Format == "kprintf") // OpenBSD. 2371 return SupportedFormat; 2372 2373 if (Format == "gcc_diag" || Format == "gcc_cdiag" || 2374 Format == "gcc_cxxdiag" || Format == "gcc_tdiag") 2375 return IgnoredFormat; 2376 2377 return InvalidFormat; 2378} 2379 2380/// Handle __attribute__((init_priority(priority))) attributes based on 2381/// http://gcc.gnu.org/onlinedocs/gcc/C_002b_002b-Attributes.html 2382static void handleInitPriorityAttr(Sema &S, Decl *D, 2383 const AttributeList &Attr) { 2384 if (!S.getLangOpts().CPlusPlus) { 2385 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 2386 return; 2387 } 2388 2389 if (!isa<VarDecl>(D) || S.getCurFunctionOrMethodDecl()) { 2390 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 2391 Attr.setInvalid(); 2392 return; 2393 } 2394 QualType T = dyn_cast<VarDecl>(D)->getType(); 2395 if (S.Context.getAsArrayType(T)) 2396 T = S.Context.getBaseElementType(T); 2397 if (!T->getAs<RecordType>()) { 2398 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 2399 Attr.setInvalid(); 2400 return; 2401 } 2402 2403 if (Attr.getNumArgs() != 1) { 2404 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2405 Attr.setInvalid(); 2406 return; 2407 } 2408 Expr *priorityExpr = Attr.getArg(0); 2409 2410 llvm::APSInt priority(32); 2411 if (priorityExpr->isTypeDependent() || priorityExpr->isValueDependent() || 2412 !priorityExpr->isIntegerConstantExpr(priority, S.Context)) { 2413 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 2414 << "init_priority" << priorityExpr->getSourceRange(); 2415 Attr.setInvalid(); 2416 return; 2417 } 2418 unsigned prioritynum = priority.getZExtValue(); 2419 if (prioritynum < 101 || prioritynum > 65535) { 2420 S.Diag(Attr.getLoc(), diag::err_attribute_argument_outof_range) 2421 << priorityExpr->getSourceRange(); 2422 Attr.setInvalid(); 2423 return; 2424 } 2425 D->addAttr(::new (S.Context) InitPriorityAttr(Attr.getRange(), S.Context, 2426 prioritynum)); 2427} 2428 2429/// Handle __attribute__((format(type,idx,firstarg))) attributes based on 2430/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 2431static void handleFormatAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2432 2433 if (!Attr.getParameterName()) { 2434 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 2435 << "format" << 1; 2436 return; 2437 } 2438 2439 if (Attr.getNumArgs() != 2) { 2440 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 3; 2441 return; 2442 } 2443 2444 if (!isFunctionOrMethodOrBlock(D) || !hasFunctionProto(D)) { 2445 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2446 << Attr.getName() << ExpectedFunction; 2447 return; 2448 } 2449 2450 // In C++ the implicit 'this' function parameter also counts, and they are 2451 // counted from one. 2452 bool HasImplicitThisParam = isInstanceMethod(D); 2453 unsigned NumArgs = getFunctionOrMethodNumArgs(D) + HasImplicitThisParam; 2454 unsigned FirstIdx = 1; 2455 2456 StringRef Format = Attr.getParameterName()->getName(); 2457 2458 // Normalize the argument, __foo__ becomes foo. 2459 if (Format.startswith("__") && Format.endswith("__")) 2460 Format = Format.substr(2, Format.size() - 4); 2461 2462 // Check for supported formats. 2463 FormatAttrKind Kind = getFormatAttrKind(Format); 2464 2465 if (Kind == IgnoredFormat) 2466 return; 2467 2468 if (Kind == InvalidFormat) { 2469 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 2470 << "format" << Attr.getParameterName()->getName(); 2471 return; 2472 } 2473 2474 // checks for the 2nd argument 2475 Expr *IdxExpr = Attr.getArg(0); 2476 llvm::APSInt Idx(32); 2477 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 2478 !IdxExpr->isIntegerConstantExpr(Idx, S.Context)) { 2479 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2480 << "format" << 2 << IdxExpr->getSourceRange(); 2481 return; 2482 } 2483 2484 if (Idx.getZExtValue() < FirstIdx || Idx.getZExtValue() > NumArgs) { 2485 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 2486 << "format" << 2 << IdxExpr->getSourceRange(); 2487 return; 2488 } 2489 2490 // FIXME: Do we need to bounds check? 2491 unsigned ArgIdx = Idx.getZExtValue() - 1; 2492 2493 if (HasImplicitThisParam) { 2494 if (ArgIdx == 0) { 2495 S.Diag(Attr.getLoc(), 2496 diag::err_format_attribute_implicit_this_format_string) 2497 << IdxExpr->getSourceRange(); 2498 return; 2499 } 2500 ArgIdx--; 2501 } 2502 2503 // make sure the format string is really a string 2504 QualType Ty = getFunctionOrMethodArgType(D, ArgIdx); 2505 2506 if (Kind == CFStringFormat) { 2507 if (!isCFStringType(Ty, S.Context)) { 2508 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2509 << "a CFString" << IdxExpr->getSourceRange(); 2510 return; 2511 } 2512 } else if (Kind == NSStringFormat) { 2513 // FIXME: do we need to check if the type is NSString*? What are the 2514 // semantics? 2515 if (!isNSStringType(Ty, S.Context)) { 2516 // FIXME: Should highlight the actual expression that has the wrong type. 2517 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2518 << "an NSString" << IdxExpr->getSourceRange(); 2519 return; 2520 } 2521 } else if (!Ty->isPointerType() || 2522 !Ty->getAs<PointerType>()->getPointeeType()->isCharType()) { 2523 // FIXME: Should highlight the actual expression that has the wrong type. 2524 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 2525 << "a string type" << IdxExpr->getSourceRange(); 2526 return; 2527 } 2528 2529 // check the 3rd argument 2530 Expr *FirstArgExpr = Attr.getArg(1); 2531 llvm::APSInt FirstArg(32); 2532 if (FirstArgExpr->isTypeDependent() || FirstArgExpr->isValueDependent() || 2533 !FirstArgExpr->isIntegerConstantExpr(FirstArg, S.Context)) { 2534 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2535 << "format" << 3 << FirstArgExpr->getSourceRange(); 2536 return; 2537 } 2538 2539 // check if the function is variadic if the 3rd argument non-zero 2540 if (FirstArg != 0) { 2541 if (isFunctionOrMethodVariadic(D)) { 2542 ++NumArgs; // +1 for ... 2543 } else { 2544 S.Diag(D->getLocation(), diag::err_format_attribute_requires_variadic); 2545 return; 2546 } 2547 } 2548 2549 // strftime requires FirstArg to be 0 because it doesn't read from any 2550 // variable the input is just the current time + the format string. 2551 if (Kind == StrftimeFormat) { 2552 if (FirstArg != 0) { 2553 S.Diag(Attr.getLoc(), diag::err_format_strftime_third_parameter) 2554 << FirstArgExpr->getSourceRange(); 2555 return; 2556 } 2557 // if 0 it disables parameter checking (to use with e.g. va_list) 2558 } else if (FirstArg != 0 && FirstArg != NumArgs) { 2559 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 2560 << "format" << 3 << FirstArgExpr->getSourceRange(); 2561 return; 2562 } 2563 2564 // Check whether we already have an equivalent format attribute. 2565 for (specific_attr_iterator<FormatAttr> 2566 i = D->specific_attr_begin<FormatAttr>(), 2567 e = D->specific_attr_end<FormatAttr>(); 2568 i != e ; ++i) { 2569 FormatAttr *f = *i; 2570 if (f->getType() == Format && 2571 f->getFormatIdx() == (int)Idx.getZExtValue() && 2572 f->getFirstArg() == (int)FirstArg.getZExtValue()) { 2573 // If we don't have a valid location for this attribute, adopt the 2574 // location. 2575 if (f->getLocation().isInvalid()) 2576 f->setRange(Attr.getRange()); 2577 return; 2578 } 2579 } 2580 2581 D->addAttr(::new (S.Context) FormatAttr(Attr.getRange(), S.Context, Format, 2582 Idx.getZExtValue(), 2583 FirstArg.getZExtValue())); 2584} 2585 2586static void handleTransparentUnionAttr(Sema &S, Decl *D, 2587 const AttributeList &Attr) { 2588 // check the attribute arguments. 2589 if (!checkAttributeNumArgs(S, Attr, 0)) 2590 return; 2591 2592 2593 // Try to find the underlying union declaration. 2594 RecordDecl *RD = 0; 2595 TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D); 2596 if (TD && TD->getUnderlyingType()->isUnionType()) 2597 RD = TD->getUnderlyingType()->getAsUnionType()->getDecl(); 2598 else 2599 RD = dyn_cast<RecordDecl>(D); 2600 2601 if (!RD || !RD->isUnion()) { 2602 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2603 << Attr.getName() << ExpectedUnion; 2604 return; 2605 } 2606 2607 if (!RD->isCompleteDefinition()) { 2608 S.Diag(Attr.getLoc(), 2609 diag::warn_transparent_union_attribute_not_definition); 2610 return; 2611 } 2612 2613 RecordDecl::field_iterator Field = RD->field_begin(), 2614 FieldEnd = RD->field_end(); 2615 if (Field == FieldEnd) { 2616 S.Diag(Attr.getLoc(), diag::warn_transparent_union_attribute_zero_fields); 2617 return; 2618 } 2619 2620 FieldDecl *FirstField = &*Field; 2621 QualType FirstType = FirstField->getType(); 2622 if (FirstType->hasFloatingRepresentation() || FirstType->isVectorType()) { 2623 S.Diag(FirstField->getLocation(), 2624 diag::warn_transparent_union_attribute_floating) 2625 << FirstType->isVectorType() << FirstType; 2626 return; 2627 } 2628 2629 uint64_t FirstSize = S.Context.getTypeSize(FirstType); 2630 uint64_t FirstAlign = S.Context.getTypeAlign(FirstType); 2631 for (; Field != FieldEnd; ++Field) { 2632 QualType FieldType = Field->getType(); 2633 if (S.Context.getTypeSize(FieldType) != FirstSize || 2634 S.Context.getTypeAlign(FieldType) != FirstAlign) { 2635 // Warn if we drop the attribute. 2636 bool isSize = S.Context.getTypeSize(FieldType) != FirstSize; 2637 unsigned FieldBits = isSize? S.Context.getTypeSize(FieldType) 2638 : S.Context.getTypeAlign(FieldType); 2639 S.Diag(Field->getLocation(), 2640 diag::warn_transparent_union_attribute_field_size_align) 2641 << isSize << Field->getDeclName() << FieldBits; 2642 unsigned FirstBits = isSize? FirstSize : FirstAlign; 2643 S.Diag(FirstField->getLocation(), 2644 diag::note_transparent_union_first_field_size_align) 2645 << isSize << FirstBits; 2646 return; 2647 } 2648 } 2649 2650 RD->addAttr(::new (S.Context) TransparentUnionAttr(Attr.getRange(), S.Context)); 2651} 2652 2653static void handleAnnotateAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2654 // check the attribute arguments. 2655 if (!checkAttributeNumArgs(S, Attr, 1)) 2656 return; 2657 2658 Expr *ArgExpr = Attr.getArg(0); 2659 StringLiteral *SE = dyn_cast<StringLiteral>(ArgExpr); 2660 2661 // Make sure that there is a string literal as the annotation's single 2662 // argument. 2663 if (!SE) { 2664 S.Diag(ArgExpr->getLocStart(), diag::err_attribute_not_string) <<"annotate"; 2665 return; 2666 } 2667 2668 // Don't duplicate annotations that are already set. 2669 for (specific_attr_iterator<AnnotateAttr> 2670 i = D->specific_attr_begin<AnnotateAttr>(), 2671 e = D->specific_attr_end<AnnotateAttr>(); i != e; ++i) { 2672 if ((*i)->getAnnotation() == SE->getString()) 2673 return; 2674 } 2675 D->addAttr(::new (S.Context) AnnotateAttr(Attr.getRange(), S.Context, 2676 SE->getString())); 2677} 2678 2679static void handleAlignedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2680 // check the attribute arguments. 2681 if (Attr.getNumArgs() > 1) { 2682 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2683 return; 2684 } 2685 2686 //FIXME: The C++0x version of this attribute has more limited applicabilty 2687 // than GNU's, and should error out when it is used to specify a 2688 // weaker alignment, rather than being silently ignored. 2689 2690 if (Attr.getNumArgs() == 0) { 2691 D->addAttr(::new (S.Context) AlignedAttr(Attr.getRange(), S.Context, true, 0)); 2692 return; 2693 } 2694 2695 S.AddAlignedAttr(Attr.getRange(), D, Attr.getArg(0)); 2696} 2697 2698void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, Expr *E) { 2699 // FIXME: Handle pack-expansions here. 2700 if (DiagnoseUnexpandedParameterPack(E)) 2701 return; 2702 2703 if (E->isTypeDependent() || E->isValueDependent()) { 2704 // Save dependent expressions in the AST to be instantiated. 2705 D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, E)); 2706 return; 2707 } 2708 2709 SourceLocation AttrLoc = AttrRange.getBegin(); 2710 // FIXME: Cache the number on the Attr object? 2711 llvm::APSInt Alignment(32); 2712 ExprResult ICE 2713 = VerifyIntegerConstantExpression(E, &Alignment, 2714 diag::err_aligned_attribute_argument_not_int, 2715 /*AllowFold*/ false); 2716 if (ICE.isInvalid()) 2717 return; 2718 if (!llvm::isPowerOf2_64(Alignment.getZExtValue())) { 2719 Diag(AttrLoc, diag::err_attribute_aligned_not_power_of_two) 2720 << E->getSourceRange(); 2721 return; 2722 } 2723 2724 D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, true, ICE.take())); 2725} 2726 2727void Sema::AddAlignedAttr(SourceRange AttrRange, Decl *D, TypeSourceInfo *TS) { 2728 // FIXME: Cache the number on the Attr object if non-dependent? 2729 // FIXME: Perform checking of type validity 2730 D->addAttr(::new (Context) AlignedAttr(AttrRange, Context, false, TS)); 2731 return; 2732} 2733 2734/// handleModeAttr - This attribute modifies the width of a decl with primitive 2735/// type. 2736/// 2737/// Despite what would be logical, the mode attribute is a decl attribute, not a 2738/// type attribute: 'int ** __attribute((mode(HI))) *G;' tries to make 'G' be 2739/// HImode, not an intermediate pointer. 2740static void handleModeAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2741 // This attribute isn't documented, but glibc uses it. It changes 2742 // the width of an int or unsigned int to the specified size. 2743 2744 // Check that there aren't any arguments 2745 if (!checkAttributeNumArgs(S, Attr, 0)) 2746 return; 2747 2748 2749 IdentifierInfo *Name = Attr.getParameterName(); 2750 if (!Name) { 2751 S.Diag(Attr.getLoc(), diag::err_attribute_missing_parameter_name); 2752 return; 2753 } 2754 2755 StringRef Str = Attr.getParameterName()->getName(); 2756 2757 // Normalize the attribute name, __foo__ becomes foo. 2758 if (Str.startswith("__") && Str.endswith("__")) 2759 Str = Str.substr(2, Str.size() - 4); 2760 2761 unsigned DestWidth = 0; 2762 bool IntegerMode = true; 2763 bool ComplexMode = false; 2764 switch (Str.size()) { 2765 case 2: 2766 switch (Str[0]) { 2767 case 'Q': DestWidth = 8; break; 2768 case 'H': DestWidth = 16; break; 2769 case 'S': DestWidth = 32; break; 2770 case 'D': DestWidth = 64; break; 2771 case 'X': DestWidth = 96; break; 2772 case 'T': DestWidth = 128; break; 2773 } 2774 if (Str[1] == 'F') { 2775 IntegerMode = false; 2776 } else if (Str[1] == 'C') { 2777 IntegerMode = false; 2778 ComplexMode = true; 2779 } else if (Str[1] != 'I') { 2780 DestWidth = 0; 2781 } 2782 break; 2783 case 4: 2784 // FIXME: glibc uses 'word' to define register_t; this is narrower than a 2785 // pointer on PIC16 and other embedded platforms. 2786 if (Str == "word") 2787 DestWidth = S.Context.getTargetInfo().getPointerWidth(0); 2788 else if (Str == "byte") 2789 DestWidth = S.Context.getTargetInfo().getCharWidth(); 2790 break; 2791 case 7: 2792 if (Str == "pointer") 2793 DestWidth = S.Context.getTargetInfo().getPointerWidth(0); 2794 break; 2795 } 2796 2797 QualType OldTy; 2798 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) 2799 OldTy = TD->getUnderlyingType(); 2800 else if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) 2801 OldTy = VD->getType(); 2802 else { 2803 S.Diag(D->getLocation(), diag::err_attr_wrong_decl) 2804 << "mode" << Attr.getRange(); 2805 return; 2806 } 2807 2808 if (!OldTy->getAs<BuiltinType>() && !OldTy->isComplexType()) 2809 S.Diag(Attr.getLoc(), diag::err_mode_not_primitive); 2810 else if (IntegerMode) { 2811 if (!OldTy->isIntegralOrEnumerationType()) 2812 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2813 } else if (ComplexMode) { 2814 if (!OldTy->isComplexType()) 2815 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2816 } else { 2817 if (!OldTy->isFloatingType()) 2818 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2819 } 2820 2821 // FIXME: Sync this with InitializePredefinedMacros; we need to match int8_t 2822 // and friends, at least with glibc. 2823 // FIXME: Make sure 32/64-bit integers don't get defined to types of the wrong 2824 // width on unusual platforms. 2825 // FIXME: Make sure floating-point mappings are accurate 2826 // FIXME: Support XF and TF types 2827 QualType NewTy; 2828 switch (DestWidth) { 2829 case 0: 2830 S.Diag(Attr.getLoc(), diag::err_unknown_machine_mode) << Name; 2831 return; 2832 default: 2833 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2834 return; 2835 case 8: 2836 if (!IntegerMode) { 2837 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2838 return; 2839 } 2840 if (OldTy->isSignedIntegerType()) 2841 NewTy = S.Context.SignedCharTy; 2842 else 2843 NewTy = S.Context.UnsignedCharTy; 2844 break; 2845 case 16: 2846 if (!IntegerMode) { 2847 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2848 return; 2849 } 2850 if (OldTy->isSignedIntegerType()) 2851 NewTy = S.Context.ShortTy; 2852 else 2853 NewTy = S.Context.UnsignedShortTy; 2854 break; 2855 case 32: 2856 if (!IntegerMode) 2857 NewTy = S.Context.FloatTy; 2858 else if (OldTy->isSignedIntegerType()) 2859 NewTy = S.Context.IntTy; 2860 else 2861 NewTy = S.Context.UnsignedIntTy; 2862 break; 2863 case 64: 2864 if (!IntegerMode) 2865 NewTy = S.Context.DoubleTy; 2866 else if (OldTy->isSignedIntegerType()) 2867 if (S.Context.getTargetInfo().getLongWidth() == 64) 2868 NewTy = S.Context.LongTy; 2869 else 2870 NewTy = S.Context.LongLongTy; 2871 else 2872 if (S.Context.getTargetInfo().getLongWidth() == 64) 2873 NewTy = S.Context.UnsignedLongTy; 2874 else 2875 NewTy = S.Context.UnsignedLongLongTy; 2876 break; 2877 case 96: 2878 NewTy = S.Context.LongDoubleTy; 2879 break; 2880 case 128: 2881 if (!IntegerMode) { 2882 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2883 return; 2884 } 2885 if (OldTy->isSignedIntegerType()) 2886 NewTy = S.Context.Int128Ty; 2887 else 2888 NewTy = S.Context.UnsignedInt128Ty; 2889 break; 2890 } 2891 2892 if (ComplexMode) { 2893 NewTy = S.Context.getComplexType(NewTy); 2894 } 2895 2896 // Install the new type. 2897 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) { 2898 // FIXME: preserve existing source info. 2899 TD->setTypeSourceInfo(S.Context.getTrivialTypeSourceInfo(NewTy)); 2900 } else 2901 cast<ValueDecl>(D)->setType(NewTy); 2902} 2903 2904static void handleNoDebugAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2905 // check the attribute arguments. 2906 if (!checkAttributeNumArgs(S, Attr, 0)) 2907 return; 2908 2909 if (!isFunctionOrMethod(D)) { 2910 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2911 << Attr.getName() << ExpectedFunction; 2912 return; 2913 } 2914 2915 D->addAttr(::new (S.Context) NoDebugAttr(Attr.getRange(), S.Context)); 2916} 2917 2918static void handleNoInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2919 // check the attribute arguments. 2920 if (!checkAttributeNumArgs(S, Attr, 0)) 2921 return; 2922 2923 2924 if (!isa<FunctionDecl>(D)) { 2925 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2926 << Attr.getName() << ExpectedFunction; 2927 return; 2928 } 2929 2930 D->addAttr(::new (S.Context) NoInlineAttr(Attr.getRange(), S.Context)); 2931} 2932 2933static void handleNoInstrumentFunctionAttr(Sema &S, Decl *D, 2934 const AttributeList &Attr) { 2935 // check the attribute arguments. 2936 if (!checkAttributeNumArgs(S, Attr, 0)) 2937 return; 2938 2939 2940 if (!isa<FunctionDecl>(D)) { 2941 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2942 << Attr.getName() << ExpectedFunction; 2943 return; 2944 } 2945 2946 D->addAttr(::new (S.Context) NoInstrumentFunctionAttr(Attr.getRange(), 2947 S.Context)); 2948} 2949 2950static void handleConstantAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2951 if (S.LangOpts.CUDA) { 2952 // check the attribute arguments. 2953 if (Attr.hasParameterOrArguments()) { 2954 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2955 return; 2956 } 2957 2958 if (!isa<VarDecl>(D)) { 2959 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2960 << Attr.getName() << ExpectedVariable; 2961 return; 2962 } 2963 2964 D->addAttr(::new (S.Context) CUDAConstantAttr(Attr.getRange(), S.Context)); 2965 } else { 2966 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "constant"; 2967 } 2968} 2969 2970static void handleDeviceAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2971 if (S.LangOpts.CUDA) { 2972 // check the attribute arguments. 2973 if (Attr.getNumArgs() != 0) { 2974 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2975 return; 2976 } 2977 2978 if (!isa<FunctionDecl>(D) && !isa<VarDecl>(D)) { 2979 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2980 << Attr.getName() << ExpectedVariableOrFunction; 2981 return; 2982 } 2983 2984 D->addAttr(::new (S.Context) CUDADeviceAttr(Attr.getRange(), S.Context)); 2985 } else { 2986 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "device"; 2987 } 2988} 2989 2990static void handleGlobalAttr(Sema &S, Decl *D, const AttributeList &Attr) { 2991 if (S.LangOpts.CUDA) { 2992 // check the attribute arguments. 2993 if (!checkAttributeNumArgs(S, Attr, 0)) 2994 return; 2995 2996 if (!isa<FunctionDecl>(D)) { 2997 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2998 << Attr.getName() << ExpectedFunction; 2999 return; 3000 } 3001 3002 FunctionDecl *FD = cast<FunctionDecl>(D); 3003 if (!FD->getResultType()->isVoidType()) { 3004 TypeLoc TL = FD->getTypeSourceInfo()->getTypeLoc().IgnoreParens(); 3005 if (FunctionTypeLoc* FTL = dyn_cast<FunctionTypeLoc>(&TL)) { 3006 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 3007 << FD->getType() 3008 << FixItHint::CreateReplacement(FTL->getResultLoc().getSourceRange(), 3009 "void"); 3010 } else { 3011 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 3012 << FD->getType(); 3013 } 3014 return; 3015 } 3016 3017 D->addAttr(::new (S.Context) CUDAGlobalAttr(Attr.getRange(), S.Context)); 3018 } else { 3019 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "global"; 3020 } 3021} 3022 3023static void handleHostAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3024 if (S.LangOpts.CUDA) { 3025 // check the attribute arguments. 3026 if (!checkAttributeNumArgs(S, Attr, 0)) 3027 return; 3028 3029 3030 if (!isa<FunctionDecl>(D)) { 3031 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3032 << Attr.getName() << ExpectedFunction; 3033 return; 3034 } 3035 3036 D->addAttr(::new (S.Context) CUDAHostAttr(Attr.getRange(), S.Context)); 3037 } else { 3038 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "host"; 3039 } 3040} 3041 3042static void handleSharedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3043 if (S.LangOpts.CUDA) { 3044 // check the attribute arguments. 3045 if (!checkAttributeNumArgs(S, Attr, 0)) 3046 return; 3047 3048 3049 if (!isa<VarDecl>(D)) { 3050 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3051 << Attr.getName() << ExpectedVariable; 3052 return; 3053 } 3054 3055 D->addAttr(::new (S.Context) CUDASharedAttr(Attr.getRange(), S.Context)); 3056 } else { 3057 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "shared"; 3058 } 3059} 3060 3061static void handleGNUInlineAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3062 // check the attribute arguments. 3063 if (!checkAttributeNumArgs(S, Attr, 0)) 3064 return; 3065 3066 FunctionDecl *Fn = dyn_cast<FunctionDecl>(D); 3067 if (Fn == 0) { 3068 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3069 << Attr.getName() << ExpectedFunction; 3070 return; 3071 } 3072 3073 if (!Fn->isInlineSpecified()) { 3074 S.Diag(Attr.getLoc(), diag::warn_gnu_inline_attribute_requires_inline); 3075 return; 3076 } 3077 3078 D->addAttr(::new (S.Context) GNUInlineAttr(Attr.getRange(), S.Context)); 3079} 3080 3081static void handleCallConvAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3082 if (hasDeclarator(D)) return; 3083 3084 // Diagnostic is emitted elsewhere: here we store the (valid) Attr 3085 // in the Decl node for syntactic reasoning, e.g., pretty-printing. 3086 CallingConv CC; 3087 if (S.CheckCallingConvAttr(Attr, CC)) 3088 return; 3089 3090 if (!isa<ObjCMethodDecl>(D)) { 3091 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3092 << Attr.getName() << ExpectedFunctionOrMethod; 3093 return; 3094 } 3095 3096 switch (Attr.getKind()) { 3097 case AttributeList::AT_fastcall: 3098 D->addAttr(::new (S.Context) FastCallAttr(Attr.getRange(), S.Context)); 3099 return; 3100 case AttributeList::AT_stdcall: 3101 D->addAttr(::new (S.Context) StdCallAttr(Attr.getRange(), S.Context)); 3102 return; 3103 case AttributeList::AT_thiscall: 3104 D->addAttr(::new (S.Context) ThisCallAttr(Attr.getRange(), S.Context)); 3105 return; 3106 case AttributeList::AT_cdecl: 3107 D->addAttr(::new (S.Context) CDeclAttr(Attr.getRange(), S.Context)); 3108 return; 3109 case AttributeList::AT_pascal: 3110 D->addAttr(::new (S.Context) PascalAttr(Attr.getRange(), S.Context)); 3111 return; 3112 case AttributeList::AT_pcs: { 3113 Expr *Arg = Attr.getArg(0); 3114 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 3115 if (!Str || !Str->isAscii()) { 3116 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 3117 << "pcs" << 1; 3118 Attr.setInvalid(); 3119 return; 3120 } 3121 3122 StringRef StrRef = Str->getString(); 3123 PcsAttr::PCSType PCS; 3124 if (StrRef == "aapcs") 3125 PCS = PcsAttr::AAPCS; 3126 else if (StrRef == "aapcs-vfp") 3127 PCS = PcsAttr::AAPCS_VFP; 3128 else { 3129 S.Diag(Attr.getLoc(), diag::err_invalid_pcs); 3130 Attr.setInvalid(); 3131 return; 3132 } 3133 3134 D->addAttr(::new (S.Context) PcsAttr(Attr.getRange(), S.Context, PCS)); 3135 } 3136 default: 3137 llvm_unreachable("unexpected attribute kind"); 3138 } 3139} 3140 3141static void handleOpenCLKernelAttr(Sema &S, Decl *D, const AttributeList &Attr){ 3142 assert(!Attr.isInvalid()); 3143 D->addAttr(::new (S.Context) OpenCLKernelAttr(Attr.getRange(), S.Context)); 3144} 3145 3146bool Sema::CheckCallingConvAttr(const AttributeList &attr, CallingConv &CC) { 3147 if (attr.isInvalid()) 3148 return true; 3149 3150 if ((attr.getNumArgs() != 0 && 3151 !(attr.getKind() == AttributeList::AT_pcs && attr.getNumArgs() == 1)) || 3152 attr.getParameterName()) { 3153 Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 3154 attr.setInvalid(); 3155 return true; 3156 } 3157 3158 // TODO: diagnose uses of these conventions on the wrong target. Or, better 3159 // move to TargetAttributesSema one day. 3160 switch (attr.getKind()) { 3161 case AttributeList::AT_cdecl: CC = CC_C; break; 3162 case AttributeList::AT_fastcall: CC = CC_X86FastCall; break; 3163 case AttributeList::AT_stdcall: CC = CC_X86StdCall; break; 3164 case AttributeList::AT_thiscall: CC = CC_X86ThisCall; break; 3165 case AttributeList::AT_pascal: CC = CC_X86Pascal; break; 3166 case AttributeList::AT_pcs: { 3167 Expr *Arg = attr.getArg(0); 3168 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 3169 if (!Str || !Str->isAscii()) { 3170 Diag(attr.getLoc(), diag::err_attribute_argument_n_not_string) 3171 << "pcs" << 1; 3172 attr.setInvalid(); 3173 return true; 3174 } 3175 3176 StringRef StrRef = Str->getString(); 3177 if (StrRef == "aapcs") { 3178 CC = CC_AAPCS; 3179 break; 3180 } else if (StrRef == "aapcs-vfp") { 3181 CC = CC_AAPCS_VFP; 3182 break; 3183 } 3184 // FALLS THROUGH 3185 } 3186 default: llvm_unreachable("unexpected attribute kind"); 3187 } 3188 3189 return false; 3190} 3191 3192static void handleRegparmAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3193 if (hasDeclarator(D)) return; 3194 3195 unsigned numParams; 3196 if (S.CheckRegparmAttr(Attr, numParams)) 3197 return; 3198 3199 if (!isa<ObjCMethodDecl>(D)) { 3200 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3201 << Attr.getName() << ExpectedFunctionOrMethod; 3202 return; 3203 } 3204 3205 D->addAttr(::new (S.Context) RegparmAttr(Attr.getRange(), S.Context, numParams)); 3206} 3207 3208/// Checks a regparm attribute, returning true if it is ill-formed and 3209/// otherwise setting numParams to the appropriate value. 3210bool Sema::CheckRegparmAttr(const AttributeList &Attr, unsigned &numParams) { 3211 if (Attr.isInvalid()) 3212 return true; 3213 3214 if (Attr.getNumArgs() != 1) { 3215 Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 3216 Attr.setInvalid(); 3217 return true; 3218 } 3219 3220 Expr *NumParamsExpr = Attr.getArg(0); 3221 llvm::APSInt NumParams(32); 3222 if (NumParamsExpr->isTypeDependent() || NumParamsExpr->isValueDependent() || 3223 !NumParamsExpr->isIntegerConstantExpr(NumParams, Context)) { 3224 Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 3225 << "regparm" << NumParamsExpr->getSourceRange(); 3226 Attr.setInvalid(); 3227 return true; 3228 } 3229 3230 if (Context.getTargetInfo().getRegParmMax() == 0) { 3231 Diag(Attr.getLoc(), diag::err_attribute_regparm_wrong_platform) 3232 << NumParamsExpr->getSourceRange(); 3233 Attr.setInvalid(); 3234 return true; 3235 } 3236 3237 numParams = NumParams.getZExtValue(); 3238 if (numParams > Context.getTargetInfo().getRegParmMax()) { 3239 Diag(Attr.getLoc(), diag::err_attribute_regparm_invalid_number) 3240 << Context.getTargetInfo().getRegParmMax() << NumParamsExpr->getSourceRange(); 3241 Attr.setInvalid(); 3242 return true; 3243 } 3244 3245 return false; 3246} 3247 3248static void handleLaunchBoundsAttr(Sema &S, Decl *D, const AttributeList &Attr){ 3249 if (S.LangOpts.CUDA) { 3250 // check the attribute arguments. 3251 if (Attr.getNumArgs() != 1 && Attr.getNumArgs() != 2) { 3252 // FIXME: 0 is not okay. 3253 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 3254 return; 3255 } 3256 3257 if (!isFunctionOrMethod(D)) { 3258 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 3259 << Attr.getName() << ExpectedFunctionOrMethod; 3260 return; 3261 } 3262 3263 Expr *MaxThreadsExpr = Attr.getArg(0); 3264 llvm::APSInt MaxThreads(32); 3265 if (MaxThreadsExpr->isTypeDependent() || 3266 MaxThreadsExpr->isValueDependent() || 3267 !MaxThreadsExpr->isIntegerConstantExpr(MaxThreads, S.Context)) { 3268 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 3269 << "launch_bounds" << 1 << MaxThreadsExpr->getSourceRange(); 3270 return; 3271 } 3272 3273 llvm::APSInt MinBlocks(32); 3274 if (Attr.getNumArgs() > 1) { 3275 Expr *MinBlocksExpr = Attr.getArg(1); 3276 if (MinBlocksExpr->isTypeDependent() || 3277 MinBlocksExpr->isValueDependent() || 3278 !MinBlocksExpr->isIntegerConstantExpr(MinBlocks, S.Context)) { 3279 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 3280 << "launch_bounds" << 2 << MinBlocksExpr->getSourceRange(); 3281 return; 3282 } 3283 } 3284 3285 D->addAttr(::new (S.Context) CUDALaunchBoundsAttr(Attr.getRange(), S.Context, 3286 MaxThreads.getZExtValue(), 3287 MinBlocks.getZExtValue())); 3288 } else { 3289 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "launch_bounds"; 3290 } 3291} 3292 3293//===----------------------------------------------------------------------===// 3294// Checker-specific attribute handlers. 3295//===----------------------------------------------------------------------===// 3296 3297static bool isValidSubjectOfNSAttribute(Sema &S, QualType type) { 3298 return type->isDependentType() || 3299 type->isObjCObjectPointerType() || 3300 S.Context.isObjCNSObjectType(type); 3301} 3302static bool isValidSubjectOfCFAttribute(Sema &S, QualType type) { 3303 return type->isDependentType() || 3304 type->isPointerType() || 3305 isValidSubjectOfNSAttribute(S, type); 3306} 3307 3308static void handleNSConsumedAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3309 ParmVarDecl *param = dyn_cast<ParmVarDecl>(D); 3310 if (!param) { 3311 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 3312 << Attr.getRange() << Attr.getName() << ExpectedParameter; 3313 return; 3314 } 3315 3316 bool typeOK, cf; 3317 if (Attr.getKind() == AttributeList::AT_ns_consumed) { 3318 typeOK = isValidSubjectOfNSAttribute(S, param->getType()); 3319 cf = false; 3320 } else { 3321 typeOK = isValidSubjectOfCFAttribute(S, param->getType()); 3322 cf = true; 3323 } 3324 3325 if (!typeOK) { 3326 S.Diag(D->getLocStart(), diag::warn_ns_attribute_wrong_parameter_type) 3327 << Attr.getRange() << Attr.getName() << cf; 3328 return; 3329 } 3330 3331 if (cf) 3332 param->addAttr(::new (S.Context) CFConsumedAttr(Attr.getRange(), S.Context)); 3333 else 3334 param->addAttr(::new (S.Context) NSConsumedAttr(Attr.getRange(), S.Context)); 3335} 3336 3337static void handleNSConsumesSelfAttr(Sema &S, Decl *D, 3338 const AttributeList &Attr) { 3339 if (!isa<ObjCMethodDecl>(D)) { 3340 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 3341 << Attr.getRange() << Attr.getName() << ExpectedMethod; 3342 return; 3343 } 3344 3345 D->addAttr(::new (S.Context) NSConsumesSelfAttr(Attr.getRange(), S.Context)); 3346} 3347 3348static void handleNSReturnsRetainedAttr(Sema &S, Decl *D, 3349 const AttributeList &Attr) { 3350 3351 QualType returnType; 3352 3353 if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 3354 returnType = MD->getResultType(); 3355 else if (ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(D)) 3356 returnType = PD->getType(); 3357 else if (S.getLangOpts().ObjCAutoRefCount && hasDeclarator(D) && 3358 (Attr.getKind() == AttributeList::AT_ns_returns_retained)) 3359 return; // ignore: was handled as a type attribute 3360 else if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) 3361 returnType = FD->getResultType(); 3362 else { 3363 S.Diag(D->getLocStart(), diag::warn_attribute_wrong_decl_type) 3364 << Attr.getRange() << Attr.getName() 3365 << ExpectedFunctionOrMethod; 3366 return; 3367 } 3368 3369 bool typeOK; 3370 bool cf; 3371 switch (Attr.getKind()) { 3372 default: llvm_unreachable("invalid ownership attribute"); 3373 case AttributeList::AT_ns_returns_autoreleased: 3374 case AttributeList::AT_ns_returns_retained: 3375 case AttributeList::AT_ns_returns_not_retained: 3376 typeOK = isValidSubjectOfNSAttribute(S, returnType); 3377 cf = false; 3378 break; 3379 3380 case AttributeList::AT_cf_returns_retained: 3381 case AttributeList::AT_cf_returns_not_retained: 3382 typeOK = isValidSubjectOfCFAttribute(S, returnType); 3383 cf = true; 3384 break; 3385 } 3386 3387 if (!typeOK) { 3388 S.Diag(D->getLocStart(), diag::warn_ns_attribute_wrong_return_type) 3389 << Attr.getRange() << Attr.getName() << isa<ObjCMethodDecl>(D) << cf; 3390 return; 3391 } 3392 3393 switch (Attr.getKind()) { 3394 default: 3395 llvm_unreachable("invalid ownership attribute"); 3396 case AttributeList::AT_ns_returns_autoreleased: 3397 D->addAttr(::new (S.Context) NSReturnsAutoreleasedAttr(Attr.getRange(), 3398 S.Context)); 3399 return; 3400 case AttributeList::AT_cf_returns_not_retained: 3401 D->addAttr(::new (S.Context) CFReturnsNotRetainedAttr(Attr.getRange(), 3402 S.Context)); 3403 return; 3404 case AttributeList::AT_ns_returns_not_retained: 3405 D->addAttr(::new (S.Context) NSReturnsNotRetainedAttr(Attr.getRange(), 3406 S.Context)); 3407 return; 3408 case AttributeList::AT_cf_returns_retained: 3409 D->addAttr(::new (S.Context) CFReturnsRetainedAttr(Attr.getRange(), 3410 S.Context)); 3411 return; 3412 case AttributeList::AT_ns_returns_retained: 3413 D->addAttr(::new (S.Context) NSReturnsRetainedAttr(Attr.getRange(), 3414 S.Context)); 3415 return; 3416 }; 3417} 3418 3419static void handleObjCReturnsInnerPointerAttr(Sema &S, Decl *D, 3420 const AttributeList &attr) { 3421 SourceLocation loc = attr.getLoc(); 3422 3423 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(D); 3424 3425 if (!method) { 3426 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3427 << SourceRange(loc, loc) << attr.getName() << ExpectedMethod; 3428 return; 3429 } 3430 3431 // Check that the method returns a normal pointer. 3432 QualType resultType = method->getResultType(); 3433 3434 if (!resultType->isReferenceType() && 3435 (!resultType->isPointerType() || resultType->isObjCRetainableType())) { 3436 S.Diag(method->getLocStart(), diag::warn_ns_attribute_wrong_return_type) 3437 << SourceRange(loc) 3438 << attr.getName() << /*method*/ 1 << /*non-retainable pointer*/ 2; 3439 3440 // Drop the attribute. 3441 return; 3442 } 3443 3444 method->addAttr( 3445 ::new (S.Context) ObjCReturnsInnerPointerAttr(attr.getRange(), S.Context)); 3446} 3447 3448/// Handle cf_audited_transfer and cf_unknown_transfer. 3449static void handleCFTransferAttr(Sema &S, Decl *D, const AttributeList &A) { 3450 if (!isa<FunctionDecl>(D)) { 3451 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3452 << A.getRange() << A.getName() << ExpectedFunction; 3453 return; 3454 } 3455 3456 bool IsAudited = (A.getKind() == AttributeList::AT_cf_audited_transfer); 3457 3458 // Check whether there's a conflicting attribute already present. 3459 Attr *Existing; 3460 if (IsAudited) { 3461 Existing = D->getAttr<CFUnknownTransferAttr>(); 3462 } else { 3463 Existing = D->getAttr<CFAuditedTransferAttr>(); 3464 } 3465 if (Existing) { 3466 S.Diag(D->getLocStart(), diag::err_attributes_are_not_compatible) 3467 << A.getName() 3468 << (IsAudited ? "cf_unknown_transfer" : "cf_audited_transfer") 3469 << A.getRange() << Existing->getRange(); 3470 return; 3471 } 3472 3473 // All clear; add the attribute. 3474 if (IsAudited) { 3475 D->addAttr( 3476 ::new (S.Context) CFAuditedTransferAttr(A.getRange(), S.Context)); 3477 } else { 3478 D->addAttr( 3479 ::new (S.Context) CFUnknownTransferAttr(A.getRange(), S.Context)); 3480 } 3481} 3482 3483static void handleNSBridgedAttr(Sema &S, Scope *Sc, Decl *D, 3484 const AttributeList &Attr) { 3485 RecordDecl *RD = dyn_cast<RecordDecl>(D); 3486 if (!RD || RD->isUnion()) { 3487 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3488 << Attr.getRange() << Attr.getName() << ExpectedStruct; 3489 } 3490 3491 IdentifierInfo *ParmName = Attr.getParameterName(); 3492 3493 // In Objective-C, verify that the type names an Objective-C type. 3494 // We don't want to check this outside of ObjC because people sometimes 3495 // do crazy C declarations of Objective-C types. 3496 if (ParmName && S.getLangOpts().ObjC1) { 3497 // Check for an existing type with this name. 3498 LookupResult R(S, DeclarationName(ParmName), Attr.getParameterLoc(), 3499 Sema::LookupOrdinaryName); 3500 if (S.LookupName(R, Sc)) { 3501 NamedDecl *Target = R.getFoundDecl(); 3502 if (Target && !isa<ObjCInterfaceDecl>(Target)) { 3503 S.Diag(D->getLocStart(), diag::err_ns_bridged_not_interface); 3504 S.Diag(Target->getLocStart(), diag::note_declared_at); 3505 } 3506 } 3507 } 3508 3509 D->addAttr(::new (S.Context) NSBridgedAttr(Attr.getRange(), S.Context, 3510 ParmName)); 3511} 3512 3513static void handleObjCOwnershipAttr(Sema &S, Decl *D, 3514 const AttributeList &Attr) { 3515 if (hasDeclarator(D)) return; 3516 3517 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3518 << Attr.getRange() << Attr.getName() << ExpectedVariable; 3519} 3520 3521static void handleObjCPreciseLifetimeAttr(Sema &S, Decl *D, 3522 const AttributeList &Attr) { 3523 if (!isa<VarDecl>(D) && !isa<FieldDecl>(D)) { 3524 S.Diag(D->getLocStart(), diag::err_attribute_wrong_decl_type) 3525 << Attr.getRange() << Attr.getName() << ExpectedVariable; 3526 return; 3527 } 3528 3529 ValueDecl *vd = cast<ValueDecl>(D); 3530 QualType type = vd->getType(); 3531 3532 if (!type->isDependentType() && 3533 !type->isObjCLifetimeType()) { 3534 S.Diag(Attr.getLoc(), diag::err_objc_precise_lifetime_bad_type) 3535 << type; 3536 return; 3537 } 3538 3539 Qualifiers::ObjCLifetime lifetime = type.getObjCLifetime(); 3540 3541 // If we have no lifetime yet, check the lifetime we're presumably 3542 // going to infer. 3543 if (lifetime == Qualifiers::OCL_None && !type->isDependentType()) 3544 lifetime = type->getObjCARCImplicitLifetime(); 3545 3546 switch (lifetime) { 3547 case Qualifiers::OCL_None: 3548 assert(type->isDependentType() && 3549 "didn't infer lifetime for non-dependent type?"); 3550 break; 3551 3552 case Qualifiers::OCL_Weak: // meaningful 3553 case Qualifiers::OCL_Strong: // meaningful 3554 break; 3555 3556 case Qualifiers::OCL_ExplicitNone: 3557 case Qualifiers::OCL_Autoreleasing: 3558 S.Diag(Attr.getLoc(), diag::warn_objc_precise_lifetime_meaningless) 3559 << (lifetime == Qualifiers::OCL_Autoreleasing); 3560 break; 3561 } 3562 3563 D->addAttr(::new (S.Context) 3564 ObjCPreciseLifetimeAttr(Attr.getRange(), S.Context)); 3565} 3566 3567static bool isKnownDeclSpecAttr(const AttributeList &Attr) { 3568 switch (Attr.getKind()) { 3569 default: 3570 return false; 3571 case AttributeList::AT_dllimport: 3572 case AttributeList::AT_dllexport: 3573 case AttributeList::AT_uuid: 3574 case AttributeList::AT_deprecated: 3575 case AttributeList::AT_noreturn: 3576 case AttributeList::AT_nothrow: 3577 case AttributeList::AT_naked: 3578 case AttributeList::AT_noinline: 3579 return true; 3580 } 3581} 3582 3583//===----------------------------------------------------------------------===// 3584// Microsoft specific attribute handlers. 3585//===----------------------------------------------------------------------===// 3586 3587static void handleUuidAttr(Sema &S, Decl *D, const AttributeList &Attr) { 3588 if (S.LangOpts.MicrosoftExt || S.LangOpts.Borland) { 3589 // check the attribute arguments. 3590 if (!checkAttributeNumArgs(S, Attr, 1)) 3591 return; 3592 3593 Expr *Arg = Attr.getArg(0); 3594 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 3595 if (!Str || !Str->isAscii()) { 3596 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 3597 << "uuid" << 1; 3598 return; 3599 } 3600 3601 StringRef StrRef = Str->getString(); 3602 3603 bool IsCurly = StrRef.size() > 1 && StrRef.front() == '{' && 3604 StrRef.back() == '}'; 3605 3606 // Validate GUID length. 3607 if (IsCurly && StrRef.size() != 38) { 3608 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3609 return; 3610 } 3611 if (!IsCurly && StrRef.size() != 36) { 3612 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3613 return; 3614 } 3615 3616 // GUID format is "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX" or 3617 // "{XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX}" 3618 StringRef::iterator I = StrRef.begin(); 3619 if (IsCurly) // Skip the optional '{' 3620 ++I; 3621 3622 for (int i = 0; i < 36; ++i) { 3623 if (i == 8 || i == 13 || i == 18 || i == 23) { 3624 if (*I != '-') { 3625 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3626 return; 3627 } 3628 } else if (!isxdigit(*I)) { 3629 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 3630 return; 3631 } 3632 I++; 3633 } 3634 3635 D->addAttr(::new (S.Context) UuidAttr(Attr.getRange(), S.Context, 3636 Str->getString())); 3637 } else 3638 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "uuid"; 3639} 3640 3641//===----------------------------------------------------------------------===// 3642// Top Level Sema Entry Points 3643//===----------------------------------------------------------------------===// 3644 3645static void ProcessNonInheritableDeclAttr(Sema &S, Scope *scope, Decl *D, 3646 const AttributeList &Attr) { 3647 switch (Attr.getKind()) { 3648 case AttributeList::AT_device: handleDeviceAttr (S, D, Attr); break; 3649 case AttributeList::AT_host: handleHostAttr (S, D, Attr); break; 3650 case AttributeList::AT_overloadable:handleOverloadableAttr(S, D, Attr); break; 3651 default: 3652 break; 3653 } 3654} 3655 3656static void ProcessInheritableDeclAttr(Sema &S, Scope *scope, Decl *D, 3657 const AttributeList &Attr) { 3658 switch (Attr.getKind()) { 3659 case AttributeList::AT_ibaction: handleIBAction(S, D, Attr); break; 3660 case AttributeList::AT_iboutlet: handleIBOutlet(S, D, Attr); break; 3661 case AttributeList::AT_iboutletcollection: 3662 handleIBOutletCollection(S, D, Attr); break; 3663 case AttributeList::AT_address_space: 3664 case AttributeList::AT_opencl_image_access: 3665 case AttributeList::AT_objc_gc: 3666 case AttributeList::AT_vector_size: 3667 case AttributeList::AT_neon_vector_type: 3668 case AttributeList::AT_neon_polyvector_type: 3669 // Ignore these, these are type attributes, handled by 3670 // ProcessTypeAttributes. 3671 break; 3672 case AttributeList::AT_device: 3673 case AttributeList::AT_host: 3674 case AttributeList::AT_overloadable: 3675 // Ignore, this is a non-inheritable attribute, handled 3676 // by ProcessNonInheritableDeclAttr. 3677 break; 3678 case AttributeList::AT_alias: handleAliasAttr (S, D, Attr); break; 3679 case AttributeList::AT_aligned: handleAlignedAttr (S, D, Attr); break; 3680 case AttributeList::AT_always_inline: 3681 handleAlwaysInlineAttr (S, D, Attr); break; 3682 case AttributeList::AT_analyzer_noreturn: 3683 handleAnalyzerNoReturnAttr (S, D, Attr); break; 3684 case AttributeList::AT_annotate: handleAnnotateAttr (S, D, Attr); break; 3685 case AttributeList::AT_availability:handleAvailabilityAttr(S, D, Attr); break; 3686 case AttributeList::AT_carries_dependency: 3687 handleDependencyAttr (S, D, Attr); break; 3688 case AttributeList::AT_common: handleCommonAttr (S, D, Attr); break; 3689 case AttributeList::AT_constant: handleConstantAttr (S, D, Attr); break; 3690 case AttributeList::AT_constructor: handleConstructorAttr (S, D, Attr); break; 3691 case AttributeList::AT_deprecated: handleDeprecatedAttr (S, D, Attr); break; 3692 case AttributeList::AT_destructor: handleDestructorAttr (S, D, Attr); break; 3693 case AttributeList::AT_ext_vector_type: 3694 handleExtVectorTypeAttr(S, scope, D, Attr); 3695 break; 3696 case AttributeList::AT_format: handleFormatAttr (S, D, Attr); break; 3697 case AttributeList::AT_format_arg: handleFormatArgAttr (S, D, Attr); break; 3698 case AttributeList::AT_global: handleGlobalAttr (S, D, Attr); break; 3699 case AttributeList::AT_gnu_inline: handleGNUInlineAttr (S, D, Attr); break; 3700 case AttributeList::AT_launch_bounds: 3701 handleLaunchBoundsAttr(S, D, Attr); 3702 break; 3703 case AttributeList::AT_mode: handleModeAttr (S, D, Attr); break; 3704 case AttributeList::AT_malloc: handleMallocAttr (S, D, Attr); break; 3705 case AttributeList::AT_may_alias: handleMayAliasAttr (S, D, Attr); break; 3706 case AttributeList::AT_nocommon: handleNoCommonAttr (S, D, Attr); break; 3707 case AttributeList::AT_nonnull: handleNonNullAttr (S, D, Attr); break; 3708 case AttributeList::AT_ownership_returns: 3709 case AttributeList::AT_ownership_takes: 3710 case AttributeList::AT_ownership_holds: 3711 handleOwnershipAttr (S, D, Attr); break; 3712 case AttributeList::AT_naked: handleNakedAttr (S, D, Attr); break; 3713 case AttributeList::AT_noreturn: handleNoReturnAttr (S, D, Attr); break; 3714 case AttributeList::AT_nothrow: handleNothrowAttr (S, D, Attr); break; 3715 case AttributeList::AT_shared: handleSharedAttr (S, D, Attr); break; 3716 case AttributeList::AT_vecreturn: handleVecReturnAttr (S, D, Attr); break; 3717 3718 case AttributeList::AT_objc_ownership: 3719 handleObjCOwnershipAttr(S, D, Attr); break; 3720 case AttributeList::AT_objc_precise_lifetime: 3721 handleObjCPreciseLifetimeAttr(S, D, Attr); break; 3722 3723 case AttributeList::AT_objc_returns_inner_pointer: 3724 handleObjCReturnsInnerPointerAttr(S, D, Attr); break; 3725 3726 case AttributeList::AT_ns_bridged: 3727 handleNSBridgedAttr(S, scope, D, Attr); break; 3728 3729 case AttributeList::AT_cf_audited_transfer: 3730 case AttributeList::AT_cf_unknown_transfer: 3731 handleCFTransferAttr(S, D, Attr); break; 3732 3733 // Checker-specific. 3734 case AttributeList::AT_cf_consumed: 3735 case AttributeList::AT_ns_consumed: handleNSConsumedAttr (S, D, Attr); break; 3736 case AttributeList::AT_ns_consumes_self: 3737 handleNSConsumesSelfAttr(S, D, Attr); break; 3738 3739 case AttributeList::AT_ns_returns_autoreleased: 3740 case AttributeList::AT_ns_returns_not_retained: 3741 case AttributeList::AT_cf_returns_not_retained: 3742 case AttributeList::AT_ns_returns_retained: 3743 case AttributeList::AT_cf_returns_retained: 3744 handleNSReturnsRetainedAttr(S, D, Attr); break; 3745 3746 case AttributeList::AT_reqd_work_group_size: 3747 handleReqdWorkGroupSize(S, D, Attr); break; 3748 3749 case AttributeList::AT_init_priority: 3750 handleInitPriorityAttr(S, D, Attr); break; 3751 3752 case AttributeList::AT_packed: handlePackedAttr (S, D, Attr); break; 3753 case AttributeList::AT_ms_struct: handleMsStructAttr (S, D, Attr); break; 3754 case AttributeList::AT_section: handleSectionAttr (S, D, Attr); break; 3755 case AttributeList::AT_unavailable: handleUnavailableAttr (S, D, Attr); break; 3756 case AttributeList::AT_objc_arc_weak_reference_unavailable: 3757 handleArcWeakrefUnavailableAttr (S, D, Attr); 3758 break; 3759 case AttributeList::AT_objc_root_class: 3760 handleObjCRootClassAttr(S, D, Attr); 3761 break; 3762 case AttributeList::AT_objc_requires_property_definitions: 3763 handleObjCRequiresPropertyDefsAttr (S, D, Attr); 3764 break; 3765 case AttributeList::AT_unused: handleUnusedAttr (S, D, Attr); break; 3766 case AttributeList::AT_returns_twice: 3767 handleReturnsTwiceAttr(S, D, Attr); 3768 break; 3769 case AttributeList::AT_used: handleUsedAttr (S, D, Attr); break; 3770 case AttributeList::AT_visibility: handleVisibilityAttr (S, D, Attr); break; 3771 case AttributeList::AT_warn_unused_result: handleWarnUnusedResult(S, D, Attr); 3772 break; 3773 case AttributeList::AT_weak: handleWeakAttr (S, D, Attr); break; 3774 case AttributeList::AT_weakref: handleWeakRefAttr (S, D, Attr); break; 3775 case AttributeList::AT_weak_import: handleWeakImportAttr (S, D, Attr); break; 3776 case AttributeList::AT_transparent_union: 3777 handleTransparentUnionAttr(S, D, Attr); 3778 break; 3779 case AttributeList::AT_objc_exception: 3780 handleObjCExceptionAttr(S, D, Attr); 3781 break; 3782 case AttributeList::AT_objc_method_family: 3783 handleObjCMethodFamilyAttr(S, D, Attr); 3784 break; 3785 case AttributeList::AT_NSObject: handleObjCNSObject (S, D, Attr); break; 3786 case AttributeList::AT_blocks: handleBlocksAttr (S, D, Attr); break; 3787 case AttributeList::AT_sentinel: handleSentinelAttr (S, D, Attr); break; 3788 case AttributeList::AT_const: handleConstAttr (S, D, Attr); break; 3789 case AttributeList::AT_pure: handlePureAttr (S, D, Attr); break; 3790 case AttributeList::AT_cleanup: handleCleanupAttr (S, D, Attr); break; 3791 case AttributeList::AT_nodebug: handleNoDebugAttr (S, D, Attr); break; 3792 case AttributeList::AT_noinline: handleNoInlineAttr (S, D, Attr); break; 3793 case AttributeList::AT_regparm: handleRegparmAttr (S, D, Attr); break; 3794 case AttributeList::IgnoredAttribute: 3795 // Just ignore 3796 break; 3797 case AttributeList::AT_no_instrument_function: // Interacts with -pg. 3798 handleNoInstrumentFunctionAttr(S, D, Attr); 3799 break; 3800 case AttributeList::AT_stdcall: 3801 case AttributeList::AT_cdecl: 3802 case AttributeList::AT_fastcall: 3803 case AttributeList::AT_thiscall: 3804 case AttributeList::AT_pascal: 3805 case AttributeList::AT_pcs: 3806 handleCallConvAttr(S, D, Attr); 3807 break; 3808 case AttributeList::AT_opencl_kernel_function: 3809 handleOpenCLKernelAttr(S, D, Attr); 3810 break; 3811 case AttributeList::AT_uuid: 3812 handleUuidAttr(S, D, Attr); 3813 break; 3814 3815 // Thread safety attributes: 3816 case AttributeList::AT_guarded_var: 3817 handleGuardedVarAttr(S, D, Attr); 3818 break; 3819 case AttributeList::AT_pt_guarded_var: 3820 handleGuardedVarAttr(S, D, Attr, /*pointer = */true); 3821 break; 3822 case AttributeList::AT_scoped_lockable: 3823 handleLockableAttr(S, D, Attr, /*scoped = */true); 3824 break; 3825 case AttributeList::AT_no_address_safety_analysis: 3826 handleNoAddressSafetyAttr(S, D, Attr); 3827 break; 3828 case AttributeList::AT_no_thread_safety_analysis: 3829 handleNoThreadSafetyAttr(S, D, Attr); 3830 break; 3831 case AttributeList::AT_lockable: 3832 handleLockableAttr(S, D, Attr); 3833 break; 3834 case AttributeList::AT_guarded_by: 3835 handleGuardedByAttr(S, D, Attr); 3836 break; 3837 case AttributeList::AT_pt_guarded_by: 3838 handleGuardedByAttr(S, D, Attr, /*pointer = */true); 3839 break; 3840 case AttributeList::AT_exclusive_lock_function: 3841 handleLockFunAttr(S, D, Attr, /*exclusive = */true); 3842 break; 3843 case AttributeList::AT_exclusive_locks_required: 3844 handleLocksRequiredAttr(S, D, Attr, /*exclusive = */true); 3845 break; 3846 case AttributeList::AT_exclusive_trylock_function: 3847 handleTrylockFunAttr(S, D, Attr, /*exclusive = */true); 3848 break; 3849 case AttributeList::AT_lock_returned: 3850 handleLockReturnedAttr(S, D, Attr); 3851 break; 3852 case AttributeList::AT_locks_excluded: 3853 handleLocksExcludedAttr(S, D, Attr); 3854 break; 3855 case AttributeList::AT_shared_lock_function: 3856 handleLockFunAttr(S, D, Attr); 3857 break; 3858 case AttributeList::AT_shared_locks_required: 3859 handleLocksRequiredAttr(S, D, Attr); 3860 break; 3861 case AttributeList::AT_shared_trylock_function: 3862 handleTrylockFunAttr(S, D, Attr); 3863 break; 3864 case AttributeList::AT_unlock_function: 3865 handleUnlockFunAttr(S, D, Attr); 3866 break; 3867 case AttributeList::AT_acquired_before: 3868 handleAcquireOrderAttr(S, D, Attr, /*before = */true); 3869 break; 3870 case AttributeList::AT_acquired_after: 3871 handleAcquireOrderAttr(S, D, Attr, /*before = */false); 3872 break; 3873 3874 default: 3875 // Ask target about the attribute. 3876 const TargetAttributesSema &TargetAttrs = S.getTargetAttributesSema(); 3877 if (!TargetAttrs.ProcessDeclAttribute(scope, D, Attr, S)) 3878 S.Diag(Attr.getLoc(), diag::warn_unknown_attribute_ignored) 3879 << Attr.getName(); 3880 break; 3881 } 3882} 3883 3884/// ProcessDeclAttribute - Apply the specific attribute to the specified decl if 3885/// the attribute applies to decls. If the attribute is a type attribute, just 3886/// silently ignore it if a GNU attribute. FIXME: Applying a C++0x attribute to 3887/// the wrong thing is illegal (C++0x [dcl.attr.grammar]/4). 3888static void ProcessDeclAttribute(Sema &S, Scope *scope, Decl *D, 3889 const AttributeList &Attr, 3890 bool NonInheritable, bool Inheritable) { 3891 if (Attr.isInvalid()) 3892 return; 3893 3894 if (Attr.isDeclspecAttribute() && !isKnownDeclSpecAttr(Attr)) 3895 // FIXME: Try to deal with other __declspec attributes! 3896 return; 3897 3898 if (NonInheritable) 3899 ProcessNonInheritableDeclAttr(S, scope, D, Attr); 3900 3901 if (Inheritable) 3902 ProcessInheritableDeclAttr(S, scope, D, Attr); 3903} 3904 3905/// ProcessDeclAttributeList - Apply all the decl attributes in the specified 3906/// attribute list to the specified decl, ignoring any type attributes. 3907void Sema::ProcessDeclAttributeList(Scope *S, Decl *D, 3908 const AttributeList *AttrList, 3909 bool NonInheritable, bool Inheritable) { 3910 for (const AttributeList* l = AttrList; l; l = l->getNext()) { 3911 ProcessDeclAttribute(*this, S, D, *l, NonInheritable, Inheritable); 3912 } 3913 3914 // GCC accepts 3915 // static int a9 __attribute__((weakref)); 3916 // but that looks really pointless. We reject it. 3917 if (Inheritable && D->hasAttr<WeakRefAttr>() && !D->hasAttr<AliasAttr>()) { 3918 Diag(AttrList->getLoc(), diag::err_attribute_weakref_without_alias) << 3919 dyn_cast<NamedDecl>(D)->getNameAsString(); 3920 return; 3921 } 3922} 3923 3924// Annotation attributes are the only attributes allowed after an access 3925// specifier. 3926bool Sema::ProcessAccessDeclAttributeList(AccessSpecDecl *ASDecl, 3927 const AttributeList *AttrList) { 3928 for (const AttributeList* l = AttrList; l; l = l->getNext()) { 3929 if (l->getKind() == AttributeList::AT_annotate) { 3930 handleAnnotateAttr(*this, ASDecl, *l); 3931 } else { 3932 Diag(l->getLoc(), diag::err_only_annotate_after_access_spec); 3933 return true; 3934 } 3935 } 3936 3937 return false; 3938} 3939 3940/// checkUnusedDeclAttributes - Check a list of attributes to see if it 3941/// contains any decl attributes that we should warn about. 3942static void checkUnusedDeclAttributes(Sema &S, const AttributeList *A) { 3943 for ( ; A; A = A->getNext()) { 3944 // Only warn if the attribute is an unignored, non-type attribute. 3945 if (A->isUsedAsTypeAttr()) continue; 3946 if (A->getKind() == AttributeList::IgnoredAttribute) continue; 3947 3948 if (A->getKind() == AttributeList::UnknownAttribute) { 3949 S.Diag(A->getLoc(), diag::warn_unknown_attribute_ignored) 3950 << A->getName() << A->getRange(); 3951 } else { 3952 S.Diag(A->getLoc(), diag::warn_attribute_not_on_decl) 3953 << A->getName() << A->getRange(); 3954 } 3955 } 3956} 3957 3958/// checkUnusedDeclAttributes - Given a declarator which is not being 3959/// used to build a declaration, complain about any decl attributes 3960/// which might be lying around on it. 3961void Sema::checkUnusedDeclAttributes(Declarator &D) { 3962 ::checkUnusedDeclAttributes(*this, D.getDeclSpec().getAttributes().getList()); 3963 ::checkUnusedDeclAttributes(*this, D.getAttributes()); 3964 for (unsigned i = 0, e = D.getNumTypeObjects(); i != e; ++i) 3965 ::checkUnusedDeclAttributes(*this, D.getTypeObject(i).getAttrs()); 3966} 3967 3968/// DeclClonePragmaWeak - clone existing decl (maybe definition), 3969/// #pragma weak needs a non-definition decl and source may not have one 3970NamedDecl * Sema::DeclClonePragmaWeak(NamedDecl *ND, IdentifierInfo *II, 3971 SourceLocation Loc) { 3972 assert(isa<FunctionDecl>(ND) || isa<VarDecl>(ND)); 3973 NamedDecl *NewD = 0; 3974 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(ND)) { 3975 FunctionDecl *NewFD; 3976 // FIXME: Missing call to CheckFunctionDeclaration(). 3977 // FIXME: Mangling? 3978 // FIXME: Is the qualifier info correct? 3979 // FIXME: Is the DeclContext correct? 3980 NewFD = FunctionDecl::Create(FD->getASTContext(), FD->getDeclContext(), 3981 Loc, Loc, DeclarationName(II), 3982 FD->getType(), FD->getTypeSourceInfo(), 3983 SC_None, SC_None, 3984 false/*isInlineSpecified*/, 3985 FD->hasPrototype(), 3986 false/*isConstexprSpecified*/); 3987 NewD = NewFD; 3988 3989 if (FD->getQualifier()) 3990 NewFD->setQualifierInfo(FD->getQualifierLoc()); 3991 3992 // Fake up parameter variables; they are declared as if this were 3993 // a typedef. 3994 QualType FDTy = FD->getType(); 3995 if (const FunctionProtoType *FT = FDTy->getAs<FunctionProtoType>()) { 3996 SmallVector<ParmVarDecl*, 16> Params; 3997 for (FunctionProtoType::arg_type_iterator AI = FT->arg_type_begin(), 3998 AE = FT->arg_type_end(); AI != AE; ++AI) { 3999 ParmVarDecl *Param = BuildParmVarDeclForTypedef(NewFD, Loc, *AI); 4000 Param->setScopeInfo(0, Params.size()); 4001 Params.push_back(Param); 4002 } 4003 NewFD->setParams(Params); 4004 } 4005 } else if (VarDecl *VD = dyn_cast<VarDecl>(ND)) { 4006 NewD = VarDecl::Create(VD->getASTContext(), VD->getDeclContext(), 4007 VD->getInnerLocStart(), VD->getLocation(), II, 4008 VD->getType(), VD->getTypeSourceInfo(), 4009 VD->getStorageClass(), 4010 VD->getStorageClassAsWritten()); 4011 if (VD->getQualifier()) { 4012 VarDecl *NewVD = cast<VarDecl>(NewD); 4013 NewVD->setQualifierInfo(VD->getQualifierLoc()); 4014 } 4015 } 4016 return NewD; 4017} 4018 4019/// DeclApplyPragmaWeak - A declaration (maybe definition) needs #pragma weak 4020/// applied to it, possibly with an alias. 4021void Sema::DeclApplyPragmaWeak(Scope *S, NamedDecl *ND, WeakInfo &W) { 4022 if (W.getUsed()) return; // only do this once 4023 W.setUsed(true); 4024 if (W.getAlias()) { // clone decl, impersonate __attribute(weak,alias(...)) 4025 IdentifierInfo *NDId = ND->getIdentifier(); 4026 NamedDecl *NewD = DeclClonePragmaWeak(ND, W.getAlias(), W.getLocation()); 4027 NewD->addAttr(::new (Context) AliasAttr(W.getLocation(), Context, 4028 NDId->getName())); 4029 NewD->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 4030 WeakTopLevelDecl.push_back(NewD); 4031 // FIXME: "hideous" code from Sema::LazilyCreateBuiltin 4032 // to insert Decl at TU scope, sorry. 4033 DeclContext *SavedContext = CurContext; 4034 CurContext = Context.getTranslationUnitDecl(); 4035 PushOnScopeChains(NewD, S); 4036 CurContext = SavedContext; 4037 } else { // just add weak to existing 4038 ND->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 4039 } 4040} 4041 4042/// ProcessDeclAttributes - Given a declarator (PD) with attributes indicated in 4043/// it, apply them to D. This is a bit tricky because PD can have attributes 4044/// specified in many different places, and we need to find and apply them all. 4045void Sema::ProcessDeclAttributes(Scope *S, Decl *D, const Declarator &PD, 4046 bool NonInheritable, bool Inheritable) { 4047 // It's valid to "forward-declare" #pragma weak, in which case we 4048 // have to do this. 4049 if (Inheritable) { 4050 LoadExternalWeakUndeclaredIdentifiers(); 4051 if (!WeakUndeclaredIdentifiers.empty()) { 4052 if (NamedDecl *ND = dyn_cast<NamedDecl>(D)) { 4053 if (IdentifierInfo *Id = ND->getIdentifier()) { 4054 llvm::DenseMap<IdentifierInfo*,WeakInfo>::iterator I 4055 = WeakUndeclaredIdentifiers.find(Id); 4056 if (I != WeakUndeclaredIdentifiers.end() && ND->hasLinkage()) { 4057 WeakInfo W = I->second; 4058 DeclApplyPragmaWeak(S, ND, W); 4059 WeakUndeclaredIdentifiers[Id] = W; 4060 } 4061 } 4062 } 4063 } 4064 } 4065 4066 // Apply decl attributes from the DeclSpec if present. 4067 if (const AttributeList *Attrs = PD.getDeclSpec().getAttributes().getList()) 4068 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 4069 4070 // Walk the declarator structure, applying decl attributes that were in a type 4071 // position to the decl itself. This handles cases like: 4072 // int *__attr__(x)** D; 4073 // when X is a decl attribute. 4074 for (unsigned i = 0, e = PD.getNumTypeObjects(); i != e; ++i) 4075 if (const AttributeList *Attrs = PD.getTypeObject(i).getAttrs()) 4076 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 4077 4078 // Finally, apply any attributes on the decl itself. 4079 if (const AttributeList *Attrs = PD.getAttributes()) 4080 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 4081} 4082 4083/// Is the given declaration allowed to use a forbidden type? 4084static bool isForbiddenTypeAllowed(Sema &S, Decl *decl) { 4085 // Private ivars are always okay. Unfortunately, people don't 4086 // always properly make their ivars private, even in system headers. 4087 // Plus we need to make fields okay, too. 4088 // Function declarations in sys headers will be marked unavailable. 4089 if (!isa<FieldDecl>(decl) && !isa<ObjCPropertyDecl>(decl) && 4090 !isa<FunctionDecl>(decl)) 4091 return false; 4092 4093 // Require it to be declared in a system header. 4094 return S.Context.getSourceManager().isInSystemHeader(decl->getLocation()); 4095} 4096 4097/// Handle a delayed forbidden-type diagnostic. 4098static void handleDelayedForbiddenType(Sema &S, DelayedDiagnostic &diag, 4099 Decl *decl) { 4100 if (decl && isForbiddenTypeAllowed(S, decl)) { 4101 decl->addAttr(new (S.Context) UnavailableAttr(diag.Loc, S.Context, 4102 "this system declaration uses an unsupported type")); 4103 return; 4104 } 4105 if (S.getLangOpts().ObjCAutoRefCount) 4106 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(decl)) { 4107 // FIXME. we may want to supress diagnostics for all 4108 // kind of forbidden type messages on unavailable functions. 4109 if (FD->hasAttr<UnavailableAttr>() && 4110 diag.getForbiddenTypeDiagnostic() == 4111 diag::err_arc_array_param_no_ownership) { 4112 diag.Triggered = true; 4113 return; 4114 } 4115 } 4116 4117 S.Diag(diag.Loc, diag.getForbiddenTypeDiagnostic()) 4118 << diag.getForbiddenTypeOperand() << diag.getForbiddenTypeArgument(); 4119 diag.Triggered = true; 4120} 4121 4122// This duplicates a vector push_back but hides the need to know the 4123// size of the type. 4124void Sema::DelayedDiagnostics::add(const DelayedDiagnostic &diag) { 4125 assert(StackSize <= StackCapacity); 4126 4127 // Grow the stack if necessary. 4128 if (StackSize == StackCapacity) { 4129 unsigned newCapacity = 2 * StackCapacity + 2; 4130 char *newBuffer = new char[newCapacity * sizeof(DelayedDiagnostic)]; 4131 const char *oldBuffer = (const char*) Stack; 4132 4133 if (StackCapacity) 4134 memcpy(newBuffer, oldBuffer, StackCapacity * sizeof(DelayedDiagnostic)); 4135 4136 delete[] oldBuffer; 4137 Stack = reinterpret_cast<sema::DelayedDiagnostic*>(newBuffer); 4138 StackCapacity = newCapacity; 4139 } 4140 4141 assert(StackSize < StackCapacity); 4142 new (&Stack[StackSize++]) DelayedDiagnostic(diag); 4143} 4144 4145void Sema::DelayedDiagnostics::popParsingDecl(Sema &S, ParsingDeclState state, 4146 Decl *decl) { 4147 DelayedDiagnostics &DD = S.DelayedDiagnostics; 4148 4149 // Check the invariants. 4150 assert(DD.StackSize >= state.SavedStackSize); 4151 assert(state.SavedStackSize >= DD.ActiveStackBase); 4152 assert(DD.ParsingDepth > 0); 4153 4154 // Drop the parsing depth. 4155 DD.ParsingDepth--; 4156 4157 // If there are no active diagnostics, we're done. 4158 if (DD.StackSize == DD.ActiveStackBase) 4159 return; 4160 4161 // We only want to actually emit delayed diagnostics when we 4162 // successfully parsed a decl. 4163 if (decl) { 4164 // We emit all the active diagnostics, not just those starting 4165 // from the saved state. The idea is this: we get one push for a 4166 // decl spec and another for each declarator; in a decl group like: 4167 // deprecated_typedef foo, *bar, baz(); 4168 // only the declarator pops will be passed decls. This is correct; 4169 // we really do need to consider delayed diagnostics from the decl spec 4170 // for each of the different declarations. 4171 for (unsigned i = DD.ActiveStackBase, e = DD.StackSize; i != e; ++i) { 4172 DelayedDiagnostic &diag = DD.Stack[i]; 4173 if (diag.Triggered) 4174 continue; 4175 4176 switch (diag.Kind) { 4177 case DelayedDiagnostic::Deprecation: 4178 // Don't bother giving deprecation diagnostics if the decl is invalid. 4179 if (!decl->isInvalidDecl()) 4180 S.HandleDelayedDeprecationCheck(diag, decl); 4181 break; 4182 4183 case DelayedDiagnostic::Access: 4184 S.HandleDelayedAccessCheck(diag, decl); 4185 break; 4186 4187 case DelayedDiagnostic::ForbiddenType: 4188 handleDelayedForbiddenType(S, diag, decl); 4189 break; 4190 } 4191 } 4192 } 4193 4194 // Destroy all the delayed diagnostics we're about to pop off. 4195 for (unsigned i = state.SavedStackSize, e = DD.StackSize; i != e; ++i) 4196 DD.Stack[i].Destroy(); 4197 4198 DD.StackSize = state.SavedStackSize; 4199} 4200 4201static bool isDeclDeprecated(Decl *D) { 4202 do { 4203 if (D->isDeprecated()) 4204 return true; 4205 // A category implicitly has the availability of the interface. 4206 if (const ObjCCategoryDecl *CatD = dyn_cast<ObjCCategoryDecl>(D)) 4207 return CatD->getClassInterface()->isDeprecated(); 4208 } while ((D = cast_or_null<Decl>(D->getDeclContext()))); 4209 return false; 4210} 4211 4212void Sema::HandleDelayedDeprecationCheck(DelayedDiagnostic &DD, 4213 Decl *Ctx) { 4214 if (isDeclDeprecated(Ctx)) 4215 return; 4216 4217 DD.Triggered = true; 4218 if (!DD.getDeprecationMessage().empty()) 4219 Diag(DD.Loc, diag::warn_deprecated_message) 4220 << DD.getDeprecationDecl()->getDeclName() 4221 << DD.getDeprecationMessage(); 4222 else if (DD.getUnknownObjCClass()) { 4223 Diag(DD.Loc, diag::warn_deprecated_fwdclass_message) 4224 << DD.getDeprecationDecl()->getDeclName(); 4225 Diag(DD.getUnknownObjCClass()->getLocation(), diag::note_forward_class); 4226 } 4227 else 4228 Diag(DD.Loc, diag::warn_deprecated) 4229 << DD.getDeprecationDecl()->getDeclName(); 4230} 4231 4232void Sema::EmitDeprecationWarning(NamedDecl *D, StringRef Message, 4233 SourceLocation Loc, 4234 const ObjCInterfaceDecl *UnknownObjCClass) { 4235 // Delay if we're currently parsing a declaration. 4236 if (DelayedDiagnostics.shouldDelayDiagnostics()) { 4237 DelayedDiagnostics.add(DelayedDiagnostic::makeDeprecation(Loc, D, 4238 UnknownObjCClass, 4239 Message)); 4240 return; 4241 } 4242 4243 // Otherwise, don't warn if our current context is deprecated. 4244 if (isDeclDeprecated(cast<Decl>(getCurLexicalContext()))) 4245 return; 4246 if (!Message.empty()) { 4247 Diag(Loc, diag::warn_deprecated_message) << D->getDeclName() 4248 << Message; 4249 Diag(D->getLocation(), 4250 isa<ObjCMethodDecl>(D) ? diag::note_method_declared_at 4251 : diag::note_previous_decl) << D->getDeclName(); 4252 } 4253 else { 4254 if (!UnknownObjCClass) 4255 Diag(Loc, diag::warn_deprecated) << D->getDeclName(); 4256 else { 4257 Diag(Loc, diag::warn_deprecated_fwdclass_message) << D->getDeclName(); 4258 Diag(UnknownObjCClass->getLocation(), diag::note_forward_class); 4259 } 4260 } 4261} 4262