| [350] | 1 | // toiiter.cc | 
|---|
|  | 2 | // Eric Aubourg         CEA/DAPNIA/SPP   juillet 1999 | 
|---|
|  | 3 |  | 
|---|
| [534] | 4 | #include "ark.h" | 
|---|
| [350] | 5 |  | 
|---|
| [310] | 6 | #include "toiiter.h" | 
|---|
| [534] | 7 | #include "toimanager.h" | 
|---|
|  | 8 | #include "toiproducer.h" | 
|---|
| [394] | 9 | #include "archparam.h" | 
|---|
| [534] | 10 | #include "asigps.h" | 
|---|
|  | 11 | #include "toiauxgpsproducer.h" | 
|---|
| [342] | 12 | #include <iostream.h> | 
|---|
| [534] | 13 | #include <fstream.h> | 
|---|
| [310] | 14 |  | 
|---|
| [534] | 15 | #define CHK_INITED if (initDone) \ | 
|---|
|  | 16 | throw ArchExc("Trying to modify TOIIter after init done."); | 
|---|
| [310] | 17 |  | 
|---|
|  | 18 | TOIIter::TOIIter() { | 
|---|
| [534] | 19 | mjdStart = -999999999; | 
|---|
|  | 20 | mjdEnd   =  999999999; | 
|---|
|  | 21 | utcStart = -999999999; | 
|---|
|  | 22 | utcEnd   =  999999999; | 
|---|
|  | 23 | sStart   = -999999999; | 
|---|
|  | 24 | sEnd     =  999999999; | 
|---|
| [342] | 25 |  | 
|---|
| [534] | 26 | underSample = 1; | 
|---|
|  | 27 | curSample = -1; | 
|---|
|  | 28 |  | 
|---|
|  | 29 | initDone = false; | 
|---|
|  | 30 | incDone  = false; | 
|---|
|  | 31 | } | 
|---|
| [342] | 32 |  | 
|---|
| [534] | 33 | #ifdef __MWERKS__ | 
|---|
|  | 34 | #pragma mark - | 
|---|
|  | 35 | #endif | 
|---|
|  | 36 |  | 
|---|
|  | 37 | void TOIIter::addDirectory(string dir) { | 
|---|
|  | 38 | CHK_INITED | 
|---|
|  | 39 | fset.addDirectory(dir); | 
|---|
| [310] | 40 | } | 
|---|
|  | 41 |  | 
|---|
| [534] | 42 | void TOIIter::addFile(string fn) { | 
|---|
|  | 43 | CHK_INITED | 
|---|
|  | 44 | fset.addFile(fn); | 
|---|
|  | 45 | } | 
|---|
| [310] | 46 |  | 
|---|
| [534] | 47 | void TOIIter::setMJDInterval(double tStart, double tEnd) { | 
|---|
|  | 48 | CHK_INITED | 
|---|
|  | 49 | if (tStart>0) mjdStart = tStart; | 
|---|
|  | 50 | if (tEnd>0)   mjdEnd = tEnd; | 
|---|
| [310] | 51 | } | 
|---|
|  | 52 |  | 
|---|
| [534] | 53 | void TOIIter::setUTCInterval(double tStart, double tEnd) { | 
|---|
|  | 54 | CHK_INITED | 
|---|
|  | 55 | if (tStart>0) utcStart = tStart; | 
|---|
|  | 56 | if (tEnd>0)   utcEnd = tEnd; | 
|---|
| [310] | 57 | } | 
|---|
|  | 58 |  | 
|---|
| [534] | 59 | void TOIIter::setSNInterval(long tStart, long tEnd) { | 
|---|
|  | 60 | CHK_INITED | 
|---|
|  | 61 | if (tStart>0) sStart = tStart; | 
|---|
|  | 62 | if (tEnd>0)   sEnd = tEnd; | 
|---|
|  | 63 | } | 
|---|
|  | 64 |  | 
|---|
|  | 65 | void TOIIter::setUnderSample(int n) { | 
|---|
|  | 66 | CHK_INITED | 
|---|
|  | 67 | if (n<=1) n=1; | 
|---|
|  | 68 | underSample = n; | 
|---|
|  | 69 | } | 
|---|
|  | 70 |  | 
|---|
|  | 71 | int TOIIter::getUnderSample() { | 
|---|
|  | 72 | return underSample; | 
|---|
|  | 73 | } | 
|---|
|  | 74 |  | 
|---|
|  | 75 | void TOIIter::addTOI(TOI& toi, bool trg) { | 
|---|
|  | 76 | CHK_INITED | 
|---|
|  | 77 | TOIProducer* prod = TOIManager::findTOIProducer(toi); | 
|---|
|  | 78 | if (!prod) throw ArchExc("Cannot produce " + toi.fullName()); | 
|---|
|  | 79 | prod->addTOI(toi, this); | 
|---|
|  | 80 | request.push_back(TOIInfo(toi,prod,trg?1:0)); | 
|---|
|  | 81 | } | 
|---|
|  | 82 |  | 
|---|
| [342] | 83 | #ifdef __MWERKS__ | 
|---|
| [534] | 84 | #pragma mark - | 
|---|
| [342] | 85 | #endif | 
|---|
|  | 86 |  | 
|---|
| [310] | 87 |  | 
|---|
| [534] | 88 | void TOIIter::registerReqHandler(RequestHandler* h) { | 
|---|
|  | 89 | CHK_INITED | 
|---|
|  | 90 | handlers.push_back(h); | 
|---|
|  | 91 | } | 
|---|
| [315] | 92 |  | 
|---|
|  | 93 |  | 
|---|
| [534] | 94 | void TOIIter::readReq(istream& str) { | 
|---|
|  | 95 | CHK_INITED | 
|---|
|  | 96 | if (!incDone) defaultInclude(); | 
|---|
|  | 97 | string line; | 
|---|
|  | 98 | while (str) { | 
|---|
|  | 99 | getline(str,line); | 
|---|
|  | 100 | if (!str) break; | 
|---|
|  | 101 | if (line.substr(0,4)=="#END" && (line.length()==4 || line[5] == ' ')) break; | 
|---|
|  | 102 | if (line[0] != '@' && line[0] != '#') continue; | 
|---|
|  | 103 | if (!processRequest(line)) { | 
|---|
|  | 104 | throw ArchExc("Unrecognized directive " + line); | 
|---|
|  | 105 | } | 
|---|
|  | 106 | } | 
|---|
| [310] | 107 | } | 
|---|
|  | 108 |  | 
|---|
| [534] | 109 |  | 
|---|
|  | 110 | bool TOIIter::processRequest(string line) { | 
|---|
|  | 111 | if (line[0] == '#') { | 
|---|
|  | 112 | int x = line.find(' '); | 
|---|
|  | 113 | string keyw = line.substr(0, x); | 
|---|
|  | 114 | string args = (x>0) ? line.substr(x) : string(""); | 
|---|
|  | 115 | bool handled = processOption(keyw,args); | 
|---|
|  | 116 | for (list<RequestHandler*>::iterator i = handlers.begin(); | 
|---|
|  | 117 | i != handlers.end(); i++) { | 
|---|
|  | 118 | handled |= (*i)->processOption(keyw,args); | 
|---|
| [350] | 119 | } | 
|---|
| [534] | 120 | return handled; | 
|---|
| [350] | 121 | } | 
|---|
| [534] | 122 |  | 
|---|
|  | 123 | if (line[0] == '@') { | 
|---|
|  | 124 | TOI toi(line.substr(1)); | 
|---|
|  | 125 | // if (kind  == sampleNum || kind == mjd || kind == mutc) notrig = true; | 
|---|
|  | 126 | bool handled = processTOIReq(toi,line); | 
|---|
|  | 127 | for (list<RequestHandler*>::iterator i = handlers.begin(); | 
|---|
|  | 128 | i != handlers.end(); i++) { | 
|---|
|  | 129 | handled |= (*i)->processTOIReq(toi,line); | 
|---|
| [350] | 130 | } | 
|---|
| [534] | 131 | return handled; | 
|---|
| [350] | 132 | } | 
|---|
| [534] | 133 | return false; | 
|---|
| [350] | 134 | } | 
|---|
|  | 135 |  | 
|---|
| [534] | 136 |  | 
|---|
|  | 137 | bool TOIIter::processTOIReq(TOI& toi,string) | 
|---|
|  | 138 | { | 
|---|
|  | 139 | TOI toi2 = toi; | 
|---|
|  | 140 | bool trg=true; | 
|---|
|  | 141 | if (toi.options.find("notrig") != toi.options.end()) { | 
|---|
|  | 142 | toi2.options.erase("notrig"); | 
|---|
|  | 143 | trg=false; | 
|---|
|  | 144 | } | 
|---|
|  | 145 | addTOI(toi2, trg); | 
|---|
|  | 146 | toi.unit = toi2.unit; | 
|---|
|  | 147 | return true; | 
|---|
|  | 148 | } | 
|---|
|  | 149 |  | 
|---|
|  | 150 |  | 
|---|
|  | 151 | bool TOIIter::processOption(string key, string arg) | 
|---|
|  | 152 | { | 
|---|
|  | 153 | if (arg.length()>0 && arg[0] == ' ') { | 
|---|
|  | 154 | arg = arg.substr(arg.find_first_not_of(' ')); | 
|---|
|  | 155 | } | 
|---|
|  | 156 | if (key == "#MJDRANGE") { | 
|---|
|  | 157 | double tmin, tmax; | 
|---|
|  | 158 | sscanf(arg.c_str(), "%lg %lg", &tmin, &tmax); | 
|---|
|  | 159 | setMJDInterval(tmin, tmax); | 
|---|
|  | 160 | } else if (key == "#UTCRANGE") { | 
|---|
|  | 161 | double tmin, tmax; | 
|---|
|  | 162 | sscanf(arg.c_str(), "%lg %lg", &tmin, &tmax); | 
|---|
|  | 163 | setUTCInterval(tmin, tmax); | 
|---|
|  | 164 | } else if (key == "#SNRANGE") { | 
|---|
|  | 165 | long tmin, tmax; | 
|---|
|  | 166 | sscanf(arg.c_str(), "%ld %ld", &tmin, &tmax); | 
|---|
|  | 167 | setSNInterval(tmin, tmax); | 
|---|
|  | 168 | } else if (key == "#PATH") { | 
|---|
|  | 169 | addDirectory(arg); | 
|---|
|  | 170 | } else if (key == "#FILE") { | 
|---|
|  | 171 | addFile(arg); | 
|---|
|  | 172 | } else if (key == "#UNDERSAMPLE") { | 
|---|
|  | 173 | setUnderSample(atoi(arg.c_str())); | 
|---|
|  | 174 | } else if (key == "#MJD0") { | 
|---|
|  | 175 | double t0; | 
|---|
|  | 176 | sscanf(arg.c_str(), "%lg", &t0); | 
|---|
|  | 177 | archParam.acq.tBlock0 = t0; | 
|---|
|  | 178 | } else if (key == "#UTCORIGIN") { | 
|---|
|  | 179 | double t0; | 
|---|
|  | 180 | sscanf(arg.c_str(), "%lg", &t0); | 
|---|
|  | 181 | archParam.acq.utcOrigin = t0; | 
|---|
|  | 182 | } else if (key == "#PERECH") { | 
|---|
|  | 183 | double t0; | 
|---|
|  | 184 | sscanf(arg.c_str(), "%lg", &t0); | 
|---|
|  | 185 | archParam.acq.perEch = t0; | 
|---|
|  | 186 | } else if (key == "#ASIGPS") { | 
|---|
|  | 187 | ASIGPS* gps = new ASIGPS(arg); | 
|---|
|  | 188 | TOIManager::registerProducer(new TOIAuxGPSProducer(gps)); | 
|---|
|  | 189 | //    gps->FitsDump("GPSDump.fits"); | 
|---|
|  | 190 | } else if (key == "#INCLUDE") { | 
|---|
|  | 191 | ifstream f(arg.c_str()); | 
|---|
|  | 192 | readReq(f); | 
|---|
|  | 193 | } else { | 
|---|
| [310] | 194 | return false; | 
|---|
|  | 195 | } | 
|---|
| [426] | 196 | return true; | 
|---|
|  | 197 | } | 
|---|
| [350] | 198 |  | 
|---|
| [534] | 199 |  | 
|---|
|  | 200 | void TOIIter::defaultInclude() { | 
|---|
|  | 201 | incDone = true; | 
|---|
| [625] | 202 | processRequest("#REQVERSION V_231199"); | 
|---|
| [534] | 203 | processRequest("#MJD0 1376.8358818"); | 
|---|
|  | 204 | processRequest("#PERECH 0.005836818076"); | 
|---|
|  | 205 | processRequest("#UTCORIGIN 1376.5"); | 
|---|
|  | 206 | processRequest("#ASIGPS ASI_GPS_archeops1999.ascii"); | 
|---|
| [612] | 207 | processRequest("#COMMENT Archtoi V3 -- novembre 1999 -- Eric Aubourg CEA/DAPNIA"); | 
|---|
| [625] | 208 | processRequest("#COMMENT **** WARNING ****"); | 
|---|
|  | 209 | processRequest("#COMMENT SST attitude reconstruction should be ok where provided"); | 
|---|
|  | 210 | processRequest("#COMMENT     Gaps remain to be dealt with"); | 
|---|
|  | 211 | processRequest("#COMMENT Focal plane geometry is theoric"); | 
|---|
|  | 212 | processRequest("#COMMENT Bolo 1 aligned with SST using Jupiter (ONE crossing)"); | 
|---|
|  | 213 | processRequest("#COMMENT => statistical error on pendulation at that instant"); | 
|---|
|  | 214 | processRequest("#COMMENT    might induce systematic error on bolo 1 attitude"); | 
|---|
|  | 215 | processRequest("#COMMENT gyros calibrated with galactic crossings only"); | 
|---|
|  | 216 | processRequest("#COMMENT    algorithm = integral of gyro = delta Az"); | 
|---|
|  | 217 | processRequest("#COMMENT    Warning : slope found on z gyro applied to x and y"); | 
|---|
|  | 218 | processRequest("#COMMENT    offsets found on x and y applied (average) to z"); | 
|---|
| [350] | 219 | } | 
|---|
|  | 220 |  | 
|---|
| [534] | 221 | #ifdef __MWERKS__ | 
|---|
|  | 222 | #pragma mark - | 
|---|
|  | 223 | #endif | 
|---|
| [310] | 224 |  | 
|---|
| [534] | 225 | void TOIIter::init() { | 
|---|
|  | 226 | if (initDone) return; | 
|---|
|  | 227 | initDone = true; | 
|---|
|  | 228 |  | 
|---|
|  | 229 | if (utcStart > 0) { | 
|---|
|  | 230 | double t = (utcStart/24.) + archParam.acq.utcOrigin; | 
|---|
|  | 231 | if (t > mjdStart) mjdStart=t; | 
|---|
| [310] | 232 | } | 
|---|
| [534] | 233 | if (utcEnd > 0) { | 
|---|
|  | 234 | double t = (utcEnd/24.) + archParam.acq.utcOrigin; | 
|---|
|  | 235 | if (t < mjdEnd) mjdEnd=t; | 
|---|
| [310] | 236 | } | 
|---|
|  | 237 |  | 
|---|
| [619] | 238 | // Let's add some time on each side, 90 seconds should be ok, at least | 
|---|
| [612] | 239 | // for Trapani | 
|---|
|  | 240 |  | 
|---|
| [619] | 241 | double delT = 90. / 86400; | 
|---|
|  | 242 | long   delSN = long(90. / archParam.acq.perEch); | 
|---|
| [400] | 243 |  | 
|---|
| [612] | 244 | fset.setMJDRange(mjdStart-delT, mjdEnd+delT); | 
|---|
|  | 245 | fset.setSNumRange(sStart-delSN, sEnd+delSN); | 
|---|
|  | 246 |  | 
|---|
| [534] | 247 | fset.init(); | 
|---|
|  | 248 | //curSample = fset.getSampleIndex(); | 
|---|
| [315] | 249 | } | 
|---|
| [342] | 250 |  | 
|---|
|  | 251 | bool TOIIter::isTrig(int column) { | 
|---|
| [534] | 252 | return (request[column].third & triggering) != 0; | 
|---|
| [342] | 253 | } | 
|---|
| [310] | 254 |  | 
|---|
| [534] | 255 | TOI TOIIter::getKind(int column) { | 
|---|
|  | 256 | return request[column].first; | 
|---|
| [315] | 257 | } | 
|---|
| [534] | 258 |  | 
|---|
|  | 259 | long TOIIter::getSampleNum() { | 
|---|
|  | 260 | return curSample; | 
|---|
| [315] | 261 | } | 
|---|
|  | 262 |  | 
|---|
| [534] | 263 | bool TOIIter::next() { | 
|---|
|  | 264 | if (!initDone) init(); | 
|---|
|  | 265 | for (int ii=0; ii<underSample; ii++) | 
|---|
|  | 266 | if (!next1()) return false; | 
|---|
|  | 267 |  | 
|---|
|  | 268 | return true; | 
|---|
| [315] | 269 | } | 
|---|
|  | 270 |  | 
|---|
| [534] | 271 | bool TOIIter::next1() { | 
|---|
|  | 272 | // On tente de produire curSample+1 pour toutes les toi | 
|---|
|  | 273 | // Eventuellement en avancant sur le fichier... | 
|---|
|  | 274 | // Puis on regarde si une TOI triggering a eu une nouvelle | 
|---|
|  | 275 | // valeur. | 
|---|
|  | 276 | // Si on a epuise les fichiers de donnees, on s'arrete des qu'aucune | 
|---|
|  | 277 | // TOI n'a de valeurs apres curSample... | 
|---|
| [612] | 278 | if (curSample <= 0) curSample = sStart-1; | 
|---|
|  | 279 | if (curSample <= 0) { | 
|---|
| [635] | 280 | long sn = (long)(archParam.acq.MJD2SN(mjdStart) - 1); | 
|---|
| [612] | 281 | if (sn > curSample) curSample = sn; | 
|---|
|  | 282 | } | 
|---|
|  | 283 |  | 
|---|
| [534] | 284 | if (curSample <= 0) curSample = fset.getSampleIndex()-1; | 
|---|
|  | 285 |  | 
|---|
|  | 286 | if (curSample >= sEnd || archParam.acq.SN2MJD(curSample) >= mjdEnd) return false; | 
|---|
|  | 287 |  | 
|---|
| [555] | 288 | static long lastClean = 0; | 
|---|
|  | 289 | if (curSample - lastClean > 100) { | 
|---|
|  | 290 | for (int i=0; i<request.size(); i++) | 
|---|
|  | 291 | request[i].second->wontNeedEarlier(request[i].first, this, curSample); | 
|---|
|  | 292 | lastClean = curSample; | 
|---|
|  | 293 | } | 
|---|
| [534] | 294 |  | 
|---|
|  | 295 | bool endFound = false; | 
|---|
|  | 296 | while(1) { | 
|---|
|  | 297 | curSample++; | 
|---|
|  | 298 | for (vector<TOIInfo>::iterator i = request.begin(); i != request.end(); i++) { | 
|---|
|  | 299 | while ((*i).second->canGetValueLater(curSample, (*i).first)) { | 
|---|
|  | 300 | if (! fset.next()) {endFound = true; break;} //return false; | 
|---|
|  | 301 | } | 
|---|
|  | 302 | } | 
|---|
| [614] | 303 | if (endFound && curSample >= fset.getSampleIndex()+71) return false; | 
|---|
| [534] | 304 | bool found=false; | 
|---|
| [612] | 305 | //bool valuesAhead = false; | 
|---|
| [534] | 306 | for (vector<TOIInfo>::iterator i = request.begin(); i != request.end(); i++) { | 
|---|
|  | 307 | if (((*i).third & triggering) == 0) continue; | 
|---|
|  | 308 | if ((*i).second->canGetValue(curSample, (*i).first)) {found=true;break;} | 
|---|
| [612] | 309 | //if ((*i).second->lastSampleNum((*i).first)>curSample) valuesAhead=true; | 
|---|
| [534] | 310 | } | 
|---|
|  | 311 | if (found) break; | 
|---|
|  | 312 | } | 
|---|
|  | 313 | return true; | 
|---|
| [315] | 314 | } | 
|---|
|  | 315 |  | 
|---|
| [534] | 316 | int TOIIter::getColTOI(TOI const& toi) { | 
|---|
|  | 317 | for (int i=0; i<request.size(); i++) | 
|---|
|  | 318 | if (request[i].first == toi) return i; | 
|---|
|  | 319 | throw ArchExc("getColTOI : no such TOI " + toi.name); | 
|---|
| [315] | 320 | } | 
|---|
|  | 321 |  | 
|---|
| [534] | 322 | bool TOIIter::canGetValue(int column) { | 
|---|
|  | 323 | TOIInfo& info = request[column]; | 
|---|
|  | 324 | return(info.second->canGetValue(curSample, info.first)); | 
|---|
| [315] | 325 | } | 
|---|
| [426] | 326 |  | 
|---|
| [534] | 327 | double TOIIter::getValue(int column) { | 
|---|
|  | 328 | TOIInfo& info = request[column]; | 
|---|
|  | 329 | return(info.second->getValue(curSample, info.first)); | 
|---|
| [315] | 330 | } | 
|---|
| [358] | 331 |  | 
|---|
| [534] | 332 | bool TOIIter::canGetValue(TOI const& toi) { | 
|---|
|  | 333 | return canGetValue(getColTOI(toi)); | 
|---|
| [358] | 334 | } | 
|---|
| [315] | 335 |  | 
|---|
| [534] | 336 | double TOIIter::getValue(TOI const& toi) { | 
|---|
|  | 337 | return getValue(getColTOI(toi)); | 
|---|
| [342] | 338 | } | 
|---|
|  | 339 |  | 
|---|