Pico GPS Teseo
Loading...
Searching...
No Matches
teseo.cpp
Go to the documentation of this file.
1module;
2
3#include<algorithm>
4#include <cassert>
5#include <string>
6#include <utility>
7#include <span>
8
9module teseo;
10
11namespace teseo {
12
13nmea_rr teseo::gll_("$PSTMNMEAREQUEST,100000,0\r\n", "GLL,");
14nmea_rr teseo::gsv_("$PSTMNMEAREQUEST,80000,0\r\n", "GSV,");
15nmea_rr teseo::gsa_("$PSTMNMEAREQUEST,4,0\r\n", "GSA,");
16nmea_rr teseo::gga_("$PSTMNMEAREQUEST,2,0\r\n", "GGA,");
17nmea_rr teseo::rmc_("$PSTMNMEAREQUEST,40,0\r\n", "RMC,");
18nmea_rr teseo::vtg_("$PSTMNMEAREQUEST,10,0\r\n", "VTG,");
19
20/*
21when the teseo is preset for i2c according to AN5203,
22init is not required, and you can cut 4s 10ms from the startup sequence
23https://www.st.com/resource/en/application_note/an5203-teseoliv3f--i2c-positioning-sensor--stmicroelectronics.pdf
24*/
26 assert(writer_.is_set());
27 assert(reader_.is_set());
28 assert(resetter_.is_set());
29
30 std::string s;
31 resetter_();
32
33 // stop the engine
34 write("$PSTMGPSSUSPEND\r\n");
35
36 // reset the UART message list
37 write("$PSTMCFGMSGL,0,1,0,0\r\n");
38 // reset the I2C message list
39 write("$PSTMCFGMSGL,3,1,0,0\r\n");
40 // disable the eco-ing message
41 write("$PSTMSETPAR,1227,1,2\r\n");
42
43 // restart the engine
44 write("$PSTMGPSRESTART\r\n");
45 do {
46 read(s);
47 }
48 while(((s.length()) && s.find("$PSTMGPSRESTART") == std::string::npos)); // command successful
49}
50
51bool teseo::parse_multiline_reply(std::span<std::string> strings, const std::string s, unsigned int& count, const nmea_rr& command) {
52 std::size_t message_count = strings.size();
53 std::size_t string_index = 0;
54 std::size_t new_string_index; // intentionally uninitialised
55 std::size_t span_index; // intentionally uninitialised
56 bool valid = false;
57
58 for(span_index = 0; span_index < message_count; span_index++) {
59 new_string_index = s.find("\r\n", string_index);
60 if (new_string_index == s.length() - 2) { // exhausted. This should be the status string
61 valid = s.substr(string_index, s.length() - string_index).starts_with(command.command.substr(0, command.command.length()-2));
62 break;
63 }
64 assert(span_index < message_count);
65 strings[span_index] = s.substr(string_index, (new_string_index + 2) - string_index); // include the separator
66 valid = strings[span_index].length() >= 7 && strings[span_index].substr(3, 4).starts_with(command.signature);
67 if (!valid) {
68 span_index = 0;
69 break;
70 }
71 string_index = new_string_index + 2; // skip the separator
72 }
73 count = span_index; // report the number of retrieved data lines.
74 std::for_each(strings.begin() + count, strings.end(),
75 [](auto &discard) { discard = std::string(); }); // clean out unused positions
76 return valid;
77}
78
79void teseo::write(const std::string& s) {
80 assert(writer_.is_set());
81 writer_(s);
82}
83
84void teseo::read(std::string& s) {
85 assert(reader_.is_set());
86 reader_(s);
87}
88
89bool teseo::ask_nmea(const nmea_rr& command, std::string& s) {
90 bool retval; // intentionally not initialised
91 unsigned int count;
92 write(command.command);
93 read(s);
94 retval = parse_multiline_reply(single_line_parser_, s, count, command);
95 s = single_line_parser_[0];
96 return retval;
97}
98
99bool teseo::ask_nmea_multiple(const nmea_rr& command, std::span<std::string> strings, unsigned int& count) {
100 unsigned int retval; // intentionally not initialised
101 std::string s;
102 write(command.command);
103 read(s);
104 retval = parse_multiline_reply(strings, s, count, command);
105 return retval;
106}
107
108bool teseo::ask_gll(std::string& s) {
109 return ask_nmea(gll_, s);
110}
111
112bool teseo::ask_gsv(std::span<std::string> strings, unsigned int& count) {
113 return ask_nmea_multiple(gsv_, strings, count);
114}
115
116bool teseo::ask_gsa(std::span<std::string> strings, unsigned int& count) {
117 return ask_nmea_multiple(gsa_, strings, count);
118}
119bool teseo::ask_gga(std::string& s) {
120 return ask_nmea(gga_, s);
121}
122
123bool teseo::ask_rmc(std::string& s) {
124 return ask_nmea(rmc_, s);
125}
126
127bool teseo::ask_vtg(std::string& s) {
128 return ask_nmea(vtg_, s);
129}
130
131} // namespace teseo
bool ask_gga(std::string &s)
get GGA request to the Teseo and read reply
Definition teseo.cpp:119
bool ask_gsv(std::span< std::string > strings, unsigned int &count)
get GSV request to the Teseo and read reply
Definition teseo.cpp:112
bool ask_vtg(std::string &s)
get VTG request to the Teseo and read reply
Definition teseo.cpp:127
static bool parse_multiline_reply(std::span< std::string > strings, const std::string s, unsigned int &count, const nmea_rr &command)
utility to parse a multiline Teseo reply into separate strings
Definition teseo.cpp:51
bool ask_gsa(std::span< std::string > strings, unsigned int &count)
get GSA request to the Teseo and read reply
Definition teseo.cpp:116
bool ask_nmea(const nmea_rr &command, std::string &s)
send NMEA request to the Teseo and return reply
Definition teseo.cpp:89
bool ask_rmc(std::string &s)
get RMC request to the Teseo and read reply
Definition teseo.cpp:123
void read(std::string &s)
read data from the Teseo
Definition teseo.cpp:84
bool ask_gll(std::string &s)
get GLL request to the Teseo and read reply
Definition teseo.cpp:108
void initialize()
configure the Teseo for use as a position sensor (optional).
Definition teseo.cpp:25
void write(const std::string &s)
write command to the Teseo
Definition teseo.cpp:79
bool ask_nmea_multiple(const nmea_rr &command, std::span< std::string > strings, unsigned int &count)
send NMEA request to the Teseo and return multi line reply
Definition teseo.cpp:99
void read(::std::string &s)
void write(const ::std::string &s)
Struct holds combinations of NMEA commands and their reply signature validation string.
const std::string command
const std::string signature