Bootstrap.cpp
Go to the documentation of this file.
1 #include <iostream>
2 
3 #include "GaudiKernel/Bootstrap.h"
4 #include "GaudiKernel/System.h"
5 
6 #include "GaudiKernel/IInterface.h"
7 #include "GaudiKernel/IAlgorithm.h"
8 #include "GaudiKernel/IService.h"
9 #include "GaudiKernel/IAppMgrUI.h"
10 #include "GaudiKernel/ISvcLocator.h"
11 #include "GaudiKernel/IClassManager.h"
12 
13 #include "GaudiKernel/ObjectFactory.h"
14 #include "GaudiKernel/Service.h"
15 #include "GaudiKernel/Algorithm.h"
16 
17 #include "GaudiKernel/IJobOptionsSvc.h"
18 #include "GaudiKernel/IEventProcessor.h"
19 
20 #include "RVersion.h"
21 
22 namespace Gaudi
23 {
24 
40  class BootSvcLocator : public implements1<ISvcLocator> {
41  public:
43  virtual ~BootSvcLocator();
44 #if !defined(GAUDI_V22_API)|| defined(G22_NEW_SVCLOCATOR)
46  const InterfaceID& iid,
47  IInterface*& pinterface );
48  virtual StatusCode getService( const Gaudi::Utils::TypeNameString& typeName,
49  IService*& svc,
50  const bool createIf = true);
51 #endif
52  virtual const std::list<IService*>& getServices( ) const;
53  virtual bool existsService( const std::string& name ) const;
54 
56  virtual SmartIF<IService> &service(const Gaudi::Utils::TypeNameString &typeName, const bool createIf = true);
57 
58  };
59 }
60 
61 
62 static SmartIF<ISvcLocator> s_svclocInstance;
63 static SmartIF<IAppMgrUI> s_appmgrInstance;
64 
65 //------------------------------------------------------------------------------
66 IAppMgrUI* Gaudi::createApplicationMgr(const std::string& dllname,
67  const std::string& factname)
68 //------------------------------------------------------------------------------
69 {
70  // Allow not for multiple AppManagers: If already instantiated then just
71  // return it
72  if ( !s_appmgrInstance.isValid() ) {
73  s_appmgrInstance = createApplicationMgrEx(dllname, factname);
74  s_svclocInstance = s_appmgrInstance;
75  }
76  return s_appmgrInstance.get();
77 }
78 
79 //------------------------------------------------------------------------------
80 IAppMgrUI* Gaudi::createApplicationMgrEx(const std::string& dllname,
81  const std::string& factname)
82 //------------------------------------------------------------------------------
83 {
84  StatusCode status;
85  IInterface* iif;
86  IAppMgrUI* iappmgr;
87 
88  // Create an instance of the application Manager
89  iif = Gaudi::createInstance( "ApplicationMgr", factname, dllname );
90  if( iif == 0 ) {
91  return 0;
92  }
93  // Locate few interfaces of the Application Manager
94  status = iif->queryInterface( IAppMgrUI::interfaceID(), pp_cast<void>(&iappmgr) );
95  if( status.isFailure() ) {
96  return 0;
97  }
98  iif->release();
99  return iappmgr;
100 }
101 
102 //------------------------------------------------------------------------------
104 //------------------------------------------------------------------------------
105 //
106 // A dual-stage bootstrap mechanism is used to ensure an orderly startup
107 // of the ApplicationMgr. If this function is called before the singleton
108 // ApplicationMgr instance exists, a BootSvcLocator singleton instance is
109 // created. This responds to any subsequent requests for services by
110 // returning StatusCode::FAILURE, unless the ApplicationMgr singleton
111 // instance has been created in the interim. In this case, the BootSvcLocator
112 // forwards the request to the ApplicationMgr instance. The motivation for
113 // this is to handle static object instances where the constructor attempts
114 // to locate services and would otherwise instantiate the ApplicationMgr
115 // instance in an unorderly manner. This logic requires that the
116 // ApplicationMgr instance is created explicitly.
117 
118 {
119  if( !s_svclocInstance.isValid() ) {
120  IAppMgrUI* iappmgr = createApplicationMgr();
121  if( iappmgr ) {
122  s_svclocInstance = iappmgr;
123  if( s_svclocInstance.isValid() ) {
124  return s_svclocInstance;
125  }
126  }
127  //---Reverted change to create a Minimal SvcLocator in case is requested before AppMgr is created
128  //if( 0 == s_appmgrInstance ) {
129  // s_svclocInstance = new BootSvcLocator();
130  //} else {
131  // StatusCode sc = s_appmgrInstance->queryInterface( ISvcLocator::interfaceID(),
132  // pp_cast<void>(&s_svclocInstance) );
133  // if( sc.isSuccess() ) {
134  // return s_svclocInstance;
135  // }
136  //}
137  }
138  return s_svclocInstance;
139 }
140 
141 //------------------------------------------------------------------------------
143 //------------------------------------------------------------------------------
144 {
145  ISvcLocator* oldInstance = s_svclocInstance.get();
146  s_svclocInstance = newInstance;
147  s_appmgrInstance = s_svclocInstance;
148  return oldInstance;
149 }
150 
151 //------------------------------------------------------------------------------
153 //------------------------------------------------------------------------------
154 {
155  IAppMgrUI* oldInstance = s_appmgrInstance.get();
156  s_appmgrInstance = newInstance;
157  s_svclocInstance = s_appmgrInstance;
158  return oldInstance;
159 }
160 
161 //------------------------------------------------------------------------------
162 IInterface* Gaudi::createInstance( const std::string& name,
163  const std::string& factname,
164  const std::string& dllname)
165 //------------------------------------------------------------------------------
166 {
167 
168  IInterface* ii = ObjFactory::create(factname, (IInterface*)0);
169  if ( ii ) return ii;
170  IService* is = Service::Factory::create(factname, name, (ISvcLocator*)0);
171  if ( is ) return is;
172  IAlgorithm* ia = Algorithm::Factory::create(factname, name, (ISvcLocator*)0);
173  if ( ia ) return ia;
174 
175  StatusCode status;
176  void* libHandle = 0;
177  status = System::loadDynamicLib( dllname, &libHandle);
178  if ( status.isSuccess() ) {
179  ii = ObjFactory::create(factname, (IInterface*)0);
180  if ( ii ) return ii;
181  is = Service::Factory::create(factname, name, (ISvcLocator*)0);
182  if ( is ) return is;
183  ia = Algorithm::Factory::create(factname, name, (ISvcLocator*)0);
184  if ( ia ) return ia;
185 
186  return 0;
187  }
188  else {
189  // DLL library not loaded. Try in the local module
190  std::cout << System::getLastErrorString() << std::endl;
191  std::cout << "Gaudi::Bootstrap: Not found DLL " << dllname << std::endl;
192  return 0;
193  }
194 }
195 
196 //------------------------------------------------------------------------------
197 IAppMgrUI* Gaudi::createApplicationMgr(const std::string& dllname ) {
198 //------------------------------------------------------------------------------
199  return createApplicationMgr(dllname, "ApplicationMgr");
200 }
201 
202 //------------------------------------------------------------------------------
204 //------------------------------------------------------------------------------
205  return createApplicationMgr("GaudiCoreSvc", "ApplicationMgr");
206 }
207 
208 //=======================================================================
209 // BootSvcLocator
210 //=======================================================================
211 
212 static std::list<IService*> s_bootServices;
213 static SmartIF<IService> s_bootService;
214 static SmartIF<IInterface> s_bootInterface;
215 
217 
218 BootSvcLocator::BootSvcLocator() {
219 }
221 }
222 
223 #if !defined(GAUDI_V22_API) || defined(G22_NEW_SVCLOCATOR)
225  const InterfaceID& iid,
226  IInterface*& pinterface ) {
228  if ( s_appmgrInstance.isValid() ) {
229  sc = s_svclocInstance->getService(typeName, iid, pinterface );
230  } else {
231  pinterface = s_bootInterface.get();
232  }
233  return sc;
234 }
236  IService*& svc,
237  const bool createIf ) {
239  if ( s_appmgrInstance.isValid() ) {
240  sc = s_svclocInstance->getService(typeName, svc, createIf );
241  } else {
242  svc = s_bootService.get();
243  }
244  return sc;
245 }
246 #endif
247 
248 const std::list<IService*>& Gaudi::BootSvcLocator::getServices( ) const {
250  if ( s_appmgrInstance.isValid() ) {
251  return s_svclocInstance->getServices( );
252  } else {
253  return s_bootServices;
254  }
255 }
256 bool Gaudi::BootSvcLocator::existsService( const std::string& name ) const {
257  bool result = false;
258  if ( s_appmgrInstance.isValid() ) {
259  result = s_svclocInstance->existsService(name);
260  }
261  return result;
262 }
263 
264 
266  if ( s_appmgrInstance.isValid() ) {
267  return s_svclocInstance->service(typeName, createIf);
268  } else {
269  return s_bootService;
270  }
271 }
272 
273 
274 #ifdef GAUDI_HASCLASSVISIBILITY
275 #pragma GCC visibility push(default)
276 #endif
277 // Python bootstrap helpers
278 extern "C" {
279 #define PyHelper(x) py_bootstrap_ ## x
282  }
283  IInterface* PyHelper(getService)(IInterface* app, char* name) {
284  auto svcloc = SmartIF<ISvcLocator>(app);
285  if (svcloc) {
286  return SmartIF<IInterface>(svcloc->service(name)).get();
287  }
288  return nullptr;
289  }
290  bool PyHelper(setProperty)(IInterface* p, char* name, char* value) {
291  auto prop = SmartIF<IProperty>(p);
292  if (prop) {
293  return prop->setProperty(name, value).isSuccess();
294  }
295  return false;
296  }
297  const char* PyHelper(getProperty)(IInterface* p, char* name) {
298  auto prop = SmartIF<IProperty>(p);
299  if (prop) {
300  return prop->getProperty(name).toString().c_str();
301  }
302  return nullptr;
303  }
305  auto ui = SmartIF<IAppMgrUI>(app);
306  if (ui) {
307  return ui->configure().isSuccess();
308  }
309  return false;
310  }
311  bool PyHelper(addPropertyToCatalogue)(IInterface* p, char* comp, char* name, char* value) {
312  auto jos = SmartIF<IJobOptionsSvc>(p);
313  if (jos) {
314  return jos->addPropertyToCatalogue(comp, StringProperty(name, value)).isSuccess();
315  }
316  return false;
317  }
319  return ROOT_VERSION_CODE;
320  }
321 
322 #define PyFSMHelper(s) bool py_bootstrap_fsm_ ## s (IInterface* i) { \
323  auto fsm = SmartIF<IStateful>(i); \
324  if (fsm) { return fsm-> s ().isSuccess(); } \
325  return false; \
326  }
327 
328  PyFSMHelper(configure)
331  PyFSMHelper(stop)
332  PyFSMHelper(finalize)
333  PyFSMHelper(terminate)
334 
335  bool py_bootstrap_app_run(IInterface* i, int maxevt) {
337  if (ep) { return ep->executeRun(maxevt).isSuccess(); }
338  return false;
339  }
340 }
341 #ifdef GAUDI_HASCLASSVISIBILITY
342 #pragma GCC visibility pop
343 #endif
#define PyHelper(x)
Definition: Bootstrap.cpp:279
int PyHelper() ROOT_VERSION_CODE()
Definition: Bootstrap.cpp:318
#define PyFSMHelper(s)
Definition: Bootstrap.cpp:322
def initialize()
Definition: AnalysisTest.py:12
The ISvcLocator is the interface implemented by the Service Factory in the Application Manager to loc...
Definition: ISvcLocator.h:26
virtual StatusCode getProperty(Property *p) const =0
Get the property by property.
virtual bool existsService(const std::string &name) const
Check the existence of a service given a service name.
Definition: Bootstrap.cpp:256
int maxevt auto ep
Definition: Bootstrap.cpp:336
bool isSuccess() const
Test for a status code of SUCCESS.
Definition: StatusCode.h:75
virtual ~BootSvcLocator()
Definition: Bootstrap.cpp:220
bool PyHelper() addPropertyToCatalogue(IInterface *p, char *comp, char *name, char *value)
Definition: Bootstrap.cpp:311
GAUDI_API IAppMgrUI * createApplicationMgrEx(const std::string &dllname, const std::string &factname)
const char *PyHelper() getProperty(IInterface *p, char *name)
Definition: Bootstrap.cpp:297
bool isFailure() const
Test for a status code of FAILURE.
Definition: StatusCode.h:85
virtual SmartIF< IService > & service(const Gaudi::Utils::TypeNameString &typeName, const bool createIf=true)
Returns a smart pointer to a service.
Definition: Bootstrap.cpp:265
TYPE * get() const
Get interface pointer.
Definition: SmartIF.h:62
Gaudi::InterfaceId< IInterface, 0, 0 > iid
Interface ID.
Definition: IInterface.h:164
StatusCode service(const Gaudi::Utils::TypeNameString &name, T *&svc, bool createIf=true)
Templated method to access a service by name.
Definition: ISvcLocator.h:82
Base class used to implement the interfaces.
Definition: implements.h:133
Interface ID class.
Definition: IInterface.h:55
virtual StatusCode getService(const Gaudi::Utils::TypeNameString &typeName, const InterfaceID &iid, IInterface *&pinterface)
Get a specific interface pointer given a service name and interface id.
Definition: Bootstrap.cpp:224
Helper class to parse a string of format "type/name".
Definition: TypeNameString.h:9
GAUDI_API ISvcLocator * svcLocator()
General service interface definition.
Definition: IService.h:19
This class is used for returning status codes from appropriate routines.
Definition: StatusCode.h:30
Definition of the basic interface.
Definition: IInterface.h:160
virtual StatusCode setProperty(const Property &p)=0
Set the property by property.
virtual StatusCode getService(const Gaudi::Utils::TypeNameString &typeName, IService *&svc, const bool createIf=true)
Get a reference to the service given a service name.
Definition: ISvcLocator.h:36
bool PyHelper() setProperty(IInterface *p, char *name, char *value)
Definition: Bootstrap.cpp:290
SimpleProperty< std::string > StringProperty
Definition: Property.h:743
The IAlgorithm is the interface implemented by the Algorithm base class.
Definition: IAlgorithm.h:20
virtual const std::list< IService * > & getServices() const
Get a reference to a service and create it if it does not exists.
Definition: Bootstrap.cpp:248
Application Manager User Interface.
Definition: IAppMgrUI.h:21
GAUDI_API ISvcLocator * setInstance(ISvcLocator *newInstance)
Set new instance of service locator.
virtual unsigned long release()=0
Release Interface instance.
bool isValid() const
Allow for check if smart pointer is valid.
Definition: SmartIF.h:51
GAUDI_API const std::string getLastErrorString()
Get last system error as string.
Definition: System.cpp:254
virtual StatusCode addPropertyToCatalogue(const std::string &client, const Property &property)=0
Add a property into the JobOptions catalog.
A dual-stage boostrap mechanism is used to ensure an orderly startup of the ApplicationMgr.
Definition: Bootstrap.cpp:40
GAUDI_API unsigned long loadDynamicLib(const std::string &name, ImageHandle *handle)
Load dynamic link library.
Definition: System.cpp:124
virtual bool existsService(const std::string &name) const =0
Check the existence of a service given a service name.
virtual const std::list< IService * > & getServices() const =0
Get a reference to a service and create it if it does not exists.
std::string typeName(const std::type_info &typ)
Definition: Dictionary.cpp:22
virtual StatusCode configure()=0
Configure the job.
list i
Definition: ana.py:128
static const InterfaceID & interfaceID()
Return an instance of InterfaceID identifying the interface.
Definition: IInterface.h:171
bool PyHelper() configureApp(IInterface *app)
Definition: Bootstrap.cpp:304
IInterface *PyHelper() getService(IInterface *app, char *name)
Definition: Bootstrap.cpp:283
Helper functions to set/get the application return code.
Definition: __init__.py:1
GAUDI_API IInterface * createInstance(const std::string &name, const std::string &factname, const std::string &ddlname)
tuple start
Definition: IOTest.py:88
GAUDI_API IAppMgrUI * createApplicationMgr(const std::string &dllname, const std::string &factname)
virtual StatusCode queryInterface(const InterfaceID &ti, void **pp)=0
Set the void** to the pointer to the requested interface of the instance.