aboutsummaryrefslogtreecommitdiff
path: root/lib/Analysis/CFG.cpp
diff options
context:
space:
mode:
authorJohn McCall <rjmccall@apple.com>2011-05-11 07:19:11 +0000
committerJohn McCall <rjmccall@apple.com>2011-05-11 07:19:11 +0000
commit1de85338543dd6228eb518185e385d94d377f4cb (patch)
tree401dd9ce59f59f69fe2de82492068c3917920f03 /lib/Analysis/CFG.cpp
parentbe57cf41fb55b48e3f889787960b3ac2eb5e4dbd (diff)
Teach CFG building how to deal with CXXMemberCallExprs and BoundMemberTy,
then teach -Wreturn-type to handle the same. Net effect: we now correctly handle noreturn attributes on member calls in the CFG. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@131178 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Analysis/CFG.cpp')
-rw-r--r--lib/Analysis/CFG.cpp27
1 files changed, 12 insertions, 15 deletions
diff --git a/lib/Analysis/CFG.cpp b/lib/Analysis/CFG.cpp
index a247a9d194..77c30dd987 100644
--- a/lib/Analysis/CFG.cpp
+++ b/lib/Analysis/CFG.cpp
@@ -320,7 +320,6 @@ private:
AddStmtChoice asc);
CFGBlock *VisitCXXTemporaryObjectExpr(CXXTemporaryObjectExpr *C,
AddStmtChoice asc);
- CFGBlock *VisitCXXMemberCallExpr(CXXMemberCallExpr *C, AddStmtChoice asc);
CFGBlock *VisitCallExpr(CallExpr *C, AddStmtChoice asc);
CFGBlock *VisitCaseStmt(CaseStmt *C);
CFGBlock *VisitChooseExpr(ChooseExpr *C, AddStmtChoice asc);
@@ -868,6 +867,7 @@ tryAgain:
case Stmt::CallExprClass:
case Stmt::CXXOperatorCallExprClass:
+ case Stmt::CXXMemberCallExprClass:
return VisitCallExpr(cast<CallExpr>(S), asc);
case Stmt::CaseStmtClass:
@@ -903,9 +903,6 @@ tryAgain:
case Stmt::CXXTemporaryObjectExprClass:
return VisitCXXTemporaryObjectExpr(cast<CXXTemporaryObjectExpr>(S), asc);
- case Stmt::CXXMemberCallExprClass:
- return VisitCXXMemberCallExpr(cast<CXXMemberCallExpr>(S), asc);
-
case Stmt::CXXThrowExprClass:
return VisitCXXThrowExpr(cast<CXXThrowExpr>(S));
@@ -1153,12 +1150,19 @@ static bool CanThrow(Expr *E, ASTContext &Ctx) {
}
CFGBlock *CFGBuilder::VisitCallExpr(CallExpr *C, AddStmtChoice asc) {
- // If this is a call to a no-return function, this stops the block here.
- bool NoReturn = false;
- if (getFunctionExtInfo(*C->getCallee()->getType()).getNoReturn()) {
- NoReturn = true;
+ // Compute the callee type.
+ QualType calleeType = C->getCallee()->getType();
+ if (calleeType == Context->BoundMemberTy) {
+ QualType boundType = Expr::findBoundMemberType(C->getCallee());
+
+ // We should only get a null bound type if processing a dependent
+ // CFG. Recover by assuming nothing.
+ if (!boundType.isNull()) calleeType = boundType;
}
+ // If this is a call to a no-return function, this stops the block here.
+ bool NoReturn = getFunctionExtInfo(*calleeType).getNoReturn();
+
bool AddEHEdge = false;
// Languages without exceptions are assumed to not throw.
@@ -2691,13 +2695,6 @@ CFGBlock *CFGBuilder::VisitCXXTemporaryObjectExpr(CXXTemporaryObjectExpr *C,
return VisitChildren(C);
}
-CFGBlock *CFGBuilder::VisitCXXMemberCallExpr(CXXMemberCallExpr *C,
- AddStmtChoice asc) {
- autoCreateBlock();
- appendStmt(Block, C);
- return VisitChildren(C);
-}
-
CFGBlock *CFGBuilder::VisitImplicitCastExpr(ImplicitCastExpr *E,
AddStmtChoice asc) {
if (asc.alwaysAdd(*this, E)) {