diff options
author | Andreas.Eversberg <jolly@eversberg.eu> | 2010-10-20 18:09:31 +0000 |
---|---|---|
committer | Andreas.Eversberg <jolly@eversberg.eu> | 2010-10-20 18:09:31 +0000 |
commit | f181a04121053c8d046cf41a98aa4abfc5c89fde (patch) | |
tree | 422173407709cef55a87e487ced1b1bdc17ccd12 /src/host | |
parent | 50be02f78e2009c8a75d1f3c6abf63b5f17931ad (diff) |
[layer23] Completed GPS reading process
This includes "double" values of logitude and latitude, as well as time
stamp, and if the values are valid or not (GPS fix).
Diffstat (limited to 'src/host')
-rw-r--r-- | src/host/layer23/include/osmocom/bb/common/logging.h | 1 | ||||
-rw-r--r-- | src/host/layer23/include/osmocom/bb/mobile/gps.h | 12 | ||||
-rw-r--r-- | src/host/layer23/src/mobile/gps.c | 80 |
3 files changed, 87 insertions, 6 deletions
diff --git a/src/host/layer23/include/osmocom/bb/common/logging.h b/src/host/layer23/include/osmocom/bb/common/logging.h index 683c6858..eb9f4821 100644 --- a/src/host/layer23/include/osmocom/bb/common/logging.h +++ b/src/host/layer23/include/osmocom/bb/common/logging.h @@ -20,6 +20,7 @@ enum { DSAP, DSUM, DSIM, + DGPS, }; extern const struct log_info log_info; diff --git a/src/host/layer23/include/osmocom/bb/mobile/gps.h b/src/host/layer23/include/osmocom/bb/mobile/gps.h index a62eab77..b3b43351 100644 --- a/src/host/layer23/include/osmocom/bb/mobile/gps.h +++ b/src/host/layer23/include/osmocom/bb/mobile/gps.h @@ -20,9 +20,15 @@ */ struct gps { - uint8_t enable; - char device[32]; - uint32_t baud; + /* GPS device */ + uint8_t enable; + char device[32]; + uint32_t baud; + + /* current data */ + uint8_t valid; /* we have a fix */ + time_t gmt; /* GMT time when position was received */ + double latitude, longitude; }; extern struct gps gps; diff --git a/src/host/layer23/src/mobile/gps.c b/src/host/layer23/src/mobile/gps.c index 520aff82..c66da6db 100644 --- a/src/host/layer23/src/mobile/gps.c +++ b/src/host/layer23/src/mobile/gps.c @@ -25,16 +25,22 @@ #include <unistd.h> #include <stdlib.h> #include <errno.h> +#include <time.h> #include <osmocore/utils.h> #include <osmocom/bb/common/osmocom_data.h> +#include <osmocom/bb/common/logging.h> #include <osmocom/bb/mobile/gps.h> struct gps gps = { 0, "/dev/ttyACM0", - 0 + 0, + + 0, + 0, + 0,0, }; static struct bsc_fd gps_bfd; @@ -42,6 +48,11 @@ static struct termios gps_termios, gps_old_termios; static int gps_line(char *line) { + time_t gps_now, host_now; + struct tm *tm; + int32_t diff; + double latitude, longitude; + if (!!strncmp(line, "$GPGLL", 6)) return 0; line += 7; @@ -50,8 +61,66 @@ static int gps_line(char *line) line[37] = '\0'; /* ddmm.mmmm,N,dddmm.mmmm,E,hhmmss.mmm,A */ - printf("'%s'\n", line); - + /* valid position */ + if (line[36] != 'A') { + LOGP(DGPS, LOGL_INFO, "%s (invalid)\n", line); + gps.valid = 0; + } + gps.valid = 1; + + /* time stamp */ + gps_now = line[30] - '0'; + gps_now += (line[29] - '0') * 10; + gps_now += (line[28] - '0') * 60; + gps_now += (line[27] - '0') * 600; + gps_now += (line[26] - '0') * 3600; + gps_now += (line[25] - '0') * 36000; + time(&host_now); + /* calculate the number of seconds the host differs from GPS */ + diff = host_now % 86400 - gps_now; + if (diff < 0) + diff += 86400; + if (diff >= 43200) + diff -= 86400; + /* apply the "date" part to the GPS time */ + gps_now = host_now - diff; + gps.gmt = gps_now; + tm = localtime(&gps_now); + + /* position */ + latitude = (double)(line[0] - '0') * 10.0; + latitude += (double)(line[1] - '0'); + latitude += (double)(line[2] - '0') / 6.0; + latitude += (double)(line[3] - '0') / 60.0; + latitude += (double)(line[5] - '0') / 600.0; + latitude += (double)(line[6] - '0') / 6000.0; + latitude += (double)(line[7] - '0') / 60000.0; + latitude += (double)(line[8] - '0') / 600000.0; + if (line[10] == 'S') + latitude = 0.0 - latitude; + gps.latitude = latitude; + longitude = (double)(line[12] - '0') * 100.0; + longitude += (double)(line[13] - '0') * 10.0; + longitude += (double)(line[14] - '0'); + longitude += (double)(line[15] - '0') / 6.0; + longitude += (double)(line[16] - '0') / 60.0; + longitude += (double)(line[18] - '0') / 600.0; + longitude += (double)(line[19] - '0') / 6000.0; + longitude += (double)(line[20] - '0') / 60000.0; + longitude += (double)(line[21] - '0') / 600000.0; + if (line[23] == 'W') + longitude = 360.0 - longitude; + gps.longitude = longitude; + + LOGP(DGPS, LOGL_INFO, "%s\n", line); + LOGP(DGPS, LOGL_INFO, " time=%02d:%02d:%02d %04d-%02d-%02d, " + "diff-to-host=%d, latitude=%do%.4f, longitude=%do%.4f\n", + tm->tm_hour, tm->tm_min, tm->tm_sec, tm->tm_year + 1900, + tm->tm_mday, tm->tm_mon + 1, diff, + (int)gps.latitude, + (gps.latitude - ((int)gps.latitude)) * 60.0, + (int)gps.longitude, + (gps.longitude - ((int)gps.longitude)) * 60.0); return 0; } @@ -112,6 +181,9 @@ int gps_open(void) if (gps_bfd.fd > 0) return 0; + + LOGP(DGPS, LOGL_INFO, "Open GPS device '%s'\n", gps.device); + gps_bfd.data = NULL; gps_bfd.when = BSC_FD_READ; gps_bfd.cb = gps_cb; @@ -159,6 +231,8 @@ void gps_close(void) if (gps_bfd.fd <= 0) return; + LOGP(DGPS, LOGL_INFO, "Close GPS device\n"); + bsc_unregister_fd(&gps_bfd); if (isatty(gps_bfd.fd)) |