All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
IoComponentMgr.cpp
Go to the documentation of this file.
1 // IoComponentMgr.cxx
3 // Implementation file for class IoComponentMgr
4 // Author: S.Binet<binet@cern.ch>
6 
7 // GaudiMP includes
8 #include "IoComponentMgr.h"
11 
12 #include "GaudiKernel/IFileMgr.h"
14 #include <boost/filesystem.hpp>
15 
16 // STL includes
17 
18 // FrameWork includes
19 #include "GaudiKernel/Property.h"
20 
21 #define ON_DEBUG if (UNLIKELY(outputLevel() <= MSG::DEBUG))
22 #define ON_VERBOSE if (UNLIKELY(outputLevel() <= MSG::VERBOSE))
23 
24 #define DEBMSG ON_DEBUG debug()
25 #define VERMSG ON_VERBOSE verbose()
26 
28 
29 using namespace std;
30 
31 
32 std::ostream&
33 operator<< ( std::ostream& os, const IIoComponentMgr::IoMode::Type& m) {
34  switch (m) {
35  case IIoComponentMgr::IoMode::READ : os << "READ"; break;
36  case IIoComponentMgr::IoMode::WRITE : os << "WRITE"; break;
37  case IIoComponentMgr::IoMode::RW : os << "RW"; break;
38  default:
39  os << "INVALID"; break;
40  }
41 
42  return os;
43 
44 }
45 
46 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
47 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
48 
49 IoComponentMgr::IoComponentMgr( const std::string& name,
50  ISvcLocator* svc )
51 : base_class(name,svc), m_log(msgSvc(), name )
52 {
53  //
54  // Property declaration
55  //
56  //declareProperty( "Property", m_nProperty );
57 
58 // declareProperty ("Registry",
59 // m_dict_location = "GaudiMP.IoRegistry.registry",
60 // "Location of the python dictionary holding the "
61 // "associations: \n"
62 // " {component-name:{ 'old-fname' : ['io','new-fname'] }}\n"
63 // "\nSyntax: <python-module>.<python-module>.<fct-name> \n"
64 // " where fct-name is a function returning the wanted "
65 // " dictionary.");
66 }
67 
68 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
69 
71 {
72 }
73 
74 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
75 
78  m_log << MSG::DEBUG << "--> initialize()" << endmsg;
79 
80  if ( Service::initialize().isFailure() ) {
81  m_log << MSG::ERROR << "Unable to initialize Service base class" << endmsg;
82  return StatusCode::FAILURE;
83  }
85 
86  IIncidentSvc* p_incSvc(0);
87 
88  if (service("IncidentSvc", p_incSvc, true).isFailure()) {
89  m_log << MSG::ERROR << "unable to get the IncidentSvc" << endmsg;
90  return StatusCode::FAILURE;
91  } else {
92  p_incSvc->addListener( this, IncidentType::BeginOutputFile, 100, true);
93  p_incSvc->addListener( this, IncidentType::BeginInputFile, 100, true);
94  }
95 
96  return StatusCode::SUCCESS;
97 }
98 
99 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
100 
103  m_log << MSG::DEBUG << "--> finalize()" << endmsg;
104 
105  return StatusCode::SUCCESS;
106 }
107 
108 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
109 
112 bool
114  DEBMSG << "--> io_hasitem()" << endmsg;
115  if ( 0 == iocomponent ) {
116  return false;
117  }
118  const std::string& ioname = iocomponent->name();
119  IoRegistry_t::const_iterator io = m_ioregistry.find (ioname);
120  return io != m_ioregistry.end();
121 }
122 
123 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
124 
128 bool
130  const std::string& fname) const
131 {
132  m_log << MSG::DEBUG << "--> io_contains()" << endmsg;
133  if ( 0 == iocomponent ) {
134  return false;
135  }
136  const std::string& ioname = iocomponent->name();
137 
138  DEBMSG << "io_contains: c: " << ioname << " f: " << fname << endmsg;
139 
140  pair<iodITR,iodITR> fit = m_cdict.equal_range(iocomponent);
141  if (fit.first == fit.second) {
142  return false;
143  } else {
144  iodITR it;
145  for (it=fit.first; it != fit.second; ++it) {
146  IoComponentEntry ioe = it->second;
147  DEBMSG << " " << ioe << endmsg;
148  if (ioe.m_oldfname == "") {
149  m_log << MSG::ERROR << "IIoComponent " << ioname
150  << " has empty old filename" << endmsg;
151  return false;
152  } else if (ioe.m_oldfname == fname) {
153  return true;
154  }
155  }
156  }
157 
158  return false;
159 }
160 
161 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
162 
171 {
172  if ( 0 == iocomponent ) {
173  m_log << MSG::ERROR
174  << "io_register (component) received a NULL pointer !" << endmsg;
175  return StatusCode::FAILURE;
176  }
177  const std::string& ioname = iocomponent->name();
178  DEBMSG << "--> io_register(" << ioname << ")" << endmsg;
179  IoRegistry_t::iterator itr = m_ioregistry.find (ioname);
180  if ( itr == m_ioregistry.end() ) {
181  DEBMSG << " registering IoComponent \"" << ioname << "\"" << endmsg;
182  iocomponent->addRef(); // ownership...
183  m_ioregistry[ioname] = iocomponent;
184  m_iostack.push_back (iocomponent);
185  } else {
186  m_log << MSG::INFO << "IoComponent[" << iocomponent->name()
187  <<"] already registered @" << (void*)itr->second << endmsg;
188  }
189  return StatusCode::SUCCESS;
190 }
191 
192 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
193 
203  const std::string& fname,
204  const std::string& pfn)
205 {
206  if ( 0 == iocomponent ) {
207  return StatusCode::FAILURE;
208  }
209  const std::string& ioname = iocomponent->name();
210 
211  DEBMSG << "--> io_register(" << ioname << ","
212  << ( (iomode== IIoComponentMgr::IoMode::READ) ? "R" : "W" )
213  << "," << fname << ")" << endmsg;
214 
215  if ( !io_hasitem (iocomponent) ) {
216  if ( !io_register (iocomponent).isSuccess() ) {
217  m_log << MSG::ERROR
218  << "could not register component [" << iocomponent->name() << "] "
219  << "with the I/O component manager !"
220  << endmsg;
221  return StatusCode::FAILURE;
222  }
223  }
224 
225  pair<iodITR,iodITR> fit = m_cdict.equal_range(iocomponent);
226  if (fit.first != fit.second) {
227  for (iodITR it=fit.first; it != fit.second; ++it) {
228  IoComponentEntry ioe = it->second;
229  if (ioe.m_oldfname == fname) {
230  if (ioe.m_iomode == iomode) {
231  m_log << MSG::INFO << "IoComponent " << ioname
232  << " has already had file " << fname
233  << " registered with i/o mode " << iomode << endmsg;
234  return StatusCode::SUCCESS;
235  } else {
236  m_log << MSG::WARNING << "IoComponent " << ioname
237  << " has already had file " << fname
238  << " registered with a different i/o mode " << ioe.m_iomode
239  << " - now trying " << iomode << endmsg;
240  }
241  }
242  }
243  }
244 
245  // We need to take into account that boost::filesystem::absolute() does not
246  // work for files read from eos, i.e. starting with "root:"
247  std::string tmp_name = pfn.empty()?fname:pfn;
248  bool from_eos = tmp_name.find("root:")==0;
249  IoComponentEntry ioc(fname,(from_eos?tmp_name:boost::filesystem::absolute(tmp_name).string()),iomode);
250  m_cdict.insert( pair<IIoComponent*, IoComponentEntry>(iocomponent, ioc) );
251 
252  return StatusCode::SUCCESS;
253 }
254 
255 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
256 
262  std::string& fname)
263 {
264  if ( 0 == iocomponent ) {
265  return StatusCode::FAILURE;
266  }
267 
268  std::string ofname = fname;
269  const std::string& ioname = iocomponent->name();
270 
271  m_log << MSG::DEBUG << "--> io_retrieve(" << ioname << "," << fname << ")"
272  << endmsg;
273 
274  iodITR it;
275  if (!findComp(iocomponent,ofname,it)) {
276  DEBMSG << "could not find c: " << ioname << " old_f: " << ofname << endmsg;
277  return StatusCode::FAILURE;
278  } else {
279 
280  IoDict_t::iterator it;
281  for (it = m_cdict.equal_range(iocomponent).first;
282  it != m_cdict.equal_range(iocomponent).second;
283  ++it) {
284 
285  if (it->second.m_oldfname == ofname) {
286  DEBMSG << "retrieving new name for the component " << iocomponent->name()
287  << " old name: " << ofname
288  << ", new name: " << it->second.m_newfname << endmsg;
289  fname = it->second.m_newfname;
290  return StatusCode::SUCCESS;
291  }
292  }
293  }
294 
295  DEBMSG << "Unexpected error! Unable to find entry in the dictionary corresponding to old filename: " << ofname << endmsg;
296  return StatusCode::FAILURE;
297 }
298 
299 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
300 
307 {
308  m_log << MSG::DEBUG << "--> io_reinitialize()" << endmsg;
309  m_log << MSG::DEBUG << "reinitializing I/O subsystem..." << endmsg;
310 
311  if (m_log.level() <= MSG::DEBUG) {
312  m_log << MSG::DEBUG << "Listing all monitored entries: " << std::endl;
313  DEBMSG << list() << endmsg;
314  }
315 
316  bool allgood = true;
317  for ( IoStack_t::iterator io = m_iostack.begin(), ioEnd = m_iostack.end();
318  io != ioEnd;
319  ++io ) {
320  m_log << MSG::DEBUG << " [" << (*io)->name() << "]->io_reinit()..."
321  << endmsg;
322  if ( !(*io)->io_reinit().isSuccess() ) {
323  allgood = false;
324  m_log << MSG::ERROR << "problem in [" << (*io)->name()
325  << "]->io_reinit() !" << endmsg;
326  }
327  // we are done with this guy... release it
328  (*io)->release();
329  }
330 
331  // we are done.
332  // FIXME: shall we allow for multiple io_reinitialize ?
333  // m_iostack.clear();
334  // m_ioregistry.clear();
335  // m_cdict.clear();
336 
337  return allgood
340 }
341 
342 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
343 
345 IoComponentMgr::io_update(IIoComponent* ioc, const std::string& old_fname,
346  const std::string& new_fname) {
347 
348  DEBMSG << "--> io_update(" << ioc->name() << ","
349  << old_fname << "," << new_fname << ")" << endmsg;
350 
351  IoDict_t::iterator it;
352  for (it = m_cdict.equal_range(ioc).first;
353  it != m_cdict.equal_range(ioc).second;
354  ++it) {
355 
356  if (it->second.m_oldfname == old_fname) {
357  DEBMSG << "updating " << ioc->name() << " f: " << old_fname << " -> "
358  << new_fname << endmsg;
359  it->second.m_newfname = new_fname;
360  return StatusCode::SUCCESS;
361  }
362  }
363 
364  return StatusCode::FAILURE;
365 
366 }
367 
368 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
369 
371 IoComponentMgr::io_update(IIoComponent* ioc, const std::string& work_dir) {
372 
373  DEBMSG << "--> io_update(" << ioc->name() << ","
374  << work_dir << ")" << endmsg;
375 
376  IoDict_t::iterator it;
377  for (it = m_cdict.equal_range(ioc).first;
378  it != m_cdict.equal_range(ioc).second;
379  ++it) {
380 
381  switch(it->second.m_iomode) {
383  {
384  it->second.m_newfname = it->second.m_oldabspath;
385  break;
386  }
388  {
389  boost::filesystem::path oldPath(it->second.m_oldfname);
390  if(oldPath.is_relative() &&
391  oldPath.filename()==oldPath.relative_path()) {
392 
393  // Only file name was provided for writing. This is the usual mode of operation
394  // ***
395  // NB. In such cases it would make sense to set newfname=oldfname, however this will break
396  // existing client codes, which assume that newfname contains "/"
397  // Thus we set newfname=workdir/oldfname
398  // ***
399 
400  boost::filesystem::path newfname(work_dir);
401  newfname /= oldPath;
402  it->second.m_newfname = newfname.string();
403  }
404  else {
405  // New name should be the old absolute path
406  it->second.m_newfname = it->second.m_oldabspath;
407  }
408 
409  break;
410  }
411  default:
412  {
413  // Don't know how to deal with either RW or INVALID
414  m_log << MSG::ERROR << "Unable to update IoComponent for the mode " << it->second.m_iomode << endmsg;
415  return StatusCode::FAILURE;
416  }
417  }
418 
419  } // for
420 
421  return StatusCode::SUCCESS;
422 
423 }
424 
425 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
426 
428 IoComponentMgr::io_update_all (const std::string& work_dir)
429 {
430  DEBMSG << "-->io_update_all for the directory " << work_dir << endmsg;
431  bool allgood = true;
432  for ( IoStack_t::iterator io = m_iostack.begin(), ioEnd = m_iostack.end();
433  io != ioEnd;
434  ++io ) {
435  if ( !io_update(*io,work_dir).isSuccess() ) {
436  allgood = false;
437  m_log << MSG::ERROR << "problem in [" << (*io)->name()
438  << "]->io_update() !" << endmsg;
439  }
440  }
441  return allgood ? StatusCode::SUCCESS : StatusCode::FAILURE;
442 }
443 
444 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
445 
452 {
453 
454  m_log << MSG::DEBUG << "--> io_finalize()" << endmsg;
455  m_log << MSG::DEBUG << "finalizing I/O subsystem..." << endmsg;
456 
457  if (m_log.level() <= MSG::DEBUG) {
458  m_log << MSG::DEBUG << "Listing all monitored entries: " << std::endl;
459  DEBMSG << list() << endmsg;
460  }
461 
462  bool allgood = true;
463  for ( IoStack_t::iterator io = m_iostack.begin(), ioEnd = m_iostack.end();
464  io != ioEnd;
465  ++io ) {
466  m_log << MSG::DEBUG << " [" << (*io)->name() << "]->io_finalize()..."
467  << endmsg;
468  if ( !(*io)->io_finalize().isSuccess() ) {
469  allgood = false;
470  m_log << MSG::ERROR << "problem in [" << (*io)->name()
471  << "]->io_finalize() !" << endmsg;
472  }
473  }
474 
475  return allgood
478 }
479 
480 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
481 
482 bool
483 IoComponentMgr::findComp(IIoComponent* c, const std::string& f, iodITR& itr)
484  const {
485 
486  pair<iodITR,iodITR> pit;
487  if (!findComp(c,pit)) {
488  itr = pit.first;
489  return false;
490  }
491 
492  for (itr = pit.first; itr != pit.second; ++itr) {
493  if (itr->second.m_oldfname == f) {
494  return true;
495  }
496  }
497 
498  return false;
499 
500 }
501 
502 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
503 
504 bool
505 IoComponentMgr::findComp(IIoComponent* c, std::pair<iodITR,iodITR>& pit) const {
506 
507  pit = m_cdict.equal_range(c);
508 
509  if (pit.first == pit.second) {
510  return false;
511  } else {
512  return true;
513  }
514 
515 }
516 
517 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
518 
519 bool
520 IoComponentMgr::findComp(const std::string& c,
521  std::pair<iodITR,iodITR>& pit) const {
522 
523  pit.first = m_cdict.end();
524  pit.second = m_cdict.end();
525 
526  IoRegistry_t::const_iterator itr = m_ioregistry.find(c);
527  if (itr == m_ioregistry.end()) {
528  return false;
529  }
530 
531  return findComp(itr->second, pit);
532 }
533 
534 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
535 
536 std::string
538 
539  ostringstream ost;
540 
541  ost << "Listing all IoComponents (" << m_cdict.size() << "): " << endl;
542  for (iodITR it = m_cdict.begin(); it != m_cdict.end(); ++it) {
543  ost << " " << it->first->name() << " " << it->second
544  << endl;
545  }
546 
547  return ost.str();
548 }
549 
550 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
551 
552 void
554 
555  pair<iodITR,iodITR> pit;
556 
557 
558  if ( i.type() == IncidentType::BeginInputFile ) {
559 
560  const FileIncident *fi = dynamic_cast<const FileIncident*> ( &i );
561  DEBMSG << "BeginInputFile: s: " << fi->source() << " t: " << fi->type()
562  << " n: " << fi->fileName() << " g: " << fi->fileGuid()
563  << endmsg;
564 
565  if (findComp(fi->source(),pit)) {
566  DEBMSG << " found component: " << endmsg;
567  while (pit.first != pit.second) {
568  IIoComponent* c = pit.first->first;
569  IoComponentEntry e = pit.first->second;
570  DEBMSG << " c: " << c->name() << " " << e << endmsg;
571 
572  ++pit.first;
573  }
574  } else {
575  DEBMSG << " could not find component \"" << fi->source()
576  << "\"!" << endmsg;
577  }
578 
579 
580 
581  } else if ( i.type() == IncidentType::BeginOutputFile ) {
582 
583  const FileIncident *fi = dynamic_cast<const FileIncident*> ( &i );
584  DEBMSG << "BeginOutputFile: s: " << fi->source() << " t: " << fi->type()
585  << " n: " << fi->fileName() << " g: " << fi->fileGuid()
586  << endmsg;
587 
588  if (findComp(fi->source(),pit)) {
589  DEBMSG << " found component: " << endmsg;
590  while (pit.first != pit.second) {
591  IIoComponent* c = pit.first->first;
592  IoComponentEntry e = pit.first->second;
593  DEBMSG << " c: " << c->name() << " " << e << endmsg;
594 
595  ++pit.first;
596  }
597  } else {
598  DEBMSG << " could not find component \"" << fi->source()
599  << "\"!" << endmsg;
600  }
601 
602  }
603 
604 }
IntegerProperty m_outputLevel
Service output level.
Definition: Service.h:243
virtual bool io_contains(IIoComponent *iocomponent, const std::string &fname) const
: check if the registry contains a given IIoComponent and that component had
This class is the FileIncident.
Definition: FileIncident.h:18
The ISvcLocator is the interface implemented by the Service Factory in the Application Manager to loc...
Definition: ISvcLocator.h:26
const std::string & type() const
Access to the incident type.
Definition: Incident.h:34
MSG::Level level()
Retrieve output level.
Definition: MsgStream.h:112
This file contains the class definition for the FileIncident class.
const std::string & source() const
Access to the source of the incident.
Definition: Incident.h:40
bool isSuccess() const
Test for a status code of SUCCESS.
Definition: StatusCode.h:75
tuple c
Definition: gaudirun.py:341
IoDict_t::const_iterator iodITR
IoRegistry_t m_ioregistry
Registry of IIoComponents.
void handle(const Incident &)
Inform that a new incident has occurred.
#define DEBMSG
#define DECLARE_COMPONENT(type)
Definition: PluginService.h:36
virtual StatusCode io_update(IIoComponent *iocomponent, const std::string &old_fname, const std::string &new_fname)
: allow a IIoComponent to update the contents of the registry with a new file name ...
virtual const std::string & name() const =0
Retrieve the name of the instance.
std::string list() const
bool findComp(IIoComponent *, const std::string &, iodITR &) const
This class is used for returning status codes from appropriate routines.
Definition: StatusCode.h:30
virtual StatusCode io_reinitialize()
: reinitialize the I/O subsystem.
virtual StatusCode io_finalize()
: finalize the I/O subsystem.
IoComponentMgr()
Default constructor:
const std::string BeginOutputFile
a new output file has been created
Definition: Incident.h:72
virtual StatusCode initialize()
Gaudi Service Implementation.
const TYPE & value() const
explicit conversion
Definition: Property.h:355
std::string m_oldfname
GAUDI_API std::string path(const AIDA::IBaseHistogram *aida)
get the path in THS for AIDA histogram
virtual StatusCode initialize()
Initialization (from CONFIGURED to INITIALIZED).
Definition: Service.cpp:74
IIoComponentMgr::IoMode::Type m_iomode
Base class for all Incidents (computing events).
Definition: Incident.h:16
virtual void addListener(IIncidentListener *lis, const std::string &type="", long priority=0, bool rethrow=false, bool singleShot=false)=0
Add listener.
void setLevel(int level)
Update outputlevel.
Definition: MsgStream.h:106
Templated class to add the standard messaging functionalities.
virtual bool io_hasitem(IIoComponent *iocomponent) const
: check if the registry contains a given IIoComponent
virtual unsigned long addRef()=0
Increment the reference count of Interface instance.
const std::string & fileGuid() const
Definition: FileIncident.h:62
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:142
virtual ~IoComponentMgr()
Destructor:
virtual StatusCode io_retrieve(IIoComponent *iocomponent, std::string &fname)
: retrieve the new filename for a given IIoComponent and
IoStack_t m_iostack
Stack of IIoComponents to properly handle order of registration.
virtual StatusCode io_register(IIoComponent *iocomponent)
: allow a IIoComponent to register itself with this manager so appropriate actions can be taken when ...
virtual StatusCode finalize()
Finalize (from INITIALIZED to CONFIGURED).
const std::string & fileName() const
Definition: FileIncident.h:61
list i
Definition: ana.py:128
Type
the list of available types for ntuples
Definition: TupleObj.h:63
virtual StatusCode io_update_all(const std::string &work_dir)
: Update all IIoComponents with a new work directory
MsgStream & endmsg(MsgStream &s)
MsgStream Modifier: endmsg. Calls the output method of the MsgStream.
Definition: MsgStream.h:244
The interface implemented by the IncidentSvc service.
Definition: IIncidentSvc.h:22
const std::string BeginInputFile
a new input file has been started
Definition: Incident.h:77