diff options
-rw-r--r-- | Changelog | 2 | ||||
-rw-r--r-- | src/checks/level1/connect-3arg-lambda.cpp | 25 | ||||
-rw-r--r-- | src/checks/level1/connect-3arg-lambda.h | 1 | ||||
-rw-r--r-- | tests/connect-3arg-lambda/main.cpp | 11 | ||||
-rw-r--r-- | tests/connect-3arg-lambda/main.cpp.expected | 3 |
5 files changed, 36 insertions, 6 deletions
@@ -86,5 +86,5 @@ - unused-non-trivial-variable got user-blacklist and user-whitelist support - container-inside-loop is now a manual check instead of level2 - HiddenLevel was renamed to ManualLevel - - connect-3arg-lambda now warns when passing a lambda to QTimer::singleShot() without a context + - connect-3arg-lambda now warns when passing a lambda to QTimer::singleShot() or QMenu::addAction() without a context object - old-style-connect warns for QMenu::addAction() and QMessageBox::open() too now diff --git a/src/checks/level1/connect-3arg-lambda.cpp b/src/checks/level1/connect-3arg-lambda.cpp index a66110f7..9422c986 100644 --- a/src/checks/level1/connect-3arg-lambda.cpp +++ b/src/checks/level1/connect-3arg-lambda.cpp @@ -49,11 +49,17 @@ void Connect3ArgLambda::VisitStmt(clang::Stmt *stmt) if (numParams != 2 && numParams != 3) return; - if (fdecl->getQualifiedNameAsString() == "QTimer::singleShot") { + string qualifiedName = fdecl->getQualifiedNameAsString(); + if (qualifiedName == "QTimer::singleShot") { processQTimer(fdecl, stmt); return; } + if (qualifiedName == "QMenu::addAction") { + processQMenu(fdecl, stmt); + return; + } + if (numParams != 3 || !clazy::isConnect(fdecl)) return; @@ -112,7 +118,6 @@ void Connect3ArgLambda::processQTimer(FunctionDecl *func, Stmt *stmt) // QTimer::singleShot(int msec, Functor functor) // QTimer::singleShot(int msec, Qt::TimerType timerType, Functor functor) - const uint numParams = func->getNumParams(); if (numParams == 2) { if (func->getParamDecl(0)->getNameAsString() == "interval" && @@ -123,7 +128,21 @@ void Connect3ArgLambda::processQTimer(FunctionDecl *func, Stmt *stmt) if (func->getParamDecl(0)->getNameAsString() == "interval" && func->getParamDecl(1)->getNameAsString() == "timerType" && func->getParamDecl(2)->getNameAsString() == "slot") { - emitWarning(stmt, "Pass a context object as 3nd singleShot parameter"); + emitWarning(stmt, "Pass a context object as 3rd singleShot parameter"); } } } + +void Connect3ArgLambda::processQMenu(FunctionDecl *func, Stmt *stmt) +{ + // Signatures to catch: + // QMenu::addAction(const QString &text, Func1 slot, const QKeySequence &shortcut = 0) + const uint numParams = func->getNumParams(); + if (numParams == 3) { + if (func->getParamDecl(0)->getNameAsString() == "text" && + func->getParamDecl(1)->getNameAsString() == "slot" && + func->getParamDecl(2)->getNameAsString() == "shortcut") { + emitWarning(stmt, "Pass a context object as 2nd singleShot parameter"); + } + } +} diff --git a/src/checks/level1/connect-3arg-lambda.h b/src/checks/level1/connect-3arg-lambda.h index 66f3d3ff..13c819dd 100644 --- a/src/checks/level1/connect-3arg-lambda.h +++ b/src/checks/level1/connect-3arg-lambda.h @@ -35,6 +35,7 @@ public: void VisitStmt(clang::Stmt *stmt) override; private: void processQTimer(clang::FunctionDecl *, clang::Stmt *); + void processQMenu(clang::FunctionDecl *, clang::Stmt *); }; #endif diff --git a/tests/connect-3arg-lambda/main.cpp b/tests/connect-3arg-lambda/main.cpp index a3d5f170..ef36d9d3 100644 --- a/tests/connect-3arg-lambda/main.cpp +++ b/tests/connect-3arg-lambda/main.cpp @@ -1,5 +1,5 @@ #include <QtCore/QString> -#include <QtCore/QObject> +#include <QtWidgets/QMenu> #include <QtCore/QTimer> void another_global(); void test() @@ -84,3 +84,12 @@ void testTimer() QTimer::singleShot(0, Qt::CoarseTimer, [] {}); // Warn QTimer::singleShot(0, Qt::CoarseTimer, o, [] {}); // OK } + +void testQMenu() +{ + MyObject o; + QMenu menu; + menu.addAction("foo", &o, &MyObject::test); // OK + menu.addAction("foo", &o, []{}); // OK + menu.addAction("foo", []{}); // Warn +} diff --git a/tests/connect-3arg-lambda/main.cpp.expected b/tests/connect-3arg-lambda/main.cpp.expected index 51427c19..b5229203 100644 --- a/tests/connect-3arg-lambda/main.cpp.expected +++ b/tests/connect-3arg-lambda/main.cpp.expected @@ -7,4 +7,5 @@ connect-3arg-lambda/main.cpp:59:9: warning: Pass a context object as 3rd connect connect-3arg-lambda/main.cpp:63:9: warning: Pass a context object as 3rd connect parameter [-Wclazy-connect-3arg-lambda] connect-3arg-lambda/main.cpp:68:9: warning: Pass a context object as 3rd connect parameter [-Wclazy-connect-3arg-lambda] connect-3arg-lambda/main.cpp:81:5: warning: Pass a context object as 2nd singleShot parameter [-Wclazy-connect-3arg-lambda] -connect-3arg-lambda/main.cpp:84:5: warning: Pass a context object as 3nd singleShot parameter [-Wclazy-connect-3arg-lambda] +connect-3arg-lambda/main.cpp:84:5: warning: Pass a context object as 3rd singleShot parameter [-Wclazy-connect-3arg-lambda] +connect-3arg-lambda/main.cpp:94:5: warning: Pass a context object as 2nd singleShot parameter [-Wclazy-connect-3arg-lambda] |