summaryrefslogtreecommitdiff
path: root/compilerplugins
diff options
context:
space:
mode:
authorStephan Bergmann <sbergman@redhat.com>2023-11-08 08:49:28 +0100
committerStephan Bergmann <sbergman@redhat.com>2023-11-08 13:44:52 +0100
commit71d9e8d3e403329428edbda747c7d6bbc705c95f (patch)
tree824f0143ace32358d06f8785dad9b0fe05e1d6e3 /compilerplugins
parenta9d2b9b7c0c0c9f45f8893ba75f0fff31ef2b4af (diff)
Adapt loplugin:stringconcatliterals to clang-cl
...whose handling of PredefinedExpr (representing `__func__`) deliberately differs in IgnoreParens and IgnoreParenImpCasts, see the comment in StringConcatLiterals::isStringLiteral Change-Id: I8b001d65369adc3d2a2c47e0cf32578a72ef4eec Reviewed-on: https://gerrit.libreoffice.org/c/core/+/159111 Tested-by: Jenkins Reviewed-by: Stephan Bergmann <sbergman@redhat.com>
Diffstat (limited to 'compilerplugins')
-rw-r--r--compilerplugins/clang/stringconcatliterals.cxx26
-rw-r--r--compilerplugins/clang/test/stringconcatliterals.cxx1
2 files changed, 21 insertions, 6 deletions
diff --git a/compilerplugins/clang/stringconcatliterals.cxx b/compilerplugins/clang/stringconcatliterals.cxx
index 54ca706e208f..9f6482d218f8 100644
--- a/compilerplugins/clang/stringconcatliterals.cxx
+++ b/compilerplugins/clang/stringconcatliterals.cxx
@@ -78,16 +78,16 @@ bool StringConcatLiterals::VisitCallExpr(CallExpr const * expr) {
if ((oo != OverloadedOperatorKind::OO_Plus
&& oo != OverloadedOperatorKind::OO_LessLess)
|| fdecl->getNumParams() != 2 || expr->getNumArgs() != 2
- || !isStringLiteral(expr->getArg(1)->IgnoreParenImpCasts()))
+ || !isStringLiteral(expr->getArg(1)))
{
return true;
}
SourceLocation leftLoc;
- auto const leftExpr = expr->getArg(0)->IgnoreParenImpCasts();
+ auto const leftExpr = expr->getArg(0);
if (isStringLiteral(leftExpr)) {
- leftLoc = leftExpr->getBeginLoc();
+ leftLoc = leftExpr->IgnoreParenImpCasts()->getBeginLoc();
} else {
- CallExpr const * left = dyn_cast<CallExpr>(leftExpr);
+ CallExpr const * left = dyn_cast<CallExpr>(leftExpr->IgnoreParenImpCasts());
if (left == nullptr) {
return true;
}
@@ -99,7 +99,7 @@ bool StringConcatLiterals::VisitCallExpr(CallExpr const * expr) {
if ((loo != OverloadedOperatorKind::OO_Plus
&& loo != OverloadedOperatorKind::OO_LessLess)
|| ldecl->getNumParams() != 2 || left->getNumArgs() != 2
- || !isStringLiteral(left->getArg(1)->IgnoreParenImpCasts()))
+ || !isStringLiteral(left->getArg(1)))
{
return true;
}
@@ -140,7 +140,21 @@ bool StringConcatLiterals::VisitCallExpr(CallExpr const * expr) {
}
bool StringConcatLiterals::isStringLiteral(Expr const * expr) {
- expr = stripCtor(expr);
+ // Since <https://github.com/llvm/llvm-project/commit/878e590503dff0d9097e91c2bec4409f14503b82>
+ // "Reland [clang] Make predefined expressions string literals under -fms-extensions", in MS
+ // compatibility mode only, IgnoreParens and IgnoreParenImpCasts look through a PredefinedExpr
+ // representing __func__, but which we do not want to do here:
+ while (auto const e = dyn_cast<ParenExpr>(expr)) {
+ expr = e->getSubExpr();
+ }
+ expr = expr->IgnoreImpCasts();
+ if (isa<PredefinedExpr>(expr)) {
+ return false;
+ }
+ // Once we have filtered out the problematic PredefinedExpr above, still call
+ // IgnoreParenImpCasts again, because it does more than just ignore ParenExpr and call
+ // IgnoreImpCasts as is done above:
+ expr = stripCtor(expr->IgnoreParenImpCasts());
if (!isa<clang::StringLiteral>(expr)) {
return false;
}
diff --git a/compilerplugins/clang/test/stringconcatliterals.cxx b/compilerplugins/clang/test/stringconcatliterals.cxx
index 8b390f28fbbb..0575eb252bc0 100644
--- a/compilerplugins/clang/test/stringconcatliterals.cxx
+++ b/compilerplugins/clang/test/stringconcatliterals.cxx
@@ -40,6 +40,7 @@ void f(std::ostream& s1)
s1 << "foo" << OUString(FOO);
// expected-error@-1 {{replace '<<' between string literals with juxtaposition}}
s1 << "foo" << OUString(foo);
+ s1 << "foo" << __func__;
OString s2;
s2 = "foo" + OString("foo");
// expected-error@-1 {{replace '+' between string literals with juxtaposition}}