diff options
author | Christian Grothoff <christian@grothoff.org> | 2009-11-01 20:47:52 +0000 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2009-11-01 20:47:52 +0000 |
commit | 652e89b59ed2207c2c12172fdabcd6e659995c81 (patch) | |
tree | f054c819d483c1056e18c1099afd4c7fcd2582a0 /src/util/network.c | |
parent | 5e4113e83368849500792e57946c3d8dd9e548d8 (diff) | |
download | gnunet-652e89b59ed2207c2c12172fdabcd6e659995c81.tar.gz gnunet-652e89b59ed2207c2c12172fdabcd6e659995c81.zip |
fixing bio testcase and a bug in bio.c, also indenting
Diffstat (limited to 'src/util/network.c')
-rw-r--r-- | src/util/network.c | 1600 |
1 files changed, 827 insertions, 773 deletions
diff --git a/src/util/network.c b/src/util/network.c index 071b18cc6..df3c90c81 100644 --- a/src/util/network.c +++ b/src/util/network.c | |||
@@ -16,90 +16,94 @@ | |||
16 | along with GNUnet; see the file COPYING. If not, write to the | 16 | along with GNUnet; see the file COPYING. If not, write to the |
17 | Free Software Foundation, Inc., 59 Temple Place - Suite 330, | 17 | Free Software Foundation, Inc., 59 Temple Place - Suite 330, |
18 | Boston, MA 02111-1307, USA. | 18 | Boston, MA 02111-1307, USA. |
19 | */ | 19 | */ |
20 | 20 | ||
21 | /** | 21 | /** |
22 | * @file util/network.c | 22 | * @file util/network.c |
23 | * @brief basic, low-level networking interface | 23 | * @brief basic, low-level networking interface |
24 | * @author Nils Durner | 24 | * @author Nils Durner |
25 | */ | 25 | */ |
26 | 26 | ||
27 | #include "platform.h" | 27 | #include "platform.h" |
28 | #include "gnunet_disk_lib.h" | 28 | #include "gnunet_disk_lib.h" |
29 | #include "disk.h" | 29 | #include "disk.h" |
30 | #include "gnunet_container_lib.h" | 30 | #include "gnunet_container_lib.h" |
31 | 31 | ||
32 | #define DEBUG_NETWORK GNUNET_NO | 32 | #define DEBUG_NETWORK GNUNET_NO |
33 | 33 | ||
34 | #ifndef INVALID_SOCKET | 34 | #ifndef INVALID_SOCKET |
35 | #define INVALID_SOCKET -1 | 35 | #define INVALID_SOCKET -1 |
36 | #endif | 36 | #endif /* */ |
37 | 37 | struct GNUNET_NETWORK_Handle | |
38 | struct GNUNET_NETWORK_Handle | 38 | { |
39 | { | 39 | int fd; |
40 | int fd; | 40 | }; |
41 | }; | 41 | struct GNUNET_NETWORK_FDSet |
42 | 42 | { | |
43 | struct GNUNET_NETWORK_FDSet | 43 | |
44 | { | 44 | /* socket descriptors */ |
45 | /* socket descriptors */ | 45 | int nsds; |
46 | int nsds; | 46 | fd_set sds; |
47 | fd_set sds; | 47 | |
48 | #ifdef WINDOWS | 48 | #ifdef WINDOWS |
49 | /* handles */ | 49 | /* handles */ |
50 | struct GNUNET_CONTAINER_SList *handles; | 50 | struct GNUNET_CONTAINER_SList *handles; |
51 | #endif | 51 | |
52 | }; | 52 | #endif /* */ |
53 | 53 | }; | |
54 | |||
54 | #ifndef FD_COPY | 55 | #ifndef FD_COPY |
55 | #define FD_COPY(s, d) (memcpy ((d), (s), sizeof (fd_set))) | 56 | #define FD_COPY(s, d) (memcpy ((d), (s), sizeof (fd_set))) |
56 | #endif | 57 | #endif /* */ |
57 | 58 | ||
58 | |||
59 | |||
60 | /** | 59 | /** |
61 | * Set if a socket should use blocking or non-blocking IO. | 60 | * Set if a socket should use blocking or non-blocking IO. |
62 | * @param fd socket | 61 | * @param fd socket |
63 | * @param doBlock blocking mode | 62 | * @param doBlock blocking mode |
64 | * @return GNUNET_OK on success, GNUNET_SYSERR on error | 63 | * @return GNUNET_OK on success, GNUNET_SYSERR on error |
65 | */ | 64 | */ |
66 | static int | 65 | static int |
67 | socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, | 66 | socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, int doBlock) |
68 | int doBlock) | 67 | { |
69 | { | 68 | |
70 | #if MINGW | 69 | #if MINGW |
71 | u_long mode; | 70 | u_long mode; |
72 | mode = !doBlock; | 71 | mode = !doBlock; |
73 | if (ioctlsocket (fd->fd, FIONBIO, &mode) == SOCKET_ERROR) | 72 | if (ioctlsocket (fd->fd, FIONBIO, &mode) == SOCKET_ERROR) |
74 | { | 73 | |
75 | SetErrnoFromWinsockError (WSAGetLastError ()); | 74 | { |
76 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "ioctlsocket"); | 75 | SetErrnoFromWinsockError (WSAGetLastError ()); |
77 | return GNUNET_SYSERR; | 76 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "ioctlsocket"); |
78 | } | 77 | return GNUNET_SYSERR; |
79 | return GNUNET_OK; | 78 | } |
80 | 79 | return GNUNET_OK; | |
81 | #else | 80 | |
82 | /* not MINGW */ | 81 | #else /* */ |
83 | int flags = fcntl (fd->fd, F_GETFL); | 82 | /* not MINGW */ |
84 | if (flags == -1) | 83 | int flags = fcntl (fd->fd, F_GETFL); |
85 | { | 84 | if (flags == -1) |
86 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "fcntl"); | 85 | |
87 | return GNUNET_SYSERR; | 86 | { |
88 | } | 87 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "fcntl"); |
89 | if (doBlock) | 88 | return GNUNET_SYSERR; |
90 | flags &= ~O_NONBLOCK; | 89 | } |
91 | else | 90 | if (doBlock) |
92 | flags |= O_NONBLOCK; | 91 | flags &= ~O_NONBLOCK; |
93 | if (0 != fcntl (fd->fd, F_SETFL, flags)) | 92 | |
94 | { | 93 | else |
95 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "fcntl"); | 94 | flags |= O_NONBLOCK; |
96 | return GNUNET_SYSERR; | 95 | if (0 != fcntl (fd->fd, F_SETFL, flags)) |
97 | } | 96 | |
98 | return GNUNET_OK; | 97 | { |
99 | #endif | 98 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "fcntl"); |
100 | } | 99 | return GNUNET_SYSERR; |
101 | 100 | } | |
102 | 101 | return GNUNET_OK; | |
102 | |||
103 | #endif /* */ | ||
104 | } | ||
105 | |||
106 | |||
103 | #ifndef MINGW | 107 | #ifndef MINGW |
104 | /** | 108 | /** |
105 | * Make a socket non-inheritable to child processes | 109 | * Make a socket non-inheritable to child processes |
@@ -107,62 +111,56 @@ socket_set_blocking (struct GNUNET_NETWORK_Handle *fd, | |||
107 | * @param h the socket to make non-inheritable | 111 | * @param h the socket to make non-inheritable |
108 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 112 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
109 | * @warning Not implemented on Windows | 113 | * @warning Not implemented on Windows |
110 | */ | 114 | */ |
111 | static int | 115 | static int |
112 | socket_set_inheritable (const struct GNUNET_NETWORK_Handle | 116 | socket_set_inheritable (const struct GNUNET_NETWORK_Handle *h) |
113 | *h) | 117 | { |
114 | { | 118 | int i; |
115 | int i; | 119 | i = fcntl (h->fd, F_GETFD); |
116 | 120 | if (i == (i | FD_CLOEXEC)) | |
117 | i = fcntl (h->fd, F_GETFD); | 121 | return GNUNET_OK; |
118 | if (i == (i | FD_CLOEXEC)) | 122 | return (fcntl (h->fd, F_SETFD, i | FD_CLOEXEC) == 0) |
119 | return GNUNET_OK; | 123 | ? GNUNET_OK : GNUNET_SYSERR; |
120 | return (fcntl (h->fd, F_SETFD, i | FD_CLOEXEC) == 0) | 124 | } |
121 | ? GNUNET_OK : GNUNET_SYSERR; | 125 | |
122 | } | 126 | |
123 | #endif | 127 | #endif /* */ |
124 | 128 | ||
125 | |||
126 | |||
127 | #ifdef DARWIN | 129 | #ifdef DARWIN |
128 | /** | 130 | /** |
129 | * The MSG_NOSIGNAL equivalent on Mac OS X | 131 | * The MSG_NOSIGNAL equivalent on Mac OS X |
130 | * | 132 | * |
131 | * @param h the socket to make non-delaying | 133 | * @param h the socket to make non-delaying |
132 | */ | 134 | */ |
133 | static void | 135 | static void |
134 | socket_set_nosigpipe (const struct GNUNET_NETWORK_Handle | 136 | socket_set_nosigpipe (const struct GNUNET_NETWORK_Handle *h) |
135 | *h) | 137 | { |
136 | { | 138 | int value = 1; |
137 | int value = 1; | 139 | if (0 != |
138 | if (0 != setsockopt (h->fd, SOL_SOCKET, SO_NOSIGPIPE, &value, sizeof(value))) | 140 | setsockopt (h->fd, SOL_SOCKET, SO_NOSIGPIPE, &value, sizeof (value))) |
139 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, | 141 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "setsockopt"); |
140 | "setsockopt"); | 142 | } |
141 | } | 143 | |
142 | #endif | 144 | |
143 | 145 | #endif /* */ | |
144 | 146 | ||
145 | |||
146 | /** | 147 | /** |
147 | * Disable delays when sending data via the socket. | 148 | * Disable delays when sending data via the socket. |
148 | * (GNUnet makes sure that messages are as big as | 149 | * (GNUnet makes sure that messages are as big as |
149 | * possible already). | 150 | * possible already). |
150 | * | 151 | * |
151 | * @param h the socket to make non-delaying | 152 | * @param h the socket to make non-delaying |
152 | */ | 153 | */ |
153 | static void | 154 | static void |
154 | socket_set_nodelay (const struct GNUNET_NETWORK_Handle | 155 | socket_set_nodelay (const struct GNUNET_NETWORK_Handle *h) |
155 | *h) | 156 | { |
156 | { | 157 | int value = 1; |
157 | int value = 1; | 158 | if (0 != |
158 | if (0 != setsockopt (h->fd, IPPROTO_TCP, TCP_NODELAY, &value, sizeof(value))) | 159 | setsockopt (h->fd, IPPROTO_TCP, TCP_NODELAY, &value, sizeof (value))) |
159 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, | 160 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "setsockopt"); |
160 | "setsockopt"); | 161 | } |
161 | 162 | ||
162 | } | 163 | |
163 | |||
164 | |||
165 | |||
166 | /** | 164 | /** |
167 | * accept a new connection on a socket | 165 | * accept a new connection on a socket |
168 | * | 166 | * |
@@ -170,124 +168,142 @@ socket_set_nodelay (const struct GNUNET_NETWORK_Handle | |||
170 | * @param address address of the connecting peer, may be NULL | 168 | * @param address address of the connecting peer, may be NULL |
171 | * @param address_len length of address | 169 | * @param address_len length of address |
172 | * @return client socket | 170 | * @return client socket |
173 | */ | 171 | */ |
174 | struct GNUNET_NETWORK_Handle * | 172 | struct GNUNET_NETWORK_Handle * |
175 | GNUNET_NETWORK_socket_accept (const struct GNUNET_NETWORK_Handle *desc, | 173 | GNUNET_NETWORK_socket_accept (const struct GNUNET_NETWORK_Handle *desc, |
176 | struct sockaddr *address, | 174 | struct sockaddr *address, |
177 | socklen_t * address_len) | 175 | socklen_t * address_len) |
178 | { | 176 | { |
179 | struct GNUNET_NETWORK_Handle *ret; | 177 | struct GNUNET_NETWORK_Handle *ret; |
180 | 178 | ret = GNUNET_malloc (sizeof (struct GNUNET_NETWORK_Handle)); | |
181 | ret = GNUNET_malloc (sizeof (struct GNUNET_NETWORK_Handle)); | 179 | ret->fd = accept (desc->fd, address, address_len); |
182 | ret->fd = accept (desc->fd, address, address_len); | 180 | if (ret->fd == INVALID_SOCKET) |
183 | if (ret->fd == INVALID_SOCKET) | 181 | |
184 | { | 182 | { |
183 | |||
185 | #ifdef MINGW | 184 | #ifdef MINGW |
186 | SetErrnoFromWinsockError (WSAGetLastError ()); | 185 | SetErrnoFromWinsockError (WSAGetLastError ()); |
187 | #endif | 186 | |
188 | GNUNET_free (ret); | 187 | #endif /* */ |
189 | return NULL; | 188 | GNUNET_free (ret); |
190 | } | 189 | return NULL; |
190 | } | ||
191 | |||
191 | #ifndef MINGW | 192 | #ifndef MINGW |
192 | if (ret->fd >= FD_SETSIZE) | 193 | if (ret->fd >= FD_SETSIZE) |
193 | { | 194 | |
194 | GNUNET_break (0 == close (ret->fd)); | 195 | { |
195 | GNUNET_free (ret); | 196 | GNUNET_break (0 == close (ret->fd)); |
196 | errno = EMFILE; | 197 | GNUNET_free (ret); |
197 | return NULL; | 198 | errno = EMFILE; |
198 | } | 199 | return NULL; |
199 | #endif | 200 | } |
200 | if (GNUNET_SYSERR == socket_set_blocking (ret, GNUNET_NO)) | 201 | |
201 | { | 202 | #endif /* */ |
202 | /* we might want to treat this one as fatal... */ | 203 | if (GNUNET_SYSERR == socket_set_blocking (ret, GNUNET_NO)) |
203 | GNUNET_break (0); | 204 | |
204 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (ret)); | 205 | { |
205 | return NULL; | 206 | |
206 | } | 207 | /* we might want to treat this one as fatal... */ |
208 | GNUNET_break (0); | ||
209 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (ret)); | ||
210 | return NULL; | ||
211 | } | ||
212 | |||
207 | #ifndef MINGW | 213 | #ifndef MINGW |
208 | if (GNUNET_OK != socket_set_inheritable (ret)) | 214 | if (GNUNET_OK != socket_set_inheritable (ret)) |
209 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, | 215 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, |
210 | "socket_set_inheritable"); | 216 | "socket_set_inheritable"); |
211 | #endif | 217 | |
218 | #endif /* */ | ||
212 | #ifdef DARWIN | 219 | #ifdef DARWIN |
213 | socket_set_nosigpipe (ret); | 220 | socket_set_nosigpipe (ret); |
214 | #endif | 221 | |
215 | socket_set_nodelay (ret); | 222 | #endif /* */ |
216 | return ret; | 223 | socket_set_nodelay (ret); |
217 | } | 224 | return ret; |
218 | 225 | } | |
226 | |||
227 | |||
219 | /** | 228 | /** |
220 | * Bind to a connected socket | 229 | * Bind to a connected socket |
221 | * @param desc socket | 230 | * @param desc socket |
222 | * @param address address to be bound | 231 | * @param address address to be bound |
223 | * @param address_len length of address | 232 | * @param address_len length of address |
224 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 233 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
225 | */ | 234 | */ |
226 | int | 235 | int |
227 | GNUNET_NETWORK_socket_bind (struct GNUNET_NETWORK_Handle *desc, | 236 | GNUNET_NETWORK_socket_bind (struct GNUNET_NETWORK_Handle *desc, |
228 | const struct sockaddr *address, | 237 | const struct sockaddr *address, |
229 | socklen_t address_len) | 238 | socklen_t address_len) |
230 | { | 239 | { |
231 | int ret; | 240 | int ret; |
232 | 241 | ret = bind (desc->fd, address, address_len); | |
233 | ret = bind (desc->fd, address, address_len); | 242 | |
234 | #ifdef MINGW | 243 | #ifdef MINGW |
235 | if (SOCKET_ERROR == ret) | 244 | if (SOCKET_ERROR == ret) |
236 | SetErrnoFromWinsockError (WSAGetLastError ()); | 245 | SetErrnoFromWinsockError (WSAGetLastError ()); |
237 | #endif | 246 | |
238 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | 247 | #endif /* */ |
239 | } | 248 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; |
240 | 249 | } | |
241 | 250 | ||
251 | |||
242 | /** | 252 | /** |
243 | * Close a socket | 253 | * Close a socket |
244 | * @param desc socket | 254 | * @param desc socket |
245 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 255 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
246 | */ | 256 | */ |
247 | int | 257 | int |
248 | GNUNET_NETWORK_socket_close (struct GNUNET_NETWORK_Handle *desc) | 258 | GNUNET_NETWORK_socket_close (struct GNUNET_NETWORK_Handle *desc) |
249 | { | 259 | { |
250 | int ret; | 260 | int ret; |
251 | int eno; | 261 | int eno; |
252 | 262 | ||
253 | #ifdef MINGW | 263 | #ifdef MINGW |
254 | ret = closesocket (desc->fd); | 264 | ret = closesocket (desc->fd); |
255 | SetErrnoFromWinsockError (WSAGetLastError ()); | 265 | SetErrnoFromWinsockError (WSAGetLastError ()); |
256 | #else | 266 | |
257 | ret = close (desc->fd); | 267 | #else /* */ |
258 | #endif | 268 | ret = close (desc->fd); |
259 | eno = errno; | 269 | |
260 | GNUNET_free (desc); | 270 | #endif /* */ |
261 | errno = eno; | 271 | eno = errno; |
262 | return (ret == 0) ? GNUNET_OK : GNUNET_SYSERR; | 272 | GNUNET_free (desc); |
263 | } | 273 | errno = eno; |
264 | 274 | return (ret == 0) ? GNUNET_OK : GNUNET_SYSERR; | |
275 | } | ||
276 | |||
277 | |||
265 | /** | 278 | /** |
266 | * Connect a socket | 279 | * Connect a socket |
267 | * @param desc socket | 280 | * @param desc socket |
268 | * @param address peer address | 281 | * @param address peer address |
269 | * @param address_len length of address | 282 | * @param address_len length of address |
270 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 283 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
271 | */ | 284 | */ |
272 | int | 285 | int |
273 | GNUNET_NETWORK_socket_connect (const struct GNUNET_NETWORK_Handle *desc, | 286 | GNUNET_NETWORK_socket_connect (const struct GNUNET_NETWORK_Handle *desc, |
274 | const struct sockaddr *address, | 287 | const struct sockaddr *address, |
275 | socklen_t address_len) | 288 | socklen_t address_len) |
276 | { | 289 | { |
277 | int ret; | 290 | int ret; |
278 | 291 | ret = connect (desc->fd, address, address_len); | |
279 | ret = connect (desc->fd, address, address_len); | 292 | |
280 | #ifdef MINGW | 293 | #ifdef MINGW |
281 | if (SOCKET_ERROR == ret) | 294 | if (SOCKET_ERROR == ret) |
282 | { | 295 | |
283 | SetErrnoFromWinsockError (WSAGetLastError ()); | 296 | { |
284 | if (errno == EWOULDBLOCK) | 297 | SetErrnoFromWinsockError (WSAGetLastError ()); |
285 | errno = EINPROGRESS; | 298 | if (errno == EWOULDBLOCK) |
286 | } | 299 | errno = EINPROGRESS; |
287 | #endif | 300 | } |
288 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | 301 | |
289 | } | 302 | #endif /* */ |
290 | 303 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | |
304 | } | ||
305 | |||
306 | |||
291 | /** | 307 | /** |
292 | * Get socket options | 308 | * Get socket options |
293 | * | 309 | * |
@@ -297,71 +313,78 @@ GNUNET_NETWORK_socket_connect (const struct GNUNET_NETWORK_Handle *desc, | |||
297 | * @param optval options | 313 | * @param optval options |
298 | * @param optlen length of optval | 314 | * @param optlen length of optval |
299 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 315 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
300 | */ | 316 | */ |
301 | int | 317 | int |
302 | GNUNET_NETWORK_socket_getsockopt (const struct GNUNET_NETWORK_Handle *desc, | 318 | GNUNET_NETWORK_socket_getsockopt (const struct GNUNET_NETWORK_Handle *desc, |
303 | int level, int optname, void *optval, | 319 | int level, int optname, void *optval, |
304 | socklen_t * optlen) | 320 | socklen_t * optlen) |
305 | { | 321 | { |
306 | int ret; | 322 | int ret; |
307 | 323 | ret = getsockopt (desc->fd, level, optname, optval, optlen); | |
308 | ret = getsockopt (desc->fd, level, optname, optval, optlen); | 324 | |
309 | #ifdef MINGW | 325 | #ifdef MINGW |
310 | if (ret == 0 && level == SOL_SOCKET && optname == SO_ERROR) | 326 | if (ret == 0 && level == SOL_SOCKET && optname == SO_ERROR) |
311 | *((int *) optval) = GetErrnoFromWinsockError (*((int *) optval)); | 327 | *((int *) optval) = GetErrnoFromWinsockError (*((int *) optval)); |
312 | else if (SOCKET_ERROR == ret) | 328 | |
313 | SetErrnoFromWinsockError (WSAGetLastError ()); | 329 | else if (SOCKET_ERROR == ret) |
314 | #endif | 330 | SetErrnoFromWinsockError (WSAGetLastError ()); |
315 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | 331 | |
316 | } | 332 | #endif /* */ |
317 | 333 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | |
334 | } | ||
335 | |||
336 | |||
318 | /** | 337 | /** |
319 | * Listen on a socket | 338 | * Listen on a socket |
320 | * @param desc socket | 339 | * @param desc socket |
321 | * @param backlog length of the listen queue | 340 | * @param backlog length of the listen queue |
322 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 341 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
323 | */ | 342 | */ |
324 | int | 343 | int |
325 | GNUNET_NETWORK_socket_listen (const struct GNUNET_NETWORK_Handle *desc, | 344 | GNUNET_NETWORK_socket_listen (const struct GNUNET_NETWORK_Handle *desc, |
326 | int backlog) | 345 | int backlog) |
327 | { | 346 | { |
328 | int ret; | 347 | int ret; |
329 | 348 | ret = listen (desc->fd, backlog); | |
330 | ret = listen (desc->fd, backlog); | 349 | |
331 | #ifdef MINGW | 350 | #ifdef MINGW |
332 | if (SOCKET_ERROR == ret) | 351 | if (SOCKET_ERROR == ret) |
333 | SetErrnoFromWinsockError (WSAGetLastError ()); | 352 | SetErrnoFromWinsockError (WSAGetLastError ()); |
334 | #endif | 353 | |
335 | 354 | #endif /* */ | |
336 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | 355 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; |
337 | } | 356 | } |
338 | 357 | ||
358 | |||
339 | /** | 359 | /** |
340 | * Read data from a connected socket (always non-blocking). | 360 | * Read data from a connected socket (always non-blocking). |
341 | * @param desc socket | 361 | * @param desc socket |
342 | * @param buffer buffer | 362 | * @param buffer buffer |
343 | * @param length length of buffer | 363 | * @param length length of buffer |
344 | */ | 364 | */ |
345 | ssize_t | 365 | ssize_t |
346 | GNUNET_NETWORK_socket_recv (const struct GNUNET_NETWORK_Handle * desc, | 366 | GNUNET_NETWORK_socket_recv (const struct GNUNET_NETWORK_Handle * desc, |
347 | void *buffer, size_t length) | 367 | void *buffer, size_t length) |
348 | { | 368 | { |
349 | int ret; | 369 | int ret; |
350 | int flags; | 370 | int flags; |
351 | 371 | flags = 0; | |
352 | flags = 0; | 372 | |
353 | #ifdef MSG_DONTWAIT | 373 | #ifdef MSG_DONTWAIT |
354 | flags |= MSG_DONTWAIT; | 374 | flags |= MSG_DONTWAIT; |
355 | #endif | 375 | |
356 | ret = recv (desc->fd, buffer, length, flags); | 376 | #endif /* */ |
377 | ret = recv (desc->fd, buffer, length, flags); | ||
378 | |||
357 | #ifdef MINGW | 379 | #ifdef MINGW |
358 | if (SOCKET_ERROR == ret) | 380 | if (SOCKET_ERROR == ret) |
359 | SetErrnoFromWinsockError (WSAGetLastError ()); | 381 | SetErrnoFromWinsockError (WSAGetLastError ()); |
360 | #endif | 382 | |
361 | 383 | #endif /* */ | |
362 | return ret; | 384 | return ret; |
363 | } | 385 | } |
364 | 386 | ||
387 | |||
365 | /** | 388 | /** |
366 | * Send data (always non-blocking). | 389 | * Send data (always non-blocking). |
367 | * | 390 | * |
@@ -369,31 +392,34 @@ GNUNET_NETWORK_socket_recv (const struct GNUNET_NETWORK_Handle * desc, | |||
369 | * @param buffer data to send | 392 | * @param buffer data to send |
370 | * @param length size of the buffer | 393 | * @param length size of the buffer |
371 | * @return number of bytes sent, GNUNET_SYSERR on error | 394 | * @return number of bytes sent, GNUNET_SYSERR on error |
372 | */ | 395 | */ |
373 | ssize_t | 396 | ssize_t |
374 | GNUNET_NETWORK_socket_send (const struct GNUNET_NETWORK_Handle * desc, | 397 | GNUNET_NETWORK_socket_send (const struct GNUNET_NETWORK_Handle * desc, |
375 | const void *buffer, size_t length) | 398 | const void *buffer, size_t length) |
376 | { | 399 | { |
377 | int ret; | 400 | int ret; |
378 | int flags; | 401 | int flags; |
379 | 402 | flags = 0; | |
380 | flags = 0; | 403 | |
381 | #ifdef MSG_DONTWAIT | 404 | #ifdef MSG_DONTWAIT |
382 | flags |= MSG_DONTWAIT; | 405 | flags |= MSG_DONTWAIT; |
383 | #endif | 406 | |
407 | #endif /* */ | ||
384 | #ifdef MSG_NOSIGNAL | 408 | #ifdef MSG_NOSIGNAL |
385 | flags |= MSG_NOSIGNAL; | 409 | flags |= MSG_NOSIGNAL; |
386 | #endif | 410 | |
387 | ret = send (desc->fd, buffer, length, flags); | 411 | #endif /* */ |
412 | ret = send (desc->fd, buffer, length, flags); | ||
413 | |||
388 | #ifdef MINGW | 414 | #ifdef MINGW |
389 | if (SOCKET_ERROR == ret) | 415 | if (SOCKET_ERROR == ret) |
390 | SetErrnoFromWinsockError (WSAGetLastError ()); | 416 | SetErrnoFromWinsockError (WSAGetLastError ()); |
391 | #endif | 417 | |
392 | 418 | #endif /* */ | |
393 | return ret; | 419 | return ret; |
394 | } | 420 | } |
395 | 421 | ||
396 | 422 | ||
397 | /** | 423 | /** |
398 | * Send data to a particular destination (always non-blocking). | 424 | * Send data to a particular destination (always non-blocking). |
399 | * This function only works for UDP sockets. | 425 | * This function only works for UDP sockets. |
@@ -404,32 +430,36 @@ GNUNET_NETWORK_socket_send (const struct GNUNET_NETWORK_Handle * desc, | |||
404 | * @param dest_addr destination address | 430 | * @param dest_addr destination address |
405 | * @param dest_len length of address | 431 | * @param dest_len length of address |
406 | * @return number of bytes sent, GNUNET_SYSERR on error | 432 | * @return number of bytes sent, GNUNET_SYSERR on error |
407 | */ | 433 | */ |
408 | ssize_t | 434 | ssize_t |
409 | GNUNET_NETWORK_socket_sendto (const struct GNUNET_NETWORK_Handle * desc, | 435 | GNUNET_NETWORK_socket_sendto (const struct GNUNET_NETWORK_Handle * desc, |
410 | const void *message, size_t length, | 436 | const void *message, size_t length, |
411 | const struct sockaddr * dest_addr, | 437 | const struct sockaddr * dest_addr, |
412 | socklen_t dest_len) | 438 | socklen_t dest_len) |
413 | { | 439 | { |
414 | int ret; | 440 | int ret; |
415 | int flags; | 441 | int flags; |
416 | 442 | flags = 0; | |
417 | flags = 0; | 443 | |
418 | #ifdef MSG_DONTWAIT | 444 | #ifdef MSG_DONTWAIT |
419 | flags |= MSG_DONTWAIT; | 445 | flags |= MSG_DONTWAIT; |
420 | #endif | 446 | |
447 | #endif /* */ | ||
421 | #ifdef MSG_NOSIGNAL | 448 | #ifdef MSG_NOSIGNAL |
422 | flags |= MSG_NOSIGNAL; | 449 | flags |= MSG_NOSIGNAL; |
423 | #endif | 450 | |
424 | ret = sendto (desc->fd, message, length, flags, dest_addr, dest_len); | 451 | #endif /* */ |
452 | ret = sendto (desc->fd, message, length, flags, dest_addr, dest_len); | ||
453 | |||
425 | #ifdef MINGW | 454 | #ifdef MINGW |
426 | if (SOCKET_ERROR == ret) | 455 | if (SOCKET_ERROR == ret) |
427 | SetErrnoFromWinsockError (WSAGetLastError ()); | 456 | SetErrnoFromWinsockError (WSAGetLastError ()); |
428 | #endif | 457 | |
429 | 458 | #endif /* */ | |
430 | return ret; | 459 | return ret; |
431 | } | 460 | } |
432 | 461 | ||
462 | |||
433 | /** | 463 | /** |
434 | * Set socket option | 464 | * Set socket option |
435 | * @param fd socket | 465 | * @param fd socket |
@@ -438,26 +468,25 @@ GNUNET_NETWORK_socket_sendto (const struct GNUNET_NETWORK_Handle * desc, | |||
438 | * @param option_value value to set | 468 | * @param option_value value to set |
439 | * @param option_len size of option_value | 469 | * @param option_len size of option_value |
440 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 470 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
441 | */ | 471 | */ |
442 | int | 472 | int |
443 | GNUNET_NETWORK_socket_setsockopt (struct GNUNET_NETWORK_Handle *fd, | 473 | GNUNET_NETWORK_socket_setsockopt (struct GNUNET_NETWORK_Handle *fd, |
444 | int level, int option_name, | 474 | int level, int option_name, |
445 | const void *option_value, | 475 | const void *option_value, |
446 | socklen_t option_len) | 476 | socklen_t option_len) |
447 | { | 477 | { |
448 | int ret; | 478 | int ret; |
449 | 479 | ret = setsockopt (fd->fd, level, option_name, option_value, option_len); | |
450 | ret = setsockopt (fd->fd, level, option_name, option_value, option_len); | 480 | |
451 | #ifdef MINGW | 481 | #ifdef MINGW |
452 | if (SOCKET_ERROR == ret) | 482 | if (SOCKET_ERROR == ret) |
453 | SetErrnoFromWinsockError (WSAGetLastError ()); | 483 | SetErrnoFromWinsockError (WSAGetLastError ()); |
454 | #endif | 484 | |
455 | 485 | #endif /* */ | |
456 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | 486 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; |
457 | } | 487 | } |
458 | 488 | ||
459 | 489 | ||
460 | |||
461 | /** | 490 | /** |
462 | * Create a new socket. Configure it for non-blocking IO and | 491 | * Create a new socket. Configure it for non-blocking IO and |
463 | * mark it as non-inheritable to child processes (set the | 492 | * mark it as non-inheritable to child processes (set the |
@@ -467,282 +496,297 @@ GNUNET_NETWORK_socket_setsockopt (struct GNUNET_NETWORK_Handle *fd, | |||
467 | * @param type socket type | 496 | * @param type socket type |
468 | * @param protocol network protocol | 497 | * @param protocol network protocol |
469 | * @return new socket, NULL on error | 498 | * @return new socket, NULL on error |
470 | */ | 499 | */ |
471 | struct GNUNET_NETWORK_Handle * | 500 | struct GNUNET_NETWORK_Handle * |
472 | GNUNET_NETWORK_socket_create (int domain, int type, int protocol) | 501 | GNUNET_NETWORK_socket_create (int domain, int type, int protocol) |
473 | { | 502 | { |
474 | struct GNUNET_NETWORK_Handle *ret; | 503 | struct GNUNET_NETWORK_Handle *ret; |
475 | 504 | ret = GNUNET_malloc (sizeof (struct GNUNET_NETWORK_Handle)); | |
476 | ret = GNUNET_malloc (sizeof (struct GNUNET_NETWORK_Handle)); | 505 | ret->fd = socket (domain, type, protocol); |
477 | ret->fd = socket (domain, type, protocol); | 506 | if (INVALID_SOCKET == ret->fd) |
478 | if (INVALID_SOCKET == ret->fd) | 507 | |
479 | { | 508 | { |
509 | |||
480 | #ifdef MINGW | 510 | #ifdef MINGW |
481 | SetErrnoFromWinsockError (WSAGetLastError ()); | 511 | SetErrnoFromWinsockError (WSAGetLastError ()); |
482 | #endif | 512 | |
483 | GNUNET_free (ret); | 513 | #endif /* */ |
484 | return NULL; | 514 | GNUNET_free (ret); |
485 | } | 515 | return NULL; |
516 | } | ||
517 | |||
486 | #ifndef MINGW | 518 | #ifndef MINGW |
487 | if (ret->fd >= FD_SETSIZE) | 519 | if (ret->fd >= FD_SETSIZE) |
488 | { | 520 | |
489 | GNUNET_break (0 == close (ret->fd)); | 521 | { |
490 | GNUNET_free (ret); | 522 | GNUNET_break (0 == close (ret->fd)); |
491 | errno = EMFILE; | 523 | GNUNET_free (ret); |
492 | return NULL; | 524 | errno = EMFILE; |
493 | } | 525 | return NULL; |
494 | #endif | 526 | } |
495 | 527 | ||
496 | if (GNUNET_SYSERR == socket_set_blocking (ret, GNUNET_NO)) | 528 | #endif /* */ |
497 | { | 529 | if (GNUNET_SYSERR == socket_set_blocking (ret, GNUNET_NO)) |
498 | /* we might want to treat this one as fatal... */ | 530 | |
499 | GNUNET_break (0); | 531 | { |
500 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (ret)); | 532 | |
501 | return NULL; | 533 | /* we might want to treat this one as fatal... */ |
502 | } | 534 | GNUNET_break (0); |
535 | GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (ret)); | ||
536 | return NULL; | ||
537 | } | ||
538 | |||
503 | #ifndef MINGW | 539 | #ifndef MINGW |
504 | if (GNUNET_OK != socket_set_inheritable (ret)) | 540 | if (GNUNET_OK != socket_set_inheritable (ret)) |
505 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, | 541 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, |
506 | "socket_set_inheritable"); | 542 | "socket_set_inheritable"); |
507 | #endif | 543 | |
544 | #endif /* */ | ||
508 | #ifdef DARWIN | 545 | #ifdef DARWIN |
509 | socket_set_nosigpipe (ret); | 546 | socket_set_nosigpipe (ret); |
510 | #endif | 547 | |
511 | if (type == SOCK_STREAM) | 548 | #endif /* */ |
512 | socket_set_nodelay (ret); | 549 | if (type == SOCK_STREAM) |
513 | 550 | socket_set_nodelay (ret); | |
514 | return ret; | 551 | return ret; |
515 | } | 552 | } |
516 | 553 | ||
554 | |||
517 | /** | 555 | /** |
518 | * Shut down socket operations | 556 | * Shut down socket operations |
519 | * @param desc socket | 557 | * @param desc socket |
520 | * @param how type of shutdown | 558 | * @param how type of shutdown |
521 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise | 559 | * @return GNUNET_OK on success, GNUNET_SYSERR otherwise |
522 | */ | 560 | */ |
523 | int | 561 | int |
524 | GNUNET_NETWORK_socket_shutdown (struct GNUNET_NETWORK_Handle *desc, | 562 | GNUNET_NETWORK_socket_shutdown (struct GNUNET_NETWORK_Handle *desc, |
525 | int how) | 563 | int how) |
526 | { | 564 | { |
527 | int ret; | 565 | int ret; |
528 | 566 | ret = shutdown (desc->fd, how); | |
529 | ret = shutdown (desc->fd, how); | 567 | |
530 | #ifdef MINGW | 568 | #ifdef MINGW |
531 | if (ret != 0) | 569 | if (ret != 0) |
532 | SetErrnoFromWinsockError (WSAGetLastError ()); | 570 | SetErrnoFromWinsockError (WSAGetLastError ()); |
533 | #endif | 571 | |
534 | 572 | #endif /* */ | |
535 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; | 573 | return ret == 0 ? GNUNET_OK : GNUNET_SYSERR; |
536 | } | 574 | } |
537 | 575 | ||
538 | 576 | ||
539 | /** | 577 | /** |
540 | * Reset FD set | 578 | * Reset FD set |
541 | * @param fds fd set | 579 | * @param fds fd set |
542 | */ | 580 | */ |
543 | void | 581 | void |
544 | GNUNET_NETWORK_fdset_zero (struct GNUNET_NETWORK_FDSet *fds) | 582 | GNUNET_NETWORK_fdset_zero (struct GNUNET_NETWORK_FDSet *fds) |
545 | { | 583 | { |
546 | FD_ZERO (&fds->sds); | 584 | FD_ZERO (&fds->sds); |
547 | fds->nsds = 0; | 585 | fds->nsds = 0; |
586 | |||
548 | #ifdef MINGW | 587 | #ifdef MINGW |
549 | GNUNET_CONTAINER_slist_clear (fds->handles); | 588 | GNUNET_CONTAINER_slist_clear (fds->handles); |
550 | #endif | 589 | |
551 | } | 590 | #endif /* */ |
552 | 591 | } | |
553 | 592 | ||
554 | /** | 593 | /** |
555 | * Add a socket to the FD set | 594 | * Add a socket to the FD set |
556 | * @param fds fd set | 595 | * @param fds fd set |
557 | * @param desc socket to add | 596 | * @param desc socket to add |
558 | */ | 597 | */ |
559 | void | 598 | void |
560 | GNUNET_NETWORK_fdset_set (struct GNUNET_NETWORK_FDSet *fds, | 599 | GNUNET_NETWORK_fdset_set (struct GNUNET_NETWORK_FDSet *fds, |
561 | const struct GNUNET_NETWORK_Handle *desc) | 600 | const struct GNUNET_NETWORK_Handle *desc) |
562 | { | 601 | { |
563 | FD_SET (desc->fd, &fds->sds); | 602 | FD_SET (desc->fd, &fds->sds); |
564 | 603 | if (desc->fd + 1 > fds->nsds) | |
565 | if (desc->fd + 1 > fds->nsds) | 604 | fds->nsds = desc->fd + 1; |
566 | fds->nsds = desc->fd + 1; | 605 | } |
567 | } | 606 | |
568 | 607 | ||
569 | |||
570 | /** | 608 | /** |
571 | * Check whether a socket is part of the fd set | 609 | * Check whether a socket is part of the fd set |
572 | * @param fds fd set | 610 | * @param fds fd set |
573 | * @param desc socket | 611 | * @param desc socket |
574 | * @return 0 if the FD is not set | 612 | * @return 0 if the FD is not set |
575 | */ | 613 | */ |
576 | int | 614 | int |
577 | GNUNET_NETWORK_fdset_isset (const struct GNUNET_NETWORK_FDSet *fds, | 615 | GNUNET_NETWORK_fdset_isset (const struct GNUNET_NETWORK_FDSet *fds, |
578 | const struct GNUNET_NETWORK_Handle *desc) | 616 | const struct GNUNET_NETWORK_Handle *desc) |
579 | { | 617 | { |
580 | return FD_ISSET (desc->fd, &fds->sds); | 618 | return FD_ISSET (desc->fd, &fds->sds); |
581 | } | 619 | } |
582 | 620 | ||
583 | 621 | ||
584 | /** | 622 | /** |
585 | * Add one fd set to another | 623 | * Add one fd set to another |
586 | * @param dst the fd set to add to | 624 | * @param dst the fd set to add to |
587 | * @param src the fd set to add from | 625 | * @param src the fd set to add from |
588 | */ | 626 | */ |
589 | void | 627 | void |
590 | GNUNET_NETWORK_fdset_add (struct GNUNET_NETWORK_FDSet *dst, | 628 | GNUNET_NETWORK_fdset_add (struct GNUNET_NETWORK_FDSet *dst, |
591 | const struct GNUNET_NETWORK_FDSet *src) | 629 | const struct GNUNET_NETWORK_FDSet *src) |
592 | { | 630 | { |
593 | int nfds; | 631 | int nfds; |
594 | 632 | for (nfds = src->nsds; nfds > 0; nfds--) | |
595 | for (nfds = src->nsds; nfds > 0; nfds--) | 633 | if (FD_ISSET (nfds, &src->sds)) |
596 | if (FD_ISSET (nfds, &src->sds)) | 634 | |
597 | { | 635 | { |
598 | FD_SET (nfds, &dst->sds); | 636 | FD_SET (nfds, &dst->sds); |
599 | if (nfds + 1 > dst->nsds) | 637 | if (nfds + 1 > dst->nsds) |
600 | dst->nsds = nfds + 1; | 638 | dst->nsds = nfds + 1; |
601 | } | 639 | } |
602 | } | 640 | } |
603 | 641 | ||
604 | 642 | ||
605 | /** | 643 | /** |
606 | * Copy one fd set to another | 644 | * Copy one fd set to another |
607 | * @param to destination | 645 | * @param to destination |
608 | * @param from source | 646 | * @param from source |
609 | */ | 647 | */ |
610 | void | 648 | void |
611 | GNUNET_NETWORK_fdset_copy (struct GNUNET_NETWORK_FDSet *to, | 649 | GNUNET_NETWORK_fdset_copy (struct GNUNET_NETWORK_FDSet *to, |
612 | const struct GNUNET_NETWORK_FDSet *from) | 650 | const struct GNUNET_NETWORK_FDSet *from) |
613 | { | 651 | { |
614 | FD_COPY (&from->sds, &to->sds); | 652 | FD_COPY (&from->sds, &to->sds); |
615 | to->nsds = from->nsds; | 653 | to->nsds = from->nsds; |
654 | |||
616 | #ifdef MINGW | 655 | #ifdef MINGW |
617 | struct GNUNET_CONTAINER_SList_Iterator *iter; | 656 | struct GNUNET_CONTAINER_SList_Iterator *iter; |
618 | 657 | GNUNET_CONTAINER_slist_clear (to->handles); | |
619 | 658 | for (iter = GNUNET_CONTAINER_slist_begin (from->handles); | |
620 | GNUNET_CONTAINER_slist_clear (to->handles); | 659 | GNUNET_CONTAINER_slist_end (iter) != GNUNET_YES; |
621 | 660 | GNUNET_CONTAINER_slist_next (iter)) | |
622 | for (iter = GNUNET_CONTAINER_slist_begin (from->handles); | 661 | |
623 | GNUNET_CONTAINER_slist_end (iter) != GNUNET_YES; GNUNET_CONTAINER_slist_next (iter)) | 662 | { |
624 | { | 663 | void *handle; |
625 | void *handle; | 664 | size_t len; |
626 | size_t len; | 665 | handle = GNUNET_CONTAINER_slist_get (iter, &len); |
627 | 666 | GNUNET_CONTAINER_slist_add (to->handles, | |
628 | handle = GNUNET_CONTAINER_slist_get (iter, &len); | 667 | GNUNET_CONTAINER_SLIST_DISPOSITION_TRANSIENT, |
629 | GNUNET_CONTAINER_slist_add (to->handles, GNUNET_CONTAINER_SLIST_DISPOSITION_TRANSIENT, handle, len); | 668 | handle, len); |
630 | } | 669 | } |
631 | #endif | 670 | #endif /* */ |
632 | } | 671 | } |
633 | 672 | ||
634 | |||
635 | /** | 673 | /** |
636 | * Copy a native fd set | 674 | * Copy a native fd set |
637 | * @param to destination | 675 | * @param to destination |
638 | * @param from native source set | 676 | * @param from native source set |
639 | * @param nfds the biggest socket number in from + 1 | 677 | * @param nfds the biggest socket number in from + 1 |
640 | */ | 678 | */ |
641 | void | 679 | void |
642 | GNUNET_NETWORK_fdset_copy_native (struct GNUNET_NETWORK_FDSet *to, | 680 | GNUNET_NETWORK_fdset_copy_native (struct GNUNET_NETWORK_FDSet *to, |
643 | const fd_set * from, int nfds) | 681 | const fd_set * from, int nfds) |
644 | { | 682 | { |
645 | FD_COPY (from, &to->sds); | 683 | FD_COPY (from, &to->sds); |
646 | to->nsds = nfds; | 684 | to->nsds = nfds; |
647 | } | 685 | } |
648 | 686 | ||
649 | |||
650 | /** | 687 | /** |
651 | * Add a file handle to the fd set | 688 | * Add a file handle to the fd set |
652 | * @param fds fd set | 689 | * @param fds fd set |
653 | * @param h the file handle to add | 690 | * @param h the file handle to add |
654 | */ | 691 | */ |
655 | void | 692 | void |
656 | GNUNET_NETWORK_fdset_handle_set (struct GNUNET_NETWORK_FDSet *fds, | 693 | GNUNET_NETWORK_fdset_handle_set (struct GNUNET_NETWORK_FDSet *fds, |
657 | const struct GNUNET_DISK_FileHandle *h) | 694 | const struct GNUNET_DISK_FileHandle *h) |
658 | { | 695 | { |
696 | |||
659 | #ifdef MINGW | 697 | #ifdef MINGW |
660 | HANDLE hw; | 698 | HANDLE hw; |
661 | 699 | GNUNET_DISK_internal_file_handle_ (h, &hw, sizeof (HANDLE)); | |
662 | GNUNET_DISK_internal_file_handle_ (h, &hw, sizeof (HANDLE)); | 700 | GNUNET_CONTAINER_slist_add (fds->handles, GNUNET_NO, &hw, sizeof (HANDLE)); |
663 | GNUNET_CONTAINER_slist_add (fds->handles, GNUNET_NO, &hw, sizeof (HANDLE)); | 701 | |
664 | #else | 702 | #else /* */ |
665 | int fd; | 703 | int fd; |
666 | 704 | GNUNET_DISK_internal_file_handle_ (h, &fd, sizeof (int)); | |
667 | GNUNET_DISK_internal_file_handle_ (h, &fd, sizeof (int)); | 705 | FD_SET (fd, &fds->sds); |
668 | FD_SET (fd, &fds->sds); | 706 | if (fd + 1 > fds->nsds) |
669 | if (fd + 1 > fds->nsds) | 707 | fds->nsds = fd + 1; |
670 | fds->nsds = fd + 1; | 708 | |
671 | #endif | 709 | #endif /* */ |
672 | } | 710 | } |
673 | 711 | ||
712 | |||
674 | /** | 713 | /** |
675 | * Check if a file handle is part of an fd set | 714 | * Check if a file handle is part of an fd set |
676 | * @param fds fd set | 715 | * @param fds fd set |
677 | * @param h file handle | 716 | * @param h file handle |
678 | * @return GNUNET_YES if the file handle is part of the set | 717 | * @return GNUNET_YES if the file handle is part of the set |
679 | */ | 718 | */ |
680 | int | 719 | int |
681 | GNUNET_NETWORK_fdset_handle_isset (const struct GNUNET_NETWORK_FDSet *fds, | 720 | GNUNET_NETWORK_fdset_handle_isset (const struct GNUNET_NETWORK_FDSet *fds, |
682 | const struct GNUNET_DISK_FileHandle *h) | 721 | const struct GNUNET_DISK_FileHandle *h) |
683 | { | 722 | { |
723 | |||
684 | #ifdef MINGW | 724 | #ifdef MINGW |
685 | return GNUNET_CONTAINER_slist_contains (fds->handles, h->h, sizeof (HANDLE)); | 725 | return GNUNET_CONTAINER_slist_contains (fds->handles, h->h, |
686 | #else | 726 | sizeof (HANDLE)); |
687 | return FD_ISSET (h->fd, &fds->sds); | 727 | |
688 | #endif | 728 | #else /* */ |
689 | } | 729 | return FD_ISSET (h->fd, &fds->sds); |
690 | 730 | ||
731 | #endif /* */ | ||
732 | } | ||
733 | |||
734 | |||
691 | /** | 735 | /** |
692 | * Checks if two fd sets overlap | 736 | * Checks if two fd sets overlap |
693 | * @param fds1 first fd set | 737 | * @param fds1 first fd set |
694 | * @param fds2 second fd set | 738 | * @param fds2 second fd set |
695 | * @return GNUNET_YES if they do overlap, GNUNET_NO otherwise | 739 | * @return GNUNET_YES if they do overlap, GNUNET_NO otherwise |
696 | */ | 740 | */ |
697 | int | 741 | int |
698 | GNUNET_NETWORK_fdset_overlap (const struct GNUNET_NETWORK_FDSet *fds1, | 742 | GNUNET_NETWORK_fdset_overlap (const struct GNUNET_NETWORK_FDSet *fds1, |
699 | const struct GNUNET_NETWORK_FDSet *fds2) | 743 | const struct GNUNET_NETWORK_FDSet *fds2) |
700 | { | 744 | { |
701 | int nfds; | 745 | int nfds; |
702 | 746 | nfds = fds1->nsds; | |
703 | nfds = fds1->nsds; | 747 | if (nfds < fds2->nsds) |
704 | if (nfds < fds2->nsds) | 748 | nfds = fds2->nsds; |
705 | nfds = fds2->nsds; | 749 | for (; nfds >= 0; nfds--) |
706 | 750 | if (FD_ISSET (nfds, &fds1->sds) && FD_ISSET (nfds, &fds2->sds)) | |
707 | for (; nfds >= 0; nfds--) | 751 | return GNUNET_YES; |
708 | if (FD_ISSET (nfds, &fds1->sds) && FD_ISSET (nfds, &fds2->sds)) | 752 | return GNUNET_NO; |
709 | return GNUNET_YES; | 753 | } |
710 | 754 | ||
711 | return GNUNET_NO; | 755 | |
712 | } | ||
713 | |||
714 | /** | 756 | /** |
715 | * Creates an fd set | 757 | * Creates an fd set |
716 | * @return a new fd set | 758 | * @return a new fd set |
717 | */ | 759 | */ |
718 | struct GNUNET_NETWORK_FDSet * | 760 | struct GNUNET_NETWORK_FDSet * |
719 | GNUNET_NETWORK_fdset_create () | 761 | GNUNET_NETWORK_fdset_create () |
720 | { | 762 | { |
721 | struct GNUNET_NETWORK_FDSet *fds; | 763 | struct GNUNET_NETWORK_FDSet *fds; |
722 | 764 | fds = GNUNET_malloc (sizeof (struct GNUNET_NETWORK_FDSet)); | |
723 | fds = GNUNET_malloc (sizeof (struct GNUNET_NETWORK_FDSet)); | 765 | |
724 | #ifdef MINGW | 766 | #ifdef MINGW |
725 | fds->handles = GNUNET_CONTAINER_slist_create (); | 767 | fds->handles = GNUNET_CONTAINER_slist_create (); |
726 | #endif | 768 | |
727 | GNUNET_NETWORK_fdset_zero (fds); | 769 | #endif /* */ |
728 | return fds; | 770 | GNUNET_NETWORK_fdset_zero (fds); |
729 | } | 771 | return fds; |
730 | 772 | } | |
731 | 773 | ||
774 | |||
732 | /** | 775 | /** |
733 | * Releases the associated memory of an fd set | 776 | * Releases the associated memory of an fd set |
734 | * @param fds fd set | 777 | * @param fds fd set |
735 | */ | 778 | */ |
736 | void | 779 | void |
737 | GNUNET_NETWORK_fdset_destroy (struct GNUNET_NETWORK_FDSet *fds) | 780 | GNUNET_NETWORK_fdset_destroy (struct GNUNET_NETWORK_FDSet *fds) |
738 | { | 781 | { |
782 | |||
739 | #ifdef MINGW | 783 | #ifdef MINGW |
740 | GNUNET_CONTAINER_slist_destroy (fds->handles); | 784 | GNUNET_CONTAINER_slist_destroy (fds->handles); |
741 | #endif | 785 | |
742 | GNUNET_free (fds); | 786 | #endif /* */ |
743 | } | 787 | GNUNET_free (fds); |
744 | 788 | } | |
745 | 789 | ||
746 | /** | 790 | /** |
747 | * Check if sockets meet certain conditions | 791 | * Check if sockets meet certain conditions |
748 | * @param rfds set of sockets to be checked for readability | 792 | * @param rfds set of sockets to be checked for readability |
@@ -750,249 +794,259 @@ GNUNET_NETWORK_fdset_destroy (struct GNUNET_NETWORK_FDSet *fds) | |||
750 | * @param efds set of sockets to be checked for exceptions | 794 | * @param efds set of sockets to be checked for exceptions |
751 | * @param timeout relative value when to return | 795 | * @param timeout relative value when to return |
752 | * @return number of selected sockets, GNUNET_SYSERR on error | 796 | * @return number of selected sockets, GNUNET_SYSERR on error |
753 | */ | 797 | */ |
754 | int | 798 | int |
755 | GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, | 799 | GNUNET_NETWORK_socket_select (struct GNUNET_NETWORK_FDSet *rfds, |
756 | struct GNUNET_NETWORK_FDSet *wfds, | 800 | struct GNUNET_NETWORK_FDSet *wfds, |
757 | struct GNUNET_NETWORK_FDSet *efds, | 801 | struct GNUNET_NETWORK_FDSet *efds, |
758 | const struct GNUNET_TIME_Relative timeout) | 802 | const struct GNUNET_TIME_Relative timeout) |
759 | { | 803 | { |
760 | int nfds; | 804 | int nfds; |
761 | 805 | nfds = 0; | |
762 | nfds = 0; | 806 | if (NULL != rfds) |
763 | if (NULL != rfds) | 807 | nfds = rfds->nsds; |
764 | nfds = rfds->nsds; | 808 | if (NULL != wfds) |
765 | if (NULL != wfds) | 809 | nfds = GNUNET_MAX (nfds, wfds->nsds); |
766 | nfds = GNUNET_MAX (nfds, wfds->nsds); | 810 | if (NULL != efds) |
767 | if (NULL != efds) | 811 | nfds = GNUNET_MAX (nfds, efds->nsds); |
768 | nfds = GNUNET_MAX (nfds, efds->nsds); | 812 | |
769 | |||
770 | #ifndef MINGW | 813 | #ifndef MINGW |
771 | struct timeval tv; | 814 | struct timeval tv; |
772 | 815 | tv.tv_sec = timeout.value / GNUNET_TIME_UNIT_SECONDS.value; | |
773 | tv.tv_sec = timeout.value / GNUNET_TIME_UNIT_SECONDS.value; | 816 | tv.tv_usec = |
774 | tv.tv_usec = 1000 * (timeout.value - (tv.tv_sec * GNUNET_TIME_UNIT_SECONDS.value)); | 817 | 1000 * (timeout.value - (tv.tv_sec * GNUNET_TIME_UNIT_SECONDS.value)); |
775 | if ( (nfds == 0) && | 818 | if ((nfds == 0) && (timeout.value == GNUNET_TIME_UNIT_FOREVER_REL.value)) |
776 | (timeout.value == GNUNET_TIME_UNIT_FOREVER_REL.value) ) | 819 | |
777 | { | 820 | { |
778 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 821 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
779 | _("Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n"), | 822 | _ |
780 | "select"); | 823 | ("Fatal internal logic error, process hangs in `%s' (abort with CTRL-C)!\n"), |
781 | GNUNET_break (0); | 824 | "select"); |
782 | } | 825 | GNUNET_break (0); |
783 | return select (nfds + 1, | 826 | } |
784 | (rfds != NULL) ? &rfds->sds : NULL, | 827 | return select (nfds + 1, |
785 | (wfds != NULL) ? &wfds->sds : NULL, | 828 | (rfds != NULL) ? &rfds->sds : NULL, |
786 | (efds != NULL) ? &efds->sds : NULL, | 829 | (wfds != NULL) ? &wfds->sds : NULL, |
787 | (timeout.value == GNUNET_TIME_UNIT_FOREVER_REL.value) | 830 | (efds != NULL) ? &efds->sds : NULL, |
788 | ? NULL | 831 | (timeout.value == GNUNET_TIME_UNIT_FOREVER_REL.value) |
789 | : &tv); | 832 | ? NULL : &tv); |
790 | #else | 833 | |
791 | DWORD limit; | 834 | #else /* */ |
792 | fd_set sock_read, sock_write, sock_except; | 835 | DWORD limit; |
793 | fd_set aread, awrite, aexcept; | 836 | fd_set sock_read, sock_write, sock_except; |
794 | int i; | 837 | fd_set aread, awrite, aexcept; |
795 | struct timeval tvslice; | 838 | int i; |
796 | int retcode; | 839 | struct timeval tvslice; |
797 | DWORD ms_total; | 840 | int retcode; |
798 | 841 | DWORD ms_total; | |
842 | |||
799 | #define SAFE_FD_ISSET(fd, set) (set != NULL && FD_ISSET(fd, set)) | 843 | #define SAFE_FD_ISSET(fd, set) (set != NULL && FD_ISSET(fd, set)) |
800 | 844 | ||
801 | /* calculate how long we need to wait in milliseconds */ | 845 | /* calculate how long we need to wait in milliseconds */ |
802 | if (timeout.value == GNUNET_TIME_UNIT_FOREVER_REL.value) | 846 | if (timeout.value == GNUNET_TIME_UNIT_FOREVER_REL.value) |
803 | ms_total = INFINITE; | 847 | ms_total = INFINITE; |
804 | else | 848 | |
805 | ms_total = timeout.value / GNUNET_TIME_UNIT_MILLISECONDS.value; | 849 | else |
806 | 850 | ms_total = timeout.value / GNUNET_TIME_UNIT_MILLISECONDS.value; | |
807 | /* select() may be used as a portable way to sleep */ | 851 | |
808 | if (!(rfds || wfds || efds)) | 852 | /* select() may be used as a portable way to sleep */ |
809 | { | 853 | if (!(rfds || wfds || efds)) |
810 | Sleep (ms_total); | 854 | |
811 | return 0; | 855 | { |
812 | } | 856 | Sleep (ms_total); |
813 | 857 | return 0; | |
814 | if (rfds) | 858 | } |
815 | sock_read = rfds->sds; | 859 | if (rfds) |
816 | else | 860 | sock_read = rfds->sds; |
817 | FD_ZERO(&sock_read); | 861 | |
818 | 862 | else | |
819 | if (wfds) | 863 | FD_ZERO (&sock_read); |
820 | sock_write = wfds->sds; | 864 | if (wfds) |
821 | else | 865 | sock_write = wfds->sds; |
822 | FD_ZERO(&sock_write); | 866 | |
823 | 867 | else | |
824 | if (efds) | 868 | FD_ZERO (&sock_write); |
825 | sock_except = efds->sds; | 869 | if (efds) |
826 | else | 870 | sock_except = efds->sds; |
827 | FD_ZERO(&sock_except); | 871 | |
828 | 872 | else | |
829 | /* multiplex between winsock select() and waiting on the handles */ | 873 | FD_ZERO (&sock_except); |
830 | 874 | ||
831 | FD_ZERO (&aread); | 875 | /* multiplex between winsock select() and waiting on the handles */ |
832 | FD_ZERO (&awrite); | 876 | FD_ZERO (&aread); |
833 | FD_ZERO (&aexcept); | 877 | FD_ZERO (&awrite); |
834 | 878 | FD_ZERO (&aexcept); | |
835 | limit = GetTickCount () + ms_total; | 879 | limit = GetTickCount () + ms_total; |
836 | do | 880 | |
837 | { | 881 | do |
838 | retcode = 0; | 882 | |
839 | 883 | { | |
840 | if (nfds > 0) | 884 | retcode = 0; |
841 | { | 885 | if (nfds > 0) |
842 | /* overwrite the zero'd sets here; the select call | 886 | |
843 | * will clear those that are not active */ | 887 | { |
844 | 888 | ||
845 | FD_COPY (&sock_read, &aread); | 889 | /* overwrite the zero'd sets here; the select call |
846 | FD_COPY (&sock_write, &awrite); | 890 | * will clear those that are not active */ |
847 | FD_COPY (&sock_except, &aexcept); | 891 | FD_COPY (&sock_read, &aread); |
848 | 892 | FD_COPY (&sock_write, &awrite); | |
849 | tvslice.tv_sec = 0; | 893 | FD_COPY (&sock_except, &aexcept); |
850 | tvslice.tv_usec = 100000; | 894 | tvslice.tv_sec = 0; |
851 | 895 | tvslice.tv_usec = 100000; | |
852 | if ((retcode = | 896 | if ((retcode = |
853 | select (nfds + 1, &aread, &awrite, &aexcept, | 897 | select (nfds + 1, &aread, &awrite, &aexcept, |
854 | &tvslice)) == SOCKET_ERROR) | 898 | &tvslice)) == SOCKET_ERROR) |
855 | { | 899 | |
856 | SetErrnoFromWinsockError (WSAGetLastError ()); | 900 | { |
857 | if (errno == ENOTSOCK) | 901 | SetErrnoFromWinsockError (WSAGetLastError ()); |
858 | errno = EBADF; | 902 | if (errno == ENOTSOCK) |
859 | 903 | errno = EBADF; | |
904 | |||
860 | #if DEBUG_NETWORK | 905 | #if DEBUG_NETWORK |
861 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "select"); | 906 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "select"); |
862 | #endif | 907 | |
863 | 908 | #endif /* */ | |
864 | goto select_loop_end; | 909 | goto select_loop_end; |
865 | } | 910 | } |
866 | } | 911 | } |
867 | 912 | ||
868 | /* Poll read pipes */ | 913 | /* Poll read pipes */ |
869 | if (rfds) | 914 | if (rfds) |
870 | { | 915 | |
871 | struct GNUNET_CONTAINER_SList_Iterator *i; | 916 | { |
872 | int on_next; | 917 | struct GNUNET_CONTAINER_SList_Iterator *i; |
873 | 918 | int on_next; | |
874 | on_next = GNUNET_NO; | 919 | on_next = GNUNET_NO; |
875 | for (i = GNUNET_CONTAINER_slist_begin (rfds->handles); | 920 | for (i = GNUNET_CONTAINER_slist_begin (rfds->handles); |
876 | GNUNET_CONTAINER_slist_end (i) != GNUNET_YES; | 921 | GNUNET_CONTAINER_slist_end (i) != GNUNET_YES; |
877 | on_next || GNUNET_CONTAINER_slist_next (i)) | 922 | on_next || GNUNET_CONTAINER_slist_next (i)) |
878 | { | 923 | |
879 | HANDLE h; | 924 | { |
880 | DWORD dwBytes; | 925 | HANDLE h; |
881 | 926 | DWORD dwBytes; | |
882 | h = *(HANDLE *) GNUNET_CONTAINER_slist_get (i, NULL); | 927 | h = *(HANDLE *) GNUNET_CONTAINER_slist_get (i, NULL); |
883 | on_next = GNUNET_NO; | 928 | on_next = GNUNET_NO; |
884 | 929 | if (!PeekNamedPipe (h, NULL, 0, NULL, &dwBytes, NULL)) | |
885 | if (!PeekNamedPipe (h, NULL, 0, NULL, &dwBytes, NULL)) | 930 | |
886 | { | 931 | { |
887 | GNUNET_CONTAINER_slist_erase (i); | 932 | GNUNET_CONTAINER_slist_erase (i); |
888 | on_next = GNUNET_YES; | 933 | on_next = GNUNET_YES; |
889 | 934 | retcode = -1; | |
890 | retcode = -1; | 935 | SetErrnoFromWinError (GetLastError ()); |
891 | SetErrnoFromWinError (GetLastError ()); | 936 | |
892 | #if DEBUG_NETWORK | 937 | #if DEBUG_NETWORK |
893 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "PeekNamedPipe"); | 938 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, |
894 | #endif | 939 | "PeekNamedPipe"); |
895 | goto select_loop_end; | 940 | |
896 | } | 941 | #endif /* */ |
897 | else if (dwBytes) | 942 | goto select_loop_end; |
898 | { | 943 | } |
899 | retcode++; | 944 | |
900 | } | 945 | else if (dwBytes) |
901 | else | 946 | |
902 | { | 947 | { |
903 | GNUNET_CONTAINER_slist_erase (i); | 948 | retcode++; |
904 | on_next = GNUNET_YES; | 949 | } |
905 | } | 950 | |
906 | } | 951 | else |
907 | } | 952 | |
908 | 953 | { | |
909 | /* Poll for faulty pipes */ | 954 | GNUNET_CONTAINER_slist_erase (i); |
910 | if (efds) | 955 | on_next = GNUNET_YES; |
911 | { | 956 | } |
912 | struct GNUNET_CONTAINER_SList_Iterator *i; | 957 | } |
913 | int on_next; | 958 | } |
914 | 959 | ||
915 | on_next = GNUNET_NO; | 960 | /* Poll for faulty pipes */ |
916 | for (i = GNUNET_CONTAINER_slist_begin (efds->handles); | 961 | if (efds) |
917 | GNUNET_CONTAINER_slist_end (i) != GNUNET_YES; | 962 | |
918 | on_next || GNUNET_CONTAINER_slist_next (i)) | 963 | { |
919 | { | 964 | struct GNUNET_CONTAINER_SList_Iterator *i; |
920 | HANDLE h; | 965 | int on_next; |
921 | DWORD dwBytes; | 966 | on_next = GNUNET_NO; |
922 | 967 | for (i = GNUNET_CONTAINER_slist_begin (efds->handles); | |
923 | h = *(HANDLE *) GNUNET_CONTAINER_slist_get (i, NULL); | 968 | GNUNET_CONTAINER_slist_end (i) != GNUNET_YES; |
924 | 969 | on_next || GNUNET_CONTAINER_slist_next (i)) | |
925 | if (PeekNamedPipe (h, NULL, 0, NULL, &dwBytes, NULL)) | 970 | |
926 | { | 971 | { |
927 | GNUNET_CONTAINER_slist_erase (i); | 972 | HANDLE h; |
928 | on_next = GNUNET_YES; | 973 | DWORD dwBytes; |
929 | 974 | h = *(HANDLE *) GNUNET_CONTAINER_slist_get (i, NULL); | |
930 | retcode++; | 975 | if (PeekNamedPipe (h, NULL, 0, NULL, &dwBytes, NULL)) |
931 | } | 976 | |
932 | else | 977 | { |
933 | on_next = GNUNET_NO; | 978 | GNUNET_CONTAINER_slist_erase (i); |
934 | } | 979 | on_next = GNUNET_YES; |
935 | } | 980 | retcode++; |
936 | 981 | } | |
937 | /* FIXME */ | 982 | |
938 | if (wfds) | 983 | else |
939 | GNUNET_assert (GNUNET_CONTAINER_slist_count (wfds->handles) == 0); | 984 | on_next = GNUNET_NO; |
940 | 985 | } | |
941 | /* Check for closed sockets */ | 986 | } |
942 | for (i = 0; i < nfds; i++) | 987 | |
943 | { | 988 | /* FIXME */ |
944 | if (SAFE_FD_ISSET (i, &sock_read)) | 989 | if (wfds) |
945 | { | 990 | GNUNET_assert (GNUNET_CONTAINER_slist_count (wfds->handles) == 0); |
946 | struct sockaddr addr; | 991 | |
947 | int len; | 992 | /* Check for closed sockets */ |
948 | 993 | for (i = 0; i < nfds; i++) | |
949 | if (getpeername (i, &addr, &len) == SOCKET_ERROR) | 994 | |
950 | { | 995 | { |
951 | int err, len; | 996 | if (SAFE_FD_ISSET (i, &sock_read)) |
952 | 997 | ||
953 | len = sizeof (err); | 998 | { |
954 | if (getsockopt | 999 | struct sockaddr addr; |
955 | (i, SOL_SOCKET, SO_ERROR, (char *) &err, &len) == 0 | 1000 | int len; |
956 | && err == WSAENOTCONN) | 1001 | if (getpeername (i, &addr, &len) == SOCKET_ERROR) |
957 | { | 1002 | |
958 | if (!SAFE_FD_ISSET (i, &aread)) | 1003 | { |
959 | { | 1004 | int err, len; |
960 | FD_SET (i, &aread); | 1005 | len = sizeof (err); |
961 | retcode++; | 1006 | if (getsockopt |
962 | } | 1007 | (i, SOL_SOCKET, SO_ERROR, (char *) &err, &len) == 0 |
963 | } | 1008 | &&err == WSAENOTCONN) |
964 | } | 1009 | |
965 | } | 1010 | { |
966 | } | 1011 | if (!SAFE_FD_ISSET (i, &aread)) |
967 | 1012 | ||
968 | select_loop_end:; | 1013 | { |
969 | } | 1014 | FD_SET (i, &aread); |
970 | while (retcode == 0 && (ms_total == INFINITE || GetTickCount () < limit)); | 1015 | retcode++; |
971 | 1016 | } | |
972 | if (retcode != -1) | 1017 | } |
973 | { | 1018 | } |
974 | if (rfds) | 1019 | } |
975 | { | 1020 | } |
976 | GNUNET_NETWORK_fdset_zero (rfds); | 1021 | select_loop_end:; |
977 | GNUNET_NETWORK_fdset_copy_native (rfds, &aread, retcode); | 1022 | } |
978 | } | 1023 | while (retcode == 0 && (ms_total == INFINITE || GetTickCount () < limit)); |
979 | 1024 | if (retcode != -1) | |
980 | if (wfds) | 1025 | |
981 | { | 1026 | { |
982 | GNUNET_NETWORK_fdset_zero (wfds); | 1027 | if (rfds) |
983 | GNUNET_NETWORK_fdset_copy_native (wfds, &awrite, retcode); | 1028 | |
984 | } | 1029 | { |
985 | 1030 | GNUNET_NETWORK_fdset_zero (rfds); | |
986 | if (efds) | 1031 | GNUNET_NETWORK_fdset_copy_native (rfds, &aread, retcode); |
987 | { | 1032 | } |
988 | GNUNET_NETWORK_fdset_zero (efds); | 1033 | if (wfds) |
989 | GNUNET_NETWORK_fdset_copy_native (efds, &aexcept, retcode); | 1034 | |
990 | } | 1035 | { |
991 | } | 1036 | GNUNET_NETWORK_fdset_zero (wfds); |
992 | 1037 | GNUNET_NETWORK_fdset_copy_native (wfds, &awrite, retcode); | |
993 | return retcode; | 1038 | } |
994 | #endif | 1039 | if (efds) |
995 | } | 1040 | |
996 | 1041 | { | |
997 | 1042 | GNUNET_NETWORK_fdset_zero (efds); | |
998 | /* end of network.c */ | 1043 | GNUNET_NETWORK_fdset_copy_native (efds, &aexcept, retcode); |
1044 | } | ||
1045 | } | ||
1046 | return retcode; | ||
1047 | |||
1048 | #endif /* */ | ||
1049 | } | ||
1050 | |||
1051 | |||
1052 | /* end of network.c */ | ||