AliPhysics  e6c8d43 (e6c8d43)
AliOfflineTrigger.cxx
Go to the documentation of this file.
1 
9 
10 /*
11  Example usage:
12  // 0.) Init offline trigger class
13  AliOfflineTrigger trigger("default", 30,100000000);
14  //
15  // 1.) Dump event header info. Used to make consitency checks (diff, meld, TTree diff)
16  //
17  trigger.DumpGIDRAWReader("alien:///alice/data/2013/LHC13b/000195483/raw/13000195483000.10.root");
18  trigger.DumpGIDRAWTree("alien:///alice/data/2013/LHC13b/000195483/raw/13000195483000.10.root");
19  trigger.DumpGIDESD("alien:///alice/data/2013/LHC13b/000195483/pass4/13000195483000.10/AliESDs.root","1");
20  //
21  trigger.DumpGIDESD("alien:///alice/data/2013/LHC13b/000195483/ESDs/pass3/13000195483000.10/AliESDs.root","1","gidesdpass3.list");
22  trigger.DumpGIDESD("alien:///alice/data/2013/LHC13b/000195483/pass4/13000195483000.10/AliESDs.root","1","gidesdpass4.list");
23  //
24  // 2.) Make custom esd filter. Example set sum pt and multiplicity trigger
25  // Define ESD trigger aliases - used later in the AliOfflineTrigger::DumpGIDESD
26  //
27  trigger.AddESDAlias("sumPt","Sum$(Tracks[].Pt()*(Tracks[].fTPCncls>120&&Tracks[].fITSncls>4))");
28  trigger.AddESDAlias("mult","Sum$(Tracks[].fITSncls>4&&Tracks[].fTPCncls>120&&Tracks[].fTRDncls>50)");
29  trigger.AddESDAlias("triggerPt","sumPt>20");
30  trigger.AddESDAlias("triggerMult","mult>50");
31  trigger.DumpGIDESD("alien:///alice/data/2013/LHC13b/000195483/pass4/13000195483000.10/AliESDs.root","(sumPt>30&&mult>50)||sumPt>50","gidesdTrigger.list");
32  // eventually trigger can be set in tree for cut tuning
33  TFile *finput = TFile::Open("alien:///alice/data/2013/LHC13b/000195483/pass4/13000195483000.10/AliESDs.root");
34  TTree* esdTree = (TTree*)finput->Get("esdTree");
35  trigger.SetTriggerAlias(esdTree,"(sumPt>30&&mult>50)||sumPt>50");
36  //
37  // 4.) Make a diff between event header trees. Example compare ESD pass4, rawreader, rawtree and ESD pass3
38  // Particular case of pass3 there is an event mismatch
39  //
40  tree = AliOfflineTrigger::MakeDiffTree("gidesdpass4.list","gidrawReader.list;gidrawTree.list;gidesdpass3.list")
41  tree->Scan("eventID:T0.eventID:T1.eventID:T2.eventID","eventID>0");
42  tree->Scan("timeStamp:T0.timeStamp:T1.timeStamp:T2.timeStamp","eventID>0","colsize=20");
43  //
44  // 5.) Trigger raw data file example:
45  //
46  AliOfflineTrigger trigger("default", 30,100000000);
47  trigger.LoadTriggerList("gidesdTrigger.list");
48  trigger.ExtractSelected("raw.list", "gidesdTrigger.list", "rawSelected[].root",1000000, 1 );
49  //
50  // 6.) Example to compare content of the raw filtered data with input flitered list as used in the filterning produnction
51  TTree * tree = AliOfflineTrigger::MakeDiffTree("gidrawTree.list","filteredHighPt.list;filteredHighPtV0s.list;filteredMult.list");
52  Int_t entriesAll=tree->GetEntries();
53  Int_t entriesHighPt = tree->Draw("gid/10.","(gid==T0.gid)","goff");
54  Int_t entriesHighPtV0 = tree->Draw("gid/10.","(gid==T1.gid)","goff");
55  Int_t entriesMult = tree->Draw("gid/10.","(gid==T2.gid)","goff");
56  ::Info("AliOfflineTrigger::MakeDiffTree.KeyValue","All:%d",entriesAll);
57  ::Info("AliOfflineTrigger::MakeDiffTree.KeyValue","entriesHighPt+entriesHighPtV0+entriesMult:%d",entriesHighPt+entriesHighPtV0+entriesMult);
58 
59 */
60 
61 
62 #include <fstream>
63 #include <iostream>
64 #include "TError.h"
65 #include "TSystem.h"
66 #include "TFile.h"
67 #include "TTree.h"
68 #include "TChain.h"
69 #include "TBranch.h"
70 #include "TEntryList.h"
71 #include "TPRegexp.h"
72 #include "TGrid.h"
73 #include "TEnv.h"
74 #include "TPad.h"
75 #include "TMath.h"
76 #include "AliRawReaderRoot.h"
77 #include "AliXRDPROOFtoolkit.h"
78 #include "AliRawVEvent.h"
79 #include "AliRawEventHeaderBase.h"
80 #include "AliOfflineTrigger.h"
81 #include "AliSysInfo.h"
82 #include "TTimeStamp.h"
83 #ifdef WITHALIEN
84 #include "TAlienCollection.h"
85 #endif
86 #include "TPRegexp.h"
87 using std::cout;
88 using std::endl;
89 
90 ClassImp(AliOfflineTrigger)
91 
92 
93 AliOfflineTrigger::AliOfflineTrigger(const char *triggerName, Int_t timeOut, Int_t cacheSize):
94  TNamed(triggerName,triggerName),
95  fTrgGIDChunkName(),
96  fTrgGIDEventNr(),
97  fTrgGIDTimeStamp(),
98  fCounterFileInput(0),
99  fCounterEventInput(0),
100  fCounterFileOutput(0),
101  fCounterEventOutput(0),
102  fRawName(""),
103  fRawTriggerFile(0),
104  fRawTriggerTree(0),
105  fRAWGIDChunkName(),
106  fRAWGIDEventNr(),
107  fRAWGIDTimeStamp(),
108  fDefaultTimeOut(timeOut),
109  fDefaultTreeCache(cacheSize),
110  fESDTriggerList(NULL)
111 {
112  // set timeouts
113  gSystem->Setenv("XRDCLIENTMAXWAIT",Form("%d",timeOut));
114  gEnv->SetValue("XNet.RequestTimeout", timeOut);
115  gEnv->SetValue("XNet.ConnectTimeout", timeOut);
116  gEnv->SetValue("XNet.TransactionTimeout", timeOut);
117  gEnv->SetValue("XNet.FirstConnectMaxCnt", 2);
118  gEnv->SetValue("TFile.AsyncPrefetching", 1);
119 }
120 
121 void AliOfflineTrigger::AddESDAlias(const char *aliasName, const char *aliasValue ){
122  //
123  // esd aliases to define ESD triggers
124  if (fESDTriggerList==NULL) fESDTriggerList = new TObjArray(100);
125  fESDTriggerList->AddLast(new TNamed(aliasName,aliasValue));
126 }
127 
128 void AliOfflineTrigger::SetTriggerAlias(TTree* tree, const char * trigger){
129  if (tree==NULL || fESDTriggerList ==NULL) return;
130  Int_t entries=fESDTriggerList->GetEntries();
131  for (Int_t i=0; i<entries; i++){
132  tree->SetAlias(fESDTriggerList->At(i)->GetName(), fESDTriggerList->At(i)->GetTitle());
133  }
134  tree->SetAlias("trigger",trigger); // in trigger sets of the aliases can be used - in the list trigger mask to be returned
135 }
136 
137 
138 void AliOfflineTrigger::DumpGIDRAWReader(const char *rawFile){
139  //
140  // DUMP event ids using AliRawReaderRoot
141  // Input:
142  // rawFile - ID of raw file
143  // Output: csv ascii file with following columns
144  // fname/C:eventCounter/i:gid/l:timeStamp/i:period/i:orbit/i:bcid/i:eventID/i
145  /*
146  Example usage:
147  AliOfflineTrigger::DumpRAWGIDReader("alien:///alice/data/2013/LHC13b/000195483/raw/13000195483000.10.root");
148  */
149  if (rawFile==NULL) return;
150  if (TPRegexp("^alien").Match(rawFile) && gGrid==0) TGrid::Connect("alien");
151  TString chunkName=rawFile;
152  TPRegexp reg0(".*/");
153  reg0.Substitute(chunkName,"");
154  TPRegexp reg1(".root$");
155  reg1.Substitute(chunkName,"");
156 
157  std::ofstream file_out("gidrawReader.list");
158  // file_out<<"gid/D:eventCounter/D:period/D:orbit/D:bcid/D:fname/C:eventID/D\n"; // print header
159  file_out<<"fname/C:eventCounter/i:gid/l:timeStamp/i:period/i:orbit/i:bcid/i:eventID/i"<<endl; // print header
160  Int_t counter=0;
161  AliRawReaderRoot *preader = new AliRawReaderRoot(rawFile);
162  if (preader==NULL){
163  ::Error("dumpRAWGIDTree","rawFile %s not accessible",rawFile);
164  return;
165  }
166 
167  while (preader->NextEvent()){
168  file_out<<
169  chunkName<< // chunkName
170  "\t"<<counter<< // event counter
171  "\t"<<preader->GetEventIdAsLong()<< // gid
172  "\t"<<preader->GetTimestamp()<< // time stamp
173  "\t"<<preader->GetPeriod()<< // period
174  "\t"<<preader->GetOrbitID()<< // orbit
175  "\t"<<preader->GetBCID()<< // bcid
176  "\t"<<counter<< // the same as coutner for the moment. Checking the AliRawReaderRoot there is no approprate getter, I will try to add this function
177  endl; //
178  if (counter%100==0) printf("EventNumber\t%d\t%llu\n",counter,preader->GetEventIdAsLong());
179  counter++;
180  }
181  file_out.close();
182 }
183 
184 void AliOfflineTrigger::DumpGIDRAWTree(const char *rawFile){
185  //
186  // DUMP event ids using AliRawReaderRoot.
187  // Input:
188  // rawFile - ID of raw file
189  // Output: csv ascii file with following columns
190  // fname/C:eventCounter/i:gid/l:timeStamp/i:period/i:orbit/i:bcid/i:eventID/i
191 
192  // In the raw data triggering raw data are acessed using TTree functionality
193  // TTree::GetEntry() and ttree->Fill() for paricular entry numbers
194  // In some circumstancies entry number in tree and entry number if ESD can be different
195  //
196  // Dumping GID and other IDs using the tree->GetEntry()
197  /* Example usage:
198  dumpRAWGIDTree("alien:///alice/data/2013/LHC13b/000195483/raw/13000195483000.10.root",20,100000000);
199  */
200 
201  if (rawFile==NULL) return;
202  if (TPRegexp("^alien").Match(rawFile) && gGrid==0) TGrid::Connect("alien");
203  TFile * finput=NULL;
204  TTree * tree=NULL;
205  TPRegexp expRoot(".root$");
206  TPRegexp expList(".list$");
207  TObjArray *fileList=NULL;
208 
209  if (TString(rawFile).Contains(expRoot)){
210  fileList = new TObjArray(1);
211  fileList->AddLast(new TObjString(rawFile));
212  }
213  if (TString(rawFile).Contains(expList)){
214  fileList = gSystem->GetFromPipe(TString::Format("cat %s", rawFile)).Tokenize("\n");
215  }
216  if (fileList==NULL){
217  ::Error("dumpRAWGIDTree","Invalid input r %s",rawFile);
218  }
219  std::ofstream file_out("gidrawTree.list");
220  // file_out<<"gid/D:eventCounter/D:period/D:orbit/D:bcid/D:fname/C:eventID/D\n"; // print headaer
221  //file_out<<"fname/C:eventCounter/D:gid/D:timeStamp/D:period/D:orbit/D:bcid/D:eventID/D"<<endl; // print header
222  file_out<<"fname/C:eventCounter/i:gid/l:timeStamp/i:period/i:orbit/i:bcid/i:eventID/i"<<endl; // print header
223 
224  Int_t nFiles= fileList->GetEntries();
225  for (Int_t iFile=0; iFile<nFiles; iFile++){
226  if (TPRegexp("^alien").Match(fileList->At(iFile)->GetName()) && gGrid==0) TGrid::Connect("alien");
227  finput =TFile::Open(fileList->At(iFile)->GetName());
228  if (finput==NULL){
229  ::Error("dumpRAWGIDTree","rawFile %s not accessible", fileList->At(iFile)->GetName());
230  continue;
231  }
232  tree = (TTree*)finput->Get("RAW");
233  if (tree==NULL){
234  ::Error("dumpRAWGIDTree","rawFile %s does not contained requested tree",rawFile);
235  continue;
236  }
237 
238  TString chunkName=fileList->At(iFile)->GetName();
239  TPRegexp yearExp("./20.*/");
240  Int_t indexShort=chunkName.Index(yearExp);
241  TString chunkShort(&(chunkName[indexShort+7]));
242  //
243  TPRegexp reg0(".*/");
244  reg0.Substitute(chunkName,"");
245  TPRegexp reg1(".root$");
246  reg1.Substitute(chunkName,"");
247 
248  AliRawVEvent* fEvent=0; // (super) event
249  tree->SetBranchStatus("TPC*",kFALSE);
250  tree->SetBranchStatus("TRD*",kFALSE);
251  tree->SetBranchStatus("rawevent",kTRUE);
252  TBranch *fBranch = tree->GetBranch("rawevent"); // as in AliRawReaderRoot::AliRawReaderRoot
253  // fBranch->SetAddress(&fEvent);
254  if (fDefaultTreeCache>0) {
255  tree->SetCacheSize(fDefaultTreeCache);
256  //tree->AddBranchToCache("*",kFALSE);
257  }
258  Int_t nevents=tree->GetEntries();
259 
260  AliSysInfo::AddStamp(TString::Format("%s_0",chunkShort.Data()).Data(), 1, fCounterFileInput,fCounterFileInput);
261  for (Int_t ievent=0; ievent<nevents; ievent++){
262  fBranch->SetAddress(&fEvent);
263  fBranch->GetEntry(ievent);
264  AliRawEventHeaderBase *header = fEvent->GetHeader();
265  Int_t run = header->Get("RunNb");
266  //
267  const UInt_t *id = header->GetP("Id"); // copy of AliRawReaderRoot::GetEventId()
268  ULong64_t period = id ? (((id)[0]>>4)&0x0fffffff): 0; // AliRawReader::Get<>
269  ULong64_t orbit = id ? ((((id)[0]<<20)&0xf00000)|(((id)[1]>>12)&0xfffff)) : 0; // AliRawReader::Get<>
270  ULong64_t bcID = id ? ((id)[1]&0x00000fff) : 0; // AliRawReader::Get<>
271  ULong64_t gid = (((ULong64_t)period << 36) | ((ULong64_t)orbit << 12) |(ULong64_t)bcID); // AliRawReader::GetEventIdAsLong()
272  UInt_t timeStamp=header->Get("Timestamp");
273  delete fEvent;
274  fEvent=NULL;
275  //
276  AliSysInfo::AddStamp(TString::Format("%s",chunkShort.Data()).Data(), 2, iFile, ievent);
277  file_out<< // dump contet
278  chunkShort.Data()<< // chunkName
279  "\t"<< ievent<< // event counter
280  "\t"<<gid<< // gid
281  "\t"<<timeStamp<< // time stamp
282  "\t"<< period<< // period
283  "\t"<< orbit<< // orbit
284  "\t"<< bcID<< // bcID
285  "\t"<<ievent<< // event ID - for the tree ir is the same as counter
286  endl;
287  if (ievent%100==0) printf("EventNumber\t%d\t%llu\n",ievent,gid);
288  }
289  AliSysInfo::AddStamp(TString::Format("%s_1",chunkShort.Data()).Data(), 3, fCounterFileInput,fCounterFileInput);
290  delete fBranch;
291  delete fEvent;
292  delete tree;
293  finput->Close();
294  delete finput;
295  AliSysInfo::AddStamp(TString::Format("%s_2",chunkShort.Data()).Data(), 4, fCounterFileInput,fCounterFileInput);
296  }
297 }
298 
299 
300 void AliOfflineTrigger::DumpGIDESD(const char * chinput, const char *trigger,const char *choutput){
301  //
302  // DUMP event ids for selected events. Can be used for the fast OFFLINE triggering using ESD files only
303  //
304  // Input:
305  // chinput - esdFile
306  // trigger - trigger filter (TCut)
307  // chouput - name of output file
308  //
309  // Output: csv ascii file with following columns
310  // fname/C:eventCounter/i:gid/l:timeStamp/i:period/i:orbit/i:bcid/i:eventID/i
311  /* Example usage:
312  dumpGIDESD("alien:///alice/data/2013/LHC13b/000195483/pass4/13000195483000.10/AliESDs.root");
313  */
314  if (TPRegexp("^alien").Match(chinput) && gGrid==0) TGrid::Connect("alien");
315  TFile * finput = TFile::Open(chinput);
316  if (finput==NULL){
317  ::Error("dumpRAWGIDTree","rawFile %s not accessible",chinput);
318  return;
319  }
320  TTree * esdTree= (TTree*)finput->Get("esdTree");
321  if (esdTree==NULL){
322  ::Error("dumpRAWGIDTree","rawFile %s does not contained requested tree",chinput);
323  return;
324  }
325  TString chunkName=chinput;
326  TPRegexp regE("/AliESDs.root$");
327  regE.Substitute(chunkName,"");
328  TPRegexp reg0(".*/");
329  reg0.Substitute(chunkName,"");
330  //
331  if (fDefaultTreeCache>0) {
332  esdTree->SetCacheSize(fDefaultTreeCache);
333  // esdTree->AddBranchToCache("*",kFALSE); // check which branches needed to evaluate trigger formula
334  // esdTree->AddBranchToCache("Tracks*",kTRUE);
335  // esdTree->AddBranchToCache("*Header*",kTRUE);
336  }
337 
338  Int_t entries=esdTree->GetEntries();
339  ::Info("dumpAndCompareGID::DumpGIDESD","Entries=%llu",esdTree->GetEntries());
340  esdTree->SetAlias("gid","((fPeriodNumber << 36) | (fOrbitNumber << 12) | fBunchCrossNumber)");
341  SetTriggerAlias(esdTree,trigger);
342  entries=esdTree->Draw("gid:Entry$:fPeriodNumber:fOrbitNumber:fBunchCrossNumber:fEventNumberInFile:fTimeStamp",trigger,"goffpara");
343  //
344  std::ofstream file_out(choutput);
345  // file_out<<"fname/C:eventCounter/D:gid/D:timeStamp/D:period/D:orbit/D:bcid/D:eventID/D"<<endl; // print header
346  file_out<<"fname/C:eventCounter/i:gid/l:timeStamp/i:period/i:orbit/i:bcid/i:eventID/i"<<endl; // print header
347 
348  if (entries>0) for (Int_t i=0;i<entries; i++){
349  file_out<<
350  chunkName.Data()<< // chunkname
351  "\t"<<Long64_t(esdTree->GetVal(1)[i])<< // event counter
352  "\t"<<Long64_t(esdTree->GetVal(0)[i])<< // gid
353  "\t"<<Long64_t(esdTree->GetVal(6)[i])<< // timeStamp
354  "\t"<<Long64_t(esdTree->GetVal(2)[i])<< // period
355  "\t"<<Long64_t(esdTree->GetVal(3)[i])<< // orbit
356  "\t"<<Long64_t(esdTree->GetVal(4)[i])<< // bcid
357  "\t"<<Long64_t(esdTree->GetVal(5)[i])<< // eventID
358  endl;
359  }
360  file_out.close();
361 }
362 
363 
364 
365 
367  //
368  // Routine to test internal consitency of the IDs files
369  //
370  // Check if the ESD gidlist and rawesd.list are identical
371  // This is expected to be the case for the standard ppass reconstruction
372  //
373  TTree * treeGIDESD=new TTree;
374  TTree * treeGIDRAWReader=new TTree;
375  TTree * treeGIDRAWTree=new TTree;
376  treeGIDRAWReader->ReadFile("gidrawReeader.list","",'\t');
377  treeGIDRAWTree->ReadFile("gidrawTree.list","",'\t');
378  treeGIDESD->ReadFile("gidesd.list","",'\t');
379 
380  treeGIDESD->BuildIndex("gid");
381  treeGIDRAWTree->BuildIndex("gid");
382  treeGIDRAWReader->BuildIndex("gid");
383  treeGIDESD->AddFriend(treeGIDRAWReader,"RAW");
384  treeGIDESD->AddFriend(treeGIDRAWTree,"RAWTree");
385  //
386  if ( treeGIDRAWReader->GetEntries()!= treeGIDESD->GetEntries()){
387  ::Error("dumpAndCompareGID::diffList","TestFailed. Mismatch in number of events RAW=%llu\tESD=%llu", treeGIDRAWReader->GetEntries(), treeGIDESD->GetEntries());
388  }else{
389  ::Info("dumpAndCompareGID::diffList","TestOK. Match in number of events RAW=%llu\tESD=%llu", treeGIDRAWReader->GetEntries(), treeGIDESD->GetEntries());
390  }
391  if ( treeGIDRAWTree->GetEntries()!= treeGIDESD->GetEntries()){
392  ::Error("dumpAndCompareGID::diffList","TestFailed. Mismatch in number of events RAWTree=%llu\tESD=%llu", treeGIDRAWTree->GetEntries(), treeGIDESD->GetEntries());
393  }else{
394  ::Info("dumpAndCompareGID::diffList","TestOK. Match in number of events RAWTree=%llu\tESD=%llu", treeGIDRAWTree->GetEntries(), treeGIDESD->GetEntries());
395  }
396  Int_t entriesMatch=treeGIDESD->Draw("event-RAW.event","1");
397  Double_t diff= 0;
398  if (entriesMatch>0) diff= TMath::Mean(entriesMatch, treeGIDESD->GetV1());
399  if (entriesMatch!= treeGIDRAWReader->GetEntries() || diff!=0){
400  ::Error("dumpAndCompareGID::diffList","TestFailed. Mismatch in GID");
401  }else{
402  ::Info("dumpAndCompareGID::diffList","TestOK. Match in GID");
403  }
404 }
405 
406 TTree* AliOfflineTrigger::MakeDiffTree(const char *refTree, const char *friendTrees){
407  //
408  // Build trees out of the csv files.
409  // For expert usage and debugging
410  // Input:
411  // refTree - csv file name for main tree
412  // friendTrees - semicolomn separated list of the csv files defining freind trees
413  // Output:
414  // tree with friend trees properly indesed attached
415  if (!friendTrees) return NULL;
416  TObjArray * array=TString(friendTrees).Tokenize(";");
417  Int_t ntrees=array->GetEntries();
418  TTree * tree= new TTree();
419  tree->ReadFile(refTree,"",'\t');
420  tree->BuildIndex("gid");
421  for (Int_t jf=0; jf<ntrees; jf++){
422  TTree * ftree= new TTree;
423  ftree->ReadFile(array->At(jf)->GetName(),"",'\t');
424  ftree->BuildIndex("gid");
425  tree->AddFriend(ftree,TString::Format("T%d",jf));
426  }
427  return tree;
428 }
429 
430 void AliOfflineTrigger::LoadTriggerList(const char * triggerList){
431  //
432  // Load triger maps from the ascii trigger list csv file into internal maps
433  //
434  // Assuming fname,gid, eventID and timeStamp branch has to be present
435  // trigger branch is a recomendation
436  //
437  // Format of branches:
438  // fname/C:eventCounter/i:gid/l:timeStamp/i:period/i:orbit/i:bcid/i:eventID/i
439  /*
440  const char * triggerList = "gidesd.list"
441  */
442  TTree * tree= new TTree();
443  tree->ReadFile(triggerList,"",'\t');
444  Int_t entries=tree->GetEntries();
445  if (entries<=0) {
446  ::Error("AliOfflineTrigger::LoadTriggerList","Invalid input trigger list\t%s", triggerList);
447  return;
448  }
449  TBranch *chBranch=tree->GetBranch("fname");
450  TBranch *gidBranch=tree->GetBranch("gid");
451  TBranch *eventBranch=tree->GetBranch("eventID");
452  TBranch *timeBranch=tree->GetBranch("timeStamp");
453  TBranch *triggerBranch=tree->GetBranch("trigger");
454  Bool_t isOK=(chBranch!=NULL && gidBranch!=NULL &&eventBranch && timeBranch!=NULL);
455  if (isOK==kFALSE){
456  ::Error("AliOfflineTrigger::LoadTriggerList","Missing information - in trigger list\t%s", triggerList);
457  return;
458  }
459  ULong64_t gid;
460  UInt_t eventNr,timeStamp;
461  char * chbuffer= new char[10000];
462  char * chtrigger= new char[10000];
463  chBranch->SetAddress(chbuffer);
464  gidBranch->SetAddress(&gid);
465  timeBranch->SetAddress(&timeStamp);
466  eventBranch->SetAddress(&eventNr);
467  if (triggerBranch) triggerBranch->SetAddress(chtrigger);
468  for (Int_t i=0; i<entries; i++){
469  tree->GetEntry(i);
470  if (triggerBranch) fTrgGIDTrigger[gid]=chtrigger;
471  fTrgGIDChunkName[gid]=chbuffer;
472  fTrgGIDEventNr[gid]=i;
473  fTrgGIDTimeStamp[gid]=timeStamp; // for consitency check
474  }
475  delete tree;
476 }
477 
478 
479 
480 Int_t AliOfflineTrigger::LoadMapFromRawData(const char *rawFile, Int_t verbose){
481  //
482  // 1.) Load RAW headers and fill event ID in std::maps
483  // 2.) Calculate number of selected events
484  // 3.) To be added:
485  // hardware trigger mask
486  // calibration event without unique gid (e.g calibration event)
487  if (rawFile==NULL) return 0;
488  if (TPRegexp("^alien").Match(rawFile) && gGrid==0) TGrid::Connect("alien");
489  TFile * finput =TFile::Open(rawFile);
490  if (finput==NULL){
491  ::Error("dumpRAWGIDTree","rawFile %s not accessible",rawFile);
492  return 0;
493  }
494  TTree * tree = (TTree*)finput->Get("RAW");
495  if (tree==NULL){
496  ::Error("dumpRAWGIDTree","rawFile %s does not contained requested tree",rawFile);
497  return 0;
498  }
499  TString chunkName=rawFile;
500  TPRegexp reg0(".*/");
501  reg0.Substitute(chunkName,"");
502  TPRegexp reg1(".root$");
503  reg1.Substitute(chunkName,"");
504  //
505  AliRawVEvent* fEvent=0; // (super) event
506  tree->SetBranchStatus("TPC*",kFALSE);
507  tree->SetBranchStatus("TRD*",kFALSE);
508  tree->SetBranchStatus("rawevent",kTRUE);
509  TBranch *fBranch = tree->GetBranch("rawevent"); // as in AliRawReaderRoot::AliRawReaderRoot
510  fBranch->SetAddress(&fEvent);
511  if (fDefaultTreeCache>0) {
512  tree->SetCacheSize(fDefaultTreeCache);
513  //tree->AddBranchToCache("*",kFALSE);
514  }
515  Int_t nevents=tree->GetEntries();
516  Int_t nTriggered=0;
517  ULong64_t gidOld=0;
518  for (Int_t ievent=0; ievent<nevents; ievent++){
519  fBranch->GetEntry(ievent);
520  Int_t run = fEvent->GetHeader()->Get("RunNb");
521  const UInt_t *id = fEvent->GetHeader()->GetP("Id"); // copy of AliRawReaderRoot::GetEventId()
522  ULong64_t period = id ? (((id)[0]>>4)&0x0fffffff): 0; // AliRawReader::Get<>
523  ULong64_t orbit = id ? ((((id)[0]<<20)&0xf00000)|(((id)[1]>>12)&0xfffff)) : 0; // AliRawReader::Get<>
524  ULong64_t bcID = id ? ((id)[1]&0x00000fff) : 0; // AliRawReader::Get<>
525  ULong64_t gid = (((ULong64_t)period << 36) | ((ULong64_t)orbit << 12) |(ULong64_t)bcID); // AliRawReader::GetEventIdAsLong()
526  UInt_t timeStamp=fEvent->GetHeader()->Get("Timestamp");
527  if (gid==gidOld && verbose>0){
528  ::Error("AliOfflineTrigger::LoadMapFromRawData)","Event %d not unique GID. GID %llu can not be used as unique ID. Time %d", ievent, gid, timeStamp);
529  continue;
530  }
531  fRAWGIDChunkName[gid]=rawFile;
532  fRAWGIDTimeStamp[gid]=timeStamp;
533  fRAWGIDEventNr[gid]=ievent;
534  fRAWEventNrGID[ievent]=gid;
535  if (verbose==1&&ievent%100==0) ::Info("AliOfflineTrigger::LoadMapFromRawData", "Event # \t%d\t%llu",ievent,gid);
536  if ((verbose&2)>0) ::Info("AliOfflineTrigger::LoadMapFromRawData", "Event # \t%d\t%llu",ievent,gid);
537  // check if event triggered
538  UInt_t trgTimeStamp=fTrgGIDTimeStamp[gid];
539  if (trgTimeStamp>0){
540  nTriggered++;
541  ::Info("AliOfflineTrigger::LoadMapFromRawData()","Trig.event=%d. GID=%llu\tTime=%d", ievent, gid, timeStamp);
542  if (trgTimeStamp!=timeStamp){
543  ::Error("AliOfflineTrigger::LoadMapFromRawData()","Inconsistent timestamp");
544  }else{
545  fTrgGIDEventNr[gid]=ievent;
546  }
547  }
548  gidOld=gid;
549  }
550  tree->SetCacheSize(0);
551  delete tree;
552  delete finput;
553  return nTriggered;
554 }
555 
556 
557 
558 void AliOfflineTrigger::ExtractSelected(const char *rawFile, Int_t verbose){
559  //
560  // Extract selected events from raw data file
561  // Trigger list has to be loaded before filtering
562  //
563  AliRawVEvent* fEvent=0; // event
564  TBranch *fEventBranch = 0; // branch for event header
565 
566  if (fRawTriggerFile==NULL){
567  ::Error("AliOfflineTrigger::ExtractSelected","Output file not intitialized");
568  return;
569  }
570  Int_t nTriggered=0;
571  if (fTrgGIDTimeStamp.size()<=0){
572  ::Info("AliOfflineTrigger::LoadMapFromRawData", "Trigger list is empty. Nothing to filter for file %s", rawFile);
573  return;
574  }
575  nTriggered=LoadMapFromRawData(rawFile, verbose);
576  ::Info(" AliOfflineTrigger::ExtractSelected", "%s:\t N_{trig}=%d", rawFile,nTriggered);
577  if ( nTriggered==0){
578  return;
579  }
580  TFile * finput = TFile::Open(rawFile);
581  if (finput==NULL){
582  ::Info(" AliOfflineTrigger::ExtractSelected", "File %s not exist or not accessible within TimeOut %d", rawFile, fDefaultTimeOut);
583  return;
584  }
585  if (finput->IsOpen()==kFALSE || finput->IsZombie()){
586  ::Info(" AliOfflineTrigger::ExtractSelected", "File %s not accessible within TimeOut %d", rawFile, fDefaultTimeOut);
587  return;
588  }
589  TTree *itree=dynamic_cast<TTree*>(finput->Get("RAW"));
590  if (finput==NULL){
591  ::Info(" AliOfflineTrigger::ExtractSelected", "Tree in file %s not exist or not accessible within TimeOut %d", rawFile, fDefaultTimeOut);
592  }
593 
594  fEventBranch = itree->GetBranch("rawevent"); // as in AliRawReaderRoot::AliRawReaderRoot
595  fEventBranch->SetAddress(&fEvent); // access event header
596 
597 
598  if (fRawTriggerTree==NULL){
599  fRawTriggerFile->cd();
600  fRawTriggerTree=itree->CloneTree(0);
601  }
602  Int_t nEvents=itree->GetEntries();
603  Int_t size= itree->GetEntry(0);
604  fRawTriggerTree->CopyAddresses(itree);
605  for (Int_t iEvent=0; iEvent<nEvents; iEvent++){
606  ULong64_t gid=fRAWEventNrGID[iEvent];
607  Bool_t isSelected = kFALSE;
608  isSelected=(fTrgGIDEventNr[gid]==iEvent && fTrgGIDTimeStamp[gid]>0); // gid in the list of triggered events
610  if (!isSelected) continue;
611  if ((verbose&1)>0) {
612  ::Info(" AliOfflineTrigger::ExtractSelected", "%s\t%d\t%llu\t%d\t%s",rawFile,iEvent,gid,fTrgGIDTimeStamp[fRAWEventNrGID[iEvent]], TTimeStamp(fTrgGIDTimeStamp[fRAWEventNrGID[iEvent]]).AsString("short"));
613  }
614  AliSysInfo::AddStamp(TString::Format("%s_BR",rawFile).Data(), 10, fCounterFileInput,fCounterFileInput);
615  size= itree->GetEntry(iEvent);
616  AliSysInfo::AddStamp(TString::Format("%s_ER",rawFile).Data(), 11, fCounterFileInput,fCounterFileInput);
617  Int_t readEntry=itree->GetReadEntry();
618  //fRawTriggerTree->CopyAddresses(itree);
619  AliSysInfo::AddStamp(TString::Format("%s_BF",rawFile).Data(), 100, fCounterFileInput,fCounterFileInput);
620  fRawTriggerTree->Fill();
621  AliSysInfo::AddStamp(TString::Format("%s_EF",rawFile).Data(), 101, fCounterFileInput,fCounterFileInput);
623  }
624  itree->ResetBranchAddresses();
625  delete fEvent;
626  delete itree;
627  delete finput;
629 }
630 
631 
632 
633 void AliOfflineTrigger::ExtractSelected(const char *rawList, const char * triggerList, const char * outputName, Long_t maxSize, Int_t verbose){
634  //
635  /*
636  const char *rawList="raw.list";
637  const char *triggerList="gidesdTrigger.list";
638  const char *outputName="filteredraw_[].root"
639  Int_t maxSize=100000000; // max size of raw trees before moving to next file
640  verbose=2
641  */
642  TObjArray* rawArray = 0;
643  if (TPRegexp(".xml$").Match(rawList)){
644 #ifdef WITHALIEN
645  TAlienCollection *coll = (TAlienCollection *)TAlienCollection::Open(rawList);
646  Int_t nFiles = coll->GetNofGroups();
647  rawArray=new TObjArray(nFiles);
648  while( coll->Next()){
649  rawArray->AddLast(new TObjString(coll->GetTURL()));
650  }
651 #endif
652  }else{
653  rawArray = gSystem->GetFromPipe(TString::Format("cat %s", rawList)).Tokenize("\n");
654  }
655  if (rawArray == 0) {
656  ::Fatal("AliOfflineTrigger::ExtractSelected","Unable to get list of RAW files");
657  }
658  Int_t nFiles=rawArray->GetEntries();
659  if (nFiles<=0){
660  ::Error("AliOfflineTrigger::ExtractSelected","Empty input list");
661  }
662  LoadTriggerList(triggerList);
663  for (Int_t iFile=0; iFile<nFiles; iFile++){
664  if (fRawTriggerTree!=NULL){
665  if (fRawTriggerTree->GetZipBytes()>maxSize){ // close file if content bigger than max Size
666  fRawTriggerFile->cd();
667  fRawTriggerTree->Write();
668  fRawTriggerTree->ResetBranchAddresses();
669  delete fRawTriggerTree;
670  fRawTriggerFile->Close();
671  fRawTriggerFile=NULL;
672  fRawTriggerTree=NULL;
674  }
675  }
676  if (fRawTriggerFile==NULL){
677  TString fName=outputName;
678  fName.ReplaceAll("[]",TString::Format("%d",fCounterFileOutput));
679  fRawTriggerFile= TFile::Open(fName.Data(),"recreate");
680  }
681  ExtractSelected(rawArray->At(iFile)->GetName(),verbose);
682  }
683  if (fRawTriggerTree!=NULL){
684  fRawTriggerFile->cd();
685  fRawTriggerTree->Write();
686  fRawTriggerTree->ResetBranchAddresses();
687  fRawTriggerFile->Close();
688  //delete fRawTriggerTree;
689  delete fRawTriggerFile;
690  fRawTriggerFile=NULL;
691  fRawTriggerTree=NULL;
693  }
694 }
void SetTriggerAlias(TTree *tree, const char *trigger)
double Double_t
Definition: External.C:58
std::map< ULong64_t, TString > fTrgGIDTrigger
GID -> ChunkName.
void DumpGIDESD(const char *chinput="AliESDs.root", const char *trigger="1", const char *choutput="gidesd.list")
long long Long64_t
Definition: External.C:43
TSystem * gSystem
TObjArray * fESDTriggerList
std::map< ULong64_t, UInt_t > fRAWGIDTimeStamp
EventNumber -> GID.
void LoadTriggerList(const char *triggerList)
int Int_t
Definition: External.C:63
TFile * fRawTriggerFile
name of the output file
TTree * fRawTriggerTree
! pointer to ouput raw trigger files
unsigned int UInt_t
Definition: External.C:33
Int_t LoadMapFromRawData(const char *rawFile="raw.root", Int_t verbose=1)
void AddESDAlias(const char *aliasName, const char *aliasValue)
std::map< ULong64_t, TString > fTrgGIDChunkName
std::map< UInt_t, ULong64_t > fRAWEventNrGID
GID -> EventNumber.
Int_t fCounterFileInput
input event counter
Int_t fDefaultTimeOut
triger map GID -> TimeStamp map
std::map< ULong64_t, UInt_t > fRAWGIDEventNr
GID -> ChunkName.
Double_t nEvents
plot quality messages
static TTree * MakeDiffTree(const char *refTree, const char *friendTrees)
Bool_t Data(TH1F *h, Double_t *rangefit, Bool_t writefit, Double_t &sgn, Double_t &errsgn, Double_t &bkg, Double_t &errbkg, Double_t &sgnf, Double_t &errsgnf, Double_t &sigmafit, Int_t &status)
Int_t fCounterFileOutput
triger map GID -> TimeStamp map
std::map< ULong64_t, TString > fRAWGIDChunkName
! pointer to output raw trigger tree
void DumpGIDRAWTree(const char *rawFile="raw.root")
Int_t nevents[nsamples]
void DumpGIDRAWReader(const char *rawFile="raw.root")
std::map< ULong64_t, UInt_t > fTrgGIDEventNr
GID -> Trigger type.
std::map< ULong64_t, UInt_t > fTrgGIDTimeStamp
GID -> EventNumber.
bool Bool_t
Definition: External.C:53
void ExtractSelected(const char *rawList, const char *triggerList, const char *outputName, Long_t maxCounter, Int_t verbose=1)
This class provides fucntionality for OFFLINE Trigger raw data selection and consistency checks...