]> git.uio.no Git - u/mrichter/AliRoot.git/blob - STEER/AliGRPPreprocessor.cxx
8ff30685d0464f24cbb8bc80ae7695e4ea5a9966
[u/mrichter/AliRoot.git] / STEER / AliGRPPreprocessor.cxx
1 /**************************************************************************
2  * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3  *                                                                        *
4  * Author: The ALICE Off-line Project.                                    *
5  * Contributors are mentioned in the code where appropriate.              *
6  *                                                                        *
7  * Permission to use, copy, modify and distribute this software and its   *
8  * documentation strictly for non-commercial purposes is hereby granted   *
9  * without fee, provided that the above copyright notice appears in all   *
10  * copies and that both the copyright notice and this permission notice   *
11  * appear in the supporting documentation. The authors make no claims     *
12  * about the suitability of this software for any purpose. It is          *
13  * provided "as is" without express or implied warranty.                  *
14  **************************************************************************/
15
16 /* $Id$ */
17
18 //-------------------------------------------------------------------------
19 //                          Class AliGRPPreprocessor
20 //                  Global Run Parameters (GRP) preprocessor
21 //    Origin: Panos Christakoglou, UOA-CERN, Panos.Christakoglou@cern.ch
22 //    Modified: Ernesto.Lopez.Torres@cern.ch  CEADEN-CERN
23 //    Modified: Chiara.Zampolli@cern.ch  CERN
24 //-------------------------------------------------------------------------
25
26 #include <TChain.h>
27 #include <TList.h>
28 #include <TMap.h>
29 #include <TObjString.h>
30 #include <TObjArray.h>
31 #include <TGraph.h>
32 #include <TString.h>
33 #include <TFile.h>
34
35 #include <float.h>
36
37 #include "AliGRPPreprocessor.h"
38 #include "AliGRPObject.h"
39 #include "AliDCSSensor.h"
40 #include "AliSplineFit.h"
41 #include "AliDCSSensorArray.h"
42 #include "AliRawEventHeaderVersions.h"
43
44 #include "AliTriggerConfiguration.h"
45 #include "AliTriggerRunScalers.h"
46 #include "AliTriggerInput.h"
47
48 #include "AliCDBMetaData.h"
49 #include "AliESDVertex.h"
50 #include "AliLHCReader.h"
51 #include "AliLHCData.h"
52 #include "AliDCSArray.h"
53 #include "AliDAQ.h"
54 #include "AliLTUConfig.h"
55
56 class AliLog;
57 class AliDCSValue;
58 class AliShuttleInterface;
59
60 // needed for ReceivePromptRecoParameters
61
62 #include <TSQLServer.h>
63 #include <TSQLResult.h>
64 #include <TSQLRow.h>
65 #include <AliCDBManager.h>
66 #include <AliCDBMetaData.h>
67 #include <AliCDBId.h>
68 #include <AliTriggerConfiguration.h>
69 #include <AliCTPTimeParams.h>
70 #include <AliLHCClockPhase.h>
71
72 const Double_t kFitFraction = -1.;                 // Fraction of DCS sensor fits required
73
74 ClassImp(AliGRPPreprocessor)
75
76 //_______________________________________________________________
77
78   const Int_t AliGRPPreprocessor::fgknDAQLbPar = 6; // num parameters in the logbook used to fill the GRP object
79   const Int_t AliGRPPreprocessor::fgknDCSDP = 48;   // number of dcs dps
80   const Int_t AliGRPPreprocessor::fgknDCSDPHallProbes = 40;   // number of dcs dps
81   const Int_t AliGRPPreprocessor::fgknLHCDP = 6;   // number of dcs dps from LHC data
82   const Int_t AliGRPPreprocessor::fgkDCSDPHallTopShift = 4;   // shift from the top to get tp the Hall Probes names in the list of DCS DPs
83   const Int_t AliGRPPreprocessor::fgkDCSDPNonWorking = 5; // number of non working DCS DPs
84   const char* AliGRPPreprocessor::fgkDCSDataPoints[AliGRPPreprocessor::fgknDCSDP] = {
85                    "L3Polarity",
86                    "DipolePolarity",
87                    "L3Current",
88                    "DipoleCurrent",
89                    "L3_BSF17_H1",
90                    "L3_BSF17_H2",
91                    "L3_BSF17_H3",
92                    "L3_BSF17_Temperature",
93                    "L3_BSF4_H1",
94                    "L3_BSF4_H2",
95                    "L3_BSF4_H3",
96                    "L3_BSF4_Temperature",
97                    "L3_BKF17_H1",
98                    "L3_BKF17_H2",
99                    "L3_BKF17_H3",
100                    "L3_BKF17_Temperature",
101                    "L3_BKF4_H1",
102                    "L3_BKF4_H2",
103                    "L3_BKF4_H3",
104                    "L3_BKF4_Temperature",
105                    "L3_BSF13_H1",
106                    "L3_BSF13_H2",
107                    "L3_BSF13_H3",
108                    "L3_BSF13_Temperature",
109                    "L3_BSF8_H1",
110                    "L3_BSF8_H2",
111                    "L3_BSF8_H3",
112                    "L3_BSF8_Temperature",
113                    "L3_BKF13_H1",
114                    "L3_BKF13_H2",
115                    "L3_BKF13_H3",
116                    "L3_BKF13_Temperature",
117                    "L3_BKF8_H1",
118                    "L3_BKF8_H2",
119                    "L3_BKF8_H3",
120                    "L3_BKF8_Temperature",
121                    "Dipole_Inside_H1",
122                    "Dipole_Inside_H2",
123                    "Dipole_Inside_H3",
124                    "Dipole_Inside_Temperature",
125                    "Dipole_Outside_H1",
126                    "Dipole_Outside_H2",
127                    "Dipole_Outside_H3",
128                    "Dipole_Outside_Temperature",
129                    "CavernTemperature",
130                    "CavernAtmosPressure",
131                    "SurfaceAtmosPressure",
132                    "CavernAtmosPressure2"
133                  };
134
135   const char* AliGRPPreprocessor::fgkDCSDataPointsHallProbes[AliGRPPreprocessor::fgknDCSDPHallProbes] = {
136                    "L3_BSF17_H1",
137                    "L3_BSF17_H2",
138                    "L3_BSF17_H3",
139                    "L3_BSF17_Temperature",
140                    "L3_BSF4_H1",
141                    "L3_BSF4_H2",
142                    "L3_BSF4_H3",
143                    "L3_BSF4_Temperature",
144                    "L3_BKF17_H1",
145                    "L3_BKF17_H2",
146                    "L3_BKF17_H3",
147                    "L3_BKF17_Temperature",
148                    "L3_BKF4_H1",
149                    "L3_BKF4_H2",
150                    "L3_BKF4_H3",
151                    "L3_BKF4_Temperature",
152                    "L3_BSF13_H1",
153                    "L3_BSF13_H2",
154                    "L3_BSF13_H3",
155                    "L3_BSF13_Temperature",
156                    "L3_BSF8_H1",
157                    "L3_BSF8_H2",
158                    "L3_BSF8_H3",
159                    "L3_BSF8_Temperature",
160                    "L3_BKF13_H1",
161                    "L3_BKF13_H2",
162                    "L3_BKF13_H3",
163                    "L3_BKF13_Temperature",
164                    "L3_BKF8_H1",
165                    "L3_BKF8_H2",
166                    "L3_BKF8_H3",
167                    "L3_BKF8_Temperature",
168                    "Dipole_Inside_H1",
169                    "Dipole_Inside_H2",
170                    "Dipole_Inside_H3",
171                    "Dipole_Inside_Temperature",
172                    "Dipole_Outside_H1",
173                    "Dipole_Outside_H2",
174                    "Dipole_Outside_H3",
175                    "Dipole_Outside_Temperature"
176                  };
177                  
178   const Short_t kSensors = 45; // start index position of sensor in DCS DPs
179   const Short_t kNumSensors = 3; // Number of sensors in DCS DPs (CavernAtmosPressure, SurfaceAtmosPressure, CavernAtmosPressure2)
180
181
182   const char* AliGRPPreprocessor::fgkLHCDataPoints[AliGRPPreprocessor::fgknLHCDP] = {
183           "LHC_Beam_Energy",
184           "LHC_MachineMode",
185           "LHC_BeamMode",
186           "LHC_Beams_Particle_Type",
187           "BPTX_Phase_Shift_B1",
188           "BPTX_Phase_Shift_B2"
189   };
190
191   const char* kppError[] = {
192                    "",
193                    "(DAQ logbook ERROR)",
194                    "(DAQ FXS ERROR)",
195                    "(Trigger Scalers not found in DCS FXS - ERROR)",
196                    "(DCS data points ERROR)",
197                    "(Trigger Configuration ERROR)",
198                    "(DAQ logbook ERROR determining partition of the run)",
199                    "(CTP timing ERROR)",
200                    "(SPD Mean Vertex ERROR)",
201                    "(DCS FXS Error for LHC Data)",
202                    "(LHC Data Error)",
203                    "(LHC Clock Phase Error (from LHC Data))",
204                    "(LTU Configuration Error)"
205   };
206
207 //_______________________________________________________________
208
209 AliGRPPreprocessor::AliGRPPreprocessor(AliShuttleInterface* shuttle):
210         AliPreprocessor("GRP",shuttle),  fPressure(0), fmaxFloat(0), fminFloat(0),fmaxDouble(0), fminDouble(0), fmaxInt(0), fminInt(0), fmaxUInt(0), fminUInt(0),fdaqStartEndTimeOk(kTRUE),ffailedDPs(new TObjArray(fgknDCSDP))
211 {
212         // constructor - shuttle must be instantiated!
213
214         AddRunType("COSMIC");
215         AddRunType("LASER");
216         AddRunType("PHYSICS");
217         AddRunType("CALIBRATION_BC");
218         AddRunType("CALIBRATION_CENTRAL");
219         AddRunType("CALIBRATION_EMD");
220         AddRunType("CALIBRATION_MB");
221         AddRunType("CALIBRATION_SEMICENTRAL");
222         AddRunType("CALIBRATION");
223         AddRunType("PEDESTAL");
224         AddRunType("STANDALONE");
225         AddRunType("GAIN");
226         AddRunType("NOISE");
227         AddRunType("PULSER");
228         AddRunType("STANDALONE_PULSER");
229         AddRunType("STANDALONE_BC");
230
231         fmaxFloat = FLT_MAX;
232         fminFloat = -FLT_MAX;
233         fmaxDouble = DBL_MAX;
234         fminDouble = -DBL_MAX;
235         fmaxInt = kMaxInt;
236         fminInt = kMinInt;
237         fmaxUInt = kMaxUInt;
238         fminUInt = 0;
239
240         AliInfo(Form("Max allowed float = %6.5e",fmaxFloat));
241         AliInfo(Form("Min allowed float = %6.5e",fminFloat));
242         AliInfo(Form("Max allowed double = %6.5e",fmaxDouble));
243         AliInfo(Form("Min allowed double = %6.5e",fminDouble));
244         AliInfo(Form("Max allowed integer = %d",fmaxInt));
245         AliInfo(Form("Min allowed integer = %d",fminInt));
246         AliInfo(Form("Max allowed unsigned integer = %u",(Int_t)fmaxUInt));
247         AliInfo(Form("Min allowed unsigned integer = %u",(Int_t)fminUInt));
248
249         ffailedDPs->SetOwner(kTRUE);
250 }
251
252 //_______________________________________________________________
253
254 AliGRPPreprocessor::~AliGRPPreprocessor()
255 {
256         //destructor
257         
258         delete fPressure;
259         delete ffailedDPs;
260
261 }
262
263 //_______________________________________________________________
264
265 void AliGRPPreprocessor::Initialize(Int_t run, UInt_t startTime, UInt_t endTime)
266 {
267         // Initialize preprocessor
268
269         AliPreprocessor::Initialize(run, startTime, endTime);
270         
271         AliInfo("Initialization of the GRP preprocessor.");
272         AliInfo(Form("Start Time DCS = %d",GetStartTimeDCSQuery()));
273         AliInfo(Form("End Time DCS = %d",GetEndTimeDCSQuery()));
274         TClonesArray * array = new TClonesArray("AliDCSSensor",kNumSensors); 
275         for(Int_t j = 0; j < kNumSensors; j++) {
276                 AliDCSSensor * sens = new ((*array)[j])AliDCSSensor;
277                 sens->SetStringID(fgkDCSDataPoints[j+kSensors]);
278         }
279         AliInfo(Form("Pressure Entries: %d",array->GetEntries()));
280         
281         fPressure = new AliDCSSensorArray(GetStartTimeDCSQuery(), GetEndTimeDCSQuery(), array);
282
283         for (Int_t iDP=0; iDP < fgknDCSDP; iDP++){
284                 TObjString* dp = new TObjString(fgkDCSDataPoints[iDP]);
285                 ffailedDPs->AddAt(dp,iDP);
286         }
287
288 }
289
290 //_______________________________________________________________
291
292 UInt_t AliGRPPreprocessor::Process(TMap* valueMap)
293 {
294         // process data retrieved by the Shuttle
295         
296         // retrieving "partition" and "detector" fields from DAQ logbook to 
297         // determine the partition in which the run was taken
298         // the partition is used to decide how to react in case of errors for CTP
299
300         TString partition = (TString)GetRunParameter("partition");  
301         TString detector = (TString)GetRunParameter("detector");   
302
303         AliGRPObject *grpobj = new AliGRPObject();  // object to store data
304         grpobj->SetBeamEnergyIsSqrtSHalfGeV(); // new format
305
306         //=================//
307         // DAQ logbook     //
308         //=================//
309
310         Log("*************** Processing DAQ logbook");
311
312         UInt_t error = 0;
313         
314         Int_t iDaqLB = ProcessDaqLB(grpobj);
315         TString runType = (TString)GetRunType();
316         TString beamType = (TString)GetRunParameter("beamType");
317         if(iDaqLB == fgknDAQLbPar) {
318                 Log(Form("DAQ Logbook, successful! Retrieved %d/%d entries",iDaqLB,fgknDAQLbPar));
319         } else {
320                 Log(Form("DAQ Logbook, could not get all expected entries!!! Retrieved only %d/%d entries",iDaqLB,fgknDAQLbPar));
321                 error |= 1;
322         }
323
324         //=================//
325         // DAQ FXS         //
326         //=================//
327
328         Log("*************** Processing DAQ FXS");
329
330         UInt_t iDaqFxs = ProcessDaqFxs();
331         if( iDaqFxs == 0 ) {
332                 Log(Form("DAQ FXS, successful!"));
333         } else {
334                 Log(Form("DAQ FXS, could not store run raw tag file!!!"));
335                 error |= 2;
336         }
337         
338         //=================//
339         // DCS FXS         //
340         //=================//
341
342         Log("*************** Processing DCS FXS");
343
344         UInt_t iDcsFxs = ProcessDcsFxs(partition, detector);
345         if( iDcsFxs == 0 ) {
346                 Log(Form("DCS FXS, successful!"));
347         } else  if (iDcsFxs ==1) {
348                 Log(Form("DCS FXS, Could not store CTP scalers!!!"));
349                 error |= 4;
350         } else{
351                 Log(Form("Incorrect field in DAQ logbook for partition = %s and detector = %s, going into error without CTP scalers...",partition.Data(),detector.Data()));
352                 error |= 32;
353         }
354         
355         //=================//
356         // DCS data points //
357         //=================//
358
359         Log("*************** Processing DCS DPs");
360
361         Log(Form("Starting DCS Query at %d and finishing at %d",GetStartTimeDCSQuery(),GetEndTimeDCSQuery()));
362         Int_t entries = ProcessDcsDPs( valueMap, grpobj );
363         Log(Form("entries found = %d (should be %d)",entries, fgknDCSDP-fgkDCSDPNonWorking));
364         if (fdaqStartEndTimeOk){
365                 if( entries < fgknDCSDP - fgkDCSDPNonWorking ) { // L3_BSF4_H3, L3_BSF17_H1, L3_BSF17_H2, L3_BSF17_H3, L3_BSF17_Temperature are not working yet...  
366                         Log(Form("Possible problem with the DCS data points!!! Only %d/%d entries found - Please read further for more details",entries,fgknDCSDP-fgkDCSDPNonWorking));
367                         Log(Form("The DPs giving problems were:"));
368                         for (Int_t iDP = 0; iDP < fgknDCSDP; iDP++){
369                                 TObjString *dpString = (TObjString*)ffailedDPs->At(iDP);
370                                 if (dpString){
371                                         TString name = dpString->String();
372                                         if (name != "L3_BSF4_H3" && name != "L3_BSF17_H1" && name != "L3_BSF17_H2" && name != "L3_BSF17_H3" && name != "L3_BSF17_Temperature" ){
373                                                 Log(Form("******** %s ******** not present, but foreseen --> causing an ERROR",name.Data()));
374                                         }
375                                         else {
376                                                 Log(Form(" %s is not present, but was not generating any error since it is not ready in DCS - check the other DPs in this list!",name.Data()));
377                                         }
378                                 }
379                         }
380                         error |= 8;
381                 }
382                 else  Log(Form("DCS data points, successful!"));
383         }
384         else Log(Form("Statistical values for DCS DPs could not be computed due to missing DAQ_time_start and DAQ_time_end fields in DAQ logbook")); 
385         
386         //=======================//
387         // Trigger Configuration //
388         //=======================//
389
390         Log("*************** Processing Trigger Configuration");
391
392         const char * triggerConf = GetTriggerConfiguration();
393
394         if (partition.IsNull() && !detector.IsNull()){ // standalone partition
395                 Log("STANDALONE partition for current run, using Trigger Configuration dummy value");
396                 AliCDBEntry *cdbEntry = GetFromOCDB("CTP","DummyConfig");
397                 if (!cdbEntry) {
398                         Log(Form("No dummy CTP configuration entry found, going into error..."));
399                         error |= 16;
400                 }
401                 else{
402                         AliTriggerConfiguration *runcfg = (AliTriggerConfiguration*)cdbEntry->GetObject();
403                         if (!runcfg){
404                                 Log(Form("dummy CTP config not found in OCDB entry, going into error..."));
405                                 error |= 16;
406                         }
407                         else {
408                                 TString titleCTPcfg = Form("CTP cfg for run %i from Dummy entry in OCDB",fRun);
409                                 runcfg->SetTitle(titleCTPcfg);
410                                 AliCDBMetaData metaData;
411                                 metaData.SetResponsible("Roman Lietava");
412                                 metaData.SetComment("CTP run configuration from dummy entry in OCDB");
413                                 if (!Store("CTP","Config", runcfg, &metaData, 0, 0)) {
414                                         Log("Unable to store the dummy CTP run configuration object to OCDB!");
415                                         error |= 16;
416                                 }
417                         }
418                 }
419         }
420
421         else if (!partition.IsNull() && detector.IsNull()){ // global partition
422                 Log("GLOBAL partition for current run, using Trigger Configuration from DAQ Logbook");
423                 if (triggerConf!= NULL) {
424                         Log("Found trigger configuration in DAQ logbook");
425                         AliTriggerConfiguration *runcfg = AliTriggerConfiguration::LoadConfigurationFromString(triggerConf);      
426                         if (!runcfg) {
427                                 Log("Bad CTP run configuration file from DAQ logbook! The corresponding CDB entry will not be filled!");
428                                 error |= 16;
429                         }
430                         else {
431                                 TString titleCTPcfg = Form("CTP cfg for run %i from DAQ",fRun);
432                                 runcfg->SetTitle(titleCTPcfg);
433                                 AliCDBMetaData metaData;
434                                 metaData.SetBeamPeriod(0);
435                                 metaData.SetResponsible("Roman Lietava");
436                                 metaData.SetComment("CTP run configuration from DAQ logbook");
437                                 if (!Store("CTP","Config", runcfg, &metaData, 0, 0)) {
438                                         Log("Unable to store the CTP run configuration object to OCDB!");
439                                         error |= 16;
440                                 }
441                         }
442                 }
443
444                 else {
445                         Log("Trigger configuration NULL in DAQ logbook");
446                         error |= 16;
447                 }
448         }
449
450         else {
451                 Log(Form("Incorrect field in DAQ logbook for partition = %s and detector = %s, going into error without trigger configuration...",partition.Data(),detector.Data()));
452                 error |= 32;
453         }
454
455         //===========================//
456         // Trigger Timing Parameters //
457         //===========================//
458
459         Log("*************** Processing Trigger Time Params");
460         
461         const char * triggerCTPtiming = GetCTPTimeParams();
462
463         if (partition.IsNull() && !detector.IsNull()){ // standalone partition
464                 Log("STANDALONE partition for current run, using CTP timing params dummy value");
465                 AliCDBEntry *cdbEntry = GetFromOCDB("CTP","DummyCTPtime");
466                 if (!cdbEntry) {
467                         Log(Form("No dummy CTP timing parameters entry found, going into error..."));
468                         error |= 64;
469                 }
470                 else{
471                         AliCTPTimeParams *runCTPtiming = (AliCTPTimeParams*)cdbEntry->GetObject();
472                         if (!runCTPtiming){
473                                 Log(Form("dummy CTP timing parameters not found in OCDB entry, going into error..."));
474                                 error |= 64;
475                         }
476                         else {
477                                 TString titleCTPtiming = Form("CTP timing params for run %i from Dummy entry in OCDB",fRun);
478                                 runCTPtiming->SetTitle(titleCTPtiming);
479                                 AliCDBMetaData metadata;
480                                 metadata.SetResponsible("Roman Lietava");
481                                 metadata.SetComment("CTP run timing parameters from dummy entry in OCDB");
482                                 if (!Store("CTP","CTPtiming", runCTPtiming, &metadata, 0, 0)) {
483                                         Log("Unable to store the dummy CTP timing params object to OCDB!");
484                                         error |= 64;
485                                 }
486                         }
487                 }
488         }
489
490         else if (!partition.IsNull() && detector.IsNull()){ // global partition
491                 Log("GLOBAL partition for current run, using Trigger Timing Parameters from DAQ Logbook");
492                 if (triggerCTPtiming!= NULL) {
493                         Log("Found trigger timing params in DAQ logbook");
494                         AliDebug(2,Form("%s",triggerCTPtiming));
495                         AliCTPTimeParams *runCTPtiming = AliCTPTimeParams::LoadCTPTimeParamsFromString(triggerCTPtiming);         
496                         if (!runCTPtiming) {
497                                 Log("Bad CTP trigger timing params file from DAQ logbook! The corresponding CDB entry will not be filled!");
498                                 error |= 64;
499                         }
500                         else {
501                                 TString titleCTPtiming = Form("CTP timing params for run %i from DAQ",fRun);
502                                 runCTPtiming->SetTitle(titleCTPtiming);
503                                 AliCDBMetaData metadata;
504                                 metadata.SetBeamPeriod(0);
505                                 metadata.SetResponsible("Roman Lietava");
506                                 metadata.SetComment("CTP timing params from DAQ logbook");
507                                 if (!Store("CTP","CTPtiming", runCTPtiming, &metadata, 0, 0)) {
508                                         Log("Unable to store the CTP timing params object to OCDB!");
509                                         error |= 64;
510                                 }
511                         }
512                 }
513
514                 else {
515                         Log("Trigger timing params NULL in DAQ logbook");
516                         error |= 64;
517                 }
518         }
519
520         else {
521                 Log(Form("Incorrect field in DAQ logbook for partition = %s and detector = %s, going into error without trigger timing parameters...",partition.Data(),detector.Data()));
522                 error |= 32;
523         }
524
525         //===========================//
526         // LTU Configuration         //
527         //===========================//
528
529         Log("*************** Processing LTU Configuration");
530         
531         if (partition.IsNull() && !detector.IsNull()){ // standalone partition
532                 Log("STANDALONE partition for current run, using LTU configuration dummy value");
533                 AliCDBEntry *cdbEntry = GetFromOCDB("CTP","DummyLTUConfig");
534                 if (!cdbEntry) {
535                         Log(Form("No dummy LTU Config entry found, going into error..."));
536                         error |= 2048;
537                 }
538                 else{
539                         TObjArray *ltuConfig = (TObjArray*)cdbEntry->GetObject();
540                         if (!ltuConfig){
541                                 Log(Form("dummy LTU Config not found in OCDB entry, going into error..."));
542                                 error |= 2048;
543                         }
544                         else {
545                                 AliCDBMetaData metadata;
546                                 metadata.SetResponsible("Roman Lietava");
547                                 metadata.SetComment("LTU Config from dummy entry in OCDB");
548                                 if (!Store("CTP","LTUConfig", ltuConfig, &metadata, 0, 0)) {
549                                         Log("Unable to store the dummy LTU Config object to OCDB!");
550                                         error |= 2048;
551                                 }
552                         }
553                 }
554         }
555
556         else if (!partition.IsNull() && detector.IsNull()){ // global partition
557         
558                 Log("GLOBAL partition for current run, getting LTU Config from DAQ Logbook (logbook_detectors table)");
559                 UInt_t  detectorMask = (UInt_t)(((TString)GetRunParameter("detectorMask")).Atoi());
560                 Printf ("detectormask = %d",detectorMask);
561                 TObjArray * ltuarray = new TObjArray();
562                 ltuarray->SetOwner(1);
563                 Bool_t isLTUok = kTRUE;
564                 for(Int_t i = 0; i<AliDAQ::kNDetectors-2; i++){
565                         if ((detectorMask >> i) & 0x1) {
566                                 TString det = AliDAQ::OfflineModuleName(i);
567                                 TString detCTPName = AliTriggerInput::fgkCTPDetectorName[i];
568                                 if (detCTPName == "CTP") {
569                                         detCTPName="TRG"; // converting according to what is found in DAQ logbook_detectors                                     
570                                         Printf("Processing CTP (CTP Detector name %s) --> SKIPPING, CTP does not have any LTU!!!!!!",detCTPName.Data());
571                                         continue;
572                                 }                               
573                                 Printf("Processing detector %s (CTP Detector name %s)",det.Data(),detCTPName.Data());
574                                 TString* ltu = GetLTUConfig(detCTPName.Data());
575                                 if (!ltu){
576                                         Log(Form("No LTU Configuration from DAQ logbook for detector %s (BUT it was expected)! The corresponding CDB entry will not be filled!",detCTPName.Data()));
577                                         error |= 2048;
578                                         isLTUok = kFALSE;
579                                         break;
580                                 }
581                                 else{
582                                         Float_t ltuFineDelay1 = ltu[0].Atof();
583                                         Float_t ltuFineDelay2 = ltu[1].Atof();
584                                         Float_t ltuBCDelayAdd = ltu[2].Atof();
585                                         const char* name = AliDAQ::DetectorName(i);
586                                         AliLTUConfig* ltuConfig = new AliLTUConfig((UChar_t)AliDAQ::DetectorID(name),ltuFineDelay1,ltuFineDelay2,ltuBCDelayAdd);
587                                         ltuarray->AddAtAndExpand(ltuConfig,i);
588                                 }                               
589                         }
590                 }
591                 if (isLTUok){
592                         AliCDBMetaData metadata;
593                         metadata.SetBeamPeriod(0);
594                         metadata.SetResponsible("Roman Lietava");
595                         metadata.SetComment("LTU Configuration for current run");
596                         if (!Store("CTP","LTUConfig", ltuarray, &metadata, 0, 0)) {
597                                 Log("Unable to store the LTU Config object to OCDB!");
598                                 error |= 2048;
599                         }               
600                 }
601                 if (ltuarray) delete ltuarray;
602         }
603
604         else {
605                 Log(Form("Incorrect field in DAQ logbook for partition = %s and detector = %s, going into error without trigger timing parameters...",partition.Data(),detector.Data()));
606                 error |= 32;
607         }
608
609
610         //=================//
611         // LHC Data        //
612         //=================//
613
614         if (runType == "PHYSICS"){  // processing the LHC file only in PHYSICS runs
615                 Log("*************** Processing LHC Data");
616
617                 UInt_t iLHCData = ProcessLHCData(grpobj);
618                 
619                 if( iLHCData == 0 ) {
620                         Log(Form("LHC Data from DCS FXS, successful!"));
621                 } else  if (iLHCData == 1) {
622                         Log(Form("LHC Data, problems with DCS FXS!"));
623                         error |= 256;
624                 } else  if (iLHCData == 2) {
625                         Log(Form("LHC Data, problems with DAQ_time_start/DAQ_time_end!"));
626                         error |= 512;
627                 } else if (iLHCData ==3){
628                         Log(Form("Problems in storing LHC Phase - going into Error"));
629                         error |= 1024;
630                 } else if (iLHCData ==4){
631                         Log(Form("Problems with LHC Phase - going into Error"));
632                         error |= 1024;
633                 } else{
634                         Log(Form("LHC Data problems"));
635                         error |= 512;
636                 }
637         
638         }
639
640         //==================//
641         // SPD Mean Vertex  //
642         //==================//
643
644         Log("*************** Processing SPD Mean Vertex");
645
646         if (runType == "PHYSICS"){
647                 UInt_t iSPDMeanVertex = ProcessSPDMeanVertex();
648                 if( iSPDMeanVertex == 1 ) {
649                         Log(Form("SPD Mean Vertex, successful!"));
650                 } else {
651                         Log(Form("SPD Mean Vertex failed!!!"));
652                         error |= 128; 
653                 }
654         }
655         else {
656                 Log("SPD Mean Vertex not processed since runType != PHYSICS");
657         }
658
659         // storing AliGRPObject in OCDB
660
661         AliCDBMetaData md;
662         md.SetResponsible("Chiara Zampolli");
663         md.SetComment("Output parameters from the GRP preprocessor.");
664         
665         Bool_t result = kTRUE;
666         result = Store("GRP", "Data", grpobj, &md); 
667         delete grpobj;
668
669         if (result && !error ) {
670                 Log("GRP Preprocessor Success");
671                 return 0;
672         } else {
673                 Log( Form("GRP Preprocessor FAILS!!! %s%s%s%s%s%s%s%s%s%s%s%s",
674                           kppError[(error&1)?1:0],
675                           kppError[(error&2)?2:0],
676                           kppError[(error&4)?3:0],
677                           kppError[(error&8)?4:0],
678                           kppError[(error&16)?5:0],
679                           kppError[(error&32)?6:0],
680                           kppError[(error&64)?7:0],
681                           kppError[(error&128)?8:0],
682                           kppError[(error&256)?9:0],
683                           kppError[(error&512)?10:0],
684                           kppError[(error&1024)?11:0],
685                           kppError[(error&2048)?12:0]
686                           ));
687                 return error;
688         }
689
690
691 }
692
693 //_______________________________________________________________
694
695 UInt_t AliGRPPreprocessor::ProcessLHCData(AliGRPObject *grpobj)
696 {
697         //
698         //Getting the LHC Data from DCS FXS
699         //
700
701         TString timeStartString = (TString)GetRunParameter("DAQ_time_start");
702         TString timeEndString = (TString)GetRunParameter("DAQ_time_end");
703         if (timeStartString.IsNull() || timeEndString.IsNull()){
704                 if (timeStartString.IsNull()){ 
705                         AliError("DAQ_time_start not set in logbook! Setting statistical values for current DP to invalid");
706                 }
707                 else if (timeEndString.IsNull()){
708                         AliError("DAQ_time_end not set in logbook! Setting statistical values for current DP to invalid");
709                 }
710                 return 2;
711         }  
712
713         Double_t timeStart = timeStartString.Atof();
714         Double_t timeEnd = timeEndString.Atof();
715
716         TString fileName = GetFile(kDCS, "LHCData","");
717         if (fileName.Length()>0){
718                 AliInfo("Got The LHC Data file");
719                 AliLHCReader lhcReader;
720
721                 // Processing data to be put in AliGRPObject
722
723                 // Energy
724                 Log("*************Energy ");
725                 TObjArray* energyArray = lhcReader.ReadSingleLHCDP(fileName.Data(),fgkLHCDataPoints[0]);
726                 if (energyArray){                       
727                         Float_t energy = ProcessEnergy(energyArray,timeStart);
728                         if (energy != -1.) {
729                                 grpobj->SetBeamEnergy(energy);
730                                 grpobj->SetBeamEnergyIsSqrtSHalfGeV(kTRUE);
731                         }
732                         delete energyArray;
733                 }
734                 else {
735                         AliError("Energy not found in LHC Data file!!!");
736                 }       
737
738                 Double_t timeBeamModeEnd = timeEnd;        // max validity for Beam Mode 
739                 Double_t timeMachineModeEnd = timeEnd;     // max validity for Machine Mode
740                 Double_t timeBeamEnd = timeEnd;            // max validity for Beam Type
741                 Double_t timeBeamModeStart = -1;    // min validity for Beam Mode
742                 Double_t timeMachineModeStart = -1; // min validity for Machine Mode
743                 Double_t timeBeamStart = -1;        // min validity for Beam Type
744                 Int_t indexBeamMode = -1;                  // index of measurement used to set Beam Mode
745                 Int_t indexMachineMode = -1;               // index of measurement used to set Beam Mode
746                 Int_t indexBeam = -1;                      // index of measurement used to set Beam Mode
747                 Bool_t foundBeamModeStart = kFALSE;        // flag to be set in case an entry for the Beam Mode is found before (or at) SOR
748                 Bool_t foundMachineModeStart = kFALSE;     // flag to be set in case an entry for the Beam Mode is found before (or at) SOR
749                 Bool_t foundBeamStart = kFALSE;            // flag to be set in case an entry for the Beam Mode is found before (or at) SOR
750                 Bool_t flagBeamMode = kFALSE;  //flag set true if a changed occurred in BeamMode
751                 Bool_t flagMachineMode = kFALSE;  //flag set true if a changed occurred in MachineMode
752                 Bool_t flagBeam = kFALSE;  //flag set true if a changed occurred in BeamType
753                 
754                 // BeamMode
755                 Log("*************BeamMode (LHCState) ");
756                 TObjArray* beamModeArray = lhcReader.ReadSingleLHCDP(fileName.Data(),fgkLHCDataPoints[2]);
757                 Int_t nBeamMode = -1;
758                 if (beamModeArray){     
759                         nBeamMode = beamModeArray->GetEntries();        
760                         if (nBeamMode==0){
761                                 AliInfo("Found zero entries for the Beam Mode, leaving it empty");
762                         }
763                         else{
764                                 for (Int_t iBeamMode = 0; iBeamMode<nBeamMode; iBeamMode++){
765                                         AliDCSArray* beamMode = (AliDCSArray*)beamModeArray->At(iBeamMode);
766                                         if (beamMode){
767                                                 if (beamMode->GetTimeStamp()<=timeStart && beamMode->GetTimeStamp()>=timeBeamModeStart){// taking always the very last entry: of two measurements have the same timestamp, the last one is taken
768                                                         timeBeamModeStart = beamMode->GetTimeStamp();
769                                                         indexBeamMode = iBeamMode;
770                                                         foundBeamModeStart = kTRUE;
771                                                 }
772                                                 else {
773                                                         break;
774
775                                                 }
776                                         }
777                                 }
778                                 if (!foundBeamModeStart){
779                                         AliInfo("No value for the Beam Mode found before start of run, the Beam Mode will remain empty");
780                                 }
781                                 else {
782                                         AliDCSArray* beamMode = (AliDCSArray*)beamModeArray->At(indexBeamMode);
783                                         TObjString* beamModeString = beamMode->GetStringArray(0);
784                                         AliInfo(Form("LHC State (corresponding to BeamMode) = %s (set at %f)",(beamModeString->String()).Data(),beamMode->GetTimeStamp()));
785                                         grpobj->SetLHCState(beamModeString->String());
786                                         if (indexBeamMode < nBeamMode-1){
787                                                 AliDCSArray* beamMode1 = (AliDCSArray*)beamModeArray->At(indexBeamMode+1);
788                                                 if (beamMode1){
789                                                         if (beamMode1->GetTimeStamp()<=timeStart){
790                                                                 AliError("you did not choose the correct value! there is still something before (or at) SOR, but later than this!");
791                                                         }
792                                                         else if (beamMode1->GetTimeStamp()>timeStart && beamMode1->GetTimeStamp()<=timeEnd){
793                                                                 timeBeamModeEnd = beamMode1->GetTimeStamp();
794                                                                 TObjString* beamModeString1 = beamMode1->GetStringArray(0);
795                                                                 TString bmString0 = beamModeString->String();
796                                                                 TString bmString1 = beamModeString1->String();
797                                                                 if (bmString0.CompareTo(bmString1.Data(),TString::kIgnoreCase) == -1){
798                                                                         AliWarning(Form("The beam mode changed from %s to %s during the run at timestamp %f! Setting it to %s and keeping track of the time of the change to set MaxTimeLHCValidity afterward",bmString0.Data(), bmString1.Data(), timeBeamModeEnd, bmString0.Data()));
799                                                                         flagBeamMode = kTRUE;
800                                                                 }
801                                                         }
802                                                 }
803                                                 else {
804                                                         AliInfo("Invalid pointer for the first entry for Beam Mode after the first valid one, not considering anything after what has already been found");
805                                                 }
806                                         }
807                                 }
808                         }
809                         delete beamModeArray;
810                 }
811                 else{
812                         AliError("Beam mode array not found in LHC Data file!!!");
813                 }
814                 
815                 // MachineMode
816                 Log("*************MachineMode ");
817                 TObjArray* machineModeArray = lhcReader.ReadSingleLHCDP(fileName.Data(),fgkLHCDataPoints[1]);
818                 Int_t nMachineMode = -1;
819                 if (machineModeArray){
820                         nMachineMode = machineModeArray->GetEntries();
821                         if (nMachineMode==0){
822                                 AliInfo("No Machine Mode found, leaving it empty");
823                         }
824                         else{
825                                 for (Int_t iMachineMode = 0; iMachineMode<nMachineMode; iMachineMode++){
826                                         AliDCSArray* machineMode = (AliDCSArray*)machineModeArray->At(iMachineMode);
827                                         if (machineMode){
828                                                 if (machineMode->GetTimeStamp()<=timeStart && machineMode->GetTimeStamp()>=timeMachineModeStart){// taking always the very last entry: of two measurements have the same timestamp, the last one is taken
829                                                         timeMachineModeStart = machineMode->GetTimeStamp();
830                                                         indexMachineMode = iMachineMode;
831                                                         foundMachineModeStart = kTRUE;
832                                                 }
833                                                 else{
834                                                         break;
835                                                 }
836                                         }
837                                 }
838                                 if (!foundMachineModeStart){
839                                         AliInfo("No value for the Machine Mode found before start of run, the Machine Mode will remain empty");
840                                 }
841                                 else {
842                                         AliDCSArray* machineMode = (AliDCSArray*)machineModeArray->At(indexMachineMode);
843                                         TObjString* machineModeString = machineMode->GetStringArray(0);
844                                         AliInfo(Form("MachineMode = %s (set at %f)",(machineModeString->String()).Data(),machineMode->GetTimeStamp()));
845                                         grpobj->SetMachineMode(machineModeString->String());
846                                         if (indexMachineMode < nMachineMode-1){
847                                                 AliDCSArray* machineMode1 = (AliDCSArray*)machineModeArray->At(indexMachineMode+1);
848                                                 if (machineMode1){
849                                                         if (machineMode1->GetTimeStamp()>timeStart && machineMode1->GetTimeStamp()<=timeEnd){
850                                                                 timeMachineModeEnd = machineMode1->GetTimeStamp();
851                                                                 TObjString* machineModeString1 = machineMode1->GetStringArray(0);
852                                                                 TString mmString0 = machineModeString->String();
853                                                                 TString mmString1 = machineModeString1->String();
854                                                                 if (mmString0.CompareTo(mmString1.Data(),TString::kIgnoreCase) == -1){
855                                                                         AliWarning(Form("The machine mode changed from %s to %s during the run at timestamp %f! Setting it to %s and keeping track of the time of the change to set MaxTimeLHCValidity afterward",mmString0.Data(),mmString1.Data(),timeMachineModeEnd,mmString0.Data()));
856                                                                         flagMachineMode = kTRUE;
857                                                                 }
858                                                         }
859                                                 }
860                                                 else {
861                                                         AliInfo("Invalid pointer for the first entry for Machine Mode after the first valid one, not considering anything after what has already been found");
862                                                 }
863                                         }
864                                 }
865                         }
866                         delete machineModeArray;
867                 }
868                 else{
869                         AliError("Machine mode array not found in LHC Data file!!!");
870                 }
871                 
872                 // BeamType1 and BeamType2 - both put in the same string
873                 Log("*************BeamType ");
874                 TObjArray* beamArray = lhcReader.ReadSingleLHCDP(fileName.Data(),fgkLHCDataPoints[3]);
875                 if (beamArray){                 
876                         Int_t nBeam = beamArray->GetEntries();
877                         if (nBeam==0){
878                                 AliInfo("No Beam Type found, leaving it empty");
879                         }
880                         else{
881                                 for (Int_t iBeam = 0; iBeam<nBeam; iBeam++){
882                                         AliDCSArray* beam = (AliDCSArray*)beamArray->At(iBeam);
883                                         if (beam){
884                                                 if (beam->GetTimeStamp()<=timeStart && beam->GetTimeStamp()>=timeBeamStart){// taking always the very last entry: of two measurements have the same timestamp, the last one is taken
885                                                         timeBeamStart = beam->GetTimeStamp();
886                                                         indexBeam = iBeam;
887                                                         foundBeamStart = kTRUE;
888                                                 }
889                                                 else{
890                                                         break;
891                                                 }
892                                         }
893                                 }
894                                 if (!foundBeamStart){
895                                         AliInfo("No value for the Beam Type found before start of run, the Machine Mode will remain empty");
896                                 }
897                                 else {
898                                         AliDCSArray* beam = (AliDCSArray*)beamArray->At(indexBeam);
899                                         TObjString* beamString = beam->GetStringArray(0);
900                                         TString beamType = beamString->String();
901                                         AliInfo(Form("Beam Type = %s",beamType.Data()));        
902                                         if (beamType.CompareTo("PROTON",TString::kIgnoreCase) == 0){
903                                                 AliInfo("Setting beam type to p-p");
904                                                 grpobj->SetBeamType("p-p");
905                                         }
906                                         else { // if there is no PROTON beam, we suppose it is Pb, and we put A-A
907                                                 AliInfo("Setting beam type to A-A");
908                                                 grpobj->SetBeamType("A-A");
909                                         }
910                                         /*
911                                           else if (beamType.CompareTo("LEAD82",TString::kIgnoreCase) == 0){
912                                                 AliInfo("Setting beam type to Pb-Pb");
913                                                 grpobj->SetBeamType("Pb-Pb");
914                                         }
915                                         else{
916                                                 AliError("Beam Type not known, leaving it empty");
917                                         }
918                                         */
919                                         if (indexBeam < nBeam-1){
920                                                 AliDCSArray* beam1 = (AliDCSArray*)beamArray->At(indexBeam+1);
921                                                 if (beam1){
922                                                         if (beam1->GetTimeStamp()>timeStart && beam1->GetTimeStamp()<=timeEnd){
923                                                                 timeBeamEnd = beam1->GetTimeStamp();
924                                                                 TObjString* beamString1 = beam1->GetStringArray(0);
925                                                                 TString beamType1 = beamString1->String();
926                                                                 if (beamType.CompareTo(beamType1.Data(),TString::kIgnoreCase) == -1){
927                                                                         AliWarning(Form("The Beam Type changed from %s to %s during the run at timestamp %f! Setting it to %s and keeping track of the time of the change to set MaxTimeLHCValidity afterward",beamType.Data(),(beamString1->String()).Data(),timeBeamEnd,beamType.Data()));
928                                                                         flagBeam = kTRUE;
929                                                                 }
930                                                         }
931                                                 }
932                                                 else {
933                                                         AliInfo("Invalid pointer for the first entry for Beam Type after the first valid one, not considering anything after what has already been found");
934                                                 }
935                                         }
936                                 }
937                         }
938                         delete beamArray;
939                 }
940                 else{
941                         AliError("Beam Type array not found in LHC Data file!!!");
942                 }               
943                 
944                 // Setting minTimeLHCValidity
945                 if (timeBeamModeEnd!=0 || timeMachineModeEnd!=0 || timeBeamEnd !=0){
946                         Double_t minTimeLHCValidity;
947                         if (flagBeamMode == kFALSE && flagMachineMode == kFALSE && flagBeam == kTRUE){ // flagBeam only true
948                                 minTimeLHCValidity = timeBeamEnd;
949                         }
950                         else if (flagBeamMode == kFALSE && flagMachineMode == kTRUE && flagBeam == kFALSE){ // flagMachineMode only true
951                                 minTimeLHCValidity = timeMachineModeEnd;
952                         }
953                         else if (flagBeamMode == kTRUE && flagMachineMode == kFALSE && flagBeam == kFALSE){ // flagBeamMode only true
954                                 minTimeLHCValidity = timeBeamModeEnd;
955                         }
956                         else if (flagBeamMode == kFALSE && flagMachineMode == kTRUE && flagBeam == kTRUE){ // flagBeam and flagMachineMode only true
957                                 minTimeLHCValidity= TMath::Min(timeBeamEnd,timeMachineModeEnd);
958                         }
959                         else if (flagBeamMode == kTRUE && flagMachineMode == kFALSE && flagBeam == kTRUE){ // flagBeam and flagBeamMode only true
960                                 minTimeLHCValidity= TMath::Min(timeBeamEnd,timeBeamModeEnd);
961                         }
962                         else if (flagBeamMode == kTRUE && flagMachineMode == kTRUE && flagBeam == kFALSE){ // flagMachineMode and flagBeamMode only true
963                                 minTimeLHCValidity= TMath::Min(timeMachineModeEnd,timeBeamModeEnd);
964                         }
965                         else {
966                                 Double_t arrayTimes[3] = {timeBeamModeEnd,timeMachineModeEnd,timeBeamEnd};// flagMachineMode and flagBeamMode and flagBeam 
967                                 minTimeLHCValidity= TMath::MinElement(3,arrayTimes);
968                         }
969                         AliWarning(Form("Setting MaxTimeLHCValidity to %f",minTimeLHCValidity));
970                         grpobj->SetMaxTimeLHCValidity(minTimeLHCValidity);
971                 }
972                 
973                 // Processing data to go to AliLHCData object
974                 AliLHCData* dt = new AliLHCData(fileName.Data(),timeStart,timeEnd);
975                 // storing AliLHCData in OCDB
976                 if (dt){
977                   AliInfo(Form("Filled %d records to AliLHCData object",dt->GetData().GetEntriesFast()));
978                   AliCDBMetaData md;
979                   md.SetResponsible("Ruben Shahoyan");
980                   md.SetComment("LHC data from the GRP preprocessor.");
981                   Bool_t result = kTRUE;
982                   result = Store("GRP", "LHCData", dt, &md); 
983                   delete dt;
984                   if (!result){
985                         Log(Form("Problems in storing LHC Data - but not going into Error"));
986                   }
987                 }
988
989                 // processing LHC Phase
990
991                 TObjArray *beam1phase = lhcReader.ReadSingleLHCDP(fileName.Data(),fgkLHCDataPoints[4]);
992                 TObjArray *beam2phase = lhcReader.ReadSingleLHCDP(fileName.Data(),fgkLHCDataPoints[5]);
993                 if (beam1phase == 0x0 || beam2phase == 0x0){
994                         Log(Form("Problems in retrieving LHC Clock data from LHC file"));
995                         return 4;
996                 }                       
997                 AliLHCClockPhase *phaseObj = ProcessLHCClockPhase(beam1phase,beam2phase,timeEnd);
998                 if (phaseObj){
999                         AliInfo(Form("LHC Phase found"));
1000                         AliCDBMetaData mdPhase;
1001                         mdPhase.SetResponsible("Cvetan Cheshkov");
1002                         mdPhase.SetComment("LHC Clock Phase");
1003                         Bool_t result = kTRUE;
1004                         result = Store("Calib", "LHCClockPhase", phaseObj, &mdPhase); 
1005                         delete phaseObj;
1006                         if (!result) return 3;
1007                 }
1008                 else return 4;
1009         }
1010         
1011         else {
1012                 AliError("No LHCData file found in DCS FXS");
1013                 return 1;
1014         }
1015
1016         return 0;
1017 }
1018
1019 //_______________________________________________________________
1020
1021 UInt_t AliGRPPreprocessor::ProcessSPDMeanVertex()
1022 {
1023         //
1024         //Getting the SPD Mean Vertex
1025         //
1026
1027         TList* list = GetForeignFileSources("SPD", kDAQ, "VertexDiamond");
1028         Bool_t storeResult = kTRUE;
1029         if (list !=0x0 && list->GetEntries()!=0)
1030                 {
1031                         AliInfo("The following sources produced files with the id VertexDiamond from SPD");
1032                         list->Print();
1033                         for (Int_t jj=0;jj<list->GetEntries();jj++){
1034                                 TObjString * str = dynamic_cast<TObjString*> (list->At(jj));
1035                                 AliInfo(Form("found source %s", str->String().Data()));
1036                                 TString fileNameRun = GetForeignFile("SPD", kDAQ, "VertexDiamond", str->GetName());
1037                                 if (fileNameRun.Length()>0){
1038                                         AliInfo(Form("Got the file %s", fileNameRun.Data()));
1039                                         TFile daqFile(fileNameRun.Data(),"READ");
1040                                         if (daqFile.IsOpen()) {
1041                                                 AliESDVertex* meanVtx = dynamic_cast<AliESDVertex*>(daqFile.Get("MeanVertexPos"));
1042                                                 if (meanVtx){
1043                                                         meanVtx->Print();       
1044                                                         // storing in the OCDB 
1045                                                         AliCDBMetaData md;
1046                                                         md.SetResponsible("Cvetan Cheshkov");
1047                                                         md.SetComment("SPD Mean Vertex");                                       
1048                                                         storeResult = Store("Calib", "MeanVertexSPD", meanVtx, &md, 0, kTRUE); 
1049                                                 }
1050                                                 else{
1051                                                         AliWarning("No SPD Mean Vertex object found in file");
1052                                                 } 
1053                                         }
1054                                         else {
1055                                                 AliError("Can't open file");
1056                                                 storeResult = kFALSE;
1057                                         }
1058                                 }
1059                                 else{
1060                                         AliWarning("No file found for current source for SPD Mean Vertex");
1061                                 }
1062                         }
1063                 }
1064         else {
1065                 AliWarning("No list found for SPD Mean Vertex");
1066         }
1067
1068         if (list) delete list;
1069
1070         return storeResult;
1071 }
1072
1073
1074 //_______________________________________________________________
1075
1076 Int_t AliGRPPreprocessor::ProcessDaqLB(AliGRPObject* grpObj)
1077 {
1078         //Getting the DAQ lb information
1079         
1080         time_t timeStart = (time_t)(((TString)GetRunParameter("DAQ_time_start")).Atoi());
1081         time_t timeEnd = (time_t)(((TString)GetRunParameter("DAQ_time_end")).Atoi());
1082         Float_t beamEnergy = (Float_t)(((TString)GetRunParameter("beamEnergy")).Atof());
1083         TString beamType = (TString)GetRunParameter("beamType");
1084         Char_t numberOfDetectors = (Char_t)(((TString)GetRunParameter("numberOfDetectors")).Atoi());
1085         UInt_t  detectorMask = (UInt_t)(((TString)GetRunParameter("detectorMask")).Atoi());
1086         TString lhcPeriod = (TString)GetRunParameter("LHCperiod");
1087         TString runType = (TString)GetRunType();
1088
1089         UInt_t nparameter = 0;
1090         if (timeStart != 0){
1091                 grpObj->SetTimeStart(timeStart);
1092                 Log(Form("Start time for run %d: %d",fRun, (Int_t)timeStart));
1093                 nparameter++;
1094         } 
1095         else {
1096                 Log(Form("Start time not put in logbook, setting to invalid in GRP entry, and causing an error!"));
1097         }
1098
1099         if (timeEnd != 0){
1100                 grpObj->SetTimeEnd(timeEnd);
1101                 Log(Form("End time for run %d: %i",fRun, (Int_t)timeEnd));
1102                 nparameter++;
1103         } 
1104         else {
1105                 Log(Form("End time not put in logbook, setting to invalid in GRP entry, and causing an error!"));
1106         }
1107
1108         if (beamEnergy != 0){
1109                 Log(Form("Beam Energy for run %d: %f (NOT USING IT TO FILL THE GRP OBJECT, taking it from the LHC file)",fRun, beamEnergy));
1110         } 
1111         else {
1112                 Log(Form("Beam Energy not put in logbook, but not using it anyway for the GRP object (taking it from the LHC file)"));
1113         }
1114
1115                 
1116         if (beamType.Length() != 0){
1117                 Log(Form("Beam Type for run %d: %s (NOT USING IT TO FILL THE GRP OBJECT, taking it from the LHC file)",fRun, beamType.Data()));
1118         } 
1119         else {
1120                 Log(Form("Beam Type not put in logbook, but not using it anyway for the GRP entry (taking it from the LHC file)"));
1121         }
1122                 
1123         if (numberOfDetectors != 0){
1124                 grpObj->SetNumberOfDetectors(numberOfDetectors);
1125                 Log(Form("Number Of Detectors for run %d: %d",fRun, (Int_t)numberOfDetectors));
1126                 nparameter++;
1127         } 
1128         else {
1129                 Log(Form("Number Of Detectors not put in logbook, setting to invalid in GRP entry, and causing an error!"));
1130         }
1131
1132         if (detectorMask != 0){
1133                 grpObj->SetDetectorMask(detectorMask);
1134                 Log(Form("Detector Mask for run %d: %d",fRun, detectorMask));
1135                 nparameter++;
1136         } 
1137         else {
1138                 Log(Form("Detector Mask not put in logbook, setting to invalid in GRP entry, and causing an error!"));
1139         }
1140
1141         if (lhcPeriod.Length() != 0) {
1142                 grpObj->SetLHCPeriod(lhcPeriod);
1143                 Log(Form("LHC period (DAQ) for run %d: %s",fRun, lhcPeriod.Data()));
1144                 nparameter++;
1145         } 
1146         else {
1147                 Log(Form("LHCperiod not put in logbook, setting to invalid in GRP entry, and causing an error!"));
1148         }
1149         if (runType.Length() != 0) {
1150                 grpObj->SetRunType(runType);
1151                 Log(Form("Run Type (DAQ) for run %d: %s",fRun, runType.Data()));
1152                 nparameter++;
1153         } 
1154         else {
1155                 Log(Form("Run Type not put in logbook, setting to invalid in GRP entry, and causing an error!"));
1156         }
1157
1158         return nparameter;
1159 }
1160
1161 //_______________________________________________________________
1162
1163 UInt_t AliGRPPreprocessor::ProcessDaqFxs()
1164 {
1165         //======DAQ FXS======//
1166         
1167         AliRawEventHeaderV3_9::Class()->IgnoreTObjectStreamer(); // to avoid trying reading TObject store in AliRawEventHeaderV3_9 - temporary fix 
1168         TList* list = GetFileSources(kDAQ);  
1169         if (!list) {
1170                 Log("No raw data tag list: connection problems with DAQ FXS logbook!");
1171                 return 1;
1172         }
1173         
1174         if (list->GetEntries() == 0) {
1175                 Log("no raw data tags in this run: nothing to merge!");
1176                 delete  list; list=0;
1177                 return 0;
1178         }
1179         
1180         TChain *fRawTagChain = new TChain("T");
1181         Int_t nFiles=0;
1182         TIterator* iter = list->MakeIterator();
1183         TObject* obj = 0;
1184         while ((obj = iter->Next())) {
1185                 TObjString* objStr = dynamic_cast<TObjString*> (obj);
1186                 if (objStr) {
1187                         Log(Form("Found source %s", objStr->String().Data()));
1188                         TList* list2 = GetFileIDs(kDAQ, objStr->String());
1189                         if (!list2) {
1190                                 Log("No list with ids from DAQ was found: connection problems with DAQ FXS logbook!");
1191                                 delete fRawTagChain; fRawTagChain=0;
1192                                 return 1;
1193                         }
1194                         Log(Form("Number of ids: %d",list2->GetEntries()));
1195                         for(Int_t i = 0; i < list2->GetEntries(); i++) {
1196                                 TObjString *idStr = (TObjString *)list2->At(i);
1197                                 TString fileName = GetFile(kDAQ,idStr->String().Data(),objStr->String().Data());
1198                                 if (fileName.Length() > 0) {
1199                                         Log(Form("Adding file in the chain: %s",fileName.Data()));
1200                                         fRawTagChain->Add(fileName.Data());
1201                                         nFiles++;
1202                                 } else {
1203                                         Log(Form("Could not retrieve file with id %s from source %s: "
1204                                                  "connection problems with DAQ FXS!",
1205                                                  idStr->String().Data(), objStr->String().Data()));
1206                                         delete list; list=0;
1207                                         delete list2; list2=0;
1208                                         delete fRawTagChain; fRawTagChain=0;
1209                                         return 2;
1210                                 }
1211                         }
1212                         delete list2;
1213                 }
1214         }
1215         
1216         TString fRawDataFileName = "GRP_Merged.tag.root";
1217         Log(Form("Merging %d raw data tags into file: %s", nFiles, fRawDataFileName.Data()));
1218         
1219         if( fRawTagChain->Merge(fRawDataFileName) < 1 ) {
1220                 Log("Error merging raw data files!!!");
1221                 return 3;
1222         }
1223         
1224         TString outputfile = Form("Run%d.Merged.RAW.tag.root", fRun);
1225         Bool_t result = StoreRunMetadataFile(fRawDataFileName.Data(),outputfile.Data());
1226         
1227         if (!result) {
1228                 Log("Problem storing raw data tags in local file!!!");
1229         } else {
1230                 Log("Raw data tags merged successfully!!");
1231         }
1232         
1233         delete iter;
1234         delete list;
1235         delete fRawTagChain; fRawTagChain=0;
1236         
1237         if (result == kFALSE) {
1238                 return 4;
1239         }
1240         
1241         return 0;
1242         
1243 }
1244
1245 //_______________________________________________________________
1246 UInt_t AliGRPPreprocessor::ProcessDcsFxs(TString partition, TString detector)
1247 {
1248
1249         // processing the info
1250         // stored in the DCS FXS
1251         // coming from the trigger
1252
1253         // Get the CTP counters information
1254
1255         if (partition.IsNull() && !detector.IsNull()){ // standalone partition
1256                 Log("STANDALONE partition for current run, using Trigger Scalers dummy value");
1257                 AliCDBEntry *cdbEntry = GetFromOCDB("CTP","DummyScalers");
1258                 if (!cdbEntry) {
1259                         Log(Form("No dummy CTP scalers entry found, going into error..."));
1260                         return 1;
1261                 }
1262                 else{
1263                         AliTriggerRunScalers *scalers = (AliTriggerRunScalers*)cdbEntry->GetObject();
1264                         if (!scalers){
1265                                 Log(Form("CTP dummy scalers not found in OCDB entry, going into error..."));
1266                                 return 1;
1267                         }
1268                         else {
1269                                 AliCDBMetaData metaData;
1270                                 metaData.SetResponsible("Roman Lietava");
1271                                 metaData.SetComment("CTP scalers from dummy entry in OCDB");
1272                                 if (!Store("CTP","Scalers", scalers, &metaData, 0, 0)) {
1273                                         Log("Unable to store the dummy CTP scalers object to OCDB!");
1274                                         return 1;
1275                                 }
1276                         }
1277                 }
1278         }
1279
1280         else if (!partition.IsNull() && detector.IsNull()){ // global partition
1281                 Log("GLOBAL partition for current run, using CTP scalers from DCS FXS");
1282                 TString countersfile = GetFile(kDCS, "CTP_xcounters","");
1283                 if (countersfile.IsNull()) {
1284                         Log("No CTP counters files has been found: empty source!");
1285                         return 1;
1286                 }
1287                 else {
1288                         Log(Form("File with Id CTP_xcounters found in DCS FXS! Copied to %s",countersfile.Data()));
1289                         AliTriggerRunScalers *scalers = AliTriggerRunScalers::ReadScalers(countersfile);
1290                         if (!scalers) {
1291                                 Log("Bad CTP counters file! The corresponding CDB entry will not be filled!");
1292                                 return 1;
1293                         }
1294                         else {
1295                                 AliCDBMetaData metaData;
1296                                 metaData.SetBeamPeriod(0);
1297                                 metaData.SetResponsible("Roman Lietava");
1298                                 metaData.SetComment("CTP scalers");
1299                                 if (!Store("CTP","Scalers", scalers, &metaData, 0, 0)) {
1300                                         Log("Unable to store the CTP scalers object to OCDB!");
1301                                         delete scalers;                                 
1302                                         return 1;
1303                                 }
1304                         }
1305                         delete scalers;
1306                 }
1307         }
1308         
1309
1310         else{   
1311                 Log(Form("Incorrect field in DAQ logbook for partition = %s and detector = %s, going into error...",partition.Data(),detector.Data()));
1312                 return 2;
1313         }
1314
1315         return 0;
1316
1317 }
1318 //_______________________________________________________________
1319
1320 Int_t AliGRPPreprocessor::ProcessDcsDPs(TMap* valueMap, AliGRPObject* grpObj)
1321 {
1322
1323         //
1324         // processing DCS DPs
1325         //
1326
1327         Int_t entries = 0;  // counting the entries that are in the DCS DB, not taking care whether they have values or not
1328         Int_t nL3Entries = 0;
1329         Int_t nDipoleEntries = 0;
1330         Int_t nEnvEntries = 0;
1331         Int_t nHallProbesEntries = 0;
1332         nL3Entries = ProcessL3DPs(valueMap, grpObj);
1333         nDipoleEntries = ProcessDipoleDPs(valueMap, grpObj);
1334         nEnvEntries = ProcessEnvDPs(valueMap, grpObj);
1335         nHallProbesEntries = ProcessHPDPs(valueMap, grpObj);
1336         grpObj->SetPolarityConventionLHC();  // after the dipole cables swap we comply with LHC convention
1337         Log(Form("L3Entries = %d, nDipoleEntries =%d, nEnvEntries = %d, nHallProbesEntries = %d", nL3Entries, nDipoleEntries, nEnvEntries, nHallProbesEntries));
1338         entries = nL3Entries + nDipoleEntries + nEnvEntries + nHallProbesEntries;
1339         return entries;
1340
1341 }
1342
1343 //_______________________________________________________________
1344
1345 Int_t AliGRPPreprocessor::ProcessL3DPs(const TMap* valueMap, AliGRPObject* grpObj)
1346 {
1347
1348         // processing DPs
1349         // related to 
1350         // L3 info
1351
1352         Int_t nL3Entries = 0;
1353
1354         TObjArray *array = 0x0;
1355         Int_t indexDP = -1;
1356         Bool_t isZero = kTRUE; // flag to monitor L3Current. If set to true, the magnet is OFF, and the polarity can change
1357
1358         AliInfo(Form("==========L3Current==========="));
1359         Bool_t outOfRange = kFALSE;  // flag to monitor if any value collected by DCS is out of range
1360         indexDP = kL3Current;
1361         array = (TObjArray *)valueMap->GetValue(fgkDCSDataPoints[indexDP]);
1362         if(!array) {
1363                 Log(Form("%s not found in the map!!!",fgkDCSDataPoints[indexDP]));
1364         } 
1365         else {
1366                 if (array->GetEntries() == 0){
1367                         AliError(Form("No entries found in array! setting %s to invalid...",fgkDCSDataPoints[indexDP]));
1368                 }
1369                 else {
1370                         Float_t *floatDCS = ProcessFloatAllMagnet(array, indexDP, isZero);
1371                         if (floatDCS != NULL){
1372                                 grpObj->SetL3Current(floatDCS);
1373                         }
1374                         else{
1375                                 outOfRange = kTRUE;
1376                         }       
1377                         if (floatDCS){
1378                                 delete[] floatDCS;
1379                                 floatDCS = 0x0;
1380                         }
1381                 }
1382                 if (!outOfRange) {
1383                         nL3Entries++;
1384                         ffailedDPs->RemoveAt(indexDP);
1385                 }
1386         }
1387
1388         if (array) array = 0x0;
1389
1390         AliInfo(Form("==========L3Polarity==========="));
1391         indexDP = kL3Polarity;
1392         array = (TObjArray *)valueMap->GetValue(fgkDCSDataPoints[indexDP]);
1393         if(!array) {
1394                 Log(Form("%s not found in the map!!!",fgkDCSDataPoints[indexDP]));
1395         } 
1396         else {
1397                 if (array->GetEntries() == 0){
1398                         AliError(Form("No entries found in array! setting %s Polarity to invalid...",fgkDCSDataPoints[indexDP]));
1399                 }
1400                 else {
1401                         Bool_t change = kFALSE;
1402                         Char_t charDCS = ProcessBool(array,change);
1403                         if (change == kFALSE){
1404                                 grpObj->SetL3Polarity(charDCS);
1405                                 AliInfo(Form("%s set to %d",fgkDCSDataPoints[indexDP],(Int_t)(grpObj->GetL3Polarity())));
1406                                 ffailedDPs->RemoveAt(indexDP);
1407                                 nL3Entries++;
1408                         }
1409                         else if (isZero){
1410                                 AliInfo(Form("%s set to invalid, but magnet was OFF (according to the current), DP not considered wrong",fgkDCSDataPoints[indexDP]));
1411                                 ffailedDPs->RemoveAt(indexDP);
1412                                 nL3Entries++;
1413                         }
1414                         else {
1415                                 AliError(Form("%s value changed within the run, while the magnet was ON (according to the current), setting it to invalid and considering the DP as wrong",fgkDCSDataPoints[indexDP]));
1416                         }
1417                 }
1418         }
1419
1420         return nL3Entries;
1421
1422 }
1423 //_______________________________________________________________
1424
1425 Int_t AliGRPPreprocessor::ProcessDipoleDPs(const TMap* valueMap, AliGRPObject* grpObj)
1426 {
1427         // processing DPs
1428         // related to 
1429         // the Dipole info
1430
1431         Int_t nDipoleEntries = 0;
1432         TObjArray *array = 0x0;
1433         Int_t indexDP = -1;
1434         Bool_t isZero = kTRUE; // flag to monitor L3Current. If set to true, the magnet is OFF, and the polarity can change
1435
1436         AliInfo(Form("==========DipoleCurrent==========="));
1437         Bool_t outOfRange = kFALSE;  // flag to monitor if any value collected by DCS is out of range
1438         indexDP = kDipoleCurrent;
1439         array = (TObjArray *)valueMap->GetValue(fgkDCSDataPoints[indexDP]);
1440         if(!array) {
1441                 Log(Form("%s not found in the map!!!",fgkDCSDataPoints[indexDP]));
1442         } 
1443         else {
1444                 if (array->GetEntries() == 0){
1445                         AliError(Form("No entries found in array! setting %s to invalid...",fgkDCSDataPoints[indexDP]));
1446                 }
1447                 else {
1448                         Float_t *floatDCS = ProcessFloatAllMagnet(array, indexDP, isZero);
1449                         if (floatDCS != NULL){
1450                                 grpObj->SetDipoleCurrent(floatDCS);
1451                         } 
1452                         else{
1453                                 outOfRange=kTRUE;
1454                         }
1455                         if (floatDCS){
1456                                 delete[] floatDCS;
1457                                 floatDCS = 0x0;
1458                         }
1459                 }
1460                 if (!outOfRange) {
1461                         nDipoleEntries++;
1462                         ffailedDPs->RemoveAt(indexDP);
1463                 }
1464         }
1465
1466         if (array) array = 0x0;
1467
1468         AliInfo(Form("==========DipolePolarity==========="));
1469         indexDP = kDipolePolarity;
1470         array = (TObjArray *)valueMap->GetValue(fgkDCSDataPoints[indexDP]);
1471         if(!array) {
1472                 Log(Form("%s not found in the map!!!",fgkDCSDataPoints[indexDP]));
1473         } 
1474         else {
1475                 if (array->GetEntries() == 0){
1476                         AliError(Form("No entries found in array! setting %s to invalid...",fgkDCSDataPoints[indexDP]));
1477                 }
1478                 else {
1479                         Bool_t change = kFALSE;
1480                         Char_t charDCS = ProcessBool(array,change);
1481                         if (!change){
1482                                 grpObj->SetDipolePolarity(charDCS);
1483                                 AliInfo(Form("%s set to %d",fgkDCSDataPoints[indexDP],(Int_t)(grpObj->GetDipolePolarity())));
1484                                 ffailedDPs->RemoveAt(indexDP);
1485                                 nDipoleEntries++;
1486                         }
1487                         else if (isZero){
1488                                 AliInfo(Form("%s set to invalid, but magnet was OFF (according to the current), DP not considered wrong",fgkDCSDataPoints[indexDP]));
1489                                 ffailedDPs->RemoveAt(indexDP);
1490                                 nDipoleEntries++;
1491                         }
1492                         else{
1493                                 AliError(Form("%s value changed within the run while the magnet was ON (according to the current), setting it to invalid and considering the DP as wrong", fgkDCSDataPoints[indexDP]));
1494                         }
1495                 }
1496         }
1497
1498         return nDipoleEntries;
1499
1500 }
1501 //_______________________________________________________________
1502
1503 Int_t AliGRPPreprocessor::ProcessEnvDPs(TMap* valueMap, AliGRPObject* grpObj)
1504 {
1505         // processing DPs
1506         // related to 
1507         // evironment conditions (temperature, pressure) info
1508
1509         Int_t nEnvEntries = 0;
1510         TObjArray *array = 0x0;
1511         Int_t indexDP = -1;
1512
1513         AliInfo(Form("==========CavernTemperature==========="));
1514         Bool_t outOfRange = kFALSE;  // flag to monitor if any value collected by DCS is out of range
1515         indexDP = kCavernTemperature;
1516         array = (TObjArray *)valueMap->GetValue(fgkDCSDataPoints[indexDP]);
1517         if(!array) {
1518                 Log(Form("%s not found in the map!!!",fgkDCSDataPoints[indexDP]));
1519         } 
1520         else {
1521                 if (array->GetEntries() == 0){
1522                         AliError(Form("No entries found in array! setting %s to invalid...",fgkDCSDataPoints[indexDP]));
1523                 }
1524                 else {
1525                         Float_t *floatDCS = ProcessFloatAll(array);
1526                         if (floatDCS != NULL){
1527                                 grpObj->SetCavernTemperature(floatDCS);
1528                         }
1529                         else{
1530                                 outOfRange = kTRUE;
1531                         }
1532                         if (floatDCS){
1533                                 delete[] floatDCS;
1534                                 floatDCS = 0x0;
1535                         }
1536                 }
1537                 if (!outOfRange) {
1538                         ffailedDPs->RemoveAt(indexDP);
1539                         nEnvEntries++;
1540                 }
1541         }
1542
1543         if (array) array = 0x0;
1544
1545         AliInfo(Form("========== AtmosPressures (Cavern + Surface + Cavern2) ==========="));
1546         AliDCSSensorArray *dcsSensorArray = GetPressureMap(valueMap);
1547         //dcsSensorArray->Print();
1548         if( fPressure->NumFits()<kNumSensors ) {
1549                 Log(Form("Check the pressure sensor values! Not all the %d pressure sensors have been fit",kNumSensors));
1550         } 
1551         Log(Form("Number of fits performed = %d",fPressure->NumFits()));
1552
1553         AliInfo(Form("==========CavernAtmosPressure==========="));
1554         indexDP = kCavernAtmosPressure;
1555         AliDCSSensor* sensorCavernP2 = dcsSensorArray->GetSensor(fgkDCSDataPoints[indexDP]);
1556         TGraph* graph = sensorCavernP2->GetGraph();
1557         AliDebug(3,Form("index = %d",indexDP));
1558         AliDebug(3,Form("name = %s",fgkDCSDataPoints[indexDP]));
1559         AliDebug(2,Form("graph = %p",graph));
1560         AliDebug(3,Form("sensorCavernP2 = %p", sensorCavernP2));
1561         if(sensorCavernP2->GetFit() || graph) {
1562                 if (sensorCavernP2->GetFit()){
1563                         Log(Form("Fit for sensor %s found",fgkDCSDataPoints[indexDP]));
1564                 }
1565                 else {
1566                         Log(Form("Fit for sensor %s not found, but the graph is there - NOT going into error",fgkDCSDataPoints[indexDP]));
1567                 }
1568                 grpObj->SetCavernAtmosPressure(sensorCavernP2);
1569                 ffailedDPs->RemoveAt(indexDP);
1570                 nEnvEntries++;
1571         } 
1572         //if (sensorP2) delete sensorP2;
1573         else {
1574                 Log(Form("ERROR!!! Neither graph nor fit found for sensor %s - this will not increase the number of found DCS DPs and will cause an error", fgkDCSDataPoints[indexDP] ));
1575         }
1576         
1577         AliInfo(Form("==========SurfaceAtmosPressure==========="));
1578         indexDP = kSurfaceAtmosPressure;
1579         AliDCSSensor* sensorP2 = dcsSensorArray->GetSensor(fgkDCSDataPoints[indexDP]);
1580         graph = sensorP2->GetGraph();
1581         AliDebug(3,Form("index = %d",indexDP));
1582         AliDebug(3,Form("name = %s",fgkDCSDataPoints[indexDP]));
1583         AliDebug(2,Form("graph = %p",graph));   
1584         AliDebug(3,Form("sensorP2 = %p", sensorP2));
1585         if(sensorP2->GetFit() || graph) {
1586                 if (sensorP2->GetFit()){
1587                         Log(Form("Fit for sensor %s found",fgkDCSDataPoints[indexDP]));
1588                 }
1589                 else {
1590                         Log(Form("Fit for sensor %s not found, but the graph is there - NOT going into error",fgkDCSDataPoints[indexDP]));
1591                 }
1592                 grpObj->SetSurfaceAtmosPressure(sensorP2);
1593                 ffailedDPs->RemoveAt(indexDP);
1594                 nEnvEntries++;
1595         } 
1596         //if (sensorP2) delete sensorP2;
1597         else {
1598                 Log(Form("ERROR!!! Neither graph nor fit found for sensor %s - this will not increase the number of found DCS DPs and will cause an error", fgkDCSDataPoints[indexDP] ));
1599         }
1600
1601         AliInfo(Form("==========CavernAtmosPressure2==========="));
1602         indexDP = kCavernAtmosPressure2;
1603         AliDCSSensor* sensorCavernP22 = dcsSensorArray->GetSensor(fgkDCSDataPoints[indexDP]);
1604         graph = sensorCavernP22->GetGraph();
1605         AliDebug(3,Form("index = %d",indexDP));
1606         AliDebug(3,Form("name = %s",fgkDCSDataPoints[indexDP]));
1607         AliDebug(2,Form("graph = %p",graph));   
1608         AliDebug(3,Form("sensorCavernP2_2 = %p", sensorCavernP22));
1609         if(sensorCavernP22->GetFit() || graph) {
1610                 if (sensorCavernP22->GetFit()){
1611                         Log(Form("Fit for sensor %s found",fgkDCSDataPoints[indexDP]));
1612                 }
1613                 else {
1614                         Log(Form("Fit for sensor %s not found, but the graph is there - NOT going into error",fgkDCSDataPoints[indexDP]));
1615                 }
1616                 grpObj->SetCavernAtmosPressure2(sensorCavernP22);
1617                 ffailedDPs->RemoveAt(indexDP);
1618                 nEnvEntries++;
1619         } 
1620         //if (sensorP2) delete sensorP2;
1621         else {
1622                 Log(Form("ERROR!!! Neither graph nor fit found for sensor %s - this will not increase the number of found DCS DPs and will cause an error", fgkDCSDataPoints[indexDP] ));
1623         }
1624         
1625         
1626         return nEnvEntries;
1627 }
1628 //_______________________________________________________________
1629
1630 Int_t AliGRPPreprocessor::ProcessHPDPs(const TMap* valueMap, AliGRPObject* grpObj)
1631 {
1632         // processing DPs
1633         // related to 
1634         // Hall Probes info
1635
1636         Int_t nHPEntries = 0;
1637         TObjArray *array = 0x0;
1638         Int_t indexDP = -1;
1639         Bool_t outOfRange; // flag to monitor if any value collected by DCS is out of range
1640
1641         if (fgknDCSDPHallProbes != AliGRPObject::GetNumberOfHP()){
1642                 AliError(Form("Number of Hall probes expected in GRP Preprocessor (i.e. %d) different from number of Hall Probes foreseen in GRP object (i.e. %d). Looping on entries from GRP object anyway.", fgknDCSDPHallProbes, AliGRPObject::GetNumberOfHP()));
1643         }
1644         for (indexDP = 0; indexDP < AliGRPObject::GetNumberOfHP(); indexDP++){
1645                 outOfRange = kFALSE; // resetting outOfRange flag at each HP
1646                 AliInfo(Form("==========%s===========",AliGRPObject::GetHPDP(indexDP)));
1647                 array = (TObjArray *)valueMap->GetValue(AliGRPObject::GetHPDP(indexDP));
1648                 if(!array) {
1649                         Log(Form("%s not found in the map!!!",AliGRPObject::GetHPDP(indexDP)));
1650                 } 
1651                 else {
1652                         if (array->GetEntries() == 0){
1653                                 AliError(Form("No entries found in array! setting %s to invalid...",AliGRPObject::GetHPDP(indexDP)));
1654                         }
1655                         else {
1656                                 Float_t *floatDCS = ProcessFloatAll(array);
1657                                 if (floatDCS != NULL){
1658                                         AliDebug(2,Form("value[0] = %f, value[1] = %f, value[2] = %f, value[3] = %f, value[4] = %f",floatDCS[0],floatDCS[1],floatDCS[2],floatDCS[3],floatDCS[4])); 
1659                                         grpObj->SetHallProbes((AliGRPObject::DP_HallProbes)indexDP,floatDCS);
1660                                         for (Int_t kk = 0 ; kk< 5; kk++){
1661                                                 AliDebug(2,Form("HallProbe[%d][%d]=%f",indexDP,kk,grpObj->GetHallProbes((AliGRPObject::DP_HallProbes)indexDP,(AliGRPObject::Stats)kk)));
1662                                         }
1663                                 }
1664                                 else{
1665                                         outOfRange = kTRUE;
1666                                 }
1667                                 if (floatDCS){
1668                                         delete[] floatDCS;
1669                                         floatDCS = 0x0;
1670                                 }
1671                         }
1672                         if (!outOfRange) {
1673                                 ffailedDPs->RemoveAt(indexDP + fgkDCSDPHallTopShift);  // 7 = shift in the complete list of DPs to get to the Hall Probes
1674                                 nHPEntries++;
1675                         }
1676                 }
1677         }
1678                 
1679         Log(Form("Hall Probes = %d ", nHPEntries));
1680         return nHPEntries;
1681 }
1682
1683 //_________________________________________________________________________
1684
1685 AliSplineFit* AliGRPPreprocessor::GetSplineFit(const TObjArray *array, const TString& stringID){
1686
1687
1688         // 
1689         // returning Spline Fit 
1690         // 
1691
1692         Int_t entriesarray = array->GetEntries();
1693         Float_t* value = new Float_t[entriesarray];
1694         Float_t* time = new Float_t[entriesarray];
1695         AliDCSValue* v = 0x0;
1696         for (Int_t iarray = 0; iarray < entriesarray; iarray++){
1697                 v = (AliDCSValue*)array->At(iarray);
1698                 value[iarray] = v->GetFloat();
1699                 time[iarray] = v->GetTimeStamp();
1700                 AliDebug(2,Form("iarray = %d, value = %f, time = %f",iarray,value[iarray],time[iarray]));
1701         }
1702         TGraph* gr = new TGraph(entriesarray,value,time);
1703         if (!gr ) {
1704                 AliWarning(Form("%s: no input graph to compute SplineFit",stringID.Data()));
1705                 return NULL;
1706         }
1707         AliSplineFit *fit = new AliSplineFit();
1708         fit->SetMinPoints(10);
1709         fit->InitKnots(gr,10,10,0.0);
1710         fit->SplineFit(2);
1711         fit->Cleanup();
1712         if (!fit) {
1713                 AliWarning(Form("%s: no fit performed",stringID.Data()));
1714                 return NULL;
1715         } 
1716         return fit;
1717 }
1718
1719 //_________________________________________________________________________
1720
1721 TString AliGRPPreprocessor::ProcessChar(const TObjArray *array)
1722 {
1723
1724         // 
1725         // processing char
1726         //
1727
1728         TString aDCSString="";
1729         
1730         AliDCSValue *v = 0x0;
1731         for(Int_t iCount = 0; iCount < array->GetEntries(); iCount++) {
1732                 v = (AliDCSValue *)array->At(iCount);
1733                 if (((Int_t)(v->GetTimeStamp()) < (Int_t)GetStartTimeDCSQuery()) || ((Int_t)(v->GetTimeStamp()) > (Int_t)GetEndTimeDCSQuery())) {
1734                         AliError(Form("DCS values for the parameter outside the queried interval"));
1735                         continue;
1736                 }
1737                 if (iCount > 0) {
1738                         if (aDCSString != v->GetChar())
1739                         AliError(Form("DCS values for the parameter changed from %s to %c within the queried interval", aDCSString.Data(), (Char_t)v->GetChar()));
1740                 }
1741                 aDCSString = (TString)v->GetChar();  // keeping always last value in the array
1742         }
1743         return aDCSString;
1744 }
1745
1746 //__________________________________________________________________________________________________________________
1747
1748 Float_t* AliGRPPreprocessor::ProcessFloatAll(const TObjArray* array)
1749 {
1750         // 
1751         // processing Float values using Mean, Median, Standard Deviation wrt Mean, Standar Deviation wrt Median 
1752         //
1753         // parameters[0] = mean
1754         // parameters[1] = truncated mean (calculated excluding points outside +/- 3RMS from mean
1755         // parameters[2] = median
1756         // parameters[3] = standard deviation wrt mean
1757         // parameters[4] = standard deviation wrt median
1758         //
1759
1760         TString timeStartString = (TString)GetRunParameter("DAQ_time_start");
1761         TString timeEndString = (TString)GetRunParameter("DAQ_time_end");
1762         if (timeStartString.IsNull() || timeStartString.IsNull()){
1763                 if (timeStartString.IsNull()){ 
1764                         AliError("DAQ_time_start not set in logbook! Setting statistical values for current DP to invalid");
1765                 }
1766                 else if (timeStartString.IsNull()){
1767                         AliError("DAQ_time_end not set in logbook! Setting statistical values for current DP to invalid");
1768                 }
1769                 fdaqStartEndTimeOk = kFALSE;
1770                 return 0;
1771         }  
1772
1773         Int_t timeStart = (Int_t)(timeStartString.Atoi());
1774         Int_t timeEnd = (Int_t)(timeEndString.Atoi());
1775         Float_t* parameters = new Float_t[5];
1776         Int_t iCounts = 0;
1777         Int_t iCountsRun = 0;
1778         Int_t nCounts = array->GetEntries();
1779         Float_t valueBeforeSOR = 0;
1780         Float_t valueAfterEOR = 0;
1781         Int_t timestampBeforeSOR = -1;
1782         Int_t timestampAfterEOR = -1;
1783         Int_t ientrySOR = -1;
1784         Int_t ientryEOR = -1;
1785         Float_t* arrayValues = 0x0; 
1786         Double_t* arrayWeights = 0x0; 
1787         Bool_t truncMeanFlag = kTRUE;  // flag to indicate whether Truncated Mean should be calculated or not
1788         Bool_t sdFlag = kTRUE;  // flag to indicate whether SD (wrt Mean/Median) should be calculated or not
1789
1790         for(Int_t i = 0; i < nCounts; i++) {
1791                 AliDCSValue *v = (AliDCSValue *)array->At(i);
1792                 if ((v->GetFloat() <= fminFloat) || (v->GetFloat() >= fmaxFloat)) {
1793                         AliError(Form("Error! Float value found in DCS map at %d-th entry is OUT OF RANGE: value = %6.5e",i,v->GetFloat()));
1794                         if (v->GetFloat() < fminFloat) AliInfo(Form("The value is smaller than %6.5e",fminFloat));
1795                         if (v->GetFloat() > fmaxFloat) AliInfo(Form("The value is greater than %6.5e",fmaxFloat));
1796                         return NULL;
1797                 }
1798                 if(((Int_t)(v->GetTimeStamp()) >= (Int_t)GetStartTimeDCSQuery()) &&((Int_t)(v->GetTimeStamp()) <= (Int_t)GetEndTimeDCSQuery())) {
1799                         AliDebug(2,Form("%d-th entry = %f at timestamp %i",i,v->GetFloat(),v->GetTimeStamp()));
1800                         iCounts += 1;
1801                         // look for the last value before SOR and the first value before EOR
1802                         if (((Int_t)(v->GetTimeStamp()) >= (Int_t)GetStartTimeDCSQuery()) && (Int_t)(v->GetTimeStamp()) < timeStart) {
1803                                 timestampBeforeSOR = (Int_t)(v->GetTimeStamp());
1804                                 AliDebug(2,Form("timestamp of last value before SOR = %d, with DAQ_time_start = %d",timestampBeforeSOR,timeStart));
1805                                 valueBeforeSOR = v->GetFloat();
1806                         }
1807                         else if ((Int_t)(v->GetTimeStamp()) <= (Int_t)GetEndTimeDCSQuery() && (Int_t)(v->GetTimeStamp()) > timeEnd && timestampAfterEOR == -1){
1808                                 timestampAfterEOR = (Int_t)(v->GetTimeStamp());
1809                                 valueAfterEOR = v->GetFloat();
1810                                 AliDebug(2,Form("timestamp of first value after EOR = %d, with DAQ_time_end = %d",timestampAfterEOR,timeEnd));
1811                         }
1812                         // check if there are DPs between DAQ_time_start and DAQ_time_end
1813                         if(((Int_t)(v->GetTimeStamp()) >= timeStart) &&((Int_t)(v->GetTimeStamp()) <= timeEnd)) {
1814                                 if (ientrySOR == -1) ientrySOR = i;  // first entry after SOR
1815                                 if (ientryEOR < i) ientryEOR = i;  // last entry before EOR
1816                                 AliDebug(2,Form("entry between SOR and EOR"));
1817                                 iCountsRun += 1;
1818                         }
1819                 }
1820                 else {
1821                         AliError(Form("DCS values for the parameter outside the queried interval: timestamp = %d",v->GetTimeStamp()));
1822                 }
1823         }
1824
1825         if (timestampBeforeSOR == -1){
1826                 AliWarning("No value found before SOR");
1827         }
1828         if (timestampAfterEOR == -1){
1829                 AliWarning("No value found after EOR");
1830         }
1831
1832         AliDebug(2,Form("Number of valid entries (within DCS query interval) = %i, from a total amount of %i entries",iCounts,nCounts));
1833         AliDebug(2,Form("Last value before DAQ_time_start (SOR) = %f at timestamp = %d",valueBeforeSOR,timestampBeforeSOR));
1834         AliDebug(2,Form("First value after DAQ_time_end (EOR)   = %f at timestamp = %d",valueAfterEOR,timestampAfterEOR));
1835         AliInfo(Form("Found %d entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)",iCountsRun));
1836         AliDebug(2,Form("Index of first entry after DAQ_time_start (SOR) = %d ",ientrySOR));
1837         AliDebug(2,Form("Index of first entry before DAQ_time_end (EOR) = %d ",ientryEOR));
1838
1839         Int_t nentriesUsed = 0;
1840         if (iCountsRun > 1){
1841                 AliInfo("Using entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)");
1842                 AliDebug(2,"Calculating (weighted) Mean and Median");
1843                 arrayValues = new Float_t[iCountsRun]; 
1844                 arrayWeights = new Double_t[iCountsRun]; 
1845                 nentriesUsed = iCountsRun;
1846                 for (Int_t i = ientrySOR; i <= ientryEOR; i++){
1847                         AliDCSValue *v = (AliDCSValue *)array->At(i);
1848                         Int_t timestamp2 = 0;
1849                         if (i < ientryEOR){
1850                                 AliDCSValue *v1 = (AliDCSValue *)array->At(i+1);
1851                                 timestamp2 = (Int_t)v1->GetTimeStamp();
1852                         }
1853                         else {
1854                                 timestamp2 = timeEnd+1;
1855                         }
1856                         arrayWeights[i-ientrySOR] = (Double_t)(timestamp2 - (Int_t)v->GetTimeStamp());
1857                         arrayValues[i-ientrySOR] = v->GetFloat();
1858                 }
1859                 parameters[0] = TMath::Mean(iCountsRun,arrayValues,arrayWeights);
1860                 parameters[2] = TMath::Median(iCountsRun,arrayValues,arrayWeights);
1861         }
1862         else if (iCountsRun == 1){
1863                 AliDCSValue* v = (AliDCSValue *)array->At(ientrySOR);
1864                 nentriesUsed = 2;
1865                 if (timestampBeforeSOR != -1 && timestampBeforeSOR != (Int_t)v->GetTimeStamp()){
1866                         AliWarning("Using single entry between DAQ_time_start (SOR) and DAQ_time_end (EOR) and last entry before SOR. Truncated mean won't be calculated.");
1867                         arrayValues = new Float_t[2];
1868                         arrayWeights = new Double_t[2];
1869                         arrayValues[0] = valueBeforeSOR;
1870                         arrayWeights[0] = (Double_t)((Int_t)v->GetTimeStamp()-timestampBeforeSOR);
1871                         arrayValues[1] = v->GetFloat();
1872                         arrayWeights[1] = (Double_t)(timeEnd+1-(Int_t)v->GetTimeStamp());
1873                         AliDebug(2, Form("value0 = %f, with weight = %f",arrayValues[0],arrayWeights[0])); 
1874                         AliDebug(2, Form("value1 = %f, with weight = %f",arrayValues[1],arrayWeights[1])); 
1875                         parameters[0] = TMath::Mean(2,arrayValues,arrayWeights);
1876                         parameters[2] = TMath::Median(2,arrayValues,arrayWeights);
1877                         truncMeanFlag = kFALSE;
1878                 }
1879                 else{
1880                         AliError("Cannot calculate mean, truncated mean, median, SD wrt mean, SD wrt median for current DP - only one value collected during the run, but no value before with which to calculate the statistical quantities");
1881                         parameters[0] = AliGRPObject::GetInvalidFloat();
1882                         parameters[1] = AliGRPObject::GetInvalidFloat();
1883                         parameters[2] = AliGRPObject::GetInvalidFloat();
1884                         parameters[3] = AliGRPObject::GetInvalidFloat();
1885                         parameters[4] = AliGRPObject::GetInvalidFloat();
1886                         return parameters;
1887                 }
1888         }
1889         else { // iCountsRun == 0, using only the point immediately before SOR
1890                 if (timestampBeforeSOR == -1){
1891                         AliError("Cannot set mean, truncated mean, median, SD wrt mean, SD wrt median for current DP - no points during the run collected, and point before SOR missing");
1892                         parameters[0] = AliGRPObject::GetInvalidFloat();
1893                         parameters[1] = AliGRPObject::GetInvalidFloat();
1894                         parameters[2] = AliGRPObject::GetInvalidFloat();
1895                         parameters[3] = AliGRPObject::GetInvalidFloat();
1896                         parameters[4] = AliGRPObject::GetInvalidFloat();
1897                         return parameters;
1898                 }
1899                 else {
1900                         AliWarning("Using only last entry before SOR. Truncated mean and Standard deviations (wrt mean/median) won't be calculated.");
1901                         AliDebug(2,Form("value = %f",valueBeforeSOR)); 
1902                         parameters[0] = valueBeforeSOR;
1903                         parameters[2] = valueBeforeSOR;
1904                         truncMeanFlag = kFALSE;
1905                         sdFlag = kFALSE;
1906                 }
1907         }
1908
1909         Float_t temp = 0;
1910         Float_t temp1 = 0;
1911         Float_t sumweights = 0; 
1912         Int_t entriesTruncMean = 0;
1913         Float_t* arrayValuesTruncMean = new Float_t[nentriesUsed]; 
1914         Double_t* arrayWeightsTruncMean = new Double_t[nentriesUsed]; 
1915
1916         // calculating SD wrt Mean and Median
1917         AliDebug(2,"Calculating SD wrt Mean and SD wrt Median");
1918         if (sdFlag){
1919                 for (Int_t i =0; i< nentriesUsed; i++){
1920                         AliDebug(2,Form("Entry %d: value = %f, weight = %f",i,arrayValues[i],arrayWeights[i]));
1921                         temp += (arrayValues[i]-parameters[2])*(arrayValues[i]-parameters[2]);
1922                         temp1 += arrayWeights[i]*(arrayValues[i]-parameters[0])*(arrayValues[i]-parameters[0]);
1923                         sumweights += arrayWeights[i];
1924                 }
1925                 // setting SD wrt Mean 
1926                 if (sumweights != 0 ){
1927                         parameters[3] = TMath::Sqrt(temp1/sumweights);
1928                 }
1929                 else {
1930                         AliError("Sum of weights to calculate Standard Deviation (wrt mean) <= 0, setting the SD to invalid");
1931                         parameters[3] = AliGRPObject::GetInvalidFloat();
1932                 }
1933                 // setting SD wrt Median
1934                 if (nentriesUsed != 0){
1935                         parameters[4] = TMath::Sqrt(temp/nentriesUsed);
1936                 }
1937                 else{
1938                         AliError("Number of entries used to calculate Standard Deviation (wrt median) <= 0, setting the SD to invalid");
1939                         parameters[4] = AliGRPObject::GetInvalidFloat();
1940                 }
1941         }
1942         else {
1943                 parameters[3] = AliGRPObject::GetInvalidFloat();
1944                 parameters[4] = AliGRPObject::GetInvalidFloat();
1945         }               
1946
1947         // calculating truncated mean (this comes afterwards since you need the SD wrt Mean)
1948         if (truncMeanFlag){
1949                 AliDebug(2,"Calculating Truncated Mean");
1950                 for (Int_t i =0; i< nentriesUsed; i++){
1951                         AliDebug(2,Form("Entry %d: value = %f, weight = %f",i,arrayValues[i],arrayWeights[i]));
1952                         if ((arrayValues[i]<=parameters[0]+3*parameters[3]) && (arrayValues[i]>=parameters[0]-3*parameters[3])){
1953                                 arrayValuesTruncMean[entriesTruncMean]=arrayValues[i];
1954                                 arrayWeightsTruncMean[entriesTruncMean]=arrayWeights[i];
1955                                 AliDebug(2,Form("For Truncated Mean: Entry %d: value = %f, weight = %f",entriesTruncMean,arrayValuesTruncMean[entriesTruncMean],arrayWeightsTruncMean[entriesTruncMean]));
1956                                 entriesTruncMean++;                     
1957                         }
1958                         else{
1959                                 AliDebug(2,"Discarding entry");
1960                         }
1961                 }
1962                 // setting truncated mean 
1963                 if (entriesTruncMean >1){
1964                         AliDebug(2,Form("%d entries used for truncated mean",entriesTruncMean));
1965                         parameters[1] = TMath::Mean(entriesTruncMean,arrayValuesTruncMean,arrayWeightsTruncMean);
1966                 }
1967                 else{   
1968                         AliDebug(2,Form("Too few entries (%d) to calculate truncated mean",entriesTruncMean));
1969                         parameters[1] = AliGRPObject::GetInvalidFloat();
1970                 }
1971         }
1972         else{
1973                         parameters[1] = AliGRPObject::GetInvalidFloat();
1974         }
1975
1976         AliInfo(Form("(weighted) mean = %f ",parameters[0]));
1977         AliInfo(Form("(weighted) truncated mean = %f ",parameters[1]));
1978         AliInfo(Form("median = %f ",parameters[2]));
1979         AliInfo(Form("(weighted) standard deviation with (weighted) mean = %f ",parameters[3]));
1980         AliInfo(Form("standard deviation with median = %f ",parameters[4]));
1981         
1982         return parameters;
1983 }
1984
1985 //__________________________________________________________________________________________________________________
1986
1987 Float_t* AliGRPPreprocessor::ProcessFloatAllMagnet(const TObjArray* array, Int_t indexDP, Bool_t &isZero)
1988 {
1989         // 
1990         // processing Float values using Mean, Median, Standard Deviation wrt Mean, Standar Deviation wrt Median 
1991         // used for L3 and Dipole magnets, using isZero flag to decide whther the magnet was OFF/ON
1992         // the flag is set according to the L3/Dipole current value
1993         // current threshold for L3 = 350 A (value provided by DCS)
1994         // current threshold for Dipole = 450 A (value provided by DCS)
1995         //
1996         // parameters[0] = mean
1997         // parameters[1] = truncated mean (calculated excluding points outside +/- 3RMS from mean
1998         // parameters[2] = median
1999         // parameters[3] = standard deviation wrt mean
2000         // parameters[4] = standard deviation wrt median
2001         //
2002
2003         AliInfo(Form("indexDP = %d",indexDP)); 
2004
2005         Int_t nCounts = array->GetEntries();
2006         for(Int_t i = 0; i < nCounts; i++) {
2007                 AliDCSValue *v = (AliDCSValue *)array->At(i);
2008                 if ((v->GetFloat() <= fminFloat) || (v->GetFloat() >= fmaxFloat)) {
2009                         AliError(Form("Error! Float value found in DCS map at %d-th entry is OUT OF RANGE: value = %6.5e",i,v->GetFloat()));
2010                         if (v->GetFloat() < fminFloat) AliInfo(Form("The value is smaller than %6.5e",fminFloat));
2011                         if (v->GetFloat() > fmaxFloat) AliInfo(Form("The value is greater than %6.5e",fmaxFloat));
2012                         return NULL;
2013                 }
2014                 if(((Int_t)(v->GetTimeStamp()) >= (Int_t)GetStartTimeDCSQuery()) &&((Int_t)(v->GetTimeStamp()) <= (Int_t)GetEndTimeDCSQuery())) {
2015                         AliDebug(2,Form("%d-th entry = %f",i,v->GetFloat()));
2016                         if (indexDP == kL3Current && v->GetFloat() > 350 && isZero == kTRUE) isZero=kFALSE; 
2017                         if (indexDP == kDipoleCurrent && v->GetFloat() > 450 && isZero == kTRUE) isZero=kFALSE; 
2018                 }
2019                 else {
2020                         AliError(Form("DCS values for the parameter outside the queried interval"));
2021                 }
2022         }
2023
2024         return ProcessFloatAll(array);
2025 }
2026
2027
2028 //_______________________________________________________________
2029
2030 Char_t AliGRPPreprocessor::ProcessBool(const TObjArray* array, Bool_t &change)
2031 {
2032         // 
2033         // processing Boolean values
2034         //
2035
2036         Bool_t aDCSBool = kTRUE;
2037
2038         AliDCSValue *v = 0x0;
2039
2040         for(Int_t iCount = 0; iCount < array->GetEntries(); iCount++) {
2041                 v = (AliDCSValue *)array->At(iCount);
2042                 if (((Int_t)(v->GetTimeStamp()) < (Int_t)GetStartTimeDCSQuery()) || ((Int_t)(v->GetTimeStamp()) > (Int_t)GetEndTimeDCSQuery())) {
2043                         AliError(Form("DCS values for the parameter outside the queried interval"));
2044                         continue;
2045                 }
2046                 if (iCount > 0) {
2047                         if (aDCSBool != v->GetBool()) {
2048                                 AliError(Form("DCS values for the parameter changed from %d to %d within the queried interval", (UInt_t)aDCSBool, (UInt_t)v->GetBool()));
2049                                 change = kTRUE;
2050                         }
2051                 }
2052                 aDCSBool = v->GetBool(); // always keeping last value
2053                 AliDebug(2,Form("Bool = %d",(Int_t)aDCSBool));
2054         }
2055         
2056         Char_t caDCSBool = (Char_t) aDCSBool;
2057         return caDCSBool;
2058         
2059 }
2060
2061 //_______________________________________________________________
2062
2063 Float_t AliGRPPreprocessor::ProcessInt(const TObjArray* array)
2064 {
2065         // 
2066         // processing Int values, returning mean
2067         // AliGRPObject::GetInvalidFloat() is returned if any of the DCS values
2068         // are outside the queried time interval or their value is out of range
2069         //
2070
2071         TString timeStartString = (TString)GetRunParameter("DAQ_time_start");
2072         TString timeEndString = (TString)GetRunParameter("DAQ_time_end");
2073         if (timeStartString.IsNull() || timeStartString.IsNull()){
2074                 if (timeStartString.IsNull()){ 
2075                         AliError("DAQ_time_start not set in logbook! Setting statistical values for current DP to invalid");
2076                 }
2077                 else if (timeStartString.IsNull()){
2078                         AliError("DAQ_time_end not set in logbook! Setting statistical values for current DP to invalid");
2079                 }
2080                 return 0;
2081         }  
2082
2083         Int_t timeStart = (Int_t)(timeStartString.Atoi());
2084         Int_t timeEnd = (Int_t)(timeEndString.Atoi());
2085         Float_t aDCSArrayMean = 0.0;
2086         Int_t iCounts = 0;
2087         Float_t valueBeforeSOR = 0;
2088         Float_t valueAfterEOR = 0;
2089         Int_t timestampBeforeSOR = -1;
2090         Int_t timestampAfterEOR = -1;
2091         Int_t ientrySOR = -1;
2092         Int_t ientryEOR = -1;
2093         Float_t* arrayValues = 0x0; 
2094         Double_t* arrayWeights = 0x0; 
2095         Int_t iCountsRun = 0;
2096         Int_t nCounts = array->GetEntries();
2097
2098         for(Int_t i = 0; i < nCounts; i++) {
2099                 AliDCSValue* v = (AliDCSValue *)array->At(i);
2100                 if ((v->GetInt() < fminInt) || (v->GetInt() > fmaxInt)) {
2101                         AliError(Form("Error! Int value found in DCS map at %d-th entry is OUT OF RANGE: value = %d",i, v->GetInt()));
2102                         return AliGRPObject::GetInvalidFloat();
2103                 }
2104                 if(((Int_t)(v->GetTimeStamp()) >= (Int_t)GetStartTimeDCSQuery()) &&((Int_t)(v->GetTimeStamp()) <= (Int_t)GetEndTimeDCSQuery())) {
2105                         AliDebug(2,Form("%d-th entry = %d at timestamp %i",i,v->GetInt(),v->GetTimeStamp()));
2106                         iCounts += 1;
2107                         // look for the last value before SOR and the first value before EOR
2108                         if (((Int_t)(v->GetTimeStamp()) >= (Int_t)GetStartTimeDCSQuery()) && (Int_t)(v->GetTimeStamp()) < timeStart) {
2109                                 timestampBeforeSOR = (Int_t)(v->GetTimeStamp());
2110                                 AliDebug(2,Form("timestamp of last entry before SOR = %d, with DAQ_time_start = %d",timestampBeforeSOR,timeStart));
2111                                 valueBeforeSOR = (Float_t) v->GetInt();
2112                         }
2113                         else if ((Int_t)(v->GetTimeStamp()) <= (Int_t)GetEndTimeDCSQuery() && (Int_t)(v->GetTimeStamp()) > timeEnd && timestampAfterEOR == -1){
2114                                 timestampAfterEOR = (Int_t)(v->GetTimeStamp());
2115                                 valueAfterEOR = (Float_t) v->GetInt();
2116                                 AliDebug(2,Form("timestamp of first entry after EOR = %d, with DAQ_time_end = %d",timestampAfterEOR,timeEnd));
2117                         }
2118                         // check if there are DPs between DAQ_time_start and DAQ_time_end
2119                         if(((Int_t)(v->GetTimeStamp()) >= timeStart) &&((Int_t)(v->GetTimeStamp()) <= timeEnd)) {
2120                                 if (ientrySOR == -1) ientrySOR = i;  // first entry after SOR
2121                                 if (ientryEOR < i) ientryEOR = i;  // last entry before EOR
2122                                 AliDebug(2,Form("entry between SOR and EOR"));
2123                                 iCountsRun += 1;
2124                         }
2125                 }
2126                 else {
2127                         AliError(Form("DCS values for the parameter outside the queried interval: timestamp = %d",v->GetTimeStamp()));
2128                 }
2129         }
2130
2131         if (timestampBeforeSOR == -1){
2132                 AliWarning("No value found before SOR!");
2133         }
2134         if (timestampAfterEOR == -1){
2135                 AliWarning("No value found after EOR!");
2136         }
2137
2138         AliDebug(2,Form("Number of valid entries (within query interval) = %i, starting from %i entries",iCounts,nCounts));
2139         AliDebug(2,Form("Last value before DAQ_time_start (SOR) = %f at timestamp = %d",valueBeforeSOR,timestampBeforeSOR));
2140         AliDebug(2,Form("First value after DAQ_time_end (EOR)   = %f at timestamp = %d",valueAfterEOR,timestampAfterEOR));
2141         AliInfo(Form("Found %d entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)",iCountsRun));
2142         AliDebug(2,Form("Index of first entry after DAQ_time_start (SOR) = %d ",ientrySOR));
2143         AliDebug(2,Form("Index of first entry before DAQ_time_end (EOR) = %d ",ientryEOR));
2144
2145         Int_t nentriesUsed = 0;
2146         if (iCountsRun > 1){
2147                 AliInfo("Using entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)");
2148                 AliDebug(2,"Calculating (weighted) Mean");
2149                 arrayValues = new Float_t[iCountsRun]; 
2150                 arrayWeights = new Double_t[iCountsRun]; 
2151                 nentriesUsed = iCountsRun;
2152                 for (Int_t i = ientrySOR; i <= ientryEOR; i++){
2153                         AliDCSValue *v = (AliDCSValue *)array->At(i);
2154                         Int_t timestamp2 = 0;
2155                         if (i < ientryEOR){
2156                                 AliDCSValue *v1 = (AliDCSValue *)array->At(i+1);
2157                                 timestamp2 = (Int_t)v1->GetTimeStamp();
2158                         }
2159                         else {
2160                                 timestamp2 = timeEnd+1;
2161                         }
2162                         arrayWeights[i-ientrySOR] = (Double_t)(timestamp2 - (Int_t)v->GetTimeStamp());
2163                         arrayValues[i-ientrySOR] = (Float_t)v->GetInt();
2164                 }
2165                 aDCSArrayMean = TMath::Mean(iCountsRun,arrayValues,arrayWeights);
2166         }
2167         else if (iCountsRun == 1){
2168                 AliDCSValue* v = (AliDCSValue *)array->At(ientrySOR);
2169                 nentriesUsed = 2;
2170                 if (timestampBeforeSOR != -1 && timestampBeforeSOR != (Int_t)v->GetTimeStamp()){
2171                         AliWarning("Using single entry between DAQ_time_start (SOR) and DAQ_time_end (EOR) and last entry before SOR.");
2172                         arrayValues = new Float_t[2];
2173                         arrayWeights = new Double_t[2];
2174                         arrayValues[0] = valueBeforeSOR;
2175                         arrayWeights[0] = (Double_t)((Int_t)v->GetTimeStamp()-timestampBeforeSOR);
2176                         arrayValues[1] = (Float_t)v->GetInt();
2177                         arrayWeights[1] = (Double_t)(timeEnd+1-(Int_t)v->GetTimeStamp());
2178                         AliDebug(2,Form("value0 = %f, with weight = %f",arrayValues[0],arrayWeights[0])); 
2179                         AliDebug(2,Form("value1 = %f, with weight = %f",arrayValues[1],arrayWeights[1])); 
2180                         aDCSArrayMean = TMath::Mean(2,arrayValues,arrayWeights);
2181                 }
2182                 else{
2183                         AliError("Cannot calculate mean - only one value collected during the run, but no value before with which to calculate the statistical quantities");
2184                         return AliGRPObject::GetInvalidFloat();
2185                 }
2186         }
2187         else { // iCountsRun == 0, using the point immediately before SOR and the one immediately after EOR
2188                 if (timestampBeforeSOR == -1 || timestampAfterEOR == -1){
2189                         if (timestampBeforeSOR == -1){
2190                                 AliError("Cannot calculate mean - no points during the run collected, and point before SOR missing");
2191                         }
2192                         if (timestampAfterEOR == -1){
2193                                 AliError("Cannot calculate maen - no points during the run collected, and point after EOR missing");
2194                         }
2195                         return AliGRPObject::GetInvalidFloat();
2196                 }
2197                 else {
2198                         AliWarning("Using last entry before SOR and first entry after EOR.");
2199                         nentriesUsed = 2;
2200                         arrayValues = new Float_t[2];
2201                         arrayWeights = new Double_t[2];
2202                         arrayValues[0] = valueBeforeSOR;
2203                         arrayWeights[0] = (Double_t)(timestampAfterEOR - timestampBeforeSOR);
2204                         arrayValues[1] = valueAfterEOR;
2205                         arrayWeights[1] = 1.;
2206                         AliDebug(2,Form("value0 = %f, with weight = %f",arrayValues[0],arrayWeights[0])); 
2207                         AliDebug(2,Form("value1 = %f, with weight = %f",arrayValues[1],arrayWeights[1])); 
2208                         aDCSArrayMean = TMath::Mean(1,arrayValues,arrayWeights);
2209                 }
2210         }
2211
2212         AliInfo(Form("mean = %f ", aDCSArrayMean));
2213         return aDCSArrayMean;
2214
2215 }
2216 //_______________________________________________________________
2217
2218 Float_t AliGRPPreprocessor::ProcessUInt(const TObjArray* array)
2219 {
2220         // 
2221         // processing Int values, returning mean 
2222         // AliGRPObject::GetInvalidFloat() is returned if any of the DCS values
2223         // are outside the queried time interval or their value is out of range
2224         //
2225
2226         TString timeStartString = (TString)GetRunParameter("DAQ_time_start");
2227         TString timeEndString = (TString)GetRunParameter("DAQ_time_end");
2228         if (timeStartString.IsNull() || timeStartString.IsNull()){
2229                 if (timeStartString.IsNull()){ 
2230                         AliError("DAQ_time_start not set in logbook! Setting statistical values for current DP to invalid");
2231                 }
2232                 else if (timeStartString.IsNull()){
2233                         AliError("DAQ_time_end not set in logbook! Setting statistical values for current DP to invalid");
2234                 }
2235                 return 0;
2236         }  
2237
2238         Int_t timeStart = (Int_t)(timeStartString.Atoi());
2239         Int_t timeEnd = (Int_t)(timeEndString.Atoi());
2240         Float_t aDCSArrayMean = 0.0;
2241         Int_t iCounts = 0;
2242         Float_t valueBeforeSOR = 0;
2243         Float_t valueAfterEOR = 0;
2244         Int_t timestampBeforeSOR = -1;
2245         Int_t timestampAfterEOR = -1;
2246         Int_t ientrySOR = -1;
2247         Int_t ientryEOR = -1;
2248         Float_t* arrayValues = 0x0; 
2249         Double_t* arrayWeights = 0x0; 
2250         Int_t iCountsRun = 0;
2251         Int_t nCounts = array->GetEntries();
2252
2253         for(Int_t i = 0; i < nCounts; i++) {
2254                 AliDCSValue* v = (AliDCSValue *)array->At(i);
2255                 if ((v->GetUInt() < fminUInt) || (v->GetUInt() > fmaxUInt)) {
2256                         AliError(Form("Error! UInt value found in DCS map at %d-th entry is OUT OF RANGE: value = %u",i,v->GetUInt()));
2257                         return AliGRPObject::GetInvalidFloat();
2258                 }
2259                 if(((Int_t)(v->GetTimeStamp()) >= (Int_t)GetStartTimeDCSQuery()) &&((Int_t)(v->GetTimeStamp()) <= (Int_t)GetEndTimeDCSQuery())) {
2260                         AliDebug(2,Form("%d-th entry = %d at timestamp %i",i,v->GetUInt(),v->GetTimeStamp()));
2261                         iCounts += 1;
2262                         // look for the last value before SOR and the first value before EOR
2263                         if (((Int_t)(v->GetTimeStamp()) >= (Int_t)GetStartTimeDCSQuery()) && (Int_t)(v->GetTimeStamp()) < timeStart) {
2264                                 timestampBeforeSOR = (Int_t)(v->GetTimeStamp());
2265                                 AliDebug(2,Form("timestamp of last entry before SOR = %d, with DAQ_time_start = %d",timestampBeforeSOR,timeStart));
2266                                 valueBeforeSOR = (Float_t)v->GetUInt();
2267                         }
2268                         else if ((Int_t)(v->GetTimeStamp()) <= (Int_t)GetEndTimeDCSQuery() && (Int_t)(v->GetTimeStamp()) > timeEnd && timestampAfterEOR == -1){
2269                                 timestampAfterEOR = (Int_t)(v->GetTimeStamp());
2270                                 valueAfterEOR = (Float_t)v->GetUInt();
2271                                 AliDebug(2,Form("timestamp of first entry after EOR = %d, with DAQ_time_end = %d",timestampAfterEOR,timeEnd));
2272                         }
2273                         // check if there are DPs between DAQ_time_start and DAQ_time_end
2274                         if(((Int_t)(v->GetTimeStamp()) >= timeStart) &&((Int_t)(v->GetTimeStamp()) <= timeEnd)) {
2275                                 if (ientrySOR == -1) ientrySOR = i;  // first entry after SOR
2276                                 if (ientryEOR < i) ientryEOR = i;  // last entry before EOR
2277                                 AliDebug(2,Form("entry between SOR and EOR"));
2278                                 iCountsRun += 1;
2279                         }
2280                 }
2281                 else {
2282                         AliError(Form("DCS values for the parameter outside the queried interval: timestamp = %d",v->GetTimeStamp()));
2283                 }
2284         }
2285
2286         if (timestampBeforeSOR == -1){
2287                 AliWarning("No value found before SOR!");
2288         }
2289         if (timestampAfterEOR == -1){
2290                 AliWarning("No value found after EOR!");
2291         }
2292
2293         AliDebug(2,Form("Number of valid entries (within query interval) = %i, starting from %i entries",iCounts,nCounts));
2294         AliDebug(2,Form("Last value before DAQ_time_start (SOR) = %f at timestamp = %d",valueBeforeSOR,timestampBeforeSOR));
2295         AliDebug(2,Form("First value after DAQ_time_end (EOR)   = %f at timestamp = %d",valueAfterEOR,timestampAfterEOR));
2296         AliInfo(Form("Found %d entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)",iCountsRun));
2297         AliDebug(2,Form("Index of first entry after DAQ_time_start (SOR) = %d ",ientrySOR));
2298         AliDebug(2,Form("Index of first entry before DAQ_time_end (EOR) = %d ",ientryEOR));
2299
2300         Int_t nentriesUsed = 0;
2301         if (iCountsRun > 1){
2302                 AliInfo("Using entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)");
2303                 AliDebug(2,"Calculating (weighted) Mean");
2304                 arrayValues = new Float_t[iCountsRun]; 
2305                 arrayWeights = new Double_t[iCountsRun]; 
2306                 nentriesUsed = iCountsRun;
2307                 for (Int_t i = ientrySOR; i <= ientryEOR; i++){
2308                         AliDCSValue *v = (AliDCSValue *)array->At(i);
2309                         Int_t timestamp2 = 0;
2310                         if (i < ientryEOR){
2311                                 AliDCSValue *v1 = (AliDCSValue *)array->At(i+1);
2312                                 timestamp2 = (Int_t)v1->GetTimeStamp();
2313                         }
2314                         else {
2315                                 timestamp2 = timeEnd+1;
2316                         }
2317                         arrayWeights[i-ientrySOR] = (Double_t)(timestamp2 - (Int_t)v->GetTimeStamp());
2318                         arrayValues[i-ientrySOR] = (Float_t)v->GetUInt();
2319                 }
2320                 aDCSArrayMean = TMath::Mean(iCountsRun,arrayValues,arrayWeights);
2321         }
2322         else if (iCountsRun == 1){
2323                 AliDCSValue* v = (AliDCSValue *)array->At(ientrySOR);
2324                 nentriesUsed = 2;
2325                 if (timestampBeforeSOR != -1 && timestampBeforeSOR != (Int_t)v->GetTimeStamp()){
2326                         AliWarning("Using single entry between DAQ_time_start (SOR) and DAQ_time_end (EOR) and last entry before SOR.");
2327                         arrayValues = new Float_t[2];
2328                         arrayWeights = new Double_t[2];
2329                         arrayValues[0] = valueBeforeSOR;
2330                         arrayWeights[0] = (Double_t)((Int_t)v->GetTimeStamp()-timestampBeforeSOR);
2331                         arrayValues[1] = (Float_t)v->GetUInt();
2332                         arrayWeights[1] = (Double_t)(timeEnd+1-(Int_t)v->GetTimeStamp());
2333                         AliDebug(2,Form("value0 = %f, with weight = %f",arrayValues[0],arrayWeights[0])); 
2334                         AliDebug(2,Form("value1 = %f, with weight = %f",arrayValues[1],arrayWeights[1])); 
2335                         aDCSArrayMean = TMath::Mean(2,arrayValues,arrayWeights);
2336                 }
2337                 else{
2338                         AliError("Cannot calculate mean - only one value collected during the run, but no value before with which to calculate the statistical quantities");
2339                         return AliGRPObject::GetInvalidFloat();
2340                 }
2341         }
2342         else { // iCountsRun == 0, using the point immediately before SOR and the one immediately after EOR
2343                 if (timestampBeforeSOR == -1 || timestampAfterEOR == -1){
2344                         if (timestampBeforeSOR == -1){
2345                                 AliError("Cannot calculate mean - no points during the run collected, and point before SOR missing");
2346                         }
2347                         if (timestampAfterEOR == -1){
2348                                 AliError("Cannot calculate maen - no points during the run collected, and point after EOR missing");
2349                         }
2350                         return AliGRPObject::GetInvalidFloat();
2351                 }
2352                 else {
2353                         AliWarning("Using last entry before SOR and first entry after EOR.");
2354                         nentriesUsed = 2;
2355                         arrayValues = new Float_t[2];
2356                         arrayWeights = new Double_t[2];
2357                         arrayValues[0] = valueBeforeSOR;
2358                         arrayWeights[0] = (Double_t)(timestampAfterEOR - timestampBeforeSOR);
2359                         arrayValues[1] = valueAfterEOR;
2360                         arrayWeights[1] = 1.;
2361                         AliDebug(2,Form("value0 = %f, with weight = %f",arrayValues[0],arrayWeights[0])); 
2362                         AliDebug(2,Form("value1 = %f, with weight = %f",arrayValues[1],arrayWeights[1])); 
2363                         aDCSArrayMean = TMath::Mean(1,arrayValues,arrayWeights);
2364                 }
2365         }
2366
2367         AliInfo(Form("mean = %f ",aDCSArrayMean));
2368         return aDCSArrayMean;
2369
2370 }
2371
2372
2373 //_______________________________________________________________
2374
2375 AliDCSSensorArray *AliGRPPreprocessor::GetPressureMap(TMap* dcsAliasMap)
2376 {
2377         // extract DCS pressure maps. Perform fits to save space
2378         
2379         TMap *map = fPressure->ExtractDCS(dcsAliasMap);
2380         if (map) {
2381                 AliDebug(2,Form("Map has %d entries",map->GetEntries()));
2382                 fPressure->MakeSplineFit(map);
2383                 Double_t fitFraction = fPressure->NumFits()/fPressure->NumSensors(); 
2384                 if (fitFraction > kFitFraction ) {
2385                         AliInfo(Form("Pressure values extracted, %d fits performed for %d sensors.", fPressure->NumFits(),fPressure->NumSensors()));
2386                 } else { 
2387                         AliInfo("Too few pressure maps fitted!!!");
2388                 }
2389         } else {
2390                 AliInfo("no atmospheric pressure map extracted!!!");
2391         }
2392         delete map;
2393         
2394         return fPressure;
2395 }
2396
2397
2398   
2399 //_______________________________________________________________
2400 Int_t AliGRPPreprocessor::ReceivePromptRecoParameters(UInt_t run, const char* dbHost, Int_t dbPort, const char* dbName, const char* user, const char* password, const char *cdbRoot, TString &gdc)
2401 {
2402         //
2403         // Retrieves logbook and trigger information from the online logbook
2404         // This information is needed for prompt reconstruction
2405         //
2406         // Parameters are:
2407         // Run number
2408         // DAQ params: dbHost, dbPort, dbName, user, password, logbookTable, triggerTable
2409         // cdbRoot
2410         //
2411         // returns:
2412         //         positive on success: the return code is the run number of last run processed of the same run type already processed by the SHUTTLE
2413         //         0 on success and no run was found
2414         //         negative on error
2415         //
2416         // This function is NOT called during the preprocessor run in the Shuttle!
2417         //
2418         
2419         // defaults
2420         if (dbPort == 0)
2421                 dbPort = 3306;
2422         
2423         // CDB connection
2424         AliCDBManager* cdb = AliCDBManager::Instance();
2425         cdb->SetDefaultStorage(cdbRoot);
2426         
2427         // SQL connection
2428         TSQLServer* server = TSQLServer::Connect(Form("mysql://%s:%d/%s", dbHost, dbPort, dbName), user, password);
2429         
2430         if (!server)
2431                 {
2432                         Printf("ERROR: Could not connect to DAQ LB");
2433                         return -1;
2434                 }
2435         
2436         // main logbook
2437         TString sqlQuery;
2438         sqlQuery.Form("SELECT DAQ_time_start, run_type, detectorMask, L3_magnetCurrent, Dipole_magnetCurrent,beamType FROM logbook WHERE run = %d", run);
2439         TSQLResult* result = server->Query(sqlQuery);
2440         if (!result)
2441                 {
2442                         Printf("ERROR: Can't execute query <%s>!", sqlQuery.Data());
2443                         return -2;
2444                 }
2445         
2446         if (result->GetRowCount() == 0)
2447                 {
2448                         Printf("ERROR: Run %d not found", run);
2449                         delete result;
2450                         return -3;
2451                 }
2452         
2453         TSQLRow* row = result->Next();
2454         if (!row)
2455                 {
2456                         Printf("ERROR: Could not receive data from run %d", run);
2457                         delete result;
2458                         return -4;
2459                 }
2460         
2461         TString timeStartString(row->GetField(0));
2462         TString runType(row->GetField(1));
2463         TString detectorMaskString(row->GetField(2));
2464         TString l3CurrentString(row->GetField(3));
2465         TString dipoleCurrentString(row->GetField(4));
2466         TString beamTypeString(row->GetField(5));
2467         time_t timeStart = (time_t)(timeStartString.Atoi());
2468         UInt_t detectorMask = (UInt_t)(detectorMaskString.Atoi());
2469         Float_t l3Current = (Float_t)(TMath::Abs(l3CurrentString.Atof()));
2470         Float_t dipoleCurrent = (Float_t)(TMath::Abs(dipoleCurrentString.Atof()));
2471         Char_t l3Polarity = (l3CurrentString.Atof() < 0) ? 1 : 0;
2472         Char_t dipolePolarity = (dipoleCurrentString.Atof() < 0) ? 1 : 0;
2473         if (beamTypeString.CompareTo("Pb-Pb",TString::kIgnoreCase) == 0){
2474                 beamTypeString="A-A";
2475         }
2476         
2477         AliGRPObject * grpObj = new AliGRPObject();
2478         grpObj->SetTimeStart(timeStart); 
2479         grpObj->SetRunType((TString)(row->GetField(1)));
2480         grpObj->SetDetectorMask(detectorMask);
2481         grpObj->SetL3Current(l3Current,(AliGRPObject::Stats)0);
2482         grpObj->SetDipoleCurrent(dipoleCurrent,(AliGRPObject::Stats)0);
2483         grpObj->SetL3Polarity(l3Polarity);
2484         grpObj->SetDipolePolarity(dipolePolarity);
2485         grpObj->SetPolarityConventionLHC();  // after the dipole cables swap we comply with LHC convention
2486         grpObj->SetBeamType(beamTypeString);
2487
2488         delete row;
2489         row = 0;
2490         
2491         delete result;
2492         result = 0;
2493         
2494         Printf("Storing GRP/GRP/Data object with the following content");
2495         grpObj->Dump();
2496         
2497         AliCDBMetaData metadata;
2498         metadata.SetResponsible("Jan Fiete Grosse-Oetringhaus & Chiara Zampolli");
2499         metadata.SetComment("GRP Output parameters received during online running");
2500         
2501         AliCDBId id("GRP/GRP/Data", run, run);
2502         Bool_t success = cdb->Put(grpObj, id, &metadata);
2503         
2504         delete grpObj;
2505         
2506         if (!success)
2507                 {
2508                         Printf("ERROR: Could not store GRP/GRP/Data into OCDB");
2509                         return -5;
2510                 }
2511         
2512         // Receive trigger information
2513         sqlQuery.Form("SELECT configFile FROM logbook_trigger_config WHERE run = %d", run);
2514         result = server->Query(sqlQuery);
2515         if (!result)
2516                 {
2517                         Printf("ERROR: Can't execute query <%s>!", sqlQuery.Data());
2518                         return -11;
2519                 }
2520         
2521         if (result->GetRowCount() == 0)
2522                 {
2523                         Printf("ERROR: Run %d not found in logbook_trigger_config", run);
2524                         delete result;
2525                         return -12;
2526                 }
2527         
2528         row = result->Next();
2529         if (!row)
2530                 {
2531                         Printf("ERROR: Could not receive logbook_trigger_config data from run %d", run);
2532                         delete result;
2533                         return -13;
2534                 }
2535         
2536         TString triggerConfig(row->GetField(0));
2537         
2538         delete row;
2539         row = 0;
2540         
2541         delete result;
2542         result = 0;
2543         
2544         Printf("Found trigger configuration: %s", triggerConfig.Data());
2545         
2546         AliTriggerConfiguration *runcfg = AliTriggerConfiguration::LoadConfigurationFromString(triggerConfig);
2547         if (!runcfg)
2548                 {
2549                         Printf("ERROR: Could not create CTP configuration object");
2550                         return -14;
2551                 }
2552         
2553         metadata.SetComment("CTP run configuration received during online running");
2554         
2555         AliCDBId id2("GRP/CTP/Config", run, run);
2556         success = cdb->Put(runcfg, id2, &metadata);
2557         
2558         delete runcfg;
2559         runcfg = 0;
2560         
2561         if (!success)
2562                 {
2563                         Printf("ERROR: Could not store GRP/CTP/Config into OCDB");
2564                         return -15;
2565                 }
2566         
2567
2568         // Receive list of GDCs for this run
2569         sqlQuery.Form("SELECT GDC FROM logbook_stats_GDC WHERE run = %d", run);
2570         result = server->Query(sqlQuery);
2571         if (!result)
2572                 {
2573                         Printf("ERROR: Can't execute query <%s>!", sqlQuery.Data());
2574                         return -24;
2575                 }
2576         
2577         if (result->GetRowCount() == 0)
2578                 {
2579                         Printf("ERROR: Run %d not found in logbook_stats_GDC", run);
2580                         delete result;
2581                         return -25;
2582                 }
2583
2584         gdc = "";
2585         for (Int_t iGDC = 0; iGDC < result->GetRowCount(); iGDC++) {
2586           row = result->Next();
2587           if (!row)
2588             {
2589               Printf("ERROR: Could not receive logbook_stats_GDC data from run %d", run);
2590               delete result;
2591               return -26;
2592             }
2593           gdc += row->GetField(0);
2594           gdc += " ";
2595         }
2596
2597         delete row;
2598         row = 0;
2599         
2600         delete result;
2601         result = 0;
2602         
2603         Printf("Found GDC: %s", gdc.Data());
2604
2605         // get last run with same run type that was already processed by the SHUTTLE
2606         
2607         sqlQuery.Form("SELECT max(logbook.run) FROM logbook LEFT JOIN logbook_shuttle ON logbook_shuttle.run = logbook.run WHERE run_type = '%s' AND shuttle_done = 1", runType.Data());
2608         result = server->Query(sqlQuery);
2609         if (!result)
2610                 {
2611                         Printf("ERROR: Can't execute query <%s>!", sqlQuery.Data());
2612                         return -21;
2613                 }
2614         
2615         if (result->GetRowCount() == 0)
2616                 {
2617                         Printf("ERROR: No result with query <%s>", sqlQuery.Data());
2618                         delete result;
2619                         return -22;
2620                 }
2621         
2622         row = result->Next();
2623         if (!row)
2624                 {
2625                         Printf("ERROR: Could not receive data for query <%s>", sqlQuery.Data());
2626                         delete result;
2627                         return -23;
2628                 }
2629         
2630         TString lastRunStr(row->GetField(0));
2631         Int_t lastRun = lastRunStr.Atoi();
2632         
2633         Printf("Last run with same run type %s is %d", runType.Data(), lastRun);
2634         
2635         delete row;
2636         row = 0;
2637         
2638         delete result;
2639         result = 0;
2640         
2641         server->Close();
2642         delete server;
2643         server = 0;
2644         
2645         return lastRun;
2646 }
2647 //-----------------------------------------------------------------
2648 Double_t AliGRPPreprocessor::CalculateMean(TObjArray* const array){
2649
2650         //
2651         // Calculating mean over TObjArray from LHC Data
2652         //
2653
2654         TString timeStartString = (TString)GetRunParameter("DAQ_time_start");
2655         TString timeEndString = (TString)GetRunParameter("DAQ_time_end");
2656         if (timeStartString.IsNull() || timeStartString.IsNull()){
2657                 if (timeStartString.IsNull()){ 
2658                         AliError("DAQ_time_start not set in logbook! Setting statistical values for current DP to invalid");
2659                 }
2660                 else if (timeStartString.IsNull()){
2661                         AliError("DAQ_time_end not set in logbook! Setting statistical values for current DP to invalid");
2662                 }
2663                 return 0;
2664         }  
2665
2666         Int_t timeStart = (Int_t)(timeStartString.Atoi());
2667         Int_t timeEnd = (Int_t)(timeEndString.Atoi());
2668         timeStart = 1260646960;
2669         timeEnd = 1260652740;
2670         Double_t* parameters = new Double_t[5];
2671         parameters[0] = -1.;
2672         parameters[1] = -1.;
2673         parameters[2] = -1.;
2674         parameters[3] = -1.;
2675         parameters[4] = -1.;
2676         Int_t iCounts = 0;
2677         Int_t iCountsRun = 0;
2678         Int_t nCounts = array->GetEntries();
2679         printf("ncounts = %d\n",nCounts);
2680         Double_t valueBeforeSOR = 0;
2681         Double_t valueAfterEOR = 0;
2682         Double_t timestampBeforeSOR = -1.;
2683         Double_t timestampAfterEOR = -1.;
2684         Int_t ientrySOR = -1;
2685         Int_t ientryEOR = -1;
2686         Double_t* arrayValues = 0x0; 
2687         Double_t* arrayWeights = 0x0; 
2688         Bool_t truncMeanFlag = kTRUE;  // flag to indicate whether Truncated Mean should be calculated or not
2689         Bool_t sdFlag = kTRUE;  // flag to indicate whether SD (wrt Mean/Median) should be calculated or not
2690
2691         for(Int_t i = 0; i < nCounts; i++) {
2692                 AliDCSArray *dcs = (AliDCSArray*)array->At(i);
2693                 if((dcs->GetTimeStamp() >= timeStart) &&(dcs->GetTimeStamp() <= timeEnd)) {
2694                         AliDebug(2,Form("%d-th entry = %f at timestamp %f\n",i,(Double_t)(dcs->GetInt(0)),dcs->GetTimeStamp()));
2695                         iCounts += 1;
2696                         // look for the last value before SOR and the first value before EOR
2697                         if ((dcs->GetTimeStamp() >= timeStart) && (dcs->GetTimeStamp() < timeStart)) {
2698                                 timestampBeforeSOR = dcs->GetTimeStamp();
2699                                 AliDebug(2,Form("timestamp of last value before SOR = %f, with DAQ_time_start = %d\n",timestampBeforeSOR,timeStart));
2700                                 valueBeforeSOR = (Double_t)(dcs->GetInt(0));
2701                         }
2702                         else if ((dcs->GetTimeStamp() <= timeEnd) && (dcs->GetTimeStamp() > timeEnd) && timestampAfterEOR == -1){
2703                                 timestampAfterEOR = dcs->GetTimeStamp();
2704                                 valueAfterEOR = (Double_t)(dcs->GetInt(0));
2705                                 AliDebug(2,Form("timestamp of first value after EOR = %f, with DAQ_time_end = %d\n",timestampAfterEOR,timeEnd));
2706                         }
2707                         // check if there are DPs between DAQ_time_start and DAQ_time_end
2708                         if((dcs->GetTimeStamp() >= timeStart) &&(dcs->GetTimeStamp() <= timeEnd)) {
2709                                 if (ientrySOR == -1) ientrySOR = i;  // first entry after SOR
2710                                 if (ientryEOR < i) ientryEOR = i;  // last entry before EOR
2711                                 AliDebug(2,Form("entry between SOR and EOR\n"));
2712                                 iCountsRun += 1;
2713                         }
2714                 }
2715                 else {
2716                         printf("DCS values for the parameter outside the queried interval: timestamp = %f\n",dcs->GetTimeStamp());
2717                 }
2718         }
2719
2720         if (timestampBeforeSOR == -1.){
2721                 printf("No value found before SOR\n");
2722         }
2723         if (timestampAfterEOR == -1.){
2724                 printf("No value found after EOR\n");
2725         }
2726
2727         printf("Number of valid entries (within DCS query interval) = %i, from a total amount of %i entries\n",iCounts,nCounts);
2728         printf("Last value before DAQ_time_start (SOR) = %f at timestamp = %f\n",valueBeforeSOR,timestampBeforeSOR);
2729         printf("First value after DAQ_time_end (EOR)   = %f at timestamp = %f\n",valueAfterEOR,timestampAfterEOR);
2730         printf("Found %d entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)\n",iCountsRun);
2731         printf("Index of first entry after DAQ_time_start (SOR) = %d\n ",ientrySOR);
2732         printf("Index of first entry before DAQ_time_end (EOR) = %d\n ",ientryEOR);
2733
2734         Int_t nentriesUsed = 0;
2735         if (iCountsRun > 1){
2736                 printf("Using entries between DAQ_time_start (SOR) and DAQ_time_end (EOR)\n");
2737                 printf("Calculating (weighted) Mean and Median\n" );
2738                 arrayValues = new Double_t[iCountsRun]; 
2739                 arrayWeights = new Double_t[iCountsRun]; 
2740                 nentriesUsed = iCountsRun;
2741                 for (Int_t i = ientrySOR; i <= ientryEOR; i++){
2742                         AliDCSArray *dcs = (AliDCSArray *)array->At(i);
2743                         Double_t timestamp2 = 0;
2744                         if (i < ientryEOR){
2745                                 AliDCSArray *dcs1 = (AliDCSArray *)array->At(i+1);
2746                                 timestamp2 = dcs1->GetTimeStamp();
2747                         }
2748                         else {
2749                                 timestamp2 = (Double_t)timeEnd+1;
2750                         }
2751                         arrayWeights[i-ientrySOR] = (Double_t)((Double_t)timestamp2 - dcs->GetTimeStamp());
2752                         arrayValues[i-ientrySOR] = (Double_t)(dcs->GetInt(0));
2753                         printf("Entry %d: value = %f, weight = %f\n",i-ientrySOR,arrayValues[i-ientrySOR],arrayWeights[i-ientrySOR]);
2754                 }
2755                 parameters[0] = TMath::Mean(iCountsRun,arrayValues,arrayWeights);
2756                 parameters[2] = TMath::Median(iCountsRun,arrayValues,arrayWeights);
2757         }
2758         else if (iCountsRun == 1){
2759                 AliDCSArray* dcs = (AliDCSArray *)array->At(ientrySOR);
2760                 nentriesUsed = 2;
2761                 if (timestampBeforeSOR != -1 && timestampBeforeSOR != (Int_t)dcs->GetTimeStamp()){
2762                         printf("Using single entry between DAQ_time_start (SOR) and DAQ_time_end (EOR) and last entry before SOR. Truncated mean won't be calculated.\n");
2763                         arrayValues = new Double_t[2];
2764                         arrayWeights = new Double_t[2];
2765                         arrayValues[0] = valueBeforeSOR;
2766                         arrayWeights[0] = (Double_t)(dcs->GetTimeStamp()-(Double_t)timestampBeforeSOR);
2767                         arrayValues[1] = (Double_t)(dcs->GetInt(0));
2768                         arrayWeights[1] = (Double_t)((Double_t)timeEnd+1-dcs->GetTimeStamp());
2769                         printf("value0 = %f, with weight = %f\n",arrayValues[0],arrayWeights[0]); 
2770                         printf("value1 = %f, with weight = %f\n",arrayValues[1],arrayWeights[1]); 
2771                         parameters[0] = TMath::Mean(2,arrayValues,arrayWeights);
2772                         parameters[2] = TMath::Median(2,arrayValues,arrayWeights);
2773                         truncMeanFlag = kFALSE;
2774                 }
2775                 else{
2776                         printf("Cannot calculate mean, truncated mean, median, SD wrt mean, SD wrt median for current DP - only one value collected during the run, but no value before with which to calculate the statistical quantities\n");
2777                         parameters[0] = -1;
2778                         parameters[1] = -1;
2779                         parameters[2] = -1;
2780                         parameters[3] = -1;
2781                         parameters[4] = -1;
2782                         return parameters[0];
2783                 }
2784         }
2785         else { // iCountsRun == 0, using only the point immediately before SOR
2786                 if (timestampBeforeSOR == -1.){
2787                         printf("Cannot set mean, truncated mean, median, SD wrt mean, SD wrt median for current DP - no points during the run collected, and point before SOR missing\n");
2788                         parameters[0] = -1;
2789                         parameters[1] = -1;
2790                         parameters[2] = -1;
2791                         parameters[3] = -1;
2792                         parameters[4] = -1;
2793                         return parameters[0];
2794                 }
2795                 else {
2796                         printf("Using only last entry before SOR. Truncated mean and Standard deviations (wrt mean/median) won't be calculated.\n");
2797                         printf("value = %f\n",valueBeforeSOR); 
2798                         parameters[0] = valueBeforeSOR;
2799                         parameters[2] = valueBeforeSOR;
2800                         truncMeanFlag = kFALSE;
2801                         sdFlag = kFALSE;
2802                 }
2803         }
2804
2805         Double_t temp = 0;
2806         Double_t temp1 = 0;
2807         Double_t sumweights = 0; 
2808         Int_t entriesTruncMean = 0;
2809         Double_t* arrayValuesTruncMean = new Double_t[nentriesUsed]; 
2810         Double_t* arrayWeightsTruncMean = new Double_t[nentriesUsed]; 
2811
2812         // calculating SD wrt Mean and Median
2813         printf("Calculating SD wrt Mean and SD wrt Median\n");
2814         if (sdFlag){
2815                 for (Int_t i =0; i< nentriesUsed; i++){
2816                         //printf("Entry %d: value = %f, weight = %f\n",i,arrayValues[i],arrayWeights[i]);
2817                         temp += (arrayValues[i]-parameters[2])*(arrayValues[i]-parameters[2]);
2818                         temp1 += arrayWeights[i]*(arrayValues[i]-parameters[0])*(arrayValues[i]-parameters[0]);
2819                         sumweights += arrayWeights[i];
2820                 }
2821                 // setting SD wrt Mean 
2822                 if (sumweights != 0 ){
2823                         parameters[3] = TMath::Sqrt(temp1/sumweights);
2824                 }
2825                 else {
2826                         printf("Sum of weights to calculate Standard Deviation (wrt mean) <= 0, setting the SD to invalid\n");
2827                         parameters[3] = -1;
2828                 }
2829                 // setting SD wrt Median
2830                 if (nentriesUsed != 0){
2831                         parameters[4] = TMath::Sqrt(temp/nentriesUsed);
2832                 }
2833                 else{
2834                         printf("Number of entries used to calculate Standard Deviation (wrt median) <= 0, setting the SD to invalid\n");
2835                         parameters[4] = -1;
2836                 }
2837         }
2838         else {
2839                 parameters[3] = -1;
2840                 parameters[4] = -1;
2841         }               
2842
2843         // calculating truncated mean (this comes afterwards since you need the SD wrt Mean)
2844         if (truncMeanFlag){
2845                 printf("Calculating Truncated Mean\n");
2846                 for (Int_t i =0; i< nentriesUsed; i++){
2847                         //printf("Entry %d: value = %f, weight = %f\n",i,arrayValues[i],arrayWeights[i]);
2848                         if ((arrayValues[i]<=parameters[0]+3*parameters[3]) && (arrayValues[i]>=parameters[0]-3*parameters[3])){
2849                                 arrayValuesTruncMean[entriesTruncMean]=arrayValues[i];
2850                                 arrayWeightsTruncMean[entriesTruncMean]=arrayWeights[i];
2851                                 printf("For Truncated Mean: Entry %d: value = %f, weight = %f\n",entriesTruncMean,arrayValuesTruncMean[entriesTruncMean],arrayWeightsTruncMean[entriesTruncMean]);
2852                                 entriesTruncMean++;                     
2853                         }
2854                         else{
2855                                 printf("Discarding entry\n");
2856                         }
2857                 }
2858                 // setting truncated mean 
2859                 if (entriesTruncMean >1){
2860                         printf("%d entries used for truncated mean\n",entriesTruncMean);
2861                         parameters[1] = TMath::Mean(entriesTruncMean,arrayValuesTruncMean,arrayWeightsTruncMean);
2862                 }
2863                 else{   
2864                         printf("Too few entries (%d) to calculate truncated mean\n",entriesTruncMean);
2865                         parameters[1] = -1;
2866                 }
2867         }
2868         else{
2869                         parameters[1] = -1;
2870         }
2871         
2872         printf("(weighted) mean = %f \n",parameters[0]);
2873         printf("(weighted) truncated mean = %f \n",parameters[1]);
2874         printf("median = %f \n",parameters[2]);
2875         printf("(weighted) standard deviation with (weighted) mean = %f \n",parameters[3]);
2876         printf("standard deviation with median = %f \n",parameters[4]);
2877         
2878         return (parameters[0]);
2879 }
2880 //------------------------------------------------------------------------------------------------------
2881 Float_t AliGRPPreprocessor::ProcessEnergy(TObjArray* const array, Double_t timeStart){
2882
2883         //
2884         // Method to processo LHC Energy information
2885         // Only the first value is returned, provided that it is withing DAQ_time_start and DAQ_time_end
2886         //
2887
2888         Int_t nCounts = array->GetEntries();
2889         Float_t energy = -1;
2890         Double_t timeEnergy = -1;
2891         Int_t indexEnergy = -1;
2892         Bool_t foundEnergy = kFALSE;
2893
2894         AliDebug(2,Form("Energy measurements = %d\n",nCounts));
2895         if (nCounts ==0){
2896                 AliWarning("No Energy values found! Beam Energy remaining invalid!");
2897         }
2898         else{
2899                 for (Int_t i = 0; i < nCounts; i++){
2900                         AliDCSArray *dcs = (AliDCSArray*)array->At(i);
2901                         if (dcs){
2902                                 if (dcs->GetTimeStamp()<=timeStart && dcs->GetTimeStamp()>=timeEnergy){// taking always the very last entry: of two measurements have the same timestamp, the last one is taken
2903                                         timeEnergy = dcs->GetTimeStamp();
2904                                         indexEnergy = i;
2905                                         foundEnergy = kTRUE;
2906                                 }
2907                                 else{
2908                                         break;
2909                                 }
2910                         }
2911                 }
2912                 if (!foundEnergy){
2913                         AliInfo("No value for the Energy found before start of run, the Energy will remain invalid");
2914                 }
2915                 else {
2916                         AliDCSArray* dcs = (AliDCSArray*)array->At(indexEnergy);
2917                         energy = (Float_t)(TMath::Nint(((Double_t)(dcs->GetInt(0)))*120/1000)); // sqrt(s)/2 energy in GeV
2918                         AliInfo(Form("Energy value found = %d (at %f), converting --> sqrt(s)/2 = %f (GeV)", dcs->GetInt(0),dcs->GetTimeStamp(),energy));
2919                 }
2920         }
2921
2922         return energy;
2923 }
2924 //------------------------------------------------------------------------------------------------------
2925 AliLHCClockPhase* AliGRPPreprocessor::ProcessLHCClockPhase(TObjArray *beam1phase,TObjArray *beam2phase, Double_t timeEnd)
2926 {
2927   //
2928   // Method to process LHC-Clock Phase data
2929   // Only the values between DAQ_time_start and DAQ_time_end are kept
2930   //
2931   AliLHCClockPhase *phaseObj = new AliLHCClockPhase;
2932
2933   Bool_t foundBeam1Phase = kFALSE, foundBeam2Phase = kFALSE;
2934   const Float_t threshold = 0.050; // we store the measurement only in case they differ with more 50ps from the previous one 
2935
2936   TString timeCreatedStr = GetRunParameter("time_created");
2937   Double_t timeCreated = timeCreatedStr.Atof();
2938
2939   Int_t nCounts = beam1phase->GetEntries();
2940   AliDebug(2,Form("Beam1 phase measurements = %d\n",nCounts));
2941   if (nCounts ==0){
2942     AliWarning("No beam1 LHC clock phase values found!");
2943     delete phaseObj;
2944     return NULL;
2945   }
2946   else{
2947     Double_t prevPhase = 0;
2948     for (Int_t i = 0; i < nCounts; i++){
2949       AliDCSArray *dcs = (AliDCSArray*)beam1phase->At(i);
2950       if (dcs){
2951               //if (dcs->GetTimeStamp()>=timeStart && dcs->GetTimeStamp()<=timeEnd) {
2952               if (dcs->GetTimeStamp()>=timeCreated && dcs->GetTimeStamp()<=timeEnd) {
2953           if ((i == 0) || (i == (nCounts-1)) ||
2954               !foundBeam1Phase ||
2955               (TMath::Abs(dcs->GetDouble(0)-prevPhase) > threshold)) {
2956             prevPhase = dcs->GetDouble(0);
2957             foundBeam1Phase = kTRUE;
2958             AliInfo(Form("B1 Clk Phase = %f at TS = %f",
2959                          (Float_t)dcs->GetDouble(0),dcs->GetTimeStamp()));  
2960             phaseObj->AddPhaseB1DP((UInt_t)dcs->GetTimeStamp(),(Float_t)dcs->GetDouble(0));
2961           }
2962         }
2963       }
2964     }
2965     if (!foundBeam1Phase){
2966       AliError("No beam1 LHC clock phase values found within the run!");
2967       delete phaseObj;
2968       return NULL;
2969     }
2970   }
2971
2972   nCounts = beam2phase->GetEntries();
2973   AliDebug(2,Form("Beam2 phase measurements = %d\n",nCounts));
2974   if (nCounts ==0){
2975     AliWarning("No beam2 LHC clock phase values found!");
2976     delete phaseObj;
2977     return NULL;
2978   }
2979   else{
2980     Double_t prevPhase = 0;
2981     for (Int_t i = 0; i < nCounts; i++){
2982       AliDCSArray *dcs = (AliDCSArray*)beam2phase->At(i);
2983       if (dcs){
2984         if (dcs->GetTimeStamp()>=timeCreated && dcs->GetTimeStamp()<=timeEnd) {
2985           if ((i == 0) || (i == (nCounts-1)) ||
2986               !foundBeam2Phase ||
2987               (TMath::Abs(dcs->GetDouble(0)-prevPhase) > threshold)) {
2988             prevPhase = dcs->GetDouble(0);
2989             foundBeam2Phase = kTRUE;
2990             AliInfo(Form("B2 Clk Phase = %f at TS = %f",
2991                          (Float_t)dcs->GetDouble(0),dcs->GetTimeStamp()));  
2992             phaseObj->AddPhaseB2DP((UInt_t)dcs->GetTimeStamp(),(Float_t)dcs->GetDouble(0));
2993           }
2994         }
2995       }
2996     }
2997     if (!foundBeam2Phase){
2998       AliError("No beam2 LHC clock phase values found within the run!");
2999       delete phaseObj;
3000       return NULL;
3001     }
3002   }
3003
3004   return phaseObj;
3005 }