-
Notifications
You must be signed in to change notification settings - Fork 14.3k
[Wunsafe-buffer-usage] Fix false positives in handling string literals. #115552
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Wunsafe-buffer-usage] Fix false positives in handling string literals. #115552
Conversation
@llvm/pr-subscribers-clang-analysis @llvm/pr-subscribers-clang Author: Malavika Samak (malavikasamak) ChangesDo not warn when a string literal is indexed and the idex value is within the bounds of the length of the string. (rdar://139106996) Full diff: https://github.com/llvm/llvm-project/pull/115552.diff 2 Files Affected:
diff --git a/clang/lib/Analysis/UnsafeBufferUsage.cpp b/clang/lib/Analysis/UnsafeBufferUsage.cpp
index 2c68409b846bc8..650d51bebd66f7 100644
--- a/clang/lib/Analysis/UnsafeBufferUsage.cpp
+++ b/clang/lib/Analysis/UnsafeBufferUsage.cpp
@@ -436,21 +436,31 @@ AST_MATCHER(ArraySubscriptExpr, isSafeArraySubscript) {
const auto *BaseDRE =
dyn_cast<DeclRefExpr>(Node.getBase()->IgnoreParenImpCasts());
- if (!BaseDRE)
- return false;
- if (!BaseDRE->getDecl())
- return false;
- const auto *CATy = Finder->getASTContext().getAsConstantArrayType(
- BaseDRE->getDecl()->getType());
- if (!CATy)
+ const auto *SLiteral = dyn_cast<StringLiteral>(Node.getBase()->IgnoreParenImpCasts());
+ uint64_t size;
+
+ if (!BaseDRE && !SLiteral)
return false;
+ if(BaseDRE) {
+ if (!BaseDRE->getDecl())
+ return false;
+ const auto *CATy = Finder->getASTContext().getAsConstantArrayType(
+ BaseDRE->getDecl()->getType());
+ if (!CATy) {
+ return false;
+ }
+ size = CATy->getLimitedSize();
+ } else if(SLiteral) {
+ size = SLiteral->getLength();
+ }
+
if (const auto *IdxLit = dyn_cast<IntegerLiteral>(Node.getIdx())) {
const APInt ArrIdx = IdxLit->getValue();
// FIXME: ArrIdx.isNegative() we could immediately emit an error as that's a
// bug
if (ArrIdx.isNonNegative() &&
- ArrIdx.getLimitedValue() < CATy->getLimitedSize())
+ ArrIdx.getLimitedValue() < size)
return true;
}
@@ -1142,7 +1152,7 @@ class ArraySubscriptGadget : public WarningGadget {
// clang-format off
return stmt(arraySubscriptExpr(
hasBase(ignoringParenImpCasts(
- anyOf(hasPointerType(), hasArrayType()))),
+ anyOf(hasPointerType(), hasArrayType(), stringLiteral()))),
unless(anyOf(
isSafeArraySubscript(),
hasIndex(
diff --git a/clang/test/SemaCXX/warn-unsafe-buffer-usage-array.cpp b/clang/test/SemaCXX/warn-unsafe-buffer-usage-array.cpp
index 8b2f103ec66708..0a443543d3f604 100644
--- a/clang/test/SemaCXX/warn-unsafe-buffer-usage-array.cpp
+++ b/clang/test/SemaCXX/warn-unsafe-buffer-usage-array.cpp
@@ -38,3 +38,10 @@ void constant_idx_unsafe(unsigned idx) {
// expected-note@-1{{change type of 'buffer' to 'std::array' to label it for hardening}}
buffer[10] = 0; // expected-note{{used in buffer access here}}
}
+
+void constant_id_string() {
+ char safe_char = "abc"[1]; // no-warning
+ char abcd[5] = "abc";
+ abcd[2]; // no-warning
+ safe_char = "abc"[3]; //expected-warning{{unsafe buffer access}}
+}
|
✅ With the latest revision this PR passed the C/C++ code formatter. |
3be112e
to
a3f41d4
Compare
|
||
char unsafe_char = "abc"[3]; //expected-warning{{unsafe buffer access}} | ||
unsafe_char = "abc"[-1]; //expected-warning{{unsafe buffer access}} | ||
unsafe_char = ""[1]; //expected-warning{{unsafe buffer access}} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This shouldn't be a warning either.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In this case, I think we should warn, as the length here including the null terminator is 1.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sorry, my bad. You're right
Do not warn when a string literal is indexed and the idex value is within the bounds of the length of the string. (rdar://139106996)
a3f41d4
to
94ba7d8
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM! Thank you @malavikasamak
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
Thank you!
…s. (llvm#115552) Do not warn when a string literal is indexed and the idex value is within the bounds of the length of the string. (rdar://139106996) Co-authored-by: MalavikaSamak <[email protected]>
…s. (llvm#115552) Do not warn when a string literal is indexed and the idex value is within the bounds of the length of the string. (rdar://139106996) Co-authored-by: MalavikaSamak <[email protected]> (cherry picked from commit da032a6)
…terals [Cherry-Pick][Wunsafe-buffer-usage] Fix false positives in handling string literals. (llvm#115552)
Do not warn when a string literal is indexed and the idex value is within the bounds of the length of the string.
(rdar://139106996)