NoQ created this revision. NoQ added a reviewer: dcoughlin. Herald added subscribers: cfe-commits, a.sidorin, szepet, xazax.hun. Herald added a reviewer: george.karpenkov.
Because we're planning to add more cases when temporary constructors will be inlined, it is important to document the fact that the current heuristic of terminating the analysis upon encountering constructors that correspond to noreturn temporary destructors //does not work in this case//. For now these constructors are not inlined for the sole reason that their respective destructors are non-trivial and missing from the CFG. We will hopefully be able to enable temporary destructors in the CFG by default, so it won't be an issue. However, the intent is to maintain the mode without temporary destructors usable in short-term, and this assertion will force us to put the checks for presence of the destructor in the CFG wherever we enable inlining temporary constructors. In other words, if any new code violates this assertion, it should be fixed by un-inlining this constructor when `-analyzer-config cfg-temporary-dtors` is set to `false`. Repository: rC Clang https://reviews.llvm.org/D42779 Files: lib/StaticAnalyzer/Core/ExprEngineCXX.cpp Index: lib/StaticAnalyzer/Core/ExprEngineCXX.cpp =================================================================== --- lib/StaticAnalyzer/Core/ExprEngineCXX.cpp +++ lib/StaticAnalyzer/Core/ExprEngineCXX.cpp @@ -323,20 +323,23 @@ // paths when no-return temporary destructors are used for assertions. const AnalysisDeclContext *ADC = LCtx->getAnalysisDeclContext(); if (!ADC->getCFGBuildOptions().AddTemporaryDtors) { - const MemRegion *Target = Call->getCXXThisVal().getAsRegion(); - if (Target && isa<CXXTempObjectRegion>(Target) && - Call->getDecl()->getParent()->isAnyDestructorNoReturn()) { + const MemRegion *Target = Call->getCXXThisVal().getAsRegion(); + if (Target && isa<CXXTempObjectRegion>(Target) && + Call->getDecl()->getParent()->isAnyDestructorNoReturn()) { + + assert(!DstEvaluated.empty() && + "We should not have inlined this constructor!"); for (ExplodedNode *N : DstEvaluated) { Bldr.generateSink(CE, N, N->getState()); } - // There is no need to run the PostCall and PostStmtchecker + // There is no need to run the PostCall and PostStmt checker // callbacks because we just generated sinks on all nodes in th // frontier. return; } - } + } ExplodedNodeSet DstPostCall; getCheckerManager().runCheckersForPostCall(DstPostCall, DstEvaluated,
Index: lib/StaticAnalyzer/Core/ExprEngineCXX.cpp =================================================================== --- lib/StaticAnalyzer/Core/ExprEngineCXX.cpp +++ lib/StaticAnalyzer/Core/ExprEngineCXX.cpp @@ -323,20 +323,23 @@ // paths when no-return temporary destructors are used for assertions. const AnalysisDeclContext *ADC = LCtx->getAnalysisDeclContext(); if (!ADC->getCFGBuildOptions().AddTemporaryDtors) { - const MemRegion *Target = Call->getCXXThisVal().getAsRegion(); - if (Target && isa<CXXTempObjectRegion>(Target) && - Call->getDecl()->getParent()->isAnyDestructorNoReturn()) { + const MemRegion *Target = Call->getCXXThisVal().getAsRegion(); + if (Target && isa<CXXTempObjectRegion>(Target) && + Call->getDecl()->getParent()->isAnyDestructorNoReturn()) { + + assert(!DstEvaluated.empty() && + "We should not have inlined this constructor!"); for (ExplodedNode *N : DstEvaluated) { Bldr.generateSink(CE, N, N->getState()); } - // There is no need to run the PostCall and PostStmtchecker + // There is no need to run the PostCall and PostStmt checker // callbacks because we just generated sinks on all nodes in th // frontier. return; } - } + } ExplodedNodeSet DstPostCall; getCheckerManager().runCheckersForPostCall(DstPostCall, DstEvaluated,
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits