17#include <TChainElement.h>
20#include <TFriendElement.h>
22#include <TMethodCall.h>
88 "Did not call finishWritingTo() before destroying the TEvent object!");
104 if (pattern.size()) {
113 return StatusCode::SUCCESS;
127 std::string_view treeName) {
130 if (
file ==
nullptr) {
132 return StatusCode::SUCCESS;
158 ATH_MSG_ERROR(
"Couldn't find metadata tree on input. Object is unusable!");
159 return StatusCode::FAILURE;
166 return StatusCode::FAILURE;
171 ATH_MSG_WARNING(
"Was expecting a metadata tree with size 1, instead of "
173 ATH_MSG_WARNING(
"The input file was most probably produced by hadd...");
179 static const std::string eventFormatTypeName =
181 ::TClass* cl = ::TClass::GetClass(eventFormatTypeName.c_str());
188 auto readEventFormatMetadata =
189 [&](std::string_view thisTreeName) -> StatusCode {
191 TTree* metaTree =
file->Get<TTree>(thisTreeName.data());
192 if (metaTree ==
nullptr) {
193 ATH_MSG_ERROR(
"Couldn't find metadata tree \"" << thisTreeName
195 return StatusCode::FAILURE;
198 if (metaTree->LoadTree(0) < 0) {
200 << thisTreeName <<
"\"");
201 return StatusCode::FAILURE;
205 const std::string eventFormatBranchName =
207 if (!metaTree->GetBranch(eventFormatBranchName.c_str())) {
211 ATH_MSG_INFO(
"Input file provides no event or metadata");
212 return StatusCode::RECOVERABLE;
219 metaTree->SetBranchAddress(eventFormatBranchName.c_str(), &format, &br);
221 ATH_MSG_ERROR(
"Failed to connect to xAOD::EventFormat object");
222 return StatusCode::FAILURE;
227 for (
const auto &[key, element] : *format) {
238 return StatusCode::SUCCESS;
244 if (
sc.isRecoverable()) {
247 return StatusCode::SUCCESS;
254 std::set<std::string> lOtherMetaTreeNames = {};
255 TList* lKeys =
file->GetListOfKeys();
258 for (
int iKey = 0; iKey < lKeys->GetEntries(); iKey++) {
260 std::string keyName = lKeys->At(iKey)->GetName();
267 const char* className = ((::TKey* )lKeys->At(iKey))->GetClassName();
268 static constexpr Bool_t LOAD = kFALSE;
269 static constexpr Bool_t SILENT = kTRUE;
270 ::TClass* cl = ::TClass::GetClass(className, LOAD, SILENT);
271 if ((cl !=
nullptr) && cl->InheritsFrom(::TTree::Class())) {
273 lOtherMetaTreeNames.insert(std::move(keyName));
280 for (
const std::string &metaTreeName : lOtherMetaTreeNames) {
281 ATH_CHECK(readEventFormatMetadata(metaTreeName));
304 stats.setNEvents(stats.nEvents() +
m_inTree->GetEntries());
310 listener->handle(beginIncident);
319 listener->handle(endIncident);
323 return StatusCode::SUCCESS;
346 if (useTreeCache && (!
m_inChain->GetCacheSize())) {
356 ATH_MSG_ERROR(
"Couldn't get the list of files from the input TChain");
357 return StatusCode::FAILURE;
359 if (!
files->GetEntries()) {
360 ATH_MSG_ERROR(
"No files are present in the received TChain");
361 return StatusCode::FAILURE;
363 const ::TChainElement* chEl =
364 dynamic_cast<const ::TChainElement*
>(
files->At(0));
367 return StatusCode::FAILURE;
370 std::unique_ptr<TFile> dummyFile{TFile::Open(chEl->GetTitle())};
373 return StatusCode::FAILURE;
388 return StatusCode::SUCCESS;
398 ::TFile*
file =
tree->GetCurrentFile();
416 return StatusCode::SUCCESS;
428 std::string_view treeName) {
433 return StatusCode::FAILURE;
438 ATH_MSG_ERROR(
"Object already writing to a file. Close that file first!");
439 return StatusCode::FAILURE;
447 m_outTree = std::make_unique<TTree>(treeName.data(),
"xAOD event tree");
457 return StatusCode::SUCCESS;
480 ATH_MSG_ERROR(
"The object doesn't seem to be connected to an output file!");
481 return StatusCode::FAILURE;
491 listener->handle(incident);
505 return StatusCode::SUCCESS;
511 metatree->SetAutoSave(10000);
512 metatree->SetAutoFlush(-30000000);
513 metatree->SetDirectory(
file);
521 }
catch (
const CxxUtils::ClassName::ExcBadClassName &
e) {
522 ::Error(
"xAOD::TEvent::finishWritingTo",
523 XAOD_MESSAGE(
"Class name parsing fails for %s ! "),
e.what());
524 return StatusCode::FAILURE;
530 std::vector<std::pair<std::string, TObjectManager* >> outputMetaObjects;
534 if (objMgr ==
nullptr) {
536 return StatusCode::FAILURE;
538 outputMetaObjects.emplace_back(key, objMgr);
543 for (
auto &[key, mgr] : outputMetaObjects) {
547 const ::Int_t splitLevel = (key.ends_with(
"Aux.") ? 1 : 0);
549 *(mgr->branchPtr()) =
550 metatree->Branch(key.c_str(), mgr->holder()->getClass()->GetName(),
551 mgr->holder()->getPtr(), 32000, splitLevel);
552 if (!mgr->branch()) {
554 << mgr->holder()->getClass()->GetName() <<
"/" << key
556 return StatusCode::FAILURE;
560 static constexpr bool METADATA =
true;
565 if (metatree->Fill() <= 0) {
566 ATH_MSG_ERROR(
"Failed to write event format metadata into the output");
567 metatree->SetDirectory(
nullptr);
568 return StatusCode::FAILURE;
573 metatree->SetDirectory(
nullptr);
579 return StatusCode::SUCCESS;
618 static constexpr bool TOP_STORE =
true;
620 key, TOP_STORE, mode), key)
622 ATH_MSG_ERROR(
"Couldn't connect TAuxStore object to the output");
691 const ::Long64_t fileEntry =
m_inChain->LoadTree(entry);
694 <<
" from the input chain");
708 static constexpr bool USE_TREE_CACHE =
false;
733 <<
" from the input file");
749 static const std::string dynStorePostfix =
"Aux.Dynamic";
750 if (key.ends_with(dynStorePostfix)) {
758 static constexpr bool SILENT =
true;
759 static constexpr bool METADATA =
false;
766 result += mgr->getEntry(getall);
774 listener->handle(incident);
793 return m_inChain->GetListOfFiles()->GetEntries();
829 ::Long64_t entry = 0;
830 for (::Long64_t i = 0; i <
file; ++i) {
871 std::string unsetObjects;
872 std::vector<std::pair<std::string, TVirtualManager* >> outputObjectsCopy;
875 outputObjectsCopy.emplace_back(key, mgr.get());
877 for (
auto &[key, mgr] : outputObjectsCopy) {
879 if (!mgr->create()) {
882 if (unsetObjects.size()) {
883 unsetObjects +=
", ";
885 unsetObjects.append(
"\"" + key +
"\"");
891 static constexpr bool METADATA =
false;
894 "in the output for object \""
901 if (unsetObjects.size()) {
902 ATH_MSG_ERROR(
"The following objects were not set in the current event: "
910 ATH_MSG_ERROR(
"Output tree filling failed with return value: " << ret);
930 std::vector<std::string> &vkeys,
931 bool metadata)
const {
933 std::set<std::string>
keys;
937 std::vector<TObjArray* > fullListOfBranches = {};
943 fullListOfBranches.push_back(
m_inMetaTree->GetListOfBranches());
949 fullListOfBranches.push_back(
m_inTree->GetListOfBranches());
954 TList* fList =
m_inTree->GetListOfFriends();
956 for (TObject* feObj : *fList) {
959 auto* pElement =
dynamic_cast<TFriendElement*
>(feObj);
960 if (pElement ==
nullptr) {
963 TTree* friendTree = pElement->GetTree();
965 fullListOfBranches.push_back(friendTree->GetListOfBranches());
973 for (
const TObjArray* in : fullListOfBranches) {
975 for (
const TObject* obj : *in) {
977 if (obj ==
nullptr) {
980 const TBranch* element =
dynamic_cast<const TBranch*
>(obj);
983 return StatusCode::FAILURE;
985 const std::string objClassName = element->GetClassName();
986 std::string key = obj->GetName();
989 if (objClassName == targetClassName) {
990 ATH_MSG_DEBUG(
"Matched \"" << targetClassName <<
"\" to key \"" << key
992 keys.insert(std::move(key));
999 ATH_MSG_DEBUG(
"Scanning input objects for \"" << targetClassName <<
"\"");
1000 for (
const auto &[key, vmgr] : inAux) {
1004 if (mgr ==
nullptr) {
1007 const std::string &objClassName = mgr->holder()->getClass()->GetName();
1010 if (objClassName == targetClassName) {
1011 ATH_MSG_DEBUG(
"Matched \"" << targetClassName <<
"\" to key \"" << key
1019 const TObjArray* out =
m_outTree->GetListOfBranches();
1022 for (
const TObject* obj : *out) {
1023 if (obj ==
nullptr) {
1026 const TBranch* element =
dynamic_cast<const TBranch*
>(obj);
1027 if (element ==
nullptr) {
1029 return StatusCode::FAILURE;
1031 const std::string objClassName = element->GetClassName();
1032 std::string key = obj->GetName();
1035 if (objClassName == targetClassName) {
1036 ATH_MSG_DEBUG(
"Matched \"" << targetClassName <<
"\" to key \"" << key
1038 keys.insert(std::move(key));
1046 ATH_MSG_DEBUG(
"Scanning output objects for \"" << targetClassName <<
"\"");
1047 for (
const auto &[key, vmgr] : outAux) {
1050 if (mgr ==
nullptr) {
1053 const std::string &objClassName = mgr->holder()->getClass()->GetName();
1056 if (objClassName == targetClassName) {
1057 ATH_MSG_DEBUG(
"Matched \"" << targetClassName <<
"\" to key \"" << key
1063 vkeys.insert(vkeys.end(),
keys.begin(),
keys.end());
1066 return StatusCode::SUCCESS;
1091 return StatusCode::FAILURE;
1099 return StatusCode::SUCCESS;
1103 if (silent ==
false) {
1106 return StatusCode::RECOVERABLE;
1112 if (silent ==
false) {
1120 ::TBranch* br =
m_inTree->GetBranch(key.c_str());
1121 if (br ==
nullptr) {
1126 return StatusCode::RECOVERABLE;
1130 br->SetMakeClass(0);
1134 std::string className = br->GetClassName();
1135 if (className ==
"") {
1139 className = ef->className();
1142 "Couldn't find an appropriate type with a dictionary for branch \""
1144 return StatusCode::FAILURE;
1147 ::TClass* realClass = ::TClass::GetClass(className.c_str());
1148 if (((!realClass) || (!realClass->IsLoaded())) && ef) {
1152 className = ef->className();
1153 realClass = ::TClass::GetClass(className.c_str());
1155 if ((!realClass) || (!realClass->IsLoaded())) {
1158 "Couldn't find an appropriate type with a dictionary for branch \""
1160 return StatusCode::FAILURE;
1167 static const ::EDataType dataType = kOther_t;
1173 void* ptr =
nullptr;
1178 if (mgr ==
nullptr) {
1179 ATH_MSG_ERROR(
"Couldn't access output manager for: " << key);
1180 return StatusCode::FAILURE;
1183 ptr = mgr->holder()->get();
1189 if (ptr ==
nullptr) {
1190 ptr = realClass->New();
1195 auto mgr = std::make_unique<TObjectManager>(
1196 nullptr, std::make_unique<THolder>(ptr, realClass), renewOnRead);
1205 << key <<
"\" is " << br->GetSplitLevel()
1206 <<
". This can only be read in kAthenaAccess mode.");
1208 *(mgr->holder()->getPtr()) =
nullptr;
1210 return StatusCode::FAILURE;
1214 const ::Int_t status =
1215 m_inTree->SetBranchAddress(key.c_str(), mgr->holder()->getPtr(),
1216 mgr->branchPtr(), realClass, dataType, kTRUE);
1219 << className <<
"\" to input branch \"" << key
1220 <<
"\". Return code: " << status);
1222 *(mgr->holder()->getPtr()) = 0;
1224 return StatusCode::FAILURE;
1244 return StatusCode::SUCCESS;
1260 return StatusCode::FAILURE;
1265 return StatusCode::SUCCESS;
1270 if (br ==
nullptr) {
1271 if (silent ==
false) {
1273 <<
"\" not available on input");
1275 return StatusCode::RECOVERABLE;
1279 if (br->GetEntries() == 0) {
1280 if (silent ==
false) {
1282 <<
"\" doesn't hold any data");
1284 return StatusCode::RECOVERABLE;
1288 br->SetMakeClass(0);
1292 ::EDataType dt = kOther_t;
1293 if (br->GetExpectedType(cl, dt) || (!cl)) {
1294 ATH_MSG_ERROR(
"Couldn't get the type for metadata branch \"" << key
1296 return StatusCode::FAILURE;
1300 void* ptr = cl->New();
1302 auto mgr = std::make_unique<TObjectManager>(
1303 nullptr, std::make_unique<THolder>(ptr, cl), renewOnRead);
1307 key.c_str(), mgr->holder()->getPtr(), mgr->branchPtr(), cl, dt, kTRUE);
1310 << cl->GetName() <<
"\" to input branch \"" << key
1311 <<
"\". Return code: " << status);
1313 *(mgr->holder()->getPtr()) = 0;
1315 return StatusCode::FAILURE;
1324 ATH_MSG_ERROR(
"Couldn't read in metadata object with key \"" << key
1326 return StatusCode::FAILURE;
1339 static constexpr bool METADATA =
true;
1344 return StatusCode::SUCCESS;
1361 return StatusCode::FAILURE;
1365 if ((!
m_inTree->GetBranch(prefix.c_str())) &&
1369 return StatusCode::SUCCESS;
1374 return StatusCode::SUCCESS;
1382 static constexpr bool SILENT =
false;
1386 return StatusCode::SUCCESS;
1392 static constexpr bool TOP_STORE =
true;
1393 auto store = std::make_unique<TAuxStore>(
1407 static constexpr bool IS_OWNER =
true;
1409 std::make_unique<TAuxManager>(store.release(), IS_OWNER);
1412 return StatusCode::SUCCESS;
1417 return StatusCode::FAILURE;
1433 return StatusCode::SUCCESS;
1439 return StatusCode::FAILURE;
1447 static constexpr bool SILENT =
false;
1451 return StatusCode::SUCCESS;
1457 static constexpr bool TOP_STORE =
true;
1458 auto store = std::make_unique<TAuxStore>(
1472 static constexpr bool IS_OWNER =
true;
1474 std::make_unique<TAuxManager>(store.release(), IS_OWNER);
1477 return StatusCode::SUCCESS;
1482 return StatusCode::FAILURE;
1502 (isAuxStore ==
false)) {
1503 return StatusCode::SUCCESS;
1516 auto itr = objects.find(key +
"Aux.");
1517 if (itr == objects.end()) {
1520 return StatusCode::SUCCESS;
1522 auxMgr = itr->second.get();
1523 auxKey = key +
"Aux.";
1526 if (metadata ==
false) {
1528 const ::Int_t readBytes = auxMgr->
getEntry();
1529 if (readBytes < 0) {
1531 "Couldn't load current entry for auxiliary object with key \""
1533 return StatusCode::FAILURE;
1538 const std::string dynAuxKey = auxKey +
"Dynamic";
1539 auto dynAuxMgr = objects.find(dynAuxKey);
1541 if ((dynAuxMgr != objects.end()) &&
1547 dynAuxMgr->second->getEntry();
1558 auto dynAuxMgr = objects.find(dynAuxKey);
1559 if (dynAuxMgr == objects.end()) {
1561 return StatusCode::FAILURE;
1563 dynAuxMgr->second->getEntry();
1570 return StatusCode::SUCCESS;
1576 switch (mgr.holder()->typeKind()) {
1591 if (
vec && (!
vec->trackIndices())) {
1592 Details::forceTrackIndices(*
vec);
1596 if ((!
vec) && (!aux)) {
1598 << mgr.holder()->getClass()->GetName()
1599 <<
"\" as SG::AuxVectorBase or SG::AuxElement");
1600 return StatusCode::FAILURE;
1604 const SG::IConstAuxStore* store = 0;
1610 << auxKey <<
"\" is not of the right type");
1611 return StatusCode::FAILURE;
1627 << auxKey <<
"\" is not of the right type");
1628 return StatusCode::FAILURE;
1630 void* p = omgr->
holder()->
getAs(
typeid(SG::IConstAuxStore));
1631 store =
reinterpret_cast<const SG::IConstAuxStore*
>(p);
1635 return StatusCode::FAILURE;
1640 vec->setStore(store);
1642 aux->setStore(store);
1645 return StatusCode::FAILURE;
1649 return StatusCode::SUCCESS;
1668 const std::string &key,
bool overwrite,
bool metadata,
1674 "No output tree defined. Did you forget to call writeTo(...)?");
1675 return StatusCode::FAILURE;
1685 ATH_MSG_ERROR(
"Meta-object \"" << typeName <<
"\"/\"" << key
1686 <<
"\" already recorded");
1687 return StatusCode::FAILURE;
1690 TClass* cl = TClass::GetClass(typeName.c_str());
1692 ATH_MSG_ERROR(
"Didn't find dictionary for type: " << typeName);
1693 return StatusCode::FAILURE;
1698 nullptr, std::make_unique<THolder>(obj, cl, isOwner), renewOnRead);
1700 return StatusCode::SUCCESS;
1707 <<
"\" already accessed from the input, can't be "
1708 "overwritten in memory");
1709 return StatusCode::FAILURE;
1713 const Int_t splitLevel = (key.ends_with(
"Aux.") ? 1 : 0);
1720 TClass* cl = TClass::GetClass(typeName.c_str());
1721 if (cl ==
nullptr) {
1722 ATH_MSG_ERROR(
"Didn't find dictionary for type: " << typeName);
1723 return StatusCode::FAILURE;
1734 auto mgr = std::make_unique<TObjectManager>(
1735 nullptr, std::make_unique<THolder>(obj, cl, isOwner), renewOnRead);
1740 static constexpr Int_t basketSize = 32000;
1742 m_outTree->Branch(key.c_str(), cl->GetName(),
1745 ATH_MSG_ERROR(
"Failed to create branch \"" << key <<
"\" out of type \""
1746 << cl->GetName() <<
"\"");
1749 return StatusCode::FAILURE;
1754 static constexpr bool METADATA =
false;
1759 return StatusCode::SUCCESS;
1765 ATH_MSG_ERROR(
"Manager object of the wrong type encountered");
1766 return StatusCode::FAILURE;
1775 TClass* cl = TClass::GetClass(typeName.c_str());
1777 ::strcmp(cl->GetName(), omgr->
holder()->
getClass()->GetName())) {
1779 << key <<
"\" the previous type was \""
1781 <<
"\", but the newly requested type is \"" << typeName
1783 return StatusCode::FAILURE;
1791 static constexpr bool METADATA =
false;
1795 return StatusCode::SUCCESS;
1803 if (iomgr !=
nullptr) {
1805 static const bool OVERWRITE =
true;
1806 static const bool IS_OWNER =
true;
1808 key, OVERWRITE, metadata, IS_OWNER));
1809 return StatusCode::SUCCESS;
1814 if (auxmgr !=
nullptr) {
1818 "TAuxStore auxiliary objects can only be recorded for event data");
1819 return StatusCode::FAILURE;
1823 return StatusCode::SUCCESS;
1827 ATH_MSG_ERROR(
"Unknown auxiliary store manager type encountered");
1828 return StatusCode::FAILURE;
1841 return StatusCode::SUCCESS;
1846 ATH_MSG_ERROR(
"Function called on an uninitialised object");
1847 return StatusCode::FAILURE;
1856 for (; itr != end; ++itr) {
1859 const std::string &branchName = itr->second.branchName();
1862 if (branchName.find(
"Aux.") != std::string::npos) {
1871 const std::string intName = branchName.substr(0, branchName.size() - 4);
1879 ::Bool_t auxFound = kFALSE;
1882 std::vector<TObjArray* > fullListOfBranches = {};
1884 fullListOfBranches.push_back(
m_inTree->GetListOfBranches());
1887 if (
m_inTree->GetListOfFriends()) {
1889 TList* fList =
m_inTree->GetListOfFriends();
1891 for (TObject* feObj : *fList) {
1894 auto* pElement =
dynamic_cast<TFriendElement*
>(feObj);
1897 TTree* friendTree = pElement->GetTree();
1899 fullListOfBranches.push_back(friendTree->GetListOfBranches());
1904 for (TObjArray* branches : fullListOfBranches) {
1905 for (Int_t i = 0; i < branches->GetEntriesFast(); ++i) {
1906 if (!branches->At(i))
1909 const TString
name(branches->At(i)->GetName());
1910 if (
name.BeginsWith(branchName) ||
name.BeginsWith(dynName)) {
1918 << intName <<
"\" belonging to branch \""
1919 << branchName <<
"\"");
1926 ::TClass* cl = ::TClass::GetClass(el->className().c_str());
1927 if ((!cl) || (!cl->IsLoaded())) {
1929 << el->className() <<
"\"");
1936 static ::TClass*
const baseCl = ::TClass::GetClass(baseName.c_str());
1938 ATH_MSG_ERROR(
"Couldn't get dictionary for type \"" << baseName
1940 return StatusCode::FAILURE;
1950 static constexpr bool TOP_STORE =
true;
1952 static constexpr bool PRINT_WARNINGS =
false;
1960 stats.branch(branchName,
id);
1964 stats.setBranchNum(stats.branchNum() + temp.getAuxIDs().size());
1969 const ::TBranch* container =
m_inTree->GetBranch(branchName.c_str());
1978 return StatusCode::SUCCESS;
1994 const std::string &key) {
1999 "No output tree defined. Did you forget to call writeTo(...)?");
2000 return StatusCode::FAILURE;
2004 const std::set<std::string>* filter = 0;
2007 filter = &(filter_itr->second);
2016 store->selectAux(*filter);
2021 static constexpr bool OWNS_STORE =
true;
2023 std::make_unique<TAuxManager>(store.release(), OWNS_STORE);
2026 return StatusCode::SUCCESS;
2030 if (vitr->second->object() == store.get()) {
2032 return StatusCode::SUCCESS;
2041 if (mgr ==
nullptr) {
2043 << key <<
"\" already exists, and is not of type TAuxStore");
2044 return StatusCode::FAILURE;
2049 store->selectAux(*filter);
2056 mgr->setObject(store.release());
2059 return StatusCode::SUCCESS;
2073 ::TMethodCall setNameCall;
2077 setNameCall.InitWithPrototype(mgr.holder()->getClass(),
"setName",
2079 if (setNameCall.IsValid()) {
2082 const ::TString params =
2083 ::TString::Format(
"\"%s\"", mgr.branch()->GetName());
2084 const char* charParams = params.Data();
2085 setNameCall.Execute(mgr.holder()->get(), charParams);
2088 ATH_MSG_WARNING(
"Couldn't find setName(...) function for container \""
2089 << mgr.branch()->GetName() <<
"\" (type: "
2090 << mgr.holder()->getClass()->GetName() <<
")");
2095 static const TClass*
const holderClass =
2097 if (!mgr.holder()->getClass()->InheritsFrom(holderClass)) {
2099 return StatusCode::SUCCESS;
2107 return StatusCode::FAILURE;
2112#ifndef XAOD_STANDALONE
2114 istore->toTransient( ctx );
2122 static constexpr bool TOP_STORE =
false;
2123 auto store = std::make_unique<TAuxStore>(
2124 ctx, mgr.branch()->GetName(), TOP_STORE,
2143 static constexpr bool SHARED_OWNER =
false;
2144 m_inputObjects[std::string(mgr.branch()->GetName()) +
"Dynamic"] =
2145 std::make_unique<TAuxManager>(store.get(), SHARED_OWNER);
2148 storeHolder->
setStore(store.release());
2151 return StatusCode::SUCCESS;
2174 return StatusCode::SUCCESS;
2178 if (!mgr->holder()->getClass()->InheritsFrom(
"SG::IAuxStoreIO")) {
2179 return StatusCode::SUCCESS;
2187 return StatusCode::FAILURE;
2194 auto item_itr =
m_auxItemList.find(mgr->branch()->GetName());
2196 sel.selectAux(item_itr->second);
2207 if (auxids.empty()) {
2208 return StatusCode::SUCCESS;
2212 const std::string dynNamePrefix =
2221 typedef std::pair<std::string, SG::auxid_t> AuxVarSort_t;
2222 std::vector<AuxVarSort_t> varsort;
2223 varsort.reserve(auxids.size());
2225 varsort.emplace_back(
r.getName(
id),
id);
2227 std::sort(varsort.begin(), varsort.end());
2230 for (
const auto &p : varsort) {
2236 const std::string brName = dynNamePrefix + p.first;
2239 Object_t::iterator bmgr = objects.find(brName);
2242 if (bmgr == objects.end()) {
2245 const std::type_info* brType = aux->
getIOType(
id);
2248 return StatusCode::FAILURE;
2251 std::string brProperTypeName =
"<unknown>";
2257 if (strlen(brType->name()) == 1) {
2260 brProperTypeName = brTypeName;
2264 if (rootType ==
'\0') {
2266 << brName <<
"\" of type \"" << brTypeName <<
"\"");
2267 return StatusCode::FAILURE;
2271 std::ostringstream leaflist;
2272 leaflist << brName <<
"/" << rootType;
2275 static constexpr bool IS_OWNER =
false;
2276 auto auxmgr = std::make_unique<TPrimitiveAuxBranchManager>(
2280 static constexpr Int_t BASKET_SIZE = 32000;
2281 *(auxmgr->branchPtr()) =
2282 outTree.Branch(brName.c_str(), auxmgr->holder()->get(),
2283 leaflist.str().c_str(), BASKET_SIZE);
2284 if (!auxmgr->branch()) {
2286 << brName <<
"\" out of type \"" << brProperTypeName
2289 *(auxmgr->holder()->getPtr()) = 0;
2290 return StatusCode::FAILURE;
2292 br = auxmgr->branch();
2295 objects[brName] = std::move(auxmgr);
2300 static constexpr Bool_t LOAD_IF_NOT_FOUND = kTRUE;
2301 static constexpr Bool_t SILENT = kTRUE;
2302 TClass* cl = TClass::GetClass(*brType, LOAD_IF_NOT_FOUND, SILENT);
2303 if (cl ==
nullptr) {
2306 cl = TClass::GetClass(brTypeName.c_str());
2308 if (cl ==
nullptr) {
2310 << brName <<
"\" of type \"" << brTypeName <<
"\"");
2311 return StatusCode::FAILURE;
2316 brProperTypeName = cl->GetName();
2319 static constexpr bool IS_OWNER =
false;
2320 auto auxmgr = std::make_unique<TAuxBranchManager>(
2324 static constexpr Int_t BASKET_SIZE = 32000;
2325 static constexpr Int_t SPLIT_LEVEL = 0;
2326 *(auxmgr->branchPtr()) = outTree.Branch(brName.c_str(), cl->GetName(),
2327 auxmgr->holder()->getPtr(),
2328 BASKET_SIZE, SPLIT_LEVEL);
2329 if (!auxmgr->branch()) {
2331 << brName <<
"\" out of type \"" << brProperTypeName
2334 *(auxmgr->holder()->getPtr()) = 0;
2335 return StatusCode::FAILURE;
2337 br = auxmgr->branch();
2340 objects[brName] = std::move(auxmgr);
2345 if (outTree.GetEntries()) {
2346 void* ptr = br->GetAddress();
2348 for (::Long64_t i = 0; i < outTree.GetEntries(); ++i) {
2351 br->SetAddress(ptr);
2358 mgr->branch()->GetName(),
2367 bmgr = objects.find(brName);
2368 if (bmgr == objects.end()) {
2369 ATH_MSG_FATAL(
"There is an internal logic error in the code...");
2370 return StatusCode::FAILURE;
2376 const_cast<void*
>(
static_cast<const void*
>(aux->
getIOData(
id)));
2377 bmgr->second->setObject(nc_data);
2381 return StatusCode::SUCCESS;
2389 return StatusCode::FAILURE;
2393 const std::set<std::string>* filter = 0;
2396 filter = &(filter_itr->second);
2405 store->selectAux(*filter);
2410 static constexpr bool OWNS_STORE =
false;
2411 m_outputObjects[key] = std::make_unique<TAuxManager>(store, OWNS_STORE);
2414 return StatusCode::SUCCESS;
2418 if (vitr->second->object() == store) {
2420 return StatusCode::SUCCESS;
2429 if (mgr ==
nullptr) {
2431 << key <<
"\" already exists, and is not of type TAuxStore");
2432 return StatusCode::FAILURE;
2437 store->selectAux(*filter);
2444 mgr->setObject(store);
2447 return StatusCode::SUCCESS;
#define ATH_CHECK
Evaluate an expression and check for errors.
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
Base class for elements of a container that can have aux data.
Handle mappings between names and auxid_t.
Manage index tracking and synchronization of auxiliary data.
std::vector< size_t > vec
Recursively separate out template arguments in a C++ class name.
Interface providing I/O for a generic auxiliary store.
virtual void lock()=0
Interface to allow an object to lock itself when made const in SG.
Handle mappings between names and auxid_t.
static AuxTypeRegistry & instance()
Return the singleton registry instance.
Manage index tracking and synchronization of auxiliary data.
Interface for objects taking part in direct ROOT I/O.
AuxStoreType
Type of the auxiliary store.
@ AST_ContainerStore
The store describes a container.
@ AST_ObjectStore
The store describes a single object.
virtual AuxStoreType getStoreType() const =0
Return the type of the store object.
virtual void setStore(IAuxStore *store)=0
Give an auxiliary store object to the holder object.
Interface providing I/O for a generic auxiliary store.
virtual SG::auxid_set_t getSelectedAuxIDs() const
Get a list of dynamic variables that need to be written out.
virtual const std::type_info * getIOType(SG::auxid_t auxid) const =0
Return the type of the data to be stored for one aux data item.
virtual const void * getIOData(SG::auxid_t auxid) const =0
Return a pointer to the data to be stored for one aux data item.
Interface for non-const operations on an auxiliary store.
A set of aux data identifiers.
Class helping in dealing with dynamic branch selection.
Manager for EDM objects created by ROOT.
const THolder * holder() const
Accessor to the Holder object.
EventFormat m_inputEventFormat
Format of the current input file.
const std::string & name() const override
Get the name of the instance.
std::set< std::string > m_inputMissingObjects
Objects that have been asked for, but were found to be missing in the current input.
const void * getInputObject(SG::sgkey_t key, const std::type_info &ti, bool silent) override
Function for retrieving an input object in a non-template way.
upgrade_mutex_t m_branchesMutex
Mutex for multithread synchronization.
std::unordered_map< std::string, std::unique_ptr< TVirtualManager > > Object_t
Definition of the internal data structure type.
Object_t m_inputObjects
Collection of all the managed input objects.
static const char *const METADATA_OBJECT_NAME
Name of the metadata tree or RNTuple.
Event(std::string_view name)
Constructor with a name.
StatusCode keys(std::vector< std::string > &vkeys, bool metadata) const
Provide a list of all data object keys associated with a specific type.
void setActive() const
Set this event object as the currently active one.
SG::sgkey_t getHash(const std::string &key) const override
Function returning the hash describing an object name.
Object_t m_inputMetaObjects
Collection of all the managed input meta-objects.
std::unordered_map< std::string, std::set< std::string > > m_auxItemList
Rules for selecting which auxiliary branches to write.
EventFormat * m_outputEventFormat
Format of the current output file.
Object_t m_outputObjects
Collection of all the managed output object.
SG::SGKeyMap< BranchInfo > m_branches ATLAS_THREAD_SAFE
Map from hashed sgkey to BranchInfo.
AthContainers_detail::upgrading_lock< upgrade_mutex_t > upgrading_lock_t
Lock type for multithread synchronization.
const EventContext & currentContext() const
Return the event context corresponding to this event.
std::vector< TVirtualIncidentListener * > m_listeners
Listeners who should be notified when certain incidents happen.
Object_t m_outputMetaObjects
Collection of all the managed output meta-objects.
ReadStats & stats()
Access the object belonging to the current thread.
static IOStats & instance()
Singleton object accessor.
Class describing the access statistics of a collection of branches.
void nextEvent()
Function incrementing the processed event counter.
BranchStats * container(const std::string &name)
Access the description of a container. Creating it if necessary.
void setBranchNum(::Int_t num)
Set the total number of branches on the input.
void readContainer(const std::string &name)
Function incrementing the read counter on a specific container.
Manager for TAuxStore objects.
TAuxStore * getStore()
Get a type-specific pointer to the managed object.
const SG::IConstAuxStore * getConstStore() const
Get a convenience pointer to the managed object.
"ROOT @c TTree implementation" of IAuxStore
Helper class for making sure the current directory is preserved.
EAuxMode
Auxiliary store "mode".
@ kAthenaAccess
Access containers/objects like Athena does.
@ kClassAccess
Access auxiliary data using the aux containers.
@ kBranchAccess
Access auxiliary data branch-by-branch.
::TTree * m_inMetaTree
Pointer to the metadata tree in the input file.
StatusCode connectObject(const std::string &key, bool silent) override
Function setting up access to a particular object.
StatusCode connectMetaAux(const std::string &prefix, bool standalone) override
Function setting up access to a set of auxiliary branches for a metadata object.
StatusCode connectAux(const std::string &prefix, bool standalone) override
Function setting up access to a set of auxiliary branches.
bool hasOutput() const override
Check if an output file is connected to the object.
std::unique_ptr< TChainStateTracker > m_inChainTracker
Optional object for tracking the state changes of an input TChain.
::Int_t getEntry(::Long64_t entry, ::Int_t getall=0) override
Function loading a given entry of the input TTree.
StatusCode setAuxStore(const std::string &key, Details::IObjectManager &mgr, bool metadata) override
Function connecting a DV object to its auxiliary store.
EAuxMode auxMode() const
Get what auxiliary access mode the object was constructed with.
bool hasInput() const override
Check if an input file is connected to the object.
StatusCode initStats()
Function to initialise the statistics for all Tree content.
::Long64_t m_entry
The entry to look at from the input tree.
::Long64_t getFiles() const
Get how many files are available on the currently defined input.
void setOtherMetaDataTreeNamePattern(const std::string &pattern)
Change the pattern used for collecting information from other MetaData trees NB: Additional MetaData ...
StatusCode finishWritingTo(TFile &file) override
Finish writing to an output file.
StatusCode getNames(const std::string &targetClassName, std::vector< std::string > &vkeys, bool metadata) const override
Function determining the list keys associated with a type name.
StatusCode setUpDynamicStore(TObjectManager &mgr, ::TTree *tree)
Function adding dynamic variable reading capabilities to an auxiliary store object.
std::regex m_otherMetaDataTreeNamePattern
::TChain * m_inChain
The (optional) chain provided as input.
StatusCode putAux(::TTree &outTree, TVirtualManager &mgr, bool metadata)
Function saving the dynamically created auxiliary properties.
EAuxMode m_auxMode
The auxiliary access mode.
::Int_t fill() override
Function filling one event into the output tree.
StatusCode readFrom(::TFile &inFile) override
Set up the reading of an input file from TFile This method implements the interface from Event.
virtual ~TEvent()
Destructor.
TEvent(EAuxMode mode=kClassAccess)
Default constructor.
SG::IAuxStore * recordAux(const std::string &key, SG::IAuxStoreHolder::AuxStoreType type=SG::IAuxStoreHolder::AST_ContainerStore)
Add an auxiliary store object to the output.
StatusCode record(void *obj, const std::string &typeName, const std::string &key, bool overwrite, bool metadata, bool isOwner) override
Record an object into a connected output file.
std::unique_ptr<::TTree > m_outTree
The tree that we are writing to.
bool m_inTreeMissing
Internal status flag showing that an input file is open, but it doesn't contain an event tree.
::Int_t m_inTreeNumber
The number of the currently open tree in the input chain.
::Int_t getFile(::Long64_t file, ::Int_t getall=0)
Load the first event for a given file from the input TChain.
StatusCode writeTo(TFile &file) override
Connect the object to an output file.
::TTree * m_inTree
The main tree that we are reading from.
StatusCode connectMetaObject(const std::string &key, bool silent) override
Function setting up access to a particular metadata object.
::Long64_t getEntries() const override
Get how many entries are available from the current input file(s).
void add(std::string_view fileName)
Add information about a new file that got accessed.
static TFileAccessTracer & instance()
Access the singleton instance of this class.
This class takes care of holding EDM objects in memory.
void setOwner(::Bool_t state=kTRUE)
Set whether the holder should own its object.
void ** getPtr()
Return a typeless pointer to the held object's pointer.
const ::TClass * getClass() const
virtual void * getAs(const std::type_info &tid, ::Bool_t silent=kFALSE) const
Return the object as a specific pointer.
@ DATAVECTOR
A DataVector container.
@ AUXELEMENT
A type inheriting from SG::AuxElement.
Class describing a certain "incident" that is communicated to user code.
Manager for EDM objects created by ROOT.
::TBranch ** branchPtr()
Pointer to the branch's pointer.
virtual void setObject(void *obj) override
Function replacing the object being handled.
virtual::Int_t getEntry(::Int_t getall=0) override
Function for updating the object in memory if needed.
::TBranch * branch()
Accessor to the branch.
Class providing an interface for classes listening to xAOD incidents.
Interface class for the "manager classes".
virtual const void * object() const =0
Function getting a const pointer to the object being handled.
virtual::Int_t getEntry(::Int_t getall=0)=0
Function for updating the object in memory if needed.
void setStructMode(EStructMode mode)
Set the structure mode of the object to a new value.
EStructMode
"Structural" modes of the object
@ kUndefinedStore
The structure mode is not defined.
@ kObjectStore
The object describes a single object.
@ kContainerStore
The object describes an entire container.
EStructMode structMode() const
Get what structure mode the object was constructed with.
std::vector< std::string > files
file names and file pointers
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...
AuxElement(SG::AuxVectorData *container, size_t index)
Base class for elements of a container that can have aux data.
size_t auxid_t
Identifier for a particular aux data item.
void sort(typename DataModel_detail::iterator< DVL > beg, typename DataModel_detail::iterator< DVL > end)
Specialization of sort for DataVector/List.
bool hasAuxStore(const TClass &cl)
Helper function deciding if a given type "has an auxiliary store".
bool isAuxStore(const TClass &cl)
Helper function deciding if a given type "is an auxiliary store".
bool isStandalone(const TClass &cl)
Helper function deciding if a given type "is a standalone object".
static const ::Int_t BeginEvent
A new event was just loaded.
static const ::Int_t EndInputFile
The processing of an input file has finished.
static const ::Int_t MetaDataStop
The metadata for the output file should be written out.
static const ::Int_t BeginInputFile
A new input file was just opened.
std::string dynBranchPrefix(const std::string &key)
This function is used to figure out what to name dynamic auxiliary branches coming from a container c...
char rootType(char typeidType)
This function is used internally in the code when creating primitive dynamic auxiliary branches.
std::string getFirstBranchMatch(TTree *tree, const std::string &pre)
This function is used to search for a branch in a TTree that contains a given substring.
std::string getTypeName(const std::type_info &ti)
This function is necessary in order to create type names that ROOT can understand.
ICaloAffectedTool is abstract interface for tools checking if 4 mom is in calo affected region.
EventFormat_v1 EventFormat
Definition of the current event format version.
static const ::Int_t CACHE_SIZE
Size of a possible TTreeCache.
Helper to disable undefined behavior sanitizer for a function.
Convert a type_info to a normalized string representation (matching the names used in the root dictio...