source: trunk/MagicSoft/Mars/mreport/MReportFileRead.cc@ 2624

Last change on this file since 2624 was 2592, checked in by tbretz, 21 years ago
*** empty log message ***
File size: 9.4 KB
Line 
1/* ======================================================================== *\
2!
3! *
4! * This file is part of MARS, the MAGIC Analysis and Reconstruction
5! * Software. It is distributed to you in the hope that it can be a useful
6! * and timesaving tool in analysing Data of imaging Cerenkov telescopes.
7! * It is distributed WITHOUT ANY WARRANTY.
8! *
9! * Permission to use, copy, modify and distribute this software and its
10! * documentation for any purpose is hereby granted without fee,
11! * provided that the above copyright notice appear in all copies and
12! * that both that copyright notice and this permission notice appear
13! * in supporting documentation. It is provided "as is" without express
14! * or implied warranty.
15! *
16!
17!
18! Author(s): Thomas Bretz, 11/2003 <mailto:tbretz@astro.uni-wuerzburg.de>
19!
20! Copyright: MAGIC Software Development, 2000-2003
21!
22!
23\* ======================================================================== */
24
25//////////////////////////////////////////////////////////////////////////////
26//
27// MReportFileRead
28//
29// Task to read the central control report file. For more information see
30// the base class of all reports MReport.
31//
32// To add a report which should be read use AddToList.
33//
34// eg. AddToList("Drive") will assume the existance of a class called
35// MReportDrive. It will create such an object automatically. It will
36// send all lines starting with 'MReportDrive::fIndetifier-REPORT'
37// to this class.
38//
39//////////////////////////////////////////////////////////////////////////////
40#include "MReportFileRead.h"
41
42#include <fstream>
43
44#include <TClass.h>
45#include <TRegexp.h>
46#include <THashTable.h>
47
48#include "MLog.h"
49#include "MLogManip.h"
50
51#include "MReport.h"
52#include "MParList.h"
53
54ClassImp(MReportFileRead);
55
56using namespace std;
57
58const TString MReportFileRead::gsReportHeader ="[CC Report File]";
59const TString MReportFileRead::gsVersionPrefix="Arehucas Version Number";
60
61class MReportHelp : public TObject
62{
63private:
64 MReport *fReport;
65 ULong_t fNumReports;
66
67public:
68 MReportHelp(const char *name, MLog *fLog) : fReport(NULL), fNumReports(0)
69 {
70 TClass *cls = gROOT->GetClass(name);
71 Int_t rc = 0;
72 if (!cls)
73 rc =1;
74 else
75 {
76 if (!cls->Property())
77 rc = 5;
78 if (!cls->Size())
79 rc = 4;
80 if (!cls->IsLoaded())
81 rc = 3;
82 if (!cls->HasDefaultConstructor())
83 rc = 2;
84 }
85
86 if (rc)
87 {
88 *fLog << err << dbginf << "Cannot create new instance of class '" << name << "': ";
89 switch (rc)
90 {
91 case 1:
92 *fLog << "gROOT->GetClass() returned NULL." << endl;
93 return;
94 case 2:
95 *fLog << "no default constructor." << endl;
96 return;
97 case 3:
98 *fLog << "not loaded." << endl;
99 return;
100 case 4:
101 *fLog << "zero size." << endl;
102 return;
103 case 5:
104 *fLog << "no property." << endl;
105 return;
106 }
107 }
108
109 //
110 // create the parameter container of the the given class type
111 //
112 fReport = (MReport*)cls->New();
113 }
114 ~MReportHelp() { if (fReport) delete fReport; }
115
116 const char *GetName() const { return fReport->GetIdentifier(); }
117 ULong_t GetNumReports() const { return fNumReports; }
118 ULong_t Hash() const { return fReport->GetIdentifier().Hash(); }
119 MReport *GetReport() { return fReport; }
120 //void SetTime(MTime *t) { fReport->SetTime(t); }
121 Bool_t Interprete(TString &str)
122 {
123 if (!fReport->Interprete(str))
124 return kFALSE;
125
126 fNumReports++;
127 return kTRUE;
128 }
129 Bool_t SetupReading(MParList &plist) { return fReport->SetupReading(plist); }
130 void AddToList(MParList &plist) { plist.AddToList(fReport); }
131};
132
133// --------------------------------------------------------------------------
134//
135// Default constructor. It tries to open the given file and creates a
136// THashTable which allows faster access to the MReport* objects.
137//
138MReportFileRead::MReportFileRead(const char *fname, const char *name, const char *title)
139 : fFileName(fname), fIn(NULL)
140{
141 fName = name ? name : "MReportFileRead";
142 fTitle = title ? title : "Read task to read Central Control report files";
143
144 fIn = new ifstream;
145 fList = new THashTable(1,1);
146 fList->SetOwner();
147}
148
149// --------------------------------------------------------------------------
150//
151// Destructor. Delete input stream and hash table.
152//
153MReportFileRead::~MReportFileRead()
154{
155 delete fIn;
156 delete fList;
157}
158
159MReportHelp *MReportFileRead::GetReportHelp(const TString &str) const
160{
161 return (MReportHelp*)fList->FindObject(str);
162}
163
164MReport *MReportFileRead::GetReport(MReportHelp *help) const
165{
166 return help ? help->GetReport() : 0;
167}
168
169MReport *MReportFileRead::GetReport(const TString &str) const
170{
171 return GetReport(GetReportHelp(str));
172}
173
174// --------------------------------------------------------------------------
175//
176// Add a new MReport* to the list (eg 'Drive' will add MReportDrive)
177// For convinience the object is created as a MReportHelp object.
178//
179Bool_t MReportFileRead::AddToList(const char *name) const
180{
181 MReportHelp *help = new MReportHelp(name, fLog);
182
183 MReport *rep = NULL;
184 if (!(rep=help->GetReport()))
185 return kFALSE;
186
187 if (GetReport(rep->GetIdentifier()))
188 {
189 *fLog << warn << "WARNING - Report with Identifier '";
190 *fLog << rep->GetIdentifier() << "' already added to the list... ";
191 *fLog << "ignored." << endl;
192 delete help;
193 return kFALSE;
194 }
195
196 fList->Add(help);
197 return kTRUE;
198}
199
200// --------------------------------------------------------------------------
201//
202// Check whether the file header corresponds to a central control file
203// header and check for the existance of a correct version number.
204// The version number may later be used to be able to read different
205// file versions
206//
207Bool_t MReportFileRead::CheckFileHeader() const
208{
209 TString str;
210 str.ReadLine(*fIn); // Read to EOF or newline
211 if (str != gsReportHeader)
212 {
213 *fLog << err << "ERROR - First line doesn't match '" << gsReportHeader <<"' ";
214 *fLog << "in file '" << fFileName << "'"<<endl;
215 return kFALSE;
216 }
217
218 str.ReadLine(*fIn); // Read to EOF or newline
219 if (!str.BeginsWith(gsVersionPrefix))
220 {
221 *fLog << err << "ERROR - Version prefix '" << gsVersionPrefix <<"' ";
222 *fLog << "not found in second line of file '" << fFileName << "'"<<endl;
223 return kFALSE;
224 }
225
226 str.Remove(0, gsVersionPrefix.Length());
227 str = str.Strip(TString::kBoth);
228
229 TString ver = str(TRegexp("^[0-9][0-9][0-9][0-9][0-9][0-9]-[0-9]$"));
230 if (ver.IsNull())
231 {
232 *fLog << err << "ERROR - Version string '" << str <<"' doesn't ";
233 *fLog << "match regular expression." << endl;
234 return kFALSE;
235 }
236
237 *fLog << dbg << "Report File version: <" << ver << ">" << endl;
238
239 return kTRUE;
240}
241
242// --------------------------------------------------------------------------
243//
244// Call SetupReading for all MReportHelp objects scheduled.
245// Try to open the file and check the file header.
246//
247Int_t MReportFileRead::PreProcess(MParList *pList)
248{
249 //MTime *time = (MTime*)pList->FindCreateObj("MTime");
250 //if (!time)
251 // return kFALSE;
252
253 TIter Next(fList);
254 MReportHelp *help=0;
255 while ((help=(MReportHelp*)Next()))
256 if (!help->SetupReading(*pList))
257 return kFALSE;
258
259 fList->ForEach(MReportHelp, AddToList)(*pList);
260
261 //
262 // open the input stream
263 // first of all check if opening the file in the constructor was
264 // successfull
265 //
266 fIn->open(fFileName);
267 if (!(*fIn))
268 {
269 *fLog << err << "Error: Cannot open file '" << fFileName << "'" << endl;
270 return kFALSE;
271 }
272
273 return CheckFileHeader();
274}
275
276// --------------------------------------------------------------------------
277//
278// Read the file line by line as long as a matching MReport* class is found.
279// In this case call its interpreter (Interprete()) and remove the identifier
280// first (XYZ-REPORT)
281//
282Int_t MReportFileRead::Process()
283{
284 TString str;
285
286 MReportHelp *rep=NULL;
287 while (!GetReport(rep))
288 {
289 str.ReadLine(*fIn);
290 if (!*fIn)
291 {
292 *fLog << dbg << "EOF detected." << endl;
293 return kFALSE;
294 }
295
296 const Int_t pos = str.First(' ');
297 if (pos<=0)
298 continue;
299
300 rep = GetReportHelp(str(0,pos));
301 if (GetReport(rep))
302 str.Remove(0, pos);
303 }
304
305 if (!rep->Interprete(str))
306 {
307 *fLog << err << "ERROR - Interpretation of '" << rep->GetName() << "' failed." << endl;
308 return kFALSE;
309 }
310
311 return kTRUE;
312}
313
314// --------------------------------------------------------------------------
315//
316// Close the file and print some execution statistics
317//
318Int_t MReportFileRead::PostProcess()
319{
320 fIn->close();
321
322 if (!GetNumExecutions())
323 return kTRUE;
324
325 *fLog << inf << endl;
326 *fLog << GetDescriptor() << " statistics:" << endl;
327 *fLog << dec << setfill(' ');
328
329 TIter Next(fList);
330 MReportHelp *rep=0;
331
332 while ((rep=(MReportHelp*)Next()))
333 {
334 *fLog << " " << setw(7) << rep->GetNumReports() << " (";
335 *fLog << setw(3) << (int)(100.*rep->GetNumReports()/GetNumExecutions());
336 *fLog << "%): " << rep->GetName() << endl;
337 }
338
339 return kTRUE;
340}
Note: See TracBrowser for help on using the repository browser.