Add macro for local gain table OCDB entry
[u/mrichter/AliRoot.git] / FMD / FMDutil / AliFMDPedestalDA.cxx
CommitLineData
3bd993ba 1/**************************************************************************
2 * Copyright(c) 2004, 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
3490bd31 16/** @file AliMDPedestalDA.cxx
3bd993ba 17 @author Hans Hjersing Dalsgaard <canute@nbi.dk>
18 @date Mon Mar 10 09:46:05 2008
19 @brief Derived class for the pedestal detector algorithm.
20*/
21//
e9c06036 22// This class implements the virtual functions of the AliFMDBaseDA
23// class. The most important of these functions, FillChannels(..) and
24// Analyse(...) collect and analyse the data of each channel. The
25// resulting pedestal and noise values are written to a comma
26// separated values (csv) file on the go. The csv files produced in
27// this way are the basic input to the AliFMDPreprocessor.
3bd993ba 28//
29
30#include "AliFMDPedestalDA.h"
5cf05dbb 31#include "AliFMDAltroMapping.h"
09b6c804 32#include "AliFMDParameters.h"
33#include "AliFMDCalibPedestal.h"
34#include "AliFMDDigit.h"
35#include "AliLog.h"
408bf2b4 36#include <iostream>
37#include <fstream>
45cffd06 38#include <iomanip>
09b6c804 39#include <TFile.h>
40#include <TF1.h>
41#include <TObject.h>
42#include <TMath.h>
408bf2b4 43#include <TSystem.h>
6cf6e7a0 44#include <TDatime.h>
2a082c96 45#include <TH2.h>
3bd993ba 46
47//_____________________________________________________________________
48ClassImp(AliFMDPedestalDA)
49
50//_____________________________________________________________________
2a082c96 51AliFMDPedestalDA::AliFMDPedestalDA()
52 : AliFMDBaseDA(),
53 fCurrentChannel(1),
54 fPedSummary("PedestalSummary","pedestals",51200,0,51200),
55 fNoiseSummary("NoiseSummary","noise",51200,0,51200),
56 fZSfileFMD1(),
57 fZSfileFMD2(),
58 fZSfileFMD3(),
59 fMinTimebin(3 * 4 * 3 * 16), // 3 ddls, 4 FECs, 3 Altros, 16 channels
60 fMaxTimebin(3 * 4 * 3 * 16), // 3 ddls, 4 FECs, 3 Altros, 16 channels
61 fSummaryFMD1i(0),
62 fSummaryFMD2i(0),
63 fSummaryFMD2o(0),
64 fSummaryFMD3i(0),
65 fSummaryFMD3o(0)
3bd993ba 66{
5cf05dbb 67 // Default constructor
6cf6e7a0 68 Rotate("peds.csv", 3);
3bd993ba 69 fOutputFile.open("peds.csv");
6cf6e7a0 70 Rotate("ddl3072.csv", 10);
7bce699b 71 fZSfileFMD1.open("ddl3072.csv");
6cf6e7a0 72 Rotate("ddl3073.csv", 10);
7bce699b 73 fZSfileFMD2.open("ddl3073.csv");
6cf6e7a0 74 Rotate("ddl3074.csv", 10);
7bce699b 75 fZSfileFMD3.open("ddl3074.csv");
a31ea3ce 76 fDiagnosticsFilename = "diagnosticsPedestal.root";
3bd993ba 77}
78
79//_____________________________________________________________________
80AliFMDPedestalDA::AliFMDPedestalDA(const AliFMDPedestalDA & pedDA) :
f7f0b643 81 AliFMDBaseDA(pedDA),
f14ede67 82 fCurrentChannel(1),
f7f0b643 83 fPedSummary("PedestalSummary","pedestals",51200,0,51200),
7bce699b 84 fNoiseSummary("NoiseSummary","noise",51200,0,51200),
85 fZSfileFMD1(),
86 fZSfileFMD2(),
5cf05dbb 87 fZSfileFMD3(),
88 fMinTimebin(pedDA.fMinTimebin),
2a082c96 89 fMaxTimebin(pedDA.fMaxTimebin),
90 fSummaryFMD1i(pedDA.fSummaryFMD1i),
91 fSummaryFMD2i(pedDA.fSummaryFMD2i),
92 fSummaryFMD2o(pedDA.fSummaryFMD2o),
93 fSummaryFMD3i(pedDA.fSummaryFMD3i),
94 fSummaryFMD3o(pedDA.fSummaryFMD3o)
3bd993ba 95{
5cf05dbb 96 // Copy constructor
3bd993ba 97}
98
99//_____________________________________________________________________
e9c06036 100AliFMDPedestalDA::~AliFMDPedestalDA()
101{
5cf05dbb 102 // Destructor.
3bd993ba 103}
104
105//_____________________________________________________________________
e9c06036 106void AliFMDPedestalDA::Init()
107{
5cf05dbb 108 // Initialise
3bd993ba 109 SetRequiredEvents(1000);
5cf05dbb 110 fMinTimebin.Reset(1024);
111 fMaxTimebin.Reset(-1);
2a082c96 112
113
3bd993ba 114}
115
116//_____________________________________________________________________
3490bd31 117void AliFMDPedestalDA::AddChannelContainer(Array* sampleArray,
3bd993ba 118 UShort_t det,
e9c06036 119 Char_t ring,
3bd993ba 120 UShort_t sec,
e9c06036 121 UShort_t strip)
122{
5cf05dbb 123 // Add a channel to the containers.
124 //
125 // Parameters:
126 // sectorArray Array of sectors
127 // det Detector
128 // ring Ring
129 // sec Sector
130 // strip Strip
e9c06036 131 AliFMDParameters* pars = AliFMDParameters::Instance();
5cf05dbb 132 UInt_t samples = pars->GetSampleRate(det, ring, sec, strip);
7bce699b 133 for (UInt_t sample = 0; sample < samples; sample++) {
45cffd06 134 TString name(Form("FMD%d%c[%02d,%03d]_%d", det,ring,sec,strip,sample));
135 TH1S* hSample = new TH1S(name.Data(),name.Data(), 1024,-.5,1023.5);
e9c06036 136 hSample->SetXTitle("ADC");
137 hSample->SetYTitle("Events");
7bce699b 138 hSample->SetDirectory(0);
3490bd31 139 hSample->ResetBit(TObject::kMustCleanup);
a31ea3ce 140 sampleArray->AddAtAndExpand(hSample, sample);
e9c06036 141 }
a31ea3ce 142}
143
144//_____________________________________________________________________
3490bd31 145void AliFMDPedestalDA::AddSectorSummary(Array* sectorArray,
a31ea3ce 146 UShort_t det,
147 Char_t ring,
148 UShort_t sec,
149 UShort_t nStr)
150{
151 TH1F* sumPed = new TH1F("Pedestals",
152 Form("Summary of pedestals in FMD%d%c[%02d]",
153 det, ring, sec),
154 nStr, -.5, nStr-.5);
155 sumPed->SetXTitle("Strip");
156 sumPed->SetYTitle("Pedestal [ADC]");
157 sumPed->SetDirectory(0);
3490bd31 158 sumPed->ResetBit(TObject::kMustCleanup);
a31ea3ce 159
160 TH1F* sumNoise = static_cast<TH1F*>(sumPed->Clone("Noise"));
161 sumNoise->SetYTitle("Noise [ADC]");
162 sumNoise->SetDirectory(0);
3490bd31 163 sumNoise->ResetBit(TObject::kMustCleanup);
a31ea3ce 164
165 Int_t n = sectorArray->GetEntriesFast();
166 sectorArray->AddAtAndExpand(sumPed, n + kPedestalOffset - 1);
167 sectorArray->AddAtAndExpand(sumNoise, n + kNoiseOffset - 1);
3bd993ba 168}
169
170//_____________________________________________________________________
e9c06036 171void AliFMDPedestalDA::FillChannels(AliFMDDigit* digit)
172{
5cf05dbb 173 // Fill ADC values from a digit into the corresponding histogram.
174 //
175 // Parameters:
176 // digit Digit to fill ADC values for.
3bd993ba 177 UShort_t det = digit->Detector();
178 Char_t ring = digit->Ring();
179 UShort_t sec = digit->Sector();
180 UShort_t strip = digit->Strip();
15e37b0a 181
e9c06036 182 AliFMDParameters* pars = AliFMDParameters::Instance();
5cf05dbb 183 UInt_t samples = pars->GetSampleRate(det, ring, sec, strip);
7bce699b 184 for (UInt_t sample = 0; sample < samples; sample++) {
e9c06036 185 TH1S* hSample = GetChannel(det, ring, sec, strip, sample);
a31ea3ce 186 if (!hSample) continue;
187
e9c06036 188 hSample->Fill(digit->Count(sample));
189 }
7bce699b 190
3bd993ba 191}
192
193//_____________________________________________________________________
2a082c96 194void AliFMDPedestalDA::MakeSummary(UShort_t det, Char_t ring)
195{
8e23c82d 196 //Create summary hists for FMD pedestals
a31ea3ce 197 // std::cout << "Making summary for FMD" << det << ring << " ..."
198 // << std::endl;
2a082c96 199 switch (det) {
200 case 1:
201 fSummaryFMD1i = MakeSummaryHistogram("ped", "Pedestals", det, ring);
202 break;
203 case 2:
204 switch (ring) {
205 case 'I': case 'i':
206 fSummaryFMD2i = MakeSummaryHistogram("ped", "Pedestals", det, ring);
207 break;
208 case 'O': case 'o':
209 fSummaryFMD2o = MakeSummaryHistogram("ped", "Pedestals", det, ring);
210 break;
211 }
212 break;
213 case 3:
214 switch (ring) {
215 case 'I': case 'i':
216 fSummaryFMD3i = MakeSummaryHistogram("ped", "Pedestals", det, ring);
217 break;
218 case 'O': case 'o':
219 fSummaryFMD3o = MakeSummaryHistogram("ped", "Pedestals", det, ring);
220 break;
221 }
222 break;
223 }
224}
225
226//_____________________________________________________________________
3bd993ba 227void AliFMDPedestalDA::Analyse(UShort_t det,
e9c06036 228 Char_t ring,
3bd993ba 229 UShort_t sec,
5cf05dbb 230 UShort_t strip)
231{
232 // Analyse a strip. That is, compute the mean and spread of the ADC
233 // spectra for all strips. Also output on files the values.
234 //
235 // Parameters:
236 // det Detector
237 // ring Ring
238 // sec Sector
239 // strip Strip.
7bce699b 240 AliFMDParameters* pars = AliFMDParameters::Instance();
2a082c96 241 TH2* summary = 0;
242 switch (det) {
243 case 1: summary = fSummaryFMD1i; break;
244 case 2:
245 switch (ring) {
246 case 'I': summary = fSummaryFMD2i; break;
247 case 'O': summary = fSummaryFMD2o; break;
248 }
249 break;
250 case 3:
251 switch (ring) {
252 case 'I': summary = fSummaryFMD3i; break;
253 case 'O': summary = fSummaryFMD3o; break;
254 }
255 break;
256 }
3490bd31 257
258 UInt_t samples = pars->GetSampleRate(det, ring, sec, strip);
7bce699b 259 for (UShort_t sample = 0; sample < samples; sample++) {
5cf05dbb 260 TH1S* hChannel = GetChannel(det, ring, sec, strip,sample);
a31ea3ce 261 if(!hChannel || hChannel->GetEntries() == 0) {
7bce699b 262 //AliWarning(Form("No entries for FMD%d%c, sector %d, strip %d",
263 // det,ring,sec,strip));
264 return;
e9c06036 265 }
f7f0b643 266
3490bd31 267 AliDebugF(50, "Fitting FMD%d%c[%02d,%03d] with %d entries",
268 det,ring,sec,strip, int(hChannel->GetEntries()));
269 TF1* fitFunc = new TF1("fitFunc","gausn",0,300);
270 fitFunc->ResetBit(TObject::kMustCleanup);
271 fitFunc->SetParameters(100,100,1);
272 hChannel->Fit(fitFunc,"Q0","",10,200);
273 hChannel->GetListOfFunctions()->Remove(fitFunc);
7bce699b 274
275 Float_t mean = hChannel->GetMean();
276 Float_t rms = hChannel->GetRMS();
277
7bce699b 278 hChannel->GetXaxis()->SetRangeUser(mean-5*rms,mean+5*rms);
7bce699b 279 mean = hChannel->GetMean();
280 rms = hChannel->GetRMS();
93519ec4 281
7bce699b 282
283 UShort_t ddl, board, altro, channel;
284 UShort_t timebin;
285
5cf05dbb 286 pars->Detector2Hardware(det,ring,sec,strip,sample,
287 ddl,board,altro,channel,timebin);
288 Int_t idx = HWIndex(ddl, board, altro, channel);
289 if (idx >= 0) {
290 fMinTimebin[idx] = TMath::Min(Short_t(timebin), fMinTimebin[idx]);
291 fMaxTimebin[idx] = TMath::Max(Short_t(timebin+1), fMaxTimebin[idx]);
292 }
7bce699b 293
5cf05dbb 294 std::ostream* zsFile = 0;
7bce699b 295 switch(det) {
5cf05dbb 296 case 1: zsFile = &fZSfileFMD1; break;
297 case 2: zsFile = &fZSfileFMD2; break;
298 case 3: zsFile = &fZSfileFMD3; break;
299 default: AliWarning("Unknown sample!"); break;
7bce699b 300
301 }
5cf05dbb 302 *zsFile << board << ','
303 << altro << ','
304 << channel << ','
305 << timebin << ','
306 << mean << ','
276b1261 307 << rms << "\n";
7bce699b 308
309 Float_t chi2ndf = 0;
15e37b0a 310
311
3490bd31 312 if(fitFunc->GetNDF())
313 chi2ndf = fitFunc->GetChisquare() / fitFunc->GetNDF();
7bce699b 314
5cf05dbb 315
15e37b0a 316 Int_t sampleToWrite = 2;
5cf05dbb 317 if (samples == 2) sampleToWrite = 1;
318 else if (samples < 2) sampleToWrite = 0;
15e37b0a 319
a31ea3ce 320 hChannel->GetXaxis()->SetRange(1,1024);
321
5cf05dbb 322 if(sample != sampleToWrite) continue;
15e37b0a 323
15e37b0a 324
5cf05dbb 325 fOutputFile << det << ','
326 << ring << ','
327 << sec << ','
328 << strip << ','
329 << mean << ','
330 << rms << ','
3490bd31 331 << fitFunc->GetParameter(1) << ','
332 << fitFunc->GetParameter(2) << ','
5cf05dbb 333 << chi2ndf <<"\n";
2a082c96 334
3490bd31 335 delete fitFunc;
336
2a082c96 337 if (summary) {
338 Int_t bin = summary->FindBin(sec, strip);
339 summary->SetBinContent(bin, mean);
340 summary->SetBinError(bin, rms);
341 }
342
5cf05dbb 343 if(fSaveHistograms ) {
a31ea3ce 344 TH1F* sumPed = GetSectorSummary(det, ring, sec, true);
345 TH1F* sumNoise = GetSectorSummary(det, ring, sec, false);
5cf05dbb 346 sumPed->SetBinContent(strip+1, mean);
347 sumPed->SetBinError(strip+1, rms);
348 sumNoise->SetBinContent(strip+1, rms);
a31ea3ce 349
5cf05dbb 350 fPedSummary.SetBinContent(fCurrentChannel,mean);
5cf05dbb 351 fNoiseSummary.SetBinContent(fCurrentChannel,rms);
352 fCurrentChannel++;
7bce699b 353 }
354 }
3bd993ba 355}
356
357//_____________________________________________________________________
f7f0b643 358void AliFMDPedestalDA::Terminate(TFile* diagFile)
359{
5cf05dbb 360 // Called at the end of a job. Fills in missing time-bins and
361 // closes output files
a31ea3ce 362 if(fSaveHistograms && diagFile) {
7bce699b 363 diagFile->cd();
364
365 fPedSummary.Write();
366 fNoiseSummary.Write();
367 }
5cf05dbb 368 AliFMDAltroMapping* map = AliFMDParameters::Instance()->GetAltroMap();
276b1261 369 for (Int_t i = 0; i < 3; i++) {
370 std::ofstream& out = (i == 0 ? fZSfileFMD1 :
371 i == 1 ? fZSfileFMD2 :
372 fZSfileFMD3);
373 if (out.is_open() && fSeenDetectors[i]) {
374 FillinTimebins(out, map->Detector2DDL(i+1));
375 }
408bf2b4 376 if (!fSeenDetectors[i]) {
377 TString n(Form("ddl%d.csv",3072+map->Detector2DDL(i+1)));
378 gSystem->Unlink(n.Data());
379 }
380 }
f7f0b643 381
5cf05dbb 382}
383
384//_____________________________________________________________________
7af3df7f 385void AliFMDPedestalDA::FillinTimebins(std::ofstream& out, UShort_t /*ddl*/)
5cf05dbb 386{
45cffd06 387 //
388 // Fill missing timebins
389 //
762e54b7 390#if 0
5cf05dbb 391 unsigned short boards[] = { 0x0, 0x1, 0x10, 0x11, 0xFFFF };
392 unsigned short* board = boards;
393 while ((*boards) != 0xFFFF) {
394 for (UShort_t altro = 0; altro < 3; altro++) {
395 for (UShort_t channel = 0; channel < 16; channel++) {
396 Int_t idx = HWIndex(ddl, *board, altro, channel);
397 if (idx < 0) {
3490bd31 398 AliWarningF("Invalid index for %4d/0x%02x/0x%x/0x%x: %d",
399 ddl, *board, altro, channel, idx);
5cf05dbb 400 continue;
401 }
402 Short_t min = fMinTimebin[idx];
403 Short_t max = fMaxTimebin[idx];
404
405 // Channel not seen at all.
406 if (min > 1023 || max < 0) continue;
407
408 out << "# Extra timebins for 0x" << std::hex
409 << board << ',' << altro << ',' << channel
410 << " got time-bins " << min << " to " << max-1
411 << std::dec << std::endl;
412
413 for (UShort_t t = 15; t < min; t++)
414 // Write a phony line
415 out << board << "," << altro << "," << channel << ","
416 << t << "," << 1023 << "," << 0 << std::endl;
417
418 for (UShort_t t = max; t < 1024; t++)
419 // Write a phony line
420 out << board << "," << altro << "," << channel << ","
421 << t << "," << 1023 << "," << 0 << std::endl;
422 } // channel loop
423 } // altro loop
424 } // board loop
425 // Write trailer, and close
762e54b7 426#endif
5cf05dbb 427 out.write("# EOF\n", 6);
428 out.close();
f7f0b643 429}
430
431//_____________________________________________________________________
e9c06036 432void AliFMDPedestalDA::WriteHeaderToFile()
433{
45cffd06 434 //
5cf05dbb 435 // Write headers to output files
45cffd06 436 //
80fdb9f3 437 AliFMDParameters* pars = AliFMDParameters::Instance();
438 fOutputFile.write(Form("# %s \n",pars->GetPedestalShuttleID()),13);
6cf6e7a0 439 TDatime now;
440 fOutputFile << "# This file created from run # " << fRunno
441 << " @ " << now.AsString() << std::endl;
f7f0b643 442 fOutputFile.write("# Detector, "
443 "Ring, "
444 "Sector, "
e9c06036 445 "Strip, "
e9c06036 446 "Pedestal, "
447 "Noise, "
448 "Mu, "
449 "Sigma, "
f7f0b643 450 "Chi2/NDF \n", 71);
5cf05dbb 451
452 std::ostream* zss[] = { &fZSfileFMD1, &fZSfileFMD2, &fZSfileFMD3, 0 };
6cf6e7a0 453 for (size_t i = 0; i < 3; i++) {
454 *(zss[i]) << "# FMD " << (i+1) << " pedestals \n"
5cf05dbb 455 << "# board, "
456 << "altro, "
457 << "channel, "
458 << "timebin, "
459 << "pedestal, "
762e54b7 460 << "noise\n";
6cf6e7a0 461 *(zss[i]) << "# This file created from run # " << fRunno
462 << " @ " << now.AsString() << std::endl;
463 }
3bd993ba 464}
465
466//_____________________________________________________________________
e9c06036 467TH1S* AliFMDPedestalDA::GetChannel(UShort_t det,
468 Char_t ring,
469 UShort_t sec,
7bce699b 470 UShort_t strip,
5cf05dbb 471 UInt_t sample)
e9c06036 472{
5cf05dbb 473 // Get the histogram corresponding to a strip sample.
474 //
475 // Parameters:
476 // det Detector
477 // ring Ring
478 // sec Sector
479 // strip Strip
480 // sample Sample
481 //
482 // Return:
483 // ADC spectra of a strip.
3490bd31 484 Array* sampleArray = GetStripArray(det, ring, sec, strip);
a31ea3ce 485 if (!sampleArray) return 0;
5cf05dbb 486 TH1S* hSample = static_cast<TH1S*>(sampleArray->At(sample));
a31ea3ce 487 if (!hSample) {
488 AliErrorF("No channel histogram for FMD%d%c[%02d,%03d]_%d",
489 det, ring, sec, strip, sample);
490 sampleArray->ls();
491 AliErrorF("Path is %s <- %s <- %s <- %s",
492 sampleArray->GetName(),
493 GetSectorArray(det, ring, sec)->GetName(),
494 GetRingArray(det, ring)->GetName(),
495 GetDetectorArray(det)->GetName());
496
497 }
e9c06036 498 return hSample;
7bce699b 499
3bd993ba 500}
a31ea3ce 501//_____________________________________________________________________
502TH1F* AliFMDPedestalDA::GetSectorSummary(UShort_t det,
503 Char_t ring,
504 UShort_t sec,
505 Bool_t pedNotNoise)
506{
3490bd31 507 Array* secArray = GetSectorArray(det, ring, sec);
a31ea3ce 508 Int_t n = secArray->GetEntriesFast();
509 Int_t i = n - (pedNotNoise ? kNoiseOffset : kPedestalOffset);
510 return static_cast<TH1F*>(secArray->At(i));
511}
93519ec4 512
3bd993ba 513//_____________________________________________________________________
514//
515//EOF
516//