diff options
-rw-r--r-- | compilerplugins/clang/check.hxx | 2 | ||||
-rw-r--r-- | compilerplugins/clang/cppunitassertequals.cxx | 5 | ||||
-rw-r--r-- | compilerplugins/clang/rendercontext.cxx | 9 | ||||
-rw-r--r-- | compilerplugins/clang/sallogareas.cxx | 8 | ||||
-rw-r--r-- | compilerplugins/clang/sfxpoolitem.cxx | 15 | ||||
-rw-r--r-- | compilerplugins/clang/staticmethods.cxx | 2 | ||||
-rw-r--r-- | compilerplugins/clang/store/changefunctioncalls.cxx | 6 | ||||
-rw-r--r-- | compilerplugins/clang/stringconcat.cxx | 6 | ||||
-rw-r--r-- | compilerplugins/clang/stringconstant.cxx | 3 | ||||
-rw-r--r-- | compilerplugins/clang/unusedvariablecheck.cxx | 27 | ||||
-rw-r--r-- | compilerplugins/clang/weakobject.cxx | 22 |
11 files changed, 58 insertions, 47 deletions
diff --git a/compilerplugins/clang/check.hxx b/compilerplugins/clang/check.hxx index 40f205d977fa..8c3edf773ea1 100644 --- a/compilerplugins/clang/check.hxx +++ b/compilerplugins/clang/check.hxx @@ -33,6 +33,8 @@ class TypeCheck { public: explicit TypeCheck(clang::QualType type): type_(type) {} + explicit TypeCheck(clang::TypeDecl const * decl): type_(decl->getTypeForDecl(), 0) {} + explicit operator bool() const { return !type_.isNull(); } TypeCheck NonConstVolatile() const; diff --git a/compilerplugins/clang/cppunitassertequals.cxx b/compilerplugins/clang/cppunitassertequals.cxx index f14dde6300e4..e9f4c0256516 100644 --- a/compilerplugins/clang/cppunitassertequals.cxx +++ b/compilerplugins/clang/cppunitassertequals.cxx @@ -13,6 +13,7 @@ #include <fstream> #include <set> #include "plugin.hxx" +#include "check.hxx" /** Check for calls to CPPUNIT_ASSERT when it should be using CPPUNIT_ASSERT_EQUALS @@ -87,7 +88,9 @@ void CppunitAssertEquals::checkExpr(const Stmt* stmt) return; } const FunctionDecl* functionDecl = callExpr->getDirectCallee()->getCanonicalDecl(); - if (!functionDecl || functionDecl->getQualifiedNameAsString().find("Asserter::failIf") == std::string::npos) { + if (!functionDecl || + !loplugin::DeclCheck(functionDecl).Function("failIf").Namespace("Asserter").Namespace("CppUnit").GlobalNamespace()) + { return; } report( diff --git a/compilerplugins/clang/rendercontext.cxx b/compilerplugins/clang/rendercontext.cxx index e3d1da40ae1e..2ea4a0c3380b 100644 --- a/compilerplugins/clang/rendercontext.cxx +++ b/compilerplugins/clang/rendercontext.cxx @@ -11,6 +11,7 @@ #include <iostream> #include "plugin.hxx" +#include "check.hxx" #include "clang/AST/CXXInheritance.h" // Check for calls to OutputDevice methods that are not passing through RenderContext @@ -51,15 +52,13 @@ bool RenderContext::TraverseFunctionDecl(const FunctionDecl * pFunctionDecl) // Ignore methods inside the OutputDevice class const CXXMethodDecl *pCXXMethodDecl = dyn_cast<CXXMethodDecl>(pFunctionDecl); if (pCXXMethodDecl) { - std::string aParentName = pCXXMethodDecl->getParent()->getQualifiedNameAsString(); - if (aParentName == "OutputDevice") + if (loplugin::TypeCheck(pCXXMethodDecl->getParent()).Class("OutputDevice").GlobalNamespace()) return true; } // we are only currently interested in methods where the first parameter is RenderContext if (pFunctionDecl->getNumParams() == 0) return true; - string arg0 = pFunctionDecl->getParamDecl( 0 )->getType().getAsString(); - if ( arg0.find("RenderContext") != std::string::npos ) { + if ( loplugin::TypeCheck(pFunctionDecl->getParamDecl( 0 )->getType()).Class("RenderContext").GlobalNamespace() ) { return true; } mbChecking = true; @@ -76,7 +75,7 @@ bool RenderContext::VisitCXXMemberCallExpr(const CXXMemberCallExpr* pCXXMemberCa return true; } const CXXRecordDecl *pCXXRecordDecl = pCXXMemberCallExpr->getRecordDecl(); - if (pCXXRecordDecl->getQualifiedNameAsString() != "OutputDevice") { + if (!loplugin::TypeCheck(pCXXRecordDecl).Class("OutputDevice").GlobalNamespace()) { return true; } // ignore a handful of methods. They will most probably still be present in Window for use during processing outside of the Paint() diff --git a/compilerplugins/clang/sallogareas.cxx b/compilerplugins/clang/sallogareas.cxx index d54918755624..e0ccf0bde7a3 100644 --- a/compilerplugins/clang/sallogareas.cxx +++ b/compilerplugins/clang/sallogareas.cxx @@ -10,6 +10,7 @@ */ #include "sallogareas.hxx" +#include "check.hxx" #include <clang/Lex/Lexer.h> @@ -50,12 +51,11 @@ bool SalLogAreas::VisitCallExpr( const CallExpr* call ) return true; if( const FunctionDecl* func = call->getDirectCallee()) { - // Optimize, getQualifiedNameAsString() is reportedly expensive. if( func->getNumParams() == 4 && func->getIdentifier() != NULL && ( func->getName() == "sal_detail_log" || func->getName() == "log" )) { - string qualifiedName = func->getQualifiedNameAsString(); - if( qualifiedName == "sal_detail_log" || qualifiedName == "sal::detail::log" ) + auto tc = loplugin::DeclCheck(func); + if( tc.Function("sal_detail_log") || tc.Function("log").Namespace("detail").Namespace("sal").GlobalNamespace() ) { // The SAL_DETAIL_LOG_STREAM macro expands to two calls to sal::detail::log(), // so do not warn repeatedly about the same macro (the area->getLocStart() of all the calls @@ -73,7 +73,7 @@ bool SalLogAreas::VisitCallExpr( const CallExpr* call ) area->getLocStart()); return true; } - if( inFunction->getQualifiedNameAsString() == "sal::detail::log" ) + if( loplugin::DeclCheck(inFunction).Function("log").Namespace("detail").Namespace("sal").GlobalNamespace() ) return true; // This function only forwards to sal_detail_log, so ok. if( call->getArg( 1 )->isNullPointerConstant( compiler.getASTContext(), Expr::NPC_ValueDependentIsNotNull ) != Expr::NPCK_NotNull ) diff --git a/compilerplugins/clang/sfxpoolitem.cxx b/compilerplugins/clang/sfxpoolitem.cxx index f01adf578235..b18251795486 100644 --- a/compilerplugins/clang/sfxpoolitem.cxx +++ b/compilerplugins/clang/sfxpoolitem.cxx @@ -12,6 +12,7 @@ #include "plugin.hxx" #include "compat.hxx" +#include "check.hxx" #include "clang/AST/CXXInheritance.h" /* @@ -39,7 +40,7 @@ bool BaseCheckNotSfxPoolItemSubclass( #endif ) { - if (BaseDefinition && BaseDefinition->getQualifiedNameAsString() == "SfxPoolItem") { + if (BaseDefinition && loplugin::TypeCheck(BaseDefinition).Class("SfxPoolItem").GlobalNamespace()) { return false; } return true; @@ -48,7 +49,7 @@ bool BaseCheckNotSfxPoolItemSubclass( bool isDerivedFromSfxPoolItem(const CXXRecordDecl *decl) { if (!decl) return false; - if (decl->getQualifiedNameAsString() == "SfxPoolItem") + if (loplugin::TypeCheck(decl).Class("SfxPoolItem").GlobalNamespace()) return true; if (!decl->hasDefinition()) { return false; @@ -70,7 +71,7 @@ bool BaseCheckNotSwMsgPoolItemSubclass( #endif ) { - if (BaseDefinition && BaseDefinition->getQualifiedNameAsString() == "SwMsgPoolItem") { + if (BaseDefinition && loplugin::TypeCheck(BaseDefinition).Class("SwMsgPoolItem")) { return false; } return true; @@ -79,7 +80,7 @@ bool BaseCheckNotSwMsgPoolItemSubclass( bool isDerivedFromSwMsgPoolItem(const CXXRecordDecl *decl) { if (!decl) return false; - if (decl->getQualifiedNameAsString() == "SwMsgPoolItem") + if (loplugin::TypeCheck(decl).Class("SwMsgPoolItem").GlobalNamespace()) return true; if (!decl->hasDefinition()) { return false; @@ -118,12 +119,12 @@ bool SfxPoolItem::VisitCXXRecordDecl(const CXXRecordDecl* decl) return true; } // the enum types do some weird stuff involving SfxEnumItemInterface - std::string sRecordName = decl->getQualifiedNameAsString(); - if (sRecordName == "SfxEnumItem" || sRecordName == "SfxAllEnumItem") + auto tc = loplugin::TypeCheck(decl); + if (tc.Class("SfxEnumItem").GlobalNamespace() || tc.Class("SfxAllEnumItem").GlobalNamespace()) return true; // the new field is only used for reading and writing to storage - if (sRecordName == "SvxCharSetColorItem") + if (tc.Class("SvxCharSetColorItem").GlobalNamespace()) return true; for (auto it = decl->method_begin(); it != decl->method_end(); ++it) { diff --git a/compilerplugins/clang/staticmethods.cxx b/compilerplugins/clang/staticmethods.cxx index 588e534c482c..f33f10f907c7 100644 --- a/compilerplugins/clang/staticmethods.cxx +++ b/compilerplugins/clang/staticmethods.cxx @@ -46,7 +46,7 @@ bool BaseCheckNotTestFixtureSubclass( #endif ) { - if (BaseDefinition->getQualifiedNameAsString().compare("CppUnit::TestFixture") == 0) { + if (loplugin::TypeCheck(BaseDefinition).Class("TestFixture").Namespace("CppUnit").GlobalNamespace()) { return false; } return true; diff --git a/compilerplugins/clang/store/changefunctioncalls.cxx b/compilerplugins/clang/store/changefunctioncalls.cxx index abc8ce62ceba..a728ad5a310a 100644 --- a/compilerplugins/clang/store/changefunctioncalls.cxx +++ b/compilerplugins/clang/store/changefunctioncalls.cxx @@ -27,6 +27,7 @@ This can be easily adjusted for different modifications to a function: */ #include "plugin.hxx" +#include "check.hxx" namespace loplugin { @@ -61,15 +62,14 @@ bool ChangeFunctionCalls::VisitCallExpr( const CallExpr* call ) // if( const FunctionDecl* func = dyn_cast_or_null< FunctionDecl >( call->getCalleeDecl())) if( const FunctionDecl* func = call->getDirectCallee()) { - // Optimize, getQualifiedNameAsString() is reportedly expensive, // so first check fast details like number of arguments or the (unqualified) // name before checking the fully qualified name. // See FunctionDecl for all the API about the function. if( func->getNumParams() == 1 && func->getIdentifier() != NULL && ( func->getName() == "bar" )) { - string qualifiedName = func->getQualifiedNameAsString(); - if( qualifiedName == "bar" ) + auto qt = loplugin::DeclCheck(func); + if( qt.Function("bar").GlobalNamespace() ) { // Further checks about arguments. Check mainly ParmVarDecl, VarDecl, // ValueDecl and QualType for Clang API details. diff --git a/compilerplugins/clang/stringconcat.cxx b/compilerplugins/clang/stringconcat.cxx index a944f4fcf319..670d8929016a 100644 --- a/compilerplugins/clang/stringconcat.cxx +++ b/compilerplugins/clang/stringconcat.cxx @@ -8,6 +8,7 @@ */ #include "plugin.hxx" +#include "check.hxx" namespace { @@ -26,8 +27,9 @@ Expr const * stripCtor(Expr const * expr) { if (e3 == nullptr) { return expr; } - auto const n = e3->getConstructor()->getQualifiedNameAsString(); - if (n != "rtl::OString::OString" && n != "rtl::OUString::OUString") { + auto qt = loplugin::DeclCheck(e3->getConstructor()); + if (!qt.Function("OString").Class("OString").Namespace("rtl").GlobalNamespace() && + !qt.Function("OUString").Class("OUString").Namespace("rtl").GlobalNamespace()) { return expr; } if (e3->getNumArgs() != 2) { diff --git a/compilerplugins/clang/stringconstant.cxx b/compilerplugins/clang/stringconstant.cxx index 9ae672ae9050..426f8bd2c244 100644 --- a/compilerplugins/clang/stringconstant.cxx +++ b/compilerplugins/clang/stringconstant.cxx @@ -1626,8 +1626,7 @@ void StringConstant::handleOUStringCtor( if (e3 == nullptr) { return; } - if (e3->getConstructor()->getQualifiedNameAsString() - != "rtl::OUString::OUString") + if (!loplugin::DeclCheck(e3->getConstructor()).Function("OUString").Class("OUString").Namespace("rtl").GlobalNamespace()) { return; } diff --git a/compilerplugins/clang/unusedvariablecheck.cxx b/compilerplugins/clang/unusedvariablecheck.cxx index db6a45e1ae3f..50b41d5664f8 100644 --- a/compilerplugins/clang/unusedvariablecheck.cxx +++ b/compilerplugins/clang/unusedvariablecheck.cxx @@ -17,6 +17,7 @@ #if !HAVE_GCC_ATTRIBUTE_WARN_UNUSED_STL #include "compat.hxx" +#include "check.hxx" #include "unusedvariablecheck.hxx" #include <clang/AST/Attr.h> @@ -56,11 +57,11 @@ bool BaseCheckNotSomethingInterestingSubclass( #endif ) { - if (BaseDefinition && BaseDefinition->getQualifiedNameAsString().compare("Dialog") == 0) { - return false; - } - if (BaseDefinition && BaseDefinition->getQualifiedNameAsString().compare("SfxPoolItem") == 0) { - return false; + if (BaseDefinition) { + auto tc = loplugin::TypeCheck(BaseDefinition); + if (tc.Class("Dialog").GlobalNamespace() || tc.Class("SfxPoolItem").GlobalNamespace()) { + return false; + } } return true; } @@ -68,9 +69,10 @@ bool BaseCheckNotSomethingInterestingSubclass( bool isDerivedFromSomethingInteresting(const CXXRecordDecl *decl) { if (!decl) return false; - if (decl->getQualifiedNameAsString() == "Dialog") + auto tc = loplugin::TypeCheck(decl); + if (tc.Class("Dialog")) return true; - if (decl->getQualifiedNameAsString() == "SfxPoolItem") + if (tc.Class("SfxPoolItem")) return true; if (!decl->hasDefinition()) { return false; @@ -113,11 +115,14 @@ bool UnusedVariableCheck::VisitVarDecl( const VarDecl* var ) } if( !warn_unused ) { - string n = type->getQualifiedNameAsString(); + auto tc = loplugin::TypeCheck(type); // Check some common non-LO types. - if( n == "std::string" || n == "std::basic_string" - || n == "std::list" || n == "std::__debug::list" - || n == "std::vector" || n == "std::__debug::vector" ) + if( tc.Class("string").Namespace("std").GlobalNamespace() + || tc.Class("basic_string").Namespace("std").GlobalNamespace() + || tc.Class("list").Namespace("std").GlobalNamespace() + || tc.Class("list").Namespace("__debug").Namespace("std").GlobalNamespace() + || tc.Class("vector").Namespace("std").GlobalNamespace() + || tc.Class("vector" ).Namespace("__debug").Namespace("std").GlobalNamespace()) warn_unused = true; if (!warn_unused && isDerivedFromSomethingInteresting(type)) warn_unused = true; diff --git a/compilerplugins/clang/weakobject.cxx b/compilerplugins/clang/weakobject.cxx index 7c36f93a1d92..9ccbb8ac3c86 100644 --- a/compilerplugins/clang/weakobject.cxx +++ b/compilerplugins/clang/weakobject.cxx @@ -117,8 +117,8 @@ public: // Allow this convenient shortcut: auto td = dyn_cast<TypeDecl>(pCalled->getParent()); if (td != nullptr - && (loplugin::TypeCheck(QualType(td->getTypeForDecl(), 0)).Class("OWeakObject").Namespace("cppu") - || loplugin::TypeCheck(QualType(td->getTypeForDecl(), 0)).Class("OWeakAggObject").Namespace("cppu"))) + && (loplugin::TypeCheck(td).Class("OWeakObject").Namespace("cppu").GlobalNamespace() + || loplugin::TypeCheck(td).Class("OWeakAggObject").Namespace("cppu").GlobalNamespace())) { return true; } @@ -131,15 +131,15 @@ public: } // whitelist - auto const name(pMethodDecl->getParent()->getQualifiedNameAsString()); - if ( name == "cppu::OWeakAggObject" // conditional call - || name == "cppu::WeakComponentImplHelperBase" // extra magic - || name == "cppu::WeakAggComponentImplHelperBase" // extra magic - || name == "DOM::CDOMImplementation" // a static oddity - || name == "SwXTextFrame" // ambiguous, 3 parents - || name == "SwXTextDocument" // ambiguous, ~4 parents - || name == "SdStyleSheet" // same extra magic as WeakComponentImplHelperBase - || name == "SdXImpressDocument" // same extra magic as WeakComponentImplHelperBase + auto tc = loplugin::TypeCheck(pMethodDecl->getParent()); + if ( tc.Class("OWeakAggObject").Namespace("cppu").GlobalNamespace() // conditional call + || tc.Class("WeakComponentImplHelperBase").Namespace("cppu").GlobalNamespace() // extra magic + || tc.Class("WeakAggComponentImplHelperBase").Namespace("cppu").GlobalNamespace() // extra magic + || tc.Class("CDOMImplementation").Namespace("DOM").GlobalNamespace() // a static oddity + || tc.Class("SwXTextFrame").GlobalNamespace() // ambiguous, 3 parents + || tc.Class("SwXTextDocument").GlobalNamespace() // ambiguous, ~4 parents + || tc.Class("SdStyleSheet").GlobalNamespace() // same extra magic as WeakComponentImplHelperBase + || tc.Class("SdXImpressDocument").GlobalNamespace() // same extra magic as WeakComponentImplHelperBase ) { return true; |