Trouble with emitting checker reports

Hi all,

I’m working on a checker rule which is functioning well, but the bug reports it emits are quite problematic. Instead of reporting the source location that is interesting to the developer, it reports a very different location.

Through my testing I’ve identified that my problem comes down to my need to emit the report late. I catch the potential trouble early, but I need to keep exploring to ensure that the problem exists before I can emit the bug report. As such, I don’t generate the error node until later in the analysis. I hold onto the relevant SourceRange object at the time of detection so that I can reference it later in the report, but it doesn’t seem to be doing much of anything.

I’m using code like the following to emit my report:

clang::ento::ExplodedNode *error = C.generateNonFatalErrorNode();
if (error == nullptr) {

auto report = llvm::make_uniqueclang::ento::BugReport(*bugType, text, error);

I’ve confirmed that “sourceRange” is, in fact, the desired range (and is valid), via its dump() function. Yet in my test case, while the sourceRange states “file:6:4 - file:6:13”, I end up getting a report on the next line (which is not interesting to the developer). I’ve noticed that if I emit my report immediately, rather than holding the source range for later, the emitted report is correct.

Is there anything special I need to do here? Or what am I doing wrong when emitting my reports such that clang is refusing to reference my supplied source range?

For reference, I tried to boil my checker down to a minimalist case that reproduces my trouble (attached). I mark the source range during the call to checkPostCall and then later emit all captured ranges during checkEndFunction. (Note that I’m not actually using check::EndFunction in my checker; it was just the easiest way to reproduce this.) The test file I’m running this checker against follows, from which I expect two reports, both on line 6, but I end up getting a single report marking the ‘}’ on line 7 instead:

int foo();
void bar(int);

void baz()

Thanks for any advice,
– Matthew P. Del Buono

checkerReproduction.cpp (2.07 KB)

Hello Matthew,

It seems like the problem here is that you emit a report at the node generated on function end so it is considered as a bug place. There are two ways of solving this problem depending on what you need.
1. You don't want to show the path from the call to the end of function. In this case, you can create a non-fatal error node at function call and emit a report with this node. You can store this node in your state or retrieve it via walking up the path in the exploded graph when emitting the report in function's end.
2. If the function's end is the place you want to show, you can generate a diagnostic at the place where call happened using a BugReporterVisitor. There are some examples in different checkers (in MallocChecker, for example).

03.07.2017 08:48, Matthew Del Buono via cfe-dev пишет: