Modified BugReport::getEndPath() to handle the case where end path is at

the exit block of the CFG.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@49880 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Ted Kremenek 2008-04-17 23:44:37 +00:00
Родитель 989d519636
Коммит bd7efa8ca2
2 изменённых файлов: 47 добавлений и 16 удалений

Просмотреть файл

@ -63,7 +63,8 @@ public:
return getBugType().getDescription(); return getBugType().getDescription();
} }
virtual PathDiagnosticPiece* getEndPath(ASTContext& Ctx) const; virtual PathDiagnosticPiece* getEndPath(BugReporter& BR,
ExplodedNode<ValueState>* N) const;
virtual FullSourceLoc getLocation(SourceManager& Mgr); virtual FullSourceLoc getLocation(SourceManager& Mgr);
@ -124,6 +125,8 @@ public:
GRExprEngine& getEngine() { return Eng; } GRExprEngine& getEngine() { return Eng; }
CFG& getCFG() { return getGraph().getCFG(); }
void EmitPathWarning(BugReport& R); void EmitPathWarning(BugReport& R);
void EmitWarning(BugReport& R); void EmitWarning(BugReport& R);

Просмотреть файл

@ -56,14 +56,43 @@ Stmt* BugReport::getStmt() const {
return N ? GetStmt(N->getLocation()) : NULL; return N ? GetStmt(N->getLocation()) : NULL;
} }
PathDiagnosticPiece* BugReport::getEndPath(ASTContext& Ctx) const { static inline ExplodedNode<ValueState>*
GetNextNode(ExplodedNode<ValueState>* N) {
return N->pred_empty() ? NULL : *(N->pred_begin());
}
Stmt* S = getStmt();
static Stmt* GetLastStmt(ExplodedNode<ValueState>* N) {
assert (isa<BlockEntrance>(N->getLocation()));
for (N = GetNextNode(N); N; N = GetNextNode(N)) {
ProgramPoint P = N->getLocation();
if (PostStmt* PS = dyn_cast<PostStmt>(&P))
return PS->getStmt();
}
return NULL;
}
PathDiagnosticPiece*
BugReport::getEndPath(BugReporter& BR,
ExplodedNode<ValueState>* EndPathNode) const {
ProgramPoint ProgP = EndPathNode->getLocation();
Stmt *S = NULL;
if (BlockEntrance* BE = dyn_cast<BlockEntrance>(&ProgP))
if (BE->getBlock() == &BR.getCFG().getExit())
S = GetLastStmt(EndPathNode);
if (!S)
S = GetStmt(ProgP);
if (!S) if (!S)
return NULL; return NULL;
FullSourceLoc L(S->getLocStart(), Ctx.getSourceManager()); FullSourceLoc L(S->getLocStart(), BR.getContext().getSourceManager());
PathDiagnosticPiece* P = PathDiagnosticPiece* P =
new PathDiagnosticPiece(L, getDescription()); new PathDiagnosticPiece(L, getDescription());
@ -114,16 +143,8 @@ void BugReporter::GeneratePathDiagnostic(PathDiagnostic& PD,
BugReport& R) { BugReport& R) {
ExplodedNode<ValueState>* N = R.getEndNode(); ExplodedNode<ValueState>* N = R.getEndNode();
assert (N && "Path diagnostic requires a ExplodedNode."); assert (N && "Path diagnostic requires a ExplodedNode.");
if (PathDiagnosticPiece* Piece = R.getEndPath(Ctx))
PD.push_back(Piece);
else
return;
SourceManager& SMgr = Ctx.getSourceManager();
llvm::OwningPtr<ExplodedGraph<ValueState> > GTrim(getGraph().Trim(&N, &N+1)); llvm::OwningPtr<ExplodedGraph<ValueState> > GTrim(getGraph().Trim(&N, &N+1));
// Find the sink in the trimmed graph. // Find the sink in the trimmed graph.
@ -145,14 +166,21 @@ void BugReporter::GeneratePathDiagnostic(PathDiagnostic& PD,
N = NewN; N = NewN;
if (PathDiagnosticPiece* Piece = R.getEndPath(*this, N))
PD.push_back(Piece);
else
return;
ExplodedNode<ValueState>* NextNode = N->pred_empty() ExplodedNode<ValueState>* NextNode = N->pred_empty()
? NULL : *(N->pred_begin()); ? NULL : *(N->pred_begin());
SourceManager& SMgr = Ctx.getSourceManager();
while (NextNode) { while (NextNode) {
ExplodedNode<ValueState>* LastNode = N; ExplodedNode<ValueState>* LastNode = N;
N = NextNode; N = NextNode;
NextNode = N->pred_empty() ? NULL : *(N->pred_begin()); NextNode = GetNextNode(N);
ProgramPoint P = N->getLocation(); ProgramPoint P = N->getLocation();