strsep replaced by strtok (HP,Sun,Alpha)
[u/mrichter/AliRoot.git] / MONITOR / AliMonitorProcess.cxx
CommitLineData
04fa961a 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// //
20// This is the class for perfoming the monitoring process. //
21// It checks if a raw data file exists, loops over the events in the raw //
22// data file, reconstructs TPC and ITS clusters and tracks, fills the //
23// monitor histograms and sends the updated histograms to the clients. //
24// Then the raw data file is deleted and it waits for a new file. //
25// //
26///////////////////////////////////////////////////////////////////////////////
27
28
29#include "AliMonitorProcess.h"
30#include "AliMonitorTPC.h"
31#include "AliMonitorITS.h"
32#include "AliMonitorV0s.h"
33#include "AliRawReaderRoot.h"
34#include "AliLoader.h"
35#include "AliRun.h"
36#include "AliTPC.h"
37#include "AliTPCclustererMI.h"
38#include "AliTPCtrackerMI.h"
39#include "AliITS.h"
40#include "AliITSclustererV2.h"
41#include "AliITStrackerV2.h"
42#include "AliITSLoader.h"
43#include "AliV0vertexer.h"
44#include <TSystem.h>
45#include <TSocket.h>
46#include <TMessage.h>
47#include <TGridResult.h>
48#include <TROOT.h>
49
50
51ClassImp(AliMonitorProcess)
52
53
54const Int_t AliMonitorProcess::kgPort = 9327;
55
56
57//_____________________________________________________________________________
58AliMonitorProcess::AliMonitorProcess(const char* alienDir,
59 const char* fileNameGalice)
60{
61// initialize the monitoring process and the monitor histograms
62
63 fGrid = TGrid::Connect("alien", gSystem->Getenv("USER"));
64 if (!fGrid || fGrid->IsZombie() || !fGrid->IsConnected()) {
65 delete fGrid;
66 Fatal("AliMonitorProcess", "could not connect to alien");
67 }
68 fGrid->cd(alienDir);
69 fLogicalFileName = "";
70 fFileName = "";
71
72 fRunLoader = AliRunLoader::Open(fileNameGalice);
73 if (!fRunLoader) Fatal("AliMonitorProcess",
74 "could not get run loader from file %s",
75 fileNameGalice);
76
77 fRunLoader->CdGAFile();
78 fTPCParam = AliTPC::LoadTPCParam(gFile);
79 if (!fTPCParam) Fatal("AliMonitorProcess", "could not load TPC parameters");
80
81 fRunLoader->LoadgAlice();
82 gAlice = fRunLoader->GetAliRun();
83 if (!gAlice) Fatal("AliMonitorProcess", "no gAlice object found");
84 AliITS* ITS = (AliITS*) gAlice->GetModule("ITS");
85 if (!ITS) Fatal("AliMonitorProcess", "no ITS detector found");
86 fITSgeom = ITS->GetITSgeom();
87 if (!fITSgeom) Fatal("AliMonitorProcess", "could not load ITS geometry");
88
89 fRunNumber = 0;
90 fSubRunNumber = 0;
91 fNEvents = 0;
92 fNEventsMin = 2;
93 fWriteHistoList = kFALSE;
94
95 fTopFolder = new TFolder("Monitor", "monitor histograms");
96 fTopFolder->SetOwner(kTRUE);
97
98 fMonitors.Add(new AliMonitorTPC(fTPCParam));
99 fMonitors.Add(new AliMonitorITS(fITSgeom));
100 fMonitors.Add(new AliMonitorV0s);
101
102 for (Int_t iMonitor = 0; iMonitor < fMonitors.GetEntriesFast(); iMonitor++) {
103 ((AliMonitor*) fMonitors[iMonitor])->CreateHistos(fTopFolder);
104 }
105
106 TIterator* iFolder = fTopFolder->GetListOfFolders()->MakeIterator();
107 while (TFolder* folder = (TFolder*) iFolder->Next()) folder->SetOwner(kTRUE);
108 delete iFolder;
109
110 fFile = TFile::Open("monitor_tree.root", "RECREATE");
111 if (!fFile || !fFile->IsOpen()) {
112 Fatal("AliMonitorProcess", "could not open file for tree");
113 }
114 fTree = new TTree("MonitorTree", "tree for monitoring");
115 for (Int_t iMonitor = 0; iMonitor < fMonitors.GetEntriesFast(); iMonitor++) {
116 ((AliMonitor*) fMonitors[iMonitor])->CreateBranches(fTree);
117 }
118 gROOT->cd();
119
120 fServerSocket = new TServerSocket(kgPort, kTRUE);
121 fServerSocket->SetOption(kNoBlock, 1);
122 fDisplaySocket = NULL;
123 CheckForConnections();
124
125 fStatus = kStopped;
126 fStopping = kFALSE;
127}
128
129//_____________________________________________________________________________
130AliMonitorProcess::~AliMonitorProcess()
131{
132// clean up
133
134 fMonitors.Delete();
135 delete fTopFolder;
136 delete fRunLoader;
137
138 delete fServerSocket;
139 fSockets.Delete();
140 delete fDisplaySocket;
141
142 fGrid->Close();
143 delete fGrid;
144
145 fFile->Close();
146 delete fFile;
147 gSystem->Unlink("monitor_tree.root");
148}
149
150
151//_____________________________________________________________________________
152const char* AliMonitorProcess::GetRevision()
153{
154 return "$Revision$";
155}
156
157
158//_____________________________________________________________________________
159void AliMonitorProcess::Run()
160{
161// run the monitor process:
162// check for a raw data file, process the raw data file and delete it
163
164 fStopping = kFALSE;
165
166 while (!fStopping) {
167 fStatus = kWaiting;
168 while (!CheckForNewFile()) {
169 CheckForConnections();
170 fStatus = kWaiting;
171 if (fStopping) break;
172 gSystem->Sleep(10);
173 }
174 if (fStopping) break;
175
176 ProcessFile();
177 }
178
179 WriteHistos();
180
181 fStopping = kFALSE;
182 fStatus = kStopped;
183}
184
185
186//_____________________________________________________________________________
187void AliMonitorProcess::Stop()
188{
189// set the fStopping flag to terminate the monitor process after the current
190// event was processed
191
192 if (fStatus != kStopped) fStopping = kTRUE;
193}
194
195
196//_____________________________________________________________________________
197void AliMonitorProcess::ProcessFile(const char* fileName)
198{
199// create a file with monitor histograms for a single file
200
201 if (fStatus != kStopped) {
202 Error("ProcessFile", "ProcessFile can not be called"
203 " while the monitor process is running");
204 return;
205 }
206
207 fFileName = fileName;
208 Int_t nEventMin = fNEventsMin;
209 fNEventsMin = 1;
210 ProcessFile();
211 WriteHistos();
212 fNEventsMin = nEventMin;
213 fStatus = kStopped;
214}
215
216
217//_____________________________________________________________________________
218Bool_t AliMonitorProcess::CheckForNewFile()
219{
220// check whether a new file was registered in alien
221
222 TGridResult* result = fGrid->Ls();
223 Long_t maxDate = -1;
224 Long_t maxTime = -1;
225 TString fileName;
226
227 while (const char* entry = result->Next()) {
228 // entry = host_date_time.root
229 TString entryCopy(entry);
230 char* p = const_cast<char*>(entryCopy.Data());
6ad9b9d5 231 if (!strtok(p, "_") || !p) continue; // host name
232 char* dateStr = strtok(p, "_");
04fa961a 233 if (!dateStr || !p) continue;
6ad9b9d5 234 char* timeStr = strtok(p, ".");
04fa961a 235 if (!timeStr || !p) continue;
236 Long_t date = atoi(dateStr);
237 Long_t time = atoi(timeStr);
238
239 if ((date > maxDate) || ((date == maxDate) && (time > maxTime))) {
240 maxDate = date;
241 maxTime = time;
242 fileName = entry;
243 }
244 }
245
246 if (maxDate < 0) return kFALSE; // no files found
247 if (fLogicalFileName.CompareTo(fileName) == 0) return kFALSE; // no new file
248
249 fLogicalFileName = fileName;
250 fFileName = fGrid->GetPhysicalFileName(fLogicalFileName.Data());
251 return kTRUE;
252}
253
254//_____________________________________________________________________________
255Bool_t AliMonitorProcess::ProcessFile()
256{
257// loop over all events in the raw data file, run the reconstruction
258// and fill the monitor histograms
259
260 Int_t nEvents = GetNumberOfEvents(fFileName);
261 if (nEvents <= 0) return kFALSE;
262 Info("ProcessFile", "found %d event(s) in file %s",
263 nEvents, fFileName.Data());
264
265 // loop over the events
266 for (Int_t iEvent = 0; iEvent < nEvents; iEvent++) {
267 fStatus = kReading;
268 fRunLoader->SetEventNumber(0);
269 AliRawReaderRoot rawReader(fFileName, iEvent);
270 if (fStopping) break;
271 if (rawReader.GetRunNumber() != fRunNumber) {
272 WriteHistos();
273 StartNewRun();
274 fRunNumber = rawReader.GetRunNumber();
275 fEventNumber[0] = rawReader.GetEventId()[0];
276 fEventNumber[1] = rawReader.GetEventId()[1];
277 fSubRunNumber = 0;
278 if (fStopping) break;
279 }
280
281 if (!ReconstructTPC(&rawReader)) return kFALSE;
282 if (fStopping) break;
283 if (!ReconstructITS(&rawReader)) return kFALSE;
284 if (fStopping) break;
285 if (!ReconstructV0s()) return kFALSE;
286 if (fStopping) break;
287
288 if (fDisplaySocket) fDisplaySocket->Send("new event");
289
290 Info("ProcessFile", "filling histograms...");
291 fStatus = kFilling;
292 for (Int_t iMonitor = 0; iMonitor < fMonitors.GetEntriesFast(); iMonitor++) {
293 ((AliMonitor*) fMonitors[iMonitor])->FillHistos(fRunLoader, &rawReader);
294 if (fStopping) break;
295 }
296 if (fStopping) break;
297
298 Info("ProcessFile", "updating histograms...");
299 fStatus = kUpdating;
300 TIterator* iFolder = fTopFolder->GetListOfFolders()->MakeIterator();
301 while (TFolder* folder = (TFolder*) iFolder->Next()) {
302 TIterator* iHisto = folder->GetListOfFolders()->MakeIterator();
303 while (AliMonitorPlot* histo = (AliMonitorPlot*) iHisto->Next()) {
304 histo->Update();
305 }
306 delete iHisto;
307 }
308 delete iFolder;
309 if (fStopping) break;
310
311 Info("ProcessFile", "filling the tree...");
312 fTree->Fill();
313
314 Info("ProcessFile", "broadcasting histograms...");
315 CheckForConnections();
316 BroadcastHistos();
317
318 fNEvents++;
319 if (fStopping) break;
320 }
321
322 return kTRUE;
323}
324
325//_____________________________________________________________________________
326void AliMonitorProcess::Reset()
327{
328// write the current histograms to a file and reset them
329
330 if (fSubRunNumber == 0) fSubRunNumber++;
331 WriteHistos();
332 StartNewRun();
333 fSubRunNumber++;
334}
335
336
337//_____________________________________________________________________________
338UInt_t AliMonitorProcess::GetEventPeriodNumber()
339{
340// get the period number from the event id
341
342 return (fEventNumber[1] >> 4);
343}
344
345//_____________________________________________________________________________
346UInt_t AliMonitorProcess::GetEventOrbitNumber()
347{
348// get the orbit number from the event id
349
350 return ((fEventNumber[1] & 0x000F) << 20) + (fEventNumber[0] >> 12);
351}
352
353//_____________________________________________________________________________
354UInt_t AliMonitorProcess::GetEventBunchNumber()
355{
356// get the bunch number from the event id
357
358 return (fEventNumber[0] % 0x0FFF);
359}
360
361//_____________________________________________________________________________
362Int_t AliMonitorProcess::GetNumberOfEvents(const char* fileName)
363{
364// determine the number of events in the given raw data file
365
366 Int_t nEvents = -1;
367
368 TFile* file = TFile::Open(fileName);
369 if (!file || !file->IsOpen()) {
370 Error("GetNumberOfEvents", "could not open file %s", fileName);
371 if (file) delete file;
372 return -1;
373 }
374
375 TTree* tree = (TTree*) file->Get("RAW");
376 if (!tree) {
377 Error("GetNumberOfEvents", "could not find tree with raw data");
378 } else {
379 nEvents = (Int_t) tree->GetEntries();
380 }
381 file->Close();
382 delete file;
383
384 return nEvents;
385}
386
387//_____________________________________________________________________________
388Bool_t AliMonitorProcess::ReconstructTPC(AliRawReader* rawReader)
389{
390// find TPC clusters and tracks
391
392 fStatus = kRecTPC;
393
394 AliLoader* tpcLoader = fRunLoader->GetLoader("TPCLoader");
395 if (!tpcLoader) {
396 Error("ReconstructTPC", "no TPC loader found");
397 return kFALSE;
398 }
399 gSystem->Unlink("TPC.RecPoints.root");
400 gSystem->Unlink("TPC.Tracks.root");
401
402 // cluster finder
403 Info("ReconstructTPC", "reconstructing clusters...");
404 tpcLoader->LoadRecPoints("recreate");
405 AliTPCclustererMI clusterer(fTPCParam);
406 tpcLoader->MakeRecPointsContainer();
407 clusterer.SetOutput(tpcLoader->TreeR());
408 clusterer.Digits2Clusters(rawReader);
409 tpcLoader->WriteRecPoints("OVERWRITE");
410
411 // track finder
412 Info("ReconstructTPC", "reconstructing tracks...");
413 tpcLoader->LoadTracks("recreate");
414 {
415 AliTPCtrackerMI tracker(fTPCParam);
416 tracker.Clusters2Tracks();
417 }
418
419 tpcLoader->UnloadRecPoints();
420 tpcLoader->UnloadTracks();
421 return kTRUE;
422}
423
424//_____________________________________________________________________________
425Bool_t AliMonitorProcess::ReconstructITS(AliRawReader* rawReader)
426{
427// find ITS clusters and tracks
428
429 fStatus = kRecITS;
430
431 AliLoader* itsLoader = fRunLoader->GetLoader("ITSLoader");
432 if (!itsLoader) {
433 Error("ReconstructITS", "no ITS loader found");
434 return kFALSE;
435 }
436 AliLoader* tpcLoader = fRunLoader->GetLoader("TPCLoader");
437 if (!tpcLoader) {
438 Error("ReconstructITS", "no TPC loader found");
439 return kFALSE;
440 }
441 gSystem->Unlink("ITS.RecPoints.root");
442 gSystem->Unlink("ITS.Tracks.root");
443
444 // cluster finder
445 Info("ReconstructITS", "reconstructing clusters...");
446 itsLoader->LoadRecPoints("recreate");
447 AliITSclustererV2 clusterer(fITSgeom);
448 itsLoader->MakeRecPointsContainer();
449 clusterer.Digits2Clusters(rawReader);
450
451 // track finder
452 Info("ReconstructITS", "reconstructing tracks...");
453 itsLoader->LoadTracks("recreate");
454 itsLoader->MakeTracksContainer();
455 tpcLoader->LoadTracks();
456 AliITStrackerV2 tracker(fITSgeom);
457 tracker.LoadClusters(itsLoader->TreeR());
458 tracker.Clusters2Tracks(tpcLoader->TreeT(), itsLoader->TreeT());
459 tracker.UnloadClusters();
460 itsLoader->WriteTracks("OVERWRITE");
461
462 itsLoader->UnloadRecPoints();
463 itsLoader->UnloadTracks();
464 tpcLoader->UnloadTracks();
465 return kTRUE;
466}
467
468//_____________________________________________________________________________
469Bool_t AliMonitorProcess::ReconstructV0s()
470{
471// find V0s
472
473 fStatus = kRecV0s;
474
475 AliITSLoader* itsLoader = (AliITSLoader*) fRunLoader->GetLoader("ITSLoader");
476 if (!itsLoader) {
477 Error("ReconstructV0", "no ITS loader found");
478 return kFALSE;
479 }
480 gSystem->Unlink("ITS.V0s.root");
481
482 // V0 finder
483 Info("ReconstructV0s", "reconstructing V0s...");
484 itsLoader->LoadTracks("read");
485 itsLoader->LoadV0s("recreate");
486 AliV0vertexer vertexer;
487 TTree* tracks = itsLoader->TreeT();
488 if (!tracks) {
489 Error("ReconstructV0s", "no ITS tracks tree found");
490 return kFALSE;
491 }
492 if (!itsLoader->TreeV0()) itsLoader->MakeTree("V0");
493 TTree* v0s = itsLoader->TreeV0();
494 vertexer.Tracks2V0vertices(tracks, v0s);
495 itsLoader->WriteV0s("OVERWRITE");
496
497 itsLoader->UnloadTracks();
498 itsLoader->UnloadV0s();
499 return kTRUE;
500}
501
502
503//_____________________________________________________________________________
504Bool_t AliMonitorProcess::WriteHistos()
505{
506// write the monitor tree and the monitor histograms to the file
507// "monitor_<run number>[_<sub_run_number>].root"
508// if at least fNEventsMin events were monitored
509
510 fStatus = kWriting;
511
512 // rename tree file and create a new one
513 fFile->cd();
514 fTree->Write();
515 fFile->Close();
516 delete fFile;
517
518 char fileName[256];
519 sprintf(fileName, "monitor_tree_%d.root", fRunNumber);
520 if (fSubRunNumber > 0) {
521 sprintf(fileName, "monitor_tree_%d_%d.root", fRunNumber, fSubRunNumber);
522 }
523 if (fNEvents < fNEventsMin) {
524 gSystem->Unlink("monitor_tree.root");
525 } else {
526 gSystem->Rename("monitor_tree.root", fileName);
527 }
528
529 fFile = TFile::Open("monitor_tree.root", "RECREATE");
530 if (!fFile || !fFile->IsOpen()) {
531 Fatal("WriteHistos", "could not open file for tree");
532 }
533 fTree = new TTree("MonitorTree", "tree for monitoring");
534 for (Int_t iMonitor = 0; iMonitor < fMonitors.GetEntriesFast(); iMonitor++) {
535 ((AliMonitor*) fMonitors[iMonitor])->CreateBranches(fTree);
536 }
537 gROOT->cd();
538
539 // write the histograms
540 if (fNEvents < fNEventsMin) return kTRUE;
541
542 if (!fWriteHistoList) {
543 TIterator* iFolder = fTopFolder->GetListOfFolders()->MakeIterator();
544 while (TFolder* folder = (TFolder*) iFolder->Next()) {
545 TIterator* iHisto = folder->GetListOfFolders()->MakeIterator();
546 while (AliMonitorPlot* histo = (AliMonitorPlot*) iHisto->Next()) {
547 histo->ResetList();
548 }
549 delete iHisto;
550 }
551 delete iFolder;
552 }
553
554 Bool_t result = kTRUE;
555 sprintf(fileName, "monitor_%d.root", fRunNumber);
556 if (fSubRunNumber > 0) {
557 sprintf(fileName, "monitor_%d_%d.root", fRunNumber, fSubRunNumber);
558 }
559 TFile* file = TFile::Open(fileName, "recreate");
560 if (!file || !file->IsOpen()) {
561 Error("WriteHistos", "could not open file %s", fileName);
562 result = kFALSE;
563 } else {
564 fTopFolder->Write();
565 file->Close();
566 }
567 if (file) delete file;
568
569 return result;
570}
571
572//_____________________________________________________________________________
573void AliMonitorProcess::StartNewRun()
574{
575// reset the histograms for a new run
576
577 fStatus = kResetting;
578 TIterator* iFolder = fTopFolder->GetListOfFolders()->MakeIterator();
579 while (TFolder* folder = (TFolder*) iFolder->Next()) {
580 TIterator* iHisto = folder->GetListOfFolders()->MakeIterator();
581 while (AliMonitorPlot* histo = (AliMonitorPlot*) iHisto->Next()) {
582 histo->Reset();
583 }
584 delete iHisto;
585 }
586 delete iFolder;
587
588 fNEvents = 0;
589}
590
591
592//_____________________________________________________________________________
593void AliMonitorProcess::CheckForConnections()
594{
595// check if new clients want to connect and add them to the list of sockets
596
597 TMessage message(kMESS_OBJECT);
598 message.WriteObject(fTopFolder);
599 fStatus = kConnecting;
600
601 TSocket* socket;
602 while ((socket = fServerSocket->Accept()) != (TSocket*)-1) {
603 char socketType[256];
604 if (!socket->Recv(socketType, 255)) continue;
605 if (strcmp(socketType, "client") == 0) {
606 if ((fNEvents == 0) || (socket->Send(message) >= 0)) {
607 fSockets.Add(socket);
608 TInetAddress adr = socket->GetInetAddress();
609 Info("CheckForConnections", "new client:\n %s (%s), port %d\n",
610 adr.GetHostName(), adr.GetHostAddress(), adr.GetPort());
611 }
612 } else if (strcmp(socketType, "display") == 0) {
613 if (fDisplaySocket) {
614 fDisplaySocket->Close();
615 delete fDisplaySocket;
616 }
617 fDisplaySocket = socket;
618 fDisplaySocket->SetOption(kNoBlock, 1);
619 TInetAddress adr = socket->GetInetAddress();
620 Info("CheckForConnections", "new display:\n %s (%s), port %d\n",
621 adr.GetHostName(), adr.GetHostAddress(), adr.GetPort());
622 }
623 }
624
625 for (Int_t iSocket = 0; iSocket < fSockets.GetEntriesFast(); iSocket++) {
626 socket = (TSocket*) fSockets[iSocket];
627 if (!socket) continue;
628 if (!socket->IsValid()) {
629 // remove invalid sockets from the list
630 TInetAddress adr = socket->GetInetAddress();
631 Info("BroadcastHistos", "disconnect client:\n %s (%s), port %d\n",
632 adr.GetHostName(), adr.GetHostAddress(), adr.GetPort());
633 delete fSockets.RemoveAt(iSocket);
634 }
635 }
636 fSockets.Compress();
637}
638
639//_____________________________________________________________________________
640void AliMonitorProcess::BroadcastHistos()
641{
642// send the monitor histograms to the clients
643
644 fStatus = kBroadcasting;
645 TMessage message(kMESS_OBJECT);
646 message.WriteObject(fTopFolder);
647
648 for (Int_t iSocket = 0; iSocket < fSockets.GetEntriesFast(); iSocket++) {
649 TSocket* socket = (TSocket*) fSockets[iSocket];
650 if (!socket) continue;
651 if (!socket->IsValid() || (socket->Send(message) < 0)) {
652 // remove the socket from the list if there was an error
653 TInetAddress adr = socket->GetInetAddress();
654 Info("BroadcastHistos", "disconnect client:\n %s (%s), port %d\n",
655 adr.GetHostName(), adr.GetHostAddress(), adr.GetPort());
656 delete fSockets.RemoveAt(iSocket);
657 }
658 }
659 fSockets.Compress();
660}