]> git.uio.no Git - u/mrichter/AliRoot.git/blame - TPC/CalibMacros/AnalyzeLaser.C
Pseudo code to fill the AliTPCclusterParam
[u/mrichter/AliRoot.git] / TPC / CalibMacros / AnalyzeLaser.C
CommitLineData
c602279c 1/*
2
3Macro to perform fits of the Laser Central electrode data
4Several fit methods implemented
5
61. RebuildData() - transform arbitrary layeut of the Input data to the internal format
7 StoreData(); - The data tree expected in file inname (see variable bellow)
8 StoreTree(); - Modify inname and xxside and tcor in order to transform data
9
102. MakeFit(); - Make a fit of the data - already in internal format
11 StoreData(); - Store
12 StoreTree();
13
e47b6390 143. MakeRes(); - Make the final calibration + conbination of different components
15
164. LoadViewer(); - Browse the fit parameters
c602279c 17
184.
19
20
21.x ~/rootlogon.C
22gSystem->AddIncludePath("-I$ALICE_ROOT/TPC -I$ALICE_ROOT/STAT");
23gSystem->Load("libSTAT.so");
24.L $ALICE_ROOT/TPC/CalibMacros/AnalyzeLaser.C+
25
26
27
28
29*/
30#include "TString.h"
31#include "TSystem.h"
32#include "TTree.h"
33#include "TStatToolkit.h"
34#include "AliTPCCalibViewer.h"
35#include "AliTPCCalibViewerGUI.h"
36#include "AliTPCPreprocessorOnline.h"
37//
38//Define interesting variables - file names
39//
40char * inname = "treeCE08_05-07.root"; // input file with tree
41//
42// variable name definition in input tree - change it according the input
43//
44TString qaside("CE_A00_Q_05");
45TString taside("CE_A00_T_05");
46TString raside("CE_A00_rms_05");
47TString qcside("CE_C00_Q_05");
48TString tcside("CE_C00_T_05");
49TString rcside("CE_C00_rms_05");
50//
51// correction variable - usually Pulser time
52//
53TString tcor("(sector%36>30)*2");
54
55//
56char * fname = "treefitCE.root"; // output file with tree
57char * oname = "fitCE.root"; // output file with CalPads fit
58
59//
60//
61// Input CalPads
62//
63AliTPCCalPad *calPadIn = 0; // original time pad
64AliTPCCalPad *calPadF1 = 0; // original time pad - fit plane
65AliTPCCalPad *calPadF2 = 0; // original time pad - fit parabola
66AliTPCCalPad *calPadQIn = 0; // original Q pad
67AliTPCCalPad *calPadQF1 = 0; // original Q pad
68AliTPCCalPad *calPadQF2 = 0; // original Q pad
69
70AliTPCCalPad *calPadCor = 0; // base correction CalPad
71AliTPCCalPad *calPadOut = 0; // outlyer CalPad
72//
73// cuts
74//
75const Float_t tThr=0.5; // max diff in the sector
76const Float_t qThr0=0.5; // max Q diff in the sector
77const Float_t qThr1=2; // max Q diff in the sector
78
79//
80//
81// fit Cal Pads
82AliTPCCalPad *calPad0 = 0; // global fit 0 - base
83AliTPCCalPad *calPad1 = 0; // global fit 1 - common behavior rotation -A-C
84AliTPCCalPad *calPad2 = 0; // gloabl fit 2 - CE missalign rotation A-C
85//
86AliTPCCalPad *calPadInOut = 0; // misaalign in-out
87AliTPCCalPad *calPadLX = 0; // local x missalign
88AliTPCCalPad *calPadTL = 0; // tan
89AliTPCCalPad *calPadQ = 0; // time (q) correction
90AliTPCCalPad *calPadGXY = 0; // global XY missalign (drift velocity grad)
91AliTPCCalPad *calPadOff = 0; // normalization offset fit
e47b6390 92AliTPCCalPad *calPadRes = 0; // final calibration
93
c602279c 94
95//
96// working variables
97//
98AliTPCCalibViewerGUI * viewer=0; //viewerGUI
99AliTPCCalibViewer *makePad=0; //viewer
100TTree * tree=0; // working tree
101
102void LoadViewer();
103void RebuildData(); // transform the input data to the fit format
104void MakeFit(); // make fits
105//
106// internal functions
107//
108void MakeAliases0(); // Make Aliases 0 - for user tree
109void MakeAliases1(); // Make Aliases 1 - for default tree
110void LoadData(); // Load data
111void StoreData(); // store current data
112void StoreTree(); // store fit data in the output tree
113
114
115void AnalyzeLaser(){
116 //
117 //
118 //
119 LoadViewer();
120 MakeAliases1();
121}
122
123
124void MakeFit(){
125 //
126 //
9ee9c908 127 LoadData();
128 LoadViewer();
c602279c 129 TStatToolkit stat;
130 Int_t npoints;
131 Double_t chi2;
132 TVectorD vec0,vec1,vec2;
133 TMatrixD mat;
134 TString fstring="";
135 //
136 //Basic correction
137 //
138 fstring+="side++"; // offset on 2 different sides //1
139 fstring+="(1/qp)++"; // Q -threshold effect correction //2
140 fstring+="(qp)++"; // Q -threshold effect correction //3
141 fstring+="(inn)++"; // inner outer misalign - common //4
142 fstring+="(side*inn)++"; // - opposite //5
143 //
144 fstring+="(gyr)++"; // drift velocity gradient - common //6
145 fstring+="(side*gyr)++"; // - opposite //7
146 fstring+="(gxr)++"; // global x tilt - common //8
147 fstring+="(side*gxr)++"; // - opposite //9
148 //
149 fstring+="tl^2++"; // local phi correction //10
150 //
151 fstring+="(lxr)++"; // zr angle - common //11
152 fstring+="(side*lxr)++"; // - opposite //12
153 fstring+="(inn*lxr)++"; // inner outer angle - common //13
154 fstring+="(side*inn*lxr)++";// - opposite //14
155 fstring+="(lxr^2)++"; // zr second - common //15
156 fstring+="(side*lxr^2)++"; // - opposite //16
157 //
158 TString *fit0 =stat.FitPlane(tree,"dt",fstring.Data(),"cutF&&cutCE",chi2,npoints,vec0,mat,0.90);
159 tree->SetAlias("f0",fit0->Data());
160 //
161 // Common "deformation" tendencies
162 //
163 fstring+="(sin(atan2(gy.fElements,gx.fElements)))++";
164 fstring+="(cos(atan2(gy.fElements,gx.fElements)))++";
165 //
166 fstring+="(sin(atan2(gy.fElements,gx.fElements)*2))++";
167 fstring+="(cos(atan2(gy.fElements,gx.fElements)*2))++";
168 fstring+="(sin(atan2(gy.fElements,gx.fElements)*3))++";
169 fstring+="(cos(atan2(gy.fElements,gx.fElements)*3))++";
170 //
171 fstring+="(sin(atan2(gy.fElements,gx.fElements)*2))*lxr++";
172 fstring+="(cos(atan2(gy.fElements,gx.fElements)*2))*lxr++";
173 fstring+="(sin(atan2(gy.fElements,gx.fElements)*3))*lxr++";
174 fstring+="(cos(atan2(gy.fElements,gx.fElements)*3))*lxr++";
175 //
176
177 TString *fit1 =stat.FitPlane(tree,"dt",fstring.Data(),"cutF&&cutCE",chi2,npoints,vec1,mat,0.95);
178 tree->SetAlias("f1",fit1->Data());
179 //
180 // Central electrode "deformation"
181 //
182 fstring+="(side*sin(atan2(gy.fElements,gx.fElements)))++";
183 fstring+="(side*cos(atan2(gy.fElements,gx.fElements)))++";
184 //
185 fstring+="(side*sin(atan2(gy.fElements,gx.fElements)*2))++";
186 fstring+="(side*cos(atan2(gy.fElements,gx.fElements)*2))++";
187 fstring+="(side*sin(atan2(gy.fElements,gx.fElements)*3))++";
188 fstring+="(side*cos(atan2(gy.fElements,gx.fElements)*3))++";
189 //
190 fstring+="(side*sin(atan2(gy.fElements,gx.fElements)*2))*lxr++";
191 fstring+="(side*cos(atan2(gy.fElements,gx.fElements)*2))*lxr++";
192 fstring+="(side*sin(atan2(gy.fElements,gx.fElements)*3))*lxr++";
193 fstring+="(side*cos(atan2(gy.fElements,gx.fElements)*3))*lxr++";
194
195 TString *fit2 =stat.FitPlane(tree,"dt",fstring.Data(),"cutF&&abs(dt-f0)<0.7&&cutCE",chi2,npoints,vec2,mat,0.90);
196 tree->SetAlias("f2",fit2->Data());
197 //
198 // Extract variables
199 //
200 TString tmpstr = fstring;
201 TObjArray *arr = tmpstr.Tokenize("++");
202 TString fitQ("0"); // q correction
203 TString fitLX("0"); // lx correction
204 TString fitInOut("0"); // inner-outer - match
205 TString fitGXY("0"); // global xy fit
206 TString fitOff("0"); // side offsets
207 TString fitTL("0"); // side offsets
208 //
209 fitOff+="+";
210 fitOff+=vec2[0];
211 fitOff+="+side*";
212 fitOff+=vec2[1];
213 {
214 for(Int_t i=0;i<arr->GetEntriesFast();i++){
215 if (!arr->At(i)) continue;
216 TString *fitstr = new TString(arr->At(i)->GetName());
217 //
218 Bool_t isQ = fitstr->Contains("qp)");
219 Bool_t isRot = fitstr->Contains("sin(")+fitstr->Contains("cos(");
220 Bool_t isLX = fitstr->Contains("lxr");
221 Bool_t isIn = fitstr->Contains("inn");
222 Bool_t isGXY = fitstr->Contains("gxr")+fitstr->Contains("gyr");
223 if (fitstr->Contains("tl^2")){
224 fitTL+="+";
225 fitTL+=(*fitstr)+"*";
226 fitTL+=vec2[i+1];
227 }
228 if (isGXY){
229 fitGXY+="+";
230 fitGXY+=(*fitstr)+"*";
231 fitGXY+=vec2[i+1];
232 }
233 if (isQ){
234 //
235 fitQ+="+";
236 fitQ+=(*fitstr)+"*";
237 fitQ+=vec2[i+1];
238 }
239 //
240 if (isLX&&!isRot&&!isIn){
241 fitLX+="+";
242 fitLX+=(*fitstr)+"*";
243 fitLX+=vec2[i+1];
244 }
245 //
246 if (!isRot&&isIn){
247 fitInOut+="+";
248 fitInOut+=(*fitstr)+"*";
249 fitInOut+=vec2[i+1];
250 }
251 }
252 }
253 //
254 tree->SetAlias("fInOut",fitInOut.Data());
255 tree->SetAlias("fLX",fitLX.Data());
256 tree->SetAlias("fGXY",fitGXY.Data());
257 tree->SetAlias("fOff",fitOff.Data());
258 tree->SetAlias("fQ",fitQ.Data());
259 tree->SetAlias("fTL",fitTL.Data());
260 //
261 //
262 // fits
263 //
e47b6390 264 calPad0 = makePad->GetCalPad("f0","1", "ffit0");
265 calPad1 = makePad->GetCalPad("f1","1", "ffit1");
266 calPad2 = makePad->GetCalPad("f2","1", "ffit2");
267 calPadInOut = makePad->GetCalPad("fInOut","1", "fInOut");
268 calPadLX = makePad->GetCalPad("fLX","1", "fLX");
269 calPadTL = makePad->GetCalPad("fTL","1", "fTL");
270 calPadQ = makePad->GetCalPad("fQ","1", "fQ");
271 calPadGXY = makePad->GetCalPad("fGXY","1", "fGXY");
272 calPadOff = makePad->GetCalPad("fOff","1", "fOff");
c602279c 273}
274
275void LoadViewer(){
276 //
277 // Load calib Viewer
278 //
279 TObjArray * array = AliTPCCalibViewerGUI::ShowGUI(fname);
280 viewer = (AliTPCCalibViewerGUI*)array->At(0);
281 makePad = viewer->GetViewer();
282 tree = viewer->GetViewer()->GetTree();
283 MakeAliases1();
284}
285
286
287
288
289
290
291void RebuildData(){
292 //
293 // transform the input data to the fit format
294 //
295 makePad = new AliTPCCalibViewer(inname);
296 tree = makePad->GetTree();
297 MakeAliases0(); //
298 //
e47b6390 299 calPadCor = makePad->GetCalPad("tcor","1", "tcor");
c602279c 300 calPadOut = makePad->GetCalPad("1","!((cutA||cutC)&&abs(ly.fElements/lx.fElements)<0.155)", "out");
301 calPadIn = makePad->GetCalPad("dt-tcor","(cutA||cutC)&&abs(ly.fElements/lx.fElements)<0.155","timeIn");
302 calPadF1 = calPadIn->GlobalFit("timeF1", calPadOut,kTRUE,0,0.9);
303 calPadQIn = makePad->GetCalPad("qa*(sector%36<18)+qc*(sector%36>17)","1","qIn");
304 //
305 // Update outlyer maps
306 //
307 for (Int_t isector=0;isector<72; isector++){
308 for (UInt_t ich=0;ich<calPadIn->GetCalROC(isector)->GetNchannels();ich++){
309 Float_t val0= calPadIn->GetCalROC(isector)->GetValue(ich);
310 Float_t val1= calPadF1->GetCalROC(isector)->GetValue(ich);
311 if (TMath::Abs(val0-val1)>tThr) calPadOut->GetCalROC(isector)->SetValue(ich,1);
312 }
313 }
314 calPadF1 = calPadIn->GlobalFit("timeF1", calPadOut,kTRUE,0,0.9);
315 calPadF2 = calPadIn->GlobalFit("timeF2", calPadOut,kTRUE,1,0.9);
316 calPadQF1 = calPadQIn->GlobalFit("qF1", calPadOut,kTRUE,0,0.9);
317 calPadQF2 = calPadQIn->GlobalFit("qF2", calPadOut,kFALSE,1);
318 //
319 // Update outlyer maps
320 //
321 for (Int_t isector=0;isector<72; isector++){
322 for (UInt_t ich=0;ich<calPadIn->GetCalROC(isector)->GetNchannels();ich++){
323 Float_t val0= calPadQIn->GetCalROC(isector)->GetValue(ich);
324 Float_t val1= calPadQF2->GetCalROC(isector)->GetValue(ich);
325 if (val1<0.1) {
326 calPadOut->GetCalROC(isector)->SetValue(ich,1);
327 continue;
328 }
329 if (TMath::Abs(val0/val1)<qThr0) calPadOut->GetCalROC(isector)->SetValue(ich,1);
330 if (TMath::Abs(val0/val1)>qThr1) calPadOut->GetCalROC(isector)->SetValue(ich,1);
331 }
332 }
333 calPadF1 = calPadIn->GlobalFit("timeF1", calPadOut,kTRUE,0,0.9);
334 calPadF2 = calPadIn->GlobalFit("timeF2", calPadOut,kTRUE,1,0.9);
335 calPadQF1 = calPadQIn->GlobalFit("qF1", calPadOut,kTRUE,0,0.9);
336 calPadQF2 = calPadQIn->GlobalFit("qF2", calPadOut,kFALSE,1);
337}
338
339void LoadData(){
340 //
341 // Get Data
342 //
343 TFile f(oname);
344 calPadIn = (AliTPCCalPad*)f.Get("timeIn"); // original time pad
345 calPadF1 = (AliTPCCalPad*)f.Get("timeF1"); // original time pad - fit plane
346 calPadF2 = (AliTPCCalPad*)f.Get("timeF2"); // original time pad - fit parabola
347 //
348 calPadQIn = (AliTPCCalPad*)f.Get("qIn"); // original time pad
349 calPadQF1 = (AliTPCCalPad*)f.Get("qF1"); // original time pad - fit plane
350 calPadQF2 = (AliTPCCalPad*)f.Get("qF2"); // original time pad - fit parabola
351 //
352 calPadCor = (AliTPCCalPad*)f.Get("tcor"); // base correction CalPad
353 calPadOut = (AliTPCCalPad*)f.Get("out"); // outlyer CalPad
354 //
355 calPad0 = (AliTPCCalPad*)f.Get("ffit0"); // global fit 0 - base
356 calPad1 = (AliTPCCalPad*)f.Get("ffit1"); // global fit 1 - common behavior rotation -A-C
357 calPad2 = (AliTPCCalPad*)f.Get("ffit2"); // gloabl fit 2 - CE missalign rotation A-C
358 calPadInOut = (AliTPCCalPad*)f.Get("fInOut");// misaalign in-out
359 calPadLX = (AliTPCCalPad*)f.Get("fLX"); // local x missalign
360 calPadTL = (AliTPCCalPad*)f.Get("fTL"); // local y/x missalign
361 calPadQ = (AliTPCCalPad*)f.Get("fQ"); // time (q) correction
362 calPadGXY = (AliTPCCalPad*)f.Get("fGXY"); // global XY missalign (drift velocity grad)
363 calPadOff = (AliTPCCalPad*)f.Get("fOff"); // normalization offset fit
e47b6390 364 calPadRes = (AliTPCCalPad*)f.Get("Result"); //resulting calibration
c602279c 365}
366
367void StoreData(){
368 //
369 // Store data
370 //
371 TFile * fstore = new TFile(oname,"recreate");
372 if (calPadIn) calPadIn->Write("timeIn"); // original time pad
373 if (calPadF1) calPadF1->Write("timeF1"); // original time pad - fit plane
374 if (calPadF2) calPadF2->Write("timeF2"); // original time pad - fit parabola
375 //
376 if (calPadQIn) calPadQIn->Write("qIn"); // original time pad
377 if (calPadQF1) calPadQF1->Write("qF1"); // original time pad - fit plane
378 if (calPadQF2) calPadQF2->Write("qF2"); // original time pad - fit parabola
379 //
380 if (calPadCor) calPadCor->Write("tcor"); // base correction CalPad
381 if (calPadOut) calPadOut->Write("out"); // outlyer CalPad
382 //
383 if (calPad0) calPad0->Write("ffit0"); // global fit 0 - base
384 if (calPad1) calPad1->Write("ffit1"); // global fit 1 - common behavior rotation -A-C
385 if (calPad2) calPad2->Write("ffit2"); // gloabl fit 2 - CE missalign rotation A-C
386 if (calPadInOut)calPadInOut->Write("fInOut"); // misaalign in-out
387 if (calPadLX) calPadLX->Write("fLX"); // local x missalign
388 if (calPadTL) calPadTL->Write("fTL"); // local y/x missalign
389 if (calPadQ) calPadQ->Write("fQ"); // time (q) correction
390 if (calPadGXY) calPadGXY->Write("fGXY"); // global XY missalign (drift velocity grad)
391 if (calPadOff) calPadOff->Write("fOff"); // normalization offset fit
e47b6390 392 if (calPadRes) calPadRes->Write("Result"); //resulting calibration
c602279c 393 fstore->Close();
394 delete fstore;
395}
396
397void StoreTree(){
398 //
399 //
400 //
401 AliTPCPreprocessorOnline * preprocesor = new AliTPCPreprocessorOnline;
402 //
403 if (calPadIn) preprocesor->AddComponent(calPadIn->Clone());
404 if (calPadF1) preprocesor->AddComponent(calPadF1->Clone());
405 if (calPadF2) preprocesor->AddComponent(calPadF2->Clone());
406 //
407 if (calPadQIn) preprocesor->AddComponent(calPadQIn->Clone());
408 if (calPadQF1) preprocesor->AddComponent(calPadQF1->Clone());
409 if (calPadQF2) preprocesor->AddComponent(calPadQF2->Clone());
410 //
411 if (calPadCor) preprocesor->AddComponent(calPadCor->Clone());
412 if (calPadOut) preprocesor->AddComponent(calPadOut->Clone());
413 //
414 if (calPad0) preprocesor->AddComponent(calPad0->Clone());
415 if (calPad1) preprocesor->AddComponent(calPad1->Clone());
416 if (calPad2) preprocesor->AddComponent(calPad2->Clone());
417 if (calPadInOut)preprocesor->AddComponent(calPadInOut->Clone());
418 if (calPadLX) preprocesor->AddComponent(calPadLX->Clone());
419 if (calPadTL) preprocesor->AddComponent(calPadTL->Clone());
420 if (calPadQ) preprocesor->AddComponent(calPadQ->Clone());
421 if (calPadGXY) preprocesor->AddComponent(calPadGXY->Clone());
422 if (calPadOff) preprocesor->AddComponent(calPadOff->Clone());
e47b6390 423 if (calPadRes) preprocesor->AddComponent(calPadRes->Clone());
c602279c 424 preprocesor->DumpToFile(fname);
425 delete preprocesor;
426}
427
428
429void MakeAliases0(){
430 //
431 // Define variables and selection of outliers - for user defined tree
432 //
433 tree->SetAlias("tcor",tcor.Data()); // correction variable
434 tree->SetAlias("ta",taside+".fElements");
435 tree->SetAlias("tc",tcside+".fElements");
436 tree->SetAlias("qa",qaside+".fElements");
437 tree->SetAlias("qc",qcside+".fElements");
438 tree->SetAlias("ra",raside+".fElements");
439 tree->SetAlias("rc",rcside+".fElements");
440 tree->SetAlias("side","1-(sector%36>17)*2");
441 tree->SetAlias("dt","(ta)*(sector%36<18)+(tc)*(sector%36>17)+tcor");
442 tree->SetAlias("cutA","qa>30&&qa<400&&abs(ta)<2&&ra>0.5&&ra<2");
443 tree->SetAlias("cutC","qc>30&&qc<400&&abs(tc)<2&&rc>0.5&&rc<2");
444 tree->SetAlias("cutF","(pad.fElements%4==0)&&(row.fElements%3==0)");
445 tree->SetAlias("cutCE","V.out.fElements");
446 //
447 // fit param aliases
448 //
449 tree->SetAlias("inn","sector<36");
450 tree->SetAlias("gxr","(gx.fElements/250.)"); //
451 tree->SetAlias("gyr","(gy.fElements/250.)"); //
452 tree->SetAlias("lxr","(lx.fElements-133.41)/250.");
453 tree->SetAlias("qp","((sector%36<18)*sqrt(qa)/10.+(sector%36>17)*sqrt(qc)/10.)"); //
454 tree->SetAlias("tl","(ly.fElements/lx.fElements)/0.17");
455}
456
457
458void MakeAliases1(){
459 //
460 // Define variables and selection of outliers -for default usage
461 //
462 tree->SetAlias("tcor","tcor.fElements"); // correction variable
463 tree->SetAlias("side","1-(sector%36>17)*2");
464 tree->SetAlias("dt","timeIn.fElements+tcor");
465 //
466 tree->SetAlias("cutA","out.fElements==1");
467 tree->SetAlias("cutC","out.fElements==1");
468 tree->SetAlias("cutF","(pad.fElements%5==0)&&(row.fElements%4==0)");
469 tree->SetAlias("cutCE","out.fElements<0.5");
470 //
471 // fit param aliases
472 //
473 tree->SetAlias("inn","sector<36");
474 tree->SetAlias("gxr","(gx.fElements/250.)"); //
475 tree->SetAlias("gyr","(gy.fElements/250.)"); //
476 tree->SetAlias("lxr","(lx.fElements-133.41)/250.");
e47b6390 477 tree->SetAlias("qp","(sqrt(qIn.fElements)/10.+(out.fElements>0.5))"); //
c602279c 478 tree->SetAlias("tl","(ly.fElements/lx.fElements)/0.17");
479}
480
481
e47b6390 482void MakeRes()
483{
484 //
485 // make final calibration
486 //
487 AliTPCCalPad * calPadRes0 =new AliTPCCalPad(*calPadIn);
488 calPadRes0->Add(calPadCor); // add correction
489 calPadRes0->Add(calPad2,-1); // remove global fit
490 calPadRes = calPadRes0->GlobalFit("Result", calPadOut,kTRUE,1,0.9);
491 //
492 //
493 {
494 Float_t tlmedian = calPadTL->GetMedian();
495 for (Int_t isector=0;isector<72; isector++){
496 for (UInt_t ich=0;ich<calPadIn->GetCalROC(isector)->GetNchannels();ich++){
497 //
498 //
499 Float_t val0 = calPadRes->GetCalROC(isector)->GetValue(ich);
500 if (TMath::Abs(val0)>0.5) calPadRes->GetCalROC(isector)->SetValue(ich,0);
501 Float_t tl = calPadTL->GetCalROC(isector)->GetValue(ich);
502 Float_t inOut = calPadInOut->GetCalROC(isector)->GetValue(ich);
503 calPadRes->GetCalROC(isector)->SetValue(ich,calPadRes->GetCalROC(isector)->GetValue(ich)+tl+inOut);
504 //
505 }
506 }
507 }
508 calPadRes->Add(calPadCor,-1); // remove back correction (e.g Pulser time 0)
509
510}