source: ntrip/branches/BNC_2.12/src/RTCM3/RTCM3Decoder.cpp @ 8819

Last change on this file since 8819 was 8819, checked in by stuerze, 22 months ago

update with respect to BDS signal mapping IDs as far as consistent with RINEX v3.04

File size: 55.9 KB
Line 
1// Part of BNC, a utility for retrieving decoding and
2// converting GNSS data streams from NTRIP broadcasters.
3//
4// Copyright (C) 2007
5// German Federal Agency for Cartography and Geodesy (BKG)
6// http://www.bkg.bund.de
7// Czech Technical University Prague, Department of Geodesy
8// http://www.fsv.cvut.cz
9//
10// Email: euref-ip@bkg.bund.de
11//
12// This program is free software; you can redistribute it and/or
13// modify it under the terms of the GNU General Public License
14// as published by the Free Software Foundation, version 2.
15//
16// This program is distributed in the hope that it will be useful,
17// but WITHOUT ANY WARRANTY; without even the implied warranty of
18// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19// GNU General Public License for more details.
20//
21// You should have received a copy of the GNU General Public License
22// along with this program; if not, write to the Free Software
23// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
24
25/* -------------------------------------------------------------------------
26 * BKG NTRIP Client
27 * -------------------------------------------------------------------------
28 *
29 * Class:      RTCM3Decoder
30 *
31 * Purpose:    RTCM3 Decoder
32 *
33 * Author:     L. Mervart
34 *
35 * Created:    24-Aug-2006
36 *
37 * Changes:
38 *
39 * -----------------------------------------------------------------------*/
40
41#include <iostream>
42#include <iomanip>
43#include <sstream>
44#include <math.h>
45#include <string.h>
46
47#include "bits.h"
48#include "gnss.h"
49#include "RTCM3Decoder.h"
50#include "rtcm_utils.h"
51#include "bncconst.h"
52#include "bnccore.h"
53#include "bncutils.h"
54#include "bncsettings.h"
55
56using namespace std;
57
58// Error Handling
59////////////////////////////////////////////////////////////////////////////
60void RTCM3Error(const char*, ...) {
61}
62
63// Constructor
64////////////////////////////////////////////////////////////////////////////
65RTCM3Decoder::RTCM3Decoder(const QString& staID, bncRawFile* rawFile) :
66    GPSDecoder() {
67
68  _staID = staID;
69  _rawFile = rawFile;
70
71  connect(this, SIGNAL(newGPSEph(t_ephGPS)), BNC_CORE,
72      SLOT(slotNewGPSEph(t_ephGPS)));
73  connect(this, SIGNAL(newGlonassEph(t_ephGlo)), BNC_CORE,
74      SLOT(slotNewGlonassEph(t_ephGlo)));
75  connect(this, SIGNAL(newGalileoEph(t_ephGal)), BNC_CORE,
76      SLOT(slotNewGalileoEph(t_ephGal)));
77  connect(this, SIGNAL(newSBASEph(t_ephSBAS)), BNC_CORE,
78      SLOT(slotNewSBASEph(t_ephSBAS)));
79  connect(this, SIGNAL(newBDSEph(t_ephBDS)), BNC_CORE,
80      SLOT(slotNewBDSEph(t_ephBDS)));
81
82  _MessageSize = _SkipBytes = _BlockSize = _NeedBytes = 0;
83}
84
85// Destructor
86////////////////////////////////////////////////////////////////////////////
87RTCM3Decoder::~RTCM3Decoder() {
88  QMapIterator<QByteArray, RTCM3coDecoder*> it(_coDecoders);
89  while (it.hasNext())
90  {
91    it.next();
92    delete it.value();
93  }
94}
95
96//
97////////////////////////////////////////////////////////////////////////////
98bool RTCM3Decoder::DecodeRTCM3GPS(unsigned char* data, int size) {
99  bool decoded = false;
100  bncTime CurrentObsTime;
101  int i, numsats, syncf, type;
102  uint64_t numbits = 0, bitfield = 0;
103
104  data += 3; /* header */
105  size -= 6; /* header + crc */
106
107  GETBITS(type, 12)
108  SKIPBITS(12)
109  /* id */
110  GETBITS(i, 30)
111
112  CurrentObsTime.set(i);
113  if (_CurrentTime.valid() && CurrentObsTime != _CurrentTime) {
114    decoded = true;
115    _obsList.append(_CurrentObsList);
116    _CurrentObsList.clear();
117  }
118
119  _CurrentTime = CurrentObsTime;
120
121  GETBITS(syncf, 1)
122  /* sync */
123  GETBITS(numsats, 5)
124  SKIPBITS(4)
125  /* smind, smint */
126
127  while (numsats--) {
128    int sv, code, l1range, amb = 0;
129    t_satObs CurrentObs;
130    CurrentObs._time = CurrentObsTime;
131
132    GETBITS(sv, 6)
133    if (sv < 40)
134      CurrentObs._prn.set('G', sv);
135    else
136      CurrentObs._prn.set('S', sv - 20);
137
138    t_frqObs *frqObs = new t_frqObs;
139    /* L1 */
140    GETBITS(code, 1);
141    (code) ?
142        frqObs->_rnxType2ch.assign("1W") : frqObs->_rnxType2ch.assign("1C");
143    GETBITS(l1range, 24);
144    GETBITSSIGN(i, 20);
145    if ((i & ((1 << 20) - 1)) != 0x80000) {
146      frqObs->_code = l1range * 0.02;
147      frqObs->_phase = (l1range * 0.02 + i * 0.0005) / GPS_WAVELENGTH_L1;
148      frqObs->_codeValid = frqObs->_phaseValid = true;
149    }
150    GETBITS(i, 7);
151    frqObs->_lockTime = lti2sec(type,i);
152    frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0 && frqObs->_phaseValid);
153    frqObs->_slipCounter = i;
154    if (type == 1002 || type == 1004) {
155      GETBITS(amb, 8);
156      if (amb) {
157        frqObs->_code += amb * 299792.458;
158        frqObs->_phase += (amb * 299792.458) / GPS_WAVELENGTH_L1;
159      }
160      GETBITS(i, 8);
161      if (i) {
162        frqObs->_snr = i * 0.25;
163        frqObs->_snrValid = true;
164      }
165    }
166    CurrentObs._obs.push_back(frqObs);
167    if (type == 1003 || type == 1004) {
168      frqObs = new t_frqObs;
169      /* L2 */
170      GETBITS(code, 2);
171      switch (code) {
172        case 3:
173          frqObs->_rnxType2ch.assign("2W"); /* or "2Y"? */
174          break;
175        case 2:
176          frqObs->_rnxType2ch.assign("2W");
177          break;
178        case 1:
179          frqObs->_rnxType2ch.assign("2P");
180          break;
181        case 0:
182          frqObs->_rnxType2ch.assign("2X"); /* or "2S" or "2L"? */
183          break;
184      }
185      GETBITSSIGN(i, 14);
186      if ((i & ((1 << 14) - 1)) != 0x2000) {
187        frqObs->_code = l1range * 0.02 + i * 0.02 + amb * 299792.458;
188        frqObs->_codeValid = true;
189      }
190      GETBITSSIGN(i, 20);
191      if ((i & ((1 << 20) - 1)) != 0x80000) {
192        frqObs->_phase = (l1range * 0.02 + i * 0.0005 + amb * 299792.458)
193            / GPS_WAVELENGTH_L2;
194        frqObs->_phaseValid = true;
195      }
196      GETBITS(i, 7);
197      frqObs->_lockTime = lti2sec(type,i);
198      frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0 && frqObs->_phaseValid);
199      frqObs->_slipCounter = i;
200      if (type == 1004) {
201        GETBITS(i, 8);
202        if (i) {
203          frqObs->_snr = i * 0.25;
204          frqObs->_snrValid = true;
205        }
206      }
207      CurrentObs._obs.push_back(frqObs);
208    }
209    _CurrentObsList.push_back(CurrentObs);
210  }
211
212  if (!syncf) {
213    decoded = true;
214    _obsList.append(_CurrentObsList);
215    _CurrentTime.reset();
216    _CurrentObsList.clear();
217  }
218  return decoded;
219}
220
221#define RTCM3_MSM_NUMSIG      32
222#define RTCM3_MSM_NUMSAT      64
223#define RTCM3_MSM_NUMCELLS    96 /* arbitrary limit */
224
225/**
226 * Frequency numbers of GLONASS with an offset of 100 to detect unset values.
227 * Gets filled by ephemeris and data blocks and shared between different streams.
228 */
229static int GLOFreq[RTCM3_MSM_NUMSAT];
230
231/*
232 * Storage structure to store frequency and RINEX ID assignment for MSM
233 * message */
234struct CodeData {
235  double wl;
236  const char *code; /* currently unused */
237};
238
239/** MSM signal types for GPS and SBAS */
240static struct CodeData gps[RTCM3_MSM_NUMSIG] = {
241        {0.0, 0},
242        {GPS_WAVELENGTH_L1, "1C"},
243        {GPS_WAVELENGTH_L1, "1P"},
244        {GPS_WAVELENGTH_L1, "1W"},
245        {0.0, 0},
246        {0.0, 0},
247        {0.0, 0},
248        {GPS_WAVELENGTH_L2, "2C"},
249        {GPS_WAVELENGTH_L2, "2P"},
250        {GPS_WAVELENGTH_L2, "2W"},
251        {0.0, 0},
252        {0.0, 0},
253        {0.0, 0},
254        {0.0, 0},
255        {GPS_WAVELENGTH_L2, "2S"},
256        {GPS_WAVELENGTH_L2, "2L"},
257        {GPS_WAVELENGTH_L2, "2X"},
258        {0.0, 0},
259        {0.0, 0},
260        {0.0, 0},
261        {0.0, 0},
262        {GPS_WAVELENGTH_L5, "5I"},
263        {GPS_WAVELENGTH_L5, "5Q"},
264        {GPS_WAVELENGTH_L5, "5X"},
265        {0.0, 0},
266        {0.0, 0},
267        {0.0, 0},
268        {0.0, 0},
269        {0.0, 0},
270        {GPS_WAVELENGTH_L1, "1S"},
271        {GPS_WAVELENGTH_L1, "1L"},
272        {GPS_WAVELENGTH_L1, "1X"}
273    };
274
275/**
276 * MSM signal types for GLONASS
277 *
278 * NOTE: Uses 0.0, 1.0 for wavelength as sat index dependence is done later!
279 */
280static struct CodeData glo[RTCM3_MSM_NUMSIG] = {
281        {0.0, 0},
282        {0.0, "1C"},
283        {0.0, "1P"},
284        {0.0, 0},
285        {0.0, 0},
286        {0.0, 0},
287        {0.0, 0},
288        {1.0, "2C"},
289        {1.0, "2P"},
290        {GLO_WAVELENGTH_L1a, "4A"},
291        {GLO_WAVELENGTH_L1a, "4B"},
292        {GLO_WAVELENGTH_L1a, "4X"},
293        {GLO_WAVELENGTH_L2a, "6A"},
294        {GLO_WAVELENGTH_L2a, "6B"},
295        {GLO_WAVELENGTH_L2a, "6X"},
296        {GLO_WAVELENGTH_L3,  "3I"},
297        {GLO_WAVELENGTH_L3,  "3Q"},
298        {GLO_WAVELENGTH_L3,  "3X"},
299        {0.0, 0},
300        {0.0, 0},
301        {0.0, 0},
302        {0.0, 0},
303        {0.0, 0},
304        {0.0, 0},
305        {0.0, 0},
306        {0.0, 0},
307        {0.0, 0},
308        {0.0, 0},
309        {0.0, 0},
310        {0.0, 0},
311        {0.0, 0},
312        {0.0, 0}
313    };
314
315/** MSM signal types for Galileo */
316static struct CodeData gal[RTCM3_MSM_NUMSIG] = {
317        {0.0, 0},
318        {GAL_WAVELENGTH_E1, "1C"},
319        {GAL_WAVELENGTH_E1, "1A"},
320        {GAL_WAVELENGTH_E1, "1B"},
321        {GAL_WAVELENGTH_E1, "1X"},
322        {GAL_WAVELENGTH_E1, "1Z"},
323        {0.0, 0},
324        {GAL_WAVELENGTH_E6, "6C"},
325        {GAL_WAVELENGTH_E6, "6A"},
326        {GAL_WAVELENGTH_E6, "6B"},
327        {GAL_WAVELENGTH_E6, "6X"},
328        {GAL_WAVELENGTH_E6, "6Z"},
329        {0.0, 0},
330        {GAL_WAVELENGTH_E5B, "7I"},
331        {GAL_WAVELENGTH_E5B, "7Q"},
332        {GAL_WAVELENGTH_E5B, "7X"},
333        {0.0, 0},
334        {GAL_WAVELENGTH_E5AB, "8I"},
335        {GAL_WAVELENGTH_E5AB, "8Q"},
336        {GAL_WAVELENGTH_E5AB, "8X"},
337        {0.0, 0},
338        {GAL_WAVELENGTH_E5A, "5I"},
339        {GAL_WAVELENGTH_E5A, "5Q"},
340        {GAL_WAVELENGTH_E5A, "5X"},
341        {0.0, 0},
342        {0.0, 0},
343        {0.0, 0},
344        {0.0, 0},
345        {0.0, 0},
346        {0.0, 0},
347        {0.0, 0},
348        {0.0, 0}
349    };
350
351/** MSM signal types for QZSS */
352static struct CodeData qzss[RTCM3_MSM_NUMSIG] = {
353        {0.0, 0},
354        {GPS_WAVELENGTH_L1, "1C"},
355        {0.0, 0},
356        {0.0, 0},
357        {0.0, 0},
358        {GPS_WAVELENGTH_L1, "1Z"}, // not defined in RTCM3.3?
359        {0.0, 0},
360        {0.0, 0},
361        {QZSS_WAVELENGTH_L6, "6S"},
362        {QZSS_WAVELENGTH_L6, "6L"},
363        {QZSS_WAVELENGTH_L6, "6X"},
364        {0.0, 0},
365        {0.0, 0},
366        {0.0, 0},
367        {GPS_WAVELENGTH_L2, "2S"},
368        {GPS_WAVELENGTH_L2, "2L"},
369        {GPS_WAVELENGTH_L2, "2X"},
370        {0.0, 0},
371        {0.0, 0},
372        {0.0, 0},
373        {0.0, 0},
374        {GPS_WAVELENGTH_L5, "5I"},
375        {GPS_WAVELENGTH_L5, "5Q"},
376        {GPS_WAVELENGTH_L5, "5X"},
377        {0.0, 0},
378        {0.0, 0},
379        {0.0, 0},
380        {0.0, 0},
381        {0.0, 0},
382        {GPS_WAVELENGTH_L1, "1S"},
383        {GPS_WAVELENGTH_L1, "1L"},
384        {GPS_WAVELENGTH_L1, "1X"}
385    };
386
387/** MSM signal types for Beidou/BDS */
388static struct CodeData bds[RTCM3_MSM_NUMSIG] = {
389        {0.0, 0},
390        {BDS_WAVELENGTH_B1, "2I"},
391        {BDS_WAVELENGTH_B1, "2Q"},
392        {BDS_WAVELENGTH_B1, "2X"},
393        {0.0, 0},
394        {0.0, 0},
395        {0.0, 0},
396        {BDS_WAVELENGTH_B3, "6I"},
397        {BDS_WAVELENGTH_B3, "6Q"},
398        {BDS_WAVELENGTH_B3, "6X"},
399        {0.0, 0},
400        {0.0, 0},
401        {0.0, 0},
402        {BDS_WAVELENGTH_B2, "7I"},
403        {BDS_WAVELENGTH_B2, "7Q"},
404        {BDS_WAVELENGTH_B2, "7X"},
405        {0.0, 0},
406        {0.0, 0},
407        {0.0, 0},
408        {0.0, 0},
409        {0.0, 0},
410        {BDS_WAVELENGTH_B2a, "5D"},
411        {BDS_WAVELENGTH_B2a, "5P"},
412        {BDS_WAVELENGTH_B2a, "5X"},
413        {0.0, 0},
414        {0.0, 0},
415        {0.0, 0},
416        {0.0, 0},
417        {0.0, 0},
418        {BDS_WAVELENGTH_B1C, "1D"},
419        {BDS_WAVELENGTH_B1C, "1P"},
420        {BDS_WAVELENGTH_B1C, "1X"}
421    };
422
423/**
424 * MSM signal types for IRNSS
425 *
426 * NOTE: Uses 0.0, 1.0 for wavelength as sat index dependence is done later!
427 */
428static struct CodeData irn[RTCM3_MSM_NUMSIG] = {
429        {0.0, 0},
430        {0.0, 0},
431        {0.0, 0},
432        {0.0, 0},
433        {0.0, 0},
434        {0.0, 0},
435        {0.0, 0},
436        {IRNSS_WAVELENGTH_S, "9A"},
437        {0.0, 0},
438        {0.0, 0},
439        {0.0, 0},
440        {0.0, 0},
441        {0.0, 0},
442        {0.0, 0},
443        {0.0, 0},
444        {0.0, 0},
445        {0.0, 0},
446        {0.0, 0},
447        {0.0, 0},
448        {0.0, 0},
449        {0.0, 0},
450        {IRNSS_WAVELENGTH_L5, "5A"},
451        {0.0, 0},
452        {0.0, 0},
453        {0.0, 0},
454        {0.0, 0},
455        {0.0, 0},
456        {0.0, 0},
457        {0.0, 0},
458        {0.0, 0},
459        {0.0, 0},
460        {0.0, 0}
461    };
462
463#define UINT64(c) c ## ULL
464
465//
466////////////////////////////////////////////////////////////////////////////
467bool RTCM3Decoder::DecodeRTCM3MSM(unsigned char* data, int size) {
468  bool decoded = false;
469  int type, syncf, i;
470  uint64_t numbits = 0, bitfield = 0;
471
472  data += 3; /* header */
473  size -= 6; /* header + crc */
474
475  GETBITS(type, 12)
476  SKIPBITS(12)
477  /* id */
478  char sys;
479  if      (type >= 1121)
480    sys = 'C';
481  else if (type >= 1111)
482    sys = 'J';
483  else if (type >= 1101)
484    sys = 'S';
485  else if (type >= 1091)
486    sys = 'E';
487  else if (type >= 1081)
488    sys = 'R';
489  else if (type >= 1071)
490    sys = 'G';
491  else if (type >=   21) // test
492    sys = 'I';
493
494  bncTime CurrentObsTime;
495  if (sys == 'C') /* BDS */ {
496    GETBITS(i, 30)
497    CurrentObsTime.setBDS(i);
498  }
499  else if (sys == 'R') /* GLONASS */ {
500    SKIPBITS(3)
501    GETBITS(i, 27)
502    /* tk */
503    CurrentObsTime.setTk(i);
504  }
505  else /* GPS style date */ {
506    GETBITS(i, 30)
507    CurrentObsTime.set(i);
508  }
509  if (_CurrentTime.valid() && CurrentObsTime != _CurrentTime) {
510    decoded = true;
511    _obsList.append(_CurrentObsList);
512    _CurrentObsList.clear();
513  }
514  _CurrentTime = CurrentObsTime;
515
516  GETBITS(syncf, 1)
517  /**
518   * Ignore unknown types except for sync flag
519   *
520   * We actually support types 1-3 in following code, but as they are missing
521   * the full cycles and can't be used later we skip interpretation here already.
522   */
523  if (type <= 1130 && (type % 10) >= 4 && (type % 10) <= 7) {
524    int sigmask, numsat = 0, numsig = 0;
525    uint64_t satmask, cellmask, ui;
526    // satellite data
527    double rrmod[RTCM3_MSM_NUMSAT]; // GNSS sat rough ranges modulo 1 millisecond
528    int    rrint[RTCM3_MSM_NUMSAT]; // number of integer msecs in GNSS sat rough ranges
529    int    rdop[RTCM3_MSM_NUMSAT];  // GNSS sat rough phase range rates
530    int    extsat[RTCM3_MSM_NUMSAT];// extended sat info
531    // signal data
532    int    ll[RTCM3_MSM_NUMCELLS];  // lock time indicator
533    /*int    hc[RTCM3_MSM_NUMCELLS];*/  // half cycle ambiguity indicator
534    double cnr[RTCM3_MSM_NUMCELLS]; // signal cnr
535    double cp[RTCM3_MSM_NUMCELLS];  // fine phase range data
536    double psr[RTCM3_MSM_NUMCELLS]; // fine psr
537    double dop[RTCM3_MSM_NUMCELLS]; // fine phase range rates
538
539    SKIPBITS(3 + 7 + 2 + 2 + 1 + 3)
540    GETBITS64(satmask, RTCM3_MSM_NUMSAT)
541
542    /* http://gurmeetsingh.wordpress.com/2008/08/05/fast-bit-counting-routines/ */
543    for (ui = satmask; ui; ui &= (ui - 1) /* remove rightmost bit */)
544      ++numsat;
545    GETBITS(sigmask, RTCM3_MSM_NUMSIG)
546    for (i = sigmask; i; i &= (i - 1) /* remove rightmost bit */)
547      ++numsig;
548    for (i = 0; i < RTCM3_MSM_NUMSAT; ++i)
549      extsat[i] = 15;
550
551    i = numsat * numsig;
552    GETBITS64(cellmask, (unsigned )i)
553    // satellite data
554    switch (type % 10) {
555      case 1:
556      case 2:
557      case 3:
558        /* partial data, already skipped above, but implemented for future expansion ! */
559        for (int j = numsat; j--;)
560          GETFLOAT(rrmod[j], 10, 1.0 / 1024.0)
561        break;
562      case 4:
563      case 6:
564        for (int j = numsat; j--;)
565          GETBITS(rrint[j], 8)
566        for (int j = numsat; j--;)
567          GETFLOAT(rrmod[j], 10, 1.0 / 1024.0)
568        break;
569      case 5:
570      case 7:
571        for (int j = numsat; j--;)
572          GETBITS(rrint[j], 8)
573        for (int j = numsat; j--;)
574          GETBITS(extsat[j], 4)
575        for (int j = numsat; j--;)
576          GETFLOAT(rrmod[j], 10, 1.0 / 1024.0)
577        for (int j = numsat; j--;)
578          GETBITSSIGN(rdop[j], 14)
579        break;
580    }
581    // signal data
582    int numcells = numsat * numsig;
583    /** Drop anything which exceeds our cell limit. Increase limit definition
584     * when that happens. */
585    if (numcells <= RTCM3_MSM_NUMCELLS) {
586      switch (type % 10) {
587        case 1:
588          for (int count = numcells; count--;)
589            if (cellmask & (UINT64(1) << count))
590              GETFLOATSIGN(psr[count], 15, 1.0 / (1 << 24))
591          break;
592        case 2:
593          for (int count = numcells; count--;)
594            if (cellmask & (UINT64(1) << count))
595              GETFLOATSIGN(cp[count], 22, 1.0 / (1 << 29))
596          for (int count = numcells; count--;)
597            if (cellmask & (UINT64(1) << count))
598              GETBITS(ll[count], 4)
599          for (int count = numcells; count--;)
600            if (cellmask & (UINT64(1) << count))
601              SKIPBITS(1)/*GETBITS(hc[count], 1)*/
602          break;
603        case 3:
604          for (int count = numcells; count--;)
605            if (cellmask & (UINT64(1) << count))
606              GETFLOATSIGN(psr[count], 15, 1.0 / (1 << 24))
607          for (int count = numcells; count--;)
608            if (cellmask & (UINT64(1) << count))
609              GETFLOATSIGN(cp[count], 22, 1.0 / (1 << 29))
610          for (int count = numcells; count--;)
611            if (cellmask & (UINT64(1) << count))
612              GETBITS(ll[count], 4)
613          for (int count = numcells; count--;)
614            if (cellmask & (UINT64(1) << count))
615              SKIPBITS(1)/*GETBITS(hc[count], 1)*/
616          break;
617        case 4:
618          for (int count = numcells; count--;)
619            if (cellmask & (UINT64(1) << count))
620              GETFLOATSIGN(psr[count], 15, 1.0 / (1 << 24))
621          for (int count = numcells; count--;)
622            if (cellmask & (UINT64(1) << count))
623              GETFLOATSIGN(cp[count], 22, 1.0 / (1 << 29))
624          for (int count = numcells; count--;)
625            if (cellmask & (UINT64(1) << count))
626              GETBITS(ll[count], 4)
627          for (int count = numcells; count--;)
628            if (cellmask & (UINT64(1) << count))
629              SKIPBITS(1)/*GETBITS(hc[count], 1)*/
630          for (int count = numcells; count--;)
631            if (cellmask & (UINT64(1) << count))
632              GETBITS(cnr[count], 6)
633          break;
634        case 5:
635          for (int count = numcells; count--;)
636            if (cellmask & (UINT64(1) << count))
637              GETFLOATSIGN(psr[count], 15, 1.0 / (1 << 24))
638          for (int count = numcells; count--;)
639            if (cellmask & (UINT64(1) << count))
640              GETFLOATSIGN(cp[count], 22, 1.0 / (1 << 29))
641          for (int count = numcells; count--;)
642            if (cellmask & (UINT64(1) << count))
643              GETBITS(ll[count], 4)
644          for (int count = numcells; count--;)
645            if (cellmask & (UINT64(1) << count))
646              SKIPBITS(1)/*GETBITS(hc[count], 1)*/
647          for (int count = numcells; count--;)
648            if (cellmask & (UINT64(1) << count))
649              GETFLOAT(cnr[count], 6, 1.0)
650          for (int count = numcells; count--;)
651            if (cellmask & (UINT64(1) << count))
652              GETFLOATSIGN(dop[count], 15, 0.0001)
653          break;
654        case 6:
655          for (int count = numcells; count--;)
656            if (cellmask & (UINT64(1) << count))
657              GETFLOATSIGN(psr[count], 20, 1.0 / (1 << 29))
658          for (int count = numcells; count--;)
659            if (cellmask & (UINT64(1) << count))
660              GETFLOATSIGN(cp[count], 24, 1.0 / (1U << 31))
661          for (int count = numcells; count--;)
662            if (cellmask & (UINT64(1) << count))
663              GETBITS(ll[count], 10)
664          for (int count = numcells; count--;)
665            if (cellmask & (UINT64(1) << count))
666              SKIPBITS(1)/*GETBITS(hc[count], 1)*/
667          for (int count = numcells; count--;)
668            if (cellmask & (UINT64(1) << count))
669              GETFLOAT(cnr[count], 10, 1.0 / (1 << 4))
670          break;
671        case 7:
672          for (int count = numcells; count--;)
673            if (cellmask & (UINT64(1) << count))
674              GETFLOATSIGN(psr[count], 20, 1.0 / (1 << 29))
675          for (int count = numcells; count--;)
676            if (cellmask & (UINT64(1) << count))
677              GETFLOATSIGN(cp[count], 24, 1.0 / (1U << 31))
678          for (int count = numcells; count--;)
679            if (cellmask & (UINT64(1) << count))
680              GETBITS(ll[count], 10)
681          for (int count = numcells; count--;)
682            if (cellmask & (UINT64(1) << count))
683              SKIPBITS(1)/*GETBITS(hc[count], 1)*/
684          for (int count = numcells; count--;)
685            if (cellmask & (UINT64(1) << count))
686              GETFLOAT(cnr[count], 10, 1.0 / (1 << 4))
687          for (int count = numcells; count--;)
688            if (cellmask & (UINT64(1) << count))
689              GETFLOATSIGN(dop[count], 15, 0.0001)
690          break;
691      }
692      i = RTCM3_MSM_NUMSAT;
693      int j = -1;
694      t_satObs CurrentObs;
695      for (int count = numcells; count--;) {
696        while (j >= 0 && !(sigmask & (1 << --j)))
697          ;
698        if (j < 0) {
699          while (!(satmask & (UINT64(1) << (--i))))
700            /* next satellite */
701            ;
702          if (CurrentObs._obs.size() > 0)
703            _CurrentObsList.push_back(CurrentObs);
704          CurrentObs.clear();
705          CurrentObs._time = CurrentObsTime;
706          if (sys == 'S')
707            CurrentObs._prn.set(sys, 20 - 1 + RTCM3_MSM_NUMSAT - i);
708          else
709            CurrentObs._prn.set(sys, RTCM3_MSM_NUMSAT - i);
710          j = RTCM3_MSM_NUMSIG;
711          while (!(sigmask & (1 << --j)))
712            ;
713          --numsat;
714        }
715        if (cellmask & (UINT64(1) << count)) {
716          struct CodeData cd = {0.0, 0};
717          switch (sys) {
718            case 'J':
719              cd = qzss[RTCM3_MSM_NUMSIG - j - 1];
720              break;
721            case 'C':
722              cd = bds[RTCM3_MSM_NUMSIG - j - 1];
723              break;
724            case 'G':
725            case 'S':
726              cd = gps[RTCM3_MSM_NUMSIG - j - 1];
727              break;
728            case 'R':
729              cd = glo[RTCM3_MSM_NUMSIG - j - 1];
730              {
731                int k = GLOFreq[RTCM3_MSM_NUMSAT - i - 1];
732                if (extsat[numsat] < 14) { // channel number is available as extended info for MSM5/7
733                  k = GLOFreq[RTCM3_MSM_NUMSAT - i - 1] = 100 + extsat[numsat] - 7;
734                }
735                if (k) {
736                  if      (cd.wl == 0.0) {
737                    cd.wl = GLO_WAVELENGTH_L1(k - 100);
738                  }
739                  else if (cd.wl == 1.0) {
740                    cd.wl = GLO_WAVELENGTH_L2(k - 100);
741                  }
742                }
743                else if (!k && cd.wl <= 1) {
744                  cd.code = 0;
745                }
746              }
747              break;
748            case 'E':
749              cd = gal[RTCM3_MSM_NUMSIG - j - 1];
750              break;
751            case 'I':
752              cd = irn[RTCM3_MSM_NUMSIG - j - 1];
753              break;             
754          }
755          if (cd.code) {
756            t_frqObs *frqObs = new t_frqObs;
757            frqObs->_rnxType2ch.assign(cd.code);
758
759            switch (type % 10) {
760              case 1:
761                if (psr[count] > -1.0 / (1 << 10)) {
762                  frqObs->_code = psr[count] * LIGHTSPEED / 1000.0
763                      + (rrmod[numsat]) * LIGHTSPEED / 1000.0;
764                  frqObs->_codeValid = true;
765                }
766                break;
767              case 2:
768                if (cp[count] > -1.0 / (1 << 8)) {
769                  frqObs->_phase = cp[count] * LIGHTSPEED / 1000.0 / cd.wl
770                      + (rrmod[numsat]) * LIGHTSPEED / 1000.0 / cd.wl;
771                  frqObs->_phaseValid = true;
772                  frqObs->_lockTime = lti2sec(type,ll[count]);
773                  frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0);
774                  frqObs->_slipCounter = ll[count];
775                }
776                break;
777              case 3:
778                if (psr[count] > -1.0 / (1 << 10)) {
779                  frqObs->_code = psr[count] * LIGHTSPEED / 1000.0
780                      + (rrmod[numsat]) * LIGHTSPEED / 1000.0;
781                  frqObs->_codeValid = true;
782                }
783
784                if (cp[count] > -1.0 / (1 << 8)) {
785                  frqObs->_phase = cp[count] * LIGHTSPEED / 1000.0 / cd.wl
786                      + rrmod[numsat] * LIGHTSPEED / 1000.0 / cd.wl;
787                  frqObs->_phaseValid = true;
788                  frqObs->_lockTime = lti2sec(type,ll[count]);
789                  frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0);
790                  frqObs->_slipCounter = ll[count];
791                }
792                break;
793              case 4:
794                if (psr[count] > -1.0 / (1 << 10)) {
795                  frqObs->_code = psr[count] * LIGHTSPEED / 1000.0
796                      + (rrmod[numsat] + rrint[numsat]) * LIGHTSPEED / 1000.0;
797                  frqObs->_codeValid = true;
798                }
799
800                if (cp[count] > -1.0 / (1 << 8)) {
801                  frqObs->_phase = cp[count] * LIGHTSPEED / 1000.0 / cd.wl
802                                 + (rrmod[numsat] +  rrint[numsat]) * LIGHTSPEED / 1000.0 / cd.wl;
803                  frqObs->_phaseValid = true;
804                  frqObs->_lockTime = lti2sec(type,ll[count]);
805                  frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0);
806                  frqObs->_slipCounter = ll[count];
807                }
808
809                frqObs->_snr = cnr[count];
810                frqObs->_snrValid = true;
811                break;
812              case 5:
813                if (psr[count] > -1.0 / (1 << 10)) {
814                  frqObs->_code = psr[count] * LIGHTSPEED / 1000.0
815                      + (rrmod[numsat] + rrint[numsat]) * LIGHTSPEED / 1000.0;
816                  frqObs->_codeValid = true;
817                }
818
819                if (cp[count] > -1.0 / (1 << 8)) {
820                  frqObs->_phase = cp[count] * LIGHTSPEED / 1000.0 / cd.wl
821                                 + (rrmod[numsat] + rrint[numsat]) * LIGHTSPEED / 1000.0 / cd.wl;
822                  frqObs->_phaseValid = true;
823                  frqObs->_lockTime = lti2sec(type,ll[count]);
824                  frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0);
825                  frqObs->_slipCounter = ll[count];
826                }
827
828                frqObs->_snr = cnr[count];
829                frqObs->_snrValid = true;
830
831                if (dop[count] > -1.6384) {
832                  frqObs->_doppler = -(dop[count] + rdop[numsat]) / cd.wl;
833                  frqObs->_dopplerValid = true;
834                }
835                break;
836              case 6:
837                if (psr[count] > -1.0 / (1 << 10)) {
838                  frqObs->_code = psr[count] * LIGHTSPEED / 1000.0
839                      + (rrmod[numsat] + rrint[numsat]) * LIGHTSPEED / 1000.0;
840                  frqObs->_codeValid = true;
841                }
842
843                if (cp[count] > -1.0 / (1 << 8)) {
844                  frqObs->_phase = cp[count] * LIGHTSPEED / 1000.0 / cd.wl
845                                 + (rrmod[numsat] + rrint[numsat]) * LIGHTSPEED / 1000.0 / cd.wl;
846                  frqObs->_phaseValid = true;
847                  frqObs->_lockTime = lti2sec(type,ll[count]);
848                  frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0);
849                  frqObs->_slipCounter = ll[count];
850                }
851
852                frqObs->_snr = cnr[count];
853                frqObs->_snrValid = true;
854                break;
855              case 7:
856                if (psr[count] > -1.0 / (1 << 10)) {
857                  frqObs->_code = psr[count] * LIGHTSPEED / 1000.0
858                      + (rrmod[numsat] + rrint[numsat]) * LIGHTSPEED / 1000.0;
859                  frqObs->_codeValid = true;
860                }
861
862                if (cp[count] > -1.0 / (1 << 8)) {
863                  frqObs->_phase = cp[count] * LIGHTSPEED / 1000.0 / cd.wl
864                                 + (rrmod[numsat] + rrint[numsat]) * LIGHTSPEED / 1000.0 / cd.wl;
865                  frqObs->_phaseValid = true;
866                  frqObs->_lockTime = lti2sec(type,ll[count]);
867                  frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0);
868                  frqObs->_slipCounter = ll[count];
869                }
870
871                frqObs->_snr = cnr[count];
872                frqObs->_snrValid = true;
873
874                if (dop[count] > -1.6384) {
875                  frqObs->_doppler = -(dop[count] + rdop[numsat]) / cd.wl;
876                  frqObs->_dopplerValid = true;
877                }
878                break;
879            }
880            CurrentObs._obs.push_back(frqObs);
881          }
882        }
883      }
884      if (CurrentObs._obs.size() > 0) {
885        _CurrentObsList.push_back(CurrentObs);
886      }
887    }
888  }
889  else if ((type % 10) < 3) {
890    emit(newMessage(QString("%1: Block %2 contain partial data! Ignored!")
891        .arg(_staID).arg(type).toAscii(), true));
892  }
893  if (!syncf) {
894    decoded = true;
895    _obsList.append(_CurrentObsList);
896    _CurrentTime.reset();
897    _CurrentObsList.clear();
898  }
899  return decoded;
900}
901
902//
903////////////////////////////////////////////////////////////////////////////
904bool RTCM3Decoder::DecodeRTCM3GLONASS(unsigned char* data, int size) {
905  bool decoded = false;
906  bncTime CurrentObsTime;
907  int i, numsats, syncf, type;
908  uint64_t numbits = 0, bitfield = 0;
909
910  data += 3; /* header */
911  size -= 6; /* header + crc */
912
913  GETBITS(type, 12)
914  SKIPBITS(12)
915  /* id */
916  GETBITS(i, 27)
917  /* tk */
918
919  CurrentObsTime.setTk(i);
920  if (_CurrentTime.valid() && CurrentObsTime != _CurrentTime) {
921    decoded = true;
922    _obsList.append(_CurrentObsList);
923    _CurrentObsList.clear();
924  }
925  _CurrentTime = CurrentObsTime;
926
927  GETBITS(syncf, 1)
928  /* sync */
929  GETBITS(numsats, 5)
930  SKIPBITS(4)
931  /* smind, smint */
932
933  while (numsats--) {
934    int sv, code, l1range, amb = 0, freq;
935    t_satObs CurrentObs;
936    CurrentObs._time = CurrentObsTime;
937
938    GETBITS(sv, 6)
939    CurrentObs._prn.set('R', sv);
940    GETBITS(code, 1)
941    GETBITS(freq, 5)
942    GLOFreq[sv - 1] = 100 + freq - 7; /* store frequency for other users (MSM) */
943
944    t_frqObs *frqObs = new t_frqObs;
945    /* L1 */
946    (code) ?
947        frqObs->_rnxType2ch.assign("1P") : frqObs->_rnxType2ch.assign("1C");
948    GETBITS(l1range, 25);
949    GETBITSSIGN(i, 20);
950    if ((i & ((1 << 20) - 1)) != 0x80000) {
951      frqObs->_code = l1range * 0.02;
952      frqObs->_phase = (l1range * 0.02 + i * 0.0005)
953          / GLO_WAVELENGTH_L1(freq - 7);
954      frqObs->_codeValid = frqObs->_phaseValid = true;
955    }
956    GETBITS(i, 7);
957    frqObs->_lockTime = lti2sec(type,i);
958    frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0 && frqObs->_phaseValid);
959    frqObs->_slipCounter = i;
960    if (type == 1010 || type == 1012) {
961      GETBITS(amb, 7);
962      if (amb) {
963        frqObs->_code += amb * 599584.916;
964        frqObs->_phase += (amb * 599584.916) / GLO_WAVELENGTH_L1(freq - 7);
965      }
966      GETBITS(i, 8);
967      if (i) {
968        frqObs->_snr = i * 0.25;
969        frqObs->_snrValid = true;
970      }
971    }
972    CurrentObs._obs.push_back(frqObs);
973    if (type == 1011 || type == 1012) {
974      frqObs = new t_frqObs;
975      /* L2 */
976      GETBITS(code, 2);
977      switch (code) {
978        case 3:
979          frqObs->_rnxType2ch.assign("2P");
980          break;
981        case 2:
982          frqObs->_rnxType2ch.assign("2P");
983          break;
984        case 1:
985          frqObs->_rnxType2ch.assign("2P");
986          break;
987        case 0:
988          frqObs->_rnxType2ch.assign("2C");
989          break;
990      }
991      GETBITSSIGN(i, 14);
992      if ((i & ((1 << 14) - 1)) != 0x2000) {
993        frqObs->_code = l1range * 0.02 + i * 0.02 + amb * 599584.916;
994        frqObs->_codeValid = true;
995      }
996      GETBITSSIGN(i, 20);
997      if ((i & ((1 << 20) - 1)) != 0x80000) {
998        frqObs->_phase = (l1range * 0.02 + i * 0.0005 + amb * 599584.916)
999            / GLO_WAVELENGTH_L2(freq - 7);
1000        frqObs->_phaseValid = true;
1001      }
1002      GETBITS(i, 7);
1003      frqObs->_lockTime = lti2sec(type,i);
1004      frqObs->_lockTimeValid = (frqObs->_lockTime >= 0.0 && frqObs->_phaseValid);
1005      frqObs->_slipCounter = i;
1006      if (type == 1012) {
1007        GETBITS(i, 8);
1008        if (i) {
1009          frqObs->_snr = i * 0.25;
1010          frqObs->_snrValid = true;
1011        }
1012      }
1013      CurrentObs._obs.push_back(frqObs);
1014    }
1015    _CurrentObsList.push_back(CurrentObs);
1016  }
1017  if (!syncf) {
1018    decoded = true;
1019    _obsList.append(_CurrentObsList);
1020    _CurrentTime.reset();
1021    _CurrentObsList.clear();
1022  }
1023  return decoded;
1024}
1025
1026//
1027////////////////////////////////////////////////////////////////////////////
1028bool RTCM3Decoder::DecodeGPSEphemeris(unsigned char* data, int size) {
1029  bool decoded = false;
1030
1031  if (size == 67) {
1032    t_ephGPS eph;
1033    int i, week;
1034    uint64_t numbits = 0, bitfield = 0;
1035
1036    data += 3; /* header */
1037    size -= 6; /* header + crc */
1038    SKIPBITS(12)
1039
1040    eph._receptDateTime = currentDateAndTimeGPS();
1041
1042    GETBITS(i, 6)
1043    eph._prn.set('G', i);
1044    GETBITS(week, 10)
1045    GETBITS(i, 4)
1046    eph._ura = accuracyFromIndex(i, eph.type());
1047    GETBITS(eph._L2Codes, 2)
1048    GETFLOATSIGN(eph._IDOT, 14, R2R_PI/(double)(1<<30)/(double)(1<<13))
1049    GETBITS(eph._IODE, 8)
1050    GETBITS(i, 16)
1051    i <<= 4;
1052    eph._TOC.set(i * 1000);
1053    GETFLOATSIGN(eph._clock_driftrate, 8, 1.0 / (double )(1 << 30) / (double )(1 << 25))
1054    GETFLOATSIGN(eph._clock_drift,    16, 1.0 / (double )(1 << 30) / (double )(1 << 13))
1055    GETFLOATSIGN(eph._clock_bias,     22, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1056
1057    GETBITS(eph._IODC, 10)
1058    GETFLOATSIGN(eph._Crs, 16, 1.0 / (double )(1 << 5))
1059    GETFLOATSIGN(eph._Delta_n, 16, R2R_PI/(double)(1<<30)/(double)(1<<13))
1060    GETFLOATSIGN(eph._M0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1061    GETFLOATSIGN(eph._Cuc, 16, 1.0 / (double )(1 << 29))
1062    GETFLOAT(eph._e, 32, 1.0 / (double )(1 << 30) / (double )(1 << 3))
1063    GETFLOATSIGN(eph._Cus, 16, 1.0 / (double )(1 << 29))
1064    GETFLOAT(eph._sqrt_A, 32, 1.0 / (double )(1 << 19))
1065    GETBITS(i, 16)
1066    i <<= 4;
1067    eph._TOEsec = i;
1068    bncTime t;
1069    t.set(i * 1000);
1070    eph._TOEweek = t.gpsw();
1071    int numOfRollOvers = int(floor(t.gpsw()/1024.0));
1072    week += (numOfRollOvers * 1024);
1073    /* week from HOW, differs from TOC, TOE week, we use adapted value instead */
1074    if (eph._TOEweek > week + 1 || eph._TOEweek < week - 1) /* invalid week */
1075      return false;
1076    GETFLOATSIGN(eph._Cic, 16, 1.0 / (double )(1 << 29))
1077    GETFLOATSIGN(eph._OMEGA0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1078    GETFLOATSIGN(eph._Cis, 16, 1.0 / (double )(1 << 29))
1079    GETFLOATSIGN(eph._i0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1080    GETFLOATSIGN(eph._Crc, 16, 1.0 / (double )(1 << 5))
1081    GETFLOATSIGN(eph._omega, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1082    GETFLOATSIGN(eph._OMEGADOT, 24, R2R_PI/(double)(1<<30)/(double)(1<<13))
1083    GETFLOATSIGN(eph._TGD, 8, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1084    GETBITS(eph._health, 6)
1085    GETBITS(eph._L2PFlag, 1)
1086    GETBITS(eph._fitInterval, 1)
1087    eph._TOT = 0.9999e9;
1088
1089    emit newGPSEph(eph);
1090    decoded = true;
1091  }
1092  return decoded;
1093}
1094
1095//
1096////////////////////////////////////////////////////////////////////////////
1097bool RTCM3Decoder::DecodeGLONASSEphemeris(unsigned char* data, int size) {
1098  bool decoded = false;
1099
1100  if (size == 51) {
1101    t_ephGlo eph;
1102    int sv, i, tk;
1103    uint64_t numbits = 0, bitfield = 0;
1104
1105    data += 3; /* header */
1106    size -= 6; /* header + crc */
1107    SKIPBITS(12)
1108
1109    eph._receptDateTime = currentDateAndTimeGPS();
1110
1111    GETBITS(sv, 6)
1112    eph._prn.set('R', sv);
1113
1114    GETBITS(i, 5)
1115    eph._frequency_number = i - 7;
1116    GETBITS(eph._almanac_health, 1) /* almanac healthy */
1117    GETBITS(eph._almanac_health_availablility_indicator, 1) /* almanac health ok */
1118    GETBITS(eph._P1, 2) /*  P1 */
1119    GETBITS(i, 5)
1120    tk = i * 60 * 60;
1121    GETBITS(i, 6)
1122    tk += i * 60;
1123    GETBITS(i, 1)
1124    tk += i * 30;
1125       eph._tki = tk - 3*60*60;
1126    if(eph._tki < 0.0) {
1127      eph._tki += 86400.0;
1128    }
1129    GETBITS(eph._health, 1) /* MSB of Bn*/
1130    GETBITS(eph._P2, 1)  /* P2 */
1131    GETBITS(i, 7)
1132    eph._TOC.setTk(i * 15 * 60 * 1000); /* tb */
1133
1134    GETFLOATSIGNM(eph._x_velocity, 24, 1.0 / (double )(1 << 20))
1135    GETFLOATSIGNM(eph._x_pos, 27, 1.0 / (double )(1 << 11))
1136    GETFLOATSIGNM(eph._x_acceleration, 5, 1.0 / (double )(1 << 30))
1137    GETFLOATSIGNM(eph._y_velocity, 24, 1.0 / (double )(1 << 20))
1138    GETFLOATSIGNM(eph._y_pos, 27, 1.0 / (double )(1 << 11))
1139    GETFLOATSIGNM(eph._y_acceleration, 5, 1.0 / (double )(1 << 30))
1140    GETFLOATSIGNM(eph._z_velocity, 24, 1.0 / (double )(1 << 20))
1141    GETFLOATSIGNM(eph._z_pos, 27, 1.0 / (double )(1 << 11))
1142    GETFLOATSIGNM(eph._z_acceleration, 5, 1.0 / (double )(1 << 30))
1143    GETBITS(eph._P3, 1)    /* P3 */
1144    GETFLOATSIGNM(eph._gamma, 11, 1.0 / (double )(1 << 30) / (double )(1 << 10))
1145    GETBITS(eph._M_P, 2) /* GLONASS-M P, */
1146    GETBITS(eph._M_l3, 1) /*GLONASS-M ln (third string) */
1147    GETFLOATSIGNM(eph._tau, 22, 1.0 / (double )(1 << 30)) /* GLONASS tau n(tb) */
1148    GETFLOATSIGNM(eph._M_delta_tau, 5, 1.0 / (double )(1 << 30))  /* GLONASS-M delta tau n(tb) */
1149    GETBITS(eph._E, 5)
1150    GETBITS(eph._M_P4, 1) /* GLONASS-M P4 */
1151    GETBITS(eph._M_FT, 4) /* GLONASS-M Ft */
1152    GETBITS(eph._M_NT, 11) /* GLONASS-M Nt */
1153    GETBITS(eph._M_M, 2) /* GLONASS-M M */
1154    GETBITS(eph._additional_data_availability, 1) /* GLONASS-M The Availability of Additional Data */
1155    GETBITS(eph._NA, 11) /* GLONASS-M Na */
1156    GETFLOATSIGNM(eph._tauC, 32, 1.0/(double)(1<<30)/(double)(1<<1)) /* GLONASS tau c */
1157    GETBITS(eph._M_N4, 5) /* GLONASS-M N4 */
1158    GETFLOATSIGNM(eph._M_tau_GPS, 22, 1.0/(double)(1<<30)) /* GLONASS-M tau GPS */
1159    GETBITS(eph._M_l5, 1) /* GLONASS-M ln (fifth string) */
1160
1161    unsigned year, month, day;
1162    eph._TOC.civil_date(year, month, day);
1163    eph._gps_utc = gnumleap(year, month, day);
1164    eph._tt = eph._TOC;
1165
1166    eph._xv(1) = eph._x_pos * 1.e3;
1167    eph._xv(2) = eph._y_pos * 1.e3;
1168    eph._xv(3) = eph._z_pos * 1.e3;
1169    eph._xv(4) = eph._x_velocity * 1.e3;
1170    eph._xv(5) = eph._y_velocity * 1.e3;
1171    eph._xv(6) = eph._z_velocity * 1.e3;
1172
1173    GLOFreq[sv - 1] = 100 + eph._frequency_number ; /* store frequency for other users (MSM) */
1174    _gloFrq = QString("%1 %2").arg(eph._prn.toString().c_str()).arg(eph._frequency_number, 2, 'f', 0);
1175
1176    emit newGlonassEph(eph);
1177    decoded = true;
1178  }
1179  return decoded;
1180}
1181
1182//
1183////////////////////////////////////////////////////////////////////////////
1184bool RTCM3Decoder::DecodeQZSSEphemeris(unsigned char* data, int size) {
1185  bool decoded = false;
1186
1187  if (size == 67) {
1188    t_ephGPS eph;
1189    int i, week;
1190    uint64_t numbits = 0, bitfield = 0;
1191
1192    data += 3; /* header */
1193    size -= 6; /* header + crc */
1194    SKIPBITS(12)
1195
1196    eph._receptDateTime = currentDateAndTimeGPS();
1197
1198    GETBITS(i, 4)
1199    eph._prn.set('J', i);
1200
1201    GETBITS(i, 16)
1202    i <<= 4;
1203    eph._TOC.set(i * 1000);
1204
1205    GETFLOATSIGN(eph._clock_driftrate, 8, 1.0 / (double )(1 << 30) / (double )(1 << 25))
1206    GETFLOATSIGN(eph._clock_drift,    16, 1.0 / (double )(1 << 30) / (double )(1 << 13))
1207    GETFLOATSIGN(eph._clock_bias,     22, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1208
1209    GETBITS(eph._IODE, 8)
1210    GETFLOATSIGN(eph._Crs, 16, 1.0 / (double )(1 << 5))
1211    GETFLOATSIGN(eph._Delta_n, 16, R2R_PI/(double)(1<<30)/(double)(1<<13))
1212    GETFLOATSIGN(eph._M0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1213    GETFLOATSIGN(eph._Cuc, 16, 1.0 / (double )(1 << 29))
1214    GETFLOAT(eph._e, 32, 1.0 / (double )(1 << 30) / (double )(1 << 3))
1215    GETFLOATSIGN(eph._Cus, 16, 1.0 / (double )(1 << 29))
1216    GETFLOAT(eph._sqrt_A, 32, 1.0 / (double )(1 << 19))
1217    GETBITS(i, 16)
1218    i <<= 4;
1219    eph._TOEsec = i;
1220    bncTime t;
1221    t.set(i*1000);
1222    eph._TOEweek = t.gpsw();
1223    GETFLOATSIGN(eph._Cic, 16, 1.0 / (double )(1 << 29))
1224    GETFLOATSIGN(eph._OMEGA0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1225    GETFLOATSIGN(eph._Cis, 16, 1.0 / (double )(1 << 29))
1226    GETFLOATSIGN(eph._i0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1227    GETFLOATSIGN(eph._Crc, 16, 1.0 / (double )(1 << 5))
1228    GETFLOATSIGN(eph._omega, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1229    GETFLOATSIGN(eph._OMEGADOT, 24, R2R_PI/(double)(1<<30)/(double)(1<<13))
1230    GETFLOATSIGN(eph._IDOT, 14, R2R_PI/(double)(1<<30)/(double)(1<<13))
1231    GETBITS(eph._L2Codes, 2)
1232    GETBITS(week, 10)
1233    int numOfRollOvers = int(floor(t.gpsw()/1024.0));
1234    week += (numOfRollOvers * 1024);
1235    /* week from HOW, differs from TOC, TOE week, we use adapted value instead */
1236    if (eph._TOEweek > week + 1 || eph._TOEweek < week - 1) /* invalid week */
1237      return false;
1238
1239    GETBITS(i, 4)
1240    if (i <= 6)
1241      eph._ura = ceil(10.0 * pow(2.0, 1.0 + i / 2.0)) / 10.0;
1242    else
1243      eph._ura = ceil(10.0 * pow(2.0, i / 2.0)) / 10.0;
1244    GETBITS(eph._health, 6)
1245    GETFLOATSIGN(eph._TGD, 8, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1246    GETBITS(eph._IODC, 10)
1247    GETBITS(eph._fitInterval, 1)
1248    eph._TOT = 0.9999e9;
1249
1250    emit newGPSEph(eph);
1251    decoded = true;
1252  }
1253  return decoded;
1254}
1255
1256//
1257////////////////////////////////////////////////////////////////////////////
1258bool RTCM3Decoder::DecodeIRNSSEphemeris(unsigned char* data, int size) {
1259  bool decoded = false;
1260
1261  if (size == 67) {
1262    t_ephGPS eph;
1263    int i, week, L5Flag, SFlag;
1264    uint64_t numbits = 0, bitfield = 0;
1265
1266    data += 3; /* header */
1267    size -= 6; /* header + crc */
1268    SKIPBITS(12)
1269
1270    eph._receptDateTime = currentDateAndTimeGPS();
1271
1272    GETBITS(i, 6)
1273    eph._prn.set('I', i);
1274    GETBITS(week, 10)
1275    GETFLOATSIGN(eph._clock_bias,     22, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1276    GETFLOATSIGN(eph._clock_drift,    16, 1.0 / (double )(1 << 30) / (double )(1 << 13))
1277    GETFLOATSIGN(eph._clock_driftrate, 8, 1.0 / (double )(1 << 30) / (double )(1 << 25))
1278    GETBITS(i, 4)
1279    eph._ura = accuracyFromIndex(i, eph.type());
1280    GETBITS(i, 16)
1281    i <<= 4;
1282    eph._TOC.set(i * 1000);
1283    GETFLOATSIGN(eph._TGD, 8, 1.0 / (double )(1 << 30) / (double )(1 <<  1))
1284    GETFLOATSIGN(eph._Delta_n, 22, R2R_PI/(double)(1<<30)/(double)(1 << 11))
1285    // IODCE
1286    GETBITS(eph._IODE, 8)
1287    eph._IODC = eph._IODE;
1288    SKIPBITS(10)
1289    GETBITS(L5Flag, 1)
1290    GETBITS(SFlag, 1)
1291    if      (L5Flag == 0 && SFlag == 0) {
1292      eph._health = 0.0;
1293    }
1294    else if (L5Flag == 0 && SFlag == 1) {
1295      eph._health = 1.0;
1296    }
1297    else if (L5Flag == 1 && SFlag == 0) {
1298      eph._health = 2.0;
1299    }
1300    else if (L5Flag == 1 && SFlag == 1) {
1301      eph._health = 3.0;
1302    }
1303    GETFLOATSIGN(eph._Cuc,  15, 1.0 / (double )(1 << 28))
1304    GETFLOATSIGN(eph._Cus,  15, 1.0 / (double )(1 << 28))
1305    GETFLOATSIGN(eph._Cic,  15, 1.0 / (double )(1 << 28))
1306    GETFLOATSIGN(eph._Cis,  15, 1.0 / (double )(1 << 28))
1307    GETFLOATSIGN(eph._Crc,  15, 1.0 / (double )(1 <<  4))
1308    GETFLOATSIGN(eph._Crs,  15, 1.0 / (double )(1 <<  4))
1309    GETFLOATSIGN(eph._IDOT, 14, R2R_PI/(double)(1<<30)/(double)(1<<13))
1310    GETFLOATSIGN(eph._M0,   32, R2R_PI/(double)(1<<30)/(double)(1<< 1))
1311    GETBITS(i, 16)
1312    i <<= 4;
1313    eph._TOEsec = i;
1314    bncTime t;
1315    t.set(i * 1000);
1316    eph._TOEweek = t.gpsw();
1317    int numOfRollOvers = int(floor(t.gpsw()/1024.0));
1318    week += (numOfRollOvers * 1024);
1319    /* week from HOW, differs from TOC, TOE week, we use adapted value instead */
1320    if (eph._TOEweek > week + 1 || eph._TOEweek < week - 1) /* invalid week */
1321      return false;
1322    GETFLOAT(eph._e,            32, 1.0 / (double )(1 << 30) / (double )(1 << 3))
1323    GETFLOAT(eph._sqrt_A,       32, 1.0 / (double )(1 << 19))
1324    GETFLOATSIGN(eph._OMEGA0,   32, R2R_PI/(double)(1<<30)/(double)(1<< 1))
1325    GETFLOATSIGN(eph._omega,    32, R2R_PI/(double)(1<<30)/(double)(1<< 1))
1326    GETFLOATSIGN(eph._OMEGADOT, 22, R2R_PI/(double)(1<<30)/(double)(1<<11))
1327    GETFLOATSIGN(eph._i0,       32, R2R_PI/(double)(1<<30)/(double)(1<< 1))
1328    SKIPBITS(2)
1329    SKIPBITS(2)
1330    eph._TOT = 0.9999e9;
1331
1332    emit newGPSEph(eph);
1333    decoded = true;
1334  }
1335  return decoded;
1336}
1337
1338//
1339////////////////////////////////////////////////////////////////////////////
1340bool RTCM3Decoder::DecodeSBASEphemeris(unsigned char* data, int size) {
1341  bool decoded = false;
1342
1343  if (size == 35) {
1344    t_ephSBAS eph;
1345    int i;
1346    uint64_t numbits = 0, bitfield = 0;
1347
1348    data += 3; /* header */
1349    size -= 6; /* header + crc */
1350    SKIPBITS(12)
1351
1352    eph._receptDateTime = currentDateAndTimeGPS();
1353
1354    GETBITS(i, 6)
1355    eph._prn.set('S', 20 + i);
1356    GETBITS(eph._IODN, 8)
1357    GETBITS(i, 13)
1358    i <<= 4;
1359    eph._TOC.setTOD(i * 1000);
1360    GETBITS(i, 4)
1361    eph._ura = accuracyFromIndex(i, eph.type());
1362    GETFLOATSIGN(eph._x_pos, 30, 0.08)
1363    GETFLOATSIGN(eph._y_pos, 30, 0.08)
1364    GETFLOATSIGN(eph._z_pos, 25, 0.4)
1365    GETFLOATSIGN(eph._x_velocity, 17, 0.000625)
1366    GETFLOATSIGN(eph._y_velocity, 17, 0.000625)
1367    GETFLOATSIGN(eph._z_velocity, 18, 0.004)
1368    GETFLOATSIGN(eph._x_acceleration, 10, 0.0000125)
1369    GETFLOATSIGN(eph._y_acceleration, 10, 0.0000125)
1370    GETFLOATSIGN(eph._z_acceleration, 10, 0.0000625)
1371    GETFLOATSIGN(eph._agf0, 12, 1.0 / (1 << 30) / (1 << 1))
1372    GETFLOATSIGN(eph._agf1, 8, 1.0 / (1 << 30) / (1 << 10))
1373
1374    eph._TOT = 0.9999E9;
1375    eph._health = 0;
1376
1377    emit newSBASEph(eph);
1378    decoded = true;
1379  }
1380  return decoded;
1381}
1382
1383//
1384////////////////////////////////////////////////////////////////////////////
1385bool RTCM3Decoder::DecodeGalileoEphemeris(unsigned char* data, int size) {
1386  bool decoded = false;
1387  uint64_t numbits = 0, bitfield = 0;
1388  int i;
1389
1390  data += 3; /* header */
1391  size -= 6; /* header + crc */
1392  GETBITS(i, 12)
1393
1394  if ((i == 1046 && size == 61) || (i == 1045 && size == 60)) {
1395    t_ephGal eph;
1396
1397    eph._receptDateTime = currentDateAndTimeGPS();
1398
1399    eph._inav = (i == 1046);
1400    eph._fnav = (i == 1045);
1401    GETBITS(i, 6)
1402    eph._prn.set('E', i, eph._inav ? 1 : 0);
1403
1404    GETBITS(eph._TOEweek, 12) //FIXME: roll-over after week 4095!!
1405    GETBITS(eph._IODnav, 10)
1406    GETBITS(i, 8)
1407    eph._SISA = accuracyFromIndex(i, eph.type());
1408    GETFLOATSIGN(eph._IDOT, 14, R2R_PI/(double)(1<<30)/(double)(1<<13))
1409    GETBITSFACTOR(i, 14, 60)
1410    eph._TOC.set(1024 + eph._TOEweek, i);
1411    GETFLOATSIGN(eph._clock_driftrate, 6, 1.0 / (double )(1 << 30) / (double )(1 << 29))
1412    GETFLOATSIGN(eph._clock_drift,    21, 1.0 / (double )(1 << 30) / (double )(1 << 16))
1413    GETFLOATSIGN(eph._clock_bias,     31, 1.0 / (double )(1 << 30) / (double )(1 << 4))
1414    GETFLOATSIGN(eph._Crs, 16, 1.0 / (double )(1 << 5))
1415    GETFLOATSIGN(eph._Delta_n, 16, R2R_PI/(double)(1<<30)/(double)(1<<13))
1416    GETFLOATSIGN(eph._M0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1417    GETFLOATSIGN(eph._Cuc, 16, 1.0 / (double )(1 << 29))
1418    GETFLOAT(eph._e, 32, 1.0 / (double )(1 << 30) / (double )(1 << 3))
1419    GETFLOATSIGN(eph._Cus, 16, 1.0 / (double )(1 << 29))
1420    GETFLOAT(eph._sqrt_A, 32, 1.0 / (double )(1 << 19))
1421    GETBITSFACTOR(eph._TOEsec, 14, 60)
1422    /* FIXME: overwrite value, copied from old code */
1423    eph._TOEsec = eph._TOC.gpssec();
1424    GETFLOATSIGN(eph._Cic, 16, 1.0 / (double )(1 << 29))
1425    GETFLOATSIGN(eph._OMEGA0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1426    GETFLOATSIGN(eph._Cis, 16, 1.0 / (double )(1 << 29))
1427    GETFLOATSIGN(eph._i0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1428    GETFLOATSIGN(eph._Crc, 16, 1.0 / (double )(1 << 5))
1429    GETFLOATSIGN(eph._omega, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1430    GETFLOATSIGN(eph._OMEGADOT, 24, R2R_PI/(double)(1<<30)/(double)(1<<13))
1431    GETFLOATSIGN(eph._BGD_1_5A, 10,
1432        1.0 / (double )(1 << 30) / (double )(1 << 2))
1433    if (eph._inav) {
1434      /* set unused F/NAV values */
1435      eph._E5aHS = 0.0;
1436      eph._e5aDataInValid = false;
1437
1438GETFLOATSIGN(eph._BGD_1_5B, 10, 1.0 / (double )(1 << 30) / (double )(1 << 2))
1439      GETBITS(eph._E5bHS, 2)
1440      GETBITS(eph._e5bDataInValid, 1)
1441      GETBITS(eph._E1_bHS, 2)
1442      GETBITS(eph._e1DataInValid, 1)
1443    }
1444    else {
1445      /* set unused I/NAV values */
1446      eph._BGD_1_5B = 0.0;
1447      eph._E5bHS = 0.0;
1448      eph._E1_bHS = 0.0;
1449      eph._e1DataInValid = false;
1450      eph._e5bDataInValid = false;
1451
1452      GETBITS(eph._E5aHS, 2)
1453      GETBITS(eph._e5aDataInValid, 1)
1454    }
1455    eph._TOT = 0.9999e9;
1456
1457    emit newGalileoEph(eph);
1458    decoded = true;
1459  }
1460  return decoded;
1461}
1462
1463//
1464////////////////////////////////////////////////////////////////////////////
1465bool RTCM3Decoder::DecodeBDSEphemeris(unsigned char* data, int size) {
1466  bool decoded = false;
1467
1468  if (size == 70) {
1469    t_ephBDS eph;
1470    int i;
1471    uint64_t numbits = 0, bitfield = 0;
1472
1473    data += 3; /* header */
1474    size -= 6; /* header + crc */
1475    SKIPBITS(12)
1476
1477    eph._receptDateTime = currentDateAndTimeGPS();
1478
1479    GETBITS(i, 6)
1480    eph._prn.set('C', i);
1481
1482    SKIPBITS(13)
1483    /* week */
1484    GETBITS(i, 4)
1485    eph._URA = accuracyFromIndex(i, eph.type());
1486    GETFLOATSIGN(eph._IDOT, 14, R2R_PI/(double)(1<<30)/(double)(1<<13))
1487    GETBITS(eph._AODE, 5)
1488    GETBITS(i, 17)
1489    i <<= 3;
1490    eph._TOC.setBDS(i * 1000);
1491    GETFLOATSIGN(eph._clock_driftrate, 11,  1.0 / (double )(1 << 30) / (double )(1 << 30) / (double )(1 << 6))
1492    GETFLOATSIGN(eph._clock_drift,     22,  1.0 / (double )(1 << 30) / (double )(1 << 20))
1493    GETFLOATSIGN(eph._clock_bias,      24,  1.0 / (double )(1 << 30) / (double )(1 << 3))
1494    GETBITS(eph._AODC, 5)
1495    GETFLOATSIGN(eph._Crs, 18, 1.0 / (double )(1 << 6))
1496    GETFLOATSIGN(eph._Delta_n, 16, R2R_PI/(double)(1<<30)/(double)(1<<13))
1497    GETFLOATSIGN(eph._M0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1498    GETFLOATSIGN(eph._Cuc, 18, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1499    GETFLOAT(eph._e, 32, 1.0 / (double )(1 << 30) / (double )(1 << 3))
1500    GETFLOATSIGN(eph._Cus, 18, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1501    GETFLOAT(eph._sqrt_A, 32, 1.0 / (double )(1 << 19))
1502    GETBITS(i, 17)
1503    i <<= 3;
1504    eph._TOEsec = i;
1505    eph._TOE.setBDS(i * 1000);
1506    GETFLOATSIGN(eph._Cic, 18, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1507    GETFLOATSIGN(eph._OMEGA0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1508    GETFLOATSIGN(eph._Cis, 18, 1.0 / (double )(1 << 30) / (double )(1 << 1))
1509    GETFLOATSIGN(eph._i0, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1510    GETFLOATSIGN(eph._Crc, 18, 1.0 / (double )(1 << 6))
1511    GETFLOATSIGN(eph._omega, 32, R2R_PI/(double)(1<<30)/(double)(1<<1))
1512    GETFLOATSIGN(eph._OMEGADOT, 24, R2R_PI/(double)(1<<30)/(double)(1<<13))
1513    GETFLOATSIGN(eph._TGD1, 10, 0.0000000001)
1514    GETFLOATSIGN(eph._TGD2, 10, 0.0000000001)
1515    GETBITS(eph._SatH1, 1)
1516
1517    eph._TOT = 0.9999E9;
1518    emit newBDSEph(eph);
1519    decoded = true;
1520  }
1521  return decoded;
1522}
1523
1524//
1525////////////////////////////////////////////////////////////////////////////
1526bool RTCM3Decoder::DecodeAntennaReceiver(unsigned char* data, int size) {
1527  char *antenna, anttype[256];
1528  char *dummy;
1529  char *receiver, rectype[256];
1530
1531  int type;
1532
1533  int dnum = -1;
1534  int antnum = -1;
1535  int recnum = -1;
1536  uint64_t numbits = 0, bitfield = 0;
1537
1538  data += 3; /* header*/
1539  size -= 6; /* header + crc */
1540
1541  GETBITS(type, 12)
1542  SKIPBITS(12)
1543  GETSTRING(antnum, antenna)
1544  if (antnum > -1 && antnum < 265) {
1545    memcpy(anttype, antenna, antnum);
1546    anttype[antnum] = 0;
1547    if (!_antType.contains(anttype)) {
1548      _antType.push_back(anttype);
1549    }
1550  }
1551  if (type == 1033) {
1552    SKIPBITS(8)
1553    GETSTRING(dnum, dummy)
1554    GETSTRING(recnum, receiver)
1555    if (recnum > -1 && recnum < 265) {
1556      memcpy(rectype, receiver, recnum);
1557      rectype[recnum] = 0;
1558      if (!_recType.contains(rectype)) {
1559        _recType.push_back(rectype);
1560      }
1561    }
1562  }
1563  return true;
1564}
1565
1566//
1567////////////////////////////////////////////////////////////////////////////
1568bool RTCM3Decoder::DecodeAntennaPosition(unsigned char* data, int size) {
1569  int type;
1570  uint64_t numbits = 0, bitfield = 0;
1571  double x, y, z;
1572
1573  data += 3; /* header */
1574  size -= 6; /* header + crc */
1575
1576  GETBITS(type, 12)
1577  _antList.push_back(t_antInfo());
1578  _antList.back().type = t_antInfo::ARP;
1579  SKIPBITS(22)
1580  GETBITSSIGN(x, 38)
1581  _antList.back().xx = x * 1e-4;
1582  SKIPBITS(2)
1583  GETBITSSIGN(y, 38)
1584  _antList.back().yy = y * 1e-4;
1585  SKIPBITS(2)
1586  GETBITSSIGN(z, 38)
1587  _antList.back().zz = z * 1e-4;
1588  if (type == 1006)
1589      {
1590    double h;
1591    GETBITS(h, 16)
1592    _antList.back().height = h * 1e-4;
1593    _antList.back().height_f = true;
1594  }
1595  _antList.back().message = type;
1596
1597  return true;
1598}
1599
1600//
1601////////////////////////////////////////////////////////////////////////////
1602t_irc RTCM3Decoder::Decode(char* buffer, int bufLen, vector<string>& errmsg) {
1603  bool decoded = false;
1604
1605  errmsg.clear();
1606
1607  while (bufLen && _MessageSize < sizeof(_Message)) {
1608    int l = sizeof(_Message) - _MessageSize;
1609    if (l > bufLen)
1610      l = bufLen;
1611    memcpy(_Message + _MessageSize, buffer, l);
1612    _MessageSize += l;
1613    bufLen -= l;
1614    buffer += l;
1615    int id;
1616    while ((id = GetMessage())) {
1617      /* reset station ID for file loading as it can change */
1618      if (_rawFile)
1619        _staID = _rawFile->staID();
1620      /* store the id into the list of loaded blocks */
1621      _typeList.push_back(id);
1622
1623      /* SSR I+II data handled in another function, already pass the
1624       * extracted data block. That does no harm, as it anyway skip everything
1625       * else. */
1626      if ((id >= 1057 && id <= 1068) || (id >= 1240 && id <= 1270)) {
1627        if (!_coDecoders.contains(_staID.toAscii()))
1628          _coDecoders[_staID.toAscii()] = new RTCM3coDecoder(_staID);
1629        RTCM3coDecoder* coDecoder = _coDecoders[_staID.toAscii()];
1630        if (coDecoder->Decode(reinterpret_cast<char *>(_Message), _BlockSize,
1631            errmsg) == success) {
1632          decoded = true;
1633        }
1634      }
1635      else if ((id >= 1070 && id <= 1229) ||
1636               (id >=   21 && id <=   27)) /* MSM */ {
1637        if (DecodeRTCM3MSM(_Message, _BlockSize))
1638          decoded = true;
1639      }
1640      else {
1641        switch (id) {
1642          case 1001:
1643          case 1003:
1644            emit(newMessage(
1645                QString("%1: Block %2 contain partial data! Ignored!")
1646                    .arg(_staID).arg(id).toAscii(), true));
1647            break; /* no use decoding partial data ATM, remove break when data can be used */
1648          case 1002:
1649          case 1004:
1650            if (DecodeRTCM3GPS(_Message, _BlockSize))
1651              decoded = true;
1652            break;
1653          case 1009:
1654          case 1011:
1655            emit(newMessage(
1656                QString("%1: Block %2 contain partial data! Ignored!")
1657                    .arg(_staID).arg(id).toAscii(), true));
1658            break; /* no use decoding partial data ATM, remove break when data can be used */
1659          case 1010:
1660          case 1012:
1661            if (DecodeRTCM3GLONASS(_Message, _BlockSize))
1662              decoded = true;
1663            break;
1664          case 1019:
1665            if (DecodeGPSEphemeris(_Message, _BlockSize))
1666              decoded = true;
1667            break;
1668          case 1020:
1669            if (DecodeGLONASSEphemeris(_Message, _BlockSize))
1670              decoded = true;
1671            break;
1672          case 1043:
1673            if (DecodeSBASEphemeris(_Message, _BlockSize))
1674              decoded = true;
1675            break;
1676          case 1044:
1677            if (DecodeQZSSEphemeris(_Message, _BlockSize))
1678              decoded = true;
1679            break;
1680          case 29:
1681            if (DecodeIRNSSEphemeris(_Message, _BlockSize))
1682              decoded = true;
1683            break;           
1684          case 1045:
1685          case 1046:
1686            if (DecodeGalileoEphemeris(_Message, _BlockSize))
1687              decoded = true;
1688            break;
1689          case RTCM3ID_BDS:
1690            if (DecodeBDSEphemeris(_Message, _BlockSize))
1691              decoded = true;
1692            break;
1693          case 1007:
1694          case 1008:
1695          case 1033:
1696            DecodeAntennaReceiver(_Message, _BlockSize);
1697            break;
1698          case 1005:
1699          case 1006:
1700            DecodeAntennaPosition(_Message, _BlockSize);
1701            break;
1702        }
1703      }
1704    }
1705  }
1706  return decoded ? success : failure;
1707}
1708;
1709
1710//
1711////////////////////////////////////////////////////////////////////////////
1712uint32_t RTCM3Decoder::CRC24(long size, const unsigned char *buf) {
1713  uint32_t crc = 0;
1714  int i;
1715
1716  while (size--) {
1717    crc ^= (*buf++) << (16);
1718    for (i = 0; i < 8; i++)
1719        {
1720      crc <<= 1;
1721      if (crc & 0x1000000)
1722        crc ^= 0x01864cfb;
1723    }
1724  }
1725  return crc;
1726}
1727
1728//
1729////////////////////////////////////////////////////////////////////////////
1730int RTCM3Decoder::GetMessage(void) {
1731  unsigned char *m, *e;
1732  int i;
1733
1734  m = _Message + _SkipBytes;
1735  e = _Message + _MessageSize;
1736  _NeedBytes = _SkipBytes = 0;
1737  while (e - m >= 3) {
1738    if (m[0] == 0xD3) {
1739      _BlockSize = ((m[1] & 3) << 8) | m[2];
1740      if (e - m >= static_cast<int>(_BlockSize + 6)) {
1741        if (static_cast<uint32_t>((m[3 + _BlockSize] << 16)
1742            | (m[3 + _BlockSize + 1] << 8)
1743            | (m[3 + _BlockSize + 2])) == CRC24(_BlockSize + 3, m)) {
1744          _BlockSize += 6;
1745          _SkipBytes = _BlockSize;
1746          break;
1747        }
1748        else
1749          ++m;
1750      }
1751      else {
1752        _NeedBytes = _BlockSize;
1753        break;
1754      }
1755    }
1756    else
1757      ++m;
1758  }
1759  if (e - m < 3)
1760    _NeedBytes = 3;
1761
1762  /* copy buffer to front */
1763  i = m - _Message;
1764  if (i && m < e)
1765    memmove(_Message, m, static_cast<size_t>(_MessageSize - i));
1766  _MessageSize -= i;
1767
1768  return !_NeedBytes ? ((_Message[3] << 4) | (_Message[4] >> 4)) : 0;
1769}
1770
1771// Time of Corrections
1772//////////////////////////////////////////////////////////////////////////////
1773int RTCM3Decoder::corrGPSEpochTime() const {
1774  return
1775      _coDecoders.size() > 0 ?
1776          _coDecoders.begin().value()->corrGPSEpochTime() : -1;
1777}
Note: See TracBrowser for help on using the repository browser.