| # Gaudi Framework, version v20r3
Generated: 24 Nov 2008

# DataSvc.cpp

Go to the documentation of this file.

    00001 // $Header: /local/reps/Gaudi/GaudiKernel/src/Lib/DataSvc.cpp,v 1.38 2008/10/23 15:57:37 marcocle Exp $
    00002 //====================================================================
    00003 //      DataSvc.cpp
    00004 //--------------------------------------------------------------------
    00005 //
    00006 //      Package    : System ( The LHCb Offline System)
    00007 //
    00008 //  Description: implementation of the Transient data service: DataSvc
    00009 //
    00010 //  Author     : M.Frank
    00011 //  History    :
    00012 // +---------+----------------------------------------------+---------
    00013 // |    Date |                 Comment                      | Who
    00014 // +---------+----------------------------------------------+---------
    00015 // | 29/10/98| Initial version                              | M.Frank
    00016 // | 20/2/99 | Automatic data preloading introduced.        | M.Frank
    00017 // +---------+----------------------------------------------+---------
    00018 //
    00019 //====================================================================
    00020 #define  DATASVC_DATASVC_CPP
    00021
    00022 // Framework include files
    00023 #include "GaudiKernel/IConverter.h"
    00024 #include "GaudiKernel/IOpaqueAddress.h"
    00025 #include "GaudiKernel/IConversionSvc.h"
    00026
    00027 #include "GaudiKernel/xtoa.h"
    00028 #include "GaudiKernel/SvcFactory.h"
    00029 #include "GaudiKernel/DataObject.h"
    00030 #include "GaudiKernel/GaudiException.h"
    00031
    00032 #include "GaudiKernel/RegistryEntry.h"
    00033 #include "GaudiKernel/DataSvc.h"
    00034 #include "GaudiKernel/DataIncident.h"
    00035 #include "GaudiKernel/IIncidentSvc.h"
    00036
    00037 // Include files
    00038 #include <cassert>
    00039 #include <cstdlib>
    00040 #include <vector>
    00041 #include <algorithm>
    00042
    00043 // If you absolutely need optimization: switch off dynamic_cast.
    00044 // This improves access to the data store roughly by 10 %
    00045 // for balanced trees.
    00046 //
    00047 // M.Frank
    00048 #define CAST_REGENTRY(x,y) dynamic_cast<x>(y)
    00049 //#define CAST_REGENTRY(x,y) (x)(y)
    00050 typedef DataSvcHelpers::RegistryEntry RegEntry;
    00051
    00055 StatusCode DataSvc::clearSubTree(const std::string& sub_tree_path)    {
    00056   DataObject* pObject = 0;
    00057   StatusCode status = findObject(sub_tree_path, pObject);
    00058   if ( status.isSuccess() )   {
    00059     RegEntry* node_entry = CAST_REGENTRY(RegEntry*,pObject->registry());
    00060     if ( 0 != node_entry )   {
    00061       RegEntry* parent = node_entry->parentEntry();
    00062       if ( 0 != parent )  {
    00063         parent->remove(node_entry);
    00064         return StatusCode::SUCCESS;
    00065       }
    00066       return INVALID_PARENT;
    00067     }
    00068     return INVALID_OBJECT;
    00069   }
    00070   return status;
    00071 }
    00072
    00076 StatusCode DataSvc::clearSubTree(DataObject* pObject)    {
    00077   if ( checkRoot() )  {
    00078     RegEntry* entry = CAST_REGENTRY(RegEntry*,pObject->registry());
    00079     if ( 0 != entry )   {
    00080       RegEntry* parent = entry->parentEntry();
    00081       if ( 0 != parent )  {
    00082         parent->remove(entry);
    00083         return SUCCESS;
    00084       }
    00085       return INVALID_PARENT;
    00086     }
    00087     return INVALID_OBJECT;
    00088   }
    00089   return INVALID_ROOT;
    00090 }
    00091
    00093 StatusCode DataSvc::clearStore()   {
    00094   if ( checkRoot() )    {
    00095     m_root->release();
    00096     m_root = 0;
    00097     return SUCCESS;
    00098   }
    00099   return INVALID_ROOT;
    00100 }
    00101
    00105 StatusCode DataSvc::traverseSubTree (const std::string& sub_tree_path,
    00106                                      IDataStoreAgent* pAgent)  {
    00107   DataObject* pO = 0;
    00108   StatusCode status = findObject(sub_tree_path, pO);
    00109   if ( status.isSuccess() )   {
    00110     status = traverseSubTree(pO, pAgent);
    00111   }
    00112   return status;
    00113 }
    00114
    00116 StatusCode DataSvc::traverseSubTree ( DataObject* pObject,
    00117                                       IDataStoreAgent* pAgent )  {
    00118   if ( checkRoot() )    {
    00119     RegEntry* entry = CAST_REGENTRY(RegEntry*,pObject->registry());
    00120     if ( 0 != entry )   {
    00121       return entry->traverseTree(pAgent);
    00122     }
    00123     return INVALID_OBJECT;
    00124   }
    00125   return INVALID_ROOT;
    00126 }
    00127
    00129 StatusCode DataSvc::traverseTree(IDataStoreAgent* pAgent)   {
    00130   if ( checkRoot() )    {
    00131     return m_root->traverseTree(pAgent);
    00132   }
    00133   return INVALID_ROOT;
    00134 }
    00135
    00140 StatusCode DataSvc::setRoot(const std::string& root_path,
    00141                             DataObject* pRootObj)    {
    00142   clearStore().ignore();
    00143   return i_setRoot (root_path, pRootObj);
    00144 }
    00145
    00151 StatusCode DataSvc::i_setRoot(const std::string& root_path,
    00152                               DataObject* pRootObj)    {
    00153   if ( 0 != pRootObj )  {
    00154     m_root = new RegEntry(root_path);
    00155     m_root->makeHard(pRootObj);
    00156     m_root->setDataSvc(this);
    00157     preLoad().ignore();
    00158   }
    00159   return SUCCESS;
    00160 }
    00161
    00166 StatusCode DataSvc::setRoot(const std::string& root_path,
    00167                             IOpaqueAddress* pRootAddr)    {
    00168   clearStore().ignore();
    00169   return i_setRoot (root_path, pRootAddr);
    00170 }
    00171
    00177 StatusCode DataSvc::i_setRoot(const std::string& root_path,
    00178                               IOpaqueAddress* pRootAddr)    {
    00179   if ( 0 != pRootAddr )  {
    00180     m_root = new RegEntry(root_path);
    00181     m_root->makeHard(pRootAddr);
    00182     m_root->setDataSvc(this);
    00183     preLoad().ignore();
    00184   }
    00185   return SUCCESS;
    00186 }
    00187
    00189 StatusCode DataSvc::setDataLoader(IConversionSvc* pDataLoader)    {
    00190   if ( 0 != pDataLoader  ) pDataLoader->addRef();
    00191   if ( 0 != m_dataLoader ) m_dataLoader->release();
    00192   if ( 0 != pDataLoader  )    {
    00193     pDataLoader->setDataProvider(this).ignore();
    00194   }
    00195   m_dataLoader = pDataLoader;
    00196   return SUCCESS;
    00197 }
    00198
    00200 StatusCode DataSvc::objectParent(const DataObject*  pObject,
    00201                                  IRegistry*& refpParent)   {
    00202   if ( pObject )    {
    00203     return objectParent(pObject->registry(), refpParent);
    00204   }
    00205   return INVALID_OBJECT;
    00206 }
    00208 StatusCode DataSvc::objectParent(const IRegistry*   pRegistry,
    00209                                  IRegistry*& refpParent)  {
    00210   if ( checkRoot() )    {
    00211     const RegEntry* node_entry = CAST_REGENTRY(const RegEntry*,pRegistry);
    00212     if ( node_entry )   {
    00213       refpParent = node_entry->parent();
    00214       return StatusCode::SUCCESS;
    00215     }
    00216     return INVALID_OBJECT;
    00217   }
    00218   return INVALID_ROOT;
    00219 }
    00220
    00222 StatusCode DataSvc::objectLeaves( const DataObject*  pObject,
    00223                                  std::vector<IRegistry*>& leaves)   {
    00224   if ( pObject )    {
    00225     return objectLeaves(pObject->registry(), leaves);
    00226   }
    00227   return INVALID_OBJECT;
    00228 }
    00229
    00233 StatusCode DataSvc::objectLeaves( const IRegistry*   pRegistry,
    00234                                  std::vector<IRegistry*>& leaves)   {
    00235   if ( checkRoot() )    {
    00236     const RegEntry* node_entry = CAST_REGENTRY(const RegEntry*,pRegistry);
    00237     if ( node_entry )   {
    00238       leaves = node_entry->leaves();
    00239       return StatusCode::SUCCESS;
    00240     }
    00241     return INVALID_OBJECT;
    00242   }
    00243   return INVALID_ROOT;
    00244 }
    00245
    00247 StatusCode DataSvc::registerAddress(const std::string& fullPath,
    00248                                     IOpaqueAddress* pAddress)   {
    00249   if ( fullPath.length() > 0 )    {
    00250     if ( fullPath[0] != SEPARATOR )   {
    00251       return registerAddress(m_root, fullPath, pAddress);
    00252     }
    00253     IRegistry* pRegistry = 0;
    00254     return registerAddress(pRegistry, fullPath, pAddress);
    00255   }
    00256   return INVALID_OBJ_PATH;
    00257 }
    00258
    00260 StatusCode DataSvc::registerAddress(DataObject* parentObj,
    00261                                     const std::string& objectPath,
    00262                                     IOpaqueAddress* pAddress)   {
    00263   IRegistry* pRegistry = (0 == parentObj) ? 0 : parentObj->registry();
    00264   return registerAddress(pRegistry, objectPath, pAddress);
    00265 }
    00266
    00268 StatusCode DataSvc::registerAddress(IRegistry* parentObj,
    00269                                     const std::string& objPath,
    00270                                     IOpaqueAddress* pAddress)   {
    00271   if ( checkRoot() )  {
    00272     if ( objPath.length() > 0 )   {
    00273       if ( 0 == parentObj )   {
    00274         if ( objPath[0] != SEPARATOR )    {
    00275           return registerAddress(m_root, objPath, pAddress);
    00276         }
    00277         std::string::size_type sep = objPath.find(SEPARATOR,1);
    00278         if ( sep != std::string::npos )    {
    00279           std::string p_path (objPath, 0, sep);
    00280           if ( p_path == m_rootName )   {
    00281             std::string o_path (objPath, sep, objPath.length());
    00282             return registerAddress(m_root, o_path, pAddress);
    00283           }
    00284         }
    00285         return INVALID_PARENT;
    00286       }
    00287       if ( objPath[0] != SEPARATOR )    {
    00288         std::string path;
    00289         path  = SEPARATOR;
    00290         path += objPath;
    00291         return registerAddress(parentObj, path, pAddress);
    00292       }
    00293       RegEntry* par_entry = CAST_REGENTRY(RegEntry*,parentObj);
    00294       if ( 0 != par_entry )   {
    00295         std::string::size_type sep = objPath.rfind(SEPARATOR);
    00296         if ( sep > 0 && sep != std::string::npos )    {
    00297           std::string p_path (objPath, 0, sep);
    00298           std::string o_path (objPath, sep, objPath.length());
    00299           RegEntry* p_entry = par_entry->findLeaf(p_path);
    00300           // Create default object leafs if the
    00301           // intermediate nodes are not present
    00302           if ( 0 == p_entry && m_forceLeaves )    {
    00303             DataObject *pLeaf = createDefaultObject();
    00304             StatusCode sc = registerObject(par_entry->identifier(),
    00305                                            p_path,
    00306                                            pLeaf);
    00307             if ( ! sc.isSuccess() )   {
    00308               delete pLeaf;
    00309             }
    00310             p_entry = par_entry->findLeaf(p_path);
    00311           }
    00312           if ( 0 != p_entry )  {
    00313             return registerAddress(p_entry, o_path, pAddress);
    00314           }
    00315           return INVALID_PARENT;
    00316         }
    00317         StatusCode status = par_entry->add(objPath, pAddress);
    00318         if ( status.isSuccess() )   {
    00319           return status;
    00320         }
    00321         return DOUBL_OBJ_PATH;
    00322       }
    00323       return INVALID_PARENT;
    00324     }
    00325     return INVALID_OBJ_PATH;
    00326   }
    00327   return INVALID_ROOT;
    00328 }
    00329
    00331 StatusCode DataSvc::unregisterAddress(const std::string& fullPath)    {
    00332   if ( fullPath.length() > 0 )    {
    00333     IRegistry* pRegistry = 0;
    00334     if ( fullPath[0] != SEPARATOR )   {
    00335       return unregisterAddress(m_root, fullPath);
    00336     }
    00337     return unregisterAddress(pRegistry, fullPath);
    00338   }
    00339   return INVALID_OBJ_PATH;
    00340 }
    00341
    00343 StatusCode DataSvc::unregisterAddress(DataObject* pParent,
    00344                                       const std::string& objPath)   {
    00345   IRegistry* pRegistry = (0 == pParent) ? 0 : pParent->registry();
    00346   return unregisterAddress(pRegistry, objPath);
    00347 }
    00348
    00350 StatusCode DataSvc::unregisterAddress(IRegistry* pParent,
    00351                                       const std::string& objPath)   {
    00352   if ( checkRoot() )  {
    00353     if ( objPath.length() > 0 )   {
    00354       if ( 0 == pParent )   {
    00355         if ( objPath[0] != SEPARATOR )    {
    00356           return unregisterAddress(m_root, objPath);
    00357         }
    00358         std::string::size_type sep = objPath.find(SEPARATOR,1);
    00359         if ( sep != std::string::npos )    {
    00360           std::string p_path (objPath, 0, sep);
    00361           if ( p_path == m_rootName )   {
    00362             std::string o_path (objPath, sep, objPath.length());
    00363             return unregisterAddress(m_root, o_path);
    00364           }
    00365         }
    00366         return INVALID_PARENT;
    00367       }
    00368       if ( objPath[0] != SEPARATOR )    {
    00369         std::string path;
    00370         path  = SEPARATOR;
    00371         path += objPath;
    00372         return unregisterAddress(pParent, path);
    00373       }
    00374       RegEntry* node_entry = CAST_REGENTRY(RegEntry*,pParent);
    00375       if ( 0 != node_entry )   {
    00376         RegEntry* leaf_entry = node_entry->findLeaf(objPath);
    00377         if ( 0 != leaf_entry )    {
    00378           std::string::size_type sep = objPath.rfind(SEPARATOR);
    00379           if ( sep > 0 && sep != std::string::npos )    {
    00380             std::string path = objPath.substr(sep);
    00381             return unregisterAddress(leaf_entry->parent(), path);
    00382           }
    00383           StatusCode status = node_entry->remove(objPath);
    00384           if ( status.isSuccess() )   {
    00385             return status;
    00386           }
    00387         }
    00388       }
    00389       return INVALID_PARENT;
    00390     }
    00391     return INVALID_OBJ_PATH;
    00392   }
    00393   return INVALID_ROOT;
    00394 }
    00395
    00397 StatusCode DataSvc::registerObject (const std::string& fullPath,
    00398                                     DataObject* pObject)   {
    00399   return registerObject(0, fullPath, pObject);
    00400 }
    00401
    00402
    00404 StatusCode DataSvc::registerObject (const std::string& parentPath,
    00405                                     const std::string& objPath,
    00406                                     DataObject* pObject)   {
    00407   DataObject* pO = 0;
    00408   StatusCode status = retrieveObject(parentPath, pO);
    00409   if ( !status.isSuccess() && m_forceLeaves )   {
    00410     pO = createDefaultObject();
    00411     status = registerObject(parentPath, pO);
    00412     if ( !status.isSuccess() )   {
    00413       pO->release();
    00414     }
    00415   }
    00416   if ( status.isSuccess() )   {
    00417     status = registerObject(pO, objPath, pObject);
    00418   }
    00419   return status;
    00420 }
    00421
    00423 StatusCode DataSvc::registerObject(const std::string& parentPath,
    00424                                    int item,
    00425                                    DataObject* pObject)   {
    00426   char buffer[32] = "/";
    00427   ::_itoa( item, &buffer[1] , 10 );
    00428   return registerObject(parentPath, buffer, pObject);
    00429 }
    00430
    00432 StatusCode DataSvc::registerObject(DataObject* parentObj,
    00433                                    int item,
    00434                                    DataObject* pObject)   {
    00435   char buffer[32] = "/";
    00436   ::_itoa( item, &buffer[1] , 10 );
    00437   return registerObject(parentObj, buffer, pObject);
    00438 }
    00439
    00441 StatusCode DataSvc::registerObject(DataObject* parentObj,
    00442                                    const std::string& objPath,
    00443                                    DataObject* pObject)   {
    00444   if ( checkRoot() )  {
    00445     if ( 0 == parentObj )   {
    00446       if ( objPath.length() > 0 )   {
    00447         if ( objPath[0] == SEPARATOR )    {
    00448           std::string::size_type sep = objPath.find(SEPARATOR,1);
    00449           if ( sep != std::string::npos )    {
    00450             std::string p_path (objPath, 0, sep);
    00451             std::string o_path (objPath, sep, objPath.length());
    00452             return registerObject(p_path, o_path, pObject);
    00453           }
    00454         }
    00455         else  {
    00456           return registerObject(m_rootName, objPath, pObject);
    00457         }
    00458       }
    00459       return INVALID_OBJ_PATH;
    00460     }
    00461     RegEntry* node_entry = CAST_REGENTRY(RegEntry*,parentObj->registry());
    00462     if ( 0 != node_entry )   {
    00463       StatusCode status = INVALID_PARENT;
    00464       std::string::size_type sep = objPath.find(SEPARATOR,1);
    00465       if ( sep != std::string::npos )    {
    00466         std::string p_path (objPath, 0, sep);
    00467         std::string o_path (objPath, sep, objPath.length());
    00468         RegEntry* par_entry = node_entry->findLeaf(p_path);
    00469         // Create default object leafs if the
    00470         // intermediate nodes are not present
    00471         if ( 0 == par_entry && m_forceLeaves )    {
    00472           DataObject *pLeaf = createDefaultObject();
    00473           StatusCode sc = registerObject(parentObj, p_path, pLeaf);
    00474           if ( ! sc.isSuccess() )   {
    00475             delete pLeaf;
    00476           }
    00477           par_entry = node_entry->findLeaf(p_path);
    00478         }
    00479         else if ( 0 != par_entry && par_entry->object() == 0 )  {
    00480           status = retrieveEntry( node_entry, p_path, par_entry);
    00481           if ( !status.isSuccess() && !par_entry->address() && m_forceLeaves )  {
    00482             DataObject *pLeaf = createDefaultObject();
    00483             StatusCode sc = registerObject(parentObj, p_path, pLeaf);
    00484             if ( ! sc.isSuccess() )   {
    00485               delete pLeaf;
    00486             }
    00487             par_entry = node_entry->findLeaf(p_path);
    00488           }
    00489         }
    00490         node_entry = par_entry;
    00491         if ( 0 != node_entry )    {
    00492           DataObject* obj = node_entry->object();
    00493           if ( 0 != obj )   {
    00494             status = registerObject( obj, o_path, pObject );
    00495           }
    00496         }
    00497       }
    00498       else   {
    00499         RegEntry* leaf = node_entry->findLeaf(objPath);
    00500         if ( 0 == leaf )    {
    00501           status = node_entry->add( objPath, pObject );
    00502         }
    00503         else    {
    00504           DataObject* obj = leaf->object();
    00505           if ( 0 == obj )    {
    00506             if (0 == pObject) {
    00507               MsgStream log(msgSvc(), name());
    00508               log << MSG::ERROR
    00509                   << "registerObject: trying to register null DataObject" << endreq;
    00510               return StatusCode::FAILURE;
    00511             }
    00512             else  {
    00513               pObject->setRegistry(leaf);
    00514             }
    00515             leaf->setAddress(0);
    00516             leaf->setObject(pObject);
    00517             status = StatusCode::SUCCESS;
    00518           }
    00519           else  {
    00520             status = DOUBL_OBJ_PATH;
    00521           }
    00522         }
    00523       }
    00524       return status;
    00525     }
    00526     return INVALID_PARENT;
    00527   }
    00528   return INVALID_ROOT;
    00529 }
    00530
    00532 StatusCode DataSvc::unregisterObject(const std::string& fullPath)   {
    00533   DataObject* pObject = 0;
    00534   StatusCode status = findObject(fullPath, pObject);
    00535   if ( status.isSuccess() )   {
    00536     RegEntry* pEntry = CAST_REGENTRY(RegEntry*,pObject->registry());
    00537     if ( 0 != pEntry )    {
    00538       if ( pEntry->isEmpty() )    {
    00539         RegEntry* pParent = pEntry->parentEntry();
    00540         if ( 0 != pParent )   {
    00541           if ( 0 != pObject )    {
    00542             pObject->addRef();
    00543           }
    00544           pParent->remove(pEntry);
    00545           return StatusCode::SUCCESS;
    00546         }
    00547         return INVALID_PARENT;
    00548       }
    00549       return DIR_NOT_EMPTY;
    00550     }
    00551     return INVALID_ROOT;
    00552   }
    00553   return status;
    00554 }
    00555
    00557 StatusCode DataSvc::unregisterObject(const std::string& parentPath,
    00558                                      const std::string& objPath)   {
    00559   DataObject* pO = 0;
    00560   StatusCode status = findObject(parentPath, pO);
    00561   if ( status.isSuccess() )   {
    00562     status = unregisterObject(pO, objPath);
    00563   }
    00564   return status;
    00565 }
    00566
    00568 StatusCode DataSvc::unregisterObject(const std::string& parentPath, int item) {
    00569   char objPath[32] = "/";
    00570   ::_itoa( item, &objPath[1] , 10 );
    00571   return unregisterObject(parentPath, objPath);
    00572 }
    00573
    00575 StatusCode DataSvc::unregisterObject(DataObject* pObject)    {
    00576   if ( checkRoot() )  {
    00577     RegEntry* entry = m_root->findLeaf(pObject);
    00578     if ( 0 != entry )   {
    00579       RegEntry* parent = entry->parentEntry();
    00580       if ( 0 != parent )    {
    00581         if ( entry->isEmpty() )    {
    00582           if ( 0 != entry->object() )    {
    00583             entry->object()->addRef();
    00584           }
    00585           if ( 0 != parent )  {
    00586             parent->remove(entry);
    00587           }
    00588           return SUCCESS;
    00589         }
    00590         return INVALID_PARENT;
    00591       }
    00592       return DIR_NOT_EMPTY;
    00593     }
    00594     return INVALID_OBJECT;
    00595   }
    00596   return INVALID_ROOT;
    00597 }
    00598
    00600 StatusCode DataSvc::unregisterObject (DataObject* pParentObj,
    00601                                       const std::string& objectPath) {
    00602   if ( checkRoot() )  {
    00603     try   {
    00604       RegEntry* parent = CAST_REGENTRY(RegEntry*,pParentObj->registry());
    00605       if ( 0 != parent )   {
    00606         RegEntry* entry = parent->findLeaf(objectPath);
    00607         if ( 0 != entry )   {
    00608           if ( entry->isEmpty() )    {
    00609             if ( 0 != entry->object() )    {
    00610               entry->object()->addRef();
    00611             }
    00612             parent->remove(entry);
    00613             return SUCCESS;
    00614           }
    00615           return DIR_NOT_EMPTY;
    00616         }
    00617         return INVALID_OBJECT;
    00618       }
    00619     }
    00620     catch(...) {
    00621     }
    00622     return INVALID_PARENT;
    00623   }
    00624   return INVALID_ROOT;
    00625 }
    00626
    00628 StatusCode DataSvc::unregisterObject(DataObject* pParentObj, int item)    {
    00629   char objPath[32] = "/";
    00630   ::_itoa( item, &objPath[1] , 10 );
    00631   return unregisterObject(pParentObj, objPath);
    00632 }
    00633
    00636 DataObject* DataSvc::handleDataFault(IRegistry* pReg, const std::string& path)
    00637 {
    00638   if ( m_enableFaultHdlr )  {
    00639     IRegistry* pLeaf = 0;
    00640     if ( pReg && path.length() == 0 )   {
    00641       DataIncident incident(name(), m_faultName, pReg->identifier());
    00642       m_incidentSvc->fireIncident(incident);
    00643       return pReg->object();
    00644     }
    00645     else if ( pReg )  {
    00646       std::string p = pReg->identifier();
    00647       if (path[0] != SEPARATOR ) p += SEPARATOR;
    00648       p += path;
    00649       DataIncident incident(name(), m_faultName, p);
    00650       m_incidentSvc->fireIncident(incident);
    00651       pLeaf = m_root->findLeaf(p);
    00652     }
    00653     else  {
    00654       std::string p = m_root->identifier();
    00655       if (path[0] != SEPARATOR ) p += SEPARATOR;
    00656       p += path;
    00657       DataIncident incident(name(), m_faultName, p);
    00658       m_incidentSvc->fireIncident(incident);
    00659       pLeaf = m_root->findLeaf(p);
    00660     }
    00661     if ( pLeaf )  {
    00662       return pLeaf->object();
    00663     }
    00664   }
    00665   return 0;
    00666 }
    00667
    00671 StatusCode DataSvc::loadObject(IRegistry* pRegistry)   {
    00672   IConversionSvc* pLoader = getDataLoader(pRegistry);
    00673   return loadObject(pLoader, pRegistry);
    00674 }
    00675
    00679 StatusCode DataSvc::loadObject(IConversionSvc* pLoader, IRegistry* pRegistry) {
    00680   StatusCode status = INVALID_OBJ_ADDR;
    00681   DataObject* pObject = 0;
    00682   if ( 0 == pLoader )   {         // Precondition: Data loader must be present
    00683     if (handleDataFault(pRegistry) != 0) return  SUCCESS;
    00684     else                                 return  NO_DATA_LOADER;
    00685   }
    00686   if ( 0 == pRegistry )    {      // Precondition: Directory must be valid
    00687     if (handleDataFault(pRegistry) != 0) return  SUCCESS;
    00688     else                                 return  INVALID_OBJ_ADDR;
    00689   }
    00690
    00691   MsgStream log( msgSvc(), name() );
    00692   log << MSG::VERBOSE << "Requested object " << pRegistry->identifier() << endmsg;
    00693
    00694   if ( m_enableAccessHdlr )  {
    00695     // Fire data access incident
    00696     DataIncident incident(name(), m_accessName, pRegistry->identifier());
    00697     m_incidentSvc->fireIncident(incident);
    00698   }
    00699   if ( m_inhibitPathes.size() > 0 )   {
    00700     const std::string& ident = pRegistry->identifier();
    00701     std::vector<std::string>::iterator inhibit =
    00702       std::find(m_inhibitPathes.begin(), m_inhibitPathes.end(), ident);
    00703     if ( inhibit != m_inhibitPathes.end() )   {
    00704       return NO_ACCESS;
    00705     }
    00706   }
    00707   IOpaqueAddress* pAddress = pRegistry->address();
    00708   if ( 0 == pAddress )  {         // Precondition:
    00709     return INVALID_OBJ_ADDR;      // Address must be valid
    00710   }
    00711   try   {
    00712     status = pLoader->createObj(pAddress, pObject);  // Call data loader
    00713     if ( status.isSuccess() )    {
    00714
    00715       log << MSG::VERBOSE << "Object " << pRegistry->identifier() << " created" << endmsg;
    00716
    00717       RegEntry *pEntry = CAST_REGENTRY(RegEntry*,pRegistry);
    00718       pEntry->setObject(pObject);
    00719
    00720       log << MSG::VERBOSE << "Filling object " << pRegistry->identifier() << endmsg;
    00721       status = pLoader->fillObjRefs(pAddress, pObject);
    00722     }
    00723   }
    00724   catch( const GaudiException& exc ) {
    00725     if ( handleDataFault(pRegistry) != 0 )  {
    00726       return SUCCESS;
    00727     }
    00728     throw GaudiException("GaudiException in loadObject() " + pRegistry->identifier(),
    00729         name(), StatusCode::FAILURE, exc);
    00730   }
    00731   catch( const std::exception& x) {
    00732     if ( handleDataFault(pRegistry) != 0 )  {
    00733       return SUCCESS;
    00734     }
    00735     throw GaudiException("std::exception in loadObject() " + pRegistry->identifier() +
    00736         ": " + System::typeinfoName(typeid(x)) + ", " + x.what(),
    00737       name(), StatusCode::FAILURE);
    00738   }
    00739   catch(...) {
    00740     if ( handleDataFault(pRegistry) != 0 )  {
    00741       return SUCCESS;
    00742     }
    00743     throw GaudiException("UNKN exception in loadObject() " + pRegistry->identifier(),
    00744       name(), StatusCode::FAILURE);
    00745   }
    00746   if ( !status.isSuccess() )  {
    00747     if ( handleDataFault(pRegistry) != 0 )  {
    00748       return StatusCode::SUCCESS;
    00749     }
    00750   }
    00751   if ( status.isSuccess() ) {
    00752     log << MSG::VERBOSE << "Object " << pRegistry->identifier() << " successfully loaded" << endmsg;
    00753   }
    00754   return status;
    00755 }
    00756
    00758 StatusCode DataSvc::retrieveEntry(RegEntry* parentObj,
    00759                                   const std::string& path,
    00760                                   RegEntry*& pEntry)  {
    00761   std::string::size_type        sep    = path.find(SEPARATOR,1);
    00762   StatusCode status = StatusCode(INVALID_ROOT,true);
    00763   pEntry = 0;
    00764   // A.Valassi 16.08.2001 avoid core dump if store is empty
    00765   if ( checkRoot() )  {
    00766     if ( 0 == parentObj )    {
    00767       if ( path.length() == 0 || path == m_rootName )   {
    00768         return retrieveEntry(m_root, "", pEntry);
    00769       }
    00770       else if ( path[0] != SEPARATOR )  {
    00771         return retrieveEntry(m_root, path, pEntry);
    00772       }
    00773       else if ( sep != std::string::npos )    {
    00774         if ( m_root->object() == 0 )  {
    00775           RegEntry* r = 0;
    00776           status = retrieveEntry(m_root, "", r);
    00777           if ( !status.isSuccess() )  {
    00778             return status;
    00779           }
    00780         }
    00781         std::string o_path (path, sep, path.length());
    00782         return retrieveEntry(m_root, o_path, pEntry);
    00783       }
    00784       return INVALID_OBJ_PATH;
    00785     }
    00786     if ( sep != std::string::npos )  { // the string contains a separator (after pos 0)
    00787       std::string p_path (path,0,sep);
    00788       std::string o_path (path,sep,path.length());
    00789       if (!parentObj->object()) { // if the parent object has not been loaded yet, load it now
    00790         status = loadObject(parentObj);
    00791         if ( !status.isSuccess() )  {
    00792           return status;
    00793         }
    00794       }
    00795       RegEntry* root_entry = parentObj->findLeaf(p_path);
    00796       if ( !root_entry && m_enableFaultHdlr )    {
    00797         // If not even the parent is there, an incident
    00798         // to load the parent must be fired...
    00799         handleDataFault(parentObj, p_path);
    00800         root_entry = parentObj->findLeaf(p_path);
    00801       }
    00802       if ( root_entry )    {
    00803         DataObject* pO = root_entry->object();
    00804         if ( 0 == pO )  {
    00805           // Object is not loaded: load the object if at all possible
    00806           status = loadObject(root_entry);
    00807           if ( !status.isSuccess() )  {
    00808             return status;
    00809           }
    00810         }
    00811         if ( root_entry->isSoft() )    {
    00812           root_entry = CAST_REGENTRY(RegEntry*,pO->registry());
    00813         }
    00814         return retrieveEntry (root_entry, o_path, pEntry);
    00815       }
    00816       return status;
    00817     }
    00818     else if ( path.length() == 0 )    {
    00819       pEntry = parentObj;
    00820     }
    00821     else {
    00822       if (!parentObj->object()) { // if the parent object has not been loaded yet, load it now
    00823         status = loadObject(parentObj);
    00824         if ( !status.isSuccess() )  {
    00825           return status;
    00826         }
    00827       }
    00828       // last leave in search: find leaf and load
    00829       pEntry = parentObj->findLeaf(path);
    00830       // If no registry entry was found, trigger incident for action-on-demand
    00831       if ( !pEntry && m_enableFaultHdlr )  {
    00832         handleDataFault(parentObj, path);
    00833         pEntry = (0==path.length()) ? parentObj : parentObj->findLeaf(path);
    00834       }
    00835     }
    00836     // Check results and return
    00837     if ( 0 == pEntry )  {
    00838       status = INVALID_OBJ_PATH;
    00839     }
    00840     else if ( 0 == pEntry->object() )  {
    00841       status = loadObject(pEntry);
    00842     }
    00843     else if ( m_enableAccessHdlr )  {
    00844       // Fire data access incident
    00845       // I do not know if this is a good idea....
    00846       // This fires too often!
    00847       //
    00848       //DataIncident incident(name(), m_accessName, pEntry->identifier());
    00849       //m_incidentSvc->fireIncident(incident);
    00850       status = SUCCESS;
    00851     }
    00852     else  {
    00853       status = SUCCESS;
    00854     }
    00855   }
    00856   return status;
    00857 }
    00858
    00860 StatusCode DataSvc::retrieveObject(IRegistry* pRegistry,
    00861                                    const std::string& path,
    00862                                    DataObject*& pObject)   {
    00863   pObject = 0;
    00864   RegEntry *result = 0, *parent = CAST_REGENTRY(RegEntry*,pRegistry);
    00865   StatusCode status = retrieveEntry(parent, path, result);
    00866   if ( status.isSuccess() )   {
    00867     pObject = result->object();
    00868   }
    00869   return status;
    00870 }
    00871
    00873 StatusCode DataSvc::retrieveObject(const std::string& fullPath,
    00874                                    DataObject*& pObject)   {
    00875   IRegistry* nullDir = 0;
    00876   return retrieveObject(nullDir, fullPath, pObject);
    00877 }
    00878
    00880 StatusCode DataSvc::retrieveObject(const std::string& parentPath,
    00881                                    const std::string& objectPath,
    00882                                    DataObject*& pObject)   {
    00883   DataObject* parent = 0;
    00884   StatusCode status = retrieveObject(parentPath, parent);
    00885   if ( status.isSuccess() )   {
    00886     status = retrieveObject (parent, objectPath, pObject);
    00887   }
    00888   return status;
    00889 }
    00890
    00892 StatusCode DataSvc::retrieveObject(const std::string& parentPath,
    00893                                    int item,
    00894                                    DataObject*& pObject)   {
    00895   char buffer[32] = "/";
    00896   ::_itoa(item,&buffer[1],10);
    00897   return retrieveObject(parentPath, buffer, pObject);
    00898 }
    00899
    00901 StatusCode DataSvc::retrieveObject(DataObject* parentObj,
    00902                                    const std::string& path,
    00903                                    DataObject*& pObject)  {
    00904   IRegistry* pRegistry = (0==parentObj) ? 0 : parentObj->registry();
    00905   return retrieveObject(pRegistry, path, pObject);
    00906 }
    00907
    00909 StatusCode DataSvc::retrieveObject(DataObject* parentObj,
    00910                                    int item,
    00911                                    DataObject*& pObject)  {
    00912   char buffer[32] = "/";
    00913   ::_itoa(item,&buffer[1],10);
    00914   return retrieveObject(parentObj, buffer, pObject);
    00915 }
    00916
    00918 StatusCode DataSvc::findObject(IRegistry* pRegistry,
    00919                                const std::string& path,
    00920                                DataObject*& pObject)   {
    00921   pObject = 0;
    00922   IRegistry* pReg = (0==pRegistry) ? m_root : pRegistry;
    00923   RegEntry* root_entry = CAST_REGENTRY(RegEntry*, pReg);
    00924   if ( 0 != root_entry )    {
    00925     if ( path.length() > 0 )  {
    00926       pReg = root_entry->find(path);
    00927     }
    00928     if ( 0 == pReg )    {
    00929       return INVALID_OBJ_PATH;
    00930     }
    00931     pObject = pReg->object();
    00932   }
    00933   return (0 == pObject) ? OBJ_NOT_LOADED : IID_IDataProviderSvc_NO_ERROR;
    00934 }
    00935
    00937 StatusCode DataSvc::findObject(const std::string& path,
    00938                                DataObject*& pObject)   {
    00939   pObject = 0;
    00940   if ( checkRoot() )  {
    00941     if ( path.length() == 0 || path == m_rootName )   {
    00942       pObject = m_root->object();
    00943       return (0 == pObject) ? OBJ_NOT_LOADED : IID_IDataProviderSvc_NO_ERROR;
    00944     }
    00945     else if ( path[0] != SEPARATOR )    {
    00946       return findObject(m_rootName, path, pObject);
    00947     }
    00948     return findObject((IRegistry*)0, path, pObject);
    00949   }
    00950   return INVALID_ROOT;
    00951 }
    00952
    00954 StatusCode DataSvc::findObject(const std::string& parentPath,
    00955                                const std::string& objectPath,
    00956                                DataObject*& pObject)   {
    00957   DataObject* parent = 0;
    00958   StatusCode status = findObject(parentPath, parent);
    00959   if ( status.isSuccess() )   {
    00960     status = findObject (parent, objectPath, pObject);
    00961   }
    00962   return status;
    00963 }
    00964
    00966 StatusCode DataSvc::findObject(const std::string& parentPath,
    00967                                int item, DataObject*& pObject)   {
    00968   char buffer[32] = "/";
    00969   ::_itoa(item,&buffer[1],10);
    00970   return findObject(parentPath, buffer, pObject);
    00971 }
    00972
    00974 StatusCode DataSvc::findObject(DataObject* parentObj,
    00975                                int item,
    00976                                DataObject*& pObject)    {
    00977   char buffer[32] = "/";
    00978   ::_itoa(item,&buffer[1],10);
    00979   return findObject(parentObj, buffer, pObject);
    00980 }
    00981
    00983 StatusCode DataSvc::findObject(DataObject* parentObj,
    00984                                const std::string& path,
    00985                                DataObject*& pObject)    {
    00986   IRegistry* pDir = (0==parentObj) ? 0 : parentObj->registry();
    00987   return findObject(pDir, path, pObject);
    00988 }
    00989
    00991 StatusCode DataSvc::updateObject(const std::string& updatePath)   {
    00992   DataObject* pO = 0;
    00993   StatusCode status = findObject(updatePath, pO);
    00994   if ( status.isSuccess() )   {
    00995     return updateObject(pO);
    00996   }
    00997   return retrieveObject(updatePath, pO);
    00998 }
    00999
    01001 StatusCode DataSvc::updateObject(IRegistry* pRegistry)    {
    01002   if ( 0 == pRegistry )  {                     // Precondition:
    01003     return INVALID_OBJ_ADDR;                   // Addres must be valid
    01004   }
    01005   DataObject* toUpdate = pRegistry->object();
    01006   if ( 0 == toUpdate )  {                      // Try first to load
    01007     return loadObject(pRegistry);
    01008   }
    01009   return updateObject(toUpdate);
    01010 }
    01011
    01013 StatusCode DataSvc::updateObject(DataObject* toUpdate)    {
    01014   StatusCode status = INVALID_OBJ_ADDR;
    01015   if ( 0 == toUpdate )  {                          // Precondition:
    01016     return INVALID_OBJECT;                         // Address must be valid
    01017   }
    01018   IRegistry* pRegistry = toUpdate->registry();     // Precondition:
    01019   if ( 0 == pRegistry )    {                       // Need valid registry
    01020     return INVALID_OBJECT;
    01021   }
    01022   IOpaqueAddress* pAddress = pRegistry->address(); // Precondition:
    01023   if ( 0 == pAddress )    {                        // Need valid address
    01024     return INVALID_OBJ_ADDR;
    01025   }
    01026   IConversionSvc* pLoader = getDataLoader(pRegistry);
    01027   if ( 0 == pLoader )   {                      // Precondition:
    01028     return NO_DATA_LOADER;                     // Data loader must be present
    01029   }
    01030   if ( m_inhibitPathes.size() > 0 )   {
    01031     const std::string& ident = pRegistry->identifier();
    01032     std::vector<std::string>::iterator inhibit =
    01033       std::find(m_inhibitPathes.begin(), m_inhibitPathes.end(), ident);
    01034     if ( inhibit != m_inhibitPathes.end() )   {
    01035       return NO_ACCESS;
    01036     }
    01037   }
    01038   try   {
    01039     status = pLoader->updateObj(pAddress, toUpdate);  // Call data loader
    01040     if ( status.isSuccess() )   {
    01041       status = pLoader->updateObjRefs(pAddress, toUpdate);
    01042     }
    01043   }
    01044   catch( const GaudiException& exc ) {
    01045     throw GaudiException("GaudiException in updateObject() " +
    01046                          pRegistry->name(),
    01047                          name(),
    01048                          StatusCode::FAILURE, exc);
    01049   }
    01050   catch( const std::exception& x) {
    01051     throw GaudiException("std::exception in updateObject() " +
    01052                          pRegistry->name() + ": " +
    01053                          System::typeinfoName(typeid(x)) + ", " +
    01054                          x.what(),
    01055                          name(), StatusCode::FAILURE);
    01056   }
    01057   catch(...) {
    01058     throw GaudiException("UNKN exception in updateObject() " +
    01059                          pRegistry->name(),
    01060       name(), StatusCode::FAILURE);
    01061   }
    01062   return status;
    01063 }
    01064
    01066 StatusCode DataSvc::updateObject(const std::string& parentPath,
    01067                                  const std::string& updatePath)    {
    01068   DataObject* pParent = 0;
    01069   StatusCode status = findObject(parentPath, pParent);
    01070   if ( status.isSuccess() )   {
    01071     status = updateObject( pParent, updatePath);
    01072   }
    01073   return status;
    01074 }
    01075
    01077 StatusCode DataSvc::updateObject(DataObject* parent,
    01078                                  const std::string& updatePath)   {
    01079   DataObject* pObject = 0;
    01080   StatusCode status = findObject(parent, updatePath, pObject);
    01081   if ( status.isSuccess() )   {
    01082     status = updateObject(pObject);
    01083   }
    01084   return status;
    01085 }
    01086
    01087 // Link object
    01088 StatusCode DataSvc::linkObject(IRegistry* from,
    01089                                const std::string& objPath, DataObject* to) {
    01090   if ( checkRoot() )  {
    01091     try   {
    01092       RegEntry* from_entry = CAST_REGENTRY(RegEntry*,from);
    01093       if ( 0 != from_entry )    {
    01094         // First check if both objects are already registered to the store
    01095         RegEntry* to_entry   = m_root->findLeaf(to);
    01096         if ( 0 == to_entry )   {
    01097           return INVALID_OBJECT;
    01098         }
    01099         else  {
    01100           std::string::size_type sep = objPath.rfind(SEPARATOR);
    01101           if ( sep > 0 && sep != std::string::npos )    {   // in case the objPath is a sub-directory itself
    01102             DataObject* pO = 0;
    01103             std::string fromPath(objPath, 0, sep);
    01104             StatusCode sc = retrieveObject(from, fromPath, pO);
    01105             if ( sc.isSuccess() )    {
    01106               std::string toPath(objPath, sep, objPath.length());
    01107               sc = linkObject(pO->registry(), toPath, to);
    01108             }
    01109             return sc;
    01110           }
    01111           // Now register the soft link
    01112           StatusCode status = from_entry->add( objPath, to, true);
    01113           return status.isSuccess() ?
    01114             IID_IDataProviderSvc_NO_ERROR : DOUBL_OBJ_PATH;
    01115         }
    01116       }
    01117     }
    01118     catch (...) {
    01119     }
    01120     return INVALID_PARENT;
    01121   }
    01122   return INVALID_ROOT;
    01123 }
    01124
    01126 StatusCode DataSvc::linkObject(const std::string& fullPath,
    01127                                DataObject* to)    {
    01128   if ( fullPath.length() > 0 )    {
    01129     if ( fullPath[0] != SEPARATOR )   {
    01130       return linkObject(m_rootName, fullPath, to);
    01131     }
    01132     std::string::size_type sep = fullPath.rfind(SEPARATOR);
    01133     std::string objPath(fullPath, sep, fullPath.length());
    01134     std::string fromPath(fullPath, 0, sep);
    01135     return linkObject( fromPath, objPath, to);
    01136   }
    01137   return INVALID_OBJ_PATH;
    01138 }
    01139
    01141 StatusCode DataSvc::linkObject(const std::string& from,
    01142                                const std::string& objPath,
    01143                                DataObject* to)    {
    01144   DataObject* pO = 0;
    01145   StatusCode status = retrieveObject(from, pO);
    01146   if ( status.isSuccess() )   {
    01147     return linkObject(pO->registry(), objPath, to);
    01148   }
    01149   return status;
    01150 }
    01151
    01153 StatusCode DataSvc::linkObject(DataObject* from,
    01154                                const std::string& objPath,
    01155                                DataObject* to)    {
    01156   if ( 0 != from )    {
    01157     IRegistry* from_entry = from->registry();
    01158     if ( 0 != from_entry )   {
    01159       return linkObject( from_entry, objPath, to);
    01160     }
    01161   }
    01162   return INVALID_PARENT;
    01163 }
    01164
    01166 StatusCode DataSvc::unlinkObject(IRegistry* from,
    01167                                  const std::string& objPath)    {
    01168   if ( checkRoot() )  {
    01169     try   {
    01170       RegEntry* from_entry = CAST_REGENTRY(RegEntry*,from);
    01171       if ( 0 != from_entry )    {
    01172         std::string::size_type sep = objPath.rfind(SEPARATOR);
    01173         if ( sep > 0 && sep != std::string::npos )    {  // in case the objPath is a sub-directory itself
    01174           DataObject* pO = 0;
    01175           std::string fromPath(objPath, 0, sep);
    01176           StatusCode sc = findObject(from, fromPath, pO);
    01177           if ( sc.isSuccess() )    {
    01178             std::string toPath(objPath, sep, objPath.length());
    01179             sc = unlinkObject(pO->registry(), toPath);
    01180           }
    01181           return sc;
    01182         }
    01183         StatusCode status = from_entry->remove( objPath );
    01184         if ( status.isSuccess() )     {
    01185           return status;
    01186         }
    01187         return INVALID_OBJ_PATH;
    01188       }
    01189     }
    01190     catch (...)   {
    01191     }
    01192     return INVALID_PARENT;
    01193   }
    01194   return INVALID_ROOT;
    01195 }
    01196
    01198 StatusCode DataSvc::unlinkObject(const std::string& fullPath)    {
    01199   if ( fullPath.length() > 0 )    {
    01200     if ( fullPath[0] != SEPARATOR )   {
    01201       return unlinkObject(m_rootName, fullPath);
    01202     }
    01203     std::string::size_type sep = fullPath.rfind(SEPARATOR);
    01204     std::string objPath(fullPath, sep, fullPath.length());
    01205     std::string fromPath(fullPath, 0, sep);
    01206     return unlinkObject(fromPath, objPath);
    01207   }
    01208   return INVALID_OBJ_PATH;
    01209 }
    01210
    01212 StatusCode DataSvc::unlinkObject(const std::string& from,
    01213                                  const std::string& objPath)    {
    01214   DataObject* pObject = 0;
    01215   StatusCode status = findObject(from, pObject);
    01216   if ( status.isSuccess() )   {
    01217     status = unlinkObject(pObject->registry(), objPath);
    01218   }
    01219   return status;
    01220 }
    01221
    01223 StatusCode DataSvc::unlinkObject(DataObject* from,
    01224                                  const std::string& objPath)    {
    01225   if ( checkRoot() )  {
    01226     IRegistry* from_entry = m_root->findLeaf(from);
    01227     return unlinkObject(from_entry, objPath);
    01228   }
    01229   return INVALID_ROOT;
    01230 }
    01231
    01233 StatusCode DataSvc::addPreLoadItem(const DataStoreItem& item)    {
    01234   LoadItems::iterator i = std::find(m_preLoads.begin(), m_preLoads.end(), item);
    01235   if ( i == m_preLoads.end() )    {
    01236     m_preLoads.push_back(item);
    01237   }
    01238   return StatusCode::SUCCESS;
    01239 }
    01240
    01242 StatusCode DataSvc::addPreLoadItem(const std::string& itemPath)    {
    01243   return addPreLoadItem( DataStoreItem(itemPath,1) );
    01244 }
    01245
    01247 StatusCode DataSvc::removePreLoadItem(const DataStoreItem& item)   {
    01248   LoadItems::iterator i =
    01249     std::remove(m_preLoads.begin(), m_preLoads.end(), item);
    01250   if ( i != m_preLoads.end() )  {
    01251     m_preLoads.erase(i, m_preLoads.end());
    01252   }
    01253   return StatusCode::SUCCESS;
    01254 }
    01255
    01257 StatusCode DataSvc::removePreLoadItem(const std::string& itemPath)    {
    01258   return removePreLoadItem( DataStoreItem(itemPath,1) );
    01259 }
    01260
    01262 StatusCode DataSvc::resetPreLoad()    {
    01263   m_preLoads.erase(m_preLoads.begin(), m_preLoads.end());
    01264   return StatusCode::SUCCESS;
    01265 }
    01266
    01268 StatusCode DataSvc::preLoad(int depth, int load_depth, DataObject* pObject)    {
    01269   //unused:  StatusCode sc = StatusCode::FAILURE;
    01270   if ( 0 != pObject && depth++ < load_depth )    {
    01271     RegEntry* dir = CAST_REGENTRY(RegEntry*,pObject->registry());
    01272     if ( 0 != dir )   {
    01273       for (RegEntry::Iterator i = dir->begin(); i != dir->end(); i++ )    {
    01274         DataObject *pObj = 0;
    01275         StatusCode status = retrieveObject(pObject, (*i)->name(), pObj);
    01276         if ( status.isSuccess() && depth < load_depth )   {
    01277           preLoad(depth, load_depth, pObj).ignore();
    01278         }
    01279       }
    01280     }
    01281   }
    01282   return StatusCode::SUCCESS;
    01283 }
    01284
    01286 StatusCode DataSvc::preLoad()   {
    01287   DataObject* pObj = 0;
    01288   for (LoadItems::iterator i = m_preLoads.begin(); i != m_preLoads.end(); i++) {
    01289     StatusCode sc = retrieveObject( (*i).path(), pObj);
    01290     int load_depth = (*i).depth();
    01291     if ( sc.isSuccess() && load_depth > 1 )   {
    01292       preLoad(1, load_depth, pObj).ignore();
    01293     }
    01294   }
    01295   return StatusCode::SUCCESS;
    01296 }
    01297
    01299 StatusCode DataSvc::queryInterface(const InterfaceID& riid, void** ppvInterface)  {
    01300   if ( IID_IDataProviderSvc.versionMatch(riid) )  {
    01301     *ppvInterface = (IDataProviderSvc*)this;
    01302     addRef();
    01303     return SUCCESS;
    01304   }
    01305   else if ( IID_IDataManagerSvc.versionMatch(riid) )   {
    01306     *ppvInterface = (IDataManagerSvc*)this;
    01307     addRef();
    01308     return SUCCESS;
    01309   }
    01310   return Service::queryInterface(riid, ppvInterface);
    01311 }
    01312
    01314 StatusCode DataSvc::initialize()    {
    01315   // Nothing to do: just call base class initialisation
    01316   StatusCode sc = Service::initialize();
    01317   if ( !sc.isSuccess() )  {
    01318     return sc;
    01319   }
    01320   sc = service("IncidentSvc", m_incidentSvc, true);
    01321   if ( !sc.isSuccess() )  {
    01322     MsgStream log(msgSvc(), name());
    01323     log << MSG::ERROR << "Failed to access incident service." << endmsg;
    01324   }
    01325   return sc;
    01326 }
    01327
    01329 StatusCode DataSvc::reinitialize()    {
    01330   StatusCode sc;
    01331   // the finalize part is copied here
    01332   setDataLoader(0).ignore();
    01333   resetPreLoad().ignore();
    01334   clearStore().ignore();
    01335   if ( m_incidentSvc )  {
    01336     m_incidentSvc->release();
    01337     m_incidentSvc = 0;
    01338   }
    01339   // re-initialize the base class
    01340   sc = Service::reinitialize();
    01341   if (!sc.isSuccess()) {
    01342     MsgStream log(msgSvc(), name());
    01343     log << MSG::ERROR << "Unable to reinitialize base class" << endreq;
    01344     return sc;
    01345   }
    01346   // the initialize part is copied here
    01347   sc = service("IncidentSvc", m_incidentSvc, true);
    01348   if ( !sc.isSuccess() )  {
    01349     MsgStream log(msgSvc(), name());
    01350     log << MSG::ERROR << "Failed to access incident service." << endmsg;
    01351     return sc;
    01352   }
    01353   // return
    01354   return StatusCode::SUCCESS;
    01355 }
    01356
    01358 StatusCode DataSvc::finalize()    {
    01359   // Nothing to do: just call base class initialisation
    01360   setDataLoader(0).ignore();
    01361   resetPreLoad().ignore();
    01362   clearStore().ignore();
    01363   if ( m_incidentSvc )  {
    01364     m_incidentSvc->release();
    01365     m_incidentSvc = 0;
    01366   }
    01367   return Service::finalize();
    01368 }
    01369
    01371 CLID DataSvc::rootCLID() const {
    01372   return( (CLID)m_rootCLID );
    01373 }
    01374
    01376 std::string DataSvc::rootName() const {
    01377   return( m_rootName );
    01378 }
    01379
    01381 DataObject* DataSvc::createDefaultObject()   const    {
    01382   return new DataObject();
    01383 }
    01384
    01388 IConversionSvc* DataSvc::getDataLoader(IRegistry* /* pReg */)   {
    01389   return m_dataLoader;
    01390 }
    01391
    01393 DataSvc::DataSvc(const std::string& name,ISvcLocator* svc)
    01394 : Service(name,svc), m_rootCLID( /*CLID_Event*/ 110),
    01395   m_rootName( "/Event"), m_root(0)
    01396 {
    01397   m_dataLoader = 0;
    01398   m_inhibitMap = 0;
    01399   m_incidentSvc = 0;
    01400   m_forceLeaves = false;
    01401   m_enableFaultHdlr = false;
    01402   m_enableAccessHdlr = false;
    01403   m_faultName  = "DataFault";
    01404   m_accessName = "DataAccess";
    01405   declareProperty("RootCLID",            m_rootCLID);
    01406   declareProperty("RootName",            m_rootName);
    01407   declareProperty("ForceLeaves",         m_forceLeaves);
    01408   declareProperty("InhibitPathes",       m_inhibitPathes);
    01409   declareProperty("DataFaultName",       m_faultName);
    01410   declareProperty("DataAccessName",      m_accessName);
    01411   declareProperty("EnableFaultHandler",  m_enableFaultHdlr);
    01412   declareProperty("EnableAccessHandler", m_enableAccessHdlr);
    01413 }
    01414
    01416 DataSvc::~DataSvc()  {
    01417   setDataLoader(0).ignore();
    01418   resetPreLoad().ignore();
    01419   clearStore().ignore();
    01420 }