checkrun cppcheck or clang-tidy on Prism sources
Prepend prism check to the analyzer command you already run. Source arguments are swapped for transpiled standard-C artifacts, everything else passes through verbatim, and findings cite your original source lines.
added in: v1.1.5
#Overview
A C static analyzer cannot read Prism source. Point CppCheck at a file containing orelse and it stops at the first keyword with an unknownMacro configuration error, because orelse is not C.
prism check wraps the analyzer the same way CC=prism wraps your compiler. It transpiles the .c and .i arguments to standard C, runs the tool against those artifacts, and preserves the tool's exit code so it still works as a build gate. The emitted #line directives do the rest: every finding maps back to the line you wrote.
prism check cppcheck --enable=all src.c
# src.c:12:4: error: Array 'arr[8]' accessed at index 8, out of boundsThe finding cites src.c line 12, not a line in the generated artifact.
#Usage
Anything after the tool name is passed through untouched, including the analyzer's own -- separator:
prism check cppcheck --enable=all src.c
prism check clang-tidy src.c -- -I includePrism's own flags go before check, and still apply to the transpile:
prism -fno-zeroinit check cppcheck src.c#How the artifact is shaped
Two of Prism's defaults would blind an analyzer, so check turns them off for the analysis artifact only:
- Header flattening is off.
#includelines stay intact, so the analyzer resolves headers the way it normally would instead of reading one enormous translation unit. - Bounds checking is off. Subscripts stay bare, so the tool sees
arr[8]rather than a__prism_bchkwrapper it does not understand.
This affects the analysis artifact and nothing else. Your shipping build keeps both features on.
#Bugs only the expansion shows
Analyzing the transpiled output is stronger than analyzing the source, because the expansion contains the real control flow. Cleanup that defer schedules becomes ordinary C statements on every exit path, and the analyzer can finally reason about it.
Consider a manual close alongside a deferred one:
FILE *f = fopen(path, "r") orelse return -1;
defer fclose(f);
if (bad) {
fclose(f); // and then the defer runs too
return -1;
}CppCheck reports it:
src.c:14:9: error: doubleFree: Resource handle 'f' freed twiceNo source-level C analyzer finds this on its own, because none of them parse defer. The bug is only visible once the cleanup is lowered to the exit paths it actually runs on.
#Doing it by hand
If you want the artifact itself, check is equivalent to transpiling with the two flags above and running the tool yourself:
prism transpile -fno-flatten-headers -fno-bounds-check src.c > build/src.c
cppcheck --enable=all build/src.c#Caveats
- Files that use no Prism keywords are plain C and analyze as-is. You do not need
checkfor those. - Automatic zero-initialization can surface as
redundantAssignmentat style level when you overwrite a variable immediately. Suppress that id, or read it as intentional. - Findings inside headers still cite the header. Only the translation unit passes through the
#linemapping.