From 110eaaceddcec790f7e6a5e3bf1261c9aa1e73ab Mon Sep 17 00:00:00 2001 From: dim Date: Mon, 2 May 2011 19:39:53 +0000 Subject: Vendor import of clang trunk r130700: http://llvm.org/svn/llvm-project/cfe/trunk@130700 --- lib/StaticAnalyzer/Core/ObjCMessage.cpp | 56 +++++++++++++++++++++++++++++++-- 1 file changed, 53 insertions(+), 3 deletions(-) (limited to 'lib/StaticAnalyzer/Core/ObjCMessage.cpp') diff --git a/lib/StaticAnalyzer/Core/ObjCMessage.cpp b/lib/StaticAnalyzer/Core/ObjCMessage.cpp index 2e370d6..c005819 100644 --- a/lib/StaticAnalyzer/Core/ObjCMessage.cpp +++ b/lib/StaticAnalyzer/Core/ObjCMessage.cpp @@ -37,6 +37,35 @@ Selector ObjCMessage::getSelector() const { return propE->getGetterSelector(); } +ObjCMethodFamily ObjCMessage::getMethodFamily() const { + assert(isValid() && "This ObjCMessage is uninitialized!"); + // Case 1. Explicit message send. + if (const ObjCMessageExpr *msgE = dyn_cast(MsgOrPropE)) + return msgE->getMethodFamily(); + + const ObjCPropertyRefExpr *propE = cast(MsgOrPropE); + + // Case 2. Reference to implicit property. + if (propE->isImplicitProperty()) { + if (isPropertySetter()) + return propE->getImplicitPropertySetter()->getMethodFamily(); + else + return propE->getImplicitPropertyGetter()->getMethodFamily(); + } + + // Case 3. Reference to explicit property. + const ObjCPropertyDecl *prop = propE->getExplicitProperty(); + if (isPropertySetter()) { + if (prop->getSetterMethodDecl()) + return prop->getSetterMethodDecl()->getMethodFamily(); + return prop->getSetterName().getMethodFamily(); + } else { + if (prop->getGetterMethodDecl()) + return prop->getGetterMethodDecl()->getMethodFamily(); + return prop->getGetterName().getMethodFamily(); + } +} + const ObjCMethodDecl *ObjCMessage::getMethodDecl() const { assert(isValid() && "This ObjCMessage is uninitialized!"); if (const ObjCMessageExpr *msgE = dyn_cast(MsgOrPropE)) @@ -80,13 +109,27 @@ const Expr *ObjCMessage::getArgExpr(unsigned i) const { } QualType CallOrObjCMessage::getResultType(ASTContext &ctx) const { + QualType resultTy; + bool isLVal = false; + if (CallE) { + isLVal = CallE->isLValue(); const Expr *Callee = CallE->getCallee(); if (const FunctionDecl *FD = State->getSVal(Callee).getAsFunctionDecl()) - return FD->getResultType(); - return CallE->getType(); + resultTy = FD->getResultType(); + else + resultTy = CallE->getType(); + } + else { + isLVal = isa(Msg.getOriginExpr()) && + Msg.getOriginExpr()->isLValue(); + resultTy = Msg.getResultType(ctx); } - return Msg.getResultType(ctx); + + if (isLVal) + resultTy = ctx.getPointerType(resultTy); + + return resultTy; } SVal CallOrObjCMessage::getArgSValAsScalarOrLoc(unsigned i) const { @@ -97,3 +140,10 @@ SVal CallOrObjCMessage::getArgSValAsScalarOrLoc(unsigned i) const { return Msg.getArgSVal(i, State); return UnknownVal(); } + +SVal CallOrObjCMessage::getCXXCallee() const { + assert(isCXXCall()); + const Expr *callee = + cast(CallE)->getImplicitObjectArgument(); + return State->getSVal(callee); +} -- cgit v1.1