зеркало из https://github.com/microsoft/clang.git
Teach GRExprEngine to handle the initialization of the condition variable of a SwitchStmt.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@92102 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Родитель
6b501ebaf1
Коммит
fcfb503c28
|
@ -293,10 +293,10 @@ protected:
|
|||
void VisitGuardedExpr(Expr* Ex, Expr* L, Expr* R, ExplodedNode* Pred,
|
||||
ExplodedNodeSet& Dst);
|
||||
|
||||
/// VisitIfStmtCondInit - Transfer function for handling the initialization
|
||||
/// of a condition variable in an IfStmt.
|
||||
void VisitIfStmtCondInit(IfStmt *IS, ExplodedNode *Pred,
|
||||
ExplodedNodeSet& Dst);
|
||||
/// VisitCondInit - Transfer function for handling the initialization
|
||||
/// of a condition variable in an IfStmt, SwitchStmt, etc.
|
||||
void VisitCondInit(VarDecl *VD, Stmt *S, ExplodedNode *Pred,
|
||||
ExplodedNodeSet& Dst);
|
||||
|
||||
void VisitInitListExpr(InitListExpr* E, ExplodedNode* Pred,
|
||||
ExplodedNodeSet& Dst);
|
||||
|
|
|
@ -665,7 +665,7 @@ void GRExprEngine::Visit(Stmt* S, ExplodedNode* Pred, ExplodedNodeSet& Dst) {
|
|||
case Stmt::IfStmtClass:
|
||||
// This case isn't for branch processing, but for handling the
|
||||
// initialization of a condition variable.
|
||||
VisitIfStmtCondInit(cast<IfStmt>(S), Pred, Dst);
|
||||
VisitCondInit(cast<IfStmt>(S)->getConditionVariable(), S, Pred, Dst);
|
||||
break;
|
||||
|
||||
case Stmt::InitListExprClass:
|
||||
|
@ -733,6 +733,12 @@ void GRExprEngine::Visit(Stmt* S, ExplodedNode* Pred, ExplodedNodeSet& Dst) {
|
|||
case Stmt::StringLiteralClass:
|
||||
VisitLValue(cast<StringLiteral>(S), Pred, Dst);
|
||||
break;
|
||||
|
||||
case Stmt::SwitchStmtClass:
|
||||
// This case isn't for branch processing, but for handling the
|
||||
// initialization of a condition variable.
|
||||
VisitCondInit(cast<SwitchStmt>(S)->getConditionVariable(), S, Pred, Dst);
|
||||
break;
|
||||
|
||||
case Stmt::UnaryOperatorClass: {
|
||||
UnaryOperator *U = cast<UnaryOperator>(S);
|
||||
|
@ -2230,12 +2236,10 @@ void GRExprEngine::VisitDeclStmt(DeclStmt *DS, ExplodedNode *Pred,
|
|||
}
|
||||
}
|
||||
|
||||
void GRExprEngine::VisitIfStmtCondInit(IfStmt *IS, ExplodedNode *Pred,
|
||||
ExplodedNodeSet& Dst) {
|
||||
|
||||
VarDecl* VD = IS->getConditionVariable();
|
||||
Expr* InitEx = VD->getInit();
|
||||
void GRExprEngine::VisitCondInit(VarDecl *VD, Stmt *S,
|
||||
ExplodedNode *Pred, ExplodedNodeSet& Dst) {
|
||||
|
||||
Expr* InitEx = VD->getInit();
|
||||
ExplodedNodeSet Tmp;
|
||||
Visit(InitEx, Pred, Tmp);
|
||||
|
||||
|
@ -2255,7 +2259,7 @@ void GRExprEngine::VisitIfStmtCondInit(IfStmt *IS, ExplodedNode *Pred,
|
|||
Builder->getCurrentBlockCount());
|
||||
}
|
||||
|
||||
EvalBind(Dst, IS, IS, N, state,
|
||||
EvalBind(Dst, S, S, N, state,
|
||||
loc::MemRegionVal(state->getRegion(VD, LC)), InitVal, true);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -41,3 +41,21 @@ int test_init_in_condition() {
|
|||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int test_init_in_condition_switch() {
|
||||
switch (int x = test_init_in_condition_aux()) { // no-warning
|
||||
case 1:
|
||||
return 0;
|
||||
case 2:
|
||||
if (x == 2)
|
||||
return 0;
|
||||
else {
|
||||
// Unreachable.
|
||||
int *p = 0;
|
||||
*p = 0xDEADBEEF; // no-warning
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
Загрузка…
Ссылка в новой задаче