aboutsummaryrefslogtreecommitdiffstats
path: root/host/lib/usrp/gps_ctrl.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'host/lib/usrp/gps_ctrl.cpp')
-rw-r--r--host/lib/usrp/gps_ctrl.cpp83
1 files changed, 44 insertions, 39 deletions
diff --git a/host/lib/usrp/gps_ctrl.cpp b/host/lib/usrp/gps_ctrl.cpp
index 98bc90a3f..6f5c75dec 100644
--- a/host/lib/usrp/gps_ctrl.cpp
+++ b/host/lib/usrp/gps_ctrl.cpp
@@ -38,7 +38,7 @@ using namespace boost::algorithm;
using namespace boost::this_thread;
/*!
- * A GPS control for NMEA compatible GPSes
+ * A control for GPSDO devices
*/
class gps_ctrl_impl : public gps_ctrl{
@@ -63,39 +63,41 @@ private:
}
std::string update_cached_sensors(const std::string sensor) {
- if(not gps_detected() || (gps_type != GPS_TYPE_ER_GPSDO)) {
+ if(not gps_detected() || (gps_type != GPS_TYPE_INTERNAL_GPSDO)) {
UHD_MSG(error) << "get_stat(): unsupported GPS or no GPS detected";
return std::string();
}
- std::string msg = _recv();
+ const std::list<std::string> list = boost::assign::list_of("GPGGA")("GPRMC")("SERVO");
static const boost::regex status_regex("\\d\\d-\\d\\d-\\d\\d");
+ std::map<std::string,std::string> msgs;
+
+ // Get all GPSDO messages available
+ // Creating a map here because we only want the latest of each message type
+ for (std::string msg = _recv(); msg.length() > 6; msg = _recv())
+ {
+ // Look for SERVO message
+ if (boost::regex_search(msg, status_regex, boost::regex_constants::match_continuous))
+ msgs["SERVO"] = msg;
+ else
+ msgs[msg.substr(1,5)] = msg;
+ }
+
boost::system_time time = boost::get_system_time();
- if(msg.size() < 6)
- return std::string();
- std::string nmea = msg.substr(1,5);
- const std::list<std::string> list = boost::assign::list_of("GPGGA")("GPRMC");
+ // Update sensors with newly read data
BOOST_FOREACH(std::string key, list) {
- // beginning matches one of the NMEA keys
- if(!nmea.compare(key)) {
- sensors[key] = boost::make_tuple(msg, time, !sensor.compare(key));
- // if this was what we're looking for return it
- return (!sensor.compare(key))? msg : std::string();
- }
+ if (msgs[key].length())
+ sensors[key] = boost::make_tuple(msgs[key], time, !sensor.compare(key));
}
- //We're still here so it's not one of the NMEA strings from above
- if(boost::regex_search(msg, status_regex, boost::regex_constants::match_continuous)) {
- trim(msg);
- sensors["SERVO"] = boost::make_tuple(msg, time, false);
- if(!sensor.compare("SERVO"))
- return msg;
- else
- return std::string();
- }
+ // Return requested sensor if it was updated
+ if (msgs[sensor].length())
+ return msgs[sensor];
+
return std::string();
}
+
public:
gps_ctrl_impl(uart_iface::sptr uart){
_uart = uart;
@@ -105,18 +107,19 @@ public:
bool i_heard_some_nmea = false, i_heard_something_weird = false;
gps_type = GPS_TYPE_NONE;
+ //first we look for an internal GPSDO
_flush(); //get whatever junk is in the rx buffer right now, and throw it away
_send("HAAAY GUYYYYS\n"); //to elicit a response from the GPSDO
//wait for _send(...) to return
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
//then we loop until we either timeout, or until we get a response that indicates we're a JL device
const boost::system_time comm_timeout = boost::get_system_time() + milliseconds(GPS_COMM_TIMEOUT_MS);
while(boost::get_system_time() < comm_timeout) {
reply = _recv();
if(reply.find("Command Error") != std::string::npos) {
- gps_type = GPS_TYPE_ER_GPSDO;
+ gps_type = GPS_TYPE_INTERNAL_GPSDO;
break;
}
else if(reply.substr(0, 3) == "$GP") i_heard_some_nmea = true; //but keep looking for that "Command Error" response
@@ -124,24 +127,25 @@ public:
sleep(milliseconds(GPS_TIMEOUT_DELAY_MS));
}
- if((i_heard_some_nmea) && (gps_type != GPS_TYPE_ER_GPSDO)) gps_type = GPS_TYPE_GENERIC_NMEA;
+ if((i_heard_some_nmea) && (gps_type != GPS_TYPE_INTERNAL_GPSDO)) gps_type = GPS_TYPE_GENERIC_NMEA;
if((gps_type == GPS_TYPE_NONE) && i_heard_something_weird) {
UHD_MSG(error) << "GPS invalid reply \"" << reply << "\", assuming none available" << std::endl;
}
switch(gps_type) {
- case GPS_TYPE_ER_GPSDO:
- UHD_MSG(status) << "Found an Ettus Research NMEA-capable GPSDO" << std::endl;
+ case GPS_TYPE_INTERNAL_GPSDO:
+ UHD_MSG(status) << "Found an internal GPSDO" << std::endl;
init_gpsdo();
break;
case GPS_TYPE_GENERIC_NMEA:
- if(gps_type == GPS_TYPE_GENERIC_NMEA) UHD_MSG(status) << "Found a generic NMEA GPS device" << std::endl;
+ UHD_MSG(status) << "Found a generic NMEA GPS device" << std::endl;
break;
case GPS_TYPE_NONE:
default:
+ UHD_MSG(status) << "No GPSDO found" << std::endl;
break;
}
@@ -189,19 +193,19 @@ private:
//issue some setup stuff so it spits out the appropriate data
//none of these should issue replies so we don't bother looking for them
//we have to sleep between commands because the JL device, despite not acking, takes considerable time to process each command.
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
_send("SYST:COMM:SER:ECHO OFF\n");
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
_send("SYST:COMM:SER:PRO OFF\n");
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
_send("GPS:GPGGA 1\n");
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
_send("GPS:GGAST 0\n");
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
_send("GPS:GPRMC 1\n");
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
_send("SERV:TRAC 0\n");
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
}
//retrieve a raw NMEA sentence
@@ -304,7 +308,7 @@ private:
//enable servo reporting
_send("SERV:TRAC 1\n");
- sleep(milliseconds(200));
+ sleep(milliseconds(GPSDO_STUPID_DELAY_MS));
std::string reply;
@@ -330,8 +334,8 @@ private:
}
}
- std::string _recv(void){
- return _uart->read_uart(GPS_TIMEOUT_DELAY_MS/1000.);
+ std::string _recv(double timeout = GPS_TIMEOUT_DELAY_MS/1000.){
+ return _uart->read_uart(timeout);
}
void _send(const std::string &buf){
@@ -339,7 +343,7 @@ private:
}
enum {
- GPS_TYPE_ER_GPSDO,
+ GPS_TYPE_INTERNAL_GPSDO,
GPS_TYPE_GENERIC_NMEA,
GPS_TYPE_NONE
} gps_type;
@@ -351,6 +355,7 @@ private:
static const int GPS_SERVO_FRESHNESS = 2500;
static const int GPS_LOCK_FRESHNESS = 2500;
static const int GPS_TIMEOUT_DELAY_MS = 200;
+ static const int GPSDO_STUPID_DELAY_MS = 200;
};
/***********************************************************************