2 * This is the main sequence of the gpsd daemon. The IO dispatcher, main
3 * select loop, and user command handling lives here.
5 * This file is Copyright (c) 2010 by the GPSD project
6 * BSD terms apply: see the file COPYING in the distribution root for details.
9 #include "gpsd_config.h"
10 #include <sys/types.h>
13 #endif /* S_SPLINT_S */
16 #endif /* HAVE_SYSLOG_H */
23 #ifdef HAVE_SYS_SOCKET_H
24 #include <sys/socket.h>
27 #endif /* HAVE_SYS_SOCKET_H */
30 #endif /* HAVE_SYS_UN_H */
31 #ifdef HAVE_NETINET_IN_H
32 #include <netinet/in.h>
33 #endif /* HAVE_NETINET_IN_H */
34 #ifdef HAVE_ARPA_INET_H
35 #include <arpa/inet.h>
36 #endif /* HAVE_ARPA_INET_H */
39 #endif /* HAVE_NETDB_H */
40 #endif /* S_SPLINT_S */
47 #endif /* HAVE_PWD_H */
50 #endif /* HAVE_GRP_H */
54 #if defined (HAVE_PATH_H)
57 #if !defined (_PATH_DEVNULL)
58 #define _PATH_DEVNULL "/dev/null"
61 #if defined (HAVE_SYS_SELECT_H)
62 #include <sys/select.h>
64 #if defined (HAVE_SYS_STAT_H)
67 #if defined(HAVE_SYS_TIME_H)
75 #include <gpsd_dbus.h>
85 * The name of a tty device from which to pick up whatever the local
86 * owning group for tty devices is. Used when we drop privileges.
88 #if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__)
89 #define PROTO_TTY "/dev/tty00" /* correct for *BSD */
91 #define PROTO_TTY "/dev/ttyS0" /* correct for Linux */
94 /* Name of (unprivileged) user to change to when we drop privileges. */
96 #define GPSD_USER "nobody"
100 * Timeout policy. We can't rely on clients closing connections
101 * correctly, so we need timeouts to tell us when it's OK to
102 * reclaim client fds. COMMAND_TIMEOUT fends off programs
103 * that open connections and just sit there, not issuing a WATCH or
104 * doing anything else that triggers a device assignment. Clients
105 * in watcher or raw mode that don't read their data will get dropped
106 * when throttled_write() fills up the outbound buffers and the
107 * NOREAD_TIMEOUT expires.
109 * RELEASE_TIMEOUT sets the amount of time we hold a device
110 * open after the last subscriber closes it; this is nonzero so a
111 * client that does open/query/close will have time to come back and
112 * do another single-shot query, if it wants to, before the device is
113 * actually closed. The reason this matters is because some Bluetooth
114 * GPSes not only shut down the GPS receiver on close to save battery
115 * power, they actually shut down the Bluetooth RF stage as well and
116 * only re-wake it periodically to see if an attempt to raise the
117 * device is in progress. The result is that if you close the device
118 * when it's powered up, a re-open can fail with EIO and needs to be
119 * tried repeatedly. Better to avoid this...
121 * DEVICE_REAWAKE says how long to wait before repolling after a zero-length
122 * read. It's there so we avoid spinning forever on an EOF condition.
124 #define COMMAND_TIMEOUT 60*15
125 #define NOREAD_TIMEOUT 60*3
126 #define RELEASE_TIMEOUT 60
127 #define DEVICE_REAWAKE 0.01
132 * If ntpshm is enabled, we renice the process to this priority level.
133 * For precise timekeeping increase priority.
137 /* Needed because 4.x versions of GCC are really annoying */
138 #define ignore_return(funcall) assert(funcall != -23)
140 /* IP version used by the program */
143 * AF_INET6: IPv6 only
146 static const int af = AF_UNSPEC;
148 static const int af = AF_INET;
153 static fd_set all_fds;
155 static int debuglevel;
156 static bool in_background = false;
157 static bool listen_global = false;
158 static bool nowait = false;
159 static jmp_buf restartbuf;
162 /*@ -initallelements -nullassign -nullderef @*/
163 struct gps_context_t context = {
167 .netgnss_service = netgnss_none,
170 .netgnss_privdata = NULL,
174 .leap_seconds = LEAP_SECONDS,
177 .century = CENTURY_BASE,
179 .enable_ntpshm = false,
184 # endif /* PPS_ENABLE */
185 #endif /* NTPSHM_ENABLE */
187 /*@ +initallelements +nullassign +nullderef @*/
190 static volatile sig_atomic_t signalled;
192 static void onsig(int sig)
194 /* just set a variable, and deal with it in the main loop */
195 signalled = (sig_atomic_t) sig;
198 static int daemonize(void)
203 /*@ -type @*//* weirdly, splint 3.1.2 is confused by fork() */
204 switch (pid = fork()) {
207 case 0: /* child side */
209 default: /* parent side */
216 if (chdir("/") == -1)
219 if ((fd = open(_PATH_DEVNULL, O_RDWR, 0)) != -1) {
220 (void)dup2(fd, STDIN_FILENO);
221 (void)dup2(fd, STDOUT_FILENO);
222 (void)dup2(fd, STDERR_FILENO);
227 in_background = true;
231 #if defined(PPS_ENABLE)
232 static pthread_mutex_t report_mutex;
233 #endif /* PPS_ENABLE */
235 static void visibilize(/*@out@*/char *buf2, size_t len, const char *buf)
240 for (sp = buf; *sp != '\0' && strlen(buf2)+4 < len; sp++)
241 if (isprint(*sp) || (sp[0] == '\n' && sp[1] == '\0') || (sp[0] == '\r' && sp[2] == '\0'))
242 (void)snprintf(buf2 + strlen(buf2), 2, "%c", *sp);
244 (void)snprintf(buf2 + strlen(buf2), 6, "\\x%02x",
248 void gpsd_report(int errlevel, const char *fmt, ...)
249 /* assemble command in printf(3) style, use stderr or syslog */
251 #ifndef SQUELCH_ENABLE
252 if (errlevel <= debuglevel) {
253 char buf[BUFSIZ], buf2[BUFSIZ];
256 #if defined(PPS_ENABLE)
257 /*@ -unrecog (splint has no pthread declarations as yet) @*/
258 (void)pthread_mutex_lock(&report_mutex);
260 #endif /* PPS_ENABLE */
261 (void)strlcpy(buf, "gpsd: ", BUFSIZ);
263 (void)vsnprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), fmt,
267 visibilize(buf2, sizeof(buf2), buf);
270 syslog((errlevel == 0) ? LOG_ERR : LOG_NOTICE, "%s", buf2);
272 (void)fputs(buf2, stderr);
273 #if defined(PPS_ENABLE)
274 /*@ -unrecog (splint has no pthread declarations as yet) @*/
275 (void)pthread_mutex_unlock(&report_mutex);
277 #endif /* PPS_ENABLE */
279 #endif /* !SQUELCH_ENABLE */
282 static void usage(void)
284 const struct gps_type_t **dp;
286 (void)printf("usage: gpsd [-b] [-n] [-N] [-D n] [-F sockfile] [-G] [-P pidfile] [-S port] [-h] device...\n\
288 -b = bluetooth-safe: open data sources read-only\n\
289 -n = don't wait for client connects to poll GPS\n\
290 -N = don't go into background\n\
291 -F sockfile = specify control socket location\n\
292 -G = make gpsd listen on INADDR_ANY\n\
293 -P pidfile = set file to record process ID \n\
294 -D integer (default 0) = set debug level \n\
295 -S integer (default %s) = set port for daemon \n\
296 -h = help message \n\
297 -V = emit version and exit.\n\
298 A device may be a local serial device for GPS input, or a URL of the form:\n\
299 {dgpsip|ntrip}://[user:passwd@]host[:port][/stream]\n\
300 gpsd://host[:port][/device][?protocol]\n\
301 in which case it specifies an input source for GPSD, DGPS or ntrip data.\n\
303 The following driver types are compiled into this gpsd instance:\n",
305 for (dp = gpsd_drivers; *dp; dp++) {
306 (void)printf(" %s\n", (*dp)->type_name);
310 static int passivesock_af(int af, char *service, char *tcp_or_udp, int qlen)
311 /* bind a passive command socket for the daemon */
314 * af = address family,
315 * service = IANA protocol name or number.
316 * tcp_or_udp = TCP or UDP
317 * qlen = maximum wait-queue length for connections
320 struct protoent *ppe; /* splint has a bug here */
323 int s = -1, type, proto, one = 1;
327 if ((pse = getservbyname(service, tcp_or_udp)))
328 port = ntohs((in_port_t) pse->s_port);
329 else if ((port = (in_port_t) atoi(service)) == 0) {
330 gpsd_report(LOG_ERROR, "can't get \"%s\" service entry.\n", service);
333 ppe = getprotobyname(tcp_or_udp);
334 if (strcmp(tcp_or_udp, "udp") == 0) {
336 /*@i@*/ proto = (ppe) ? ppe->p_proto : IPPROTO_UDP;
339 /*@i@*/ proto = (ppe) ? ppe->p_proto : IPPROTO_TCP;
342 /*@ -mustfreefresh +matchanyintegral @*/
345 sin_len = sizeof(sat.sa_in);
347 memset((char *)&sat.sa_in, 0, sin_len);
348 sat.sa_in.sin_family = (sa_family_t) AF_INET;
350 sat.sa_in.sin_addr.s_addr = htonl(INADDR_ANY);
352 sat.sa_in.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
353 sat.sa_in.sin_port = htons(port);
356 /* see PF_INET6 case below */
357 s = socket(PF_INET, type, proto);
361 sin_len = sizeof(sat.sa_in6);
363 memset((char *)&sat.sa_in6, 0, sin_len);
364 sat.sa_in6.sin6_family = (sa_family_t) AF_INET6;
366 /* BAD: sat.sa_in6.sin6_addr = in6addr_any;
367 * the simple assignment will not work (except as an initializer)
368 * because sin6_addr is an array not a simple type
369 * we could do something like this:
370 * memcpy(sat.sa_in6.sin6_addr, in6addr_any, sizeof(sin6_addr));
371 * BUT, all zeros is IPv6 wildcard, and we just zeroed the array
372 * so really nothing to do here
375 sat.sa_in6.sin6_addr = in6addr_loopback;
376 sat.sa_in6.sin6_port = htons(port);
379 * Traditionally BSD uses "communication domains", named by
380 * constants starting with PF_ as the first argument for
381 * select. In practice PF_INET has the same value as AF_INET
382 * (on BSD and Linux, and probably everywhere else). POSIX
383 * leaves much of this unspecified, but requires that AF_INET
384 * be recognized. We follow tradition here.
387 s = socket(PF_INET6, type, proto);
391 gpsd_report(LOG_ERROR, "unhandled address family %d\n", af);
394 gpsd_report(LOG_IO, "opening %s socket\n", af_str);
397 gpsd_report(LOG_ERROR, "can't create %s socket\n", af_str);
400 if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR, (char *)&one,
401 (int)sizeof(one)) == -1) {
402 gpsd_report(LOG_ERROR, "Error: SETSOCKOPT SO_REUSEADDR\n");
405 if (bind(s, &sat.sa, sin_len) < 0) {
406 gpsd_report(LOG_ERROR, "can't bind to %s port %s, %s\n", af_str,
407 service, strerror(errno));
408 if (errno == EADDRINUSE) {
409 gpsd_report(LOG_ERROR, "maybe gpsd is already running!\n");
413 if (type == SOCK_STREAM && listen(s, qlen) == -1) {
414 gpsd_report(LOG_ERROR, "can't listen on port %s\n", service);
418 gpsd_report(LOG_SPIN, "passivesock_af() -> %d\n", s);
420 /*@ +mustfreefresh -matchanyintegral @*/
424 static int passivesocks(char *service, char *tcp_or_udp,
425 int qlen, /*@out@*/int socks[])
427 int numsocks = AFCOUNT;
430 for (i = 0; i < AFCOUNT; i++)
433 if (AF_UNSPEC == af || (AF_INET == af))
434 socks[0] = passivesock_af(AF_INET, service, tcp_or_udp, qlen);
436 if (AF_UNSPEC == af || (AF_INET6 == af))
437 socks[1] = passivesock_af(AF_INET6, service, tcp_or_udp, qlen);
439 for (i = 0; i < AFCOUNT; i++)
443 /* Return the number of succesfully opened sockets
444 * The failed ones are identified by negative values */
449 static int filesock(char *filename)
451 struct sockaddr_un addr;
454 /*@ -mayaliasunique -usedef @*/
455 if ((sock = socket(AF_UNIX, SOCK_STREAM, 0)) == -1) {
456 gpsd_report(LOG_ERROR, "Can't create device-control socket\n");
459 (void)strlcpy(addr.sun_path, filename, 104); /* from sys/un.h */
460 addr.sun_family = AF_UNIX;
461 (void)bind(sock, (struct sockaddr *)&addr, (int)sizeof(addr));
462 if (listen(sock, QLEN) == -1) {
463 gpsd_report(LOG_ERROR, "can't listen on local socket %s\n", filename);
466 /*@ +mayaliasunique +usedef @*/
472 int fd; /* client file descriptor. -1 if unused */
473 double active; /* when subscriber last polled for data */
474 struct policy_t policy; /* configurable bits */
478 * This hackery is intended to support SBCs that are resource-limited
479 * and only need to support one or a few devices each. It avoids the
480 * space overhead of allocating thousands of unused device structures.
481 * This array fills from the bottom, so as an extreme case you could
482 * reduce LIMITED_MAX_DEVICES to 1.
484 #ifdef LIMITED_MAX_DEVICES
485 #define MAXDEVICES LIMITED_MAX_DEVICES
487 /* we used to make this FD_SETSIZE, but that cost 14MB of wasted core! */
491 #ifdef LIMITED_MAX_CLIENTS
492 #define MAXSUBSCRIBERS LIMITED_MAX_CLIENTS
494 /* subscriber structure is small enough that there's no need to limit this */
495 #define MAXSUBSCRIBERS FD_SETSIZE
497 #define sub_index(s) (int)((s) - subscribers)
498 #define allocated_device(devp) ((devp)->gpsdata.dev.path[0] != '\0')
499 #define free_device(devp) (devp)->gpsdata.dev.path[0] = '\0'
500 #define initialized_device(devp) ((devp)->context != NULL)
501 #define subscribed(sub, devp) (sub->policy.devpath[0]=='\0' || strcmp(sub->policy.devpath, devp->gpsdata.dev.path)==0)
503 struct gps_device_t devices[MAXDEVICES];
504 struct subscriber_t subscribers[MAXSUBSCRIBERS]; /* indexed by client file descriptor */
506 static void adjust_max_fd(int fd, bool on)
507 /* track the largest fd currently in use */
513 #if !defined(LIMITED_MAX_DEVICES) && !defined(LIMITED_MAX_CLIENT_FD)
515 * I suspect there could be some weird interactions here if
516 * either of these were set lower than FD_SETSIZE. We'll avoid
517 * potential bugs by not scavenging in this case at all -- should
518 * be OK, as the use case for limiting is SBCs where the limits
519 * will be very low (typically 1) and the maximum size of fd
520 * set to scan through correspondingly small.
526 for (maxfd = tfd = 0; tfd < FD_SETSIZE; tfd++)
527 if (FD_ISSET(tfd, &all_fds))
531 #endif /* !defined(LIMITED_MAX_DEVICES) && !defined(LIMITED_MAX_CLIENT_FD) */
534 #define UNALLOCATED_FD -1
536 static /*@null@*//*@observer@ */ struct subscriber_t *allocate_client(void)
537 /* return the address of a subscriber structure allocated for a new session */
541 #if UNALLOCATED_FD == 0
542 #error client allocation code will fail horribly
544 for (si = 0; si < NITEMS(subscribers); si++) {
545 if (subscribers[si].fd == UNALLOCATED_FD) {
546 subscribers[si].fd = 0; /* mark subscriber as allocated */
547 return &subscribers[si];
553 static void detach_client(struct subscriber_t *sub)
554 /* detach a client and terminate the session */
557 if (sub->fd == UNALLOCATED_FD)
559 c_ip = netlib_sock2ip(sub->fd);
560 (void)shutdown(sub->fd, SHUT_RDWR);
561 gpsd_report(LOG_SPIN, "close(%d) in detach_client()\n", sub->fd);
562 (void)close(sub->fd);
563 gpsd_report(LOG_INF, "detaching %s (sub %d, fd %d) in detach_client\n",
564 c_ip, sub_index(sub), sub->fd);
565 FD_CLR(sub->fd, &all_fds);
566 adjust_max_fd(sub->fd, false);
568 sub->policy.watcher = false;
569 sub->policy.nmea = false;
571 sub->policy.scaled = false;
572 sub->policy.timing = false;
573 sub->policy.devpath[0] = '\0';
574 sub->fd = UNALLOCATED_FD;
578 static ssize_t throttled_write(struct subscriber_t *sub, char *buf,
580 /* write to client -- throttle if it's gone or we're close to buffer overrun */
584 if (debuglevel >= 3) {
586 gpsd_report(LOG_IO, "=> client(%d): %s\n", sub_index(sub), buf);
588 char *cp, buf2[MAX_PACKET_LENGTH * 3];
590 for (cp = buf; cp < buf + len; cp++)
591 (void)snprintf(buf2 + strlen(buf2),
592 sizeof(buf2) - strlen(buf2),
593 "%02x", (unsigned int)(*cp & 0xff));
594 gpsd_report(LOG_IO, "=> client(%d): =%s\n", sub_index(sub),
599 status = send(sub->fd, buf, len, 0);
600 if (status == (ssize_t) len)
602 else if (status > -1) {
603 gpsd_report(LOG_INF, "short write disconnecting client(%d)\n",
607 } else if (errno == EAGAIN || errno == EINTR)
608 return 0; /* no data written, and errno says to retry */
609 else if (errno == EBADF)
610 gpsd_report(LOG_WARN, "client(%d) has vanished.\n", sub_index(sub));
611 else if (errno == EWOULDBLOCK
612 && timestamp() - sub->active > NOREAD_TIMEOUT)
613 gpsd_report(LOG_INF, "client(%d) timed out.\n", sub_index(sub));
615 gpsd_report(LOG_INF, "client(%d) write: %s\n", sub_index(sub),
621 static void notify_watchers(struct gps_device_t *device, char *sentence, ...)
622 /* notify all clients watching a given device of an event */
626 struct subscriber_t *sub;
628 va_start(ap, sentence);
629 (void)vsnprintf(buf, sizeof(buf), sentence, ap);
632 for (sub = subscribers; sub < subscribers + MAXSUBSCRIBERS; sub++)
633 if (sub->active != 0 && subscribed(sub, device))
634 (void)throttled_write(sub, buf, strlen(buf));
637 static void deactivate_device(struct gps_device_t *device)
638 /* deactivate device, but leave it in the pool (do not free it) */
640 notify_watchers(device,
641 "{\"class\":\"DEVICE\",\"path\":\"%s\",\"activated\":0}\r\n",
642 device->gpsdata.dev.path);
643 if (device->gpsdata.gps_fd != -1) {
644 FD_CLR(device->gpsdata.gps_fd, &all_fds);
645 adjust_max_fd(device->gpsdata.gps_fd, false);
646 gpsd_deactivate(device);
652 /*@null@*//*@observer@*/ static struct gps_device_t *find_device(char
654 /* find the device block for an existing device name */
656 struct gps_device_t *devp;
658 for (devp = devices; devp < devices + MAXDEVICES; devp++)
659 if (allocated_device(devp)
660 && strcmp(devp->gpsdata.dev.path, device_name) == 0)
668 static bool open_device(char *device_name)
669 /* open and initialize a new device block */
671 struct gps_device_t *devp;
673 for (devp = devices; devp < devices + MAXDEVICES; devp++)
674 if (!allocated_device(devp)
675 || (strcmp(devp->gpsdata.dev.path, device_name) == 0
676 && !initialized_device(devp))) {
681 gpsd_init(devp, &context, device_name);
682 if (gpsd_activate(devp) < 0)
684 FD_SET(devp->gpsdata.gps_fd, &all_fds);
685 adjust_max_fd(devp->gpsdata.gps_fd, true);
689 static bool add_device(char *device_name)
690 /* add a device to the pool; open it right away if in nowait mode */
693 return open_device(device_name);
695 struct gps_device_t *devp;
696 /* stash devicename away for probing when the first client connects */
697 for (devp = devices; devp < devices + MAXDEVICES; devp++)
698 if (!allocated_device(devp)) {
699 gpsd_init(devp, &context, device_name);
700 gpsd_report(LOG_INF, "stashing device %s at slot %d\n",
701 device_name, (int)(devp - devices));
702 devp->gpsdata.gps_fd = -1;
703 notify_watchers(devp,
704 "{\"class\":\"DEVICE\",\"path\":\"%s\",\"activated\":%ld}\r\n",
705 devp->gpsdata.dev.path, timestamp());
716 static bool awaken(struct gps_device_t *device)
717 /* awaken a device and notify all watchers*/
719 /* open that device */
720 if (!initialized_device(device)) {
721 if (!open_device(device->gpsdata.dev.path)) {
722 gpsd_report(LOG_PROG, "%s: open failed\n",
723 device->gpsdata.dev.path);
729 if (device->gpsdata.gps_fd != -1) {
730 gpsd_report(LOG_PROG,
731 "device %d (fd=%d, path %s) already active.\n",
732 (int)(device - devices),
733 device->gpsdata.gps_fd, device->gpsdata.dev.path);
736 if (gpsd_activate(device) < 0) {
737 gpsd_report(LOG_ERROR, "%s: device activation failed.\n",
738 device->gpsdata.dev.path);
742 "flagging descriptor %d in assign_channel()\n",
743 device->gpsdata.gps_fd);
744 FD_SET(device->gpsdata.gps_fd, &all_fds);
745 adjust_max_fd(device->gpsdata.gps_fd, true);
751 /*@ observer @*/ static char *snarfline(char *p, /*@out@*/ char **out)
752 /* copy the rest of the command line, before CR-LF */
755 static char stash[BUFSIZ];
757 /*@ -temptrans -mayaliasunique @*/
758 for (q = p; isprint(*p) && !isspace(*p) && /*@i@*/ (p - q < BUFSIZ - 1);
761 (void)memcpy(stash, q, (size_t) (p - q));
765 /*@ +temptrans +mayaliasunique @*/
768 #ifdef ALLOW_RECONFIGURE
769 static bool privileged_user(struct gps_device_t *device)
770 /* is this channel privileged to change a device's behavior? */
772 /* grant user privilege if he's the only one listening to the device */
773 struct subscriber_t *sub;
775 for (sub = subscribers; sub < subscribers + MAXSUBSCRIBERS; sub++) {
776 if (sub->active == 0)
778 else if (subscribed(sub, device))
781 return subcount == 1;
783 #endif /* ALLOW_CONFIGURE */
785 static void handle_control(int sfd, char *buf)
786 /* handle privileged commands coming through the control socket */
788 char *p, *stash, *eq;
789 struct gps_device_t *devp;
793 p = snarfline(buf + 1, &stash);
794 gpsd_report(LOG_INF, "<= control(%d): removing %s\n", sfd, stash);
795 if ((devp = find_device(stash))) {
796 deactivate_device(devp);
798 ignore_return(write(sfd, "OK\n", 3));
800 ignore_return(write(sfd, "ERROR\n", 6));
801 } else if (buf[0] == '+') {
802 p = snarfline(buf + 1, &stash);
803 if (find_device(stash)) {
804 gpsd_report(LOG_INF, "<= control(%d): %s already active \n", sfd,
806 ignore_return(write(sfd, "ERROR\n", 6));
808 gpsd_report(LOG_INF, "<= control(%d): adding %s\n", sfd, stash);
809 if (add_device(stash))
810 ignore_return(write(sfd, "OK\n", 3));
812 ignore_return(write(sfd, "ERROR\n", 6));
814 } else if (buf[0] == '!') {
815 p = snarfline(buf + 1, &stash);
816 eq = strchr(stash, '=');
818 gpsd_report(LOG_WARN, "<= control(%d): ill-formed command \n",
820 ignore_return(write(sfd, "ERROR\n", 6));
823 if ((devp = find_device(stash))) {
824 gpsd_report(LOG_INF, "<= control(%d): writing to %s \n", sfd,
826 ignore_return(write(devp->gpsdata.gps_fd, eq, strlen(eq)));
827 ignore_return(write(sfd, "OK\n", 3));
829 gpsd_report(LOG_INF, "<= control(%d): %s not active \n", sfd,
831 ignore_return(write(sfd, "ERROR\n", 6));
834 } else if (buf[0] == '&') {
835 p = snarfline(buf + 1, &stash);
836 eq = strchr(stash, '=');
838 gpsd_report(LOG_WARN, "<= control(%d): ill-formed command\n",
840 ignore_return(write(sfd, "ERROR\n", 6));
845 len = strlen(eq) + 5;
846 if ((devp = find_device(stash)) != NULL) {
847 /* NOTE: this destroys the original buffer contents */
848 st = gpsd_hexpack(eq, eq, len);
851 "<= control(%d): invalid hex string (error %d).\n",
853 ignore_return(write(sfd, "ERROR\n", 6));
856 "<= control(%d): writing %d bytes fromhex(%s) to %s\n",
859 (devp->gpsdata.gps_fd, eq, (size_t) st));
860 ignore_return(write(sfd, "OK\n", 3));
863 gpsd_report(LOG_INF, "<= control(%d): %s not active\n", sfd,
865 ignore_return(write(sfd, "ERROR\n", 6));
872 #ifdef ALLOW_RECONFIGURE
873 static void set_serial(struct gps_device_t *device,
874 speed_t speed, char *modestring)
875 /* set serial parameters for a device from a speed and modestring */
877 unsigned int stopbits = device->gpsdata.dev.stopbits;
878 char parity = device->gpsdata.dev.parity;
881 if (strchr("78", *modestring) != NULL) {
882 while (isspace(*modestring))
884 wordsize = (int)(*modestring++ - '0');
885 if (strchr("NOE", *modestring) != NULL) {
886 parity = *modestring++;
887 while (isspace(*modestring))
889 if (strchr("12", *modestring) != NULL)
890 stopbits = (unsigned int)(*modestring - '0');
894 gpsd_report(LOG_PROG, "set_serial(,%d,%s) %c%d\n", speed, modestring,
896 /* no support for other word sizes yet */
898 if (wordsize == (int)(9 - stopbits)
899 && device->device_type->speed_switcher != NULL) {
900 if (device->device_type->speed_switcher(device, speed, parity, (int)stopbits)) {
902 * Deep black magic is required here. We have to
903 * allow the control string time to register at the
904 * GPS before we do the baud rate switch, which
905 * effectively trashes the UART's buffer.
907 * This definitely fails below 40 milliseconds on a
908 * BU-303b. 50ms is also verified by Chris Kuethe on
909 * Pharos iGPS360 + GSW 2.3.1ES + prolific
910 * Rayming TN-200 + GSW 2.3.1 + ftdi
911 * Rayming TN-200 + GSW 2.3.2 + ftdi
912 * so it looks pretty solid.
914 * The minimum delay time is probably constant
915 * across any given type of UART.
917 (void)tcdrain(device->gpsdata.gps_fd);
919 gpsd_set_speed(device, speed, parity, stopbits);
924 #endif /* ALLOW_RECONFIGURE */
926 static void json_devicelist_dump(char *reply, size_t replylen)
928 struct gps_device_t *devp;
929 (void)strlcpy(reply, "{\"class\":\"DEVICES\",\"devices\":[", replylen);
930 for (devp = devices; devp < devices + MAXDEVICES; devp++)
931 if (allocated_device(devp)
932 && strlen(reply) + strlen(devp->gpsdata.dev.path) + 3 <
935 json_device_dump(devp,
936 reply + strlen(reply), replylen - strlen(reply));
937 cp = reply + strlen(reply);
940 (void)strlcat(reply, ",", replylen);
943 if (reply[strlen(reply) - 1] == ',')
944 reply[strlen(reply) - 1] = '\0';
945 (void)strlcat(reply, "]}\r\n", replylen);
948 static void rstrip(char *str)
949 /* strip trailing \r\n\t\SP from a string */
952 strend = str + strlen(str) - 1;
953 while (isspace(*strend)) {
959 static void handle_request(struct subscriber_t *sub,
960 const char *buf, const char **after,
961 char *reply, size_t replylen)
963 struct gps_device_t *devp;
964 const char *end = NULL;
967 * There's a splint limitation that parameters can be declared
968 * @out@ or @null@ but not, apparently, both. This collides with
969 * the (admittedly tricky) way we use endptr. The workaround is to
970 * declare it @null@ and use -compdef around the JSON reader calls.
976 /*@-nullderef -nullpass@*/
978 if (strncmp(buf, "DEVICES;", 8) == 0) {
980 json_devicelist_dump(reply, replylen);
981 } else if (strncmp(buf, "WATCH", 5) == 0
982 && (buf[5] == ';' || buf[5] == '=')) {
987 int status = json_watch_read(buf + 1, &sub->policy, &end);
996 (void)snprintf(reply, replylen,
997 "{\"class\":\"ERROR\",\"message\":\"Invalid WATCH: %s\"}\r\n",
998 json_error_string(status));
999 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1000 } else if (sub->policy.watcher) {
1001 if (sub->policy.devpath[0] == '\0') {
1002 /* awaken all devices */
1003 for (devp = devices; devp < devices + MAXDEVICES; devp++)
1004 if (allocated_device(devp))
1007 devp = find_device(sub->policy.devpath);
1009 (void)snprintf(reply, replylen,
1010 "{\"class\":\"ERROR\",\"message\":\"Do nuch device as %s\"}\r\n",
1011 sub->policy.devpath);
1012 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1014 } else if (!awaken(devp))
1015 (void)snprintf(reply, replylen,
1016 "{\"class\":\"ERROR\",\"message\":\"Can't assign %s\"}\r\n",
1017 sub->policy.devpath);
1018 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1023 /* display a device list and the user's policy */
1024 json_devicelist_dump(reply + strlen(reply), replylen - strlen(reply));
1025 json_watch_dump(&sub->policy,
1026 reply + strlen(reply), replylen - strlen(reply));
1027 } else if (strncmp(buf, "DEVICE", 6) == 0
1028 && (buf[6] == ';' || buf[6] == '=')) {
1029 struct devconfig_t devconf;
1030 struct gps_device_t *device;
1032 devconf.path[0] = '\0'; /* initially, no device selection */
1036 #ifdef ALLOW_RECONFIGURE
1037 /* first, select a device to operate on */
1038 int status = json_device_read(buf + 1, &devconf, &end);
1049 (void)snprintf(reply, replylen,
1050 "{\"class\":\"ERROR\",\"message\":\"Invalid DEVICE: %s\"}\r\n",
1051 json_error_string(status));
1052 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1055 if (devconf.path[0] != '\0') {
1056 /* user specified a path, try to assign it */
1057 if (!awaken(find_device(devconf.path))) {
1058 (void)snprintf(reply, replylen,
1059 "{\"class\":\"ERROR\",\"message\":\"Can't open %s.\"}\r\n",
1061 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1065 /* no path specified */
1067 for (devp = devices; devp < devices + MAXDEVICES; devp++)
1068 if (allocated_device(devp)) {
1072 if (devcount == 0) {
1073 (void)strlcat(reply,
1074 "{\"class\":\"ERROR\",\"message\":\"Can't perform DEVICE configuration, no devices attached.\"}\r\n",
1076 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1078 } else if (devcount > 1) {
1079 (void)snprintf(reply + strlen(reply),
1080 replylen - strlen(reply),
1081 "{\"class\":\"ERROR\",\"message\":\"No path specified in DEVICE, but multiple devices are attached.\"}\r\n");
1082 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1085 /* we should have exactly one device now */
1088 (void)snprintf(reply + strlen(reply),
1089 replylen - strlen(reply),
1090 "{\"class\":\"ERROR\",\"message\":\"Channel has no device (possible internal error).\"}\r\n");
1091 else if (!privileged_user(device))
1092 (void)snprintf(reply + strlen(reply),
1093 replylen - strlen(reply),
1094 "{\"class\":\"ERROR\",\"message\":\"Multiple subscribers, cannot change control bits on %s.\"}\r\n",
1095 device->gpsdata.dev.path);
1096 else if (device->device_type == NULL)
1097 (void)snprintf(reply + strlen(reply),
1098 replylen - strlen(reply),
1099 "{\"class\":\"ERROR\",\"message\":\"Type of %s is unknown.\"}\r\n",
1100 device->gpsdata.dev.path);
1103 const struct gps_type_t *dt = device->device_type;
1104 /* interpret defaults */
1105 if (devconf.baudrate == DEVDEFAULT_BPS)
1107 (uint) gpsd_get_speed(&device->ttyset);
1108 if (devconf.parity == DEVDEFAULT_PARITY)
1109 devconf.stopbits = device->gpsdata.dev.stopbits;
1110 if (devconf.stopbits == DEVDEFAULT_STOPBITS)
1111 devconf.stopbits = device->gpsdata.dev.stopbits;
1112 if (isnan(devconf.cycle))
1113 devconf.cycle = device->gpsdata.dev.cycle;
1115 /* now that channel is selected, apply changes */
1116 if (devconf.driver_mode != device->gpsdata.dev.driver_mode
1117 && devconf.driver_mode != DEVDEFAULT_NATIVE
1118 && dt->mode_switcher != NULL)
1119 dt->mode_switcher(device, devconf.driver_mode);
1121 serialmode[0] = devconf.parity;
1122 serialmode[1] = '0' + devconf.stopbits;
1123 serialmode[2] = '\0';
1125 (speed_t) devconf.baudrate, serialmode);
1126 if (dt->rate_switcher != NULL
1127 && isnan(devconf.cycle) == 0
1128 && devconf.cycle >= dt->min_cycle)
1129 if (dt->rate_switcher(device, devconf.cycle))
1130 device->gpsdata.dev.cycle = devconf.cycle;
1134 #else /* ALLOW_RECONFIGURE */
1135 (void)snprintf(reply + strlen(reply), replylen - strlen(reply),
1136 "{\"class\":\"ERROR\",\"message\":\"Device configuration support not compiled.\"}\r\n");
1137 #endif /* ALLOW_RECONFIGURE */
1139 /* dump a response for each selected channel */
1140 for (devp = devices; devp < devices + MAXDEVICES; devp++)
1141 if (!allocated_device(devp))
1143 else if (devconf.path[0] != '\0' && devp != NULL
1144 && strcmp(devp->gpsdata.dev.path, devconf.path) != 0)
1147 json_device_dump(devp,
1148 reply + strlen(reply),
1149 replylen - strlen(reply));
1151 } else if (strncmp(buf, "POLL;", 5) == 0) {
1154 for (devp = devices; devp < devices + MAXDEVICES; devp++)
1155 if (allocated_device(devp) && subscribed(sub, devp))
1156 if ((devp->observed & GPS_TYPEMASK) != 0)
1158 (void)snprintf(reply, replylen,
1159 "{\"class\":\"POLL\",\"timestamp\":%.3f,\"active\":%d,\"fixes\":[",
1160 timestamp(), active);
1161 for (devp = devices; devp < devices + MAXDEVICES; devp++) {
1162 if (allocated_device(devp) && subscribed(sub, devp)) {
1163 if ((devp->observed & GPS_TYPEMASK) != 0) {
1164 json_tpv_dump(&devp->gpsdata,
1165 reply + strlen(reply),
1166 replylen - strlen(reply));
1168 (void)strlcat(reply, ",", replylen);
1172 if (reply[strlen(reply) - 1] == ',')
1173 reply[strlen(reply) - 1] = '\0'; /* trim trailing comma */
1174 (void)strlcat(reply, "],\"skyviews\":[", replylen);
1175 for (devp = devices; devp < devices + MAXDEVICES; devp++) {
1176 if (allocated_device(devp) && subscribed(sub, devp)) {
1177 if ((devp->observed & GPS_TYPEMASK) != 0) {
1178 json_sky_dump(&devp->gpsdata,
1179 reply + strlen(reply),
1180 replylen - strlen(reply));
1182 (void)strlcat(reply, ",", replylen);
1186 if (reply[strlen(reply) - 1] == ',')
1187 reply[strlen(reply) - 1] = '\0'; /* trim trailing comma */
1188 (void)strlcat(reply, "]}]}\r\n", replylen);
1189 } else if (strncmp(buf, "VERSION;", 8) == 0) {
1191 json_version_dump(reply, replylen);
1194 errend = buf + strlen(buf) - 1;
1195 while (isspace(*errend) && errend > buf)
1197 (void)snprintf(reply, replylen,
1198 "{\"class\":\"ERROR\",\"message\":\"Unrecognized request '%.*s'\"}\r\n",
1199 (int)(errend - buf), buf);
1200 gpsd_report(LOG_ERROR, "ERROR response: %s\n", reply);
1205 /*@+nullderef +nullpass@*/
1209 static void raw_report(struct subscriber_t *sub, struct gps_device_t *device)
1210 /* report a raw packet to a subscriber */
1214 * NMEA and other textual sentences are simply
1215 * copied to all clients that are in raw or nmea
1218 if (TEXTUAL_PACKET_TYPE(device->packet.type)
1219 && (sub->policy.raw > 0 || sub->policy.nmea)) {
1220 (void)throttled_write(sub,
1221 (char *)device->packet.
1223 device->packet.outbuflen);
1228 * Also, simply copy if user has specified
1231 if (sub->policy.raw > 1) {
1232 (void)throttled_write(sub,
1233 (char *)device->packet.
1235 device->packet.outbuflen);
1238 #ifdef BINARY_ENABLE
1240 * Maybe the user wants a binary packet hexdumped.
1242 if (sub->policy.raw == 1) {
1244 gpsd_hexdump((char *)device->packet.outbuffer,
1245 device->packet.outbuflen);
1247 * Ugh...depends on knowing the length of gpsd_hexdump's
1250 (void)strlcat(hd, "\r\n", MAX_PACKET_LENGTH * 2 + 1);
1251 (void)throttled_write(sub, hd, strlen(hd));
1253 #endif /* BINARY_ENABLE */
1256 static void pseudonmea_report(struct subscriber_t *sub,
1258 struct gps_device_t *device)
1259 /* report pseodo-NMEA in appropriate circumstances */
1261 if (GPS_PACKET_TYPE(device->packet.type)
1262 && !TEXTUAL_PACKET_TYPE(device->packet.type)) {
1263 char buf[MAX_PACKET_LENGTH * 3 + 2];
1265 gpsd_report(LOG_PROG, "data mask is %s\n",
1266 gpsd_maskdump(device->gpsdata.set));
1267 if ((changed & REPORT_IS) != 0) {
1268 nmea_tpv_dump(device, buf, sizeof(buf));
1269 gpsd_report(LOG_IO, "<= GPS (binary1) %s: %s\n",
1270 device->gpsdata.dev.path, buf);
1271 (void)throttled_write(sub, buf, strlen(buf));
1272 } else if ((changed & SATELLITE_IS) != 0) {
1273 nmea_sky_dump(device, buf, sizeof(buf));
1274 gpsd_report(LOG_IO, "<= GPS (binary2) %s: %s\n",
1275 device->gpsdata.dev.path, buf);
1276 (void)throttled_write(sub, buf, strlen(buf));
1281 static void json_report(struct subscriber_t *sub,
1283 struct gps_device_t *device)
1284 /* report in JSON format to a subscriber */
1286 char buf[GPS_JSON_RESPONSE_MAX * 4];
1289 if ((changed & REPORT_IS) != 0) {
1290 json_tpv_dump(&device->gpsdata,
1292 (void)throttled_write(sub, buf, strlen(buf));
1295 if ((changed & SATELLITE_IS) != 0) {
1296 json_sky_dump(&device->gpsdata,
1298 (void)throttled_write(sub, buf, strlen(buf));
1300 #ifdef COMPASS_ENABLE
1301 if ((changed & ATT_IS) != 0) {
1302 json_att_dump(&device->gpsdata,
1304 (void)throttled_write(sub, buf, strlen(buf));
1306 #endif /* COMPASS_ENABLE */
1307 #ifdef RTCM104V2_ENABLE
1308 if ((changed & RTCM2_IS) != 0) {
1309 rtcm2_json_dump(&device->gpsdata.rtcm2, buf,
1311 (void)throttled_write(sub, buf, strlen(buf));
1313 #endif /* RTCM104V2_ENABLE */
1315 if ((changed & AIS_IS) != 0) {
1316 aivdm_json_dump(&device->gpsdata.ais,
1319 (void)throttled_write(sub, buf, strlen(buf));
1321 #endif /* AIVDM_ENABLE */
1323 #ifdef TIMING_ENABLE
1324 if (buf[0] != '\0' && sub->policy.timing) {
1325 (void)snprintf(buf, sizeof(buf),
1326 "{\"class\":\"TIMING\","
1327 "\"tag\":\"%s\",\"len\":%d,"
1328 "\"xmit\":%lf,\"recv\":%lf,"
1330 "\"emit\":%lf}\r\n",
1331 device->gpsdata.tag,
1332 (int)device->packet.outbuflen,
1333 device->d_xmit_time,
1334 device->d_recv_time,
1335 device->d_decode_time,
1337 (void)throttled_write(sub, buf, strlen(buf));
1339 #endif /* TIMING_ENABLE */
1342 static void consume_packets(struct gps_device_t *device)
1343 /* consume and report packets from a specified device */
1347 struct subscriber_t *sub;
1349 gpsd_report(LOG_RAW + 1, "polling %d\n",
1350 device->gpsdata.gps_fd);
1352 for (fragments = 0; ; fragments++) {
1353 changed = gpsd_poll(device);
1355 if (changed == ERROR_IS) {
1356 gpsd_report(LOG_WARN,
1357 "device read of %s returned error or packet sniffer failed sync (flags %s)\n",
1358 device->gpsdata.dev.path,
1359 gpsd_maskdump(changed));
1360 deactivate_device(device);
1362 } else if (changed == NODATA_IS) {
1364 * No data on the first fragment read means the device
1365 * fd may have been in an end-of-file condition on select.
1367 if (fragments == 0) {
1368 gpsd_report(LOG_DATA,
1369 "%s returned zero bytes\n",
1370 device->gpsdata.dev.path);
1371 if (device->zerokill)
1372 /* failed timeout-and-reawake, kill it */
1373 deactivate_device(device);
1376 * Disable listening to this fd for long enough
1377 * that the buffer can fill up again.
1379 gpsd_report(LOG_DATA,
1380 "%s will be repolled in %f seconds\n",
1381 device->gpsdata.dev.path, DEVICE_REAWAKE);
1382 device->reawake = timestamp() + DEVICE_REAWAKE;
1383 FD_CLR(device->gpsdata.gps_fd, &all_fds);
1384 adjust_max_fd(device->gpsdata.gps_fd, false);
1388 * No data on later fragment reads just means the
1389 * input buffer is empty. In this case break out
1390 * of the packet-processing loop but don't drop
1396 /* we got actual data, head off the reawake special case */
1397 device->zerokill = false;
1398 device->reawake = 0;
1400 /* must have a full packet to continue */
1401 if ((changed & PACKET_IS) == 0)
1404 gpsd_report(LOG_DATA,
1405 "packet from %s with %s\n",
1406 device->gpsdata.dev.path,
1407 gpsd_maskdump(device->gpsdata.set));
1409 /* add any just-identified device to watcher lists */
1410 if ((changed & DRIVER_IS) != 0) {
1411 bool listeners = false;
1412 for (sub = subscribers;
1413 sub < subscribers + MAXSUBSCRIBERS; sub++)
1414 if (sub->active != 0
1415 && sub->policy.watcher
1416 && (sub->policy.devpath[0] == '\0'
1417 || strcmp(sub->policy.devpath,
1418 device->gpsdata.dev.path) == 0))
1421 (void)awaken(device);
1424 /* handle laggy response to a firmware version query */
1425 if ((changed & (DEVICEID_IS | DRIVER_IS)) != 0) {
1426 assert(device->device_type != NULL);
1428 char id2[GPS_JSON_RESPONSE_MAX];
1429 json_device_dump(device, id2, sizeof(id2));
1430 notify_watchers(device, id2);
1435 * If the device provided an RTCM packet, stash it
1436 * in the context structure for use as a future correction.
1438 if ((changed & RTCM2_IS) != 0 || (changed & RTCM3_IS) != 0) {
1439 if (device->packet.outbuflen > RTCM_MAX) {
1440 gpsd_report(LOG_ERROR,
1441 "overlong RTCM packet (%zd bytes)\n",
1442 device->packet.outbuflen);
1444 context.rtcmbytes = device->packet.outbuflen;
1445 memcpy(context.rtcmbuf,
1446 device->packet.outbuffer,
1452 * If no reliable end of cycle, must report every time
1453 * a sentence changes position or mode. Likely to
1454 * cause display jitter.
1456 if (!device->cycle_end_reliable && (changed & (LATLON_IS | MODE_IS))!=0)
1457 changed |= REPORT_IS;
1459 /* a few things are not per-subscriber reports */
1460 if ((changed & REPORT_IS) != 0) {
1461 if (device->gpsdata.fix.mode == MODE_3D)
1462 netgnss_report(device);
1464 send_dbus_fix(device);
1465 #endif /* DBUS_ENABLE */
1468 /* update all subscribers associated with this device */
1469 for (sub = subscribers; sub < subscribers + MAXSUBSCRIBERS; sub++) {
1471 if (sub == NULL || sub->active == 0)
1474 /* report raw packets to users subscribed to those */
1475 raw_report(sub, device);
1477 /* some listeners may be in watcher mode */
1478 if (sub->policy.watcher) {
1479 if (changed & DATA_IS) {
1480 gpsd_report(LOG_PROG,
1481 "Changed mask: %s with %sreliable cycle detection\n",
1482 gpsd_maskdump(changed),
1483 device->cycle_end_reliable ? "" : "un");
1484 if ((changed & REPORT_IS) != 0)
1485 gpsd_report(LOG_PROG, "time to report a fix\n");
1487 if (sub->policy.nmea)
1488 pseudonmea_report(sub, changed, device);
1490 if (sub->policy.json)
1491 json_report(sub, changed, device);
1498 * Trying to read a nonexistent datagram hangs,
1499 * so only go through the poll loop once after
1500 * select in this case.
1502 if (device->sourcetype == source_udp)
1507 static int handle_gpsd_request(struct subscriber_t *sub, const char *buf)
1508 /* execute GPSD requests from a buffer */
1510 char reply[GPS_JSON_RESPONSE_MAX + 1];
1513 if (buf[0] == '?') {
1515 for (end = ++buf; *buf != '\0'; buf = end)
1519 handle_request(sub, buf, &end,
1520 reply + strlen(reply),
1521 sizeof(reply) - strlen(reply));
1523 return (int)throttled_write(sub, reply, strlen(reply));
1526 /*@ -mustfreefresh @*/
1527 int main(int argc, char *argv[])
1529 char *pid_file = NULL;
1531 static char *gpsd_service = NULL; /* static pacifies splint */
1532 char *control_socket = NULL;
1533 struct gps_device_t *device;
1535 fd_set rfds, control_fds;
1536 int i, option, msocks[2], cfd, dfd;
1537 bool go_background = true;
1539 struct subscriber_t *sub;
1540 const struct gps_type_t **dp;
1543 pthread_mutex_init(&report_mutex, NULL);
1544 #endif /* PPS_ENABLE */
1546 #ifdef HAVE_SETLOCALE
1547 (void)setlocale(LC_NUMERIC, "C");
1550 gpsd_hexdump_level = 0;
1551 while ((option = getopt(argc, argv, "F:D:S:bGhlNnP:V")) != -1) {
1554 debuglevel = (int)strtol(optarg, 0, 0);
1555 gpsd_hexdump_level = debuglevel;
1556 #ifdef CLIENTDEBUG_ENABLE
1557 gps_enable_debug(debuglevel, stderr);
1558 #endif /* CLIENTDEBUG_ENABLE */
1561 control_socket = optarg;
1564 go_background = false;
1567 context.readonly = true;
1570 listen_global = true;
1572 case 'l': /* list known device types and exit */
1573 for (dp = gpsd_drivers; *dp; dp++) {
1574 #ifdef ALLOW_RECONFIGURE
1575 if ((*dp)->mode_switcher != NULL)
1576 (void)fputs("n\t", stdout);
1578 (void)fputc('\t', stdout);
1579 if ((*dp)->speed_switcher != NULL)
1580 (void)fputs("b\t", stdout);
1582 (void)fputc('\t', stdout);
1583 if ((*dp)->rate_switcher != NULL)
1584 (void)fputs("c\t", stdout);
1586 (void)fputc('\t', stdout);
1587 #endif /* ALLOW_RECONFIGURE */
1588 (void)puts((*dp)->type_name);
1592 gpsd_service = optarg;
1601 (void)printf("gpsd: %s (revision %s)\n", VERSION, REVISION);
1611 #ifdef FIXED_PORT_SPEED
1612 /* Assume that if we're running with FIXED_PORT_SPEED we're some sort
1613 * of embedded configuration where we don't want to wait for connect */
1617 if (!control_socket && optind >= argc) {
1618 gpsd_report(LOG_ERROR,
1619 "can't run with neither control socket nor devices\n");
1624 * Control socket has to be created before we go background in order to
1625 * avoid a race condition in which hotplug scripts can try opening
1626 * the socket before it's created.
1628 if (control_socket) {
1629 (void)unlink(control_socket);
1630 if ((csock = filesock(control_socket)) == -1) {
1631 gpsd_report(LOG_ERROR,
1632 "control socket create failed, netlib error %d\n",
1636 gpsd_report(LOG_SPIN, "control socket %s is fd %d\n",
1637 control_socket, csock);
1638 FD_SET(csock, &all_fds);
1639 adjust_max_fd(csock, true);
1640 gpsd_report(LOG_PROG, "control socket opened at %s\n",
1650 if ((fp = fopen(pid_file, "w")) != NULL) {
1651 (void)fprintf(fp, "%u\n", (unsigned int)getpid());
1654 gpsd_report(LOG_ERROR, "Cannot create PID file: %s.\n", pid_file);
1658 openlog("gpsd", LOG_PID, LOG_USER);
1659 gpsd_report(LOG_INF, "launching (Version %s)\n", VERSION);
1660 /*@ -observertrans @*/
1663 getservbyname("gpsd", "tcp") ? "gpsd" : DEFAULT_GPSD_PORT;
1664 /*@ +observertrans @*/
1665 if (passivesocks(gpsd_service, "tcp", QLEN, msocks) < 1) {
1666 gpsd_report(LOG_ERR,
1667 "command sockets creation failed, netlib errors %d, %d\n",
1668 msocks[0], msocks[1]);
1671 gpsd_report(LOG_INF, "listening on port %s\n", gpsd_service);
1673 #ifdef NTPSHM_ENABLE
1674 if (getuid() == 0) {
1676 // nice() can ONLY succeed when run as root!
1677 // do not even bother as non-root
1678 if (nice(NICEVAL) == -1 && errno != 0)
1679 gpsd_report(LOG_INF, "NTPD Priority setting failed.\n");
1681 (void)ntpshm_init(&context, nowait);
1682 #endif /* NTPSHM_ENABLE */
1685 /* we need to connect to dbus as root */
1686 if (initialize_dbus_connection()) {
1687 /* the connection could not be started */
1688 gpsd_report(LOG_ERROR, "unable to connect to the DBUS system bus\n");
1690 gpsd_report(LOG_PROG,
1691 "successfully connected to the DBUS system bus\n");
1692 #endif /* DBUS_ENABLE */
1694 if (getuid() == 0 && go_background) {
1698 /* make default devices accessible even after we drop privileges */
1699 for (i = optind; i < argc; i++)
1700 if (stat(argv[i], &stb) == 0)
1701 (void)chmod(argv[i], stb.st_mode | S_IRGRP | S_IWGRP);
1703 * Drop privileges. Up to now we've been running as root. Instead,
1704 * set the user ID to 'nobody' (or whatever the --enable-gpsd-user
1705 * is) and the group ID to the owning group of a prototypical TTY
1706 * device. This limits the scope of any compromises in the code.
1707 * It requires that all GPS devices have their group read/write
1711 if ((optind < argc && stat(argv[optind], &stb) == 0)
1712 || stat(PROTO_TTY, &stb) == 0) {
1713 gpsd_report(LOG_PROG, "changing to group %d\n", stb.st_gid);
1714 if (setgid(stb.st_gid) != 0)
1715 gpsd_report(LOG_ERROR, "setgid() failed, errno %s\n",
1720 struct group *grp = getgrnam(GPSD_GROUP);
1722 (void)setgid(grp->gr_gid);
1725 pw = getpwnam(GPSD_USER);
1727 (void)setuid(pw->pw_uid);
1730 gpsd_report(LOG_INF, "running with effective group ID %d\n", getegid());
1731 gpsd_report(LOG_INF, "running with effective user ID %d\n", geteuid());
1733 for (i = 0; i < NITEMS(subscribers); i++)
1734 subscribers[i].fd = UNALLOCATED_FD;
1736 /* daemon got termination or interrupt signal */
1737 if ((st = setjmp(restartbuf)) > 0) {
1738 /* try to undo all device configurations */
1739 for (dfd = 0; dfd < MAXDEVICES; dfd++) {
1740 if (allocated_device(&devices[dfd]))
1741 (void)gpsd_wrap(&devices[dfd]);
1743 gpsd_report(LOG_WARN, "gpsd restarted by SIGHUP\n");
1746 /* Handle some signals */
1748 (void)signal(SIGHUP, onsig);
1749 (void)signal(SIGINT, onsig);
1750 (void)signal(SIGTERM, onsig);
1751 (void)signal(SIGQUIT, onsig);
1752 (void)signal(SIGPIPE, SIG_IGN);
1754 for (i = 0; i < AFCOUNT; i++)
1755 if (msocks[i] >= 0) {
1756 FD_SET(msocks[i], &all_fds);
1757 adjust_max_fd(msocks[i], true);
1759 FD_ZERO(&control_fds);
1761 /* optimization hack to defer having to read subframe data */
1762 if (time(NULL) < START_SUBFRAME)
1763 context.valid |= LEAP_SECOND_VALID;
1765 for (i = optind; i < argc; i++) {
1766 if (!add_device(argv[i])) {
1767 gpsd_report(LOG_ERROR,
1768 "GPS device %s nonexistent or can't be read\n",
1773 while (0 == signalled) {
1774 (void)memcpy((char *)&rfds, (char *)&all_fds, sizeof(rfds));
1776 gpsd_report(LOG_RAW + 2, "select waits\n");
1778 * Poll for user commands or GPS data. The timeout doesn't
1779 * actually matter here since select returns whenever one of
1780 * the file descriptors in the set goes ready. The point
1781 * of tracking maxfd is to keep the set of descriptors that
1782 * select(2) has to poll here as small as possible (for
1783 * low-clock-rate SBCs and the like).
1789 if (select(maxfd + 1, &rfds, NULL, NULL, &tv) == -1) {
1792 gpsd_report(LOG_ERROR, "select: %s\n", strerror(errno));
1797 if (debuglevel >= LOG_SPIN) {
1800 for (i = 0; i < FD_SETSIZE; i++)
1801 if (FD_ISSET(i, &all_fds))
1802 (void)snprintf(dbuf + strlen(dbuf),
1803 sizeof(dbuf) - strlen(dbuf), "%d ", i);
1804 if (strlen(dbuf) > 0)
1805 dbuf[strlen(dbuf) - 1] = '\0';
1806 (void)strlcat(dbuf, "} -> {", BUFSIZ);
1807 for (i = 0; i < FD_SETSIZE; i++)
1808 if (FD_ISSET(i, &rfds))
1809 (void)snprintf(dbuf + strlen(dbuf),
1810 sizeof(dbuf) - strlen(dbuf), " %d ", i);
1811 gpsd_report(LOG_SPIN, "select() {%s} at %f (errno %d)\n",
1812 dbuf, timestamp(), errno);
1815 /* always be open to new client connections */
1816 for (i = 0; i < AFCOUNT; i++) {
1817 if (msocks[i] >= 0 && FD_ISSET(msocks[i], &rfds)) {
1818 socklen_t alen = (socklen_t) sizeof(fsin);
1820 /*@+matchanyintegral@*/
1822 accept(msocks[i], (struct sockaddr *)&fsin, &alen);
1823 /*@+matchanyintegral@*/
1826 gpsd_report(LOG_ERROR, "accept: %s\n", strerror(errno));
1828 struct subscriber_t *client = NULL;
1829 int opts = fcntl(ssock, F_GETFL);
1830 static struct linger linger = { 1, RELEASE_TIMEOUT };
1833 (void)fcntl(ssock, F_SETFL, opts | O_NONBLOCK);
1835 c_ip = netlib_sock2ip(ssock);
1836 client = allocate_client();
1837 if (client == NULL) {
1838 gpsd_report(LOG_ERROR, "Client %s connect on fd %d -"
1839 "no subscriber slots available\n", c_ip,
1844 (ssock, SOL_SOCKET, SO_LINGER, (char *)&linger,
1845 (int)sizeof(struct linger)) == -1) {
1846 gpsd_report(LOG_ERROR,
1847 "Error: SETSOCKOPT SO_LINGER\n");
1850 char announce[GPS_JSON_RESPONSE_MAX];
1851 FD_SET(ssock, &all_fds);
1852 adjust_max_fd(ssock, true);
1854 client->active = timestamp();
1855 gpsd_report(LOG_SPIN,
1856 "client %s (%d) connect on fd %d\n", c_ip,
1857 sub_index(client), ssock);
1858 json_version_dump(announce, sizeof(announce));
1859 (void)throttled_write(client, announce,
1863 FD_CLR(msocks[i], &rfds);
1867 /* also be open to new control-socket connections */
1868 if (csock > -1 && FD_ISSET(csock, &rfds)) {
1869 socklen_t alen = (socklen_t) sizeof(fsin);
1870 /*@+matchanyintegral@*/
1871 int ssock = accept(csock, (struct sockaddr *)&fsin, &alen);
1872 /*@-matchanyintegral@*/
1875 gpsd_report(LOG_ERROR, "accept: %s\n", strerror(errno));
1877 gpsd_report(LOG_INF, "control socket connect on fd %d\n",
1879 FD_SET(ssock, &all_fds);
1880 FD_SET(ssock, &control_fds);
1881 adjust_max_fd(ssock, true);
1883 FD_CLR(csock, &rfds);
1886 if (context.dsock >= 0 && FD_ISSET(context.dsock, &rfds)) {
1887 /* be ready for DGPS reports */
1888 if (netgnss_poll(&context) == -1) {
1889 FD_CLR(context.dsock, &all_fds);
1890 FD_CLR(context.dsock, &rfds);
1895 /* read any commands that came in over control sockets */
1896 for (cfd = 0; cfd < FD_SETSIZE; cfd++)
1897 if (FD_ISSET(cfd, &control_fds)) {
1900 while (read(cfd, buf, sizeof(buf) - 1) > 0) {
1901 gpsd_report(LOG_IO, "<= control(%d): %s\n", cfd, buf);
1902 handle_control(cfd, buf);
1904 gpsd_report(LOG_SPIN, "close(%d) of control socket\n", cfd);
1906 FD_CLR(cfd, &all_fds);
1907 FD_CLR(cfd, &control_fds);
1908 adjust_max_fd(cfd, false);
1911 /* poll all active devices */
1912 for (device = devices; device < devices + MAXDEVICES; device++) {
1913 if (!allocated_device(device))
1916 /* pass the current RTCM correction to the GPS if new */
1917 if (device->device_type != NULL)
1920 if (device->gpsdata.gps_fd >= 0) {
1921 if (FD_ISSET(device->gpsdata.gps_fd, &rfds))
1922 /* get data from the device */
1923 consume_packets(device);
1924 else if (device->reawake>0 && timestamp()>device->reawake) {
1925 /* device may have had a zero-length read */
1926 gpsd_report(LOG_DATA,
1927 "%s reawakened after zero-length read\n",
1928 device->gpsdata.dev.path);
1929 device->reawake = 0;
1930 device->zerokill = true;
1931 FD_SET(device->gpsdata.gps_fd, &all_fds);
1932 adjust_max_fd(device->gpsdata.gps_fd, true);
1938 if (context.fixcnt > 0 && context.dsock == -1) {
1939 for (device = devices; device < devices + MAXDEVICES; device++) {
1940 if (device->gpsdata.fix.mode > MODE_NO_FIX) {
1941 netgnss_autoconnect(&context,
1942 device->gpsdata.fix.latitude,
1943 device->gpsdata.fix.longitude);
1950 /* accept and execute commands for all clients */
1951 for (sub = subscribers; sub < subscribers + MAXSUBSCRIBERS; sub++) {
1952 if (sub->active == 0)
1955 if (FD_ISSET(sub->fd, &rfds)) {
1959 gpsd_report(LOG_PROG, "checking client(%d)\n",
1962 (int)recv(sub->fd, buf, sizeof(buf) - 1, 0)) <= 0) {
1965 if (buf[buflen - 1] != '\n')
1966 buf[buflen++] = '\n';
1969 "<= client(%d): %s\n", sub_index(sub), buf);
1972 * When a command comes in, update subscriber.active to
1973 * timestamp() so we don't close the connection
1974 * after COMMAND_TIMEOUT seconds. This makes
1975 * COMMAND_TIMEOUT useful.
1977 sub->active = timestamp();
1978 if (handle_gpsd_request(sub, buf) < 0)
1982 if (!sub->policy.watcher
1983 && timestamp() - sub->active > COMMAND_TIMEOUT) {
1984 gpsd_report(LOG_WARN,
1985 "client(%d) timed out on command wait.\n",
1993 * Mark devices with an identified packet type but no
1994 * remaining subscribers to be closed in RELEASE_TIME seconds.
1995 * See the explanation of RELEASE_TIME for the reasoning.
1998 for (device = devices; device < devices + MAXDEVICES; device++) {
1999 if (allocated_device(device)) {
2000 if (device->packet.type != BAD_PACKET) {
2001 bool device_needed = false;
2003 for (sub = subscribers;
2004 sub < subscribers + MAXSUBSCRIBERS; sub++) {
2005 if (sub->active == 0)
2007 else if (subscribed(sub, device)) {
2008 device_needed = true;
2013 if (!device_needed && device->gpsdata.gps_fd > -1) {
2014 if (device->releasetime == 0) {
2015 device->releasetime = timestamp();
2016 gpsd_report(LOG_PROG,
2017 "device %d (fd %d) released\n",
2018 (int)(device - devices),
2019 device->gpsdata.gps_fd);
2020 } else if (timestamp() - device->releasetime >
2022 gpsd_report(LOG_PROG, "device %d closed\n",
2023 (int)(device - devices));
2024 gpsd_report(LOG_RAW,
2025 "unflagging descriptor %d\n",
2026 device->gpsdata.gps_fd);
2027 deactivate_device(device);
2038 /* if we make it here, we got a signal... deal with it */
2039 /* restart on SIGHUP, clean up and exit otherwise */
2040 if (SIGHUP == (int)signalled)
2041 longjmp(restartbuf, 1);
2043 gpsd_report(LOG_WARN, "received terminating signal %d.\n", signalled);
2045 /* try to undo all device configurations */
2046 for (dfd = 0; dfd < MAXDEVICES; dfd++) {
2047 if (allocated_device(&devices[dfd]))
2048 (void)gpsd_wrap(&devices[dfd]);
2051 gpsd_report(LOG_WARN, "exiting.\n");
2053 * A linger option was set on each client socket when it was
2054 * created. Now, shut them down gracefully, letting I/O drain.
2055 * This is an attempt to avoid the sporadic race errors at the ends
2056 * of our regression tests.
2058 for (sub = subscribers; sub < subscribers + MAXSUBSCRIBERS; sub++) {
2059 if (sub->active != 0)
2064 (void)unlink(control_socket);
2066 (void)unlink(pid_file);
2070 /*@ +mustfreefresh @*/