4 Copyright (c) 2021 Mario Konrad (mario.konrad@gmx.net)
11 This is a C++ library for **MAR**itime **NAV**igation purposes.
13 It supports (partially):
16 - SeaTalk (Raymarine device communication)
17 - Reading data from serial ports (NMEA, SeaTalk)
18 - Basic geodesic functions, suitable for martime navigation.
20 See chapter _Features_ for a complete and detailed list.
27 There are already implementaions for reading and writing NMEA-0183 or AIS.
28 The goal of this library is
29 - to have an implementation in modern C++
30 - easy to use API (std lib like, integrating well)
31 - unit tested (high test coverage)
32 - trivial integration into projects (liberal license, as few dependencies as
34 - (more or less) well documented
35 - (more or less) complete, as far as information is freely available
45 Supported sentences for NMEA-0183 (read and write):
47 - AAM: Waypoint Arrival Alarm
48 - ACK: Acknowledge Alarm
49 - ALM: GPS Almanac Data
50 - ALR: Set Alarm State
51 - APB: Autopilot Sentence "B"
52 - BEC: Bearing and Distance to Waypoint
53 - BOD: Bearing - Waypoint to Waypoint
54 - BWC: Bearing & Distance to Waypoint - Geat Circle
55 - BWR: Bearing and Distance to Waypoint - Rhumb Line
56 - BWW: Bearing - Waypoint to Waypoint
57 - DBT: Depth Below Transducer
59 - DSC: Digital Selective Calling Information (**experimental**)
60 - DSE: Extended DSC (**experimental**)
61 - DTM: Datum Reference
62 - FSI: Frequency Set Information
63 - GBS: GPS Satellite Fault Detection
64 - GGA: Global Positioning System Fix Data
65 - GLC: Geographic Position, Loran-C
66 - GLL: Geographic Position - Latitude/Longitude
68 - GRS: GPS Range Residuals
69 - GSA: Geographic Position - Latitude/Longitude
70 - GST: GPS Pseudorange Noise Statistics
71 - GSV: Satellites in view
72 - HDG: Heading - Deviation & Variation
74 - HFB: Trawl Headrope to Footrope and Bottom
75 - HSC: Heading Steering Command
76 - ITS: Trawl Door Spread 2 Distance
77 - LCD: Loran-C Signal Data
79 - MSK: Control for a Beacon Receiver
80 - MSS: Beacon Receiver Status
81 - MTW: Mean Temperature of Water
82 - MWD: Wind Direction and Speed
83 - MWV: Wind Speed and Angle
85 - RMA: Recommended Minimum Navigation Information
86 - RMB: Recommended Minimum Navigation Information
87 - RMC: Recommended Minimum Navigation Information
90 - RSA: Rudder Sensor Angle
91 - RSD: RADAR System Data (**experimental**)
93 - SFI: Scanning Frequency Information
94 - STN: Multiple Data ID
95 - TDS: Trawl Door Spread Distance
96 - TEP: Transit Satellite Predicted Elevation
97 - TFI: Trawl Filling Indicator
98 - TLL: Target Latitude and Longitude
99 - TPC: Trawl Position Cartesian Coordinates
100 - TPR: Trawl Position Relative Vessel
101 - TPT: Trawl Position True
102 - TTM: Tracked Target Message
103 - VBW: Dual Ground/Water Speed
104 - VDM: AIS VHF Data-Link Message
105 - VDO: AIS VHF Data-Link Own-Vessel Report
107 - VHW: Water speed and heading
108 - VLW: Distance Traveled through Water
109 - VPW: Speed - Measured Parallel to Wind
110 - VTG: Track made good and Ground speed
111 - WCV: Waypoint Closure Velocity
112 - WNC: Distance - Waypoint to Waypoint
113 - WPL: Waypoint Location
114 - XDR: Transducer Measurement
115 - XTE: Cross-Track Error, Measured
116 - XTR: Cross Track Error - Dead Reckoning
117 - ZDA: Time & Date - UTC, day, month, year and local time zone
118 - ZDL: Time and Distance to Variable Point
119 - ZFO: UTC & Time from origin Waypoint
120 - ZPI - Arrival time at point of interest
121 - ZTG: UTC & Time to Destination Waypoint
123 Obsolete (according to [NMEA Revealed]) but implemented:
125 - APA: Autopilot Sentence "A"
126 - DBK: Depth Below Keel
127 - GTD: Geographic Location in Time Differences
128 - HDM: Heading - Magnetic (obsolete as of 2009)
129 - MTA: Air Temperature
130 - R00: Waypoints in active route
131 - VWE: Wind Track Efficiency
132 - VWR: Relative Wind Speed and Angle.
133 - WDC: Distance to Waypoint
134 - WDR: Distance to Waypoint, Rumb line
135 - ZFI: Elapsed time since point of interest
137 - ZTA: UTC & Estimated arrival time at point of interest
138 - ZTE: UTC & Estimated remaining time to event
142 - PGRME: Garmin Estimated Error
143 - PGRMM: Garmin Map Datum
144 - PGRMZ: Garmin Altitude Information
145 - STALK: SeaTalk Raw Format
149 - Tag Block Support (generic for all sentences)
154 Supported messages for AIS (decode and encode):
156 - Type 01: Position Report Class A
157 - Type 02: Position Report Class A (Assigned Schedule)
158 - Type 03: Position Report Class A (Response to Interrogation)
159 - Type 04: Base Station Report
160 - Type 05: Static and Voyage Related Data
161 - Type 06: Binary Addressed Message
162 - Type 07: Binary Acknowledge
163 - Type 08: Binary Broadcast Message
164 - Type 09: Standard SAR Aircraft Position Report
165 - Type 10: UTC/Date Inquiry
166 - Type 11: UTC/Date Response
167 - Type 12: Addressed Safety-Related Message
168 - Type 13: Safety-Related Acknowledgement
169 - Type 14: Safety-Related Broadcast Message
170 - Type 17: DGNSS Broadcast Binary Message
171 - Type 18: Standard Class B CS Position Report
172 - Type 19: Extended Class B CS Position Report
173 - Type 20: Data Link Management
174 - Type 21: Aid-to-Navigation Report
175 - Type 22: Channel Management
176 - Type 23: Group Assignment Command
177 - Type 24: Static Data Report (part A and B, norma and auxiliary vessel)
179 Supported payload of binary message 08:
180 - 001/11: Meteorological and Hydrological Data (IMO236)
181 - 200/10: Inland ship static and voyage related data (Inland AIS)
185 Suported messages for SeaTalk (decode and encode):
187 - Type 00: depth below transducer
188 - Type 01: equipment id
189 - Type 05: Engine RPM and PITCH
190 - Type 10: apparent wind angle
191 - Type 11: apparent wind speed
192 - Type 20: speed through water
193 - Type 21: trip mileage
194 - Type 22: total mileage
195 - Type 23: water temperature 1
196 - Type 24: Display unit for Mileage and Speed
197 - Type 25: total and trip log
198 - Type 26: Speed through Water
199 - Type 27: water temperature 2
200 - Type 30: Set Lamp Intensity
201 - Type 36: Cancel MOB condition
202 - Type 38: Codelock data (**experimental**)
203 - Type 50: LAT Postion
204 - Type 51: LON Postion
205 - Type 52: Speed over Ground
206 - Type 53: Magnetic Course in Degrees
210 - Type 59: Set Count Down Timer (sent by ST60)
211 - Type 65: Select Fathom display unit for depth display (see message 00)
212 - Type 66: Wind Alarm
213 - Type 6C: Second equipment-ID
215 - Type 87: Response Level
216 - Type 89: Compass heading (sent by ST40 compass instrument)
221 - Reading data from serial ports (NMEA, SeaTalk)
224 ### Geodesic Functions
226 Basic geodesic functions, suitable for martime navigation.
228 - Calculation of CPA (closest point of approach)
229 and TCPA (time to closest point of approach)
230 - Distance of two points on a sphere
231 - Distance of two points on an ellipsoid using formula of Vincenty
232 - Distance of two points on an ellipsoid using formula of Lambert
240 More examples [here](examples/README.md).
242 ### Parse NMEA Sentence
245 using namespace marnav;
247 auto sentence = nmea::make_sentence(
248 "$GPRMC,201034,A,4702.4040,N,00818.3281,E,0.0,328.4,260807,0.6,E,A*17");
249 std::cout << sentence->tag() << "\n";
250 auto rmc = nmea::sentence_cast<nmea::rmc>(sentence);
251 std::cout << "latitude : " << nmea::to_string(rmc->get_latitude()) << "\n";
252 std::cout << "longitude: " << nmea::to_string(rmc->get_longitude()) << "\n";
255 Create a specific sentence directly:
258 using namespace marnav;
260 auto rmc = nmea::create_sentence<nmea::rmc>(
261 "$GPRMC,201034,A,4702.4040,N,00818.3281,E,0.0,328.4,260807,0.6,E,A*17");
262 std::cout << "latitude : " << nmea::to_string(rmc.get_latitude()) << "\n";
263 std::cout << "longitude: " << nmea::to_string(rmc.get_longitude()) << "\n";
266 ### Write NMEA Sentence
270 mtw.set_temperature(units::celsius{22.5});
271 std::string data = nmea::to_string(mtw);
274 ### Parse AIS Message from NMEA data
277 using namespace marnav;
279 // received sentences
280 const std::vector<std::string> received_strings
281 = {"!AIVDM,2,1,3,B,55P5TL01VIaAL@7WKO@mBplU@<PDhh000000001S;AJ::4A80?4i@E53,0*3E",
282 "!AIVDM,2,2,3,B,1@0000000000000,2*55"};
284 // parse NMEA sentences
285 std::vector<std::unique_ptr<nmea::sentence>> sentences;
286 for (auto const & txt : received_strings) {
287 auto sentence = nmea::make_sentence(txt);
288 if (sentence->id() == nmea::sentence_id::VDM) {
289 sentences.push_back(std::move(sentence));
293 // parse and and process AIS messags
294 auto payload = nmea::collect_payload(sentences.begin(), sentences.end());
295 auto message = ais::make_message(payload);
296 if (message->type() == ais::message_id::static_and_voyage_related_data) {
297 auto report = ais::message_cast<ais::message_05>(message);
298 std::cout << "shipname: " << report->get_shipname() << "\n";
299 std::cout << "callsign: " << report->get_callsign() << "\n";
303 ### Create NMEA sentences from AIS data
306 using namespace marnav;
309 ais::message_01 pos_report;
310 pos_report.set_sog(units::knots{8.2});
311 // ... most data not shown here
314 auto payload = ais::encode_message(pos_report);
316 // create NMEA sentences
317 for (uint32_t fragment = 0; fragment < payload.size(); ++fragment) {
319 vdm.set_n_fragments(payload.size());
320 vdm.set_fragment(fragment + 1);
321 vdm.set_radio_channel(nmea::ais_channel::B);
322 vdm.set_payload(payload[fragment]);
324 // collect, send or do something with the sentence...
325 std::string s = nmea::to_string(vdm);
326 std::cout << s << "\n";
330 or simply use `nmea::make_vdms`:
333 using namespace marnav;
336 ais::message_01 pos_report;
337 pos_report.set_sog(units::knots{8.2});
338 // ... most data not shown here
341 auto payload = ais::encode_message(pos_report);
343 // create NMEA sentences
344 auto sentences = nmea::make_vdms(payload);
346 // process sentences, somehow...
347 for (auto const & sentence : sentences) {
348 std::cout << nmea::to_string(*sentence) << "\n";
357 This chapter describes the requirements in order to build the library.
358 Tools and their versions are listed below, newer/older/other tools
359 (i.e. compilers, etc.) may work, but not tested.
378 Tools needed to build the library:
379 - cmake 3.19 or newer
381 Tools needed to develop the library:
385 Tools needed to build the documentation:
388 - LaTeX (there are formulas!)
390 Optional used for development:
391 - lcov / genhtml, c++filt
393 - clang-tools (analyzer)
397 Optional (no core dependency):
398 - Boost.ASIO (used only for some examples)
399 - Qt 5 (used only for some examples)
404 There are no other dependencies despite the standard library (C++17)
405 to build this library.
412 The following build types `-DCMAKE_BUILD_TYPE=x` are possible:
418 - `ENABLE_STATIC` : enables static build, if `OFF`, a shared library is being built.
420 - `ENABLE_PROFILING` : enables profiling for `gprof`
421 - `ENABLE_BENCHMARK` : enables benchmarking (disables some optimization)
422 - `ENABLE_SANITIZER` : enables address and undefined sanitizers
425 - `ENABLE_IO` : enables IO support. Default: `ON`
428 - `ENABLE_EXAMPLES`: enables examples. Default: `ON`
429 - `ENABLE_TOOLS`: enables tools. Default: `ON`
430 - `ENABLE_TESTS`: enables unit tests, integration tests and benchmarks. Default: `ON`
431 - `ENABLE_TESTS_BENCHMARK`: enables benchmark tests, enabled only if `ENABLE_TESTS` is also enabled. Default: `ON`
438 cmake -DCMAKE_BUILD_TYPE=Release ..
454 or individual package types:
460 ### Developpers Choice
464 cmake -DCMAKE_BUILD_TYPE=Coverage ..
466 make coverage doc cppcheck
469 ### Static Analysis with Clang
471 There is a script ```bin/static-analysis-clang``` for doing this, there is not yet
472 an integration of clang-tidy in the cmake build.
475 ### Perform Benchmarks
477 Build in `Release` mode, perform individual benchmarks:
481 cmake -DCMAKE_BUILD_TYPE=Release ..
483 test/benchmark_nmea_split
485 Using `perf` to do performance analysis:
489 cmake -DCMAKE_BUILD_TYPE=Release -DENABLE_BENCHMARK=ON ..
491 perf record -g test/benchmark_nmea_split
492 perf report -g 'graph,0.5,caller'
497 There is a helper script ```bin/check-format``` which uses ```clang-format``` to
498 check the formatting of all files in the directories containing code (```src```,
499 ```test``` and ```examples```). This script can be used manually:
503 or used as git pre-commit hook:
506 ln -s ../../bin/check-format pre-commit
508 which prevents a commit if there are files not complying with the formatting
509 rules. Be aware of using the script as pre-commit hook, the checking can take
518 Mario Konrad (mario.konrad@gmx.net) with help from others.
520 Search the repository for a complete list:
522 git log --format=%an | sort -u
529 A (non-complete) collection of resources from where information was gathered.
531 - [NMEA Revealed](http://www.catb.org/gpsd/NMEA.html) (by Eric S. Raymond)
532 - [NMEA FAQ](http://www.kh-gps.de/nmea.faq)
533 - [it-digin's blog](http://www.it-digin.com/blog/?cat=4)
534 - [AIVDM/AIVDO Protocol decoding](http://www.catb.org/gpsd/AIVDM.html) (by Eric S. Raymond)
535 - [DSC Position Request](http://www.thehulltruth.com/marine-electronics-forum/43945-dsc-position-request.html)
536 - [NMEA-0183 Sentences DSC,DSE](http://www.cruisersforum.com/forums/f13/nmea-0183-sentences-dsc-dse-124887.html)
537 - [NMEA-0183 Sentence ALR](https://www.cruisersforum.com/forums/f134/opencpn-and-external-nmea0183-alarms-81396.html)
538 - [SerialMon - NMEA 0183 Protocol](http://www.serialmon.com/protocols/nmea0183.html)
539 - [SeaTalk Reference](http://thomasknauf.de/seatalk.htm) (by Thomas Knauf)
540 - [Navigation Center - AIS Standard Class B Equipment Position Report](http://www.navcen.uscg.gov/?pageName=AISMessagesB)
541 - [GPS Forums](http://www.gps-forums.net)
542 - [NMEA Datensaetze](http://www.nmea.de/nmea0183datensaetze.html)
543 - [AIS VDM & VDO Message Decoder](http://www.maritec.co.za/tools/aisvdmvdodecoding/)
544 - [AIS VDM & VDO Message Decoder](http://www.maritec.co.za/tools/aisvdmvdodecoding/)
545 - [Code comments from library NMEA0183](https://github.com/SammyB428/NMEA0183)
553 > The official NMEA 0183 Standard document is not available for free. It was not
554 > consulted at any point during the development of this library. All information
555 > was found from free sources on the internet. This library (especially the NMEA
556 > part) is not derivative work of this standard.
559 See also [LICENSE](LICENSE)
564 Copyright (c) 2021, Mario Konrad
567 Redistribution and use in source and binary forms, with or without
568 modification, are permitted provided that the following conditions are met:
569 1. Redistributions of source code must retain the above copyright
570 notice, this list of conditions and the following disclaimer.
571 2. Redistributions in binary form must reproduce the above copyright
572 notice, this list of conditions and the following disclaimer in the
573 documentation and/or other materials provided with the distribution.
574 3. All advertising materials mentioning features or use of this software
575 must display the following acknowledgement:
576 This product includes software developed by Mario Konrad.
577 4. Neither the name of the software nor the names of its contributors
578 may be used to endorse or promote products derived from this software
579 without specific prior written permission.
581 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
582 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
583 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
584 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
585 FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
586 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
587 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
588 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
589 OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
590 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.