//************************************************ // Author: Federica Lionetto, Adam Davis, Biplab Dey, Paolo Gandini // Created on: 07/30/2014 //************************************************ /* TbNtupleMaker reads an Alibava file and creates a ROOT file (same filename) with the following information: - int NEvents, the number of events read from the header of the Alibava file; - int RunType, the run type; - std::vector<double> PedByGain, the pedestals calculated by the Alibava; - std::vector<double> NoiseByGain, the noise calculated by the Alibava; - std::vector<double> Gain, the gain calculated by the Alibava; - TH1F histo_PedByGain("histo_PedByGain","histo_PedByGain",N,0,N-1); - TH1F histo_NoiseByGain("histo_NoiseByGain","histo_NoiseByGain",N,0,N-1); - TH1F histo_Gain("histo_Gain","histo_Gain",N,0,N-1); - string Date = a->date(), the date read from the header of the Alibava file; - std::vector<unsigned short> ADC, the raw ADC counts, one per event; - double TDCTime, the TDC time (meaningful only in radioactive source runs), one per event; - double Temp, the temperature, one per event; - int n, a counter, one per event (starting from 1). The ROOT file will be saved in a folder named RootFiles in the same folder where the Alibava file is (if no external path is provided) or in the folder specified by the external path. Compile with: make Run with: ./TbNtupleMaker [Alibava file] [external path] where: - [Alibava file] is the complete path, including the folder and the filename, of the Alibava file one wants to process; - [external path] is the optional external path where the RootFiles folder will be created. For example: ./TbNtupleMaker /.../run_xxxxxx_xxxx_xxxx.ali or ./TbNtupleMaker /.../run_xxxxxx_xxxx_xxxx.ali /... */ //************************************************ // Types: // 1 = calibration run // 2 = laser synchronization run // 3 = laser run // 4 = radioactive source run // 5 = pedestal run //************************************************ #include <iostream> #include <string> #include <vector> #include <cstdlib> #include "TFile.h" #include "TROOT.h" #include "TSystem.h" #include "TTree.h" #include "Alibava/AsciiRoot.h" #ifdef __MAKECINT__ #pragma link C++ class vector<float>+; #endif using namespace std; // Number of Beetle channels. const int N = 256; void TbNtupleMaker(char *filename, char *externalPath = 0); int main(int argc, char *argv[]) { if(argc < 2) { cout << "**************************************************" << endl; cout << "Error! Input file missing..." << endl; cout << "Please use the following format:" << endl; cout << "./TbNtupleMaker [1] [2]" << endl; cout << "with:" << endl; cout << "[1] = Alibava file, complete path;" << endl; cout << "[2] = External path, optional." << endl; cout << "Type ./TbNtupleMaker --info for more information." << endl; cout << "**************************************************" << endl; return 0; } else if (string(argv[1]) == "--info") { cout << "**************************************************" << endl; cout << "TbNtupleMaker reads an Alibava file and creates a ROOT file (same filename) with the following information:" << endl; cout << "- int NEvents, the number of events read from the header of the Alibava file;" << endl; cout << "- int RunType, the run type;" << endl; cout << "- std::vector<double> PedByGain, the pedestals calculated by the Alibava;" << endl; cout << "- std::vector<double> NoiseByGain, the noise calculated by the Alibava;" << endl; cout << "- std::vector<double> Gain, the gain calculated by the Alibava;" << endl; cout << "- TH1F histo_PedByGain;" << endl; cout << "- TH1F histo_NoiseByGain;" << endl; cout << "- TH1F histo_Gain;" << endl; cout << "- string Date = a->date(), the date read from the header of the Alibava file;" << endl; cout << "- std::vector<unsigned short> ADC, the raw ADC counts, one per event;" << endl; cout << "- double TDCTime, the TDC time (meaningful only in radioactive source runs), one per event;" << endl; cout << "- double Temp, the temperature, one per event;" << endl; cout << "- int n, a counter, one per event (starting from 1)." << endl; cout << "**************************************************" << endl; cout << "The ROOT file will be saved in a folder named RootFiles in the same folder where the Alibava file is (if no external path is provided) or in the folder specified by the external path." << endl; cout << "**************************************************" << endl; cout << "Compile with:" << endl; cout << "make" << endl; cout << "Run with:" << endl; cout << "./TbNtupleMaker [Alibava file] [external path]" << endl; cout << "where:" << endl; cout << "- [Alibava file] is the complete path, including the folder and the filename, of the Alibava file one wants to process;" << endl; cout << "- [external path] is the optional external path where the RootFiles folder will be created." << endl; cout << "For example:" << endl; cout << "./TbNtupleMaker /.../run_xxxxxx_xxxx_xxxx.ali" << endl; cout << "or" << endl; cout << "./TbNtupleMaker /.../run_xxxxxx_xxxx_xxxx.ali /..." << endl; cout << "**************************************************" << endl; return 0; } else { cout << "File to process: " << argv[1] << endl; if (argc == 2) TbNtupleMaker(argv[1]); else if (argc == 3) TbNtupleMaker(argv[1],argv[2]); else { cout << "Error! Too many arguments given..." << endl; return 0; } return 0; } } void TbNtupleMaker(char *filename, char *externalPath){ cout << "**************************************************" << endl; cout << "Decoding raw data..." << endl; cout << "**************************************************" << endl; // Do not comment this line. gROOT->ProcessLine("#include <vector>"); // Do some fanciness to get the directory right. string filename_as_string = string(filename); string prefix = filename_as_string.substr(0,filename_as_string.find_last_of('/')); if (externalPath!=0) prefix = string(externalPath); string ali_filename = filename_as_string.substr(filename_as_string.find_last_of('/')+1); TString outfilename = ((TString)prefix)+"/RootFiles/"+((TString)ali_filename); outfilename.ReplaceAll(".ali",".root"); // Create a folder named RootFiles. Do not worry, nothing bad is going to happen if the folder already exists. cout << "Create a folder named RootFiles" << endl; cout << "Setting output to: " << prefix+"/RootFiles" << endl; string path_to_make = "mkdir "+prefix+"/RootFiles"; system(path_to_make.c_str()); // Open ROOT file. TFile *output = TFile::Open(outfilename,"RECREATE"); // Open Alibava file. AsciiRoot *a = new AsciiRoot(filename); // Create tree structure in ROOT file, to be filled once per file. int NEvents; int RunType; std::vector<double> PedByGain; std::vector<double> NoiseByGain; std::vector<double> Gain; TH1F histo_PedByGain("histo_PedByGain","histo_PedByGain",N,0,N); TH1F histo_NoiseByGain("histo_NoiseByGain","histo_NoiseByGain",N,0,N); TH1F histo_Gain("histo_Gain","histo_Gain",N,0,N); TH1F histo_Signal20("histo_Signal20","Signal calculated by Alibava > 20, distribution over the strips",N,0,N); TH1F histo_Signal40("histo_Signal40","Signal calculated by Alibava > 40, distribution over the strips",N,0,N); TH1F histo_Signal60("histo_Signal60","Signal calculated by Alibava > 60, distribution over the strips",N,0,N); TH1F histo_TDC("histo_TDC","TDC distribution, ADC > 40",50,0,50); string Date = a->date(); /////// vito TH1D** ADC_ch = new TH1D*[256]; TH2D* ADCvsEv = new TH2D("ADCvsEv_%d", "ADCvsEv_%d", 1e5, -0.5, 99999.5, 200, 399.5, 600.5 ); for(int i=0; i<256; i++){ ADC_ch[i] = new TH1D(Form("ADC_ch_%d", i), Form("ADC_ch_%d", i), 1024, -0.5, 1023.5 ); } // Allocate only necessary space. PedByGain.reserve(N); NoiseByGain.reserve(N); Gain.reserve(N); // Create tree structure in ROOT file, to be filled once per event. std::vector<unsigned short> ADC; double TDCTime; double Temp; int n; // Fill the header, once per file. TTree *Header = new TTree("Header","Header"); Header->Branch("NEvents",&NEvents); Header->Branch("RunType",&RunType); Header->Branch("PedByGain",&PedByGain); Header->Branch("NoiseByGain",&NoiseByGain); Header->Branch("Gain",&Gain); Header->Branch("Date",&Date); NEvents = a->get_nevents(); cout << "Number of events in the Alibava file: " << NEvents << endl; RunType = a->type(); for(int iChannel=0; iChannel<N;++iChannel) { Gain[iChannel]= a->get_gain(iChannel); PedByGain[iChannel]=a->ped(iChannel); NoiseByGain[iChannel] = a->noise(iChannel); histo_Gain.SetBinContent(iChannel+1,a->get_gain(iChannel)); histo_PedByGain.SetBinContent(iChannel+1,a->ped(iChannel)); histo_NoiseByGain.SetBinContent(iChannel+1,a->noise(iChannel)); } Header->Fill(); cout << "Information in the header:" << endl; Header->Print(); cout << "**************************************************" << endl; cout << "Date from Alibava file: " << Date <<endl; cout << "**************************************************" << endl; // Fill the data, once per event. TTree *EventInfo = new TTree("EventInfo","EventInfo"); EventInfo->Branch("n",&n); EventInfo->Branch("ADC",&ADC); EventInfo->Branch("TDCTime",&TDCTime); EventInfo->Branch("Temp",&Temp); // Loop over events. for (int iEvent=0; iEvent<NEvents; iEvent++) { ADC.clear(); a->read_event(); // Loop over Beetle channels. for (int jChannel=0; jChannel<N; jChannel++) { if(a->data(jChannel)-PedByGain[jChannel]>20) histo_Signal20.Fill(jChannel); if(a->data(jChannel)-PedByGain[jChannel]>40) histo_Signal40.Fill(jChannel); if(a->data(jChannel)-PedByGain[jChannel]>60) histo_Signal60.Fill(jChannel); ADC.push_back(a->data(jChannel)); ADC_ch[jChannel]->Fill( a->data(jChannel) ); if(jChannel==200) ADCvsEv->Fill( iEvent, a->data(jChannel) ); } n = iEvent+1; TDCTime =a->time(); for(int t=0; t<N; t++) if(ADC.at(t)-PedByGain[t]>40) {histo_TDC.Fill(TDCTime,1); break;} Temp = a->temp(); EventInfo->Fill(); } cout << "Information in the data: " << endl; EventInfo->Print(); // Close Alibava file. a->close(); // Write and close ROOT file. for(int i=0; i<256; i++) ADC_ch[i]->Write(); ADCvsEv->Write(); output->Write(); output->Close(); return; }