diff --git a/clang/include/clang/Checker/PathSensitive/GRCoreEngine.h b/clang/include/clang/Checker/PathSensitive/GRCoreEngine.h index 40ff93bb5b0b..dd789cb73529 100644 --- a/clang/include/clang/Checker/PathSensitive/GRCoreEngine.h +++ b/clang/include/clang/Checker/PathSensitive/GRCoreEngine.h @@ -502,7 +502,11 @@ public: GRCallExitNodeBuilder(GRCoreEngine &eng, const ExplodedNode *pred) : Eng(eng), Pred(pred) {} - void GenerateNode(); + const ExplodedNode *getPredecessor() const { return Pred; } + + const GRState *getState() const { return Pred->getState(); } + + void GenerateNode(const GRState *state); }; } // end clang namespace diff --git a/clang/lib/Checker/CallInliner.cpp b/clang/lib/Checker/CallInliner.cpp index e3c5e6036a51..150102c5ef26 100644 --- a/clang/lib/Checker/CallInliner.cpp +++ b/clang/lib/Checker/CallInliner.cpp @@ -60,20 +60,10 @@ void CallInliner::EvalEndPath(GREndPathNodeBuilder &B, void *tag, ExplodedNode *Pred = B.getPredecessor(); const StackFrameContext *LocCtx = - cast(Pred->getLocationContext()); + cast(Pred->getLocationContext()); // Check if this is the top level stack frame. if (!LocCtx->getParent()) - return; - - const StackFrameContext *ParentSF = - cast(LocCtx->getParent()); - - SymbolReaper SymReaper(*ParentSF->getLiveVariables(), Eng.getSymbolManager(), - ParentSF); - const Stmt *CE = LocCtx->getCallSite(); - // FIXME: move this logic to GRExprEngine::ProcessCallExit(). - state = Eng.getStateManager().RemoveDeadBindings(state, const_cast(CE), - SymReaper); + return; B.GenerateCallExitNode(state); } diff --git a/clang/lib/Checker/GRCoreEngine.cpp b/clang/lib/Checker/GRCoreEngine.cpp index 17ef1d48f50a..cbc1cf26216c 100644 --- a/clang/lib/Checker/GRCoreEngine.cpp +++ b/clang/lib/Checker/GRCoreEngine.cpp @@ -674,14 +674,14 @@ void GRCallEnterNodeBuilder::GenerateNode(const GRState *state, Eng.WList->Enqueue(Node); } -void GRCallExitNodeBuilder::GenerateNode() { +void GRCallExitNodeBuilder::GenerateNode(const GRState *state) { // Get the callee's location context. const StackFrameContext *LocCtx = cast(Pred->getLocationContext()); PostStmt Loc(LocCtx->getCallSite(), LocCtx->getParent()); bool isNew; - ExplodedNode *Node = Eng.G->getNode(Loc, Pred->getState(), &isNew); + ExplodedNode *Node = Eng.G->getNode(Loc, state, &isNew); Node->addPredecessor(const_cast(Pred), *Eng.G); if (isNew) Eng.WList->Enqueue(Node, *const_cast(LocCtx->getCallSiteBlock()), diff --git a/clang/lib/Checker/GRExprEngine.cpp b/clang/lib/Checker/GRExprEngine.cpp index 695ed02e22f8..30b82f70ce0c 100644 --- a/clang/lib/Checker/GRExprEngine.cpp +++ b/clang/lib/Checker/GRExprEngine.cpp @@ -1305,7 +1305,21 @@ void GRExprEngine::ProcessCallEnter(GRCallEnterNodeBuilder &B) { } void GRExprEngine::ProcessCallExit(GRCallExitNodeBuilder &B) { - B.GenerateNode(); + const GRState *state = B.getState(); + const ExplodedNode *Pred = B.getPredecessor(); + const StackFrameContext *LocCtx = + cast(Pred->getLocationContext()); + const StackFrameContext *ParentSF = + cast(LocCtx->getParent()); + + SymbolReaper SymReaper(*ParentSF->getLiveVariables(), getSymbolManager(), + ParentSF); + const Stmt *CE = LocCtx->getCallSite(); + + state = getStateManager().RemoveDeadBindings(state, const_cast(CE), + SymReaper); + + B.GenerateNode(state); } //===----------------------------------------------------------------------===//