source: trunk/MagicSoft/Mars/mcorsika/MCorsikaRunHeader.cc@ 9341

Last change on this file since 9341 was 9336, checked in by tbretz, 16 years ago
*** empty log message ***
File size: 8.1 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 12/2000 <mailto:tbretz@astro.uni-wuerzburg.de>
19 Qi Zhe, 06/2007 <mailto:qizhe@astro.uni-wuerzburg.de>
20
21! Copyright: Software Development, 2000-2009
22!
23!
24\* ======================================================================== */
25
26/////////////////////////////////////////////////////////////////////////////
27//
28// MCorsikaRunHeader
29//
30// Root storage container for the RUN HEADER information
31//
32// Class Version 2:
33// ----------------
34// + UInt_t fParticleID
35// + Float_t fImpactMax
36// + Float_t fMagneticFieldX
37// + Float_t fMagneticFieldZ
38// + Float_t fMagneticFieldAz
39//
40////////////////////////////////////////////////////////////////////////////
41
42#include "MCorsikaRunHeader.h"
43
44#include <fstream>
45#include <iomanip>
46
47#include "MLog.h"
48#include "MLogManip.h"
49
50#include "MMcEvt.hxx"
51
52ClassImp(MCorsikaRunHeader);
53
54using namespace std;
55
56// --------------------------------------------------------------------------
57//
58// Default constructor. Creates array which stores the pixel assignment.
59//
60//
61MCorsikaRunHeader::MCorsikaRunHeader(const char *name, const char *title)
62 : fNumObsLevel(0), fZdMin(0), fZdMax(-1), fAzMin(0), fAzMax(0),
63 fViewConeInnerAngle(0), fViewConeOuterAngle(-1)
64{
65 fName = name ? name : "MCorsikaRunHeader";
66 fTitle = title ? title : "Raw Run Header Information";
67}
68
69// --------------------------------------------------------------------------
70//
71// Read in one run header from the binary file
72//
73Bool_t MCorsikaRunHeader::ReadEvt(istream& fin)
74{
75 char runh[4];
76 fin.read(runh, 4);
77 if (memcmp(runh, "RUNH", 4))
78 {
79 *fLog << err << "ERROR - Wrong identifier: RUNH expected." << endl;
80 return kFALSE;
81 }
82
83 Float_t f[68];
84 fin.read((char*)f, 68);
85
86 fRunNumber = TMath::Nint(f[0]);
87 fNumEvents = 0;
88
89 fRunStart.SetCorsikaTime(f[1]);
90
91 fProgramVersion = f[2];
92 fNumObsLevel = TMath::Nint(f[3]);
93
94 if (fNumObsLevel!=1)
95 {
96 *fLog << err << "ERROR - Currently only one observation level is allowed." << endl;
97 return kFALSE;
98 }
99
100 memset(fObsLevel, 0, 10*4);
101 memcpy(fObsLevel, f+4, fNumObsLevel*4);
102
103 fSlopeSpectrum = f[14];
104 fEnergyMin = f[15];
105 fEnergyMax = f[16];
106
107 fin.seekg(1020, ios::cur); // skip the remaining data of this block
108
109 // -------------------- Read first event header -------------------
110
111 // FIXME: Add sanity checks!
112
113 // f[76] Cherenkov flag:
114 // bit(1) : CERENKOV option compiled in
115 // bit(2) : IACT option compiled in
116 // bit(3) : CEFFIC option compiled in
117 // bit(4) : ATMEXT option compiled in
118 // bit(5) : ATMEXT option used with refraction enabled
119 // bit(6) : VOLUMEDET option compiled in
120 // bit(7) : CURVED option compiled in
121 // bit(9) : SLATN option compiled in
122 // 11-21 : table number for externam athmosphere (but<1024)
123 //
124 // f[78] Curved athmosphere? (0=flat, 1=curved)
125 // f[84] cherenkov bunch size
126 // f[93] flag for additinal muon information of particle output file
127 // f[145] Muon multiple scattering flag
128 // f[156] altitude of horizontal shower axis
129
130 char evth[4];
131 fin.read(evth, 4);
132 if (memcmp(evth, "EVTH", 4))
133 {
134 *fLog << err << "ERROR - Wrong identifier: EVTH expected." << endl;
135 return kFALSE;
136 }
137
138 Float_t g[273];
139 fin.read((char*)&g, 273*4);
140 if (fin.eof())
141 return kFALSE;
142
143 fin.seekg(-274*4, ios::cur);
144
145 const Int_t n = TMath::Nint(g[96]); // Number i of uses of each cherenkov event
146 if (n!=1)
147 {
148 *fLog << err << "ERROR - Currently only one impact parameter per event is supported." << endl;
149 return kFALSE;
150 }
151
152 fParticleID = TMath::Nint(g[1]);
153
154 // MAGNETIC FIELD: x/z-component of earth magnetic field in muT
155 fMagneticFieldX = g[69]; // x-component ( BX)
156 fMagneticFieldZ = -g[70]; // z-component (-BZ)
157 fMagneticFieldAz = g[91]; // Azimuth angle of magnetic north expressed in telescope coordinates
158
159 fZdMin = g[79]; // lower edge of theta in °
160 fZdMax = g[80]; // upper edge of theta in °
161 fAzMin = 180-g[81]; // lower edge of phi in °
162 fAzMax = 180-g[82]; // upper edge of phi in °
163 // FIXME: Correct for direction of magnetic field!
164
165 // Number of cherenkov detectors in x
166 // Number of cherenkov detectors in y
167 // Grid spacing x
168 // Grid spacing y
169
170 // g[93] angle between array x-direction and magnetic north
171
172
173 fImpactMax = g[86];
174
175 fWavelengthMin = g[95]; // Cherenkov bandwidth lower end in nm
176 fWavelengthMax = g[96]; // Cherenkov bandwidth upper end in nm
177
178 fViewConeInnerAngle = g[151]; // inner angle of view cone (°)
179 fViewConeOuterAngle = g[152]; // outer angle of view cone (°)
180
181 return kTRUE;
182}
183
184Bool_t MCorsikaRunHeader::ReadEvtEnd(istream& fin)
185{
186 char runh[4];
187 fin.read(runh, 4);
188 if (memcmp(runh, "RUNE", 4))
189 {
190 *fLog << err << "ERROR - Wrong identifier: RUNE expected." << endl;
191 return kFALSE;
192 }
193
194 Float_t f[2];
195 fin.read((char*)f, 2*4);
196
197 const UInt_t runnum = TMath::Nint(f[0]);
198 if (runnum!=fRunNumber)
199 {
200 *fLog << err << "ERROR - Mismatch in stream: Run number in RUNE (";
201 *fLog << runnum << ") doesn't match RUNH (" << fRunNumber << ")." << endl;
202 return kFALSE;
203 }
204
205 fNumEvents = TMath::Nint(f[1]);
206
207 fin.seekg(270*4, ios::cur); // skip the remaining data of this block
208
209 return kTRUE;
210}
211
212Bool_t MCorsikaRunHeader::SeekEvtEnd(istream &fin)
213{
214 // Search subblockwise backward (Block: 5733*4 = 21*273*4)
215 for (int i=1; i<22; i++)
216 {
217 fin.seekg(-i*273*4, ios::end);
218
219 char runh[4];
220 fin.read(runh, 4);
221
222 if (!memcmp(runh, "RUNE", 4))
223 {
224 fin.seekg(-4, ios::cur);
225 return kTRUE;
226 }
227 }
228
229 return kFALSE;
230}
231
232// --------------------------------------------------------------------------
233//
234// print run header information on *fLog. The option 'header' supresses
235// the pixel index translation table.
236//
237void MCorsikaRunHeader::Print(Option_t *t) const
238{
239 *fLog << all << endl;
240 *fLog << "Run Number: " << fRunNumber << " (" << fRunStart.GetStringFmt("%d.%m.%Y") << ", V" << fProgramVersion << ")" << endl;
241 *fLog << "Particle ID: " << MMcEvt::GetParticleName(fParticleID) << endl;
242 if (fNumEvents>0)
243 *fLog << "Num Events: " << fNumEvents << endl;
244 *fLog << "Obs Level: ";
245 for (Byte_t i=0; i<fNumObsLevel; i++)
246 *fLog << " " << fObsLevel[i]/100. << "m";
247 *fLog << endl;
248
249 *fLog << "MagneticField: X/Z=(" << fMagneticFieldX << "/";
250 *fLog << fMagneticFieldZ << ") Az=" << fMagneticFieldAz*TMath::RadToDeg() << "deg" << endl;
251
252 *fLog << "Spectrum: Slope=" << fSlopeSpectrum << " (" << fEnergyMin << "GeV-" << fEnergyMax << "GeV)" << endl;
253
254 if (fViewConeOuterAngle>0)
255 *fLog << "ViewCone: " << fViewConeInnerAngle << "deg-" << fViewConeOuterAngle << "deg" << endl;
256
257 if (fZdMax>=0)
258 {
259 *fLog << "Zd/Az: " << fZdMin << "deg";
260 if (fZdMin==fZdMax)
261 *fLog << " (fixed)";
262 else
263 *fLog << "-" << fZdMax << "deg";
264 *fLog << " / " << fAzMin << "deg";
265 if (fAzMin==fAzMax)
266 *fLog << " (fixed)";
267 else
268 *fLog << "-" << fAzMax << "deg";
269 *fLog << endl;
270 }
271}
272
Note: See TracBrowser for help on using the repository browser.