Author: Balázs Benics
Date: 2026-06-24T11:42:42Z
New Revision: a62cd2c465310718736956f24cd4d0d5f6cb27b7

URL: 
https://github.com/llvm/llvm-project/commit/a62cd2c465310718736956f24cd4d0d5f6cb27b7
DIFF: 
https://github.com/llvm/llvm-project/commit/a62cd2c465310718736956f24cd4d0d5f6cb27b7.diff

LOG: [analyzer][NFC] Take BugReport descriptions as Twine instead of StringRef 
(#205527)

The constructors of `BugReport`, `BasicBugReport`, and
`PathSensitiveBugReport` previously took the description (and short
description) as `StringRef`. The base class always copies into a
`std::string` member regardless, so taking `const llvm::Twine &` is
strictly more flexible at no storage cost: callers can keep passing
string literals, `StringRef`, `std::string`, `SmallString::str()`, or
`formatv(...).str()` exactly as before, and now they can also pass a
`Twine` concatenation directly without first materializing a temporary
through `SmallString` + `raw_svector_ostream` or `+`/`formatv`.

Assisted-By: claude

Added: 
    

Modified: 
    clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h
    clang/lib/StaticAnalyzer/Checkers/CXXDeleteChecker.cpp
    clang/lib/StaticAnalyzer/Checkers/MacOSKeychainAPIChecker.cpp
    clang/lib/StaticAnalyzer/Checkers/NonNullParamChecker.cpp
    clang/lib/StaticAnalyzer/Checkers/UndefCapturedBlockVarChecker.cpp
    clang/lib/StaticAnalyzer/Checkers/UndefinedNewArraySizeChecker.cpp
    clang/lib/StaticAnalyzer/Checkers/UnixAPIChecker.cpp
    clang/lib/StaticAnalyzer/Checkers/VLASizeChecker.cpp
    clang/lib/StaticAnalyzer/Core/BugReporter.cpp

Removed: 
    


################################################################################
diff  --git a/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h 
b/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h
index 6d2de7a27608c..51c54151ac07b 100644
--- a/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h
+++ b/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h
@@ -33,6 +33,7 @@
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/ADT/StringMap.h"
 #include "llvm/ADT/StringRef.h"
+#include "llvm/ADT/Twine.h"
 #include "llvm/ADT/ilist.h"
 #include "llvm/ADT/ilist_node.h"
 #include "llvm/ADT/iterator_range.h"
@@ -132,13 +133,13 @@ class BugReport {
   SmallVector<std::shared_ptr<PathDiagnosticNotePiece>, 4> Notes;
   SmallVector<FixItHint, 4> Fixits;
 
-  BugReport(Kind kind, const BugType &bt, StringRef desc)
+  BugReport(Kind kind, const BugType &bt, const llvm::Twine &desc)
       : BugReport(kind, bt, "", desc) {}
 
-  BugReport(Kind K, const BugType &BT, StringRef ShortDescription,
-            StringRef Description)
-      : K(K), BT(BT), ShortDescription(ShortDescription),
-        Description(Description) {}
+  BugReport(Kind K, const BugType &BT, const llvm::Twine &ShortDescription,
+            const llvm::Twine &Description)
+      : K(K), BT(BT), ShortDescription(ShortDescription.str()),
+        Description(Description.str()) {}
 
 public:
   virtual ~BugReport() = default;
@@ -252,11 +253,12 @@ class BasicBugReport : public BugReport {
   const Decl *DeclWithIssue = nullptr;
 
 public:
-  BasicBugReport(const BugType &bt, StringRef desc, PathDiagnosticLocation l)
+  BasicBugReport(const BugType &bt, const llvm::Twine &desc,
+                 PathDiagnosticLocation l)
       : BugReport(Kind::Basic, bt, desc), Location(l) {}
 
-  BasicBugReport(const BugType &BT, StringRef ShortDesc, StringRef Desc,
-                 PathDiagnosticLocation L)
+  BasicBugReport(const BugType &BT, const llvm::Twine &ShortDesc,
+                 const llvm::Twine &Desc, PathDiagnosticLocation L)
       : BugReport(Kind::Basic, BT, ShortDesc, Desc), Location(L) {}
 
   static bool classof(const BugReport *R) {
@@ -369,12 +371,12 @@ class PathSensitiveBugReport : public BugReport {
       StackHints;
 
 public:
-  PathSensitiveBugReport(const BugType &bt, StringRef desc,
+  PathSensitiveBugReport(const BugType &bt, const llvm::Twine &desc,
                          const ExplodedNode *errorNode)
       : PathSensitiveBugReport(bt, desc, desc, errorNode) {}
 
-  PathSensitiveBugReport(const BugType &bt, StringRef shortDesc, StringRef 
desc,
-                         const ExplodedNode *errorNode)
+  PathSensitiveBugReport(const BugType &bt, const llvm::Twine &shortDesc,
+                         const llvm::Twine &desc, const ExplodedNode 
*errorNode)
       : PathSensitiveBugReport(bt, shortDesc, desc, errorNode,
                                /*LocationToUnique*/ {},
                                /*DeclToUnique*/ nullptr) {}
@@ -386,15 +388,15 @@ class PathSensitiveBugReport : public BugReport {
   /// to the user. This method allows to rest the location which should be used
   /// for uniquing reports. For example, memory leaks checker, could set this 
to
   /// the allocation site, rather then the location where the bug is reported.
-  PathSensitiveBugReport(const BugType &bt, StringRef desc,
+  PathSensitiveBugReport(const BugType &bt, const llvm::Twine &desc,
                          const ExplodedNode *errorNode,
                          PathDiagnosticLocation LocationToUnique,
                          const Decl *DeclToUnique)
       : PathSensitiveBugReport(bt, desc, desc, errorNode, LocationToUnique,
                                DeclToUnique) {}
 
-  PathSensitiveBugReport(const BugType &bt, StringRef shortDesc, StringRef 
desc,
-                         const ExplodedNode *errorNode,
+  PathSensitiveBugReport(const BugType &bt, const llvm::Twine &shortDesc,
+                         const llvm::Twine &desc, const ExplodedNode 
*errorNode,
                          PathDiagnosticLocation LocationToUnique,
                          const Decl *DeclToUnique);
 

diff  --git a/clang/lib/StaticAnalyzer/Checkers/CXXDeleteChecker.cpp 
b/clang/lib/StaticAnalyzer/Checkers/CXXDeleteChecker.cpp
index bfab91dd67919..0bc628eaabe8c 100644
--- a/clang/lib/StaticAnalyzer/Checkers/CXXDeleteChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/CXXDeleteChecker.cpp
@@ -156,19 +156,17 @@ void CXXArrayDeleteChecker::checkTypedDeleteExpr(
   if (!N)
     return;
 
-  SmallString<256> Buf;
-  llvm::raw_svector_ostream OS(Buf);
-
   QualType SourceType = BaseClassRegion->getValueType();
   QualType TargetType =
       DerivedClassRegion->getSymbol()->getType()->getPointeeType();
 
-  OS << "Deleting an array of '" << TargetType.getAsString()
-     << "' objects as their base class '"
-     << SourceType.getAsString(C.getASTContext().getPrintingPolicy())
-     << "' is undefined";
-
-  auto R = std::make_unique<PathSensitiveBugReport>(BT, OS.str(), N);
+  auto R = std::make_unique<PathSensitiveBugReport>(
+      BT,
+      "Deleting an array of '" + Twine(TargetType.getAsString()) +
+          "' objects as their base class '" +
+          SourceType.getAsString(C.getASTContext().getPrintingPolicy()) +
+          "' is undefined",
+      N);
 
   // Mark region of problematic base class for later use in the BugVisitor.
   R->markInteresting(BaseClassRegion);

diff  --git a/clang/lib/StaticAnalyzer/Checkers/MacOSKeychainAPIChecker.cpp 
b/clang/lib/StaticAnalyzer/Checkers/MacOSKeychainAPIChecker.cpp
index 5d4a8b6b24766..02794da032f2f 100644
--- a/clang/lib/StaticAnalyzer/Checkers/MacOSKeychainAPIChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/MacOSKeychainAPIChecker.cpp
@@ -19,8 +19,6 @@
 #include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/ProgramStateTrait.h"
-#include "llvm/ADT/STLExtras.h"
-#include "llvm/Support/raw_ostream.h"
 #include <optional>
 
 using namespace clang;
@@ -226,14 +224,14 @@ void MacOSKeychainAPIChecker::
 
   if (!N)
     return;
-  SmallString<80> sbuf;
-  llvm::raw_svector_ostream os(sbuf);
   unsigned int PDeallocIdx =
-               FunctionsToTrack[AP.second->AllocatorIdx].DeallocatorIdx;
+      FunctionsToTrack[AP.second->AllocatorIdx].DeallocatorIdx;
 
-  os << "Deallocator doesn't match the allocator: '"
-     << FunctionsToTrack[PDeallocIdx].Name << "' should be used.";
-  auto Report = std::make_unique<PathSensitiveBugReport>(BT, os.str(), N);
+  auto Report = std::make_unique<PathSensitiveBugReport>(
+      BT,
+      "Deallocator doesn't match the allocator: '" +
+          Twine(FunctionsToTrack[PDeallocIdx].Name) + "' should be used.",
+      N);
   Report->addVisitor(std::make_unique<SecKeychainBugVisitor>(AP.first));
   Report->addRange(ArgExpr->getSourceRange());
   markInteresting(Report.get(), AP);
@@ -269,14 +267,13 @@ void MacOSKeychainAPIChecker::checkPreStmt(const CallExpr 
*CE,
         ExplodedNode *N = C.generateNonFatalErrorNode(State);
         if (!N)
           return;
-        SmallString<128> sbuf;
-        llvm::raw_svector_ostream os(sbuf);
         unsigned int DIdx = FunctionsToTrack[AS->AllocatorIdx].DeallocatorIdx;
-        os << "Allocated data should be released before another call to "
-            << "the allocator: missing a call to '"
-            << FunctionsToTrack[DIdx].Name
-            << "'.";
-        auto Report = std::make_unique<PathSensitiveBugReport>(BT, os.str(), 
N);
+        auto Report = std::make_unique<PathSensitiveBugReport>(
+            BT,
+            "Allocated data should be released before another call to "
+            "the allocator: missing a call to '" +
+                Twine(FunctionsToTrack[DIdx].Name) + "'.",
+            N);
         Report->addVisitor(std::make_unique<SecKeychainBugVisitor>(V));
         Report->addRange(ArgExpr->getSourceRange());
         Report->markInteresting(AS->Region);
@@ -463,10 +460,6 @@ std::unique_ptr<PathSensitiveBugReport>
 MacOSKeychainAPIChecker::generateAllocatedDataNotReleasedReport(
     const AllocationPair &AP, ExplodedNode *N, CheckerContext &C) const {
   const ADFunctionInfo &FI = FunctionsToTrack[AP.second->AllocatorIdx];
-  SmallString<70> sbuf;
-  llvm::raw_svector_ostream os(sbuf);
-  os << "Allocated data is not released: missing a call to '"
-      << FunctionsToTrack[FI.DeallocatorIdx].Name << "'.";
 
   // Most bug reports are cached at the location where they occurred.
   // With leaks, we want to unique them by the location where they were
@@ -480,8 +473,10 @@ 
MacOSKeychainAPIChecker::generateAllocatedDataNotReleasedReport(
         AllocStmt, C.getSourceManager(), AllocNode->getStackFrame());
 
   auto Report = std::make_unique<PathSensitiveBugReport>(
-      BT, os.str(), N, LocUsedForUniqueing,
-      AllocNode->getStackFrame()->getDecl());
+      BT,
+      "Allocated data is not released: missing a call to '" +
+          Twine(FunctionsToTrack[FI.DeallocatorIdx].Name) + "'.",
+      N, LocUsedForUniqueing, AllocNode->getStackFrame()->getDecl());
 
   Report->addVisitor(std::make_unique<SecKeychainBugVisitor>(AP.first));
   markInteresting(Report.get(), AP);

diff  --git a/clang/lib/StaticAnalyzer/Checkers/NonNullParamChecker.cpp 
b/clang/lib/StaticAnalyzer/Checkers/NonNullParamChecker.cpp
index 4b55c7c49caa8..2cc633fa5649f 100644
--- a/clang/lib/StaticAnalyzer/Checkers/NonNullParamChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/NonNullParamChecker.cpp
@@ -22,7 +22,6 @@
 #include "clang/StaticAnalyzer/Core/CheckerManager.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h"
-#include "llvm/ADT/StringExtras.h"
 
 using namespace clang;
 using namespace ento;
@@ -280,14 +279,11 @@ std::unique_ptr<PathSensitiveBugReport>
 NonNullParamChecker::genReportNullAttrNonNull(const ExplodedNode *ErrorNode,
                                               const Expr *ArgE,
                                               unsigned IdxOfArg) const {
-  llvm::SmallString<256> SBuf;
-  llvm::raw_svector_ostream OS(SBuf);
-  OS << "Null pointer passed to "
-     << IdxOfArg << llvm::getOrdinalSuffix(IdxOfArg)
-     << " parameter expecting 'nonnull'";
-
-  auto R =
-      std::make_unique<PathSensitiveBugReport>(BTAttrNonNull, SBuf, ErrorNode);
+  auto R = std::make_unique<PathSensitiveBugReport>(
+      BTAttrNonNull,
+      "Null pointer passed to " + Twine(IdxOfArg) +
+          llvm::getOrdinalSuffix(IdxOfArg) + " parameter expecting 'nonnull'",
+      ErrorNode);
   if (ArgE)
     bugreporter::trackExpressionValue(ErrorNode, ArgE, *R);
 

diff  --git 
a/clang/lib/StaticAnalyzer/Checkers/UndefCapturedBlockVarChecker.cpp 
b/clang/lib/StaticAnalyzer/Checkers/UndefCapturedBlockVarChecker.cpp
index 2839ef0b6d2e6..5de7daae1b10f 100644
--- a/clang/lib/StaticAnalyzer/Checkers/UndefCapturedBlockVarChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/UndefCapturedBlockVarChecker.cpp
@@ -10,15 +10,13 @@
 //
 
//===----------------------------------------------------------------------===//
 
-#include "clang/StaticAnalyzer/Checkers/BuiltinCheckerRegistration.h"
 #include "clang/AST/Attr.h"
+#include "clang/StaticAnalyzer/Checkers/BuiltinCheckerRegistration.h"
 #include "clang/StaticAnalyzer/Core/BugReporter/BugType.h"
 #include "clang/StaticAnalyzer/Core/Checker.h"
 #include "clang/StaticAnalyzer/Core/CheckerManager.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h"
-#include "llvm/ADT/SmallString.h"
-#include "llvm/Support/raw_ostream.h"
 #include <optional>
 
 using namespace clang;
@@ -70,14 +68,11 @@ UndefCapturedBlockVarChecker::checkPostStmt(const BlockExpr 
*BE,
     if (std::optional<UndefinedVal> V =
             state->getSVal(Var.getOriginalRegion()).getAs<UndefinedVal>()) {
       if (ExplodedNode *N = C.generateErrorNode()) {
-        // Generate a bug report.
-        SmallString<128> buf;
-        llvm::raw_svector_ostream os(buf);
-
-        os << "Variable '" << VD->getName()
-           << "' is uninitialized when captured by block";
-
-        auto R = std::make_unique<PathSensitiveBugReport>(BT, os.str(), N);
+        auto R = std::make_unique<PathSensitiveBugReport>(
+            BT,
+            "Variable '" + Twine(VD->getName()) +
+                "' is uninitialized when captured by block",
+            N);
         if (const Expr *Ex = FindBlockDeclRefExpr(BE->getBody(), VD))
           R->addRange(Ex->getSourceRange());
         bugreporter::trackStoredValue(*V, VR, *R,

diff  --git 
a/clang/lib/StaticAnalyzer/Checkers/UndefinedNewArraySizeChecker.cpp 
b/clang/lib/StaticAnalyzer/Checkers/UndefinedNewArraySizeChecker.cpp
index f053ee887a1aa..dcab55a7e370d 100644
--- a/clang/lib/StaticAnalyzer/Checkers/UndefinedNewArraySizeChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/UndefinedNewArraySizeChecker.cpp
@@ -55,13 +55,8 @@ void 
UndefinedNewArraySizeChecker::HandleUndefinedArrayElementCount(
     CheckerContext &C, SVal ArgVal, const Expr *Init, SourceRange Range) const 
{
 
   if (ExplodedNode *N = C.generateErrorNode()) {
-
-    SmallString<100> buf;
-    llvm::raw_svector_ostream os(buf);
-
-    os << "Element count in new[] is a garbage value";
-
-    auto R = std::make_unique<PathSensitiveBugReport>(BT, os.str(), N);
+    auto R = std::make_unique<PathSensitiveBugReport>(
+        BT, "Element count in new[] is a garbage value", N);
     R->markInteresting(ArgVal);
     R->addRange(Range);
     bugreporter::trackExpressionValue(N, Init, *R);

diff  --git a/clang/lib/StaticAnalyzer/Checkers/UnixAPIChecker.cpp 
b/clang/lib/StaticAnalyzer/Checkers/UnixAPIChecker.cpp
index 4df751d203973..e51a74f725975 100644
--- a/clang/lib/StaticAnalyzer/Checkers/UnixAPIChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/UnixAPIChecker.cpp
@@ -22,8 +22,6 @@
 #include "clang/StaticAnalyzer/Core/PathSensitive/CheckerHelpers.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/DynamicExtent.h"
 #include "llvm/ADT/STLExtras.h"
-#include "llvm/ADT/StringExtras.h"
-#include "llvm/Support/raw_ostream.h"
 #include <optional>
 
 using namespace clang;
@@ -480,11 +478,9 @@ bool UnixAPIPortabilityChecker::ReportZeroByteAllocation(
   if (!N)
     return false;
 
-  SmallString<256> S;
-  llvm::raw_svector_ostream os(S);
-  os << "Call to '" << fn_name << "' has an allocation size of 0 bytes";
-  auto report =
-      std::make_unique<PathSensitiveBugReport>(BT_mallocZero, os.str(), N);
+  auto report = std::make_unique<PathSensitiveBugReport>(
+      BT_mallocZero,
+      "Call to '" + Twine(fn_name) + "' has an allocation size of 0 bytes", N);
 
   report->addRange(arg->getSourceRange());
   bugreporter::trackExpressionValue(N, arg, *report);

diff  --git a/clang/lib/StaticAnalyzer/Checkers/VLASizeChecker.cpp 
b/clang/lib/StaticAnalyzer/Checkers/VLASizeChecker.cpp
index d5c91a20d60b2..1d82ac0f7225a 100644
--- a/clang/lib/StaticAnalyzer/Checkers/VLASizeChecker.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/VLASizeChecker.cpp
@@ -21,7 +21,6 @@
 #include "clang/StaticAnalyzer/Core/CheckerManager.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/DynamicExtent.h"
-#include "llvm/Support/raw_ostream.h"
 #include <optional>
 
 using namespace clang;
@@ -213,12 +212,11 @@ void VLASizeChecker::reportTaintBug(const Expr *SizeE, 
ProgramStateRef State,
   if (!N)
     return;
 
-  SmallString<256> buf;
-  llvm::raw_svector_ostream os(buf);
-  os << "Declared variable-length array (VLA) ";
-  os << "has tainted (attacker controlled) size that can be 0 or negative";
-
-  auto report = std::make_unique<PathSensitiveBugReport>(TaintBT, os.str(), N);
+  auto report = std::make_unique<PathSensitiveBugReport>(
+      TaintBT,
+      "Declared variable-length array (VLA) has tainted (attacker controlled) "
+      "size that can be 0 or negative",
+      N);
   report->addRange(SizeE->getSourceRange());
   bugreporter::trackExpressionValue(N, SizeE, *report);
   // The vla size may be a complex expression where multiple memory locations

diff  --git a/clang/lib/StaticAnalyzer/Core/BugReporter.cpp 
b/clang/lib/StaticAnalyzer/Core/BugReporter.cpp
index b6c709963501f..b609a98b0aed2 100644
--- a/clang/lib/StaticAnalyzer/Core/BugReporter.cpp
+++ b/clang/lib/StaticAnalyzer/Core/BugReporter.cpp
@@ -2154,7 +2154,7 @@ LLVM_ATTRIBUTE_USED static bool isHidden(const 
CheckerRegistryData &Registry,
 }
 
 PathSensitiveBugReport::PathSensitiveBugReport(
-    const BugType &bt, StringRef shortDesc, StringRef desc,
+    const BugType &bt, const llvm::Twine &shortDesc, const llvm::Twine &desc,
     const ExplodedNode *errorNode, PathDiagnosticLocation LocationToUnique,
     const Decl *DeclToUnique)
     : BugReport(Kind::PathSensitive, bt, shortDesc, desc), 
ErrorNode(errorNode),


        
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to