1 //==============================================================================
2 //
3 //  This file is part of GPSTk, the GPS Toolkit.
4 //
5 //  The GPSTk is free software; you can redistribute it and/or modify
6 //  it under the terms of the GNU Lesser General Public License as published
7 //  by the Free Software Foundation; either version 3.0 of the License, or
8 //  any later version.
9 //
10 //  The GPSTk is distributed in the hope that it will be useful,
11 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
12 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 //  GNU Lesser General Public License for more details.
14 //
15 //  You should have received a copy of the GNU Lesser General Public
16 //  License along with GPSTk; if not, write to the Free Software Foundation,
17 //  Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
18 //
19 //  This software was developed by Applied Research Laboratories at the
20 //  University of Texas at Austin.
21 //  Copyright 2004-2020, The Board of Regents of The University of Texas System
22 //
23 //==============================================================================
24 
25 //==============================================================================
26 //
27 //  This software was developed by Applied Research Laboratories at the
28 //  University of Texas at Austin, under contract to an agency or agencies
29 //  within the U.S. Department of Defense. The U.S. Government retains all
30 //  rights to use, duplicate, distribute, disclose, or release this software.
31 //
32 //  Pursuant to DoD Directive 523024
33 //
34 //  DISTRIBUTION STATEMENT A: This software has been approved for public
35 //                            release, distribution is unlimited.
36 //
37 //==============================================================================
38 
39 /**
40  * @file PackedNavBits_T.cpp
41  * Tests for gpstk/ext/lib/GNSSEph/PackedNavBits
42  */
43 #include "CivilTime.hpp"
44 #include "CommonTime.hpp"
45 #include "GNSSconstants.hpp"
46 #include "ObsID.hpp"
47 #include "PackedNavBits.hpp"
48 #include "SatID.hpp"
49 #include "TestUtil.hpp"
50 #include "TimeString.hpp"
51 #include "TimeSystem.hpp"
52 
53 using namespace std;
54 using namespace gpstk;
55 
56 class PackedNavBits_T
57 {
58 public:
59    PackedNavBits_T();
60 
61    void init();
62 
63    unsigned abstractTest();
64    unsigned realDataTest();
65    unsigned equalityTest();
66    unsigned ancillaryMethods();
67 
68    double eps;
69 };
70 
71 PackedNavBits_T ::
PackedNavBits_T()72 PackedNavBits_T()
73 {
74    init();
75 }
76 
77 void PackedNavBits_T ::
init()78 init()
79 {
80    TUDEF("PackedNavBits", "initialize");
81    eps = 1E-12;   // Set the precision value
82 }
83 
84    // These tests are NOT real data, but are designed to test
85    // edge cases and limits.
86 unsigned PackedNavBits_T ::
abstractTest()87 abstractTest()
88 {
89     // Test Unsigned Integers
90    TUDEF("PackedNavBits", "addUnsigned");
91    unsigned long u_i1 = 32767;
92    int u_n1           = 16;
93    int u_s1           = 1;
94 
95    unsigned long u_i2 = 1;
96    int u_n2           = 8;
97    int u_s2           = 1;
98 
99    unsigned long u_i3 = 255;
100    int u_n3           = 8;
101    int u_s3           = 1;
102 
103    unsigned long u_i4 = 604500;
104    int u_n4           = 11;
105    int u_s4           = 300;
106 
107       // Pack the data
108    PackedNavBits pnb;
109    pnb.addUnsignedLong(u_i1, u_n1, u_s1);
110    pnb.addUnsignedLong(u_i2, u_n2, u_s2);
111    pnb.addUnsignedLong(u_i3, u_n3, u_s3);
112    pnb.addUnsignedLong(u_i4, u_n4, u_s4);
113 
114       // Unpack the data and see that the round-trip worked.
115    int startbit = 0;
116    unsigned long ultest = pnb.asUnsignedLong(startbit, u_n1, u_s1);
117    TUASSERTE(unsigned long, ultest, u_i1);
118    startbit += u_n1;
119    ultest = pnb.asUnsignedLong(startbit, u_n2, u_s2);
120    TUASSERTE(unsigned long, ultest, u_i2);
121    startbit += u_n2;
122    ultest = pnb.asUnsignedLong(startbit, u_n3, u_s3);
123    TUASSERTE(unsigned long, ultest, u_i3);
124    startbit += u_n3;
125    ultest = pnb.asUnsignedLong(startbit, u_n4, u_s4);
126    TUASSERTE(unsigned long, ultest, u_i4);
127    startbit += u_n4;
128 
129     // Test Signed Integers
130    TUCSM("addSigned");
131    long s_i1 = 15;
132    int s_n1  = 5;
133    int s_s1  = 1;
134 
135    long s_i2 = -16;
136    int s_n2  = 5;
137    int s_s2  = 1;
138 
139    long s_i3 = -1;
140    int s_n3  = 5;
141    int s_s3  = 1;
142 
143    long s_i4 = 0;
144    int s_n4  = 6;
145    int s_s4  = 1;
146 
147    long s_i5 = 4194304;
148    int s_n5  = 24;
149    int s_s5  = 1;
150 
151    pnb.addLong(s_i1, s_n1, s_s1);
152    pnb.addLong(s_i2, s_n2, s_s2);
153    pnb.addLong(s_i3, s_n3, s_s3);
154    pnb.addLong(s_i4, s_n4, s_s4);
155    pnb.addLong(s_i5, s_n5, s_s5);
156 
157    long ltest;
158    ltest = pnb.asLong(startbit, s_n1, s_s1);
159    TUASSERTE(long, ltest, s_i1);
160    startbit += s_n1;
161    ltest = pnb.asLong(startbit, s_n2, s_s2);
162    TUASSERTE(long, ltest, s_i2);
163    startbit += s_n2;
164    ltest = pnb.asLong(startbit, s_n3, s_s3);
165    TUASSERTE(long, ltest, s_i3);
166    startbit += s_n3;
167    ltest = pnb.asLong(startbit, s_n4, s_s4);
168    TUASSERTE(long, ltest, s_i4);
169    startbit += s_n4;
170    ltest = pnb.asLong(startbit, s_n5, s_s5);
171    TUASSERTE(long, ltest, s_i5);
172    startbit += s_n5;
173 
174    // Test Signed Doubles
175    TUCSM("addDouble");
176    double d_i1 = 0.490005493;
177    int d_n1    = 16;
178    int d_s1    = -16;
179    double d_e1 = pow(2.0,d_s1);   // value of lsb
180 
181    double d_i2 = -0.5;
182    int d_n2    = 16;
183    int d_s2    = -16;
184    double d_e2 = pow(2.0,d_s2);   // value of lsb
185 
186    double d_i3 = 0;
187    int d_n3    = 16;
188    int d_s3    = -16;
189    double d_e3 = pow(2.0,d_s3);   // value of lsb
190 
191    // Test Unsigned Doubles
192    double d_i4 = 32000.0;
193    int d_n4    = 16;
194    int d_s4    = 0;
195    double d_e4 = pow(2.0,d_s4);   // value of lsb
196 
197    pnb.addSignedDouble(d_i1, d_n1, d_s1);
198    pnb.addSignedDouble(d_i2, d_n2, d_s2);
199    pnb.addSignedDouble(d_i3, d_n3, d_s3);
200    pnb.addUnsignedDouble(d_i4, d_n4, d_s4);
201 
202    double dtest;
203    dtest = pnb.asSignedDouble(startbit, d_n1, d_s1);
204    TUASSERTFEPS(dtest, d_i1, d_e1);
205    startbit += d_n1;
206    dtest = pnb.asSignedDouble(startbit, d_n2, d_s2);
207    TUASSERTFEPS(dtest, d_i2, d_e2);
208    startbit += d_n2;
209    dtest = pnb.asSignedDouble(startbit, d_n3, d_s3);
210    TUASSERTFEPS(dtest, d_i3, d_e3);
211    startbit += d_n3;
212    dtest = pnb.asUnsignedDouble(startbit, d_n4, d_s4);
213    TUASSERTFEPS(dtest, d_i4, d_e4);
214    startbit += d_n4;
215 
216    // Test Semi-Circles
217    TUCSM("addSemiCircles");
218    double sd_i1 = PI-2*pow(2.0,-31);
219    int sd_n1    = 32;
220    int sd_s1    = -31;
221    double sd_e1 = pow(2.0,sd_s1) * 3.0;   // value of lsb in semi-circles
222 
223    double sd_i2 = -PI;
224    int sd_n2    = 32;
225    int sd_s2    = -31;
226    double sd_e2 = pow(2.0,sd_s1) * 3.0;   // value of lsb
227 
228    pnb.addDoubleSemiCircles(sd_i1, sd_n1, sd_s1);
229    pnb.addDoubleSemiCircles(sd_i2, sd_n2, sd_s2);
230 
231    dtest = pnb.asDoubleSemiCircles(startbit, sd_n1, sd_s1);
232    TUASSERTFEPS(dtest, sd_i1, sd_e1);
233    startbit += sd_n1;
234    dtest = pnb.asDoubleSemiCircles(startbit, sd_n2, sd_s2);
235    TUASSERTFEPS(dtest, sd_i2, sd_e2);
236 
237    return testFramework.countFails();
238 }
239 
240    // These test cases are examples from real data.
241 unsigned PackedNavBits_T ::
realDataTest()242 realDataTest()
243 {
244    TUDEF("PackedNavBits", "real data round-trip");
245 
246       //Test Data copied from RINEX file for PRN3, week 1638, day 153 2011
247    SatID satID(3, SatelliteSystem::GPS);
248    ObsID obsID( ObservationType::NavMsg, CarrierBand::L1, TrackingCode::CA );
249    std::string rxID = "rx1";
250    CommonTime ct = CivilTime( 2011, 6, 2, 10, 00, 0.0, TimeSystem::GPS );
251    PackedNavBits pnb(satID,obsID,rxID,ct);
252 
253    double rToe         = 388800.0;
254    int n_rToe          = 16;
255    int s_rToe          = 4;
256 
257    unsigned long riodc = 22;
258    int n_riodc         = 8;
259    int s_riodc         = 1;
260 
261    unsigned long riode = 22;
262    int n_riode         = 8;
263    int s_riode         = 1;
264 
265    unsigned long raodo = 10;
266    int n_raodo         = 5;
267    int s_raodo         = 1;
268 
269    unsigned long rfitInt = 0;
270    int n_rfitInt    = 1;
271    int s_rfitInt    = 1;
272 
273    double rToc      = 388800.0;
274    int n_rToc       = 16;
275    int s_rToc       = 4;
276 
277    double rCuc      = 9.57399606705E-07;
278    int n_rCuc       = 16;
279    int s_rCuc       = -29;
280 
281    double rCus      = 8.35768878460E-06;
282    int n_rCus       = 16;
283    int s_rCus       = -29;
284 
285    double rCrc      = 2.03562500000E+02;
286    int n_rCrc       = 16;
287    int s_rCrc       = -5;
288 
289    double rCrs      = 1.87812500000E+01;
290    int n_rCrs       = 16;
291    int s_rCrs       = -5;
292 
293    double rCic      = -2.30967998505E-07;
294    int n_rCic       = 16;
295    int s_rCic       = -29;
296 
297    double rCis      = 5.02914190292E-08;
298    int n_rCis       = 16;
299    int s_rCis       = -29;
300 
301    double rM0       = 1.05539162795E+00;
302    int n_rM0        = 32;
303    int s_rM0        = -31;
304 
305    double rdn       = 5.39093883996E-09;
306    int n_rdn        = 16;
307    int s_rdn        = -43;
308 
309    double recc      = 1.42575260252E-02;
310    int n_recc       = 32;
311    int s_recc       = -33;
312 
313    double rAhalf    = 5.15365527534E+03;
314    int n_rAhalf     = 32;
315    int s_rAhalf     = -19;
316 
317    double rOMEGA0   = -2.16947563164E+00;
318    int n_rOMEGA0    = 32;
319    int s_rOMEGA0    = -31;
320 
321    double ri0       = 9.28692497530E-01;
322    int n_ri0        = 32;
323    int s_ri0        = -31;
324 
325    double rw        = 1.09154604931E+00;
326    int n_rw         = 32;
327    int s_rw         = -31;
328 
329    double rOMEGAdot = -8.56285667735E-09;
330    int n_rOMEGAdot  = 24;
331    int s_rOMEGAdot  = -43;
332 
333    double ridot     = 5.52880172536E-10;
334    int n_ridot      = 14;
335    int s_ridot       = -43;
336 
337    double raf0      = 7.23189674318E-04;
338    int n_raf0       = 22;
339    int s_raf0       = -31;
340 
341    double raf1      = 5.11590769747E-12;
342    int n_raf1       = 16;
343    int s_raf1       = -43;
344 
345    double raf2      = 0.0;
346    int n_raf2       = 8;
347    int s_raf2       = -55;
348 
349    double rTgd      = -4.65661287308E-09;
350    int n_rTgd       = 8;
351    int s_rTgd       = -31;
352 
353       // Pack legacy nav message data in order
354       // (But w/o parity)
355    pnb.addSignedDouble(rTgd, n_rTgd, s_rTgd);
356    pnb.addUnsignedLong(riodc, n_riodc, s_riodc);
357    pnb.addUnsignedDouble(rToc, n_rToc, s_rToc);
358    pnb.addSignedDouble(raf2, n_raf2, s_raf2);
359    pnb.addSignedDouble(raf1, n_raf1, s_raf1);
360    pnb.addSignedDouble(raf0, n_raf0, s_raf0);
361    pnb.addUnsignedLong(riode, n_riode, s_riode);
362    pnb.addSignedDouble(rCrs, n_rCrs, s_rCrs);
363    pnb.addDoubleSemiCircles(rdn, n_rdn, s_rdn);
364    pnb.addDoubleSemiCircles(rM0, n_rM0, s_rM0);
365    pnb.addSignedDouble(rCuc, n_rCuc, s_rCuc);
366    pnb.addUnsignedDouble(recc, n_recc, s_recc);
367    pnb.addSignedDouble(rCus, n_rCus, s_rCus);
368    pnb.addUnsignedDouble(rAhalf, n_rAhalf, s_rAhalf);
369    pnb.addUnsignedDouble(rToe, n_rToe, s_rToe);
370    pnb.addUnsignedLong(rfitInt, n_rfitInt, s_rfitInt);
371    pnb.addUnsignedLong(raodo, n_raodo, s_raodo);
372    pnb.addSignedDouble(rCic, n_rCic, s_rCic);
373    pnb.addDoubleSemiCircles(rOMEGA0, n_rOMEGA0, s_rOMEGA0);
374    pnb.addSignedDouble(rCis, n_rCis, s_rCis);
375    pnb.addDoubleSemiCircles(ri0, n_ri0, s_ri0);
376    pnb.addSignedDouble(rCrc, n_rCrc, s_rCrc);
377    pnb.addDoubleSemiCircles(rw, n_rw, s_rw);
378    pnb.addDoubleSemiCircles(rOMEGAdot, n_rOMEGAdot, s_rOMEGAdot);
379    pnb.addUnsignedLong(riode, n_riode, s_riode);
380    pnb.addDoubleSemiCircles(ridot, n_ridot, s_ridot);
381    pnb.trimsize();
382 
383    int startbit = 0;
384    double dtest;
385    unsigned long ultest;
386    long ltest;
387    double eps;     // value of lsb
388 
389    dtest = pnb.asSignedDouble(startbit, n_rTgd, s_rTgd);
390    eps = pow(2.0,s_rTgd);
391    TUASSERTFEPS(dtest,rTgd,eps);
392 
393    startbit += n_rTgd;
394    ultest = pnb.asUnsignedLong(startbit, n_riodc, s_riodc);
395    TUASSERTE(unsigned long, ultest, riodc);
396 
397    startbit += n_riodc;
398    dtest = pnb.asUnsignedDouble(startbit, n_rToc, s_rToc);
399    eps = pow(2.0,s_rToc);
400    TUASSERTFEPS(dtest,rToc,eps);
401 
402    startbit += n_rToc;
403    dtest = pnb.asSignedDouble(startbit, n_raf2, s_raf2);
404    eps = pow(2.0,s_raf2);
405    TUASSERTFEPS(dtest,raf2,eps);
406 
407    startbit += n_raf2;
408    dtest = pnb.asSignedDouble(startbit, n_raf1, s_raf1);
409    eps = pow(2.0,s_raf1);
410    TUASSERTFEPS(dtest,raf1,eps);
411 
412    startbit += n_raf1;
413    dtest = pnb.asSignedDouble(startbit, n_raf0, s_raf0);
414    eps = pow(2.0,s_raf0);
415    TUASSERTFEPS(dtest,raf0,eps);
416 
417    startbit += n_raf0;
418    ultest = pnb.asUnsignedLong(startbit, n_riode, s_riode);
419    TUASSERTE(unsigned long, ultest, riode);
420 
421    startbit += n_riode;
422    dtest = pnb.asSignedDouble(startbit, n_rCrs, s_rCrs);
423    eps = pow(2.0,s_rCrs);
424    TUASSERTFEPS(dtest,rCrs,eps);
425 
426    startbit += n_rCrs;
427    dtest = pnb.asDoubleSemiCircles(startbit, n_rdn, s_rdn);
428    eps = pow(2.0,s_rdn) * 3.0;
429    TUASSERTFEPS(dtest,rdn,eps);
430 
431    startbit += n_rdn;
432    dtest = pnb.asDoubleSemiCircles(startbit, n_rM0, s_rM0);
433    eps = pow(2.0,s_rM0) * 3.0;
434    TUASSERTFEPS(dtest,rM0,eps);
435 
436    startbit += n_rM0;
437    dtest = pnb.asSignedDouble(startbit, n_rCuc, s_rCuc);
438    eps = pow(2.0,s_rCuc);
439    TUASSERTFEPS(dtest,rCuc,eps);
440 
441    startbit += n_rCuc;
442    dtest = pnb.asUnsignedDouble(startbit, n_recc, s_recc);
443    eps = pow(2.0,s_recc);
444    TUASSERTFEPS(dtest,recc,eps);
445 
446    startbit += n_recc;
447    dtest = pnb.asSignedDouble(startbit, n_rCus, s_rCus);
448    eps = pow(2.0,s_rCus);
449    TUASSERTFEPS(dtest,rCus,eps);
450 
451    startbit += n_rCus;
452    dtest = pnb.asUnsignedDouble(startbit, n_rAhalf, s_rAhalf);
453    eps = pow(2.0,s_rAhalf);
454    TUASSERTFEPS(dtest,rAhalf,eps);
455 
456    startbit += n_rAhalf;
457    dtest = pnb.asUnsignedDouble(startbit, n_rToe, s_rToe);
458    eps = pow(2.0,s_rToe);
459    TUASSERTFEPS(dtest,rToe,eps);
460 
461    startbit += n_rToe;
462    ultest = pnb.asUnsignedLong(startbit, n_rfitInt, s_rfitInt);
463    TUASSERTE(unsigned long, ultest, rfitInt);
464 
465    startbit += n_rfitInt;
466    ultest = pnb.asUnsignedLong(startbit, n_raodo, s_raodo);
467    TUASSERTE(unsigned long, ultest, raodo);
468 
469    startbit += n_raodo;
470    dtest = pnb.asSignedDouble(startbit, n_rCic, s_rCic);
471    eps = pow(2.0,s_rCic);
472    TUASSERTFEPS(dtest,rCic,eps);
473 
474    startbit += n_rCic;
475    dtest = pnb.asDoubleSemiCircles(startbit, n_rOMEGA0, s_rOMEGA0);
476    eps = pow(2.0,s_rOMEGA0) * 3.0;
477    TUASSERTFEPS(dtest,rOMEGA0,eps);
478 
479    startbit += n_rOMEGA0;
480    dtest = pnb.asSignedDouble(startbit, n_rCis, s_rCis);
481    eps = pow(2.0,s_rCis);
482    TUASSERTFEPS(dtest,rCis,eps);
483 
484    startbit += n_rCis;
485    dtest = pnb.asDoubleSemiCircles(startbit, n_ri0, s_ri0);
486    eps = pow(2.0,s_ri0) * 3.0;
487    TUASSERTFEPS(dtest,ri0,eps);
488 
489    startbit += n_ri0;
490    dtest = pnb.asSignedDouble(startbit, n_rCrc, s_rCrc);
491    eps = pow(2.0,s_rCrc);
492    TUASSERTFEPS(dtest,rCrc,eps);
493 
494    startbit += n_rCrc;
495    dtest = pnb.asDoubleSemiCircles(startbit, n_rw, s_rw);
496    eps = pow(2.0,s_rw) * 3.0;
497    TUASSERTFEPS(dtest,rw,eps);
498 
499    startbit += n_rw;
500    dtest = pnb.asDoubleSemiCircles(startbit, n_rOMEGAdot, s_rOMEGAdot);
501    eps = pow(2.0,s_rOMEGAdot) * 3.0;
502    TUASSERTFEPS(dtest,rOMEGAdot,eps);
503 
504    startbit += n_rOMEGAdot;
505    dtest = pnb.asUnsignedLong(startbit, n_riode, s_riode);
506    eps = pow(2.0,s_riode);
507    TUASSERTFEPS(dtest,riode,eps);
508 
509    startbit += n_riode;
510    dtest = pnb.asDoubleSemiCircles(startbit, n_ridot, s_ridot);
511    eps = pow(2.0,s_ridot) * 3.0;
512    TUASSERTFEPS(dtest,ridot,eps);
513 
514    return testFramework.countFails();
515 }
516 
517 unsigned PackedNavBits_T ::
equalityTest()518 equalityTest()
519 {
520       // Create a master PackedNavBits, a copy, and
521       // several not-quite-copies.
522       // At this point, the "packed bits" section of
523       // this object is empty.  We are focused on testing
524       // the metadata handling.
525    SatID satID(1, SatelliteSystem::GPS);
526    ObsID obsID( ObservationType::NavMsg, CarrierBand::L2, TrackingCode::L2CML );
527    NavID navID(satID,obsID);
528    std::string rxID = "rx1";
529    CommonTime ct = CivilTime( 2011, 6, 2, 12, 14, 44.0, TimeSystem::GPS );
530 
531    SatID satID2(2, SatelliteSystem::GPS);
532    ObsID obsID2(ObservationType::NavMsg, CarrierBand::L5, TrackingCode::L5Q );
533    NavID navID2(satID2,obsID2);
534    std::string rxID2 = "rx2";
535    CommonTime ctPlus = ct + 900.0;
536 
537    PackedNavBits master(satID,obsID,navID,rxID,ct);
538    PackedNavBits masterCopy(master);
539 
540    PackedNavBits diffSat(satID2,obsID,navID,rxID,ct);
541    PackedNavBits diffObs(satID,obsID2,navID,rxID,ct);
542    PackedNavBits diffNav(satID,obsID,navID2,rxID,ct);
543    PackedNavBits diffRx(satID,obsID,navID,rxID2,ct);
544    PackedNavBits diffTime(satID,obsID,navID,rxID,ctPlus);
545       // Typical same SV/OBS/NAV across multiple Rx/Time case.
546    PackedNavBits diffRxTime(satID,obsID,navID,rxID2,ctPlus);
547 
548    TUDEF("PackedNavBits","matchMetaData");
549    TUASSERTE(bool,true,master.matchMetaData(master));
550    TUASSERTE(bool,true,master.matchMetaData(masterCopy));
551    TUASSERTE(bool,false,master.matchMetaData(diffSat));
552    TUASSERTE(bool,false,master.matchMetaData(diffObs));
553    TUASSERTE(bool,false,master.matchMetaData(diffNav));
554    TUASSERTE(bool,false,master.matchMetaData(diffRx));
555    TUASSERTE(bool,false,master.matchMetaData(diffTime));
556 
557    unsigned int ignoreSAT  =                        PackedNavBits::mmOBS | PackedNavBits::mmNAV | PackedNavBits::mmRX | PackedNavBits::mmTIME;
558    unsigned int ignoreOBS  = PackedNavBits::mmSAT |                        PackedNavBits::mmNAV | PackedNavBits::mmRX | PackedNavBits::mmTIME;
559    unsigned int ignoreNAV  = PackedNavBits::mmSAT | PackedNavBits::mmOBS |                        PackedNavBits::mmRX | PackedNavBits::mmTIME;
560    unsigned int ignoreRX   = PackedNavBits::mmSAT | PackedNavBits::mmOBS | PackedNavBits::mmNAV |                       PackedNavBits::mmTIME;
561    unsigned int ignoreTIME = PackedNavBits::mmSAT | PackedNavBits::mmOBS | PackedNavBits::mmNAV | PackedNavBits::mmRX;
562    unsigned int checkRXTIME = PackedNavBits::mmRX | PackedNavBits::mmTIME;
563    unsigned int checkSATOBS = PackedNavBits::mmSAT | PackedNavBits::mmOBS;
564    TUASSERTE(bool,true,master.matchMetaData( diffSat, ignoreSAT));
565    TUASSERTE(bool,true,master.matchMetaData( diffObs, ignoreOBS));
566    TUASSERTE(bool,true,master.matchMetaData( diffNav, ignoreNAV));
567    TUASSERTE(bool,true,master.matchMetaData(  diffRx,  ignoreRX));
568    TUASSERTE(bool,true,master.matchMetaData(diffTime,ignoreTIME));
569    TUASSERTE(bool,true,master.matchMetaData(diffRxTime,checkSATOBS));
570 
571    TUASSERTE(bool,false,master.matchMetaData(  diffSat,  PackedNavBits::mmSAT));
572    TUASSERTE(bool,false,master.matchMetaData(  diffObs,  PackedNavBits::mmOBS));
573    TUASSERTE(bool,false,master.matchMetaData(  diffNav,  PackedNavBits::mmNAV));
574    TUASSERTE(bool,false,master.matchMetaData(   diffRx,   PackedNavBits::mmRX));
575    TUASSERTE(bool,false,master.matchMetaData( diffTime, PackedNavBits::mmTIME));
576    TUASSERTE(bool,false,master.matchMetaData(diffRxTime, checkRXTIME));
577 
578       // Now keep the metadata the same across copies, but add some
579       // bits.  NOTE: The metadata is all left identical.
580    TUCSM("matchBits");
581    PackedNavBits withBits(satID,obsID,navID,rxID,ct);
582    PackedNavBits withSameBits(satID,obsID,navID,rxID,ct);
583    PackedNavBits withShortBits(satID,obsID,navID,rxID,ct);
584    PackedNavBits withLongBits(satID,obsID,navID,rxID,ct);
585 
586       // Reuse test data from abstractTest( )
587    unsigned long u_i1 = 32767;
588    int u_n1           = 16;
589    int u_s1           = 1;
590 
591    unsigned long u_i2 = 1;
592    int u_n2           = 8;
593    int u_s2           = 1;
594 
595    unsigned long u_i3 = 255;
596    int u_n3           = 8;
597    int u_s3           = 1;
598 
599    unsigned long u_i4 = 604500;
600    int u_n4           = 11;
601    int u_s4           = 300;
602 
603       // Pack the data
604    withBits.addUnsignedLong(u_i1, u_n1, u_s1);
605    withBits.addUnsignedLong(u_i2, u_n2, u_s2);
606    withBits.addUnsignedLong(u_i3, u_n3, u_s3);
607    withBits.trimsize();
608 
609    withSameBits.addUnsignedLong(u_i1, u_n1, u_s1);
610    withSameBits.addUnsignedLong(u_i2, u_n2, u_s2);
611    withSameBits.addUnsignedLong(u_i3, u_n3, u_s3);
612    withSameBits.trimsize();
613 
614    withShortBits.addUnsignedLong(u_i1, u_n1, u_s1);
615    withShortBits.addUnsignedLong(u_i2, u_n2, u_s2);
616    withShortBits.trimsize();
617 
618    withLongBits.addUnsignedLong(u_i1, u_n1, u_s1);
619    withLongBits.addUnsignedLong(u_i2, u_n2, u_s2);
620    withLongBits.addUnsignedLong(u_i3, u_n3, u_s3);
621    withLongBits.addUnsignedLong(u_i4, u_n4, u_s4);
622    withLongBits.trimsize();
623 
624       // Basic "test for complete match"
625    TUASSERTE(bool, true,withBits.matchBits(withSameBits));
626    TUASSERTE(bool,false,withBits.matchBits(withShortBits));
627    TUASSERTE(bool,false,withBits.matchBits(withLongBits));
628 
629       // Test for same bits in area that matches
630       // NOTE: The second argument is the ending BIT NUMBER
631       // NOT the number of bits.
632    TUASSERTE(bool, true,withBits.matchBits( withSameBits,0,23));
633 
634       // It is CORRECT that these two fail. Even though the
635       // bits match, the overall length of the bits sets
636       // does NOT match.
637    TUASSERTE(bool,false,withBits.matchBits(withShortBits,0,23));
638    TUASSERTE(bool,false,withBits.matchBits( withLongBits,0,23));
639 
640       // Same bits as withBits, but in different order.
641       // Therefore, same length, but different contents.
642       // In fact, the first TWO entries are swapped, but
643       // the third entry should be the same bits in the
644       // same location.
645    PackedNavBits diffOrder(satID,obsID,navID,rxID,ct);
646 
647    diffOrder.addUnsignedLong(u_i2, u_n2, u_s2);  // 8 bits  (0- 7)
648    diffOrder.addUnsignedLong(u_i1, u_n1, u_s1);  // 16 bits (8-23)
649    diffOrder.addUnsignedLong(u_i3, u_n3, u_s3);
650    diffOrder.trimsize();
651    TUASSERTE(bool,false,withBits.matchBits(diffOrder));
652    TUASSERTE(bool, true,withBits.matchBits(diffOrder,24,31));
653 
654       // Now build some test cases with both metadata AND bits
655    TUCSM("match");
656    PackedNavBits sameAsWithBits(satID,obsID,navID,rxID,ct);
657    sameAsWithBits.addUnsignedLong(u_i1, u_n1, u_s1);
658    sameAsWithBits.addUnsignedLong(u_i2, u_n2, u_s2);
659    sameAsWithBits.addUnsignedLong(u_i3, u_n3, u_s3);
660    sameAsWithBits.trimsize();
661 
662    PackedNavBits diffMetaWithBits(satID2,obsID2,rxID2,ctPlus);
663    diffMetaWithBits.addUnsignedLong(u_i1, u_n1, u_s1);
664    diffMetaWithBits.addUnsignedLong(u_i2, u_n2, u_s2);
665    diffMetaWithBits.addUnsignedLong(u_i3, u_n3, u_s3);
666    diffMetaWithBits.trimsize();
667 
668       // Same SatID, ObsID, and NavID but different Rx and XmitTime
669       // and with same bits 24-31 but different bits 0-23.
670    PackedNavBits diffMetaWithBits2(satID,obsID,navID,rxID2,ctPlus);
671    diffMetaWithBits2.addUnsignedLong(u_i2, u_n2, u_s2);
672    diffMetaWithBits2.addUnsignedLong(u_i1, u_n1, u_s1);
673    diffMetaWithBits2.addUnsignedLong(u_i3, u_n3, u_s3);
674    diffMetaWithBits2.trimsize();
675 
676    TUASSERTE(bool,  true,withBits.match(sameAsWithBits));
677    TUASSERTE(bool, false,withBits.match(diffMetaWithBits));
678    TUASSERTE(bool, false,withBits.match(diffMetaWithBits2));
679    TUASSERTE(bool, false,withBits.match(diffMetaWithBits2,0,-1,checkSATOBS));
680    TUASSERTE(bool,  true,withBits.match(diffMetaWithBits2,24,31,checkSATOBS));
681 
682    TUCSM("operator==");
683    TUASSERTE(bool,  true,withBits==sameAsWithBits);
684    TUASSERTE(bool, false,withBits==diffMetaWithBits2);
685 
686    TUCSM("operator<");
687    PackedNavBits rightTest(satID,obsID,navID,rxID2,ct);
688    PackedNavBits leftSmall(satID,obsID,navID,rxID2,ct);
689    PackedNavBits leftLarge(satID,obsID,navID,rxID2,ct);
690    PackedNavBits leftEqual(satID,obsID,navID,rxID2,ct);
691    PackedNavBits longer(satID,obsID,navID,rxID2,ct);
692    rightTest.rawBitInput("035 0xFFFFFF0F 0xE0000000");
693    leftEqual.rawBitInput("035 0xFFFFFF0F 0xE0000000");
694    leftSmall.rawBitInput("035 0xFFFFFE0F 0xE0000000");
695    leftLarge.rawBitInput("035 0xFFFFFFFF 0xE0000000");
696 
697       // Ovbserved real-world case that trggered a failure.
698       // Right is greater than left at bit 5, but less than
699       // at bit 6.   The greater than was not causing false, so
700       // when the code got to bit 6, it would (incorrectly) return
701       // true.
702    PackedNavBits leftMixed(satID,obsID,navID,rxID2,ct);
703    PackedNavBits rightMixed(satID,obsID,navID,rxID2,ct);
704    leftMixed.rawBitInput( "035 0x03019AA1 0x00000000");
705    rightMixed.rawBitInput("035 0x057E77B8 0x00000000");
706    longer.rawBitInput(   "064 0x00000000 0x00000000");
707    TUASSERTE(bool,  true, leftSmall<rightTest);
708    TUASSERTE(bool, false, leftEqual<rightTest);
709    TUASSERTE(bool, false, leftLarge<rightTest);
710    TUASSERTE(bool,  true, leftSmall<longer);
711    TUASSERTE(bool, false, longer<leftSmall);
712    TUASSERTE(bool,  true, leftMixed<rightMixed);
713    TUASSERTE(bool, false, rightMixed<leftMixed);
714 
715    TURETURN();
716 }
717 
718    // These test cases are designed to test the methods
719    // test were added to enable more flexible use of
720    // PackedNavBits in testing:
721    //    invert()
722    //    copyBits()
723    //    insertUnsignedBits()
724    //
725 unsigned PackedNavBits_T::
ancillaryMethods()726 ancillaryMethods()
727 {
728    TUDEF("PackedNavBits", "ancillary methods");
729 
730       // -------------------------------------------------------------
731       // First test the invert() method.
732       // Create a sample PackedNavBits.
733       // At this point, the "packed bits" section of
734       // this object is empty.  We are focused on testing
735       // the metadata handling.
736    SatID satID(1, SatelliteSystem::GPS);
737    ObsID obsID( ObservationType::NavMsg, CarrierBand::L2, TrackingCode::L2CML );
738    NavID navID(satID,obsID);
739    std::string rxID = "rx1";
740    CommonTime ct = CivilTime( 2011, 6, 2, 12, 14, 44.0, TimeSystem::GPS );
741    PackedNavBits copyUpright(satID,obsID,navID,rxID,ct);
742 
743       // Next add some bits with a fixed pattern.
744       // Make a copy with a given bit pattern,....
745    unsigned long uword = 0xAAAAAAAA;
746    try
747    {
748       copyUpright.addUnsignedLong(uword,32,1);
749       copyUpright.addUnsignedLong(uword,32,1);
750    }
751    catch (InvalidParameter ip)
752    {
753       cout << "Caught an exception" << endl;
754       cout << ip << endl;
755    }
756    copyUpright.trimsize();
757 
758       // Make copy with the inverse bit pattern
759    PackedNavBits copyInverse(satID,obsID,navID,rxID,ct);
760    unsigned long uwordInverse = (~uword) & 0xFFFFFFFF;
761    try
762    {
763       copyInverse.addUnsignedLong(uwordInverse,32,1);
764       copyInverse.addUnsignedLong(uwordInverse,32,1);
765    }
766    catch (InvalidParameter ip)
767    {
768       cout << "Caught an exception" << endl;
769       cout << ip << endl;
770    }
771    copyInverse.trimsize();
772 
773       // Invert the upright and see that the results
774       // matches expectations
775    copyUpright.invert();
776    TUASSERTE(bool,true,copyUpright.matchBits(copyInverse));
777 
778       // -------------------------------------------------------------
779       // Now test copyBits()
780       // Create a PNB with 64 1's and a PNB with 64 0's
781    PackedNavBits allOnes(satID,obsID,navID,rxID,ct);
782    unsigned long uwordOnes = 0xFFFFFFFF;
783    allOnes.addUnsignedLong(uwordOnes,32,1);
784    allOnes.addUnsignedLong(uwordOnes,32,1);
785    allOnes.trimsize();
786 
787    PackedNavBits allZeros(satID,obsID,navID,rxID,ct);
788    unsigned long uwordZeros = 0x00000000;
789    allZeros.addUnsignedLong(uwordZeros,32,1);
790    allZeros.addUnsignedLong(uwordZeros,32,1);
791    allZeros.trimsize();
792 
793       // Copy first and last 16 bits from allZeros to all ones
794    allOnes.copyBits(allZeros,0,15);
795    allOnes.copyBits(allZeros,48,63);
796 
797    PackedNavBits expected(satID,obsID,navID,rxID,ct);
798    unsigned long uword1 = 0x0000FFFF;
799    unsigned long uword2 = 0xFFFF0000;
800    expected.addUnsignedLong(uword1,32,1);
801    expected.addUnsignedLong(uword2,32,1);
802    expected.trimsize();
803 
804    TUASSERTE(bool,true,expected.matchBits(allOnes));
805 
806       // -------------------------------------------------------------
807       // Now test insertUnsignedLong( )
808       // Create a PNB with 96 0's
809    PackedNavBits insertTest(satID,obsID,navID,rxID,ct);
810    insertTest.addUnsignedLong(uwordZeros,32,1);
811    insertTest.addUnsignedLong(uwordZeros,32,1);
812    insertTest.addUnsignedLong(uwordZeros,32,1);
813    insertTest.trimsize();
814 
815    unsigned long fakeSOW = 604800 - 6;
816    unsigned long tenOnes = 0x000003FF;
817 
818       // Insert an unscaled set of 10 1's into bits 20-29
819    insertTest.insertUnsignedLong(tenOnes,20,10,1);
820 
821       // Insert a 17 bit SOW of 604794 scaled by 6
822       // starting at bit 0
823    insertTest.insertUnsignedLong(fakeSOW,0,17,6);
824 
825       // Build an expected PNB
826    PackedNavBits insertExpected(satID,obsID,navID,rxID,ct);
827    insertExpected.addUnsignedLong(fakeSOW,17,6);
828    insertExpected.addUnsignedLong(uwordZeros,3,1);
829    insertExpected.addUnsignedLong(tenOnes,10,1);
830    insertExpected.addUnsignedLong(uwordZeros,32,1);
831    insertExpected.addUnsignedLong(uwordZeros,32,1);
832    insertExpected.addUnsignedLong(uwordZeros, 2,1);
833    insertExpected.trimsize();
834    TUASSERTE(bool,true,insertExpected.matchBits(insertTest));
835 
836    TURETURN();
837 }
838 
main()839 int main()
840 {
841    unsigned errorTotal = 0;
842 
843    PackedNavBits_T testClass;
844 
845    errorTotal += testClass.abstractTest();
846    errorTotal += testClass.realDataTest();
847    errorTotal += testClass.equalityTest();
848    errorTotal += testClass.ancillaryMethods();
849 
850    cout << "Total Failures for " << __FILE__ << ": " << errorTotal << endl;
851 
852    return errorTotal; // Return the total number of errors
853 }
854 
855 
856