symbol database: add support for anonymous struct and union

This commit is contained in:
Robert Reif 2011-03-31 20:54:23 -04:00
parent a39444a40f
commit 64fa7bf8d4
1 changed files with 44 additions and 6 deletions

View File

@ -139,9 +139,36 @@ SymbolDatabase::SymbolDatabase(const Tokenizer *tokenizer, const Settings *setti
tok = tok2; tok = tok2;
} }
// anonymous struct and union
else if (Token::Match(tok, "struct|union {") &&
Token::simpleMatch(tok->next()->link(), "} ;"))
{
scopeList.push_back(Scope(this, tok, scope));
Scope *new_scope = &scopeList.back();
const Token *tok2 = tok->next();
new_scope->classStart = tok2;
new_scope->classEnd = tok2->link();
// make sure we have valid code
if (!new_scope->classEnd)
{
scopeList.pop_back();
break;
}
// make the new scope the current scope
scope = &scopeList.back();
scope->nestedIn->nestedList.push_back(scope);
tok = tok2;
}
else else
{ {
// check for end of space // check for end of scope
if (tok == scope->classEnd) if (tok == scope->classEnd)
{ {
scope = scope->nestedIn; scope = scope->nestedIn;
@ -925,7 +952,7 @@ void SymbolDatabase::addFunction(Scope **scope, const Token **tok, const Token *
bool match = false; bool match = false;
if (scope1->className == tok1->str() && (scope1->type != Scope::eFunction)) if (scope1->className == tok1->str() && (scope1->type != Scope::eFunction))
{ {
// do the spaces match (same space) or do their names match (multiple namespaces) // do the scopes match (same scope) or do their names match (multiple namespaces)
if ((*scope == scope1->nestedIn) || (*scope && scope1 && if ((*scope == scope1->nestedIn) || (*scope && scope1 &&
(*scope)->className == scope1->nestedIn->className && (*scope)->className == scope1->nestedIn->className &&
!(*scope)->className.empty() && !(*scope)->className.empty() &&
@ -1331,7 +1358,7 @@ Scope::Scope(SymbolDatabase *check_, const Token *classDef_, Scope *nestedIn_) :
else if (classDef->str() == "struct") else if (classDef->str() == "struct")
{ {
type = Scope::eStruct; type = Scope::eStruct;
// unnamed structs don't have a name // anonymous and unnamed structs don't have a name
if (classDef->next()->str() != "{") if (classDef->next()->str() != "{")
className = classDef->next()->str(); className = classDef->next()->str();
access = Public; access = Public;
@ -1339,7 +1366,7 @@ Scope::Scope(SymbolDatabase *check_, const Token *classDef_, Scope *nestedIn_) :
else if (classDef->str() == "union") else if (classDef->str() == "union")
{ {
type = Scope::eUnion; type = Scope::eUnion;
// unnamed unions don't have a name // anonymous and unnamed unions don't have a name
if (classDef->next()->str() != "{") if (classDef->next()->str() != "{")
className = classDef->next()->str(); className = classDef->next()->str();
access = Public; access = Public;
@ -1400,6 +1427,7 @@ void Scope::getVariableList()
{ {
AccessControl varaccess = defaultAccess(); AccessControl varaccess = defaultAccess();
const Token *start; const Token *start;
int level = 1;
if (classStart) if (classStart)
start = classStart->next(); start = classStart->next();
@ -1408,9 +1436,13 @@ void Scope::getVariableList()
for (const Token *tok = start; tok; tok = tok->next()) for (const Token *tok = start; tok; tok = tok->next())
{ {
// end of space? // end of scope?
if (tok->str() == "}") if (tok->str() == "}")
break; {
level--;
if (level == 0)
break;
}
// syntax error? // syntax error?
else if (tok->next() == NULL) else if (tok->next() == NULL)
@ -1446,6 +1478,12 @@ void Scope::getVariableList()
tok = tok->next()->link()->next()->next(); tok = tok->next()->link()->next()->next();
continue; continue;
} }
else if (Token::Match(tok, "struct|union {") && Token::Match(tok->next()->link(), "} ;"))
{
level++;
tok = tok->next();
continue;
}
// Borland C++: Skip all variables in the __published section. // Borland C++: Skip all variables in the __published section.
// These are automatically initialized. // These are automatically initialized.