20#include "TClassTable.h"
21#include "TClassEdit.h"
22#include "TVirtualCollectionProxy.h"
24#include "TDictAttributeMap.h"
30const std::type_info* dataTypeToTypeInfo (EDataType
type, std::string& typeName)
34 return typ.getTypeInfo();
54getAuxElementType( TClass *expectedClass, EDataType expectedType,
bool standalone,
55 std::string& elementTypeName, std::string& storageTypeName)
59 elementTypeName = expectedClass->GetName();
60 storageTypeName = elementTypeName;
61 return expectedClass->GetTypeInfo();
63 const std::type_info* ret = dataTypeToTypeInfo(expectedType, elementTypeName);
64 storageTypeName = elementTypeName;
69 if (!expectedClass)
return 0;
71 storageTypeName = expectedClass->GetName();
72 if (strncmp (expectedClass->GetName(),
"vector<", 7) == 0) {
73 TVirtualCollectionProxy* prox = expectedClass->GetCollectionProxy();
75 if (prox->GetValueClass()) {
76 elementTypeName = prox->GetValueClass()->GetName();
77 return prox->GetValueClass()->GetTypeInfo();
79 return dataTypeToTypeInfo (prox->GetType(), elementTypeName);
81 else if (strncmp (expectedClass->GetName(),
"SG::PackedContainer<", 20) == 0){
82 elementTypeName.clear();
87 R__WRITE_LOCKGUARD(ROOT::gCoreMutex);
88 TClassEdit::TSplitType
split (expectedClass->GetName());
89 if (
split.fElements.size() > 1) {
90 elementTypeName =
split.fElements[1];
93 if (!elementTypeName.empty()) {
95 return typ.getTypeInfo();
103getAuxIdForAttribute(
const std::string& attr, TClass *tclass, EDataType edt,
bool standalone,
112 string elemen_type_name;
113 string branch_type_name;
114 const std::type_info* ti = getAuxElementType(tclass, edt, standalone, elemen_type_name, branch_type_name);
126 TClass *
tc =
nullptr;
128 if( branch->GetExpectedType(
tc,
type) == 0 &&
tc ) {
129 std::string
key = branch->GetName();
130 const std::string clname_pfx = std::string(
tc->GetName()) +
'_';
131 if(
key.starts_with( clname_pfx ) ) {
132 key.erase(0, clname_pfx.size());
148 sizeof(Long_t) ==
sizeof(Long64_t) ) {
157 std::ostringstream
msg;
158 msg <<
"SetBranchAddress() failed for " <<
branch->GetName() <<
" error=" <<
rc;
173 m_key( getKeyFromBranch(base_branch) ),
177 TClass *
tc =
nullptr, *storeTC =
nullptr;
179 (void)base_branch->GetExpectedType(
tc,
type);
180 if(
tc ) storeTC =
tc->GetBaseClass(
"SG::IAuxStoreHolder");
183 const std::string name = (tc? tc->GetName() : m_baseBranchName);
184 errorcheck::ReportMessage msg (MSG::INFO, ERRORCHECK_ARGS,
"TBranchAuxDynReader");
185 msg <<
"IAuxStoreHolder interface not found in " << name <<
" - will not read dynamic attributes";
190 TObjArray *all_branches =
m_tree->GetListOfBranches();
191 for(
int i=0; i<all_branches->GetEntriesFast(); i++ ) {
192 const char *bname = (*all_branches)[i]->GetName();
193 if( strncmp(bname, branch_prefix.c_str(), branch_prefix.size()) == 0 ) {
194 const string attr_inFile = bname+branch_prefix.size();
195 const string attr =
r.inputRename (
m_key, attr_inFile);
203 const std::string& attr,
206 TClass* expectedClass = 0;
207 EDataType expectedType = kOther_t;
208 if( branch->GetExpectedType(expectedClass, expectedType) != 0) {
214 std::string className = expectedClass->GetName();
219 linked_auxid =
initBranch (standalone, linkedAttr, it->second);
223 msg <<
"Could not find linked variable for " << branch->GetName()
224 <<
" type: " << expectedClass->GetName();
229 SG::auxid_t auxid = getAuxIdForAttribute(attr, expectedClass, expectedType, standalone,
238 msg <<
"Could not find auxid for " << branch->GetName()
239 <<
" type: " << expectedClass->GetName();
252 initBranch (standalone, attr2branch.first, attr2branch.second);
266 brInfo.
auxid = auxid;
284 brInfo.
branch = it->second;
288 brInfo.
branch =
m_tree->GetBranch( aux_branch_name.c_str() );
298 throw string(
"Error getting branch type for ") + brInfo.
branch->GetName();
301 if( !store.standalone() )
302 if( brInfo.
tclass && strncmp( brInfo.
tclass->GetName(),
"SG::PackedContainer<", 20) == 0)
305 string elem_tname, branch_tname;
307 const std::type_info* ti = getAuxElementType( brInfo.
tclass, brInfo.
edtyp, store.standalone(),
308 elem_tname, branch_tname );
309 const std::type_info* reg_ti =
r.getType(auxid);
311 const std::type_info *io_tinf = store.getIOType(auxid);
312 const std::type_info *tcls_tinf = brInfo.
tclass ? brInfo.
tclass->GetTypeInfo() : ti;
316 throw string(
"Error getting IO type for AUX branch ") + brInfo.
branch->GetName();
321 io_tinf != tcls_tinf && (!tcls_tinf || strcmp(io_tinf->name(), tcls_tinf->name()) != 0)
322 : ti && ti != reg_ti && strcmp(ti->name(), reg_ti->name()) != 0;
327 msg <<
"attribute '" << brInfo.
attribName <<
"' (id=" << auxid
329 <<
") has different type than the branch: " << branch_tname;
330 msg <<
" Marking for schema evolution.";
332 brInfo.
SE_tclass = TClass::GetClass(*io_tinf);
335 brInfo.
SE_edt = TDataType::GetType(*io_tinf);
338 throw string(
"Error getting ROOT type for AUX branch ") + brInfo.
branch->GetName()
339 +
" typeinfo=" + io_tinf->name();
356 store_holder->setStore(
new TBranchAuxDynStore(*
this, ttree_row, standalone, iomtx) );
Hold information about an option setting request.
Handle mappings between names and auxid_t.
Exceptions that can be thrown from AthContainers.
char data[hepevt_bytes_allocation_ATLAS]
bool addAuxID(const SG::auxid_t &id)
An auxiliary data store that holds data internally.
Handle mappings between names and auxid_t.
static std::string linkedName(const std::string &name)
Given a variable name, return the name of the corresponding linked variable.
static bool classNameHasLink(const std::string &className)
Test to see if a class name corresponds to a class with a linked variable.
static AuxTypeRegistry & instance()
Return the singleton registry instance.
Interface for objects taking part in direct ROOT I/O.
@ AST_ObjectStore
The store describes a single object.
std::string m_baseBranchName
TBranchAuxDynReader(TTree *tree, TBranch *base_branch)
SG::auxid_t initBranch(bool standalone, const std::string &attr, TBranch *branch)
std::map< std::string, TBranch * > m_branchMap
virtual void addReaderToObject(void *object, size_t ttree_row, std::recursive_mutex *iomtx=nullptr) override final
Attach specialized AuxStore for reading dynamic attributes.
BranchInfo & getBranchInfo(const SG::auxid_t &auxid, const SG::AuxStoreInternal &store)
std::map< SG::auxid_t, BranchInfo > m_branchInfos
void init(bool standalone)
Helper class to use to report a message.
Helper for emitting error messages.
Find the auxid for a dynamic branch.
std::vector< std::string > split(const std::string &s, const std::string &t=":")
std::string getKeyFromBranch(TBranch *branch)
Exctract the Aux object SG Key from the branch name.
bool removeAuxPostfix(std::string &str)
if a string ends with AUX_POSTFIX then remove it
std::string auxBranchName(const std::string &attr_name, const std::string &baseBranchName)
Construct branch name for a given dynamic attribute.
std::string normalizedTypeinfoName(const std::type_info &info)
Convert a type_info to a normalized string representation (matching the names used in the root dictio...
static const auxid_t null_auxid
To signal no aux data item.
SG::auxid_t getDynamicAuxID(const std::type_info &ti, const std::string &name, const std::string &elementTypeName, const std::string &branch_type_name, bool standalone, SG::auxid_t linked_auxid)
Find the auxid for a dynamic branch.
size_t auxid_t
Identifier for a particular aux data item.
void setAddress(void *data)