diff options
Diffstat (limited to 'compilerplugins/clang/stringconcatliterals.cxx')
-rw-r--r-- | compilerplugins/clang/stringconcatliterals.cxx | 38 |
1 files changed, 27 insertions, 11 deletions
diff --git a/compilerplugins/clang/stringconcatliterals.cxx b/compilerplugins/clang/stringconcatliterals.cxx index f82114199de8..9f6482d218f8 100644 --- a/compilerplugins/clang/stringconcatliterals.cxx +++ b/compilerplugins/clang/stringconcatliterals.cxx @@ -9,6 +9,8 @@ #ifndef LO_CLANG_SHARED_PLUGINS +#include "config_clang.h" + #include "plugin.hxx" #include "check.hxx" @@ -76,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 = compat::getBeginLoc(leftExpr); + 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; } @@ -97,11 +99,11 @@ 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; } - leftLoc = compat::getBeginLoc(left->getArg(1)); + leftLoc = left->getArg(1)->getBeginLoc(); } // We add an extra " " in the TOOLS_WARN_EXCEPTION macro, which triggers this plugin @@ -111,13 +113,13 @@ bool StringConcatLiterals::VisitCallExpr(CallExpr const * expr) { compiler.getSourceManager().getImmediateMacroCallerLoc( compiler.getSourceManager().getImmediateMacroCallerLoc( compiler.getSourceManager().getImmediateMacroCallerLoc( - compat::getBeginLoc(expr)))))), - SRCDIR "/include/tools/diagnose_ex.h")) + expr->getBeginLoc()))))), + SRCDIR "/include/comphelper/diagnose_ex.hxx")) return true; StringRef name { getFilenameOfLocation( - compiler.getSourceManager().getSpellingLoc(compat::getBeginLoc(expr))) }; + compiler.getSourceManager().getSpellingLoc(expr->getBeginLoc())) }; if (loplugin::isSamePathname( name, SRCDIR "/sal/qa/rtl/oustringbuffer/test_oustringbuffer_assign.cxx") || loplugin::isSamePathname( @@ -133,12 +135,26 @@ bool StringConcatLiterals::VisitCallExpr(CallExpr const * expr) { "replace '%0' between string literals with juxtaposition", op == nullptr ? expr->getExprLoc() : op->getOperatorLoc()) << (oo == OverloadedOperatorKind::OO_Plus ? "+" : "<<") - << SourceRange(leftLoc, compat::getEndLoc(expr->getArg(1))); + << SourceRange(leftLoc, expr->getArg(1)->getEndLoc()); return true; } 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; } |