SemaDeclAttr.cpp revision 162e1c1b487352434552147967c3dd296ebee2f7
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/DeclCXX.h" 18#include "clang/AST/DeclObjC.h" 19#include "clang/AST/Expr.h" 20#include "clang/Basic/TargetInfo.h" 21#include "clang/Sema/DeclSpec.h" 22#include "clang/Sema/DelayedDiagnostic.h" 23#include "llvm/ADT/StringExtras.h" 24using namespace clang; 25using namespace sema; 26 27/// These constants match the enumerated choices of 28/// warn_attribute_wrong_decl_type and err_attribute_wrong_decl_type. 29enum { 30 ExpectedFunction, 31 ExpectedUnion, 32 ExpectedVariableOrFunction, 33 ExpectedFunctionOrMethod, 34 ExpectedParameter, 35 ExpectedParameterOrMethod, 36 ExpectedFunctionMethodOrBlock, 37 ExpectedClassOrVirtualMethod, 38 ExpectedFunctionMethodOrParameter, 39 ExpectedClass, 40 ExpectedVirtualMethod, 41 ExpectedClassMember, 42 ExpectedVariable, 43 ExpectedMethod, 44 ExpectedVariableFunctionOrLabel 45}; 46 47//===----------------------------------------------------------------------===// 48// Helper functions 49//===----------------------------------------------------------------------===// 50 51static const FunctionType *getFunctionType(const Decl *d, 52 bool blocksToo = true) { 53 QualType Ty; 54 if (const ValueDecl *decl = dyn_cast<ValueDecl>(d)) 55 Ty = decl->getType(); 56 else if (const FieldDecl *decl = dyn_cast<FieldDecl>(d)) 57 Ty = decl->getType(); 58 else if (const TypedefNameDecl* decl = dyn_cast<TypedefNameDecl>(d)) 59 Ty = decl->getUnderlyingType(); 60 else 61 return 0; 62 63 if (Ty->isFunctionPointerType()) 64 Ty = Ty->getAs<PointerType>()->getPointeeType(); 65 else if (blocksToo && Ty->isBlockPointerType()) 66 Ty = Ty->getAs<BlockPointerType>()->getPointeeType(); 67 68 return Ty->getAs<FunctionType>(); 69} 70 71// FIXME: We should provide an abstraction around a method or function 72// to provide the following bits of information. 73 74/// isFunction - Return true if the given decl has function 75/// type (function or function-typed variable). 76static bool isFunction(const Decl *d) { 77 return getFunctionType(d, false) != NULL; 78} 79 80/// isFunctionOrMethod - Return true if the given decl has function 81/// type (function or function-typed variable) or an Objective-C 82/// method. 83static bool isFunctionOrMethod(const Decl *d) { 84 return isFunction(d)|| isa<ObjCMethodDecl>(d); 85} 86 87/// isFunctionOrMethodOrBlock - Return true if the given decl has function 88/// type (function or function-typed variable) or an Objective-C 89/// method or a block. 90static bool isFunctionOrMethodOrBlock(const Decl *d) { 91 if (isFunctionOrMethod(d)) 92 return true; 93 // check for block is more involved. 94 if (const VarDecl *V = dyn_cast<VarDecl>(d)) { 95 QualType Ty = V->getType(); 96 return Ty->isBlockPointerType(); 97 } 98 return isa<BlockDecl>(d); 99} 100 101/// Return true if the given decl has a declarator that should have 102/// been processed by Sema::GetTypeForDeclarator. 103static bool hasDeclarator(const Decl *d) { 104 // In some sense, TypedefNameDecl really *ought* to be a DeclaratorDecl. 105 return isa<DeclaratorDecl>(d) || isa<BlockDecl>(d) || isa<TypedefNameDecl>(d); 106} 107 108/// hasFunctionProto - Return true if the given decl has a argument 109/// information. This decl should have already passed 110/// isFunctionOrMethod or isFunctionOrMethodOrBlock. 111static bool hasFunctionProto(const Decl *d) { 112 if (const FunctionType *FnTy = getFunctionType(d)) 113 return isa<FunctionProtoType>(FnTy); 114 else { 115 assert(isa<ObjCMethodDecl>(d) || isa<BlockDecl>(d)); 116 return true; 117 } 118} 119 120/// getFunctionOrMethodNumArgs - Return number of function or method 121/// arguments. It is an error to call this on a K&R function (use 122/// hasFunctionProto first). 123static unsigned getFunctionOrMethodNumArgs(const Decl *d) { 124 if (const FunctionType *FnTy = getFunctionType(d)) 125 return cast<FunctionProtoType>(FnTy)->getNumArgs(); 126 if (const BlockDecl *BD = dyn_cast<BlockDecl>(d)) 127 return BD->getNumParams(); 128 return cast<ObjCMethodDecl>(d)->param_size(); 129} 130 131static QualType getFunctionOrMethodArgType(const Decl *d, unsigned Idx) { 132 if (const FunctionType *FnTy = getFunctionType(d)) 133 return cast<FunctionProtoType>(FnTy)->getArgType(Idx); 134 if (const BlockDecl *BD = dyn_cast<BlockDecl>(d)) 135 return BD->getParamDecl(Idx)->getType(); 136 137 return cast<ObjCMethodDecl>(d)->param_begin()[Idx]->getType(); 138} 139 140static QualType getFunctionOrMethodResultType(const Decl *d) { 141 if (const FunctionType *FnTy = getFunctionType(d)) 142 return cast<FunctionProtoType>(FnTy)->getResultType(); 143 return cast<ObjCMethodDecl>(d)->getResultType(); 144} 145 146static bool isFunctionOrMethodVariadic(const Decl *d) { 147 if (const FunctionType *FnTy = getFunctionType(d)) { 148 const FunctionProtoType *proto = cast<FunctionProtoType>(FnTy); 149 return proto->isVariadic(); 150 } else if (const BlockDecl *BD = dyn_cast<BlockDecl>(d)) 151 return BD->isVariadic(); 152 else { 153 return cast<ObjCMethodDecl>(d)->isVariadic(); 154 } 155} 156 157static bool isInstanceMethod(const Decl *d) { 158 if (const CXXMethodDecl *MethodDecl = dyn_cast<CXXMethodDecl>(d)) 159 return MethodDecl->isInstance(); 160 return false; 161} 162 163static inline bool isNSStringType(QualType T, ASTContext &Ctx) { 164 const ObjCObjectPointerType *PT = T->getAs<ObjCObjectPointerType>(); 165 if (!PT) 166 return false; 167 168 ObjCInterfaceDecl *Cls = PT->getObjectType()->getInterface(); 169 if (!Cls) 170 return false; 171 172 IdentifierInfo* ClsName = Cls->getIdentifier(); 173 174 // FIXME: Should we walk the chain of classes? 175 return ClsName == &Ctx.Idents.get("NSString") || 176 ClsName == &Ctx.Idents.get("NSMutableString"); 177} 178 179static inline bool isCFStringType(QualType T, ASTContext &Ctx) { 180 const PointerType *PT = T->getAs<PointerType>(); 181 if (!PT) 182 return false; 183 184 const RecordType *RT = PT->getPointeeType()->getAs<RecordType>(); 185 if (!RT) 186 return false; 187 188 const RecordDecl *RD = RT->getDecl(); 189 if (RD->getTagKind() != TTK_Struct) 190 return false; 191 192 return RD->getIdentifier() == &Ctx.Idents.get("__CFString"); 193} 194 195//===----------------------------------------------------------------------===// 196// Attribute Implementations 197//===----------------------------------------------------------------------===// 198 199// FIXME: All this manual attribute parsing code is gross. At the 200// least add some helper functions to check most argument patterns (# 201// and types of args). 202 203static void HandleExtVectorTypeAttr(Scope *scope, Decl *d, 204 const AttributeList &Attr, Sema &S) { 205 TypedefNameDecl *tDecl = dyn_cast<TypedefNameDecl>(d); 206 if (tDecl == 0) { 207 S.Diag(Attr.getLoc(), diag::err_typecheck_ext_vector_not_typedef); 208 return; 209 } 210 211 QualType curType = tDecl->getUnderlyingType(); 212 213 Expr *sizeExpr; 214 215 // Special case where the argument is a template id. 216 if (Attr.getParameterName()) { 217 CXXScopeSpec SS; 218 UnqualifiedId id; 219 id.setIdentifier(Attr.getParameterName(), Attr.getLoc()); 220 sizeExpr = S.ActOnIdExpression(scope, SS, id, false, false).takeAs<Expr>(); 221 } else { 222 // check the attribute arguments. 223 if (Attr.getNumArgs() != 1) { 224 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 225 return; 226 } 227 sizeExpr = Attr.getArg(0); 228 } 229 230 // Instantiate/Install the vector type, and let Sema build the type for us. 231 // This will run the reguired checks. 232 QualType T = S.BuildExtVectorType(curType, sizeExpr, Attr.getLoc()); 233 if (!T.isNull()) { 234 // FIXME: preserve the old source info. 235 tDecl->setTypeSourceInfo(S.Context.getTrivialTypeSourceInfo(T)); 236 237 // Remember this typedef decl, we will need it later for diagnostics. 238 S.ExtVectorDecls.push_back(tDecl); 239 } 240} 241 242static void HandlePackedAttr(Decl *d, const AttributeList &Attr, Sema &S) { 243 // check the attribute arguments. 244 if (Attr.getNumArgs() > 0) { 245 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 246 return; 247 } 248 249 if (TagDecl *TD = dyn_cast<TagDecl>(d)) 250 TD->addAttr(::new (S.Context) PackedAttr(Attr.getLoc(), S.Context)); 251 else if (FieldDecl *FD = dyn_cast<FieldDecl>(d)) { 252 // If the alignment is less than or equal to 8 bits, the packed attribute 253 // has no effect. 254 if (!FD->getType()->isIncompleteType() && 255 S.Context.getTypeAlign(FD->getType()) <= 8) 256 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored_for_field_of_type) 257 << Attr.getName() << FD->getType(); 258 else 259 FD->addAttr(::new (S.Context) PackedAttr(Attr.getLoc(), S.Context)); 260 } else 261 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 262} 263 264static void HandleIBAction(Decl *d, const AttributeList &Attr, Sema &S) { 265 // check the attribute arguments. 266 if (Attr.getNumArgs() > 0) { 267 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 268 return; 269 } 270 271 // The IBAction attributes only apply to instance methods. 272 if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(d)) 273 if (MD->isInstanceMethod()) { 274 d->addAttr(::new (S.Context) IBActionAttr(Attr.getLoc(), S.Context)); 275 return; 276 } 277 278 S.Diag(Attr.getLoc(), diag::warn_attribute_ibaction) << Attr.getName(); 279} 280 281static void HandleIBOutlet(Decl *d, const AttributeList &Attr, Sema &S) { 282 // check the attribute arguments. 283 if (Attr.getNumArgs() > 0) { 284 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 285 return; 286 } 287 288 // The IBOutlet attributes only apply to instance variables of 289 // Objective-C classes. 290 if (isa<ObjCIvarDecl>(d) || isa<ObjCPropertyDecl>(d)) { 291 d->addAttr(::new (S.Context) IBOutletAttr(Attr.getLoc(), S.Context)); 292 return; 293 } 294 295 S.Diag(Attr.getLoc(), diag::warn_attribute_iboutlet) << Attr.getName(); 296} 297 298static void HandleIBOutletCollection(Decl *d, const AttributeList &Attr, 299 Sema &S) { 300 301 // The iboutletcollection attribute can have zero or one arguments. 302 if (Attr.getParameterName() && Attr.getNumArgs() > 0) { 303 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 304 return; 305 } 306 307 // The IBOutletCollection attributes only apply to instance variables of 308 // Objective-C classes. 309 if (!(isa<ObjCIvarDecl>(d) || isa<ObjCPropertyDecl>(d))) { 310 S.Diag(Attr.getLoc(), diag::warn_attribute_iboutlet) << Attr.getName(); 311 return; 312 } 313 if (const ValueDecl *VD = dyn_cast<ValueDecl>(d)) 314 if (!VD->getType()->getAs<ObjCObjectPointerType>()) { 315 S.Diag(Attr.getLoc(), diag::err_iboutletcollection_object_type) 316 << VD->getType() << 0; 317 return; 318 } 319 if (const ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(d)) 320 if (!PD->getType()->getAs<ObjCObjectPointerType>()) { 321 S.Diag(Attr.getLoc(), diag::err_iboutletcollection_object_type) 322 << PD->getType() << 1; 323 return; 324 } 325 326 IdentifierInfo *II = Attr.getParameterName(); 327 if (!II) 328 II = &S.Context.Idents.get("id"); 329 330 ParsedType TypeRep = S.getTypeName(*II, Attr.getLoc(), 331 S.getScopeForContext(d->getDeclContext()->getParent())); 332 if (!TypeRep) { 333 S.Diag(Attr.getLoc(), diag::err_iboutletcollection_type) << II; 334 return; 335 } 336 QualType QT = TypeRep.get(); 337 // Diagnose use of non-object type in iboutletcollection attribute. 338 // FIXME. Gnu attribute extension ignores use of builtin types in 339 // attributes. So, __attribute__((iboutletcollection(char))) will be 340 // treated as __attribute__((iboutletcollection())). 341 if (!QT->isObjCIdType() && !QT->isObjCClassType() && 342 !QT->isObjCObjectType()) { 343 S.Diag(Attr.getLoc(), diag::err_iboutletcollection_type) << II; 344 return; 345 } 346 d->addAttr(::new (S.Context) IBOutletCollectionAttr(Attr.getLoc(), S.Context, 347 QT)); 348} 349 350static void HandleNonNullAttr(Decl *d, const AttributeList &Attr, Sema &S) { 351 // GCC ignores the nonnull attribute on K&R style function prototypes, so we 352 // ignore it as well 353 if (!isFunctionOrMethod(d) || !hasFunctionProto(d)) { 354 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 355 << Attr.getName() << ExpectedFunction; 356 return; 357 } 358 359 // In C++ the implicit 'this' function parameter also counts, and they are 360 // counted from one. 361 bool HasImplicitThisParam = isInstanceMethod(d); 362 unsigned NumArgs = getFunctionOrMethodNumArgs(d) + HasImplicitThisParam; 363 364 // The nonnull attribute only applies to pointers. 365 llvm::SmallVector<unsigned, 10> NonNullArgs; 366 367 for (AttributeList::arg_iterator I=Attr.arg_begin(), 368 E=Attr.arg_end(); I!=E; ++I) { 369 370 371 // The argument must be an integer constant expression. 372 Expr *Ex = *I; 373 llvm::APSInt ArgNum(32); 374 if (Ex->isTypeDependent() || Ex->isValueDependent() || 375 !Ex->isIntegerConstantExpr(ArgNum, S.Context)) { 376 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 377 << "nonnull" << Ex->getSourceRange(); 378 return; 379 } 380 381 unsigned x = (unsigned) ArgNum.getZExtValue(); 382 383 if (x < 1 || x > NumArgs) { 384 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 385 << "nonnull" << I.getArgNum() << Ex->getSourceRange(); 386 return; 387 } 388 389 --x; 390 if (HasImplicitThisParam) { 391 if (x == 0) { 392 S.Diag(Attr.getLoc(), 393 diag::err_attribute_invalid_implicit_this_argument) 394 << "nonnull" << Ex->getSourceRange(); 395 return; 396 } 397 --x; 398 } 399 400 // Is the function argument a pointer type? 401 QualType T = getFunctionOrMethodArgType(d, x).getNonReferenceType(); 402 if (!T->isAnyPointerType() && !T->isBlockPointerType()) { 403 // FIXME: Should also highlight argument in decl. 404 S.Diag(Attr.getLoc(), diag::warn_nonnull_pointers_only) 405 << "nonnull" << Ex->getSourceRange(); 406 continue; 407 } 408 409 NonNullArgs.push_back(x); 410 } 411 412 // If no arguments were specified to __attribute__((nonnull)) then all pointer 413 // arguments have a nonnull attribute. 414 if (NonNullArgs.empty()) { 415 for (unsigned I = 0, E = getFunctionOrMethodNumArgs(d); I != E; ++I) { 416 QualType T = getFunctionOrMethodArgType(d, I).getNonReferenceType(); 417 if (T->isAnyPointerType() || T->isBlockPointerType()) 418 NonNullArgs.push_back(I); 419 else if (const RecordType *UT = T->getAsUnionType()) { 420 if (UT && UT->getDecl()->hasAttr<TransparentUnionAttr>()) { 421 RecordDecl *UD = UT->getDecl(); 422 for (RecordDecl::field_iterator it = UD->field_begin(), 423 itend = UD->field_end(); it != itend; ++it) { 424 T = it->getType(); 425 if (T->isAnyPointerType() || T->isBlockPointerType()) { 426 NonNullArgs.push_back(I); 427 break; 428 } 429 } 430 } 431 } 432 } 433 434 // No pointer arguments? 435 if (NonNullArgs.empty()) { 436 // Warn the trivial case only if attribute is not coming from a 437 // macro instantiation. 438 if (Attr.getLoc().isFileID()) 439 S.Diag(Attr.getLoc(), diag::warn_attribute_nonnull_no_pointers); 440 return; 441 } 442 } 443 444 unsigned* start = &NonNullArgs[0]; 445 unsigned size = NonNullArgs.size(); 446 llvm::array_pod_sort(start, start + size); 447 d->addAttr(::new (S.Context) NonNullAttr(Attr.getLoc(), S.Context, start, 448 size)); 449} 450 451static void HandleOwnershipAttr(Decl *d, const AttributeList &AL, Sema &S) { 452 // This attribute must be applied to a function declaration. 453 // The first argument to the attribute must be a string, 454 // the name of the resource, for example "malloc". 455 // The following arguments must be argument indexes, the arguments must be 456 // of integer type for Returns, otherwise of pointer type. 457 // The difference between Holds and Takes is that a pointer may still be used 458 // after being held. free() should be __attribute((ownership_takes)), whereas 459 // a list append function may well be __attribute((ownership_holds)). 460 461 if (!AL.getParameterName()) { 462 S.Diag(AL.getLoc(), diag::err_attribute_argument_n_not_string) 463 << AL.getName()->getName() << 1; 464 return; 465 } 466 // Figure out our Kind, and check arguments while we're at it. 467 OwnershipAttr::OwnershipKind K; 468 switch (AL.getKind()) { 469 case AttributeList::AT_ownership_takes: 470 K = OwnershipAttr::Takes; 471 if (AL.getNumArgs() < 1) { 472 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << 2; 473 return; 474 } 475 break; 476 case AttributeList::AT_ownership_holds: 477 K = OwnershipAttr::Holds; 478 if (AL.getNumArgs() < 1) { 479 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << 2; 480 return; 481 } 482 break; 483 case AttributeList::AT_ownership_returns: 484 K = OwnershipAttr::Returns; 485 if (AL.getNumArgs() > 1) { 486 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) 487 << AL.getNumArgs() + 1; 488 return; 489 } 490 break; 491 default: 492 // This should never happen given how we are called. 493 llvm_unreachable("Unknown ownership attribute"); 494 } 495 496 if (!isFunction(d) || !hasFunctionProto(d)) { 497 S.Diag(AL.getLoc(), diag::warn_attribute_wrong_decl_type) 498 << AL.getName() << ExpectedFunction; 499 return; 500 } 501 502 // In C++ the implicit 'this' function parameter also counts, and they are 503 // counted from one. 504 bool HasImplicitThisParam = isInstanceMethod(d); 505 unsigned NumArgs = getFunctionOrMethodNumArgs(d) + HasImplicitThisParam; 506 507 llvm::StringRef Module = AL.getParameterName()->getName(); 508 509 // Normalize the argument, __foo__ becomes foo. 510 if (Module.startswith("__") && Module.endswith("__")) 511 Module = Module.substr(2, Module.size() - 4); 512 513 llvm::SmallVector<unsigned, 10> OwnershipArgs; 514 515 for (AttributeList::arg_iterator I = AL.arg_begin(), E = AL.arg_end(); I != E; 516 ++I) { 517 518 Expr *IdxExpr = *I; 519 llvm::APSInt ArgNum(32); 520 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() 521 || !IdxExpr->isIntegerConstantExpr(ArgNum, S.Context)) { 522 S.Diag(AL.getLoc(), diag::err_attribute_argument_not_int) 523 << AL.getName()->getName() << IdxExpr->getSourceRange(); 524 continue; 525 } 526 527 unsigned x = (unsigned) ArgNum.getZExtValue(); 528 529 if (x > NumArgs || x < 1) { 530 S.Diag(AL.getLoc(), diag::err_attribute_argument_out_of_bounds) 531 << AL.getName()->getName() << x << IdxExpr->getSourceRange(); 532 continue; 533 } 534 --x; 535 if (HasImplicitThisParam) { 536 if (x == 0) { 537 S.Diag(AL.getLoc(), diag::err_attribute_invalid_implicit_this_argument) 538 << "ownership" << IdxExpr->getSourceRange(); 539 return; 540 } 541 --x; 542 } 543 544 switch (K) { 545 case OwnershipAttr::Takes: 546 case OwnershipAttr::Holds: { 547 // Is the function argument a pointer type? 548 QualType T = getFunctionOrMethodArgType(d, x); 549 if (!T->isAnyPointerType() && !T->isBlockPointerType()) { 550 // FIXME: Should also highlight argument in decl. 551 S.Diag(AL.getLoc(), diag::err_ownership_type) 552 << ((K==OwnershipAttr::Takes)?"ownership_takes":"ownership_holds") 553 << "pointer" 554 << IdxExpr->getSourceRange(); 555 continue; 556 } 557 break; 558 } 559 case OwnershipAttr::Returns: { 560 if (AL.getNumArgs() > 1) { 561 // Is the function argument an integer type? 562 Expr *IdxExpr = AL.getArg(0); 563 llvm::APSInt ArgNum(32); 564 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() 565 || !IdxExpr->isIntegerConstantExpr(ArgNum, S.Context)) { 566 S.Diag(AL.getLoc(), diag::err_ownership_type) 567 << "ownership_returns" << "integer" 568 << IdxExpr->getSourceRange(); 569 return; 570 } 571 } 572 break; 573 } 574 default: 575 llvm_unreachable("Unknown ownership attribute"); 576 } // switch 577 578 // Check we don't have a conflict with another ownership attribute. 579 for (specific_attr_iterator<OwnershipAttr> 580 i = d->specific_attr_begin<OwnershipAttr>(), 581 e = d->specific_attr_end<OwnershipAttr>(); 582 i != e; ++i) { 583 if ((*i)->getOwnKind() != K) { 584 for (const unsigned *I = (*i)->args_begin(), *E = (*i)->args_end(); 585 I!=E; ++I) { 586 if (x == *I) { 587 S.Diag(AL.getLoc(), diag::err_attributes_are_not_compatible) 588 << AL.getName()->getName() << "ownership_*"; 589 } 590 } 591 } 592 } 593 OwnershipArgs.push_back(x); 594 } 595 596 unsigned* start = OwnershipArgs.data(); 597 unsigned size = OwnershipArgs.size(); 598 llvm::array_pod_sort(start, start + size); 599 600 if (K != OwnershipAttr::Returns && OwnershipArgs.empty()) { 601 S.Diag(AL.getLoc(), diag::err_attribute_wrong_number_arguments) << 2; 602 return; 603 } 604 605 d->addAttr(::new (S.Context) OwnershipAttr(AL.getLoc(), S.Context, K, Module, 606 start, size)); 607} 608 609/// Whether this declaration has internal linkage for the purposes of 610/// things that want to complain about things not have internal linkage. 611static bool hasEffectivelyInternalLinkage(NamedDecl *D) { 612 switch (D->getLinkage()) { 613 case NoLinkage: 614 case InternalLinkage: 615 return true; 616 617 // Template instantiations that go from external to unique-external 618 // shouldn't get diagnosed. 619 case UniqueExternalLinkage: 620 return true; 621 622 case ExternalLinkage: 623 return false; 624 } 625 llvm_unreachable("unknown linkage kind!"); 626 return false; 627} 628 629static void HandleWeakRefAttr(Decl *d, const AttributeList &Attr, Sema &S) { 630 // Check the attribute arguments. 631 if (Attr.getNumArgs() > 1) { 632 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 633 return; 634 } 635 636 if (!isa<VarDecl>(d) && !isa<FunctionDecl>(d)) { 637 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 638 << Attr.getName() << ExpectedVariableOrFunction; 639 return; 640 } 641 642 NamedDecl *nd = cast<NamedDecl>(d); 643 644 // gcc rejects 645 // class c { 646 // static int a __attribute__((weakref ("v2"))); 647 // static int b() __attribute__((weakref ("f3"))); 648 // }; 649 // and ignores the attributes of 650 // void f(void) { 651 // static int a __attribute__((weakref ("v2"))); 652 // } 653 // we reject them 654 const DeclContext *Ctx = d->getDeclContext()->getRedeclContext(); 655 if (!Ctx->isFileContext()) { 656 S.Diag(Attr.getLoc(), diag::err_attribute_weakref_not_global_context) << 657 nd->getNameAsString(); 658 return; 659 } 660 661 // The GCC manual says 662 // 663 // At present, a declaration to which `weakref' is attached can only 664 // be `static'. 665 // 666 // It also says 667 // 668 // Without a TARGET, 669 // given as an argument to `weakref' or to `alias', `weakref' is 670 // equivalent to `weak'. 671 // 672 // gcc 4.4.1 will accept 673 // int a7 __attribute__((weakref)); 674 // as 675 // int a7 __attribute__((weak)); 676 // This looks like a bug in gcc. We reject that for now. We should revisit 677 // it if this behaviour is actually used. 678 679 if (!hasEffectivelyInternalLinkage(nd)) { 680 S.Diag(Attr.getLoc(), diag::err_attribute_weakref_not_static); 681 return; 682 } 683 684 // GCC rejects 685 // static ((alias ("y"), weakref)). 686 // Should we? How to check that weakref is before or after alias? 687 688 if (Attr.getNumArgs() == 1) { 689 Expr *Arg = Attr.getArg(0); 690 Arg = Arg->IgnoreParenCasts(); 691 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 692 693 if (Str == 0 || Str->isWide()) { 694 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 695 << "weakref" << 1; 696 return; 697 } 698 // GCC will accept anything as the argument of weakref. Should we 699 // check for an existing decl? 700 d->addAttr(::new (S.Context) AliasAttr(Attr.getLoc(), S.Context, 701 Str->getString())); 702 } 703 704 d->addAttr(::new (S.Context) WeakRefAttr(Attr.getLoc(), S.Context)); 705} 706 707static void HandleAliasAttr(Decl *d, const AttributeList &Attr, Sema &S) { 708 // check the attribute arguments. 709 if (Attr.getNumArgs() != 1) { 710 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 711 return; 712 } 713 714 Expr *Arg = Attr.getArg(0); 715 Arg = Arg->IgnoreParenCasts(); 716 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 717 718 if (Str == 0 || Str->isWide()) { 719 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 720 << "alias" << 1; 721 return; 722 } 723 724 if (S.Context.Target.getTriple().getOS() == llvm::Triple::Darwin) { 725 S.Diag(Attr.getLoc(), diag::err_alias_not_supported_on_darwin); 726 return; 727 } 728 729 // FIXME: check if target symbol exists in current file 730 731 d->addAttr(::new (S.Context) AliasAttr(Attr.getLoc(), S.Context, 732 Str->getString())); 733} 734 735static void HandleNakedAttr(Decl *d, const AttributeList &Attr, 736 Sema &S) { 737 // Check the attribute arguments. 738 if (Attr.getNumArgs() != 0) { 739 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 740 return; 741 } 742 743 if (!isa<FunctionDecl>(d)) { 744 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 745 << Attr.getName() << ExpectedFunction; 746 return; 747 } 748 749 d->addAttr(::new (S.Context) NakedAttr(Attr.getLoc(), S.Context)); 750} 751 752static void HandleAlwaysInlineAttr(Decl *d, const AttributeList &Attr, 753 Sema &S) { 754 // Check the attribute arguments. 755 if (Attr.hasParameterOrArguments()) { 756 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 757 return; 758 } 759 760 if (!isa<FunctionDecl>(d)) { 761 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 762 << Attr.getName() << ExpectedFunction; 763 return; 764 } 765 766 d->addAttr(::new (S.Context) AlwaysInlineAttr(Attr.getLoc(), S.Context)); 767} 768 769static void HandleMallocAttr(Decl *d, const AttributeList &Attr, Sema &S) { 770 // Check the attribute arguments. 771 if (Attr.hasParameterOrArguments()) { 772 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 773 return; 774 } 775 776 if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(d)) { 777 QualType RetTy = FD->getResultType(); 778 if (RetTy->isAnyPointerType() || RetTy->isBlockPointerType()) { 779 d->addAttr(::new (S.Context) MallocAttr(Attr.getLoc(), S.Context)); 780 return; 781 } 782 } 783 784 S.Diag(Attr.getLoc(), diag::warn_attribute_malloc_pointer_only); 785} 786 787static void HandleMayAliasAttr(Decl *d, const AttributeList &Attr, Sema &S) { 788 // check the attribute arguments. 789 if (Attr.getNumArgs() != 0) { 790 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 791 return; 792 } 793 794 d->addAttr(::new (S.Context) MayAliasAttr(Attr.getLoc(), S.Context)); 795} 796 797static void HandleNoCommonAttr(Decl *d, const AttributeList &Attr, Sema &S) { 798 assert(Attr.isInvalid() == false); 799 if (isa<VarDecl>(d)) 800 d->addAttr(::new (S.Context) NoCommonAttr(Attr.getLoc(), S.Context)); 801 else 802 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 803 << Attr.getName() << ExpectedVariable; 804} 805 806static void HandleCommonAttr(Decl *d, const AttributeList &Attr, Sema &S) { 807 assert(Attr.isInvalid() == false); 808 if (isa<VarDecl>(d)) 809 d->addAttr(::new (S.Context) CommonAttr(Attr.getLoc(), S.Context)); 810 else 811 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 812 << Attr.getName() << ExpectedVariable; 813} 814 815static void HandleNoReturnAttr(Decl *d, const AttributeList &attr, Sema &S) { 816 if (hasDeclarator(d)) return; 817 818 if (S.CheckNoReturnAttr(attr)) return; 819 820 if (!isa<ObjCMethodDecl>(d)) { 821 S.Diag(attr.getLoc(), diag::warn_attribute_wrong_decl_type) 822 << attr.getName() << ExpectedFunctionOrMethod; 823 return; 824 } 825 826 d->addAttr(::new (S.Context) NoReturnAttr(attr.getLoc(), S.Context)); 827} 828 829bool Sema::CheckNoReturnAttr(const AttributeList &attr) { 830 if (attr.hasParameterOrArguments()) { 831 Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 832 attr.setInvalid(); 833 return true; 834 } 835 836 return false; 837} 838 839static void HandleAnalyzerNoReturnAttr(Decl *d, const AttributeList &Attr, 840 Sema &S) { 841 842 // The checking path for 'noreturn' and 'analyzer_noreturn' are different 843 // because 'analyzer_noreturn' does not impact the type. 844 845 if (Attr.getNumArgs() != 0) { 846 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 847 return; 848 } 849 850 if (!isFunctionOrMethod(d) && !isa<BlockDecl>(d)) { 851 ValueDecl *VD = dyn_cast<ValueDecl>(d); 852 if (VD == 0 || (!VD->getType()->isBlockPointerType() 853 && !VD->getType()->isFunctionPointerType())) { 854 S.Diag(Attr.getLoc(), 855 Attr.isCXX0XAttribute() ? diag::err_attribute_wrong_decl_type 856 : diag::warn_attribute_wrong_decl_type) 857 << Attr.getName() << ExpectedFunctionMethodOrBlock; 858 return; 859 } 860 } 861 862 d->addAttr(::new (S.Context) AnalyzerNoReturnAttr(Attr.getLoc(), S.Context)); 863} 864 865// PS3 PPU-specific. 866static void HandleVecReturnAttr(Decl *d, const AttributeList &Attr, 867 Sema &S) { 868/* 869 Returning a Vector Class in Registers 870 871 According to the PPU ABI specifications, a class with a single member of 872 vector type is returned in memory when used as the return value of a function. 873 This results in inefficient code when implementing vector classes. To return 874 the value in a single vector register, add the vecreturn attribute to the 875 class definition. This attribute is also applicable to struct types. 876 877 Example: 878 879 struct Vector 880 { 881 __vector float xyzw; 882 } __attribute__((vecreturn)); 883 884 Vector Add(Vector lhs, Vector rhs) 885 { 886 Vector result; 887 result.xyzw = vec_add(lhs.xyzw, rhs.xyzw); 888 return result; // This will be returned in a register 889 } 890*/ 891 if (!isa<RecordDecl>(d)) { 892 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 893 << Attr.getName() << ExpectedClass; 894 return; 895 } 896 897 if (d->getAttr<VecReturnAttr>()) { 898 S.Diag(Attr.getLoc(), diag::err_repeat_attribute) << "vecreturn"; 899 return; 900 } 901 902 RecordDecl *record = cast<RecordDecl>(d); 903 int count = 0; 904 905 if (!isa<CXXRecordDecl>(record)) { 906 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 907 return; 908 } 909 910 if (!cast<CXXRecordDecl>(record)->isPOD()) { 911 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_pod_record); 912 return; 913 } 914 915 for (RecordDecl::field_iterator iter = record->field_begin(); 916 iter != record->field_end(); iter++) { 917 if ((count == 1) || !iter->getType()->isVectorType()) { 918 S.Diag(Attr.getLoc(), diag::err_attribute_vecreturn_only_vector_member); 919 return; 920 } 921 count++; 922 } 923 924 d->addAttr(::new (S.Context) VecReturnAttr(Attr.getLoc(), S.Context)); 925} 926 927static void HandleDependencyAttr(Decl *d, const AttributeList &Attr, Sema &S) { 928 if (!isFunctionOrMethod(d) && !isa<ParmVarDecl>(d)) { 929 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_decl_type) 930 << Attr.getName() << ExpectedFunctionMethodOrParameter; 931 return; 932 } 933 // FIXME: Actually store the attribute on the declaration 934} 935 936static void HandleUnusedAttr(Decl *d, const AttributeList &Attr, Sema &S) { 937 // check the attribute arguments. 938 if (Attr.hasParameterOrArguments()) { 939 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 940 return; 941 } 942 943 if (!isa<VarDecl>(d) && !isa<ObjCIvarDecl>(d) && !isFunctionOrMethod(d) && 944 !isa<TypeDecl>(d) && !isa<LabelDecl>(d)) { 945 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 946 << Attr.getName() << ExpectedVariableFunctionOrLabel; 947 return; 948 } 949 950 d->addAttr(::new (S.Context) UnusedAttr(Attr.getLoc(), S.Context)); 951} 952 953static void HandleUsedAttr(Decl *d, const AttributeList &Attr, Sema &S) { 954 // check the attribute arguments. 955 if (Attr.hasParameterOrArguments()) { 956 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 957 return; 958 } 959 960 if (const VarDecl *VD = dyn_cast<VarDecl>(d)) { 961 if (VD->hasLocalStorage() || VD->hasExternalStorage()) { 962 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "used"; 963 return; 964 } 965 } else if (!isFunctionOrMethod(d)) { 966 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 967 << Attr.getName() << ExpectedVariableOrFunction; 968 return; 969 } 970 971 d->addAttr(::new (S.Context) UsedAttr(Attr.getLoc(), S.Context)); 972} 973 974static void HandleConstructorAttr(Decl *d, const AttributeList &Attr, Sema &S) { 975 // check the attribute arguments. 976 if (Attr.getNumArgs() > 1) { 977 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 978 return; 979 } 980 981 int priority = 65535; // FIXME: Do not hardcode such constants. 982 if (Attr.getNumArgs() > 0) { 983 Expr *E = Attr.getArg(0); 984 llvm::APSInt Idx(32); 985 if (E->isTypeDependent() || E->isValueDependent() || 986 !E->isIntegerConstantExpr(Idx, S.Context)) { 987 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 988 << "constructor" << 1 << E->getSourceRange(); 989 return; 990 } 991 priority = Idx.getZExtValue(); 992 } 993 994 if (!isa<FunctionDecl>(d)) { 995 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 996 << Attr.getName() << ExpectedFunction; 997 return; 998 } 999 1000 d->addAttr(::new (S.Context) ConstructorAttr(Attr.getLoc(), S.Context, 1001 priority)); 1002} 1003 1004static void HandleDestructorAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1005 // check the attribute arguments. 1006 if (Attr.getNumArgs() > 1) { 1007 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1008 return; 1009 } 1010 1011 int priority = 65535; // FIXME: Do not hardcode such constants. 1012 if (Attr.getNumArgs() > 0) { 1013 Expr *E = Attr.getArg(0); 1014 llvm::APSInt Idx(32); 1015 if (E->isTypeDependent() || E->isValueDependent() || 1016 !E->isIntegerConstantExpr(Idx, S.Context)) { 1017 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1018 << "destructor" << 1 << E->getSourceRange(); 1019 return; 1020 } 1021 priority = Idx.getZExtValue(); 1022 } 1023 1024 if (!isa<FunctionDecl>(d)) { 1025 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1026 << Attr.getName() << ExpectedFunction; 1027 return; 1028 } 1029 1030 d->addAttr(::new (S.Context) DestructorAttr(Attr.getLoc(), S.Context, 1031 priority)); 1032} 1033 1034static void HandleDeprecatedAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1035 unsigned NumArgs = Attr.getNumArgs(); 1036 if (NumArgs > 1) { 1037 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1038 return; 1039 } 1040 1041 // Handle the case where deprecated attribute has a text message. 1042 llvm::StringRef Str; 1043 if (NumArgs == 1) { 1044 StringLiteral *SE = dyn_cast<StringLiteral>(Attr.getArg(0)); 1045 if (!SE) { 1046 S.Diag(Attr.getArg(0)->getLocStart(), diag::err_attribute_not_string) 1047 << "deprecated"; 1048 return; 1049 } 1050 Str = SE->getString(); 1051 } 1052 1053 d->addAttr(::new (S.Context) DeprecatedAttr(Attr.getLoc(), S.Context, Str)); 1054} 1055 1056static void HandleUnavailableAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1057 unsigned NumArgs = Attr.getNumArgs(); 1058 if (NumArgs > 1) { 1059 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 1; 1060 return; 1061 } 1062 1063 // Handle the case where unavailable attribute has a text message. 1064 llvm::StringRef Str; 1065 if (NumArgs == 1) { 1066 StringLiteral *SE = dyn_cast<StringLiteral>(Attr.getArg(0)); 1067 if (!SE) { 1068 S.Diag(Attr.getArg(0)->getLocStart(), 1069 diag::err_attribute_not_string) << "unavailable"; 1070 return; 1071 } 1072 Str = SE->getString(); 1073 } 1074 d->addAttr(::new (S.Context) UnavailableAttr(Attr.getLoc(), S.Context, Str)); 1075} 1076 1077static void HandleAvailabilityAttr(Decl *d, const AttributeList &Attr, 1078 Sema &S) { 1079 IdentifierInfo *Platform = Attr.getParameterName(); 1080 SourceLocation PlatformLoc = Attr.getParameterLoc(); 1081 1082 llvm::StringRef PlatformName 1083 = AvailabilityAttr::getPrettyPlatformName(Platform->getName()); 1084 if (PlatformName.empty()) { 1085 S.Diag(PlatformLoc, diag::warn_availability_unknown_platform) 1086 << Platform; 1087 1088 PlatformName = Platform->getName(); 1089 } 1090 1091 AvailabilityChange Introduced = Attr.getAvailabilityIntroduced(); 1092 AvailabilityChange Deprecated = Attr.getAvailabilityDeprecated(); 1093 AvailabilityChange Obsoleted = Attr.getAvailabilityObsoleted(); 1094 bool IsUnavailable = Attr.getUnavailableLoc().isValid(); 1095 1096 // Ensure that Introduced < Deprecated < Obsoleted (although not all 1097 // of these steps are needed). 1098 if (Introduced.isValid() && Deprecated.isValid() && 1099 !(Introduced.Version < Deprecated.Version)) { 1100 S.Diag(Introduced.KeywordLoc, diag::warn_availability_version_ordering) 1101 << 1 << PlatformName << Deprecated.Version.getAsString() 1102 << 0 << Introduced.Version.getAsString(); 1103 return; 1104 } 1105 1106 if (Introduced.isValid() && Obsoleted.isValid() && 1107 !(Introduced.Version < Obsoleted.Version)) { 1108 S.Diag(Introduced.KeywordLoc, diag::warn_availability_version_ordering) 1109 << 2 << PlatformName << Obsoleted.Version.getAsString() 1110 << 0 << Introduced.Version.getAsString(); 1111 return; 1112 } 1113 1114 if (Deprecated.isValid() && Obsoleted.isValid() && 1115 !(Deprecated.Version < Obsoleted.Version)) { 1116 S.Diag(Deprecated.KeywordLoc, diag::warn_availability_version_ordering) 1117 << 2 << PlatformName << Obsoleted.Version.getAsString() 1118 << 1 << Deprecated.Version.getAsString(); 1119 return; 1120 } 1121 1122 d->addAttr(::new (S.Context) AvailabilityAttr(Attr.getLoc(), S.Context, 1123 Platform, 1124 Introduced.Version, 1125 Deprecated.Version, 1126 Obsoleted.Version, 1127 IsUnavailable)); 1128} 1129 1130static void HandleVisibilityAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1131 // check the attribute arguments. 1132 if (Attr.getNumArgs() != 1) { 1133 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1134 return; 1135 } 1136 1137 Expr *Arg = Attr.getArg(0); 1138 Arg = Arg->IgnoreParenCasts(); 1139 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 1140 1141 if (Str == 0 || Str->isWide()) { 1142 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1143 << "visibility" << 1; 1144 return; 1145 } 1146 1147 llvm::StringRef TypeStr = Str->getString(); 1148 VisibilityAttr::VisibilityType type; 1149 1150 if (TypeStr == "default") 1151 type = VisibilityAttr::Default; 1152 else if (TypeStr == "hidden") 1153 type = VisibilityAttr::Hidden; 1154 else if (TypeStr == "internal") 1155 type = VisibilityAttr::Hidden; // FIXME 1156 else if (TypeStr == "protected") 1157 type = VisibilityAttr::Protected; 1158 else { 1159 S.Diag(Attr.getLoc(), diag::warn_attribute_unknown_visibility) << TypeStr; 1160 return; 1161 } 1162 1163 d->addAttr(::new (S.Context) VisibilityAttr(Attr.getLoc(), S.Context, type)); 1164} 1165 1166static void HandleObjCMethodFamilyAttr(Decl *decl, const AttributeList &attr, 1167 Sema &S) { 1168 ObjCMethodDecl *method = dyn_cast<ObjCMethodDecl>(decl); 1169 if (!method) { 1170 S.Diag(attr.getLoc(), diag::err_attribute_wrong_decl_type) 1171 << ExpectedMethod; 1172 return; 1173 } 1174 1175 if (attr.getNumArgs() != 0 || !attr.getParameterName()) { 1176 if (!attr.getParameterName() && attr.getNumArgs() == 1) { 1177 S.Diag(attr.getLoc(), diag::err_attribute_argument_n_not_string) 1178 << "objc_method_family" << 1; 1179 } else { 1180 S.Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1181 } 1182 attr.setInvalid(); 1183 return; 1184 } 1185 1186 llvm::StringRef param = attr.getParameterName()->getName(); 1187 ObjCMethodFamilyAttr::FamilyKind family; 1188 if (param == "none") 1189 family = ObjCMethodFamilyAttr::OMF_None; 1190 else if (param == "alloc") 1191 family = ObjCMethodFamilyAttr::OMF_alloc; 1192 else if (param == "copy") 1193 family = ObjCMethodFamilyAttr::OMF_copy; 1194 else if (param == "init") 1195 family = ObjCMethodFamilyAttr::OMF_init; 1196 else if (param == "mutableCopy") 1197 family = ObjCMethodFamilyAttr::OMF_mutableCopy; 1198 else if (param == "new") 1199 family = ObjCMethodFamilyAttr::OMF_new; 1200 else { 1201 // Just warn and ignore it. This is future-proof against new 1202 // families being used in system headers. 1203 S.Diag(attr.getParameterLoc(), diag::warn_unknown_method_family); 1204 return; 1205 } 1206 1207 decl->addAttr(new (S.Context) ObjCMethodFamilyAttr(attr.getLoc(), 1208 S.Context, family)); 1209} 1210 1211static void HandleObjCExceptionAttr(Decl *D, const AttributeList &Attr, 1212 Sema &S) { 1213 if (Attr.getNumArgs() != 0) { 1214 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1215 return; 1216 } 1217 1218 ObjCInterfaceDecl *OCI = dyn_cast<ObjCInterfaceDecl>(D); 1219 if (OCI == 0) { 1220 S.Diag(Attr.getLoc(), diag::err_attribute_requires_objc_interface); 1221 return; 1222 } 1223 1224 D->addAttr(::new (S.Context) ObjCExceptionAttr(Attr.getLoc(), S.Context)); 1225} 1226 1227static void HandleObjCNSObject(Decl *D, const AttributeList &Attr, Sema &S) { 1228 if (Attr.getNumArgs() != 0) { 1229 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1230 return; 1231 } 1232 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) { 1233 QualType T = TD->getUnderlyingType(); 1234 if (!T->isPointerType() || 1235 !T->getAs<PointerType>()->getPointeeType()->isRecordType()) { 1236 S.Diag(TD->getLocation(), diag::err_nsobject_attribute); 1237 return; 1238 } 1239 } 1240 D->addAttr(::new (S.Context) ObjCNSObjectAttr(Attr.getLoc(), S.Context)); 1241} 1242 1243static void 1244HandleOverloadableAttr(Decl *D, const AttributeList &Attr, Sema &S) { 1245 if (Attr.getNumArgs() != 0) { 1246 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1247 return; 1248 } 1249 1250 if (!isa<FunctionDecl>(D)) { 1251 S.Diag(Attr.getLoc(), diag::err_attribute_overloadable_not_function); 1252 return; 1253 } 1254 1255 D->addAttr(::new (S.Context) OverloadableAttr(Attr.getLoc(), S.Context)); 1256} 1257 1258static void HandleBlocksAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1259 if (!Attr.getParameterName()) { 1260 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1261 << "blocks" << 1; 1262 return; 1263 } 1264 1265 if (Attr.getNumArgs() != 0) { 1266 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1267 return; 1268 } 1269 1270 BlocksAttr::BlockType type; 1271 if (Attr.getParameterName()->isStr("byref")) 1272 type = BlocksAttr::ByRef; 1273 else { 1274 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 1275 << "blocks" << Attr.getParameterName(); 1276 return; 1277 } 1278 1279 d->addAttr(::new (S.Context) BlocksAttr(Attr.getLoc(), S.Context, type)); 1280} 1281 1282static void HandleSentinelAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1283 // check the attribute arguments. 1284 if (Attr.getNumArgs() > 2) { 1285 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 1286 return; 1287 } 1288 1289 int sentinel = 0; 1290 if (Attr.getNumArgs() > 0) { 1291 Expr *E = Attr.getArg(0); 1292 llvm::APSInt Idx(32); 1293 if (E->isTypeDependent() || E->isValueDependent() || 1294 !E->isIntegerConstantExpr(Idx, S.Context)) { 1295 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1296 << "sentinel" << 1 << E->getSourceRange(); 1297 return; 1298 } 1299 sentinel = Idx.getZExtValue(); 1300 1301 if (sentinel < 0) { 1302 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_less_than_zero) 1303 << E->getSourceRange(); 1304 return; 1305 } 1306 } 1307 1308 int nullPos = 0; 1309 if (Attr.getNumArgs() > 1) { 1310 Expr *E = Attr.getArg(1); 1311 llvm::APSInt Idx(32); 1312 if (E->isTypeDependent() || E->isValueDependent() || 1313 !E->isIntegerConstantExpr(Idx, S.Context)) { 1314 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1315 << "sentinel" << 2 << E->getSourceRange(); 1316 return; 1317 } 1318 nullPos = Idx.getZExtValue(); 1319 1320 if (nullPos > 1 || nullPos < 0) { 1321 // FIXME: This error message could be improved, it would be nice 1322 // to say what the bounds actually are. 1323 S.Diag(Attr.getLoc(), diag::err_attribute_sentinel_not_zero_or_one) 1324 << E->getSourceRange(); 1325 return; 1326 } 1327 } 1328 1329 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(d)) { 1330 const FunctionType *FT = FD->getType()->getAs<FunctionType>(); 1331 assert(FT && "FunctionDecl has non-function type?"); 1332 1333 if (isa<FunctionNoProtoType>(FT)) { 1334 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_named_arguments); 1335 return; 1336 } 1337 1338 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 1339 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 1340 return; 1341 } 1342 } else if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(d)) { 1343 if (!MD->isVariadic()) { 1344 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << 0; 1345 return; 1346 } 1347 } else if (isa<BlockDecl>(d)) { 1348 // Note! BlockDecl is typeless. Variadic diagnostics will be issued by the 1349 // caller. 1350 ; 1351 } else if (const VarDecl *V = dyn_cast<VarDecl>(d)) { 1352 QualType Ty = V->getType(); 1353 if (Ty->isBlockPointerType() || Ty->isFunctionPointerType()) { 1354 const FunctionType *FT = Ty->isFunctionPointerType() ? getFunctionType(d) 1355 : Ty->getAs<BlockPointerType>()->getPointeeType()->getAs<FunctionType>(); 1356 if (!cast<FunctionProtoType>(FT)->isVariadic()) { 1357 int m = Ty->isFunctionPointerType() ? 0 : 1; 1358 S.Diag(Attr.getLoc(), diag::warn_attribute_sentinel_not_variadic) << m; 1359 return; 1360 } 1361 } else { 1362 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1363 << Attr.getName() << ExpectedFunctionMethodOrBlock; 1364 return; 1365 } 1366 } else { 1367 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1368 << Attr.getName() << ExpectedFunctionMethodOrBlock; 1369 return; 1370 } 1371 d->addAttr(::new (S.Context) SentinelAttr(Attr.getLoc(), S.Context, sentinel, 1372 nullPos)); 1373} 1374 1375static void HandleWarnUnusedResult(Decl *D, const AttributeList &Attr, Sema &S) { 1376 // check the attribute arguments. 1377 if (Attr.getNumArgs() != 0) { 1378 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1379 return; 1380 } 1381 1382 if (!isFunction(D) && !isa<ObjCMethodDecl>(D)) { 1383 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1384 << Attr.getName() << ExpectedFunctionOrMethod; 1385 return; 1386 } 1387 1388 if (isFunction(D) && getFunctionType(D)->getResultType()->isVoidType()) { 1389 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 1390 << Attr.getName() << 0; 1391 return; 1392 } 1393 if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) 1394 if (MD->getResultType()->isVoidType()) { 1395 S.Diag(Attr.getLoc(), diag::warn_attribute_void_function_method) 1396 << Attr.getName() << 1; 1397 return; 1398 } 1399 1400 D->addAttr(::new (S.Context) WarnUnusedResultAttr(Attr.getLoc(), S.Context)); 1401} 1402 1403static void HandleWeakAttr(Decl *d, const AttributeList &attr, Sema &S) { 1404 // check the attribute arguments. 1405 if (attr.hasParameterOrArguments()) { 1406 S.Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1407 return; 1408 } 1409 1410 if (!isa<VarDecl>(d) && !isa<FunctionDecl>(d)) { 1411 S.Diag(attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1412 << attr.getName() << ExpectedVariableOrFunction; 1413 return; 1414 } 1415 1416 NamedDecl *nd = cast<NamedDecl>(d); 1417 1418 // 'weak' only applies to declarations with external linkage. 1419 if (hasEffectivelyInternalLinkage(nd)) { 1420 S.Diag(attr.getLoc(), diag::err_attribute_weak_static); 1421 return; 1422 } 1423 1424 nd->addAttr(::new (S.Context) WeakAttr(attr.getLoc(), S.Context)); 1425} 1426 1427static void HandleWeakImportAttr(Decl *D, const AttributeList &Attr, Sema &S) { 1428 // check the attribute arguments. 1429 if (Attr.getNumArgs() != 0) { 1430 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1431 return; 1432 } 1433 1434 // weak_import only applies to variable & function declarations. 1435 bool isDef = false; 1436 if (!D->canBeWeakImported(isDef)) { 1437 if (isDef) 1438 S.Diag(Attr.getLoc(), 1439 diag::warn_attribute_weak_import_invalid_on_definition) 1440 << "weak_import" << 2 /*variable and function*/; 1441 else if (isa<ObjCPropertyDecl>(D) || isa<ObjCMethodDecl>(D) || 1442 (S.Context.Target.getTriple().getOS() == llvm::Triple::Darwin && 1443 isa<ObjCInterfaceDecl>(D))) { 1444 // Nothing to warn about here. 1445 } else 1446 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1447 << Attr.getName() << ExpectedVariableOrFunction; 1448 1449 return; 1450 } 1451 1452 D->addAttr(::new (S.Context) WeakImportAttr(Attr.getLoc(), S.Context)); 1453} 1454 1455static void HandleReqdWorkGroupSize(Decl *D, const AttributeList &Attr, 1456 Sema &S) { 1457 // Attribute has 3 arguments. 1458 if (Attr.getNumArgs() != 3) { 1459 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1460 return; 1461 } 1462 1463 unsigned WGSize[3]; 1464 for (unsigned i = 0; i < 3; ++i) { 1465 Expr *E = Attr.getArg(i); 1466 llvm::APSInt ArgNum(32); 1467 if (E->isTypeDependent() || E->isValueDependent() || 1468 !E->isIntegerConstantExpr(ArgNum, S.Context)) { 1469 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 1470 << "reqd_work_group_size" << E->getSourceRange(); 1471 return; 1472 } 1473 WGSize[i] = (unsigned) ArgNum.getZExtValue(); 1474 } 1475 D->addAttr(::new (S.Context) ReqdWorkGroupSizeAttr(Attr.getLoc(), S.Context, 1476 WGSize[0], WGSize[1], 1477 WGSize[2])); 1478} 1479 1480static void HandleSectionAttr(Decl *D, const AttributeList &Attr, Sema &S) { 1481 // Attribute has no arguments. 1482 if (Attr.getNumArgs() != 1) { 1483 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1484 return; 1485 } 1486 1487 // Make sure that there is a string literal as the sections's single 1488 // argument. 1489 Expr *ArgExpr = Attr.getArg(0); 1490 StringLiteral *SE = dyn_cast<StringLiteral>(ArgExpr); 1491 if (!SE) { 1492 S.Diag(ArgExpr->getLocStart(), diag::err_attribute_not_string) << "section"; 1493 return; 1494 } 1495 1496 // If the target wants to validate the section specifier, make it happen. 1497 std::string Error = S.Context.Target.isValidSectionSpecifier(SE->getString()); 1498 if (!Error.empty()) { 1499 S.Diag(SE->getLocStart(), diag::err_attribute_section_invalid_for_target) 1500 << Error; 1501 return; 1502 } 1503 1504 // This attribute cannot be applied to local variables. 1505 if (isa<VarDecl>(D) && cast<VarDecl>(D)->hasLocalStorage()) { 1506 S.Diag(SE->getLocStart(), diag::err_attribute_section_local_variable); 1507 return; 1508 } 1509 1510 D->addAttr(::new (S.Context) SectionAttr(Attr.getLoc(), S.Context, 1511 SE->getString())); 1512} 1513 1514 1515static void HandleNothrowAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1516 // check the attribute arguments. 1517 if (Attr.hasParameterOrArguments()) { 1518 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1519 return; 1520 } 1521 1522 d->addAttr(::new (S.Context) NoThrowAttr(Attr.getLoc(), S.Context)); 1523} 1524 1525static void HandleConstAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1526 // check the attribute arguments. 1527 if (Attr.hasParameterOrArguments()) { 1528 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1529 return; 1530 } 1531 1532 d->addAttr(::new (S.Context) ConstAttr(Attr.getLoc(), S.Context)); 1533} 1534 1535static void HandlePureAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1536 // check the attribute arguments. 1537 if (Attr.getNumArgs() != 0) { 1538 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1539 return; 1540 } 1541 1542 d->addAttr(::new (S.Context) PureAttr(Attr.getLoc(), S.Context)); 1543} 1544 1545static void HandleCleanupAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1546 if (!Attr.getParameterName()) { 1547 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1548 return; 1549 } 1550 1551 if (Attr.getNumArgs() != 0) { 1552 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1553 return; 1554 } 1555 1556 VarDecl *VD = dyn_cast<VarDecl>(d); 1557 1558 if (!VD || !VD->hasLocalStorage()) { 1559 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "cleanup"; 1560 return; 1561 } 1562 1563 // Look up the function 1564 // FIXME: Lookup probably isn't looking in the right place 1565 NamedDecl *CleanupDecl 1566 = S.LookupSingleName(S.TUScope, Attr.getParameterName(), 1567 Attr.getParameterLoc(), Sema::LookupOrdinaryName); 1568 if (!CleanupDecl) { 1569 S.Diag(Attr.getParameterLoc(), diag::err_attribute_cleanup_arg_not_found) << 1570 Attr.getParameterName(); 1571 return; 1572 } 1573 1574 FunctionDecl *FD = dyn_cast<FunctionDecl>(CleanupDecl); 1575 if (!FD) { 1576 S.Diag(Attr.getParameterLoc(), 1577 diag::err_attribute_cleanup_arg_not_function) 1578 << Attr.getParameterName(); 1579 return; 1580 } 1581 1582 if (FD->getNumParams() != 1) { 1583 S.Diag(Attr.getParameterLoc(), 1584 diag::err_attribute_cleanup_func_must_take_one_arg) 1585 << Attr.getParameterName(); 1586 return; 1587 } 1588 1589 // We're currently more strict than GCC about what function types we accept. 1590 // If this ever proves to be a problem it should be easy to fix. 1591 QualType Ty = S.Context.getPointerType(VD->getType()); 1592 QualType ParamTy = FD->getParamDecl(0)->getType(); 1593 if (S.CheckAssignmentConstraints(FD->getParamDecl(0)->getLocation(), 1594 ParamTy, Ty) != Sema::Compatible) { 1595 S.Diag(Attr.getParameterLoc(), 1596 diag::err_attribute_cleanup_func_arg_incompatible_type) << 1597 Attr.getParameterName() << ParamTy << Ty; 1598 return; 1599 } 1600 1601 d->addAttr(::new (S.Context) CleanupAttr(Attr.getLoc(), S.Context, FD)); 1602 S.MarkDeclarationReferenced(Attr.getParameterLoc(), FD); 1603} 1604 1605/// Handle __attribute__((format_arg((idx)))) attribute based on 1606/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 1607static void HandleFormatArgAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1608 if (Attr.getNumArgs() != 1) { 1609 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1610 return; 1611 } 1612 if (!isFunctionOrMethod(d) || !hasFunctionProto(d)) { 1613 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1614 << Attr.getName() << ExpectedFunction; 1615 return; 1616 } 1617 1618 // In C++ the implicit 'this' function parameter also counts, and they are 1619 // counted from one. 1620 bool HasImplicitThisParam = isInstanceMethod(d); 1621 unsigned NumArgs = getFunctionOrMethodNumArgs(d) + HasImplicitThisParam; 1622 unsigned FirstIdx = 1; 1623 1624 // checks for the 2nd argument 1625 Expr *IdxExpr = Attr.getArg(0); 1626 llvm::APSInt Idx(32); 1627 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 1628 !IdxExpr->isIntegerConstantExpr(Idx, S.Context)) { 1629 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1630 << "format" << 2 << IdxExpr->getSourceRange(); 1631 return; 1632 } 1633 1634 if (Idx.getZExtValue() < FirstIdx || Idx.getZExtValue() > NumArgs) { 1635 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 1636 << "format" << 2 << IdxExpr->getSourceRange(); 1637 return; 1638 } 1639 1640 unsigned ArgIdx = Idx.getZExtValue() - 1; 1641 1642 if (HasImplicitThisParam) { 1643 if (ArgIdx == 0) { 1644 S.Diag(Attr.getLoc(), diag::err_attribute_invalid_implicit_this_argument) 1645 << "format_arg" << IdxExpr->getSourceRange(); 1646 return; 1647 } 1648 ArgIdx--; 1649 } 1650 1651 // make sure the format string is really a string 1652 QualType Ty = getFunctionOrMethodArgType(d, ArgIdx); 1653 1654 bool not_nsstring_type = !isNSStringType(Ty, S.Context); 1655 if (not_nsstring_type && 1656 !isCFStringType(Ty, S.Context) && 1657 (!Ty->isPointerType() || 1658 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 1659 // FIXME: Should highlight the actual expression that has the wrong type. 1660 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 1661 << (not_nsstring_type ? "a string type" : "an NSString") 1662 << IdxExpr->getSourceRange(); 1663 return; 1664 } 1665 Ty = getFunctionOrMethodResultType(d); 1666 if (!isNSStringType(Ty, S.Context) && 1667 !isCFStringType(Ty, S.Context) && 1668 (!Ty->isPointerType() || 1669 !Ty->getAs<PointerType>()->getPointeeType()->isCharType())) { 1670 // FIXME: Should highlight the actual expression that has the wrong type. 1671 S.Diag(Attr.getLoc(), diag::err_format_attribute_result_not) 1672 << (not_nsstring_type ? "string type" : "NSString") 1673 << IdxExpr->getSourceRange(); 1674 return; 1675 } 1676 1677 d->addAttr(::new (S.Context) FormatArgAttr(Attr.getLoc(), S.Context, 1678 Idx.getZExtValue())); 1679} 1680 1681enum FormatAttrKind { 1682 CFStringFormat, 1683 NSStringFormat, 1684 StrftimeFormat, 1685 SupportedFormat, 1686 IgnoredFormat, 1687 InvalidFormat 1688}; 1689 1690/// getFormatAttrKind - Map from format attribute names to supported format 1691/// types. 1692static FormatAttrKind getFormatAttrKind(llvm::StringRef Format) { 1693 // Check for formats that get handled specially. 1694 if (Format == "NSString") 1695 return NSStringFormat; 1696 if (Format == "CFString") 1697 return CFStringFormat; 1698 if (Format == "strftime") 1699 return StrftimeFormat; 1700 1701 // Otherwise, check for supported formats. 1702 if (Format == "scanf" || Format == "printf" || Format == "printf0" || 1703 Format == "strfmon" || Format == "cmn_err" || Format == "strftime" || 1704 Format == "NSString" || Format == "CFString" || Format == "vcmn_err" || 1705 Format == "zcmn_err" || 1706 Format == "kprintf") // OpenBSD. 1707 return SupportedFormat; 1708 1709 if (Format == "gcc_diag" || Format == "gcc_cdiag" || 1710 Format == "gcc_cxxdiag" || Format == "gcc_tdiag") 1711 return IgnoredFormat; 1712 1713 return InvalidFormat; 1714} 1715 1716/// Handle __attribute__((init_priority(priority))) attributes based on 1717/// http://gcc.gnu.org/onlinedocs/gcc/C_002b_002b-Attributes.html 1718static void HandleInitPriorityAttr(Decl *d, const AttributeList &Attr, 1719 Sema &S) { 1720 if (!S.getLangOptions().CPlusPlus) { 1721 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << Attr.getName(); 1722 return; 1723 } 1724 1725 if (!isa<VarDecl>(d) || S.getCurFunctionOrMethodDecl()) { 1726 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 1727 Attr.setInvalid(); 1728 return; 1729 } 1730 QualType T = dyn_cast<VarDecl>(d)->getType(); 1731 if (S.Context.getAsArrayType(T)) 1732 T = S.Context.getBaseElementType(T); 1733 if (!T->getAs<RecordType>()) { 1734 S.Diag(Attr.getLoc(), diag::err_init_priority_object_attr); 1735 Attr.setInvalid(); 1736 return; 1737 } 1738 1739 if (Attr.getNumArgs() != 1) { 1740 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1741 Attr.setInvalid(); 1742 return; 1743 } 1744 Expr *priorityExpr = Attr.getArg(0); 1745 1746 llvm::APSInt priority(32); 1747 if (priorityExpr->isTypeDependent() || priorityExpr->isValueDependent() || 1748 !priorityExpr->isIntegerConstantExpr(priority, S.Context)) { 1749 S.Diag(Attr.getLoc(), diag::err_attribute_argument_not_int) 1750 << "init_priority" << priorityExpr->getSourceRange(); 1751 Attr.setInvalid(); 1752 return; 1753 } 1754 unsigned prioritynum = priority.getZExtValue(); 1755 if (prioritynum < 101 || prioritynum > 65535) { 1756 S.Diag(Attr.getLoc(), diag::err_attribute_argument_outof_range) 1757 << priorityExpr->getSourceRange(); 1758 Attr.setInvalid(); 1759 return; 1760 } 1761 d->addAttr(::new (S.Context) InitPriorityAttr(Attr.getLoc(), S.Context, 1762 prioritynum)); 1763} 1764 1765/// Handle __attribute__((format(type,idx,firstarg))) attributes based on 1766/// http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html 1767static void HandleFormatAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1768 1769 if (!Attr.getParameterName()) { 1770 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 1771 << "format" << 1; 1772 return; 1773 } 1774 1775 if (Attr.getNumArgs() != 2) { 1776 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 3; 1777 return; 1778 } 1779 1780 if (!isFunctionOrMethodOrBlock(d) || !hasFunctionProto(d)) { 1781 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1782 << Attr.getName() << ExpectedFunction; 1783 return; 1784 } 1785 1786 // In C++ the implicit 'this' function parameter also counts, and they are 1787 // counted from one. 1788 bool HasImplicitThisParam = isInstanceMethod(d); 1789 unsigned NumArgs = getFunctionOrMethodNumArgs(d) + HasImplicitThisParam; 1790 unsigned FirstIdx = 1; 1791 1792 llvm::StringRef Format = Attr.getParameterName()->getName(); 1793 1794 // Normalize the argument, __foo__ becomes foo. 1795 if (Format.startswith("__") && Format.endswith("__")) 1796 Format = Format.substr(2, Format.size() - 4); 1797 1798 // Check for supported formats. 1799 FormatAttrKind Kind = getFormatAttrKind(Format); 1800 1801 if (Kind == IgnoredFormat) 1802 return; 1803 1804 if (Kind == InvalidFormat) { 1805 S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported) 1806 << "format" << Attr.getParameterName()->getName(); 1807 return; 1808 } 1809 1810 // checks for the 2nd argument 1811 Expr *IdxExpr = Attr.getArg(0); 1812 llvm::APSInt Idx(32); 1813 if (IdxExpr->isTypeDependent() || IdxExpr->isValueDependent() || 1814 !IdxExpr->isIntegerConstantExpr(Idx, S.Context)) { 1815 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1816 << "format" << 2 << IdxExpr->getSourceRange(); 1817 return; 1818 } 1819 1820 if (Idx.getZExtValue() < FirstIdx || Idx.getZExtValue() > NumArgs) { 1821 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 1822 << "format" << 2 << IdxExpr->getSourceRange(); 1823 return; 1824 } 1825 1826 // FIXME: Do we need to bounds check? 1827 unsigned ArgIdx = Idx.getZExtValue() - 1; 1828 1829 if (HasImplicitThisParam) { 1830 if (ArgIdx == 0) { 1831 S.Diag(Attr.getLoc(), 1832 diag::err_format_attribute_implicit_this_format_string) 1833 << IdxExpr->getSourceRange(); 1834 return; 1835 } 1836 ArgIdx--; 1837 } 1838 1839 // make sure the format string is really a string 1840 QualType Ty = getFunctionOrMethodArgType(d, ArgIdx); 1841 1842 if (Kind == CFStringFormat) { 1843 if (!isCFStringType(Ty, S.Context)) { 1844 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 1845 << "a CFString" << IdxExpr->getSourceRange(); 1846 return; 1847 } 1848 } else if (Kind == NSStringFormat) { 1849 // FIXME: do we need to check if the type is NSString*? What are the 1850 // semantics? 1851 if (!isNSStringType(Ty, S.Context)) { 1852 // FIXME: Should highlight the actual expression that has the wrong type. 1853 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 1854 << "an NSString" << IdxExpr->getSourceRange(); 1855 return; 1856 } 1857 } else if (!Ty->isPointerType() || 1858 !Ty->getAs<PointerType>()->getPointeeType()->isCharType()) { 1859 // FIXME: Should highlight the actual expression that has the wrong type. 1860 S.Diag(Attr.getLoc(), diag::err_format_attribute_not) 1861 << "a string type" << IdxExpr->getSourceRange(); 1862 return; 1863 } 1864 1865 // check the 3rd argument 1866 Expr *FirstArgExpr = Attr.getArg(1); 1867 llvm::APSInt FirstArg(32); 1868 if (FirstArgExpr->isTypeDependent() || FirstArgExpr->isValueDependent() || 1869 !FirstArgExpr->isIntegerConstantExpr(FirstArg, S.Context)) { 1870 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 1871 << "format" << 3 << FirstArgExpr->getSourceRange(); 1872 return; 1873 } 1874 1875 // check if the function is variadic if the 3rd argument non-zero 1876 if (FirstArg != 0) { 1877 if (isFunctionOrMethodVariadic(d)) { 1878 ++NumArgs; // +1 for ... 1879 } else { 1880 S.Diag(d->getLocation(), diag::err_format_attribute_requires_variadic); 1881 return; 1882 } 1883 } 1884 1885 // strftime requires FirstArg to be 0 because it doesn't read from any 1886 // variable the input is just the current time + the format string. 1887 if (Kind == StrftimeFormat) { 1888 if (FirstArg != 0) { 1889 S.Diag(Attr.getLoc(), diag::err_format_strftime_third_parameter) 1890 << FirstArgExpr->getSourceRange(); 1891 return; 1892 } 1893 // if 0 it disables parameter checking (to use with e.g. va_list) 1894 } else if (FirstArg != 0 && FirstArg != NumArgs) { 1895 S.Diag(Attr.getLoc(), diag::err_attribute_argument_out_of_bounds) 1896 << "format" << 3 << FirstArgExpr->getSourceRange(); 1897 return; 1898 } 1899 1900 d->addAttr(::new (S.Context) FormatAttr(Attr.getLoc(), S.Context, Format, 1901 Idx.getZExtValue(), 1902 FirstArg.getZExtValue())); 1903} 1904 1905static void HandleTransparentUnionAttr(Decl *d, const AttributeList &Attr, 1906 Sema &S) { 1907 // check the attribute arguments. 1908 if (Attr.getNumArgs() != 0) { 1909 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 1910 return; 1911 } 1912 1913 // Try to find the underlying union declaration. 1914 RecordDecl *RD = 0; 1915 TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(d); 1916 if (TD && TD->getUnderlyingType()->isUnionType()) 1917 RD = TD->getUnderlyingType()->getAsUnionType()->getDecl(); 1918 else 1919 RD = dyn_cast<RecordDecl>(d); 1920 1921 if (!RD || !RD->isUnion()) { 1922 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 1923 << Attr.getName() << ExpectedUnion; 1924 return; 1925 } 1926 1927 if (!RD->isDefinition()) { 1928 S.Diag(Attr.getLoc(), 1929 diag::warn_transparent_union_attribute_not_definition); 1930 return; 1931 } 1932 1933 RecordDecl::field_iterator Field = RD->field_begin(), 1934 FieldEnd = RD->field_end(); 1935 if (Field == FieldEnd) { 1936 S.Diag(Attr.getLoc(), diag::warn_transparent_union_attribute_zero_fields); 1937 return; 1938 } 1939 1940 FieldDecl *FirstField = *Field; 1941 QualType FirstType = FirstField->getType(); 1942 if (FirstType->hasFloatingRepresentation() || FirstType->isVectorType()) { 1943 S.Diag(FirstField->getLocation(), 1944 diag::warn_transparent_union_attribute_floating) 1945 << FirstType->isVectorType() << FirstType; 1946 return; 1947 } 1948 1949 uint64_t FirstSize = S.Context.getTypeSize(FirstType); 1950 uint64_t FirstAlign = S.Context.getTypeAlign(FirstType); 1951 for (; Field != FieldEnd; ++Field) { 1952 QualType FieldType = Field->getType(); 1953 if (S.Context.getTypeSize(FieldType) != FirstSize || 1954 S.Context.getTypeAlign(FieldType) != FirstAlign) { 1955 // Warn if we drop the attribute. 1956 bool isSize = S.Context.getTypeSize(FieldType) != FirstSize; 1957 unsigned FieldBits = isSize? S.Context.getTypeSize(FieldType) 1958 : S.Context.getTypeAlign(FieldType); 1959 S.Diag(Field->getLocation(), 1960 diag::warn_transparent_union_attribute_field_size_align) 1961 << isSize << Field->getDeclName() << FieldBits; 1962 unsigned FirstBits = isSize? FirstSize : FirstAlign; 1963 S.Diag(FirstField->getLocation(), 1964 diag::note_transparent_union_first_field_size_align) 1965 << isSize << FirstBits; 1966 return; 1967 } 1968 } 1969 1970 RD->addAttr(::new (S.Context) TransparentUnionAttr(Attr.getLoc(), S.Context)); 1971} 1972 1973static void HandleAnnotateAttr(Decl *d, const AttributeList &Attr, Sema &S) { 1974 // check the attribute arguments. 1975 if (Attr.getNumArgs() != 1) { 1976 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1977 return; 1978 } 1979 Expr *ArgExpr = Attr.getArg(0); 1980 StringLiteral *SE = dyn_cast<StringLiteral>(ArgExpr); 1981 1982 // Make sure that there is a string literal as the annotation's single 1983 // argument. 1984 if (!SE) { 1985 S.Diag(ArgExpr->getLocStart(), diag::err_attribute_not_string) <<"annotate"; 1986 return; 1987 } 1988 d->addAttr(::new (S.Context) AnnotateAttr(Attr.getLoc(), S.Context, 1989 SE->getString())); 1990} 1991 1992static void HandleAlignedAttr(Decl *D, const AttributeList &Attr, Sema &S) { 1993 // check the attribute arguments. 1994 if (Attr.getNumArgs() > 1) { 1995 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 1996 return; 1997 } 1998 1999 //FIXME: The C++0x version of this attribute has more limited applicabilty 2000 // than GNU's, and should error out when it is used to specify a 2001 // weaker alignment, rather than being silently ignored. 2002 2003 if (Attr.getNumArgs() == 0) { 2004 D->addAttr(::new (S.Context) AlignedAttr(Attr.getLoc(), S.Context, true, 0)); 2005 return; 2006 } 2007 2008 S.AddAlignedAttr(Attr.getLoc(), D, Attr.getArg(0)); 2009} 2010 2011void Sema::AddAlignedAttr(SourceLocation AttrLoc, Decl *D, Expr *E) { 2012 if (E->isTypeDependent() || E->isValueDependent()) { 2013 // Save dependent expressions in the AST to be instantiated. 2014 D->addAttr(::new (Context) AlignedAttr(AttrLoc, Context, true, E)); 2015 return; 2016 } 2017 2018 // FIXME: Cache the number on the Attr object? 2019 llvm::APSInt Alignment(32); 2020 if (!E->isIntegerConstantExpr(Alignment, Context)) { 2021 Diag(AttrLoc, diag::err_attribute_argument_not_int) 2022 << "aligned" << E->getSourceRange(); 2023 return; 2024 } 2025 if (!llvm::isPowerOf2_64(Alignment.getZExtValue())) { 2026 Diag(AttrLoc, diag::err_attribute_aligned_not_power_of_two) 2027 << E->getSourceRange(); 2028 return; 2029 } 2030 2031 D->addAttr(::new (Context) AlignedAttr(AttrLoc, Context, true, E)); 2032} 2033 2034void Sema::AddAlignedAttr(SourceLocation AttrLoc, Decl *D, TypeSourceInfo *TS) { 2035 // FIXME: Cache the number on the Attr object if non-dependent? 2036 // FIXME: Perform checking of type validity 2037 D->addAttr(::new (Context) AlignedAttr(AttrLoc, Context, false, TS)); 2038 return; 2039} 2040 2041/// HandleModeAttr - This attribute modifies the width of a decl with primitive 2042/// type. 2043/// 2044/// Despite what would be logical, the mode attribute is a decl attribute, not a 2045/// type attribute: 'int ** __attribute((mode(HI))) *G;' tries to make 'G' be 2046/// HImode, not an intermediate pointer. 2047static void HandleModeAttr(Decl *D, const AttributeList &Attr, Sema &S) { 2048 // This attribute isn't documented, but glibc uses it. It changes 2049 // the width of an int or unsigned int to the specified size. 2050 2051 // Check that there aren't any arguments 2052 if (Attr.getNumArgs() != 0) { 2053 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2054 return; 2055 } 2056 2057 IdentifierInfo *Name = Attr.getParameterName(); 2058 if (!Name) { 2059 S.Diag(Attr.getLoc(), diag::err_attribute_missing_parameter_name); 2060 return; 2061 } 2062 2063 llvm::StringRef Str = Attr.getParameterName()->getName(); 2064 2065 // Normalize the attribute name, __foo__ becomes foo. 2066 if (Str.startswith("__") && Str.endswith("__")) 2067 Str = Str.substr(2, Str.size() - 4); 2068 2069 unsigned DestWidth = 0; 2070 bool IntegerMode = true; 2071 bool ComplexMode = false; 2072 switch (Str.size()) { 2073 case 2: 2074 switch (Str[0]) { 2075 case 'Q': DestWidth = 8; break; 2076 case 'H': DestWidth = 16; break; 2077 case 'S': DestWidth = 32; break; 2078 case 'D': DestWidth = 64; break; 2079 case 'X': DestWidth = 96; break; 2080 case 'T': DestWidth = 128; break; 2081 } 2082 if (Str[1] == 'F') { 2083 IntegerMode = false; 2084 } else if (Str[1] == 'C') { 2085 IntegerMode = false; 2086 ComplexMode = true; 2087 } else if (Str[1] != 'I') { 2088 DestWidth = 0; 2089 } 2090 break; 2091 case 4: 2092 // FIXME: glibc uses 'word' to define register_t; this is narrower than a 2093 // pointer on PIC16 and other embedded platforms. 2094 if (Str == "word") 2095 DestWidth = S.Context.Target.getPointerWidth(0); 2096 else if (Str == "byte") 2097 DestWidth = S.Context.Target.getCharWidth(); 2098 break; 2099 case 7: 2100 if (Str == "pointer") 2101 DestWidth = S.Context.Target.getPointerWidth(0); 2102 break; 2103 } 2104 2105 QualType OldTy; 2106 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) 2107 OldTy = TD->getUnderlyingType(); 2108 else if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) 2109 OldTy = VD->getType(); 2110 else { 2111 S.Diag(D->getLocation(), diag::err_attr_wrong_decl) 2112 << "mode" << SourceRange(Attr.getLoc(), Attr.getLoc()); 2113 return; 2114 } 2115 2116 if (!OldTy->getAs<BuiltinType>() && !OldTy->isComplexType()) 2117 S.Diag(Attr.getLoc(), diag::err_mode_not_primitive); 2118 else if (IntegerMode) { 2119 if (!OldTy->isIntegralOrEnumerationType()) 2120 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2121 } else if (ComplexMode) { 2122 if (!OldTy->isComplexType()) 2123 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2124 } else { 2125 if (!OldTy->isFloatingType()) 2126 S.Diag(Attr.getLoc(), diag::err_mode_wrong_type); 2127 } 2128 2129 // FIXME: Sync this with InitializePredefinedMacros; we need to match int8_t 2130 // and friends, at least with glibc. 2131 // FIXME: Make sure 32/64-bit integers don't get defined to types of the wrong 2132 // width on unusual platforms. 2133 // FIXME: Make sure floating-point mappings are accurate 2134 // FIXME: Support XF and TF types 2135 QualType NewTy; 2136 switch (DestWidth) { 2137 case 0: 2138 S.Diag(Attr.getLoc(), diag::err_unknown_machine_mode) << Name; 2139 return; 2140 default: 2141 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2142 return; 2143 case 8: 2144 if (!IntegerMode) { 2145 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2146 return; 2147 } 2148 if (OldTy->isSignedIntegerType()) 2149 NewTy = S.Context.SignedCharTy; 2150 else 2151 NewTy = S.Context.UnsignedCharTy; 2152 break; 2153 case 16: 2154 if (!IntegerMode) { 2155 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2156 return; 2157 } 2158 if (OldTy->isSignedIntegerType()) 2159 NewTy = S.Context.ShortTy; 2160 else 2161 NewTy = S.Context.UnsignedShortTy; 2162 break; 2163 case 32: 2164 if (!IntegerMode) 2165 NewTy = S.Context.FloatTy; 2166 else if (OldTy->isSignedIntegerType()) 2167 NewTy = S.Context.IntTy; 2168 else 2169 NewTy = S.Context.UnsignedIntTy; 2170 break; 2171 case 64: 2172 if (!IntegerMode) 2173 NewTy = S.Context.DoubleTy; 2174 else if (OldTy->isSignedIntegerType()) 2175 if (S.Context.Target.getLongWidth() == 64) 2176 NewTy = S.Context.LongTy; 2177 else 2178 NewTy = S.Context.LongLongTy; 2179 else 2180 if (S.Context.Target.getLongWidth() == 64) 2181 NewTy = S.Context.UnsignedLongTy; 2182 else 2183 NewTy = S.Context.UnsignedLongLongTy; 2184 break; 2185 case 96: 2186 NewTy = S.Context.LongDoubleTy; 2187 break; 2188 case 128: 2189 if (!IntegerMode) { 2190 S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name; 2191 return; 2192 } 2193 if (OldTy->isSignedIntegerType()) 2194 NewTy = S.Context.Int128Ty; 2195 else 2196 NewTy = S.Context.UnsignedInt128Ty; 2197 break; 2198 } 2199 2200 if (ComplexMode) { 2201 NewTy = S.Context.getComplexType(NewTy); 2202 } 2203 2204 // Install the new type. 2205 if (TypedefNameDecl *TD = dyn_cast<TypedefNameDecl>(D)) { 2206 // FIXME: preserve existing source info. 2207 TD->setTypeSourceInfo(S.Context.getTrivialTypeSourceInfo(NewTy)); 2208 } else 2209 cast<ValueDecl>(D)->setType(NewTy); 2210} 2211 2212static void HandleNoDebugAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2213 // check the attribute arguments. 2214 if (Attr.getNumArgs() > 0) { 2215 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2216 return; 2217 } 2218 2219 if (!isFunctionOrMethod(d)) { 2220 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2221 << Attr.getName() << ExpectedFunction; 2222 return; 2223 } 2224 2225 d->addAttr(::new (S.Context) NoDebugAttr(Attr.getLoc(), S.Context)); 2226} 2227 2228static void HandleNoInlineAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2229 // check the attribute arguments. 2230 if (Attr.getNumArgs() != 0) { 2231 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2232 return; 2233 } 2234 2235 if (!isa<FunctionDecl>(d)) { 2236 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2237 << Attr.getName() << ExpectedFunction; 2238 return; 2239 } 2240 2241 d->addAttr(::new (S.Context) NoInlineAttr(Attr.getLoc(), S.Context)); 2242} 2243 2244static void HandleNoInstrumentFunctionAttr(Decl *d, const AttributeList &Attr, 2245 Sema &S) { 2246 // check the attribute arguments. 2247 if (Attr.getNumArgs() != 0) { 2248 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2249 return; 2250 } 2251 2252 if (!isa<FunctionDecl>(d)) { 2253 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2254 << Attr.getName() << ExpectedFunction; 2255 return; 2256 } 2257 2258 d->addAttr(::new (S.Context) NoInstrumentFunctionAttr(Attr.getLoc(), 2259 S.Context)); 2260} 2261 2262static void HandleConstantAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2263 if (S.LangOpts.CUDA) { 2264 // check the attribute arguments. 2265 if (Attr.hasParameterOrArguments()) { 2266 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2267 return; 2268 } 2269 2270 if (!isa<VarDecl>(d)) { 2271 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2272 << Attr.getName() << ExpectedVariable; 2273 return; 2274 } 2275 2276 d->addAttr(::new (S.Context) CUDAConstantAttr(Attr.getLoc(), S.Context)); 2277 } else { 2278 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "constant"; 2279 } 2280} 2281 2282static void HandleDeviceAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2283 if (S.LangOpts.CUDA) { 2284 // check the attribute arguments. 2285 if (Attr.getNumArgs() != 0) { 2286 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2287 return; 2288 } 2289 2290 if (!isa<FunctionDecl>(d) && !isa<VarDecl>(d)) { 2291 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2292 << Attr.getName() << ExpectedVariableOrFunction; 2293 return; 2294 } 2295 2296 d->addAttr(::new (S.Context) CUDADeviceAttr(Attr.getLoc(), S.Context)); 2297 } else { 2298 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "device"; 2299 } 2300} 2301 2302static void HandleGlobalAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2303 if (S.LangOpts.CUDA) { 2304 // check the attribute arguments. 2305 if (Attr.getNumArgs() != 0) { 2306 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2307 return; 2308 } 2309 2310 if (!isa<FunctionDecl>(d)) { 2311 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2312 << Attr.getName() << ExpectedFunction; 2313 return; 2314 } 2315 2316 FunctionDecl *FD = cast<FunctionDecl>(d); 2317 if (!FD->getResultType()->isVoidType()) { 2318 TypeLoc TL = FD->getTypeSourceInfo()->getTypeLoc().IgnoreParens(); 2319 if (FunctionTypeLoc* FTL = dyn_cast<FunctionTypeLoc>(&TL)) { 2320 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 2321 << FD->getType() 2322 << FixItHint::CreateReplacement(FTL->getResultLoc().getSourceRange(), 2323 "void"); 2324 } else { 2325 S.Diag(FD->getTypeSpecStartLoc(), diag::err_kern_type_not_void_return) 2326 << FD->getType(); 2327 } 2328 return; 2329 } 2330 2331 d->addAttr(::new (S.Context) CUDAGlobalAttr(Attr.getLoc(), S.Context)); 2332 } else { 2333 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "global"; 2334 } 2335} 2336 2337static void HandleHostAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2338 if (S.LangOpts.CUDA) { 2339 // check the attribute arguments. 2340 if (Attr.getNumArgs() != 0) { 2341 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2342 return; 2343 } 2344 2345 if (!isa<FunctionDecl>(d)) { 2346 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2347 << Attr.getName() << ExpectedFunction; 2348 return; 2349 } 2350 2351 d->addAttr(::new (S.Context) CUDAHostAttr(Attr.getLoc(), S.Context)); 2352 } else { 2353 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "host"; 2354 } 2355} 2356 2357static void HandleSharedAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2358 if (S.LangOpts.CUDA) { 2359 // check the attribute arguments. 2360 if (Attr.getNumArgs() != 0) { 2361 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2362 return; 2363 } 2364 2365 if (!isa<VarDecl>(d)) { 2366 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2367 << Attr.getName() << ExpectedVariable; 2368 return; 2369 } 2370 2371 d->addAttr(::new (S.Context) CUDASharedAttr(Attr.getLoc(), S.Context)); 2372 } else { 2373 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "shared"; 2374 } 2375} 2376 2377static void HandleGNUInlineAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2378 // check the attribute arguments. 2379 if (Attr.getNumArgs() != 0) { 2380 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2381 return; 2382 } 2383 2384 FunctionDecl *Fn = dyn_cast<FunctionDecl>(d); 2385 if (Fn == 0) { 2386 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2387 << Attr.getName() << ExpectedFunction; 2388 return; 2389 } 2390 2391 if (!Fn->isInlineSpecified()) { 2392 S.Diag(Attr.getLoc(), diag::warn_gnu_inline_attribute_requires_inline); 2393 return; 2394 } 2395 2396 d->addAttr(::new (S.Context) GNUInlineAttr(Attr.getLoc(), S.Context)); 2397} 2398 2399static void HandleCallConvAttr(Decl *d, const AttributeList &attr, Sema &S) { 2400 if (hasDeclarator(d)) return; 2401 2402 // Diagnostic is emitted elsewhere: here we store the (valid) attr 2403 // in the Decl node for syntactic reasoning, e.g., pretty-printing. 2404 CallingConv CC; 2405 if (S.CheckCallingConvAttr(attr, CC)) 2406 return; 2407 2408 if (!isa<ObjCMethodDecl>(d)) { 2409 S.Diag(attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2410 << attr.getName() << ExpectedFunctionOrMethod; 2411 return; 2412 } 2413 2414 switch (attr.getKind()) { 2415 case AttributeList::AT_fastcall: 2416 d->addAttr(::new (S.Context) FastCallAttr(attr.getLoc(), S.Context)); 2417 return; 2418 case AttributeList::AT_stdcall: 2419 d->addAttr(::new (S.Context) StdCallAttr(attr.getLoc(), S.Context)); 2420 return; 2421 case AttributeList::AT_thiscall: 2422 d->addAttr(::new (S.Context) ThisCallAttr(attr.getLoc(), S.Context)); 2423 return; 2424 case AttributeList::AT_cdecl: 2425 d->addAttr(::new (S.Context) CDeclAttr(attr.getLoc(), S.Context)); 2426 return; 2427 case AttributeList::AT_pascal: 2428 d->addAttr(::new (S.Context) PascalAttr(attr.getLoc(), S.Context)); 2429 return; 2430 case AttributeList::AT_pcs: { 2431 Expr *Arg = attr.getArg(0); 2432 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 2433 if (Str == 0 || Str->isWide()) { 2434 S.Diag(attr.getLoc(), diag::err_attribute_argument_n_not_string) 2435 << "pcs" << 1; 2436 attr.setInvalid(); 2437 return; 2438 } 2439 2440 llvm::StringRef StrRef = Str->getString(); 2441 PcsAttr::PCSType PCS; 2442 if (StrRef == "aapcs") 2443 PCS = PcsAttr::AAPCS; 2444 else if (StrRef == "aapcs-vfp") 2445 PCS = PcsAttr::AAPCS_VFP; 2446 else { 2447 S.Diag(attr.getLoc(), diag::err_invalid_pcs); 2448 attr.setInvalid(); 2449 return; 2450 } 2451 2452 d->addAttr(::new (S.Context) PcsAttr(attr.getLoc(), S.Context, PCS)); 2453 } 2454 default: 2455 llvm_unreachable("unexpected attribute kind"); 2456 return; 2457 } 2458} 2459 2460static void HandleOpenCLKernelAttr(Decl *d, const AttributeList &Attr, Sema &S){ 2461 assert(Attr.isInvalid() == false); 2462 d->addAttr(::new (S.Context) OpenCLKernelAttr(Attr.getLoc(), S.Context)); 2463} 2464 2465bool Sema::CheckCallingConvAttr(const AttributeList &attr, CallingConv &CC) { 2466 if (attr.isInvalid()) 2467 return true; 2468 2469 if ((attr.getNumArgs() != 0 && 2470 !(attr.getKind() == AttributeList::AT_pcs && attr.getNumArgs() == 1)) || 2471 attr.getParameterName()) { 2472 Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 0; 2473 attr.setInvalid(); 2474 return true; 2475 } 2476 2477 // TODO: diagnose uses of these conventions on the wrong target. Or, better 2478 // move to TargetAttributesSema one day. 2479 switch (attr.getKind()) { 2480 case AttributeList::AT_cdecl: CC = CC_C; break; 2481 case AttributeList::AT_fastcall: CC = CC_X86FastCall; break; 2482 case AttributeList::AT_stdcall: CC = CC_X86StdCall; break; 2483 case AttributeList::AT_thiscall: CC = CC_X86ThisCall; break; 2484 case AttributeList::AT_pascal: CC = CC_X86Pascal; break; 2485 case AttributeList::AT_pcs: { 2486 Expr *Arg = attr.getArg(0); 2487 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 2488 if (Str == 0 || Str->isWide()) { 2489 Diag(attr.getLoc(), diag::err_attribute_argument_n_not_string) 2490 << "pcs" << 1; 2491 attr.setInvalid(); 2492 return true; 2493 } 2494 2495 llvm::StringRef StrRef = Str->getString(); 2496 if (StrRef == "aapcs") { 2497 CC = CC_AAPCS; 2498 break; 2499 } else if (StrRef == "aapcs-vfp") { 2500 CC = CC_AAPCS_VFP; 2501 break; 2502 } 2503 // FALLS THROUGH 2504 } 2505 default: llvm_unreachable("unexpected attribute kind"); return true; 2506 } 2507 2508 return false; 2509} 2510 2511static void HandleRegparmAttr(Decl *d, const AttributeList &attr, Sema &S) { 2512 if (hasDeclarator(d)) return; 2513 2514 unsigned numParams; 2515 if (S.CheckRegparmAttr(attr, numParams)) 2516 return; 2517 2518 if (!isa<ObjCMethodDecl>(d)) { 2519 S.Diag(attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2520 << attr.getName() << ExpectedFunctionOrMethod; 2521 return; 2522 } 2523 2524 d->addAttr(::new (S.Context) RegparmAttr(attr.getLoc(), S.Context, numParams)); 2525} 2526 2527/// Checks a regparm attribute, returning true if it is ill-formed and 2528/// otherwise setting numParams to the appropriate value. 2529bool Sema::CheckRegparmAttr(const AttributeList &attr, unsigned &numParams) { 2530 if (attr.isInvalid()) 2531 return true; 2532 2533 if (attr.getNumArgs() != 1) { 2534 Diag(attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2535 attr.setInvalid(); 2536 return true; 2537 } 2538 2539 Expr *NumParamsExpr = attr.getArg(0); 2540 llvm::APSInt NumParams(32); 2541 if (NumParamsExpr->isTypeDependent() || NumParamsExpr->isValueDependent() || 2542 !NumParamsExpr->isIntegerConstantExpr(NumParams, Context)) { 2543 Diag(attr.getLoc(), diag::err_attribute_argument_not_int) 2544 << "regparm" << NumParamsExpr->getSourceRange(); 2545 attr.setInvalid(); 2546 return true; 2547 } 2548 2549 if (Context.Target.getRegParmMax() == 0) { 2550 Diag(attr.getLoc(), diag::err_attribute_regparm_wrong_platform) 2551 << NumParamsExpr->getSourceRange(); 2552 attr.setInvalid(); 2553 return true; 2554 } 2555 2556 numParams = NumParams.getZExtValue(); 2557 if (numParams > Context.Target.getRegParmMax()) { 2558 Diag(attr.getLoc(), diag::err_attribute_regparm_invalid_number) 2559 << Context.Target.getRegParmMax() << NumParamsExpr->getSourceRange(); 2560 attr.setInvalid(); 2561 return true; 2562 } 2563 2564 return false; 2565} 2566 2567static void HandleLaunchBoundsAttr(Decl *d, const AttributeList &Attr, Sema &S){ 2568 if (S.LangOpts.CUDA) { 2569 // check the attribute arguments. 2570 if (Attr.getNumArgs() != 1 && Attr.getNumArgs() != 2) { 2571 // FIXME: 0 is not okay. 2572 S.Diag(Attr.getLoc(), diag::err_attribute_too_many_arguments) << 2; 2573 return; 2574 } 2575 2576 if (!isFunctionOrMethod(d)) { 2577 S.Diag(Attr.getLoc(), diag::warn_attribute_wrong_decl_type) 2578 << Attr.getName() << ExpectedFunctionOrMethod; 2579 return; 2580 } 2581 2582 Expr *MaxThreadsExpr = Attr.getArg(0); 2583 llvm::APSInt MaxThreads(32); 2584 if (MaxThreadsExpr->isTypeDependent() || 2585 MaxThreadsExpr->isValueDependent() || 2586 !MaxThreadsExpr->isIntegerConstantExpr(MaxThreads, S.Context)) { 2587 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2588 << "launch_bounds" << 1 << MaxThreadsExpr->getSourceRange(); 2589 return; 2590 } 2591 2592 llvm::APSInt MinBlocks(32); 2593 if (Attr.getNumArgs() > 1) { 2594 Expr *MinBlocksExpr = Attr.getArg(1); 2595 if (MinBlocksExpr->isTypeDependent() || 2596 MinBlocksExpr->isValueDependent() || 2597 !MinBlocksExpr->isIntegerConstantExpr(MinBlocks, S.Context)) { 2598 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_int) 2599 << "launch_bounds" << 2 << MinBlocksExpr->getSourceRange(); 2600 return; 2601 } 2602 } 2603 2604 d->addAttr(::new (S.Context) CUDALaunchBoundsAttr(Attr.getLoc(), S.Context, 2605 MaxThreads.getZExtValue(), 2606 MinBlocks.getZExtValue())); 2607 } else { 2608 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "launch_bounds"; 2609 } 2610} 2611 2612//===----------------------------------------------------------------------===// 2613// Checker-specific attribute handlers. 2614//===----------------------------------------------------------------------===// 2615 2616static bool isValidSubjectOfNSAttribute(Sema &S, QualType type) { 2617 return type->isObjCObjectPointerType() || S.Context.isObjCNSObjectType(type); 2618} 2619static bool isValidSubjectOfCFAttribute(Sema &S, QualType type) { 2620 return type->isPointerType() || isValidSubjectOfNSAttribute(S, type); 2621} 2622 2623static void HandleNSConsumedAttr(Decl *d, const AttributeList &attr, Sema &S) { 2624 ParmVarDecl *param = dyn_cast<ParmVarDecl>(d); 2625 if (!param) { 2626 S.Diag(d->getLocStart(), diag::warn_attribute_wrong_decl_type) 2627 << SourceRange(attr.getLoc()) << attr.getName() << ExpectedParameter; 2628 return; 2629 } 2630 2631 bool typeOK, cf; 2632 if (attr.getKind() == AttributeList::AT_ns_consumed) { 2633 typeOK = isValidSubjectOfNSAttribute(S, param->getType()); 2634 cf = false; 2635 } else { 2636 typeOK = isValidSubjectOfCFAttribute(S, param->getType()); 2637 cf = true; 2638 } 2639 2640 if (!typeOK) { 2641 S.Diag(d->getLocStart(), diag::warn_ns_attribute_wrong_parameter_type) 2642 << SourceRange(attr.getLoc()) << attr.getName() << cf; 2643 return; 2644 } 2645 2646 if (cf) 2647 param->addAttr(::new (S.Context) CFConsumedAttr(attr.getLoc(), S.Context)); 2648 else 2649 param->addAttr(::new (S.Context) NSConsumedAttr(attr.getLoc(), S.Context)); 2650} 2651 2652static void HandleNSConsumesSelfAttr(Decl *d, const AttributeList &attr, 2653 Sema &S) { 2654 if (!isa<ObjCMethodDecl>(d)) { 2655 S.Diag(d->getLocStart(), diag::warn_attribute_wrong_decl_type) 2656 << SourceRange(attr.getLoc()) << attr.getName() << ExpectedMethod; 2657 return; 2658 } 2659 2660 d->addAttr(::new (S.Context) NSConsumesSelfAttr(attr.getLoc(), S.Context)); 2661} 2662 2663static void HandleNSReturnsRetainedAttr(Decl *d, const AttributeList &attr, 2664 Sema &S) { 2665 2666 QualType returnType; 2667 2668 if (ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(d)) 2669 returnType = MD->getResultType(); 2670 else if (FunctionDecl *FD = dyn_cast<FunctionDecl>(d)) 2671 returnType = FD->getResultType(); 2672 else { 2673 S.Diag(d->getLocStart(), diag::warn_attribute_wrong_decl_type) 2674 << SourceRange(attr.getLoc()) << attr.getName() 2675 << ExpectedFunctionOrMethod; 2676 return; 2677 } 2678 2679 bool typeOK; 2680 bool cf; 2681 switch (attr.getKind()) { 2682 default: llvm_unreachable("invalid ownership attribute"); return; 2683 case AttributeList::AT_ns_returns_autoreleased: 2684 case AttributeList::AT_ns_returns_retained: 2685 case AttributeList::AT_ns_returns_not_retained: 2686 typeOK = isValidSubjectOfNSAttribute(S, returnType); 2687 cf = false; 2688 break; 2689 2690 case AttributeList::AT_cf_returns_retained: 2691 case AttributeList::AT_cf_returns_not_retained: 2692 typeOK = isValidSubjectOfCFAttribute(S, returnType); 2693 cf = true; 2694 break; 2695 } 2696 2697 if (!typeOK) { 2698 S.Diag(d->getLocStart(), diag::warn_ns_attribute_wrong_return_type) 2699 << SourceRange(attr.getLoc()) 2700 << attr.getName() << isa<ObjCMethodDecl>(d) << cf; 2701 return; 2702 } 2703 2704 switch (attr.getKind()) { 2705 default: 2706 assert(0 && "invalid ownership attribute"); 2707 return; 2708 case AttributeList::AT_ns_returns_autoreleased: 2709 d->addAttr(::new (S.Context) NSReturnsAutoreleasedAttr(attr.getLoc(), 2710 S.Context)); 2711 return; 2712 case AttributeList::AT_cf_returns_not_retained: 2713 d->addAttr(::new (S.Context) CFReturnsNotRetainedAttr(attr.getLoc(), 2714 S.Context)); 2715 return; 2716 case AttributeList::AT_ns_returns_not_retained: 2717 d->addAttr(::new (S.Context) NSReturnsNotRetainedAttr(attr.getLoc(), 2718 S.Context)); 2719 return; 2720 case AttributeList::AT_cf_returns_retained: 2721 d->addAttr(::new (S.Context) CFReturnsRetainedAttr(attr.getLoc(), 2722 S.Context)); 2723 return; 2724 case AttributeList::AT_ns_returns_retained: 2725 d->addAttr(::new (S.Context) NSReturnsRetainedAttr(attr.getLoc(), 2726 S.Context)); 2727 return; 2728 }; 2729} 2730 2731static bool isKnownDeclSpecAttr(const AttributeList &Attr) { 2732 return Attr.getKind() == AttributeList::AT_dllimport || 2733 Attr.getKind() == AttributeList::AT_dllexport || 2734 Attr.getKind() == AttributeList::AT_uuid; 2735} 2736 2737//===----------------------------------------------------------------------===// 2738// Microsoft specific attribute handlers. 2739//===----------------------------------------------------------------------===// 2740 2741static void HandleUuidAttr(Decl *d, const AttributeList &Attr, Sema &S) { 2742 if (S.LangOpts.Microsoft || S.LangOpts.Borland) { 2743 // check the attribute arguments. 2744 if (Attr.getNumArgs() != 1) { 2745 S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1; 2746 return; 2747 } 2748 Expr *Arg = Attr.getArg(0); 2749 StringLiteral *Str = dyn_cast<StringLiteral>(Arg); 2750 if (Str == 0 || Str->isWide()) { 2751 S.Diag(Attr.getLoc(), diag::err_attribute_argument_n_not_string) 2752 << "uuid" << 1; 2753 return; 2754 } 2755 2756 llvm::StringRef StrRef = Str->getString(); 2757 2758 bool IsCurly = StrRef.size() > 1 && StrRef.front() == '{' && 2759 StrRef.back() == '}'; 2760 2761 // Validate GUID length. 2762 if (IsCurly && StrRef.size() != 38) { 2763 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 2764 return; 2765 } 2766 if (!IsCurly && StrRef.size() != 36) { 2767 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 2768 return; 2769 } 2770 2771 // GUID format is "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX" or 2772 // "{XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX}" 2773 llvm::StringRef::iterator I = StrRef.begin(); 2774 if (IsCurly) // Skip the optional '{' 2775 ++I; 2776 2777 for (int i = 0; i < 36; ++i) { 2778 if (i == 8 || i == 13 || i == 18 || i == 23) { 2779 if (*I != '-') { 2780 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 2781 return; 2782 } 2783 } else if (!isxdigit(*I)) { 2784 S.Diag(Attr.getLoc(), diag::err_attribute_uuid_malformed_guid); 2785 return; 2786 } 2787 I++; 2788 } 2789 2790 d->addAttr(::new (S.Context) UuidAttr(Attr.getLoc(), S.Context, 2791 Str->getString())); 2792 } else 2793 S.Diag(Attr.getLoc(), diag::warn_attribute_ignored) << "uuid"; 2794} 2795 2796//===----------------------------------------------------------------------===// 2797// Top Level Sema Entry Points 2798//===----------------------------------------------------------------------===// 2799 2800static void ProcessNonInheritableDeclAttr(Scope *scope, Decl *D, 2801 const AttributeList &Attr, Sema &S) { 2802 switch (Attr.getKind()) { 2803 case AttributeList::AT_device: HandleDeviceAttr (D, Attr, S); break; 2804 case AttributeList::AT_host: HandleHostAttr (D, Attr, S); break; 2805 case AttributeList::AT_overloadable:HandleOverloadableAttr(D, Attr, S); break; 2806 default: 2807 break; 2808 } 2809} 2810 2811static void ProcessInheritableDeclAttr(Scope *scope, Decl *D, 2812 const AttributeList &Attr, Sema &S) { 2813 switch (Attr.getKind()) { 2814 case AttributeList::AT_IBAction: HandleIBAction(D, Attr, S); break; 2815 case AttributeList::AT_IBOutlet: HandleIBOutlet(D, Attr, S); break; 2816 case AttributeList::AT_IBOutletCollection: 2817 HandleIBOutletCollection(D, Attr, S); break; 2818 case AttributeList::AT_address_space: 2819 case AttributeList::AT_opencl_image_access: 2820 case AttributeList::AT_objc_gc: 2821 case AttributeList::AT_vector_size: 2822 case AttributeList::AT_neon_vector_type: 2823 case AttributeList::AT_neon_polyvector_type: 2824 // Ignore these, these are type attributes, handled by 2825 // ProcessTypeAttributes. 2826 break; 2827 case AttributeList::AT_device: 2828 case AttributeList::AT_host: 2829 case AttributeList::AT_overloadable: 2830 // Ignore, this is a non-inheritable attribute, handled 2831 // by ProcessNonInheritableDeclAttr. 2832 break; 2833 case AttributeList::AT_alias: HandleAliasAttr (D, Attr, S); break; 2834 case AttributeList::AT_aligned: HandleAlignedAttr (D, Attr, S); break; 2835 case AttributeList::AT_always_inline: 2836 HandleAlwaysInlineAttr (D, Attr, S); break; 2837 case AttributeList::AT_analyzer_noreturn: 2838 HandleAnalyzerNoReturnAttr (D, Attr, S); break; 2839 case AttributeList::AT_annotate: HandleAnnotateAttr (D, Attr, S); break; 2840 case AttributeList::AT_availability:HandleAvailabilityAttr(D, Attr, S); break; 2841 case AttributeList::AT_carries_dependency: 2842 HandleDependencyAttr (D, Attr, S); break; 2843 case AttributeList::AT_common: HandleCommonAttr (D, Attr, S); break; 2844 case AttributeList::AT_constant: HandleConstantAttr (D, Attr, S); break; 2845 case AttributeList::AT_constructor: HandleConstructorAttr (D, Attr, S); break; 2846 case AttributeList::AT_deprecated: HandleDeprecatedAttr (D, Attr, S); break; 2847 case AttributeList::AT_destructor: HandleDestructorAttr (D, Attr, S); break; 2848 case AttributeList::AT_ext_vector_type: 2849 HandleExtVectorTypeAttr(scope, D, Attr, S); 2850 break; 2851 case AttributeList::AT_format: HandleFormatAttr (D, Attr, S); break; 2852 case AttributeList::AT_format_arg: HandleFormatArgAttr (D, Attr, S); break; 2853 case AttributeList::AT_global: HandleGlobalAttr (D, Attr, S); break; 2854 case AttributeList::AT_gnu_inline: HandleGNUInlineAttr (D, Attr, S); break; 2855 case AttributeList::AT_launch_bounds: 2856 HandleLaunchBoundsAttr(D, Attr, S); 2857 break; 2858 case AttributeList::AT_mode: HandleModeAttr (D, Attr, S); break; 2859 case AttributeList::AT_malloc: HandleMallocAttr (D, Attr, S); break; 2860 case AttributeList::AT_may_alias: HandleMayAliasAttr (D, Attr, S); break; 2861 case AttributeList::AT_nocommon: HandleNoCommonAttr (D, Attr, S); break; 2862 case AttributeList::AT_nonnull: HandleNonNullAttr (D, Attr, S); break; 2863 case AttributeList::AT_ownership_returns: 2864 case AttributeList::AT_ownership_takes: 2865 case AttributeList::AT_ownership_holds: 2866 HandleOwnershipAttr (D, Attr, S); break; 2867 case AttributeList::AT_naked: HandleNakedAttr (D, Attr, S); break; 2868 case AttributeList::AT_noreturn: HandleNoReturnAttr (D, Attr, S); break; 2869 case AttributeList::AT_nothrow: HandleNothrowAttr (D, Attr, S); break; 2870 case AttributeList::AT_shared: HandleSharedAttr (D, Attr, S); break; 2871 case AttributeList::AT_vecreturn: HandleVecReturnAttr (D, Attr, S); break; 2872 2873 // Checker-specific. 2874 case AttributeList::AT_cf_consumed: 2875 case AttributeList::AT_ns_consumed: HandleNSConsumedAttr (D, Attr, S); break; 2876 case AttributeList::AT_ns_consumes_self: 2877 HandleNSConsumesSelfAttr(D, Attr, S); break; 2878 2879 case AttributeList::AT_ns_returns_autoreleased: 2880 case AttributeList::AT_ns_returns_not_retained: 2881 case AttributeList::AT_cf_returns_not_retained: 2882 case AttributeList::AT_ns_returns_retained: 2883 case AttributeList::AT_cf_returns_retained: 2884 HandleNSReturnsRetainedAttr(D, Attr, S); break; 2885 2886 case AttributeList::AT_reqd_wg_size: 2887 HandleReqdWorkGroupSize(D, Attr, S); break; 2888 2889 case AttributeList::AT_init_priority: 2890 HandleInitPriorityAttr(D, Attr, S); break; 2891 2892 case AttributeList::AT_packed: HandlePackedAttr (D, Attr, S); break; 2893 case AttributeList::AT_section: HandleSectionAttr (D, Attr, S); break; 2894 case AttributeList::AT_unavailable: HandleUnavailableAttr (D, Attr, S); break; 2895 case AttributeList::AT_unused: HandleUnusedAttr (D, Attr, S); break; 2896 case AttributeList::AT_used: HandleUsedAttr (D, Attr, S); break; 2897 case AttributeList::AT_visibility: HandleVisibilityAttr (D, Attr, S); break; 2898 case AttributeList::AT_warn_unused_result: HandleWarnUnusedResult(D,Attr,S); 2899 break; 2900 case AttributeList::AT_weak: HandleWeakAttr (D, Attr, S); break; 2901 case AttributeList::AT_weakref: HandleWeakRefAttr (D, Attr, S); break; 2902 case AttributeList::AT_weak_import: HandleWeakImportAttr (D, Attr, S); break; 2903 case AttributeList::AT_transparent_union: 2904 HandleTransparentUnionAttr(D, Attr, S); 2905 break; 2906 case AttributeList::AT_objc_exception: 2907 HandleObjCExceptionAttr(D, Attr, S); 2908 break; 2909 case AttributeList::AT_objc_method_family: 2910 HandleObjCMethodFamilyAttr(D, Attr, S); 2911 break; 2912 case AttributeList::AT_nsobject: HandleObjCNSObject (D, Attr, S); break; 2913 case AttributeList::AT_blocks: HandleBlocksAttr (D, Attr, S); break; 2914 case AttributeList::AT_sentinel: HandleSentinelAttr (D, Attr, S); break; 2915 case AttributeList::AT_const: HandleConstAttr (D, Attr, S); break; 2916 case AttributeList::AT_pure: HandlePureAttr (D, Attr, S); break; 2917 case AttributeList::AT_cleanup: HandleCleanupAttr (D, Attr, S); break; 2918 case AttributeList::AT_nodebug: HandleNoDebugAttr (D, Attr, S); break; 2919 case AttributeList::AT_noinline: HandleNoInlineAttr (D, Attr, S); break; 2920 case AttributeList::AT_regparm: HandleRegparmAttr (D, Attr, S); break; 2921 case AttributeList::IgnoredAttribute: 2922 // Just ignore 2923 break; 2924 case AttributeList::AT_no_instrument_function: // Interacts with -pg. 2925 HandleNoInstrumentFunctionAttr(D, Attr, S); 2926 break; 2927 case AttributeList::AT_stdcall: 2928 case AttributeList::AT_cdecl: 2929 case AttributeList::AT_fastcall: 2930 case AttributeList::AT_thiscall: 2931 case AttributeList::AT_pascal: 2932 case AttributeList::AT_pcs: 2933 HandleCallConvAttr(D, Attr, S); 2934 break; 2935 case AttributeList::AT_opencl_kernel_function: 2936 HandleOpenCLKernelAttr(D, Attr, S); 2937 break; 2938 case AttributeList::AT_uuid: 2939 HandleUuidAttr(D, Attr, S); 2940 break; 2941 default: 2942 // Ask target about the attribute. 2943 const TargetAttributesSema &TargetAttrs = S.getTargetAttributesSema(); 2944 if (!TargetAttrs.ProcessDeclAttribute(scope, D, Attr, S)) 2945 S.Diag(Attr.getLoc(), diag::warn_unknown_attribute_ignored) 2946 << Attr.getName(); 2947 break; 2948 } 2949} 2950 2951/// ProcessDeclAttribute - Apply the specific attribute to the specified decl if 2952/// the attribute applies to decls. If the attribute is a type attribute, just 2953/// silently ignore it if a GNU attribute. FIXME: Applying a C++0x attribute to 2954/// the wrong thing is illegal (C++0x [dcl.attr.grammar]/4). 2955static void ProcessDeclAttribute(Scope *scope, Decl *D, 2956 const AttributeList &Attr, Sema &S, 2957 bool NonInheritable, bool Inheritable) { 2958 if (Attr.isInvalid()) 2959 return; 2960 2961 if (Attr.isDeclspecAttribute() && !isKnownDeclSpecAttr(Attr)) 2962 // FIXME: Try to deal with other __declspec attributes! 2963 return; 2964 2965 if (NonInheritable) 2966 ProcessNonInheritableDeclAttr(scope, D, Attr, S); 2967 2968 if (Inheritable) 2969 ProcessInheritableDeclAttr(scope, D, Attr, S); 2970} 2971 2972/// ProcessDeclAttributeList - Apply all the decl attributes in the specified 2973/// attribute list to the specified decl, ignoring any type attributes. 2974void Sema::ProcessDeclAttributeList(Scope *S, Decl *D, 2975 const AttributeList *AttrList, 2976 bool NonInheritable, bool Inheritable) { 2977 for (const AttributeList* l = AttrList; l; l = l->getNext()) { 2978 ProcessDeclAttribute(S, D, *l, *this, NonInheritable, Inheritable); 2979 } 2980 2981 // GCC accepts 2982 // static int a9 __attribute__((weakref)); 2983 // but that looks really pointless. We reject it. 2984 if (Inheritable && D->hasAttr<WeakRefAttr>() && !D->hasAttr<AliasAttr>()) { 2985 Diag(AttrList->getLoc(), diag::err_attribute_weakref_without_alias) << 2986 dyn_cast<NamedDecl>(D)->getNameAsString(); 2987 return; 2988 } 2989} 2990 2991/// DeclClonePragmaWeak - clone existing decl (maybe definition), 2992/// #pragma weak needs a non-definition decl and source may not have one 2993NamedDecl * Sema::DeclClonePragmaWeak(NamedDecl *ND, IdentifierInfo *II) { 2994 assert(isa<FunctionDecl>(ND) || isa<VarDecl>(ND)); 2995 NamedDecl *NewD = 0; 2996 if (FunctionDecl *FD = dyn_cast<FunctionDecl>(ND)) { 2997 NewD = FunctionDecl::Create(FD->getASTContext(), FD->getDeclContext(), 2998 FD->getInnerLocStart(), 2999 FD->getLocation(), DeclarationName(II), 3000 FD->getType(), FD->getTypeSourceInfo()); 3001 if (FD->getQualifier()) { 3002 FunctionDecl *NewFD = cast<FunctionDecl>(NewD); 3003 NewFD->setQualifierInfo(FD->getQualifierLoc()); 3004 } 3005 } else if (VarDecl *VD = dyn_cast<VarDecl>(ND)) { 3006 NewD = VarDecl::Create(VD->getASTContext(), VD->getDeclContext(), 3007 VD->getInnerLocStart(), VD->getLocation(), II, 3008 VD->getType(), VD->getTypeSourceInfo(), 3009 VD->getStorageClass(), 3010 VD->getStorageClassAsWritten()); 3011 if (VD->getQualifier()) { 3012 VarDecl *NewVD = cast<VarDecl>(NewD); 3013 NewVD->setQualifierInfo(VD->getQualifierLoc()); 3014 } 3015 } 3016 return NewD; 3017} 3018 3019/// DeclApplyPragmaWeak - A declaration (maybe definition) needs #pragma weak 3020/// applied to it, possibly with an alias. 3021void Sema::DeclApplyPragmaWeak(Scope *S, NamedDecl *ND, WeakInfo &W) { 3022 if (W.getUsed()) return; // only do this once 3023 W.setUsed(true); 3024 if (W.getAlias()) { // clone decl, impersonate __attribute(weak,alias(...)) 3025 IdentifierInfo *NDId = ND->getIdentifier(); 3026 NamedDecl *NewD = DeclClonePragmaWeak(ND, W.getAlias()); 3027 NewD->addAttr(::new (Context) AliasAttr(W.getLocation(), Context, 3028 NDId->getName())); 3029 NewD->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 3030 WeakTopLevelDecl.push_back(NewD); 3031 // FIXME: "hideous" code from Sema::LazilyCreateBuiltin 3032 // to insert Decl at TU scope, sorry. 3033 DeclContext *SavedContext = CurContext; 3034 CurContext = Context.getTranslationUnitDecl(); 3035 PushOnScopeChains(NewD, S); 3036 CurContext = SavedContext; 3037 } else { // just add weak to existing 3038 ND->addAttr(::new (Context) WeakAttr(W.getLocation(), Context)); 3039 } 3040} 3041 3042/// ProcessDeclAttributes - Given a declarator (PD) with attributes indicated in 3043/// it, apply them to D. This is a bit tricky because PD can have attributes 3044/// specified in many different places, and we need to find and apply them all. 3045void Sema::ProcessDeclAttributes(Scope *S, Decl *D, const Declarator &PD, 3046 bool NonInheritable, bool Inheritable) { 3047 // It's valid to "forward-declare" #pragma weak, in which case we 3048 // have to do this. 3049 if (Inheritable && !WeakUndeclaredIdentifiers.empty()) { 3050 if (NamedDecl *ND = dyn_cast<NamedDecl>(D)) { 3051 if (IdentifierInfo *Id = ND->getIdentifier()) { 3052 llvm::DenseMap<IdentifierInfo*,WeakInfo>::iterator I 3053 = WeakUndeclaredIdentifiers.find(Id); 3054 if (I != WeakUndeclaredIdentifiers.end() && ND->hasLinkage()) { 3055 WeakInfo W = I->second; 3056 DeclApplyPragmaWeak(S, ND, W); 3057 WeakUndeclaredIdentifiers[Id] = W; 3058 } 3059 } 3060 } 3061 } 3062 3063 // Apply decl attributes from the DeclSpec if present. 3064 if (const AttributeList *Attrs = PD.getDeclSpec().getAttributes().getList()) 3065 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 3066 3067 // Walk the declarator structure, applying decl attributes that were in a type 3068 // position to the decl itself. This handles cases like: 3069 // int *__attr__(x)** D; 3070 // when X is a decl attribute. 3071 for (unsigned i = 0, e = PD.getNumTypeObjects(); i != e; ++i) 3072 if (const AttributeList *Attrs = PD.getTypeObject(i).getAttrs()) 3073 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 3074 3075 // Finally, apply any attributes on the decl itself. 3076 if (const AttributeList *Attrs = PD.getAttributes()) 3077 ProcessDeclAttributeList(S, D, Attrs, NonInheritable, Inheritable); 3078} 3079 3080// This duplicates a vector push_back but hides the need to know the 3081// size of the type. 3082void Sema::DelayedDiagnostics::add(const DelayedDiagnostic &diag) { 3083 assert(StackSize <= StackCapacity); 3084 3085 // Grow the stack if necessary. 3086 if (StackSize == StackCapacity) { 3087 unsigned newCapacity = 2 * StackCapacity + 2; 3088 char *newBuffer = new char[newCapacity * sizeof(DelayedDiagnostic)]; 3089 const char *oldBuffer = (const char*) Stack; 3090 3091 if (StackCapacity) 3092 memcpy(newBuffer, oldBuffer, StackCapacity * sizeof(DelayedDiagnostic)); 3093 3094 delete[] oldBuffer; 3095 Stack = reinterpret_cast<sema::DelayedDiagnostic*>(newBuffer); 3096 StackCapacity = newCapacity; 3097 } 3098 3099 assert(StackSize < StackCapacity); 3100 new (&Stack[StackSize++]) DelayedDiagnostic(diag); 3101} 3102 3103void Sema::DelayedDiagnostics::popParsingDecl(Sema &S, ParsingDeclState state, 3104 Decl *decl) { 3105 DelayedDiagnostics &DD = S.DelayedDiagnostics; 3106 3107 // Check the invariants. 3108 assert(DD.StackSize >= state.SavedStackSize); 3109 assert(state.SavedStackSize >= DD.ActiveStackBase); 3110 assert(DD.ParsingDepth > 0); 3111 3112 // Drop the parsing depth. 3113 DD.ParsingDepth--; 3114 3115 // If there are no active diagnostics, we're done. 3116 if (DD.StackSize == DD.ActiveStackBase) 3117 return; 3118 3119 // We only want to actually emit delayed diagnostics when we 3120 // successfully parsed a decl. 3121 if (decl) { 3122 // We emit all the active diagnostics, not just those starting 3123 // from the saved state. The idea is this: we get one push for a 3124 // decl spec and another for each declarator; in a decl group like: 3125 // deprecated_typedef foo, *bar, baz(); 3126 // only the declarator pops will be passed decls. This is correct; 3127 // we really do need to consider delayed diagnostics from the decl spec 3128 // for each of the different declarations. 3129 for (unsigned i = DD.ActiveStackBase, e = DD.StackSize; i != e; ++i) { 3130 DelayedDiagnostic &diag = DD.Stack[i]; 3131 if (diag.Triggered) 3132 continue; 3133 3134 switch (diag.Kind) { 3135 case DelayedDiagnostic::Deprecation: 3136 S.HandleDelayedDeprecationCheck(diag, decl); 3137 break; 3138 3139 case DelayedDiagnostic::Access: 3140 S.HandleDelayedAccessCheck(diag, decl); 3141 break; 3142 } 3143 } 3144 } 3145 3146 // Destroy all the delayed diagnostics we're about to pop off. 3147 for (unsigned i = state.SavedStackSize, e = DD.StackSize; i != e; ++i) 3148 DD.Stack[i].Destroy(); 3149 3150 DD.StackSize = state.SavedStackSize; 3151} 3152 3153static bool isDeclDeprecated(Decl *D) { 3154 do { 3155 if (D->isDeprecated()) 3156 return true; 3157 } while ((D = cast_or_null<Decl>(D->getDeclContext()))); 3158 return false; 3159} 3160 3161void Sema::HandleDelayedDeprecationCheck(DelayedDiagnostic &DD, 3162 Decl *Ctx) { 3163 if (isDeclDeprecated(Ctx)) 3164 return; 3165 3166 DD.Triggered = true; 3167 if (!DD.getDeprecationMessage().empty()) 3168 Diag(DD.Loc, diag::warn_deprecated_message) 3169 << DD.getDeprecationDecl()->getDeclName() 3170 << DD.getDeprecationMessage(); 3171 else 3172 Diag(DD.Loc, diag::warn_deprecated) 3173 << DD.getDeprecationDecl()->getDeclName(); 3174} 3175 3176void Sema::EmitDeprecationWarning(NamedDecl *D, llvm::StringRef Message, 3177 SourceLocation Loc, 3178 bool UnknownObjCClass) { 3179 // Delay if we're currently parsing a declaration. 3180 if (DelayedDiagnostics.shouldDelayDiagnostics()) { 3181 DelayedDiagnostics.add(DelayedDiagnostic::makeDeprecation(Loc, D, Message)); 3182 return; 3183 } 3184 3185 // Otherwise, don't warn if our current context is deprecated. 3186 if (isDeclDeprecated(cast<Decl>(CurContext))) 3187 return; 3188 if (!Message.empty()) 3189 Diag(Loc, diag::warn_deprecated_message) << D->getDeclName() 3190 << Message; 3191 else { 3192 if (!UnknownObjCClass) 3193 Diag(Loc, diag::warn_deprecated) << D->getDeclName(); 3194 else 3195 Diag(Loc, diag::warn_deprecated_fwdclass_message) << D->getDeclName(); 3196 } 3197} 3198