From acbf48c7fa24546d87bb03eca6a313d32353b0e7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Marjam=C3=A4ki?= Date: Thu, 26 Feb 2015 16:31:42 +0100 Subject: [PATCH] Fixed #6548 (Tokenizer: Wrong varid set after function which is throw()) --- lib/checkmemoryleak.cpp | 2 +- lib/tokenize.cpp | 6 +++++- test/testvarid.cpp | 10 ++++++++++ 3 files changed, 16 insertions(+), 2 deletions(-) diff --git a/lib/checkmemoryleak.cpp b/lib/checkmemoryleak.cpp index 97db0e1fa..eb5fb1d6e 100644 --- a/lib/checkmemoryleak.cpp +++ b/lib/checkmemoryleak.cpp @@ -2779,7 +2779,7 @@ void CheckMemoryLeakNoVar::checkForUnsafeArgAlloc(const Scope *scope) // Scan through the arguments to the function call for (const Token *tok2 = tok->tokAt(2); tok2 && tok2 != endParamToken; tok2 = tok2->nextArgument()) { const Function *pFunc = tok2->function(); - const bool isNothrow = pFunc && pFunc->isAttributeNothrow(); + const bool isNothrow = pFunc && (pFunc->isAttributeNothrow() || pFunc->isThrow()); if (Token::Match(tok2, "shared_ptr|unique_ptr < %name% > ( new %name%")) { pointerType = tok2->str(); diff --git a/lib/tokenize.cpp b/lib/tokenize.cpp index c238581a8..db609018a 100644 --- a/lib/tokenize.cpp +++ b/lib/tokenize.cpp @@ -2562,7 +2562,11 @@ void Tokenizer::setVarId() // scope info to handle shadow variables.. bool newScope = false; if (!initListEndToken && tok->str() == "(") { - if (Token::simpleMatch(tok->link(), ") {") || Token::Match(tok->link(), ") %type% {")) + if (Token::simpleMatch(tok->tokAt(-2), ") throw ( ) {")) { + tok = tok->next(); + continue; + } + if (Token::Match(tok->link(), ") %name%| {") || Token::simpleMatch(tok->link(), ") throw ( ) {")) newScope = true; else { initListEndToken = findInitListEndToken(tok->link()); diff --git a/test/testvarid.cpp b/test/testvarid.cpp index 18d71a458..be21fbe9d 100644 --- a/test/testvarid.cpp +++ b/test/testvarid.cpp @@ -88,6 +88,7 @@ private: TEST_CASE(varid53); // #4172 - Template instantiation: T<&functionName> list[4]; TEST_CASE(varid54); // hang TEST_CASE(varid55); // #5868: Function::addArgument with varid 0 for argument named the same as a typedef + TEST_CASE(varid56); // function with a throw() TEST_CASE(varid_cpp_keywords_in_c_code); TEST_CASE(varid_cpp_keywords_in_c_code2); // #5373: varid=0 for argument called "delete" TEST_CASE(varidFunctionCall1); @@ -970,6 +971,15 @@ private: ASSERT_EQUALS(expected, tokenize(code, false, "test.cpp")); } + void varid56() { // Ticket #6548 - function with a throw() + const char code[] = "void fred(int x) throw() {}" + "void wilma() { x++; }"; + const char expected[] = "\n\n##file 0\n1: " + "void fred ( int x@1 ) throw ( ) { } " + "void wilma ( ) { x ++ ; }\n"; + ASSERT_EQUALS(expected, tokenize(code, false, "test.cpp")); + } + void varid_cpp_keywords_in_c_code() { const char code[] = "void f() {\n" " delete d;\n"