From 0c0dba319654b1e699a6827fb6a045bbba3a671e Mon Sep 17 00:00:00 2001 From: chrchr Date: Tue, 19 Sep 2023 10:47:05 +0200 Subject: [PATCH 1/3] Don't set incomplete flag for library function --- lib/symboldatabase.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/lib/symboldatabase.cpp b/lib/symboldatabase.cpp index 9066592a99f..5f3332b8d2e 100644 --- a/lib/symboldatabase.cpp +++ b/lib/symboldatabase.cpp @@ -1504,6 +1504,8 @@ void SymbolDatabase::createSymbolDatabaseIncompleteVars() continue; if (mSettings.standards.cpp >= Standards::CPP20 && cpp20keywords.count(tok->str()) > 0) continue; + if (mSettings.library.functions.find(tok->str()) != mSettings.library.functions.end()) + continue; const_cast(tok)->isIncompleteVar(true); // TODO: avoid const_cast } } From 325eda6969a384779235c0c7c46c08a1ff421f4e Mon Sep 17 00:00:00 2001 From: chrchr Date: Tue, 19 Sep 2023 10:51:38 +0200 Subject: [PATCH 2/3] Fix valueFlowConditionExpressions for library function --- test/testsymboldatabase.cpp | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/test/testsymboldatabase.cpp b/test/testsymboldatabase.cpp index cd691b38b81..5211117f8ba 100644 --- a/test/testsymboldatabase.cpp +++ b/test/testsymboldatabase.cpp @@ -5464,6 +5464,15 @@ class TestSymbolDatabase : public TestFixture { const Token* s4 = Token::findsimplematch(s3->next(), "string )"); ASSERT(s4 && !s4->isIncompleteVar()); } + { + GET_SYMBOL_DB("void destroy(int*, void (*cb_dealloc)(void *));\n" + "void f(int* p) {\n" + " destroy(p, free);\n" + "}\n"); + ASSERT(db && errout.str().empty()); + const Token* free = Token::findsimplematch(tokenizer.tokens(), "free )"); + ASSERT(free && !free->isIncompleteVar()); + } } void enum1() { From 85e1d32579464c9f0cb340aec15c6dc8d9029b9c Mon Sep 17 00:00:00 2001 From: chrchr Date: Tue, 19 Sep 2023 19:45:31 +0200 Subject: [PATCH 3/3] Check namespace --- lib/symboldatabase.cpp | 10 +++++++++- test/testsymboldatabase.cpp | 12 +++++++++--- 2 files changed, 18 insertions(+), 4 deletions(-) diff --git a/lib/symboldatabase.cpp b/lib/symboldatabase.cpp index 782625cf4c1..d781a65da58 100644 --- a/lib/symboldatabase.cpp +++ b/lib/symboldatabase.cpp @@ -1510,7 +1510,15 @@ void SymbolDatabase::createSymbolDatabaseIncompleteVars() continue; if (mSettings.standards.cpp >= Standards::CPP20 && cpp20keywords.count(tok->str()) > 0) continue; - if (mSettings.library.functions.find(tok->str()) != mSettings.library.functions.end()) + std::string fstr = tok->str(); + const Token* ftok = tok->previous(); + while (Token::simpleMatch(ftok, "::")) { + if (!Token::Match(ftok->previous(), "%name%")) + break; + fstr.insert(0, ftok->previous()->str() + "::"); + ftok = ftok->tokAt(-2); + } + if (mSettings.library.functions.find(fstr) != mSettings.library.functions.end()) continue; const_cast(tok)->isIncompleteVar(true); // TODO: avoid const_cast } diff --git a/test/testsymboldatabase.cpp b/test/testsymboldatabase.cpp index 5211117f8ba..8d861f96310 100644 --- a/test/testsymboldatabase.cpp +++ b/test/testsymboldatabase.cpp @@ -5466,12 +5466,18 @@ class TestSymbolDatabase : public TestFixture { } { GET_SYMBOL_DB("void destroy(int*, void (*cb_dealloc)(void *));\n" - "void f(int* p) {\n" + "void f(int* p, int* q, int* r) {\n" " destroy(p, free);\n" + " destroy(q, std::free);\n" + " destroy(r, N::free);\n" "}\n"); ASSERT(db && errout.str().empty()); - const Token* free = Token::findsimplematch(tokenizer.tokens(), "free )"); - ASSERT(free && !free->isIncompleteVar()); + const Token* free1 = Token::findsimplematch(tokenizer.tokens(), "free"); + ASSERT(free1 && !free1->isIncompleteVar()); + const Token* free2 = Token::findsimplematch(free1->next(), "free"); + ASSERT(free2 && !free2->isIncompleteVar()); + const Token* free3 = Token::findsimplematch(free2->next(), "free"); + ASSERT(free3 && free3->isIncompleteVar()); } }