// $Id: EusoMapping.cc,v 1.21 2005/05/13 15:23:55 thea Exp $
// Author: M. Pallavicini 8 2003
/*****************************************************************************
* ESAF: Euso Simulation and Analysis Framework *
* *
* Id: EusoMapping *
* Package: Optics *
* Coordinator: Alessandro.Thea *
* *
*****************************************************************************/
//______________________________________________________________________________
//
// EusoMapping
// ==========
//
// Class containing the angle-pixel map.
// Every single detector config MUST have its own map.
// Map is affected by:
// OpticalSystem
// OpticalAdaptor
// PmtGeometry
// FocalSurface (layout)
//
#include "EusoMapping.hh"
#include "NumbersFileParser.hh"
#include "ERunParameters.hh"
#include "Config.hh"
#include <string>
#include "TBenchmark.h"
#include "TSystem.h"
ClassImp(EusoMapping)
// SLC gcc 3.2.3 workaround for ifstream/TString conflict
char* operator+( std::streampos&, char* );
EusoMapping *EusoMapping::fMe = 0;
//______________________________________________________________________________
EusoMapping::EusoMapping():EsafConfigurable() {
// ctor
fMapFile = Conf()->GetStr("EusoMapping.fMapFile");
fMapCacheFile = Conf()->GetStr("EusoMapping.fMapCacheFile");
if ( Conf()->GetStr("EusoMapping.fUseCache") == "yes" ) fUseCache = kTRUE;
fAnglePixelMap.resize(0);
if ( fUseCache )
if ( CheckCacheFile() ) {
Msg(EsafMsg::Info) << "Reading Pixel Map from cache... ";
LoadBinary();
Msg(EsafMsg::Info) << "Done." << MsgDispatch;
} else {
Msg(EsafMsg::Info) << "Reading Pixel Map...";
LoadAscii();
Msg(EsafMsg::Info) << "Done." << MsgDispatch;
SaveBinary();
}
else {
Msg(EsafMsg::Info) << "Reading Pixel Map...";
LoadAscii();
Msg(EsafMsg::Info) << "Done." << MsgDispatch;
}
}
//______________________________________________________________________________
EusoMapping::~EusoMapping() {
// dtor
}
//______________________________________________________________________________
EusoMapping* EusoMapping::Get() {
// instance
if ( fMe == 0 )
fMe = new EusoMapping();
return fMe;
}
//______________________________________________________________________________
Double_t EusoMapping::GetThetaFOV( ChannelUniqueId uid) {
// returns theta in field-of-view for a given unique channel id
if( uid > 0 && uid <= GetPixelsNumber() )
return fAnglePixelMap[uid-1].fThetaFOV;
else
return -1;
}
//______________________________________________________________________________
Double_t EusoMapping::GetSigmaThetaFOV( ChannelUniqueId uid) {
// returns theta in field-of-view for a given unique channel id
if( uid > 0 && uid <= GetPixelsNumber() )
return fAnglePixelMap[uid-1].fSigmaThetaFOV;
else
return -1;
}
//______________________________________________________________________________
Double_t EusoMapping::GetPhiFOV( ChannelUniqueId uid) {
// returns phi in field-of-view for a given unique channel id
if( uid > 0 && uid <= GetPixelsNumber() )
return fAnglePixelMap[uid-1].fPhiFOV;
else
return -1;
}
//______________________________________________________________________________
Double_t EusoMapping::GetSigmaPhiFOV( ChannelUniqueId uid) {
// returns phi spread in field-of-view for a given unique channel id
if( uid > 0 && uid <= GetPixelsNumber() )
return fAnglePixelMap[uid-1].fSigmaPhiFOV;
else
return -1;
}
//______________________________________________________________________________
Bool_t EusoMapping::CheckCacheFile() {
// check if aux file matches the source
Long_t id, flags, modtime;
Long64_t size;
// look for existing binary
if ( gSystem->GetPathInfo(fMapCacheFile.c_str(), &id, &size, &flags, &modtime) == 1 )
// Binary auxilar file doesn't exist
return kFALSE;
// look for original map file
if ( gSystem->GetPathInfo(fMapFile.c_str(), &id, &size, &flags, &modtime) == 1 )
// Binary auxilar file doesn't exist
throw runtime_error("EusoMapping: "+fMapFile+" doesn't exists");
// open auxilar file
ifstream fcache(fMapCacheFile.c_str());
if ( !(fcache.is_open()) )
throw runtime_error("EusoMapping: Unable to open "+fMapCacheFile);
Long_t stats[4];
fcache.read((char*)stats,sizeof(Long_t)*4);
fcache.close();
/* Debug printout
* cout << "Idt" << id << " --> " << stats[0] << endl;
* cout << "Sizet" << size << " --> " << stats[1] << endl;
* cout << "Flagst" << flags << " --> " << stats[2] << endl;
* cout << "ModTimet" << modtime << " --> " << stats[3] << endl;
*/
Bool_t check = // Id skipped since it changes if the same file is used on
// different machined that share the same disk
// ( id == stats[0] ) &&
//FIXME: disabled due to a bug in GetPathInfo in root 4.00.04
( size == stats[1] ) &&
( flags == stats[2] ) &&
( modtime == stats[3] );
return check;
}
//______________________________________________________________________________
void EusoMapping::LoadAscii(){
// read raw data from the final file of map
Int_t n_pixels, chid, lastchid;
//firstpixel is chid=1
chid = lastchid = 0;
NumbersFileParser nf(fMapFile.c_str(), 5, NumbersFileParser::gzip);
n_pixels = nf.GetCol(0).size();
Pixel p;
for(Int_t i(0); i < n_pixels; i++){
// build new pixel
vector<Double_t> row = nf.GetRow(i);
chid = (Int_t)row[0];
if(chid!=lastchid+1)
cout<< Form("Warning: pixel number %d missing!",lastchid+1)<<endl;
lastchid = chid;
// store values in EPixel
p.fThetaFOV = row[1];
p.fSigmaThetaFOV = row[2];
p.fPhiFOV = row[3];
p.fSigmaPhiFOV = row[4];
fAnglePixelMap.push_back(p);
}
}
//______________________________________________________________________________
void EusoMapping::SaveBinary() {
string dummy = fMapCacheFile;
cout << "Saving cache map to " << dummy << endl;
fstream fcache(dummy.c_str(), ios::out | ios::binary | ios::trunc);
// get stats of fMapFile to save into fMapCacheFile
Long_t stats[4];
Long64_t lsize;
if ( gSystem->GetPathInfo(fMapFile.c_str(), stats,
&lsize, stats+2, stats+3) == 1 )
throw runtime_error("EusoMapping: Unable to get stats for "+fMapFile);
stats[1] = (Long_t)lsize;
// save stats as first info in bin file
fcache.write((char*)&stats,sizeof(Long_t)*4);
// get number of pixels and put it into the bin file
Long_t npixel = (Long_t)fAnglePixelMap.size();
fcache.write((char*)&npixel,sizeof(Float_t));
Float_t buffer[4];
for(Long_t i(0); i < npixel; i++){
buffer[0] = fAnglePixelMap[i].fThetaFOV;
buffer[1] = fAnglePixelMap[i].fSigmaThetaFOV;
buffer[2] = fAnglePixelMap[i].fPhiFOV;
buffer[3] = fAnglePixelMap[i].fSigmaPhiFOV;
fcache.write((char*)buffer,sizeof(Float_t)*4);
}
fcache.close();
}
//______________________________________________________________________________
void EusoMapping::LoadBinary() {
fstream fcache(fMapCacheFile.c_str(), ios::in | ios::binary);
// extract the stats
Long_t stats[4];
fcache.read((char*)&stats,sizeof(Long_t)*4);
// get the number of pixels
Long_t npixels;
fcache.read((char*)&npixels,sizeof(Long_t));
Float_t buffer[4];
Pixel p;
for(Int_t i(0); i < npixels; i++){
// build new pixel
// get data
fcache.read((char*)buffer,sizeof(Float_t)*4);
p.fThetaFOV = buffer[0];
p.fSigmaThetaFOV = buffer[1];
p.fPhiFOV = buffer[2];
p.fSigmaPhiFOV = buffer[3];
fAnglePixelMap.push_back(p);
}
fcache.close();
}