From 63e30d1b8cc598571b1b81e8343de3f63224d493 Mon Sep 17 00:00:00 2001 From: gerboengels Date: Sun, 18 Dec 2022 16:46:04 +0100 Subject: [PATCH] Fix syntaxError on lambda inside decltype (#4650) Use case where it gave an issue: using customComparator = decltype([] (const X& lhs, const X& rhs) { return lhs.CompareTo(rhs); }); std::map m; Co-authored-by: Gerbo Engels --- lib/symboldatabase.cpp | 8 ++++++-- lib/symboldatabase.h | 8 ++++++-- test/testsymboldatabase.cpp | 10 ++++++++++ 3 files changed, 22 insertions(+), 4 deletions(-) diff --git a/lib/symboldatabase.cpp b/lib/symboldatabase.cpp index bd18cf24e..ef3811dbb 100644 --- a/lib/symboldatabase.cpp +++ b/lib/symboldatabase.cpp @@ -387,8 +387,12 @@ void SymbolDatabase::createSymbolDatabaseFindAllScopes() tok = tok->tokAt(3); - while (tok && tok->str() != ";") - tok = tok->next(); + while (tok && tok->str() != ";") { + if (Token::simpleMatch(tok, "decltype (")) + tok = tok->linkAt(1); + else + tok = tok->next(); + } } // unnamed struct and union diff --git a/lib/symboldatabase.h b/lib/symboldatabase.h index 6d0a0fa3d..5626c362e 100644 --- a/lib/symboldatabase.h +++ b/lib/symboldatabase.h @@ -122,8 +122,12 @@ public: else if (classDef_ && classDef_->str() == "using") { typeStart = classDef->tokAt(3); typeEnd = typeStart; - while (typeEnd->next() && typeEnd->next()->str() != ";") - typeEnd = typeEnd->next(); + while (typeEnd->next() && typeEnd->next()->str() != ";") { + if (Token::simpleMatch(typeEnd, "decltype (")) + typeEnd = typeEnd->linkAt(1); + else + typeEnd = typeEnd->next(); + } } } diff --git a/test/testsymboldatabase.cpp b/test/testsymboldatabase.cpp index 003a9dcca..49abc9317 100644 --- a/test/testsymboldatabase.cpp +++ b/test/testsymboldatabase.cpp @@ -366,6 +366,7 @@ private: TEST_CASE(symboldatabase100); // #10174 TEST_CASE(symboldatabase101); TEST_CASE(symboldatabase102); + TEST_CASE(symboldatabase103); TEST_CASE(createSymbolDatabaseFindAllScopes1); TEST_CASE(createSymbolDatabaseFindAllScopes2); @@ -5060,6 +5061,15 @@ private: ASSERT(db->scopeList.back().className == "g"); } + void symboldatabase103() { + GET_SYMBOL_DB("void f() {\n" + "using lambda = decltype([]() { return true; });\n" + "lambda{}();\n" + "}\n"); + ASSERT(db != nullptr); + ASSERT_EQUALS("", errout.str()); + } + void createSymbolDatabaseFindAllScopes1() { GET_SYMBOL_DB("void f() { union {int x; char *p;} a={0}; }"); ASSERT(db->scopeList.size() == 3);