Skip to content

Commit d98efaf

Browse files
Fix #12538 valueFlowBailoutIncompleteVar with nested enum (#6220)
1 parent f722f08 commit d98efaf

2 files changed

Lines changed: 41 additions & 1 deletion

File tree

lib/symboldatabase.cpp

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5209,6 +5209,21 @@ const Token * Scope::addEnum(const Token * tok)
52095209
return tok2;
52105210
}
52115211

5212+
static const Scope* findEnumScopeInBase(const Scope* scope, const std::string& tokStr)
5213+
{
5214+
if (scope->definedType) {
5215+
const std::vector<Type::BaseInfo>& derivedFrom = scope->definedType->derivedFrom;
5216+
for (const Type::BaseInfo& i : derivedFrom) {
5217+
const Type *derivedFromType = i.type;
5218+
if (derivedFromType && derivedFromType->classScope) {
5219+
if (const Scope* enumScope = derivedFromType->classScope->findRecordInNestedList(tokStr))
5220+
return enumScope;
5221+
}
5222+
}
5223+
}
5224+
return nullptr;
5225+
}
5226+
52125227
const Enumerator * SymbolDatabase::findEnumerator(const Token * tok, std::set<std::string>& tokensThatAreNotEnumeratorValues) const
52135228
{
52145229
if (tok->isKeyword())
@@ -5242,6 +5257,8 @@ const Enumerator * SymbolDatabase::findEnumerator(const Token * tok, std::set<st
52425257
temp = scope->nestedIn->findRecordInNestedList(tok1->str());
52435258
if (!temp && scope->functionOf)
52445259
temp = scope->functionOf->findRecordInNestedList(tok1->str());
5260+
if (!temp)
5261+
temp = findEnumScopeInBase(scope, tok1->str());
52455262
if (temp) {
52465263
scope = temp;
52475264
break;

test/testsymboldatabase.cpp

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -447,6 +447,7 @@ class TestSymbolDatabase : public TestFixture {
447447
TEST_CASE(enum13);
448448
TEST_CASE(enum14);
449449
TEST_CASE(enum15);
450+
TEST_CASE(enum16);
450451

451452
TEST_CASE(sizeOfType);
452453

@@ -6220,7 +6221,6 @@ class TestSymbolDatabase : public TestFixture {
62206221
std::advance(it, 2);
62216222
const Enumerator* E0 = it->findEnumerator("E0");
62226223
ASSERT(E0 && E0->value_known && E0->value == 0);
6223-
std::advance(it, 1);
62246224
const Token* const e = Token::findsimplematch(tokenizer.tokens(), "E0 ;");
62256225
ASSERT(e && e->enumerator());
62266226
ASSERT_EQUALS(E0, e->enumerator());
@@ -6289,6 +6289,29 @@ class TestSymbolDatabase : public TestFixture {
62896289
}
62906290
}
62916291

6292+
void enum16() {
6293+
{
6294+
GET_SYMBOL_DB("struct B {\n" // #12538
6295+
" struct S {\n"
6296+
" enum E { E0 = 0 };\n"
6297+
" };\n"
6298+
"};\n"
6299+
"struct D : B {\n"
6300+
" S::E f() const {\n"
6301+
" return S::E0;\n"
6302+
" }\n"
6303+
"};\n");
6304+
ASSERT(db != nullptr);
6305+
auto it = db->scopeList.begin();
6306+
std::advance(it, 3);
6307+
const Enumerator* E0 = it->findEnumerator("E0");
6308+
ASSERT(E0 && E0->value_known && E0->value == 0);
6309+
const Token* const e = Token::findsimplematch(tokenizer.tokens(), "E0 ;");
6310+
ASSERT(e && e->enumerator());
6311+
ASSERT_EQUALS(E0, e->enumerator());
6312+
}
6313+
}
6314+
62926315
void sizeOfType() {
62936316
// #7615 - crash in Symboldatabase::sizeOfType()
62946317
GET_SYMBOL_DB("enum e;\n"

0 commit comments

Comments
 (0)