Ejemplo n.º 1
0
void visitorTraversal::visit(SgNode* n)
   {
     SgGlobal* globalScope = isSgGlobal(n);
     if (globalScope != NULL)
        {
          printf ("Looking for \"x\" in the global symbol table ... \n");
          SgSymbol* symbol = globalScope->lookup_var_symbol("x");
          ROSE_ASSERT(symbol != NULL);

       // Iterate through the symbol table
          SgSymbolTable::BaseHashType* hashTable = globalScope->get_symbol_table()->get_table();
          SgSymbolTable::hash_iterator i = hashTable->begin();
          while (i != hashTable->end())
             {
               printf ("hash tabel entry: i->first = %s \n",i->first.str());
               i++;
             }
        }
#if 0
     SgScopeStatement* scope = isSgScopeStatement(n);
     if (scope != NULL)
        {
          printf ("Looking for \"x\" in the global symbol table ... \n");
          SgSymbol* symbol = globalScope->lookup_var_symbol("x");
          ROSE_ASSERT(symbol != NULL);
        }
#endif
   }
Ejemplo n.º 2
0
void
FixupAstSymbolTables::visit ( SgNode* node )
   {
  // DQ (6/27/2005): Output the local symbol table from each scope.
  // printf ("node = %s \n",node->sage_class_name());

     SgScopeStatement* scope = isSgScopeStatement(node);
     if (scope != NULL)
        {
#if 0
          printf ("AST Fixup: Fixup Symbol Table for %p = %s at: \n",scope,scope->class_name().c_str());
#endif
          SgSymbolTable* symbolTable = scope->get_symbol_table();
          if (symbolTable == NULL)
             {
#if 0
               printf ("AST Fixup: Fixup Symbol Table for %p = %s at: \n",scope,scope->class_name().c_str());
               scope->get_file_info()->display("Symbol Table Location");
#endif
               SgSymbolTable* tempSymbolTable = new SgSymbolTable();
               ROSE_ASSERT(tempSymbolTable != NULL);

            // name this table as compiler generated! The name is a static member used to store 
            // state for the next_symbol() functions. It is meaningless to set these.
            // tempSymbolTable->set_name("compiler-generated symbol table");

               scope->set_symbol_table(tempSymbolTable);

            // reset the symbolTable using the get_symbol_table() member function
               symbolTable = scope->get_symbol_table();
               ROSE_ASSERT(symbolTable != NULL);

            // DQ (2/16/2006): Set this parent directly (now tested)
               symbolTable->set_parent(scope);
               ROSE_ASSERT(symbolTable->get_parent() != NULL);
             }
          ROSE_ASSERT(symbolTable != NULL);

          if (symbolTable->get_parent() == NULL)
             {
               printf ("Warning: Fixing up symbolTable, calling symbolTable->set_parent() (parent not previously set) \n");
               symbolTable->set_parent(scope);
             }
          ROSE_ASSERT(symbolTable->get_parent() != NULL);

       // Make sure that the internal hash table used in the symbol table is also present!
          if (symbolTable->get_table() == NULL)
             {
            // DQ (6/27/2005): There are a lot of these built, perhaps more than we really need!
#if 0
               printf ("AST Fixup: Building internal Symbol Table hash table (rose_hash_multimap) for %p = %s at: \n",
                    scope,scope->sage_class_name());
               scope->get_file_info()->display("Symbol Table Location");
#endif
               rose_hash_multimap* internalHashTable = new rose_hash_multimap();
               ROSE_ASSERT(internalHashTable != NULL);
               symbolTable->set_table(internalHashTable);
             }
          ROSE_ASSERT(symbolTable->get_table() != NULL);

          SgSymbolTable::BaseHashType* internalTable = symbolTable->get_table();
          ROSE_ASSERT(internalTable != NULL);


       // DQ (6/23/2011): Note: Declarations that reference types that have not been seen yet may be placed into the 
       // wronge scope, then later when we see the correct scope we have a symbol in two or more symbol tables.  The 
       // code below detects and fixes this problem.

       // DQ (6/16/2011): List of symbols we need to remove from symbol tables where they are multibily represented.
          std::vector<SgSymbol*> listOfSymbolsToRemove;

       // DQ (6/12/2011): Fixup symbol table by removing symbols that are not associated with a declaration in the current scope.
          int idx = 0;
          SgSymbolTable::hash_iterator i = internalTable->begin();
          while (i != internalTable->end())
             {
            // DQ: removed SgName casting operator to char*
            // cout << "[" << idx << "] " << (*i).first.str();
               ROSE_ASSERT ( (*i).first.str() != NULL );
               ROSE_ASSERT ( isSgSymbol( (*i).second ) != NULL );

            // printf ("Symbol number: %d (pair.first (SgName) = %s) pair.second (SgSymbol) sage_class_name() = %s \n",
            //      idx,(*i).first.str(),(*i).second->sage_class_name());

               SgSymbol* symbol = isSgSymbol((*i).second);
               ROSE_ASSERT ( symbol != NULL );

            // We have to look at each type of symbol separately!  This is because there is no virtual function,
            // the reason for this is that each get_declaration() function returns a different type!
            // ROSE_ASSERT ( symbol->get_declaration() != NULL );
               switch(symbol->variantT())
                  {
                    case V_SgClassSymbol:
                       {
                         SgClassSymbol* classSymbol = isSgClassSymbol(symbol);
                         ROSE_ASSERT(classSymbol != NULL);
                         ROSE_ASSERT(classSymbol->get_declaration() != NULL);

                         SgDeclarationStatement* declarationToFindInScope = NULL;

                      // Search for the declaration in the associated scope.
                         declarationToFindInScope = classSymbol->get_declaration();
                         ROSE_ASSERT(declarationToFindInScope != NULL);

                         SgClassDeclaration* classDeclaration = isSgClassDeclaration(declarationToFindInScope);
                         ROSE_ASSERT(classDeclaration != NULL);

                         SgName name = classDeclaration->get_name();

                      // SgType* declarationType = declarationToFindInScope->get_type();
                         SgType* declarationType = classDeclaration->get_type();
                         ROSE_ASSERT(declarationType != NULL);

                         if (declarationToFindInScope->get_definingDeclaration() != NULL)
                            {
                              declarationToFindInScope = declarationToFindInScope->get_definingDeclaration();
                              SgClassDeclaration* definingClassDeclaration = isSgClassDeclaration(declarationToFindInScope);
                              ROSE_ASSERT(definingClassDeclaration != NULL);

                           // SgType* definingDeclarationType = declarationToFindInScope->get_type();
                              SgType* definingDeclarationType = definingClassDeclaration->get_type();
                              ROSE_ASSERT(definingDeclarationType != NULL);

                           // DQ (6/22/2011): This assertion fails for CompileTests/copyAST_tests/copytest2007_24.C
                           // A simple rule that all declarations should follow (now that we have proper global type tables).
                           // ROSE_ASSERT(definingDeclarationType == declarationType);
                              if (definingDeclarationType != declarationType)
                                 {
                                   printf ("In fixupSymbolTables.C: Note that definingDeclarationType != declarationType \n");
                                 }
                            }

                         SgNamedType* namedType = isSgNamedType(declarationType);
                         ROSE_ASSERT(namedType != NULL);

                         SgDeclarationStatement* declarationAssociatedToType = namedType->get_declaration();
                         ROSE_ASSERT(declarationAssociatedToType != NULL);
#if 0
                         printf ("Found a symbol without a matching declaration in the current scope (declList): declarationToFindInScope = %p = %s \n",declarationToFindInScope,declarationToFindInScope->class_name().c_str());
                         printf ("Symbol number: %d (pair.first (SgName) = %s) pair.second (SgSymbol) class_name() = %s \n",idx,(*i).first.str(),(*i).second->class_name().c_str());
#endif
                         SgScopeStatement* scopeOfDeclarationToFindInScope      = declarationToFindInScope->get_scope();
                         SgScopeStatement* scopeOfDeclarationAssociatedWithType = declarationAssociatedToType->get_scope();
#if 0
                         printf ("declarationToFindInScope = %p declarationToFindInScope->get_scope() = %p = %s \n",declarationToFindInScope,declarationToFindInScope->get_scope(),declarationToFindInScope->get_scope()->class_name().c_str());
                         printf ("declarationAssociatedToType = %p declarationAssociatedToType->get_scope() = %p = %s \n",declarationAssociatedToType,declarationAssociatedToType->get_scope(),declarationAssociatedToType->get_scope()->class_name().c_str());
#endif
                         if (scopeOfDeclarationToFindInScope != scopeOfDeclarationAssociatedWithType)
                            {
                           // DQ (6/12/2011): Houston, we have a problem!  The trick is to fix it...
                           // A symbol has been placed into a scope when we could not be certain which scope it should be placed.
                           // We have a default of placing such symbols into the global scope, but it might be better to just have 
                           // a special scope where such symbols could be placed so that we could have them separate from the global 
                           // scope and then fix them up more clearly.

                           // Note that test2011_80.C still fails but the AST is at least correct (I think).
                              SgGlobal* scopeOfDeclarationToFindInScope_GlobalScope      = isSgGlobal(scopeOfDeclarationToFindInScope);
                           // SgGlobal* scopeOfDeclarationAssociatedWithType_GlobalScope = isSgGlobal(scopeOfDeclarationAssociatedWithType);

                              if (scopeOfDeclarationToFindInScope_GlobalScope != NULL)
                                 {
                                // In general which ever scope is the global scope is where the error is...???
                                // This is because when we don't know where to put a symbol (e.g. from a declaration of a pointer) we put it into global scope.
                                // There is even an agrument that this is correct as a default for C/C++, but only if it must exist (see test2011_80.C).
                                // Remove the symbol from the symbol table of the global scope.

                                   printf ("Remove the associated symbol in the current symbol table \n");

                                // DQ (6/22/2011): This assertion fails for CompileTests/copyAST_tests/copytest2007_24.C
                                // ROSE_ASSERT (declarationToFindInScope->get_scope() == declarationAssociatedToType->get_scope());
                                   if (declarationToFindInScope->get_scope() != declarationAssociatedToType->get_scope())
                                        printf ("In fixupSymbolTables.C: Note that declarationToFindInScope->get_scope() != declarationAssociatedToType->get_scope() \n");
                                 }
                                else
                                 {
                                   listOfSymbolsToRemove.push_back(classSymbol);
                                 }
                            }
                      // ROSE_ASSERT (declarationToFindInScope->get_scope() == declarationAssociatedToType->get_scope());

                         break;
                       }

                    default:
                       {
                      // It night be there are are no other types of symbols to consider...

                      // printf ("Ignoring non SgClassSymbols (fixupSymbolTables.C) symbol = %s \n",symbol->class_name().c_str());
                      // ROSE_ASSERT(false);
                       }
                  }

            // Increment iterator!
               i++;

            // Increment counter!
               idx++;
             }

       // DQ (6/18/2011): Now that we are through with the symbol table we can support removal of any 
       // identified problematic symbol without worrying about STL iterator invalidation.
          for (size_t j = 0; j < listOfSymbolsToRemove.size(); j++)
             {
            // Remove these symbols.
               SgSymbol* removeSymbol = listOfSymbolsToRemove[j];
               ROSE_ASSERT(removeSymbol != NULL);
               SgSymbolTable* associatedSymbolTable = isSgSymbolTable(removeSymbol->get_parent());
               ROSE_ASSERT(associatedSymbolTable != NULL);

               ROSE_ASSERT(associatedSymbolTable == symbolTable);

               associatedSymbolTable->remove(removeSymbol);

               printf ("Redundant symbol removed...from symbol table \n");
            // ROSE_ASSERT(false);
             }
#if 0
       // debugging
          symbolTable->print("In FixupAstSymbolTables::visit(): printing out the symbol tables");
#endif
        }
   }
// DQ (8/23/2011): Made this a static function so that I could call it from the Java support.
void
FixupAstSymbolTablesToSupportAliasedSymbols::injectSymbolsFromReferencedScopeIntoCurrentScope ( SgScopeStatement* referencedScope, SgScopeStatement* currentScope, SgNode* causalNode, SgAccessModifier::access_modifier_enum accessLevel )
   {
     ROSE_ASSERT(referencedScope != NULL);
     ROSE_ASSERT(currentScope    != NULL);

#if ALIAS_SYMBOL_DEBUGGING || 0
     printf ("In injectSymbolsFromReferencedScopeIntoCurrentScope(): referencedScope = %p = %s currentScope = %p = %s accessLevel = %d \n",referencedScope,referencedScope->class_name().c_str(),currentScope,currentScope->class_name().c_str(),accessLevel);
#endif

     SgSymbolTable* symbolTable = referencedScope->get_symbol_table();
     ROSE_ASSERT(symbolTable != NULL);
     
#if 0
     printf ("AST Fixup: Building Symbol Table for %p = %s at: \n",scope,scope->sage_class_name());
     referencedScope->get_file_info()->display("Symbol Table Location");
#endif

     SgClassDefinition* classDefinition = isSgClassDefinition(referencedScope);
     if (classDefinition != NULL)
        {
       // If this is a class definition, then we need to make sure that we only for alias symbols for those declarations.
#if ALIAS_SYMBOL_DEBUGGING
          printf ("Injection of symbols from a class definition needs to respect access priviledge (private, protected, public) declarations \n");
#endif
        }

     SgSymbolTable::BaseHashType* internalTable = symbolTable->get_table();
     ROSE_ASSERT(internalTable != NULL);

     int counter = 0;
     SgSymbolTable::hash_iterator i = internalTable->begin();
     while (i != internalTable->end())
        {
       // DQ: removed SgName casting operator to char*
       // cout << "[" << idx << "] " << (*i).first.str();
          ROSE_ASSERT ( (*i).first.str() != NULL );
          ROSE_ASSERT ( isSgSymbol( (*i).second ) != NULL );

#if ALIAS_SYMBOL_DEBUGGING
          printf ("Symbol number: %d (pair.first (SgName) = %s) pair.second (SgSymbol) class_name() = %s \n",counter,(*i).first.str(),(*i).second->class_name().c_str());
#endif
          SgName name      = (*i).first;
          SgSymbol* symbol = (*i).second;

          ROSE_ASSERT ( symbol != NULL );

       // Make sure that this is not a SgLabelSymbol, I think these should not be aliased
       // (if only because I don't think that C++ support name qualification for labels).
          ROSE_ASSERT ( isSgLabelSymbol(symbol) == NULL );

       // DQ (6/22/2011): For now skip the handling of alias symbol from other scopes.
       // ROSE_ASSERT(isSgAliasSymbol(symbol) == NULL);
          if (isSgAliasSymbol(symbol) != NULL)
             {
#if ALIAS_SYMBOL_DEBUGGING
               printf ("WARNING: Not clear if we want to nest SgAliasSymbol inside of SgAliasSymbol \n");
#endif
            // DQ (9/22/2012): We need to avoid building chains of SgAliasSymbol (to simplify the representation in the AST).
               while (isSgAliasSymbol(symbol) != NULL)
                  {
#if ALIAS_SYMBOL_DEBUGGING
                    printf (" --- Iterating to root of alias: symbol = %p = %s \n",symbol,symbol->class_name().c_str());
#endif
                    symbol = isSgAliasSymbol(symbol)->get_alias();
                    ROSE_ASSERT(symbol != NULL);
                  }

#if ALIAS_SYMBOL_DEBUGGING
               printf ("Resolved aliased symbol to root symbol: symbol = %p = %s \n",symbol,symbol->class_name().c_str());
#endif
             }

          SgNode* symbolBasis = symbol->get_symbol_basis();
          ROSE_ASSERT(symbolBasis != NULL);
#if ALIAS_SYMBOL_DEBUGGING
          printf ("symbolBasis = %p = %s \n",symbolBasis,symbolBasis->class_name().c_str());
#endif
       // SgDeclarationStatement* declarationFromSymbol = symbol->get_declaration();
          SgDeclarationStatement* declarationFromSymbol = isSgDeclarationStatement(symbolBasis);

          SgAccessModifier::access_modifier_enum declarationAccessLevel = SgAccessModifier::e_unknown;

       // ROSE_ASSERT(declarationFromSymbol != NULL);
          if (declarationFromSymbol != NULL)
             {
            // DQ (6/22/2011): Can I, or should I, do relational operations on enum values (note that the values are designed to allow this).
               declarationAccessLevel = declarationFromSymbol->get_declarationModifier().get_accessModifier().get_modifier();
             }
            else
             {
               SgInitializedName* initializedNameFromSymbol = isSgInitializedName(symbolBasis);
               ROSE_ASSERT(initializedNameFromSymbol != NULL);

            // DQ (9/8/2014): This fails for test2013_234, 235, 240, 241, 242, 246.C.
            // ROSE_ASSERT(initializedNameFromSymbol->get_declptr() != NULL);
            // declarationAccessLevel = initializedNameFromSymbol->get_declptr()->get_declarationModifier().get_accessModifier().get_modifier();
               if (initializedNameFromSymbol->get_declptr() != NULL)
                  {
                    declarationAccessLevel = initializedNameFromSymbol->get_declptr()->get_declarationModifier().get_accessModifier().get_modifier();
                  }
                 else
                  {
                    mprintf ("WARNING: In injectSymbolsFromReferencedScopeIntoCurrentScope(): initializedNameFromSymbol->get_declptr() == NULL: initializedNameFromSymbol->get_name() = %s \n",initializedNameFromSymbol->get_name().str());
                  }
             }

#if ALIAS_SYMBOL_DEBUGGING || 0
          printf ("declarationAccessLevel = %d accessLevel = %d \n",declarationAccessLevel,accessLevel);
#endif

#if 0
       // DQ (12/23/2015): Is this only supporting the SgBaseClass IR nodes? No, another example is the case of a SgUsingDirectiveStatement.
          ROSE_ASSERT(causalNode != NULL);
          if (isSgBaseClass(causalNode) == NULL)
             {
               printf ("ERROR: This is not a SgBaseClass: causalNode = %p = %s \n",causalNode,causalNode->class_name().c_str());
               ROSE_ASSERT(false);
             }
#endif

       // DQ (12/23/2015): See test2015_140.C for where even private base classes will require representations 
       // of it's symbols in the derived class (to support correct name qualification).
       // if (declarationAccessLevel >= accessLevel)
          if ( (declarationAccessLevel >= accessLevel) || isSgBaseClass(causalNode) != NULL)
             {
            // This declaration is visible, so build an alias.

            // DQ (7/24/2011): Need to make sure that the symbol is not already present in the symbol table 
            // (else injection would be redundant. This is a likely key to the problem we are having with 
            // symbol table explosions for some codes.  This should be refactored to a member function of 
            // the symbol table support.
            // Note that this change improves the performance from 15 minutes to 5 seconds for the outlining example.
               bool alreadyExists = currentScope->symbol_exists(name);
               if (alreadyExists == true)
                  {
                 // Just because the names match is not strong enough.
                 // SgSymbol* symbol currentScope->symbol_exists(name);
                    switch (symbol->variantT())
                       {
                         case V_SgAliasSymbol:
                            {
                           // not clear what to do here...
                           // I think we need more symbol table support for detecting matching symbols.
                           // I think we also need more alias symbol specific query support.
                              break;
                            }

                      // DQ (11/10/2014): Added support for templated typedef symbols.
                         case V_SgTemplateTypedefSymbol:

                         case V_SgEnumSymbol:
                         case V_SgVariableSymbol:
                         case V_SgTemplateClassSymbol:
                         case V_SgClassSymbol:
                         case V_SgTemplateFunctionSymbol:
                         case V_SgTemplateMemberFunctionSymbol:
                         case V_SgFunctionSymbol:
                         case V_SgMemberFunctionSymbol:
                         case V_SgTypedefSymbol:
                         case V_SgEnumFieldSymbol:
                         case V_SgNamespaceSymbol:
                         case V_SgTemplateSymbol:
                         case V_SgLabelSymbol:
                         {
                           // Liao, 10/31/2012. 
                           // Using lookup_function_symbol () etc. is not good enough since it returns the first match only.
                           // There might be multiple hits. We have to go through them all instead of checking only the first hit
                              alreadyExists = false; // reset to be false
                             // using less expensive equal_range(), which can be O(logN) instead of O(N)
                              // This matters since this function is called inside another loop with complexity of O(N) already.
                              rose_hash_multimap * internal_table = currentScope->get_symbol_table()->get_table();
                              ROSE_ASSERT (internal_table != NULL);
                              std::pair<rose_hash_multimap::iterator, rose_hash_multimap::iterator> range = internal_table ->equal_range (name);
                              for (rose_hash_multimap::iterator i = range.first; i != range.second; ++i)
                              {
                                SgSymbol * orig_current_symbol = i->second; 
                                ROSE_ASSERT (orig_current_symbol != NULL);
                                // strip off alias symbols
                                SgSymbol * non_alias_symbol = orig_current_symbol; 
                                while (isSgAliasSymbol(non_alias_symbol))
                                {
                                  non_alias_symbol = isSgAliasSymbol(non_alias_symbol) ->get_alias();
                                  ROSE_ASSERT (non_alias_symbol != NULL);
                                }
                                SgNode* associatedDeclaration = i->second->get_symbol_basis();
                                assert(associatedDeclaration != NULL);
                                // same basis and same symbol type
                                // The assumption is that no two symbols can share the same basis declaration TODO double check this!
                                if (associatedDeclaration == symbolBasis && (non_alias_symbol->variantT() == symbol->variantT()))
                                {
                                  alreadyExists = true;
                                  break;
                                }
                              } // end for
                              break;
                           }


#if 0 // uniform handling by code above now
                         case V_SgEnumSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_enum_symbol(name) != NULL);
                              SgEnumSymbol* tmpSymbol = currentScope->lookup_enum_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }

                         case V_SgVariableSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_variable_symbol(name) != NULL);
                              SgVariableSymbol* tmpSymbol = currentScope->lookup_variable_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }

                      // DQ (2/12/2012): Not clear if this is the best way to add this support.
                         case V_SgTemplateClassSymbol:
                         case V_SgClassSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_class_symbol(name) != NULL);
                              SgClassSymbol* tmpSymbol = currentScope->lookup_class_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }
#if 0
                      // DQ (2/12/2012): Added support for SgTemplateFunctionSymbol.
                         case V_SgTemplateFunctionSymbol:
                            {
                              SgTemplateFunctionSymbol* tmpSymbol = currentScope->lookup_template_function_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }

                      // DQ (2/12/2012): Added support for SgTemplateMemberFunctionSymbol.
                         case V_SgTemplateMemberFunctionSymbol:
                            {
                              SgTemplateMemberFunctionSymbol* tmpSymbol = currentScope->lookup_template_member_function_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }
#else
                      // DQ (2/12/2012): Not clear if this is the best way to add this support.
                         case V_SgTemplateFunctionSymbol:
                         case V_SgTemplateMemberFunctionSymbol:
#endif
                         case V_SgFunctionSymbol:
                         case V_SgMemberFunctionSymbol:
                            {
                            // alreadyExists = (currentScope->lookup_function_symbol(name) != NULL);
                              SgFunctionSymbol* tmpSymbol = currentScope->lookup_function_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                             break;
                            }
                         case V_SgTypedefSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_typedef_symbol(name) != NULL);
                              SgTypedefSymbol* tmpSymbol = currentScope->lookup_typedef_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }
                         case V_SgEnumFieldSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_enum_field_symbol(name) != NULL);
                              SgEnumFieldSymbol* tmpSymbol = currentScope->lookup_enum_field_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }

                         case V_SgNamespaceSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_namespace_symbol(name) != NULL);
                              SgNamespaceSymbol* tmpSymbol = currentScope->lookup_namespace_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }

                         case V_SgTemplateSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_template_symbol(name) != NULL);
                              SgTemplateSymbol* tmpSymbol = currentScope->lookup_template_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }

                         case V_SgLabelSymbol:
                            {
                           // alreadyExists = (currentScope->lookup_label_symbol(name) != NULL);
                              SgLabelSymbol* tmpSymbol = currentScope->lookup_label_symbol(name);
                              if (tmpSymbol != NULL)
                                 {
                                   SgNode* tmpSymbolBasis = tmpSymbol->get_symbol_basis();
                                   ROSE_ASSERT(tmpSymbolBasis != NULL);
                                   alreadyExists = (tmpSymbolBasis == symbolBasis);
                                 }
                              break;
                            }

#endif
                         default:
                              printf ("Error: default reached in switch symbol = %p = %s \n",symbol,symbol->class_name().c_str());
                              ROSE_ASSERT(false);
                              break;
                       }
                  }
               
               if ( alreadyExists == false)
                  {
#if 0
                    printf ("Building a SgAliasSymbol \n");
#endif
                 // DQ: The parameter to a SgAliasSymbol is a SgSymbol (but should not be another SgAliasSymbol).
                    SgAliasSymbol* aliasSymbol = new SgAliasSymbol(symbol);
                    ROSE_ASSERT(aliasSymbol != NULL);

                 // DQ (7/12/2014): Added support to trace back the SgAliasSymbol to the declarations that caused it to be added.
                    ROSE_ASSERT(causalNode != NULL);
                    aliasSymbol->get_causal_nodes().push_back(causalNode);

#if ALIAS_SYMBOL_DEBUGGING
                 // printf ("In injectSymbolsFromReferencedScopeIntoCurrentScope(): Adding symbol to new scope as a SgAliasSymbol = %p causalNode = %p = %s \n",aliasSymbol,causalNode,causalNode->class_name().c_str());
                    printf ("In injectSymbolsFromReferencedScopeIntoCurrentScope(): Adding symbol to new scope (currentScope = %p = %s) as a SgAliasSymbol = %p causalNode = %p = %s \n",currentScope,currentScope->class_name().c_str(),aliasSymbol,causalNode,causalNode->class_name().c_str());
#endif
                 // Use the current name and the alias to the symbol
                    currentScope->insert_symbol(name, aliasSymbol);

#if ALIAS_SYMBOL_DEBUGGING
                    printf ("In injectSymbolsFromReferencedScopeIntoCurrentScope(): DONE: Adding symbol to new scope (currentScope = %p = %s) as a SgAliasSymbol = %p causalNode = %p = %s \n",currentScope,currentScope->class_name().c_str(),aliasSymbol,causalNode,causalNode->class_name().c_str());
#endif
                  }
             }
            else
             {
#if ALIAS_SYMBOL_DEBUGGING
               printf ("NO SgAliasSymbol ADDED (wrong permissions): declarationFromSymbol = %p \n",declarationFromSymbol);
#endif
             }
#if 0
       // Older version of code...
       // SgAliasSymbol* aliasSymbol = new SgAliasSymbol (SgSymbol *alias=NULL, bool isRenamed=false, SgName new_name="")
          SgAliasSymbol* aliasSymbol = new SgAliasSymbol (symbol);

       // Use the current name and the alias to the symbol
          currentScope->insert_symbol(name, aliasSymbol);
#endif

       // Increment iterator and counter
          i++;
          counter++;
        }

#if 0
  // debugging
     symbolTable->print("In injectSymbolsFromReferencedScopeIntoCurrentScope(): printing out the symbol tables");
#endif
#if ALIAS_SYMBOL_DEBUGGING
     printf ("In injectSymbolsFromReferencedScopeIntoCurrentScope(): referencedScope = %p = %s currentScope = %p = %s accessLevel = %d \n",referencedScope,referencedScope->class_name().c_str(),currentScope,currentScope->class_name().c_str(),accessLevel);
#endif
   }
Ejemplo n.º 4
0
SgFunctionTypeTable* mergeFunctionTypeSymbolTables ( vector<SgFunctionTypeTable*> functionTableArray )
   {
  // This is the function type table from the last AST read (since AST_FILE_IO::setStaticDataOfAst()
  // resets the static variable used to store the global function type table for ROSE).
     SgFunctionTypeTable* globalFunctionTypeTable = SgNode::get_globalFunctionTypeTable();
     ROSE_ASSERT(globalFunctionTypeTable != NULL);

     printf ("Using globalFunctionTypeTable = %p as a table to merge all symbols into. \n",globalFunctionTypeTable);
#if 0
     printf ("BEFORE removing the global function type table: functionTableArray size = %zu \n",functionTableArray.size());
#endif

     ROSE_ASSERT(functionTableArray.empty() == false);
     vector<SgFunctionTypeTable*>::iterator globalTable = find(functionTableArray.begin(),functionTableArray.end(),globalFunctionTypeTable);
     ROSE_ASSERT(globalTable != functionTableArray.end());
     functionTableArray.erase(globalTable);

#if 0
     printf ("AFTER removing the global function type table: functionTableArray size = %zu \n",functionTableArray.size());
#endif

     for (size_t index = 0; index < functionTableArray.size(); index++)
        {
#if 0
          printf ("Processing table = %zu \n",index);
#endif
          ROSE_ASSERT(functionTableArray[index] != NULL);
          SgSymbolTable::BaseHashType* internalTable = functionTableArray[index]->get_function_type_table()->get_table();
          ROSE_ASSERT(internalTable != NULL);

          SgSymbolTable::hash_iterator i = internalTable->begin();
          while (i != internalTable->end())
             {
#if 0
               printf ("In symbol table = %p symbol name = i->first = %s i->second = %p = %s \n",localFunctionTypeTable,i->first.str(),i->second,i->second->class_name().c_str());
#endif
               ROSE_ASSERT ( isSgSymbol( (*i).second ) != NULL );

            // printf ("Symbol number: %d (pair.first (SgName) = %s) pair.second (SgSymbol) sage_class_name() = %s \n",
            //      idx,(*i).first.str(),(*i).second->sage_class_name());

               SgSymbol* symbol = isSgSymbol((*i).second);
               ROSE_ASSERT ( symbol != NULL );

               if (globalFunctionTypeTable->lookup_function_type(i->first) == NULL)
                  {
                 // This function in the local function type table is not in the global function type table, so add it.
#if 0
                    printf ("Symbol should be added to the global table: i->first = %s \n",i->first.str());
#endif
                 // globalFunctionTypeTable->insert_function_type(i->first,i->second);
                    globalFunctionTypeTable->get_function_type_table()->insert(i->first,i->second);
                  }
                 else
                  {
                 // These are redundant symbols, but likely something in the AST points to them so be careful.

                 // This function type is already in the global function type table, so there is nothing to do (later we can delete it to save space)
#if 0
                    printf ("Symbol already in global table: i->first = %s \n",i->first.str());
#endif
                  }

               i++;
             }
        }

#if 1
     printf ("Leaving mergeFunctionTypeSymbolTables() \n");
#endif

     return globalFunctionTypeTable;
   }