nexmon – Blame information for rev 1
?pathlinks?
Rev | Author | Line No. | Line |
---|---|---|---|
1 | office | 1 | /* GIO - GLib Input, Output and Streaming Library |
2 | * |
||
3 | * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima |
||
4 | * Copyright © 2009 Codethink Limited |
||
5 | * Copyright © 2009 Red Hat, Inc |
||
6 | * Copyright © 2015 Collabora, Ltd. |
||
7 | * |
||
8 | * This library is free software; you can redistribute it and/or |
||
9 | * modify it under the terms of the GNU Lesser General Public |
||
10 | * License as published by the Free Software Foundation; either |
||
11 | * version 2 of the License, or (at your option) any later version. |
||
12 | * |
||
13 | * This library is distributed in the hope that it will be useful, |
||
14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
||
15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
||
16 | * Lesser General Public License for more details. |
||
17 | * |
||
18 | * You should have received a copy of the GNU Lesser General |
||
19 | * Public License along with this library; if not, see <http://www.gnu.org/licenses/>. |
||
20 | * |
||
21 | * Authors: Christian Kellner <gicmo@gnome.org> |
||
22 | * Samuel Cormier-Iijima <sciyoshi@gmail.com> |
||
23 | * Ryan Lortie <desrt@desrt.ca> |
||
24 | * Alexander Larsson <alexl@redhat.com> |
||
25 | * Philip Withnall <philip.withnall@collabora.co.uk> |
||
26 | */ |
||
27 | |||
28 | #include "config.h" |
||
29 | |||
30 | #include "gsocket.h" |
||
31 | |||
32 | #ifdef G_OS_UNIX |
||
33 | #include "glib-unix.h" |
||
34 | #endif |
||
35 | |||
36 | #include <errno.h> |
||
37 | #include <signal.h> |
||
38 | #include <string.h> |
||
39 | #include <stdlib.h> |
||
40 | |||
41 | #ifndef G_OS_WIN32 |
||
42 | # include <fcntl.h> |
||
43 | # include <unistd.h> |
||
44 | # include <sys/ioctl.h> |
||
45 | #endif |
||
46 | |||
47 | #ifdef HAVE_SYS_FILIO_H |
||
48 | # include <sys/filio.h> |
||
49 | #endif |
||
50 | |||
51 | #ifdef G_OS_UNIX |
||
52 | #include <sys/uio.h> |
||
53 | #endif |
||
54 | |||
55 | #include "gcancellable.h" |
||
56 | #include "gdatagrambased.h" |
||
57 | #include "gioenumtypes.h" |
||
58 | #include "ginetaddress.h" |
||
59 | #include "ginitable.h" |
||
60 | #include "gioerror.h" |
||
61 | #include "gioenums.h" |
||
62 | #include "gioerror.h" |
||
63 | #include "gnetworkingprivate.h" |
||
64 | #include "gsocketaddress.h" |
||
65 | #include "gsocketcontrolmessage.h" |
||
66 | #include "gcredentials.h" |
||
67 | #include "gcredentialsprivate.h" |
||
68 | #include "glibintl.h" |
||
69 | |||
70 | #ifdef G_OS_WIN32 |
||
71 | /* For Windows XP runtime compatibility, but use the system's if_nametoindex() if available */ |
||
72 | #include "gwin32networking.h" |
||
73 | #endif |
||
74 | |||
75 | /** |
||
76 | * SECTION:gsocket |
||
77 | * @short_description: Low-level socket object |
||
78 | * @include: gio/gio.h |
||
79 | * @see_also: #GInitable, [<gnetworking.h>][gio-gnetworking.h] |
||
80 | * |
||
81 | * A #GSocket is a low-level networking primitive. It is a more or less |
||
82 | * direct mapping of the BSD socket API in a portable GObject based API. |
||
83 | * It supports both the UNIX socket implementations and winsock2 on Windows. |
||
84 | * |
||
85 | * #GSocket is the platform independent base upon which the higher level |
||
86 | * network primitives are based. Applications are not typically meant to |
||
87 | * use it directly, but rather through classes like #GSocketClient, |
||
88 | * #GSocketService and #GSocketConnection. However there may be cases where |
||
89 | * direct use of #GSocket is useful. |
||
90 | * |
||
91 | * #GSocket implements the #GInitable interface, so if it is manually constructed |
||
92 | * by e.g. g_object_new() you must call g_initable_init() and check the |
||
93 | * results before using the object. This is done automatically in |
||
94 | * g_socket_new() and g_socket_new_from_fd(), so these functions can return |
||
95 | * %NULL. |
||
96 | * |
||
97 | * Sockets operate in two general modes, blocking or non-blocking. When |
||
98 | * in blocking mode all operations (which don’t take an explicit blocking |
||
99 | * parameter) block until the requested operation |
||
100 | * is finished or there is an error. In non-blocking mode all calls that |
||
101 | * would block return immediately with a %G_IO_ERROR_WOULD_BLOCK error. |
||
102 | * To know when a call would successfully run you can call g_socket_condition_check(), |
||
103 | * or g_socket_condition_wait(). You can also use g_socket_create_source() and |
||
104 | * attach it to a #GMainContext to get callbacks when I/O is possible. |
||
105 | * Note that all sockets are always set to non blocking mode in the system, and |
||
106 | * blocking mode is emulated in GSocket. |
||
107 | * |
||
108 | * When working in non-blocking mode applications should always be able to |
||
109 | * handle getting a %G_IO_ERROR_WOULD_BLOCK error even when some other |
||
110 | * function said that I/O was possible. This can easily happen in case |
||
111 | * of a race condition in the application, but it can also happen for other |
||
112 | * reasons. For instance, on Windows a socket is always seen as writable |
||
113 | * until a write returns %G_IO_ERROR_WOULD_BLOCK. |
||
114 | * |
||
115 | * #GSockets can be either connection oriented or datagram based. |
||
116 | * For connection oriented types you must first establish a connection by |
||
117 | * either connecting to an address or accepting a connection from another |
||
118 | * address. For connectionless socket types the target/source address is |
||
119 | * specified or received in each I/O operation. |
||
120 | * |
||
121 | * All socket file descriptors are set to be close-on-exec. |
||
122 | * |
||
123 | * Note that creating a #GSocket causes the signal %SIGPIPE to be |
||
124 | * ignored for the remainder of the program. If you are writing a |
||
125 | * command-line utility that uses #GSocket, you may need to take into |
||
126 | * account the fact that your program will not automatically be killed |
||
127 | * if it tries to write to %stdout after it has been closed. |
||
128 | * |
||
129 | * Like most other APIs in GLib, #GSocket is not inherently thread safe. To use |
||
130 | * a #GSocket concurrently from multiple threads, you must implement your own |
||
131 | * locking. |
||
132 | * |
||
133 | * Since: 2.22 |
||
134 | */ |
||
135 | |||
136 | static void g_socket_initable_iface_init (GInitableIface *iface); |
||
137 | static gboolean g_socket_initable_init (GInitable *initable, |
||
138 | GCancellable *cancellable, |
||
139 | GError **error); |
||
140 | |||
141 | static void g_socket_datagram_based_iface_init (GDatagramBasedInterface *iface); |
||
142 | static gint g_socket_datagram_based_receive_messages (GDatagramBased *self, |
||
143 | GInputMessage *messages, |
||
144 | guint num_messages, |
||
145 | gint flags, |
||
146 | gint64 timeout, |
||
147 | GCancellable *cancellable, |
||
148 | GError **error); |
||
149 | static gint g_socket_datagram_based_send_messages (GDatagramBased *self, |
||
150 | GOutputMessage *messages, |
||
151 | guint num_messages, |
||
152 | gint flags, |
||
153 | gint64 timeout, |
||
154 | GCancellable *cancellable, |
||
155 | GError **error); |
||
156 | static GSource *g_socket_datagram_based_create_source (GDatagramBased *self, |
||
157 | GIOCondition condition, |
||
158 | GCancellable *cancellable); |
||
159 | static GIOCondition g_socket_datagram_based_condition_check (GDatagramBased *datagram_based, |
||
160 | GIOCondition condition); |
||
161 | static gboolean g_socket_datagram_based_condition_wait (GDatagramBased *datagram_based, |
||
162 | GIOCondition condition, |
||
163 | gint64 timeout, |
||
164 | GCancellable *cancellable, |
||
165 | GError **error); |
||
166 | |||
167 | static GSocketAddress * |
||
168 | cache_recv_address (GSocket *socket, struct sockaddr *native, int native_len); |
||
169 | |||
170 | static gssize |
||
171 | g_socket_receive_message_with_timeout (GSocket *socket, |
||
172 | GSocketAddress **address, |
||
173 | GInputVector *vectors, |
||
174 | gint num_vectors, |
||
175 | GSocketControlMessage ***messages, |
||
176 | gint *num_messages, |
||
177 | gint *flags, |
||
178 | gint64 timeout, |
||
179 | GCancellable *cancellable, |
||
180 | GError **error); |
||
181 | static gint |
||
182 | g_socket_receive_messages_with_timeout (GSocket *socket, |
||
183 | GInputMessage *messages, |
||
184 | guint num_messages, |
||
185 | gint flags, |
||
186 | gint64 timeout, |
||
187 | GCancellable *cancellable, |
||
188 | GError **error); |
||
189 | static gssize |
||
190 | g_socket_send_message_with_timeout (GSocket *socket, |
||
191 | GSocketAddress *address, |
||
192 | GOutputVector *vectors, |
||
193 | gint num_vectors, |
||
194 | GSocketControlMessage **messages, |
||
195 | gint num_messages, |
||
196 | gint flags, |
||
197 | gint64 timeout, |
||
198 | GCancellable *cancellable, |
||
199 | GError **error); |
||
200 | static gint |
||
201 | g_socket_send_messages_with_timeout (GSocket *socket, |
||
202 | GOutputMessage *messages, |
||
203 | guint num_messages, |
||
204 | gint flags, |
||
205 | gint64 timeout, |
||
206 | GCancellable *cancellable, |
||
207 | GError **error); |
||
208 | |||
209 | enum |
||
210 | { |
||
211 | PROP_0, |
||
212 | PROP_FAMILY, |
||
213 | PROP_TYPE, |
||
214 | PROP_PROTOCOL, |
||
215 | PROP_FD, |
||
216 | PROP_BLOCKING, |
||
217 | PROP_LISTEN_BACKLOG, |
||
218 | PROP_KEEPALIVE, |
||
219 | PROP_LOCAL_ADDRESS, |
||
220 | PROP_REMOTE_ADDRESS, |
||
221 | PROP_TIMEOUT, |
||
222 | PROP_TTL, |
||
223 | PROP_BROADCAST, |
||
224 | PROP_MULTICAST_LOOPBACK, |
||
225 | PROP_MULTICAST_TTL |
||
226 | }; |
||
227 | |||
228 | /* Size of the receiver cache for g_socket_receive_from() */ |
||
229 | #define RECV_ADDR_CACHE_SIZE 8 |
||
230 | |||
231 | struct _GSocketPrivate |
||
232 | { |
||
233 | GSocketFamily family; |
||
234 | GSocketType type; |
||
235 | GSocketProtocol protocol; |
||
236 | gint fd; |
||
237 | gint listen_backlog; |
||
238 | guint timeout; |
||
239 | GError *construct_error; |
||
240 | GSocketAddress *remote_address; |
||
241 | guint inited : 1; |
||
242 | guint blocking : 1; |
||
243 | guint keepalive : 1; |
||
244 | guint closed : 1; |
||
245 | guint connected_read : 1; |
||
246 | guint connected_write : 1; |
||
247 | guint listening : 1; |
||
248 | guint timed_out : 1; |
||
249 | guint connect_pending : 1; |
||
250 | #ifdef G_OS_WIN32 |
||
251 | WSAEVENT event; |
||
252 | int current_events; |
||
253 | int current_errors; |
||
254 | int selected_events; |
||
255 | GList *requested_conditions; /* list of requested GIOCondition * */ |
||
256 | GMutex win32_source_lock; |
||
257 | #endif |
||
258 | |||
259 | struct { |
||
260 | GSocketAddress *addr; |
||
261 | struct sockaddr *native; |
||
262 | gint native_len; |
||
263 | guint64 last_used; |
||
264 | } recv_addr_cache[RECV_ADDR_CACHE_SIZE]; |
||
265 | }; |
||
266 | |||
267 | G_DEFINE_TYPE_WITH_CODE (GSocket, g_socket, G_TYPE_OBJECT, |
||
268 | G_ADD_PRIVATE (GSocket) |
||
269 | g_networking_init (); |
||
270 | G_IMPLEMENT_INTERFACE (G_TYPE_INITABLE, |
||
271 | g_socket_initable_iface_init); |
||
272 | G_IMPLEMENT_INTERFACE (G_TYPE_DATAGRAM_BASED, |
||
273 | g_socket_datagram_based_iface_init)); |
||
274 | |||
275 | static int |
||
276 | get_socket_errno (void) |
||
277 | { |
||
278 | #ifndef G_OS_WIN32 |
||
279 | return errno; |
||
280 | #else |
||
281 | return WSAGetLastError (); |
||
282 | #endif |
||
283 | } |
||
284 | |||
285 | static GIOErrorEnum |
||
286 | socket_io_error_from_errno (int err) |
||
287 | { |
||
288 | #ifdef G_OS_WIN32 |
||
289 | return g_io_error_from_win32_error (err); |
||
290 | #else |
||
291 | return g_io_error_from_errno (err); |
||
292 | #endif |
||
293 | } |
||
294 | |||
295 | static const char * |
||
296 | socket_strerror (int err) |
||
297 | { |
||
298 | #ifndef G_OS_WIN32 |
||
299 | return g_strerror (err); |
||
300 | #else |
||
301 | const char *msg_ret; |
||
302 | char *msg; |
||
303 | |||
304 | msg = g_win32_error_message (err); |
||
305 | |||
306 | msg_ret = g_intern_string (msg); |
||
307 | g_free (msg); |
||
308 | |||
309 | return msg_ret; |
||
310 | #endif |
||
311 | } |
||
312 | |||
313 | /* Wrapper around g_set_error() to avoid doing excess work */ |
||
314 | #define socket_set_error_lazy(err, errsv, fmt) \ |
||
315 | G_STMT_START { \ |
||
316 | GError **__err = (err); \ |
||
317 | int __errsv = (errsv); \ |
||
318 | \ |
||
319 | if (__err) \ |
||
320 | { \ |
||
321 | int __code = socket_io_error_from_errno (__errsv); \ |
||
322 | const char *__strerr = socket_strerror (__errsv); \ |
||
323 | \ |
||
324 | if (__code == G_IO_ERROR_WOULD_BLOCK) \ |
||
325 | g_set_error_literal (__err, G_IO_ERROR, __code, __strerr); \ |
||
326 | else \ |
||
327 | g_set_error (__err, G_IO_ERROR, __code, fmt, __strerr); \ |
||
328 | } \ |
||
329 | } G_STMT_END |
||
330 | |||
331 | #ifdef G_OS_WIN32 |
||
332 | #define win32_unset_event_mask(_socket, _mask) _win32_unset_event_mask (_socket, _mask) |
||
333 | static void |
||
334 | _win32_unset_event_mask (GSocket *socket, int mask) |
||
335 | { |
||
336 | socket->priv->current_events &= ~mask; |
||
337 | socket->priv->current_errors &= ~mask; |
||
338 | } |
||
339 | #else |
||
340 | #define win32_unset_event_mask(_socket, _mask) |
||
341 | #endif |
||
342 | |||
343 | /* Windows has broken prototypes... */ |
||
344 | #ifdef G_OS_WIN32 |
||
345 | #define getsockopt(sockfd, level, optname, optval, optlen) \ |
||
346 | getsockopt (sockfd, level, optname, (gpointer) optval, (int*) optlen) |
||
347 | #define setsockopt(sockfd, level, optname, optval, optlen) \ |
||
348 | setsockopt (sockfd, level, optname, (gpointer) optval, optlen) |
||
349 | #define getsockname(sockfd, addr, addrlen) \ |
||
350 | getsockname (sockfd, addr, (int *)addrlen) |
||
351 | #define getpeername(sockfd, addr, addrlen) \ |
||
352 | getpeername (sockfd, addr, (int *)addrlen) |
||
353 | #define recv(sockfd, buf, len, flags) \ |
||
354 | recv (sockfd, (gpointer)buf, len, flags) |
||
355 | #endif |
||
356 | |||
357 | static gboolean |
||
358 | check_socket (GSocket *socket, |
||
359 | GError **error) |
||
360 | { |
||
361 | if (!socket->priv->inited) |
||
362 | { |
||
363 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_INITIALIZED, |
||
364 | _("Invalid socket, not initialized")); |
||
365 | return FALSE; |
||
366 | } |
||
367 | |||
368 | if (socket->priv->construct_error) |
||
369 | { |
||
370 | g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_INITIALIZED, |
||
371 | _("Invalid socket, initialization failed due to: %s"), |
||
372 | socket->priv->construct_error->message); |
||
373 | return FALSE; |
||
374 | } |
||
375 | |||
376 | if (socket->priv->closed) |
||
377 | { |
||
378 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CLOSED, |
||
379 | _("Socket is already closed")); |
||
380 | return FALSE; |
||
381 | } |
||
382 | |||
383 | return TRUE; |
||
384 | } |
||
385 | |||
386 | static gboolean |
||
387 | check_timeout (GSocket *socket, |
||
388 | GError **error) |
||
389 | { |
||
390 | if (socket->priv->timed_out) |
||
391 | { |
||
392 | socket->priv->timed_out = FALSE; |
||
393 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_TIMED_OUT, |
||
394 | _("Socket I/O timed out")); |
||
395 | return FALSE; |
||
396 | } |
||
397 | |||
398 | return TRUE; |
||
399 | } |
||
400 | |||
401 | static void |
||
402 | g_socket_details_from_fd (GSocket *socket) |
||
403 | { |
||
404 | struct sockaddr_storage address; |
||
405 | gint fd; |
||
406 | guint addrlen; |
||
407 | int value, family; |
||
408 | int errsv; |
||
409 | |||
410 | fd = socket->priv->fd; |
||
411 | if (!g_socket_get_option (socket, SOL_SOCKET, SO_TYPE, &value, NULL)) |
||
412 | { |
||
413 | errsv = get_socket_errno (); |
||
414 | goto err; |
||
415 | } |
||
416 | |||
417 | switch (value) |
||
418 | { |
||
419 | case SOCK_STREAM: |
||
420 | socket->priv->type = G_SOCKET_TYPE_STREAM; |
||
421 | break; |
||
422 | |||
423 | case SOCK_DGRAM: |
||
424 | socket->priv->type = G_SOCKET_TYPE_DATAGRAM; |
||
425 | break; |
||
426 | |||
427 | case SOCK_SEQPACKET: |
||
428 | socket->priv->type = G_SOCKET_TYPE_SEQPACKET; |
||
429 | break; |
||
430 | |||
431 | default: |
||
432 | socket->priv->type = G_SOCKET_TYPE_INVALID; |
||
433 | break; |
||
434 | } |
||
435 | |||
436 | addrlen = sizeof address; |
||
437 | if (getsockname (fd, (struct sockaddr *) &address, &addrlen) != 0) |
||
438 | { |
||
439 | errsv = get_socket_errno (); |
||
440 | goto err; |
||
441 | } |
||
442 | |||
443 | if (addrlen > 0) |
||
444 | { |
||
445 | g_assert (G_STRUCT_OFFSET (struct sockaddr, sa_family) + |
||
446 | sizeof address.ss_family <= addrlen); |
||
447 | family = address.ss_family; |
||
448 | } |
||
449 | else |
||
450 | { |
||
451 | /* On Solaris, this happens if the socket is not yet connected. |
||
452 | * But we can use SO_DOMAIN as a workaround there. |
||
453 | */ |
||
454 | #ifdef SO_DOMAIN |
||
455 | if (!g_socket_get_option (socket, SOL_SOCKET, SO_DOMAIN, &family, NULL)) |
||
456 | { |
||
457 | errsv = get_socket_errno (); |
||
458 | goto err; |
||
459 | } |
||
460 | #else |
||
461 | /* This will translate to G_IO_ERROR_FAILED on either unix or windows */ |
||
462 | errsv = -1; |
||
463 | goto err; |
||
464 | #endif |
||
465 | } |
||
466 | |||
467 | switch (family) |
||
468 | { |
||
469 | case G_SOCKET_FAMILY_IPV4: |
||
470 | case G_SOCKET_FAMILY_IPV6: |
||
471 | socket->priv->family = address.ss_family; |
||
472 | switch (socket->priv->type) |
||
473 | { |
||
474 | case G_SOCKET_TYPE_STREAM: |
||
475 | socket->priv->protocol = G_SOCKET_PROTOCOL_TCP; |
||
476 | break; |
||
477 | |||
478 | case G_SOCKET_TYPE_DATAGRAM: |
||
479 | socket->priv->protocol = G_SOCKET_PROTOCOL_UDP; |
||
480 | break; |
||
481 | |||
482 | case G_SOCKET_TYPE_SEQPACKET: |
||
483 | socket->priv->protocol = G_SOCKET_PROTOCOL_SCTP; |
||
484 | break; |
||
485 | |||
486 | default: |
||
487 | break; |
||
488 | } |
||
489 | break; |
||
490 | |||
491 | case G_SOCKET_FAMILY_UNIX: |
||
492 | socket->priv->family = G_SOCKET_FAMILY_UNIX; |
||
493 | socket->priv->protocol = G_SOCKET_PROTOCOL_DEFAULT; |
||
494 | break; |
||
495 | |||
496 | default: |
||
497 | socket->priv->family = G_SOCKET_FAMILY_INVALID; |
||
498 | break; |
||
499 | } |
||
500 | |||
501 | if (socket->priv->family != G_SOCKET_FAMILY_INVALID) |
||
502 | { |
||
503 | addrlen = sizeof address; |
||
504 | if (getpeername (fd, (struct sockaddr *) &address, &addrlen) >= 0) |
||
505 | { |
||
506 | socket->priv->connected_read = TRUE; |
||
507 | socket->priv->connected_write = TRUE; |
||
508 | } |
||
509 | } |
||
510 | |||
511 | if (g_socket_get_option (socket, SOL_SOCKET, SO_KEEPALIVE, &value, NULL)) |
||
512 | { |
||
513 | socket->priv->keepalive = !!value; |
||
514 | } |
||
515 | else |
||
516 | { |
||
517 | /* Can't read, maybe not supported, assume FALSE */ |
||
518 | socket->priv->keepalive = FALSE; |
||
519 | } |
||
520 | |||
521 | return; |
||
522 | |||
523 | err: |
||
524 | g_set_error (&socket->priv->construct_error, G_IO_ERROR, |
||
525 | socket_io_error_from_errno (errsv), |
||
526 | _("creating GSocket from fd: %s"), |
||
527 | socket_strerror (errsv)); |
||
528 | } |
||
529 | |||
530 | /* Wrapper around socket() that is shared with gnetworkmonitornetlink.c */ |
||
531 | gint |
||
532 | g_socket (gint domain, |
||
533 | gint type, |
||
534 | gint protocol, |
||
535 | GError **error) |
||
536 | { |
||
537 | int fd; |
||
538 | |||
539 | #ifdef SOCK_CLOEXEC |
||
540 | fd = socket (domain, type | SOCK_CLOEXEC, protocol); |
||
541 | if (fd != -1) |
||
542 | return fd; |
||
543 | |||
544 | /* It's possible that libc has SOCK_CLOEXEC but the kernel does not */ |
||
545 | if (fd < 0 && (errno == EINVAL || errno == EPROTOTYPE)) |
||
546 | #endif |
||
547 | fd = socket (domain, type, protocol); |
||
548 | |||
549 | if (fd < 0) |
||
550 | { |
||
551 | int errsv = get_socket_errno (); |
||
552 | |||
553 | g_set_error (error, G_IO_ERROR, socket_io_error_from_errno (errsv), |
||
554 | _("Unable to create socket: %s"), socket_strerror (errsv)); |
||
555 | errno = errsv; |
||
556 | return -1; |
||
557 | } |
||
558 | |||
559 | #ifndef G_OS_WIN32 |
||
560 | { |
||
561 | int flags; |
||
562 | |||
563 | /* We always want to set close-on-exec to protect users. If you |
||
564 | need to so some weird inheritance to exec you can re-enable this |
||
565 | using lower level hacks with g_socket_get_fd(). */ |
||
566 | flags = fcntl (fd, F_GETFD, 0); |
||
567 | if (flags != -1 && |
||
568 | (flags & FD_CLOEXEC) == 0) |
||
569 | { |
||
570 | flags |= FD_CLOEXEC; |
||
571 | fcntl (fd, F_SETFD, flags); |
||
572 | } |
||
573 | } |
||
574 | #endif |
||
575 | |||
576 | return fd; |
||
577 | } |
||
578 | |||
579 | static gint |
||
580 | g_socket_create_socket (GSocketFamily family, |
||
581 | GSocketType type, |
||
582 | int protocol, |
||
583 | GError **error) |
||
584 | { |
||
585 | gint native_type; |
||
586 | |||
587 | switch (type) |
||
588 | { |
||
589 | case G_SOCKET_TYPE_STREAM: |
||
590 | native_type = SOCK_STREAM; |
||
591 | break; |
||
592 | |||
593 | case G_SOCKET_TYPE_DATAGRAM: |
||
594 | native_type = SOCK_DGRAM; |
||
595 | break; |
||
596 | |||
597 | case G_SOCKET_TYPE_SEQPACKET: |
||
598 | native_type = SOCK_SEQPACKET; |
||
599 | break; |
||
600 | |||
601 | default: |
||
602 | g_assert_not_reached (); |
||
603 | } |
||
604 | |||
605 | if (family <= 0) |
||
606 | { |
||
607 | g_set_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, |
||
608 | _("Unable to create socket: %s"), _("Unknown family was specified")); |
||
609 | return -1; |
||
610 | } |
||
611 | |||
612 | if (protocol == -1) |
||
613 | { |
||
614 | g_set_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, |
||
615 | _("Unable to create socket: %s"), _("Unknown protocol was specified")); |
||
616 | return -1; |
||
617 | } |
||
618 | |||
619 | return g_socket (family, native_type, protocol, error); |
||
620 | } |
||
621 | |||
622 | static void |
||
623 | g_socket_constructed (GObject *object) |
||
624 | { |
||
625 | GSocket *socket = G_SOCKET (object); |
||
626 | |||
627 | if (socket->priv->fd >= 0) |
||
628 | /* create socket->priv info from the fd */ |
||
629 | g_socket_details_from_fd (socket); |
||
630 | |||
631 | else |
||
632 | /* create the fd from socket->priv info */ |
||
633 | socket->priv->fd = g_socket_create_socket (socket->priv->family, |
||
634 | socket->priv->type, |
||
635 | socket->priv->protocol, |
||
636 | &socket->priv->construct_error); |
||
637 | |||
638 | if (socket->priv->fd != -1) |
||
639 | { |
||
640 | #ifndef G_OS_WIN32 |
||
641 | GError *error = NULL; |
||
642 | #else |
||
643 | gulong arg; |
||
644 | #endif |
||
645 | |||
646 | /* Always use native nonblocking sockets, as Windows sets sockets to |
||
647 | * nonblocking automatically in certain operations. This way we make |
||
648 | * things work the same on all platforms. |
||
649 | */ |
||
650 | #ifndef G_OS_WIN32 |
||
651 | if (!g_unix_set_fd_nonblocking (socket->priv->fd, TRUE, &error)) |
||
652 | { |
||
653 | g_warning ("Error setting socket nonblocking: %s", error->message); |
||
654 | g_clear_error (&error); |
||
655 | } |
||
656 | #else |
||
657 | arg = TRUE; |
||
658 | |||
659 | if (ioctlsocket (socket->priv->fd, FIONBIO, &arg) == SOCKET_ERROR) |
||
660 | { |
||
661 | int errsv = get_socket_errno (); |
||
662 | g_warning ("Error setting socket status flags: %s", socket_strerror (errsv)); |
||
663 | } |
||
664 | #endif |
||
665 | |||
666 | #ifdef SO_NOSIGPIPE |
||
667 | /* See note about SIGPIPE below. */ |
||
668 | g_socket_set_option (socket, SOL_SOCKET, SO_NOSIGPIPE, TRUE, NULL); |
||
669 | #endif |
||
670 | } |
||
671 | } |
||
672 | |||
673 | static void |
||
674 | g_socket_get_property (GObject *object, |
||
675 | guint prop_id, |
||
676 | GValue *value, |
||
677 | GParamSpec *pspec) |
||
678 | { |
||
679 | GSocket *socket = G_SOCKET (object); |
||
680 | GSocketAddress *address; |
||
681 | |||
682 | switch (prop_id) |
||
683 | { |
||
684 | case PROP_FAMILY: |
||
685 | g_value_set_enum (value, socket->priv->family); |
||
686 | break; |
||
687 | |||
688 | case PROP_TYPE: |
||
689 | g_value_set_enum (value, socket->priv->type); |
||
690 | break; |
||
691 | |||
692 | case PROP_PROTOCOL: |
||
693 | g_value_set_enum (value, socket->priv->protocol); |
||
694 | break; |
||
695 | |||
696 | case PROP_FD: |
||
697 | g_value_set_int (value, socket->priv->fd); |
||
698 | break; |
||
699 | |||
700 | case PROP_BLOCKING: |
||
701 | g_value_set_boolean (value, socket->priv->blocking); |
||
702 | break; |
||
703 | |||
704 | case PROP_LISTEN_BACKLOG: |
||
705 | g_value_set_int (value, socket->priv->listen_backlog); |
||
706 | break; |
||
707 | |||
708 | case PROP_KEEPALIVE: |
||
709 | g_value_set_boolean (value, socket->priv->keepalive); |
||
710 | break; |
||
711 | |||
712 | case PROP_LOCAL_ADDRESS: |
||
713 | address = g_socket_get_local_address (socket, NULL); |
||
714 | g_value_take_object (value, address); |
||
715 | break; |
||
716 | |||
717 | case PROP_REMOTE_ADDRESS: |
||
718 | address = g_socket_get_remote_address (socket, NULL); |
||
719 | g_value_take_object (value, address); |
||
720 | break; |
||
721 | |||
722 | case PROP_TIMEOUT: |
||
723 | g_value_set_uint (value, socket->priv->timeout); |
||
724 | break; |
||
725 | |||
726 | case PROP_TTL: |
||
727 | g_value_set_uint (value, g_socket_get_ttl (socket)); |
||
728 | break; |
||
729 | |||
730 | case PROP_BROADCAST: |
||
731 | g_value_set_boolean (value, g_socket_get_broadcast (socket)); |
||
732 | break; |
||
733 | |||
734 | case PROP_MULTICAST_LOOPBACK: |
||
735 | g_value_set_boolean (value, g_socket_get_multicast_loopback (socket)); |
||
736 | break; |
||
737 | |||
738 | case PROP_MULTICAST_TTL: |
||
739 | g_value_set_uint (value, g_socket_get_multicast_ttl (socket)); |
||
740 | break; |
||
741 | |||
742 | default: |
||
743 | G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); |
||
744 | } |
||
745 | } |
||
746 | |||
747 | static void |
||
748 | g_socket_set_property (GObject *object, |
||
749 | guint prop_id, |
||
750 | const GValue *value, |
||
751 | GParamSpec *pspec) |
||
752 | { |
||
753 | GSocket *socket = G_SOCKET (object); |
||
754 | |||
755 | switch (prop_id) |
||
756 | { |
||
757 | case PROP_FAMILY: |
||
758 | socket->priv->family = g_value_get_enum (value); |
||
759 | break; |
||
760 | |||
761 | case PROP_TYPE: |
||
762 | socket->priv->type = g_value_get_enum (value); |
||
763 | break; |
||
764 | |||
765 | case PROP_PROTOCOL: |
||
766 | socket->priv->protocol = g_value_get_enum (value); |
||
767 | break; |
||
768 | |||
769 | case PROP_FD: |
||
770 | socket->priv->fd = g_value_get_int (value); |
||
771 | break; |
||
772 | |||
773 | case PROP_BLOCKING: |
||
774 | g_socket_set_blocking (socket, g_value_get_boolean (value)); |
||
775 | break; |
||
776 | |||
777 | case PROP_LISTEN_BACKLOG: |
||
778 | g_socket_set_listen_backlog (socket, g_value_get_int (value)); |
||
779 | break; |
||
780 | |||
781 | case PROP_KEEPALIVE: |
||
782 | g_socket_set_keepalive (socket, g_value_get_boolean (value)); |
||
783 | break; |
||
784 | |||
785 | case PROP_TIMEOUT: |
||
786 | g_socket_set_timeout (socket, g_value_get_uint (value)); |
||
787 | break; |
||
788 | |||
789 | case PROP_TTL: |
||
790 | g_socket_set_ttl (socket, g_value_get_uint (value)); |
||
791 | break; |
||
792 | |||
793 | case PROP_BROADCAST: |
||
794 | g_socket_set_broadcast (socket, g_value_get_boolean (value)); |
||
795 | break; |
||
796 | |||
797 | case PROP_MULTICAST_LOOPBACK: |
||
798 | g_socket_set_multicast_loopback (socket, g_value_get_boolean (value)); |
||
799 | break; |
||
800 | |||
801 | case PROP_MULTICAST_TTL: |
||
802 | g_socket_set_multicast_ttl (socket, g_value_get_uint (value)); |
||
803 | break; |
||
804 | |||
805 | default: |
||
806 | G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); |
||
807 | } |
||
808 | } |
||
809 | |||
810 | static void |
||
811 | g_socket_finalize (GObject *object) |
||
812 | { |
||
813 | GSocket *socket = G_SOCKET (object); |
||
814 | gint i; |
||
815 | |||
816 | g_clear_error (&socket->priv->construct_error); |
||
817 | |||
818 | if (socket->priv->fd != -1 && |
||
819 | !socket->priv->closed) |
||
820 | g_socket_close (socket, NULL); |
||
821 | |||
822 | if (socket->priv->remote_address) |
||
823 | g_object_unref (socket->priv->remote_address); |
||
824 | |||
825 | #ifdef G_OS_WIN32 |
||
826 | if (socket->priv->event != WSA_INVALID_EVENT) |
||
827 | { |
||
828 | WSACloseEvent (socket->priv->event); |
||
829 | socket->priv->event = WSA_INVALID_EVENT; |
||
830 | } |
||
831 | |||
832 | g_assert (socket->priv->requested_conditions == NULL); |
||
833 | g_mutex_clear (&socket->priv->win32_source_lock); |
||
834 | #endif |
||
835 | |||
836 | for (i = 0; i < RECV_ADDR_CACHE_SIZE; i++) |
||
837 | { |
||
838 | if (socket->priv->recv_addr_cache[i].addr) |
||
839 | { |
||
840 | g_object_unref (socket->priv->recv_addr_cache[i].addr); |
||
841 | g_free (socket->priv->recv_addr_cache[i].native); |
||
842 | } |
||
843 | } |
||
844 | |||
845 | if (G_OBJECT_CLASS (g_socket_parent_class)->finalize) |
||
846 | (*G_OBJECT_CLASS (g_socket_parent_class)->finalize) (object); |
||
847 | } |
||
848 | |||
849 | static void |
||
850 | g_socket_class_init (GSocketClass *klass) |
||
851 | { |
||
852 | GObjectClass *gobject_class G_GNUC_UNUSED = G_OBJECT_CLASS (klass); |
||
853 | |||
854 | #ifdef SIGPIPE |
||
855 | /* There is no portable, thread-safe way to avoid having the process |
||
856 | * be killed by SIGPIPE when calling send() or sendmsg(), so we are |
||
857 | * forced to simply ignore the signal process-wide. |
||
858 | * |
||
859 | * Even if we ignore it though, gdb will still stop if the app |
||
860 | * receives a SIGPIPE, which can be confusing and annoying. So when |
||
861 | * possible, we also use MSG_NOSIGNAL / SO_NOSIGPIPE elsewhere to |
||
862 | * prevent the signal from occurring at all. |
||
863 | */ |
||
864 | signal (SIGPIPE, SIG_IGN); |
||
865 | #endif |
||
866 | |||
867 | gobject_class->finalize = g_socket_finalize; |
||
868 | gobject_class->constructed = g_socket_constructed; |
||
869 | gobject_class->set_property = g_socket_set_property; |
||
870 | gobject_class->get_property = g_socket_get_property; |
||
871 | |||
872 | g_object_class_install_property (gobject_class, PROP_FAMILY, |
||
873 | g_param_spec_enum ("family", |
||
874 | P_("Socket family"), |
||
875 | P_("The sockets address family"), |
||
876 | G_TYPE_SOCKET_FAMILY, |
||
877 | G_SOCKET_FAMILY_INVALID, |
||
878 | G_PARAM_CONSTRUCT_ONLY | |
||
879 | G_PARAM_READWRITE | |
||
880 | G_PARAM_STATIC_STRINGS)); |
||
881 | |||
882 | g_object_class_install_property (gobject_class, PROP_TYPE, |
||
883 | g_param_spec_enum ("type", |
||
884 | P_("Socket type"), |
||
885 | P_("The sockets type"), |
||
886 | G_TYPE_SOCKET_TYPE, |
||
887 | G_SOCKET_TYPE_STREAM, |
||
888 | G_PARAM_CONSTRUCT_ONLY | |
||
889 | G_PARAM_READWRITE | |
||
890 | G_PARAM_STATIC_STRINGS)); |
||
891 | |||
892 | g_object_class_install_property (gobject_class, PROP_PROTOCOL, |
||
893 | g_param_spec_enum ("protocol", |
||
894 | P_("Socket protocol"), |
||
895 | P_("The id of the protocol to use, or -1 for unknown"), |
||
896 | G_TYPE_SOCKET_PROTOCOL, |
||
897 | G_SOCKET_PROTOCOL_UNKNOWN, |
||
898 | G_PARAM_CONSTRUCT_ONLY | |
||
899 | G_PARAM_READWRITE | |
||
900 | G_PARAM_STATIC_STRINGS)); |
||
901 | |||
902 | g_object_class_install_property (gobject_class, PROP_FD, |
||
903 | g_param_spec_int ("fd", |
||
904 | P_("File descriptor"), |
||
905 | P_("The sockets file descriptor"), |
||
906 | G_MININT, |
||
907 | G_MAXINT, |
||
908 | -1, |
||
909 | G_PARAM_CONSTRUCT_ONLY | |
||
910 | G_PARAM_READWRITE | |
||
911 | G_PARAM_STATIC_STRINGS)); |
||
912 | |||
913 | g_object_class_install_property (gobject_class, PROP_BLOCKING, |
||
914 | g_param_spec_boolean ("blocking", |
||
915 | P_("blocking"), |
||
916 | P_("Whether or not I/O on this socket is blocking"), |
||
917 | TRUE, |
||
918 | G_PARAM_READWRITE | |
||
919 | G_PARAM_STATIC_STRINGS)); |
||
920 | |||
921 | g_object_class_install_property (gobject_class, PROP_LISTEN_BACKLOG, |
||
922 | g_param_spec_int ("listen-backlog", |
||
923 | P_("Listen backlog"), |
||
924 | P_("Outstanding connections in the listen queue"), |
||
925 | 0, |
||
926 | SOMAXCONN, |
||
927 | 10, |
||
928 | G_PARAM_READWRITE | |
||
929 | G_PARAM_STATIC_STRINGS)); |
||
930 | |||
931 | g_object_class_install_property (gobject_class, PROP_KEEPALIVE, |
||
932 | g_param_spec_boolean ("keepalive", |
||
933 | P_("Keep connection alive"), |
||
934 | P_("Keep connection alive by sending periodic pings"), |
||
935 | FALSE, |
||
936 | G_PARAM_READWRITE | |
||
937 | G_PARAM_STATIC_STRINGS)); |
||
938 | |||
939 | g_object_class_install_property (gobject_class, PROP_LOCAL_ADDRESS, |
||
940 | g_param_spec_object ("local-address", |
||
941 | P_("Local address"), |
||
942 | P_("The local address the socket is bound to"), |
||
943 | G_TYPE_SOCKET_ADDRESS, |
||
944 | G_PARAM_READABLE | |
||
945 | G_PARAM_STATIC_STRINGS)); |
||
946 | |||
947 | g_object_class_install_property (gobject_class, PROP_REMOTE_ADDRESS, |
||
948 | g_param_spec_object ("remote-address", |
||
949 | P_("Remote address"), |
||
950 | P_("The remote address the socket is connected to"), |
||
951 | G_TYPE_SOCKET_ADDRESS, |
||
952 | G_PARAM_READABLE | |
||
953 | G_PARAM_STATIC_STRINGS)); |
||
954 | |||
955 | /** |
||
956 | * GSocket:timeout: |
||
957 | * |
||
958 | * The timeout in seconds on socket I/O |
||
959 | * |
||
960 | * Since: 2.26 |
||
961 | */ |
||
962 | g_object_class_install_property (gobject_class, PROP_TIMEOUT, |
||
963 | g_param_spec_uint ("timeout", |
||
964 | P_("Timeout"), |
||
965 | P_("The timeout in seconds on socket I/O"), |
||
966 | 0, |
||
967 | G_MAXUINT, |
||
968 | 0, |
||
969 | G_PARAM_READWRITE | |
||
970 | G_PARAM_STATIC_STRINGS)); |
||
971 | |||
972 | /** |
||
973 | * GSocket:broadcast: |
||
974 | * |
||
975 | * Whether the socket should allow sending to broadcast addresses. |
||
976 | * |
||
977 | * Since: 2.32 |
||
978 | */ |
||
979 | g_object_class_install_property (gobject_class, PROP_BROADCAST, |
||
980 | g_param_spec_boolean ("broadcast", |
||
981 | P_("Broadcast"), |
||
982 | P_("Whether to allow sending to broadcast addresses"), |
||
983 | FALSE, |
||
984 | G_PARAM_READWRITE | |
||
985 | G_PARAM_STATIC_STRINGS)); |
||
986 | |||
987 | /** |
||
988 | * GSocket:ttl: |
||
989 | * |
||
990 | * Time-to-live for outgoing unicast packets |
||
991 | * |
||
992 | * Since: 2.32 |
||
993 | */ |
||
994 | g_object_class_install_property (gobject_class, PROP_TTL, |
||
995 | g_param_spec_uint ("ttl", |
||
996 | P_("TTL"), |
||
997 | P_("Time-to-live of outgoing unicast packets"), |
||
998 | 0, G_MAXUINT, 0, |
||
999 | G_PARAM_READWRITE | |
||
1000 | G_PARAM_STATIC_STRINGS)); |
||
1001 | |||
1002 | /** |
||
1003 | * GSocket:multicast-loopback: |
||
1004 | * |
||
1005 | * Whether outgoing multicast packets loop back to the local host. |
||
1006 | * |
||
1007 | * Since: 2.32 |
||
1008 | */ |
||
1009 | g_object_class_install_property (gobject_class, PROP_MULTICAST_LOOPBACK, |
||
1010 | g_param_spec_boolean ("multicast-loopback", |
||
1011 | P_("Multicast loopback"), |
||
1012 | P_("Whether outgoing multicast packets loop back to the local host"), |
||
1013 | TRUE, |
||
1014 | G_PARAM_READWRITE | |
||
1015 | G_PARAM_STATIC_STRINGS)); |
||
1016 | |||
1017 | /** |
||
1018 | * GSocket:multicast-ttl: |
||
1019 | * |
||
1020 | * Time-to-live out outgoing multicast packets |
||
1021 | * |
||
1022 | * Since: 2.32 |
||
1023 | */ |
||
1024 | g_object_class_install_property (gobject_class, PROP_MULTICAST_TTL, |
||
1025 | g_param_spec_uint ("multicast-ttl", |
||
1026 | P_("Multicast TTL"), |
||
1027 | P_("Time-to-live of outgoing multicast packets"), |
||
1028 | 0, G_MAXUINT, 1, |
||
1029 | G_PARAM_READWRITE | |
||
1030 | G_PARAM_STATIC_STRINGS)); |
||
1031 | } |
||
1032 | |||
1033 | static void |
||
1034 | g_socket_initable_iface_init (GInitableIface *iface) |
||
1035 | { |
||
1036 | iface->init = g_socket_initable_init; |
||
1037 | } |
||
1038 | |||
1039 | static void |
||
1040 | g_socket_datagram_based_iface_init (GDatagramBasedInterface *iface) |
||
1041 | { |
||
1042 | iface->receive_messages = g_socket_datagram_based_receive_messages; |
||
1043 | iface->send_messages = g_socket_datagram_based_send_messages; |
||
1044 | iface->create_source = g_socket_datagram_based_create_source; |
||
1045 | iface->condition_check = g_socket_datagram_based_condition_check; |
||
1046 | iface->condition_wait = g_socket_datagram_based_condition_wait; |
||
1047 | } |
||
1048 | |||
1049 | static void |
||
1050 | g_socket_init (GSocket *socket) |
||
1051 | { |
||
1052 | socket->priv = g_socket_get_instance_private (socket); |
||
1053 | |||
1054 | socket->priv->fd = -1; |
||
1055 | socket->priv->blocking = TRUE; |
||
1056 | socket->priv->listen_backlog = 10; |
||
1057 | socket->priv->construct_error = NULL; |
||
1058 | #ifdef G_OS_WIN32 |
||
1059 | socket->priv->event = WSA_INVALID_EVENT; |
||
1060 | g_mutex_init (&socket->priv->win32_source_lock); |
||
1061 | #endif |
||
1062 | } |
||
1063 | |||
1064 | static gboolean |
||
1065 | g_socket_initable_init (GInitable *initable, |
||
1066 | GCancellable *cancellable, |
||
1067 | GError **error) |
||
1068 | { |
||
1069 | GSocket *socket; |
||
1070 | |||
1071 | g_return_val_if_fail (G_IS_SOCKET (initable), FALSE); |
||
1072 | |||
1073 | socket = G_SOCKET (initable); |
||
1074 | |||
1075 | if (cancellable != NULL) |
||
1076 | { |
||
1077 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, |
||
1078 | _("Cancellable initialization not supported")); |
||
1079 | return FALSE; |
||
1080 | } |
||
1081 | |||
1082 | socket->priv->inited = TRUE; |
||
1083 | |||
1084 | if (socket->priv->construct_error) |
||
1085 | { |
||
1086 | if (error) |
||
1087 | *error = g_error_copy (socket->priv->construct_error); |
||
1088 | return FALSE; |
||
1089 | } |
||
1090 | |||
1091 | |||
1092 | return TRUE; |
||
1093 | } |
||
1094 | |||
1095 | static gboolean |
||
1096 | check_datagram_based (GDatagramBased *self, |
||
1097 | GError **error) |
||
1098 | { |
||
1099 | switch (g_socket_get_socket_type (G_SOCKET (self))) |
||
1100 | { |
||
1101 | case G_SOCKET_TYPE_INVALID: |
||
1102 | case G_SOCKET_TYPE_STREAM: |
||
1103 | g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, |
||
1104 | _("Cannot use datagram operations on a non-datagram " |
||
1105 | "socket.")); |
||
1106 | return FALSE; |
||
1107 | case G_SOCKET_TYPE_DATAGRAM: |
||
1108 | case G_SOCKET_TYPE_SEQPACKET: |
||
1109 | /* Fall through. */ |
||
1110 | break; |
||
1111 | } |
||
1112 | |||
1113 | /* Due to us sharing #GSocketSource with the #GSocket implementation, it is |
||
1114 | * pretty tricky to split out #GSocket:timeout so that it does not affect |
||
1115 | * #GDatagramBased operations (but still affects #GSocket operations). It is |
||
1116 | * not worth that effort — just disallow it and require the user to specify |
||
1117 | * timeouts on a per-operation basis. */ |
||
1118 | if (g_socket_get_timeout (G_SOCKET (self)) != 0) |
||
1119 | { |
||
1120 | g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, |
||
1121 | _("Cannot use datagram operations on a socket with a " |
||
1122 | "timeout set.")); |
||
1123 | return FALSE; |
||
1124 | } |
||
1125 | |||
1126 | return TRUE; |
||
1127 | } |
||
1128 | |||
1129 | static gint |
||
1130 | g_socket_datagram_based_receive_messages (GDatagramBased *self, |
||
1131 | GInputMessage *messages, |
||
1132 | guint num_messages, |
||
1133 | gint flags, |
||
1134 | gint64 timeout, |
||
1135 | GCancellable *cancellable, |
||
1136 | GError **error) |
||
1137 | { |
||
1138 | if (!check_datagram_based (self, error)) |
||
1139 | return FALSE; |
||
1140 | |||
1141 | return g_socket_receive_messages_with_timeout (G_SOCKET (self), messages, |
||
1142 | num_messages, flags, timeout, |
||
1143 | cancellable, error); |
||
1144 | } |
||
1145 | |||
1146 | static gint |
||
1147 | g_socket_datagram_based_send_messages (GDatagramBased *self, |
||
1148 | GOutputMessage *messages, |
||
1149 | guint num_messages, |
||
1150 | gint flags, |
||
1151 | gint64 timeout, |
||
1152 | GCancellable *cancellable, |
||
1153 | GError **error) |
||
1154 | { |
||
1155 | if (!check_datagram_based (self, error)) |
||
1156 | return FALSE; |
||
1157 | |||
1158 | return g_socket_send_messages_with_timeout (G_SOCKET (self), messages, |
||
1159 | num_messages, flags, timeout, |
||
1160 | cancellable, error); |
||
1161 | } |
||
1162 | |||
1163 | static GSource * |
||
1164 | g_socket_datagram_based_create_source (GDatagramBased *self, |
||
1165 | GIOCondition condition, |
||
1166 | GCancellable *cancellable) |
||
1167 | { |
||
1168 | if (!check_datagram_based (self, NULL)) |
||
1169 | return NULL; |
||
1170 | |||
1171 | return g_socket_create_source (G_SOCKET (self), condition, cancellable); |
||
1172 | } |
||
1173 | |||
1174 | static GIOCondition |
||
1175 | g_socket_datagram_based_condition_check (GDatagramBased *datagram_based, |
||
1176 | GIOCondition condition) |
||
1177 | { |
||
1178 | if (!check_datagram_based (datagram_based, NULL)) |
||
1179 | return G_IO_ERR; |
||
1180 | |||
1181 | return g_socket_condition_check (G_SOCKET (datagram_based), condition); |
||
1182 | } |
||
1183 | |||
1184 | static gboolean |
||
1185 | g_socket_datagram_based_condition_wait (GDatagramBased *datagram_based, |
||
1186 | GIOCondition condition, |
||
1187 | gint64 timeout, |
||
1188 | GCancellable *cancellable, |
||
1189 | GError **error) |
||
1190 | { |
||
1191 | if (!check_datagram_based (datagram_based, error)) |
||
1192 | return FALSE; |
||
1193 | |||
1194 | return g_socket_condition_timed_wait (G_SOCKET (datagram_based), condition, |
||
1195 | timeout, cancellable, error); |
||
1196 | } |
||
1197 | |||
1198 | /** |
||
1199 | * g_socket_new: |
||
1200 | * @family: the socket family to use, e.g. %G_SOCKET_FAMILY_IPV4. |
||
1201 | * @type: the socket type to use. |
||
1202 | * @protocol: the id of the protocol to use, or 0 for default. |
||
1203 | * @error: #GError for error reporting, or %NULL to ignore. |
||
1204 | * |
||
1205 | * Creates a new #GSocket with the defined family, type and protocol. |
||
1206 | * If @protocol is 0 (%G_SOCKET_PROTOCOL_DEFAULT) the default protocol type |
||
1207 | * for the family and type is used. |
||
1208 | * |
||
1209 | * The @protocol is a family and type specific int that specifies what |
||
1210 | * kind of protocol to use. #GSocketProtocol lists several common ones. |
||
1211 | * Many families only support one protocol, and use 0 for this, others |
||
1212 | * support several and using 0 means to use the default protocol for |
||
1213 | * the family and type. |
||
1214 | * |
||
1215 | * The protocol id is passed directly to the operating |
||
1216 | * system, so you can use protocols not listed in #GSocketProtocol if you |
||
1217 | * know the protocol number used for it. |
||
1218 | * |
||
1219 | * Returns: a #GSocket or %NULL on error. |
||
1220 | * Free the returned object with g_object_unref(). |
||
1221 | * |
||
1222 | * Since: 2.22 |
||
1223 | */ |
||
1224 | GSocket * |
||
1225 | g_socket_new (GSocketFamily family, |
||
1226 | GSocketType type, |
||
1227 | GSocketProtocol protocol, |
||
1228 | GError **error) |
||
1229 | { |
||
1230 | return G_SOCKET (g_initable_new (G_TYPE_SOCKET, |
||
1231 | NULL, error, |
||
1232 | "family", family, |
||
1233 | "type", type, |
||
1234 | "protocol", protocol, |
||
1235 | NULL)); |
||
1236 | } |
||
1237 | |||
1238 | /** |
||
1239 | * g_socket_new_from_fd: |
||
1240 | * @fd: a native socket file descriptor. |
||
1241 | * @error: #GError for error reporting, or %NULL to ignore. |
||
1242 | * |
||
1243 | * Creates a new #GSocket from a native file descriptor |
||
1244 | * or winsock SOCKET handle. |
||
1245 | * |
||
1246 | * This reads all the settings from the file descriptor so that |
||
1247 | * all properties should work. Note that the file descriptor |
||
1248 | * will be set to non-blocking mode, independent on the blocking |
||
1249 | * mode of the #GSocket. |
||
1250 | * |
||
1251 | * On success, the returned #GSocket takes ownership of @fd. On failure, the |
||
1252 | * caller must close @fd themselves. |
||
1253 | * |
||
1254 | * Since GLib 2.46, it is no longer a fatal error to call this on a non-socket |
||
1255 | * descriptor. Instead, a GError will be set with code %G_IO_ERROR_FAILED |
||
1256 | * |
||
1257 | * Returns: a #GSocket or %NULL on error. |
||
1258 | * Free the returned object with g_object_unref(). |
||
1259 | * |
||
1260 | * Since: 2.22 |
||
1261 | */ |
||
1262 | GSocket * |
||
1263 | g_socket_new_from_fd (gint fd, |
||
1264 | GError **error) |
||
1265 | { |
||
1266 | return G_SOCKET (g_initable_new (G_TYPE_SOCKET, |
||
1267 | NULL, error, |
||
1268 | "fd", fd, |
||
1269 | NULL)); |
||
1270 | } |
||
1271 | |||
1272 | /** |
||
1273 | * g_socket_set_blocking: |
||
1274 | * @socket: a #GSocket. |
||
1275 | * @blocking: Whether to use blocking I/O or not. |
||
1276 | * |
||
1277 | * Sets the blocking mode of the socket. In blocking mode |
||
1278 | * all operations (which don’t take an explicit blocking parameter) block until |
||
1279 | * they succeed or there is an error. In |
||
1280 | * non-blocking mode all functions return results immediately or |
||
1281 | * with a %G_IO_ERROR_WOULD_BLOCK error. |
||
1282 | * |
||
1283 | * All sockets are created in blocking mode. However, note that the |
||
1284 | * platform level socket is always non-blocking, and blocking mode |
||
1285 | * is a GSocket level feature. |
||
1286 | * |
||
1287 | * Since: 2.22 |
||
1288 | */ |
||
1289 | void |
||
1290 | g_socket_set_blocking (GSocket *socket, |
||
1291 | gboolean blocking) |
||
1292 | { |
||
1293 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1294 | |||
1295 | blocking = !!blocking; |
||
1296 | |||
1297 | if (socket->priv->blocking == blocking) |
||
1298 | return; |
||
1299 | |||
1300 | socket->priv->blocking = blocking; |
||
1301 | g_object_notify (G_OBJECT (socket), "blocking"); |
||
1302 | } |
||
1303 | |||
1304 | /** |
||
1305 | * g_socket_get_blocking: |
||
1306 | * @socket: a #GSocket. |
||
1307 | * |
||
1308 | * Gets the blocking mode of the socket. For details on blocking I/O, |
||
1309 | * see g_socket_set_blocking(). |
||
1310 | * |
||
1311 | * Returns: %TRUE if blocking I/O is used, %FALSE otherwise. |
||
1312 | * |
||
1313 | * Since: 2.22 |
||
1314 | */ |
||
1315 | gboolean |
||
1316 | g_socket_get_blocking (GSocket *socket) |
||
1317 | { |
||
1318 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
1319 | |||
1320 | return socket->priv->blocking; |
||
1321 | } |
||
1322 | |||
1323 | /** |
||
1324 | * g_socket_set_keepalive: |
||
1325 | * @socket: a #GSocket. |
||
1326 | * @keepalive: Value for the keepalive flag |
||
1327 | * |
||
1328 | * Sets or unsets the %SO_KEEPALIVE flag on the underlying socket. When |
||
1329 | * this flag is set on a socket, the system will attempt to verify that the |
||
1330 | * remote socket endpoint is still present if a sufficiently long period of |
||
1331 | * time passes with no data being exchanged. If the system is unable to |
||
1332 | * verify the presence of the remote endpoint, it will automatically close |
||
1333 | * the connection. |
||
1334 | * |
||
1335 | * This option is only functional on certain kinds of sockets. (Notably, |
||
1336 | * %G_SOCKET_PROTOCOL_TCP sockets.) |
||
1337 | * |
||
1338 | * The exact time between pings is system- and protocol-dependent, but will |
||
1339 | * normally be at least two hours. Most commonly, you would set this flag |
||
1340 | * on a server socket if you want to allow clients to remain idle for long |
||
1341 | * periods of time, but also want to ensure that connections are eventually |
||
1342 | * garbage-collected if clients crash or become unreachable. |
||
1343 | * |
||
1344 | * Since: 2.22 |
||
1345 | */ |
||
1346 | void |
||
1347 | g_socket_set_keepalive (GSocket *socket, |
||
1348 | gboolean keepalive) |
||
1349 | { |
||
1350 | GError *error = NULL; |
||
1351 | |||
1352 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1353 | |||
1354 | keepalive = !!keepalive; |
||
1355 | if (socket->priv->keepalive == keepalive) |
||
1356 | return; |
||
1357 | |||
1358 | if (!g_socket_set_option (socket, SOL_SOCKET, SO_KEEPALIVE, |
||
1359 | keepalive, &error)) |
||
1360 | { |
||
1361 | g_warning ("error setting keepalive: %s", error->message); |
||
1362 | g_error_free (error); |
||
1363 | return; |
||
1364 | } |
||
1365 | |||
1366 | socket->priv->keepalive = keepalive; |
||
1367 | g_object_notify (G_OBJECT (socket), "keepalive"); |
||
1368 | } |
||
1369 | |||
1370 | /** |
||
1371 | * g_socket_get_keepalive: |
||
1372 | * @socket: a #GSocket. |
||
1373 | * |
||
1374 | * Gets the keepalive mode of the socket. For details on this, |
||
1375 | * see g_socket_set_keepalive(). |
||
1376 | * |
||
1377 | * Returns: %TRUE if keepalive is active, %FALSE otherwise. |
||
1378 | * |
||
1379 | * Since: 2.22 |
||
1380 | */ |
||
1381 | gboolean |
||
1382 | g_socket_get_keepalive (GSocket *socket) |
||
1383 | { |
||
1384 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
1385 | |||
1386 | return socket->priv->keepalive; |
||
1387 | } |
||
1388 | |||
1389 | /** |
||
1390 | * g_socket_get_listen_backlog: |
||
1391 | * @socket: a #GSocket. |
||
1392 | * |
||
1393 | * Gets the listen backlog setting of the socket. For details on this, |
||
1394 | * see g_socket_set_listen_backlog(). |
||
1395 | * |
||
1396 | * Returns: the maximum number of pending connections. |
||
1397 | * |
||
1398 | * Since: 2.22 |
||
1399 | */ |
||
1400 | gint |
||
1401 | g_socket_get_listen_backlog (GSocket *socket) |
||
1402 | { |
||
1403 | g_return_val_if_fail (G_IS_SOCKET (socket), 0); |
||
1404 | |||
1405 | return socket->priv->listen_backlog; |
||
1406 | } |
||
1407 | |||
1408 | /** |
||
1409 | * g_socket_set_listen_backlog: |
||
1410 | * @socket: a #GSocket. |
||
1411 | * @backlog: the maximum number of pending connections. |
||
1412 | * |
||
1413 | * Sets the maximum number of outstanding connections allowed |
||
1414 | * when listening on this socket. If more clients than this are |
||
1415 | * connecting to the socket and the application is not handling them |
||
1416 | * on time then the new connections will be refused. |
||
1417 | * |
||
1418 | * Note that this must be called before g_socket_listen() and has no |
||
1419 | * effect if called after that. |
||
1420 | * |
||
1421 | * Since: 2.22 |
||
1422 | */ |
||
1423 | void |
||
1424 | g_socket_set_listen_backlog (GSocket *socket, |
||
1425 | gint backlog) |
||
1426 | { |
||
1427 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1428 | g_return_if_fail (!socket->priv->listening); |
||
1429 | |||
1430 | if (backlog != socket->priv->listen_backlog) |
||
1431 | { |
||
1432 | socket->priv->listen_backlog = backlog; |
||
1433 | g_object_notify (G_OBJECT (socket), "listen-backlog"); |
||
1434 | } |
||
1435 | } |
||
1436 | |||
1437 | /** |
||
1438 | * g_socket_get_timeout: |
||
1439 | * @socket: a #GSocket. |
||
1440 | * |
||
1441 | * Gets the timeout setting of the socket. For details on this, see |
||
1442 | * g_socket_set_timeout(). |
||
1443 | * |
||
1444 | * Returns: the timeout in seconds |
||
1445 | * |
||
1446 | * Since: 2.26 |
||
1447 | */ |
||
1448 | guint |
||
1449 | g_socket_get_timeout (GSocket *socket) |
||
1450 | { |
||
1451 | g_return_val_if_fail (G_IS_SOCKET (socket), 0); |
||
1452 | |||
1453 | return socket->priv->timeout; |
||
1454 | } |
||
1455 | |||
1456 | /** |
||
1457 | * g_socket_set_timeout: |
||
1458 | * @socket: a #GSocket. |
||
1459 | * @timeout: the timeout for @socket, in seconds, or 0 for none |
||
1460 | * |
||
1461 | * Sets the time in seconds after which I/O operations on @socket will |
||
1462 | * time out if they have not yet completed. |
||
1463 | * |
||
1464 | * On a blocking socket, this means that any blocking #GSocket |
||
1465 | * operation will time out after @timeout seconds of inactivity, |
||
1466 | * returning %G_IO_ERROR_TIMED_OUT. |
||
1467 | * |
||
1468 | * On a non-blocking socket, calls to g_socket_condition_wait() will |
||
1469 | * also fail with %G_IO_ERROR_TIMED_OUT after the given time. Sources |
||
1470 | * created with g_socket_create_source() will trigger after |
||
1471 | * @timeout seconds of inactivity, with the requested condition |
||
1472 | * set, at which point calling g_socket_receive(), g_socket_send(), |
||
1473 | * g_socket_check_connect_result(), etc, will fail with |
||
1474 | * %G_IO_ERROR_TIMED_OUT. |
||
1475 | * |
||
1476 | * If @timeout is 0 (the default), operations will never time out |
||
1477 | * on their own. |
||
1478 | * |
||
1479 | * Note that if an I/O operation is interrupted by a signal, this may |
||
1480 | * cause the timeout to be reset. |
||
1481 | * |
||
1482 | * Since: 2.26 |
||
1483 | */ |
||
1484 | void |
||
1485 | g_socket_set_timeout (GSocket *socket, |
||
1486 | guint timeout) |
||
1487 | { |
||
1488 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1489 | |||
1490 | if (timeout != socket->priv->timeout) |
||
1491 | { |
||
1492 | socket->priv->timeout = timeout; |
||
1493 | g_object_notify (G_OBJECT (socket), "timeout"); |
||
1494 | } |
||
1495 | } |
||
1496 | |||
1497 | /** |
||
1498 | * g_socket_get_ttl: |
||
1499 | * @socket: a #GSocket. |
||
1500 | * |
||
1501 | * Gets the unicast time-to-live setting on @socket; see |
||
1502 | * g_socket_set_ttl() for more details. |
||
1503 | * |
||
1504 | * Returns: the time-to-live setting on @socket |
||
1505 | * |
||
1506 | * Since: 2.32 |
||
1507 | */ |
||
1508 | guint |
||
1509 | g_socket_get_ttl (GSocket *socket) |
||
1510 | { |
||
1511 | GError *error = NULL; |
||
1512 | gint value; |
||
1513 | |||
1514 | g_return_val_if_fail (G_IS_SOCKET (socket), 0); |
||
1515 | |||
1516 | if (socket->priv->family == G_SOCKET_FAMILY_IPV4) |
||
1517 | { |
||
1518 | g_socket_get_option (socket, IPPROTO_IP, IP_TTL, |
||
1519 | &value, &error); |
||
1520 | } |
||
1521 | else if (socket->priv->family == G_SOCKET_FAMILY_IPV6) |
||
1522 | { |
||
1523 | g_socket_get_option (socket, IPPROTO_IPV6, IPV6_UNICAST_HOPS, |
||
1524 | &value, &error); |
||
1525 | } |
||
1526 | else |
||
1527 | g_return_val_if_reached (0); |
||
1528 | |||
1529 | if (error) |
||
1530 | { |
||
1531 | g_warning ("error getting unicast ttl: %s", error->message); |
||
1532 | g_error_free (error); |
||
1533 | return 0; |
||
1534 | } |
||
1535 | |||
1536 | return value; |
||
1537 | } |
||
1538 | |||
1539 | /** |
||
1540 | * g_socket_set_ttl: |
||
1541 | * @socket: a #GSocket. |
||
1542 | * @ttl: the time-to-live value for all unicast packets on @socket |
||
1543 | * |
||
1544 | * Sets the time-to-live for outgoing unicast packets on @socket. |
||
1545 | * By default the platform-specific default value is used. |
||
1546 | * |
||
1547 | * Since: 2.32 |
||
1548 | */ |
||
1549 | void |
||
1550 | g_socket_set_ttl (GSocket *socket, |
||
1551 | guint ttl) |
||
1552 | { |
||
1553 | GError *error = NULL; |
||
1554 | |||
1555 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1556 | |||
1557 | if (socket->priv->family == G_SOCKET_FAMILY_IPV4) |
||
1558 | { |
||
1559 | g_socket_set_option (socket, IPPROTO_IP, IP_TTL, |
||
1560 | ttl, &error); |
||
1561 | } |
||
1562 | else if (socket->priv->family == G_SOCKET_FAMILY_IPV6) |
||
1563 | { |
||
1564 | g_socket_set_option (socket, IPPROTO_IP, IP_TTL, |
||
1565 | ttl, NULL); |
||
1566 | g_socket_set_option (socket, IPPROTO_IPV6, IPV6_UNICAST_HOPS, |
||
1567 | ttl, &error); |
||
1568 | } |
||
1569 | else |
||
1570 | g_return_if_reached (); |
||
1571 | |||
1572 | if (error) |
||
1573 | { |
||
1574 | g_warning ("error setting unicast ttl: %s", error->message); |
||
1575 | g_error_free (error); |
||
1576 | return; |
||
1577 | } |
||
1578 | |||
1579 | g_object_notify (G_OBJECT (socket), "ttl"); |
||
1580 | } |
||
1581 | |||
1582 | /** |
||
1583 | * g_socket_get_broadcast: |
||
1584 | * @socket: a #GSocket. |
||
1585 | * |
||
1586 | * Gets the broadcast setting on @socket; if %TRUE, |
||
1587 | * it is possible to send packets to broadcast |
||
1588 | * addresses. |
||
1589 | * |
||
1590 | * Returns: the broadcast setting on @socket |
||
1591 | * |
||
1592 | * Since: 2.32 |
||
1593 | */ |
||
1594 | gboolean |
||
1595 | g_socket_get_broadcast (GSocket *socket) |
||
1596 | { |
||
1597 | GError *error = NULL; |
||
1598 | gint value; |
||
1599 | |||
1600 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
1601 | |||
1602 | if (!g_socket_get_option (socket, SOL_SOCKET, SO_BROADCAST, |
||
1603 | &value, &error)) |
||
1604 | { |
||
1605 | g_warning ("error getting broadcast: %s", error->message); |
||
1606 | g_error_free (error); |
||
1607 | return FALSE; |
||
1608 | } |
||
1609 | |||
1610 | return !!value; |
||
1611 | } |
||
1612 | |||
1613 | /** |
||
1614 | * g_socket_set_broadcast: |
||
1615 | * @socket: a #GSocket. |
||
1616 | * @broadcast: whether @socket should allow sending to broadcast |
||
1617 | * addresses |
||
1618 | * |
||
1619 | * Sets whether @socket should allow sending to broadcast addresses. |
||
1620 | * This is %FALSE by default. |
||
1621 | * |
||
1622 | * Since: 2.32 |
||
1623 | */ |
||
1624 | void |
||
1625 | g_socket_set_broadcast (GSocket *socket, |
||
1626 | gboolean broadcast) |
||
1627 | { |
||
1628 | GError *error = NULL; |
||
1629 | |||
1630 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1631 | |||
1632 | broadcast = !!broadcast; |
||
1633 | |||
1634 | if (!g_socket_set_option (socket, SOL_SOCKET, SO_BROADCAST, |
||
1635 | broadcast, &error)) |
||
1636 | { |
||
1637 | g_warning ("error setting broadcast: %s", error->message); |
||
1638 | g_error_free (error); |
||
1639 | return; |
||
1640 | } |
||
1641 | |||
1642 | g_object_notify (G_OBJECT (socket), "broadcast"); |
||
1643 | } |
||
1644 | |||
1645 | /** |
||
1646 | * g_socket_get_multicast_loopback: |
||
1647 | * @socket: a #GSocket. |
||
1648 | * |
||
1649 | * Gets the multicast loopback setting on @socket; if %TRUE (the |
||
1650 | * default), outgoing multicast packets will be looped back to |
||
1651 | * multicast listeners on the same host. |
||
1652 | * |
||
1653 | * Returns: the multicast loopback setting on @socket |
||
1654 | * |
||
1655 | * Since: 2.32 |
||
1656 | */ |
||
1657 | gboolean |
||
1658 | g_socket_get_multicast_loopback (GSocket *socket) |
||
1659 | { |
||
1660 | GError *error = NULL; |
||
1661 | gint value; |
||
1662 | |||
1663 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
1664 | |||
1665 | if (socket->priv->family == G_SOCKET_FAMILY_IPV4) |
||
1666 | { |
||
1667 | g_socket_get_option (socket, IPPROTO_IP, IP_MULTICAST_LOOP, |
||
1668 | &value, &error); |
||
1669 | } |
||
1670 | else if (socket->priv->family == G_SOCKET_FAMILY_IPV6) |
||
1671 | { |
||
1672 | g_socket_get_option (socket, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, |
||
1673 | &value, &error); |
||
1674 | } |
||
1675 | else |
||
1676 | g_return_val_if_reached (FALSE); |
||
1677 | |||
1678 | if (error) |
||
1679 | { |
||
1680 | g_warning ("error getting multicast loopback: %s", error->message); |
||
1681 | g_error_free (error); |
||
1682 | return FALSE; |
||
1683 | } |
||
1684 | |||
1685 | return !!value; |
||
1686 | } |
||
1687 | |||
1688 | /** |
||
1689 | * g_socket_set_multicast_loopback: |
||
1690 | * @socket: a #GSocket. |
||
1691 | * @loopback: whether @socket should receive messages sent to its |
||
1692 | * multicast groups from the local host |
||
1693 | * |
||
1694 | * Sets whether outgoing multicast packets will be received by sockets |
||
1695 | * listening on that multicast address on the same host. This is %TRUE |
||
1696 | * by default. |
||
1697 | * |
||
1698 | * Since: 2.32 |
||
1699 | */ |
||
1700 | void |
||
1701 | g_socket_set_multicast_loopback (GSocket *socket, |
||
1702 | gboolean loopback) |
||
1703 | { |
||
1704 | GError *error = NULL; |
||
1705 | |||
1706 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1707 | |||
1708 | loopback = !!loopback; |
||
1709 | |||
1710 | if (socket->priv->family == G_SOCKET_FAMILY_IPV4) |
||
1711 | { |
||
1712 | g_socket_set_option (socket, IPPROTO_IP, IP_MULTICAST_LOOP, |
||
1713 | loopback, &error); |
||
1714 | } |
||
1715 | else if (socket->priv->family == G_SOCKET_FAMILY_IPV6) |
||
1716 | { |
||
1717 | g_socket_set_option (socket, IPPROTO_IP, IP_MULTICAST_LOOP, |
||
1718 | loopback, NULL); |
||
1719 | g_socket_set_option (socket, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, |
||
1720 | loopback, &error); |
||
1721 | } |
||
1722 | else |
||
1723 | g_return_if_reached (); |
||
1724 | |||
1725 | if (error) |
||
1726 | { |
||
1727 | g_warning ("error setting multicast loopback: %s", error->message); |
||
1728 | g_error_free (error); |
||
1729 | return; |
||
1730 | } |
||
1731 | |||
1732 | g_object_notify (G_OBJECT (socket), "multicast-loopback"); |
||
1733 | } |
||
1734 | |||
1735 | /** |
||
1736 | * g_socket_get_multicast_ttl: |
||
1737 | * @socket: a #GSocket. |
||
1738 | * |
||
1739 | * Gets the multicast time-to-live setting on @socket; see |
||
1740 | * g_socket_set_multicast_ttl() for more details. |
||
1741 | * |
||
1742 | * Returns: the multicast time-to-live setting on @socket |
||
1743 | * |
||
1744 | * Since: 2.32 |
||
1745 | */ |
||
1746 | guint |
||
1747 | g_socket_get_multicast_ttl (GSocket *socket) |
||
1748 | { |
||
1749 | GError *error = NULL; |
||
1750 | gint value; |
||
1751 | |||
1752 | g_return_val_if_fail (G_IS_SOCKET (socket), 0); |
||
1753 | |||
1754 | if (socket->priv->family == G_SOCKET_FAMILY_IPV4) |
||
1755 | { |
||
1756 | g_socket_get_option (socket, IPPROTO_IP, IP_MULTICAST_TTL, |
||
1757 | &value, &error); |
||
1758 | } |
||
1759 | else if (socket->priv->family == G_SOCKET_FAMILY_IPV6) |
||
1760 | { |
||
1761 | g_socket_get_option (socket, IPPROTO_IPV6, IPV6_MULTICAST_HOPS, |
||
1762 | &value, &error); |
||
1763 | } |
||
1764 | else |
||
1765 | g_return_val_if_reached (FALSE); |
||
1766 | |||
1767 | if (error) |
||
1768 | { |
||
1769 | g_warning ("error getting multicast ttl: %s", error->message); |
||
1770 | g_error_free (error); |
||
1771 | return FALSE; |
||
1772 | } |
||
1773 | |||
1774 | return value; |
||
1775 | } |
||
1776 | |||
1777 | /** |
||
1778 | * g_socket_set_multicast_ttl: |
||
1779 | * @socket: a #GSocket. |
||
1780 | * @ttl: the time-to-live value for all multicast datagrams on @socket |
||
1781 | * |
||
1782 | * Sets the time-to-live for outgoing multicast datagrams on @socket. |
||
1783 | * By default, this is 1, meaning that multicast packets will not leave |
||
1784 | * the local network. |
||
1785 | * |
||
1786 | * Since: 2.32 |
||
1787 | */ |
||
1788 | void |
||
1789 | g_socket_set_multicast_ttl (GSocket *socket, |
||
1790 | guint ttl) |
||
1791 | { |
||
1792 | GError *error = NULL; |
||
1793 | |||
1794 | g_return_if_fail (G_IS_SOCKET (socket)); |
||
1795 | |||
1796 | if (socket->priv->family == G_SOCKET_FAMILY_IPV4) |
||
1797 | { |
||
1798 | g_socket_set_option (socket, IPPROTO_IP, IP_MULTICAST_TTL, |
||
1799 | ttl, &error); |
||
1800 | } |
||
1801 | else if (socket->priv->family == G_SOCKET_FAMILY_IPV6) |
||
1802 | { |
||
1803 | g_socket_set_option (socket, IPPROTO_IP, IP_MULTICAST_TTL, |
||
1804 | ttl, NULL); |
||
1805 | g_socket_set_option (socket, IPPROTO_IPV6, IPV6_MULTICAST_HOPS, |
||
1806 | ttl, &error); |
||
1807 | } |
||
1808 | else |
||
1809 | g_return_if_reached (); |
||
1810 | |||
1811 | if (error) |
||
1812 | { |
||
1813 | g_warning ("error setting multicast ttl: %s", error->message); |
||
1814 | g_error_free (error); |
||
1815 | return; |
||
1816 | } |
||
1817 | |||
1818 | g_object_notify (G_OBJECT (socket), "multicast-ttl"); |
||
1819 | } |
||
1820 | |||
1821 | /** |
||
1822 | * g_socket_get_family: |
||
1823 | * @socket: a #GSocket. |
||
1824 | * |
||
1825 | * Gets the socket family of the socket. |
||
1826 | * |
||
1827 | * Returns: a #GSocketFamily |
||
1828 | * |
||
1829 | * Since: 2.22 |
||
1830 | */ |
||
1831 | GSocketFamily |
||
1832 | g_socket_get_family (GSocket *socket) |
||
1833 | { |
||
1834 | g_return_val_if_fail (G_IS_SOCKET (socket), G_SOCKET_FAMILY_INVALID); |
||
1835 | |||
1836 | return socket->priv->family; |
||
1837 | } |
||
1838 | |||
1839 | /** |
||
1840 | * g_socket_get_socket_type: |
||
1841 | * @socket: a #GSocket. |
||
1842 | * |
||
1843 | * Gets the socket type of the socket. |
||
1844 | * |
||
1845 | * Returns: a #GSocketType |
||
1846 | * |
||
1847 | * Since: 2.22 |
||
1848 | */ |
||
1849 | GSocketType |
||
1850 | g_socket_get_socket_type (GSocket *socket) |
||
1851 | { |
||
1852 | g_return_val_if_fail (G_IS_SOCKET (socket), G_SOCKET_TYPE_INVALID); |
||
1853 | |||
1854 | return socket->priv->type; |
||
1855 | } |
||
1856 | |||
1857 | /** |
||
1858 | * g_socket_get_protocol: |
||
1859 | * @socket: a #GSocket. |
||
1860 | * |
||
1861 | * Gets the socket protocol id the socket was created with. |
||
1862 | * In case the protocol is unknown, -1 is returned. |
||
1863 | * |
||
1864 | * Returns: a protocol id, or -1 if unknown |
||
1865 | * |
||
1866 | * Since: 2.22 |
||
1867 | */ |
||
1868 | GSocketProtocol |
||
1869 | g_socket_get_protocol (GSocket *socket) |
||
1870 | { |
||
1871 | g_return_val_if_fail (G_IS_SOCKET (socket), -1); |
||
1872 | |||
1873 | return socket->priv->protocol; |
||
1874 | } |
||
1875 | |||
1876 | /** |
||
1877 | * g_socket_get_fd: |
||
1878 | * @socket: a #GSocket. |
||
1879 | * |
||
1880 | * Returns the underlying OS socket object. On unix this |
||
1881 | * is a socket file descriptor, and on Windows this is |
||
1882 | * a Winsock2 SOCKET handle. This may be useful for |
||
1883 | * doing platform specific or otherwise unusual operations |
||
1884 | * on the socket. |
||
1885 | * |
||
1886 | * Returns: the file descriptor of the socket. |
||
1887 | * |
||
1888 | * Since: 2.22 |
||
1889 | */ |
||
1890 | int |
||
1891 | g_socket_get_fd (GSocket *socket) |
||
1892 | { |
||
1893 | g_return_val_if_fail (G_IS_SOCKET (socket), -1); |
||
1894 | |||
1895 | return socket->priv->fd; |
||
1896 | } |
||
1897 | |||
1898 | /** |
||
1899 | * g_socket_get_local_address: |
||
1900 | * @socket: a #GSocket. |
||
1901 | * @error: #GError for error reporting, or %NULL to ignore. |
||
1902 | * |
||
1903 | * Try to get the local address of a bound socket. This is only |
||
1904 | * useful if the socket has been bound to a local address, |
||
1905 | * either explicitly or implicitly when connecting. |
||
1906 | * |
||
1907 | * Returns: (transfer full): a #GSocketAddress or %NULL on error. |
||
1908 | * Free the returned object with g_object_unref(). |
||
1909 | * |
||
1910 | * Since: 2.22 |
||
1911 | */ |
||
1912 | GSocketAddress * |
||
1913 | g_socket_get_local_address (GSocket *socket, |
||
1914 | GError **error) |
||
1915 | { |
||
1916 | struct sockaddr_storage buffer; |
||
1917 | guint len = sizeof (buffer); |
||
1918 | |||
1919 | g_return_val_if_fail (G_IS_SOCKET (socket), NULL); |
||
1920 | |||
1921 | if (getsockname (socket->priv->fd, (struct sockaddr *) &buffer, &len) < 0) |
||
1922 | { |
||
1923 | int errsv = get_socket_errno (); |
||
1924 | g_set_error (error, G_IO_ERROR, socket_io_error_from_errno (errsv), |
||
1925 | _("could not get local address: %s"), socket_strerror (errsv)); |
||
1926 | return NULL; |
||
1927 | } |
||
1928 | |||
1929 | return g_socket_address_new_from_native (&buffer, len); |
||
1930 | } |
||
1931 | |||
1932 | /** |
||
1933 | * g_socket_get_remote_address: |
||
1934 | * @socket: a #GSocket. |
||
1935 | * @error: #GError for error reporting, or %NULL to ignore. |
||
1936 | * |
||
1937 | * Try to get the remove address of a connected socket. This is only |
||
1938 | * useful for connection oriented sockets that have been connected. |
||
1939 | * |
||
1940 | * Returns: (transfer full): a #GSocketAddress or %NULL on error. |
||
1941 | * Free the returned object with g_object_unref(). |
||
1942 | * |
||
1943 | * Since: 2.22 |
||
1944 | */ |
||
1945 | GSocketAddress * |
||
1946 | g_socket_get_remote_address (GSocket *socket, |
||
1947 | GError **error) |
||
1948 | { |
||
1949 | struct sockaddr_storage buffer; |
||
1950 | guint len = sizeof (buffer); |
||
1951 | |||
1952 | g_return_val_if_fail (G_IS_SOCKET (socket), NULL); |
||
1953 | |||
1954 | if (socket->priv->connect_pending) |
||
1955 | { |
||
1956 | if (!g_socket_check_connect_result (socket, error)) |
||
1957 | return NULL; |
||
1958 | else |
||
1959 | socket->priv->connect_pending = FALSE; |
||
1960 | } |
||
1961 | |||
1962 | if (!socket->priv->remote_address) |
||
1963 | { |
||
1964 | if (getpeername (socket->priv->fd, (struct sockaddr *) &buffer, &len) < 0) |
||
1965 | { |
||
1966 | int errsv = get_socket_errno (); |
||
1967 | g_set_error (error, G_IO_ERROR, socket_io_error_from_errno (errsv), |
||
1968 | _("could not get remote address: %s"), socket_strerror (errsv)); |
||
1969 | return NULL; |
||
1970 | } |
||
1971 | |||
1972 | socket->priv->remote_address = g_socket_address_new_from_native (&buffer, len); |
||
1973 | } |
||
1974 | |||
1975 | return g_object_ref (socket->priv->remote_address); |
||
1976 | } |
||
1977 | |||
1978 | /** |
||
1979 | * g_socket_is_connected: |
||
1980 | * @socket: a #GSocket. |
||
1981 | * |
||
1982 | * Check whether the socket is connected. This is only useful for |
||
1983 | * connection-oriented sockets. |
||
1984 | * |
||
1985 | * If using g_socket_shutdown(), this function will return %TRUE until the |
||
1986 | * socket has been shut down for reading and writing. If you do a non-blocking |
||
1987 | * connect, this function will not return %TRUE until after you call |
||
1988 | * g_socket_check_connect_result(). |
||
1989 | * |
||
1990 | * Returns: %TRUE if socket is connected, %FALSE otherwise. |
||
1991 | * |
||
1992 | * Since: 2.22 |
||
1993 | */ |
||
1994 | gboolean |
||
1995 | g_socket_is_connected (GSocket *socket) |
||
1996 | { |
||
1997 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
1998 | |||
1999 | return (socket->priv->connected_read || socket->priv->connected_write); |
||
2000 | } |
||
2001 | |||
2002 | /** |
||
2003 | * g_socket_listen: |
||
2004 | * @socket: a #GSocket. |
||
2005 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2006 | * |
||
2007 | * Marks the socket as a server socket, i.e. a socket that is used |
||
2008 | * to accept incoming requests using g_socket_accept(). |
||
2009 | * |
||
2010 | * Before calling this the socket must be bound to a local address using |
||
2011 | * g_socket_bind(). |
||
2012 | * |
||
2013 | * To set the maximum amount of outstanding clients, use |
||
2014 | * g_socket_set_listen_backlog(). |
||
2015 | * |
||
2016 | * Returns: %TRUE on success, %FALSE on error. |
||
2017 | * |
||
2018 | * Since: 2.22 |
||
2019 | */ |
||
2020 | gboolean |
||
2021 | g_socket_listen (GSocket *socket, |
||
2022 | GError **error) |
||
2023 | { |
||
2024 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
2025 | |||
2026 | if (!check_socket (socket, error)) |
||
2027 | return FALSE; |
||
2028 | |||
2029 | if (listen (socket->priv->fd, socket->priv->listen_backlog) < 0) |
||
2030 | { |
||
2031 | int errsv = get_socket_errno (); |
||
2032 | |||
2033 | g_set_error (error, G_IO_ERROR, socket_io_error_from_errno (errsv), |
||
2034 | _("could not listen: %s"), socket_strerror (errsv)); |
||
2035 | return FALSE; |
||
2036 | } |
||
2037 | |||
2038 | socket->priv->listening = TRUE; |
||
2039 | |||
2040 | return TRUE; |
||
2041 | } |
||
2042 | |||
2043 | /** |
||
2044 | * g_socket_bind: |
||
2045 | * @socket: a #GSocket. |
||
2046 | * @address: a #GSocketAddress specifying the local address. |
||
2047 | * @allow_reuse: whether to allow reusing this address |
||
2048 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2049 | * |
||
2050 | * When a socket is created it is attached to an address family, but it |
||
2051 | * doesn't have an address in this family. g_socket_bind() assigns the |
||
2052 | * address (sometimes called name) of the socket. |
||
2053 | * |
||
2054 | * It is generally required to bind to a local address before you can |
||
2055 | * receive connections. (See g_socket_listen() and g_socket_accept() ). |
||
2056 | * In certain situations, you may also want to bind a socket that will be |
||
2057 | * used to initiate connections, though this is not normally required. |
||
2058 | * |
||
2059 | * If @socket is a TCP socket, then @allow_reuse controls the setting |
||
2060 | * of the `SO_REUSEADDR` socket option; normally it should be %TRUE for |
||
2061 | * server sockets (sockets that you will eventually call |
||
2062 | * g_socket_accept() on), and %FALSE for client sockets. (Failing to |
||
2063 | * set this flag on a server socket may cause g_socket_bind() to return |
||
2064 | * %G_IO_ERROR_ADDRESS_IN_USE if the server program is stopped and then |
||
2065 | * immediately restarted.) |
||
2066 | * |
||
2067 | * If @socket is a UDP socket, then @allow_reuse determines whether or |
||
2068 | * not other UDP sockets can be bound to the same address at the same |
||
2069 | * time. In particular, you can have several UDP sockets bound to the |
||
2070 | * same address, and they will all receive all of the multicast and |
||
2071 | * broadcast packets sent to that address. (The behavior of unicast |
||
2072 | * UDP packets to an address with multiple listeners is not defined.) |
||
2073 | * |
||
2074 | * Returns: %TRUE on success, %FALSE on error. |
||
2075 | * |
||
2076 | * Since: 2.22 |
||
2077 | */ |
||
2078 | gboolean |
||
2079 | g_socket_bind (GSocket *socket, |
||
2080 | GSocketAddress *address, |
||
2081 | gboolean reuse_address, |
||
2082 | GError **error) |
||
2083 | { |
||
2084 | struct sockaddr_storage addr; |
||
2085 | gboolean so_reuseaddr; |
||
2086 | #ifdef SO_REUSEPORT |
||
2087 | gboolean so_reuseport; |
||
2088 | #endif |
||
2089 | |||
2090 | g_return_val_if_fail (G_IS_SOCKET (socket) && G_IS_SOCKET_ADDRESS (address), FALSE); |
||
2091 | |||
2092 | if (!check_socket (socket, error)) |
||
2093 | return FALSE; |
||
2094 | |||
2095 | if (!g_socket_address_to_native (address, &addr, sizeof addr, error)) |
||
2096 | return FALSE; |
||
2097 | |||
2098 | /* On Windows, SO_REUSEADDR has the semantics we want for UDP |
||
2099 | * sockets, but has nasty side effects we don't want for TCP |
||
2100 | * sockets. |
||
2101 | * |
||
2102 | * On other platforms, we set SO_REUSEPORT, if it exists, for |
||
2103 | * UDP sockets, and SO_REUSEADDR for all sockets, hoping that |
||
2104 | * if SO_REUSEPORT doesn't exist, then SO_REUSEADDR will have |
||
2105 | * the desired semantics on UDP (as it does on Linux, although |
||
2106 | * Linux has SO_REUSEPORT too as of 3.9). |
||
2107 | */ |
||
2108 | |||
2109 | #ifdef G_OS_WIN32 |
||
2110 | so_reuseaddr = reuse_address && (socket->priv->type == G_SOCKET_TYPE_DATAGRAM); |
||
2111 | #else |
||
2112 | so_reuseaddr = !!reuse_address; |
||
2113 | #endif |
||
2114 | |||
2115 | #ifdef SO_REUSEPORT |
||
2116 | so_reuseport = reuse_address && (socket->priv->type == G_SOCKET_TYPE_DATAGRAM); |
||
2117 | #endif |
||
2118 | |||
2119 | /* Ignore errors here, the only likely error is "not supported", and |
||
2120 | * this is a "best effort" thing mainly. |
||
2121 | */ |
||
2122 | g_socket_set_option (socket, SOL_SOCKET, SO_REUSEADDR, so_reuseaddr, NULL); |
||
2123 | #ifdef SO_REUSEPORT |
||
2124 | g_socket_set_option (socket, SOL_SOCKET, SO_REUSEPORT, so_reuseport, NULL); |
||
2125 | #endif |
||
2126 | |||
2127 | if (bind (socket->priv->fd, (struct sockaddr *) &addr, |
||
2128 | g_socket_address_get_native_size (address)) < 0) |
||
2129 | { |
||
2130 | int errsv = get_socket_errno (); |
||
2131 | g_set_error (error, |
||
2132 | G_IO_ERROR, socket_io_error_from_errno (errsv), |
||
2133 | _("Error binding to address: %s"), socket_strerror (errsv)); |
||
2134 | return FALSE; |
||
2135 | } |
||
2136 | |||
2137 | return TRUE; |
||
2138 | } |
||
2139 | |||
2140 | #if !defined(HAVE_IF_NAMETOINDEX) && defined(G_OS_WIN32) |
||
2141 | static guint |
||
2142 | if_nametoindex (const gchar *iface) |
||
2143 | { |
||
2144 | PIP_ADAPTER_ADDRESSES addresses = NULL, p; |
||
2145 | gulong addresses_len = 0; |
||
2146 | guint idx = 0; |
||
2147 | DWORD res; |
||
2148 | |||
2149 | if (ws2funcs.pIfNameToIndex != NULL) |
||
2150 | return ws2funcs.pIfNameToIndex (iface); |
||
2151 | |||
2152 | res = GetAdaptersAddresses (AF_UNSPEC, 0, NULL, NULL, &addresses_len); |
||
2153 | if (res != NO_ERROR && res != ERROR_BUFFER_OVERFLOW) |
||
2154 | { |
||
2155 | if (res == ERROR_NO_DATA) |
||
2156 | errno = ENXIO; |
||
2157 | else |
||
2158 | errno = EINVAL; |
||
2159 | return 0; |
||
2160 | } |
||
2161 | |||
2162 | addresses = g_malloc (addresses_len); |
||
2163 | res = GetAdaptersAddresses (AF_UNSPEC, 0, NULL, addresses, &addresses_len); |
||
2164 | |||
2165 | if (res != NO_ERROR) |
||
2166 | { |
||
2167 | g_free (addresses); |
||
2168 | if (res == ERROR_NO_DATA) |
||
2169 | errno = ENXIO; |
||
2170 | else |
||
2171 | errno = EINVAL; |
||
2172 | return 0; |
||
2173 | } |
||
2174 | |||
2175 | p = addresses; |
||
2176 | while (p) |
||
2177 | { |
||
2178 | if (strcmp (p->AdapterName, iface) == 0) |
||
2179 | { |
||
2180 | idx = p->IfIndex; |
||
2181 | break; |
||
2182 | } |
||
2183 | p = p->Next; |
||
2184 | } |
||
2185 | |||
2186 | if (p == NULL) |
||
2187 | errno = ENXIO; |
||
2188 | |||
2189 | g_free (addresses); |
||
2190 | |||
2191 | return idx; |
||
2192 | } |
||
2193 | |||
2194 | #define HAVE_IF_NAMETOINDEX 1 |
||
2195 | #endif |
||
2196 | |||
2197 | static gboolean |
||
2198 | g_socket_multicast_group_operation (GSocket *socket, |
||
2199 | GInetAddress *group, |
||
2200 | gboolean source_specific, |
||
2201 | const gchar *iface, |
||
2202 | gboolean join_group, |
||
2203 | GError **error) |
||
2204 | { |
||
2205 | const guint8 *native_addr; |
||
2206 | gint optname, result; |
||
2207 | |||
2208 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
2209 | g_return_val_if_fail (socket->priv->type == G_SOCKET_TYPE_DATAGRAM, FALSE); |
||
2210 | g_return_val_if_fail (G_IS_INET_ADDRESS (group), FALSE); |
||
2211 | |||
2212 | if (!check_socket (socket, error)) |
||
2213 | return FALSE; |
||
2214 | |||
2215 | native_addr = g_inet_address_to_bytes (group); |
||
2216 | if (g_inet_address_get_family (group) == G_SOCKET_FAMILY_IPV4) |
||
2217 | { |
||
2218 | #ifdef HAVE_IP_MREQN |
||
2219 | struct ip_mreqn mc_req; |
||
2220 | #else |
||
2221 | struct ip_mreq mc_req; |
||
2222 | #endif |
||
2223 | |||
2224 | memset (&mc_req, 0, sizeof (mc_req)); |
||
2225 | memcpy (&mc_req.imr_multiaddr, native_addr, sizeof (struct in_addr)); |
||
2226 | |||
2227 | #ifdef HAVE_IP_MREQN |
||
2228 | if (iface) |
||
2229 | mc_req.imr_ifindex = if_nametoindex (iface); |
||
2230 | else |
||
2231 | mc_req.imr_ifindex = 0; /* Pick any. */ |
||
2232 | #elif defined(G_OS_WIN32) |
||
2233 | if (iface) |
||
2234 | mc_req.imr_interface.s_addr = g_htonl (if_nametoindex (iface)); |
||
2235 | else |
||
2236 | mc_req.imr_interface.s_addr = g_htonl (INADDR_ANY); |
||
2237 | #else |
||
2238 | mc_req.imr_interface.s_addr = g_htonl (INADDR_ANY); |
||
2239 | #endif |
||
2240 | |||
2241 | if (source_specific) |
||
2242 | { |
||
2243 | #ifdef IP_ADD_SOURCE_MEMBERSHIP |
||
2244 | optname = join_group ? IP_ADD_SOURCE_MEMBERSHIP : IP_DROP_SOURCE_MEMBERSHIP; |
||
2245 | #else |
||
2246 | g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, |
||
2247 | join_group ? |
||
2248 | _("Error joining multicast group: %s") : |
||
2249 | _("Error leaving multicast group: %s"), |
||
2250 | _("No support for source-specific multicast")); |
||
2251 | return FALSE; |
||
2252 | #endif |
||
2253 | } |
||
2254 | else |
||
2255 | optname = join_group ? IP_ADD_MEMBERSHIP : IP_DROP_MEMBERSHIP; |
||
2256 | result = setsockopt (socket->priv->fd, IPPROTO_IP, optname, |
||
2257 | &mc_req, sizeof (mc_req)); |
||
2258 | } |
||
2259 | else if (g_inet_address_get_family (group) == G_SOCKET_FAMILY_IPV6) |
||
2260 | { |
||
2261 | struct ipv6_mreq mc_req_ipv6; |
||
2262 | |||
2263 | memset (&mc_req_ipv6, 0, sizeof (mc_req_ipv6)); |
||
2264 | memcpy (&mc_req_ipv6.ipv6mr_multiaddr, native_addr, sizeof (struct in6_addr)); |
||
2265 | #ifdef HAVE_IF_NAMETOINDEX |
||
2266 | if (iface) |
||
2267 | mc_req_ipv6.ipv6mr_interface = if_nametoindex (iface); |
||
2268 | else |
||
2269 | #endif |
||
2270 | mc_req_ipv6.ipv6mr_interface = 0; |
||
2271 | |||
2272 | optname = join_group ? IPV6_JOIN_GROUP : IPV6_LEAVE_GROUP; |
||
2273 | result = setsockopt (socket->priv->fd, IPPROTO_IPV6, optname, |
||
2274 | &mc_req_ipv6, sizeof (mc_req_ipv6)); |
||
2275 | } |
||
2276 | else |
||
2277 | g_return_val_if_reached (FALSE); |
||
2278 | |||
2279 | if (result < 0) |
||
2280 | { |
||
2281 | int errsv = get_socket_errno (); |
||
2282 | |||
2283 | g_set_error (error, G_IO_ERROR, socket_io_error_from_errno (errsv), |
||
2284 | join_group ? |
||
2285 | _("Error joining multicast group: %s") : |
||
2286 | _("Error leaving multicast group: %s"), |
||
2287 | socket_strerror (errsv)); |
||
2288 | return FALSE; |
||
2289 | } |
||
2290 | |||
2291 | return TRUE; |
||
2292 | } |
||
2293 | |||
2294 | /** |
||
2295 | * g_socket_join_multicast_group: |
||
2296 | * @socket: a #GSocket. |
||
2297 | * @group: a #GInetAddress specifying the group address to join. |
||
2298 | * @iface: (allow-none): Name of the interface to use, or %NULL |
||
2299 | * @source_specific: %TRUE if source-specific multicast should be used |
||
2300 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2301 | * |
||
2302 | * Registers @socket to receive multicast messages sent to @group. |
||
2303 | * @socket must be a %G_SOCKET_TYPE_DATAGRAM socket, and must have |
||
2304 | * been bound to an appropriate interface and port with |
||
2305 | * g_socket_bind(). |
||
2306 | * |
||
2307 | * If @iface is %NULL, the system will automatically pick an interface |
||
2308 | * to bind to based on @group. |
||
2309 | * |
||
2310 | * If @source_specific is %TRUE, source-specific multicast as defined |
||
2311 | * in RFC 4604 is used. Note that on older platforms this may fail |
||
2312 | * with a %G_IO_ERROR_NOT_SUPPORTED error. |
||
2313 | * |
||
2314 | * Returns: %TRUE on success, %FALSE on error. |
||
2315 | * |
||
2316 | * Since: 2.32 |
||
2317 | */ |
||
2318 | gboolean |
||
2319 | g_socket_join_multicast_group (GSocket *socket, |
||
2320 | GInetAddress *group, |
||
2321 | gboolean source_specific, |
||
2322 | const gchar *iface, |
||
2323 | GError **error) |
||
2324 | { |
||
2325 | return g_socket_multicast_group_operation (socket, group, source_specific, iface, TRUE, error); |
||
2326 | } |
||
2327 | |||
2328 | /** |
||
2329 | * g_socket_leave_multicast_group: |
||
2330 | * @socket: a #GSocket. |
||
2331 | * @group: a #GInetAddress specifying the group address to leave. |
||
2332 | * @iface: (allow-none): Interface used |
||
2333 | * @source_specific: %TRUE if source-specific multicast was used |
||
2334 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2335 | * |
||
2336 | * Removes @socket from the multicast group defined by @group, @iface, |
||
2337 | * and @source_specific (which must all have the same values they had |
||
2338 | * when you joined the group). |
||
2339 | * |
||
2340 | * @socket remains bound to its address and port, and can still receive |
||
2341 | * unicast messages after calling this. |
||
2342 | * |
||
2343 | * Returns: %TRUE on success, %FALSE on error. |
||
2344 | * |
||
2345 | * Since: 2.32 |
||
2346 | */ |
||
2347 | gboolean |
||
2348 | g_socket_leave_multicast_group (GSocket *socket, |
||
2349 | GInetAddress *group, |
||
2350 | gboolean source_specific, |
||
2351 | const gchar *iface, |
||
2352 | GError **error) |
||
2353 | { |
||
2354 | return g_socket_multicast_group_operation (socket, group, source_specific, iface, FALSE, error); |
||
2355 | } |
||
2356 | |||
2357 | /** |
||
2358 | * g_socket_speaks_ipv4: |
||
2359 | * @socket: a #GSocket |
||
2360 | * |
||
2361 | * Checks if a socket is capable of speaking IPv4. |
||
2362 | * |
||
2363 | * IPv4 sockets are capable of speaking IPv4. On some operating systems |
||
2364 | * and under some combinations of circumstances IPv6 sockets are also |
||
2365 | * capable of speaking IPv4. See RFC 3493 section 3.7 for more |
||
2366 | * information. |
||
2367 | * |
||
2368 | * No other types of sockets are currently considered as being capable |
||
2369 | * of speaking IPv4. |
||
2370 | * |
||
2371 | * Returns: %TRUE if this socket can be used with IPv4. |
||
2372 | * |
||
2373 | * Since: 2.22 |
||
2374 | **/ |
||
2375 | gboolean |
||
2376 | g_socket_speaks_ipv4 (GSocket *socket) |
||
2377 | { |
||
2378 | switch (socket->priv->family) |
||
2379 | { |
||
2380 | case G_SOCKET_FAMILY_IPV4: |
||
2381 | return TRUE; |
||
2382 | |||
2383 | case G_SOCKET_FAMILY_IPV6: |
||
2384 | #if defined (IPPROTO_IPV6) && defined (IPV6_V6ONLY) |
||
2385 | { |
||
2386 | gint v6_only; |
||
2387 | |||
2388 | if (!g_socket_get_option (socket, |
||
2389 | IPPROTO_IPV6, IPV6_V6ONLY, |
||
2390 | &v6_only, NULL)) |
||
2391 | return FALSE; |
||
2392 | |||
2393 | return !v6_only; |
||
2394 | } |
||
2395 | #else |
||
2396 | return FALSE; |
||
2397 | #endif |
||
2398 | |||
2399 | default: |
||
2400 | return FALSE; |
||
2401 | } |
||
2402 | } |
||
2403 | |||
2404 | /** |
||
2405 | * g_socket_accept: |
||
2406 | * @socket: a #GSocket. |
||
2407 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
2408 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2409 | * |
||
2410 | * Accept incoming connections on a connection-based socket. This removes |
||
2411 | * the first outstanding connection request from the listening socket and |
||
2412 | * creates a #GSocket object for it. |
||
2413 | * |
||
2414 | * The @socket must be bound to a local address with g_socket_bind() and |
||
2415 | * must be listening for incoming connections (g_socket_listen()). |
||
2416 | * |
||
2417 | * If there are no outstanding connections then the operation will block |
||
2418 | * or return %G_IO_ERROR_WOULD_BLOCK if non-blocking I/O is enabled. |
||
2419 | * To be notified of an incoming connection, wait for the %G_IO_IN condition. |
||
2420 | * |
||
2421 | * Returns: (transfer full): a new #GSocket, or %NULL on error. |
||
2422 | * Free the returned object with g_object_unref(). |
||
2423 | * |
||
2424 | * Since: 2.22 |
||
2425 | */ |
||
2426 | GSocket * |
||
2427 | g_socket_accept (GSocket *socket, |
||
2428 | GCancellable *cancellable, |
||
2429 | GError **error) |
||
2430 | { |
||
2431 | GSocket *new_socket; |
||
2432 | gint ret; |
||
2433 | |||
2434 | g_return_val_if_fail (G_IS_SOCKET (socket), NULL); |
||
2435 | |||
2436 | if (!check_socket (socket, error)) |
||
2437 | return NULL; |
||
2438 | |||
2439 | if (!check_timeout (socket, error)) |
||
2440 | return NULL; |
||
2441 | |||
2442 | while (TRUE) |
||
2443 | { |
||
2444 | if ((ret = accept (socket->priv->fd, NULL, 0)) < 0) |
||
2445 | { |
||
2446 | int errsv = get_socket_errno (); |
||
2447 | |||
2448 | if (errsv == EINTR) |
||
2449 | continue; |
||
2450 | |||
2451 | #ifdef WSAEWOULDBLOCK |
||
2452 | if (errsv == WSAEWOULDBLOCK) |
||
2453 | #else |
||
2454 | if (errsv == EWOULDBLOCK || |
||
2455 | errsv == EAGAIN) |
||
2456 | #endif |
||
2457 | { |
||
2458 | win32_unset_event_mask (socket, FD_ACCEPT); |
||
2459 | |||
2460 | if (socket->priv->blocking) |
||
2461 | { |
||
2462 | if (!g_socket_condition_wait (socket, |
||
2463 | G_IO_IN, cancellable, error)) |
||
2464 | return NULL; |
||
2465 | |||
2466 | continue; |
||
2467 | } |
||
2468 | } |
||
2469 | |||
2470 | socket_set_error_lazy (error, errsv, _("Error accepting connection: %s")); |
||
2471 | return NULL; |
||
2472 | } |
||
2473 | break; |
||
2474 | } |
||
2475 | |||
2476 | win32_unset_event_mask (socket, FD_ACCEPT); |
||
2477 | |||
2478 | #ifdef G_OS_WIN32 |
||
2479 | { |
||
2480 | /* The socket inherits the accepting sockets event mask and even object, |
||
2481 | we need to remove that */ |
||
2482 | WSAEventSelect (ret, NULL, 0); |
||
2483 | } |
||
2484 | #else |
||
2485 | { |
||
2486 | int flags; |
||
2487 | |||
2488 | /* We always want to set close-on-exec to protect users. If you |
||
2489 | need to so some weird inheritance to exec you can re-enable this |
||
2490 | using lower level hacks with g_socket_get_fd(). */ |
||
2491 | flags = fcntl (ret, F_GETFD, 0); |
||
2492 | if (flags != -1 && |
||
2493 | (flags & FD_CLOEXEC) == 0) |
||
2494 | { |
||
2495 | flags |= FD_CLOEXEC; |
||
2496 | fcntl (ret, F_SETFD, flags); |
||
2497 | } |
||
2498 | } |
||
2499 | #endif |
||
2500 | |||
2501 | new_socket = g_socket_new_from_fd (ret, error); |
||
2502 | if (new_socket == NULL) |
||
2503 | { |
||
2504 | #ifdef G_OS_WIN32 |
||
2505 | closesocket (ret); |
||
2506 | #else |
||
2507 | close (ret); |
||
2508 | #endif |
||
2509 | } |
||
2510 | else |
||
2511 | new_socket->priv->protocol = socket->priv->protocol; |
||
2512 | |||
2513 | return new_socket; |
||
2514 | } |
||
2515 | |||
2516 | /** |
||
2517 | * g_socket_connect: |
||
2518 | * @socket: a #GSocket. |
||
2519 | * @address: a #GSocketAddress specifying the remote address. |
||
2520 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
2521 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2522 | * |
||
2523 | * Connect the socket to the specified remote address. |
||
2524 | * |
||
2525 | * For connection oriented socket this generally means we attempt to make |
||
2526 | * a connection to the @address. For a connection-less socket it sets |
||
2527 | * the default address for g_socket_send() and discards all incoming datagrams |
||
2528 | * from other sources. |
||
2529 | * |
||
2530 | * Generally connection oriented sockets can only connect once, but |
||
2531 | * connection-less sockets can connect multiple times to change the |
||
2532 | * default address. |
||
2533 | * |
||
2534 | * If the connect call needs to do network I/O it will block, unless |
||
2535 | * non-blocking I/O is enabled. Then %G_IO_ERROR_PENDING is returned |
||
2536 | * and the user can be notified of the connection finishing by waiting |
||
2537 | * for the G_IO_OUT condition. The result of the connection must then be |
||
2538 | * checked with g_socket_check_connect_result(). |
||
2539 | * |
||
2540 | * Returns: %TRUE if connected, %FALSE on error. |
||
2541 | * |
||
2542 | * Since: 2.22 |
||
2543 | */ |
||
2544 | gboolean |
||
2545 | g_socket_connect (GSocket *socket, |
||
2546 | GSocketAddress *address, |
||
2547 | GCancellable *cancellable, |
||
2548 | GError **error) |
||
2549 | { |
||
2550 | struct sockaddr_storage buffer; |
||
2551 | |||
2552 | g_return_val_if_fail (G_IS_SOCKET (socket) && G_IS_SOCKET_ADDRESS (address), FALSE); |
||
2553 | |||
2554 | if (!check_socket (socket, error)) |
||
2555 | return FALSE; |
||
2556 | |||
2557 | if (!g_socket_address_to_native (address, &buffer, sizeof buffer, error)) |
||
2558 | return FALSE; |
||
2559 | |||
2560 | if (socket->priv->remote_address) |
||
2561 | g_object_unref (socket->priv->remote_address); |
||
2562 | socket->priv->remote_address = g_object_ref (address); |
||
2563 | |||
2564 | while (1) |
||
2565 | { |
||
2566 | if (connect (socket->priv->fd, (struct sockaddr *) &buffer, |
||
2567 | g_socket_address_get_native_size (address)) < 0) |
||
2568 | { |
||
2569 | int errsv = get_socket_errno (); |
||
2570 | |||
2571 | if (errsv == EINTR) |
||
2572 | continue; |
||
2573 | |||
2574 | #ifndef G_OS_WIN32 |
||
2575 | if (errsv == EINPROGRESS) |
||
2576 | #else |
||
2577 | if (errsv == WSAEWOULDBLOCK) |
||
2578 | #endif |
||
2579 | { |
||
2580 | win32_unset_event_mask (socket, FD_CONNECT); |
||
2581 | |||
2582 | if (socket->priv->blocking) |
||
2583 | { |
||
2584 | if (g_socket_condition_wait (socket, G_IO_OUT, cancellable, error)) |
||
2585 | { |
||
2586 | if (g_socket_check_connect_result (socket, error)) |
||
2587 | break; |
||
2588 | } |
||
2589 | } |
||
2590 | else |
||
2591 | { |
||
2592 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_PENDING, |
||
2593 | _("Connection in progress")); |
||
2594 | socket->priv->connect_pending = TRUE; |
||
2595 | } |
||
2596 | } |
||
2597 | else |
||
2598 | g_set_error_literal (error, G_IO_ERROR, |
||
2599 | socket_io_error_from_errno (errsv), |
||
2600 | socket_strerror (errsv)); |
||
2601 | |||
2602 | return FALSE; |
||
2603 | } |
||
2604 | break; |
||
2605 | } |
||
2606 | |||
2607 | win32_unset_event_mask (socket, FD_CONNECT); |
||
2608 | |||
2609 | socket->priv->connected_read = TRUE; |
||
2610 | socket->priv->connected_write = TRUE; |
||
2611 | |||
2612 | return TRUE; |
||
2613 | } |
||
2614 | |||
2615 | /** |
||
2616 | * g_socket_check_connect_result: |
||
2617 | * @socket: a #GSocket |
||
2618 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2619 | * |
||
2620 | * Checks and resets the pending connect error for the socket. |
||
2621 | * This is used to check for errors when g_socket_connect() is |
||
2622 | * used in non-blocking mode. |
||
2623 | * |
||
2624 | * Returns: %TRUE if no error, %FALSE otherwise, setting @error to the error |
||
2625 | * |
||
2626 | * Since: 2.22 |
||
2627 | */ |
||
2628 | gboolean |
||
2629 | g_socket_check_connect_result (GSocket *socket, |
||
2630 | GError **error) |
||
2631 | { |
||
2632 | int value; |
||
2633 | |||
2634 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
2635 | |||
2636 | if (!check_socket (socket, error)) |
||
2637 | return FALSE; |
||
2638 | |||
2639 | if (!check_timeout (socket, error)) |
||
2640 | return FALSE; |
||
2641 | |||
2642 | if (!g_socket_get_option (socket, SOL_SOCKET, SO_ERROR, &value, error)) |
||
2643 | { |
||
2644 | g_prefix_error (error, _("Unable to get pending error: ")); |
||
2645 | return FALSE; |
||
2646 | } |
||
2647 | |||
2648 | if (value != 0) |
||
2649 | { |
||
2650 | g_set_error_literal (error, G_IO_ERROR, socket_io_error_from_errno (value), |
||
2651 | socket_strerror (value)); |
||
2652 | if (socket->priv->remote_address) |
||
2653 | { |
||
2654 | g_object_unref (socket->priv->remote_address); |
||
2655 | socket->priv->remote_address = NULL; |
||
2656 | } |
||
2657 | return FALSE; |
||
2658 | } |
||
2659 | |||
2660 | socket->priv->connected_read = TRUE; |
||
2661 | socket->priv->connected_write = TRUE; |
||
2662 | |||
2663 | return TRUE; |
||
2664 | } |
||
2665 | |||
2666 | /** |
||
2667 | * g_socket_get_available_bytes: |
||
2668 | * @socket: a #GSocket |
||
2669 | * |
||
2670 | * Get the amount of data pending in the OS input buffer, without blocking. |
||
2671 | * |
||
2672 | * If @socket is a UDP or SCTP socket, this will return the size of |
||
2673 | * just the next packet, even if additional packets are buffered after |
||
2674 | * that one. |
||
2675 | * |
||
2676 | * Note that on Windows, this function is rather inefficient in the |
||
2677 | * UDP case, and so if you know any plausible upper bound on the size |
||
2678 | * of the incoming packet, it is better to just do a |
||
2679 | * g_socket_receive() with a buffer of that size, rather than calling |
||
2680 | * g_socket_get_available_bytes() first and then doing a receive of |
||
2681 | * exactly the right size. |
||
2682 | * |
||
2683 | * Returns: the number of bytes that can be read from the socket |
||
2684 | * without blocking or truncating, or -1 on error. |
||
2685 | * |
||
2686 | * Since: 2.32 |
||
2687 | */ |
||
2688 | gssize |
||
2689 | g_socket_get_available_bytes (GSocket *socket) |
||
2690 | { |
||
2691 | #ifdef G_OS_WIN32 |
||
2692 | const gint bufsize = 64 * 1024; |
||
2693 | static guchar *buf = NULL; |
||
2694 | u_long avail; |
||
2695 | #else |
||
2696 | gint avail; |
||
2697 | #endif |
||
2698 | |||
2699 | g_return_val_if_fail (G_IS_SOCKET (socket), -1); |
||
2700 | |||
2701 | #if defined (SO_NREAD) |
||
2702 | if (!g_socket_get_option (socket, SOL_SOCKET, SO_NREAD, &avail, NULL)) |
||
2703 | return -1; |
||
2704 | #elif !defined (G_OS_WIN32) |
||
2705 | if (ioctl (socket->priv->fd, FIONREAD, &avail) < 0) |
||
2706 | avail = -1; |
||
2707 | #else |
||
2708 | if (socket->priv->type == G_SOCKET_TYPE_DATAGRAM) |
||
2709 | { |
||
2710 | if (G_UNLIKELY (g_once_init_enter (&buf))) |
||
2711 | g_once_init_leave (&buf, g_malloc (bufsize)); |
||
2712 | |||
2713 | avail = recv (socket->priv->fd, buf, bufsize, MSG_PEEK); |
||
2714 | if (avail == -1 && get_socket_errno () == WSAEWOULDBLOCK) |
||
2715 | avail = 0; |
||
2716 | } |
||
2717 | else |
||
2718 | { |
||
2719 | if (ioctlsocket (socket->priv->fd, FIONREAD, &avail) < 0) |
||
2720 | avail = -1; |
||
2721 | } |
||
2722 | #endif |
||
2723 | |||
2724 | return avail; |
||
2725 | } |
||
2726 | |||
2727 | /* Block on a timed wait for @condition until (@start_time + @timeout). |
||
2728 | * Return %G_IO_ERROR_TIMED_OUT if the timeout is reached; otherwise %TRUE. |
||
2729 | */ |
||
2730 | static gboolean |
||
2731 | block_on_timeout (GSocket *socket, |
||
2732 | GIOCondition condition, |
||
2733 | gint64 timeout, |
||
2734 | gint64 start_time, |
||
2735 | GCancellable *cancellable, |
||
2736 | GError **error) |
||
2737 | { |
||
2738 | gint64 wait_timeout = -1; |
||
2739 | |||
2740 | g_return_val_if_fail (timeout != 0, TRUE); |
||
2741 | |||
2742 | /* check if we've timed out or how much time to wait at most */ |
||
2743 | if (timeout >= 0) |
||
2744 | { |
||
2745 | gint64 elapsed = g_get_monotonic_time () - start_time; |
||
2746 | |||
2747 | if (elapsed >= timeout) |
||
2748 | { |
||
2749 | g_set_error_literal (error, |
||
2750 | G_IO_ERROR, G_IO_ERROR_TIMED_OUT, |
||
2751 | _("Socket I/O timed out")); |
||
2752 | return FALSE; |
||
2753 | } |
||
2754 | |||
2755 | wait_timeout = timeout - elapsed; |
||
2756 | } |
||
2757 | |||
2758 | return g_socket_condition_timed_wait (socket, condition, wait_timeout, |
||
2759 | cancellable, error); |
||
2760 | } |
||
2761 | |||
2762 | static gssize |
||
2763 | g_socket_receive_with_timeout (GSocket *socket, |
||
2764 | guint8 *buffer, |
||
2765 | gsize size, |
||
2766 | gint64 timeout, |
||
2767 | GCancellable *cancellable, |
||
2768 | GError **error) |
||
2769 | { |
||
2770 | gssize ret; |
||
2771 | gint64 start_time; |
||
2772 | |||
2773 | g_return_val_if_fail (G_IS_SOCKET (socket) && buffer != NULL, -1); |
||
2774 | |||
2775 | start_time = g_get_monotonic_time (); |
||
2776 | |||
2777 | if (!check_socket (socket, error)) |
||
2778 | return -1; |
||
2779 | |||
2780 | if (!check_timeout (socket, error)) |
||
2781 | return -1; |
||
2782 | |||
2783 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
2784 | return -1; |
||
2785 | |||
2786 | while (1) |
||
2787 | { |
||
2788 | if ((ret = recv (socket->priv->fd, buffer, size, 0)) < 0) |
||
2789 | { |
||
2790 | int errsv = get_socket_errno (); |
||
2791 | |||
2792 | if (errsv == EINTR) |
||
2793 | continue; |
||
2794 | |||
2795 | #ifdef WSAEWOULDBLOCK |
||
2796 | if (errsv == WSAEWOULDBLOCK) |
||
2797 | #else |
||
2798 | if (errsv == EWOULDBLOCK || |
||
2799 | errsv == EAGAIN) |
||
2800 | #endif |
||
2801 | { |
||
2802 | win32_unset_event_mask (socket, FD_READ); |
||
2803 | |||
2804 | if (timeout != 0) |
||
2805 | { |
||
2806 | if (!block_on_timeout (socket, G_IO_IN, timeout, start_time, |
||
2807 | cancellable, error)) |
||
2808 | return -1; |
||
2809 | |||
2810 | continue; |
||
2811 | } |
||
2812 | } |
||
2813 | |||
2814 | win32_unset_event_mask (socket, FD_READ); |
||
2815 | |||
2816 | socket_set_error_lazy (error, errsv, _("Error receiving data: %s")); |
||
2817 | return -1; |
||
2818 | } |
||
2819 | |||
2820 | win32_unset_event_mask (socket, FD_READ); |
||
2821 | |||
2822 | break; |
||
2823 | } |
||
2824 | |||
2825 | return ret; |
||
2826 | } |
||
2827 | |||
2828 | /** |
||
2829 | * g_socket_receive: |
||
2830 | * @socket: a #GSocket |
||
2831 | * @buffer: (array length=size) (element-type guint8): a buffer to |
||
2832 | * read data into (which should be at least @size bytes long). |
||
2833 | * @size: the number of bytes you want to read from the socket |
||
2834 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
2835 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2836 | * |
||
2837 | * Receive data (up to @size bytes) from a socket. This is mainly used by |
||
2838 | * connection-oriented sockets; it is identical to g_socket_receive_from() |
||
2839 | * with @address set to %NULL. |
||
2840 | * |
||
2841 | * For %G_SOCKET_TYPE_DATAGRAM and %G_SOCKET_TYPE_SEQPACKET sockets, |
||
2842 | * g_socket_receive() will always read either 0 or 1 complete messages from |
||
2843 | * the socket. If the received message is too large to fit in @buffer, then |
||
2844 | * the data beyond @size bytes will be discarded, without any explicit |
||
2845 | * indication that this has occurred. |
||
2846 | * |
||
2847 | * For %G_SOCKET_TYPE_STREAM sockets, g_socket_receive() can return any |
||
2848 | * number of bytes, up to @size. If more than @size bytes have been |
||
2849 | * received, the additional data will be returned in future calls to |
||
2850 | * g_socket_receive(). |
||
2851 | * |
||
2852 | * If the socket is in blocking mode the call will block until there |
||
2853 | * is some data to receive, the connection is closed, or there is an |
||
2854 | * error. If there is no data available and the socket is in |
||
2855 | * non-blocking mode, a %G_IO_ERROR_WOULD_BLOCK error will be |
||
2856 | * returned. To be notified when data is available, wait for the |
||
2857 | * %G_IO_IN condition. |
||
2858 | * |
||
2859 | * On error -1 is returned and @error is set accordingly. |
||
2860 | * |
||
2861 | * Returns: Number of bytes read, or 0 if the connection was closed by |
||
2862 | * the peer, or -1 on error |
||
2863 | * |
||
2864 | * Since: 2.22 |
||
2865 | */ |
||
2866 | gssize |
||
2867 | g_socket_receive (GSocket *socket, |
||
2868 | gchar *buffer, |
||
2869 | gsize size, |
||
2870 | GCancellable *cancellable, |
||
2871 | GError **error) |
||
2872 | { |
||
2873 | return g_socket_receive_with_timeout (socket, (guint8 *) buffer, size, |
||
2874 | socket->priv->blocking ? -1 : 0, |
||
2875 | cancellable, error); |
||
2876 | } |
||
2877 | |||
2878 | /** |
||
2879 | * g_socket_receive_with_blocking: |
||
2880 | * @socket: a #GSocket |
||
2881 | * @buffer: (array length=size) (element-type guint8): a buffer to |
||
2882 | * read data into (which should be at least @size bytes long). |
||
2883 | * @size: the number of bytes you want to read from the socket |
||
2884 | * @blocking: whether to do blocking or non-blocking I/O |
||
2885 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
2886 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2887 | * |
||
2888 | * This behaves exactly the same as g_socket_receive(), except that |
||
2889 | * the choice of blocking or non-blocking behavior is determined by |
||
2890 | * the @blocking argument rather than by @socket's properties. |
||
2891 | * |
||
2892 | * Returns: Number of bytes read, or 0 if the connection was closed by |
||
2893 | * the peer, or -1 on error |
||
2894 | * |
||
2895 | * Since: 2.26 |
||
2896 | */ |
||
2897 | gssize |
||
2898 | g_socket_receive_with_blocking (GSocket *socket, |
||
2899 | gchar *buffer, |
||
2900 | gsize size, |
||
2901 | gboolean blocking, |
||
2902 | GCancellable *cancellable, |
||
2903 | GError **error) |
||
2904 | { |
||
2905 | return g_socket_receive_with_timeout (socket, (guint8 *) buffer, size, |
||
2906 | blocking ? -1 : 0, cancellable, error); |
||
2907 | } |
||
2908 | |||
2909 | /** |
||
2910 | * g_socket_receive_from: |
||
2911 | * @socket: a #GSocket |
||
2912 | * @address: (out) (allow-none): a pointer to a #GSocketAddress |
||
2913 | * pointer, or %NULL |
||
2914 | * @buffer: (array length=size) (element-type guint8): a buffer to |
||
2915 | * read data into (which should be at least @size bytes long). |
||
2916 | * @size: the number of bytes you want to read from the socket |
||
2917 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
2918 | * @error: #GError for error reporting, or %NULL to ignore. |
||
2919 | * |
||
2920 | * Receive data (up to @size bytes) from a socket. |
||
2921 | * |
||
2922 | * If @address is non-%NULL then @address will be set equal to the |
||
2923 | * source address of the received packet. |
||
2924 | * @address is owned by the caller. |
||
2925 | * |
||
2926 | * See g_socket_receive() for additional information. |
||
2927 | * |
||
2928 | * Returns: Number of bytes read, or 0 if the connection was closed by |
||
2929 | * the peer, or -1 on error |
||
2930 | * |
||
2931 | * Since: 2.22 |
||
2932 | */ |
||
2933 | gssize |
||
2934 | g_socket_receive_from (GSocket *socket, |
||
2935 | GSocketAddress **address, |
||
2936 | gchar *buffer, |
||
2937 | gsize size, |
||
2938 | GCancellable *cancellable, |
||
2939 | GError **error) |
||
2940 | { |
||
2941 | GInputVector v; |
||
2942 | |||
2943 | v.buffer = buffer; |
||
2944 | v.size = size; |
||
2945 | |||
2946 | return g_socket_receive_message (socket, |
||
2947 | address, |
||
2948 | &v, 1, |
||
2949 | NULL, 0, NULL, |
||
2950 | cancellable, |
||
2951 | error); |
||
2952 | } |
||
2953 | |||
2954 | /* See the comment about SIGPIPE above. */ |
||
2955 | #ifdef MSG_NOSIGNAL |
||
2956 | #define G_SOCKET_DEFAULT_SEND_FLAGS MSG_NOSIGNAL |
||
2957 | #else |
||
2958 | #define G_SOCKET_DEFAULT_SEND_FLAGS 0 |
||
2959 | #endif |
||
2960 | |||
2961 | static gssize |
||
2962 | g_socket_send_with_timeout (GSocket *socket, |
||
2963 | const guint8 *buffer, |
||
2964 | gsize size, |
||
2965 | gint64 timeout, |
||
2966 | GCancellable *cancellable, |
||
2967 | GError **error) |
||
2968 | { |
||
2969 | gssize ret; |
||
2970 | gint64 start_time; |
||
2971 | |||
2972 | g_return_val_if_fail (G_IS_SOCKET (socket) && buffer != NULL, -1); |
||
2973 | |||
2974 | start_time = g_get_monotonic_time (); |
||
2975 | |||
2976 | if (!check_socket (socket, error)) |
||
2977 | return -1; |
||
2978 | |||
2979 | if (!check_timeout (socket, error)) |
||
2980 | return -1; |
||
2981 | |||
2982 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
2983 | return -1; |
||
2984 | |||
2985 | while (1) |
||
2986 | { |
||
2987 | if ((ret = send (socket->priv->fd, buffer, size, G_SOCKET_DEFAULT_SEND_FLAGS)) < 0) |
||
2988 | { |
||
2989 | int errsv = get_socket_errno (); |
||
2990 | |||
2991 | if (errsv == EINTR) |
||
2992 | continue; |
||
2993 | |||
2994 | #ifdef WSAEWOULDBLOCK |
||
2995 | if (errsv == WSAEWOULDBLOCK) |
||
2996 | #else |
||
2997 | if (errsv == EWOULDBLOCK || |
||
2998 | errsv == EAGAIN) |
||
2999 | #endif |
||
3000 | { |
||
3001 | win32_unset_event_mask (socket, FD_WRITE); |
||
3002 | |||
3003 | if (timeout != 0) |
||
3004 | { |
||
3005 | if (!block_on_timeout (socket, G_IO_OUT, timeout, start_time, |
||
3006 | cancellable, error)) |
||
3007 | return -1; |
||
3008 | |||
3009 | continue; |
||
3010 | } |
||
3011 | } |
||
3012 | |||
3013 | socket_set_error_lazy (error, errsv, _("Error sending data: %s")); |
||
3014 | return -1; |
||
3015 | } |
||
3016 | break; |
||
3017 | } |
||
3018 | |||
3019 | return ret; |
||
3020 | } |
||
3021 | |||
3022 | /** |
||
3023 | * g_socket_send: |
||
3024 | * @socket: a #GSocket |
||
3025 | * @buffer: (array length=size) (element-type guint8): the buffer |
||
3026 | * containing the data to send. |
||
3027 | * @size: the number of bytes to send |
||
3028 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
3029 | * @error: #GError for error reporting, or %NULL to ignore. |
||
3030 | * |
||
3031 | * Tries to send @size bytes from @buffer on the socket. This is |
||
3032 | * mainly used by connection-oriented sockets; it is identical to |
||
3033 | * g_socket_send_to() with @address set to %NULL. |
||
3034 | * |
||
3035 | * If the socket is in blocking mode the call will block until there is |
||
3036 | * space for the data in the socket queue. If there is no space available |
||
3037 | * and the socket is in non-blocking mode a %G_IO_ERROR_WOULD_BLOCK error |
||
3038 | * will be returned. To be notified when space is available, wait for the |
||
3039 | * %G_IO_OUT condition. Note though that you may still receive |
||
3040 | * %G_IO_ERROR_WOULD_BLOCK from g_socket_send() even if you were previously |
||
3041 | * notified of a %G_IO_OUT condition. (On Windows in particular, this is |
||
3042 | * very common due to the way the underlying APIs work.) |
||
3043 | * |
||
3044 | * On error -1 is returned and @error is set accordingly. |
||
3045 | * |
||
3046 | * Returns: Number of bytes written (which may be less than @size), or -1 |
||
3047 | * on error |
||
3048 | * |
||
3049 | * Since: 2.22 |
||
3050 | */ |
||
3051 | gssize |
||
3052 | g_socket_send (GSocket *socket, |
||
3053 | const gchar *buffer, |
||
3054 | gsize size, |
||
3055 | GCancellable *cancellable, |
||
3056 | GError **error) |
||
3057 | { |
||
3058 | return g_socket_send_with_blocking (socket, buffer, size, |
||
3059 | socket->priv->blocking, |
||
3060 | cancellable, error); |
||
3061 | } |
||
3062 | |||
3063 | /** |
||
3064 | * g_socket_send_with_blocking: |
||
3065 | * @socket: a #GSocket |
||
3066 | * @buffer: (array length=size) (element-type guint8): the buffer |
||
3067 | * containing the data to send. |
||
3068 | * @size: the number of bytes to send |
||
3069 | * @blocking: whether to do blocking or non-blocking I/O |
||
3070 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
3071 | * @error: #GError for error reporting, or %NULL to ignore. |
||
3072 | * |
||
3073 | * This behaves exactly the same as g_socket_send(), except that |
||
3074 | * the choice of blocking or non-blocking behavior is determined by |
||
3075 | * the @blocking argument rather than by @socket's properties. |
||
3076 | * |
||
3077 | * Returns: Number of bytes written (which may be less than @size), or -1 |
||
3078 | * on error |
||
3079 | * |
||
3080 | * Since: 2.26 |
||
3081 | */ |
||
3082 | gssize |
||
3083 | g_socket_send_with_blocking (GSocket *socket, |
||
3084 | const gchar *buffer, |
||
3085 | gsize size, |
||
3086 | gboolean blocking, |
||
3087 | GCancellable *cancellable, |
||
3088 | GError **error) |
||
3089 | { |
||
3090 | return g_socket_send_with_timeout (socket, (const guint8 *) buffer, size, |
||
3091 | blocking ? -1 : 0, cancellable, error); |
||
3092 | } |
||
3093 | |||
3094 | /** |
||
3095 | * g_socket_send_to: |
||
3096 | * @socket: a #GSocket |
||
3097 | * @address: (allow-none): a #GSocketAddress, or %NULL |
||
3098 | * @buffer: (array length=size) (element-type guint8): the buffer |
||
3099 | * containing the data to send. |
||
3100 | * @size: the number of bytes to send |
||
3101 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
3102 | * @error: #GError for error reporting, or %NULL to ignore. |
||
3103 | * |
||
3104 | * Tries to send @size bytes from @buffer to @address. If @address is |
||
3105 | * %NULL then the message is sent to the default receiver (set by |
||
3106 | * g_socket_connect()). |
||
3107 | * |
||
3108 | * See g_socket_send() for additional information. |
||
3109 | * |
||
3110 | * Returns: Number of bytes written (which may be less than @size), or -1 |
||
3111 | * on error |
||
3112 | * |
||
3113 | * Since: 2.22 |
||
3114 | */ |
||
3115 | gssize |
||
3116 | g_socket_send_to (GSocket *socket, |
||
3117 | GSocketAddress *address, |
||
3118 | const gchar *buffer, |
||
3119 | gsize size, |
||
3120 | GCancellable *cancellable, |
||
3121 | GError **error) |
||
3122 | { |
||
3123 | GOutputVector v; |
||
3124 | |||
3125 | v.buffer = buffer; |
||
3126 | v.size = size; |
||
3127 | |||
3128 | return g_socket_send_message (socket, |
||
3129 | address, |
||
3130 | &v, 1, |
||
3131 | NULL, 0, |
||
3132 | 0, |
||
3133 | cancellable, |
||
3134 | error); |
||
3135 | } |
||
3136 | |||
3137 | /** |
||
3138 | * g_socket_shutdown: |
||
3139 | * @socket: a #GSocket |
||
3140 | * @shutdown_read: whether to shut down the read side |
||
3141 | * @shutdown_write: whether to shut down the write side |
||
3142 | * @error: #GError for error reporting, or %NULL to ignore. |
||
3143 | * |
||
3144 | * Shut down part or all of a full-duplex connection. |
||
3145 | * |
||
3146 | * If @shutdown_read is %TRUE then the receiving side of the connection |
||
3147 | * is shut down, and further reading is disallowed. |
||
3148 | * |
||
3149 | * If @shutdown_write is %TRUE then the sending side of the connection |
||
3150 | * is shut down, and further writing is disallowed. |
||
3151 | * |
||
3152 | * It is allowed for both @shutdown_read and @shutdown_write to be %TRUE. |
||
3153 | * |
||
3154 | * One example where it is useful to shut down only one side of a connection is |
||
3155 | * graceful disconnect for TCP connections where you close the sending side, |
||
3156 | * then wait for the other side to close the connection, thus ensuring that the |
||
3157 | * other side saw all sent data. |
||
3158 | * |
||
3159 | * Returns: %TRUE on success, %FALSE on error |
||
3160 | * |
||
3161 | * Since: 2.22 |
||
3162 | */ |
||
3163 | gboolean |
||
3164 | g_socket_shutdown (GSocket *socket, |
||
3165 | gboolean shutdown_read, |
||
3166 | gboolean shutdown_write, |
||
3167 | GError **error) |
||
3168 | { |
||
3169 | int how; |
||
3170 | |||
3171 | g_return_val_if_fail (G_IS_SOCKET (socket), TRUE); |
||
3172 | |||
3173 | if (!check_socket (socket, error)) |
||
3174 | return FALSE; |
||
3175 | |||
3176 | /* Do nothing? */ |
||
3177 | if (!shutdown_read && !shutdown_write) |
||
3178 | return TRUE; |
||
3179 | |||
3180 | #ifndef G_OS_WIN32 |
||
3181 | if (shutdown_read && shutdown_write) |
||
3182 | how = SHUT_RDWR; |
||
3183 | else if (shutdown_read) |
||
3184 | how = SHUT_RD; |
||
3185 | else |
||
3186 | how = SHUT_WR; |
||
3187 | #else |
||
3188 | if (shutdown_read && shutdown_write) |
||
3189 | how = SD_BOTH; |
||
3190 | else if (shutdown_read) |
||
3191 | how = SD_RECEIVE; |
||
3192 | else |
||
3193 | how = SD_SEND; |
||
3194 | #endif |
||
3195 | |||
3196 | if (shutdown (socket->priv->fd, how) != 0) |
||
3197 | { |
||
3198 | int errsv = get_socket_errno (); |
||
3199 | g_set_error (error, G_IO_ERROR, socket_io_error_from_errno (errsv), |
||
3200 | _("Unable to shutdown socket: %s"), socket_strerror (errsv)); |
||
3201 | return FALSE; |
||
3202 | } |
||
3203 | |||
3204 | if (shutdown_read) |
||
3205 | socket->priv->connected_read = FALSE; |
||
3206 | if (shutdown_write) |
||
3207 | socket->priv->connected_write = FALSE; |
||
3208 | |||
3209 | return TRUE; |
||
3210 | } |
||
3211 | |||
3212 | /** |
||
3213 | * g_socket_close: |
||
3214 | * @socket: a #GSocket |
||
3215 | * @error: #GError for error reporting, or %NULL to ignore. |
||
3216 | * |
||
3217 | * Closes the socket, shutting down any active connection. |
||
3218 | * |
||
3219 | * Closing a socket does not wait for all outstanding I/O operations |
||
3220 | * to finish, so the caller should not rely on them to be guaranteed |
||
3221 | * to complete even if the close returns with no error. |
||
3222 | * |
||
3223 | * Once the socket is closed, all other operations will return |
||
3224 | * %G_IO_ERROR_CLOSED. Closing a socket multiple times will not |
||
3225 | * return an error. |
||
3226 | * |
||
3227 | * Sockets will be automatically closed when the last reference |
||
3228 | * is dropped, but you might want to call this function to make sure |
||
3229 | * resources are released as early as possible. |
||
3230 | * |
||
3231 | * Beware that due to the way that TCP works, it is possible for |
||
3232 | * recently-sent data to be lost if either you close a socket while the |
||
3233 | * %G_IO_IN condition is set, or else if the remote connection tries to |
||
3234 | * send something to you after you close the socket but before it has |
||
3235 | * finished reading all of the data you sent. There is no easy generic |
||
3236 | * way to avoid this problem; the easiest fix is to design the network |
||
3237 | * protocol such that the client will never send data "out of turn". |
||
3238 | * Another solution is for the server to half-close the connection by |
||
3239 | * calling g_socket_shutdown() with only the @shutdown_write flag set, |
||
3240 | * and then wait for the client to notice this and close its side of the |
||
3241 | * connection, after which the server can safely call g_socket_close(). |
||
3242 | * (This is what #GTcpConnection does if you call |
||
3243 | * g_tcp_connection_set_graceful_disconnect(). But of course, this |
||
3244 | * only works if the client will close its connection after the server |
||
3245 | * does.) |
||
3246 | * |
||
3247 | * Returns: %TRUE on success, %FALSE on error |
||
3248 | * |
||
3249 | * Since: 2.22 |
||
3250 | */ |
||
3251 | gboolean |
||
3252 | g_socket_close (GSocket *socket, |
||
3253 | GError **error) |
||
3254 | { |
||
3255 | int res; |
||
3256 | |||
3257 | g_return_val_if_fail (G_IS_SOCKET (socket), TRUE); |
||
3258 | |||
3259 | if (socket->priv->closed) |
||
3260 | return TRUE; /* Multiple close not an error */ |
||
3261 | |||
3262 | if (!check_socket (socket, error)) |
||
3263 | return FALSE; |
||
3264 | |||
3265 | while (1) |
||
3266 | { |
||
3267 | #ifdef G_OS_WIN32 |
||
3268 | res = closesocket (socket->priv->fd); |
||
3269 | #else |
||
3270 | res = close (socket->priv->fd); |
||
3271 | #endif |
||
3272 | if (res == -1) |
||
3273 | { |
||
3274 | int errsv = get_socket_errno (); |
||
3275 | |||
3276 | if (errsv == EINTR) |
||
3277 | continue; |
||
3278 | |||
3279 | g_set_error (error, G_IO_ERROR, |
||
3280 | socket_io_error_from_errno (errsv), |
||
3281 | _("Error closing socket: %s"), |
||
3282 | socket_strerror (errsv)); |
||
3283 | return FALSE; |
||
3284 | } |
||
3285 | break; |
||
3286 | } |
||
3287 | |||
3288 | socket->priv->fd = -1; |
||
3289 | socket->priv->connected_read = FALSE; |
||
3290 | socket->priv->connected_write = FALSE; |
||
3291 | socket->priv->closed = TRUE; |
||
3292 | if (socket->priv->remote_address) |
||
3293 | { |
||
3294 | g_object_unref (socket->priv->remote_address); |
||
3295 | socket->priv->remote_address = NULL; |
||
3296 | } |
||
3297 | |||
3298 | return TRUE; |
||
3299 | } |
||
3300 | |||
3301 | /** |
||
3302 | * g_socket_is_closed: |
||
3303 | * @socket: a #GSocket |
||
3304 | * |
||
3305 | * Checks whether a socket is closed. |
||
3306 | * |
||
3307 | * Returns: %TRUE if socket is closed, %FALSE otherwise |
||
3308 | * |
||
3309 | * Since: 2.22 |
||
3310 | */ |
||
3311 | gboolean |
||
3312 | g_socket_is_closed (GSocket *socket) |
||
3313 | { |
||
3314 | return socket->priv->closed; |
||
3315 | } |
||
3316 | |||
3317 | #ifdef G_OS_WIN32 |
||
3318 | /* Broken source, used on errors */ |
||
3319 | static gboolean |
||
3320 | broken_dispatch (GSource *source, |
||
3321 | GSourceFunc callback, |
||
3322 | gpointer user_data) |
||
3323 | { |
||
3324 | return TRUE; |
||
3325 | } |
||
3326 | |||
3327 | static GSourceFuncs broken_funcs = |
||
3328 | { |
||
3329 | NULL, |
||
3330 | NULL, |
||
3331 | broken_dispatch, |
||
3332 | NULL |
||
3333 | }; |
||
3334 | |||
3335 | static gint |
||
3336 | network_events_for_condition (GIOCondition condition) |
||
3337 | { |
||
3338 | int event_mask = 0; |
||
3339 | |||
3340 | if (condition & G_IO_IN) |
||
3341 | event_mask |= (FD_READ | FD_ACCEPT); |
||
3342 | if (condition & G_IO_OUT) |
||
3343 | event_mask |= (FD_WRITE | FD_CONNECT); |
||
3344 | event_mask |= FD_CLOSE; |
||
3345 | |||
3346 | return event_mask; |
||
3347 | } |
||
3348 | |||
3349 | static void |
||
3350 | ensure_event (GSocket *socket) |
||
3351 | { |
||
3352 | if (socket->priv->event == WSA_INVALID_EVENT) |
||
3353 | socket->priv->event = WSACreateEvent(); |
||
3354 | } |
||
3355 | |||
3356 | static void |
||
3357 | update_select_events (GSocket *socket) |
||
3358 | { |
||
3359 | int event_mask; |
||
3360 | GIOCondition *ptr; |
||
3361 | GList *l; |
||
3362 | WSAEVENT event; |
||
3363 | |||
3364 | ensure_event (socket); |
||
3365 | |||
3366 | event_mask = 0; |
||
3367 | for (l = socket->priv->requested_conditions; l != NULL; l = l->next) |
||
3368 | { |
||
3369 | ptr = l->data; |
||
3370 | event_mask |= network_events_for_condition (*ptr); |
||
3371 | } |
||
3372 | |||
3373 | if (event_mask != socket->priv->selected_events) |
||
3374 | { |
||
3375 | /* If no events selected, disable event so we can unset |
||
3376 | nonblocking mode */ |
||
3377 | |||
3378 | if (event_mask == 0) |
||
3379 | event = NULL; |
||
3380 | else |
||
3381 | event = socket->priv->event; |
||
3382 | |||
3383 | if (WSAEventSelect (socket->priv->fd, event, event_mask) == 0) |
||
3384 | socket->priv->selected_events = event_mask; |
||
3385 | } |
||
3386 | } |
||
3387 | |||
3388 | static void |
||
3389 | add_condition_watch (GSocket *socket, |
||
3390 | GIOCondition *condition) |
||
3391 | { |
||
3392 | g_mutex_lock (&socket->priv->win32_source_lock); |
||
3393 | g_assert (g_list_find (socket->priv->requested_conditions, condition) == NULL); |
||
3394 | |||
3395 | socket->priv->requested_conditions = |
||
3396 | g_list_prepend (socket->priv->requested_conditions, condition); |
||
3397 | |||
3398 | update_select_events (socket); |
||
3399 | g_mutex_unlock (&socket->priv->win32_source_lock); |
||
3400 | } |
||
3401 | |||
3402 | static void |
||
3403 | remove_condition_watch (GSocket *socket, |
||
3404 | GIOCondition *condition) |
||
3405 | { |
||
3406 | g_mutex_lock (&socket->priv->win32_source_lock); |
||
3407 | g_assert (g_list_find (socket->priv->requested_conditions, condition) != NULL); |
||
3408 | |||
3409 | socket->priv->requested_conditions = |
||
3410 | g_list_remove (socket->priv->requested_conditions, condition); |
||
3411 | |||
3412 | update_select_events (socket); |
||
3413 | g_mutex_unlock (&socket->priv->win32_source_lock); |
||
3414 | } |
||
3415 | |||
3416 | static GIOCondition |
||
3417 | update_condition (GSocket *socket) |
||
3418 | { |
||
3419 | WSANETWORKEVENTS events; |
||
3420 | GIOCondition condition; |
||
3421 | |||
3422 | if (WSAEnumNetworkEvents (socket->priv->fd, |
||
3423 | socket->priv->event, |
||
3424 | &events) == 0) |
||
3425 | { |
||
3426 | socket->priv->current_events |= events.lNetworkEvents; |
||
3427 | if (events.lNetworkEvents & FD_WRITE && |
||
3428 | events.iErrorCode[FD_WRITE_BIT] != 0) |
||
3429 | socket->priv->current_errors |= FD_WRITE; |
||
3430 | if (events.lNetworkEvents & FD_CONNECT && |
||
3431 | events.iErrorCode[FD_CONNECT_BIT] != 0) |
||
3432 | socket->priv->current_errors |= FD_CONNECT; |
||
3433 | } |
||
3434 | |||
3435 | condition = 0; |
||
3436 | if (socket->priv->current_events & (FD_READ | FD_ACCEPT)) |
||
3437 | condition |= G_IO_IN; |
||
3438 | |||
3439 | if (socket->priv->current_events & FD_CLOSE) |
||
3440 | { |
||
3441 | int r, errsv, buffer; |
||
3442 | |||
3443 | r = recv (socket->priv->fd, &buffer, sizeof (buffer), MSG_PEEK); |
||
3444 | if (r < 0) |
||
3445 | errsv = get_socket_errno (); |
||
3446 | |||
3447 | if (r > 0 || |
||
3448 | (r < 0 && errsv == WSAENOTCONN)) |
||
3449 | condition |= G_IO_IN; |
||
3450 | else if (r == 0 || |
||
3451 | (r < 0 && (errsv == WSAESHUTDOWN || errsv == WSAECONNRESET || |
||
3452 | errsv == WSAECONNABORTED || errsv == WSAENETRESET))) |
||
3453 | condition |= G_IO_HUP; |
||
3454 | else |
||
3455 | condition |= G_IO_ERR; |
||
3456 | } |
||
3457 | |||
3458 | if (socket->priv->closed) |
||
3459 | condition |= G_IO_HUP; |
||
3460 | |||
3461 | /* Never report both G_IO_OUT and HUP, these are |
||
3462 | mutually exclusive (can't write to a closed socket) */ |
||
3463 | if ((condition & G_IO_HUP) == 0 && |
||
3464 | socket->priv->current_events & FD_WRITE) |
||
3465 | { |
||
3466 | if (socket->priv->current_errors & FD_WRITE) |
||
3467 | condition |= G_IO_ERR; |
||
3468 | else |
||
3469 | condition |= G_IO_OUT; |
||
3470 | } |
||
3471 | else |
||
3472 | { |
||
3473 | if (socket->priv->current_events & FD_CONNECT) |
||
3474 | { |
||
3475 | if (socket->priv->current_errors & FD_CONNECT) |
||
3476 | condition |= (G_IO_HUP | G_IO_ERR); |
||
3477 | else |
||
3478 | condition |= G_IO_OUT; |
||
3479 | } |
||
3480 | } |
||
3481 | |||
3482 | return condition; |
||
3483 | } |
||
3484 | #endif |
||
3485 | |||
3486 | typedef struct { |
||
3487 | GSource source; |
||
3488 | #ifdef G_OS_WIN32 |
||
3489 | GPollFD pollfd; |
||
3490 | #else |
||
3491 | gpointer fd_tag; |
||
3492 | #endif |
||
3493 | GSocket *socket; |
||
3494 | GIOCondition condition; |
||
3495 | } GSocketSource; |
||
3496 | |||
3497 | #ifdef G_OS_WIN32 |
||
3498 | static gboolean |
||
3499 | socket_source_prepare_win32 (GSource *source, |
||
3500 | gint *timeout) |
||
3501 | { |
||
3502 | GSocketSource *socket_source = (GSocketSource *)source; |
||
3503 | |||
3504 | *timeout = -1; |
||
3505 | |||
3506 | return (update_condition (socket_source->socket) & socket_source->condition) != 0; |
||
3507 | } |
||
3508 | |||
3509 | static gboolean |
||
3510 | socket_source_check_win32 (GSource *source) |
||
3511 | { |
||
3512 | int timeout; |
||
3513 | |||
3514 | return socket_source_prepare_win32 (source, &timeout); |
||
3515 | } |
||
3516 | #endif |
||
3517 | |||
3518 | static gboolean |
||
3519 | socket_source_dispatch (GSource *source, |
||
3520 | GSourceFunc callback, |
||
3521 | gpointer user_data) |
||
3522 | { |
||
3523 | GSocketSourceFunc func = (GSocketSourceFunc)callback; |
||
3524 | GSocketSource *socket_source = (GSocketSource *)source; |
||
3525 | GSocket *socket = socket_source->socket; |
||
3526 | gint64 timeout; |
||
3527 | guint events; |
||
3528 | gboolean ret; |
||
3529 | |||
3530 | #ifdef G_OS_WIN32 |
||
3531 | events = update_condition (socket_source->socket); |
||
3532 | #else |
||
3533 | events = g_source_query_unix_fd (source, socket_source->fd_tag); |
||
3534 | #endif |
||
3535 | |||
3536 | timeout = g_source_get_ready_time (source); |
||
3537 | if (timeout >= 0 && timeout < g_source_get_time (source)) |
||
3538 | { |
||
3539 | socket->priv->timed_out = TRUE; |
||
3540 | events |= (G_IO_IN | G_IO_OUT); |
||
3541 | } |
||
3542 | |||
3543 | ret = (*func) (socket, events & socket_source->condition, user_data); |
||
3544 | |||
3545 | if (socket->priv->timeout) |
||
3546 | g_source_set_ready_time (source, g_get_monotonic_time () + socket->priv->timeout * 1000000); |
||
3547 | else |
||
3548 | g_source_set_ready_time (source, -1); |
||
3549 | |||
3550 | return ret; |
||
3551 | } |
||
3552 | |||
3553 | static void |
||
3554 | socket_source_finalize (GSource *source) |
||
3555 | { |
||
3556 | GSocketSource *socket_source = (GSocketSource *)source; |
||
3557 | GSocket *socket; |
||
3558 | |||
3559 | socket = socket_source->socket; |
||
3560 | |||
3561 | #ifdef G_OS_WIN32 |
||
3562 | remove_condition_watch (socket, &socket_source->condition); |
||
3563 | #endif |
||
3564 | |||
3565 | g_object_unref (socket); |
||
3566 | } |
||
3567 | |||
3568 | static gboolean |
||
3569 | socket_source_closure_callback (GSocket *socket, |
||
3570 | GIOCondition condition, |
||
3571 | gpointer data) |
||
3572 | { |
||
3573 | GClosure *closure = data; |
||
3574 | |||
3575 | GValue params[2] = { G_VALUE_INIT, G_VALUE_INIT }; |
||
3576 | GValue result_value = G_VALUE_INIT; |
||
3577 | gboolean result; |
||
3578 | |||
3579 | g_value_init (&result_value, G_TYPE_BOOLEAN); |
||
3580 | |||
3581 | g_value_init (¶ms[0], G_TYPE_SOCKET); |
||
3582 | g_value_set_object (¶ms[0], socket); |
||
3583 | g_value_init (¶ms[1], G_TYPE_IO_CONDITION); |
||
3584 | g_value_set_flags (¶ms[1], condition); |
||
3585 | |||
3586 | g_closure_invoke (closure, &result_value, 2, params, NULL); |
||
3587 | |||
3588 | result = g_value_get_boolean (&result_value); |
||
3589 | g_value_unset (&result_value); |
||
3590 | g_value_unset (¶ms[0]); |
||
3591 | g_value_unset (¶ms[1]); |
||
3592 | |||
3593 | return result; |
||
3594 | } |
||
3595 | |||
3596 | static GSourceFuncs socket_source_funcs = |
||
3597 | { |
||
3598 | #ifdef G_OS_WIN32 |
||
3599 | socket_source_prepare_win32, |
||
3600 | socket_source_check_win32, |
||
3601 | #else |
||
3602 | NULL, NULL, /* check, prepare */ |
||
3603 | #endif |
||
3604 | socket_source_dispatch, |
||
3605 | socket_source_finalize, |
||
3606 | (GSourceFunc)socket_source_closure_callback, |
||
3607 | }; |
||
3608 | |||
3609 | static GSource * |
||
3610 | socket_source_new (GSocket *socket, |
||
3611 | GIOCondition condition, |
||
3612 | GCancellable *cancellable) |
||
3613 | { |
||
3614 | GSource *source; |
||
3615 | GSocketSource *socket_source; |
||
3616 | |||
3617 | #ifdef G_OS_WIN32 |
||
3618 | ensure_event (socket); |
||
3619 | |||
3620 | if (socket->priv->event == WSA_INVALID_EVENT) |
||
3621 | { |
||
3622 | g_warning ("Failed to create WSAEvent"); |
||
3623 | return g_source_new (&broken_funcs, sizeof (GSource)); |
||
3624 | } |
||
3625 | #endif |
||
3626 | |||
3627 | condition |= G_IO_HUP | G_IO_ERR | G_IO_NVAL; |
||
3628 | |||
3629 | source = g_source_new (&socket_source_funcs, sizeof (GSocketSource)); |
||
3630 | g_source_set_name (source, "GSocket"); |
||
3631 | socket_source = (GSocketSource *)source; |
||
3632 | |||
3633 | socket_source->socket = g_object_ref (socket); |
||
3634 | socket_source->condition = condition; |
||
3635 | |||
3636 | if (cancellable) |
||
3637 | { |
||
3638 | GSource *cancellable_source; |
||
3639 | |||
3640 | cancellable_source = g_cancellable_source_new (cancellable); |
||
3641 | g_source_add_child_source (source, cancellable_source); |
||
3642 | g_source_set_dummy_callback (cancellable_source); |
||
3643 | g_source_unref (cancellable_source); |
||
3644 | } |
||
3645 | |||
3646 | #ifdef G_OS_WIN32 |
||
3647 | add_condition_watch (socket, &socket_source->condition); |
||
3648 | socket_source->pollfd.fd = (gintptr) socket->priv->event; |
||
3649 | socket_source->pollfd.events = condition; |
||
3650 | socket_source->pollfd.revents = 0; |
||
3651 | g_source_add_poll (source, &socket_source->pollfd); |
||
3652 | #else |
||
3653 | socket_source->fd_tag = g_source_add_unix_fd (source, socket->priv->fd, condition); |
||
3654 | #endif |
||
3655 | |||
3656 | if (socket->priv->timeout) |
||
3657 | g_source_set_ready_time (source, g_get_monotonic_time () + socket->priv->timeout * 1000000); |
||
3658 | else |
||
3659 | g_source_set_ready_time (source, -1); |
||
3660 | |||
3661 | return source; |
||
3662 | } |
||
3663 | |||
3664 | /** |
||
3665 | * g_socket_create_source: (skip) |
||
3666 | * @socket: a #GSocket |
||
3667 | * @condition: a #GIOCondition mask to monitor |
||
3668 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
3669 | * |
||
3670 | * Creates a #GSource that can be attached to a %GMainContext to monitor |
||
3671 | * for the availability of the specified @condition on the socket. The #GSource |
||
3672 | * keeps a reference to the @socket. |
||
3673 | * |
||
3674 | * The callback on the source is of the #GSocketSourceFunc type. |
||
3675 | * |
||
3676 | * It is meaningless to specify %G_IO_ERR or %G_IO_HUP in @condition; |
||
3677 | * these conditions will always be reported output if they are true. |
||
3678 | * |
||
3679 | * @cancellable if not %NULL can be used to cancel the source, which will |
||
3680 | * cause the source to trigger, reporting the current condition (which |
||
3681 | * is likely 0 unless cancellation happened at the same time as a |
||
3682 | * condition change). You can check for this in the callback using |
||
3683 | * g_cancellable_is_cancelled(). |
||
3684 | * |
||
3685 | * If @socket has a timeout set, and it is reached before @condition |
||
3686 | * occurs, the source will then trigger anyway, reporting %G_IO_IN or |
||
3687 | * %G_IO_OUT depending on @condition. However, @socket will have been |
||
3688 | * marked as having had a timeout, and so the next #GSocket I/O method |
||
3689 | * you call will then fail with a %G_IO_ERROR_TIMED_OUT. |
||
3690 | * |
||
3691 | * Returns: (transfer full): a newly allocated %GSource, free with g_source_unref(). |
||
3692 | * |
||
3693 | * Since: 2.22 |
||
3694 | */ |
||
3695 | GSource * |
||
3696 | g_socket_create_source (GSocket *socket, |
||
3697 | GIOCondition condition, |
||
3698 | GCancellable *cancellable) |
||
3699 | { |
||
3700 | g_return_val_if_fail (G_IS_SOCKET (socket) && (cancellable == NULL || G_IS_CANCELLABLE (cancellable)), NULL); |
||
3701 | |||
3702 | return socket_source_new (socket, condition, cancellable); |
||
3703 | } |
||
3704 | |||
3705 | /** |
||
3706 | * g_socket_condition_check: |
||
3707 | * @socket: a #GSocket |
||
3708 | * @condition: a #GIOCondition mask to check |
||
3709 | * |
||
3710 | * Checks on the readiness of @socket to perform operations. |
||
3711 | * The operations specified in @condition are checked for and masked |
||
3712 | * against the currently-satisfied conditions on @socket. The result |
||
3713 | * is returned. |
||
3714 | * |
||
3715 | * Note that on Windows, it is possible for an operation to return |
||
3716 | * %G_IO_ERROR_WOULD_BLOCK even immediately after |
||
3717 | * g_socket_condition_check() has claimed that the socket is ready for |
||
3718 | * writing. Rather than calling g_socket_condition_check() and then |
||
3719 | * writing to the socket if it succeeds, it is generally better to |
||
3720 | * simply try writing to the socket right away, and try again later if |
||
3721 | * the initial attempt returns %G_IO_ERROR_WOULD_BLOCK. |
||
3722 | * |
||
3723 | * It is meaningless to specify %G_IO_ERR or %G_IO_HUP in condition; |
||
3724 | * these conditions will always be set in the output if they are true. |
||
3725 | * |
||
3726 | * This call never blocks. |
||
3727 | * |
||
3728 | * Returns: the @GIOCondition mask of the current state |
||
3729 | * |
||
3730 | * Since: 2.22 |
||
3731 | */ |
||
3732 | GIOCondition |
||
3733 | g_socket_condition_check (GSocket *socket, |
||
3734 | GIOCondition condition) |
||
3735 | { |
||
3736 | g_return_val_if_fail (G_IS_SOCKET (socket), 0); |
||
3737 | |||
3738 | if (!check_socket (socket, NULL)) |
||
3739 | return 0; |
||
3740 | |||
3741 | #ifdef G_OS_WIN32 |
||
3742 | { |
||
3743 | GIOCondition current_condition; |
||
3744 | |||
3745 | condition |= G_IO_ERR | G_IO_HUP; |
||
3746 | |||
3747 | add_condition_watch (socket, &condition); |
||
3748 | current_condition = update_condition (socket); |
||
3749 | remove_condition_watch (socket, &condition); |
||
3750 | return condition & current_condition; |
||
3751 | } |
||
3752 | #else |
||
3753 | { |
||
3754 | GPollFD poll_fd; |
||
3755 | gint result; |
||
3756 | poll_fd.fd = socket->priv->fd; |
||
3757 | poll_fd.events = condition; |
||
3758 | poll_fd.revents = 0; |
||
3759 | |||
3760 | do |
||
3761 | result = g_poll (&poll_fd, 1, 0); |
||
3762 | while (result == -1 && get_socket_errno () == EINTR); |
||
3763 | |||
3764 | return poll_fd.revents; |
||
3765 | } |
||
3766 | #endif |
||
3767 | } |
||
3768 | |||
3769 | /** |
||
3770 | * g_socket_condition_wait: |
||
3771 | * @socket: a #GSocket |
||
3772 | * @condition: a #GIOCondition mask to wait for |
||
3773 | * @cancellable: (allow-none): a #GCancellable, or %NULL |
||
3774 | * @error: a #GError pointer, or %NULL |
||
3775 | * |
||
3776 | * Waits for @condition to become true on @socket. When the condition |
||
3777 | * is met, %TRUE is returned. |
||
3778 | * |
||
3779 | * If @cancellable is cancelled before the condition is met, or if the |
||
3780 | * socket has a timeout set and it is reached before the condition is |
||
3781 | * met, then %FALSE is returned and @error, if non-%NULL, is set to |
||
3782 | * the appropriate value (%G_IO_ERROR_CANCELLED or |
||
3783 | * %G_IO_ERROR_TIMED_OUT). |
||
3784 | * |
||
3785 | * See also g_socket_condition_timed_wait(). |
||
3786 | * |
||
3787 | * Returns: %TRUE if the condition was met, %FALSE otherwise |
||
3788 | * |
||
3789 | * Since: 2.22 |
||
3790 | */ |
||
3791 | gboolean |
||
3792 | g_socket_condition_wait (GSocket *socket, |
||
3793 | GIOCondition condition, |
||
3794 | GCancellable *cancellable, |
||
3795 | GError **error) |
||
3796 | { |
||
3797 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
3798 | |||
3799 | return g_socket_condition_timed_wait (socket, condition, -1, |
||
3800 | cancellable, error); |
||
3801 | } |
||
3802 | |||
3803 | /** |
||
3804 | * g_socket_condition_timed_wait: |
||
3805 | * @socket: a #GSocket |
||
3806 | * @condition: a #GIOCondition mask to wait for |
||
3807 | * @timeout: the maximum time (in microseconds) to wait, or -1 |
||
3808 | * @cancellable: (allow-none): a #GCancellable, or %NULL |
||
3809 | * @error: a #GError pointer, or %NULL |
||
3810 | * |
||
3811 | * Waits for up to @timeout microseconds for @condition to become true |
||
3812 | * on @socket. If the condition is met, %TRUE is returned. |
||
3813 | * |
||
3814 | * If @cancellable is cancelled before the condition is met, or if |
||
3815 | * @timeout (or the socket's #GSocket:timeout) is reached before the |
||
3816 | * condition is met, then %FALSE is returned and @error, if non-%NULL, |
||
3817 | * is set to the appropriate value (%G_IO_ERROR_CANCELLED or |
||
3818 | * %G_IO_ERROR_TIMED_OUT). |
||
3819 | * |
||
3820 | * If you don't want a timeout, use g_socket_condition_wait(). |
||
3821 | * (Alternatively, you can pass -1 for @timeout.) |
||
3822 | * |
||
3823 | * Note that although @timeout is in microseconds for consistency with |
||
3824 | * other GLib APIs, this function actually only has millisecond |
||
3825 | * resolution, and the behavior is undefined if @timeout is not an |
||
3826 | * exact number of milliseconds. |
||
3827 | * |
||
3828 | * Returns: %TRUE if the condition was met, %FALSE otherwise |
||
3829 | * |
||
3830 | * Since: 2.32 |
||
3831 | */ |
||
3832 | gboolean |
||
3833 | g_socket_condition_timed_wait (GSocket *socket, |
||
3834 | GIOCondition condition, |
||
3835 | gint64 timeout, |
||
3836 | GCancellable *cancellable, |
||
3837 | GError **error) |
||
3838 | { |
||
3839 | gint64 start_time; |
||
3840 | |||
3841 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
3842 | |||
3843 | if (!check_socket (socket, error)) |
||
3844 | return FALSE; |
||
3845 | |||
3846 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
3847 | return FALSE; |
||
3848 | |||
3849 | if (socket->priv->timeout && |
||
3850 | (timeout < 0 || socket->priv->timeout < timeout / G_USEC_PER_SEC)) |
||
3851 | timeout = socket->priv->timeout * 1000; |
||
3852 | else if (timeout != -1) |
||
3853 | timeout = timeout / 1000; |
||
3854 | |||
3855 | start_time = g_get_monotonic_time (); |
||
3856 | |||
3857 | #ifdef G_OS_WIN32 |
||
3858 | { |
||
3859 | GIOCondition current_condition; |
||
3860 | WSAEVENT events[2]; |
||
3861 | DWORD res; |
||
3862 | GPollFD cancel_fd; |
||
3863 | int num_events; |
||
3864 | |||
3865 | /* Always check these */ |
||
3866 | condition |= G_IO_ERR | G_IO_HUP; |
||
3867 | |||
3868 | add_condition_watch (socket, &condition); |
||
3869 | |||
3870 | num_events = 0; |
||
3871 | events[num_events++] = socket->priv->event; |
||
3872 | |||
3873 | if (g_cancellable_make_pollfd (cancellable, &cancel_fd)) |
||
3874 | events[num_events++] = (WSAEVENT)cancel_fd.fd; |
||
3875 | |||
3876 | if (timeout == -1) |
||
3877 | timeout = WSA_INFINITE; |
||
3878 | |||
3879 | current_condition = update_condition (socket); |
||
3880 | while ((condition & current_condition) == 0) |
||
3881 | { |
||
3882 | res = WSAWaitForMultipleEvents (num_events, events, |
||
3883 | FALSE, timeout, FALSE); |
||
3884 | if (res == WSA_WAIT_FAILED) |
||
3885 | { |
||
3886 | int errsv = get_socket_errno (); |
||
3887 | |||
3888 | g_set_error (error, G_IO_ERROR, |
||
3889 | socket_io_error_from_errno (errsv), |
||
3890 | _("Waiting for socket condition: %s"), |
||
3891 | socket_strerror (errsv)); |
||
3892 | break; |
||
3893 | } |
||
3894 | else if (res == WSA_WAIT_TIMEOUT) |
||
3895 | { |
||
3896 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_TIMED_OUT, |
||
3897 | _("Socket I/O timed out")); |
||
3898 | break; |
||
3899 | } |
||
3900 | |||
3901 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
3902 | break; |
||
3903 | |||
3904 | current_condition = update_condition (socket); |
||
3905 | |||
3906 | if (timeout != WSA_INFINITE) |
||
3907 | { |
||
3908 | timeout -= (g_get_monotonic_time () - start_time) * 1000; |
||
3909 | if (timeout < 0) |
||
3910 | timeout = 0; |
||
3911 | } |
||
3912 | } |
||
3913 | remove_condition_watch (socket, &condition); |
||
3914 | if (num_events > 1) |
||
3915 | g_cancellable_release_fd (cancellable); |
||
3916 | |||
3917 | return (condition & current_condition) != 0; |
||
3918 | } |
||
3919 | #else |
||
3920 | { |
||
3921 | GPollFD poll_fd[2]; |
||
3922 | gint result; |
||
3923 | gint num; |
||
3924 | |||
3925 | poll_fd[0].fd = socket->priv->fd; |
||
3926 | poll_fd[0].events = condition; |
||
3927 | num = 1; |
||
3928 | |||
3929 | if (g_cancellable_make_pollfd (cancellable, &poll_fd[1])) |
||
3930 | num++; |
||
3931 | |||
3932 | while (TRUE) |
||
3933 | { |
||
3934 | result = g_poll (poll_fd, num, timeout); |
||
3935 | if (result != -1 || errno != EINTR) |
||
3936 | break; |
||
3937 | |||
3938 | if (timeout != -1) |
||
3939 | { |
||
3940 | timeout -= (g_get_monotonic_time () - start_time) / 1000; |
||
3941 | if (timeout < 0) |
||
3942 | timeout = 0; |
||
3943 | } |
||
3944 | } |
||
3945 | |||
3946 | if (num > 1) |
||
3947 | g_cancellable_release_fd (cancellable); |
||
3948 | |||
3949 | if (result == 0) |
||
3950 | { |
||
3951 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_TIMED_OUT, |
||
3952 | _("Socket I/O timed out")); |
||
3953 | return FALSE; |
||
3954 | } |
||
3955 | |||
3956 | return !g_cancellable_set_error_if_cancelled (cancellable, error); |
||
3957 | } |
||
3958 | #endif |
||
3959 | } |
||
3960 | |||
3961 | #ifndef G_OS_WIN32 |
||
3962 | |||
3963 | /* Unfortunately these have to be macros rather than inline functions due to |
||
3964 | * using alloca(). */ |
||
3965 | #define output_message_to_msghdr(message, prev_message, msg, prev_msg, error) \ |
||
3966 | G_STMT_START { \ |
||
3967 | const GOutputMessage *_message = (message); \ |
||
3968 | const GOutputMessage *_prev_message = (prev_message); \ |
||
3969 | struct msghdr *_msg = (msg); \ |
||
3970 | const struct msghdr *_prev_msg = (prev_msg); \ |
||
3971 | GError **_error = (error); \ |
||
3972 | \ |
||
3973 | _msg->msg_flags = 0; \ |
||
3974 | \ |
||
3975 | /* name */ \ |
||
3976 | if (_prev_message != NULL && _prev_message->address == _message->address) \ |
||
3977 | { \ |
||
3978 | _msg->msg_name = _prev_msg->msg_name; \ |
||
3979 | _msg->msg_namelen = _prev_msg->msg_namelen; \ |
||
3980 | } \ |
||
3981 | else if (_message->address != NULL) \ |
||
3982 | { \ |
||
3983 | _msg->msg_namelen = g_socket_address_get_native_size (_message->address); \ |
||
3984 | _msg->msg_name = g_alloca (_msg->msg_namelen); \ |
||
3985 | if (!g_socket_address_to_native (_message->address, _msg->msg_name, \ |
||
3986 | _msg->msg_namelen, _error)) \ |
||
3987 | break; \ |
||
3988 | } \ |
||
3989 | else \ |
||
3990 | { \ |
||
3991 | _msg->msg_name = NULL; \ |
||
3992 | _msg->msg_namelen = 0; \ |
||
3993 | } \ |
||
3994 | \ |
||
3995 | /* iov */ \ |
||
3996 | { \ |
||
3997 | /* this entire expression will be evaluated at compile time */ \ |
||
3998 | if (sizeof *_msg->msg_iov == sizeof *_message->vectors && \ |
||
3999 | sizeof _msg->msg_iov->iov_base == sizeof _message->vectors->buffer && \ |
||
4000 | G_STRUCT_OFFSET (struct iovec, iov_base) == \ |
||
4001 | G_STRUCT_OFFSET (GOutputVector, buffer) && \ |
||
4002 | sizeof _msg->msg_iov->iov_len == sizeof _message->vectors->size && \ |
||
4003 | G_STRUCT_OFFSET (struct iovec, iov_len) == \ |
||
4004 | G_STRUCT_OFFSET (GOutputVector, size)) \ |
||
4005 | /* ABI is compatible */ \ |
||
4006 | { \ |
||
4007 | _msg->msg_iov = (struct iovec *) _message->vectors; \ |
||
4008 | _msg->msg_iovlen = _message->num_vectors; \ |
||
4009 | } \ |
||
4010 | else \ |
||
4011 | /* ABI is incompatible */ \ |
||
4012 | { \ |
||
4013 | gint i; \ |
||
4014 | \ |
||
4015 | _msg->msg_iov = g_newa (struct iovec, _message->num_vectors); \ |
||
4016 | for (i = 0; i < _message->num_vectors; i++) \ |
||
4017 | { \ |
||
4018 | _msg->msg_iov[i].iov_base = (void *) _message->vectors[i].buffer; \ |
||
4019 | _msg->msg_iov[i].iov_len = _message->vectors[i].size; \ |
||
4020 | } \ |
||
4021 | _msg->msg_iovlen = _message->num_vectors; \ |
||
4022 | } \ |
||
4023 | } \ |
||
4024 | \ |
||
4025 | /* control */ \ |
||
4026 | { \ |
||
4027 | struct cmsghdr *cmsg; \ |
||
4028 | gint i; \ |
||
4029 | \ |
||
4030 | _msg->msg_controllen = 0; \ |
||
4031 | for (i = 0; i < _message->num_control_messages; i++) \ |
||
4032 | _msg->msg_controllen += CMSG_SPACE (g_socket_control_message_get_size (_message->control_messages[i])); \ |
||
4033 | \ |
||
4034 | if (_msg->msg_controllen == 0) \ |
||
4035 | _msg->msg_control = NULL; \ |
||
4036 | else \ |
||
4037 | { \ |
||
4038 | _msg->msg_control = g_alloca (_msg->msg_controllen); \ |
||
4039 | memset (_msg->msg_control, '\0', _msg->msg_controllen); \ |
||
4040 | } \ |
||
4041 | \ |
||
4042 | cmsg = CMSG_FIRSTHDR (_msg); \ |
||
4043 | for (i = 0; i < _message->num_control_messages; i++) \ |
||
4044 | { \ |
||
4045 | cmsg->cmsg_level = g_socket_control_message_get_level (_message->control_messages[i]); \ |
||
4046 | cmsg->cmsg_type = g_socket_control_message_get_msg_type (_message->control_messages[i]); \ |
||
4047 | cmsg->cmsg_len = CMSG_LEN (g_socket_control_message_get_size (_message->control_messages[i])); \ |
||
4048 | g_socket_control_message_serialize (_message->control_messages[i], \ |
||
4049 | CMSG_DATA (cmsg)); \ |
||
4050 | cmsg = CMSG_NXTHDR (_msg, cmsg); \ |
||
4051 | } \ |
||
4052 | g_assert (cmsg == NULL); \ |
||
4053 | } \ |
||
4054 | } G_STMT_END |
||
4055 | |||
4056 | #define input_message_to_msghdr(message, msg) \ |
||
4057 | G_STMT_START { \ |
||
4058 | const GInputMessage *_message = (message); \ |
||
4059 | struct msghdr *_msg = (msg); \ |
||
4060 | \ |
||
4061 | /* name */ \ |
||
4062 | if (_message->address) \ |
||
4063 | { \ |
||
4064 | _msg->msg_namelen = sizeof (struct sockaddr_storage); \ |
||
4065 | _msg->msg_name = g_alloca (_msg->msg_namelen); \ |
||
4066 | } \ |
||
4067 | else \ |
||
4068 | { \ |
||
4069 | _msg->msg_name = NULL; \ |
||
4070 | _msg->msg_namelen = 0; \ |
||
4071 | } \ |
||
4072 | \ |
||
4073 | /* iov */ \ |
||
4074 | /* this entire expression will be evaluated at compile time */ \ |
||
4075 | if (sizeof *_msg->msg_iov == sizeof *_message->vectors && \ |
||
4076 | sizeof _msg->msg_iov->iov_base == sizeof _message->vectors->buffer && \ |
||
4077 | G_STRUCT_OFFSET (struct iovec, iov_base) == \ |
||
4078 | G_STRUCT_OFFSET (GInputVector, buffer) && \ |
||
4079 | sizeof _msg->msg_iov->iov_len == sizeof _message->vectors->size && \ |
||
4080 | G_STRUCT_OFFSET (struct iovec, iov_len) == \ |
||
4081 | G_STRUCT_OFFSET (GInputVector, size)) \ |
||
4082 | /* ABI is compatible */ \ |
||
4083 | { \ |
||
4084 | _msg->msg_iov = (struct iovec *) _message->vectors; \ |
||
4085 | _msg->msg_iovlen = _message->num_vectors; \ |
||
4086 | } \ |
||
4087 | else \ |
||
4088 | /* ABI is incompatible */ \ |
||
4089 | { \ |
||
4090 | guint i; \ |
||
4091 | \ |
||
4092 | _msg->msg_iov = g_newa (struct iovec, _message->num_vectors); \ |
||
4093 | for (i = 0; i < _message->num_vectors; i++) \ |
||
4094 | { \ |
||
4095 | _msg->msg_iov[i].iov_base = _message->vectors[i].buffer; \ |
||
4096 | _msg->msg_iov[i].iov_len = _message->vectors[i].size; \ |
||
4097 | } \ |
||
4098 | _msg->msg_iovlen = _message->num_vectors; \ |
||
4099 | } \ |
||
4100 | \ |
||
4101 | /* control */ \ |
||
4102 | _msg->msg_controllen = 2048; \ |
||
4103 | _msg->msg_control = g_alloca (_msg->msg_controllen); \ |
||
4104 | \ |
||
4105 | /* flags */ \ |
||
4106 | _msg->msg_flags = _message->flags; \ |
||
4107 | } G_STMT_END |
||
4108 | |||
4109 | static void |
||
4110 | input_message_from_msghdr (const struct msghdr *msg, |
||
4111 | GInputMessage *message, |
||
4112 | GSocket *socket) |
||
4113 | { |
||
4114 | /* decode address */ |
||
4115 | if (message->address != NULL) |
||
4116 | { |
||
4117 | *message->address = cache_recv_address (socket, msg->msg_name, |
||
4118 | msg->msg_namelen); |
||
4119 | } |
||
4120 | |||
4121 | /* decode control messages */ |
||
4122 | { |
||
4123 | GPtrArray *my_messages = NULL; |
||
4124 | struct cmsghdr *cmsg; |
||
4125 | |||
4126 | if (msg->msg_controllen >= sizeof (struct cmsghdr)) |
||
4127 | { |
||
4128 | for (cmsg = CMSG_FIRSTHDR (msg); |
||
4129 | cmsg != NULL; |
||
4130 | cmsg = CMSG_NXTHDR ((struct msghdr *) msg, cmsg)) |
||
4131 | { |
||
4132 | GSocketControlMessage *control_message; |
||
4133 | |||
4134 | control_message = g_socket_control_message_deserialize (cmsg->cmsg_level, |
||
4135 | cmsg->cmsg_type, |
||
4136 | cmsg->cmsg_len - ((char *)CMSG_DATA (cmsg) - (char *)cmsg), |
||
4137 | CMSG_DATA (cmsg)); |
||
4138 | if (control_message == NULL) |
||
4139 | /* We've already spewed about the problem in the |
||
4140 | deserialization code, so just continue */ |
||
4141 | continue; |
||
4142 | |||
4143 | if (message->control_messages == NULL) |
||
4144 | { |
||
4145 | /* we have to do it this way if the user ignores the |
||
4146 | * messages so that we will close any received fds. |
||
4147 | */ |
||
4148 | g_object_unref (control_message); |
||
4149 | } |
||
4150 | else |
||
4151 | { |
||
4152 | if (my_messages == NULL) |
||
4153 | my_messages = g_ptr_array_new (); |
||
4154 | g_ptr_array_add (my_messages, control_message); |
||
4155 | } |
||
4156 | } |
||
4157 | } |
||
4158 | |||
4159 | if (message->num_control_messages) |
||
4160 | *message->num_control_messages = my_messages != NULL ? my_messages->len : 0; |
||
4161 | |||
4162 | if (message->control_messages) |
||
4163 | { |
||
4164 | if (my_messages == NULL) |
||
4165 | { |
||
4166 | *message->control_messages = NULL; |
||
4167 | } |
||
4168 | else |
||
4169 | { |
||
4170 | g_ptr_array_add (my_messages, NULL); |
||
4171 | *message->control_messages = (GSocketControlMessage **) g_ptr_array_free (my_messages, FALSE); |
||
4172 | } |
||
4173 | } |
||
4174 | else |
||
4175 | { |
||
4176 | g_assert (my_messages == NULL); |
||
4177 | } |
||
4178 | } |
||
4179 | |||
4180 | /* capture the flags */ |
||
4181 | message->flags = msg->msg_flags; |
||
4182 | } |
||
4183 | #endif |
||
4184 | |||
4185 | /** |
||
4186 | * g_socket_send_message: |
||
4187 | * @socket: a #GSocket |
||
4188 | * @address: (allow-none): a #GSocketAddress, or %NULL |
||
4189 | * @vectors: (array length=num_vectors): an array of #GOutputVector structs |
||
4190 | * @num_vectors: the number of elements in @vectors, or -1 |
||
4191 | * @messages: (array length=num_messages) (allow-none): a pointer to an |
||
4192 | * array of #GSocketControlMessages, or %NULL. |
||
4193 | * @num_messages: number of elements in @messages, or -1. |
||
4194 | * @flags: an int containing #GSocketMsgFlags flags |
||
4195 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
4196 | * @error: #GError for error reporting, or %NULL to ignore. |
||
4197 | * |
||
4198 | * Send data to @address on @socket. For sending multiple messages see |
||
4199 | * g_socket_send_messages(); for easier use, see |
||
4200 | * g_socket_send() and g_socket_send_to(). |
||
4201 | * |
||
4202 | * If @address is %NULL then the message is sent to the default receiver |
||
4203 | * (set by g_socket_connect()). |
||
4204 | * |
||
4205 | * @vectors must point to an array of #GOutputVector structs and |
||
4206 | * @num_vectors must be the length of this array. (If @num_vectors is -1, |
||
4207 | * then @vectors is assumed to be terminated by a #GOutputVector with a |
||
4208 | * %NULL buffer pointer.) The #GOutputVector structs describe the buffers |
||
4209 | * that the sent data will be gathered from. Using multiple |
||
4210 | * #GOutputVectors is more memory-efficient than manually copying |
||
4211 | * data from multiple sources into a single buffer, and more |
||
4212 | * network-efficient than making multiple calls to g_socket_send(). |
||
4213 | * |
||
4214 | * @messages, if non-%NULL, is taken to point to an array of @num_messages |
||
4215 | * #GSocketControlMessage instances. These correspond to the control |
||
4216 | * messages to be sent on the socket. |
||
4217 | * If @num_messages is -1 then @messages is treated as a %NULL-terminated |
||
4218 | * array. |
||
4219 | * |
||
4220 | * @flags modify how the message is sent. The commonly available arguments |
||
4221 | * for this are available in the #GSocketMsgFlags enum, but the |
||
4222 | * values there are the same as the system values, and the flags |
||
4223 | * are passed in as-is, so you can pass in system-specific flags too. |
||
4224 | * |
||
4225 | * If the socket is in blocking mode the call will block until there is |
||
4226 | * space for the data in the socket queue. If there is no space available |
||
4227 | * and the socket is in non-blocking mode a %G_IO_ERROR_WOULD_BLOCK error |
||
4228 | * will be returned. To be notified when space is available, wait for the |
||
4229 | * %G_IO_OUT condition. Note though that you may still receive |
||
4230 | * %G_IO_ERROR_WOULD_BLOCK from g_socket_send() even if you were previously |
||
4231 | * notified of a %G_IO_OUT condition. (On Windows in particular, this is |
||
4232 | * very common due to the way the underlying APIs work.) |
||
4233 | * |
||
4234 | * On error -1 is returned and @error is set accordingly. |
||
4235 | * |
||
4236 | * Returns: Number of bytes written (which may be less than @size), or -1 |
||
4237 | * on error |
||
4238 | * |
||
4239 | * Since: 2.22 |
||
4240 | */ |
||
4241 | gssize |
||
4242 | g_socket_send_message (GSocket *socket, |
||
4243 | GSocketAddress *address, |
||
4244 | GOutputVector *vectors, |
||
4245 | gint num_vectors, |
||
4246 | GSocketControlMessage **messages, |
||
4247 | gint num_messages, |
||
4248 | gint flags, |
||
4249 | GCancellable *cancellable, |
||
4250 | GError **error) |
||
4251 | { |
||
4252 | return g_socket_send_message_with_timeout (socket, address, |
||
4253 | vectors, num_vectors, |
||
4254 | messages, num_messages, flags, |
||
4255 | socket->priv->blocking ? -1 : 0, |
||
4256 | cancellable, error); |
||
4257 | } |
||
4258 | |||
4259 | static gssize |
||
4260 | g_socket_send_message_with_timeout (GSocket *socket, |
||
4261 | GSocketAddress *address, |
||
4262 | GOutputVector *vectors, |
||
4263 | gint num_vectors, |
||
4264 | GSocketControlMessage **messages, |
||
4265 | gint num_messages, |
||
4266 | gint flags, |
||
4267 | gint64 timeout, |
||
4268 | GCancellable *cancellable, |
||
4269 | GError **error) |
||
4270 | { |
||
4271 | GOutputVector one_vector; |
||
4272 | char zero; |
||
4273 | gint64 start_time; |
||
4274 | |||
4275 | g_return_val_if_fail (G_IS_SOCKET (socket), -1); |
||
4276 | g_return_val_if_fail (address == NULL || G_IS_SOCKET_ADDRESS (address), -1); |
||
4277 | g_return_val_if_fail (num_vectors == 0 || vectors != NULL, -1); |
||
4278 | g_return_val_if_fail (num_messages == 0 || messages != NULL, -1); |
||
4279 | g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), -1); |
||
4280 | g_return_val_if_fail (error == NULL || *error == NULL, -1); |
||
4281 | |||
4282 | start_time = g_get_monotonic_time (); |
||
4283 | |||
4284 | if (!check_socket (socket, error)) |
||
4285 | return -1; |
||
4286 | |||
4287 | if (!check_timeout (socket, error)) |
||
4288 | return -1; |
||
4289 | |||
4290 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
4291 | return -1; |
||
4292 | |||
4293 | if (num_vectors == -1) |
||
4294 | { |
||
4295 | for (num_vectors = 0; |
||
4296 | vectors[num_vectors].buffer != NULL; |
||
4297 | num_vectors++) |
||
4298 | ; |
||
4299 | } |
||
4300 | |||
4301 | if (num_messages == -1) |
||
4302 | { |
||
4303 | for (num_messages = 0; |
||
4304 | messages != NULL && messages[num_messages] != NULL; |
||
4305 | num_messages++) |
||
4306 | ; |
||
4307 | } |
||
4308 | |||
4309 | if (num_vectors == 0) |
||
4310 | { |
||
4311 | zero = '\0'; |
||
4312 | |||
4313 | one_vector.buffer = &zero; |
||
4314 | one_vector.size = 1; |
||
4315 | num_vectors = 1; |
||
4316 | vectors = &one_vector; |
||
4317 | } |
||
4318 | |||
4319 | #ifndef G_OS_WIN32 |
||
4320 | { |
||
4321 | GOutputMessage output_message; |
||
4322 | struct msghdr msg; |
||
4323 | gssize result; |
||
4324 | GError *child_error = NULL; |
||
4325 | |||
4326 | output_message.address = address; |
||
4327 | output_message.vectors = vectors; |
||
4328 | output_message.num_vectors = num_vectors; |
||
4329 | output_message.bytes_sent = 0; |
||
4330 | output_message.control_messages = messages; |
||
4331 | output_message.num_control_messages = num_messages; |
||
4332 | |||
4333 | output_message_to_msghdr (&output_message, NULL, &msg, NULL, &child_error); |
||
4334 | |||
4335 | if (child_error != NULL) |
||
4336 | { |
||
4337 | g_propagate_error (error, child_error); |
||
4338 | return -1; |
||
4339 | } |
||
4340 | |||
4341 | while (1) |
||
4342 | { |
||
4343 | result = sendmsg (socket->priv->fd, &msg, flags | G_SOCKET_DEFAULT_SEND_FLAGS); |
||
4344 | if (result < 0) |
||
4345 | { |
||
4346 | int errsv = get_socket_errno (); |
||
4347 | |||
4348 | if (errsv == EINTR) |
||
4349 | continue; |
||
4350 | |||
4351 | if (timeout != 0 && |
||
4352 | (errsv == EWOULDBLOCK || |
||
4353 | errsv == EAGAIN)) |
||
4354 | { |
||
4355 | if (!block_on_timeout (socket, G_IO_OUT, timeout, start_time, |
||
4356 | cancellable, error)) |
||
4357 | return -1; |
||
4358 | |||
4359 | continue; |
||
4360 | } |
||
4361 | |||
4362 | socket_set_error_lazy (error, errsv, _("Error sending message: %s")); |
||
4363 | return -1; |
||
4364 | } |
||
4365 | break; |
||
4366 | } |
||
4367 | |||
4368 | return result; |
||
4369 | } |
||
4370 | #else |
||
4371 | { |
||
4372 | struct sockaddr_storage addr; |
||
4373 | guint addrlen; |
||
4374 | DWORD bytes_sent; |
||
4375 | int result; |
||
4376 | WSABUF *bufs; |
||
4377 | gint i; |
||
4378 | |||
4379 | /* Win32 doesn't support control messages. |
||
4380 | Actually this is possible for raw and datagram sockets |
||
4381 | via WSASendMessage on Vista or later, but that doesn't |
||
4382 | seem very useful */ |
||
4383 | if (num_messages != 0) |
||
4384 | { |
||
4385 | g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, |
||
4386 | _("GSocketControlMessage not supported on Windows")); |
||
4387 | return -1; |
||
4388 | } |
||
4389 | |||
4390 | /* iov */ |
||
4391 | bufs = g_newa (WSABUF, num_vectors); |
||
4392 | for (i = 0; i < num_vectors; i++) |
||
4393 | { |
||
4394 | bufs[i].buf = (char *)vectors[i].buffer; |
||
4395 | bufs[i].len = (gulong)vectors[i].size; |
||
4396 | } |
||
4397 | |||
4398 | /* name */ |
||
4399 | addrlen = 0; /* Avoid warning */ |
||
4400 | if (address) |
||
4401 | { |
||
4402 | addrlen = g_socket_address_get_native_size (address); |
||
4403 | if (!g_socket_address_to_native (address, &addr, sizeof addr, error)) |
||
4404 | return -1; |
||
4405 | } |
||
4406 | |||
4407 | while (1) |
||
4408 | { |
||
4409 | if (address) |
||
4410 | result = WSASendTo (socket->priv->fd, |
||
4411 | bufs, num_vectors, |
||
4412 | &bytes_sent, flags, |
||
4413 | (const struct sockaddr *)&addr, addrlen, |
||
4414 | NULL, NULL); |
||
4415 | else |
||
4416 | result = WSASend (socket->priv->fd, |
||
4417 | bufs, num_vectors, |
||
4418 | &bytes_sent, flags, |
||
4419 | NULL, NULL); |
||
4420 | |||
4421 | if (result != 0) |
||
4422 | { |
||
4423 | int errsv = get_socket_errno (); |
||
4424 | |||
4425 | if (errsv == WSAEINTR) |
||
4426 | continue; |
||
4427 | |||
4428 | if (errsv == WSAEWOULDBLOCK) |
||
4429 | { |
||
4430 | win32_unset_event_mask (socket, FD_WRITE); |
||
4431 | |||
4432 | if (timeout != 0) |
||
4433 | { |
||
4434 | if (!block_on_timeout (socket, G_IO_OUT, timeout, |
||
4435 | start_time, cancellable, error)) |
||
4436 | return -1; |
||
4437 | |||
4438 | continue; |
||
4439 | } |
||
4440 | } |
||
4441 | |||
4442 | socket_set_error_lazy (error, errsv, _("Error sending message: %s")); |
||
4443 | return -1; |
||
4444 | } |
||
4445 | break; |
||
4446 | } |
||
4447 | |||
4448 | return bytes_sent; |
||
4449 | } |
||
4450 | #endif |
||
4451 | } |
||
4452 | |||
4453 | /** |
||
4454 | * g_socket_send_messages: |
||
4455 | * @socket: a #GSocket |
||
4456 | * @messages: (array length=num_messages): an array of #GOutputMessage structs |
||
4457 | * @num_messages: the number of elements in @messages |
||
4458 | * @flags: an int containing #GSocketMsgFlags flags |
||
4459 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
4460 | * @error: #GError for error reporting, or %NULL to ignore. |
||
4461 | * |
||
4462 | * Send multiple data messages from @socket in one go. This is the most |
||
4463 | * complicated and fully-featured version of this call. For easier use, see |
||
4464 | * g_socket_send(), g_socket_send_to(), and g_socket_send_message(). |
||
4465 | * |
||
4466 | * @messages must point to an array of #GOutputMessage structs and |
||
4467 | * @num_messages must be the length of this array. Each #GOutputMessage |
||
4468 | * contains an address to send the data to, and a pointer to an array of |
||
4469 | * #GOutputVector structs to describe the buffers that the data to be sent |
||
4470 | * for each message will be gathered from. Using multiple #GOutputVectors is |
||
4471 | * more memory-efficient than manually copying data from multiple sources |
||
4472 | * into a single buffer, and more network-efficient than making multiple |
||
4473 | * calls to g_socket_send(). Sending multiple messages in one go avoids the |
||
4474 | * overhead of making a lot of syscalls in scenarios where a lot of data |
||
4475 | * packets need to be sent (e.g. high-bandwidth video streaming over RTP/UDP), |
||
4476 | * or where the same data needs to be sent to multiple recipients. |
||
4477 | * |
||
4478 | * @flags modify how the message is sent. The commonly available arguments |
||
4479 | * for this are available in the #GSocketMsgFlags enum, but the |
||
4480 | * values there are the same as the system values, and the flags |
||
4481 | * are passed in as-is, so you can pass in system-specific flags too. |
||
4482 | * |
||
4483 | * If the socket is in blocking mode the call will block until there is |
||
4484 | * space for all the data in the socket queue. If there is no space available |
||
4485 | * and the socket is in non-blocking mode a %G_IO_ERROR_WOULD_BLOCK error |
||
4486 | * will be returned if no data was written at all, otherwise the number of |
||
4487 | * messages sent will be returned. To be notified when space is available, |
||
4488 | * wait for the %G_IO_OUT condition. Note though that you may still receive |
||
4489 | * %G_IO_ERROR_WOULD_BLOCK from g_socket_send() even if you were previously |
||
4490 | * notified of a %G_IO_OUT condition. (On Windows in particular, this is |
||
4491 | * very common due to the way the underlying APIs work.) |
||
4492 | * |
||
4493 | * On error -1 is returned and @error is set accordingly. An error will only |
||
4494 | * be returned if zero messages could be sent; otherwise the number of messages |
||
4495 | * successfully sent before the error will be returned. |
||
4496 | * |
||
4497 | * Returns: number of messages sent, or -1 on error. Note that the number of |
||
4498 | * messages sent may be smaller than @num_messages if the socket is |
||
4499 | * non-blocking or if @num_messages was larger than UIO_MAXIOV (1024), |
||
4500 | * in which case the caller may re-try to send the remaining messages. |
||
4501 | * |
||
4502 | * Since: 2.44 |
||
4503 | */ |
||
4504 | gint |
||
4505 | g_socket_send_messages (GSocket *socket, |
||
4506 | GOutputMessage *messages, |
||
4507 | guint num_messages, |
||
4508 | gint flags, |
||
4509 | GCancellable *cancellable, |
||
4510 | GError **error) |
||
4511 | { |
||
4512 | return g_socket_send_messages_with_timeout (socket, messages, num_messages, |
||
4513 | flags, |
||
4514 | socket->priv->blocking ? -1 : 0, |
||
4515 | cancellable, error); |
||
4516 | } |
||
4517 | |||
4518 | static gint |
||
4519 | g_socket_send_messages_with_timeout (GSocket *socket, |
||
4520 | GOutputMessage *messages, |
||
4521 | guint num_messages, |
||
4522 | gint flags, |
||
4523 | gint64 timeout, |
||
4524 | GCancellable *cancellable, |
||
4525 | GError **error) |
||
4526 | { |
||
4527 | gint64 start_time; |
||
4528 | |||
4529 | g_return_val_if_fail (G_IS_SOCKET (socket), -1); |
||
4530 | g_return_val_if_fail (num_messages == 0 || messages != NULL, -1); |
||
4531 | g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), -1); |
||
4532 | g_return_val_if_fail (error == NULL || *error == NULL, -1); |
||
4533 | |||
4534 | start_time = g_get_monotonic_time (); |
||
4535 | |||
4536 | if (!check_socket (socket, error)) |
||
4537 | return -1; |
||
4538 | |||
4539 | if (!check_timeout (socket, error)) |
||
4540 | return -1; |
||
4541 | |||
4542 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
4543 | return -1; |
||
4544 | |||
4545 | if (num_messages == 0) |
||
4546 | return 0; |
||
4547 | |||
4548 | #if !defined (G_OS_WIN32) && defined (HAVE_SENDMMSG) |
||
4549 | { |
||
4550 | struct mmsghdr *msgvec; |
||
4551 | gint i, num_sent; |
||
4552 | |||
4553 | #ifdef UIO_MAXIOV |
||
4554 | #define MAX_NUM_MESSAGES UIO_MAXIOV |
||
4555 | #else |
||
4556 | #define MAX_NUM_MESSAGES 1024 |
||
4557 | #endif |
||
4558 | |||
4559 | if (num_messages > MAX_NUM_MESSAGES) |
||
4560 | num_messages = MAX_NUM_MESSAGES; |
||
4561 | |||
4562 | msgvec = g_newa (struct mmsghdr, num_messages); |
||
4563 | |||
4564 | for (i = 0; i < num_messages; ++i) |
||
4565 | { |
||
4566 | GOutputMessage *msg = &messages[i]; |
||
4567 | struct msghdr *msg_hdr = &msgvec[i].msg_hdr; |
||
4568 | GError *child_error = NULL; |
||
4569 | |||
4570 | msgvec[i].msg_len = 0; |
||
4571 | |||
4572 | output_message_to_msghdr (msg, (i > 0) ? &messages[i - 1] : NULL, |
||
4573 | msg_hdr, (i > 0) ? &msgvec[i - 1].msg_hdr : NULL, |
||
4574 | &child_error); |
||
4575 | |||
4576 | if (child_error != NULL) |
||
4577 | { |
||
4578 | g_propagate_error (error, child_error); |
||
4579 | return -1; |
||
4580 | } |
||
4581 | } |
||
4582 | |||
4583 | for (num_sent = 0; num_sent < num_messages;) |
||
4584 | { |
||
4585 | gint ret; |
||
4586 | |||
4587 | ret = sendmmsg (socket->priv->fd, msgvec + num_sent, num_messages - num_sent, |
||
4588 | flags | G_SOCKET_DEFAULT_SEND_FLAGS); |
||
4589 | |||
4590 | if (ret < 0) |
||
4591 | { |
||
4592 | int errsv = get_socket_errno (); |
||
4593 | |||
4594 | if (errsv == EINTR) |
||
4595 | continue; |
||
4596 | |||
4597 | if (timeout != 0 && |
||
4598 | (errsv == EWOULDBLOCK || |
||
4599 | errsv == EAGAIN)) |
||
4600 | { |
||
4601 | if (!block_on_timeout (socket, G_IO_OUT, timeout, start_time, |
||
4602 | cancellable, error)) |
||
4603 | { |
||
4604 | if (num_sent > 0) |
||
4605 | { |
||
4606 | g_clear_error (error); |
||
4607 | break; |
||
4608 | } |
||
4609 | |||
4610 | return -1; |
||
4611 | } |
||
4612 | |||
4613 | continue; |
||
4614 | } |
||
4615 | |||
4616 | /* If any messages were successfully sent, do not error. */ |
||
4617 | if (num_sent > 0) |
||
4618 | break; |
||
4619 | |||
4620 | socket_set_error_lazy (error, errsv, _("Error sending message: %s")); |
||
4621 | |||
4622 | return -1; |
||
4623 | } |
||
4624 | |||
4625 | num_sent += ret; |
||
4626 | } |
||
4627 | |||
4628 | for (i = 0; i < num_sent; ++i) |
||
4629 | messages[i].bytes_sent = msgvec[i].msg_len; |
||
4630 | |||
4631 | return num_sent; |
||
4632 | } |
||
4633 | #else |
||
4634 | { |
||
4635 | gssize result; |
||
4636 | gint i; |
||
4637 | gint64 wait_timeout; |
||
4638 | |||
4639 | wait_timeout = timeout; |
||
4640 | |||
4641 | for (i = 0; i < num_messages; ++i) |
||
4642 | { |
||
4643 | GOutputMessage *msg = &messages[i]; |
||
4644 | GError *msg_error = NULL; |
||
4645 | |||
4646 | result = g_socket_send_message_with_timeout (socket, msg->address, |
||
4647 | msg->vectors, |
||
4648 | msg->num_vectors, |
||
4649 | msg->control_messages, |
||
4650 | msg->num_control_messages, |
||
4651 | flags, wait_timeout, |
||
4652 | cancellable, &msg_error); |
||
4653 | |||
4654 | /* check if we've timed out or how much time to wait at most */ |
||
4655 | if (timeout > 0) |
||
4656 | { |
||
4657 | gint64 elapsed = g_get_monotonic_time () - start_time; |
||
4658 | wait_timeout = MAX (timeout - elapsed, 1); |
||
4659 | } |
||
4660 | |||
4661 | if (result < 0) |
||
4662 | { |
||
4663 | /* if we couldn't send all messages, just return how many we did |
||
4664 | * manage to send, provided we managed to send at least one */ |
||
4665 | if (i > 0 && |
||
4666 | (g_error_matches (msg_error, G_IO_ERROR, G_IO_ERROR_WOULD_BLOCK) || |
||
4667 | g_error_matches (msg_error, G_IO_ERROR, G_IO_ERROR_TIMED_OUT))) |
||
4668 | { |
||
4669 | g_error_free (msg_error); |
||
4670 | return i; |
||
4671 | } |
||
4672 | else |
||
4673 | { |
||
4674 | g_propagate_error (error, msg_error); |
||
4675 | return -1; |
||
4676 | } |
||
4677 | } |
||
4678 | |||
4679 | msg->bytes_sent = result; |
||
4680 | } |
||
4681 | |||
4682 | return i; |
||
4683 | } |
||
4684 | #endif |
||
4685 | } |
||
4686 | |||
4687 | static GSocketAddress * |
||
4688 | cache_recv_address (GSocket *socket, struct sockaddr *native, int native_len) |
||
4689 | { |
||
4690 | GSocketAddress *saddr; |
||
4691 | gint i; |
||
4692 | guint64 oldest_time = G_MAXUINT64; |
||
4693 | gint oldest_index = 0; |
||
4694 | |||
4695 | if (native_len <= 0) |
||
4696 | return NULL; |
||
4697 | |||
4698 | saddr = NULL; |
||
4699 | for (i = 0; i < RECV_ADDR_CACHE_SIZE; i++) |
||
4700 | { |
||
4701 | GSocketAddress *tmp = socket->priv->recv_addr_cache[i].addr; |
||
4702 | gpointer tmp_native = socket->priv->recv_addr_cache[i].native; |
||
4703 | gint tmp_native_len = socket->priv->recv_addr_cache[i].native_len; |
||
4704 | |||
4705 | if (!tmp) |
||
4706 | continue; |
||
4707 | |||
4708 | if (tmp_native_len != native_len) |
||
4709 | continue; |
||
4710 | |||
4711 | if (memcmp (tmp_native, native, native_len) == 0) |
||
4712 | { |
||
4713 | saddr = g_object_ref (tmp); |
||
4714 | socket->priv->recv_addr_cache[i].last_used = g_get_monotonic_time (); |
||
4715 | return saddr; |
||
4716 | } |
||
4717 | |||
4718 | if (socket->priv->recv_addr_cache[i].last_used < oldest_time) |
||
4719 | { |
||
4720 | oldest_time = socket->priv->recv_addr_cache[i].last_used; |
||
4721 | oldest_index = i; |
||
4722 | } |
||
4723 | } |
||
4724 | |||
4725 | saddr = g_socket_address_new_from_native (native, native_len); |
||
4726 | |||
4727 | if (socket->priv->recv_addr_cache[oldest_index].addr) |
||
4728 | { |
||
4729 | g_object_unref (socket->priv->recv_addr_cache[oldest_index].addr); |
||
4730 | g_free (socket->priv->recv_addr_cache[oldest_index].native); |
||
4731 | } |
||
4732 | |||
4733 | socket->priv->recv_addr_cache[oldest_index].native = g_memdup (native, native_len); |
||
4734 | socket->priv->recv_addr_cache[oldest_index].native_len = native_len; |
||
4735 | socket->priv->recv_addr_cache[oldest_index].addr = g_object_ref (saddr); |
||
4736 | socket->priv->recv_addr_cache[oldest_index].last_used = g_get_monotonic_time (); |
||
4737 | |||
4738 | return saddr; |
||
4739 | } |
||
4740 | |||
4741 | static gssize |
||
4742 | g_socket_receive_message_with_timeout (GSocket *socket, |
||
4743 | GSocketAddress **address, |
||
4744 | GInputVector *vectors, |
||
4745 | gint num_vectors, |
||
4746 | GSocketControlMessage ***messages, |
||
4747 | gint *num_messages, |
||
4748 | gint *flags, |
||
4749 | gint64 timeout, |
||
4750 | GCancellable *cancellable, |
||
4751 | GError **error) |
||
4752 | { |
||
4753 | GInputVector one_vector; |
||
4754 | char one_byte; |
||
4755 | gint64 start_time; |
||
4756 | |||
4757 | g_return_val_if_fail (G_IS_SOCKET (socket), -1); |
||
4758 | |||
4759 | start_time = g_get_monotonic_time (); |
||
4760 | |||
4761 | if (!check_socket (socket, error)) |
||
4762 | return -1; |
||
4763 | |||
4764 | if (!check_timeout (socket, error)) |
||
4765 | return -1; |
||
4766 | |||
4767 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
4768 | return -1; |
||
4769 | |||
4770 | if (num_vectors == -1) |
||
4771 | { |
||
4772 | for (num_vectors = 0; |
||
4773 | vectors[num_vectors].buffer != NULL; |
||
4774 | num_vectors++) |
||
4775 | ; |
||
4776 | } |
||
4777 | |||
4778 | if (num_vectors == 0) |
||
4779 | { |
||
4780 | one_vector.buffer = &one_byte; |
||
4781 | one_vector.size = 1; |
||
4782 | num_vectors = 1; |
||
4783 | vectors = &one_vector; |
||
4784 | } |
||
4785 | |||
4786 | #ifndef G_OS_WIN32 |
||
4787 | { |
||
4788 | GInputMessage input_message; |
||
4789 | struct msghdr msg; |
||
4790 | gssize result; |
||
4791 | |||
4792 | input_message.address = address; |
||
4793 | input_message.vectors = vectors; |
||
4794 | input_message.num_vectors = num_vectors; |
||
4795 | input_message.bytes_received = 0; |
||
4796 | input_message.flags = (flags != NULL) ? *flags : 0; |
||
4797 | input_message.control_messages = messages; |
||
4798 | input_message.num_control_messages = (guint *) num_messages; |
||
4799 | |||
4800 | /* We always set the close-on-exec flag so we don't leak file |
||
4801 | * descriptors into child processes. Note that gunixfdmessage.c |
||
4802 | * will later call fcntl (fd, FD_CLOEXEC), but that isn't atomic. |
||
4803 | */ |
||
4804 | #ifdef MSG_CMSG_CLOEXEC |
||
4805 | input_message.flags |= MSG_CMSG_CLOEXEC; |
||
4806 | #endif |
||
4807 | |||
4808 | input_message_to_msghdr (&input_message, &msg); |
||
4809 | |||
4810 | /* do it */ |
||
4811 | while (1) |
||
4812 | { |
||
4813 | result = recvmsg (socket->priv->fd, &msg, msg.msg_flags); |
||
4814 | #ifdef MSG_CMSG_CLOEXEC |
||
4815 | if (result < 0 && get_socket_errno () == EINVAL) |
||
4816 | { |
||
4817 | /* We must be running on an old kernel. Call without the flag. */ |
||
4818 | msg.msg_flags &= ~(MSG_CMSG_CLOEXEC); |
||
4819 | result = recvmsg (socket->priv->fd, &msg, msg.msg_flags); |
||
4820 | } |
||
4821 | #endif |
||
4822 | |||
4823 | if (result < 0) |
||
4824 | { |
||
4825 | int errsv = get_socket_errno (); |
||
4826 | |||
4827 | if (errsv == EINTR) |
||
4828 | continue; |
||
4829 | |||
4830 | if (timeout != 0 && |
||
4831 | (errsv == EWOULDBLOCK || |
||
4832 | errsv == EAGAIN)) |
||
4833 | { |
||
4834 | if (!block_on_timeout (socket, G_IO_IN, timeout, start_time, |
||
4835 | cancellable, error)) |
||
4836 | return -1; |
||
4837 | |||
4838 | continue; |
||
4839 | } |
||
4840 | |||
4841 | socket_set_error_lazy (error, errsv, _("Error receiving message: %s")); |
||
4842 | return -1; |
||
4843 | } |
||
4844 | break; |
||
4845 | } |
||
4846 | |||
4847 | input_message_from_msghdr (&msg, &input_message, socket); |
||
4848 | |||
4849 | if (flags != NULL) |
||
4850 | *flags = input_message.flags; |
||
4851 | |||
4852 | return result; |
||
4853 | } |
||
4854 | #else |
||
4855 | { |
||
4856 | struct sockaddr_storage addr; |
||
4857 | int addrlen; |
||
4858 | DWORD bytes_received; |
||
4859 | DWORD win_flags; |
||
4860 | int result; |
||
4861 | WSABUF *bufs; |
||
4862 | gint i; |
||
4863 | |||
4864 | /* iov */ |
||
4865 | bufs = g_newa (WSABUF, num_vectors); |
||
4866 | for (i = 0; i < num_vectors; i++) |
||
4867 | { |
||
4868 | bufs[i].buf = (char *)vectors[i].buffer; |
||
4869 | bufs[i].len = (gulong)vectors[i].size; |
||
4870 | } |
||
4871 | |||
4872 | /* flags */ |
||
4873 | if (flags != NULL) |
||
4874 | win_flags = *flags; |
||
4875 | else |
||
4876 | win_flags = 0; |
||
4877 | |||
4878 | /* do it */ |
||
4879 | while (1) |
||
4880 | { |
||
4881 | addrlen = sizeof addr; |
||
4882 | if (address) |
||
4883 | result = WSARecvFrom (socket->priv->fd, |
||
4884 | bufs, num_vectors, |
||
4885 | &bytes_received, &win_flags, |
||
4886 | (struct sockaddr *)&addr, &addrlen, |
||
4887 | NULL, NULL); |
||
4888 | else |
||
4889 | result = WSARecv (socket->priv->fd, |
||
4890 | bufs, num_vectors, |
||
4891 | &bytes_received, &win_flags, |
||
4892 | NULL, NULL); |
||
4893 | if (result != 0) |
||
4894 | { |
||
4895 | int errsv = get_socket_errno (); |
||
4896 | |||
4897 | if (errsv == WSAEINTR) |
||
4898 | continue; |
||
4899 | |||
4900 | if (errsv == WSAEWOULDBLOCK) |
||
4901 | { |
||
4902 | win32_unset_event_mask (socket, FD_READ); |
||
4903 | |||
4904 | if (timeout != 0) |
||
4905 | { |
||
4906 | if (!block_on_timeout (socket, G_IO_IN, timeout, |
||
4907 | start_time, cancellable, error)) |
||
4908 | return -1; |
||
4909 | |||
4910 | continue; |
||
4911 | } |
||
4912 | } |
||
4913 | |||
4914 | socket_set_error_lazy (error, errsv, _("Error receiving message: %s")); |
||
4915 | return -1; |
||
4916 | } |
||
4917 | win32_unset_event_mask (socket, FD_READ); |
||
4918 | break; |
||
4919 | } |
||
4920 | |||
4921 | /* decode address */ |
||
4922 | if (address != NULL) |
||
4923 | { |
||
4924 | *address = cache_recv_address (socket, (struct sockaddr *)&addr, addrlen); |
||
4925 | } |
||
4926 | |||
4927 | /* capture the flags */ |
||
4928 | if (flags != NULL) |
||
4929 | *flags = win_flags; |
||
4930 | |||
4931 | if (messages != NULL) |
||
4932 | *messages = NULL; |
||
4933 | if (num_messages != NULL) |
||
4934 | *num_messages = 0; |
||
4935 | |||
4936 | return bytes_received; |
||
4937 | } |
||
4938 | #endif |
||
4939 | } |
||
4940 | |||
4941 | /** |
||
4942 | * g_socket_receive_messages: |
||
4943 | * @socket: a #GSocket |
||
4944 | * @messages: (array length=num_messages): an array of #GInputMessage structs |
||
4945 | * @num_messages: the number of elements in @messages |
||
4946 | * @flags: an int containing #GSocketMsgFlags flags for the overall operation |
||
4947 | * @cancellable: (allow-none): a %GCancellable or %NULL |
||
4948 | * @error: #GError for error reporting, or %NULL to ignore |
||
4949 | * |
||
4950 | * Receive multiple data messages from @socket in one go. This is the most |
||
4951 | * complicated and fully-featured version of this call. For easier use, see |
||
4952 | * g_socket_receive(), g_socket_receive_from(), and g_socket_receive_message(). |
||
4953 | * |
||
4954 | * @messages must point to an array of #GInputMessage structs and |
||
4955 | * @num_messages must be the length of this array. Each #GInputMessage |
||
4956 | * contains a pointer to an array of #GInputVector structs describing the |
||
4957 | * buffers that the data received in each message will be written to. Using |
||
4958 | * multiple #GInputVectors is more memory-efficient than manually copying data |
||
4959 | * out of a single buffer to multiple sources, and more system-call-efficient |
||
4960 | * than making multiple calls to g_socket_receive(), such as in scenarios where |
||
4961 | * a lot of data packets need to be received (e.g. high-bandwidth video |
||
4962 | * streaming over RTP/UDP). |
||
4963 | * |
||
4964 | * @flags modify how all messages are received. The commonly available |
||
4965 | * arguments for this are available in the #GSocketMsgFlags enum, but the |
||
4966 | * values there are the same as the system values, and the flags |
||
4967 | * are passed in as-is, so you can pass in system-specific flags too. These |
||
4968 | * flags affect the overall receive operation. Flags affecting individual |
||
4969 | * messages are returned in #GInputMessage.flags. |
||
4970 | * |
||
4971 | * The other members of #GInputMessage are treated as described in its |
||
4972 | * documentation. |
||
4973 | * |
||
4974 | * If #GSocket:blocking is %TRUE the call will block until @num_messages have |
||
4975 | * been received, or the end of the stream is reached. |
||
4976 | * |
||
4977 | * If #GSocket:blocking is %FALSE the call will return up to @num_messages |
||
4978 | * without blocking, or %G_IO_ERROR_WOULD_BLOCK if no messages are queued in the |
||
4979 | * operating system to be received. |
||
4980 | * |
||
4981 | * In blocking mode, if #GSocket:timeout is positive and is reached before any |
||
4982 | * messages are received, %G_IO_ERROR_TIMED_OUT is returned, otherwise up to |
||
4983 | * @num_messages are returned. (Note: This is effectively the |
||
4984 | * behaviour of `MSG_WAITFORONE` with recvmmsg().) |
||
4985 | * |
||
4986 | * To be notified when messages are available, wait for the |
||
4987 | * %G_IO_IN condition. Note though that you may still receive |
||
4988 | * %G_IO_ERROR_WOULD_BLOCK from g_socket_receive_messages() even if you were |
||
4989 | * previously notified of a %G_IO_IN condition. |
||
4990 | * |
||
4991 | * If the remote peer closes the connection, any messages queued in the |
||
4992 | * operating system will be returned, and subsequent calls to |
||
4993 | * g_socket_receive_messages() will return 0 (with no error set). |
||
4994 | * |
||
4995 | * On error -1 is returned and @error is set accordingly. An error will only |
||
4996 | * be returned if zero messages could be received; otherwise the number of |
||
4997 | * messages successfully received before the error will be returned. |
||
4998 | * |
||
4999 | * Returns: number of messages received, or -1 on error. Note that the number |
||
5000 | * of messages received may be smaller than @num_messages if in non-blocking |
||
5001 | * mode, if the peer closed the connection, or if @num_messages |
||
5002 | * was larger than `UIO_MAXIOV` (1024), in which case the caller may re-try |
||
5003 | * to receive the remaining messages. |
||
5004 | * |
||
5005 | * Since: 2.48 |
||
5006 | */ |
||
5007 | gint |
||
5008 | g_socket_receive_messages (GSocket *socket, |
||
5009 | GInputMessage *messages, |
||
5010 | guint num_messages, |
||
5011 | gint flags, |
||
5012 | GCancellable *cancellable, |
||
5013 | GError **error) |
||
5014 | { |
||
5015 | if (!check_socket (socket, error) || |
||
5016 | !check_timeout (socket, error)) |
||
5017 | return -1; |
||
5018 | |||
5019 | return g_socket_receive_messages_with_timeout (socket, messages, num_messages, |
||
5020 | flags, |
||
5021 | socket->priv->blocking ? -1 : 0, |
||
5022 | cancellable, error); |
||
5023 | } |
||
5024 | |||
5025 | static gint |
||
5026 | g_socket_receive_messages_with_timeout (GSocket *socket, |
||
5027 | GInputMessage *messages, |
||
5028 | guint num_messages, |
||
5029 | gint flags, |
||
5030 | gint64 timeout, |
||
5031 | GCancellable *cancellable, |
||
5032 | GError **error) |
||
5033 | { |
||
5034 | gint64 start_time; |
||
5035 | |||
5036 | g_return_val_if_fail (G_IS_SOCKET (socket), -1); |
||
5037 | g_return_val_if_fail (num_messages == 0 || messages != NULL, -1); |
||
5038 | g_return_val_if_fail (cancellable == NULL || |
||
5039 | G_IS_CANCELLABLE (cancellable), -1); |
||
5040 | g_return_val_if_fail (error == NULL || *error == NULL, -1); |
||
5041 | |||
5042 | start_time = g_get_monotonic_time (); |
||
5043 | |||
5044 | if (!check_socket (socket, error)) |
||
5045 | return -1; |
||
5046 | |||
5047 | if (!check_timeout (socket, error)) |
||
5048 | return -1; |
||
5049 | |||
5050 | if (g_cancellable_set_error_if_cancelled (cancellable, error)) |
||
5051 | return -1; |
||
5052 | |||
5053 | if (num_messages == 0) |
||
5054 | return 0; |
||
5055 | |||
5056 | #if !defined (G_OS_WIN32) && defined (HAVE_RECVMMSG) |
||
5057 | { |
||
5058 | struct mmsghdr *msgvec; |
||
5059 | guint i, num_received; |
||
5060 | |||
5061 | #ifdef UIO_MAXIOV |
||
5062 | #define MAX_NUM_MESSAGES UIO_MAXIOV |
||
5063 | #else |
||
5064 | #define MAX_NUM_MESSAGES 1024 |
||
5065 | #endif |
||
5066 | |||
5067 | if (num_messages > MAX_NUM_MESSAGES) |
||
5068 | num_messages = MAX_NUM_MESSAGES; |
||
5069 | |||
5070 | msgvec = g_newa (struct mmsghdr, num_messages); |
||
5071 | |||
5072 | for (i = 0; i < num_messages; ++i) |
||
5073 | { |
||
5074 | GInputMessage *msg = &messages[i]; |
||
5075 | struct msghdr *msg_hdr = &msgvec[i].msg_hdr; |
||
5076 | |||
5077 | input_message_to_msghdr (msg, msg_hdr); |
||
5078 | msgvec[i].msg_len = 0; |
||
5079 | } |
||
5080 | |||
5081 | /* We always set the close-on-exec flag so we don't leak file |
||
5082 | * descriptors into child processes. Note that gunixfdmessage.c |
||
5083 | * will later call fcntl (fd, FD_CLOEXEC), but that isn't atomic. |
||
5084 | */ |
||
5085 | #ifdef MSG_CMSG_CLOEXEC |
||
5086 | flags |= MSG_CMSG_CLOEXEC; |
||
5087 | #endif |
||
5088 | |||
5089 | for (num_received = 0; num_received < num_messages;) |
||
5090 | { |
||
5091 | gint ret; |
||
5092 | |||
5093 | /* We operate in non-blocking mode and handle the timeout ourselves. */ |
||
5094 | ret = recvmmsg (socket->priv->fd, |
||
5095 | msgvec + num_received, |
||
5096 | num_messages - num_received, |
||
5097 | flags | G_SOCKET_DEFAULT_SEND_FLAGS, NULL); |
||
5098 | #ifdef MSG_CMSG_CLOEXEC |
||
5099 | if (ret < 0 && get_socket_errno () == EINVAL) |
||
5100 | { |
||
5101 | /* We must be running on an old kernel. Call without the flag. */ |
||
5102 | flags &= ~(MSG_CMSG_CLOEXEC); |
||
5103 | ret = recvmmsg (socket->priv->fd, |
||
5104 | msgvec + num_received, |
||
5105 | num_messages - num_received, |
||
5106 | flags | G_SOCKET_DEFAULT_SEND_FLAGS, NULL); |
||
5107 | } |
||
5108 | #endif |
||
5109 | |||
5110 | if (ret < 0) |
||
5111 | { |
||
5112 | int errsv = get_socket_errno (); |
||
5113 | |||
5114 | if (errsv == EINTR) |
||
5115 | continue; |
||
5116 | |||
5117 | if (timeout != 0 && |
||
5118 | (errsv == EWOULDBLOCK || |
||
5119 | errsv == EAGAIN)) |
||
5120 | { |
||
5121 | if (!block_on_timeout (socket, G_IO_IN, timeout, start_time, |
||
5122 | cancellable, error)) |
||
5123 | { |
||
5124 | if (num_received > 0) |
||
5125 | { |
||
5126 | g_clear_error (error); |
||
5127 | break; |
||
5128 | } |
||
5129 | |||
5130 | return -1; |
||
5131 | } |
||
5132 | |||
5133 | continue; |
||
5134 | } |
||
5135 | |||
5136 | /* If any messages were successfully received, do not error. */ |
||
5137 | if (num_received > 0) |
||
5138 | break; |
||
5139 | |||
5140 | socket_set_error_lazy (error, errsv, |
||
5141 | _("Error receiving message: %s")); |
||
5142 | |||
5143 | return -1; |
||
5144 | } |
||
5145 | else if (ret == 0) |
||
5146 | { |
||
5147 | /* EOS. */ |
||
5148 | break; |
||
5149 | } |
||
5150 | |||
5151 | num_received += ret; |
||
5152 | } |
||
5153 | |||
5154 | for (i = 0; i < num_received; ++i) |
||
5155 | { |
||
5156 | input_message_from_msghdr (&msgvec[i].msg_hdr, &messages[i], socket); |
||
5157 | messages[i].bytes_received = msgvec[i].msg_len; |
||
5158 | } |
||
5159 | |||
5160 | return num_received; |
||
5161 | } |
||
5162 | #else |
||
5163 | { |
||
5164 | guint i; |
||
5165 | gint64 wait_timeout; |
||
5166 | |||
5167 | wait_timeout = timeout; |
||
5168 | |||
5169 | for (i = 0; i < num_messages; i++) |
||
5170 | { |
||
5171 | GInputMessage *msg = &messages[i]; |
||
5172 | gssize len; |
||
5173 | GError *msg_error = NULL; |
||
5174 | |||
5175 | msg->flags = flags; /* in-out parameter */ |
||
5176 | |||
5177 | len = g_socket_receive_message_with_timeout (socket, |
||
5178 | msg->address, |
||
5179 | msg->vectors, |
||
5180 | msg->num_vectors, |
||
5181 | msg->control_messages, |
||
5182 | (gint *) msg->num_control_messages, |
||
5183 | &msg->flags, |
||
5184 | wait_timeout, |
||
5185 | cancellable, |
||
5186 | &msg_error); |
||
5187 | |||
5188 | /* check if we've timed out or how much time to wait at most */ |
||
5189 | if (timeout > 0) |
||
5190 | { |
||
5191 | gint64 elapsed = g_get_monotonic_time () - start_time; |
||
5192 | wait_timeout = MAX (timeout - elapsed, 1); |
||
5193 | } |
||
5194 | |||
5195 | if (len >= 0) |
||
5196 | msg->bytes_received = len; |
||
5197 | |||
5198 | if (i != 0 && |
||
5199 | (g_error_matches (msg_error, G_IO_ERROR, G_IO_ERROR_WOULD_BLOCK) || |
||
5200 | g_error_matches (msg_error, G_IO_ERROR, G_IO_ERROR_TIMED_OUT))) |
||
5201 | { |
||
5202 | g_clear_error (&msg_error); |
||
5203 | break; |
||
5204 | } |
||
5205 | |||
5206 | if (msg_error != NULL) |
||
5207 | { |
||
5208 | g_propagate_error (error, msg_error); |
||
5209 | return -1; |
||
5210 | } |
||
5211 | |||
5212 | if (len == 0) |
||
5213 | break; |
||
5214 | } |
||
5215 | |||
5216 | return i; |
||
5217 | } |
||
5218 | #endif |
||
5219 | } |
||
5220 | |||
5221 | /** |
||
5222 | * g_socket_receive_message: |
||
5223 | * @socket: a #GSocket |
||
5224 | * @address: (out) (nullable): a pointer to a #GSocketAddress |
||
5225 | * pointer, or %NULL |
||
5226 | * @vectors: (array length=num_vectors): an array of #GInputVector structs |
||
5227 | * @num_vectors: the number of elements in @vectors, or -1 |
||
5228 | * @messages: (array length=num_messages) (out) (nullable): a pointer which |
||
5229 | * may be filled with an array of #GSocketControlMessages, or %NULL |
||
5230 | * @num_messages: (out): a pointer which will be filled with the number of |
||
5231 | * elements in @messages, or %NULL |
||
5232 | * @flags: (inout): a pointer to an int containing #GSocketMsgFlags flags |
||
5233 | * @cancellable: a %GCancellable or %NULL |
||
5234 | * @error: a #GError pointer, or %NULL |
||
5235 | * |
||
5236 | * Receive data from a socket. For receiving multiple messages, see |
||
5237 | * g_socket_receive_messages(); for easier use, see |
||
5238 | * g_socket_receive() and g_socket_receive_from(). |
||
5239 | * |
||
5240 | * If @address is non-%NULL then @address will be set equal to the |
||
5241 | * source address of the received packet. |
||
5242 | * @address is owned by the caller. |
||
5243 | * |
||
5244 | * @vector must point to an array of #GInputVector structs and |
||
5245 | * @num_vectors must be the length of this array. These structs |
||
5246 | * describe the buffers that received data will be scattered into. |
||
5247 | * If @num_vectors is -1, then @vectors is assumed to be terminated |
||
5248 | * by a #GInputVector with a %NULL buffer pointer. |
||
5249 | * |
||
5250 | * As a special case, if @num_vectors is 0 (in which case, @vectors |
||
5251 | * may of course be %NULL), then a single byte is received and |
||
5252 | * discarded. This is to facilitate the common practice of sending a |
||
5253 | * single '\0' byte for the purposes of transferring ancillary data. |
||
5254 | * |
||
5255 | * @messages, if non-%NULL, will be set to point to a newly-allocated |
||
5256 | * array of #GSocketControlMessage instances or %NULL if no such |
||
5257 | * messages was received. These correspond to the control messages |
||
5258 | * received from the kernel, one #GSocketControlMessage per message |
||
5259 | * from the kernel. This array is %NULL-terminated and must be freed |
||
5260 | * by the caller using g_free() after calling g_object_unref() on each |
||
5261 | * element. If @messages is %NULL, any control messages received will |
||
5262 | * be discarded. |
||
5263 | * |
||
5264 | * @num_messages, if non-%NULL, will be set to the number of control |
||
5265 | * messages received. |
||
5266 | * |
||
5267 | * If both @messages and @num_messages are non-%NULL, then |
||
5268 | * @num_messages gives the number of #GSocketControlMessage instances |
||
5269 | * in @messages (ie: not including the %NULL terminator). |
||
5270 | * |
||
5271 | * @flags is an in/out parameter. The commonly available arguments |
||
5272 | * for this are available in the #GSocketMsgFlags enum, but the |
||
5273 | * values there are the same as the system values, and the flags |
||
5274 | * are passed in as-is, so you can pass in system-specific flags too |
||
5275 | * (and g_socket_receive_message() may pass system-specific flags out). |
||
5276 | * Flags passed in to the parameter affect the receive operation; flags returned |
||
5277 | * out of it are relevant to the specific returned message. |
||
5278 | * |
||
5279 | * As with g_socket_receive(), data may be discarded if @socket is |
||
5280 | * %G_SOCKET_TYPE_DATAGRAM or %G_SOCKET_TYPE_SEQPACKET and you do not |
||
5281 | * provide enough buffer space to read a complete message. You can pass |
||
5282 | * %G_SOCKET_MSG_PEEK in @flags to peek at the current message without |
||
5283 | * removing it from the receive queue, but there is no portable way to find |
||
5284 | * out the length of the message other than by reading it into a |
||
5285 | * sufficiently-large buffer. |
||
5286 | * |
||
5287 | * If the socket is in blocking mode the call will block until there |
||
5288 | * is some data to receive, the connection is closed, or there is an |
||
5289 | * error. If there is no data available and the socket is in |
||
5290 | * non-blocking mode, a %G_IO_ERROR_WOULD_BLOCK error will be |
||
5291 | * returned. To be notified when data is available, wait for the |
||
5292 | * %G_IO_IN condition. |
||
5293 | * |
||
5294 | * On error -1 is returned and @error is set accordingly. |
||
5295 | * |
||
5296 | * Returns: Number of bytes read, or 0 if the connection was closed by |
||
5297 | * the peer, or -1 on error |
||
5298 | * |
||
5299 | * Since: 2.22 |
||
5300 | */ |
||
5301 | gssize |
||
5302 | g_socket_receive_message (GSocket *socket, |
||
5303 | GSocketAddress **address, |
||
5304 | GInputVector *vectors, |
||
5305 | gint num_vectors, |
||
5306 | GSocketControlMessage ***messages, |
||
5307 | gint *num_messages, |
||
5308 | gint *flags, |
||
5309 | GCancellable *cancellable, |
||
5310 | GError **error) |
||
5311 | { |
||
5312 | return g_socket_receive_message_with_timeout (socket, address, vectors, |
||
5313 | num_vectors, messages, |
||
5314 | num_messages, flags, |
||
5315 | socket->priv->blocking ? -1 : 0, |
||
5316 | cancellable, error); |
||
5317 | } |
||
5318 | |||
5319 | /** |
||
5320 | * g_socket_get_credentials: |
||
5321 | * @socket: a #GSocket. |
||
5322 | * @error: #GError for error reporting, or %NULL to ignore. |
||
5323 | * |
||
5324 | * Returns the credentials of the foreign process connected to this |
||
5325 | * socket, if any (e.g. it is only supported for %G_SOCKET_FAMILY_UNIX |
||
5326 | * sockets). |
||
5327 | * |
||
5328 | * If this operation isn't supported on the OS, the method fails with |
||
5329 | * the %G_IO_ERROR_NOT_SUPPORTED error. On Linux this is implemented |
||
5330 | * by reading the %SO_PEERCRED option on the underlying socket. |
||
5331 | * |
||
5332 | * Other ways to obtain credentials from a foreign peer includes the |
||
5333 | * #GUnixCredentialsMessage type and |
||
5334 | * g_unix_connection_send_credentials() / |
||
5335 | * g_unix_connection_receive_credentials() functions. |
||
5336 | * |
||
5337 | * Returns: (transfer full): %NULL if @error is set, otherwise a #GCredentials object |
||
5338 | * that must be freed with g_object_unref(). |
||
5339 | * |
||
5340 | * Since: 2.26 |
||
5341 | */ |
||
5342 | GCredentials * |
||
5343 | g_socket_get_credentials (GSocket *socket, |
||
5344 | GError **error) |
||
5345 | { |
||
5346 | GCredentials *ret; |
||
5347 | |||
5348 | g_return_val_if_fail (G_IS_SOCKET (socket), NULL); |
||
5349 | g_return_val_if_fail (error == NULL || *error == NULL, NULL); |
||
5350 | |||
5351 | ret = NULL; |
||
5352 | |||
5353 | #if G_CREDENTIALS_SOCKET_GET_CREDENTIALS_SUPPORTED |
||
5354 | |||
5355 | #ifdef SO_PEERCRED |
||
5356 | { |
||
5357 | guint8 native_creds_buf[G_CREDENTIALS_NATIVE_SIZE]; |
||
5358 | socklen_t optlen = sizeof (native_creds_buf); |
||
5359 | |||
5360 | if (getsockopt (socket->priv->fd, |
||
5361 | SOL_SOCKET, |
||
5362 | SO_PEERCRED, |
||
5363 | native_creds_buf, |
||
5364 | &optlen) == 0) |
||
5365 | { |
||
5366 | ret = g_credentials_new (); |
||
5367 | g_credentials_set_native (ret, |
||
5368 | G_CREDENTIALS_NATIVE_TYPE, |
||
5369 | native_creds_buf); |
||
5370 | } |
||
5371 | } |
||
5372 | #elif G_CREDENTIALS_USE_NETBSD_UNPCBID |
||
5373 | { |
||
5374 | struct unpcbid cred; |
||
5375 | socklen_t optlen = sizeof (cred); |
||
5376 | |||
5377 | if (getsockopt (socket->priv->fd, |
||
5378 | 0, |
||
5379 | LOCAL_PEEREID, |
||
5380 | &cred, |
||
5381 | &optlen) == 0) |
||
5382 | { |
||
5383 | ret = g_credentials_new (); |
||
5384 | g_credentials_set_native (ret, |
||
5385 | G_CREDENTIALS_NATIVE_TYPE, |
||
5386 | &cred); |
||
5387 | } |
||
5388 | } |
||
5389 | #elif G_CREDENTIALS_USE_SOLARIS_UCRED |
||
5390 | { |
||
5391 | ucred_t *ucred = NULL; |
||
5392 | |||
5393 | if (getpeerucred (socket->priv->fd, &ucred) == 0) |
||
5394 | { |
||
5395 | ret = g_credentials_new (); |
||
5396 | g_credentials_set_native (ret, |
||
5397 | G_CREDENTIALS_TYPE_SOLARIS_UCRED, |
||
5398 | ucred); |
||
5399 | ucred_free (ucred); |
||
5400 | } |
||
5401 | } |
||
5402 | #else |
||
5403 | #error "G_CREDENTIALS_SOCKET_GET_CREDENTIALS_SUPPORTED is set but this is no code for this platform" |
||
5404 | #endif |
||
5405 | |||
5406 | if (!ret) |
||
5407 | { |
||
5408 | int errsv = get_socket_errno (); |
||
5409 | |||
5410 | g_set_error (error, |
||
5411 | G_IO_ERROR, |
||
5412 | socket_io_error_from_errno (errsv), |
||
5413 | _("Unable to read socket credentials: %s"), |
||
5414 | socket_strerror (errsv)); |
||
5415 | } |
||
5416 | |||
5417 | #else |
||
5418 | |||
5419 | g_set_error_literal (error, |
||
5420 | G_IO_ERROR, |
||
5421 | G_IO_ERROR_NOT_SUPPORTED, |
||
5422 | _("g_socket_get_credentials not implemented for this OS")); |
||
5423 | #endif |
||
5424 | |||
5425 | return ret; |
||
5426 | } |
||
5427 | |||
5428 | /** |
||
5429 | * g_socket_get_option: |
||
5430 | * @socket: a #GSocket |
||
5431 | * @level: the "API level" of the option (eg, `SOL_SOCKET`) |
||
5432 | * @optname: the "name" of the option (eg, `SO_BROADCAST`) |
||
5433 | * @value: (out): return location for the option value |
||
5434 | * @error: #GError for error reporting, or %NULL to ignore. |
||
5435 | * |
||
5436 | * Gets the value of an integer-valued option on @socket, as with |
||
5437 | * getsockopt(). (If you need to fetch a non-integer-valued option, |
||
5438 | * you will need to call getsockopt() directly.) |
||
5439 | * |
||
5440 | * The [<gio/gnetworking.h>][gio-gnetworking.h] |
||
5441 | * header pulls in system headers that will define most of the |
||
5442 | * standard/portable socket options. For unusual socket protocols or |
||
5443 | * platform-dependent options, you may need to include additional |
||
5444 | * headers. |
||
5445 | * |
||
5446 | * Note that even for socket options that are a single byte in size, |
||
5447 | * @value is still a pointer to a #gint variable, not a #guchar; |
||
5448 | * g_socket_get_option() will handle the conversion internally. |
||
5449 | * |
||
5450 | * Returns: success or failure. On failure, @error will be set, and |
||
5451 | * the system error value (`errno` or WSAGetLastError()) will still |
||
5452 | * be set to the result of the getsockopt() call. |
||
5453 | * |
||
5454 | * Since: 2.36 |
||
5455 | */ |
||
5456 | gboolean |
||
5457 | g_socket_get_option (GSocket *socket, |
||
5458 | gint level, |
||
5459 | gint optname, |
||
5460 | gint *value, |
||
5461 | GError **error) |
||
5462 | { |
||
5463 | guint size; |
||
5464 | |||
5465 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
5466 | |||
5467 | *value = 0; |
||
5468 | size = sizeof (gint); |
||
5469 | if (getsockopt (socket->priv->fd, level, optname, value, &size) != 0) |
||
5470 | { |
||
5471 | int errsv = get_socket_errno (); |
||
5472 | |||
5473 | g_set_error_literal (error, |
||
5474 | G_IO_ERROR, |
||
5475 | socket_io_error_from_errno (errsv), |
||
5476 | socket_strerror (errsv)); |
||
5477 | #ifndef G_OS_WIN32 |
||
5478 | /* Reset errno in case the caller wants to look at it */ |
||
5479 | errno = errsv; |
||
5480 | #endif |
||
5481 | return FALSE; |
||
5482 | } |
||
5483 | |||
5484 | #if G_BYTE_ORDER == G_BIG_ENDIAN |
||
5485 | /* If the returned value is smaller than an int then we need to |
||
5486 | * slide it over into the low-order bytes of *value. |
||
5487 | */ |
||
5488 | if (size != sizeof (gint)) |
||
5489 | *value = *value >> (8 * (sizeof (gint) - size)); |
||
5490 | #endif |
||
5491 | |||
5492 | return TRUE; |
||
5493 | } |
||
5494 | |||
5495 | /** |
||
5496 | * g_socket_set_option: |
||
5497 | * @socket: a #GSocket |
||
5498 | * @level: the "API level" of the option (eg, `SOL_SOCKET`) |
||
5499 | * @optname: the "name" of the option (eg, `SO_BROADCAST`) |
||
5500 | * @value: the value to set the option to |
||
5501 | * @error: #GError for error reporting, or %NULL to ignore. |
||
5502 | * |
||
5503 | * Sets the value of an integer-valued option on @socket, as with |
||
5504 | * setsockopt(). (If you need to set a non-integer-valued option, |
||
5505 | * you will need to call setsockopt() directly.) |
||
5506 | * |
||
5507 | * The [<gio/gnetworking.h>][gio-gnetworking.h] |
||
5508 | * header pulls in system headers that will define most of the |
||
5509 | * standard/portable socket options. For unusual socket protocols or |
||
5510 | * platform-dependent options, you may need to include additional |
||
5511 | * headers. |
||
5512 | * |
||
5513 | * Returns: success or failure. On failure, @error will be set, and |
||
5514 | * the system error value (`errno` or WSAGetLastError()) will still |
||
5515 | * be set to the result of the setsockopt() call. |
||
5516 | * |
||
5517 | * Since: 2.36 |
||
5518 | */ |
||
5519 | gboolean |
||
5520 | g_socket_set_option (GSocket *socket, |
||
5521 | gint level, |
||
5522 | gint optname, |
||
5523 | gint value, |
||
5524 | GError **error) |
||
5525 | { |
||
5526 | gint errsv; |
||
5527 | |||
5528 | g_return_val_if_fail (G_IS_SOCKET (socket), FALSE); |
||
5529 | |||
5530 | if (setsockopt (socket->priv->fd, level, optname, &value, sizeof (gint)) == 0) |
||
5531 | return TRUE; |
||
5532 | |||
5533 | #if !defined (__linux__) && !defined (G_OS_WIN32) |
||
5534 | /* Linux and Windows let you set a single-byte value from an int, |
||
5535 | * but most other platforms don't. |
||
5536 | */ |
||
5537 | if (errno == EINVAL && value >= SCHAR_MIN && value <= CHAR_MAX) |
||
5538 | { |
||
5539 | #if G_BYTE_ORDER == G_BIG_ENDIAN |
||
5540 | value = value << (8 * (sizeof (gint) - 1)); |
||
5541 | #endif |
||
5542 | if (setsockopt (socket->priv->fd, level, optname, &value, 1) == 0) |
||
5543 | return TRUE; |
||
5544 | } |
||
5545 | #endif |
||
5546 | |||
5547 | errsv = get_socket_errno (); |
||
5548 | |||
5549 | g_set_error_literal (error, |
||
5550 | G_IO_ERROR, |
||
5551 | socket_io_error_from_errno (errsv), |
||
5552 | socket_strerror (errsv)); |
||
5553 | #ifndef G_OS_WIN32 |
||
5554 | errno = errsv; |
||
5555 | #endif |
||
5556 | return FALSE; |
||
5557 | } |
||
5558 |