Skip to content

Commit ff4492c

Browse files
author
Gabor Marton
committed
[analyzer] StdLibraryFunctionsChecker: Add option to display loaded summaries
Reviewers: NoQ, Szelethus, baloghadamsoftware, balazske Subscribers: whisperity, xazax.hun, szepet, rnkovacs, a.sidorin, mikhail.ramalho, donat.nagy, dkrupp, gamesh411, Charusso, steakhal, ASDenysPetrov, cfe-commits Tags: #clang Differential Revision: https://reviews.llvm.org/D78118
1 parent 7994108 commit ff4492c

File tree

4 files changed

+57
-5
lines changed

4 files changed

+57
-5
lines changed

clang/include/clang/StaticAnalyzer/Checkers/Checkers.td

+8
Original file line numberDiff line numberDiff line change
@@ -294,6 +294,14 @@ let ParentPackage = APIModeling in {
294294
def StdCLibraryFunctionsChecker : Checker<"StdCLibraryFunctions">,
295295
HelpText<"Improve modeling of the C standard library functions">,
296296
Dependencies<[NonNullParamChecker, CallAndMessageChecker]>,
297+
CheckerOptions<[
298+
CmdLineOption<Boolean,
299+
"DisplayLoadedSummaries",
300+
"If set to true, the checker displays the found summaries "
301+
"for the given translation unit.",
302+
"false",
303+
Released>
304+
]>,
297305
Documentation<NotDocumented>;
298306

299307
def StdCLibraryFunctionArgsChecker : Checker<"StdCLibraryFunctionArgs">,

clang/lib/StaticAnalyzer/Checkers/StdLibraryFunctionsChecker.cpp

+18-4
Original file line numberDiff line numberDiff line change
@@ -300,6 +300,8 @@ class StdLibraryFunctionsChecker
300300
DefaultBool ChecksEnabled[CK_NumCheckKinds];
301301
CheckerNameRef CheckNames[CK_NumCheckKinds];
302302

303+
bool DisplayLoadedSummaries = false;
304+
303305
private:
304306
Optional<Summary> findFunctionSummary(const FunctionDecl *FD,
305307
CheckerContext &C) const;
@@ -639,8 +641,12 @@ void StdLibraryFunctionsChecker::initFunctionSummaries(
639641
struct AddToFunctionSummaryMap {
640642
const ASTContext &ACtx;
641643
FunctionSummaryMapType &Map;
642-
AddToFunctionSummaryMap(const ASTContext &ACtx, FunctionSummaryMapType &FSM)
643-
: ACtx(ACtx), Map(FSM) {}
644+
bool DisplayLoadedSummaries;
645+
AddToFunctionSummaryMap(const ASTContext &ACtx, FunctionSummaryMapType &FSM,
646+
bool DisplayLoadedSummaries)
647+
: ACtx(ACtx), Map(FSM), DisplayLoadedSummaries(DisplayLoadedSummaries) {
648+
}
649+
644650
// Add a summary to a FunctionDecl found by lookup. The lookup is performed
645651
// by the given Name, and in the global scope. The summary will be attached
646652
// to the found FunctionDecl only if the signatures match.
@@ -655,6 +661,11 @@ void StdLibraryFunctionsChecker::initFunctionSummaries(
655661
auto Res = Map.insert({FD->getCanonicalDecl(), S});
656662
assert(Res.second && "Function already has a summary set!");
657663
(void)Res;
664+
if (DisplayLoadedSummaries) {
665+
llvm::errs() << "Loaded summary for: ";
666+
FD->print(llvm::errs());
667+
llvm::errs() << "\n";
668+
}
658669
return;
659670
}
660671
}
@@ -665,7 +676,7 @@ void StdLibraryFunctionsChecker::initFunctionSummaries(
665676
for (const Summary &S : Summaries)
666677
operator()(Name, S);
667678
}
668-
} addToFunctionSummaryMap(ACtx, FunctionSummaryMap);
679+
} addToFunctionSummaryMap(ACtx, FunctionSummaryMap, DisplayLoadedSummaries);
669680

670681
// We are finally ready to define specifications for all supported functions.
671682
//
@@ -937,7 +948,10 @@ void StdLibraryFunctionsChecker::initFunctionSummaries(
937948
}
938949

939950
void ento::registerStdCLibraryFunctionsChecker(CheckerManager &mgr) {
940-
mgr.registerChecker<StdLibraryFunctionsChecker>();
951+
auto *Checker = mgr.registerChecker<StdLibraryFunctionsChecker>();
952+
Checker->DisplayLoadedSummaries =
953+
mgr.getAnalyzerOptions().getCheckerBooleanOption(
954+
Checker, "DisplayLoadedSummaries");
941955
}
942956

943957
bool ento::shouldRegisterStdCLibraryFunctionsChecker(const CheckerManager &mgr) {

clang/test/Analysis/analyzer-config.c

+2-1
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
// CHECK-NEXT: alpha.security.MmapWriteExec:MmapProtExec = 0x04
1212
// CHECK-NEXT: alpha.security.MmapWriteExec:MmapProtRead = 0x01
1313
// CHECK-NEXT: alpha.security.taint.TaintPropagation:Config = ""
14+
// CHECK-NEXT: apiModeling.StdCLibraryFunctions:DisplayLoadedSummaries = false
1415
// CHECK-NEXT: apply-fixits = false
1516
// CHECK-NEXT: avoid-suppressing-null-argument-paths = false
1617
// CHECK-NEXT: c++-allocator-inlining = true
@@ -106,4 +107,4 @@
106107
// CHECK-NEXT: unroll-loops = false
107108
// CHECK-NEXT: widen-loops = false
108109
// CHECK-NEXT: [stats]
109-
// CHECK-NEXT: num-entries = 103
110+
// CHECK-NEXT: num-entries = 104

clang/test/Analysis/std-c-library-functions.c

+29
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,35 @@
3030
// RUN: -triple thumbv7-a15-linux \
3131
// RUN: -verify
3232

33+
// RUN: %clang_analyze_cc1 %s \
34+
// RUN: -analyzer-checker=core \
35+
// RUN: -analyzer-checker=apiModeling.StdCLibraryFunctions \
36+
// RUN: -analyzer-config apiModeling.StdCLibraryFunctions:DisplayLoadedSummaries=true \
37+
// RUN: -analyzer-checker=debug.ExprInspection \
38+
// RUN: -analyzer-config eagerly-assume=false \
39+
// RUN: -triple i686-unknown-linux 2>&1 | FileCheck %s
40+
41+
// CHECK: Loaded summary for: int isalnum(int)
42+
// CHECK-NEXT: Loaded summary for: int isalpha(int)
43+
// CHECK-NEXT: Loaded summary for: int isascii(int)
44+
// CHECK-NEXT: Loaded summary for: int isblank(int)
45+
// CHECK-NEXT: Loaded summary for: int isdigit(int)
46+
// CHECK-NEXT: Loaded summary for: int isgraph(int)
47+
// CHECK-NEXT: Loaded summary for: int islower(int)
48+
// CHECK-NEXT: Loaded summary for: int isprint(int)
49+
// CHECK-NEXT: Loaded summary for: int ispunct(int)
50+
// CHECK-NEXT: Loaded summary for: int isspace(int)
51+
// CHECK-NEXT: Loaded summary for: int isupper(int)
52+
// CHECK-NEXT: Loaded summary for: int isxdigit(int)
53+
// CHECK-NEXT: Loaded summary for: int getc(FILE *)
54+
// CHECK-NEXT: Loaded summary for: int fgetc(FILE *)
55+
// CHECK-NEXT: Loaded summary for: int getchar()
56+
// CHECK-NEXT: Loaded summary for: ssize_t read(int, void *, size_t)
57+
// CHECK-NEXT: Loaded summary for: ssize_t write(int, const void *, size_t)
58+
// CHECK-NEXT: Loaded summary for: unsigned int fread(void *restrict, size_t, size_t, FILE *)
59+
// CHECK-NEXT: Loaded summary for: unsigned int fwrite(const void *restrict, size_t, size_t, FILE *restrict)
60+
// CHECK-NEXT: Loaded summary for: ssize_t getline(char **, size_t *, FILE *)
61+
3362
void clang_analyzer_eval(int);
3463

3564
int glob;

0 commit comments

Comments
 (0)