Line data Source code
1 : #include <alma/ASDMBinaries/SDMDataObjectParser.h>
2 : #include <iostream>
3 : #include <sstream>
4 : #include <string>
5 : #include <algorithm>
6 : #include <vector>
7 : #include <iterator>
8 :
9 : using namespace AtmPhaseCorrectionMod;
10 : using namespace AxisNameMod;
11 : using namespace BasebandNameMod;
12 : using namespace CorrelationModeMod;
13 : using namespace CorrelatorTypeMod;
14 : using namespace NetSidebandMod;
15 : using namespace PrimitiveDataTypeMod;
16 : using namespace ProcessorTypeMod;
17 : using namespace SpectralResolutionTypeMod;
18 : using namespace StokesParameterMod;
19 :
20 : using namespace std;
21 :
22 : namespace asdmbinaries {
23 :
24 : // Names of XML elements/attributes in an sdmDataHeader.
25 :
26 : #ifndef WITHOUT_BOOST
27 : const boost::regex HeaderParser::PROJECTPATH3("([0-9]+)/([0-9]+)/([0-9]+)/");
28 : #else
29 : const std::regex HeaderParser::PROJECTPATH3("([0-9]+)/([0-9]+)/([0-9]+)/");
30 : #endif
31 : const string HeaderParser::SDMDATAHEADER = "sdmDataHeader";
32 : const string HeaderParser::SCHEMAVERSION = "schemaVersion";
33 : const string HeaderParser::BYTEORDER = "byteOrder";
34 : const string HeaderParser::PROJECTPATH = "projectPath";
35 : const string HeaderParser::STARTTIME = "startTime";
36 : const string HeaderParser::DATAOID = "dataOID";
37 : const string HeaderParser::XLINKHREF = "href";
38 : const string HeaderParser::XLINKTITLE = "title";
39 : const string HeaderParser::DIMENSIONALITY = "dimensionality";
40 : const string HeaderParser::NUMTIME = "numTime";
41 : const string HeaderParser::EXECBLOCK = "execBlock";
42 : const string HeaderParser::EXECBLOCKNUM = "execBlockNum";
43 : const string HeaderParser::SCANNUM = "scanNum";
44 : const string HeaderParser::SUBSCANNUM = "subscanNum";
45 : const string HeaderParser::NUMANTENNA = "numAntenna";
46 : const string HeaderParser::CORRELATIONMODE = "correlationMode";
47 : const string HeaderParser::SPECTRALRESOLUTION = "spectralResolution";
48 : const string HeaderParser::PROCESSORTYPE = "processorType";
49 : const string HeaderParser::DATASTRUCT = "dataStruct";
50 : const string HeaderParser::APC = "apc";
51 : const string HeaderParser::REF = "ref";
52 : const string HeaderParser::BASEBAND = "baseband";
53 : const string HeaderParser::NAME = "name";
54 : const string HeaderParser::SPECTRALWINDOW = "spectralWindow";
55 : const string HeaderParser::SW = "sw";
56 : const string HeaderParser::SWBB = "swbb";
57 : const string HeaderParser::CROSSPOLPRODUCTS = "crossPolProducts";
58 : const string HeaderParser::SDPOLPRODUCTS = "sdPolProducts";
59 : const string HeaderParser::SCALEFACTOR = "scaleFactor";
60 : const string HeaderParser::NUMSPECTRALPOINT = "numSpectralPoint";
61 : const string HeaderParser::NUMBIN = "numBin";
62 : const string HeaderParser::SIDEBAND = "sideband";
63 : const string HeaderParser::IMAGE = "image";
64 : const string HeaderParser::FLAGS = "flags";
65 : const string HeaderParser::ACTUALTIMES = "actualTimes";
66 : const string HeaderParser::ACTUALDURATIONS = "actualDurations";
67 : const string HeaderParser::ZEROLAGS = "zeroLags";
68 : const string HeaderParser::CORRELATORTYPE = "correlatorType";
69 : const string HeaderParser::CROSSDATA = "crossData";
70 : const string HeaderParser::AUTODATA = "autoData";
71 : const string HeaderParser::NORMALIZED = "normalized";
72 : const string HeaderParser::SIZE = "size";
73 : const string HeaderParser::AXES = "axes";
74 : const string HeaderParser::TYPE = "type";
75 :
76 :
77 : // Names of XML elements/attributes in an sdmSubsetDataHeader with dimensionality==1 (Correlator)
78 :
79 : #ifndef WITHOUT_BOOST
80 : const boost::regex SDMDataObjectParser::PROJECTPATH3("([0-9]+)/([0-9]+)/([0-9]+)/");
81 : const boost::regex SDMDataObjectParser::PROJECTPATH4("([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/");
82 : const boost::regex SDMDataObjectParser::PROJECTPATH5("([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/");
83 : #else
84 : const std::regex SDMDataObjectParser::PROJECTPATH3("([0-9]+)/([0-9]+)/([0-9]+)/");
85 : const std::regex SDMDataObjectParser::PROJECTPATH4("([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/");
86 : const std::regex SDMDataObjectParser::PROJECTPATH5("([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/");
87 : #endif
88 :
89 :
90 : const string CorrSubsetHeaderParser::SDMDATASUBSETHEADER = "sdmDataSubsetHeader";
91 : const string CorrSubsetHeaderParser::PROJECTPATH = "projectPath";
92 : const string CorrSubsetHeaderParser::SCHEDULEPERIODTIME = "schedulePeriodTime";
93 : const string CorrSubsetHeaderParser::TIME = "time";
94 : const string CorrSubsetHeaderParser::INTERVAL = "interval";
95 : const string CorrSubsetHeaderParser::DATASTRUCT = "dataStruct";
96 : const string CorrSubsetHeaderParser::REF = "ref";
97 : const string CorrSubsetHeaderParser::ABORTOBSERVATION = "abortObservation";
98 : const string CorrSubsetHeaderParser::ABORTTIME = "stopTime";
99 : const string CorrSubsetHeaderParser::ABORTREASON = "abortReason";
100 : const string CorrSubsetHeaderParser::XLINKHREF = "href";
101 : const string CorrSubsetHeaderParser::DATAREF = "dataRef";
102 : const string CorrSubsetHeaderParser::FLAGSREF = "flags";
103 : const string CorrSubsetHeaderParser::ACTUALTIMESREF = "actualTimes";
104 : const string CorrSubsetHeaderParser::ACTUALDURATIONSREF = "actualDurations";
105 : const string CorrSubsetHeaderParser::ZEROLAGSREF = "zeroLags";
106 : const string CorrSubsetHeaderParser::CROSSDATAREF = "crossData";
107 : const string CorrSubsetHeaderParser::AUTODATAREF = "autoData";
108 : const string CorrSubsetHeaderParser::TYPE = "type";
109 :
110 : // Names of XML elements/attributes in an sdmSubsetDataHeader with dimensionality==0 (TP)
111 : #ifndef WITHOUT_BOOST
112 : const boost::regex TPSubsetHeaderParser::PROJECTPATH3("([0-9]+)/([0-9]+)/([0-9]+)/");
113 : #else
114 : const std::regex TPSubsetHeaderParser::PROJECTPATH3("([0-9]+)/([0-9]+)/([0-9]+)/");
115 : #endif
116 : const string TPSubsetHeaderParser::SDMDATASUBSETHEADER = "sdmDataSubsetHeader";
117 : const string TPSubsetHeaderParser::PROJECTPATH = "projectPath";
118 : const string TPSubsetHeaderParser::SCHEDULEPERIODTIME = "schedulePeriodTime";
119 : const string TPSubsetHeaderParser::TIME = "time";
120 : const string TPSubsetHeaderParser::INTERVAL = "interval";
121 : const string TPSubsetHeaderParser::DATASTRUCT = "dataStruct";
122 : const string TPSubsetHeaderParser::REF = "ref";
123 : const string TPSubsetHeaderParser::DATAREF = "dataRef";
124 : const string TPSubsetHeaderParser::XLINKHREF = "href";
125 : const string TPSubsetHeaderParser::FLAGSREF = "flags";
126 : const string TPSubsetHeaderParser::ACTUALTIMESREF = "actualTimes";
127 : const string TPSubsetHeaderParser::ACTUALDURATIONSREF = "actualDurations";
128 : const string TPSubsetHeaderParser::AUTODATAREF = "autoData";
129 :
130 : // HeaderParser methods.
131 0 : HeaderParser::HeaderParser(){
132 0 : doc = NULL;
133 0 : }
134 :
135 0 : HeaderParser::~HeaderParser() {
136 0 : if (doc != NULL) xmlFreeDoc(doc);
137 0 : }
138 :
139 0 : void HeaderParser::parseFile(const string& filename, SDMDataObject& sdmDataObject){
140 0 : if (doc != NULL) xmlFreeDoc(doc);
141 0 : doc = xmlReadFile(filename.c_str(), NULL, XML_PARSE_NOBLANKS);
142 0 : if (doc == NULL) {
143 0 : throw SDMDataObjectParserException("The file '"+filename+"' could not be transformed into a DOM structure");
144 : }
145 :
146 0 : xmlNode* root_element = xmlDocGetRootElement(doc);
147 0 : parseSDMDataHeader(root_element, sdmDataObject);
148 0 : }
149 :
150 0 : void HeaderParser::parseMemory(const string& buffer, SDMDataObject& sdmDataObject) {
151 0 : if (doc != NULL) xmlFreeDoc(doc);
152 0 : doc = xmlReadMemory(buffer.data(), buffer.size(), "SDMDataHeader.xml", NULL, XML_PARSE_NOBLANKS );
153 0 : if (doc == NULL) {
154 0 : throw SDMDataObjectParserException("The buffer containing the XML document could not be transformed into a DOM structure");
155 : }
156 :
157 0 : xmlNode* root_element = xmlDocGetRootElement(doc);
158 0 : parseSDMDataHeader(root_element, sdmDataObject);
159 0 : }
160 :
161 0 : void HeaderParser::reset() {
162 0 : if (doc)
163 0 : xmlFreeDoc(doc);
164 :
165 0 : doc = NULL;
166 0 : }
167 :
168 0 : void HeaderParser::parseSDMDataHeader(xmlNode* a_node, SDMDataObject& sdmDataObject){
169 : //cout << "Entering parseSDMDataHeader" << endl;
170 : // Look up for the <sdmDataHeader ... element.
171 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::SDMDATAHEADER);
172 :
173 : // And parse some of its attributes.
174 0 : sdmDataObject.schemaVersion_ = SDMDataObjectParser::parseIntAttr(a_node, HeaderParser::SCHEMAVERSION);
175 0 : sdmDataObject.byteOrder_ = SDMDataObjectParser::parseByteOrderAttr(a_node, HeaderParser::BYTEORDER);
176 :
177 :
178 : // Look up for its projectPath attribute
179 : // and determine execBlockNum, scanNum and subscanNum from its projectPath attribute.
180 0 : vector<unsigned int> v = SDMDataObjectParser::parseProjectPath(a_node, 3);
181 0 : sdmDataObject.execBlockNum_ = v.at(0);
182 0 : sdmDataObject.scanNum_ = v.at(1);
183 0 : sdmDataObject.subscanNum_ = v.at(2);
184 :
185 : // Traverse the children.
186 0 : xmlNode* child = a_node->children;
187 :
188 : // Look up for the <startTime... child
189 0 : sdmDataObject.startTime(parseStartTime(child));
190 :
191 : // Look up for the <dataOID... child
192 0 : child = child->next;
193 0 : sdmDataObject.dataOID(parseDataOID(child));
194 :
195 : // ...and its title attribute
196 0 : sdmDataObject.title(SDMDataObjectParser::parseStringAttr(child, HeaderParser::XLINKTITLE));
197 :
198 : // Look up for the <dimensionality...
199 0 : child = child->next;
200 0 : unsigned int dimensionality = parseDimensionality(child);
201 0 : sdmDataObject.dimensionality(dimensionality);
202 :
203 0 : if ( dimensionality == 0 ) {
204 : // Look up for numTime... only if dimensionality == 0
205 0 : sdmDataObject.numTime((unsigned int) parseNumTime(child) );
206 : }
207 :
208 : // Look up for the <execBlock... child
209 0 : child = child->next;
210 0 : parseExecBlock(child, sdmDataObject);
211 :
212 : // Look up for the <numAntenna... child
213 0 : child = child->next;
214 0 : int numAntenna = parseNumAntenna(child); //cout << child->name << "=" << numAntenna << endl;
215 0 : sdmDataObject.numAntenna((unsigned int) numAntenna);
216 :
217 : // Look up for the <correlationMode> ... child
218 0 : child = child->next;
219 0 : parseCorrelationMode(child, sdmDataObject);
220 :
221 : // Look up for the <spectralResolution> ... child
222 0 : child = child->next;
223 0 : parseSpectralResolution(child, sdmDataObject);
224 :
225 : // Look up for child <processorType> ... child
226 0 : child = child->next;
227 0 : parseProcessorType(child, sdmDataObject);
228 :
229 : // Look up for the <dataStruct> ... child
230 0 : child = child->next;
231 0 : parseDataStruct(child, sdmDataObject);
232 :
233 : //cout << "Exiting parseSDMDataHeader" << endl;
234 0 : }
235 :
236 : // void HeaderParser::parseProjectPath(xmlNode* a_node, SDMDataObject& sdmDataObject) {
237 : // string projectPath = SDMDataObjectParser::parseStringAttr(a_node, HeaderParser::PROJECTPATH);
238 :
239 : // boost::cmatch what;
240 :
241 : // if (boost::regex_match(projectPath.c_str(), what,PROJECTPATH3) && what[0].matched) {
242 : // sdmDataObject.execBlockNum(::atoi(what[1].first));
243 : // sdmDataObject.scanNum(::atoi(what[2].first));
244 : // sdmDataObject.subscanNum(::atoi(what[3].first));
245 : // }
246 : // else
247 : // throw SDMDataObjectParserException("HeaderParser::parseProjectPath: Invalid string for projectPath '" + projectPath + "'");
248 : // }
249 :
250 0 : long long HeaderParser::parseStartTime(xmlNode* a_node){
251 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::STARTTIME);
252 0 : return SDMDataObjectParser::parseLongLong(a_node->children);
253 : }
254 :
255 0 : string HeaderParser::parseDataOID(xmlNode* a_node) {
256 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::DATAOID);
257 :
258 : // Look for attribute
259 0 : string dataOID = SDMDataObjectParser::parseStringAttr(a_node, HeaderParser::XLINKHREF);
260 0 : return dataOID;
261 : }
262 :
263 0 : int HeaderParser::parseDimensionality(xmlNode* a_node) {
264 : //cout << "Entering parseDimensionality with " << a_node->name << endl;
265 0 : if (SDMDataObjectParser::testElement(a_node, HeaderParser::DIMENSIONALITY)) {
266 0 : return SDMDataObjectParser::parseInt(a_node->children);
267 : }
268 : else
269 0 : return 0;
270 : }
271 :
272 0 : int HeaderParser::parseNumTime(xmlNode* a_node) {
273 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::NUMTIME);
274 0 : return SDMDataObjectParser::parseInt(a_node->children);
275 : }
276 :
277 0 : void HeaderParser::parseExecBlock(xmlNode* a_node, SDMDataObject& sdmDataObject){
278 : //cout << "Entering parseExecBlock with " << a_node << endl;
279 :
280 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::EXECBLOCK);
281 :
282 : // Look up for the execBlockUID attribute.
283 0 : sdmDataObject.execBlockUID(SDMDataObjectParser::parseStringAttr(a_node, HeaderParser::XLINKHREF));
284 0 : }
285 :
286 0 : int HeaderParser::parseExecBlockNum(xmlNode* a_node){
287 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::EXECBLOCKNUM);
288 0 : return SDMDataObjectParser::parseInt(a_node->children);
289 : }
290 :
291 0 : int HeaderParser::parseScanNum(xmlNode* a_node){
292 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::SCANNUM);
293 0 : return SDMDataObjectParser::parseInt(a_node->children);
294 : }
295 :
296 0 : int HeaderParser::parseSubscanNum(xmlNode* a_node){
297 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::SUBSCANNUM);
298 0 : return SDMDataObjectParser::parseInt(a_node->children);
299 : }
300 :
301 0 : int HeaderParser::parseNumAntenna(xmlNode* a_node){
302 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::NUMANTENNA);
303 0 : return SDMDataObjectParser::parseInt(a_node->children);
304 : }
305 :
306 0 : void HeaderParser::parseCorrelationMode(xmlNode* a_node, SDMDataObject& sdmDataObject) {
307 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::CORRELATIONMODE);
308 0 : sdmDataObject.correlationMode_ = SDMDataObjectParser::parseLiteral<CorrelationMode, CCorrelationMode>(a_node->children);
309 0 : }
310 :
311 0 : void HeaderParser::parseSpectralResolution(xmlNode* a_node, SDMDataObject& sdmDataObject) {
312 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::SPECTRALRESOLUTION);
313 0 : sdmDataObject.spectralResolutionType_ = SDMDataObjectParser::parseLiteral<SpectralResolutionType, CSpectralResolutionType>(a_node->children);
314 0 : }
315 :
316 0 : void HeaderParser::parseProcessorType(xmlNode* a_node, SDMDataObject& sdmDataObject) {
317 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::PROCESSORTYPE);
318 0 : sdmDataObject.processorType_ = SDMDataObjectParser::parseLiteral<ProcessorType, CProcessorType>(a_node->children);
319 0 : }
320 :
321 0 : void HeaderParser::parseDataStruct(xmlNode* a_node, SDMDataObject& sdmDataObject){
322 : //cout << "Entering parseDataStruct with " << a_node->name << endl;
323 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::DATASTRUCT);
324 :
325 0 : SDMDataObject::DataStruct dataStruct;
326 :
327 0 : switch (sdmDataObject.correlationMode()) {
328 0 : case AUTO_ONLY:
329 0 : break;
330 :
331 0 : case CROSS_ONLY:
332 : case CROSS_AND_AUTO:
333 0 : dataStruct.apc_ = SDMDataObjectParser::parseStringsAttr<AtmPhaseCorrection, CAtmPhaseCorrection>(a_node, HeaderParser::APC);
334 0 : break;
335 : }
336 :
337 : // Traverse the children
338 :
339 : // BaseBands...
340 0 : xmlNode* child = a_node->children;
341 0 : vector <SDMDataObject::Baseband> basebands;
342 0 : while (SDMDataObjectParser::testElement(child, HeaderParser::BASEBAND)) {
343 0 : basebands.push_back(parseBaseband(child, sdmDataObject ));
344 0 : child = child->next;
345 : }
346 :
347 0 : dataStruct.basebands_ = (basebands);
348 :
349 : // Now that all the spectral windows are read set the associations between spectral windows.
350 : // We have recorded the id and image attributes when they are present in private strings in each spectralWindow.
351 : //
352 :
353 : // I want a map to associate a string of the form "<int>_<int>" to a string of the form "<int>_<int>"
354 : // and I define an entry in this map for each spectralWindow with an strSw_ non empty, the value
355 : // associated is of the form <int>_<int> where the two integers are the coordinates
356 : // (baseband index, spectralWindow index in the baseband)
357 : //
358 0 : map<string, string> id2int_int;
359 0 : ostringstream oss;
360 :
361 0 : string key, value;
362 0 : for (unsigned int ibb = 0; ibb < dataStruct.basebands_.size(); ibb++) {
363 0 : vector<SDMDataObject::SpectralWindow>& spws = dataStruct.basebands_.at(ibb).spectralWindows_;
364 0 : for (unsigned int ispw = 0; ispw < spws.size(); ispw++) {
365 :
366 0 : oss.str("");
367 0 : oss << ibb << " " << ispw;
368 0 : value = oss.str();
369 :
370 0 : oss.str("");
371 0 : oss << ibb << " " << spws.at(ispw).strSw();
372 0 : key = oss.str();
373 :
374 0 : id2int_int[key] = value;
375 :
376 : }
377 : }
378 :
379 :
380 : // Now re scan all the spectralWindows and look for the ones with an strImage_ non empty.
381 : // and define the associations.
382 : //
383 0 : istringstream iss;
384 0 : map<string, string>::iterator iter;
385 : int ibbImage, ispwImage;
386 0 : for (unsigned int ibb = 0; ibb < dataStruct.basebands_.size(); ibb++) {
387 0 : vector<SDMDataObject::SpectralWindow>& spws = dataStruct.basebands_.at(ibb).spectralWindows_;
388 0 : for (unsigned int ispw = 0; ispw < spws.size(); ispw++) {
389 0 : string image = spws.at(ispw).strImage();
390 0 : if (image.size() > 0) {
391 0 : oss.str("");
392 0 : oss << ibb << " " << image;
393 0 : key = oss.str();
394 0 : if ((iter = id2int_int.find(key)) != id2int_int.end()) {
395 0 : iss.str(iter->second);
396 0 : iss >> ibbImage;
397 0 : iss >> ispwImage;
398 0 : dataStruct.imageSPW(ibb, ispw, ispwImage);
399 : }
400 : else {
401 0 : oss.str("");
402 0 : oss << "In baseband #" << ibb << " the spectral window #" << ispw << " refers to non defined image ('" << image << "')";
403 0 : throw SDMDataObjectParserException(oss.str());
404 : }
405 : }
406 0 : }
407 : }
408 :
409 : // Metadata attachments.
410 :
411 : // flags (optional)
412 0 : if (SDMDataObjectParser::testElement(child, HeaderParser::FLAGS)) {
413 0 : dataStruct.flags_ = (parseBinaryPart(child, HeaderParser::FLAGS));
414 0 : child = child->next;
415 : }
416 :
417 : // actualTimes (optional)
418 0 : if (SDMDataObjectParser::testElement(child, HeaderParser::ACTUALTIMES)) {
419 0 : dataStruct.actualTimes_ = (parseBinaryPart(child, HeaderParser::ACTUALTIMES));
420 0 : child = child->next;
421 : }
422 :
423 : // actualDurations (optional)
424 0 : if (SDMDataObjectParser::testElement(child, HeaderParser::ACTUALDURATIONS)) {
425 0 : dataStruct.actualDurations_ = (parseBinaryPart(child, HeaderParser::ACTUALDURATIONS));
426 0 : child = child->next;
427 : }
428 :
429 : // Binary attachments elements...
430 0 : switch (sdmDataObject.correlationMode()) {
431 0 : case CROSS_ONLY :
432 0 : dataStruct.crossData_ = (parseBinaryPart(child, HeaderParser::CROSSDATA));
433 0 : child = child->next;
434 0 : break;
435 :
436 0 : case AUTO_ONLY :
437 0 : dataStruct.autoData_ = (parseAutoDataBinaryPart(child, HeaderParser::AUTODATA));
438 0 : child = child->next;
439 0 : break;
440 :
441 0 : case CROSS_AND_AUTO :
442 0 : dataStruct.crossData_ = (parseBinaryPart(child, HeaderParser::CROSSDATA));
443 0 : child = child->next;
444 0 : dataStruct.autoData_ = (parseAutoDataBinaryPart(child, HeaderParser::AUTODATA));
445 0 : child = child->next;
446 0 : break;
447 : }
448 :
449 : /*
450 : // zeroLags (mandatory in FULL_RESOLUTION)
451 : if (sdmDataObject.spectralResolutionType() == FULL_RESOLUTION) {
452 : dataStruct.zeroLags_ = (parseBinaryPart(child, HeaderParser::ZEROLAGS));
453 : child = child->next;
454 : }
455 : // (and optional in CHANNEL_AVERAGE)
456 : else if (sdmDataObject.spectralResolutionType() == CHANNEL_AVERAGE) {
457 : if (SDMDataObjectParser::testElement(child, HeaderParser::ZEROLAGS)) {
458 : dataStruct.zeroLags_ = (parseBinaryPart(child, HeaderParser::ZEROLAGS));
459 : child = child->next;
460 : }
461 : }
462 : */
463 :
464 : // zeroLags are allowed only with a non FX correlator.
465 0 : if (SDMDataObjectParser::testElement(child, HeaderParser::ZEROLAGS)) {
466 : // Reject zeroLags if the context does not allow them
467 0 : if (sdmDataObject.processorType_ != CORRELATOR)
468 0 : throw SDMDataObjectParserException("zeroLags are not expected with the declared processor type ('" +
469 0 : CProcessorType::name(sdmDataObject.processorType_) + "')");
470 :
471 :
472 0 : dataStruct.zeroLags_ = (parseZeroLagsBinaryPart(child, HeaderParser::ZEROLAGS));
473 :
474 : // Reject zeroLags if the context does not allow them ... again
475 :
476 0 : if (dataStruct.zeroLags_.correlatorType_ == FX)
477 0 : throw SDMDataObjectParserException ("zeroLags are not expected with the declared correlator type ('" +
478 0 : CCorrelatorType::name(dataStruct.zeroLags_.correlatorType_) + "')");
479 :
480 0 : child = child->next;
481 : }
482 :
483 0 : sdmDataObject.dataStruct_ = (dataStruct);
484 0 : }
485 :
486 0 : SDMDataObject::Baseband HeaderParser::parseBaseband(xmlNode* a_node, SDMDataObject& sdmDataObject){
487 0 : SDMDataObject::Baseband bb;
488 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::BASEBAND);
489 :
490 0 : bb.name_ = (SDMDataObjectParser::parseStringAttr<BasebandName, CBasebandName>(a_node, HeaderParser::NAME));
491 :
492 : // Traverse the children (spectralWindow).
493 0 : xmlNode* child = a_node->children;
494 0 : vector<SDMDataObject::SpectralWindow> spw;
495 0 : parseSpectralWindow(child, sdmDataObject, spw);
496 0 : bb.spectralWindows(spw);
497 :
498 0 : return bb;
499 0 : }
500 :
501 0 : void HeaderParser::parseSpectralWindow(xmlNode* a_node, SDMDataObject& sdmDataObject , vector<SDMDataObject::SpectralWindow>& spectralWindow){
502 0 : for (xmlNode* cur_node = a_node; cur_node; cur_node = cur_node->next) {
503 0 : SDMDataObjectParser::isElement(a_node, HeaderParser::SPECTRALWINDOW);
504 :
505 : //Look for attributes
506 0 : vector<StokesParameter> crossPolProducts;
507 0 : vector<StokesParameter> sdPolProducts;
508 : float scaleFactor;
509 : int numSpectralPoint;
510 : int numBin;
511 : NetSideband sideband;
512 :
513 0 : SDMDataObject::SpectralWindow spw;
514 :
515 :
516 0 : string dummy = SDMDataObjectParser::parseStringAttr(cur_node, HeaderParser::SWBB);
517 :
518 0 : switch (sdmDataObject.correlationMode()) {
519 :
520 0 : case CROSS_ONLY:
521 0 : crossPolProducts = SDMDataObjectParser::parseStringsAttr<StokesParameter, CStokesParameter>(cur_node, HeaderParser::CROSSPOLPRODUCTS );
522 0 : scaleFactor = SDMDataObjectParser::parseFloatAttr(cur_node, HeaderParser::SCALEFACTOR );
523 0 : numSpectralPoint = SDMDataObjectParser::parseIntAttr(cur_node, HeaderParser::NUMSPECTRALPOINT );
524 0 : numBin = SDMDataObjectParser::parseIntAttr(cur_node, HeaderParser::NUMBIN );
525 0 : sideband = SDMDataObjectParser::parseStringAttr<NetSideband, CNetSideband>(cur_node, HeaderParser::SIDEBAND);
526 0 : spw = SDMDataObject::SpectralWindow(crossPolProducts,
527 : scaleFactor,
528 : (unsigned int)numSpectralPoint,
529 : (unsigned int)numBin,
530 0 : sideband);
531 0 : break;
532 :
533 0 : case AUTO_ONLY:
534 0 : sdPolProducts = SDMDataObjectParser::parseStringsAttr<StokesParameter, CStokesParameter>(cur_node, HeaderParser::SDPOLPRODUCTS );
535 0 : numSpectralPoint = SDMDataObjectParser::parseIntAttr(cur_node, HeaderParser::NUMSPECTRALPOINT );
536 0 : numBin = SDMDataObjectParser::parseIntAttr(cur_node, HeaderParser::NUMBIN );
537 0 : sideband = SDMDataObjectParser::parseStringAttr<NetSideband, CNetSideband>(cur_node, HeaderParser::SIDEBAND);
538 0 : spw = SDMDataObject::SpectralWindow(sdPolProducts,
539 : (unsigned int)numSpectralPoint,
540 : (unsigned int)numBin,
541 0 : sideband);
542 0 : break;
543 :
544 0 : case CROSS_AND_AUTO:
545 0 : crossPolProducts = SDMDataObjectParser::parseStringsAttr<StokesParameter, CStokesParameter>(cur_node, HeaderParser::CROSSPOLPRODUCTS );
546 0 : sdPolProducts = SDMDataObjectParser::parseStringsAttr<StokesParameter, CStokesParameter>(cur_node, HeaderParser::SDPOLPRODUCTS );
547 0 : scaleFactor = SDMDataObjectParser::parseFloatAttr(cur_node, HeaderParser::SCALEFACTOR );
548 0 : numSpectralPoint = SDMDataObjectParser::parseIntAttr(cur_node, HeaderParser::NUMSPECTRALPOINT );
549 0 : numBin = SDMDataObjectParser::parseIntAttr(cur_node, HeaderParser::NUMBIN );
550 0 : sideband = SDMDataObjectParser::parseStringAttr<NetSideband, CNetSideband>(cur_node, HeaderParser::SIDEBAND);
551 0 : spw = SDMDataObject::SpectralWindow(crossPolProducts,
552 : sdPolProducts,
553 : scaleFactor,
554 : (unsigned int)numSpectralPoint,
555 : (unsigned int)numBin,
556 0 : sideband);
557 0 : break;
558 : }
559 :
560 0 : spw.strSw(SDMDataObjectParser::parseStringAttr(cur_node, HeaderParser::SW));
561 0 : if (SDMDataObjectParser::hasAttr(cur_node, HeaderParser::IMAGE))
562 0 : spw.strImage(SDMDataObjectParser::parseStringAttr(cur_node, HeaderParser::IMAGE));
563 :
564 0 : spectralWindow.push_back(spw);
565 :
566 0 : }
567 0 : }
568 :
569 0 : SDMDataObject::BinaryPart HeaderParser::parseBinaryPart(xmlNode* a_node, const string& attachmentName) {
570 0 : SDMDataObjectParser::isElement(a_node, attachmentName);
571 :
572 0 : return SDMDataObject::BinaryPart(SDMDataObjectParser::parseIntAttr(a_node, HeaderParser::SIZE),
573 0 : SDMDataObjectParser::parseStringsAttr<AxisName, CAxisName>(a_node, HeaderParser::AXES));
574 : }
575 :
576 0 : SDMDataObject::AutoDataBinaryPart HeaderParser::parseAutoDataBinaryPart(xmlNode* a_node, const string& attachmentName) {
577 0 : SDMDataObjectParser::isElement(a_node, attachmentName);
578 :
579 0 : return SDMDataObject::AutoDataBinaryPart(SDMDataObjectParser::parseIntAttr(a_node, HeaderParser::SIZE),
580 0 : SDMDataObjectParser::parseStringsAttr<AxisName, CAxisName>(a_node, HeaderParser::AXES),
581 0 : SDMDataObjectParser::parseBoolAttr(a_node, HeaderParser::NORMALIZED));
582 : }
583 :
584 0 : SDMDataObject::ZeroLagsBinaryPart HeaderParser::parseZeroLagsBinaryPart(xmlNode* a_node, const string& attachmentName) {
585 0 : SDMDataObjectParser::isElement(a_node, attachmentName);
586 :
587 0 : return SDMDataObject::ZeroLagsBinaryPart(SDMDataObjectParser::parseIntAttr(a_node, HeaderParser::SIZE),
588 0 : SDMDataObjectParser::parseStringsAttr<AxisName, CAxisName>(a_node, HeaderParser::AXES),
589 0 : SDMDataObjectParser::parseStringAttr<CorrelatorType, CCorrelatorType>(a_node, HeaderParser::CORRELATORTYPE));
590 : }
591 :
592 : // CorrSubsetHeaderParser methods.
593 :
594 0 : CorrSubsetHeaderParser::CorrSubsetHeaderParser() {
595 0 : doc = NULL;
596 0 : }
597 :
598 0 : CorrSubsetHeaderParser::~CorrSubsetHeaderParser() {
599 0 : if (doc != NULL) xmlFreeDoc(doc);
600 0 : }
601 :
602 :
603 0 : void CorrSubsetHeaderParser::parseFile(const string& filename, SDMDataSubset& sdmCorrDataSubset){
604 0 : if (doc != NULL) xmlFreeDoc(doc);
605 0 : doc = xmlReadFile(filename.c_str(), NULL, XML_PARSE_NOBLANKS);
606 0 : if (doc == NULL) {
607 0 : throw SDMDataObjectParserException("The file '"+filename+"' could not be transformed into a DOM structure");
608 : }
609 :
610 0 : xmlNode* root_element = xmlDocGetRootElement(doc);
611 0 : parseSDMDataSubsetHeader(root_element, sdmCorrDataSubset);
612 0 : }
613 :
614 0 : void CorrSubsetHeaderParser::parseMemory(const string& buffer, SDMDataSubset& sdmCorrDataSubset) {
615 0 : if (doc != NULL) xmlFreeDoc(doc);
616 0 : doc = xmlReadMemory(buffer.data(), buffer.size(), "SDMDataHeader.xml", NULL, XML_PARSE_NOBLANKS);
617 0 : if (doc == NULL) {
618 0 : throw SDMDataObjectParserException("The buffer containing the XML document could not be transformed into a DOM structure");
619 : }
620 :
621 0 : xmlNode* root_element = xmlDocGetRootElement(doc);
622 0 : parseSDMDataSubsetHeader(root_element, sdmCorrDataSubset );
623 0 : };
624 :
625 0 : void CorrSubsetHeaderParser::parseSDMDataSubsetHeader(xmlNode* a_node, SDMDataSubset& sdmCorrDataSubset) {
626 : // Look up for <sdmSubsetDataHeader...
627 0 : SDMDataObjectParser::isElement(a_node, SDMDATASUBSETHEADER);
628 :
629 : // Project path.
630 0 : vector<unsigned int> v;
631 0 : v = SDMDataObjectParser::parseProjectPath(a_node); // v should contain 4 (integration) or 5 (subintegration) elements.
632 :
633 : // Check conformity of execBlockNum, scanNum and subscanNum.
634 :
635 0 : if (v.at(0) != sdmCorrDataSubset.owner()->execBlockNum()
636 0 : || v.at(1) != sdmCorrDataSubset.owner()->scanNum()
637 0 : || v.at(2) != sdmCorrDataSubset.owner()->subscanNum())
638 0 : throw SDMDataObjectParserException("The project path of this data subset '"
639 0 : +SDMDataObjectParser::parseStringAttr(a_node, PROJECTPATH)
640 0 : +"' is not compatible with the project path announced in the global header"
641 0 : +" '"+sdmCorrDataSubset.owner()->projectPath()+"'");
642 :
643 : // Determine integrationNum [, subintegrationNum]
644 0 : sdmCorrDataSubset.integrationNum_ = v.at(3);
645 0 : sdmCorrDataSubset.subintegrationNum_ = (v.size() == 5) ? v.at(4) : 0;
646 :
647 : // Traverse the children .
648 0 : xmlNode* child = a_node->children;
649 :
650 : // <schedulePeriodTime...
651 0 : parseSchedulePeriodTime(child, sdmCorrDataSubset);
652 :
653 : // <dataStruct...
654 0 : child = child->next;
655 0 : SDMDataObjectParser::isElement(child, CorrSubsetHeaderParser::DATASTRUCT);
656 0 : sdmCorrDataSubset.dataStruct_ = SDMDataObjectParser::parseStringAttr(child, CorrSubsetHeaderParser::REF);
657 :
658 0 : child = child->next;
659 0 : if (SDMDataObjectParser::testElement(child, CorrSubsetHeaderParser::ABORTOBSERVATION)) {
660 : // Is it a cancelling [sub]integration ?
661 0 : sdmCorrDataSubset.aborted_ = true;
662 0 : parseAbortObservation(child, sdmCorrDataSubset);
663 : }
664 : else {
665 : // ... or a sequence of attachments description.
666 0 : if (SDMDataObjectParser::testElement(child, FLAGSREF)) {
667 0 : sdmCorrDataSubset.flagsREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
668 0 : child = child->next;
669 : }
670 :
671 :
672 0 : if (SDMDataObjectParser::testElement(child, ACTUALTIMESREF)) {
673 0 : sdmCorrDataSubset.actualTimesREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
674 0 : child = child->next;
675 : }
676 :
677 :
678 0 : if (SDMDataObjectParser::testElement(child, ACTUALDURATIONSREF)) {
679 0 : sdmCorrDataSubset.actualDurationsREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
680 0 : child = child->next;
681 : }
682 :
683 0 : switch (sdmCorrDataSubset.owner()->correlationMode()) {
684 0 : case CROSS_ONLY:
685 0 : SDMDataObjectParser::isElement(child, CROSSDATAREF);
686 0 : sdmCorrDataSubset.crossDataREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
687 0 : sdmCorrDataSubset.crossDataType_ = SDMDataObjectParser::parseStringAttr<PrimitiveDataType, CPrimitiveDataType>(child, CorrSubsetHeaderParser::TYPE);
688 0 : child = child->next;
689 0 : break;
690 :
691 0 : case AUTO_ONLY:
692 0 : SDMDataObjectParser::isElement(child, AUTODATAREF);
693 0 : sdmCorrDataSubset.autoDataREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
694 0 : child = child->next;
695 0 : break;
696 :
697 0 : case CROSS_AND_AUTO:
698 0 : SDMDataObjectParser::isElement(child, CROSSDATAREF);
699 0 : sdmCorrDataSubset.crossDataREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
700 0 : sdmCorrDataSubset.crossDataType_ = SDMDataObjectParser::parseStringAttr<PrimitiveDataType, CPrimitiveDataType>(child, CorrSubsetHeaderParser::TYPE);
701 0 : child = child->next;
702 :
703 0 : SDMDataObjectParser::isElement(child, AUTODATAREF);
704 0 : sdmCorrDataSubset.autoDataREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
705 0 : child = child->next;
706 0 : break;
707 : }
708 : /*
709 : if (sdmCorrDataSubset.owner()->spectralResolutionType() != CHANNEL_AVERAGE) {
710 : SDMDataObjectParser::isElement(child, ZEROLAGSREF);
711 : sdmCorrDataSubset.zeroLagsREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
712 : child = child->next;
713 : }
714 : */
715 :
716 : // zeroLags are optional in any case. Michel Caillat. 24 Jul 2008
717 0 : if (SDMDataObjectParser::testElement(child, ZEROLAGSREF)) {
718 0 : sdmCorrDataSubset.zeroLagsREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
719 0 : child = child->next;
720 : }
721 : }
722 0 : }
723 :
724 : // void CorrSubsetHeaderParser::parseProjectPath (xmlNode* a_node, SDMDataSubset& sdmCorrDataSubset) {
725 : // string projectPath = SDMDataObjectParser::parseStringAttr(a_node,CorrSubsetHeaderParser::PROJECTPATH);
726 :
727 : // boost::cmatch what;
728 : // unsigned int execBlockNum = 0;
729 : // unsigned int scanNum = 0;
730 : // unsigned int subscanNum = 0;
731 : // switch (sdmCorrDataSubset.owner()->spectralResolutionType()) {
732 : // case FULL_RESOLUTION:
733 : // if (boost::regex_match(projectPath.c_str(), what, SDMDataObjectParser::PROJECTPATH4) && what[0].matched) {
734 : // execBlockNum = ::atoi(what[1].first);
735 : // scanNum = ::atoi(what[2].first);
736 : // subscanNum = ::atoi(what[3].first);
737 : // sdmCorrDataSubset.integrationNum_ = ::atoi(what[4].first);
738 : // }
739 : // else
740 : // throw SDMDataObjectParserException("Invalid string for projectPath '" + projectPath + "'");
741 : // break;
742 :
743 : // case CHANNEL_AVERAGE:
744 : // if (boost::regex_match(projectPath.c_str(), what, SDMDataObjectParser::PROJECTPATH5) && what[0].matched) {
745 : // execBlockNum = ::atoi(what[1].first);
746 : // scanNum = ::atoi(what[2].first);
747 : // subscanNum = ::atoi(what[3].first);
748 : // sdmCorrDataSubset.integrationNum_ = ::atoi(what[4].first);
749 : // sdmCorrDataSubset.subintegrationNum_ = ::atoi(what[5].first);
750 : // }
751 : // else
752 : // throw SDMDataObjectParserException("Invalid string for projectPath '" + projectPath + "'");
753 : // break;
754 :
755 : // case BASEBAND_WIDE:
756 : // throw SDMDataObjectParserException("'"+CSpectralResolutionType::name(BASEBAND_WIDE)+"' cannot appear in this context.");
757 : // break;
758 : // }
759 :
760 : // if (execBlockNum != sdmCorrDataSubset.owner()->execBlockNum()
761 : // || scanNum != sdmCorrDataSubset.owner()->scanNum()
762 : // || subscanNum != sdmCorrDataSubset.owner()->subscanNum())
763 : // throw SDMDataObjectParserException("The project path of this data subset '"
764 : // +projectPath
765 : // +"' is not compatible with the project path announced in the global header"
766 : // +" '"+sdmCorrDataSubset.owner()->projectPath()+"'");
767 : // }
768 :
769 0 : void CorrSubsetHeaderParser::parseSchedulePeriodTime(xmlNode* a_node, SDMDataSubset& sdmCorrDataSubset) {
770 0 : SDMDataObjectParser::isElement(a_node, CorrSubsetHeaderParser::SCHEDULEPERIODTIME);
771 :
772 0 : xmlNode* child = a_node->children;
773 : // <time...
774 0 : sdmCorrDataSubset.time_ = parseTime(child);
775 :
776 : // <interval...
777 0 : child = child->next;
778 0 : sdmCorrDataSubset.interval_ = parseInterval(child);
779 0 : }
780 :
781 0 : long long CorrSubsetHeaderParser::parseTime(xmlNode* a_node) {
782 0 : SDMDataObjectParser::isElement(a_node, CorrSubsetHeaderParser::TIME);
783 0 : return SDMDataObjectParser::parseLongLong(a_node->children);
784 : }
785 :
786 :
787 0 : long long CorrSubsetHeaderParser::parseInterval(xmlNode* a_node) {
788 0 : SDMDataObjectParser::isElement(a_node, CorrSubsetHeaderParser::INTERVAL);
789 0 : return SDMDataObjectParser::parseLongLong(a_node->children);
790 : }
791 :
792 :
793 0 : void CorrSubsetHeaderParser::parseAbortObservation(xmlNode* a_node, SDMDataSubset& sdmCorrDataSubset) {
794 0 : xmlNode* child = a_node->children;
795 :
796 : // <abortTime...
797 0 : SDMDataObjectParser::isElement(child, CorrSubsetHeaderParser::ABORTTIME);
798 0 : sdmCorrDataSubset.abortTime_ = SDMDataObjectParser::parseLongLong(child->children);
799 :
800 : // <abortReason...
801 0 : child = child->next;
802 0 : SDMDataObjectParser::isElement(child, CorrSubsetHeaderParser::ABORTREASON);
803 0 : sdmCorrDataSubset.abortReason_ = SDMDataObjectParser::parseString(child->children);
804 0 : }
805 :
806 0 : void CorrSubsetHeaderParser::parseCrossDataType(xmlNode* a_node, SDMDataSubset& sdmCorrDataSubset) {
807 0 : SDMDataObjectParser::isElement(a_node, CorrSubsetHeaderParser::TYPE);
808 0 : sdmCorrDataSubset.crossDataType(SDMDataObjectParser::parseLiteral<PrimitiveDataType, CPrimitiveDataType>(a_node->children));
809 0 : }
810 :
811 :
812 0 : void CorrSubsetHeaderParser::reset() {
813 0 : if (doc)
814 0 : xmlFreeDoc(doc);
815 :
816 0 : doc = NULL;
817 0 : }
818 :
819 :
820 : // TPSubsetHeaderParser methods.
821 :
822 0 : TPSubsetHeaderParser::TPSubsetHeaderParser() {
823 0 : doc = NULL;
824 0 : }
825 :
826 0 : TPSubsetHeaderParser::~TPSubsetHeaderParser() {
827 0 : if (doc != NULL) xmlFreeDoc(doc);
828 0 : }
829 :
830 :
831 0 : void TPSubsetHeaderParser::parseFile(const string& filename, SDMDataSubset& sdmTPDataSubset){
832 0 : if (doc != NULL) xmlFreeDoc(doc);
833 0 : doc = xmlReadFile(filename.c_str(), NULL, XML_PARSE_NOBLANKS);
834 0 : if (doc == NULL) {
835 0 : throw SDMDataObjectParserException("The file '"+filename+"' could not be transformed into a DOM structure");
836 : }
837 :
838 0 : xmlNode* root_element = xmlDocGetRootElement(doc);
839 0 : parseSDMDataSubsetHeader(root_element, sdmTPDataSubset);
840 :
841 0 : }
842 :
843 0 : void TPSubsetHeaderParser::parseMemory(const string& buffer, SDMDataSubset& sdmTPDataSubset) {
844 0 : if (doc != NULL) xmlFreeDoc(doc);
845 0 : doc = xmlReadMemory(buffer.data(), buffer.size(), "SDMDataHeader.xml", NULL, XML_PARSE_NOBLANKS);
846 0 : if (doc == NULL) {
847 0 : throw SDMDataObjectParserException("The buffer containing the XML document could not be transformed into a DOM structure");
848 : }
849 :
850 0 : xmlNode* root_element = xmlDocGetRootElement(doc);
851 0 : parseSDMDataSubsetHeader(root_element, sdmTPDataSubset);
852 0 : }
853 :
854 0 : void TPSubsetHeaderParser::parseSDMDataSubsetHeader(xmlNode* a_node, SDMDataSubset& sdmTPDataSubset) {
855 : // Look up for <sdmSubsetDataHeader...
856 0 : SDMDataObjectParser::isElement(a_node, TPSubsetHeaderParser::SDMDATASUBSETHEADER);
857 :
858 : // Project path.
859 0 : int pathLen = (sdmTPDataSubset.owner()->dimensionality() == 0) ? 3 : 4;
860 0 : vector<unsigned int> v = SDMDataObjectParser::parseProjectPath(a_node, pathLen);
861 :
862 : // Check conformity of execBlockNum, scanNum and subscanNum.
863 0 : if (v.at(0) != sdmTPDataSubset.owner()->execBlockNum()
864 0 : || v.at(1) != sdmTPDataSubset.owner()->scanNum()
865 0 : || v.at(2) != sdmTPDataSubset.owner()->subscanNum())
866 0 : throw SDMDataObjectParserException("The project path of this data subset '"
867 0 : +SDMDataObjectParser::parseStringAttr(a_node, PROJECTPATH)
868 0 : +"' is not compatible with the project path announced in the global header"
869 0 : +" '"+sdmTPDataSubset.owner()->projectPath()+"'");
870 :
871 0 : if (pathLen == 4)
872 0 : sdmTPDataSubset.integrationNum_ = v.at(3);
873 :
874 : // Traverse the children...
875 0 : xmlNode* child = a_node->children;
876 :
877 : // <schedulePeriodTime...
878 0 : parseSchedulePeriodTime(child, sdmTPDataSubset);
879 :
880 : // <dataStruct...
881 0 : child = child->next;
882 0 : SDMDataObjectParser::isElement(child, TPSubsetHeaderParser::DATASTRUCT);
883 0 : sdmTPDataSubset.dataStruct_ = (SDMDataObjectParser::parseStringAttr(child, TPSubsetHeaderParser::REF));
884 :
885 0 : child = child->next;
886 : // Optional flags attachments.
887 0 : if (SDMDataObjectParser::testElement(child, FLAGSREF)) {
888 0 : sdmTPDataSubset.flagsREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
889 0 : child = child->next;
890 : }
891 :
892 0 : if (SDMDataObjectParser::testElement(child, ACTUALTIMESREF)) {
893 0 : sdmTPDataSubset.actualTimesREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
894 0 : child = child->next;
895 : }
896 :
897 0 : if (SDMDataObjectParser::testElement(child, ACTUALDURATIONSREF)) {
898 0 : sdmTPDataSubset.actualDurationsREF_ = SDMDataObjectParser::parseStringAttr(child, XLINKHREF);
899 0 : child = child->next;
900 : }
901 :
902 : // Look for mandatory autoData element.
903 0 : SDMDataObjectParser::isElement(child, AUTODATAREF);
904 0 : sdmTPDataSubset.autoDataREF_ = (SDMDataObjectParser::parseStringAttr(child, TPSubsetHeaderParser::XLINKHREF ));
905 0 : }
906 :
907 0 : void TPSubsetHeaderParser::parseProjectPath(xmlNode* a_node, SDMDataSubset& sdmTPDataSubset) {
908 0 : string projectPath = SDMDataObjectParser::parseStringAttr(a_node,TPSubsetHeaderParser::PROJECTPATH);
909 :
910 : #ifndef WITHOUT_BOOST
911 : boost::cmatch what;
912 : #else
913 0 : std::cmatch what;
914 : #endif
915 0 : unsigned int execBlockNum = 0;
916 0 : unsigned int scanNum = 0;
917 0 : unsigned int subscanNum = 0;
918 :
919 : #ifndef WITHOUT_BOOST
920 : if (boost::regex_match(projectPath.c_str(), what, PROJECTPATH3) && what[0].matched) {
921 : #else
922 0 : if (std::regex_match(projectPath.c_str(), what, PROJECTPATH3) && what[0].matched) {
923 : #endif
924 0 : execBlockNum = ::atoi(what[1].first);
925 0 : scanNum = ::atoi(what[2].first);
926 0 : subscanNum = ::atoi(what[3].first);
927 : }
928 : else
929 0 : throw SDMDataObjectParserException("Invalid string for projectPath '" + projectPath + "'");
930 :
931 0 : if (execBlockNum != sdmTPDataSubset.owner()->execBlockNum()
932 0 : || scanNum != sdmTPDataSubset.owner()->scanNum()
933 0 : || subscanNum != sdmTPDataSubset.owner()->subscanNum())
934 0 : throw SDMDataObjectParserException("The project path of this data subset '"
935 0 : +projectPath
936 0 : +"' is not compatible with the project path announced in the global header"
937 0 : +" '"+sdmTPDataSubset.owner()->projectPath()+"'");
938 0 : }
939 :
940 0 : void TPSubsetHeaderParser::parseSchedulePeriodTime(xmlNode* a_node, SDMDataSubset& sdmTPDataSubset) {
941 0 : SDMDataObjectParser::isElement(a_node, TPSubsetHeaderParser::SCHEDULEPERIODTIME);
942 :
943 0 : xmlNode* child = a_node->children;
944 : // <time...
945 0 : sdmTPDataSubset.time_ = parseTime(child);
946 :
947 : // <interval...
948 0 : child = child->next;
949 0 : sdmTPDataSubset.interval_ = parseInterval(child);
950 0 : }
951 :
952 0 : long long TPSubsetHeaderParser::parseTime(xmlNode* a_node) {
953 0 : SDMDataObjectParser::isElement(a_node, TPSubsetHeaderParser::TIME);
954 0 : return SDMDataObjectParser::parseLongLong(a_node->children);
955 : }
956 :
957 :
958 0 : long long TPSubsetHeaderParser::parseInterval(xmlNode* a_node) {
959 0 : SDMDataObjectParser::isElement(a_node, TPSubsetHeaderParser::INTERVAL);
960 0 : return SDMDataObjectParser::parseLongLong(a_node->children);
961 : }
962 : // SDMDataObject::TPSubsetHeaderParser:: methods.
963 :
964 :
965 : // SDMDataObjectHeaderParser:: methods.
966 0 : void SDMDataObjectParser::isElement(xmlNode* a_node, const string& elementName) {
967 : //cout << "Entering isElement for " << a_node->name << endl;
968 0 : if ((a_node == NULL) ||
969 0 : (a_node->type != XML_ELEMENT_NODE) ||
970 0 : (elementName.compare((const char*)a_node->name) != 0)) {
971 0 : ostringstream oss;
972 0 : oss << "Could not find '<" << elementName << "...";
973 0 : if ((a_node != NULL) && (a_node->type == XML_ELEMENT_NODE))
974 0 : oss << " ( I was given '<" << a_node->name <<"...')";
975 : else
976 0 : oss << " ( node is not an xml element ) " << endl;
977 :
978 0 : throw SDMDataObjectParserException(oss.str());
979 0 : }
980 : //cout << "Exiting isElement" << endl;
981 0 : }
982 :
983 0 : bool SDMDataObjectParser::testElement(xmlNode* a_node, const string& elementName) {
984 : //cout << "Entering testElement with " << elementName << " against " << a_node->name << endl;
985 0 : bool result = ((a_node != NULL) &&
986 0 : (a_node->type == XML_ELEMENT_NODE) &&
987 0 : (elementName.compare((const char*)a_node->name) == 0));
988 0 : return result;
989 : }
990 :
991 0 : void SDMDataObjectParser::inElements(xmlNode* a_node, const vector<string>& elementNames) {
992 0 : if (find(elementNames.begin(), elementNames.end(), string((char*) a_node->name)) == elementNames.end()) {
993 0 : ostringstream message;
994 0 : copy(elementNames.begin(), elementNames.end(), ostream_iterator<string>(message, " "));
995 0 : throw SDMDataObjectParserException("Could not find any of elements '" + message.str()+"' in " + string((const char*) a_node->name));
996 0 : }
997 0 : }
998 :
999 0 : xmlAttr* SDMDataObjectParser::hasAttr(xmlNode* a_node, const string& attrName) {
1000 0 : xmlAttr* result = 0;
1001 0 : for (struct _xmlAttr* attr = a_node->properties; attr; attr = attr->next) {
1002 0 : if (attrName.compare((const char*) attr->name) == 0) {
1003 0 : result = attr;
1004 0 : break;
1005 : }
1006 : }
1007 0 : return result;
1008 : }
1009 :
1010 0 : void SDMDataObjectParser::tokenize(const string& str,
1011 : vector<string>& tokens,
1012 : const string& delimiters) {
1013 : // Skip delimiters at beginning.
1014 0 : string::size_type lastPos = str.find_first_not_of(delimiters, 0);
1015 : // Find first "non-delimiter".
1016 0 : string::size_type pos = str.find_first_of(delimiters, lastPos);
1017 :
1018 0 : while (string::npos != pos || string::npos != lastPos) {
1019 : // Found a token, add it to the vector.
1020 0 : tokens.push_back(str.substr(lastPos, pos - lastPos));
1021 : // Skip delimiters. Note the "not_of"
1022 0 : lastPos = str.find_first_not_of(delimiters, pos);
1023 : // Find next "non-delimiter"
1024 0 : pos = str.find_first_of(delimiters, lastPos);
1025 : }
1026 0 : }
1027 :
1028 :
1029 0 : void SDMDataObjectParser::tokenize(const string& str,
1030 : set<string>& tokens,
1031 : const string& delimiters) {
1032 : // Skip delimiters at beginning.
1033 0 : string::size_type lastPos = str.find_first_not_of(delimiters, 0);
1034 : // Find first "non-delimiter".
1035 0 : string::size_type pos = str.find_first_of(delimiters, lastPos);
1036 :
1037 0 : while (string::npos != pos || string::npos != lastPos) {
1038 : // Found a token, add it to the vector.
1039 0 : tokens.insert(str.substr(lastPos, pos - lastPos));
1040 : // Skip delimiters. Note the "not_of"
1041 0 : lastPos = str.find_first_not_of(delimiters, pos);
1042 : // Find next "non-delimiter"
1043 0 : pos = str.find_first_of(delimiters, lastPos);
1044 : }
1045 0 : }
1046 :
1047 0 : string SDMDataObjectParser::substring(const string &s, int a, int b) {
1048 0 : return s.substr(a,(b - a));
1049 : }
1050 :
1051 0 : string SDMDataObjectParser::trim(const string& s) {
1052 0 : unsigned int i = 0;
1053 0 : while (s.at(i) == ' ' && i < s.length())
1054 0 : ++i;
1055 0 : if (i == s.length())
1056 0 : return "";
1057 0 : unsigned int j = s.length() - 1;
1058 0 : while (s.at(j) == ' ' && j > i)
1059 0 : --j;
1060 0 : return substring(s,i,j + 1);
1061 : }
1062 :
1063 0 : string SDMDataObjectParser::parseString(xmlNode* a_node) {
1064 0 : if ((a_node != NULL) && (a_node->next == NULL))
1065 0 : return string((const char*) a_node->content);
1066 :
1067 0 : throw SDMDataObjectParserException("Invalid node , can't be parsed into a long long");
1068 :
1069 : }
1070 :
1071 0 : long long SDMDataObjectParser::parseLongLong(xmlNode* a_node) {
1072 0 : if ((a_node != NULL) && (a_node->next == NULL)) {
1073 0 : istringstream in;
1074 0 : in.str((const char*) a_node->content);
1075 : long long x;
1076 0 : in >> x;
1077 0 : if (in.rdstate() == istream::failbit)
1078 0 : throw SDMDataObjectParserException("failed to parse '"+string((const char*)a_node->content)+"' as a long long in" + string((const char*)a_node->parent->name));
1079 0 : return x;
1080 0 : }
1081 :
1082 0 : throw SDMDataObjectParserException("Invalid node , can't be parsed into a long long");
1083 : }
1084 :
1085 0 : int SDMDataObjectParser::parseInt(xmlNode* a_node) {
1086 : //cout << "Entering parseInt with " << a_node->content << endl;
1087 0 : if ((a_node != NULL) && (a_node->next == NULL)) {
1088 : #ifndef WITHOUT_BOOST
1089 : const boost::regex UINT("[0-9]+");
1090 : boost::cmatch what;
1091 : if (boost::regex_match((char*)a_node->content, what, UINT)) {
1092 : return (::atoi(what[0].first));
1093 : }
1094 : #else
1095 0 : const std::regex UINT("[0-9]+");
1096 0 : std::cmatch what;
1097 0 : if (std::regex_match((char*)a_node->content, what, UINT)) {
1098 0 : return (::atoi(what[0].first));
1099 : }
1100 : #endif
1101 : else
1102 0 : throw SDMDataObjectParserException("failed to parse '"+string((const char*)a_node->content)+"' as an int in " + string((const char*)a_node->parent->name));
1103 0 : }
1104 :
1105 0 : throw SDMDataObjectParserException("Invalid node , can't be parsed into an int");
1106 : }
1107 :
1108 0 : bool SDMDataObjectParser::parseBool(xmlNode* a_node) {
1109 0 : if ((a_node != NULL) && (a_node->next == NULL)) {
1110 : #ifndef WITHOUT_BOOST
1111 : const boost::regex TORF("true|false");
1112 : boost::cmatch what;
1113 : if (boost::regex_match((char*)a_node->content, what, TORF)) {
1114 : return ( *(what[0].first) == 't') ? true:false;
1115 : }
1116 : #else
1117 0 : const std::regex TORF("true|false");
1118 0 : std::cmatch what;
1119 0 : if (std::regex_match((char*)a_node->content, what, TORF)) {
1120 0 : return ( *(what[0].first) == 't') ? true:false;
1121 : }
1122 : #endif
1123 : else
1124 0 : throw SDMDataObjectParserException("failed to parse '"+string((const char*)a_node->content)+"' as an int in " + string((const char*)a_node->parent->name));
1125 0 : }
1126 :
1127 0 : throw SDMDataObjectParserException("Invalid node , can't be parsed into an bool");
1128 : }
1129 :
1130 0 : float SDMDataObjectParser::parseFloat(xmlNode* a_node) {
1131 0 : if ((a_node != NULL) && (a_node->next == NULL)) {
1132 0 : istringstream in;
1133 0 : in.str((const char*) a_node->content);
1134 : float x;
1135 0 : in >> x;
1136 0 : if (in.rdstate() == istream::failbit)
1137 0 : throw SDMDataObjectParserException("failed to parse '"+string((const char*)a_node->content)+"' as a float in " + string((const char*)a_node->parent->name));
1138 0 : return x;
1139 0 : }
1140 :
1141 0 : throw SDMDataObjectParserException("Invalid node , can't be parsed into an float");
1142 : }
1143 :
1144 0 : int SDMDataObjectParser::parseIntAttr(xmlNode* a_node, const string& attrName) {
1145 0 : xmlAttr* attr = 0;
1146 :
1147 0 : if ((attr = hasAttr(a_node, attrName))) {
1148 0 : int result =parseInt(attr->children);
1149 0 : return result;
1150 : }
1151 0 : else throw SDMDataObjectParserException("could not find attribute '" + attrName + "' in " + string((const char*)a_node->name));
1152 : }
1153 :
1154 0 : bool SDMDataObjectParser::parseBoolAttr(xmlNode* a_node, const string& attrName) {
1155 0 : xmlAttr* attr = 0;
1156 :
1157 0 : if ((attr = hasAttr(a_node, attrName))) {
1158 0 : bool result = parseBool(attr->children);
1159 0 : return result;
1160 : }
1161 0 : else throw SDMDataObjectParserException("could not find attribute '" + attrName + "' in " + string((const char*)a_node->name));
1162 : }
1163 :
1164 0 : float SDMDataObjectParser::parseFloatAttr(xmlNode* a_node, const string& attrName) {
1165 0 : xmlAttr* attr = 0;
1166 :
1167 0 : if ((attr = hasAttr(a_node, attrName))) {
1168 0 : float result = parseFloat(attr->children);
1169 : //cout << attr->name << " = " << result << endl;
1170 0 : return result;
1171 : }
1172 0 : else throw SDMDataObjectParserException("could not find attribute '" + attrName + "' in " + string((const char*)a_node->name));
1173 : }
1174 :
1175 :
1176 0 : string SDMDataObjectParser::parseStringAttr(xmlNode* a_node, const string& attrName) {
1177 : //cout << "Entering parseStringAttr with " << attrName << " in " << a_node->name << endl;
1178 0 : xmlAttr* attr = 0;
1179 :
1180 0 : if ((attr = hasAttr(a_node, attrName))) {
1181 0 : string result = string((const char*)attr->children->content);
1182 : //cout << attr->name << " = " << result << endl;
1183 0 : return result;
1184 0 : }
1185 0 : else throw SDMDataObjectParserException("could not find attribute '" + attrName + "' in " + string((const char*)a_node->name));
1186 : }
1187 :
1188 :
1189 0 : vector<string> SDMDataObjectParser::parseStringsAttr(xmlNode* a_node, const string& attrName) {
1190 0 : xmlAttr* attr = 0;
1191 :
1192 0 : if ((attr = hasAttr(a_node, attrName))) {
1193 0 : vector<string> result;
1194 0 : tokenize((const char*)attr->children->content, result);
1195 : //cout << attr->name << " = '"; copy(result.begin(), result.end(), ostream_iterator<string>(cout, " ")); cout << "'" << endl;
1196 0 : return result;
1197 0 : }
1198 0 : else throw SDMDataObjectParserException("could not find attribute '" + attrName + "' in " + string((const char*)a_node->name));
1199 : }
1200 :
1201 0 : set<string> SDMDataObjectParser::parseStringSetAttr(xmlNode* a_node, const string& attrName) {
1202 0 : xmlAttr* attr = 0;
1203 :
1204 0 : if ((attr = hasAttr(a_node, attrName))) {
1205 0 : set<string> result;
1206 0 : tokenize((const char*)attr->children->content, result);
1207 : //cout << attr->name << " = '"; copy(result.begin(), result.end(), ostream_iterator<string>(cout, " ")); cout << "'" << endl;
1208 0 : return result;
1209 0 : }
1210 0 : else throw SDMDataObjectParserException("could not find attribute '" + attrName + "' in " + string((const char*)a_node->name));
1211 : }
1212 :
1213 :
1214 0 : vector<unsigned int> SDMDataObjectParser::parseProjectPath(xmlNode* a_node, unsigned int len) {
1215 0 : string projectPath = SDMDataObjectParser::parseStringAttr(a_node, HeaderParser::PROJECTPATH);
1216 0 : vector<unsigned int> result;
1217 0 : bool matched = true;
1218 : #ifndef WITHOUT_BOOST
1219 : boost::cmatch what;
1220 : switch (len) {
1221 : case 3: matched = boost::regex_match(projectPath.c_str(), what, PROJECTPATH3); break;
1222 : case 4: matched = boost::regex_match(projectPath.c_str(), what, PROJECTPATH4); break;
1223 : case 5: matched = boost::regex_match(projectPath.c_str(), what, PROJECTPATH5); break;
1224 : #else
1225 0 : std::cmatch what;
1226 0 : switch (len) {
1227 0 : case 3: matched = std::regex_match(projectPath.c_str(), what, PROJECTPATH3); break;
1228 0 : case 4: matched = std::regex_match(projectPath.c_str(), what, PROJECTPATH4); break;
1229 0 : case 5: matched = std::regex_match(projectPath.c_str(), what, PROJECTPATH5); break;
1230 : #endif
1231 0 : default: throw SDMDataObjectParserException ("internal error in method 'parseProjectPath'. The parameter 'len' has a value out of the range [3,5]");
1232 : }
1233 :
1234 0 : if (!matched)
1235 0 : throw SDMDataObjectException("'" + projectPath + "' is an invalid string for a 'projectPath' attribute");
1236 :
1237 0 : for (unsigned int i = 0; i < len; i++) {
1238 0 : result.push_back(::atoi(what[i+1].first));
1239 : }
1240 0 : return result;
1241 0 : }
1242 :
1243 : #ifndef WITHOUT_BOOST
1244 : const boost::regex SDMDataObjectParser::PROJECTPATH4OR5("([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+/)?");
1245 : #else
1246 : const std::regex SDMDataObjectParser::PROJECTPATH4OR5("([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+)/([0-9]+/)?");
1247 : #endif
1248 0 : vector<unsigned int> SDMDataObjectParser::parseProjectPath(xmlNode* a_node) {
1249 0 : string projectPath = SDMDataObjectParser::parseStringAttr(a_node, HeaderParser::PROJECTPATH);
1250 0 : vector<unsigned int> result;
1251 :
1252 0 : bool matched = true;
1253 :
1254 : #ifndef WITHOUT_BOOST
1255 : boost::cmatch what;
1256 : matched = boost::regex_match(projectPath.c_str(), what, PROJECTPATH4OR5);
1257 : #else
1258 0 : std::cmatch what;
1259 0 : matched = std::regex_match(projectPath.c_str(), what, PROJECTPATH4OR5);
1260 : #endif
1261 :
1262 0 : if (!matched)
1263 0 : throw SDMDataObjectException("'" + projectPath + "' is an invalid string for a 'projectPath' attribute.");
1264 :
1265 : // Let's retrieve the 4 first numbers.
1266 0 : for (unsigned int i = 0; i < 4; i++)
1267 0 : result.push_back(::atoi(what[i+1].first));
1268 :
1269 : // and the fifth if it exists...
1270 0 : if (what[5].matched) {
1271 0 : result.push_back(::atoi(what[5].first));
1272 : }
1273 :
1274 0 : return result;
1275 0 : }
1276 :
1277 0 : const ByteOrder* SDMDataObjectParser::parseByteOrderAttr(xmlNode* a_node, const string& attrName) {
1278 0 : string byteOrder = SDMDataObjectParser::parseStringAttr(a_node, attrName);
1279 :
1280 0 : if (byteOrder.compare("Little_Endian")==0) return ByteOrder::Little_Endian;
1281 0 : if (byteOrder.compare("Big_Endian")==0) return ByteOrder::Big_Endian;
1282 :
1283 0 : throw SDMDataObjectParserException("'" + byteOrder + "' is an invalid string for a 'byteOrder' attribute.");
1284 0 : }
1285 :
1286 0 : SDMDataObjectParser::SDMDataObjectParser() {;}
1287 0 : SDMDataObjectParser::~SDMDataObjectParser() {;}
1288 :
1289 0 : void SDMDataObjectParser::parseFileHeader(const string& filename, SDMDataObject& sdmDataObject) {
1290 0 : headerParser.parseFile(filename, sdmDataObject);
1291 0 : }
1292 :
1293 0 : void SDMDataObjectParser::parseMemoryHeader(const string& buffer, SDMDataObject& sdmDataObject) {
1294 0 : headerParser.parseMemory(buffer, sdmDataObject);
1295 0 : }
1296 :
1297 0 : void SDMDataObjectParser::parseFileCorrSubsetHeader(const string& filename, SDMDataSubset& sdmCorrDataSubset) {
1298 0 : corrSubsetHeaderParser.parseFile(filename, sdmCorrDataSubset);
1299 0 : }
1300 :
1301 0 : void SDMDataObjectParser::parseMemoryCorrSubsetHeader(const string& buffer, SDMDataSubset& sdmCorrDataSubset) {
1302 0 : corrSubsetHeaderParser.parseMemory(buffer, sdmCorrDataSubset);
1303 0 : }
1304 :
1305 0 : void SDMDataObjectParser::parseFileTPSubsetHeader(const string& filename, SDMDataSubset& sdmCorrDataSubset) {
1306 0 : tpSubsetHeaderParser.parseFile(filename, sdmCorrDataSubset);
1307 0 : }
1308 :
1309 0 : void SDMDataObjectParser::parseMemoryTPSubsetHeader(const string& buffer, SDMDataSubset& sdmCorrDataSubset) {
1310 0 : tpSubsetHeaderParser.parseMemory(buffer, sdmCorrDataSubset);
1311 0 : }
1312 :
1313 : }
1314 :
1315 : #if 0
1316 : using namespace asdmbinaries;
1317 : int main (int argC, char* argV[]) {
1318 :
1319 : if (argC != 3) return (1);
1320 :
1321 : SDMDataObjectParser parser;
1322 : SDMDataObject sdmDataObject;
1323 :
1324 : SDMDataSubset sdmDataSubset;
1325 :
1326 : cout << "Trying to parse an SDMDataHeader in " << argV[1] << " and an SDMDataSubsetHeader in " << argV[2] <<endl;
1327 : try {
1328 : parser.parseFileHeader(argV[1], sdmDataObject);
1329 : cout << "----- SDMDataObject ------" << endl;
1330 : cout << "SDMDataHeader: " << endl;
1331 : cout << endl;
1332 : cout << sdmDataObject.toString() << endl;
1333 :
1334 : // Now process the sdmDataSubsetHeader passed in argV[2]
1335 : switch (sdmDataObject.dimensionality()) {
1336 : case 0:
1337 : {
1338 : parser.parseFileTPSubsetHeader(argV[2], sdmDataSubset);
1339 : cout << endl;
1340 : cout << "SDMDataSubsetHeader: " << endl;
1341 : cout << endl;
1342 : cout << sdmDataSubset.toString(sdmDataObject.dimensionality()) << endl;
1343 : break;
1344 : }
1345 :
1346 : case 1:
1347 : {
1348 : parser.parseFileCorrSubsetHeader(argV[2], sdmDataSubset);
1349 : cout << endl;
1350 : cout << "SDMDataSubsetHeader: " << endl;
1351 : cout << endl;
1352 : cout << sdmDataSubset.toString(sdmDataObject.dimensionality());
1353 : break;
1354 : }
1355 :
1356 : default:
1357 : break;
1358 : }
1359 : }
1360 : catch (SDMDataObjectParserException e) {
1361 : cout << e.getMessage() << endl;
1362 : exit(1);
1363 : }
1364 :
1365 : cout << endl;
1366 : cout << "----------------------" << endl;
1367 : cout << "XML representation of the sdmDataHeader: " << endl;
1368 : cout << endl;
1369 : cout << sdmDataObject.toXML() << endl;
1370 :
1371 : cout << endl;
1372 : cout << "----------------------" << endl;
1373 : cout << "XML representation of the sdmDataSubsetHeader: " << endl;
1374 : cout << endl;
1375 : cout << sdmDataSubset.toXML(sdmDataObject.dimensionality()) << endl;
1376 : }
1377 : #endif
|