Fix #11533 Infinite recursion in typeDecl() (#4767)

This commit is contained in:
chrchr-github 2023-02-07 22:02:59 +01:00 committed by GitHub
parent 4d9caa99f3
commit c3225781f3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 30 additions and 4 deletions

View File

@ -1319,9 +1319,19 @@ void SymbolDatabase::createSymbolDatabaseSetVariablePointers()
const ValueType* vt = tok->astParent()->astOperand1()->valueType(); const ValueType* vt = tok->astParent()->astOperand1()->valueType();
const Library::Container* cont = vt->container; const Library::Container* cont = vt->container;
auto it = cont->functions.find(tok->str()); auto it = cont->functions.find(tok->str());
if (it != cont->functions.end() && isContainerYieldElement(it->second.yield) && vt->containerTypeToken && vt->containerTypeToken->scope()) { if (it != cont->functions.end() && isContainerYieldElement(it->second.yield) && vt->containerTypeToken) {
Token* memberTok = tok->next()->link()->tokAt(2); Token* memberTok = tok->next()->link()->tokAt(2);
setMemberVar(vt->containerTypeToken->scope()->getVariable(memberTok->str()), memberTok, vt->containerTypeToken); const Scope* scope = vt->containerTypeToken->scope();
const Type* contType{};
const std::string typeStr = vt->containerTypeToken->expressionString();
while (scope && !contType) {
contType = scope->findType(typeStr); // find the type stored in the container
scope = scope->nestedIn;
}
if (contType && contType->classScope) {
const Variable* membervar = contType->classScope->getVariable(memberTok->str());
setMemberVar(membervar, memberTok, vt->containerTypeToken);
}
} }
} }
} }

View File

@ -2004,12 +2004,12 @@ private:
ASSERT_EQUALS(expected, tokenize(code, "test.cpp")); ASSERT_EQUALS(expected, tokenize(code, "test.cpp"));
} }
void varid_in_class25() { // #11497 void varid_in_class25() {
const char *code{}, *expected{}; const char *code{}, *expected{};
Settings oldSettings = settings; Settings oldSettings = settings;
LOAD_LIB_2(settings.library, "std.cfg"); LOAD_LIB_2(settings.library, "std.cfg");
code = "struct F {\n" code = "struct F {\n" // #11497
" int i;\n" " int i;\n"
" void f(const std::vector<F>&v) {\n" " void f(const std::vector<F>&v) {\n"
" if (v.front().i) {}\n" " if (v.front().i) {}\n"
@ -2022,6 +2022,22 @@ private:
"5: }\n" "5: }\n"
"6: } ;\n"; "6: } ;\n";
ASSERT_EQUALS(expected, tokenize(code, "test.cpp")); ASSERT_EQUALS(expected, tokenize(code, "test.cpp"));
code = "struct T { };\n" // 11533
"struct U { T t; };\n"
"std::vector<U*>* g();\n"
"void f() {\n"
" std::vector<U*>* p = g();\n"
" auto t = p->front()->t;\n"
"}\n";
expected = "1: struct T { } ;\n"
"2: struct U { T t@1 ; } ;\n"
"3: std :: vector < U * > * g ( ) ;\n"
"4: void f ( ) {\n"
"5: std :: vector < U * > * p@2 ; p@2 = g ( ) ;\n"
"6: auto t@3 ; t@3 = p@2 . front ( ) . t@4 ;\n"
"7: }\n";
ASSERT_EQUALS(expected, tokenize(code, "test.cpp"));
settings = oldSettings; settings = oldSettings;
} }