Own fork of MbedSmartRestMain

Dependencies:   C027_Support C12832 LM75B MMA7660 MbedSmartRest mbed-rtos mbed

Fork of MbedSmartRestMain by Cumulocity Official

io/GPSTracker.cpp

Committer:
xinlei
Date:
2015-04-13
Revision:
92:0acd11870c6a
Parent:
76:b07effe83fb8
Child:
98:e369fc75c000

File content as of revision 92:0acd11870c6a:

#include <stdlib.h>
#include <string.h>
#include "GPSTracker.h"
#include "logging.h"

GPSTracker::GPSTracker(GPSI2C& gps) :
    _gps(gps),
    _thread(GPSTracker::thread_func, this),
    _positionSet(false)
{
}

bool GPSTracker::position(GPSTracker::Position *position)
{
    bool result;
    
    _mutex.lock();
    if (_positionSet) {
        memcpy(position, &_position, sizeof(GPSTracker::Position));
        _positionSet = false;
        result = true;
    } else {
        result = false;
    }
    _mutex.unlock();
    
    return result;
}

void GPSTracker::thread()
{
    char buf[256], chr; // needs to be that big otherwise mdm isn't working
    int ret, len, n;
    double altitude, latitude, longitude;
    aInfo("GPS thread: %p\r\n", Thread::gettid());    
    while (true) {
        ret = _gps.getMessage(buf, sizeof(buf));
        if (ret <= 0) {
            Thread::wait(100);
            continue;
        }
        
        len = LENGTH(ret);
        if ((PROTOCOL(ret) != GPSParser::NMEA) || (len <= 6)) {
            aWarning("GPS data is not in NMEA protocol!\r\n");
            continue;
        }

        // we're only interested in fixed GPS positions, data type: GPGGA
        if ((strncmp("$GPGGA", buf, 6) != 0)) {
            continue;
        }

        if (!_gps.getNmeaItem(6, buf, len, n, 10) || n == 0) {
            continue;
        }
        
        // get altitude, latitude and longitude
        if ((!_gps.getNmeaAngle(2, buf, len, latitude)) ||
            (!_gps.getNmeaAngle(4, buf, len, longitude)) ||
            (!_gps.getNmeaItem(9, buf, len, altitude)) ||
            (!_gps.getNmeaItem(10, buf, len, chr)) ||
            (chr != 'M')) {
            aWarning("Unable to retrieve GPS data!\r\n");
            continue;
        }

        _mutex.lock();
        _position.altitude = altitude;
        _position.latitude = latitude;
        _position.longitude = longitude;
        _positionSet = true;
        _mutex.unlock();
    }
}

void GPSTracker::thread_func(void const *arg)
{
    GPSTracker *that;
    that = (GPSTracker*)arg;
    that->thread();
}