Universita' di GenovaINFN Sezione di Genova  
AIRWATCH / EUSO Genova

RecoFramework - source file

// $Id: RecoFramework.cc,v 1.37 2005/11/01 12:11:31 naumov Exp $
// Author: Marco Pallavicini Oct, 16 2003
// 
/*****************************************************************************
 * ESAF: Euso Simulation and Analysis Framework                              *
 *                                                                           *
 *  Id: RecoFramework                                                        *
 *  Package: framework                                                       *
 *  Coordinator: Marco.Pallavicini                                           *
 *                                                                           *
 *****************************************************************************/

#include "RecoFramework.hh"
#include "Config.hh"
#include "ModuleFactory.hh"
#include "RecoModule.hh"
#include "InputModule.hh"
#include "RecoEvent.hh"
#include "RecoRootEvent.hh"
#include "TruthModule.hh"
#include "EsafMsgDispatcher.hh"

#include <TTree.h>
#include <TFile.h>
#include <TObjectTable.h>
#include <TDirectory.h>
#include <TBenchmark.h>

ClassImp(RecoFramework)

//_____________________________________________________________________________
 RecoFramework::RecoFramework(int argc, char** argv) : EsafConfigurable(), EsafMsgSource(), fRootFile(NULL) {
    //
    // Costructor
    //

    ParseCommandLine(argc,argv);

    const char log[] = "output/reco.root";

    EsafMsgDispatcher::Get()->LoadConfig();
    EsafMsgDispatcher::Get()->OpenLog(log);
    Msg(EsafMsg::Info) << "Logging to file " << log <<".log" << " started" << MsgDispatch;

    // get file name with module list
    string sName = Conf()->GetStr("RecoFramework.ModuleFile");
    sName = "./config/Reco/"+sName;
    
    // build factory 
    ModuleFactory factory( sName );
    
    // get unique input module
    fInputModule = factory.GetInputModule();
    if ( fInputModule == NULL ) {
        Msg(EsafMsg::Panic) << "Cannot run without input module"<< MsgDispatch;
    }
    
    // get modules
    Int_t counter=0;
    while ( RecoModule *aModule = factory.GetModule() ) {
        Msg(EsafMsg::Info) <<  "Loading module : " << aModule->GetName() << MsgDispatch;
        fModules.push_back(aModule);
        counter++;
    }
    Msg(EsafMsg::Info) << "RecoFramework: " << counter << " modules loaded" << MsgDispatch;
    fCurrentEvent = 0;

}

//_____________________________________________________________________________
 RecoFramework::~RecoFramework() {
    //
    // Destructor
    // 
}

//_____________________________________________________________________________
 void RecoFramework::ParseCommandLine(int& argc, char** argv) {
    //
    // Parse a command line
    //

    map<string,string> cmdArgs;
    
    for(Int_t i=1; i<argc; i++)
        if (strncmp(argv[i],"--",2)==0) {
            // Ok, it seems to be user-defined var
            string s = argv[i]+2;

            size_t pos = s.find('.');
            if ( pos == string::npos )
                FatalError("Invalid parameter "+string(argv[i]));
            else 

                // user defined variable syntax
                // ClassName::VarName
                //            fUsrKeys.push_back(s.substr(0,pos));	
                //        fUsrValues.push_back(s);
                cmdArgs[s.substr(0,pos)] = s;

        }    

    map<string,string>::iterator it;

//    for (size_t i(0); i< fUsrKeys.size(); i++) {
//        Config::Get()->AddUserDefinition(fUsrKeys[i],fUsrValues[i]);
//    }
    for(it = cmdArgs.begin(); it!=cmdArgs.end(); it++)
        Config::Get()->AddUserDefinition(it->first, it->second);

}

//_____________________________________________________________________________
 void RecoFramework::Execute() {
    //
    // Execute a complete run
    //
    
    string dumpRootEvent = Conf()->GetStr("RecoFramework.DumpRootEvent");

    // init input module
    fInputModule->Init();

    // init all modules
    for( Int_t i=0; i<(Int_t)fModules.size(); i++ ) {
        if ( !fModules[i]->Init() ) {
            Msg(EsafMsg::Panic) << "Module " << fModules[i]->GetName() << " failed" << MsgDispatch;
        }
    }

    OpenRoot();
    
    TString jobname = Form("Reconstruction Job");
    TBenchmark bJob;
    bJob.Start(jobname);

    // run
    while ( RecoEvent *anEvent = fInputModule->GetEvent() ) {
        fCurrentEvent++;
        fRecoRootEvent->Clear();
        if (fInputModule->GetName() == "Root") 
            fInputModule->SaveRootData(fRecoRootEvent);
        if ( anEvent->GetHeader().GetNumActiveFee() != 0 ) {
            TBenchmark bEvent;
            TString s = Form("Event %d",fCurrentEvent);
            bEvent.Start(s);
            // execute all modules
            for( Int_t i=0; i<(Int_t)fModules.size(); i++) {
                if ( ! fModules[i]->PreProcess() )
                    break;
                if ( ! fModules[i]->Process( anEvent ) )
                    break;
                if ( ! fModules[i]->PostProcess() )
                    break;
                if ( ! fModules[i]->SaveRootData(fRecoRootEvent) )
                    break;
                // write the module data in the event
                anEvent->PutRecoModuleData(fModules[i]->GetName(), fModules[i]->GetData());
            }
            if (dumpRootEvent == "yes" ) fRecoRootEvent->Dump();
	    fRecoTree->Fill();
            // clean up
            fInputModule->DestroyEvent();            // delete input event
            for( Int_t i=0; i<(Int_t)fModules.size(); i++) {
                fModules[i]->UserMemoryClean();      // delete user objects
                fModules[i]->StandardMemoryClean();  // delete Int_t and Double_t maps
            }
            bEvent.Stop(s);
            MsgForm(EsafMsg::Info,"Time per event %d:  REAL=%6.2f s   CPU=%6.2f s",fCurrentEvent,
            bEvent.GetRealTime(s), bEvent.GetCpuTime(s));
            
        }
        else {
            fInputModule->DestroyEvent();
        }
    } // end event loop

    // end all modules
    fInputModule->Done();
    for( Int_t i=0; i<(Int_t)fModules.size(); i++) {
        fModules[i]->Done();
    }

    CloseRoot();
    
    bJob.Stop(jobname);
    MsgForm(EsafMsg::Info,"Average time per event:  REAL=%6.2f s   CPU=%6.2f s",
            bJob.GetRealTime(jobname)/fCurrentEvent, (bJob.GetCpuTime(jobname)/fCurrentEvent) );  
    MsgForm(EsafMsg::Info,"Total time:              REAL=%6.2f s   CPU=%6.2f s",
            bJob.GetRealTime(jobname), bJob.GetCpuTime(jobname));

}
//_____________________________________________________________________________
 void RecoFramework::Dump( ostream& os ) const {
    //
    // Dump the module list
    //
    
    Msg(EsafMsg::Debug) << "Framework Dump" << MsgDispatch;
    Msg(EsafMsg::Debug) << "The following Modules where loaded:" << MsgDispatch;
    Msg(EsafMsg::Debug) << "InputModule: " << fInputModule->GetName() << MsgDispatch;
    
    for( Int_t i=0; i<(Int_t)fModules.size(); i++ ) {
        Msg(EsafMsg::Debug) << "Module: " << i+1 << "t" << fModules[i]->GetName()<< MsgDispatch;
    }
}

//_____________________________________________________________________________
 void RecoFramework::OpenRoot() {
    //
    // Open output rootfile
    //
    
    string filename, rootname;
    if (fInputModule->fInputFileName == "") {
        filename = Form("output/reco.root");
    } else {
        filename = fInputModule->fInputFileName.c_str();
    }
    string ext = ".root";
    if ( filename.rfind(ext) == ( filename.size()-ext.size() ) ) filename.resize(filename.size()-ext.size());
    rootname = filename + ".reco.root";
    
    fRootFile = new TFile(rootname.c_str(), "CREATE");
    if ( fRootFile->IsZombie() ) {
        delete fRootFile;
        // try adding date and time to the name
        char timestr[100];
        time_t tt=time(NULL);
        
        strftime(timestr,99,"%d-%b-%G:%H:%M:%S",localtime(&tt));
        rootname = Form("%s.%s.reco.root",filename.c_str(),timestr);
        fRootFile = new TFile(rootname.c_str(),"CREATE");
        if (fRootFile->IsZombie())
            throw runtime_error("Cannot open root file");
    }    
        Msg(EsafMsg::Info) <<  "Root file " << filename << " successfully opened" << MsgDispatch;
        fRecoTree = new TTree("recotree","RecoTree");
	CreateRecoRootEvent();
        fRecoTree->Branch("events","RecoRootEvent",&fRecoRootEvent);
}

//_____________________________________________________________________________
 void RecoFramework::CreateRecoRootEvent() {
    //
    // Create RecoRootEvent
    //
    fRecoRootEvent = new RecoRootEvent();
}

//_____________________________________________________________________________
 void RecoFramework::CloseRoot() {
    // 
    // Close output rootfile
    // 
    if ( fRootFile ) {
        fRecoTree->Write();
        fRecoTree->AutoSave("SelfSave");
	Msg(EsafMsg::Info) << "************************ " << setw(4) << 
	  fRecoTree->GetEntries() << " events read ************************" << 
	  MsgDispatch;
	Msg(EsafMsg::Info) << MsgDispatch;
        Msg(EsafMsg::Info) << fRecoTree->GetEntries() << " entries are written into " << fRootFile->GetName()<< MsgDispatch;
        fRootFile->Close();
        delete fRootFile;
    }
}
About Us | EUSO Official Website | Web pages created by Roberto Pesce and Alessandro Thea - Last Update Wed Nov 16 16:57:39 2005 Wed Nov 16 16:29:22 2005