CallEvent.cpp revision 7c99aa385178c630e29f671299cdd9c104f1c885
1//===- Calls.cpp - Wrapper for all function and method calls ------*- C++ -*--// 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/// \file This file defines CallEvent and its subclasses, which represent path- 11/// sensitive instances of different kinds of function and method calls 12/// (C, C++, and Objective-C). 13// 14//===----------------------------------------------------------------------===// 15 16#include "clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h" 17#include "clang/Analysis/ProgramPoint.h" 18#include "clang/AST/ParentMap.h" 19#include "llvm/ADT/SmallSet.h" 20#include "llvm/ADT/StringExtras.h" 21 22using namespace clang; 23using namespace ento; 24 25QualType CallEvent::getResultType() const { 26 QualType ResultTy = getDeclaredResultType(); 27 28 if (ResultTy.isNull()) 29 ResultTy = getOriginExpr()->getType(); 30 31 return ResultTy; 32} 33 34static bool isCallbackArg(SVal V, QualType T) { 35 // If the parameter is 0, it's harmless. 36 if (V.isZeroConstant()) 37 return false; 38 39 // If a parameter is a block or a callback, assume it can modify pointer. 40 if (T->isBlockPointerType() || 41 T->isFunctionPointerType() || 42 T->isObjCSelType()) 43 return true; 44 45 // Check if a callback is passed inside a struct (for both, struct passed by 46 // reference and by value). Dig just one level into the struct for now. 47 48 if (isa<PointerType>(T) || isa<ReferenceType>(T)) 49 T = T->getPointeeType(); 50 51 if (const RecordType *RT = T->getAsStructureType()) { 52 const RecordDecl *RD = RT->getDecl(); 53 for (RecordDecl::field_iterator I = RD->field_begin(), E = RD->field_end(); 54 I != E; ++I) { 55 QualType FieldT = I->getType(); 56 if (FieldT->isBlockPointerType() || FieldT->isFunctionPointerType()) 57 return true; 58 } 59 } 60 61 return false; 62} 63 64bool CallEvent::hasNonZeroCallbackArg() const { 65 unsigned NumOfArgs = getNumArgs(); 66 67 // If calling using a function pointer, assume the function does not 68 // have a callback. TODO: We could check the types of the arguments here. 69 if (!getDecl()) 70 return false; 71 72 unsigned Idx = 0; 73 for (CallEvent::param_type_iterator I = param_type_begin(), 74 E = param_type_end(); 75 I != E && Idx < NumOfArgs; ++I, ++Idx) { 76 if (NumOfArgs <= Idx) 77 break; 78 79 if (isCallbackArg(getArgSVal(Idx), *I)) 80 return true; 81 } 82 83 return false; 84} 85 86/// \brief Returns true if a type is a pointer-to-const or reference-to-const 87/// with no further indirection. 88static bool isPointerToConst(QualType Ty) { 89 QualType PointeeTy = Ty->getPointeeType(); 90 if (PointeeTy == QualType()) 91 return false; 92 if (!PointeeTy.isConstQualified()) 93 return false; 94 if (PointeeTy->isAnyPointerType()) 95 return false; 96 return true; 97} 98 99// Try to retrieve the function declaration and find the function parameter 100// types which are pointers/references to a non-pointer const. 101// We will not invalidate the corresponding argument regions. 102static void findPtrToConstParams(llvm::SmallSet<unsigned, 1> &PreserveArgs, 103 const CallEvent &Call) { 104 unsigned Idx = 0; 105 for (CallEvent::param_type_iterator I = Call.param_type_begin(), 106 E = Call.param_type_end(); 107 I != E; ++I, ++Idx) { 108 if (isPointerToConst(*I)) 109 PreserveArgs.insert(Idx); 110 } 111} 112 113ProgramStateRef CallEvent::invalidateRegions(unsigned BlockCount, 114 ProgramStateRef Orig) const { 115 ProgramStateRef Result = (Orig ? Orig : getState()); 116 117 SmallVector<const MemRegion *, 8> RegionsToInvalidate; 118 getExtraInvalidatedRegions(RegionsToInvalidate); 119 120 // Indexes of arguments whose values will be preserved by the call. 121 llvm::SmallSet<unsigned, 1> PreserveArgs; 122 if (!argumentsMayEscape()) 123 findPtrToConstParams(PreserveArgs, *this); 124 125 for (unsigned Idx = 0, Count = getNumArgs(); Idx != Count; ++Idx) { 126 if (PreserveArgs.count(Idx)) 127 continue; 128 129 SVal V = getArgSVal(Idx); 130 131 // If we are passing a location wrapped as an integer, unwrap it and 132 // invalidate the values referred by the location. 133 if (nonloc::LocAsInteger *Wrapped = dyn_cast<nonloc::LocAsInteger>(&V)) 134 V = Wrapped->getLoc(); 135 else if (!isa<Loc>(V)) 136 continue; 137 138 if (const MemRegion *R = V.getAsRegion()) { 139 // Invalidate the value of the variable passed by reference. 140 141 // Are we dealing with an ElementRegion? If the element type is 142 // a basic integer type (e.g., char, int) and the underlying region 143 // is a variable region then strip off the ElementRegion. 144 // FIXME: We really need to think about this for the general case 145 // as sometimes we are reasoning about arrays and other times 146 // about (char*), etc., is just a form of passing raw bytes. 147 // e.g., void *p = alloca(); foo((char*)p); 148 if (const ElementRegion *ER = dyn_cast<ElementRegion>(R)) { 149 // Checking for 'integral type' is probably too promiscuous, but 150 // we'll leave it in for now until we have a systematic way of 151 // handling all of these cases. Eventually we need to come up 152 // with an interface to StoreManager so that this logic can be 153 // appropriately delegated to the respective StoreManagers while 154 // still allowing us to do checker-specific logic (e.g., 155 // invalidating reference counts), probably via callbacks. 156 if (ER->getElementType()->isIntegralOrEnumerationType()) { 157 const MemRegion *superReg = ER->getSuperRegion(); 158 if (isa<VarRegion>(superReg) || isa<FieldRegion>(superReg) || 159 isa<ObjCIvarRegion>(superReg)) 160 R = cast<TypedRegion>(superReg); 161 } 162 // FIXME: What about layers of ElementRegions? 163 } 164 165 // Mark this region for invalidation. We batch invalidate regions 166 // below for efficiency. 167 RegionsToInvalidate.push_back(R); 168 } 169 } 170 171 // Invalidate designated regions using the batch invalidation API. 172 // NOTE: Even if RegionsToInvalidate is empty, we may still invalidate 173 // global variables. 174 return Result->invalidateRegions(RegionsToInvalidate, getOriginExpr(), 175 BlockCount, getLocationContext(), 176 /*Symbols=*/0, this); 177} 178 179ProgramPoint CallEvent::getProgramPoint(bool IsPreVisit, 180 const ProgramPointTag *Tag) const { 181 if (const Expr *E = getOriginExpr()) { 182 if (IsPreVisit) 183 return PreStmt(E, getLocationContext(), Tag); 184 return PostStmt(E, getLocationContext(), Tag); 185 } 186 187 const Decl *D = getDecl(); 188 assert(D && "Cannot get a program point without a statement or decl"); 189 190 SourceLocation Loc = getSourceRange().getBegin(); 191 if (IsPreVisit) 192 return PreImplicitCall(D, Loc, getLocationContext(), Tag); 193 return PostImplicitCall(D, Loc, getLocationContext(), Tag); 194} 195 196SVal CallEvent::getArgSVal(unsigned Index) const { 197 const Expr *ArgE = getArgExpr(Index); 198 if (!ArgE) 199 return UnknownVal(); 200 return getSVal(ArgE); 201} 202 203SourceRange CallEvent::getArgSourceRange(unsigned Index) const { 204 const Expr *ArgE = getArgExpr(Index); 205 if (!ArgE) 206 return SourceRange(); 207 return ArgE->getSourceRange(); 208} 209 210void CallEvent::dump(raw_ostream &Out) const { 211 ASTContext &Ctx = getState()->getStateManager().getContext(); 212 if (const Expr *E = getOriginExpr()) { 213 E->printPretty(Out, Ctx, 0, Ctx.getPrintingPolicy()); 214 Out << "\n"; 215 return; 216 } 217 218 if (const Decl *D = getDecl()) { 219 Out << "Call to "; 220 D->print(Out, Ctx.getPrintingPolicy()); 221 return; 222 } 223 224 // FIXME: a string representation of the kind would be nice. 225 Out << "Unknown call (type " << getKind() << ")"; 226} 227 228 229bool CallEvent::mayBeInlined(const Stmt *S) { 230 // FIXME: Kill this. 231 return isa<CallExpr>(S) || isa<ObjCMessageExpr>(S) 232 || isa<CXXConstructExpr>(S); 233} 234 235 236CallEvent::param_iterator 237AnyFunctionCall::param_begin(bool UseDefinitionParams) const { 238 const Decl *D = UseDefinitionParams ? getRuntimeDefinition() 239 : getDecl(); 240 if (!D) 241 return 0; 242 243 return cast<FunctionDecl>(D)->param_begin(); 244} 245 246CallEvent::param_iterator 247AnyFunctionCall::param_end(bool UseDefinitionParams) const { 248 const Decl *D = UseDefinitionParams ? getRuntimeDefinition() 249 : getDecl(); 250 if (!D) 251 return 0; 252 253 return cast<FunctionDecl>(D)->param_end(); 254} 255 256QualType AnyFunctionCall::getDeclaredResultType() const { 257 const FunctionDecl *D = getDecl(); 258 if (!D) 259 return QualType(); 260 261 return D->getResultType(); 262} 263 264bool AnyFunctionCall::argumentsMayEscape() const { 265 if (hasNonZeroCallbackArg()) 266 return true; 267 268 const FunctionDecl *D = getDecl(); 269 if (!D) 270 return true; 271 272 const IdentifierInfo *II = D->getIdentifier(); 273 if (!II) 274 return true; 275 276 // This set of "escaping" APIs is 277 278 // - 'int pthread_setspecific(ptheread_key k, const void *)' stores a 279 // value into thread local storage. The value can later be retrieved with 280 // 'void *ptheread_getspecific(pthread_key)'. So even thought the 281 // parameter is 'const void *', the region escapes through the call. 282 if (II->isStr("pthread_setspecific")) 283 return true; 284 285 // - xpc_connection_set_context stores a value which can be retrieved later 286 // with xpc_connection_get_context. 287 if (II->isStr("xpc_connection_set_context")) 288 return true; 289 290 // - funopen - sets a buffer for future IO calls. 291 if (II->isStr("funopen")) 292 return true; 293 294 StringRef FName = II->getName(); 295 296 // - CoreFoundation functions that end with "NoCopy" can free a passed-in 297 // buffer even if it is const. 298 if (FName.endswith("NoCopy")) 299 return true; 300 301 // - NSXXInsertXX, for example NSMapInsertIfAbsent, since they can 302 // be deallocated by NSMapRemove. 303 if (FName.startswith("NS") && (FName.find("Insert") != StringRef::npos)) 304 return true; 305 306 // - Many CF containers allow objects to escape through custom 307 // allocators/deallocators upon container construction. (PR12101) 308 if (FName.startswith("CF") || FName.startswith("CG")) { 309 return StrInStrNoCase(FName, "InsertValue") != StringRef::npos || 310 StrInStrNoCase(FName, "AddValue") != StringRef::npos || 311 StrInStrNoCase(FName, "SetValue") != StringRef::npos || 312 StrInStrNoCase(FName, "WithData") != StringRef::npos || 313 StrInStrNoCase(FName, "AppendValue") != StringRef::npos || 314 StrInStrNoCase(FName, "SetAttribute") != StringRef::npos; 315 } 316 317 return false; 318} 319 320 321const FunctionDecl *SimpleCall::getDecl() const { 322 const FunctionDecl *D = getOriginExpr()->getDirectCallee(); 323 if (D) 324 return D; 325 326 return getSVal(getOriginExpr()->getCallee()).getAsFunctionDecl(); 327} 328 329 330void CXXInstanceCall::getExtraInvalidatedRegions(RegionList &Regions) const { 331 if (const MemRegion *R = getCXXThisVal().getAsRegion()) 332 Regions.push_back(R); 333} 334 335static const CXXMethodDecl *devirtualize(const CXXMethodDecl *MD, SVal ThisVal){ 336 const MemRegion *R = ThisVal.getAsRegion(); 337 if (!R) 338 return 0; 339 340 const TypedValueRegion *TR = dyn_cast<TypedValueRegion>(R->StripCasts()); 341 if (!TR) 342 return 0; 343 344 const CXXRecordDecl *RD = TR->getValueType()->getAsCXXRecordDecl(); 345 if (!RD) 346 return 0; 347 348 const CXXMethodDecl *Result = MD->getCorrespondingMethodInClass(RD); 349 const FunctionDecl *Definition; 350 if (!Result->hasBody(Definition)) 351 return 0; 352 353 return cast<CXXMethodDecl>(Definition); 354} 355 356 357const Decl *CXXInstanceCall::getRuntimeDefinition() const { 358 const Decl *D = SimpleCall::getRuntimeDefinition(); 359 if (!D) 360 return 0; 361 362 const CXXMethodDecl *MD = cast<CXXMethodDecl>(D); 363 if (!MD->isVirtual()) 364 return MD; 365 366 // If the method is virtual, see if we can find the actual implementation 367 // based on context-sensitivity. 368 if (const CXXMethodDecl *Devirtualized = devirtualize(MD, getCXXThisVal())) 369 return Devirtualized; 370 371 return 0; 372} 373 374 375SVal CXXMemberCall::getCXXThisVal() const { 376 const Expr *Base = getOriginExpr()->getImplicitObjectArgument(); 377 378 // FIXME: Will eventually need to cope with member pointers. This is 379 // a limitation in getImplicitObjectArgument(). 380 if (!Base) 381 return UnknownVal(); 382 383 return getSVal(Base); 384} 385 386 387SVal CXXMemberOperatorCall::getCXXThisVal() const { 388 const Expr *Base = getOriginExpr()->getArg(0); 389 return getSVal(Base); 390} 391 392 393const BlockDataRegion *BlockCall::getBlockRegion() const { 394 const Expr *Callee = getOriginExpr()->getCallee(); 395 const MemRegion *DataReg = getSVal(Callee).getAsRegion(); 396 397 return dyn_cast_or_null<BlockDataRegion>(DataReg); 398} 399 400CallEvent::param_iterator 401BlockCall::param_begin(bool UseDefinitionParams) const { 402 // Blocks don't have distinct declarations and definitions. 403 (void)UseDefinitionParams; 404 405 const BlockDecl *D = getBlockDecl(); 406 if (!D) 407 return 0; 408 return D->param_begin(); 409} 410 411CallEvent::param_iterator 412BlockCall::param_end(bool UseDefinitionParams) const { 413 // Blocks don't have distinct declarations and definitions. 414 (void)UseDefinitionParams; 415 416 const BlockDecl *D = getBlockDecl(); 417 if (!D) 418 return 0; 419 return D->param_end(); 420} 421 422void BlockCall::getExtraInvalidatedRegions(RegionList &Regions) const { 423 // FIXME: This also needs to invalidate captured globals. 424 if (const MemRegion *R = getBlockRegion()) 425 Regions.push_back(R); 426} 427 428QualType BlockCall::getDeclaredResultType() const { 429 const BlockDataRegion *BR = getBlockRegion(); 430 if (!BR) 431 return QualType(); 432 QualType BlockTy = BR->getCodeRegion()->getLocationType(); 433 return cast<FunctionType>(BlockTy->getPointeeType())->getResultType(); 434} 435 436 437SVal CXXConstructorCall::getCXXThisVal() const { 438 if (Data) 439 return loc::MemRegionVal(static_cast<const MemRegion *>(Data)); 440 return UnknownVal(); 441} 442 443void CXXConstructorCall::getExtraInvalidatedRegions(RegionList &Regions) const { 444 if (Data) 445 Regions.push_back(static_cast<const MemRegion *>(Data)); 446} 447 448 449SVal CXXDestructorCall::getCXXThisVal() const { 450 if (Data) 451 return loc::MemRegionVal(static_cast<const MemRegion *>(Data)); 452 return UnknownVal(); 453} 454 455void CXXDestructorCall::getExtraInvalidatedRegions(RegionList &Regions) const { 456 if (Data) 457 Regions.push_back(static_cast<const MemRegion *>(Data)); 458} 459 460const Decl *CXXDestructorCall::getRuntimeDefinition() const { 461 const Decl *D = AnyFunctionCall::getRuntimeDefinition(); 462 if (!D) 463 return 0; 464 465 const CXXMethodDecl *MD = cast<CXXMethodDecl>(D); 466 if (!MD->isVirtual()) 467 return MD; 468 469 // If the method is virtual, see if we can find the actual implementation 470 // based on context-sensitivity. 471 if (const CXXMethodDecl *Devirtualized = devirtualize(MD, getCXXThisVal())) 472 return Devirtualized; 473 474 return 0; 475} 476 477 478CallEvent::param_iterator 479ObjCMethodCall::param_begin(bool UseDefinitionParams) const { 480 const Decl *D = UseDefinitionParams ? getRuntimeDefinition() 481 : getDecl(); 482 if (!D) 483 return 0; 484 485 return cast<ObjCMethodDecl>(D)->param_begin(); 486} 487 488CallEvent::param_iterator 489ObjCMethodCall::param_end(bool UseDefinitionParams) const { 490 const Decl *D = UseDefinitionParams ? getRuntimeDefinition() 491 : getDecl(); 492 if (!D) 493 return 0; 494 495 return cast<ObjCMethodDecl>(D)->param_end(); 496} 497 498void 499ObjCMethodCall::getExtraInvalidatedRegions(RegionList &Regions) const { 500 if (const MemRegion *R = getReceiverSVal().getAsRegion()) 501 Regions.push_back(R); 502} 503 504QualType ObjCMethodCall::getDeclaredResultType() const { 505 const ObjCMethodDecl *D = getDecl(); 506 if (!D) 507 return QualType(); 508 509 return D->getResultType(); 510} 511 512SVal ObjCMethodCall::getReceiverSVal() const { 513 // FIXME: Is this the best way to handle class receivers? 514 if (!isInstanceMessage()) 515 return UnknownVal(); 516 517 if (const Expr *Base = getOriginExpr()->getInstanceReceiver()) 518 return getSVal(Base); 519 520 // An instance message with no expression means we are sending to super. 521 // In this case the object reference is the same as 'self'. 522 const LocationContext *LCtx = getLocationContext(); 523 const ImplicitParamDecl *SelfDecl = LCtx->getSelfDecl(); 524 assert(SelfDecl && "No message receiver Expr, but not in an ObjC method"); 525 return getState()->getSVal(getState()->getRegion(SelfDecl, LCtx)); 526} 527 528SourceRange ObjCMethodCall::getSourceRange() const { 529 switch (getMessageKind()) { 530 case OCM_Message: 531 return getOriginExpr()->getSourceRange(); 532 case OCM_PropertyAccess: 533 case OCM_Subscript: 534 return getContainingPseudoObjectExpr()->getSourceRange(); 535 } 536 llvm_unreachable("unknown message kind"); 537} 538 539typedef llvm::PointerIntPair<const PseudoObjectExpr *, 2> ObjCMessageDataTy; 540 541const PseudoObjectExpr *ObjCMethodCall::getContainingPseudoObjectExpr() const { 542 assert(Data != 0 && "Lazy lookup not yet performed."); 543 assert(getMessageKind() != OCM_Message && "Explicit message send."); 544 return ObjCMessageDataTy::getFromOpaqueValue(Data).getPointer(); 545} 546 547ObjCMessageKind ObjCMethodCall::getMessageKind() const { 548 if (Data == 0) { 549 ParentMap &PM = getLocationContext()->getParentMap(); 550 const Stmt *S = PM.getParent(getOriginExpr()); 551 if (const PseudoObjectExpr *POE = dyn_cast_or_null<PseudoObjectExpr>(S)) { 552 const Expr *Syntactic = POE->getSyntacticForm(); 553 554 // This handles the funny case of assigning to the result of a getter. 555 // This can happen if the getter returns a non-const reference. 556 if (const BinaryOperator *BO = dyn_cast<BinaryOperator>(Syntactic)) 557 Syntactic = BO->getLHS(); 558 559 ObjCMessageKind K; 560 switch (Syntactic->getStmtClass()) { 561 case Stmt::ObjCPropertyRefExprClass: 562 K = OCM_PropertyAccess; 563 break; 564 case Stmt::ObjCSubscriptRefExprClass: 565 K = OCM_Subscript; 566 break; 567 default: 568 // FIXME: Can this ever happen? 569 K = OCM_Message; 570 break; 571 } 572 573 if (K != OCM_Message) { 574 const_cast<ObjCMethodCall *>(this)->Data 575 = ObjCMessageDataTy(POE, K).getOpaqueValue(); 576 assert(getMessageKind() == K); 577 return K; 578 } 579 } 580 581 const_cast<ObjCMethodCall *>(this)->Data 582 = ObjCMessageDataTy(0, 1).getOpaqueValue(); 583 assert(getMessageKind() == OCM_Message); 584 return OCM_Message; 585 } 586 587 ObjCMessageDataTy Info = ObjCMessageDataTy::getFromOpaqueValue(Data); 588 if (!Info.getPointer()) 589 return OCM_Message; 590 return static_cast<ObjCMessageKind>(Info.getInt()); 591} 592 593// TODO: This implementation is copied from SemaExprObjC.cpp, needs to be 594// factored into the ObjCInterfaceDecl. 595ObjCMethodDecl *ObjCMethodCall::LookupClassMethodDefinition(Selector Sel, 596 ObjCInterfaceDecl *ClassDecl) const { 597 ObjCMethodDecl *Method = 0; 598 // Lookup in class and all superclasses. 599 while (ClassDecl && !Method) { 600 if (ObjCImplementationDecl *ImpDecl = ClassDecl->getImplementation()) 601 Method = ImpDecl->getClassMethod(Sel); 602 603 // Look through local category implementations associated with the class. 604 if (!Method) 605 Method = ClassDecl->getCategoryClassMethod(Sel); 606 607 // Before we give up, check if the selector is an instance method. 608 // But only in the root. This matches gcc's behavior and what the 609 // runtime expects. 610 if (!Method && !ClassDecl->getSuperClass()) { 611 Method = ClassDecl->lookupInstanceMethod(Sel); 612 // Look through local category implementations associated 613 // with the root class. 614 //if (!Method) 615 // Method = LookupPrivateInstanceMethod(Sel, ClassDecl); 616 } 617 618 ClassDecl = ClassDecl->getSuperClass(); 619 } 620 return Method; 621} 622 623