00001 #include "EventNavigator.h"
00002
00003 #undef DEFER
00004
00005
00006 #include <iostream>
00007 #include <string>
00008 #include <cmath>
00009
00010
00011 #include "TFile.h"
00012 #include "TTree.h"
00013
00014
00015 #include "format.h"
00016 #include "SetupRecord.h"
00017 #include "BankBranch.h"
00018 #include "TPulseIsland.h"
00019 #include "TAnalysedPulse.h"
00020 #include "TDetectorPulse.h"
00021 #include "TMuonEvent.h"
00022 #include "debug_tools.h"
00023 #include "CommandLine.h"
00024
00025 namespace Format = AlCapFormat;
00026
00027
00028
00029
00030
00031
00032
00033 EventNavigator* EventNavigator::fInstance = 0x0;
00034
00035
00036 EventNavigator& EventNavigator::InitInstance(const ARGUMENTS& command_line)
00037 {
00038 if (fInstance) {
00039 std::cout << "WARNING: "
00040 << "Instance has already been created and will not be altered"
00041 << std::endl;
00042 }
00043 else {
00044 fInstance = new EventNavigator(command_line);
00045
00046 }
00047 return *fInstance;
00048 }
00049
00050 EventNavigator& EventNavigator::Instance()
00051 {
00052 if (!fInstance){
00053 fInstance = new EventNavigator();
00054 }
00055 return *fInstance;
00056 }
00057
00058
00059 EventNavigator::EventNavigator()
00060 : fCopyRaw(true)
00061 , fLoopSequence(0x0)
00062 {
00063 fRawInput = 0x0;
00064 fOutput = 0x0;
00065
00066 }
00067
00068
00069 EventNavigator::EventNavigator(const ARGUMENTS& args)
00070 : fCopyRaw(true)
00071 , fRawInput(0x0)
00072 , fOutput(0x0)
00073 , fLoopSequence(new LoopSequence(args))
00074 {
00075 }
00076
00077
00078
00079 const LoopSequence& EventNavigator::GetLoopSequence() const
00080 {
00081 if (!fLoopSequence) throw std::runtime_error("No LoopSequence");
00082 return *fLoopSequence;
00083 }
00084
00085
00086 const LoopSequence& EventNavigator::MakeLoopSequence(const ARGUMENTS& args)
00087 {
00088
00089
00090 if (fLoopSequence) throw std::runtime_error("Redfined LoopSequence");
00091 fLoopSequence = new LoopSequence(args);
00092 return GetLoopSequence();
00093 }
00094
00095
00096 const char* EventNavigator::GetOutputFileName()const{
00097 return fOutput? fOutput->GetName():"";
00098 }
00099
00100
00101 Long64_t EventNavigator::GetStartEntry() const
00102 {
00103 return GetLoopSequence().StartEntry();
00104 }
00105
00106
00107
00108 Long64_t EventNavigator::GetStopEntry() const
00109 {
00110 return GetLoopSequence().StopEntry();
00111 }
00112
00113
00114
00115 Bool_t EventNavigator::ConnectInput(const char* input_name)
00116 {
00117
00118 TFile* ifile = TFile::Open(input_name, "READ");
00119 if (!ifile) return false;
00120 TList* lok = ifile->GetListOfKeys();
00121 bool success_data = false;
00122 bool success_meta = false;
00123 fSetupTree = 0x0;
00124 if (lok->Contains(Format::Raw::SetupTreeName) ) {
00125 if ( ConnectSetupData(ifile) != 0x0)
00126 success_meta = true;
00127 }
00128
00129 if (lok->Contains(Format::Raw::DataTreeName) ) {
00130 if ( ConnectRawData(ifile) != 0x0)
00131 success_data = true;
00132 }
00133
00134
00135 fEntryNo = 0;
00136 return success_data && success_meta;
00137 }
00138
00139
00140
00141 TGlobalData* EventNavigator::ConnectRawData(TFile* raw_file)
00142 {
00143 raw_file->GetObject(Format::Raw::DataTreeName, fRawTree);
00144 if ( !VerifyRawData(fRawTree) ){
00145 raw_file->Delete(Format::Raw::DataTreeName);
00146 fRawTree = 0x0;
00147 fRawData = 0x0;
00148 return 0x0;
00149 }
00150
00151
00152
00153 fRawData = new TGlobalData;
00154 int status = fRawTree->SetBranchAddress(Format::Raw::DataBranchName,
00155 &fRawData);
00156 if (status!=0){
00157 fRawTree = 0x0;
00158 fRawData = 0x0;
00159 return 0x0;
00160 }
00161
00162 this->LoadEntry(0);
00163
00164 return fRawData;
00165 }
00166
00167
00168
00169 Bool_t EventNavigator::VerifyRawData(TTree* raw_tree)
00170 {
00171 if ( !raw_tree ){
00172 std::cerr << "No raw data tree in file" << std::endl;
00173 return false;
00174 }
00175 if ( raw_tree->GetEntriesFast() == 0 ){
00176 std::cerr << "Tree " << raw_tree->GetName() << " is empty!"
00177 << std::endl;
00178 return false;
00179 }
00180 TObjArray* lob = raw_tree->GetListOfBranches();
00181 if ( !lob->Contains(Format::Raw::DataBranchName ) ){
00182 std::cerr << "Tree " << raw_tree->GetName()
00183 << " has no branch " << Format::Raw::SetupBranchName
00184 << "!" << std::endl;
00185 return false;
00186 }
00187 return true;
00188 }
00189
00190
00191 void EventNavigator::DumpRawTree() const
00192 {
00193 TTree* raw_tree=GetRawTree();
00194 if ( !raw_tree ){
00195 std::cerr << "No raw data tree in file" << std::endl;
00196 return;
00197 }
00198 std::cout << "Raw Tree '" << raw_tree->GetName() << "' has " <<
00199 raw_tree->GetEntriesFast()<<" entries. "<< std::endl;
00200 TBranch* raw_branch=raw_tree->GetBranch(Format::Raw::DataBranchName);
00201 if(!raw_branch) {
00202 std::cout << "Tree " << raw_tree->GetName()
00203 << " has no branch called " << Format::Raw::SetupBranchName
00204 << " which should normally contain the input data." << std::endl;
00205 } else {
00206 raw_branch->Print();
00207 }
00208 }
00209
00210 template<typename T, unsigned int& I> T ADV(T t) {
00211 if (I == 0) return t;
00212 return ADV<T,I-1>(++t);
00213 };
00214
00215
00216
00217 TSetupData* EventNavigator::ConnectSetupData(TFile* raw_file)
00218 {
00219 raw_file->GetObject(Format::Raw::SetupTreeName, fSetupTree);
00220 if ( !VerifySetupData(fSetupTree) ){
00221 raw_file->Delete(Format::Raw::SetupTreeName);
00222 fSetupData = 0x0;
00223 fSetupTree = 0x0;
00224 return 0x0;
00225 }
00226
00227 fSetupData = new TSetupData;
00228 int status = fSetupTree->SetBranchAddress(Format::Raw::SetupBranchName,
00229 &fSetupData);
00230 if (status!=0){
00231 fSetupTree = 0x0;
00232 fSetupData = 0x0;
00233 return 0x0;
00234 }
00235
00236 fSetupTree->GetEntry(0);
00237 fSetupRecord = new SetupRecord(fSetupData);
00238 return fSetupData;
00239
00240 }
00241
00242
00243
00244 Bool_t EventNavigator::VerifySetupData(TTree* setup_tree)
00245 {
00246 if ( !setup_tree ){
00247 std::cerr << "No 'Setup' tree in file" << std::endl;
00248 return false;
00249 }
00250 if ( setup_tree->GetEntriesFast() == 0 ){
00251 std::cerr << "Tree " << setup_tree->GetName() << " is empty!"
00252 << std::endl;
00253 return false;
00254 }
00255 TObjArray* lob = setup_tree->GetListOfBranches();
00256 if ( !lob->Contains(Format::Raw::SetupBranchName ) ){
00257 std::cerr << "Tree " << setup_tree->GetName()
00258 << " has no branch " << Format::Raw::SetupBranchName
00259 << "!" << std::endl;
00260 return false;
00261 }
00262 return true;
00263 }
00264
00265
00266
00267 Bool_t EventNavigator::ConnectOutput(const char* output_name, OutputMode mode)
00268 {
00269 static const char* output_mode[3] = {"NEW", "RECREATE", "UPDATE"};
00270 TFile* ofile = TFile::Open(output_name, output_mode[mode]);
00271 if (!ofile) return false;
00272
00273 fOutput = ofile;
00274 #ifdef DEFER
00275 if (fRawTree && fRawData && fCopyRaw) MirrorRawInputFormat();
00276 #endif
00277
00278 return true;
00279 }
00280
00281
00282
00283 Bool_t EventNavigator::MirrorRawInputFormat()
00284 {
00285 int prev_entry_no = fEntryNo;
00286
00287
00288 int nBytes = 0;
00289 int entry = fEntryNo;
00290 while (( nBytes = LoadEntry(++entry) )){
00291 if (fRawData->fPulseIslandToChannelMap.size() > 0) break;
00292 }
00293 if (nBytes <= 0) return false;
00294
00295 fOutputTreeTPI = new TTree("TPI","TPulseIslands");
00296 fOutputTreeTPI->SetAutoSave(3000000);
00297
00298 typedef StringPulseIslandMap::const_iterator raw_map_iter;
00299 StringPulseIslandMap& rawBanks = fRawData->fPulseIslandToChannelMap;
00300
00301
00302 TObjArray* obj_arr = new TObjArray(rawBanks.size());
00303
00304
00305 Int_t element =0;
00306 for (raw_map_iter b_it = rawBanks.begin(); b_it != rawBanks.end(); ++b_it) {
00307 std::string bank_name = b_it->first;
00308
00309
00310
00311
00312 ++element;
00313
00314
00315 BankBranch<PulseIslandList>* foo =
00316 new BankBranch<PulseIslandList>(IDs::generator(bank_name));
00317 obj_arr->Add(foo);
00318 }
00319 fOutputTreeTPI->Branch(obj_arr);
00320
00321 fOutputTreeTPI->Print();
00322
00323 fOutputTreeTPI->Write();
00324 GetEntry(prev_entry_no);
00325 return true;
00326 }
00327
00328
00329
00330 #ifdef DEFER
00331 const PulseIslandList& EventNavigator::FindIslandBank(const SourceID& sid) const{
00332 if (sid.isWildCard() ) return PulseIslandList(0);
00333 else return PulseIslandList(0);
00334 }
00335 #endif
00336
00337
00338 Bool_t EventNavigator::ConnectOutputFile(const char* output_file_name,
00339 Bool_t append)
00340 {
00341
00342
00343
00344 TFile* prev_output = fOutput;
00345
00346 fOutput = TFile::Open(output_file_name, (append ? "UPDATE" : "RECREATE"));
00347 if (!fOutput || fOutput->IsZombie()) return false;
00348
00349 prev_output->cd();
00350 return true;
00351 }
00352
00353
00354 Int_t EventNavigator::LoadEntry(Long64_t entry)
00355 {
00356 Int_t nBytes = 0;
00357 if (fRawTree){
00358 fRawData->Clear();
00359 nBytes = fRawTree->GetEntry(entry);
00360 }
00361 else if (fEventTree) {
00362 nBytes = fEventTree->GetEntry(entry);
00363 }
00364 else return 0;
00365 if (nBytes < 0) throw io_error();
00366 fEntryNo = entry;
00367 return nBytes;
00368 }
00369
00370
00371 Int_t EventNavigator::WriteCurrentEntry()
00372 {
00373 fOutputTreeTPI->Fill();
00374 return 0;
00375 }
00376
00377
00378 void EventNavigator::Close()
00379 {
00380 if (fRawInput) fRawInput->Close();
00381 if (fOutput) fOutput->Close();
00382 }
00383
00384
00385 extern void ClearGlobalData(TGlobalData* data);
00386
00387
00388
00389
00395 TSetupData* TSetupData::Instance(){
00396 return const_cast<TSetupData*>(EventNavigator::Instance().GetSetupData());
00397 }