Author: DonĂ¡t Nagy Date: 2026-10-12T12:55:37+02:00 New Revision: b58dd0d0d0ab1bbceb3839d45aa797a3809e2b8f
URL: https://github.com/llvm/llvm-project/commit/b58dd0d0d0ab1bbceb3839d45aa797a3809e2b8f DIFF: https://github.com/llvm/llvm-project/commit/b58dd0d0d0ab1bbceb3839d45aa797a3809e2b8f.diff LOG: [analyzer] Ignore nonstandard function named 'memset' (#229119) Previously CStringChecker ran into an assertion failure when it encountered a function named 'memset' whose third argument was a `const int &` instead of the standard `size_t`. This PR introduces an early return to avoid this. Fixes #228865 Reported-by: k-arrows Added: clang/test/Analysis/PR228865.cpp Modified: clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp Removed: ################################################################################ diff --git a/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp index 69712d15d50c4..3749c262e8bba 100644 --- a/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp @@ -2938,6 +2938,11 @@ void CStringChecker::evalMemset(CheckerContext &C, SVal SizeVal = C.getSVal(Size.Expression); QualType SizeTy = Size.Expression->getType(); + // Avoid assertion failure in the corner case when we see a function named + // 'memset' with a nonstandard declaration. + if (!SizeTy->isUnsignedIntegerType() || !Size.Expression->isPRValue()) + return; + ProgramStateRef ZeroSize, NonZeroSize; std::tie(ZeroSize, NonZeroSize) = assumeZero(C, State, SizeVal, SizeTy); diff --git a/clang/test/Analysis/PR228865.cpp b/clang/test/Analysis/PR228865.cpp new file mode 100644 index 0000000000000..74c8e4a73da77 --- /dev/null +++ b/clang/test/Analysis/PR228865.cpp @@ -0,0 +1,20 @@ +// RUN: %clang_analyze_cc1 -analyzer-checker=core,unix.cstring -verify %s + +// Test that a nonstandard 'memset' does not trigger an assertion failure. +// Code adapted from https://github.com/llvm/llvm-project/issues/228865 + +// expected-no-diagnostics + +struct B { +} b; + +struct A { + struct B b; +} a; + +// Not the standard 'memset' -- there the third parameter would be a 'size_t'. +void *memset(void *s, int c, const unsigned &cond); + +void foo() { + memset(&a.b, 0, sizeof(b)); // no-crash +} _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
