@@ -963,23 +963,26 @@ void SymbolDatabase::createSymbolDatabaseClassAndStructScopes()
963963 }
964964}
965965
966+ void SymbolDatabase::setFunctionReturnType (Function& function, const Scope& scope) const
967+ {
968+ if (!function.retDef )
969+ return ;
970+ const Token *type = function.retDef ;
971+ while (Token::Match (type, " static|const|struct|union|enum" ))
972+ type = type->next ();
973+ if (type) {
974+ function.retType = findVariableTypeInBase (&scope, type);
975+ if (!function.retType )
976+ function.retType = findTypeInNested (type, function.nestedIn );
977+ }
978+ }
979+
966980void SymbolDatabase::createSymbolDatabaseFunctionReturnTypes ()
967981{
968982 // fill in function return types
969983 for (Scope& scope : scopeList) {
970- for (auto func = scope.functionList .begin (); func != scope.functionList .end (); ++func) {
971- // add return types
972- if (func->retDef ) {
973- const Token *type = func->retDef ;
974- while (Token::Match (type, " static|const|struct|union|enum" ))
975- type = type->next ();
976- if (type) {
977- func->retType = findVariableTypeInBase (&scope, type);
978- if (!func->retType )
979- func->retType = findTypeInNested (type, func->nestedIn );
980- }
981- }
982- }
984+ for (Function& function : scope.functionList )
985+ setFunctionReturnType (function, scope);
983986 }
984987}
985988
@@ -1084,69 +1087,79 @@ void SymbolDatabase::createSymbolDatabaseNeedInitialization()
10841087 }
10851088}
10861089
1087- void SymbolDatabase::createSymbolDatabaseVariableSymbolTable ( )
1090+ void SymbolDatabase::addVariablesToSymbolTable (Scope& scope )
10881091{
1089- // create variable symbol table
1090- mVariableList .resize (mTokenizer .varIdCount () + 1 );
1091- std::fill_n (mVariableList .begin (), mVariableList .size (), nullptr );
1092+ for (Variable& var: scope.varlist ) {
1093+ const int varId = var.declarationId ();
1094+ if (varId)
1095+ mVariableList [varId] = &var;
1096+ // fix up variables without type
1097+ if (!var.type () && !var.typeStartToken ()->isStandardType ()) {
1098+ const Type *type = findType (var.typeStartToken (), &scope);
1099+ if (type)
1100+ var.type (type);
1101+ }
1102+ }
1103+ }
10921104
1093- // check all scopes for variables
1094- for (Scope& scope : scopeList) {
1095- // add all variables
1096- for (Variable& var: scope. varlist ) {
1097- const int varId = var .declarationId ();
1098- if (varId)
1099- mVariableList [varId ] = &var ;
1100- // fix up variables without type
1101- if (!var .type () && !var .typeStartToken ()->isStandardType ()) {
1102- const Type *type = findType (var .typeStartToken (), &scope);
1105+ void SymbolDatabase::addArgumentsToSymbolTable (Function& function, const Scope& scope)
1106+ {
1107+ for (Variable& arg: function. argumentList ) {
1108+ // check for named parameters
1109+ if (arg. nameToken () && arg .declarationId ()) {
1110+ const int declarationId = arg. declarationId ();
1111+ mVariableList [declarationId ] = &arg ;
1112+ // fix up parameters without type
1113+ if (!arg .type () && !arg .typeStartToken ()->isStandardType ()) {
1114+ const Type *type = findTypeInNested (arg .typeStartToken (), &scope);
11031115 if (type)
1104- var .type (type);
1116+ arg .type (type);
11051117 }
11061118 }
1119+ }
1120+ }
11071121
1108- // add all function parameters
1109- for (Function& func : scope.functionList ) {
1110- for (Variable& arg: func.argumentList ) {
1111- // check for named parameters
1112- if (arg.nameToken () && arg.declarationId ()) {
1113- const int declarationId = arg.declarationId ();
1114- mVariableList [declarationId] = &arg;
1115- // fix up parameters without type
1116- if (!arg.type () && !arg.typeStartToken ()->isStandardType ()) {
1117- const Type *type = findTypeInNested (arg.typeStartToken (), &scope);
1118- if (type)
1119- arg.type (type);
1120- }
1122+ void SymbolDatabase::fillMissingVariables (const Scope& functionScope)
1123+ {
1124+ for (const Token *tok = functionScope.bodyStart ->next (); tok && tok != functionScope.bodyEnd ; tok = tok->next ()) {
1125+ // check for member variable
1126+ if (!Token::Match (tok, " %var% .|[" ))
1127+ continue ;
1128+ const Token* tokDot = tok->next ();
1129+ while (Token::simpleMatch (tokDot, " [" ))
1130+ tokDot = tokDot->link ()->next ();
1131+ if (!Token::Match (tokDot, " . %var%" ))
1132+ continue ;
1133+ const Token *member = tokDot->next ();
1134+ if (mVariableList [member->varId ()] == nullptr ) {
1135+ const Variable *var1 = mVariableList [tok->varId ()];
1136+ if (var1 && var1->typeScope ()) {
1137+ const Variable* memberVar = var1->typeScope ()->getVariable (member->str ());
1138+ if (memberVar) {
1139+ // add this variable to the look up table
1140+ mVariableList [member->varId ()] = memberVar;
11211141 }
11221142 }
11231143 }
11241144 }
1145+ }
11251146
1126- // fill in missing variables if possible
1127- for (const Scope *func: functionScopes) {
1128- for (const Token *tok = func->bodyStart ->next (); tok && tok != func->bodyEnd ; tok = tok->next ()) {
1129- // check for member variable
1130- if (!Token::Match (tok, " %var% .|[" ))
1131- continue ;
1132- const Token* tokDot = tok->next ();
1133- while (Token::simpleMatch (tokDot, " [" ))
1134- tokDot = tokDot->link ()->next ();
1135- if (!Token::Match (tokDot, " . %var%" ))
1136- continue ;
1137- const Token *member = tokDot->next ();
1138- if (mVariableList [member->varId ()] == nullptr ) {
1139- const Variable *var1 = mVariableList [tok->varId ()];
1140- if (var1 && var1->typeScope ()) {
1141- const Variable* memberVar = var1->typeScope ()->getVariable (member->str ());
1142- if (memberVar) {
1143- // add this variable to the look up table
1144- mVariableList [member->varId ()] = memberVar;
1145- }
1146- }
1147- }
1148- }
1147+ void SymbolDatabase::createSymbolDatabaseVariableSymbolTable ()
1148+ {
1149+ // create variable symbol table
1150+ mVariableList .resize (mTokenizer .varIdCount () + 1 );
1151+ std::fill_n (mVariableList .begin (), mVariableList .size (), nullptr );
1152+
1153+ // check all scopes for variables and function parameters
1154+ for (Scope& scope : scopeList) {
1155+ addVariablesToSymbolTable (scope);
1156+ for (Function& function : scope.functionList )
1157+ addArgumentsToSymbolTable (function, scope);
11491158 }
1159+
1160+ // fill in missing variables if possible
1161+ for (const Scope *func: functionScopes)
1162+ fillMissingVariables (*func);
11501163}
11511164
11521165void SymbolDatabase::createSymbolDatabaseSetScopePointers ()
@@ -1498,6 +1511,10 @@ void SymbolDatabase::createSymbolDatabaseEnums()
14981511
14991512 // find enumerators
15001513 for (Token* tok = mTokenizer .list .front (); tok != mTokenizer .list .back (); tok = tok->next ()) {
1514+ // an eEnumerator token without an enumerator is a copy that the template
1515+ // simplifier made of an already resolved token - resolve it again
1516+ if (tok->tokType () == Token::eEnumerator && !tok->enumerator ())
1517+ tok->tokType (Token::eName);
15011518 const bool isVariable = (tok->tokType () == Token::eVariable && !tok->variable ());
15021519 if (tok->tokType () != Token::eName && !isVariable)
15031520 continue ;
@@ -1856,29 +1873,19 @@ void SymbolDatabase::createSymbolDatabaseExprIds()
18561873 }
18571874}
18581875
1859- void SymbolDatabase::removeSymbolsInTokenRanges (const std::vector<std::pair<Token*, const Token*>>& ranges )
1876+ void SymbolDatabase::removeSymbolsForTokens (const std::unordered_set< const Token*>& removedTokens )
18601877{
1861- if (ranges .empty ())
1878+ if (removedTokens .empty ())
18621879 return ;
18631880
1864- // all tokens that are going to be removed
1865- std::set<const Token*> removedTokens;
1866- for (const auto & range : ranges) {
1867- for (const Token* tok = range.first ; tok; tok = tok->next ()) {
1868- removedTokens.insert (tok);
1869- if (tok == range.second )
1870- break ;
1871- }
1872- }
1873-
18741881 // the scopes, functions, variables, types and enumerators declared by those tokens
1875- std::set <const Scope*> removedScopes;
1882+ std::unordered_set <const Scope*> removedScopes;
18761883 for (const Scope& scope : scopeList) {
18771884 if ((scope.classDef && removedTokens.count (scope.classDef ) != 0 ) ||
18781885 (scope.bodyStart && removedTokens.count (scope.bodyStart ) != 0 ))
18791886 removedScopes.insert (&scope);
18801887 }
1881- std::set <const Function*> removedFunctions;
1888+ std::unordered_set <const Function*> removedFunctions;
18821889 for (Scope& scope : scopeList) {
18831890 for (Function& function : scope.functionList ) {
18841891 if (function.tokenDef && removedTokens.count (function.tokenDef ) != 0 )
@@ -1892,7 +1899,7 @@ void SymbolDatabase::removeSymbolsInTokenRanges(const std::vector<std::pair<Toke
18921899 }
18931900 }
18941901 }
1895- std::set <const Variable*> removedVariables;
1902+ std::unordered_set <const Variable*> removedVariables;
18961903 for (const Scope* scope : removedScopes) {
18971904 std::transform (scope->varlist .cbegin (), scope->varlist .cend (), std::inserter (removedVariables, removedVariables.end ()), [](const Variable& var) {
18981905 return &var;
@@ -1903,12 +1910,12 @@ void SymbolDatabase::removeSymbolsInTokenRanges(const std::vector<std::pair<Toke
19031910 return &arg;
19041911 });
19051912 }
1906- std::set <const Type*> removedTypes;
1913+ std::unordered_set <const Type*> removedTypes;
19071914 for (const Type& type : typeList) {
19081915 if (type.classDef && removedTokens.count (type.classDef ) != 0 )
19091916 removedTypes.insert (&type);
19101917 }
1911- std::set <const Enumerator*> removedEnumerators;
1918+ std::unordered_set <const Enumerator*> removedEnumerators;
19121919 for (const Scope* scope : removedScopes) {
19131920 std::transform (scope->enumeratorList .cbegin (), scope->enumeratorList .cend (), std::inserter (removedEnumerators, removedEnumerators.end ()), [](const Enumerator& enumerator) {
19141921 return &enumerator;
@@ -1985,7 +1992,7 @@ void SymbolDatabase::addSymbolsForNewTokenRanges(const std::vector<std::pair<Tok
19851992 const std::size_t oldScopeCount = scopeList.size ();
19861993
19871994 // all new tokens - the new functions are found through them afterwards
1988- std::set <const Token*> newTokens;
1995+ std::unordered_set <const Token*> newTokens;
19891996 for (const auto & range : newRanges) {
19901997 for (const Token* tok = range.first ; tok; tok = tok->next ()) {
19911998 newTokens.insert (tok);
@@ -2032,16 +2039,7 @@ void SymbolDatabase::addSymbolsForNewTokenRanges(const std::vector<std::pair<Tok
20322039 for (const auto & f : newFunctions) {
20332040 if (f.first ->argumentList .empty ())
20342041 f.first ->addArguments (f.second );
2035- if (f.first ->retDef ) {
2036- const Token *type = f.first ->retDef ;
2037- while (Token::Match (type, " static|const|struct|union|enum" ))
2038- type = type->next ();
2039- if (type) {
2040- f.first ->retType = findVariableTypeInBase (f.second , type);
2041- if (!f.first ->retType )
2042- f.first ->retType = findTypeInNested (type, f.first ->nestedIn );
2043- }
2044- }
2042+ setFunctionReturnType (*f.first , *f.second );
20452043 }
20462044
20472045 // fast access vectors
@@ -2055,57 +2053,14 @@ void SymbolDatabase::addSymbolsForNewTokenRanges(const std::vector<std::pair<Tok
20552053 // variable symbol table: add the new variables (incremental version of
20562054 // createSymbolDatabaseVariableSymbolTable)
20572055 mVariableList .resize (mTokenizer .varIdCount () + 1 );
2058- for (Scope* scope : newScopes) {
2059- for (Variable& var : scope->varlist ) {
2060- const int varId = var.declarationId ();
2061- if (varId)
2062- mVariableList [varId] = &var;
2063- // fix up variables without type
2064- if (!var.type () && !var.typeStartToken ()->isStandardType ()) {
2065- const Type *type = findType (var.typeStartToken (), scope);
2066- if (type)
2067- var.type (type);
2068- }
2069- }
2070- }
2071- for (const auto & f : newFunctions) {
2072- for (Variable& arg : f.first ->argumentList ) {
2073- if (arg.nameToken () && arg.declarationId ()) {
2074- mVariableList [arg.declarationId ()] = &arg;
2075- // fix up parameters without type
2076- if (!arg.type () && !arg.typeStartToken ()->isStandardType ()) {
2077- const Type *type = findTypeInNested (arg.typeStartToken (), f.second );
2078- if (type)
2079- arg.type (type);
2080- }
2081- }
2082- }
2083- }
2056+ for (Scope* scope : newScopes)
2057+ addVariablesToSymbolTable (*scope);
2058+ for (const auto & f : newFunctions)
2059+ addArgumentsToSymbolTable (*f.first , *f.second );
20842060 // fill in missing variables in the new code if possible
2085- for (const Scope* func : newScopes) {
2086- if (func->type != ScopeType::eFunction)
2087- continue ;
2088- for (const Token *tok = func->bodyStart ->next (); tok && tok != func->bodyEnd ; tok = tok->next ()) {
2089- // check for member variable
2090- if (!Token::Match (tok, " %var% .|[" ))
2091- continue ;
2092- const Token* tokDot = tok->next ();
2093- while (Token::simpleMatch (tokDot, " [" ))
2094- tokDot = tokDot->link ()->next ();
2095- if (!Token::Match (tokDot, " . %var%" ))
2096- continue ;
2097- const Token *member = tokDot->next ();
2098- if (mVariableList [member->varId ()] == nullptr ) {
2099- const Variable *var1 = mVariableList [tok->varId ()];
2100- if (var1 && var1->typeScope ()) {
2101- const Variable* memberVar = var1->typeScope ()->getVariable (member->str ());
2102- if (memberVar) {
2103- // add this variable to the look up table
2104- mVariableList [member->varId ()] = memberVar;
2105- }
2106- }
2107- }
2108- }
2061+ for (const Scope* scope : newScopes) {
2062+ if (scope->type == ScopeType::eFunction)
2063+ fillMissingVariables (*scope);
21092064 }
21102065
21112066 // set the definition and declaration pointers of the new functions. The call
0 commit comments