1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
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 **************************************************************************/
17 //________________________________________________________________________
19 // A help class for monitoring and calibration tools: MOOD, AMORE etc.,
20 // It can be created and used a la (ctor):
22 //Create the object for making the histograms
23 fPedestals = new AliCaloCalibPedestal( fDetType );
24 // AliCaloCalibPedestal knows how many modules we have for PHOS or EMCAL
25 fNumModules = fPedestals->GetModules();
28 // fPedestals->ProcessEvent(fCaloRawStream);
29 // asked to draw histograms:
30 // fPedestals->GetDeadMap(i)->Draw("col");
32 // fPedestals->GetPeakProfileHighGainRatio((i < fNumModules) ? i : fVisibleModule)->Draw("colz");
34 // The pseudo-code examples above were from the first implementation in MOOD (summer 2007).
35 //________________________________________________________________________
37 //#include "TCanvas.h"
46 #include "AliRawReader.h"
47 #include "AliCaloRawStreamV3.h"
50 #include "AliCaloCalibPedestal.h"
52 ClassImp(AliCaloCalibPedestal)
56 // ctor; initialize everything in order to avoid compiler warnings
57 AliCaloCalibPedestal::AliCaloCalibPedestal(kDetType detectorType) :
61 fPedestalLEDRefLowGain(),
62 fPedestalLEDRefHighGain(),
63 fPeakMinusPedLowGain(),
64 fPeakMinusPedHighGain(),
65 fPeakMinusPedHighGainHisto(),
66 fPedestalLowGainDiff(),
67 fPedestalHighGainDiff(),
68 fPedestalLEDRefLowGainDiff(),
69 fPedestalLEDRefHighGainDiff(),
70 fPeakMinusPedLowGainDiff(),
71 fPeakMinusPedHighGainDiff(),
72 fPedestalLowGainRatio(),
73 fPedestalHighGainRatio(),
74 fPedestalLEDRefLowGainRatio(),
75 fPedestalLEDRefHighGainRatio(),
76 fPeakMinusPedLowGainRatio(),
77 fPeakMinusPedHighGainRatio(),
83 fResurrectedTowers(0),
96 fSelectPedestalSamples(kTRUE),
97 fFirstPedestalSample(0),
98 fLastPedestalSample(15),
100 fWarningThreshold(50),
101 fWarningFraction(0.002),
104 //Default constructor. First we set the detector-type related constants.
105 if (detectorType == kPhos) {
106 fColumns = fgkPhosCols;
108 fLEDRefs = fgkPhosLEDRefs;
109 fModules = fgkPhosModules;
110 fCaloString = "PHOS";
116 //We'll just trust the enum to keep everything in line, so that if detectorType
117 //isn't kPhos then it is kEmCal. Note, however, that this is not necessarily the
118 //case, if someone intentionally gives another number
119 fColumns = AliEMCALGeoParams::fgkEMCALCols;
120 fRows = AliEMCALGeoParams::fgkEMCALRows;
121 fLEDRefs = AliEMCALGeoParams::fgkEMCALLEDRefs;
122 fModules = AliEMCALGeoParams::fgkEMCALModules;
123 fCaloString = "EMCAL";
128 fDetType = detectorType;
130 //Then, loop for the requested number of modules
132 for (int i = 0; i < fModules; i++) {
133 //Pedestals, low gain
134 name = "hPedlowgain";
136 title = "Pedestals, low gain, module ";
138 fPedestalLowGain.Add(new TProfile2D(name, title,
139 fColumns, 0.0, fColumns,
140 fRows, fRowMin, fRowMax,"s"));
142 //Pedestals, high gain
143 name = "hPedhighgain";
145 title = "Pedestals, high gain, module ";
147 fPedestalHighGain.Add(new TProfile2D(name, title,
148 fColumns, 0.0, fColumns,
149 fRows, fRowMin, fRowMax,"s"));
151 //LED Ref/Mon pedestals, low gain
152 name = "hPedestalLEDReflowgain";
154 title = "Pedestal LEDRef, low gain, module ";
156 fPedestalLEDRefLowGain.Add(new TProfile(name, title,
157 fLEDRefs, 0.0, fLEDRefs, "s"));
159 //LED Ref/Mon pedestals, high gain
160 name = "hPedestalLEDRefhighgain";
162 title = "Pedestal LEDRef, high gain, module ";
164 fPedestalLEDRefHighGain.Add(new TProfile(name, title,
165 fLEDRefs, 0.0, fLEDRefs, "s"));
167 //Peak-Pedestals, low gain
168 name = "hPeakMinusPedlowgain";
170 title = "Peak-Pedestal, low gain, module ";
172 fPeakMinusPedLowGain.Add(new TProfile2D(name, title,
173 fColumns, 0.0, fColumns,
174 fRows, fRowMin, fRowMax,"s"));
176 //Peak-Pedestals, high gain
177 name = "hPeakMinusPedhighgain";
179 title = "Peak-Pedestal, high gain, module ";
181 fPeakMinusPedHighGain.Add(new TProfile2D(name, title,
182 fColumns, 0.0, fColumns,
183 fRows, fRowMin, fRowMax,"s"));
185 //Peak-Pedestals, high gain - TH2F histo
186 name = "hPeakMinusPedhighgainHisto";
188 title = "Peak-Pedestal, high gain, module ";
190 fPeakMinusPedHighGainHisto.Add(new TH2F(name, title,
191 fColumns*fRows, 0.0, fColumns*fRows,
196 title = "Dead map, module ";
198 fDeadMap.Add(new TH2D(name, title, fColumns, 0.0, fColumns,
199 fRows, fRowMin, fRowMax));
201 }//end for nModules create the histograms
203 //Compress the arrays, in order to remove the empty objects (a 16 slot array is created by default)
204 fPedestalLowGain.Compress();
205 fPedestalHighGain.Compress();
206 fPedestalLEDRefLowGain.Compress();
207 fPedestalLEDRefHighGain.Compress();
208 fPeakMinusPedLowGain.Compress();
209 fPeakMinusPedHighGain.Compress();
210 fPeakMinusPedHighGainHisto.Compress();
216 //_____________________________________________________________________
217 AliCaloCalibPedestal::~AliCaloCalibPedestal()
219 if (fReference) delete fReference;//Delete the reference object, if it has been loaded
220 //TObjArray will delete the histos/profiles when it is deleted.
224 //_____________________________________________________________________
225 AliCaloCalibPedestal::AliCaloCalibPedestal(const AliCaloCalibPedestal &ped) :
229 fPedestalLEDRefLowGain(),
230 fPedestalLEDRefHighGain(),
231 fPeakMinusPedLowGain(),
232 fPeakMinusPedHighGain(),
233 fPeakMinusPedHighGainHisto(),
234 fPedestalLowGainDiff(),
235 fPedestalHighGainDiff(),
236 fPedestalLEDRefLowGainDiff(),
237 fPedestalLEDRefHighGainDiff(),
238 fPeakMinusPedLowGainDiff(),
239 fPeakMinusPedHighGainDiff(),
240 fPedestalLowGainRatio(),
241 fPedestalHighGainRatio(),
242 fPedestalLEDRefLowGainRatio(),
243 fPedestalLEDRefHighGainRatio(),
244 fPeakMinusPedLowGainRatio(),
245 fPeakMinusPedHighGainRatio(),
247 fNEvents(ped.GetNEvents()),
248 fNChanFills(ped.GetNChanFills()),
249 fDeadTowers(ped.GetDeadTowerCount()),
250 fNewDeadTowers(ped.GetDeadTowerNew()),
251 fResurrectedTowers(ped.GetDeadTowerResurrected()),
252 fReference( 0 ), //! note that we do not try to copy the reference info here
253 fDetType(ped.GetDetectorType()),
254 fColumns(ped.GetColumns()),
255 fRows(ped.GetRows()),
256 fLEDRefs(ped.GetLEDRefs()),
257 fModules(ped.GetModules()),
258 fRowMin(ped.GetRowMin()),
259 fRowMax(ped.GetRowMax()),
260 fRowMultiplier(ped.GetRowMultiplier()),
261 fCaloString(ped.GetCaloString()),
262 fMapping(NULL), //! note that we are not copying the map info
263 fRunNumber(ped.GetRunNumber()),
264 fSelectPedestalSamples(ped.GetSelectPedestalSamples()),
265 fFirstPedestalSample(ped.GetFirstPedestalSample()),
266 fLastPedestalSample(ped.GetLastPedestalSample()),
267 fDeadThreshold(ped.GetDeadThreshold()),
268 fWarningThreshold(ped.GetWarningThreshold()),
269 fWarningFraction(ped.GetWarningFraction()),
270 fHotSigma(ped.GetHotSigma())
272 // Then the ObjArray ones; we add the histograms rather than trying TObjArray = assignment
273 //DS: this has not really been tested yet..
274 for (int i = 0; i < fModules; i++) {
275 fPedestalLowGain.Add( ped.GetPedProfileLowGain(i) );
276 fPedestalHighGain.Add( ped.GetPedProfileHighGain(i) );
277 fPedestalLEDRefLowGain.Add( ped.GetPedLEDRefProfileLowGain(i) );
278 fPedestalLEDRefHighGain.Add( ped.GetPedLEDRefProfileHighGain(i) );
279 fPeakMinusPedLowGain.Add( ped.GetPeakProfileLowGain(i) );
280 fPeakMinusPedHighGain.Add( ped.GetPeakProfileHighGain(i) );
281 fPeakMinusPedHighGainHisto.Add( ped.GetPeakHighGainHisto(i) );
283 fDeadMap.Add( ped.GetDeadMap(i) );
286 //Compress the arrays, in order to remove the empty objects (a 16 slot array is created by default)
287 fPedestalLowGain.Compress();
288 fPedestalHighGain.Compress();
289 fPedestalLEDRefLowGain.Compress();
290 fPedestalLEDRefHighGain.Compress();
291 fPeakMinusPedLowGain.Compress();
292 fPeakMinusPedHighGain.Compress();
293 fPeakMinusPedHighGainHisto.Compress();
298 // assignment operator; use copy ctor to make life easy..
299 //_____________________________________________________________________
300 AliCaloCalibPedestal& AliCaloCalibPedestal::operator = (const AliCaloCalibPedestal &source)
302 // assignment operator; use copy ctor
303 if (&source == this) return *this;
305 new (this) AliCaloCalibPedestal(source);
309 //_____________________________________________________________________
310 void AliCaloCalibPedestal::Reset()
312 // Reset all arrays/histograms
313 for (int i = 0; i < fModules; i++) {
314 GetPedProfileLowGain(i)->Reset();
315 GetPedProfileHighGain(i)->Reset();
316 GetPedLEDRefProfileLowGain(i)->Reset();
317 GetPedLEDRefProfileHighGain(i)->Reset();
318 GetPeakProfileLowGain(i)->Reset();
319 GetPeakProfileHighGain(i)->Reset();
320 GetPeakHighGainHisto(i)->Reset();
321 GetDeadMap(i)->Reset();
323 if (!fPedestalLowGainDiff.IsEmpty()) {
324 //This means that the comparison profiles have been created.
326 GetPedProfileLowGainDiff(i)->Reset();
327 GetPedProfileHighGainDiff(i)->Reset();
328 GetPedLEDRefProfileLowGainDiff(i)->Reset();
329 GetPedLEDRefProfileHighGainDiff(i)->Reset();
330 GetPeakProfileLowGainDiff(i)->Reset();
331 GetPeakProfileHighGainDiff(i)->Reset();
333 GetPedProfileLowGainRatio(i)->Reset();
334 GetPedProfileHighGainRatio(i)->Reset();
335 GetPedLEDRefProfileLowGainRatio(i)->Reset();
336 GetPedLEDRefProfileHighGainRatio(i)->Reset();
337 GetPeakProfileLowGainRatio(i)->Reset();
338 GetPeakProfileHighGainRatio(i)->Reset();
345 fResurrectedTowers = 0;
347 //To think about: should fReference be deleted too?... let's not do it this time, at least...
350 // Parameter/cut handling
351 //_____________________________________________________________________
352 void AliCaloCalibPedestal::SetParametersFromFile(const char *parameterFile)
354 // Note: this method is a bit more complicated than it really has to be
355 // - allowing for multiple entries per line, arbitrary order of the
356 // different variables etc. But I wanted to try and do this in as
357 // correct a C++ way as I could (as an exercise).
359 static const string delimitor("::");
361 // open, check input file
362 ifstream in( parameterFile );
364 printf("in AliCaloCalibPedestal::SetParametersFromFile - Using default/run_time parameters.\n");
371 while ((in.rdstate() & ios::failbit) == 0 ) {
373 // Read into the raw char array and then construct a string
374 // to do the searching
375 in.getline(readline, 1024);
376 istringstream s(readline);
378 while ( ( s.rdstate() & ios::failbit ) == 0 ) {
383 // check stream status
384 if( s.rdstate() & ios::failbit ) break;
386 // skip rest of line if comments found
387 if( keyValue.substr( 0, 2 ) == "//" ) break;
389 // look for "::" in keyValue pair
390 size_t position = keyValue.find( delimitor );
391 if( position == string::npos ) {
392 printf("wrong format for key::value pair: %s\n", keyValue.c_str());
395 // split keyValue pair
396 string key( keyValue.substr( 0, position ) );
397 string value( keyValue.substr( position+delimitor.size(),
398 keyValue.size()-delimitor.size() ) );
400 // check value does not contain a new delimitor
401 if( value.find( delimitor ) != string::npos ) {
402 printf("wrong format for key::value pair: %s\n", keyValue.c_str());
405 // debug: check key value pair
406 // printf("AliCaloCalibPedestal::SetParametersFromFile - key %s value %s\n", key.c_str(), value.c_str());
408 // if the key matches with something we expect, we assign the new value
409 istringstream iss(value);
410 // the comparison strings defined at the beginning of this method
411 if ( (key == "fFirstPedestalSample") || (key == "fLastPedestalSample") || (key == "fDeadThreshold") || (key == "fWarningThreshold") || (key == "fWarningFraction") || (key == "fHotSigma") ) {
412 printf("AliCaloCalibPedestal::SetParametersFromFile - key %s value %s\n", key.c_str(), value.c_str());
414 if (key == "fFirstPedestalSample") {
415 iss >> fFirstPedestalSample;
417 else if (key == "fLastPedestalSample") {
418 iss >> fLastPedestalSample;
420 else if (key == "fDeadThreshold") {
421 iss >> fDeadThreshold;
423 else if (key == "fWarningThreshold") {
424 iss >> fWarningThreshold;
426 else if (key == "fWarningFraction") {
427 iss >> fWarningFraction;
429 else if (key == "fHotSigma") {
443 //_____________________________________________________________________
444 void AliCaloCalibPedestal::WriteParametersToFile(const char *parameterFile)
446 //Write parameters in file.
448 static const string delimitor("::");
449 ofstream out( parameterFile );
450 out << "// " << parameterFile << endl;
451 out << "fFirstPedestalSample" << "::" << fFirstPedestalSample << endl;
452 out << "fLastPedestalSample" << "::" << fLastPedestalSample << endl;
453 out << "fDeadThreshold" << "::" << fDeadThreshold << endl;
454 out << "fWarningThreshold" << "::" << fWarningThreshold << endl;
455 out << "fWarningFraction" << "::" << fWarningFraction << endl;
456 out << "fHotSigma" << "::" << fHotSigma << endl;
462 //_____________________________________________________________________
463 Bool_t AliCaloCalibPedestal::AddInfo(const AliCaloCalibPedestal *ped)
465 // just do this for the basic histograms/profiles that get filled in ProcessEvent
466 // may not have data for all modules, but let's just Add everything..
467 for (int i = 0; i < fModules; i++) {
468 GetPedProfileLowGain(i)->Add( ped->GetPedProfileLowGain(i) );
469 GetPedProfileHighGain(i)->Add( ped->GetPedProfileHighGain(i) );
470 GetPeakProfileLowGain(i)->Add( ped->GetPeakProfileLowGain(i) );
471 GetPeakProfileHighGain(i)->Add( ped->GetPeakProfileHighGain(i) );
472 GetPeakHighGainHisto(i)->Add( ped->GetPeakHighGainHisto(i) );
476 // DeadMap; Diff profiles etc would need to be redone after this operation
478 return kTRUE;//We succesfully added info from the supplied object
481 //_____________________________________________________________________
482 Bool_t AliCaloCalibPedestal::ProcessEvent(AliRawReader *rawReader)
484 // if fMapping is NULL the rawstream will crate its own mapping
485 AliCaloRawStreamV3 rawStream(rawReader, fCaloString, (AliAltroMapping**)fMapping);
486 if (fDetType == kEmCal) {
487 rawReader->Select("EMCAL", 0, AliEMCALGeoParams::fgkLastAltroDDL) ; //select EMCAL DDL range
489 return ProcessEvent(&rawStream);
492 //_____________________________________________________________________
493 Bool_t AliCaloCalibPedestal::ProcessEvent(AliCaloRawStreamV3 *in)
495 // Method to process=analyze one event in the data stream
496 if (!in) return kFALSE; //Return right away if there's a null pointer
497 fNEvents++; // one more event
499 // indices for the reading
502 int i = 0; // sample counter
505 // start loop over input stream
506 while (in->NextDDL()) {
507 while (in->NextChannel()) {
510 int max = AliEMCALGeoParams::fgkSampleMin, min = AliEMCALGeoParams::fgkSampleMax; // min and max sample values
515 vector<int> pedSamples;
517 while (in->NextBunch()) {
518 const UShort_t *sig = in->GetSignals();
519 startBin = in->GetStartTimeBin();
520 nsamples += in->GetBunchLength();
521 for (i = 0; i < in->GetBunchLength(); i++) {
525 // check if it's a min or max value
526 if (sample < min) min = sample;
527 if (sample > max) max = sample;
529 // should we add it for the pedestal calculation?
530 if ( (fFirstPedestalSample<=time && time<=fLastPedestalSample) || // sample time in range
531 !fSelectPedestalSamples ) { // or we don't restrict the sample range.. - then we'll take all
532 pedSamples.push_back( sig[i] );
536 } // loop over samples in bunch
537 } // loop over bunches
539 if (nsamples > 0) { // this check is needed for when we have zero-supp. on, but not sparse readout
541 // it should be enough to check the SuperModule info for each DDL really, but let's keep it here for now
542 int arrayPos = in->GetModule(); //The modules are numbered starting from 0
543 if (arrayPos >= fModules) {
544 //TODO: return an error message, if appopriate (perhaps if debug>0?)
548 if (arrayPos < 0 || arrayPos >= fModules) {
549 printf("Oh no: arrayPos = %i.\n", arrayPos);
552 fNChanFills++; // one more channel found, and profile to be filled
553 //NOTE: coordinates are (column, row) for the profiles
554 if ( in->IsLowGain() ) {
555 //fill the low gain histograms
556 ((TProfile2D*)fPeakMinusPedLowGain[arrayPos])->Fill(in->GetColumn(), fRowMultiplier*in->GetRow(), max - min);
557 if (nPed>0) { // only fill pedestal info in case it could be calculated
558 for ( i=0; i<nPed; i++) {
559 ((TProfile2D*)fPedestalLowGain[arrayPos])->Fill(in->GetColumn(), fRowMultiplier*in->GetRow(), pedSamples[i]);
563 else if ( in->IsHighGain() ) {
564 //fill the high gain ones
565 ((TProfile2D*)fPeakMinusPedHighGain[arrayPos])->Fill(in->GetColumn(), fRowMultiplier*in->GetRow(), max - min);
566 if (nPed>0) { // only fill pedestal info in case it could be calculated
567 for ( i=0; i<nPed; i++) {
568 ((TProfile2D*)fPedestalHighGain[arrayPos])->Fill(in->GetColumn(), fRowMultiplier*in->GetRow(), pedSamples[i]);
571 // for warning checks
572 int idx = in->GetRow() + fRows * in->GetColumn();
573 ((TH2F*)fPeakMinusPedHighGainHisto[arrayPos])->Fill(idx, max - min);
575 else if ( in->IsLEDMonData() ) {
576 // for LED Mon data, the mapping class holds the gain info in the Row variable
577 // and the Strip number in the Column..
578 int gain = in->GetRow();
579 int stripId = in->GetColumn();
580 if (nPed>0 && stripId<fLEDRefs) {
582 for ( i=0; i<nPed; i++) {
583 ((TProfile*)fPedestalLEDRefLowGain[arrayPos])->Fill(stripId, pedSamples[i]);
587 for ( i=0; i<nPed; i++) {
588 ((TProfile*)fPedestalLEDRefHighGain[arrayPos])->Fill(stripId, pedSamples[i]);
594 } // nsamples>0 check, some data found for this channel; not only trailer/header
595 }// end while over channel
596 }//end while over DDL's, of input stream
598 in->Reset(); // just in case the next customer forgets to check if the stream was reset..
603 //_____________________________________________________________________
604 Bool_t AliCaloCalibPedestal::SaveHistograms(TString fileName, Bool_t saveEmptyHistos)
606 //Saves all the histograms (or profiles, to be accurate) to the designated file
608 TFile destFile(fileName, "recreate");
610 if (destFile.IsZombie()) {
616 for (int i = 0; i < fModules; i++) {
617 if( ((TProfile2D *)fPeakMinusPedLowGain[i])->GetEntries() || saveEmptyHistos) {
618 fPeakMinusPedLowGain[i]->Write();
620 if( ((TProfile2D *)fPeakMinusPedHighGain[i])->GetEntries() || saveEmptyHistos) {
621 fPeakMinusPedHighGain[i]->Write();
623 if( ((TProfile2D *)fPedestalLowGain[i])->GetEntries() || saveEmptyHistos) {
624 fPedestalLowGain[i]->Write();
626 if( ((TProfile2D *)fPedestalHighGain[i])->GetEntries() || saveEmptyHistos) {
627 fPedestalHighGain[i]->Write();
629 if( ((TProfile *)fPedestalLEDRefLowGain[i])->GetEntries() || saveEmptyHistos) {
630 fPedestalLEDRefLowGain[i]->Write();
632 if( ((TProfile *)fPedestalLEDRefHighGain[i])->GetEntries() || saveEmptyHistos) {
633 fPedestalLEDRefHighGain[i]->Write();
635 if( ((TH2F *)fPeakMinusPedHighGainHisto[i])->GetEntries() || saveEmptyHistos) {
636 fPeakMinusPedHighGainHisto[i]->Write();
646 //_____________________________________________________________________
647 Bool_t AliCaloCalibPedestal::LoadReferenceCalib(TString fileName, TString objectName)
650 //Make sure that the histograms created when loading the object are not destroyed as the file object is destroyed
651 TH1::AddDirectory(kFALSE);
653 TFile *sourceFile = new TFile(fileName);
654 if (sourceFile->IsZombie()) {
655 return kFALSE;//We couldn't load the reference
658 if (fReference) delete fReference;//Delete the reference object, if it already exists
661 fReference = (AliCaloCalibPedestal*)sourceFile->Get(objectName);
663 if (!fReference || !(fReference->InheritsFrom(AliCaloCalibPedestal::Class())) || (fReference->GetDetectorType() != fDetType)) {
664 if (fReference) delete fReference;//Delete the object, in case we had an object of the wrong type
671 //Reset the histogram ownership behaviour. NOTE: a better workaround would be good, since this may accidentally set AddDirectory to true, even
672 //if we are called by someone who has set it to false...
673 TH1::AddDirectory(kTRUE);
675 return kTRUE;//We succesfully loaded the object
678 //_____________________________________________________________________
679 void AliCaloCalibPedestal::ValidateComparisonProfiles()
681 //Make sure the comparison histos exist
682 if (!fPedestalLowGainDiff.IsEmpty()) return; //The profiles already exist. We just check one, because they're all created at
686 //Then, loop for the requested number of modules
688 for (int i = 0; i < fModules; i++) {
689 //Pedestals, low gain
690 name = "hPedlowgainDiff";
692 title = "Pedestals difference, low gain, module ";
694 fPedestalLowGainDiff.Add(new TProfile2D(name, title,
695 fColumns, 0.0, fColumns,
696 fRows, fRowMin, fRowMax,"s"));
698 //Pedestals, high gain
699 name = "hPedhighgainDiff";
701 title = "Pedestals difference, high gain, module ";
703 fPedestalHighGainDiff.Add(new TProfile2D(name, title,
704 fColumns, 0.0, fColumns,
705 fRows, fRowMin, fRowMax,"s"));
707 //LED Ref/Mon pedestals, low gain
708 name = "hPedestalLEDReflowgainDiff";
710 title = "Pedestal difference LEDRef, low gain, module ";
712 fPedestalLEDRefLowGainDiff.Add(new TProfile(name, title,
713 fLEDRefs, 0.0, fLEDRefs, "s"));
715 //LED Ref/Mon pedestals, high gain
716 name = "hPedestalLEDRefhighgainDiff";
718 title = "Pedestal difference LEDRef, high gain, module ";
720 fPedestalLEDRefHighGainDiff.Add(new TProfile(name, title,
721 fLEDRefs, 0.0, fLEDRefs, "s"));
723 //Peak-Pedestals, high gain
724 name = "hPeakMinusPedhighgainDiff";
726 title = "Peak-Pedestal difference, high gain, module ";
728 fPeakMinusPedHighGainDiff.Add(new TProfile2D(name, title,
729 fColumns, 0.0, fColumns,
730 fRows, fRowMin, fRowMax,"s"));
732 //Peak-Pedestals, low gain
733 name = "hPeakMinusPedlowgainDiff";
735 title = "Peak-Pedestal difference, low gain, module ";
737 fPeakMinusPedLowGainDiff.Add(new TProfile2D(name, title,
738 fColumns, 0.0, fColumns,
739 fRows, fRowMin, fRowMax,"s"));
741 //Pedestals, low gain
742 name = "hPedlowgainRatio";
744 title = "Pedestals ratio, low gain, module ";
746 fPedestalLowGainRatio.Add(new TProfile2D(name, title,
747 fColumns, 0.0, fColumns,
748 fRows, fRowMin, fRowMax,"s"));
750 //Pedestals, high gain
751 name = "hPedhighgainRatio";
753 title = "Pedestals ratio, high gain, module ";
755 fPedestalHighGainRatio.Add(new TProfile2D(name, title,
756 fColumns, 0.0, fColumns,
757 fRows, fRowMin, fRowMax,"s"));
759 //LED Ref/Mon pedestals, low gain
760 name = "hPedestalLEDReflowgain";
762 title = "Pedestal ratio LEDRef, low gain, module ";
764 fPedestalLEDRefLowGainRatio.Add(new TProfile(name, title,
765 fLEDRefs, 0.0, fLEDRefs, "s"));
767 //LED Ref/Mon pedestals, high gain
768 name = "hPedestalLEDRefhighgainRatio";
770 title = "Pedestal ratio LEDRef, high gain, module ";
772 fPedestalLEDRefHighGainRatio.Add(new TProfile(name, title,
773 fLEDRefs, 0.0, fLEDRefs, "s"));
775 //Peak-Pedestals, low gain
776 name = "hPeakMinusPedlowgainRatio";
778 title = "Peak-Pedestal ratio, low gain, module ";
780 fPeakMinusPedLowGainRatio.Add(new TProfile2D(name, title,
781 fColumns, 0.0, fColumns,
782 fRows, fRowMin, fRowMax,"s"));
784 //Peak-Pedestals, high gain
785 name = "hPeakMinusPedhighgainRatio";
787 title = "Peak-Pedestal ratio, high gain, module ";
789 fPeakMinusPedHighGainRatio.Add(new TProfile2D(name, title,
790 fColumns, 0.0, fColumns,
791 fRows, fRowMin, fRowMax,"s"));
793 }//end for nModules create the histograms
796 //_____________________________________________________________________
797 void AliCaloCalibPedestal::ComputeDiffAndRatio()
799 // calculate differences and ratios relative to a reference
800 ValidateComparisonProfiles();//Make sure the comparison histos exist
803 return;//Return if the reference object isn't loaded
809 for (int i = 0; i < fModules; i++) {
810 //For computing the difference, we cannot simply do TProfile2D->Add(), because that subtracts the sum of all entries,
811 //which means that the mean of the new profile will not be the difference of the means. So do it by hand:
812 for (int j = 0; j < fColumns; j++) {
813 for (int k = 0; k < fRows; k++) {
814 bin = ((TProfile2D*)fPeakMinusPedHighGainDiff[i])->GetBin(j+1, k+1);//Note that we assume here that all histos have the same structure...
816 if (fReference->GetPeakProfileHighGain(i)->GetBinContent(bin) > 0) {
817 diff = GetPeakProfileHighGain(i)->GetBinContent(bin) - fReference->GetPeakProfileHighGain(i)->GetBinContent(bin);
818 ((TProfile2D*)fPeakMinusPedHighGainDiff[i])->SetBinContent(bin, diff);
819 ((TProfile2D*)fPeakMinusPedHighGainDiff[i])->SetBinEntries(bin, 1);
820 ratio = GetPeakProfileHighGain(i)->GetBinContent(bin) / fReference->GetPeakProfileHighGain(i)->GetBinContent(bin);
821 ((TProfile2D*)fPeakMinusPedHighGainRatio[i])->SetBinContent(bin, ratio);
822 ((TProfile2D*)fPeakMinusPedHighGainRatio[i])->SetBinEntries(bin, 1);
825 if (fReference->GetPeakProfileLowGain(i)->GetBinContent(bin) > 0) {
826 diff = GetPeakProfileLowGain(i)->GetBinContent(bin) - fReference->GetPeakProfileLowGain(i)->GetBinContent(bin);
827 ((TProfile2D*)fPeakMinusPedLowGainDiff[i])->SetBinContent(bin, diff);
828 ((TProfile2D*)fPeakMinusPedLowGainDiff[i])->SetBinEntries(bin, 1);
829 ratio = GetPeakProfileLowGain(i)->GetBinContent(bin) / fReference->GetPeakProfileLowGain(i)->GetBinContent(bin);
830 ((TProfile2D*)fPeakMinusPedLowGainRatio[i])->SetBinContent(bin, ratio);
831 ((TProfile2D*)fPeakMinusPedLowGainRatio[i])->SetBinEntries(bin, 1);
834 if (fReference->GetPedProfileHighGain(i)->GetBinContent(bin) > 0) {
835 diff = GetPedProfileHighGain(i)->GetBinContent(bin) - fReference->GetPedProfileHighGain(i)->GetBinContent(bin);
836 ((TProfile2D*)fPedestalHighGainDiff[i])->SetBinContent(bin, diff);
837 ((TProfile2D*)fPedestalHighGainDiff[i])->SetBinEntries(bin, 1);
838 ratio = GetPedProfileHighGain(i)->GetBinContent(bin) / fReference->GetPedProfileHighGain(i)->GetBinContent(bin);
839 ((TProfile2D*)fPedestalHighGainRatio[i])->SetBinContent(bin, ratio);
840 ((TProfile2D*)fPedestalHighGainRatio[i])->SetBinEntries(bin, 1);
843 if (fReference->GetPedProfileLowGain(i)->GetBinContent(bin) > 0) {
844 diff = GetPedProfileLowGain(i)->GetBinContent(bin) - fReference->GetPedProfileLowGain(i)->GetBinContent(bin);
845 ((TProfile2D*)fPedestalLowGainDiff[i])->SetBinContent(bin, diff);
846 ((TProfile2D*)fPedestalLowGainDiff[i])->SetBinEntries(bin, 1);
847 ratio = GetPedProfileLowGain(i)->GetBinContent(bin) / fReference->GetPedProfileLowGain(i)->GetBinContent(bin);
848 ((TProfile2D*)fPedestalLowGainRatio[i])->SetBinContent(bin, ratio);
849 ((TProfile2D*)fPedestalLowGainRatio[i])->SetBinEntries(bin, 1);
855 // same for LED Ref/Mon channels
856 for (int j = 0; j <= fLEDRefs; j++) {
857 bin = j+1;//Note that we assume here that all histos have the same structure...
859 if (fReference->GetPedLEDRefProfileHighGain(i)->GetBinContent(bin) > 0) {
860 diff = GetPedLEDRefProfileHighGain(i)->GetBinContent(bin) - fReference->GetPedLEDRefProfileHighGain(i)->GetBinContent(bin);
861 ((TProfile*)fPedestalLEDRefHighGainDiff[i])->SetBinContent(bin, diff);
862 ((TProfile*)fPedestalLEDRefHighGainDiff[i])->SetBinEntries(bin, 1);
863 ratio = GetPedLEDRefProfileHighGain(i)->GetBinContent(bin) / fReference->GetPedLEDRefProfileHighGain(i)->GetBinContent(bin);
864 ((TProfile*)fPedestalLEDRefHighGainRatio[i])->SetBinContent(bin, ratio);
865 ((TProfile*)fPedestalLEDRefHighGainRatio[i])->SetBinEntries(bin, 1);
868 if (fReference->GetPedLEDRefProfileLowGain(i)->GetBinContent(bin) > 0) {
869 diff = GetPedLEDRefProfileLowGain(i)->GetBinContent(bin) - fReference->GetPedLEDRefProfileLowGain(i)->GetBinContent(bin);
870 ((TProfile*)fPedestalLEDRefLowGainDiff[i])->SetBinContent(bin, diff);
871 ((TProfile*)fPedestalLEDRefLowGainDiff[i])->SetBinEntries(bin, 1);
872 ratio = GetPedLEDRefProfileLowGain(i)->GetBinContent(bin) / fReference->GetPedLEDRefProfileLowGain(i)->GetBinContent(bin);
873 ((TProfile*)fPedestalLEDRefLowGainRatio[i])->SetBinContent(bin, ratio);
874 ((TProfile*)fPedestalLEDRefLowGainRatio[i])->SetBinEntries(bin, 1);
883 //_____________________________________________________________________
884 void AliCaloCalibPedestal::ComputeHotAndWarningTowers(const char * hotMapFile)
885 { // look for hot/noisy towers
887 char name[512];//Quite a long temp buffer, just in case the filename includes a path
890 snprintf(name, 512, "%s.txt", hotMapFile);
891 fout = new ofstream(name);
892 if (!fout->is_open()) {
894 fout = 0;//Set the pointer to empty if the file was not opened
898 for(int i = 0; i < fModules; i++){
900 //first we compute the peak-pedestal distribution for each supermodule...
901 if( GetPeakHighGainHisto(i)->GetEntries() > 0 ) {
902 double min = GetPeakProfileHighGain(i)->GetBinContent(GetPeakProfileHighGain(i)->GetMinimumBin());
903 double max = GetPeakProfileHighGain(i)->GetBinContent(GetPeakProfileHighGain(i)->GetMaximumBin());
904 TH1D *hPeakFit = new TH1D(Form("hFit_%d", i), Form("hFit_%d", i), (int)((max-min)*10), min-1, max+1);
906 for (int j = 1; j <= fColumns; j++) {
907 for (int k = 1; k <= fRows; k++) {
908 hPeakFit->Fill(GetPeakProfileHighGain(i)->GetBinContent(j, k));
912 //...and then we fit it
913 hPeakFit->Fit("gaus", "OQ", "", hPeakFit->GetMean() - 3*hPeakFit->GetRMS(),
914 hPeakFit->GetMean() + 3*hPeakFit->GetRMS());
916 double mean = hPeakFit->GetFunction("gaus")->GetParameter(1);
917 double sigma = hPeakFit->GetFunction("gaus")->GetParameter(2);
921 //Then we look for warm/hot towers
922 TH2F * hPeak2D = GetPeakHighGainHisto(i);
923 hPeak2D->GetYaxis()->SetRangeUser( fWarningThreshold, hPeak2D->GetYaxis()->GetBinUpEdge(hPeak2D->GetNbinsY()) );
927 for (int j = 1; j <= fColumns; j++) {
928 for (int k = 1; k <= fRows; k++) {
929 //we start looking for warm/warning towers...
930 // histogram x-axis index
931 idx = k-1 + fRows*(j-1); // this is what is used in the Fill call
932 hPeak2D->GetXaxis()->SetRangeUser(idx, idx);
933 warnCounter = (int) hPeak2D->Integral();
934 if(warnCounter > fNEvents * fWarningFraction) {
935 ((TH2D*)fDeadMap[i])->SetBinContent(j, k, kWarning);
936 /* printf("mod %d col %d row %d warnCounter %d - status %d\n",
937 i, j-1, k-1, warnCounter, (int) (kWarning)); */
939 //...then we look for hot ones (towers whose values are greater than mean + X*sigma)
940 if(GetPeakProfileHighGain(i)->GetBinContent(j, k) > mean + fHotSigma*sigma ) {
941 ((TH2D*)fDeadMap[i])->SetBinContent(j, k, kHot);
942 /* printf("mod %d col %d row %d binc %d - status %d\n",
943 i, j-1, k-1, (int)(GetPeakProfileHighGain(i)->GetBinContent(j, k)), (int) (kHot)); */
946 //Write the status to the hot/warm map file, if the file is open.
947 // module - column - row - status (1=dead, 2= warm/warning , 3 = hot, see .h file enum)
948 if (fout && ((TH2D*)fDeadMap[i])->GetBinContent(j, k) > 1) {
953 << ((TH2D*)fDeadMap[i])->GetBinContent(j, k) << endl; }
963 //_____________________________________________________________________
964 void AliCaloCalibPedestal::ComputeDeadTowers(const char * deadMapFile)
966 //Computes the number of dead towers etc etc into memory, after this you can call the GetDead... -functions
972 char name[512];//Quite a long temp buffer, just in case the filename includes a path
975 snprintf(name, 512, "%s.txt", deadMapFile);
976 fout = new ofstream(name);
977 snprintf(name, 512, "%sdiff.txt", deadMapFile);
978 diff = new ofstream(name);
979 if (!fout->is_open()) {
981 fout = 0;//Set the pointer to empty if the file was not opened
983 if (!diff->is_open()) {
985 fout = 0;//Set the pointer to empty if the file was not opened
989 for (int i = 0; i < fModules; i++) {
990 if (GetPeakProfileHighGain(i)->GetEntries() > 0) { //don't care about empty histos
991 for (int j = 1; j <= fColumns; j++) {
992 for (int k = 1; k <= fRows; k++) {
994 if (GetPeakProfileHighGain(i)->GetBinContent(j, k) < fDeadThreshold) {//It's dead
995 countTot++;//One more dead total
1001 << "0" << endl;//Write the status to the deadmap file, if the file is open.
1004 if (fReference && fReference->GetPeakProfileHighGain(i)->GetBinContent(j, k) >= fDeadThreshold) {
1005 ((TH2D*)fDeadMap[i])->SetBinContent(j, k, kRecentlyDeceased);
1006 countNew++;//This tower wasn't dead before!
1008 ( *diff) << i << " "
1012 << "0" << endl;//Write the status to the deadmap difference file, if the file is open.
1016 ((TH2D*)fDeadMap[i])->SetBinContent(j, k, kDead);//This has been dead before. Nothing new
1019 else { //It's ALIVE!!
1020 //Don't bother with writing the live ones.
1021 if (fReference && fReference->GetPeakProfileHighGain(i)->GetBinContent(j, k) < fDeadThreshold) {
1022 ((TH2D*)fDeadMap[i])->SetBinContent(j, k, kResurrected);
1023 countRes++; //This tower was dead before => it's a miracle! :P
1029 << "1" << endl;//Write the status to the deadmap difference file, if the file is open.
1033 ((TH2D*)fDeadMap[i])->SetBinContent(j, k, kAlive);
1038 }//end for j/columns
1039 }//end if GetEntries >= 0
1048 fDeadTowers = countTot;
1049 fNewDeadTowers = countNew;
1050 fResurrectedTowers = countRes;
1053 //_____________________________________________________________________
1054 Bool_t AliCaloCalibPedestal::IsBadChannel(int imod, int icol, int irow) const
1056 //Check if channel is dead or hot.
1057 Int_t status = (Int_t) ( ((TH2D*)fDeadMap[imod])->GetBinContent(icol,irow) );
1058 if(status == kAlive)
1065 //_____________________________________________________________________
1066 void AliCaloCalibPedestal::SetChannelStatus(int imod, int icol, int irow, int status)
1068 //Set status of channel dead, hot, alive ...
1069 ((TH2D*)fDeadMap[imod])->SetBinContent(icol, irow, status);