30#include <TClonesArray.h>
31#include <TCollection.h>
34#include <TGeoManager.h>
37#include <TMCAutoLock.h>
40#include <TObjString.h>
62TMCMutex createMutex = TMCMUTEX_INITIALIZER;
63TMCMutex deleteMutex = TMCMUTEX_INITIALIZER;
66Int_t FairRootManager::fgCounter = 0;
67std::string FairRootManager::fFolderName =
"";
68std::string FairRootManager::fTreeName =
"";
78FairRootManager::FairRootManager()
88 , fBranchNameList(new TList())
89 , fMCTrackBranchId(-1)
90 , fTimeBasedBranchNameList(new TList())
93 , fWriteoutBufferMap()
96 , fBranchPerMap(kFALSE)
101 , fFillLastData(kFALSE)
108 , fUseFairLinks(kFALSE)
110 , fListOfBranchesFromInput(0)
111 , fListOfBranchesFromInputIter(0)
112 , fListOfNonTimebasedBranches(new TRefArray())
113 , fListOfNonTimebasedBranchesIter(0)
116 LOG(
debug) <<
"FairRootManager::FairRootManager: going to lock " <<
this;
118 TMCAutoLock lk(&createMutex);
128 LOG(
debug) <<
"Released lock and done FairRootManager::FairRootManager in " << fId <<
" " <<
this;
134 LOG(
debug) <<
"Enter Destructor of FairRootManager";
137 fBranchNameList->Delete();
138 delete fBranchNameList;
139 LOG(
debug) <<
"Leave Destructor of FairRootManager";
148 TMCAutoLock lk(&deleteMutex);
150 LOG(
debug) <<
"FairRootManager::~FairRootManager: going to lock " << fId <<
" " <<
this;
157 LOG(
debug) <<
"Released lock and done FairRootManager::~FairRootManager in " << fId <<
" " <<
this;
165 LOG(
debug) <<
"Call the initialiazer for the FairSource in FairRootManager ";
167 Bool_t sourceInitBool = fSource->
Init();
168 fListOfBranchesFromInput = fSourceChain->GetListOfBranches();
170 if (fListOfBranchesFromInput) {
171 fListOfBranchesFromInputIter = fListOfBranchesFromInput->MakeIterator();
172 while ((obj = fListOfBranchesFromInputIter->Next())) {
173 if ((fTimeBasedBranchNameList->FindObject(obj->GetName())) == 0)
174 fListOfNonTimebasedBranches->Add(obj);
177 LOG(
debug) <<
"Source is intialized and the list of branches is created in FairRootManager ";
178 fListOfNonTimebasedBranchesIter = fListOfNonTimebasedBranches->MakeIterator();
179 return sourceInitBool;
193void FairRootManager::RegisterImpl(
const char*
name,
const char* folderName, T* obj, Bool_t toFile)
202 if (strcmp(
name, folderName) == 0) {
203 LOG(fatal) <<
"The names for the object name " <<
name <<
" and the folder name " << folderName
204 <<
" are equal. This isn't allowed. So we stop the execution at this point. Pleae change either the "
205 "name or the folder name.";
213 LOG(fatal) <<
"The sink does not exist to store persistent branches.";
216 AddMemoryBranch(
name, obj);
219 if (toFile == kFALSE) {
226 RegisterImpl(
name, folderName, obj, toFile);
231 if (fBranchNameList->FindObject(
name) == 0) {
232 fBranchNameList->AddLast(
new TObjString(
name));
234 if (strcmp(
name,
"MCTrack") == 0) {
235 fMCTrackBranchId = fBranchSeqId;
244 RegisterImpl(
name, foldername, obj, toFile);
249 AddMemoryBranch(
name, obj);
257 TClonesArray* outputArray;
258 if (fActiveContainer.find(branchName) == fActiveContainer.end()) {
259 fActiveContainer[branchName] =
new TClonesArray(
className);
260 outputArray = fActiveContainer[branchName];
261 Register(branchName, folderName, outputArray, toFile);
264 return fActiveContainer[branchName];
269 if (fActiveContainer.find(branchName)
270 != fActiveContainer.end()) {
271 if (fActiveContainer[branchName] == 0) {
272 std::cout <<
"-E- FairRootManager::GetEmptyTClonesArray: Container deleted outside FairRootManager!"
275 fActiveContainer[branchName]->Delete();
277 return fActiveContainer[branchName];
279 std::cout <<
"-E- Branch: " << branchName <<
" not registered!"
287 if (fActiveContainer.find(branchName) != fActiveContainer.end()) {
288 return fActiveContainer[branchName];
290 LOG(info) <<
"Branch: " << branchName.Data() <<
" not registered!";
299 if (
id < fBranchSeqId) {
300 TObjString* ObjStr =
static_cast<TObjString*
>(fBranchNameList->At(
id));
301 return ObjStr->GetString();
303 TString NotFound(
"Branch not found");
313 for (Int_t t = 0; t < fBranchNameList->GetEntries(); t++) {
314 ObjStr =
static_cast<TObjString*
>(fBranchNameList->TList::At(t));
315 if (BrName == ObjStr->GetString()) {
330 if (fTSBufferMap[branchName] == 0) {
333 fTSBufferMap[branchName]->SetStopFunction(function);
334 return fTSBufferMap[branchName]->GetData(parameter);
339 Double_t startParameter,
341 Double_t stopParameter)
343 if (fTSBufferMap[branchName] == 0) {
346 fTSBufferMap[branchName]->SetStopFunction(stopFunction);
347 fTSBufferMap[branchName]->SetStartFunction(startFunction);
348 return fTSBufferMap[branchName]->GetData(startParameter, stopParameter);
353 if (fTSBufferMap.count(branchName) > 0) {
354 fTSBufferMap[branchName]->Terminate();
360 for (
auto& mi : fTSBufferMap) {
361 mi.second->Terminate();
367 for (
auto& mi : fTSBufferMap) {
368 if (mi.second->AllDataProcessed() == kFALSE && mi.second->TimeOut() == kFALSE) {
394 LOG(
debug) <<
"FairRootManager::Write " <<
this;
397 return (fSink->
Write());
416 TFile* oldfile = gFile;
417 TFile* file = TFile::Open(geofile,
"RECREATE");
419 gGeoManager->Write();
429 fSink->
WriteObject(fBranchNameList,
"BranchList", TObject::kSingleKey);
430 fSink->
WriteObject(fTimeBasedBranchNameList,
"TimeBasedBranchList", TObject::kSingleKey);
436 LOG(fatal) <<
"No Source available";
441 LOG(info) <<
"---FairRootManager::SpecifyRunId --- ";
454 LOG(fatal) <<
"No Source available";
460 Int_t readEventResult = fSource->
ReadEvent(
i);
465 LOG(
debug) <<
"--Event number --- " << fCurrentEntryNo <<
" with time ---- " << fCurrentTime;
467 return readEventResult;
504 fListOfNonTimebasedBranchesIter->Reset();
505 while ((Obj = fListOfNonTimebasedBranchesIter->Next())) {
518 Bool_t readentry = kFALSE;
525 fReqBrNames.emplace_back(BrName);
528 LOG(debug2) <<
" Try to find if the object " << BrName <<
" is already activated by another task or call";
531 Obj = fOutFolder->FindObjectAny(BrName);
533 LOG(debug2) <<
"Object " << BrName <<
" was already activated by another task";
538 LOG(debug2) <<
"Try to find if the object " << BrName <<
" is a memory branch";
539 Obj = GetMemoryBranch(BrName);
541 LOG(debug2) <<
"Object " << BrName <<
" is a memory branch";
545 if (fRootFolder && !Obj) {
547 LOG(debug2) <<
"Object " << BrName
548 <<
" is not a memory branch and not yet activated, try the Input Tree (Chain)";
549 Obj = fRootFolder->FindObjectAny(BrName);
550 Obj = ActivateBranch(BrName);
553 Obj = ActivateBranch(BrName);
565 Int_t fileId =
link.GetFile();
566 Int_t entryNr =
link.GetEntry();
579 }
else if (fileId == 0) {
593 TBranch* dataBranch = 0;
597 if (fileId < 0 && fInputBranchMap[
type] != 0) {
598 dataBranch = fInputBranchMap[
type];
599 }
else if (fileId < 0) {
601 dataBranch = fInputBranchMap[
type];
606 if (dataBranch == 0) {
611 if (entryNr < dataBranch->GetEntries()) {
612 dataBranch->GetEntry(entryNr);
629 if (index < dataArray->GetEntriesFast()) {
637 dataBranch->GetEntry(oldEntryNr);
647 Int_t fileId =
link.GetFile();
648 Int_t entryNr =
link.GetEntry();
661 }
else if (fileId == 0) {
675 TBranch* dataBranch = 0;
679 if (fileId < 0 && fInputBranchMap[
type] != 0) {
680 dataBranch = fInputBranchMap[
type];
681 }
else if (fileId < 0) {
683 dataBranch = fInputBranchMap[
type];
688 if (dataBranch == 0) {
693 if (entryNr < dataBranch->GetEntries()) {
694 dataBranch->GetEntry(entryNr);
710 dataBranch->GetEntry(oldEntryNr);
718 if (!fBranchPerMap) {
720 return CheckBranchSt(BrName);
722 fBrPerMapIter = fBrPerMap.find(BrName);
723 if (fBrPerMapIter != fBrPerMap.end()) {
724 return fBrPerMapIter->second;
736 fBranchNameList->Clear();
737 fMCTrackBranchId = -1;
738 for (Int_t t = 0; t < list->GetEntries(); t++) {
739 AddBranchToList(
static_cast<TObjString*
>(list->At(t))->GetString().Data());
746 fSourceChain = tempChain;
748 fSignalChainList[ident] = tempChain;
755 for (Int_t iobj = 0; iobj <= fNObj; iobj++) {
757 LOG(info) <<
"FairRootManager::UpdateBranches \"" << fObj2[iobj]->GetName() <<
"\" (\""
758 << fObj2[iobj]->GetTitle() <<
"\")";
759 TString tempBranchName = fObj2[iobj]->GetName();
767TObject* FairRootManager::ActivateBranch(
const char* BrName)
776 fObj2[fNObj] = GetMemoryBranch(BrName);
781 LOG(
debug) <<
"Try to find an object " << BrName <<
" describing the branch in the folder structure in file";
783 for (Int_t
i = 0;
i < fListFolder->GetEntriesFast();
i++) {
784 TFolder* fold =
static_cast<TFolder*
>(fListFolder->At(
i));
785 fObj2[fNObj] = fold->FindObjectAny(BrName);
787 LOG(info) <<
"Object " << BrName <<
" describing the branch in the folder structure was found";
797 LOG(info) <<
" Branch: " << BrName <<
" not found in Tree.";
805 AddMemoryBranch(BrName, fObj2[fNObj]);
809void FairRootManager::AddMemoryBranch(
const char* fName,
TObject* pObj)
812 map<TString, TObject*>::iterator
p;
813 TString BrName = fName;
814 p = fMap.find(BrName);
815 if (p != fMap.end()) {
817 fMap.insert(pair<TString, TObject*>(BrName, pObj));
821Int_t FairRootManager::CheckBranchSt(
const char* BrName)
824 Int_t returnvalue = 0;
827 if (fListFolder == 0) {
828 fListFolder =
new TObjArray(16);
833 fListFolder->Add(fRootFolder);
834 Obj1 = fRootFolder->FindObjectAny(BrName);
836 if (fOutFolder && !Obj1) {
837 fListFolder->Add(fOutFolder);
838 Obj1 = fOutFolder->FindObjectAny(BrName);
841 for (Int_t
i = 0;
i < fListFolder->GetEntriesFast();
i++) {
843 TFolder* fold =
dynamic_cast<TFolder*
>(fListFolder->At(
i));
845 Obj1 = fold->FindObjectAny(BrName);
853 Obj2 = GetMemoryBranch(BrName);
856 }
else if (Obj2 != 0) {
869void FairRootManager::CreatePerMap()
872 fBranchPerMap = kTRUE;
873 for (Int_t
i = 0;
i < fBranchSeqId;
i++) {
874 TObjString*
name =
static_cast<TObjString*
>(fBranchNameList->At(
i));
876 TString BrName =
name->GetString();
877 fBrPerMap.insert(pair<TString, Int_t>(BrName, CheckBranchSt(BrName.Data())));
881TObject* FairRootManager::GetMemoryBranch(
const char* fName)
885 TString BrName = fName;
886 map<TString, TObject*>::iterator
p;
887 p = fMap.find(BrName);
889 if (p != fMap.end()) {
899 fSink->
WriteObject(
f,
"FileHeader", TObject::kSingleKey);
911 if (fWriteoutBufferMap[branchName] == 0) {
912 fWriteoutBufferMap[branchName] =
buffer;
914 LOG(warn) <<
"Branch " << branchName.Data() <<
" is already registered in WriteoutBufferMap";
918 return fWriteoutBufferMap[branchName];
927 for (
auto& mi : fWriteoutBufferMap) {
928 if (mi.second->IsBufferingActivated())
929 fTimeBasedBranchNameList->AddLast(
new TObjString(mi.first.Data()));
940 fTimeBasedBranchNameList->Delete();
941 delete fTimeBasedBranchNameList;
942 fTimeBasedBranchNameList = list;
948 if (fWriteoutBufferMap.count(branchName) > 0) {
949 return fWriteoutBufferMap[branchName];
957 for (
auto& mi : fWriteoutBufferMap) {
958 mi.second->WriteOutData(eventTime);
964 Bool_t dataInBuffer = kFALSE;
965 for (
auto& mi : fWriteoutBufferMap) {
966 if (mi.second->GetNData() > 0) {
967 dataInBuffer = kTRUE;
969 mi.second->WriteOutAllData();
971 fFillLastData = dataInBuffer;
976 for (
auto& mi : fWriteoutBufferMap) {
977 mi.second->DeleteOldData();
981std::string FairRootManager::GetNameFromFile(
const char* namekind)
983 std::string default_name =
"";
985 if (strcmp(namekind,
"treename=") && strcmp(namekind,
"foldername=")) {
986 LOG(fatal) <<
"FairRootManager, requested " << namekind <<
", while only treename= and foldername= available.";
990 char* workdir = getenv(
"VMCWORKDIR");
991 if (
nullptr == workdir) {
996 std::ifstream
file(Form(
"%s/config/rootmanager.dat", workdir));
998 if (!
file.is_open()) {
1003 while (std::getline(file, line)) {
1004 if (
line.rfind(namekind, 0) == 0) {
1005 line.replace(0, strlen(namekind),
"");
1012 return default_name;
1017 if (fTreeName.length() > 0) {
1018 return Form(
"%s", fTreeName.c_str());
1021 std::string nameFromFile = GetNameFromFile(
"treename=");
1022 if (nameFromFile.length() > 0) {
1023 return Form(
"%s", nameFromFile.c_str());
1031 if (fFolderName.length() > 0) {
1032 return Form(
"%s", fFolderName.c_str());
1035 std::string nameFromFile = GetNameFromFile(
"foldername=");
1036 if (nameFromFile.length() > 0) {
1037 return Form(
"%s", nameFromFile.c_str());
1046void FairRootManager::EmitMemoryBranchWrongTypeWarning(
const char* brname,
const char* type1,
const char* type2)
const
1048 LOG(warn) <<
"Trying to read from memory branch " << brname <<
" with wrong type " << type1
1049 <<
" (expexted: " << type2 <<
" )";
1056 fileName.Insert(fileName.Index(
".root"), tid);
1061 LOG(warning) <<
"FairRootManager::GetOutFile() deprecated. Use separate file to store additional data.";
1063 assert(sink->GetSinkType() ==
kFILESINK);
1070 LOG(warning) <<
"FairRootManager::GetOutTree() deprecated. Use separate file to store additional data.";
1072 assert(sink->GetSinkType() ==
kFILESINK);
ClassImp(FairRootManager)
Base class for all functors which are used in the FairTSBufferFunctional.
static FairLinkManager * Instance()
virtual void AddIgnoreType(Int_t type)
void RecordRegister(const char *name, const char *folderName, Bool_t toFile)
void RecordGetting(const char *name)
static FairMonitor * GetMonitor()
TClonesArray * GetTClonesArray(TString branchName)
static const char * GetFolderName()
void Register(const char *name, const char *Foldername, TNamed *obj, Bool_t toFile)
FairWriteoutBuffer * RegisterWriteoutBuffer(TString branchName, FairWriteoutBuffer *buffer)
void UpdateListOfTimebasedBranches()
virtual ~FairRootManager()
void SetEntryNr(Int_t val)
void UpdateFileName(TString &fileName)
Int_t ReadEvent(Int_t i=0)
TChain * GetSignalChainNo(UInt_t i)
void CreateGeometryFile(const char *geofile)
TString GetBranchName(Int_t id)
void RegisterInputObject(const char *name, TObject *obj)
Int_t CheckMaxEventNo(Int_t EvtEnd=0)
void WriteFileHeader(FairFileHeader *f)
TObject * GetCloneOfLinkData(const FairLink link)
void TerminateTSBuffer(TString branchName)
void ReadBranchEvent(const char *BrName)
static const char * GetTreeName()
Int_t CheckBranch(const char *BrName)
void StoreWriteoutBufferData(Double_t eventTime)
static FairRootManager * Instance()
TClonesArray * GetData(TString branchName, BinaryFunctor *function, Double_t parameter)
Int_t AddBranchToList(const char *name)
Int_t ReadNonTimeBasedEventFromBranches(Int_t i=0)
void TerminateAllTSBuffer()
TClonesArray * GetCloneOfTClonesArray(const FairLink link)
TObject * GetObject(const char *BrName)
void InitTSBuffer(TString branchName, BinaryFunctor *function)
void SetBranchNameList(TList *list)
void SetTimeBasedBranchNameList(TList *list)
Int_t GetInstanceId() const
Int_t Write(const char *name=0, Int_t option=0, Int_t bufsize=0)
Bool_t AllDataProcessed()
Int_t GetBranchId(TString const &BrName)
Bool_t ReadNextEvent(Double_t dt)
TClonesArray * GetEmptyTClonesArray(TString branchName)
void StoreAllWriteoutBufferData()
void DeleteOldWriteoutBufferData()
void SetInChain(TChain *tempChain, Int_t ident=-1)
static FairRun * Instance()
virtual void RegisterImpl(const char *, const char *, void *)=0
virtual void WriteFolder()=0
virtual void WriteObject(TObject *f, const char *, Int_t option=0)=0
virtual Bool_t InitSink()=0
virtual Int_t Write(const char *name=0, Int_t option=0, Int_t bufsize=0)=0
virtual void WriteGeometry()=0
virtual Int_t CheckMaxEventNo(Int_t=0)
virtual Bool_t SpecifyRunId()=0
virtual Int_t ReadEvent(UInt_t=0)=0
virtual void ReadBranchEvent(const char *)
virtual void FillEventHeader(FairEventHeader *feh)
virtual Bool_t ActivateObject(TObject **, const char *)
A class to access time ordered data in a root branch.
A container class to store digi data during events.
GLuint const GLchar * name
GLint GLint GLsizei GLint GLenum GLenum type
int32_t const char * file
int32_t const char int32_t line
LOG(info)<< "Compressed in "<< sw.CpuTime()<< " s"