The Gaudi Framework  v30r3 (a5ef0a68)
TsDataSvc.cpp
Go to the documentation of this file.
1 //====================================================================
2 // TsDataSvc.cpp
3 //--------------------------------------------------------------------
4 //
5 // Package : System ( The LHCb Offline System)
6 //
7 // Description: implementation of the Transient data service: TsDataSvc
8 //
9 // Author : M.Frank
10 // History :
11 // +---------+----------------------------------------------+---------
12 // | Date | Comment | Who
13 // +---------+----------------------------------------------+---------
14 // | 29/10/98| Initial version | M.Frank
15 // | 20/2/99 | Automatic data preloading introduced. | M.Frank
16 // | 25/4/13 | Locking for concurrent access introduced. | D.Piparo
17 // +---------+----------------------------------------------+---------
18 //
19 //====================================================================
20 #define TSDATASVC_DATASVC_CPP
21 
22 // Framework include files
24 #include "GaudiKernel/IConverter.h"
26 
27 #include "GaudiKernel/DataObject.h"
29 #include "GaudiKernel/xtoa.h"
30 
34 #include "GaudiKernel/TsDataSvc.h"
35 
36 // Include files
37 #include <algorithm>
38 #include <cassert>
39 #include <cstdlib>
40 #include <mutex>
41 #include <sstream>
42 #include <vector>
43 
44 // Macro to lock a scope
45 #define STD_LOCK_GUARD_MACRO std::lock_guard<tsDataSvcMutex> lock( m_accessMutex );
46 
47 namespace
48 {
51  std::string itemToPath( int item ) { return '/' + std::to_string( item ); }
52 
53  std::string operator+( char c, boost::string_ref sr )
54  {
55  std::string s{c};
56  s.append( sr.data(), sr.size() );
57  return s;
58  }
59 
60  boost::string_ref::size_type find( boost::string_ref s, char c, size_t o )
61  {
62  if ( !s.empty() ) s.remove_prefix( o );
63  auto r = s.find( c );
64  return r == boost::string_ref::npos ? r : ( r + o );
65  }
66 
67  std::string to_string( boost::string_ref sr ) { return {sr.data(), sr.size()}; }
68 }
69 
70 // If you absolutely need optimization: switch off dynamic_cast.
71 // This improves access to the data store roughly by 10 %
72 // for balanced trees.
73 //
74 // M.Frank
75 #define CAST_REGENTRY( x, y ) dynamic_cast<x>( y )
76 //#define CAST_REGENTRY(x,y) (x)(y)
78 
79 #define ON_DEBUG if ( msgLevel( MSG::DEBUG ) )
80 #define ON_VERBOSE if ( msgLevel( MSG::VERBOSE ) )
81 
82 #define DEBMSG ON_DEBUG debug()
83 #define VERMSG ON_VERBOSE verbose()
84 
88 StatusCode TsDataSvc::clearSubTree( boost::string_ref sub_tree_path )
89 {
90  DataObject* pObject = nullptr;
91  StatusCode status = findObject( sub_tree_path, pObject );
92  if ( !status.isSuccess() ) return status;
93  RegEntry* node_entry = CAST_REGENTRY( RegEntry*, pObject->registry() );
94  if ( !node_entry ) return Status::INVALID_OBJECT;
95  RegEntry* parent = node_entry->parentEntry();
96  if ( !parent ) return Status::INVALID_PARENT;
97  parent->remove( node_entry );
98  return StatusCode::SUCCESS;
99 }
100 
105 {
106  if ( !checkRoot() ) return Status::INVALID_ROOT;
107  RegEntry* entry = CAST_REGENTRY( RegEntry*, pObject->registry() );
108  if ( !entry ) return Status::INVALID_OBJECT;
109  RegEntry* parent = entry->parentEntry();
110  if ( !parent ) return Status::INVALID_PARENT;
111  parent->remove( entry );
112  return StatusCode::SUCCESS;
113 }
114 
117 {
118  if ( !checkRoot() ) return Status::INVALID_ROOT;
119  m_root->release();
120  m_root = nullptr;
121  return StatusCode::SUCCESS;
122 }
123 
127 StatusCode TsDataSvc::traverseSubTree( boost::string_ref sub_tree_path, IDataStoreAgent* pAgent )
128 {
130  DataObject* pO = nullptr;
131  StatusCode status = findObject( sub_tree_path, pO );
132  return status.isSuccess() ? traverseSubTree( pO, pAgent ) : status;
133 }
134 
137 {
139  if ( !checkRoot() ) return Status::INVALID_ROOT;
140  RegEntry* entry = CAST_REGENTRY( RegEntry*, pObject->registry() );
141  if ( !entry ) return Status::INVALID_OBJECT;
142  return entry->traverseTree( pAgent );
143 }
144 
147 {
149  if ( !checkRoot() ) return Status::INVALID_ROOT;
150  return m_root->traverseTree( pAgent );
151 }
152 
158 {
159  clearStore().ignore();
160  return i_setRoot( std::move( root_path ), pRootObj );
161 }
162 
169 {
170  if ( pRootObj ) {
171  m_root = new RegEntry( std::move( root_path ) );
172  m_root->makeHard( pRootObj );
173  m_root->setDataSvc( this );
174  // No done with GaudiHive. preLoad().ignore();
175  }
176  return StatusCode::SUCCESS;
177 }
178 
184 {
185  clearStore().ignore();
186  return i_setRoot( std::move( root_path ), pRootAddr );
187 }
188 
195 {
196  if ( pRootAddr ) {
197  m_root = new RegEntry( std::move( root_path ) );
198  m_root->makeHard( pRootAddr );
199  m_root->setDataSvc( this );
200  // Not done with GaudiHive. preLoad().ignore();
201  }
202  return StatusCode::SUCCESS;
203 }
204 
207 {
208  if ( pDataLoader ) pDataLoader->addRef();
210  if ( pDataLoader ) {
211  pDataLoader->setDataProvider( dpsvc == nullptr ? this : dpsvc ).ignore();
212  }
213  m_dataLoader = pDataLoader;
214  return StatusCode::SUCCESS;
215 }
216 
219 {
221  if ( !pObject ) return Status::INVALID_OBJECT;
222  return objectParent( pObject->registry(), refpParent );
223 }
225 StatusCode TsDataSvc::objectParent( const IRegistry* pRegistry, IRegistry*& refpParent )
226 {
228  if ( !checkRoot() ) return Status::INVALID_ROOT;
229  const RegEntry* node_entry = CAST_REGENTRY( const RegEntry*, pRegistry );
230  if ( !node_entry ) return Status::INVALID_OBJECT;
231  refpParent = node_entry->parent();
232  return StatusCode::SUCCESS;
233 }
234 
237 {
239  if ( !pObject ) return Status::INVALID_OBJECT;
240  return objectLeaves( pObject->registry(), leaves );
241 }
242 
247 {
249  if ( !checkRoot() ) return Status::INVALID_ROOT;
250  const RegEntry* node_entry = CAST_REGENTRY( const RegEntry*, pRegistry );
251  if ( !node_entry ) return Status::INVALID_OBJECT;
252  leaves.insert( leaves.end(), node_entry->leaves().begin(), node_entry->leaves().end() );
253  // leaves = node_entry->leaves();
254  return StatusCode::SUCCESS;
255 }
256 
258 StatusCode TsDataSvc::registerAddress( boost::string_ref fullPath, IOpaqueAddress* pAddress )
259 {
260  if ( fullPath.empty() ) return Status::INVALID_OBJ_PATH;
261  if ( fullPath.front() != SEPARATOR ) {
262  return registerAddress( m_root, fullPath, pAddress );
263  }
264  IRegistry* pRegistry = nullptr;
265  return registerAddress( pRegistry, fullPath, pAddress );
266 }
267 
269 StatusCode TsDataSvc::registerAddress( DataObject* parentObj, boost::string_ref objectPath, IOpaqueAddress* pAddress )
270 {
271  IRegistry* pRegistry = ( parentObj ? parentObj->registry() : nullptr );
272  return registerAddress( pRegistry, objectPath, pAddress );
273 }
274 
276 StatusCode TsDataSvc::registerAddress( IRegistry* parentObj, boost::string_ref objPath, IOpaqueAddress* pAddress )
277 {
278  if ( !checkRoot() ) return Status::INVALID_ROOT;
279  if ( objPath.empty() ) return Status::INVALID_OBJ_PATH;
280  if ( !parentObj ) {
281  if ( objPath.front() != SEPARATOR ) {
282  return registerAddress( m_root, objPath, pAddress );
283  }
284  auto sep = find( objPath, SEPARATOR, 1 );
285  if ( sep == boost::string_ref::npos || objPath.substr( 0, sep ) != m_rootName.value() ) {
286  return Status::INVALID_PARENT;
287  }
288  return registerAddress( m_root, objPath.substr( sep ), pAddress );
289  }
290  if ( objPath.front() != SEPARATOR ) {
291  return registerAddress( parentObj, SEPARATOR + objPath, pAddress );
292  }
293  RegEntry* par_entry = CAST_REGENTRY( RegEntry*, parentObj );
294  if ( !par_entry ) return Status::INVALID_PARENT;
295  auto sep = objPath.rfind( SEPARATOR );
296  if ( sep > 0 && sep != boost::string_ref::npos ) {
297  auto p_path = objPath.substr( 0, sep );
298  auto o_path = objPath.substr( sep );
299  RegEntry* p_entry = par_entry->findLeaf( p_path );
300  // Create default object leafs if the
301  // intermediate nodes are not present
302  if ( !p_entry && m_forceLeaves ) {
303  DataObject* pLeaf = createDefaultObject();
304  StatusCode sc = registerObject( par_entry->identifier(), p_path, pLeaf );
305  if ( !sc.isSuccess() ) delete pLeaf;
306  p_entry = par_entry->findLeaf( p_path );
307  }
308  if ( !p_entry ) return Status::INVALID_PARENT;
309  return registerAddress( p_entry, o_path, pAddress );
310  }
311  StatusCode status = par_entry->add( to_string( objPath ), pAddress );
312  return status.isSuccess() ? status : Status::DOUBL_OBJ_PATH;
313 }
314 
316 StatusCode TsDataSvc::unregisterAddress( boost::string_ref fullPath )
317 {
318  if ( fullPath.empty() ) return Status::INVALID_OBJ_PATH;
319  IRegistry* pRegistry = nullptr;
320  if ( fullPath.front() != SEPARATOR ) {
321  return unregisterAddress( m_root, fullPath );
322  }
323  return unregisterAddress( pRegistry, fullPath );
324 }
325 
327 StatusCode TsDataSvc::unregisterAddress( DataObject* pParent, boost::string_ref objPath )
328 {
329  IRegistry* pRegistry = ( pParent ? pParent->registry() : nullptr );
330  return unregisterAddress( pRegistry, objPath );
331 }
332 
334 StatusCode TsDataSvc::unregisterAddress( IRegistry* pParent, boost::string_ref objPath )
335 {
336  if ( !checkRoot() ) return Status::INVALID_ROOT;
337 
338  if ( objPath.empty() ) return Status::INVALID_OBJ_PATH;
339  if ( !pParent ) {
340  if ( objPath.front() != SEPARATOR ) {
341  return unregisterAddress( m_root, objPath );
342  }
343  auto sep = find( objPath, SEPARATOR, 1 );
344  if ( sep == boost::string_ref::npos || objPath.substr( 0, sep ) != m_rootName.value() ) {
345  return Status::INVALID_PARENT;
346  }
347  return unregisterAddress( m_root, objPath.substr( sep ) );
348  }
349  if ( objPath.front() != SEPARATOR ) {
350  return unregisterAddress( pParent, SEPARATOR + objPath );
351  }
352  RegEntry* node_entry = CAST_REGENTRY( RegEntry*, pParent );
353  if ( node_entry ) {
354  RegEntry* leaf_entry = node_entry->findLeaf( objPath );
355  if ( leaf_entry ) {
356  auto sep = objPath.rfind( SEPARATOR );
357  if ( sep > 0 && sep != boost::string_ref::npos ) {
358  return unregisterAddress( leaf_entry->parent(), objPath.substr( sep ) );
359  }
360  StatusCode status = node_entry->remove( objPath );
361  if ( status.isSuccess() ) return status;
362  }
363  }
364  return Status::INVALID_PARENT;
365 }
366 
368 StatusCode TsDataSvc::registerObject( boost::string_ref fullPath, DataObject* pObject )
369 {
370  return registerObject( nullptr, fullPath, pObject );
371 }
372 
374 StatusCode TsDataSvc::registerObject( boost::string_ref parentPath, boost::string_ref objPath, DataObject* pObject )
375 {
376  DataObject* pO = nullptr;
377  StatusCode status = retrieveObject( parentPath, pO );
378  if ( !status.isSuccess() && m_forceLeaves ) {
379  pO = createDefaultObject();
380  status = registerObject( parentPath, pO );
381  if ( !status.isSuccess() ) pO->release();
382  }
383  return status.isSuccess() ? registerObject( pO, objPath, pObject ) : status;
384 }
385 
387 StatusCode TsDataSvc::registerObject( boost::string_ref parentPath, int item, DataObject* pObject )
388 {
389  return registerObject( parentPath, itemToPath( item ), pObject );
390 }
391 
394 {
395  return registerObject( parentObj, itemToPath( item ), pObject );
396 }
397 
399 StatusCode TsDataSvc::registerObject( DataObject* parentObj, boost::string_ref objPath, DataObject* pObject )
400 {
401  if ( !checkRoot() ) return Status::INVALID_ROOT;
402  if ( !parentObj ) {
403  if ( !objPath.empty() ) {
404  if ( objPath.front() != SEPARATOR ) {
405  return registerObject( m_rootName.value(), objPath, pObject );
406  }
407  auto sep = find( objPath, SEPARATOR, 1 );
408  if ( sep != boost::string_ref::npos ) {
409  return registerObject( objPath.substr( 0, sep ), objPath.substr( sep ), pObject );
410  }
411  }
412  return Status::INVALID_OBJ_PATH;
413  }
414  RegEntry* node_entry = CAST_REGENTRY( RegEntry*, parentObj->registry() );
415  if ( node_entry ) {
416  StatusCode status = Status::INVALID_PARENT;
417  auto sep = find( objPath, SEPARATOR, 1 );
418  if ( sep != boost::string_ref::npos ) {
419  auto p_path = objPath.substr( 0, sep );
420  auto o_path = objPath.substr( sep );
421  RegEntry* par_entry = node_entry->findLeaf( p_path );
422  // Create default object leafs if the
423  // intermediate nodes are not present
424  if ( !par_entry && m_forceLeaves ) {
425  DataObject* pLeaf = createDefaultObject();
426  StatusCode sc = registerObject( parentObj, p_path, pLeaf );
427  if ( !sc.isSuccess() ) delete pLeaf;
428  par_entry = node_entry->findLeaf( p_path );
429  } else if ( par_entry && !par_entry->object() ) {
430  status = retrieveEntry( node_entry, p_path, par_entry );
431  if ( !status.isSuccess() && !par_entry->address() && m_forceLeaves ) {
432  DataObject* pLeaf = createDefaultObject();
433  StatusCode sc = registerObject( parentObj, p_path, pLeaf );
434  if ( !sc.isSuccess() ) delete pLeaf;
435  par_entry = node_entry->findLeaf( p_path );
436  }
437  }
438  node_entry = par_entry;
439  if ( node_entry ) {
440  DataObject* obj = node_entry->object();
441  if ( obj ) status = registerObject( obj, o_path, pObject );
442  }
443  } else {
444  RegEntry* leaf = node_entry->findLeaf( objPath );
445  if ( !leaf ) {
446  status = node_entry->add( to_string( objPath ), pObject );
447  } else {
448  DataObject* obj = leaf->object();
449  if ( !obj ) {
450  if ( !pObject ) {
451  error() << "registerObject: trying to register null DataObject" << endmsg;
452  return StatusCode::FAILURE;
453  } else {
454  pObject->setRegistry( leaf );
455  }
456  leaf->setAddress( nullptr );
457  leaf->setObject( pObject );
458  status = StatusCode::SUCCESS;
459  } else {
460  status = Status::DOUBL_OBJ_PATH;
461  }
462  }
463  }
464  return status;
465  }
466  return Status::INVALID_PARENT;
467 }
468 
470 StatusCode TsDataSvc::unregisterObject( boost::string_ref fullPath )
471 {
472  DataObject* pObject = nullptr;
473  StatusCode status = findObject( fullPath, pObject );
474  if ( status.isFailure() ) return status;
475  RegEntry* pEntry = CAST_REGENTRY( RegEntry*, pObject->registry() );
476  if ( !pEntry ) return Status::INVALID_ROOT;
477  if ( !pEntry->isEmpty() ) return Status::DIR_NOT_EMPTY;
478  RegEntry* pParent = pEntry->parentEntry();
479  if ( !pParent ) return Status::INVALID_PARENT;
480  if ( pObject ) pObject->addRef();
481  pParent->remove( pEntry );
482  return StatusCode::SUCCESS;
483 }
484 
486 StatusCode TsDataSvc::unregisterObject( boost::string_ref parentPath, boost::string_ref objPath )
487 {
488  DataObject* pO = nullptr;
489  StatusCode status = findObject( parentPath, pO );
490  return status.isSuccess() ? unregisterObject( pO, objPath ) : status;
491 }
492 
494 StatusCode TsDataSvc::unregisterObject( boost::string_ref parentPath, int item )
495 {
496  return unregisterObject( parentPath, itemToPath( item ) );
497 }
498 
501 {
502  if ( !checkRoot() ) return Status::INVALID_ROOT;
503  RegEntry* entry = m_root->findLeaf( pObject );
504  if ( !entry ) return Status::INVALID_OBJECT;
505  RegEntry* parent = entry->parentEntry();
506  if ( !parent ) return Status::INVALID_PARENT;
507  if ( !entry->isEmpty() ) return Status::DIR_NOT_EMPTY;
508  if ( entry->object() ) entry->object()->addRef();
509  if ( parent ) parent->remove( entry );
510  return StatusCode::SUCCESS;
511 }
512 
514 StatusCode TsDataSvc::unregisterObject( DataObject* pParentObj, boost::string_ref objectPath )
515 {
516  if ( !checkRoot() ) return Status::INVALID_ROOT;
517  try {
518  RegEntry* parent = CAST_REGENTRY( RegEntry*, pParentObj->registry() );
519  if ( parent ) {
520  RegEntry* entry = parent->findLeaf( objectPath );
521  if ( !entry ) return Status::INVALID_OBJECT;
522  if ( !entry->isEmpty() ) return Status::DIR_NOT_EMPTY;
523  if ( entry->object() ) entry->object()->addRef();
524  parent->remove( entry );
525  return StatusCode::SUCCESS;
526  }
527  } catch ( ... ) {
528  }
529  return Status::INVALID_PARENT;
530 }
531 
534 {
535  return unregisterObject( pParentObj, itemToPath( item ) );
536 }
537 
541 {
542  if ( m_enableFaultHdlr ) {
543  IRegistry* pLeaf = nullptr;
544  if ( pReg && path.empty() ) {
545  DataIncident incident( name(), m_faultName, pReg->identifier() );
546  m_incidentSvc->fireIncident( incident );
547  return pReg->object();
548  } else if ( pReg ) {
549  std::string p = pReg->identifier();
550  if ( path.front() != SEPARATOR ) p += SEPARATOR;
551  p.append( path.data(), path.size() );
552  DataIncident incident( name(), m_faultName, p );
553  m_incidentSvc->fireIncident( incident );
554  pLeaf = m_root->findLeaf( p );
555  } else {
557  if ( path.front() != SEPARATOR ) p += SEPARATOR;
558  p.append( path.data(), path.size() );
559  DataIncident incident( name(), m_faultName, p );
560  m_incidentSvc->fireIncident( incident );
561  pLeaf = m_root->findLeaf( p );
562  }
563  if ( pLeaf ) return pLeaf->object();
564  }
565  return nullptr;
566 }
567 
572 {
573  IConversionSvc* pLoader = getDataLoader( pRegistry );
574  return loadObject( pLoader, pRegistry );
575 }
576 
581 {
583  StatusCode status = Status::INVALID_OBJ_ADDR;
584  DataObject* pObject = nullptr;
585  if ( !pLoader ) { // Precondition: Data loader must be present
586  if ( handleDataFault( pRegistry ) )
587  return StatusCode::SUCCESS;
588  else
589  return Status::NO_DATA_LOADER;
590  }
591  if ( !pRegistry ) { // Precondition: Directory must be valid
592  if ( handleDataFault( pRegistry ) )
593  return StatusCode::SUCCESS;
594  else
595  return Status::INVALID_OBJ_ADDR;
596  }
597 
598  VERMSG << "Requested object " << pRegistry->identifier() << endmsg;
599 
600  if ( m_enableAccessHdlr ) {
601  // Fire data access incident
602  DataIncident incident( name(), m_accessName, pRegistry->identifier() );
603  m_incidentSvc->fireIncident( incident );
604  }
605  if ( !m_inhibitPathes.empty() ) {
606  const auto& ident = pRegistry->identifier();
607  auto inhibit = std::find( m_inhibitPathes.begin(), m_inhibitPathes.end(), ident );
608  if ( inhibit != m_inhibitPathes.end() ) return Status::NO_ACCESS;
609  }
610  IOpaqueAddress* pAddress = pRegistry->address();
611  if ( !pAddress ) { // Precondition:
612  return Status::INVALID_OBJ_ADDR; // Address must be valid
613  }
614  try {
615  status = pLoader->createObj( pAddress, pObject ); // Call data loader
616  if ( status.isSuccess() ) {
617 
618  VERMSG << "Object " << pRegistry->identifier() << " created" << endmsg;
619 
620  RegEntry* pEntry = CAST_REGENTRY( RegEntry*, pRegistry );
621  pEntry->setObject( pObject );
622 
623  VERMSG << "Filling object " << pRegistry->identifier() << endmsg;
624  status = pLoader->fillObjRefs( pAddress, pObject );
625  }
626  } catch ( const GaudiException& exc ) {
627  if ( handleDataFault( pRegistry ) ) return StatusCode::SUCCESS;
628  throw GaudiException( "GaudiException in loadObject() " + pRegistry->identifier(), name(), StatusCode::FAILURE,
629  exc );
630  } catch ( const std::exception& x ) {
631  if ( handleDataFault( pRegistry ) ) return StatusCode::SUCCESS;
632  throw GaudiException( "std::exception in loadObject() " + pRegistry->identifier() + ": " +
633  System::typeinfoName( typeid( x ) ) + ", " + x.what(),
635  } catch ( ... ) {
636  if ( handleDataFault( pRegistry ) ) return StatusCode::SUCCESS;
637  throw GaudiException( "UNKN exception in loadObject() " + pRegistry->identifier(), name(), StatusCode::FAILURE );
638  }
639  if ( !status.isSuccess() ) {
640  if ( handleDataFault( pRegistry ) ) return StatusCode::SUCCESS;
641  }
642  ON_VERBOSE if ( status.isSuccess() )
643  {
644  verbose() << "Object " << pRegistry->identifier() << " successfully loaded" << endmsg;
645  }
646  return status;
647 }
648 
650 StatusCode TsDataSvc::retrieveEntry( RegEntry* parentObj, boost::string_ref path, RegEntry*& pEntry )
651 {
653  auto sep = find( path, SEPARATOR, 1 );
654  StatusCode status = StatusCode( Status::INVALID_ROOT, true );
655  pEntry = nullptr;
656  // A.Valassi 16.08.2001 avoid core dump if store is empty
657  if ( checkRoot() ) {
658  if ( !parentObj ) {
659  if ( path.empty() || path == m_rootName ) return retrieveEntry( m_root, "", pEntry );
660  if ( path.front() != SEPARATOR ) return retrieveEntry( m_root, path, pEntry );
661  if ( sep == boost::string_ref::npos ) return Status::INVALID_OBJ_PATH;
662  if ( !m_root->object() ) {
663  RegEntry* r = nullptr;
664  status = retrieveEntry( m_root, "", r );
665  if ( !status.isSuccess() ) return status;
666  }
667  return retrieveEntry( m_root, path.substr( sep ), pEntry );
668  }
669  if ( sep != boost::string_ref::npos ) { // the string contains a separator (after pos 0)
670  auto p_path = path.substr( 0, sep );
671  auto o_path = path.substr( sep );
672  if ( !parentObj->object() ) { // if the parent object has not been loaded yet, load it now
673  status = loadObject( parentObj );
674  if ( !status.isSuccess() ) return status;
675  }
676  RegEntry* root_entry = parentObj->findLeaf( p_path );
677  if ( !root_entry && m_enableFaultHdlr ) {
678  // If not even the parent is there, an incident
679  // to load the parent must be fired...
680  handleDataFault( parentObj, p_path );
681  root_entry = parentObj->findLeaf( p_path );
682  }
683  if ( root_entry ) {
684  DataObject* pO = root_entry->object();
685  if ( !pO ) {
686  // Object is not loaded: load the object if at all possible
687  status = loadObject( root_entry );
688  if ( !status.isSuccess() ) return status;
689  }
690  if ( root_entry->isSoft() ) {
691  root_entry = CAST_REGENTRY( RegEntry*, pO->registry() );
692  }
693  return retrieveEntry( root_entry, o_path, pEntry );
694  }
695  return status;
696  } else if ( path.empty() ) {
697  pEntry = parentObj;
698  } else {
699  if ( !parentObj->object() ) { // if the parent object has not been loaded yet, load it now
700  status = loadObject( parentObj );
701  if ( !status.isSuccess() ) return status;
702  }
703  // last leave in search: find leaf and load
704  pEntry = parentObj->findLeaf( path );
705  // If no registry entry was found, trigger incident for action-on-demand
706  if ( !pEntry && m_enableFaultHdlr ) {
707  handleDataFault( parentObj, path );
708  pEntry = ( path.empty() ? parentObj : parentObj->findLeaf( path ) );
709  }
710  }
711  // Check results and return
712  if ( !pEntry ) {
713  status = Status::INVALID_OBJ_PATH;
714  } else if ( !pEntry->object() ) {
715  status = loadObject( pEntry );
716  } else if ( m_enableAccessHdlr ) {
717  // Fire data access incident
718  // I do not know if this is a good idea....
719  // This fires too often!
720  //
721  // DataIncident incident(name(), m_accessName, pEntry->identifier());
722  // m_incidentSvc->fireIncident(incident);
723  status = StatusCode::SUCCESS;
724  } else {
725  status = StatusCode::SUCCESS;
726  }
727  }
728  return status;
729 }
730 
732 StatusCode TsDataSvc::retrieveObject( IRegistry* pRegistry, boost::string_ref path, DataObject*& pObject )
733 {
735  pObject = nullptr;
736  RegEntry * result = nullptr, *parent = CAST_REGENTRY( RegEntry *, pRegistry );
737  StatusCode status = retrieveEntry( parent, path, result );
738  if ( status.isSuccess() ) pObject = result->object();
739  return status;
740 }
741 
743 StatusCode TsDataSvc::retrieveObject( boost::string_ref fullPath, DataObject*& pObject )
744 {
745  IRegistry* nullDir = nullptr;
746  return retrieveObject( nullDir, fullPath, pObject );
747 }
748 
750 StatusCode TsDataSvc::retrieveObject( boost::string_ref parentPath, boost::string_ref objectPath, DataObject*& pObject )
751 {
752  DataObject* parent = nullptr;
753  StatusCode status = retrieveObject( parentPath, parent );
754  return status.isSuccess() ? retrieveObject( parent, objectPath, pObject ) : status;
755 }
756 
758 StatusCode TsDataSvc::retrieveObject( boost::string_ref parentPath, int item, DataObject*& pObject )
759 {
760  return retrieveObject( parentPath, itemToPath( item ), pObject );
761 }
762 
764 StatusCode TsDataSvc::retrieveObject( DataObject* parentObj, boost::string_ref path, DataObject*& pObject )
765 {
766  IRegistry* pRegistry = ( parentObj ? parentObj->registry() : nullptr );
767  return retrieveObject( pRegistry, path, pObject );
768 }
769 
771 StatusCode TsDataSvc::retrieveObject( DataObject* parentObj, int item, DataObject*& pObject )
772 {
773  return retrieveObject( parentObj, itemToPath( item ), pObject );
774 }
775 
777 StatusCode TsDataSvc::findObject( IRegistry* pRegistry, boost::string_ref path, DataObject*& pObject )
778 {
780  pObject = nullptr;
781  IRegistry* pReg = ( pRegistry ? pRegistry : m_root );
782  RegEntry* root_entry = CAST_REGENTRY( RegEntry*, pReg );
783  if ( root_entry ) {
784  if ( !path.empty() ) pReg = root_entry->find( path );
785  if ( !pReg ) return Status::INVALID_OBJ_PATH;
786  pObject = pReg->object();
787  }
788  return pObject ? Status::IDataProviderSvc_NO_ERROR : Status::OBJ_NOT_LOADED;
789 }
790 
792 StatusCode TsDataSvc::findObject( boost::string_ref path, DataObject*& pObject )
793 {
795  pObject = nullptr;
796  if ( !checkRoot() ) return Status::INVALID_ROOT;
797  if ( path.empty() || path == m_rootName ) {
798  pObject = m_root->object();
799  return !pObject ? Status::OBJ_NOT_LOADED : Status::IDataProviderSvc_NO_ERROR;
800  }
801  if ( path.front() != SEPARATOR ) {
802  return findObject( m_rootName.value(), path, pObject );
803  }
804  return findObject( static_cast<IRegistry*>( nullptr ), path, pObject );
805 }
806 
808 StatusCode TsDataSvc::findObject( boost::string_ref parentPath, boost::string_ref objectPath, DataObject*& pObject )
809 {
810  DataObject* parent = nullptr;
811  StatusCode status = findObject( parentPath, parent );
812  return status.isSuccess() ? findObject( parent, objectPath, pObject ) : status;
813 }
814 
816 StatusCode TsDataSvc::findObject( boost::string_ref parentPath, int item, DataObject*& pObject )
817 {
818  return findObject( parentPath, itemToPath( item ), pObject );
819 }
820 
822 StatusCode TsDataSvc::findObject( DataObject* parentObj, int item, DataObject*& pObject )
823 {
824  return findObject( parentObj, itemToPath( item ), pObject );
825 }
826 
828 StatusCode TsDataSvc::findObject( DataObject* parentObj, boost::string_ref path, DataObject*& pObject )
829 {
830  return findObject( parentObj ? parentObj->registry() : nullptr, path, pObject );
831 }
832 
834 StatusCode TsDataSvc::updateObject( boost::string_ref updatePath )
835 {
836  DataObject* pO = nullptr;
837  StatusCode status = findObject( updatePath, pO );
838  return status.isSuccess() ? updateObject( pO ) : retrieveObject( updatePath, pO );
839 }
840 
843 {
844  if ( !pRegistry ) { // Precondition:
845  return Status::INVALID_OBJ_ADDR; // Addres must be valid
846  }
847  DataObject* toUpdate = pRegistry->object();
848  if ( !toUpdate ) { // Try first to load
849  return loadObject( pRegistry );
850  }
851  return updateObject( toUpdate );
852 }
853 
856 {
858  StatusCode status = Status::INVALID_OBJ_ADDR;
859  if ( !toUpdate ) { // Precondition:
860  return Status::INVALID_OBJECT; // Address must be valid
861  }
862  IRegistry* pRegistry = toUpdate->registry(); // Precondition:
863  if ( !pRegistry ) { // Need valid registry
864  return Status::INVALID_OBJECT;
865  }
866  IOpaqueAddress* pAddress = pRegistry->address(); // Precondition:
867  if ( !pAddress ) { // Need valid address
868  return Status::INVALID_OBJ_ADDR;
869  }
870  IConversionSvc* pLoader = getDataLoader( pRegistry );
871  if ( !pLoader ) { // Precondition:
872  return Status::NO_DATA_LOADER; // Data loader must be present
873  }
874  if ( !m_inhibitPathes.empty() ) {
875  auto& ident = pRegistry->identifier();
876  auto inhibit = std::find( m_inhibitPathes.begin(), m_inhibitPathes.end(), ident );
877  if ( inhibit != m_inhibitPathes.end() ) return Status::NO_ACCESS;
878  }
879  try {
880  status = pLoader->updateObj( pAddress, toUpdate ); // Call data loader
881  if ( status.isSuccess() ) {
882  status = pLoader->updateObjRefs( pAddress, toUpdate );
883  }
884  } catch ( const GaudiException& exc ) {
885  throw GaudiException( "GaudiException in updateObject() " + pRegistry->name(), name(), StatusCode::FAILURE, exc );
886  } catch ( const std::exception& x ) {
887  throw GaudiException( "std::exception in updateObject() " + pRegistry->name() + ": " +
888  System::typeinfoName( typeid( x ) ) + ", " + x.what(),
890  } catch ( ... ) {
891  throw GaudiException( "UNKN exception in updateObject() " + pRegistry->name(), name(), StatusCode::FAILURE );
892  }
893  return status;
894 }
895 
897 StatusCode TsDataSvc::updateObject( boost::string_ref parentPath, boost::string_ref updatePath )
898 {
899  DataObject* pParent = nullptr;
900  StatusCode status = findObject( parentPath, pParent );
901  return status.isSuccess() ? updateObject( pParent, updatePath ) : status;
902 }
903 
905 StatusCode TsDataSvc::updateObject( DataObject* parent, boost::string_ref updatePath )
906 {
907  DataObject* pObject = nullptr;
908  StatusCode status = findObject( parent, updatePath, pObject );
909  return status.isSuccess() ? updateObject( pObject ) : status;
910 }
911 
912 // Link object
913 StatusCode TsDataSvc::linkObject( IRegistry* from, boost::string_ref objPath, DataObject* to )
914 {
916  if ( !checkRoot() ) return Status::INVALID_ROOT;
917  try {
918  RegEntry* from_entry = CAST_REGENTRY( RegEntry*, from );
919  if ( from_entry ) {
920  // First check if both objects are already registered to the store
921  RegEntry* to_entry = m_root->findLeaf( to );
922  if ( !to_entry ) return Status::INVALID_OBJECT;
923  auto sep = objPath.rfind( SEPARATOR );
924  if ( sep > 0 && sep != boost::string_ref::npos ) { // in case the objPath is a sub-directory itself
925  DataObject* pO = nullptr;
926  StatusCode sc = retrieveObject( from, objPath.substr( 0, sep ), pO );
927  return sc.isSuccess() ? linkObject( pO->registry(), objPath.substr( sep ), to ) : sc;
928  }
929  // Now register the soft link
930  StatusCode status = from_entry->add( to_string( objPath ), to, true );
931  return status.isSuccess() ? Status::IDataProviderSvc_NO_ERROR : Status::DOUBL_OBJ_PATH;
932  }
933  } catch ( ... ) {
934  }
935  return Status::INVALID_PARENT;
936 }
937 
939 StatusCode TsDataSvc::linkObject( boost::string_ref fullPath, DataObject* to )
940 {
942  if ( fullPath.empty() ) return Status::INVALID_OBJ_PATH;
943  if ( fullPath.front() != SEPARATOR ) return linkObject( m_rootName.value(), fullPath, to );
944  auto sep = fullPath.rfind( SEPARATOR );
945  return linkObject( fullPath.substr( 0, sep ), fullPath.substr( sep ), to );
946 }
947 
949 StatusCode TsDataSvc::linkObject( boost::string_ref from, boost::string_ref objPath, DataObject* to )
950 {
952  DataObject* pO = nullptr;
953  StatusCode status = retrieveObject( from, pO );
954  return status.isSuccess() ? linkObject( pO->registry(), objPath, to ) : status;
955 }
956 
958 StatusCode TsDataSvc::linkObject( DataObject* from, boost::string_ref objPath, DataObject* to )
959 {
961  if ( from ) {
962  IRegistry* from_entry = from->registry();
963  if ( from_entry ) return linkObject( from_entry, objPath, to );
964  }
965  return Status::INVALID_PARENT;
966 }
967 
969 StatusCode TsDataSvc::unlinkObject( IRegistry* from, boost::string_ref objPath )
970 {
972  if ( !checkRoot() ) return Status::INVALID_ROOT;
973  try {
974  RegEntry* from_entry = CAST_REGENTRY( RegEntry*, from );
975  if ( from_entry ) {
976  auto sep = objPath.rfind( SEPARATOR );
977  if ( sep > 0 && sep != boost::string_ref::npos ) { // in case the objPath is a sub-directory itself
978  DataObject* pO = nullptr;
979  StatusCode sc = findObject( from, objPath.substr( 0, sep ), pO );
980  return sc.isSuccess() ? unlinkObject( pO->registry(), objPath.substr( sep ) ) : sc;
981  }
982  StatusCode status = from_entry->remove( objPath );
983  return status.isSuccess() ? status : Status::INVALID_OBJ_PATH;
984  }
985  } catch ( ... ) {
986  }
987  return Status::INVALID_PARENT;
988 }
989 
991 StatusCode TsDataSvc::unlinkObject( boost::string_ref fullPath )
992 {
993  if ( fullPath.empty() ) return Status::INVALID_OBJ_PATH;
994  if ( fullPath.front() != SEPARATOR ) {
995  return unlinkObject( m_rootName.value(), fullPath );
996  }
997  auto sep = fullPath.rfind( SEPARATOR );
998  return unlinkObject( fullPath.substr( 0, sep ), fullPath.substr( sep ) );
999 }
1000 
1002 StatusCode TsDataSvc::unlinkObject( boost::string_ref from, boost::string_ref objPath )
1003 {
1004  DataObject* pObject = nullptr;
1005  StatusCode status = findObject( from, pObject );
1006  return status.isSuccess() ? unlinkObject( pObject->registry(), objPath ) : status;
1007 }
1008 
1010 StatusCode TsDataSvc::unlinkObject( DataObject* from, boost::string_ref objPath )
1011 {
1012  if ( !checkRoot() ) return Status::INVALID_ROOT;
1013  return unlinkObject( m_root->findLeaf( from ), objPath );
1014 }
1015 
1018 {
1019  auto i = std::find( m_preLoads.begin(), m_preLoads.end(), item );
1020  if ( i == m_preLoads.end() ) m_preLoads.push_back( item );
1021  return StatusCode::SUCCESS;
1022 }
1023 
1026 {
1027  return addPreLoadItem( DataStoreItem( std::move( itemPath ), 1 ) );
1028 }
1029 
1032 {
1033  auto i = std::remove( m_preLoads.begin(), m_preLoads.end(), item );
1034  m_preLoads.erase( i, m_preLoads.end() );
1035  return StatusCode::SUCCESS;
1036 }
1037 
1040 {
1041  return removePreLoadItem( DataStoreItem( std::move( itemPath ), 1 ) );
1042 }
1043 
1046 {
1047  m_preLoads.clear();
1048  return StatusCode::SUCCESS;
1049 }
1050 
1052 StatusCode TsDataSvc::preLoad( int depth, int load_depth, DataObject* pObject )
1053 {
1054  // unused: StatusCode sc = StatusCode::FAILURE;
1055  if ( pObject && depth++ < load_depth ) {
1056  RegEntry* dir = CAST_REGENTRY( RegEntry*, pObject->registry() );
1057  if ( dir ) {
1058  for ( const auto& i : *dir ) {
1059  DataObject* pObj = nullptr;
1060  StatusCode status = retrieveObject( pObject, i->name(), pObj );
1061  if ( status.isSuccess() && depth < load_depth ) {
1062  preLoad( depth, load_depth, pObj ).ignore();
1063  }
1064  }
1065  }
1066  }
1067  return StatusCode::SUCCESS;
1068 }
1069 
1072 {
1073  DataObject* pObj = nullptr;
1074  for ( const auto& i : m_preLoads ) {
1075  StatusCode sc = retrieveObject( i.path(), pObj );
1076  int load_depth = i.depth();
1077  if ( sc.isSuccess() && load_depth > 1 ) {
1078  preLoad( 1, load_depth, pObj ).ignore();
1079  }
1080  }
1081  return StatusCode::SUCCESS;
1082 }
1083 
1086 {
1087  // Nothing to do: just call base class initialisation
1089  if ( !sc.isSuccess() ) return sc;
1090  sc = service( "IncidentSvc", m_incidentSvc, true );
1091  if ( UNLIKELY( !sc.isSuccess() ) ) {
1092  error() << "Failed to access incident service." << endmsg;
1093  }
1094  return sc;
1095 }
1096 
1099 {
1100  StatusCode sc;
1101  // the finalize part is copied here
1102  setDataLoader( nullptr ).ignore();
1103  resetPreLoad().ignore();
1104  clearStore().ignore();
1105  if ( m_incidentSvc ) {
1107  m_incidentSvc = nullptr;
1108  }
1109  // re-initialize the base class
1110  sc = Service::reinitialize();
1111  if ( UNLIKELY( !sc.isSuccess() ) ) {
1112  error() << "Unable to reinitialize base class" << endmsg;
1113  return sc;
1114  }
1115  // the initialize part is copied here
1116  sc = service( "IncidentSvc", m_incidentSvc, true );
1117  if ( UNLIKELY( !sc.isSuccess() ) ) {
1118  error() << "Failed to access incident service." << endmsg;
1119  return sc;
1120  }
1121  // return
1122  return StatusCode::SUCCESS;
1123 }
1124 
1127 {
1128  // Nothing to do: just call base class initialisation
1129  setDataLoader( nullptr ).ignore();
1130  resetPreLoad().ignore();
1131  clearStore().ignore();
1132  if ( m_incidentSvc ) {
1134  m_incidentSvc = nullptr;
1135  }
1136  return Service::finalize();
1137 }
1138 
1140 CLID TsDataSvc::rootCLID() const { return ( (CLID)m_rootCLID ); }
1141 
1143 const std::string& TsDataSvc::rootName() const { return ( m_rootName ); }
1144 
1147 
1152 
1155 {
1156  setDataLoader( nullptr ).ignore();
1157  resetPreLoad().ignore();
1158  clearStore().ignore();
1159 }
#define UNLIKELY(x)
Definition: Kernel.h:122
constexpr static const auto FAILURE
Definition: StatusCode.h:88
constexpr double sr
StatusCode initialize() override
Definition: Service.cpp:63
RegistryEntry * findLeaf(boost::string_ref path) const
Find identified leaf in this registry node.
Definition: RegistryEntry.h:95
Define general base for Gaudi exception.
DataObject * object() const override
Retrive object behind the link.
const std::string & name() const override
Retrieve name of the service.
Definition: Service.cpp:288
virtual StatusCode createObj(IOpaqueAddress *pAddress, DataObject *&refpObject)=0
Create the transient representation of an object.
constexpr char SEPARATOR
StatusCode setRoot(std::string root_name, DataObject *pRootObj) override
Initialize data store for new event by giving new event path and root object.
Definition: TsDataSvc.cpp:157
StatusCode finalize() override
Definition: Service.cpp:173
StatusCode addPreLoadItem(const DataStoreItem &item) override
Add an item to the preload list.
Definition: TsDataSvc.cpp:1017
StatusCode linkObject(IRegistry *from, boost::string_ref objPath, DataObject *to) override
Add a link to another object.
Definition: TsDataSvc.cpp:913
StatusCode unregisterObject(boost::string_ref fullPath) override
Unregister object from the data store.
Definition: TsDataSvc.cpp:470
GAUDI_API const std::string typeinfoName(const std::type_info &)
Get platform independent information about the class type.
Definition: System.cpp:332
StatusCode traverseTree(IDataStoreAgent *pAgent, int level=0)
traverse data tree
StatusCode traverseTree(IDataStoreAgent *pAgent) override
IDataManagerSvc: Analyze by traversing all data objects in the data store.
Definition: TsDataSvc.cpp:146
bool isSuccess() const
Definition: StatusCode.h:287
StatusCode updateObject(IRegistry *pDirectory) override
Update object identified by its directory entry.
Definition: TsDataSvc.cpp:842
StatusCode unregisterAddress(boost::string_ref fullPath) override
IDataManagerSvc: Unregister object address from the data store.
Definition: TsDataSvc.cpp:316
Gaudi::Property< std::string > m_accessName
Definition: TsDataSvc.h:81
Gaudi::Property< CLID > m_rootCLID
Definition: TsDataSvc.h:70
T to_string(T...args)
StatusCode retrieveObject(IRegistry *pDirectory, boost::string_ref path, DataObject *&pObject) override
Retrieve object from data store.
Definition: TsDataSvc.cpp:732
MsgStream & verbose() const
shortcut for the method msgStream(MSG::VERBOSE)
virtual StatusCode setDataProvider(IDataProviderSvc *pService)=0
Set Data provider service.
~TsDataSvc() override
Standard Destructor.
Definition: TsDataSvc.cpp:1154
void setRegistry(IRegistry *pRegistry)
Set pointer to Registry.
Definition: DataObject.h:71
unsigned long release() override
IInterface implementation: Reference the object.
virtual const name_type & name() const =0
Name of the directory (or key)
StatusCode initialize() override
Service initialization.
Definition: TsDataSvc.cpp:1085
StatusCode removePreLoadItem(const DataStoreItem &item) override
Remove an item from the preload list.
Definition: TsDataSvc.cpp:1031
T end(T...args)
virtual IConversionSvc * getDataLoader(IRegistry *pReg)
Retrieve customizable data loader according to registry entry to be retrieved.
Definition: TsDataSvc.cpp:1151
const Store & leaves() const
Access the leaves of the object.
bool isSoft() const
Is the link soft or hard.
IConversionSvc * m_dataLoader
Pointer to data loader service.
Definition: TsDataSvc.h:66
StatusCode setDataLoader(IConversionSvc *svc, IDataProviderSvc *dpsvc=nullptr) override
IDataManagerSvc: IDataManagerSvc: Pass a default data loader to the service and optionally a data pro...
Definition: TsDataSvc.cpp:206
Data provider interface definition.
T remove(T...args)
void setAddress(IOpaqueAddress *pAddress) override
Set/Update Opaque address.
Description of the DataStoreItem class.
Definition: DataStoreItem.h:17
bool isFailure() const
Definition: StatusCode.h:139
IRegistry * registry() const
Get pointer to Registry.
Definition: DataObject.h:73
virtual StatusCode updateObj(IOpaqueAddress *pAddress, DataObject *refpObject)=0
Update the transient object from the other representation.
StatusCode resetPreLoad() override
Clear the preload list.
Definition: TsDataSvc.cpp:1045
STL class.
#define VERMSG
Definition: TsDataSvc.cpp:83
T push_back(T...args)
MsgStream & error() const
shortcut for the method msgStream(MSG::ERROR)
StatusCode registerAddress(boost::string_ref fullPath, IOpaqueAddress *pAddress) override
IDataManagerSvc: Register object address with the data store.
Definition: TsDataSvc.cpp:258
virtual unsigned long addRef()
Add reference to object.
Definition: DataObject.cpp:59
virtual void fireIncident(const Incident &incident)=0
Fire an Incident.
void setObject(DataObject *obj)
Set/Update object address.
StatusCode preLoad() override
load all preload items of the list
Definition: TsDataSvc.cpp:1071
StatusCode findObject(boost::string_ref fullPath, DataObject *&pObject) override
Find object identified by its full path in the data store.
Definition: TsDataSvc.cpp:792
IIncidentSvc * m_incidentSvc
Pointer to incident service.
Definition: TsDataSvc.h:68
virtual const id_type & identifier() const =0
Full identifier (or key)
#define ON_VERBOSE
Definition: TsDataSvc.cpp:80
T what(T...args)
DataSvcHelpers::RegistryEntry * m_root
Pointer to root entry.
Definition: TsDataSvc.h:86
This class is used for returning status codes from appropriate routines.
Definition: StatusCode.h:51
T append(T...args)
LoadItems m_preLoads
Items to be pre-loaded.
Definition: TsDataSvc.h:84
IRegistry * parent() const
Pointer to parent directory entry.
virtual StatusCode updateObjRefs(IOpaqueAddress *pAddress, DataObject *pObject)=0
Update the references of an updated transient object.
DataSvcHelpers::RegistryEntry RegEntry
Definition: TsDataSvc.cpp:77
T erase(T...args)
void setDataSvc(IDataProviderSvc *s)
Set the transient data store.
Definition: RegistryEntry.h:91
const std::string & rootName() const override
IDataManagerSvc: Accessor for root event name.
Definition: TsDataSvc.cpp:1143
Gaudi::Property< bool > m_enableAccessHdlr
Definition: TsDataSvc.h:79
StatusCode reinitialize() override
Service initialization.
Definition: TsDataSvc.cpp:1098
StatusCode objectLeaves(const DataObject *pObject, std::vector< IRegistry * > &refLeaves) override
IDataManagerSvc: Explore the object store: retrieve all leaves attached to the object.
Definition: TsDataSvc.cpp:236
The IRegistry represents the entry door to the environment any data object residing in a transient da...
Definition: IRegistry.h:22
StatusCode unlinkObject(IRegistry *from, boost::string_ref objPath) override
Remove a link to another object.
Definition: TsDataSvc.cpp:969
StatusCode reinitialize() override
Definition: Service.cpp:249
unsigned int CLID
Class ID definition.
Definition: ClassID.h:8
T clear(T...args)
IOpaqueAddress * address() const override
Retrieve opaque storage address.
STL class.
T move(T...args)
StatusCode retrieveEntry(DataSvcHelpers::RegistryEntry *pNode, boost::string_ref path, DataSvcHelpers::RegistryEntry *&pEntry)
Retrieve registry entry from store.
Definition: TsDataSvc.cpp:650
constexpr static const auto SUCCESS
Definition: StatusCode.h:87
virtual DataObject * object() const =0
Retrieve object behind the link.
Definition of an entry in the transient data store.
Definition: RegistryEntry.h:37
virtual unsigned long release()
release reference to object
Definition: DataObject.cpp:51
T insert(T...args)
T find(T...args)
StatusCode add(std::string name, DataObject *pObject, bool is_soft=false)
Add entry to data store.
virtual DataObject * createDefaultObject() const
Create default objects in case forced creation of leaves is requested.
Definition: TsDataSvc.cpp:1146
virtual StatusCode fillObjRefs(IOpaqueAddress *pAddress, DataObject *pObject)=0
Resolve the references of the created transient object.
virtual unsigned long release()=0
Release Interface instance.
StatusCode finalize() override
Service initialization.
Definition: TsDataSvc.cpp:1126
Generic data agent interface.
StatusCode clearSubTree(boost::string_ref sub_tree_path) override
IDataManagerSvc: Remove all data objects below the sub tree identified by its full path name...
Definition: TsDataSvc.cpp:88
T begin(T...args)
RegistryEntry * parentEntry()
Pointer to parent registry entry.
Definition: RegistryEntry.h:93
virtual StatusCode i_setRoot(std::string root_name, DataObject *pRootObj)
Initialize data store for new event by giving new event path and root object.
Definition: TsDataSvc.cpp:168
const StatusCode & ignore() const
Ignore/check StatusCode.
Definition: StatusCode.h:165
decltype(auto) operator+(const T &v, const Property< TP, V, H > &p)
implemantation of (value + property)
Definition: Property.h:757
IRegistry * find(const IRegistry *obj) const
Try to find an object identified by its pointer.
string s
Definition: gaudirun.py:253
const std::string & name() const
Retreive DataObject name. It is the name when registered in the store.
Definition: DataObject.cpp:68
bool checkRoot()
Check if root path is valid.
Definition: TsDataSvc.h:335
virtual unsigned long addRef()=0
Increment the reference count of Interface instance.
StatusCode traverseSubTree(boost::string_ref sub_tree_path, IDataStoreAgent *pAgent) override
IDataManagerSvc: Analyze by traversing all data objects below the sub tree identified by its full pat...
Definition: TsDataSvc.cpp:127
Gaudi::Property< bool > m_forceLeaves
Definition: TsDataSvc.h:72
StatusCode service(const std::string &name, const T *&psvc, bool createIf=true) const
Access a service by name, creating it if it doesn&#39;t already exist.
Definition: Service.h:84
const std::string & identifier() const override
Full identifier (or key)
StatusCode remove(boost::string_ref name)
Remove an entry from the store.
StatusCode clearStore() override
IDataManagerSvc: Remove all data objects in the data store.
Definition: TsDataSvc.cpp:116
bool isEmpty() const
Simple check if the Container is empty.
Data service incident class.
Opaque address interface definition.
CLID rootCLID() const override
IDataManagerSvc: Accessor for root event CLID.
Definition: TsDataSvc.cpp:1140
virtual IOpaqueAddress * address() const =0
Retrieve opaque storage address.
Gaudi::Property< std::vector< std::string > > m_inhibitPathes
Definition: TsDataSvc.h:73
DataObject * handleDataFault(IRegistry *pReg, boost::string_ref path={})
Invoke data fault handling if enabled.
Definition: TsDataSvc.cpp:540
A DataObject is the base class of any identifiable object on any data store.
Definition: DataObject.h:30
#define STD_LOCK_GUARD_MACRO
Definition: TsDataSvc.cpp:45
#define CAST_REGENTRY(x, y)
Definition: TsDataSvc.cpp:75
virtual StatusCode loadObject(IRegistry *pNode)
Invoke Persistency service to create transient object from its persistent representation.
Definition: TsDataSvc.cpp:571
StatusCode registerObject(boost::string_ref fullPath, DataObject *pObject) override
Register object with the data store.
Definition: TsDataSvc.cpp:368
StatusCode objectParent(const DataObject *pObject, IRegistry *&refpParent) override
IDataManagerSvc: Explore the object store: retrieve the object&#39;s parent.
Definition: TsDataSvc.cpp:218
MsgStream & endmsg(MsgStream &s)
MsgStream Modifier: endmsg. Calls the output method of the MsgStream.
Definition: MsgStream.h:209
Gaudi::Property< bool > m_enableFaultHdlr
Definition: TsDataSvc.h:75
Gaudi::Property< std::string > m_faultName
Definition: TsDataSvc.h:77
Gaudi::Property< std::string > m_rootName
Definition: TsDataSvc.h:71
void makeHard(DataObject *pObject)
Initialize link as hard link.