GPS coordinates exposed by EVE
Motivation
The requirement to obtain device location coordinates from a GPS (or more generally GNSS) receiver and publish them to the controller (and possibly also to applications) comes from an EVE customer. They need to be able to track locations of their outdoor deployments (with much higher precision than what IP-based geolocation can provide). This should be possible without the need for any additional hardware because the target device configuration includes a Sierra Wireless EM7565 LTE modem with an integrated GPS receiver. However, it is preferred that the method to obtain location coordinates is not specific to this hardware and instead can support a wide range of GPS-enhanced LTE modems. This can be possible by use of (de facto) standardized protocols, such as QMI/MBIM to control the modem and NMEA for formatting of GNSS data.
External (or built-in but not integrated with LTE) GNSS receivers will not be covered by this proposal.
LTE Modem Interface
Almost all well-known cellular modems get hooked to a USB bus. From there, a single device will expose different interfaces to accommodate various ways of interacting with it (each appearing as a separate /dev/ttyUSB*
device). There is always a traditional serial interface accepting AT commands. A GPS-capable modem will expose AT commands such as GPSAUTOSTART, GPSATINFO
and GPSLOC
to start location tracking and to obtain location data. The problem with AT commands is that they are not standardized and differ from modem to modem, therefore EVE avoids using the AT interface.
Additionally to AT commands, modern cellular modems expose CDC-based MBIM and QMI interfaces with well-defined APIs. EVE OS (specifically wwan microservice) uses CLI clients provided for these protocols - mbimcli
and qmicli
, to control the modem connectivity status, get state data as well as metrics. Even though the aim is to support both interfaces and MBIM is more of a standard, EVE prefers QMI simply because it uses a more reliable NCM protocol underneath. Also, qmicli
is much more feature-rich than mbimcli
, including in the area of location tracking as described below. Note that Sierra Wireless EM7565 supports both QMI and MBIM and allows switching between the two.
Lastly, GPS-enhanced cellular modems will provide additional serial interface streaming NMEA traces with location data (coordinates, satellite information, etc.). This is typically used in combination with AT commands in older applications. However, QMI/MBIM protocols also cover publishing of location data and serial ports are not needed anymore.
Location Service
Focusing now on QMI, the protocol uses request-response communication pattern between a modem and a user-space client for the modem management, and additionally allows to stream so-called indications from the modem with state updates, such as NMEA traces with location information.
The QMI protocol defines several services, each of them related to different actions that may be requested. For example, WDS (Wireless Data) service allows setting up IP connections. The service of interest for us here is LOC, aka location service, allowing to start location tracking and retrieving or subscribing for location status information, which are obtained either as raw NMEA traces or as parsed location coordinates (latitude, longitude, etc.). The location tracking is started using a request-response communication, while location updates are streamed as indications. A full set of messages of the LOC service can be found in the libqmi repository.
Here we can see the set of attributes available inside a position update indication. Note that for this feature request the latitude and longitude are required, while altitude and other attributes are optional (as confirmed by the customer, but see below what other attributes we suggest to also include).
qmicli
tool makes interaction with the LOC service very easy. Location tracking can be started using --loc-start
command option, while position updates can be watched for with --loc-follow-position-report
. A non-blocking alternative that allows to get a single report for the current location can be obtained with --loc-get-position-report
.
For example (note the use of client ID to match request with response):
# qmicli -p -d /dev/cdc-wdm0 --loc-start --client-no-release-cid
[/dev/cdc-wdm0] Successfully started location tracking (session id 0)
[/dev/cdc-wdm0] Client ID not released:
Service: 'loc'
CID: '1'
# qmicli -p -d /dev/cdc-wdm0 --loc-get-position-report --client-cid=1
[position report] status: success
latitude: 37.334464 degrees
longitude: -121.894300 degrees
circular horizontal position uncertainty: 25.000000 meters
horizontal elliptical uncertainty (semi-minor axis): 12.000000 meters
horizontal elliptical uncertainty (semi-major axis): 21.000000 meters
horizontal elliptical uncertainty azimuth: 84.375000 meters
horizontal confidence: 39%
horizontal reliability: medium
horizontal speed: 0.000000 m/s
speed uncertainty: 0.657951 m/s
altitude w.r.t. ellipsoid: 79.643311 meters
altitude w.r.t. mean sea level: 107.592033 meters
vertical uncertainty: 16.000000 meters
vertical confidence: n/a
vertical reliability: medium
vertical speed: 0.000000 m/s
heading: n/a
heading uncertainty: n/a
magnetic deviation: 15.000000 degrees
technology: satellite
position DOP: 1.300000
horizontal DOP: 1.000000
vertical DOP: 0.800000
UTC timestamp: 1647428316000 ms
Leap seconds: 18
GPS time: 2201 weeks and 298734000ms
time uncertainty: n/a
time source: navigation-solution
sensor data usage: (null)
Fix count: 1
Satellites used: 1,4,21,32,67,78,83,195,211,212,308,315
Altitude assumed: yes
What’s more, qmicli
also imports libmbim and to some extent is able to talk to modems in the MBIM mode. This does include the location service and allows us to use the same CLI command regardless of the underlying protocol (the use of the MBIM protocol over QMI can be enforced with --device-open-mbim
).
This is important not only because it simplifies the implementation, but also because mbimcli
is somewhat behind in development and does not yet provide commands for the interaction with the location service.
EVE API Additions
First of all, it should be possible to turn the location tracking ON and OFF from the controller and by default it should be disabled. We will add a new location_tracking
boolean flag into CellularConfig
(a place for LTE modem config, such as APN):
message CellularConfig {
// APN string - by default it is "internet"
string APN = 1;
// Optional cellular connectivity probing.
// By default it is enabled.
CellularConnectivityProbe probe = 2;
// Some LTE modems have GNSS receiver integrated and can be used for
// device location tracking.
// Enable this option to have location info periodically obtained from
// this modem and published to the controller and to applications.
bool location_tracking = 3;
}
EVE API already defines GeoLoc structure for device location information:
// From an IP address-based geolocation service
// XXX later define GPS coordinates from device
message GeoLoc {
string UnderlayIP = 1;
string Hostname = 2;
string City = 3;
string Region = 4;
string Country = 5;
string Loc = 6;
string Org = 7;
string Postal = 8;
}
This structure was originally defined to carry device location data determined based on a public IP address of the device (using online service http://ipinfo.io). As such, there is an instance of GeoLoc
for every device network inside ZInfoNetwork.
With IP-based geolocation, the estimated latitude and longitude are practically useless and typically point to some random place in the determined city. For this reason, not much attention was given to the Loc
field and its type. It was defined as a string and requires parsing when used for more than just display (content example: Loc:”48.7395,19.1535”).
For a much more precise GNSS-based location tracking we propose to define latitude, longitude (and altitude) as separate fields with double-precision floating-point types, encoding coordinates with decimal degrees (DD) notation. An open question is whether the address information, such as City, Region, Country, etc., should be provided in this case as well. It would require a use of an online Reverse geocoding service to obtain this data. If not required (which we will assume unless told otherwise), then it does not make much sense to reuse the GeoLoc structure at all, since all existing fields would be left empty in this case.
Answer from customer: Reverse geocoding is not required, although it would be a nice-to-have feature. But for now this will be out-of-scope of this proposal.
We propose to define a separate structure for GNSS location information:
ZinfoLocation
will be added into the list of info messages. Unlike other info messages, which are published on every change, here we may want to set a fixed (and configurable) publish period (config item: timer.location.interval
). Note that we will get location updates from the receiver one every second (at most), but our default period will be longer and in the range of tens of seconds (e.g. publish every 20 seconds), so that the controller will not get overloaded with too many updates (from all devices).
Additionally, we could expose the location information to applications. An open question is whether we need to provide this information to any application running on the device, or if it is sufficient to only post it to the (single) application designated as Local Profile Server.
Answer from customer: Every application should be able to retrieve location information.
We will add a new POST endpoint /api/v1/location
for the Local profile server, where EVE would periodically POST
the content of the ZInfoLocation
proto message. Default period for these APIs is 1 minute. For location information we would apply the same period as configured for publishing to the controller.
For other applications, we will leverage the meta-data server created for every network instance (under IP 169.254.169.254) and add a new GET endpoint /eve/v1/location.json
, providing json-encoded ZInfoLocation
on demand.
EVE implementation changes
To implement this feature, we need to extend the wwan microservice with a function/process that will periodically collect and publish location information. This will be done using qmicli
as outlined above. With further testing and experimentation we will determine if it is more reliable to watch for location indication messages (with a process running in the background), or if the microservice would rather periodically ask for a location update (with a non-blocking call, just like it is done for connection status and metrics).
Conclusion: It is more efficient and reliable to continuously watch for location indication messages using a background process.
The wwan microservice exposes state information and metrics as /run/wwan/status.json
and /run/wwan/metrics.json
, respectively, which are then picked up by the NIM microservice and published further using pubsub.
It might make sense to publish location information as a separate json file, for example as /run/wwan/location.json
. Similarly like metrics and status, location updates will be forwarded further (at a limited rate) by NIM to other microservices via pubsub.
Zedagent will subscribe to location reports and publish them periodically to the controller and the Local Profile Server. Zedrouter will also collect location information from wwan microservice and make it available to all applications on demand.