]> git.uio.no Git - u/mrichter/AliRoot.git/blame_incremental - MUON/MUONcalib/AliMUONPedestal.cxx
MUON + CheckCompiler
[u/mrichter/AliRoot.git] / MUON / MUONcalib / AliMUONPedestal.cxx
... / ...
CommitLineData
1/**************************************************************************
2* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3* *
4* Author: The ALICE Off-line Project. *
5* Contributors are mentioned in the code where appropriate. *
6* *
7* Permission to use, copy, modify and distribute this software and its *
8* documentation strictly for non-commercial purposes is hereby granted *
9* without fee, provided that the above copyright notice appears in all *
10* copies and that both the copyright notice and this permission notice *
11* appear in the supporting documentation. The authors make no claims *
12* about the suitability of this software for any purpose. It is *
13* provided "as is" without express or implied warranty. *
14**************************************************************************/
15
16// $Id$
17
18#include "AliMUONPedestal.h"
19#include "AliMUONErrorCounter.h"
20#include "AliMUONVStore.h"
21#include "AliMUON2DMap.h"
22#include "AliMUONCalibParamND.h"
23#include "AliMpConstants.h"
24#include <TString.h>
25#include <TTimeStamp.h>
26#include <TMath.h>
27#include <TTree.h>
28#include <TFile.h>
29#include <TH1F.h>
30#include <THashList.h>
31#include <Riostream.h>
32
33#include <sstream>
34
35//-----------------------------------------------------------------------------
36/// \class AliMUONPedestal
37///
38/// Implementation of the pedestal computing
39///
40/// add
41///
42///
43/// \author Alberto Baldisseri, JL Charvet (05/05/2009)
44//-----------------------------------------------------------------------------
45
46using std::ostream;
47using std::ifstream;
48using std::endl;
49using std::cout;
50using std::ios;
51/// \cond CLASSIMP
52ClassImp(AliMUONPedestal)
53/// \endcond
54
55//______________________________________________________________________________
56AliMUONPedestal::AliMUONPedestal()
57: TObject(),
58//fN(0),
59fNCurrentEvents(0),
60fNEvthreshold(0),
61fSorting(0),
62fNEvents(0),
63fRunNumber(0),
64fNChannel(0),
65fNManu(0),
66fNManuConfig(0),
67fConfig(1),
68fStatusDA(0),
69fHistos(0),
70fErrorBuspatchTable(new AliMUON2DMap(kFALSE)),
71fManuBuspatchTable(new AliMUON2DMap(kFALSE)),
72fManuBPoutofconfigTable(new AliMUON2DMap(kFALSE)),
73fDate(new TTimeStamp()),
74fFilcout(0),
75fHistoFileName(),
76fPedestalStore(new AliMUON2DMap(kTRUE)),
77fIndex(-1),
78fPrefixDA(),
79fPrefixLDC(),
80fHistoFile(0),
81fTree(0)
82{
83/// Default constructor
84}
85//______________________________________________________________________________
86AliMUONPedestal::AliMUONPedestal(TRootIOCtor* /*dummy*/)
87: TObject(),
88//fN(0),
89fNCurrentEvents(0),
90fNEvthreshold(0),
91fSorting(0),
92fNEvents(0),
93fRunNumber(0),
94fNChannel(0),
95fNManu(0),
96fNManuConfig(0),
97fConfig(1),
98fStatusDA(0),
99fHistos(0),
100fErrorBuspatchTable(0),
101fManuBuspatchTable(0),
102fManuBPoutofconfigTable(0),
103fDate(0),
104fFilcout(0),
105fHistoFileName(),
106fPedestalStore(0),
107fIndex(-1),
108fPrefixDA(),
109fPrefixLDC(),
110fHistoFile(0),
111fTree(0)
112{
113/// Root IO constructor
114}
115
116//______________________________________________________________________________
117AliMUONPedestal::~AliMUONPedestal()
118{
119/// Destructor
120 delete fErrorBuspatchTable;
121 delete fManuBuspatchTable;
122 delete fPedestalStore;
123 delete fManuBPoutofconfigTable;
124}
125
126//______________________________________________________________________________
127const char*
128AliMUONPedestal::GetHistoFileName() const
129{
130 /// Return the name of file we use to store histograms
131 return fHistoFileName.Data();
132}
133
134//______________________________________________________________________________
135void AliMUONPedestal::LoadConfig(const char* dbfile)
136{
137 /// Load MUONTRK configuration from ascii file "dbfile" (in DetDB)
138
139 Int_t manuId;
140 Int_t busPatchId;
141
142 ifstream filein(dbfile,ios::in);
143
144 while (!filein.eof())
145 {
146 filein >> busPatchId >> manuId;
147
148 AliMUONVCalibParam* ped =
149 static_cast<AliMUONVCalibParam*>(fPedestalStore ->FindObject(busPatchId, manuId));
150
151 if (!ped) {
152 fNManuConfig++;
153 fNChannel+=64;
154 ped = new AliMUONCalibParamND(2, AliMpConstants::ManuNofChannels(),busPatchId, manuId, -1.); // put default wise -1, not connected channel
155 fPedestalStore ->Add(ped);
156
157 if ( ! fManuBuspatchTable->FindObject(busPatchId,manuId) )
158 {
159 // New (buspatch,manu)
160 AliMUONErrorCounter* manuCounter = new AliMUONErrorCounter(busPatchId,manuId);
161 fManuBuspatchTable->Add(manuCounter);
162 }
163 }
164 }
165}
166//______________________________________________________________________________
167void AliMUONPedestal::MakePed(Int_t busPatchId, Int_t manuId, Int_t channelId, Int_t charge)
168{
169 static Int_t tree_charge=0;
170 static Int_t warn=0;
171 Int_t DDL= busPatchId/100+2560;
172 /// Compute pedestals values
173 AliMUONVCalibParam* ped =
174 static_cast<AliMUONVCalibParam*>(fPedestalStore ->FindObject(busPatchId, manuId));
175
176
177 if(!tree_charge && fHistos==2)
178 {
179 fTree = new TTree("tc","Charge tree");
180 fTree->Branch("bp",&busPatchId,"bp/I");
181 fTree->Branch("manu",&manuId,",manu/I");
182 fTree->Branch("channel",&channelId,",channel/I");
183 fTree->Branch("DDL",&DDL,",DDL/I");
184 fTree->Branch("charge",&charge,"charge/I");
185 // fTree->Branch("Pedestal",&Pedestal,"Pedestal/D");
186 // fTree->Branch("chargetrue",&chargeminusPed,"chargetrue/D");
187 // fTree->Branch("evt",&evt,"evt/I");
188 tree_charge=1;
189 }
190
191
192 if (!ped)
193 {
194 if(fConfig)
195 { // Fill out_of_config (buspatch,manu) table
196 if (!(static_cast<AliMUONErrorCounter*>(fManuBPoutofconfigTable->FindObject(busPatchId,manuId))))
197 fManuBPoutofconfigTable->Add(new AliMUONErrorCounter(busPatchId,manuId));
198 if(warn<10) cout << fPrefixLDC.Data() << " : !!! WARNING : busPatchId = " << busPatchId << " manuId = " << manuId << " not in the Detector configuration " << endl;
199 else if(warn==10) cout << fPrefixLDC.Data() << " : !!! see .log file for an exhaustive list of (busPatchId, manuId) out of Detector configuration \n" << endl;
200 warn++;
201 (*fFilcout) <<" !!! WARNING : busPatchId = " << busPatchId << " manuId = " << manuId << " not in the Detector configuration " << endl;
202 }
203 else {fNManu++;}
204 fNChannel+=64;
205 // put default wise -1, not connected channel
206 ped = new AliMUONCalibParamND(2, AliMpConstants::ManuNofChannels(),busPatchId, manuId, -1.);
207 fPedestalStore ->Add(ped);
208 }
209
210 // Initialization for the first value
211 if (ped->ValueAsDouble(channelId, 0) == -1)
212 {
213 if(fConfig && channelId == 0){fNManu++;}
214 ped->SetValueAsDouble(channelId, 0, 0.);
215 }
216 if (ped->ValueAsDouble(channelId, 1) == -1) ped->SetValueAsDouble(channelId, 1, 0.);
217
218 if(fHistos==2) fTree->Fill();
219
220 Double_t pedMean = ped->ValueAsDouble(channelId, 0) + (Double_t) charge;
221 Double_t pedSigma = ped->ValueAsDouble(channelId, 1) + (Double_t) charge*charge;
222
223 ped->SetValueAsDouble(channelId, 0, pedMean);
224 ped->SetValueAsDouble(channelId, 1, pedSigma);
225
226 AliMUONErrorCounter* manuCounter;
227 if (!(manuCounter = static_cast<AliMUONErrorCounter*>(fManuBuspatchTable->FindObject(busPatchId,manuId))))
228 {
229 // New (buspatch,manu)
230 manuCounter = new AliMUONErrorCounter(busPatchId,manuId);
231 fManuBuspatchTable->Add(manuCounter);
232 }
233 else
234 {
235 // Existing buspatch
236 manuCounter->Increment();
237 }
238}
239//______________________________________________________________________________
240void AliMUONPedestal::Finalize()
241{
242 /// final polishing of the store
243
244 Double_t pedMean;
245 Double_t pedSigma;
246 Double_t pedSigmalimit=0.5;
247 Int_t busPatchId;
248 Int_t manuId;
249 Int_t channelId;
250 Int_t status=0;
251
252 // print in logfile
253 if (fErrorBuspatchTable->GetSize())
254 {
255 cout<< "\n" << fPrefixLDC.Data() << " : See list of Buspatches with lower statistics (due to parity errors) in .log or .ped file "<<endl;
256 (*fFilcout)<<"\nWarning: Buspatches with less statistics (due to parity errors)"<<endl;
257 TIter nextParityError(fErrorBuspatchTable->CreateIterator());
258 AliMUONErrorCounter* parityerror;
259 while((parityerror = static_cast<AliMUONErrorCounter*>(nextParityError())))
260 {
261 // cout<<" bp "<<parityerror->BusPatch()<<": used events = "<<fNEvents-parityerror->Events()<<endl;
262 (*fFilcout)<<" bp "<<parityerror->BusPatch()<<": used events = "<<fNEvents-parityerror->Events()<<endl;
263 }
264 }
265
266 Int_t nADC4090=0;
267 Int_t nADCmax=0;
268 // iterator over pedestal
269 TIter next(fPedestalStore ->CreateIterator());
270 AliMUONVCalibParam* ped;
271
272 while ( ( ped = dynamic_cast<AliMUONVCalibParam*>(next() ) ) )
273 {
274 busPatchId = ped->ID0();
275 manuId = ped->ID1();
276 if(manuId==0)
277 {
278 cout << fPrefixLDC.Data() << " : Warning: ManuId = " << manuId << " !!! in BP = " << busPatchId << endl;
279 (*fFilcout) << "Warning: ManuId = " << manuId << " !!! in BP = " << busPatchId << endl;
280 }
281 Int_t eventCounter;
282 // Correct the number of events for buspatch with errors
283 AliMUONErrorCounter* errorCounter;
284 if ((errorCounter = (AliMUONErrorCounter*)fErrorBuspatchTable->FindObject(busPatchId)))
285 {
286 eventCounter = fNEvents - errorCounter->Events();
287 }
288 else
289 {
290 eventCounter = fNEvents;
291 }
292 Int_t occupancy=0; // channel missing in raw data or read but rejected (case of parity error)
293 // value of (buspatch, manu) occupancy
294 AliMUONErrorCounter* manuCounter;
295 manuCounter = static_cast<AliMUONErrorCounter*>(fManuBuspatchTable->FindObject(busPatchId,manuId));
296 if(eventCounter>0)occupancy = manuCounter->Events()/64/eventCounter;
297 if(occupancy>1)
298 {
299 cout << fPrefixLDC.Data() << " : Warning: ManuId = " << manuId << " !!! in BP = " << busPatchId << " occupancy (>1) = " << occupancy << endl;
300 (*fFilcout) << "Warning: ManuId = " << manuId << " !!! in BP = " << busPatchId << " occupancy (>1) = " << occupancy <<endl;
301 }
302
303 for (channelId = 0; channelId < ped->Size() ; ++channelId)
304 {
305 pedMean = ped->ValueAsDouble(channelId, 0);
306
307 if (pedMean >= 0) // connected channels
308 {
309 ped->SetValueAsDouble(channelId, 0, pedMean/(Double_t)eventCounter);
310 pedMean = ped->ValueAsDouble(channelId, 0);
311 pedSigma = ped->ValueAsDouble(channelId, 1);
312 ped->SetValueAsDouble(channelId, 1, TMath::Sqrt(TMath::Abs(pedSigma/(Double_t)eventCounter - pedMean*pedMean)));
313
314 if(eventCounter < fNEvthreshold )
315 { nADCmax++; ped->SetValueAsDouble(channelId, 0, ADCMax());
316 ped->SetValueAsDouble(channelId, 1, ADCMax());}
317 if( ped->ValueAsDouble(channelId, 1) < pedSigmalimit )
318 { nADC4090++; ped->SetValueAsDouble(channelId, 0, ADCMax()-5);
319 ped->SetValueAsDouble(channelId, 1, ADCMax()-5);}
320 if(manuId == 0 || occupancy>1)
321 { nADCmax++; ped->SetValueAsDouble(channelId, 0, ADCMax());
322 ped->SetValueAsDouble(channelId, 1, ADCMax());
323 if(occupancy>1 && channelId==0)ped->SetValueAsDouble(channelId, 0, ADCMax()+occupancy);}
324 }
325 else
326 { nADCmax++; ped->SetValueAsDouble(channelId, 0, ADCMax());
327 ped->SetValueAsDouble(channelId, 1, ADCMax());}
328 }
329 }
330
331 float frac1=0. , frac2=0. ;
332 float frac_badped = 0.25 ; // maximal acceptable ratio of bad pedestals
333 char* detail;
334
335 if(fNChannel)
336 {
337 if(nADCmax>0)
338 { frac1 = float(nADCmax)/float(fNChannel);
339 detail=Form("%s : Warning: Nb of Channels with bad Pedestal (Ped=4095) = %d over %d (%6.4f)",fPrefixLDC.Data(),nADCmax,fNChannel,frac1);
340 printf("%s\n",detail);
341 (*fFilcout) << detail << endl;}
342
343 if(nADC4090>0)
344 { frac2 = 1.*nADC4090/fNChannel;
345 detail=Form("%s : Warning: Nb of Channels with PedSigma<0.5 (Ped=4090) = %d over %d (%6.4f)",fPrefixLDC.Data(),nADC4090,fNChannel,frac2);
346 printf("%s\n",detail);
347 (*fFilcout) << detail << endl; }
348
349 if (frac1+frac2 > frac_badped) { status=-1 ;
350 detail=Form("\n%s !!! ERROR : fraction of Channels with Pedestal>=4090 = %6.4f (> %5.3f) (status= %d) \n",fPrefixLDC.Data(),frac1+frac2,frac_badped,status);
351 (*fFilcout) << detail << endl; printf("%s",detail) ;}
352 }
353 else { status= -1;
354 detail=Form("\n%s !!! ERROR : Nb good channel = 0 (all pedestals are forced to 4095) !!! (status= %d)\n",fPrefixLDC.Data(),status);
355 cout << detail; (*fFilcout) << detail ;}
356
357 SetStatusDA(status);
358}
359//______________________________________________________________________________
360void AliMUONPedestal::MakeASCIIoutput(ostream& out) const
361{
362/// put pedestal store in the output stream
363
364 out<<"//===========================================================================" << endl;
365 out<<"// Pedestal file calculated by "<< fPrefixDA.Data() << endl;
366 out<<"//===========================================================================" << endl;
367 out<<"// * Run : " << fRunNumber << endl;
368 out<<"// * Date : " << fDate->AsString("l") <<endl;
369 out<<"// * Statictics : " << fNEvents << endl;
370 if(fConfig)
371 out<<"// * Nb of MANUS : " << fNManuConfig << " read in the Det. config. " << endl;
372 out<<"// * Nb of MANUS : " << fNManu << " read in raw data " << endl;
373 out<<"// * Nb of MANUS : " << fNChannel/64 << " written in pedestal file " << endl;
374 out<<"// * Nb of channels: " << fNChannel << endl;
375 out<<"//"<<endl;
376 out<<"// * Below " << fNEvthreshold << " events=> Ped.&sig.=4095" << endl;
377 out<<"// * PedSigma < 0.5 => Ped.&sig.=4090" << endl;
378
379 if (fErrorBuspatchTable->GetSize())
380 {
381 out<<"//"<<endl;
382 out<<"// * Buspatches with less statistics (due to parity errors)"<<endl;
383 TIter next(fErrorBuspatchTable->CreateIterator());
384 AliMUONErrorCounter* parityerror;
385 while((parityerror = static_cast<AliMUONErrorCounter*>(next())))
386 {
387 if(fNEvents-parityerror->Events()>fNEvthreshold)
388 { out<<"// BusPatch = "<<parityerror->BusPatch()<<"\t Nevents used = "<<fNEvents-parityerror->Events()<<endl; }
389 else
390 { out<<"// BusPatch = "<<parityerror->BusPatch()<<"\t Nevents used = "<<fNEvents-parityerror->Events()<< " (Ped.&sig.=4095)" << endl; }
391 }
392 }
393 Int_t writitle=0;
394 Int_t occupancy=1;
395 if(occupancy)
396 {
397 TIter next(fPedestalStore ->CreateIterator());
398 AliMUONVCalibParam* ped;
399 while ( ( ped = dynamic_cast<AliMUONVCalibParam*>(next() ) ) )
400 {
401 Int_t busPatchId = ped->ID0();
402 Int_t manuId = ped->ID1();
403 Double_t pedMean = ped->ValueAsDouble(0, 0); // check pedestal value for channelId=0
404
405 if(pedMean>ADCMax())
406 {
407 writitle++;
408 if(writitle==1){
409 out<<"//"<<endl;
410 out<<"// * Puzzling (Buspatch,Manu) read in raw data ? (Ped.&sig.=4095)"<<endl;}
411 occupancy=TMath::Nint(pedMean-ADCMax());
412 ped->SetValueAsDouble(0, 0, ADCMax());
413 out<<"// BusPatch = "<< busPatchId <<"\t ManuId = "<< manuId << "\t occupancy = " << occupancy << endl;
414 }
415
416 if (manuId==0 || (fConfig && static_cast<AliMUONErrorCounter*>(fManuBPoutofconfigTable->FindObject(busPatchId,manuId))))
417 {
418 writitle++;
419 if(writitle==1){
420 out<<"//"<<endl;
421 out<<"// * Puzzling (Buspatch,Manu) read in raw data ? (Ped.&sig.=4095)"<<endl;}
422 out<<"// BusPatch = "<< busPatchId <<"\t ManuId = "<< manuId << "\t missing in the mapping" << endl;
423 }
424 }
425 }
426 out<<"//"<<endl;
427 out<<"//---------------------------------------------------------------------------" << endl;
428 out<<"//---------------------------------------------------------------------------" << endl;
429 out<<"// BP MANU CH. MEAN SIGMA"<<endl;
430 out<<"//---------------------------------------------------------------------------" << endl;
431
432 TIter next(fPedestalStore->CreateIterator());
433 AliMUONVCalibParam* ped;
434
435 // Sorting
436 if (fSorting)
437 {
438 printf("%s : ..... sorting pedestal values .....\n",fPrefixLDC.Data());
439 THashList pedtable(100,2);
440 while ( ( ped = dynamic_cast<AliMUONVCalibParam*>(next() ) ) )
441 {
442 pedtable.Add(ped);
443 }
444 pedtable.Sort();
445 // iterator over sorted pedestal
446 TIter nextSorted(&pedtable);
447 while ( (ped = (AliMUONVCalibParam*)(nextSorted()) ) )
448 {
449 Int_t busPatchId = ped->ID0();
450 Int_t manuId = ped->ID1();
451 for ( Int_t channelId = 0; channelId < ped->Size(); ++channelId )
452 {
453 Double_t pedMean = ped->ValueAsDouble(channelId, 0);
454 Double_t pedSigma = ped->ValueAsDouble(channelId, 1);
455 out << "\t" << busPatchId << "\t" << manuId <<"\t"<< channelId << "\t" << pedMean <<"\t"<< pedSigma << endl;
456 }
457 }
458 }
459 else
460 {
461 while ( ( ped = dynamic_cast<AliMUONVCalibParam*>(next() ) ) )
462 {
463 Int_t busPatchId = ped->ID0();
464 Int_t manuId = ped->ID1();
465 for ( Int_t channelId = 0; channelId < ped->Size(); ++channelId )
466 {
467 Double_t pedMean = ped->ValueAsDouble(channelId, 0);
468 Double_t pedSigma = ped->ValueAsDouble(channelId, 1);
469 out << "\t" << busPatchId << "\t" << manuId <<"\t"<< channelId << "\t" << pedMean <<"\t"<< pedSigma << endl;
470 }
471 }
472 }
473}
474
475//______________________________________________________________________________
476void AliMUONPedestal::CreateControlHistos()
477{
478// Create histo
479 fHistoFileName=Form("%s.root",fPrefixDA.Data());
480 fHistoFile = new TFile(fHistoFileName,"RECREATE","MUON Tracking pedestals");
481}
482//______________________________________________________________________________
483void AliMUONPedestal::MakeControlHistos()
484{
485 /// Create control histograms
486 if (fIndex>=0) return; // Pedestal run (fIndex=-1)
487
488 Double_t pedMean;
489 Double_t pedSigma;
490 Double_t evt;
491 Int_t busPatchId;
492 Int_t manuId;
493 Int_t channelId;
494 Int_t DDL;
495
496// histo
497// TFile* histoFile = 0;
498 TTree* tree = 0;
499 TH1F* pedMeanHisto = 0;
500 TH1F* pedSigmaHisto = 0;
501
502 // fHistoFileName=Form("%s.root",fPrefixDA.Data());
503 // histoFile = new TFile(fHistoFileName,"RECREATE","MUON Tracking pedestals");
504
505 Int_t nx = ADCMax()+1;
506 Int_t xmin = 0;
507 Int_t xmax = ADCMax();
508 pedMeanHisto = new TH1F("pedmean_allch","Pedestal mean all channels",nx,xmin,xmax);
509 pedMeanHisto->SetDirectory(fHistoFile);
510
511 nx = 201;
512 xmin = 0;
513 xmax = 200;
514 pedSigmaHisto = new TH1F("pedsigma_allch","Pedestal sigma all channels",nx,xmin,xmax);
515 pedSigmaHisto->SetDirectory(fHistoFile);
516
517 tree = new TTree("t","Pedestal tree");
518 tree->Branch("DDL",&DDL,",DDL/I");
519 tree->Branch("bp",&busPatchId,"bp/I");
520 tree->Branch("manu",&manuId,",manu/I");
521 tree->Branch("channel",&channelId,",channel/I");
522 tree->Branch("pedMean",&pedMean,",pedMean/D");
523 tree->Branch("pedSigma",&pedSigma,",pedSigma/D");
524 tree->Branch("nevt",&evt,",evt/D");
525
526 // iterator over pedestal
527 TIter next(fPedestalStore ->CreateIterator());
528 AliMUONVCalibParam* ped;
529 AliMUONErrorCounter* manuCounter;
530
531 while ( ( ped = dynamic_cast<AliMUONVCalibParam*>(next() ) ) )
532 {
533 busPatchId = ped->ID0();
534 manuId = ped->ID1();
535 DDL= busPatchId/100+2560;
536
537 for ( channelId = 0; channelId < ped->Size(); ++channelId )
538 {
539 pedMean = ped->ValueAsDouble(channelId, 0);
540 pedSigma = ped->ValueAsDouble(channelId, 1);
541 manuCounter = static_cast<AliMUONErrorCounter*>(fManuBuspatchTable->FindObject(busPatchId,manuId));
542 evt = manuCounter->Events()/64;
543
544 pedMeanHisto->Fill(pedMean);
545 pedSigmaHisto->Fill(pedSigma);
546 tree->Fill();
547 }
548 }
549
550 fHistoFile->Write();
551 fHistoFile->Close();
552
553}