source: fact/tools/pyscripts/pyfact/factfits.h@ 17693

Last change on this file since 17693 was 17693, checked in by dneise, 11 years ago
removed warning about time marker channels, since it is there since ages and nothing happens. So why should we warn about it?
File size: 6.0 KB
Line 
1/*
2 * factfits.h
3 *
4 * Created on: May 26, 2013
5 * Author: lyard
6 */
7
8#ifndef MARS_FACTFITS
9#define MARS_FACTFITS
10
11#include "zfits.h"
12
13class factfits : public zfits
14{
15public:
16 // Default constructor
17 factfits(const std::string& fname, const std::string& tableName="", bool force=false) :
18 zfits(fname, tableName, force),
19 fOffsetCalibration(0),
20 fOffsetStartCellData(0),
21 fOffsetData(0),
22 fNumRoi(0)
23 {
24 if (init())
25 readDrsCalib(fname);
26 }
27
28 // Alternative constructor
29 factfits(const std::string& fname, const std::string& fout, const std::string& tableName, bool force=false) :
30 zfits(fname, fout, tableName, force),
31 fOffsetCalibration(0),
32 fOffsetStartCellData(0),
33 fOffsetData(0),
34 fNumRoi(0)
35 {
36 if (init())
37 readDrsCalib(fname);
38 }
39
40private:
41
42 void StageRow(size_t row, char* dest)
43 {
44 zfits::StageRow(row, dest);
45
46 // This file does not contain fact data or no calibration to be applied
47 if (fOffsetCalibration.empty())
48 return;
49
50 //re-get the pointer to the data to access the offsets
51 const uint8_t offset = (row*fTable.bytes_per_row)%4;
52
53 int16_t *startCell = reinterpret_cast<int16_t*>(fBufferRow.data() + offset + fOffsetStartCellData);
54 int16_t *data = reinterpret_cast<int16_t*>(fBufferRow.data() + offset + fOffsetData);
55
56 /*
57 for (uint32_t i=0; i<1440*1024; i+=1024, startCell++)
58 {
59 if (*startCell < 0)
60 {
61 data += fNumRoi;
62 continue;
63 }
64 for (uint32_t j=0; j<fNumRoi; j++, data++)
65 *data += fOffsetCalibration[i + (*startCell+j)%1024];
66 }
67 */
68
69 // This version is faster because the compilers optimization
70 // is not biased by the evaluation of %1024
71 for (int ch=0; ch<1440; ch++)
72 {
73 if (startCell[ch]<0)
74 {
75 data += fNumRoi;
76 continue;
77 }
78
79 const int16_t modStart = startCell[ch] % 1024;
80 const int16_t *off = fOffsetCalibration.data() + ch*1024;
81
82 const int16_t *cal = off+modStart;
83 const int16_t *end_stride = data+fNumRoi;
84
85 if (modStart+fNumRoi>1024)
86 {
87 while (cal<off+1024)
88 *data++ += *cal++;
89
90 cal = off;
91 }
92 while (data<end_stride)
93 *data++ += *cal++;
94 }
95
96 }
97
98 bool init()
99 {
100 if (!HasKey("NPIX") || !HasKey("NROI"))
101 return false;
102
103 if (Get<uint16_t>("NPIX")!=1440)
104 return false;
105
106 fNumRoi = Get<uint16_t>("NROI");
107 if (fNumRoi>1024)
108 return false;
109
110 // check column details for Data
111 const Table::Columns::const_iterator it = fTable.cols.find("Data");
112 if (it==fTable.cols.end() || it->second.num!=1440*fNumRoi || it->second.type!='I')
113 return false;
114
115 // check column details for StartCellData
116 const Table::Columns::const_iterator is = fTable.cols.find("StartCellData");
117 if (is==fTable.cols.end() || is->second.num!=1440 || is->second.type!='I')
118 return false;
119
120 fOffsetStartCellData = is->second.offset;
121 fOffsetData = it->second.offset;
122
123 return true;
124 }
125
126 // Read the Drs calibration data
127 void readDrsCalib(const std::string& fileName)
128 {
129 //should not be mandatory, but improves the perfs a lot when reading not compressed, gzipped files
130 if (!IsCompressedFITS())
131 return;
132
133 zfits calib(fileName, "ZDrsCellOffsets");
134
135 if (calib.bad())
136 {
137 clear(rdstate()|std::ios::badbit);
138 return;
139 }
140
141 if (calib.eof())
142 return;
143
144 // Check correct size and format of table
145 if (calib.GetNumRows() != 1)
146 {
147 clear(rdstate()|std::ios::badbit);
148#ifdef __EXCEPTIONS
149 throw std::runtime_error("Table 'ZDrsCellOffsets' found, but not with one row as expected");
150#else
151 gLog << ___err___ << "ERROR - Table 'ZDrsCellOffsets' found, but not with one row as expected" << std::endl;
152 return;
153#endif
154 }
155 if (calib.GetStr("TTYPE1") != "OffsetCalibration")
156 {
157 clear(rdstate()|std::ios::badbit);
158#ifdef __EXCEPTIONS
159 throw std::runtime_error("Table 'ZDrsCellOffsets' found, but first column is not the one expected");
160#else
161 gLog << ___err___ << "ERROR - Table 'ZDrsCellOffsets' found, but first column is not the one expected" << std::endl;
162 return;
163#endif
164 }
165 bool isColumnPresent = false;
166 if (calib.HasKey("TFORM1") && calib.GetStr("TFORM1") == "1474560I") isColumnPresent = true;
167 if (calib.HasKey("ZFORM1") && calib.GetStr("ZFORM1") == "1474560I") isColumnPresent = true;
168 if (!isColumnPresent) // 1024*1440
169 {
170 clear(rdstate()|std::ios::badbit);
171#ifdef __EXCEPTIONS
172 throw std::runtime_error("Table 'ZDrsCellOffsets' has wrong column format (TFROM1)");
173#else
174 gLog << ___err___ << "ERROR - Table 'ZDrsCellOffsets' has wrong column format (TFORM1)" << std::endl;
175 return;
176#endif
177 }
178
179 fOffsetCalibration.resize(1024*1440);
180
181 calib.SetPtrAddress("OffsetCalibration", fOffsetCalibration.data());
182 if (calib.GetNextRow())
183 return;
184
185 clear(rdstate()|std::ios::badbit);
186
187#ifdef __EXCEPTIONS
188 throw std::runtime_error("Reading column 'OffsetCalibration' failed.");
189#else
190 gLog << ___err___ << "ERROR - Reading column 'OffsetCalibration' failed." << std::endl;
191#endif
192
193 }
194
195 std::vector<int16_t> fOffsetCalibration; ///< integer values of the drs calibration used for compression
196
197 size_t fOffsetStartCellData;
198 size_t fOffsetData;
199
200 uint16_t fNumRoi;
201
202//#warning Time marker channels currently unhandled
203
204}; //class factfits
205
206#endif
Note: See TracBrowser for help on using the repository browser.