aboutsummaryrefslogtreecommitdiff
path: root/clang
diff options
context:
space:
mode:
Diffstat (limited to 'clang')
-rw-r--r--clang/docs/ReleaseNotes.rst5
-rw-r--r--clang/lib/StaticAnalyzer/Checkers/StdLibraryFunctionsChecker.cpp13
-rw-r--r--clang/test/Analysis/errno-stdlibraryfunctions.c15
3 files changed, 30 insertions, 3 deletions
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index c9b577b..803eb2f 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -1150,9 +1150,10 @@ Improvements
^^^^^^^^^^^^
- Improved the ``unix.StdCLibraryFunctions`` checker by modeling more
- functions like ``send``, ``recv``, ``readlink``, ``fflush``, ``mkdtemp`` and
- ``errno`` behavior.
+ functions like ``send``, ``recv``, ``readlink``, ``fflush``, ``mkdtemp``,
+ ``getcwd`` and ``errno`` behavior.
(`52ac71f92d38 <https://github.com/llvm/llvm-project/commit/52ac71f92d38f75df5cb88e9c090ac5fd5a71548>`_,
+ `#77040 <https://github.com/llvm/llvm-project/pull/77040>`_,
`#76671 <https://github.com/llvm/llvm-project/pull/76671>`_,
`#71373 <https://github.com/llvm/llvm-project/pull/71373>`_,
`#76557 <https://github.com/llvm/llvm-project/pull/76557>`_,
diff --git a/clang/lib/StaticAnalyzer/Checkers/StdLibraryFunctionsChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/StdLibraryFunctionsChecker.cpp
index 2006865..034825d 100644
--- a/clang/lib/StaticAnalyzer/Checkers/StdLibraryFunctionsChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/StdLibraryFunctionsChecker.cpp
@@ -2516,10 +2516,21 @@ void StdLibraryFunctionsChecker::initFunctionSummaries(
.ArgConstraint(NotNull(ArgNo(0))));
// char *getcwd(char *buf, size_t size);
- // FIXME: Improve for errno modeling.
addToFunctionSummaryMap(
"getcwd", Signature(ArgTypes{CharPtrTy, SizeTy}, RetType{CharPtrTy}),
Summary(NoEvalCall)
+ .Case({ArgumentCondition(1, WithinRange, Range(1, SizeMax)),
+ ReturnValueCondition(BO_EQ, ArgNo(0))},
+ ErrnoMustNotBeChecked, GenericSuccessMsg)
+ .Case({ArgumentCondition(1, WithinRange, SingleValue(0)),
+ IsNull(Ret)},
+ ErrnoNEZeroIrrelevant, "Assuming that argument 'size' is 0")
+ .Case({ArgumentCondition(1, WithinRange, Range(1, SizeMax)),
+ IsNull(Ret)},
+ ErrnoNEZeroIrrelevant, GenericFailureMsg)
+ .ArgConstraint(NotNull(ArgNo(0)))
+ .ArgConstraint(
+ BufferSize(/*Buffer*/ ArgNo(0), /*BufSize*/ ArgNo(1)))
.ArgConstraint(
ArgumentCondition(1, WithinRange, Range(0, SizeMax))));
diff --git a/clang/test/Analysis/errno-stdlibraryfunctions.c b/clang/test/Analysis/errno-stdlibraryfunctions.c
index 80e14c4..9e3d07e 100644
--- a/clang/test/Analysis/errno-stdlibraryfunctions.c
+++ b/clang/test/Analysis/errno-stdlibraryfunctions.c
@@ -74,3 +74,18 @@ void errno_mkdtemp(char *template) {
if (errno) {} // expected-warning{{An undefined value may be read from 'errno'}}
}
}
+
+void errno_getcwd(char *Buf, size_t Sz) {
+ char *Path = getcwd(Buf, Sz);
+ if (Sz == 0) {
+ clang_analyzer_eval(errno != 0); // expected-warning{{TRUE}}
+ clang_analyzer_eval(Path == NULL); // expected-warning{{TRUE}}
+ if (errno) {} // no warning
+ } else if (Path == NULL) {
+ clang_analyzer_eval(errno != 0); // expected-warning{{TRUE}}
+ if (errno) {} // no warning
+ } else {
+ clang_analyzer_eval(Path == Buf); // expected-warning{{TRUE}}
+ if (errno) {} // expected-warning{{An undefined value may be read from 'errno'}}
+ }
+}