8 #include "StTpcdEdxCorrection.h"
9 #include "StTpcDb/StTpcDb.h"
10 #include "StBichsel/Bichsel.h"
11 #include "StMessMgr.h"
12 #include "St_db_Maker/St_db_Maker.h"
13 #include "TUnixTime.h"
15 #include "StDetectorDbMaker/St_tss_tssparC.h"
16 #include "StDetectorDbMaker/St_TpcEdgeC.h"
17 #include "StDetectorDbMaker/St_TpcAdcCorrectionBC.h"
18 #include "StDetectorDbMaker/St_TpcAdcCorrectionCC.h"
19 #include "StDetectorDbMaker/St_TpcAdcCorrectionMDF.h"
20 #include "StDetectorDbMaker/St_TpcAdcCorrection3MDF.h"
21 #include "StDetectorDbMaker/St_TpcAdcCorrection4MDF.h"
22 #include "StDetectorDbMaker/St_TpcAdcCorrection5MDF.h"
23 #include "StDetectorDbMaker/St_TpcAdcCorrection6MDF.h"
24 #include "StDetectorDbMaker/St_TpcdChargeC.h"
25 #include "StDetectorDbMaker/St_TpcrChargeC.h"
26 #include "StDetectorDbMaker/St_TpcCurrentCorrectionC.h"
27 #include "StDetectorDbMaker/St_TpcRowQC.h"
28 #include "StDetectorDbMaker/St_TpcAccumulatedQC.h"
29 #include "StDetectorDbMaker/St_TpcSecRowBC.h"
30 #include "StDetectorDbMaker/St_TpcSecRowCC.h"
31 #include "StDetectorDbMaker/St_tpcPressureBC.h"
32 #include "StDetectorDbMaker/St_TpcDriftDistOxygenC.h"
33 #include "StDetectorDbMaker/St_TpcMultiplicityC.h"
34 #include "StDetectorDbMaker/St_TpcZCorrectionBC.h"
35 #include "StDetectorDbMaker/St_TpcZCorrectionCC.h"
36 #include "StDetectorDbMaker/St_tpcMethaneInC.h"
37 #include "StDetectorDbMaker/St_tpcGasTemperatureC.h"
38 #include "StDetectorDbMaker/St_tpcWaterOutC.h"
39 #include "StDetectorDbMaker/St_TpcSpaceChargeC.h"
40 #include "StDetectorDbMaker/St_TpcPhiDirectionC.h"
41 #include "StDetectorDbMaker/St_TpcTanLC.h"
42 #include "StDetectorDbMaker/St_TpcAdcIC.h"
43 #include "StDetectorDbMaker/St_TpcnPadC.h"
44 #include "StDetectorDbMaker/St_TpcnTbkC.h"
45 #include "StDetectorDbMaker/St_TpcdZdYC.h"
46 #include "StDetectorDbMaker/St_TpcdXdYC.h"
47 #include "StDetectorDbMaker/St_TpcdXCorrectionBC.h"
48 #include "StDetectorDbMaker/St_TpcEtaCorrectionC.h"
49 #include "StDetectorDbMaker/St_TpcEtaCorrectionBC.h"
50 #include "StDetectorDbMaker/St_TpcEffectivedXC.h"
51 #include "StDetectorDbMaker/St_TpcZDCC.h"
52 #include "StDetectorDbMaker/St_TpcLengthCorrectionBC.h"
53 #include "StDetectorDbMaker/St_TpcLengthCorrectionMDF.h"
54 #include "StDetectorDbMaker/St_TpcLengthCorrectionMD2.h"
55 #include "StDetectorDbMaker/St_TpcLengthCorrectionMDN.h"
56 #include "StDetectorDbMaker/St_TpcPadCorrectionMDF.h"
57 #include "StDetectorDbMaker/St_TpcPadCorrectionMDC.h"
58 #include "StDetectorDbMaker/St_TpcdEdxCorC.h"
59 #include "StDetectorDbMaker/St_tpcAnodeHVavgC.h"
60 #include "StDetectorDbMaker/St_TpcAvgCurrentC.h"
61 #include "StDetectorDbMaker/St_TpcAvgPowerSupplyC.h"
62 #include "StDetectorDbMaker/St_tpcTimeDependenceC.h"
63 #include "StDetectorDbMaker/St_trigDetSumsC.h"
64 #include "StDetectorDbMaker/St_beamInfoC.h"
65 #include "StDetectorDbMaker/St_starTriggerDelayC.h"
67 StTpcdEdxCorrection::StTpcdEdxCorrection(Int_t option, Int_t debug) :
68 m_Mask(option), m_tpcGas(0),
69 m_Debug(debug), m_IsSimulation(kFALSE)
72 if (!m_Mask) m_Mask = -1;
73 static const Char_t *FXTtables[] = {
"TpcAdcCorrectionB",
77 "TpcAdcCorrection6MDF",
78 "TpcAdcCorrection5MDF",
79 "TpcAdcCorrection4MDF",
80 "TpcAdcCorrection3MDF",
83 "TpcCurrentCorrection",
105 "TpcPadCorrectionMDF",
106 "TpcPadCorrectionMDC",
112 "TpcLengthCorrectionB",
113 "TpcLengthCorrectionMDF",
114 "TpcLengthCorrectionMD2",
115 "TpcLengthCorrectionMDN",
117 static Int_t NT =
sizeof(FXTtables)/
sizeof(
const Char_t *);
118 m_isFixedTarget = St_beamInfoC::instance()->IsFixedTarget();
119 TString flavor(
"sim+ofl");
120 #ifdef __TFG__VERSION__
123 if (m_isFixedTarget) flavor +=
"+FXT";
125 for (Int_t i = 0; i < NT; i++) {
126 dbMk->SetFlavor(flavor, FXTtables[i]);
131 void StTpcdEdxCorrection::ReSetCorrections() {
132 St_tpcGas *tpcGas = (St_tpcGas *) St_tpcGasC::instance()->Table();
134 if (!tpcGas || ! tpcGas->GetNRows()) {
135 LOG_ERROR <<
"=== tpcGas is missing ===" << endm;
139 mTimeBinWidth = 1./StTpcDb::instance()->Electronics()->samplingFrequency();
140 mInnerSectorzOffset = StTpcDb::instance()->Dimensions()->zInnerOffset();
141 mOuterSectorzOffset = StTpcDb::instance()->Dimensions()->zOuterOffset();
142 Double_t trigT0 = 0, elecT0 = 0;
143 if (! St_starTriggerDelayC::instance()->Table()->IsMarked()) {
144 trigT0 = St_starTriggerDelayC::instance()->clocks()*mTimeBinWidth;
145 elecT0 = St_starTriggerDelayC::instance()->tZero();
147 trigT0 = StTpcDb::instance()->triggerTimeOffset()*1e6;
148 elecT0 = StTpcDb::instance()->Electronics()->tZero();
150 m_TrigT0 = trigT0 + elecT0;
153 m_Corrections[kAdcCorrection ] =
dEdxCorrection_t(
"TpcAdcCorrectionB" ,
"ADC/Clustering nonlinearity correction" ,St_TpcAdcCorrectionBC::instance());
154 m_Corrections[kAdcCorrectionC ] =
dEdxCorrection_t(
"TpcAdcCorrectionC" ,
"alternative ADC/Clustering nonlinearity correction" ,St_TpcAdcCorrectionCC::instance());
155 m_Corrections[kEdge ] =
dEdxCorrection_t(
"TpcEdge" ,
"Gain on distance from Chamber edge" ,St_TpcEdgeC::instance());
156 m_Corrections[kAdcCorrectionMDF ] =
dEdxCorrection_t(
"TpcAdcCorrectionMDF" ,
"ADC/Clustering nonlinearity correction MDF" ,St_TpcAdcCorrectionMDF::instance());
162 m_Corrections[kAdcCorrection6MDF ] =
dEdxCorrection_t(
"TpcAdcCorrection6MDF",
"alternative ADC/Clustering nonlinearity correction MDF+4D" ,St_TpcAdcCorrection6MDF::instance());
163 m_Corrections[kTpcdCharge ] =
dEdxCorrection_t(
"TpcdCharge" ,
"ADC/Clustering undershoot correction" ,St_TpcdChargeC::instance());
167 m_Corrections[kTpcCurrentCorrection ] =
dEdxCorrection_t(
"TpcCurrentCorrection",
"Correction due to sagg of Voltage due to anode current" ,St_TpcCurrentCorrectionC::instance());
168 m_Corrections[kTpcRowQ ] =
dEdxCorrection_t(
"TpcRowQ" ,
"Gas gain correction for row versus accumulated charge," ,St_TpcRowQC::instance());
169 m_Corrections[kTpcAccumulatedQ ] =
dEdxCorrection_t(
"TpcAccumulatedQ" ,
"Gas gain correction for HV channel versus accumulated charge," ,St_TpcAccumulatedQC::instance());
170 m_Corrections[kTpcSecRowB ] =
dEdxCorrection_t(
"TpcSecRowB" ,
"Gas gain correction for sector/row" ,St_TpcSecRowBC::instance());
174 m_Corrections[ktpcPressure ] =
dEdxCorrection_t(
"tpcPressureB" ,
"Gain on Gas Density due to Pressure" ,St_tpcPressureBC::instance());
175 m_Corrections[ktpcTime ] =
dEdxCorrection_t(
"tpcTime" ,
"Unregognized time dependce" ,St_tpcTimeDependenceC::instance());
176 m_Corrections[kDrift ] =
dEdxCorrection_t(
"TpcDriftDistOxygen" ,
"Correction for Electron Attachment due to O2" ,St_TpcDriftDistOxygenC::instance());
177 m_Corrections[kMultiplicity ] =
dEdxCorrection_t(
"TpcMultiplicity" ,
"Global track multiplicity dependence" ,St_TpcMultiplicityC::instance());
178 m_Corrections[kzCorrectionC ] =
dEdxCorrection_t(
"TpcZCorrectionC" ,
"Variation on drift distance with Gating Grid one" ,St_TpcZCorrectionCC::instance());
179 m_Corrections[kzCorrection ] =
dEdxCorrection_t(
"TpcZCorrectionB" ,
"Variation on drift distance without Gating Gird one" ,St_TpcZCorrectionBC::instance());
183 m_Corrections[ktpcGasTemperature ] =
dEdxCorrection_t(
"tpcGasTemperature" ,
"Gain on Gas Dens. due to Output (T5) Temperature" ,St_tpcGasTemperatureC::instance());
188 m_Corrections[kPhiDirection ] =
dEdxCorrection_t(
"TpcPhiDirection" ,
"Gain on interception angle" ,St_TpcPhiDirectionC::instance());
189 m_Corrections[kTanL ] =
dEdxCorrection_t(
"TpcTanL" ,
"Gain on Tan(lambda)" ,St_TpcTanLC::instance());
190 m_Corrections[kdXCorrection ] =
dEdxCorrection_t(
"TpcdXCorrectionB" ,
"dX correction" ,St_TpcdXCorrectionBC::instance());
191 m_Corrections[kEtaCorrection ] =
dEdxCorrection_t(
"TpcEtaCorrection" ,
"Eta correction MC" ,St_TpcEtaCorrectionC::instance());
192 m_Corrections[kEtaCorrectionB ] =
dEdxCorrection_t(
"TpcEtaCorrectionB" ,
"Eta correction RC" ,St_TpcEtaCorrectionBC::instance());
193 m_Corrections[kTpcEffectivedX ] =
dEdxCorrection_t(
"TpcEffectivedX" ,
"dEdx correction wrt Bichsel parameterization" ,St_TpcEffectivedXC::instance());
194 m_Corrections[kTpcPadTBins ] =
dEdxCorrection_t(
"TpcPadTBins" ,
"Variation on cluster size" ,0);
195 m_Corrections[kTpcZDC ] =
dEdxCorrection_t(
"TpcZDC" ,
"Gain on Zdc CoincidenceRate" ,St_TpcZDCC::instance());
196 m_Corrections[kTpcPadMDF ] =
dEdxCorrection_t(
"TpcPadCorrectionMDF" ,
"Gain Variation along the anode wire" ,St_TpcPadCorrectionMDF::instance());
197 m_Corrections[kTpcPadMDC ] =
dEdxCorrection_t(
"TpcPadCorrectionMDC" ,
"Gain Variation along the anode wire with track curvature" ,St_TpcPadCorrectionMDC::instance());
201 m_Corrections[knPad ] =
dEdxCorrection_t(
"TpcnPad" ,
"Gain on cluster length in pads" ,St_TpcnPadC::instance());
202 m_Corrections[knTbk ] =
dEdxCorrection_t(
"TpcnTbk" ,
"Gain on cluster length in time buckets" ,St_TpcnTbkC::instance());
208 m_Corrections[kTpcLengthCorrection ] =
dEdxCorrection_t(
"TpcLengthCorrectionB" ,
"Variation vs Track length and relative error in Ionization" ,St_TpcLengthCorrectionBC::instance());
209 m_Corrections[kTpcLengthCorrectionMDF] =
dEdxCorrection_t(
"TpcLengthCorrectionMDF",
"Variation vs Track length and <log2(dX)> and rel. error in dE/dx" ,St_TpcLengthCorrectionMDF::instance());
210 m_Corrections[kTpcLengthCorrectionMD2] =
dEdxCorrection_t(
"TpcLengthCorrectionMD2",
"Variation vs Track length and <log2(dX)> for pred. with fixed dx2",St_TpcLengthCorrectionMD2::instance());
211 m_Corrections[kTpcLengthCorrectionMDN] =
dEdxCorrection_t(
"TpcLengthCorrectionMDN",
"Variation vs Track length and <log2(dX)> for pred. with fixed dx2",St_TpcLengthCorrectionMDN::instance());
212 m_Corrections[kTpcNoAnodeVGainC ] =
dEdxCorrection_t(
"TpcNoAnodeVGainC" ,
"Remove tpc Anode Voltage gain correction" ,0);
213 m_Corrections[kTpcdEdxCor ] =
dEdxCorrection_t(
"TpcdEdxCor" ,
"dEdx correction wrt Bichsel parameterization" ,St_TpcdEdxCorC::instance());
224 for (k = kUncorrected+1; k < kTpcAllCorrections; k++) {
225 if (! m_Corrections[k].Chair)
continue;
226 CommentLine = Form(
"StTpcdEdxCorrection: %24s/%66s",m_Corrections[k].Name,m_Corrections[k].Title);
227 table = m_Corrections[k].Chair->Table();
228 if (! table)
continue;
229 if (Debug() > 2) table->
Print(0,10);
230 if (! TESTBIT(m_Mask,k) || m_Corrections[k].Chair->Table()->IsMarked()) {
231 CommentLine +=
" \tis missing";
233 SafeDelete(m_Corrections[k].Chair);
235 LOG_WARN << CommentLine.Data() << endm;
239 if (St_db_Maker::GetValidity(table,t) > 0) {
240 CommentLine += Form(
"\tValidity:%08i.%06i --- %08i.%06i",t[0].GetDate(),t[0].GetTime(),t[1].GetDate(),t[1].GetTime());
247 if (chair ) { npar = chair ->IsActiveChair();
248 }
else if (chairMDF ) { npar = chairMDF ->IsActiveChair();
249 }
else if (chair3MDF) { npar = chair3MDF->IsActiveChair();
250 }
else if (chair4MDF) { npar = chair4MDF->IsActiveChair();
252 chairSecRow =
dynamic_cast<const St_TpcSecRowCorC *
>(m_Corrections[k].Chair);
254 if (! chairSecRow && ! chairEffectivedX) {
255 CommentLine +=
"\tis not tpcCorrection, MDFCorrection, TpcEffectivedX, TpcEffectivedX, or TpcSecRowCor types";
258 LOG_WARN << CommentLine.Data() << endm;
263 CommentLine +=
" \thas no significant corrections => switch it off \tIt is cleaned";
265 SafeDelete(m_Corrections[k].Chair);
267 LOG_WARN << CommentLine.Data() << endm;
271 LOG_WARN << CommentLine.Data() << endm;
274 if ( m_Corrections[kzCorrectionC].Chair) {
275 vector<Int_t> kvect = {kzCorrection};
276 for (
auto k : kvect) {
277 if (m_Corrections[k].Chair) {
278 LOG_WARN << m_Corrections[kzCorrectionC].Name <<
" is already active => disable " << m_Corrections[k].Name << endm;
280 SafeDelete(m_Corrections[k].Chair);
285 Int_t PriorityList[] = { kAdcCorrection6MDF, kAdcCorrection5MDF, kAdcCorrection4MDF, kAdcCorrection3MDF, kAdcCorrectionMDF, kAdcCorrectionC, kAdcCorrection};
287 for (
auto k : PriorityList) {
289 if (! m_Corrections[k].Chair)
continue;
291 for (
auto x : PriorityList) {
293 if (j <= i)
continue;
294 if (! m_Corrections[x].Chair)
continue;
295 if (x == k)
continue;
296 if (k == kAdcCorrection6MDF && x == kAdcCorrectionC) {
297 assert(m_Corrections[x].Chair);
300 LOG_WARN <<
"With" << m_Corrections[k].Name <<
" activated => Deactivate " << m_Corrections[x].Name << endm;
302 SafeDelete(m_Corrections[x].Chair);
306 Int_t PriorityListL[] = {kTpcLengthCorrectionMDN,kTpcLengthCorrectionMD2, kTpcLengthCorrectionMDF, kTpcLengthCorrection};
308 for (
auto k : PriorityListL) {
310 if (! m_Corrections[k].Chair)
continue;
312 for (
auto x : PriorityListL) {
314 if (j <= i)
continue;
315 if (! m_Corrections[x].Chair)
continue;
316 if (x == k)
continue;
317 LOG_WARN <<
"With " << m_Corrections[k].Name <<
" activated => Deactivate " << m_Corrections[x].Name << endm;
319 SafeDelete(m_Corrections[x].Chair);
323 Int_t PriorityListP[] = {kTpcPadMDC, kTpcPadMDF};
325 for (
auto k : PriorityListP) {
327 if (! m_Corrections[k].Chair)
continue;
329 for (
auto x : PriorityListP) {
331 if (j <= i)
continue;
332 if (! m_Corrections[x].Chair)
continue;
333 if (x == k)
continue;
334 LOG_WARN <<
"With " << m_Corrections[k].Name <<
" activated => Deactivate " << m_Corrections[x].Name << endm;
336 SafeDelete(m_Corrections[x].Chair);
341 StTpcdEdxCorrection::~StTpcdEdxCorrection() {
346 Int_t StTpcdEdxCorrection::dEdxCorrection(
dEdxY2_t &CdEdx, Bool_t doIT) {
349 if (CdEdx.F.dE <= 0.) CdEdx.F.dE = 1;
350 Double_t dEU = CdEdx.F.dE;
352 Int_t sector = CdEdx.sector;
353 Int_t row = CdEdx.row;
354 Double_t dxC = CdEdx.F.dx;
356 Double_t adcCF = CdEdx.adc;
358 if (dxC <= 0 || (dEU <= 0 && adcCF <= 0)) {
362 Int_t channel = St_TpcAvgPowerSupplyC::instance()->ChannelFromRow(sector,row);
363 CdEdx.channel = channel;
365 CdEdx.Voltage = St_tpcAnodeHVavgC::instance()->voltagePadrow(sector,row);
366 CdEdx.Crow = St_TpcAvgCurrentC::instance()->AvCurrRow(sector,row);
367 Double_t Qcm = St_TpcAvgCurrentC::instance()->AcChargeRowL(sector,row);
369 TUnixTime u(StMaker::GetChain()->GetDateTime(), kTRUE);
370 if (! St_trigDetSumsC::GetInstance()) {
371 StMaker::GetChain()->
AddData(St_trigDetSumsC::instance());
374 if ( ! St_trigDetSumsC::instance() ) {LOG_ERROR <<
"StTpcdEdxCorrection::dEdxCorrection Cannot find trigDetSums" << endm;}
376 if (!St_trigDetSumsC::instance()->GetNRows()) {LOG_ERROR <<
"StTpcdEdxCorrection::dEdxCorrection trigDetSums has not data" << endm;}
378 TUnixTime u2(St_trigDetSumsC::instance()->timeOffset());
379 if (u() + 30 < u2()) {
380 LOG_ERROR <<
"StTpcdEdxCorrection::dEdxCorrection Illegal time for scalers = "
381 << u2() <<
"/" << u()
382 <<
" Run " << St_trigDetSumsC::instance()->runNumber() <<
"/" << StMaker::GetChain()->
GetRunNumber() << endm;
389 if (St_TpcAvgPowerSupplyC::instance()->run() > 0) {
390 TUnixTime u2(St_trigDetSumsC::instance()->timeOffset()+5*3600);
391 if (u2() < u() + 30) {
392 LOG_ERROR <<
"StTpcdEdxCorrection::dEdxCorrection Illegal TpcAvgPowerSupply stop time = " << u2() <<
" GMT from local " << u2.GetGString()
393 <<
" < event time = " << u() <<
" GMT\t=" << StMaker::GetChain()->GetDateTime().AsString() << endm;
400 Double_t ZdriftDistance = CdEdx.ZdriftDistance;
401 ESector kTpcOutIn = kTpcOuter;
403 Float_t gainNominal = 0;
405 if (row <= St_tpcPadConfigC::instance()->innerPadRows(sector)) {
406 kTpcOutIn = kTpcInner;
407 gainNominal = tsspar->gain_in()*tsspar->wire_coupling_in();
408 gasGain = tsspar->gain_in(sector,row) *tsspar->wire_coupling_in();
410 kTpcOutIn = kTpcOuter;
411 gainNominal = tsspar->gain_out()*tsspar->wire_coupling_out();
412 gasGain = tsspar->gain_out(sector,row)*tsspar->wire_coupling_out();
414 if (St_tpcPadConfigC::instance()->iTpc(sector) && row <= St_tpcPadConfigC::instance()->innerPadRows(sector)) kTpcOutIn = kiTpc;
415 if (gasGain <= 0.0) {
419 CdEdx.driftTime = ZdriftDistance/gStTpcDb->DriftVelocity(sector)*1e6 - m_TrigT0;
421 mAdc2GeV = tsspar->ave_ion_pot() * tsspar->scale()/gainNominal;
422 Double_t Adc2GeVReal = tsspar->ave_ion_pot() * tsspar->scale()/gasGain;
423 tpcGas_st *gas = m_tpcGas->GetTable();
424 Double_t ZdriftDistanceO2 = ZdriftDistance*(*m_tpcGas)[0].ppmOxygenIn;
425 Double_t ZdriftDistanceO2W = ZdriftDistanceO2*(*m_tpcGas)[0].ppmWaterOut;
426 CdEdx.ZdriftDistanceO2 = ZdriftDistanceO2;
427 CdEdx.ZdriftDistanceO2W = ZdriftDistanceO2W;
428 Double_t gc, ADC = 0, xL2, dXCorr;
431 Double_t VarXs[kTpcLast] = {-999.};
432 VarXs[kAdcCorrection] = adcCF;
433 VarXs[kEdge] = TMath::Abs(CdEdx.edge);
434 VarXs[kAdcCorrectionMDF] = adcCF;
435 VarXs[kTpcrCharge] = CdEdx.rCharge;
436 VarXs[kTpcCurrentCorrection] = CdEdx.Crow;
437 VarXs[kTpcRowQ] = CdEdx.Qcm;
438 VarXs[kTpcAccumulatedQ] = CdEdx.Qcm;
439 VarXs[ktpcPressure] = TMath::Log(gas->barometricPressure);
440 VarXs[ktpcTime] = CdEdx.tpcTime;
441 VarXs[kDrift] = ZdriftDistanceO2;
442 VarXs[kMultiplicity] = CdEdx.QRatio;
443 VarXs[kGatingGrid] = CdEdx.driftTime;
444 VarXs[kzCorrectionC] = ZdriftDistance;
445 VarXs[kzCorrection] = ZdriftDistance;
446 VarXs[ktpcMethaneIn] = gas->percentMethaneIn*1000./gas->barometricPressure;
447 VarXs[ktpcGasTemperature] = gas->outputGasTemperature;
448 VarXs[ktpcWaterOut] = gas->ppmWaterOut;
449 VarXs[kPhiDirection] = (TMath::Abs(CdEdx.xyzD[0]) > 1.e-7) ? TMath::Abs(CdEdx.xyzD[1]/CdEdx.xyzD[0]) : 999.;
450 VarXs[kTanL] = CdEdx.TanL;
451 VarXs[kTpcPadTBins] = CdEdx.Npads*CdEdx.Ntbks;
452 VarXs[kTpcZDC] = (CdEdx.Zdc > 0) ? TMath::Log10(CdEdx.Zdc) : 0;
453 VarXs[kAdcI] = CdEdx.AdcI;
454 VarXs[knPad] = CdEdx.Npads;
455 VarXs[knTbk] = CdEdx.Ntbks;
456 VarXs[kdZdY] = CdEdx.dZdY;
457 VarXs[kdXdY] = CdEdx.dXdY;
458 VarXs[kEtaCorrection] = CdEdx.etaG*CdEdx.etaG;
459 VarXs[kEtaCorrectionB] = CdEdx.etaG;
462 for (Int_t k = kUncorrected; k <= kTpcLast; k++) {
464 tpcCorrection_st *cor = 0;
465 tpcCorrection_st *corl = 0;
467 if (CdEdx.lSimulated) {
468 if (k == kAdcCorrection) dE *= 2.116;
471 if (! TESTBIT(m_Mask, k))
goto ENDL;
472 if (! m_Corrections[k].Chair)
goto ENDL;
474 if (k == kTpcSecRowB || k == kTpcSecRowC ) {
475 const St_TpcSecRowCor *table = (
const St_TpcSecRowCor *) m_Corrections[k].Chair->Table();
476 if (! table)
goto ENDL;
477 const TpcSecRowCor_st *gain = table->GetTable() + sector - 1;
478 gc = gain->GainScale[row-1];
486 if (gain->GainRms[row-1] > 0.1) CdEdx.Weight = 1./(gain->GainRms[row-1]*gain->GainRms[row-1]);
488 }
else if (k == kTpcEffectivedX) {
489 if (kTpcOutIn == kTpcOuter) dxC *= ((
const St_TpcEffectivedXC* ) m_Corrections[k].Chair)->scaleOuter();
490 else if (kTpcOutIn == kTpcInner ||
491 kTpcOutIn == kiTpc ) dxC *= ((
const St_TpcEffectivedXC* ) m_Corrections[k].Chair)->scaleInner();
493 }
else if (k == kTpcPadMDF) {
495 if (row <= St_tpcPadConfigC::instance()->innerPadRows(sector)) l += kTpcInner;
496 dE *= TMath::Exp(-((
St_MDFCorrectionC *)m_Corrections[k].Chair)->Eval(l,CdEdx.yrow,CdEdx.xpad));
498 }
else if (k == kTpcPadMDC) {
501 if (nrows > 48 && qB) l += 48*qB;
502 if (row <= St_tpcPadConfigC::instance()->innerPadRows(sector)) l += kTpcInner;
503 dE *= TMath::Exp(-((
St_MDFCorrectionC *)m_Corrections[k].Chair)->Eval(l,CdEdx.yrow+24*qB,CdEdx.xpadR));
505 }
else if (k == kAdcCorrectionMDF) {
512 if (l >= nrows) l = nrows - 1;
513 Double_t xx[2] = {TMath::Log(ADC), (Double_t)(CdEdx.Npads+CdEdx.Ntbks)};
515 dE = ADC*Adc2GeVReal*TMath::Exp(Cor);
517 }
else if (k == kAdcCorrection3MDF) {
524 if (l >= nrows) l = nrows - 1;
525 Double_t xx[3] = {(Double_t) CdEdx.Ntbks, TMath::Abs(CdEdx.zG), TMath::Log(ADC)};
527 dE = ADC*Adc2GeVReal*TMath::Exp(Cor);
529 }
else if (k == kAdcCorrection4MDF) {
536 if (l >= nrows) l = nrows - 1;
537 Double_t xx[4] = {(Double_t) CdEdx.Ntbks, (Double_t) CdEdx.Npads, TMath::Abs(CdEdx.zG), TMath::Log(ADC)};
539 dE = ADC*Adc2GeVReal*TMath::Exp(Cor);
541 }
else if (k == kAdcCorrection5MDF) {
544 if (l >= nrows) l = nrows - 1;
545 Double_t xx[4] = {(Double_t) CdEdx.Ntbks, (Double_t) CdEdx.Npads, TMath::Abs(CdEdx.zG), TMath::Log(ADC)};
547 dE *= TMath::Exp(Cor);
549 }
else if (k == kAdcCorrection6MDF) {
552 cor = ((St_tpcCorrection *) m_Corrections[k].Chair->Table())->GetTable();
553 if (! cor)
goto ENDL;
554 NLoops = cor->type/100000 + 1;
555 nrows = cor->nrows/NLoops;
557 l = TMath::Min(nrows-1, kTpcOutIn);
559 if (nrows == St_tpcPadConfigC::instance()->numberOfRows(sector)) l = row - 1;
560 else if (nrows == 192) {l = 8*(sector-1) + channel - 1; assert(l == (cor+l)->idx-1);}
561 else if (nrows == 8) {l = channel - 1; assert(l == (cor+l)->idx-1);}
562 else if (nrows == 48) {l = 2*(sector-1) + kTpcOutIn;}
563 else if (nrows == 6) {l = kTpcOutIn;
if (sector > 12) l+= 3;}
564 else if (nrows == 4) {l = TMath::Min(kTpcOutIn, 1);
if (sector > 12) l+= 2;}
568 if (k == kAdcCorrection) {
573 if (corl->type == 12)
574 dE = Adc2GeVReal*chairC->CalcCorrection(l,ADC,VarXs[kTanL]);
576 dE = Adc2GeVReal*chairC->CalcCorrection(l,ADC,TMath::Abs(CdEdx.zG));
581 }
else if (k == kAdcCorrection6MDF) {
583 }
else if (k == kAdcCorrectionC) {
588 ADC = chairC->CalcCorrection(l,adcCF);
589 if (m_Corrections[kAdcCorrection6MDF].Chair) {
590 Double_t xx[4] = {(Double_t) CdEdx.Ntbks, (Double_t) CdEdx.Npads, TMath::Abs(CdEdx.zG), TMath::Log(adcCF)};
593 dE = Adc2GeVReal*ADC;
595 }
else if (k == kTpcdCharge) {
597 slope = chairC->CalcCorrection(l,row+0.5);
598 dE *= TMath::Exp(-slope*CdEdx.dCharge);
599 dE *= TMath::Exp(-chairC->CalcCorrection(2+l,CdEdx.dCharge));
601 }
else if (k == kdXCorrection) {
602 xL2 = TMath::Log2(dxC);
603 dXCorr = chairC->CalcCorrection(l,xL2);
604 if (TMath::Abs(dXCorr) > 10) {
608 dXCorr += chairC->CalcCorrection(2,xL2);
609 dXCorr += chairC->CalcCorrection(5+kTpcOutIn,xL2);
611 dxC = TMath::Exp(dXCorr)*CdEdx.F.dx;
613 dE *= TMath::Exp(-dXCorr);
615 }
else if (k == kSpaceCharge) {
616 if (cor[2*l ].min <= CdEdx.QRatio && CdEdx.QRatio <= cor[2*l ].max &&
617 cor[2*l+1].min <= CdEdx.DeltaZ && CdEdx.DeltaZ <= cor[2*l+1].max)
618 dE *= TMath::Exp(-chairC->CalcCorrection(2*l ,CdEdx.QRatio)
619 -chairC->CalcCorrection(2*l+1,CdEdx.DeltaZ));
621 }
else if (k == ktpcTime) {
622 if (corl->min >= corl->max || corl->min > VarXs[ktpcTime] || VarXs[ktpcTime] > corl->max)
goto ENDL;
623 Double_t xx = VarXs[ktpcTime];
624 dE *= TMath::Exp(-chairC->CalcCorrection(l,xx));
627 if (k == kzCorrection || k == kzCorrectionC) {
629 if ((corl->min < corl->max) && (corl->min > VarXs[k] || VarXs[k] > corl->max)) {
630 if (! IsSimulation()) {
634 if (ZdriftDistance < -0.6) {
635 dE *= TMath::Exp(1.2);
637 }
else if (VarXs[k] < 0.0) {
640 if (k == kzCorrectionC && corl->type == 20) {
641 Int_t np = TMath::Abs(corl->npar)%100;
642 if (TMath::Abs(corl->a[np]) > 1e-7) {
643 Double_t dEcor = corl->a[np]*TMath::Exp( corl->a[np+1]*VarXs[k]);
647 dE *= TMath::Exp(-dEcor);
651 if (corl->type == 200 && (corl->min < corl->max) && ! IsSimulation() ) {
652 if ((corl->min > VarXs[k] || corl->max < VarXs[k])) {
656 if (corl->type == 300 && (corl->min < corl->max)) {
657 VarXs[k] = TMath::Min(corl->max, TMath::Max( corl->min, VarXs[k]));
659 if (TMath::Abs(corl->npar) >= 100) {
661 if (corl->min >= corl->max) {
664 if (corl->min <= VarXs[k] && VarXs[k] <= corl->max) {
672 if (corl->npar%100) {
673 Double_t dECor = TMath::Exp(-chairC->CalcCorrection(l,VarXs[k]));
677 for (m = 0; m < NLoops; m++, l += nrows) {
679 if (corl->min < corl->max && corl->min <= VarXs[k] && VarXs[k] < corl->max) {
680 dE *= TMath::Exp(-chairC->CalcCorrection(l,VarXs[k]));
688 CdEdx.C[k].dEdx = CdEdx.C[k].dE/CdEdx.C[k].dx;
689 CdEdx.C[k].dEdxL = TMath::Log(CdEdx.C[k].dEdx);
690 if (! k) CdEdx.C[k].ddEdxL = 0;
691 else CdEdx.C[k].ddEdxL = CdEdx.C[k].dEdxL - CdEdx.C[k-1].dEdxL;
694 cout << m_Corrections[k].Name; CdEdx.C[k].Print();
699 if (TMath::IsNaN(CdEdx.C[kTpcLast].dE)) {
700 static Int_t iBreak = 0;
704 CdEdx.F = CdEdx.C[kTpcLast];
709 Int_t StTpcdEdxCorrection::dEdxTrackCorrection(Int_t type,
dst_dedx_st &dedx, Double_t etaG) {
711 if (m_Corrections[kTpcLengthCorrectionMDN].Chair) ok = dEdxTrackCorrection(kTpcLengthCorrectionMDN,type,dedx, etaG);
712 else if (m_Corrections[kTpcLengthCorrectionMD2].Chair) ok = dEdxTrackCorrection(kTpcLengthCorrectionMD2,type,dedx);
713 else if (m_Corrections[kTpcLengthCorrectionMDF].Chair) ok = dEdxTrackCorrection(kTpcLengthCorrectionMDF,type,dedx);
714 else if (m_Corrections[kTpcLengthCorrection ].Chair) ok = dEdxTrackCorrection(kTpcLengthCorrection ,type,dedx);
715 if (m_Corrections[kTpcdEdxCor].Chair) ok = dEdxTrackCorrection(kTpcdEdxCor ,type,dedx);
719 Int_t StTpcdEdxCorrection::dEdxTrackCorrection(EOptions opt, Int_t type,
dst_dedx_st &dedx, Double_t etaG) {
720 Double_t xx[2] = {0};
721 Double_t LogTrackLength = TMath::Log((Double_t) (dedx.ndedx/100));
722 if (opt != kTpcLengthCorrectionMDN) {
723 Double_t dxLog2 = dedx.dedx[2];
724 xx[0] = LogTrackLength;
727 Double_t LogNodEdx = TMath::Log((Double_t) (dedx.ndedx%100));
733 if (! m_Corrections[k].Chair)
return 0;
736 Double_t dEdxError = 0;
739 case kTpcLengthCorrection:
740 nrows = chairC->nrows(l);
746 dedx.dedx[0] *= TMath::Exp(-chairC->CalcCorrection( l,LogTrackLength));
747 dEdxError = chairC->CalcCorrection(l+1,LogTrackLength);
748 if (dEdxError > 0) dedx.dedx[1] = dEdxError;
751 dedx.dedx[0] *= TMath::Exp(-chairC->CalcCorrection(l+6,LogTrackLength));
758 case kTpcLengthCorrectionMDF:
759 case kTpcLengthCorrectionMD2:
760 case kTpcLengthCorrectionMDN:
762 if (dedx.det_id > 100 && nrows > l+6) l += 6;
768 dedx.dedx[0] *= TMath::Exp(-((
St_MDFCorrectionC *)m_Corrections[k].Chair)->Eval( l,xx));
770 if (dEdxError > 0) dedx.dedx[1] = dEdxError;
778 I70L = TMath::Log(1.e6*dedx.dedx[0]);
779 if (I70L > 0) dedx.dedx[0] *= TMath::Exp(-chairC->SumSeries(0,I70L));
787 void StTpcdEdxCorrection::Print(Option_t *opt)
const {
789 cout <<
"StTpcdEdxCorrection:: Sector/row/pad " << mdEdx->sector <<
"/" << mdEdx->row <<
"/" << mdEdx->pad << endl;
790 cout <<
"Npads/Ntbks " << mdEdx->Npads <<
"/" << mdEdx->Ntbks
791 <<
"\tdrift distance / O2 / O2W " << mdEdx->ZdriftDistance <<
"/" << mdEdx->ZdriftDistanceO2 <<
"/" << mdEdx->ZdriftDistanceO2W << endl;
792 cout <<
"Local xyz " << mdEdx->xyz[0] <<
"\t" << mdEdx->xyz[1] <<
"\t" << mdEdx->xyz[2] << endl;
793 cout <<
"Local xyzD " << mdEdx->xyzD[0] <<
"\t" << mdEdx->xyzD[1] <<
"\t" << mdEdx->xyzD[2] << endl;
795 for (Int_t k = (Int_t)kUncorrected; k <= ((Int_t)kTpcLast); k++) {
796 Line = Form(
"%2i",k);
797 static Double_t log10keV = TMath::Log10(1e6);
798 if (k <= (Int_t) kTpcLast) {
799 Line += Form(
"\tdE %10.5g keV", 1e6*mdEdx->C[k].dE);
800 Line += Form(
"\tdx %10.5g cm",mdEdx->C[k].dx);
801 Line += Form(
"\tdE/dx %10.5g keV/cm", 1e6*mdEdx->C[k].dEdx);
802 Line += Form(
"\tlog(dE/dx) %10.5g",mdEdx->C[k].dEdxL + log10keV);
803 Line += Form(
"\tdlog(dE/dx) %10.5g",mdEdx->C[k].ddEdxL);
804 Line +=
"\t"; Line += TString(m_Corrections[k].Name); Line +=
"\t"; Line += TString(m_Corrections[k].Title);
806 Line += Form(
"\tdE %10.5g",mdEdx->F.dE);
807 Line += Form(
"\tdx %10.5g",mdEdx->F.dx);
808 Line += Form(
"\tdE/dx %10.5g",mdEdx->F.dEdx);
809 Line += Form(
"\tlog(dE/dx) %10.5g",mdEdx->F.dEdxL);
810 Line +=
"\tFinal \t ";
812 cout << Line.Data() << endl;
virtual void AddData(TDataSet *data, const char *dir=".data")
User methods.
virtual Int_t GetRunNumber() const
Returns the current RunNumber.
virtual Char_t * Print(Char_t *buf, Int_t n) const
Create IDL table defintion (to be used for XDF I/O)