diff --git a/lib/astutils.cpp b/lib/astutils.cpp index f16144310ac..d77f387f24f 100644 --- a/lib/astutils.cpp +++ b/lib/astutils.cpp @@ -3425,8 +3425,14 @@ static ExprUsage getFunctionUsage(const Token* tok, int indirect, const Settings // TODO: resolve multiple constructors if (ftok->variable()->type() && ftok->variable()->type()->classScope) { const int nCtor = ftok->variable()->type()->classScope->numConstructors; - if (nCtor == 0) + if (nCtor == 0) { + if (indirect > 0) { + const std::vector argvar = getArgumentVars(ftok->astParent(), argnr); + if (argvar.size() == 1 && argvar[0]->valueType() && argvar[0]->valueType()->pointer == indirect) + return ExprUsage::NotUsed; + } return ExprUsage::Used; + } if (nCtor == 1) { const Scope* scope = ftok->variable()->type()->classScope; auto it = std::find_if(scope->functionList.begin(), scope->functionList.end(), [](const Function& f) { diff --git a/lib/token.cpp b/lib/token.cpp index 4d1d2f5890f..c27d8807a63 100644 --- a/lib/token.cpp +++ b/lib/token.cpp @@ -2361,6 +2361,8 @@ const ::Type* Token::typeOf(const Token* tok, const Token** typeTok) return tok->variable()->type(); if (tok->function()) return tok->function()->retType; + if (tok->valueType() && tok->valueType()->typeScope && tok->valueType()->typeScope->definedType) + return tok->valueType()->typeScope->definedType; if (Token::simpleMatch(tok, "return")) { // cppcheck-suppress shadowFunction - TODO: fix this const Scope *scope = tok->scope(); diff --git a/test/testuninitvar.cpp b/test/testuninitvar.cpp index ecb467524c3..e61579f8024 100644 --- a/test/testuninitvar.cpp +++ b/test/testuninitvar.cpp @@ -7776,6 +7776,14 @@ class TestUninitVar : public TestFixture { " return (&s)->y;\n" "}\n"); ASSERT_EQUALS("[test.cpp:5:16]: (error) Uninitialized variable: s.y [uninitvar]\n", errout_str()); + + valueFlowUninit("struct S { int* p; };\n" // #14640 + "void f() {\n" + " int x;\n" + " S s{ &x };\n" + " *s.p = 0;\n" + "}\n"); + ASSERT_EQUALS("", errout_str()); } void valueFlowUninitForLoop()