summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGravatar Nikias Bassen2014-11-12 19:53:06 +0100
committerGravatar Nikias Bassen2014-11-12 19:53:06 +0100
commita3cae2b7a3dfe8120f2a65a1fae8640bb4f095a5 (patch)
tree855adf6fdeb4dd526ddd549ecb5a5a3bcce5241d
parenta5e57e872bb5be8b13d3497f2c07fff8a8e37f3f (diff)
downloadusbmuxd-a3cae2b7a3dfe8120f2a65a1fae8640bb4f095a5.tar.gz
usbmuxd-a3cae2b7a3dfe8120f2a65a1fae8640bb4f095a5.tar.bz2
Use non-blocking sockets for client communication
This approach is better than using blocking sockets and select() since there's no guarantee that send() doesn't block. Plus we're using poll() anyway so send() and recv() will only be called if the socket is actually ready for writing/reading.
-rw-r--r--src/client.c23
-rw-r--r--src/main.c9
2 files changed, 31 insertions, 1 deletions
diff --git a/src/client.c b/src/client.c
index 268c8b9..4ec4025 100644
--- a/src/client.c
+++ b/src/client.c
@@ -33,6 +33,7 @@
33#include <sys/un.h> 33#include <sys/un.h>
34#include <arpa/inet.h> 34#include <arpa/inet.h>
35#include <pthread.h> 35#include <pthread.h>
36#include <fcntl.h>
36 37
37#include <plist/plist.h> 38#include <plist/plist.h>
38 39
@@ -100,12 +101,23 @@ int client_read(struct mux_client *client, void *buffer, uint32_t len)
100 */ 101 */
101int client_write(struct mux_client *client, void *buffer, uint32_t len) 102int client_write(struct mux_client *client, void *buffer, uint32_t len)
102{ 103{
104 int sret = -1;
105
103 usbmuxd_log(LL_SPEW, "client_write fd %d buf %p len %d", client->fd, buffer, len); 106 usbmuxd_log(LL_SPEW, "client_write fd %d buf %p len %d", client->fd, buffer, len);
104 if(client->state != CLIENT_CONNECTED) { 107 if(client->state != CLIENT_CONNECTED) {
105 usbmuxd_log(LL_ERROR, "Attempted to write to client %d not in CONNECTED state", client->fd); 108 usbmuxd_log(LL_ERROR, "Attempted to write to client %d not in CONNECTED state", client->fd);
106 return -1; 109 return -1;
107 } 110 }
108 return send(client->fd, buffer, len, 0); 111
112 sret = send(client->fd, buffer, len, 0);
113 if (sret < 0) {
114 if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) {
115 usbmuxd_log(LL_ERROR, "ERROR: client_write: fd %d not ready for writing", client->fd);
116 } else {
117 usbmuxd_log(LL_ERROR, "ERROR: client_write: sending to fd %d failed: %s", client->fd, strerror(errno));
118 }
119 }
120 return sret;
109} 121}
110 122
111/** 123/**
@@ -150,6 +162,15 @@ int client_accept(int listenfd)
150 return cfd; 162 return cfd;
151 } 163 }
152 164
165 int flags = fcntl(cfd, F_GETFL, 0);
166 if (flags < 0) {
167 usbmuxd_log(LL_ERROR, "ERROR: Could not get socket flags!");
168 } else {
169 if (fcntl(cfd, F_SETFL, flags | O_NONBLOCK) < 0) {
170 usbmuxd_log(LL_ERROR, "ERROR: Could not set socket to non-blocking mode");
171 }
172 }
173
153 struct mux_client *client; 174 struct mux_client *client;
154 client = malloc(sizeof(struct mux_client)); 175 client = malloc(sizeof(struct mux_client));
155 memset(client, 0, sizeof(struct mux_client)); 176 memset(client, 0, sizeof(struct mux_client));
diff --git a/src/main.c b/src/main.c
index b1f4eeb..2e4439c 100644
--- a/src/main.c
+++ b/src/main.c
@@ -82,6 +82,15 @@ static int create_socket(void) {
82 return -1; 82 return -1;
83 } 83 }
84 84
85 int flags = fcntl(listenfd, F_GETFL, 0);
86 if (flags < 0) {
87 usbmuxd_log(LL_FATAL, "ERROR: Could not get flags for socket");
88 } else {
89 if (fcntl(listenfd, F_SETFL, flags | O_NONBLOCK) < 0) {
90 usbmuxd_log(LL_FATAL, "ERROR: Could not set socket to non-blocking");
91 }
92 }
93
85 bzero(&bind_addr, sizeof(bind_addr)); 94 bzero(&bind_addr, sizeof(bind_addr));
86 bind_addr.sun_family = AF_UNIX; 95 bind_addr.sun_family = AF_UNIX;
87 strcpy(bind_addr.sun_path, socket_path); 96 strcpy(bind_addr.sun_path, socket_path);