Skip to content

Commit 09189b8

Browse files
Fix #12338 "Analysis failed (lambda not recognized)" with trailing type in lambda parameter (danmar#5869)
1 parent 14e540a commit 09189b8

File tree

2 files changed

+45
-9
lines changed

2 files changed

+45
-9
lines changed

lib/tokenlist.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1373,6 +1373,15 @@ const Token* findLambdaEndTokenWithoutAST(const Token* tok) {
13731373
tok = tok->link()->next();
13741374
if (Token::simpleMatch(tok, "(") && tok->link())
13751375
tok = tok->link()->next();
1376+
if (Token::simpleMatch(tok, ".")) { // trailing return type
1377+
tok = tok->next();
1378+
while (Token::Match(tok, "%type%|%name%|::|&|&&|*|<|(")) {
1379+
if (tok->link())
1380+
tok = tok->link()->next();
1381+
else
1382+
tok = tok->next();
1383+
}
1384+
}
13761385
if (!(Token::simpleMatch(tok, "{") && tok->link()))
13771386
return nullptr;
13781387
return tok->link()->next();

test/testsymboldatabase.cpp

Lines changed: 36 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2814,15 +2814,42 @@ class TestSymbolDatabase : public TestFixture {
28142814
ASSERT_EQUALS(3, func->argCount());
28152815
}
28162816

2817-
void functionArgs20() { // #11769
2818-
const char code[] = "void f(void *(*g)(void *) = [](void *p) { return p; }) {}";
2819-
GET_SYMBOL_DB(code);
2820-
ASSERT(db != nullptr);
2821-
const Scope *scope = db->functionScopes.front();
2822-
const Function *func = scope->function;
2823-
ASSERT_EQUALS(1, func->argCount());
2824-
const Variable* arg = func->getArgumentVar(0);
2825-
TODO_ASSERT(arg->hasDefault());
2817+
void functionArgs20() {
2818+
{
2819+
const char code[] = "void f(void *(*g)(void *) = [](void *p) { return p; }) {}"; // #11769
2820+
GET_SYMBOL_DB(code);
2821+
ASSERT(db != nullptr);
2822+
const Scope *scope = db->functionScopes.front();
2823+
const Function *func = scope->function;
2824+
ASSERT_EQUALS(1, func->argCount());
2825+
const Variable* arg = func->getArgumentVar(0);
2826+
TODO_ASSERT(arg->hasDefault());
2827+
}
2828+
{
2829+
const char code[] = "void f() { auto g = [&](const std::function<int(int)>& h = [](int i) -> int { return i; }) {}; }"; // #12338
2830+
GET_SYMBOL_DB(code);
2831+
ASSERT(db != nullptr);
2832+
ASSERT_EQUALS(3, db->scopeList.size());
2833+
ASSERT_EQUALS(Scope::ScopeType::eLambda, db->scopeList.back().type);
2834+
}
2835+
{
2836+
const char code[] = "void f() {\n"
2837+
" auto g = [&](const std::function<const std::vector<int>&(const std::vector<int>&)>& h = [](const std::vector<int>& v) -> const std::vector<int>& { return v; }) {};\n"
2838+
"}\n";
2839+
GET_SYMBOL_DB(code);
2840+
ASSERT(db != nullptr);
2841+
ASSERT_EQUALS(3, db->scopeList.size());
2842+
ASSERT_EQUALS(Scope::ScopeType::eLambda, db->scopeList.back().type);
2843+
}
2844+
{
2845+
const char code[] = "void f() {\n"
2846+
" auto g = [&](const std::function<int(int)>& h = [](int i) -> decltype(0) { return i; }) {};\n"
2847+
"}\n";
2848+
GET_SYMBOL_DB(code);
2849+
ASSERT(db != nullptr);
2850+
ASSERT_EQUALS(3, db->scopeList.size());
2851+
ASSERT_EQUALS(Scope::ScopeType::eLambda, db->scopeList.back().type);
2852+
}
28262853
}
28272854

28282855
void functionArgs21() {

0 commit comments

Comments
 (0)