new functionality and new class added
[u/mrichter/AliRoot.git] / MUON / MUONTRKPEDda.cxx
CommitLineData
dc928fbf 1/*
18ec51a0 2 Contact: Jean-Luc Charvet <jean-luc.charvet@cern.ch>
f3cfa63e 3 Link: http://aliceinfo.cern.ch/static/Offline/dimuon/muon_html/README_mchda.html
18ec51a0 4 Reference Run: 109302 (station 3 only)
f3cfa63e 5 Run Type: PEDESTAL
6 DA Type: LDC
7 Number of events needed: 400 events for pedestal run
18ec51a0 8 Input Files: mutrkpedvalues and config_ldc-MTRK-S3-0 in path : /afs/cern.ch/user/j/jcharvet/public/DA_validation
f3cfa63e 9 Output Files: local dir (not persistent) -> MUONTRKPEDda.ped FXS -> run<#>_MCH_<ldc>_PEDESTALS
10 Trigger types used:
dc928fbf 11*/
12
13/**************************************************************************
14 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
15 * *
16 * Author: The ALICE Off-line Project. *
17 * Contributors are mentioned in the code where appropriate. *
18 * *
19 * Permission to use, copy, modify and distribute this software and its *
20 * documentation strictly for non-commercial purposes is hereby granted *
21 * without fee, provided that the above copyright notice appears in all *
22 * copies and that both the copyright notice and this permission notice *
23 * appear in the supporting documentation. The authors make no claims *
24 * about the suitability of this software for any purpose. It is *
25 * provided "as is" without express or implied warranty. *
26 **************************************************************************/
27
28/* $Id$ */
29
30/*
31 -------------------------------------------------------------------------
b9c33bca 32 2010-02-16 New version: MUONTRKPEDda.cxx,v 1.5
dc928fbf 33 -------------------------------------------------------------------------
34
35 Version for MUONTRKPEDda MUON tracking
36 (A. Baldisseri, J.-L. Charvet)
37
38
39 Rem: AliMUON2DMap stores all channels, even those which are not connected
40 if pedMean == -1, channel not connected to a pad
41
1b15b395 42&
dc928fbf 43
44*/
45extern "C" {
46#include <daqDA.h>
47}
48
49#include "event.h"
50#include "monitor.h"
51
52#include <Riostream.h>
53#include <stdio.h>
54#include <stdlib.h>
55#include <sstream>
56#include <math.h>
57
58//AliRoot
59#include "AliMUONRawStreamTrackerHP.h"
60#include "AliRawReader.h"
61#include "AliMUONVStore.h"
62#include "AliMUON2DMap.h"
63#include "AliMUONCalibParamND.h"
64#include "AliMpIntPair.h"
65#include "AliMpConstants.h"
66#include "AliRawDataErrorLog.h"
67#include "AliMUONTrackerIO.h"
18ec51a0 68#include "AliLog.h"
dc928fbf 69
70//ROOT
71#include "TFile.h"
72#include "TSystem.h"
73#include "TTree.h"
74#include "TH1F.h"
75#include "TString.h"
76#include "TStopwatch.h"
77#include "TMath.h"
78#include "TTimeStamp.h"
79#include "TGraphErrors.h"
80#include "TF1.h"
81#include "TROOT.h"
82#include "TPluginManager.h"
83#include "TFitter.h"
84#include "TObjString.h"
85#include "THashTable.h"
86#include <THashList.h>
dbbb2c64 87//
88//AMORE
89//
90#ifdef ALI_AMORE
91#include <AmoreDA.h>
92#endif
dc928fbf 93
94#include "AliMUONPedestal.h"
95#include "AliMUONErrorCounter.h"
96
18ec51a0 97
dc928fbf 98// main routine
f3cfa63e 99int main(Int_t argc, const char **argv)
dc928fbf 100{
dc928fbf 101 Int_t status=0;
102 TStopwatch timers;
103 timers.Start(kTRUE);
104
f3cfa63e 105 const char* prefixDA = "MUONTRKPEDda"; // program prefix
106 printf(" ######## Begin execution : %s ######## \n\n",prefixDA);
107
dc928fbf 108 // needed for streamer application
109 gROOT->GetPluginManager()->AddHandler("TVirtualStreamerInfo",
110 "*",
111 "TStreamerInfo",
112 "RIO",
113 "TStreamerInfo()");
dc928fbf 114 // needed for Minuit plugin
115 gROOT->GetPluginManager()->AddHandler("ROOT::Math::Minimizer",
116 "Minuit",
117 "TMinuitMinimizer",
118 "Minuit",
119 "TMinuitMinimizer(const char*)");
dc928fbf 120// cout << argv[0];
121
122 Int_t skipEvents = 0;
123 Int_t maxEvents = 1000000;
124 Int_t maxDateEvents = 1000000;
f3cfa63e 125 TString inputFile;
dc928fbf 126
127 Int_t nDateEvents = 0;
128 Int_t nGlitchErrors= 0;
129 Int_t nParityErrors= 0;
130 Int_t nPaddingErrors= 0;
18ec51a0 131 Int_t nTokenlostErrors= 0;
dc928fbf 132 Int_t recoverParityErrors = 1;
133
134 TString logOutputFile;
135
136 Char_t flatFile[256]="";
137 TString shuttleFile;
138
139 Int_t nEventsRecovered = 0;
140 Int_t nEvents = 0;
141 UInt_t runNumber = 0;
b9c33bca 142 Int_t nConfig = 1;
dc928fbf 143 ofstream filcout;
dc928fbf 144
145 // decode the input line
146 for (Int_t i = 1; i < argc; i++) // argument 0 is the executable name
147 {
f3cfa63e 148 const char* arg = argv[i];
dc928fbf 149
150 arg = argv[i];
151 if (arg[0] != '-')
152 {
153 // If only one argument and no "-" => DA calling from ECS
154 if (argc == 2)
155 {
f3cfa63e 156 inputFile=argv[i];
dc928fbf 157 }
158 continue;
159 }
160 switch (arg[1])
161 {
162 case 'f' :
163 i++;
f3cfa63e 164 inputFile=argv[i];
165 nConfig=0;
dc928fbf 166 break;
167 case 'a' :
168 i++;
169 shuttleFile = argv[i];
170 break;
171 case 's' :
172 i++;
173 skipEvents=atoi(argv[i]);
174 break;
175 case 'm' :
176 i++;
177 sscanf(argv[i],"%d",&maxDateEvents);
178 break;
179 case 'n' :
180 i++;
181 sscanf(argv[i],"%d",&maxEvents);
182 break;
dc928fbf 183 case 'h' :
184 i++;
185 printf("\n******************* %s usage **********************",argv[0]);
186 printf("\nOnline (called from ECS) : %s <raw data file> (no inline options)\n",argv[0]);
f3cfa63e 187 printf("\n%s can be used locally only with options (without DiMuon configuration file)",argv[0]);
dc928fbf 188 printf("\n%s -options, the available options are :",argv[0]);
189 printf("\n-h help (this screen)");
190 printf("\n");
191 printf("\n Input");
f3cfa63e 192 printf("\n-f <raw data file> (default = %s)",inputFile.Data());
dc928fbf 193 printf("\n");
194 printf("\n Output");
195 printf("\n-a <Flat ASCII file> (default = %s)",shuttleFile.Data());
196 printf("\n");
197 printf("\n Options");
198 printf("\n-m <max date events> (default = %d)",maxDateEvents);
199 printf("\n-s <skip events> (default = %d)",skipEvents);
200 printf("\n-n <max events> (default = %d)",maxEvents);
dc928fbf 201
202 printf("\n\n");
203 exit(-1);
204 default :
205 printf("%s : bad argument %s (please check %s -h)\n",argv[0],argv[i],argv[0]);
206 argc = 2; exit(-1); // exit if error
207 } // end of switch
208 } // end of for i
209
210 // decoding the events
211
212 UShort_t manuId;
213 UChar_t channelId;
214 UShort_t charge;
215
216 //Pedestal object
217 AliMUONPedestal* muonPedestal = new AliMUONPedestal();
218 muonPedestal->SetprefixDA(prefixDA);
219
f3cfa63e 220 Char_t dbfile[256]="";
221 // nConfig=1 : Reading configuration (or not) status via "mutrkpedvalues" file located in DetDB
222 if(nConfig)
223 {
1ccd531d 224 sprintf(dbfile,"mutrkpedvalues");
225 status=daqDA_DB_getFile(dbfile,dbfile);
226 if(status) {printf(" !!! Failed : input file %s is missing, status = %d\n",dbfile,status); return -1; }
227 ifstream filein(dbfile,ios::in);
228 filein >> nConfig;
f3cfa63e 229 }
1ccd531d 230 else printf(" *** Config= %d: no configuration ascii file is used \n",nConfig);
1b15b395 231 muonPedestal->SetconfigDA(nConfig);
232
b9c33bca 233 // nConfig=1: configuration ascii file config_$DATE_ROLE_NAME read from DetDB
1b15b395 234 if(nConfig)
235 {
1ccd531d 236 sprintf(dbfile,"config_%s",getenv("DATE_ROLE_NAME"));
237 status=daqDA_DB_getFile(dbfile,dbfile);
238 if(status) {printf(" !!! Failed : Configuration file %s is missing, status = %d\n",dbfile,status); return -1; }
b9c33bca 239 // else printf(" *** Copy ascii config file: %s from DetDB to working directory and reading ...*** \n",dbfile);
1ccd531d 240 muonPedestal->LoadConfig(dbfile);
1b15b395 241 }
242
dc928fbf 243 // Rawdeader, RawStreamHP
244 AliRawReader* rawReader = AliRawReader::Create(inputFile);
245 AliMUONRawStreamTrackerHP* rawStream = new AliMUONRawStreamTrackerHP(rawReader);
18ec51a0 246// rawStream->DisableWarnings();
dc928fbf 247 rawStream->EnabbleErrorLogger();
18ec51a0 248 //
249 // kLowErrorDetail, /// Logs minimal information in the error messages.
250 // kMediumErrorDetail, /// Logs a medium level of detail in the error messages.
251 // kHighErrorDetail /// Logs maximum information in the error messages.
252 // rawStream->SetLoggingDetailLevel(AliMUONRawStreamTrackerHP::kLowErrorDetail);
253 rawStream->SetLoggingDetailLevel(AliMUONRawStreamTrackerHP::kHighErrorDetail);
dc928fbf 254
f3cfa63e 255 printf("\n %s : Reading data from file %s\n",prefixDA,inputFile.Data());
dc928fbf 256
257 while (rawReader->NextEvent())
258 {
259 if (nDateEvents >= maxDateEvents) break;
260 if (nEvents >= maxEvents) break;
261 if (nDateEvents>0 && nDateEvents % 100 == 0)
262 cout<<"Cumulated: DATE events = " << nDateEvents << " Used events = " << nEvents << endl;
263
264 // check shutdown condition
265 if (daqDA_checkShutdown())
266 break;
267
268 //Skip events
269 while (skipEvents)
270 {
271 rawReader->NextEvent();
272 skipEvents--;
273 }
274
275 Int_t eventType = rawReader->GetType();
276 runNumber = rawReader->GetRunNumber();
277
278 // Output log file initialisations
279 if(nDateEvents==0)
280 {
5431405e 281 sprintf(flatFile,"%s.log",prefixDA);
dc928fbf 282 logOutputFile=flatFile;
18ec51a0 283 AliLog::SetStreamOutput(&filcout); // Print details on logfile
dc928fbf 284 filcout.open(logOutputFile.Data());
285 filcout<<"//=================================================" << endl;
286 filcout<<"// " << prefixDA << " for run = " << runNumber << endl;
287 filcout<<"//=================================================" << endl;
288 filcout<<"// * Date : " << muonPedestal->GetDate()->AsString("l") << "\n" << endl;
289 cout<<"\n ******** " << prefixDA << " for run = " << runNumber << " ********\n" << endl;
290 cout<<" * Date : " << muonPedestal->GetDate()->AsString("l") << "\n" << endl;
291
292 }
293
294 muonPedestal->SetAlifilcout(&filcout);
295
296 nDateEvents++;
297 if (eventType != PHYSICS_EVENT)
298 continue; // for the moment
299
300 // First lopp over DDL's to find good events
301 // Error counters per event (counters in the decoding lib are for each DDL)
302 Bool_t eventIsErrorMessage = kFALSE;
303 int eventGlitchErrors = 0;
304 int eventParityErrors = 0;
305 int eventPaddingErrors = 0;
18ec51a0 306 int eventTokenlostErrors = 0;
dc928fbf 307 rawStream->First();
308 do
309 {
310 if (rawStream->IsErrorMessage()) eventIsErrorMessage = kTRUE;
311 eventGlitchErrors += rawStream->GetGlitchErrors();
312 eventParityErrors += rawStream->GetParityErrors();
313 eventPaddingErrors += rawStream->GetPaddingErrors();
18ec51a0 314 eventTokenlostErrors += rawStream->GetTokenLostErrors();
dc928fbf 315 } while(rawStream->NextDDL());
316
317 AliMUONRawStreamTrackerHP::AliBusPatch* busPatch;
318 if (!eventIsErrorMessage)
319 {
320 // Good events (no error) -> compute pedestal for all channels
321 rawStream->First();
322 while( (busPatch = (AliMUONRawStreamTrackerHP::AliBusPatch*) rawStream->Next()))
323 {
324 for(int i = 0; i < busPatch->GetLength(); ++i)
325 {
dc928fbf 326 busPatch->GetData(i, manuId, channelId, charge);
327 muonPedestal->MakePed(busPatch->GetBusPatchId(), (Int_t)manuId, (Int_t)channelId, (Int_t)charge);
328 }
329 }
330 nEvents++;
331 }
332 else
333 {
334 // Events with errors
335 if (recoverParityErrors && eventParityErrors && !eventGlitchErrors&& !eventPaddingErrors)
336 {
18ec51a0 337 filcout << " ----------- Date Event recovered = " << nDateEvents << " ----------------" << endl;
dc928fbf 338 // Recover parity errors -> compute pedestal for all good buspatches
339 if ( TEST_SYSTEM_ATTRIBUTE( rawReader->GetAttributes(),
340 ATTR_ORBIT_BC ))
341 {
342 filcout <<"Event recovered -> Period:"<<EVENT_ID_GET_PERIOD( rawReader->GetEventId() )
343 <<" Orbit:"<<EVENT_ID_GET_ORBIT( rawReader->GetEventId() )
344 <<" BunchCrossing:"<<EVENT_ID_GET_BUNCH_CROSSING( rawReader->GetEventId() )<<endl;
345 }
346 else
347 {
348 filcout <<"Event recovered -> nbInRun:"<<EVENT_ID_GET_NB_IN_RUN( rawReader->GetEventId() )
349 <<" burstNb:"<<EVENT_ID_GET_BURST_NB( rawReader->GetEventId() )
350 <<" nbInBurst:"<<EVENT_ID_GET_NB_IN_BURST( rawReader->GetEventId() )<<endl;
351 }
352 rawStream->First();
353 while( (busPatch = (AliMUONRawStreamTrackerHP::AliBusPatch*) rawStream->Next()))
354 {
355 // Check the buspatch -> if error not use it in the pedestal calculation
356 int errorCount = 0;
357 for(int i = 0; i < busPatch->GetLength(); ++i)
358 {
359 if (!busPatch->IsParityOk(i)) errorCount++;
360 }
361 if (!errorCount)
362 {
363 // Good buspatch
364 for(int i = 0; i < busPatch->GetLength(); ++i)
365 {
dc928fbf 366 busPatch->GetData(i, manuId, channelId, charge);
dc928fbf 367 muonPedestal->MakePed(busPatch->GetBusPatchId(), (Int_t)manuId, (Int_t)channelId, (Int_t)charge);
368 }
369 }
370 else
371 {
dc928fbf 372 AliMUONErrorCounter* errorCounter;
373 // Bad buspatch -> not used (just print)
374 filcout<<"bpId "<<busPatch->GetBusPatchId()<<" words "<<busPatch->GetLength()
375 <<" parity errors "<<errorCount<<endl;
376 // Number of events where this buspatch is missing
a54854fc 377 if (!(errorCounter = (AliMUONErrorCounter*) (muonPedestal->GetErrorBuspatchTable()->FindObject(busPatch->GetBusPatchId()))))
dc928fbf 378 {
379 // New buspatch
380 errorCounter = new AliMUONErrorCounter(busPatch->GetBusPatchId());
dc928fbf 381 muonPedestal->GetErrorBuspatchTable()->Add(errorCounter);
382 }
383 else
384 {
385 // Existing buspatch
386 errorCounter->Increment();
387 }
388 // errorCounter->Print();
389 } // end of if (!errorCount)
390 } // end of while( (busPatch = (AliMUONRawStreamTrackerHP ...
391 nEvents++;
392 nEventsRecovered++;
393 } //end of if (recoverParityErrors && eventParityErrors && !eventGlitchErrors&& !eventPaddingErrors)
394 else
395 {
18ec51a0 396 filcout << " ----------- Date Event rejected = " << nDateEvents << " ----------------" << endl;
dc928fbf 397 // Fatal errors reject the event
398 if ( TEST_SYSTEM_ATTRIBUTE( rawReader->GetAttributes(),
399 ATTR_ORBIT_BC ))
400 {
401 filcout <<"Event rejected -> Period:"<<EVENT_ID_GET_PERIOD( rawReader->GetEventId() )
402 <<" Orbit:"<<EVENT_ID_GET_ORBIT( rawReader->GetEventId() )
403 <<" BunchCrossing:"<<EVENT_ID_GET_BUNCH_CROSSING( rawReader->GetEventId() )<<endl;
404 }
405 else
406 {
407 filcout <<"Event rejected -> nbInRun:"<<EVENT_ID_GET_NB_IN_RUN( rawReader->GetEventId() )
408 <<" burstNb:"<<EVENT_ID_GET_BURST_NB( rawReader->GetEventId() )
409 <<" nbInBurst:"<<EVENT_ID_GET_NB_IN_BURST( rawReader->GetEventId() )<<endl;
410
411 }
412 } // end of if (!rawStream->GetGlitchErrors() && !rawStream->GetPaddingErrors() ...
413 filcout<<"Number of errors : Glitch "<<eventGlitchErrors
414 <<" Parity "<<eventParityErrors
18ec51a0 415 <<" Padding "<<eventPaddingErrors
416 <<" Token lost "<<eventTokenlostErrors<<endl;
dc928fbf 417 filcout<<endl;
418 } // end of if (!rawStream->IsErrorMessage())
419
420 if (eventGlitchErrors) nGlitchErrors++;
421 if (eventParityErrors) nParityErrors++;
422 if (eventPaddingErrors) nPaddingErrors++;
18ec51a0 423 if (eventTokenlostErrors) nTokenlostErrors++;
dc928fbf 424
425 } // while (rawReader->NextEvent())
426 delete rawReader;
427 delete rawStream;
428
5431405e 429 sprintf(flatFile,"%s.ped",prefixDA);
dc928fbf 430 if(shuttleFile.IsNull())shuttleFile=flatFile;
431 muonPedestal->SetAliNEvents(nEvents);
432 muonPedestal->SetAliRunNumber(runNumber);
dbbb2c64 433
434 muonPedestal->Finalize();
435 muonPedestal->MakeControlHistos();
436 if (!shuttleFile.IsNull())
437 {
438 ofstream out(shuttleFile.Data());
439 muonPedestal->MakeASCIIoutput(out);
440 out.close();
441#ifdef ALI_AMORE
442 //
443 //Send objects to the AMORE DB
444 //
445 ostringstream stringout;
446 muonPedestal->MakeASCIIoutput(stringout);
447
448 amore::da::AmoreDA amoreDA(amore::da::AmoreDA::kSender);
449 TObjString peddata(stringout.str().c_str());
450 Int_t status =0;
451 status = amoreDA.Send("Pedestals",&peddata);
452 if ( status )
453 cout << "Warning: Failed to write Pedestals in the AMORE database : " << status << endl;
454 else
455 cout << "amoreDA.Send(Pedestals) ok" << endl;
456#else
457 cout << "Warning: MCH DA not compiled with AMORE support" << endl;
458#endif
459
460 }
dc928fbf 461
462 // writing some counters
463 cout << endl;
464 cout << prefixDA << " : Nb of DATE events = " << nDateEvents << endl;
465 cout << prefixDA << " : Nb of Glitch errors = " << nGlitchErrors << endl;
466 cout << prefixDA << " : Nb of Parity errors = " << nParityErrors << endl;
18ec51a0 467 cout << prefixDA << " : Nb of Padding errors = " << nPaddingErrors << endl;
468 cout << prefixDA << " : Nb of Token lost errors = " << nTokenlostErrors << endl;
dc928fbf 469 cout << prefixDA << " : Nb of events recovered = " << nEventsRecovered<< endl;
470 cout << prefixDA << " : Nb of events without errors = " << nEvents-nEventsRecovered<< endl;
471 cout << prefixDA << " : Nb of events used = " << nEvents << endl;
472
473 filcout << endl;
474 filcout << prefixDA << " : Nb of DATE events = " << nDateEvents << endl;
475 filcout << prefixDA << " : Nb of Glitch errors = " << nGlitchErrors << endl;
476 filcout << prefixDA << " : Nb of Parity errors = " << nParityErrors << endl;
477 filcout << prefixDA << " : Nb of Padding errors = " << nPaddingErrors << endl;
18ec51a0 478 filcout << prefixDA << " : Nb of Token lost errors = " << nTokenlostErrors << endl;
dc928fbf 479 filcout << prefixDA << " : Nb of events recovered = " << nEventsRecovered<< endl;
480 filcout << prefixDA << " : Nb of events without errors = " << nEvents-nEventsRecovered<< endl;
481 filcout << prefixDA << " : Nb of events used = " << nEvents << endl;
482
dc928fbf 483 // ouput files
484 cout << endl;
485 cout << prefixDA << " : Output logfile : " << logOutputFile << endl;
5431405e 486 cout << prefixDA << " : Pedestal Histo file : " << muonPedestal->GetHistoFileName() << endl;
487 cout << prefixDA << " : Ped. file (to SHUTTLE) : " << shuttleFile << endl;
dc928fbf 488
1dd09aa3 489 filcout << endl;
dc928fbf 490 filcout << prefixDA << " : Output logfile : " << logOutputFile << endl;
5431405e 491 filcout << prefixDA << " : Pedestal Histo file : " << muonPedestal->GetHistoFileName() << endl;
492 filcout << prefixDA << " : Ped. file (to SHUTTLE) : " << shuttleFile << endl;
dc928fbf 493
5431405e 494 // Copying files to local DB folder defined by DAQ_DETDB_LOCAL
495 Char_t *dir;
496 dir= getenv("DAQ_DETDB_LOCAL");
1ccd531d 497 unsigned int nLastVersions=50;
5431405e 498 cout << "\n *** Local DataBase: " << dir << " (Max= " << nLastVersions << ") ***" << endl;
1dd09aa3 499 status = daqDA_localDB_storeFile(muonPedestal->GetHistoFileName(),nLastVersions);
f3cfa63e 500 if(status)printf(" Store file : %s status = %d\n",muonPedestal->GetHistoFileName(),status);
1dd09aa3 501 status = daqDA_localDB_storeFile(shuttleFile.Data(),nLastVersions);
f3cfa63e 502 if(status)printf(" Store file : %s status = %d\n",shuttleFile.Data(),status);
1dd09aa3 503 status = daqDA_localDB_storeFile(logOutputFile.Data(),nLastVersions);
f3cfa63e 504 if(status)printf(" Store file : %s status = %d\n",logOutputFile.Data(),status);
dc928fbf 505
f3cfa63e 506 filcout.close();
dc928fbf 507
b9c33bca 508 // Transferring to FES (be sure that env variable DAQDALIB_PATH is set)
509 printf("\n ***** STORE Pedestal FILE in FES ****** \n");
dc928fbf 510 status = daqDA_FES_storeFile(shuttleFile.Data(),"PEDESTALS");
1ccd531d 511 if (status) { printf(" !!! Failed to export file : %s , status = %d\n",shuttleFile.Data(),status); return -1; }
b9c33bca 512 // else printf(" %s successfully exported to FES \n",shuttleFile.Data());
513
514 // Transferring to FES (be sure that env variable DAQDALIB_PATH is set)
515 printf("\n ***** STORE Configuration FILE in FES ****** \n");
516 status = daqDA_FES_storeFile(dbfile,"CONFIG");
517 if (status) { printf(" !!! Failed to export file : %s , status = %d\n",dbfile,status); return -1; }
518 // else printf(" %s successfully exported to FES \n",dbfile);
dc928fbf 519
1ccd531d 520
f3cfa63e 521 printf("\n ######## End execution : %s ######## \n",prefixDA);
dc928fbf 522 timers.Stop();
523 printf("\nExecution time : R:%7.2fs C:%7.2fs\n", timers.RealTime(), timers.CpuTime());
524 return status;
5431405e 525}