The Gaudi Framework  master (181af51f)
Loading...
Searching...
No Matches
PoolTool.h
Go to the documentation of this file.
1/***********************************************************************************\
2* (c) Copyright 1998-2025 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#pragma once
12
14#include <RootCnv/PoolClasses.h>
15#include <algorithm>
16/*
17 * Gaudi namespace declaration
18 */
19namespace Gaudi {
20
30 class PoolTool : virtual public RootDataConnection::Tool {
32 std::vector<Gaudi::RootRef> m_poolLinks;
33
34 public:
36 PoolTool( RootDataConnection* con ) { c = con; }
37
39 string _treeName( std::string_view sr ) {
40 std::string t{ sr };
41 std::replace( begin( t ), end( t ), '/', '_' );
42 return t;
43 }
44
45 RootRef poolRef( size_t i ) const override { return m_poolLinks[i]; }
46
48 int loadRefs( std::string_view /* section */, std::string_view cnt, unsigned long entry,
49 RootObjectRefs& refs ) override {
50 auto ti = sections().find( cnt );
51 TTree* t = ( ti != sections().end() ? ti->second : nullptr );
52 if ( !t ) { t = (TTree*)c->file()->Get( _treeName( cnt ).c_str() ); }
53 if ( t ) {
54 TBranch* b1 = t->GetBranch( "Links" );
55 TBranch* b2 = t->GetBranch( "Refs" );
56 MsgStream& msg = msgSvc();
57 if ( b1 && b2 ) {
58 LinkManager lm, *plm = &lm;
59 PoolDbLinkManager mgr, *pmgr = &mgr;
60 b1->SetAutoDelete( kFALSE );
61 b2->SetAutoDelete( kFALSE );
62 b1->SetAddress( &plm );
63 b2->SetAddress( &pmgr );
64 int nb1 = b1->GetEvent( entry );
65 int nb2 = b2->GetEvent( entry );
66 if ( nb1 > 1 && nb2 > 1 ) {
67 size_t ref_size = mgr.references().size();
68 refs.refs.resize( ref_size );
69 msg << MSG::VERBOSE;
70 for ( size_t j = 0; j < ref_size; ++j ) {
71 const pair<int, int>& oid = mgr.references()[j]->m_oid;
72 string loc = mgr.links()[j].substr( 1 );
73 RootRef& r = refs.refs[j];
74 if ( oid.first >= 0 ) {
75 r = m_poolLinks[oid.first];
76 r.entry = oid.second;
77 r.link = c->makeLink( loc );
78 msg << "Add leaf:" << oid.first << "->" << loc << " from " << c->getDb( r.dbase ) << "#"
79 << c->getCont( r.container ) << " Link:" << c->getLink( r.link ) << " CLID:" << hex << r.clid
80 << " Typ:" << hex << int( r.svc ) << " Ent:" << dec << r.entry << endl;
81 }
82 }
83 for ( int i = 0, n = lm.size(); i < n; ++i ) {
84 const LinkManager::Link* lnk = lm.link( i );
85 int link_id = c->makeLink( lnk->path() );
86 msg << "Add Link:" << lnk->path() << endl;
87 refs.links.push_back( link_id );
88 }
89 return nb1 + nb2;
90 }
91 }
92 msg << MSG::ERROR << "Failed to access POOL Ref/Link branches:" << cnt << " [" << _treeName( cnt ) << "]"
93 << endmsg;
94 t->Print();
95 }
96 return -1;
97 }
98
100 TBranch* getBranch( std::string_view /* section */, std::string_view branch_name ) override {
101 auto ti = sections().find( branch_name );
102 TTree* t = ( ti != sections().end() ? ti->second : nullptr );
103 if ( t ) { return (TBranch*)t->GetListOfBranches()->At( 0 ); }
104 string tname = _treeName( branch_name );
105 t = (TTree*)c->file()->Get( tname.c_str() ); // c->getSection(tname);
106 if ( t ) {
107 TBranch* b = (TBranch*)t->GetListOfBranches()->At( 0 );
108 if ( b ) {
109 sections()[std::string{ branch_name }] = t;
110 return b;
111 }
112 incidentSvc()->fireIncident( Incident( c->pfn(), IncidentType::CorruptedInputFile ) );
113 msgSvc() << MSG::ERROR << "Failed to access POOL branch:" << branch_name << " [" << tname << "]" << endmsg;
114 t->Print();
115 }
116 return nullptr;
117 }
118
121
123 StatusCode readRefs() override {
124 int i;
125 char text[2048];
126 msgSvc() << MSG::VERBOSE;
127
128 // First read ##Params
129 TTree* t = (TTree*)c->file()->Get( "##Params" );
130 if ( !t ) return StatusCode::FAILURE;
131 TBranch* b = t->GetBranch( "db_string" );
132 if ( !b ) return StatusCode::FAILURE;
133 for ( i = 0, b->SetAddress( text ); i < b->GetEntries(); ++i ) {
134 b->GetEvent( i );
135 char* id1 = strstr( text, "[NAME=" );
136 char* id2 = strstr( text, "[VALUE=" );
137 if ( id1 && id2 ) {
138 id1 += 6;
139 id2 += 7;
140 char* id11 = strstr( id1, "]" );
141 char* id22 = strstr( id2, "]" );
142 if ( id11 && id22 ) {
143 *id11 = 0;
144 *id22 = 0;
145 params().emplace_back( id1, id2 );
146 msgSvc() << "Param:" << id1 << "=" << id2 << "." << endmsg;
147 }
148 }
149 }
150
151 // Read ##Links
152 t = (TTree*)c->file()->Get( "##Links" );
153 if ( !t ) return StatusCode::FAILURE;
154 b = t->GetBranch( "db_string" );
155 if ( !b ) return StatusCode::FAILURE;
156 m_poolLinks.resize( (size_t)b->GetEntries() + 2 ); // Take into account the ##Links and ##Shapes entry of POOL!
157 for ( i = 0, b->SetAddress( text ); i < b->GetEntries(); ++i ) {
158 b->GetEvent( i );
159 std::string db, container;
160 int clid = 1, technology = 0, ipar[2] = { -1, -1 };
161 for ( char* p1 = (char*)text; p1; p1 = ::strchr( ++p1, '[' ) ) {
162 char* p2 = ::strchr( p1, '=' );
163 char* p3 = ::strchr( p1, ']' );
164 if ( p2 && p3 ) {
165 if ( ::strncmp( "[DB=", p1, 4 ) == 0 ) {
166 *p3 = 0;
167 db = p1 + 4;
168 } else if ( ::strncmp( "[CNT=", p1, 5 ) == 0 ) {
169 *p3 = 0;
170 container = p1 + 5;
171 } else if ( ::strncmp( "[OID=", p1, 5 ) == 0 ) {
172 *p3 = 0;
173 ::sscanf( p1 + 5, "%08X,%08X", (unsigned int*)&ipar[0], (unsigned int*)&ipar[1] );
174 } else if ( ::strncmp( "[CLID=", p1, 6 ) == 0 ) {
175 *p3 = 0;
176 ::sscanf( p1 + 6, "%08X", (unsigned int*)&clid );
177 } else if ( ::strncmp( "[TECH=", p1, 6 ) == 0 ) {
178 *p3 = 0;
179 ::sscanf( p1 + 6, "%08X", (unsigned int*)&technology );
180 } else {
181 *p3 = *p2 = 0;
182 }
183 *p3 = ']';
184 *p2 = '=';
185 }
186 }
187 c->makeRef( "", clid, technology, db, container, -1, m_poolLinks[i + 2] );
188 RootRef& r = m_poolLinks[i];
189 msgSvc() << "Add link[" << i << "]:" << db << container << " [" << r.dbase << "," << r.container << "] "
190 << " tech:" << hex << setw( 8 ) << r.svc << " CLID:" << setw( 8 ) << r.clid << dec << endmsg;
191 }
192 return StatusCode::SUCCESS;
193 }
194 };
195} // namespace Gaudi
MsgStream & endmsg(MsgStream &s)
MsgStream Modifier: endmsg. Calls the output method of the MsgStream.
Definition MsgStream.h:198
int loadRefs(std::string_view, std::string_view cnt, unsigned long entry, RootObjectRefs &refs) override
Load references object from file.
Definition PoolTool.h:48
PoolTool(RootDataConnection *con)
Standard constructor.
Definition PoolTool.h:36
RootRef poolRef(size_t i) const override
Internal overload to facilitate the access to POOL files.
Definition PoolTool.h:45
string _treeName(std::string_view sr)
Convert TES object identifier to ROOT tree name.
Definition PoolTool.h:39
std::vector< Gaudi::RootRef > m_poolLinks
Image of the POOL ##Links table.
Definition PoolTool.h:32
TBranch * getBranch(std::string_view, std::string_view branch_name) override
Access data branch by name: Get existing branch in read only mode.
Definition PoolTool.h:100
StatusCode saveRefs() override
Save references section when closing data file (NOT SUPPORTED)
Definition PoolTool.h:120
StatusCode readRefs() override
Internal helper to read reference tables ##Params and ##Links.
Definition PoolTool.h:123
Helper class to facilitate an abstraction layer for reading POOL style files with this package.
RootDataConnection * c
Pointer to containing data connection object.
Concrete implementation of the IDataConnection interface to access ROOT files.
virtual void fireIncident(const Incident &incident)=0
Fire an Incident.
Base class for all Incidents (computing events).
Definition Incident.h:24
Definition of the MsgStream class used to transmit messages.
Definition MsgStream.h:29
This class is used for returning status codes from appropriate routines.
Definition StatusCode.h:64
constexpr static const auto SUCCESS
Definition StatusCode.h:99
constexpr static const auto FAILURE
Definition StatusCode.h:100
This file provides a Grammar for the type Gaudi::Accumulators::Axis It allows to use that type from p...
Definition __init__.py:1
@ ERROR
Definition IMessageSvc.h:22
@ VERBOSE
Definition IMessageSvc.h:22
Persistent reference object containing all leafs and links corresponding to a Gaudi DataObject.
Definition extractEvt.C:81
Persistent reference object.
Definition extractEvt.C:44
int dbase
Data members to define object location in the persistent world.
Definition RootRefs.h:41