The Gaudi Framework  master (37c0b60a)
AlgResourcePool.cpp
Go to the documentation of this file.
1 /***********************************************************************************\
2 * (c) Copyright 1998-2023 CERN for the benefit of the LHCb and ATLAS collaborations *
3 * *
4 * This software is distributed under the terms of the Apache version 2 licence, *
5 * copied verbatim in the file "LICENSE". *
6 * *
7 * In applying this licence, CERN does not waive the privileges and immunities *
8 * granted to it by virtue of its status as an Intergovernmental Organization *
9 * or submit itself to any jurisdiction. *
10 \***********************************************************************************/
11 #include "AlgResourcePool.h"
12 #include <Gaudi/Sequence.h>
14 #include <functional>
15 #include <queue>
16 #include <sstream>
17 
18 // DP TODO: Manage SmartIFs and not pointers to algorithms
19 
20 // Instantiation of a static factory class used by clients to create instances of this service
22 
23 #define ON_DEBUG if ( msgLevel( MSG::DEBUG ) )
24 #define DEBUG_MSG ON_DEBUG debug()
25 
26 //---------------------------------------------------------------------------
27 
28 // Destructor
30  for ( auto& algoId_algoQueue : m_algqueue_map ) {
31  auto* queue = algoId_algoQueue.second;
32  delete queue;
33  }
34 }
35 
36 //---------------------------------------------------------------------------
37 
38 // Initialize the pool with the list of algorithms known to the IAlgManager
40 
42  if ( !sc.isSuccess() ) warning() << "Base class could not be started" << endmsg;
43 
44  // Try to recover the topAlgList from the ApplicationManager for backward-compatibility
45  if ( m_topAlgNames.value().empty() ) {
46  info() << "TopAlg list empty. Recovering the one of Application Manager" << endmsg;
47  const Gaudi::Utils::TypeNameString appMgrName( "ApplicationMgr/ApplicationMgr" );
48  SmartIF<IProperty> appMgrProps( serviceLocator()->service( appMgrName ) );
49  m_topAlgNames.assign( appMgrProps->getProperty( "TopAlg" ) );
50  }
51 
52  sc = decodeTopAlgs();
53  if ( sc.isFailure() ) warning() << "Algorithms could not be properly decoded." << endmsg;
54 
55  // let's assume all resources are there
57  return StatusCode::SUCCESS;
58 }
59 
60 //---------------------------------------------------------------------------
61 
63 
64  StatusCode startSc = Service::start();
65  if ( !startSc.isSuccess() ) return startSc;
66 
67  // sys-Start the algorithms
68  for ( auto& ialgo : m_algList ) {
69  startSc = ialgo->sysStart();
70  if ( startSc.isFailure() ) {
71  error() << "Unable to start Algorithm: " << ialgo->name() << endmsg;
72  return startSc;
73  }
74  }
75  return StatusCode::SUCCESS;
76 }
77 
78 //---------------------------------------------------------------------------
79 
80 StatusCode AlgResourcePool::acquireAlgorithm( std::string_view name, IAlgorithm*& algo, bool blocking ) {
81 
82  std::hash<std::string_view> hash_function;
83  size_t algo_id = hash_function( name );
84  auto itQueueIAlgPtr = m_algqueue_map.find( algo_id );
85 
86  if ( itQueueIAlgPtr == m_algqueue_map.end() ) {
87  error() << "Algorithm " << name << " requested, but not recognised" << endmsg;
88  algo = nullptr;
89  return StatusCode::FAILURE;
90  }
91 
92  StatusCode sc;
93  if ( blocking ) {
94  itQueueIAlgPtr->second->pop( algo );
95  } else {
96  if ( !itQueueIAlgPtr->second->try_pop( algo ) ) {
97  if ( m_countAlgInstMisses ) {
98  auto result = m_algInstanceMisses.find( name );
99  if ( result != m_algInstanceMisses.end() )
100  ++( result->second );
101  else
103  }
104  sc = StatusCode::FAILURE;
105  }
106  }
107 
108  // Note that reentrant algorithms are not consumed so we put them
109  // back immediately in the queue at the end of this function.
110  // Now we may still be called again in between and get this
111  // error. In such a case, the Scheduler will retry later.
112  // This is of course not optimal, but should only happen very
113  // seldom and thud won't affect the global efficiency
114  if ( sc.isFailure() )
115  DEBUG_MSG << "No instance of algorithm " << name << " could be retrieved in non-blocking mode" << endmsg;
116 
117  // if (m_lazyCreation ) {
118  // TODO: fill the lazyCreation part
119  // }
120  if ( sc.isSuccess() ) {
121  state_type requirements = m_resource_requirements[algo_id];
123  if ( requirements.is_subset_of( m_available_resources ) ) {
124  m_available_resources ^= requirements;
125  } else {
126  sc = StatusCode::FAILURE;
127  error() << "Failure to allocate resources of algorithm " << name << endmsg;
128  // in case of not reentrant, push it back. Reentrant ones are pushed back
129  // in all cases further down
130  if ( !algo->isReEntrant() ) { itQueueIAlgPtr->second->push( algo ); }
131  }
133  if ( algo->isReEntrant() ) {
134  // push back reentrant algorithms immediately as it can be reused
135  itQueueIAlgPtr->second->push( algo );
136  }
137  }
138  return sc;
139 }
140 
141 //---------------------------------------------------------------------------
142 
144 
145  std::hash<std::string_view> hash_function;
146  size_t algo_id = hash_function( name );
147 
148  // release resources used by the algorithm
152 
153  // release algorithm itself if not reentrant
154  if ( !algo->isReEntrant() ) { m_algqueue_map[algo_id]->push( algo ); }
155  return StatusCode::SUCCESS;
156 }
157 
158 //---------------------------------------------------------------------------
159 
164  return StatusCode::SUCCESS;
165 }
166 
167 //---------------------------------------------------------------------------
168 
173  return StatusCode::SUCCESS;
174 }
175 
176 //---------------------------------------------------------------------------
177 
178 StatusCode AlgResourcePool::flattenSequencer( Gaudi::Algorithm* algo, ListAlg& alglist, unsigned int recursionDepth ) {
179 
181 
182  if ( algo->isSequence() ) {
183  auto seq = dynamic_cast<Gaudi::Sequence*>( algo );
184  if ( seq == 0 ) {
185  error() << "Unable to dcast Algorithm " << algo->name() << " to a Sequence, but it has isSequence==true"
186  << endmsg;
187  return StatusCode::FAILURE;
188  }
189 
190  auto subAlgorithms = seq->subAlgorithms();
191 
192  // Recursively unroll
193  ++recursionDepth;
194 
195  for ( auto subalgo : *subAlgorithms ) {
196  sc = flattenSequencer( subalgo, alglist, recursionDepth );
197  if ( sc.isFailure() ) {
198  error() << "Algorithm " << subalgo->name() << " could not be flattened" << endmsg;
199  return sc;
200  }
201  }
202  } else {
203  alglist.emplace_back( algo );
204  return sc;
205  }
206  return sc;
207 }
208 
209 //---------------------------------------------------------------------------
210 
212 
214  if ( !algMan.isValid() ) {
215  error() << "Algorithm manager could not be properly fetched." << endmsg;
216  return StatusCode::FAILURE;
217  }
218 
219  // Useful lambda not to repeat ourselves --------------------------
220  auto createAlg = [&algMan, this]( const std::string& item_type, const std::string& item_name, IAlgorithm*& algo ) {
221  StatusCode createAlgSc = algMan->createAlgorithm( item_type, item_name, algo, true, false );
222  if ( createAlgSc.isFailure() )
223  this->warning() << "Algorithm " << item_type << "/" << item_name << " could not be created." << endmsg;
224  };
225  // End of lambda --------------------------------------------------
226 
228 
229  // Fill the top algorithm list ----
230  const std::vector<std::string>& topAlgNames = m_topAlgNames.value();
231  for ( auto& name : topAlgNames ) {
232  IAlgorithm* algo( nullptr );
233 
235  const std::string& item_name = item.name();
236  const std::string& item_type = item.type();
237  SmartIF<IAlgorithm> algoSmartIF( algMan->algorithm( item_name, false ) );
238 
239  if ( !algoSmartIF.isValid() ) {
240  createAlg( item_type, item_name, algo );
241  algoSmartIF = algo;
242  }
243 
244  algoSmartIF->sysInitialize().ignore();
245  m_topAlgList.push_back( algoSmartIF );
246  }
247  // Top algorithm list filled ----
248 
249  // Now we unroll it ----
250  for ( auto& algoSmartIF : m_topAlgList ) {
251  Gaudi::Algorithm* algorithm = dynamic_cast<Gaudi::Algorithm*>( algoSmartIF.get() );
252  if ( !algorithm ) {
253  fatal() << "Conversion from IAlgorithm to Gaudi::Algorithm failed" << endmsg;
254  return StatusCode::FAILURE;
255  }
256  sc = flattenSequencer( algorithm, m_flatUniqueAlgList );
257  }
258  // stupid O(N^2) unique-ification..
259  for ( auto i = begin( m_flatUniqueAlgList ); i != end( m_flatUniqueAlgList ); ++i ) {
260  auto n = next( i );
261  while ( n != end( m_flatUniqueAlgList ) ) {
262  if ( *n == *i )
264  else
265  ++n;
266  }
267  }
268  if ( msgLevel( MSG::DEBUG ) ) {
269  debug() << "List of algorithms is: " << endmsg;
270  for ( auto& algo : m_flatUniqueAlgList )
271  debug() << " o " << algo->type() << "/" << algo->name() << " @ " << algo << endmsg;
272  }
273 
274  // Unrolled ---
275 
276  // Now let's manage the clones
277  unsigned int resource_counter( 0 );
278  std::hash<std::string> hash_function;
279  for ( auto& ialgoSmartIF : m_flatUniqueAlgList ) {
280 
281  const std::string& item_name = ialgoSmartIF->name();
282 
283  verbose() << "Treating resource management and clones of " << item_name << endmsg;
284 
285  Gaudi::Algorithm* algo = dynamic_cast<Gaudi::Algorithm*>( ialgoSmartIF.get() );
286  if ( !algo ) {
287  fatal() << "Conversion from IAlgorithm to Gaudi::Algorithm failed" << endmsg;
288  return StatusCode::FAILURE;
289  }
290  const std::string& item_type = algo->type();
291 
292  size_t algo_id = hash_function( item_name );
294  m_algqueue_map[algo_id] = queue;
295 
296  // DP TODO Do it properly with SmartIFs, also in the queues
297  IAlgorithm* ialgo( ialgoSmartIF.get() );
298 
299  queue->push( ialgo );
300  m_algList.push_back( ialgo );
301  if ( ialgo->isReEntrant() ) {
302  if ( ialgo->cardinality() != 0 ) {
303  info() << "Algorithm " << ialgo->name() << " is ReEntrant, but Cardinality was set to " << ialgo->cardinality()
304  << ". Only creating 1 instance" << endmsg;
305  }
306  m_n_of_allowed_instances[algo_id] = 1;
307  } else if ( ialgo->isClonable() ) {
308  m_n_of_allowed_instances[algo_id] = ialgo->cardinality();
309  } else {
310  if ( ialgo->cardinality() == 1 ) {
311  m_n_of_allowed_instances[algo_id] = 1;
312  } else {
313  if ( !m_overrideUnClonable ) {
314  info() << "Algorithm " << ialgo->name() << " is un-Clonable but Cardinality was set to "
315  << ialgo->cardinality() << ". Only creating 1 instance" << endmsg;
316  m_n_of_allowed_instances[algo_id] = 1;
317  } else {
318  warning() << "Overriding UnClonability of Algorithm " << ialgo->name() << ". Setting Cardinality to "
319  << ialgo->cardinality() << endmsg;
320  m_n_of_allowed_instances[algo_id] = ialgo->cardinality();
321  }
322  }
323  }
324  m_n_of_created_instances[algo_id] = 1;
325 
326  state_type requirements( 0 );
327 
328  for ( auto& resource_name : ialgo->neededResources() ) {
329  auto ret = m_resource_indices.emplace( resource_name, resource_counter );
330  // insert successful means == wasn't known before. So increment counter
331  if ( ret.second ) ++resource_counter;
332  // Resize for every algorithm according to the found resources
333  requirements.resize( resource_counter );
334  // in any case the return value holds the proper product index
335  requirements[ret.first->second] = true;
336  }
337 
338  m_resource_requirements[algo_id] = requirements;
339 
340  // potentially create clones; if not lazy creation we have to do it now
341  if ( !m_lazyCreation ) {
342  for ( unsigned int i = 1, end = m_n_of_allowed_instances[algo_id]; i < end; ++i ) {
343  debug() << "type/name to create clone of: " << item_type << "/" << item_name << endmsg;
344  IAlgorithm* ialgoClone( nullptr );
345  createAlg( item_type, item_name, ialgoClone );
346  ialgoClone->setIndex( i );
347  if ( ialgoClone->sysInitialize().isFailure() ) {
348  error() << "unable to initialize Algorithm clone " << ialgoClone->name() << endmsg;
349  sc = StatusCode::FAILURE;
350  // FIXME: should we delete this failed clone?
351  } else {
352  queue->push( ialgoClone );
353  m_n_of_created_instances[algo_id] += 1;
354  }
355  }
356  }
357  }
358 
359  // Now resize all the requirement bitsets to the same size
360  for ( auto& kv : m_resource_requirements ) { kv.second.resize( resource_counter ); }
361 
362  // Set all resources to be available
363  m_available_resources.resize( resource_counter );
364  m_available_resources.set();
365 
366  return sc;
367 }
368 
369 //---------------------------------------------------------------------------
370 
373  for ( auto algoSmartIF : m_flatUniqueAlgList ) m_flatUniqueAlgPtrList.push_back( algoSmartIF.get() );
374  return m_flatUniqueAlgPtrList;
375 }
376 
377 //---------------------------------------------------------------------------
378 
381  for ( auto algoSmartIF : m_topAlgList ) m_topAlgPtrList.push_back( algoSmartIF.get() );
382  return m_topAlgPtrList;
383 }
384 
385 //---------------------------------------------------------------------------
387 
389 
390  for ( auto& p : m_algInstanceMisses ) sortedAlgInstanceMisses.insert( { p.second, p.first } );
391 
392  // determine optimal indentation
393  int indnt = std::to_string( sortedAlgInstanceMisses.cbegin()->first ).length();
394 
396 
397  out << "Hit parade of algorithm instance misses:\n"
398  << std::right << std::setfill( ' ' )
399  << " ===============================================================================\n"
400  << std::setw( indnt + 7 ) << "Misses "
401  << "| Algorithm (# of clones) \n"
402  << " ===============================================================================\n";
403 
404  std::hash<std::string_view> hash_function;
405 
406  out << std::right << std::setfill( ' ' );
407  for ( const auto& p : sortedAlgInstanceMisses ) {
408  out << std::setw( indnt + 7 ) << std::to_string( p.first ) + " "
409  << " " << p.second << " (" << m_n_of_allowed_instances.at( hash_function( p.second ) ) << ")\n";
410  }
411 
412  info() << out.str() << endmsg;
413 }
414 
415 //---------------------------------------------------------------------------
416 
418 
419  StatusCode stopSc = Service::stop();
420  if ( !stopSc.isSuccess() ) return stopSc;
421 
422  // sys-Stop the algorithm
423  for ( auto& ialgo : m_algList ) {
424  stopSc = ialgo->sysStop();
425  if ( stopSc.isFailure() ) {
426  error() << "Unable to stop Algorithm: " << ialgo->name() << endmsg;
427  return stopSc;
428  }
429  }
431 
432  return StatusCode::SUCCESS;
433 }
434 
436  // we do not need to hold the ref counts of the algorithms anymore
437  // (this triggers algorithms destructors)
439  m_algList.clear();
441  return extends::finalize();
442 }
MSG::DEBUG
@ DEBUG
Definition: IMessageSvc.h:25
AlgResourcePool::~AlgResourcePool
~AlgResourcePool() override
Definition: AlgResourcePool.cpp:29
AlgResourcePool::initialize
StatusCode initialize() override
Definition: AlgResourcePool.cpp:39
std::mutex::lock
T lock(T... args)
Service::initialize
StatusCode initialize() override
Definition: Service.cpp:118
std::string
STL class.
AlgResourcePool::m_countAlgInstMisses
Gaudi::Property< bool > m_countAlgInstMisses
Definition: AlgResourcePool.h:92
AlgResourcePool::m_available_resources
state_type m_available_resources
Definition: AlgResourcePool.h:69
Gaudi::Utils::TypeNameString::name
const std::string & name() const
Definition: TypeNameString.h:49
std::list< SmartIF< IAlgorithm > >
AlgResourcePool::releaseResource
StatusCode releaseResource(std::string_view name) override
Release a certain resource.
Definition: AlgResourcePool.cpp:169
Gaudi::Algorithm::name
const std::string & name() const override
The identifying name of the algorithm object.
Definition: Algorithm.cpp:526
StatusCode::isSuccess
bool isSuccess() const
Definition: StatusCode.h:314
queue
std::deque< Stream_t > queue
Definition: CUDAStream.cpp:40
Service::start
StatusCode start() override
Definition: Service.cpp:187
IAlgorithm::setIndex
virtual void setIndex(const unsigned int &idx)=0
Set instantiation index of Alg.
Gaudi::Algorithm::type
const std::string & type() const override
The type of the algorithm object.
Definition: Algorithm.h:165
AlgResourcePool::m_algList
ListAlg m_algList
The list of all algorithms created within the Pool which are not top.
Definition: AlgResourcePool.h:97
std::vector< std::string >
std::map::find
T find(T... args)
AlgResourcePool::m_flatUniqueAlgList
ListAlg m_flatUniqueAlgList
The flat list of algorithms w/o clones.
Definition: AlgResourcePool.h:103
std::map::emplace
T emplace(T... args)
IAlgorithm::cardinality
virtual unsigned int cardinality() const =0
Cardinality (Maximum number of clones that can exist) special value 0 means that algorithm is reentra...
AlgResourcePool::state_type
boost::dynamic_bitset state_type
Definition: AlgResourcePool.h:65
std::setfill
T setfill(T... args)
Gaudi::Property::assign
bool assign(const Details::PropertyBase &source) override
get the value from another property
Definition: Property.h:370
AlgResourcePool::m_flatUniqueAlgPtrList
std::list< IAlgorithm * > m_flatUniqueAlgPtrList
The flat list of algorithms w/o clones which is returned.
Definition: AlgResourcePool.h:106
IAlgorithm::neededResources
virtual const std::vector< std::string > & neededResources() const =0
Named, non thread-safe resources used during event processing.
CommonMessaging< implements< IService, IProperty, IStateful > >::msgLevel
MSG::Level msgLevel() const
get the cached level (originally extracted from the embedded MsgStream)
Definition: CommonMessaging.h:148
IAlgorithm::isClonable
virtual bool isClonable() const
Specify if the algorithm is clonable.
Definition: IAlgorithm.h:64
std::list::clear
T clear(T... args)
IAlgorithm::isReEntrant
virtual bool isReEntrant() const =0
std::mutex::unlock
T unlock(T... args)
AlgResourcePool::m_n_of_created_instances
std::map< size_t, unsigned int > m_n_of_created_instances
Definition: AlgResourcePool.h:73
AlgResourcePool::finalize
StatusCode finalize() override
Definition: AlgResourcePool.cpp:435
std::list::push_back
T push_back(T... args)
AlgResourcePool
Definition: AlgResourcePool.h:38
Gaudi::Utils::begin
AttribStringParser::Iterator begin(const AttribStringParser &parser)
Definition: AttribStringParser.h:136
SmartIF::isValid
bool isValid() const
Allow for check if smart pointer is valid.
Definition: SmartIF.h:72
Gaudi::Utils::TypeNameString
Helper class to parse a string of format "type/name".
Definition: TypeNameString.h:20
AlgResourcePool::m_resource_requirements
std::map< size_t, state_type > m_resource_requirements
Definition: AlgResourcePool.h:71
Service::name
const std::string & name() const override
Retrieve name of the service
Definition: Service.cpp:332
StatusCode
Definition: StatusCode.h:65
std::map::at
T at(T... args)
IAlgorithm
Definition: IAlgorithm.h:38
AlgResourcePool::m_resource_indices
std::map< std::string_view, unsigned int > m_resource_indices
Definition: AlgResourcePool.h:74
Gaudi::Algorithm
Base class from which all concrete algorithm classes should be derived.
Definition: Algorithm.h:90
Gaudi::Property::value
const ValueType & value() const
Definition: Property.h:237
std::to_string
T to_string(T... args)
std::list::erase
T erase(T... args)
AlgResourcePool::stop
StatusCode stop() override
Definition: AlgResourcePool.cpp:417
AlgResourcePool::dumpInstanceMisses
void dumpInstanceMisses() const
Dump recorded Algorithm instance misses.
Definition: AlgResourcePool.cpp:386
SmartIF< IProperty >
AlgResourcePool::decodeTopAlgs
StatusCode decodeTopAlgs()
Decode the top Algorithm list.
Definition: AlgResourcePool.cpp:211
genconfuser.verbose
verbose
Definition: genconfuser.py:28
AlgResourcePool::concurrentQueueIAlgPtr
tbb::concurrent_bounded_queue< IAlgorithm * > concurrentQueueIAlgPtr
Definition: AlgResourcePool.h:63
endmsg
MsgStream & endmsg(MsgStream &s)
MsgStream Modifier: endmsg. Calls the output method of the MsgStream.
Definition: MsgStream.h:202
AlgResourcePool::m_overrideUnClonable
Gaudi::Property< bool > m_overrideUnClonable
Definition: AlgResourcePool.h:90
AlgResourcePool::m_n_of_allowed_instances
std::map< size_t, size_t > m_n_of_allowed_instances
Definition: AlgResourcePool.h:72
AlgResourcePool::start
StatusCode start() override
Definition: AlgResourcePool.cpp:62
Gaudi::Utils::TypeNameString::type
const std::string & type() const
Definition: TypeNameString.h:48
cpluginsvc.n
n
Definition: cpluginsvc.py:234
std::ostringstream
STL class.
AlgResourcePool::m_algInstanceMisses
std::unordered_map< std::string_view, unsigned int > m_algInstanceMisses
Counters for Algorithm instance misses.
Definition: AlgResourcePool.h:85
StatusCode::isFailure
bool isFailure() const
Definition: StatusCode.h:129
AlgResourcePool::m_lazyCreation
Gaudi::Property< bool > m_lazyCreation
Definition: AlgResourcePool.h:87
AlgResourcePool::acquireResource
StatusCode acquireResource(std::string_view name) override
Acquire a certain resource.
Definition: AlgResourcePool.cpp:160
std::list::emplace_back
T emplace_back(T... args)
ConditionsStallTest.name
name
Definition: ConditionsStallTest.py:77
StatusCode::SUCCESS
constexpr static const auto SUCCESS
Definition: StatusCode.h:100
Service::stop
StatusCode stop() override
Definition: Service.cpp:181
std::right
T right(T... args)
AlgResourcePool::m_topAlgNames
Gaudi::Property< std::vector< std::string > > m_topAlgNames
Definition: AlgResourcePool.h:88
AlgResourcePool.h
std::multimap::cbegin
T cbegin(T... args)
AlgResourcePool::flattenSequencer
StatusCode flattenSequencer(Gaudi::Algorithm *sequencer, ListAlg &alglist, unsigned int recursionDepth=0)
Recursively flatten an algList.
Definition: AlgResourcePool.cpp:178
DECLARE_COMPONENT
#define DECLARE_COMPONENT(type)
Definition: PluginServiceV1.h:46
std::multimap::insert
T insert(T... args)
AlgResourcePool::m_algqueue_map
std::map< size_t, concurrentQueueIAlgPtr * > m_algqueue_map
Definition: AlgResourcePool.h:70
AlgResourcePool::acquireAlgorithm
StatusCode acquireAlgorithm(std::string_view name, IAlgorithm *&algo, bool blocking=false) override
Acquire a certain algorithm using its name.
Definition: AlgResourcePool.cpp:80
DEBUG_MSG
#define DEBUG_MSG
Definition: AlgResourcePool.cpp:24
Sequence.h
AlgResourcePool::getFlatAlgList
std::list< IAlgorithm * > getFlatAlgList() override
Definition: AlgResourcePool.cpp:371
std::multimap
STL class.
AlgResourcePool::m_resource_mutex
std::mutex m_resource_mutex
Definition: AlgResourcePool.h:67
std::map::end
T end(T... args)
IOTest.end
end
Definition: IOTest.py:125
ManySmallAlgs.seq
seq
Definition: ManySmallAlgs.py:102
std::setw
T setw(T... args)
StatusCode::FAILURE
constexpr static const auto FAILURE
Definition: StatusCode.h:101
Gaudi::Sequence
Definition: Sequence.h:18
AlgResourcePool::releaseAlgorithm
StatusCode releaseAlgorithm(std::string_view name, IAlgorithm *&algo) override
Release a certain algorithm.
Definition: AlgResourcePool.cpp:143
IAlgorithm::sysInitialize
virtual StatusCode sysInitialize()=0
Initialization method invoked by the framework.
ISvcLocator.h
AlgResourcePool::m_topAlgPtrList
std::list< IAlgorithm * > m_topAlgPtrList
The top list of algorithms.
Definition: AlgResourcePool.h:109
Service::service
StatusCode service(const std::string &name, const T *&psvc, bool createIf=true) const
Access a service by name, creating it if it doesn't already exist.
Definition: Service.h:89
Gaudi::Algorithm::isSequence
bool isSequence() const override
Are we a Sequence?
Definition: Algorithm.h:198
AlgResourcePool::m_topAlgList
ListAlg m_topAlgList
The list of top algorithms.
Definition: AlgResourcePool.h:100
AlgResourcePool::getTopAlgList
std::list< IAlgorithm * > getTopAlgList() override
Definition: AlgResourcePool.cpp:379
Service::serviceLocator
SmartIF< ISvcLocator > & serviceLocator() const override
Retrieve pointer to service locator
Definition: Service.cpp:335
std::hash
PrepareBase.out
out
Definition: PrepareBase.py:20