Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

Ignore:
Timestamp:
Aug 25, 2013, 9:08:42 PM (11 years ago)
Author:
landauf
Message:

merged core6 back to trunk

Location:
code/trunk
Files:
2 edited
1 copied

Legend:

Unmodified
Added
Removed
  • code/trunk

  • code/trunk/src/libraries/core/class/IdentifierManager.cc

    r9564 r9667  
    3737
    3838#include "util/StringUtils.h"
     39#include "core/CoreIncludes.h"
    3940#include "core/config/ConfigValueContainer.h"
    4041#include "core/XMLPort.h"
     
    4344namespace orxonox
    4445{
    45     int IdentifierManager::hierarchyCreatingCounter_s = 0;
    46     unsigned int IdentifierManager::classIDCounter_s = 0;
    47 
    48     /**
    49         @brief Returns the identifier map with the names as received by typeid(). This is only used internally.
    50     */
    51     std::map<std::string, Identifier*>& IdentifierManager::getTypeIDIdentifierMap()
    52     {
    53         static std::map<std::string, Identifier*> identifiers;    //!< The map to store all Identifiers.
    54         return identifiers;
     46    /* static */ IdentifierManager& IdentifierManager::getInstance()
     47    {
     48        static IdentifierManager instance;
     49        return instance;
     50    }
     51
     52    IdentifierManager::IdentifierManager()
     53    {
     54        this->hierarchyCreatingCounter_s = 0;
     55        this->classIDCounter_s = 0;
    5556    }
    5657
    5758    /**
    5859        @brief Returns an identifier by name and adds it if not available
    59         @param name The name of the identifier as typeid().name() suggests
    6060        @param proposal A pointer to a newly created identifier for the case of non existence in the map
    6161        @return The identifier (unique instance)
    6262    */
    63     Identifier* IdentifierManager::getIdentifierSingleton(const std::string& name, Identifier* proposal)
    64     {
    65         std::map<std::string, Identifier*>::const_iterator it = getTypeIDIdentifierMap().find(name);
    66 
    67         if (it != getTypeIDIdentifierMap().end())
    68         {
    69             // There is already an entry: return it and delete the proposal
    70             delete proposal;
     63    Identifier* IdentifierManager::getGloballyUniqueIdentifier(Identifier* proposal)
     64    {
     65        const std::string& typeidName = proposal->getTypeidName();
     66        std::map<std::string, Identifier*>::const_iterator it = this->identifierByTypeidName_.find(typeidName);
     67
     68        if (it != this->identifierByTypeidName_.end())
     69        {
     70            // There is already an entry: return it
    7171            return it->second;
    7272        }
     
    7474        {
    7575            // There is no entry: put the proposal into the map and return it
    76             getTypeIDIdentifierMap()[name] = proposal;
     76            this->identifierByTypeidName_[typeidName] = proposal;
    7777            return proposal;
    7878        }
     
    8080
    8181    /**
     82     * Registers the identifier in all maps of the IdentifierManager.
     83     */
     84    void IdentifierManager::addIdentifierToLookupMaps(Identifier* identifier)
     85    {
     86        const std::string& typeidName = identifier->getTypeidName();
     87        if (this->identifierByTypeidName_.find(typeidName) != this->identifierByTypeidName_.end())
     88        {
     89            this->identifierByString_[identifier->getName()] = identifier;
     90            this->identifierByLowercaseString_[getLowercase(identifier->getName())] = identifier;
     91            this->identifierByNetworkId_[identifier->getNetworkID()] = identifier;
     92        }
     93        else
     94            orxout(internal_warning) << "Trying to add an identifier to lookup maps which is not known to IdentifierManager" << endl;
     95    }
     96
     97    /**
    8298        @brief Creates the class-hierarchy by creating and destroying one object of each type.
    8399    */
     
    85101    {
    86102        orxout(internal_status) << "Create class-hierarchy" << endl;
    87         IdentifierManager::startCreatingHierarchy();
    88         for (std::map<std::string, Identifier*>::const_iterator it = IdentifierManager::getStringIdentifierMap().begin(); it != IdentifierManager::getStringIdentifierMap().end(); ++it)
    89         {
    90             // To create the new branch of the class-hierarchy, we create a new object and delete it afterwards.
    91             if (it->second->hasFactory())
     103        this->startCreatingHierarchy();
     104
     105        std::set<Identifier*> initializedIdentifiers;
     106
     107        // ensure root context exists before starting to create objects. if the root context is dynamically created while creating the class hierarchy, we
     108        // would mistakenly assume the class of the currently created object inherits from Context
     109        Context::getRootContext();
     110
     111        // iterate over all identifiers, create one instance of each class and initialize the identifiers
     112        {
     113            Context temporaryContext(NULL);
     114            for (std::map<std::string, Identifier*>::const_iterator it = this->identifierByTypeidName_.begin(); it != this->identifierByTypeidName_.end(); ++it)
    92115            {
    93                 OrxonoxClass* temp = it->second->fabricate(0);
    94                 temp->destroy();
     116                orxout(verbose, context::identifier) << "Initialize ClassIdentifier<" << it->second->getName() << ">-Singleton." << endl;
     117                // To initialize the identifier, we create a new object and delete it afterwards.
     118                if (it->second->hasFactory())
     119                {
     120                    this->identifiersOfNewObject_.clear();
     121                    Identifiable* temp = it->second->fabricate(&temporaryContext);
     122                    if (temp->getIdentifier() != it->second)
     123                        orxout(internal_error) << "Newly created object of type " << it->second->getName() << " has unexpected identifier. Did you forget to use RegisterObject(classname)?" << endl;
     124                    delete temp;
     125
     126                    it->second->initializeParents(this->identifiersOfNewObject_);
     127                }
     128                else
     129                    it->second->initializeDirectParentsOfAbstractClass();
     130
     131                initializedIdentifiers.insert(it->second);
    95132            }
    96         }
    97         IdentifierManager::stopCreatingHierarchy();
     133
     134            size_t numberOfObjects = temporaryContext.getObjectList<Listable>()->size();
     135            if (numberOfObjects > 0)
     136                orxout(internal_warning) << "There are still " << numberOfObjects << " listables left after creating the class hierarchy" << endl;
     137        }
     138
     139        // finish the initialization of all identifiers
     140        for (std::map<std::string, Identifier*>::const_iterator it = this->identifierByTypeidName_.begin(); it != this->identifierByTypeidName_.end(); ++it)
     141        {
     142            if (initializedIdentifiers.find(it->second) != initializedIdentifiers.end())
     143                it->second->finishInitialization();
     144            else
     145                orxout(internal_error) << "Identifier was registered late and is not initialized: " << it->second->getName() << " / " << it->second->getTypeidName() << endl;
     146        }
     147
     148        this->stopCreatingHierarchy();
    98149        orxout(internal_status) << "Finished class-hierarchy creation" << endl;
    99150    }
     
    104155    void IdentifierManager::destroyAllIdentifiers()
    105156    {
    106         for (std::map<std::string, Identifier*>::iterator it = IdentifierManager::getTypeIDIdentifierMap().begin(); it != IdentifierManager::getTypeIDIdentifierMap().end(); ++it)
     157        for (std::map<std::string, Identifier*>::iterator it = this->identifierByTypeidName_.begin(); it != this->identifierByTypeidName_.end(); ++it)
    107158            delete (it->second);
    108     }
    109 
    110     /**
    111         @brief Returns the map that stores all Identifiers with their names.
    112         @return The map
    113     */
    114     std::map<std::string, Identifier*>& IdentifierManager::getStringIdentifierMapIntern()
    115     {
    116         static std::map<std::string, Identifier*> identifierMap;
    117         return identifierMap;
    118     }
    119 
    120     /**
    121         @brief Returns the map that stores all Identifiers with their names in lowercase.
    122         @return The map
    123     */
    124     std::map<std::string, Identifier*>& IdentifierManager::getLowercaseStringIdentifierMapIntern()
    125     {
    126         static std::map<std::string, Identifier*> lowercaseIdentifierMap;
    127         return lowercaseIdentifierMap;
    128     }
    129 
    130     /**
    131         @brief Returns the map that stores all Identifiers with their network IDs.
    132         @return The map
    133     */
    134     std::map<uint32_t, Identifier*>& IdentifierManager::getIDIdentifierMapIntern()
    135     {
    136         static std::map<uint32_t, Identifier*> identifierMap;
    137         return identifierMap;
     159
     160        this->identifierByTypeidName_.clear();
     161        this->identifierByString_.clear();
     162        this->identifierByLowercaseString_.clear();
     163        this->identifierByNetworkId_.clear();
     164    }
     165
     166    /**
     167     * @brief Notifies the IdentifierManager about a newly created object while creating the class hierarchy.
     168     */
     169    void IdentifierManager::createdObject(Identifiable* identifiable)
     170    {
     171        if (this->isCreatingHierarchy())
     172            this->identifiersOfNewObject_.insert(identifiable->getIdentifier());
     173        else
     174            orxout(internal_warning) << "createdObject() called outside of class hierarchy creation" << endl;
    138175    }
    139176
     
    145182    Identifier* IdentifierManager::getIdentifierByString(const std::string& name)
    146183    {
    147         std::map<std::string, Identifier*>::const_iterator it = IdentifierManager::getStringIdentifierMapIntern().find(name);
    148         if (it != IdentifierManager::getStringIdentifierMapIntern().end())
     184        std::map<std::string, Identifier*>::const_iterator it = this->identifierByString_.find(name);
     185        if (it != this->identifierByString_.end())
    149186            return it->second;
    150187        else
     
    159196    Identifier* IdentifierManager::getIdentifierByLowercaseString(const std::string& name)
    160197    {
    161         std::map<std::string, Identifier*>::const_iterator it = IdentifierManager::getLowercaseStringIdentifierMapIntern().find(name);
    162         if (it != IdentifierManager::getLowercaseStringIdentifierMapIntern().end())
     198        std::map<std::string, Identifier*>::const_iterator it = this->identifierByLowercaseString_.find(name);
     199        if (it != this->identifierByLowercaseString_.end())
    163200            return it->second;
    164201        else
     
    173210    Identifier* IdentifierManager::getIdentifierByID(const uint32_t id)
    174211    {
    175         std::map<uint32_t, Identifier*>::const_iterator it = IdentifierManager::getIDIdentifierMapIntern().find(id);
    176         if (it != IdentifierManager::getIDIdentifierMapIntern().end())
     212        std::map<uint32_t, Identifier*>::const_iterator it = this->identifierByNetworkId_.find(id);
     213        if (it != this->identifierByNetworkId_.end())
    177214            return it->second;
    178215        else
     
    185222    void IdentifierManager::clearNetworkIDs()
    186223    {
    187         IdentifierManager::getIDIdentifierMapIntern().clear();
     224        this->identifierByNetworkId_.clear();
    188225    }
    189226}
Note: See TracChangeset for help on using the changeset viewer.