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 #include "SP3SatID.hpp"
40 #include "TestUtil.hpp"
41 #include <iostream>
42 #include <string>
43 #include <sstream>
44 
45 class SP3SatID_T
46 {
47 public:
SP3SatID_T()48    SP3SatID_T() {} // Default Constructor, set the precision value
~SP3SatID_T()49    ~SP3SatID_T() {} // Default Desructor
50 
51 //==========================================================================================================================
52 // initializationTest ensures the constructors set the values properly
53 //==========================================================================================================================
initializationTest(void)54    int initializationTest(void)
55    {
56       gpstk::TestUtil testFramework("SP3SatID", "Constructor", __FILE__, __LINE__);
57 
58 
59          //---------------------------------------------------------------------
60          //Does the Explicit Constructor function?
61          //---------------------------------------------------------------------
62       gpstk::SP3SatID Compare1(5, gpstk::SatelliteSystem(1));
63       testFramework.assert(Compare1.id == 5,
64                            "Explicit constructor did not set the correct ID", __LINE__);
65       testFramework.assert(Compare1.system == gpstk::SatelliteSystem(1),
66                            "Explicit constructor did not set the correct SatelliteSystem", __LINE__);
67 
68 
69          //---------------------------------------------------------------------
70          //Does the Default Constructor function?
71          //---------------------------------------------------------------------
72       testFramework.changeSourceMethod("ConstructorDefault");
73       gpstk::SP3SatID Compare2;
74       testFramework.assert(Compare2.id == -1,
75                            "Default constructor did not set the expected ID", __LINE__);
76       testFramework.assert(Compare2.system == gpstk::SatelliteSystem(1),
77                            "Default constructor did not set the expected SatelliteSystem", __LINE__);
78 
79 
80          //---------------------------------------------------------------------
81          //Does the fromString Constructor function?
82          //---------------------------------------------------------------------
83       testFramework.changeSourceMethod("ConstructorFromString");
84       gpstk::SP3SatID Compare3("G 10");
85       testFramework.assert(Compare3.id == 10,
86                            "fromString constructor did not set the correct ID", __LINE__);
87       testFramework.assert(Compare3.system == gpstk::SatelliteSystem(1),
88                            "fromString constructor did not set the correct SatelliteSystem", __LINE__);
89 
90          //Did the constructor throw an exception for an improper string?
91       try
92       {
93          gpstk::SP3SatID Compare4("Z 1");
94          testFramework.assert(false,
95                               "fromString constructor did not throw an exception for an improper string",
96                               __LINE__);
97       }
98       catch(gpstk::Exception& e)
99       {
100          testFramework.assert(true, "fromString threw the expected exception",
101                               __LINE__);
102       }
103 
104          //---------------------------------------------------------------------
105          //Does the SatID Constructor function?
106          //---------------------------------------------------------------------
107       testFramework.changeSourceMethod("ConstructorSatID");
108       gpstk::SatID sat1(7, gpstk::SatelliteSystem(1));
109       gpstk::SP3SatID Compare4(sat1);
110       testFramework.assert(Compare4.id == 7,
111                            "SatID constructor did not set the correct ID", __LINE__);
112       testFramework.assert(Compare4.system == gpstk::SatelliteSystem(1),
113                            "SatID constructor did not set the correct SatelliteSystem", __LINE__);
114 
115       return testFramework.countFails();
116    }
117 
118 
119 //==========================================================================================================================
120 // operatorTest verifies the various operators of the SatID class
121 //==========================================================================================================================
operatorTest(void)122    int operatorTest(void) //including <<
123    {
124       gpstk::TestUtil testFramework( "SatID", "OperatorEquivalence", __FILE__, __LINE__);
125 
126 
127       gpstk::SP3SatID Compare    (5, gpstk::SatelliteSystem(2) );
128       gpstk::SP3SatID Equivalent (5, gpstk::SatelliteSystem(2) );
129       gpstk::SP3SatID LessThanID (2, gpstk::SatelliteSystem(2) );
130       gpstk::SP3SatID DiffSatSys (5, gpstk::SatelliteSystem(3) );
131       gpstk::SP3SatID DiffEvery  (2, gpstk::SatelliteSystem(3) );
132       gpstk::SP3SatID DiffEvery2 (7, gpstk::SatelliteSystem(1) );
133       gpstk::SP3SatID Redirected (6, gpstk::SatelliteSystem(1) );
134 
135          //---------------------------------------------------------------------
136          //Does the == Operator function?
137          //---------------------------------------------------------------------
138       testFramework.assert(  Compare == Equivalent ,
139                              "Equivalence Operator found equivalent objects to not be equal"    , __LINE__);
140       testFramework.assert(!(Compare == LessThanID),
141                            "Equivalence Operator found differing IDs to be equal"             , __LINE__);
142       testFramework.assert(!(Compare == DiffSatSys),
143                            "Equivalence Operator found differing SatteliteSystems to be equal", __LINE__);
144 
145 
146       testFramework.changeSourceMethod("OperatorNotEquals");
147          //---------------------------------------------------------------------
148          //Does the != Operator function?
149          //---------------------------------------------------------------------
150       testFramework.assert(!(Compare != Equivalent),
151                            "Not Equals Operator found equivalent objects to be not equal"    , __LINE__);
152       testFramework.assert(  Compare != LessThanID ,
153                              "Not Equals Operator found differing IDs to be equal"             , __LINE__);
154       testFramework.assert(  Compare != DiffSatSys ,
155                              "Not Equals Operator found differing SatteliteSystems to be equal", __LINE__);
156 
157 
158       testFramework.changeSourceMethod("OperatorLessThan");
159          //---------------------------------------------------------------------
160          //Does the < Operator function?
161          //---------------------------------------------------------------------
162 
163          //ID only comparisons
164       testFramework.assert(!(Compare < LessThanID),
165                            "Less-than Operator found object with greater IDs and same SatSys to be less-than"
166                            , __LINE__);
167       testFramework.assert(  LessThanID < Compare ,
168                              "Less-than Operator found object with lesser IDs and same SatSys to not be less-than",
169                              __LINE__);
170       testFramework.assert(!(Compare < Equivalent),
171                            "Less-than Operator found equivalent object to be less-than"
172                            , __LINE__);
173 
174          //SatelliteSystem only comparisons
175       testFramework.assert(  Compare < DiffSatSys ,
176                              "Less-than Operator found object with lesser SatSys and same IDs to not be less-than",
177                              __LINE__);
178       testFramework.assert(!(DiffSatSys < Compare),
179                            "Less-than Operator found object with greater SatSys and same IDs to be less-than"
180                            , __LINE__);
181 
182          //Completely different comparisons
183       testFramework.assert(  Compare < DiffEvery  ,
184                              "Less-than Operator found object with lesser SatSys and greater ID to not be less-than",
185                              __LINE__);
186       testFramework.assert(!(DiffEvery < Compare) ,
187                            "Less-than Operator found object with greater SatSys and lesser ID to be less-than"
188                            , __LINE__);
189       testFramework.assert(!(Compare < DiffEvery2),
190                            "Less-than Operator found object with greater SatSys and lesser ID to be less-than"
191                            , __LINE__);
192       testFramework.assert(  DiffEvery2 < Compare ,
193                              "Less-than Operator found object with lesser SatSys and greater ID to not be less-than",
194                              __LINE__);
195 
196       testFramework.changeSourceMethod("OperatorGreaterThan");
197          //---------------------------------------------------------------------
198          //Does the > Operator function?
199          //---------------------------------------------------------------------
200 
201          //ID only comparisons
202       testFramework.assert( (Compare > LessThanID),
203                             "Greater-than Operator found object with greater IDs and same SatSys to not be greater-than",
204                             __LINE__);
205       testFramework.assert(!(LessThanID > Compare),
206                            "Greater-than Operator found object with lesser IDs and same SatSys to be greater-than"
207                            , __LINE__);
208       testFramework.assert(!(Compare > Equivalent),
209                            "Greater-than Operator found equivalent object to be greater-than"
210                            , __LINE__);
211 
212          //SatelliteSystem only comparisons
213       testFramework.assert(!(Compare > DiffSatSys),
214                            "Greater-than Operator found object with lesser SatSys and same IDs to be greater-than"
215                            , __LINE__);
216       testFramework.assert( (DiffSatSys > Compare),
217                             "Greater-than Operator found object with greater SatSys and same IDs to not be greater-than",
218                             __LINE__);
219 
220          //Completely different comparisons
221       testFramework.assert(!(Compare > DiffEvery) ,
222                            "Greater-than Operator found object with lesser SatSys and greater ID to be greater-than"
223                            , __LINE__);
224       testFramework.assert( (DiffEvery > Compare) ,
225                             "Greater-than Operator found object with greater SatSys and lesser ID to not be greater-than",
226                             __LINE__);
227       testFramework.assert( (Compare > DiffEvery2),
228                             "Greater-than Operator found object with greater SatSys and lesser ID to not be greater-than",
229                             __LINE__);
230       testFramework.assert(!(DiffEvery2 > Compare),
231                            "Greater-than Operator found object with lesser SatSys and greater ID to be greater-than"
232                            , __LINE__);
233 
234 
235       testFramework.changeSourceMethod("OperatorLessThanOrEqualTo");
236          //---------------------------------------------------------------------
237          //Does the <= Operator function?
238          //---------------------------------------------------------------------
239 
240          //ID only comparisons
241       testFramework.assert(!(Compare <= LessThanID),
242                            "Less-than-or-equal-to Operator found object with greater IDs and same SatSys to be less-than-or-equal-to"
243                            , __LINE__);
244       testFramework.assert(  LessThanID <= Compare ,
245                              "Less-than-or-equal-to Operator found object with lesser IDs and same SatSys to not be less-than-or-equal-to",
246                              __LINE__);
247       testFramework.assert( (Compare <= Equivalent),
248                             "Less-than-or-equal-to Operator found equivalent object to not be less-than-or-equal-to"
249                             , __LINE__);
250 
251          //SatelliteSystem only comparisons
252       testFramework.assert(  Compare <= DiffSatSys ,
253                              "Less-than-or-equal-to Operator found object with lesser SatSys and same IDs to not be less-than-or-equal-to",
254                              __LINE__);
255       testFramework.assert(!(DiffSatSys <= Compare),
256                            "Less-than-or-equal-to Operator found object with greater SatSys and same IDs to be less-than-or-equal-to"
257                            , __LINE__);
258 
259          //Completely different comparisons
260       testFramework.assert(  Compare <= DiffEvery  ,
261                              "Less-than-or-equal-to Operator found object with lesser SatSys and greater ID to not be less-than-or-equal-to",
262                              __LINE__);
263       testFramework.assert(!(DiffEvery <= Compare) ,
264                            "Less-than-or-equal-to Operator found object with greater SatSys and lesser ID to be less-than-or-equal-to"
265                            , __LINE__);
266       testFramework.assert(!(Compare <= DiffEvery2),
267                            "Less-than-or-equal-to Operator found object with greater SatSys and lesser ID to be less-than-or-equal-to"
268                            , __LINE__);
269       testFramework.assert(  DiffEvery2 <= Compare ,
270                              "Less-than-or-equal-to Operator found object with lesser SatSys and greater ID to not be less-than-or-equal-to",
271                              __LINE__);
272 
273       testFramework.changeSourceMethod("OperatorGreaterThanOrEqualTo");
274          //---------------------------------------------------------------------
275          //Does the >= Operator function?
276          //---------------------------------------------------------------------
277 
278          //ID only comparisons
279       testFramework.assert( (Compare >= LessThanID),
280                             "Greater-than-or-equal-to Operator found object with greater IDs and same SatSys to not be greater-than-or-equal-to",
281                             __LINE__);
282       testFramework.assert(!(LessThanID >= Compare),
283                            "Greater-than-or-equal-to Operator found object with lesser IDs and same SatSys to be greater-than-or-equal-to"
284                            , __LINE__);
285       testFramework.assert( (Compare >= Equivalent),
286                             "Greater-than-or-equal-to Operator found equivalent object to not be greater-than-or-equal-to"
287                             , __LINE__);
288 
289          //SatelliteSystem only comparisons
290       testFramework.assert(!(Compare >= DiffSatSys),
291                            "Greater-than-or-equal-to Operator found object with lesser SatSys and same IDs to be greater-than-or-equal-to"
292                            , __LINE__);
293       testFramework.assert( (DiffSatSys >= Compare),
294                             "Greater-than-or-equal-to Operator found object with greater SatSys and same IDs to not be greater-than-or-equal-to",
295                             __LINE__);
296 
297          //Completely different comparisons
298       testFramework.assert(!(Compare >= DiffEvery) ,
299                            "Greater-than-or-equal-to Operator found object with lesser SatSys and greater ID to be greater-than-or-equal-to"
300                            , __LINE__);
301       testFramework.assert( (DiffEvery >= Compare) ,
302                             "Greater-than-or-equal-to Operator found object with greater SatSys and lesser ID to not be greater-than-or-equal-to",
303                             __LINE__);
304       testFramework.assert( (Compare >= DiffEvery2),
305                             "Greater-than-or-equal-to Operator found object with greater SatSys and lesser ID to not be greater-than-or-equal-to",
306                             __LINE__);
307       testFramework.assert(!(DiffEvery2 >= Compare),
308                            "Greater-than-or-equal-to Operator found object with lesser SatSys and greater ID to be greater-than-or-equal-to"
309                            , __LINE__);
310 
311 
312       testFramework.changeSourceMethod("OperatorRedirect");
313          //---------------------------------------------------------------------
314          //Does the << Operator function?
315          //---------------------------------------------------------------------
316       std::string outputString, compareString;
317       std::stringstream outputStream;
318       outputStream << Redirected;
319       outputString = outputStream.str();
320       compareString = "G06";
321       testFramework.assert(outputString == compareString,
322                            "Redirect operator did not function properly", __LINE__);
323 
324 
325       return testFramework.countFails();
326    }
327 
328 
329 //==========================================================================================================================
330 // fromStringTest verifies that the fromString method sets the SP3SatID attributes appropriately
331 //==========================================================================================================================
fromStringTest(void)332    int fromStringTest(void)
333    {
334       gpstk::TestUtil testFramework("SP3SatID", "fromString", __FILE__, __LINE__);
335 
336       std::string inputStringArray[12] = {"7", "07", "30", "E10", "E100", "G08", "E08", "R08", "L08", "C08", "J08", "M08"};
337       int         expectedID[12]       = {  7,    7,   30,    10,    100,     8,     8,     8,     8,     8,    200,     8};
338       gpstk::SatelliteSystem expectedSatSysArray[12] =
339          {
340             gpstk::SatelliteSystem::GPS,
341             gpstk::SatelliteSystem::GPS,
342             gpstk::SatelliteSystem::GPS,
343             gpstk::SatelliteSystem::Galileo,
344             gpstk::SatelliteSystem::Galileo,
345             gpstk::SatelliteSystem::GPS,
346             gpstk::SatelliteSystem::Galileo,
347             gpstk::SatelliteSystem::Glonass,
348             gpstk::SatelliteSystem::LEO,
349             gpstk::SatelliteSystem::BeiDou,
350             gpstk::SatelliteSystem::QZSS,
351             gpstk::SatelliteSystem::Mixed
352          };
353       gpstk::SP3SatID Compare;
354 
355 
356       for (int i = 0; i < (sizeof(expectedID)/sizeof(expectedID[0])); i++)
357       {
358          try
359          {
360             Compare.fromString(inputStringArray[i]);
361          }
362          catch(gpstk::Exception& e)
363          {
364             std::stringstream s;
365             s << "Exception in fromString call on input: " << inputStringArray[i];
366             testFramework.assert(false,
367                                  s.str(),__LINE__);
368          }
369 
370          testFramework.assert(Compare.id == expectedID[i],
371                               "fromString did not set the correct ID", __LINE__);
372          testFramework.assert(Compare.system == expectedSatSysArray[i],
373                               "fromString did not set the correct SatelliteSystem", __LINE__);
374       }
375 
376          //Additional check to ensure fromString cannot set an improper string
377       try
378       {
379          gpstk::SP3SatID Compare4("Z 1");
380          testFramework.assert(false,
381                               "fromString did not throw an exception for an improper string", __LINE__);
382       }
383       catch(gpstk::Exception& e)
384       {
385          testFramework.assert(true, "fromString threw the expected exception",
386                               __LINE__);
387       }
388 
389       return testFramework.countFails();
390    }
391 
392 
393 //==========================================================================================================================
394 // toStringTest checks that a SP3SatID object can be output as a string
395 //==========================================================================================================================
toStringTest(void)396    int toStringTest(void)
397    {
398       gpstk::TestUtil testFramework("SP3SatID", "toString", __FILE__, __LINE__);
399       std::stringstream s;
400       std::string outputString1, compareString1;
401       std::string outputString2, compareString2;
402       std::string outputString3, compareString3;
403       std::string outputString4, compareString4;
404       std::string outputString5, compareString5;
405       std::string outputString6, compareString6;
406       std::string outputString7, compareString7;
407       std::string outputString8, compareString8;
408       std::string outputString9, compareString9;
409 
410       try
411       {
412          gpstk::SP3SatID Compare1(5, gpstk::SatelliteSystem::GPS);
413          outputString1 = Compare1.toString();
414          compareString1 = "G05";
415          s.str("");
416          s  << "toString did not return the expected string, exp: "
417             << compareString1 << ", but got: " << outputString1;
418          testFramework.assert(outputString1 == compareString1,
419                               s.str(), __LINE__);
420       }
421       catch(gpstk::Exception& e)
422       {
423          s.str("Exception in toString call, expected output: ");
424          s << compareString1;
425          testFramework.assert(false,
426                               s.str(),__LINE__);
427       }
428 
429       try
430       {
431          gpstk::SP3SatID Compare2(20, gpstk::SatelliteSystem::Galileo);
432          outputString2 = Compare2.toString();
433          compareString2 = "E20";
434          s.str("");
435          s  << "toString did not return the expected string, exp: "
436             << compareString2 << ", but got: " << outputString2;
437          testFramework.assert(outputString2 == compareString2,
438                               s.str(), __LINE__);
439       }
440       catch(gpstk::Exception& e)
441       {
442          s.str("Exception in toString call, expected output: ");
443          s << compareString2;
444          testFramework.assert(false,
445                               s.str(),__LINE__);
446       }
447 
448       try
449       {
450          gpstk::SP3SatID Compare3(-5, gpstk::SatelliteSystem::GPS);
451          outputString3 = Compare3.toString();
452          compareString3 = "G-5";
453          s.str("");
454          s  << "toString did not return the expected string, exp: "
455             << compareString3 << ", but got: " << outputString3;
456          testFramework.assert(outputString3 == compareString3,
457                               s.str(), __LINE__);
458       }
459       catch(gpstk::Exception& e)
460       {
461          s.str("Exception in toString call, expected output: ");
462          s << compareString3;
463          testFramework.assert(false,
464                               s.str(),__LINE__);
465       }
466 
467       try
468       {
469          gpstk::SP3SatID Compare4(1, gpstk::SatelliteSystem::Glonass);
470          outputString4 = Compare4.toString();
471          compareString4 = "R01";
472          s.str("");
473          s  << "toString did not return the expected string, exp: "
474             << compareString4 << ", but got: " << outputString4;
475          testFramework.assert(outputString4 == compareString4,
476                               s.str(), __LINE__);
477       }
478       catch(gpstk::Exception& e)
479       {
480          s.str("Exception in toString call, expected output: ");
481          s << compareString4;
482          testFramework.assert(false,
483                               s.str(),__LINE__);
484       }
485 
486       try
487       {
488          gpstk::SP3SatID Compare5(1, gpstk::SatelliteSystem::LEO);
489          outputString5 = Compare5.toString();
490          compareString5 = "L01";
491          s.str("");
492          s  << "toString did not return the expected string, exp: "
493             << compareString5 << ", but got: " << outputString5;
494          testFramework.assert(outputString5 == compareString5,
495                               s.str(), __LINE__);
496       }
497       catch(gpstk::Exception& e)
498       {
499          s.str("Exception in toString call, expected output: ");
500          s << compareString5;
501          testFramework.assert(false,
502                               s.str(),__LINE__);
503       }
504 
505       try
506       {
507          gpstk::SP3SatID Compare6(1, gpstk::SatelliteSystem::BeiDou);
508          outputString6 = Compare6.toString();
509          compareString6 = "C01";
510          s.str("");
511          s  << "toString did not return the expected string, exp: "
512             << compareString6 << ", but got: " << outputString6;
513          testFramework.assert(outputString6 == compareString6,
514                               s.str(), __LINE__);
515       }
516       catch(gpstk::Exception& e)
517       {
518          s.str("Exception in toString call, expected output: ");
519          s << compareString6;
520          testFramework.assert(false,
521                               s.str(),__LINE__);
522       }
523 
524       try
525       {
526          gpstk::SP3SatID Compare7(193, gpstk::SatelliteSystem::QZSS);
527          outputString7 = Compare7.toString();
528          compareString7 = "J01";
529          s.str("");
530          s  << "toString did not return the expected string, exp: "
531             << compareString7 << ", but got: " << outputString7;
532          testFramework.assert(outputString7 == compareString7,
533                               s.str(), __LINE__);
534       }
535       catch(gpstk::Exception& e)
536       {
537          s.str("Exception in toString call, expected output: ");
538          s << compareString7;
539          testFramework.assert(false,
540                               s.str(),__LINE__);
541       }
542 
543       try
544       {
545          gpstk::SP3SatID Compare8(1, gpstk::SatelliteSystem::Mixed);
546          outputString8 = Compare8.toString();
547          compareString8 = "M01";
548          s.str("");
549          s  << "toString did not return the expected string, exp: "
550             << compareString8 << ", but got: " << outputString8;
551          testFramework.assert(outputString8 == compareString8,
552                               s.str(), __LINE__);
553       }
554       catch(gpstk::Exception& e)
555       {
556          s.str("Exception in toString call, expected output: ");
557          s << compareString8;
558          testFramework.assert(false,
559                               s.str(),__LINE__);
560       }
561 
562       // finally, test that bad system inputs cause '?' outputs from toString
563       try
564       {
565          gpstk::SP3SatID Compare9(1, gpstk::SatelliteSystem::Unknown);
566          outputString9 = Compare9.toString();
567          compareString9 = "?-1";
568          s.str("");
569          s  << "toString did not return the expected string, exp: "
570             << compareString9 << ", but got: " << outputString9;
571          testFramework.assert(outputString9 == compareString9,
572                               s.str(), __LINE__);
573       }
574       catch(gpstk::Exception& e)
575       {
576          s.str("Exception in toString call, expected output: ");
577          s << compareString9;
578          testFramework.assert(false,
579                               s.str(),__LINE__);
580       }
581 
582       return testFramework.countFails();
583    }
584 
585 };
586 
587 
main()588 int main() //Main function to initialize and run all tests above
589 {
590    SP3SatID_T testClass;
591    int check = 0,errorCounter = 0;
592 
593    check = testClass.initializationTest();
594    errorCounter += check;
595 
596    check = testClass.operatorTest();
597    errorCounter += check;
598 
599    check = testClass.fromStringTest();
600    errorCounter += check;
601 
602    check = testClass.toStringTest();
603    errorCounter += check;
604 
605    std::cout << "Total Failures for " << __FILE__ << ": " << errorCounter <<
606              std::endl;
607 
608    return errorCounter;
609 }
610