summaryrefslogtreecommitdiff
path: root/netlib.c
diff options
context:
space:
mode:
authorEric S. Raymond <esr@thyrsus.com>2010-09-15 09:54:52 -0400
committerEric S. Raymond <esr@thyrsus.com>2010-09-15 09:54:52 -0400
commitbeebdc432d19aa4ffe029bda0b186706fa563aad (patch)
tree4dbf7af280451e40668e748606078d2bc7006e17 /netlib.c
parent318fed1131119802b4702c009f83177702742a4c (diff)
downloadgpsd-beebdc432d19aa4ffe029bda0b186706fa563aad.tar.gz
Switch TCP socket sources to nonblocking mode.
This follows a suggestion from Christian Eddie Dost <ecd@brainaid.de>, who had this to say: However, gpsd hangs when used with a tcp:// device, if you start the device without waiting for clients (-n option), there will never be a client connection accepted. If you start gpsd without -n option one client will be accepted and receive data, but when closing the client connection there will be no new connection possible. The problem is gpsd hangs inside consume_packets() or more exactly inside a blocking read() on the tcp socket a few functions further down. consume_packets() never returns to the main select() loop. The following patch configures sockets to non blocking, this fixes the problem and gpsd works fine for me with tcp:// devices. Using this patch should allow the special udp handling at the end of the function consume_packets() to be removed. I applied the suggested patch and also removed the special UDP handing. All regressions test pass (including the UDP one), and gpsd -N tcp://data.aishub.net:4006 reads AIS data as expected.
Diffstat (limited to 'netlib.c')
-rw-r--r--netlib.c4
1 files changed, 4 insertions, 0 deletions
diff --git a/netlib.c b/netlib.c
index 9726f36f..bff75c7b 100644
--- a/netlib.c
+++ b/netlib.c
@@ -34,6 +34,7 @@
#include <unistd.h>
#endif /* S_SPLINT_S */
#include <string.h>
+#include <fcntl.h>
#include "gpsd.h"
#include "sockaddr.h"
@@ -138,6 +139,9 @@ socket_t netlib_connectsock(int af, const char *host, const char *service,
setsockopt(s, IPPROTO_TCP, TCP_NODELAY, (char *)&one, sizeof one);
#endif
+ /* set socket to noblocking */
+ fcntl(s, F_SETFL, fcntl(s, F_GETFL) | O_NONBLOCK);
+
gpsd_report(LOG_SPIN, "netlib_connectsock() returns socket on fd %d\n",
s);
return s;