basic/source/uno/namecont.cxx               |    2 -
 compilerplugins/clang/bufferadd.cxx         |   38 +++++++++++++++++++++++++++-
 compilerplugins/clang/test/bufferadd.cxx    |    6 ++++
 sdext/source/pdfimport/wrapper/wrapper.cxx  |    3 --
 svgio/source/svgreader/svgtools.cxx         |    2 -
 sw/source/filter/ww8/rtfattributeoutput.cxx |    2 -
 vcl/unx/generic/printer/ppdparser.cxx       |   19 ++++++--------
 7 files changed, 56 insertions(+), 16 deletions(-)

New commits:
commit fbe05bc89a53f4c31e5ccf62edb21e83184c0a34
Author:     Noel Grandin <noel.gran...@collabora.co.uk>
AuthorDate: Wed Apr 16 12:40:19 2025 +0200
Commit:     Noel Grandin <noel.gran...@collabora.co.uk>
CommitDate: Tue Apr 22 11:53:07 2025 +0200

    loplugin:bufferadd extend it to find some more places
    
    where we can simplify *StringBuffer usage
    
    Change-Id: Ic2005b886b486a6627a43f8dcfba3258cb168921
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/184428
    Reviewed-by: Noel Grandin <noel.gran...@collabora.co.uk>
    Tested-by: Jenkins

diff --git a/basic/source/uno/namecont.cxx b/basic/source/uno/namecont.cxx
index 8c66cebbbfcf..5436b3c6c380 100644
--- a/basic/source/uno/namecont.cxx
+++ b/basic/source/uno/namecont.cxx
@@ -1744,7 +1744,7 @@ void SfxLibraryContainer::storeLibraries_Impl( const 
uno::Reference< embed::XSto
             if ( bInplaceStorage )
             {
                 // create a temporary target storage
-                const OUStringBuffer aTempTargetNameBase = maLibrariesDir + 
"_temp_";
+                const OUString aTempTargetNameBase = maLibrariesDir + "_temp_";
                 sal_Int32 index = 0;
                 do
                 {
diff --git a/compilerplugins/clang/bufferadd.cxx 
b/compilerplugins/clang/bufferadd.cxx
index 8f58e46aba14..0dd65868f640 100644
--- a/compilerplugins/clang/bufferadd.cxx
+++ b/compilerplugins/clang/bufferadd.cxx
@@ -119,12 +119,26 @@ bool BufferAdd::VisitCallExpr(CallExpr const* callExpr)
     if (ignoreLocation(callExpr))
         return true;
 
+    // calls to "buffer = foo" are OK
+    // calls to "xxx = foo1 + buffer" are OK
+    if (auto operatorCall = dyn_cast<CXXOperatorCallExpr>(callExpr))
+    {
+        auto op = operatorCall->getOperator();
+        if (op == OO_PlusEqual || op == OO_Equal || op == OO_Plus)
+            return true;
+    }
+
+    // exclude buffer vars where the var is passed as a parameter to another 
function
     for (unsigned i = 0; i != callExpr->getNumArgs(); ++i)
     {
         auto a = ignore(callExpr->getArg(i));
         if (auto declRefExpr = dyn_cast<DeclRefExpr>(a))
             if (auto varDecl = dyn_cast<VarDecl>(declRefExpr->getDecl()))
+            {
                 badMap.insert(varDecl);
+                if (varDecl->getName() == "noelf7")
+                    callExpr->dump();
+            }
     }
     return true;
 }
@@ -215,6 +229,28 @@ void BufferAdd::findBufferAssignOrAdd(const Stmt* 
parentStmt, Stmt const* stmt)
         }
     }
 
+    // check for assignment to string buffer
+    if (auto operatorCall = dyn_cast<CXXOperatorCallExpr>(stmt))
+    {
+        auto op = operatorCall->getOperator();
+        if (op == OO_PlusEqual || op == OO_Equal)
+        {
+            if (auto declRefExprLHS = 
dyn_cast<DeclRefExpr>(ignore(operatorCall->getArg(0))))
+            {
+                if (auto varDeclLHS = 
dyn_cast<VarDecl>(declRefExprLHS->getDecl()))
+                {
+                    auto tc = loplugin::TypeCheck(varDeclLHS->getType());
+                    if 
(tc.Class("OUStringBuffer").Namespace("rtl").GlobalNamespace()
+                        || 
tc.Class("OStringBuffer").Namespace("rtl").GlobalNamespace())
+                    {
+                        addToGoodMap(varDeclLHS, parentStmt);
+                        return;
+                    }
+                }
+            }
+        }
+    }
+
     // now check for chained append calls
 
     auto expr = dyn_cast<Expr>(stmt);
@@ -316,7 +352,7 @@ bool BufferAdd::isSideEffectFree(Expr const* expr)
     if (auto operatorCall = dyn_cast<CXXOperatorCallExpr>(expr))
     {
         auto op = operatorCall->getOperator();
-        if (op == OO_PlusEqual || op == OO_Plus)
+        if (op == OO_PlusEqual || op == OO_Plus || op == OO_Equal)
             if (isSideEffectFree(operatorCall->getArg(0))
                 && isSideEffectFree(operatorCall->getArg(1)))
                 return true;
diff --git a/compilerplugins/clang/test/bufferadd.cxx 
b/compilerplugins/clang/test/bufferadd.cxx
index c8057a6f497b..464214461083 100644
--- a/compilerplugins/clang/test/bufferadd.cxx
+++ b/compilerplugins/clang/test/bufferadd.cxx
@@ -111,6 +111,12 @@ void f6()
     while (true)
         noel1.append("ffff").append("aaa");
 }
+void f7()
+{
+    // expected-error@+1 {{convert this append sequence into a *String + 
sequence [loplugin:bufferadd]}}
+    OStringBuffer noelf7("xxx");
+    noelf7 = "xxx" + noelf7 + "xxx";
+}
 }
 
 /* vim:set shiftwidth=4 softtabstop=4 expandtab cinoptions=b1,g0,N-s 
cinkeys+=0=break: */
diff --git a/sdext/source/pdfimport/wrapper/wrapper.cxx 
b/sdext/source/pdfimport/wrapper/wrapper.cxx
index 461681439be4..fcac1cdacfa2 100644
--- a/sdext/source/pdfimport/wrapper/wrapper.cxx
+++ b/sdext/source/pdfimport/wrapper/wrapper.cxx
@@ -1097,9 +1097,8 @@ bool xpdf_ImportFromFile(const OUString& rURL,
         bool bEntered = false;
         do
         {
-            OStringBuffer aBuf(256);
             // Password lines are Pmypassword
 followed by "O
" to try to open
-            aBuf = "P" + OUStringToOString(aPwd, RTL_TEXTENCODING_ISO_8859_1) 
+ "
O
";
+            OString aBuf = "P" + OUStringToOString(aPwd, 
RTL_TEXTENCODING_ISO_8859_1) + "
O
";
 
             osl_writeFile(pIn, aBuf.getStr(), sal_uInt64(aBuf.getLength()), 
&nWritten);
 
diff --git a/svgio/source/svgreader/svgtools.cxx 
b/svgio/source/svgreader/svgtools.cxx
index 3918660fb7bd..d2795198504b 100644
--- a/svgio/source/svgreader/svgtools.cxx
+++ b/svgio/source/svgreader/svgtools.cxx
@@ -407,7 +407,7 @@ namespace svgio::svgreader
                         // by error. First try if there are numbers after the 
'e',
                         // safe current state
                         nPos++;
-                        const OUStringBuffer aNum2(aNum);
+                        const OUString aNum2(aNum);
                         const sal_Int32 nPosAfterE(nPos);
 
                         aNum.append(aChar);
diff --git a/sw/source/filter/ww8/rtfattributeoutput.cxx 
b/sw/source/filter/ww8/rtfattributeoutput.cxx
index abda306d67cb..9e832a45c9a7 100644
--- a/sw/source/filter/ww8/rtfattributeoutput.cxx
+++ b/sw/source/filter/ww8/rtfattributeoutput.cxx
@@ -1988,7 +1988,7 @@ void 
RtfAttributeOutput::WriteAnnotationMarks_Impl(std::vector<ReferenceMarkerNa
 void RtfAttributeOutput::WriteHeaderFooter_Impl(const SwFrameFormat& rFormat, 
bool bHeader,
                                                 const char* pStr, bool 
bTitlepg)
 {
-    OStringBuffer aSectionBreaks = m_aSectionBreaks;
+    OString aSectionBreaks = m_aSectionBreaks.toString();
     m_aSectionBreaks.setLength(0);
     RtfStringBuffer aRun = m_aRun;
     m_aRun.clear();
diff --git a/vcl/unx/generic/printer/ppdparser.cxx 
b/vcl/unx/generic/printer/ppdparser.cxx
index b6c25830fd37..c68e285b0433 100644
--- a/vcl/unx/generic/printer/ppdparser.cxx
+++ b/vcl/unx/generic/printer/ppdparser.cxx
@@ -635,18 +635,17 @@ PPDParser::PPDParser(OUString aFile, const 
std::vector<PPDKey*>& keys)
             OString o = OUStringToOString( aValueName, aEncoding );
             pwg_media_t *pPWGMedia = pwgMediaForPWG(o.pData->buffer);
             if (pPWGMedia != nullptr) {
-                OUStringBuffer aBuf( 256 );
-                aBuf = "0 0 " +
-                    OUString::number(PWG_TO_POINTS(pPWGMedia -> width)) +
-                    " " +
-                    OUString::number(PWG_TO_POINTS(pPWGMedia -> length));
                 if ( pImageableAreaValue )
-                    pImageableAreaValue->m_aValue = aBuf.makeStringAndClear();
-                aBuf.append( OUString::number(PWG_TO_POINTS(pPWGMedia -> 
width))
-                    + " "
-                    + OUString::number(PWG_TO_POINTS(pPWGMedia -> length) ));
+                    pImageableAreaValue->m_aValue =
+                        "0 0 " +
+                        OUString::number(PWG_TO_POINTS(pPWGMedia -> width)) +
+                        " " +
+                        OUString::number(PWG_TO_POINTS(pPWGMedia -> length));
                 if ( pPaperDimensionValue )
-                    pPaperDimensionValue->m_aValue = aBuf.makeStringAndClear();
+                    pPaperDimensionValue->m_aValue =
+                        OUString::number(PWG_TO_POINTS(pPWGMedia -> width))
+                        + " "
+                        + OUString::number(PWG_TO_POINTS(pPWGMedia -> length));
                 if (aValueName.equals(pKey -> getDefaultValue() -> m_aOption)) 
{
                     pImageableAreas -> m_pDefaultValue = pImageableAreaValue;
                     pPaperDimensions -> m_pDefaultValue = pPaperDimensionValue;

Reply via email to