1 /* 2 * This program is free software; you can redistribute it and/or modify 3 * it under the terms of the GNU General Public License as published by 4 * the Free Software Foundation; either version 2 of the License, or 5 * (at your option) any later version. 6 * 7 * This program is distributed in the hope that it will be useful, 8 * but WITHOUT ANY WARRANTY; without even the implied warranty of 9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 10 * GNU General Public License for more details. 11 * 12 * You should have received a copy of the GNU General Public License 13 * along with this program; if not, write to the Free Software 14 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. 15 * 16 * Copyright (C) 2014 John Crispin <blogic@openwrt.org> 17 */ 18 19 #include <string.h> 20 #include <stdint.h> 21 #include <stdlib.h> 22 #include <unistd.h> 23 24 #include <libubox/uloop.h> 25 #include <libubus.h> 26 27 #include "log.h" 28 #include "nmea.h" 29 30 unsigned int debug; 31 static struct ustream_fd stream; 32 static struct ubus_auto_conn conn; 33 static struct blob_buf b; 34 static char *ubus_socket; 35 struct timespec stamp = { 0 }; 36 unsigned int adjust_clock = 0; 37 38 void 39 gps_timestamp(void) 40 { 41 clock_gettime(CLOCK_MONOTONIC, &stamp); 42 } 43 44 static int 45 gps_info(struct ubus_context *ctx, struct ubus_object *obj, 46 struct ubus_request_data *req, const char *method, 47 struct blob_attr *msg) 48 { 49 struct timespec now; 50 51 clock_gettime(CLOCK_MONOTONIC, &now); 52 53 blob_buf_init(&b, 0); 54 55 if (!stamp.tv_sec || !gps_fields) { 56 blobmsg_add_u8(&b, "signal", 0); 57 } else { 58 blobmsg_add_u32(&b, "age", now.tv_sec - stamp.tv_sec); 59 if (gps_fields & GPS_FIELD_LAT) 60 blobmsg_add_string(&b, "latitude", latitude); 61 if (gps_fields & GPS_FIELD_LON) 62 blobmsg_add_string(&b, "longitude", longitude); 63 if (gps_fields & GPS_FIELD_ALT) 64 blobmsg_add_string(&b, "elevation", elevation); 65 if (gps_fields & GPS_FIELD_COG) 66 blobmsg_add_string(&b, "course", course); 67 if (gps_fields & GPS_FIELD_SPD) 68 blobmsg_add_string(&b, "speed", speed); 69 } 70 ubus_send_reply(ctx, req, b.head); 71 72 return UBUS_STATUS_OK; 73 } 74 75 static const struct ubus_method gps_methods[] = { 76 UBUS_METHOD_NOARG("info", gps_info), 77 }; 78 79 static struct ubus_object_type gps_object_type = 80 UBUS_OBJECT_TYPE("gps", gps_methods); 81 82 static struct ubus_object gps_object = { 83 .name = "gps", 84 .type = &gps_object_type, 85 .methods = gps_methods, 86 .n_methods = ARRAY_SIZE(gps_methods), 87 }; 88 89 static void 90 ubus_connect_handler(struct ubus_context *ctx) 91 { 92 int ret; 93 94 ret = ubus_add_object(ctx, &gps_object); 95 if (ret) 96 fprintf(stderr, "Failed to add object: %s\n", ubus_strerror(ret)); 97 } 98 99 static int 100 usage(const char *prog) 101 { 102 fprintf(stderr, "Usage: %s [options] <device>\n" 103 "Options:\n" 104 " -a Adjust system clock from gps\n" 105 " -s <path> Path to ubus socket\n" 106 " -d <level> Enable debug messages\n" 107 " -S Print messages to stdout\n" 108 " -b Set gps device baud rate\n" 109 "\n", prog); 110 return -1; 111 } 112 113 static speed_t get_baudrate(int baudrate) 114 { 115 switch (baudrate) { 116 case 4800: 117 return B4800; 118 case 9600: 119 return B9600; 120 case 19200: 121 return B19200; 122 case 38400: 123 return B38400; 124 case 57600: 125 return B57600; 126 case 115200: 127 return B115200; 128 default: 129 fprintf(stderr, "ERROR: incorrect baud rate. Default 4800 baud rate has been set\n"); 130 return B4800; 131 } 132 } 133 134 int 135 main(int argc, char ** argv) 136 { 137 int ch; 138 char *device = NULL; 139 char *dbglvl = getenv("DBGLVL"); 140 int ulog_channels = ULOG_KMSG; 141 speed_t baudrate = B4800; 142 143 signal(SIGPIPE, SIG_IGN); 144 145 if (dbglvl) { 146 debug = atoi(dbglvl); 147 unsetenv("DBGLVL"); 148 } 149 150 while ((ch = getopt(argc, argv, "ad:s:Sb:")) != -1) { 151 switch (ch) { 152 case 'a': 153 adjust_clock = -1; 154 break; 155 case 's': 156 ubus_socket = optarg; 157 break; 158 case 'd': 159 debug = atoi(optarg); 160 break; 161 case 'S': 162 ulog_channels = ULOG_STDIO; 163 break; 164 case 'b': 165 baudrate = get_baudrate(atoi(optarg)); 166 break; 167 default: 168 return usage(argv[0]); 169 } 170 } 171 172 if (argc - optind < 1) { 173 fprintf(stderr, "ERROR: missing device parameter\n"); 174 return usage(argv[0]); 175 } 176 177 device = argv[optind]; 178 ulog_open(ulog_channels, LOG_DAEMON, "ugps"); 179 180 uloop_init(); 181 conn.path = ubus_socket; 182 conn.cb = ubus_connect_handler; 183 ubus_auto_connect(&conn); 184 185 if (nmea_open(device, &stream, baudrate) < 0) 186 return -1; 187 188 uloop_run(); 189 uloop_done(); 190 191 return 0; 192 } 193
This page was automatically generated by LXR 0.3.1. • OpenWrt