swrap: Add a mutex for resetting socket index
[socket_wrapper.git] / src / socket_wrapper.c
1 /*
2  * BSD 3-Clause License
3  *
4  * Copyright (c) 2005-2008, Jelmer Vernooij <jelmer@samba.org>
5  * Copyright (c) 2006-2018, Stefan Metzmacher <metze@samba.org>
6  * Copyright (c) 2013-2018, Andreas Schneider <asn@samba.org>
7  * Copyright (c) 2014-2017, Michael Adam <obnox@samba.org>
8  * Copyright (c) 2016-2018, Anoop C S <anoopcs@redhat.com>
9  * All rights reserved.
10  *
11  * Redistribution and use in source and binary forms, with or without
12  * modification, are permitted provided that the following conditions
13  * are met:
14  *
15  * 1. Redistributions of source code must retain the above copyright
16  *    notice, this list of conditions and the following disclaimer.
17  *
18  * 2. Redistributions in binary form must reproduce the above copyright
19  *    notice, this list of conditions and the following disclaimer in the
20  *    documentation and/or other materials provided with the distribution.
21  *
22  * 3. Neither the name of the author nor the names of its contributors
23  *    may be used to endorse or promote products derived from this software
24  *    without specific prior written permission.
25  *
26  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
27  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
30  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
31  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
32  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
34  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36  * SUCH DAMAGE.
37  */
38
39 /*
40    Socket wrapper library. Passes all socket communication over
41    unix domain sockets if the environment variable SOCKET_WRAPPER_DIR
42    is set.
43 */
44
45 #include "config.h"
46
47 #include <sys/types.h>
48 #include <sys/time.h>
49 #include <sys/stat.h>
50 #include <sys/socket.h>
51 #include <sys/ioctl.h>
52 #ifdef HAVE_SYS_FILIO_H
53 #include <sys/filio.h>
54 #endif
55 #ifdef HAVE_SYS_SIGNALFD_H
56 #include <sys/signalfd.h>
57 #endif
58 #ifdef HAVE_SYS_EVENTFD_H
59 #include <sys/eventfd.h>
60 #endif
61 #ifdef HAVE_SYS_TIMERFD_H
62 #include <sys/timerfd.h>
63 #endif
64 #include <sys/uio.h>
65 #include <errno.h>
66 #include <sys/un.h>
67 #include <netinet/in.h>
68 #include <netinet/tcp.h>
69 #include <arpa/inet.h>
70 #include <fcntl.h>
71 #include <stdlib.h>
72 #include <string.h>
73 #include <stdio.h>
74 #include <stdint.h>
75 #include <stdarg.h>
76 #include <stdbool.h>
77 #include <unistd.h>
78 #ifdef HAVE_GNU_LIB_NAMES_H
79 #include <gnu/lib-names.h>
80 #endif
81 #ifdef HAVE_RPC_RPC_H
82 #include <rpc/rpc.h>
83 #endif
84 #include <pthread.h>
85
86 enum swrap_dbglvl_e {
87         SWRAP_LOG_ERROR = 0,
88         SWRAP_LOG_WARN,
89         SWRAP_LOG_DEBUG,
90         SWRAP_LOG_TRACE
91 };
92
93 /* GCC have printf type attribute check. */
94 #ifdef HAVE_FUNCTION_ATTRIBUTE_FORMAT
95 #define PRINTF_ATTRIBUTE(a,b) __attribute__ ((__format__ (__printf__, a, b)))
96 #else
97 #define PRINTF_ATTRIBUTE(a,b)
98 #endif /* HAVE_FUNCTION_ATTRIBUTE_FORMAT */
99
100 #ifdef HAVE_CONSTRUCTOR_ATTRIBUTE
101 #define CONSTRUCTOR_ATTRIBUTE __attribute__ ((constructor))
102 #else
103 #define CONSTRUCTOR_ATTRIBUTE
104 #endif /* HAVE_CONSTRUCTOR_ATTRIBUTE */
105
106 #ifdef HAVE_DESTRUCTOR_ATTRIBUTE
107 #define DESTRUCTOR_ATTRIBUTE __attribute__ ((destructor))
108 #else
109 #define DESTRUCTOR_ATTRIBUTE
110 #endif
111
112 #ifndef FALL_THROUGH
113 # ifdef HAVE_FALLTHROUGH_ATTRIBUTE
114 #  define FALL_THROUGH __attribute__ ((fallthrough))
115 # else /* HAVE_FALLTHROUGH_ATTRIBUTE */
116 #  define FALL_THROUGH ((void)0)
117 # endif /* HAVE_FALLTHROUGH_ATTRIBUTE */
118 #endif /* FALL_THROUGH */
119
120 #ifdef HAVE_ADDRESS_SANITIZER_ATTRIBUTE
121 #define DO_NOT_SANITIZE_ADDRESS_ATTRIBUTE __attribute__((no_sanitize_address))
122 #else
123 #define DO_NOT_SANITIZE_ADDRESS_ATTRIBUTE
124 #endif
125
126 #ifdef HAVE_GCC_THREAD_LOCAL_STORAGE
127 # define SWRAP_THREAD __thread
128 #else
129 # define SWRAP_THREAD
130 #endif
131
132 #ifndef MIN
133 #define MIN(a,b) ((a)<(b)?(a):(b))
134 #endif
135
136 #ifndef ZERO_STRUCT
137 #define ZERO_STRUCT(x) memset((char *)&(x), 0, sizeof(x))
138 #endif
139
140 #ifndef ZERO_STRUCTP
141 #define ZERO_STRUCTP(x) do { \
142                 if ((x) != NULL) \
143                         memset((char *)(x), 0, sizeof(*(x))); \
144         } while(0)
145 #endif
146
147 #ifndef SAFE_FREE
148 #define SAFE_FREE(x) do { if ((x) != NULL) {free(x); (x)=NULL;} } while(0)
149 #endif
150
151 #ifndef discard_const
152 #define discard_const(ptr) ((void *)((uintptr_t)(ptr)))
153 #endif
154
155 #ifndef discard_const_p
156 #define discard_const_p(type, ptr) ((type *)discard_const(ptr))
157 #endif
158
159 #define UNUSED(x) (void)(x)
160
161 #ifdef IPV6_PKTINFO
162 # ifndef IPV6_RECVPKTINFO
163 #  define IPV6_RECVPKTINFO IPV6_PKTINFO
164 # endif /* IPV6_RECVPKTINFO */
165 #endif /* IPV6_PKTINFO */
166
167 /*
168  * On BSD IP_PKTINFO has a different name because during
169  * the time when they implemented it, there was no RFC.
170  * The name for IPv6 is the same as on Linux.
171  */
172 #ifndef IP_PKTINFO
173 # ifdef IP_RECVDSTADDR
174 #  define IP_PKTINFO IP_RECVDSTADDR
175 # endif
176 #endif
177
178 /* Add new global locks here please */
179 # define SWRAP_LOCK_ALL \
180         swrap_mutex_lock(&libc_symbol_binding_mutex); \
181
182 # define SWRAP_UNLOCK_ALL \
183         swrap_mutex_unlock(&libc_symbol_binding_mutex); \
184
185 #define SOCKET_INFO_CONTAINER(si) \
186         (struct socket_info_container *)(si)
187
188 #define SWRAP_LOCK_SI(si) do { \
189         struct socket_info_container *sic = SOCKET_INFO_CONTAINER(si); \
190         swrap_mutex_lock(&sic->meta.mutex); \
191 } while(0)
192
193 #define SWRAP_UNLOCK_SI(si) do { \
194         struct socket_info_container *sic = SOCKET_INFO_CONTAINER(si); \
195         swrap_mutex_unlock(&sic->meta.mutex); \
196 } while(0)
197
198 #if defined(HAVE_GETTIMEOFDAY_TZ) || defined(HAVE_GETTIMEOFDAY_TZ_VOID)
199 #define swrapGetTimeOfDay(tval) gettimeofday(tval,NULL)
200 #else
201 #define swrapGetTimeOfDay(tval) gettimeofday(tval)
202 #endif
203
204 /* we need to use a very terse format here as IRIX 6.4 silently
205    truncates names to 16 chars, so if we use a longer name then we
206    can't tell which port a packet came from with recvfrom()
207
208    with this format we have 8 chars left for the directory name
209 */
210 #define SOCKET_FORMAT "%c%02X%04X"
211 #define SOCKET_TYPE_CHAR_TCP            'T'
212 #define SOCKET_TYPE_CHAR_UDP            'U'
213 #define SOCKET_TYPE_CHAR_TCP_V6         'X'
214 #define SOCKET_TYPE_CHAR_UDP_V6         'Y'
215
216 /*
217  * Set the packet MTU to 1500 bytes for stream sockets to make it it easier to
218  * format PCAP capture files (as the caller will simply continue from here).
219  */
220 #define SOCKET_WRAPPER_MTU_DEFAULT 1500
221 #define SOCKET_WRAPPER_MTU_MIN     512
222 #define SOCKET_WRAPPER_MTU_MAX     32768
223
224 #define SOCKET_MAX_SOCKETS 1024
225
226 /*
227  * Maximum number of socket_info structures that can
228  * be used. Can be overriden by the environment variable
229  * SOCKET_WRAPPER_MAX_SOCKETS.
230  */
231 #define SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT 65535
232
233 #define SOCKET_WRAPPER_MAX_SOCKETS_LIMIT 256000
234
235 /* This limit is to avoid broadcast sendto() needing to stat too many
236  * files.  It may be raised (with a performance cost) to up to 254
237  * without changing the format above */
238 #define MAX_WRAPPED_INTERFACES 64
239
240 struct swrap_address {
241         socklen_t sa_socklen;
242         union {
243                 struct sockaddr s;
244                 struct sockaddr_in in;
245 #ifdef HAVE_IPV6
246                 struct sockaddr_in6 in6;
247 #endif
248                 struct sockaddr_un un;
249                 struct sockaddr_storage ss;
250         } sa;
251 };
252
253 int first_free;
254
255 struct socket_info
256 {
257         int family;
258         int type;
259         int protocol;
260         int bound;
261         int bcast;
262         int is_server;
263         int connected;
264         int defer_connect;
265         int pktinfo;
266         int tcp_nodelay;
267
268         /* The unix path so we can unlink it on close() */
269         struct sockaddr_un un_addr;
270
271         struct swrap_address bindname;
272         struct swrap_address myname;
273         struct swrap_address peername;
274
275         struct {
276                 unsigned long pck_snd;
277                 unsigned long pck_rcv;
278         } io;
279 };
280
281 struct socket_info_meta
282 {
283         unsigned int refcount;
284         int next_free;
285         pthread_mutex_t mutex;
286 };
287
288 struct socket_info_container
289 {
290         struct socket_info info;
291         struct socket_info_meta meta;
292 };
293
294 static struct socket_info_container *sockets;
295
296 static size_t max_sockets = 0;
297
298 /* Hash table to map fds to corresponding socket_info index */
299 static int *socket_fds_idx;
300
301 /* Mutex to synchronize access to global libc.symbols */
302 static pthread_mutex_t libc_symbol_binding_mutex = PTHREAD_MUTEX_INITIALIZER;
303
304 /* Mutex for syncronizing port selection during swrap_auto_bind() */
305 static pthread_mutex_t autobind_start_mutex;
306
307 /* Mutex to guard the initialization of array of socket_info structures */
308 static pthread_mutex_t sockets_mutex;
309
310 /* Mutex to guard the socket reset in swrap_close() and swrap_remove_stale() */
311 static pthread_mutex_t socket_reset_mutex;
312
313 /* Mutex to synchronize access to first free index in socket_info array */
314 static pthread_mutex_t first_free_mutex;
315
316 /* Mutex to synchronize access to packet capture dump file */
317 static pthread_mutex_t pcap_dump_mutex;
318
319 /* Mutex for synchronizing mtu value fetch*/
320 static pthread_mutex_t mtu_update_mutex;
321
322 /* Function prototypes */
323
324 bool socket_wrapper_enabled(void);
325
326 void swrap_constructor(void) CONSTRUCTOR_ATTRIBUTE;
327 void swrap_destructor(void) DESTRUCTOR_ATTRIBUTE;
328
329 static void swrap_log(enum swrap_dbglvl_e dbglvl, const char *func, const char *format, ...) PRINTF_ATTRIBUTE(3, 4);
330 # define SWRAP_LOG(dbglvl, ...) swrap_log((dbglvl), __func__, __VA_ARGS__)
331
332 static void swrap_log(enum swrap_dbglvl_e dbglvl,
333                       const char *func,
334                       const char *format, ...)
335 {
336         char buffer[1024];
337         va_list va;
338         const char *d;
339         unsigned int lvl = 0;
340         const char *prefix = "SWRAP";
341
342         d = getenv("SOCKET_WRAPPER_DEBUGLEVEL");
343         if (d != NULL) {
344                 lvl = atoi(d);
345         }
346
347         if (lvl < dbglvl) {
348                 return;
349         }
350
351         va_start(va, format);
352         vsnprintf(buffer, sizeof(buffer), format, va);
353         va_end(va);
354
355         switch (dbglvl) {
356                 case SWRAP_LOG_ERROR:
357                         prefix = "SWRAP_ERROR";
358                         break;
359                 case SWRAP_LOG_WARN:
360                         prefix = "SWRAP_WARN";
361                         break;
362                 case SWRAP_LOG_DEBUG:
363                         prefix = "SWRAP_DEBUG";
364                         break;
365                 case SWRAP_LOG_TRACE:
366                         prefix = "SWRAP_TRACE";
367                         break;
368         }
369
370         fprintf(stderr,
371                 "%s(%d) - %s: %s\n",
372                 prefix, (int)getpid(), func, buffer);
373 }
374
375 /*********************************************************
376  * SWRAP LOADING LIBC FUNCTIONS
377  *********************************************************/
378
379 #include <dlfcn.h>
380
381 #ifdef HAVE_ACCEPT4
382 typedef int (*__libc_accept4)(int sockfd,
383                               struct sockaddr *addr,
384                               socklen_t *addrlen,
385                               int flags);
386 #else
387 typedef int (*__libc_accept)(int sockfd,
388                              struct sockaddr *addr,
389                              socklen_t *addrlen);
390 #endif
391 typedef int (*__libc_bind)(int sockfd,
392                            const struct sockaddr *addr,
393                            socklen_t addrlen);
394 typedef int (*__libc_close)(int fd);
395 typedef int (*__libc_connect)(int sockfd,
396                               const struct sockaddr *addr,
397                               socklen_t addrlen);
398 typedef int (*__libc_dup)(int fd);
399 typedef int (*__libc_dup2)(int oldfd, int newfd);
400 typedef int (*__libc_fcntl)(int fd, int cmd, ...);
401 typedef FILE *(*__libc_fopen)(const char *name, const char *mode);
402 #ifdef HAVE_FOPEN64
403 typedef FILE *(*__libc_fopen64)(const char *name, const char *mode);
404 #endif
405 #ifdef HAVE_EVENTFD
406 typedef int (*__libc_eventfd)(int count, int flags);
407 #endif
408 typedef int (*__libc_getpeername)(int sockfd,
409                                   struct sockaddr *addr,
410                                   socklen_t *addrlen);
411 typedef int (*__libc_getsockname)(int sockfd,
412                                   struct sockaddr *addr,
413                                   socklen_t *addrlen);
414 typedef int (*__libc_getsockopt)(int sockfd,
415                                int level,
416                                int optname,
417                                void *optval,
418                                socklen_t *optlen);
419 typedef int (*__libc_ioctl)(int d, unsigned long int request, ...);
420 typedef int (*__libc_listen)(int sockfd, int backlog);
421 typedef int (*__libc_open)(const char *pathname, int flags, ...);
422 #ifdef HAVE_OPEN64
423 typedef int (*__libc_open64)(const char *pathname, int flags, ...);
424 #endif /* HAVE_OPEN64 */
425 typedef int (*__libc_openat)(int dirfd, const char *path, int flags, ...);
426 typedef int (*__libc_pipe)(int pipefd[2]);
427 typedef int (*__libc_read)(int fd, void *buf, size_t count);
428 typedef ssize_t (*__libc_readv)(int fd, const struct iovec *iov, int iovcnt);
429 typedef int (*__libc_recv)(int sockfd, void *buf, size_t len, int flags);
430 typedef int (*__libc_recvfrom)(int sockfd,
431                              void *buf,
432                              size_t len,
433                              int flags,
434                              struct sockaddr *src_addr,
435                              socklen_t *addrlen);
436 typedef int (*__libc_recvmsg)(int sockfd, const struct msghdr *msg, int flags);
437 typedef int (*__libc_send)(int sockfd, const void *buf, size_t len, int flags);
438 typedef int (*__libc_sendmsg)(int sockfd, const struct msghdr *msg, int flags);
439 typedef int (*__libc_sendto)(int sockfd,
440                            const void *buf,
441                            size_t len,
442                            int flags,
443                            const  struct sockaddr *dst_addr,
444                            socklen_t addrlen);
445 typedef int (*__libc_setsockopt)(int sockfd,
446                                int level,
447                                int optname,
448                                const void *optval,
449                                socklen_t optlen);
450 #ifdef HAVE_SIGNALFD
451 typedef int (*__libc_signalfd)(int fd, const sigset_t *mask, int flags);
452 #endif
453 typedef int (*__libc_socket)(int domain, int type, int protocol);
454 typedef int (*__libc_socketpair)(int domain, int type, int protocol, int sv[2]);
455 #ifdef HAVE_TIMERFD_CREATE
456 typedef int (*__libc_timerfd_create)(int clockid, int flags);
457 #endif
458 typedef ssize_t (*__libc_write)(int fd, const void *buf, size_t count);
459 typedef ssize_t (*__libc_writev)(int fd, const struct iovec *iov, int iovcnt);
460
461 #define SWRAP_SYMBOL_ENTRY(i) \
462         union { \
463                 __libc_##i f; \
464                 void *obj; \
465         } _libc_##i
466
467 struct swrap_libc_symbols {
468 #ifdef HAVE_ACCEPT4
469         SWRAP_SYMBOL_ENTRY(accept4);
470 #else
471         SWRAP_SYMBOL_ENTRY(accept);
472 #endif
473         SWRAP_SYMBOL_ENTRY(bind);
474         SWRAP_SYMBOL_ENTRY(close);
475         SWRAP_SYMBOL_ENTRY(connect);
476         SWRAP_SYMBOL_ENTRY(dup);
477         SWRAP_SYMBOL_ENTRY(dup2);
478         SWRAP_SYMBOL_ENTRY(fcntl);
479         SWRAP_SYMBOL_ENTRY(fopen);
480 #ifdef HAVE_FOPEN64
481         SWRAP_SYMBOL_ENTRY(fopen64);
482 #endif
483 #ifdef HAVE_EVENTFD
484         SWRAP_SYMBOL_ENTRY(eventfd);
485 #endif
486         SWRAP_SYMBOL_ENTRY(getpeername);
487         SWRAP_SYMBOL_ENTRY(getsockname);
488         SWRAP_SYMBOL_ENTRY(getsockopt);
489         SWRAP_SYMBOL_ENTRY(ioctl);
490         SWRAP_SYMBOL_ENTRY(listen);
491         SWRAP_SYMBOL_ENTRY(open);
492 #ifdef HAVE_OPEN64
493         SWRAP_SYMBOL_ENTRY(open64);
494 #endif
495         SWRAP_SYMBOL_ENTRY(openat);
496         SWRAP_SYMBOL_ENTRY(pipe);
497         SWRAP_SYMBOL_ENTRY(read);
498         SWRAP_SYMBOL_ENTRY(readv);
499         SWRAP_SYMBOL_ENTRY(recv);
500         SWRAP_SYMBOL_ENTRY(recvfrom);
501         SWRAP_SYMBOL_ENTRY(recvmsg);
502         SWRAP_SYMBOL_ENTRY(send);
503         SWRAP_SYMBOL_ENTRY(sendmsg);
504         SWRAP_SYMBOL_ENTRY(sendto);
505         SWRAP_SYMBOL_ENTRY(setsockopt);
506 #ifdef HAVE_SIGNALFD
507         SWRAP_SYMBOL_ENTRY(signalfd);
508 #endif
509         SWRAP_SYMBOL_ENTRY(socket);
510         SWRAP_SYMBOL_ENTRY(socketpair);
511 #ifdef HAVE_TIMERFD_CREATE
512         SWRAP_SYMBOL_ENTRY(timerfd_create);
513 #endif
514         SWRAP_SYMBOL_ENTRY(write);
515         SWRAP_SYMBOL_ENTRY(writev);
516 };
517
518 struct swrap {
519         struct {
520                 void *handle;
521                 void *socket_handle;
522                 struct swrap_libc_symbols symbols;
523         } libc;
524 };
525
526 static struct swrap swrap;
527
528 /* prototypes */
529 static const char *socket_wrapper_dir(void);
530
531 #define LIBC_NAME "libc.so"
532
533 enum swrap_lib {
534     SWRAP_LIBC,
535     SWRAP_LIBNSL,
536     SWRAP_LIBSOCKET,
537 };
538
539 static const char *swrap_str_lib(enum swrap_lib lib)
540 {
541         switch (lib) {
542         case SWRAP_LIBC:
543                 return "libc";
544         case SWRAP_LIBNSL:
545                 return "libnsl";
546         case SWRAP_LIBSOCKET:
547                 return "libsocket";
548         }
549
550         /* Compiler would warn us about unhandled enum value if we get here */
551         return "unknown";
552 }
553
554 static void *swrap_load_lib_handle(enum swrap_lib lib)
555 {
556         int flags = RTLD_LAZY;
557         void *handle = NULL;
558         int i;
559
560 #ifdef RTLD_DEEPBIND
561         flags |= RTLD_DEEPBIND;
562 #endif
563
564         switch (lib) {
565         case SWRAP_LIBNSL:
566                 FALL_THROUGH;
567         case SWRAP_LIBSOCKET:
568 #ifdef HAVE_LIBSOCKET
569                 handle = swrap.libc.socket_handle;
570                 if (handle == NULL) {
571                         for (i = 10; i >= 0; i--) {
572                                 char soname[256] = {0};
573
574                                 snprintf(soname, sizeof(soname), "libsocket.so.%d", i);
575                                 handle = dlopen(soname, flags);
576                                 if (handle != NULL) {
577                                         break;
578                                 }
579                         }
580
581                         swrap.libc.socket_handle = handle;
582                 }
583                 break;
584 #endif
585                 FALL_THROUGH;
586         case SWRAP_LIBC:
587                 handle = swrap.libc.handle;
588 #ifdef LIBC_SO
589                 if (handle == NULL) {
590                         handle = dlopen(LIBC_SO, flags);
591
592                         swrap.libc.handle = handle;
593                 }
594 #endif
595                 if (handle == NULL) {
596                         for (i = 10; i >= 0; i--) {
597                                 char soname[256] = {0};
598
599                                 snprintf(soname, sizeof(soname), "libc.so.%d", i);
600                                 handle = dlopen(soname, flags);
601                                 if (handle != NULL) {
602                                         break;
603                                 }
604                         }
605
606                         swrap.libc.handle = handle;
607                 }
608                 break;
609         }
610
611         if (handle == NULL) {
612 #ifdef RTLD_NEXT
613                 handle = swrap.libc.handle = swrap.libc.socket_handle = RTLD_NEXT;
614 #else
615                 SWRAP_LOG(SWRAP_LOG_ERROR,
616                           "Failed to dlopen library: %s\n",
617                           dlerror());
618                 exit(-1);
619 #endif
620         }
621
622         return handle;
623 }
624
625 static void *_swrap_bind_symbol(enum swrap_lib lib, const char *fn_name)
626 {
627         void *handle;
628         void *func;
629
630         handle = swrap_load_lib_handle(lib);
631
632         func = dlsym(handle, fn_name);
633         if (func == NULL) {
634                 SWRAP_LOG(SWRAP_LOG_ERROR,
635                           "Failed to find %s: %s\n",
636                           fn_name,
637                           dlerror());
638                 exit(-1);
639         }
640
641         SWRAP_LOG(SWRAP_LOG_TRACE,
642                   "Loaded %s from %s",
643                   fn_name,
644                   swrap_str_lib(lib));
645
646         return func;
647 }
648
649 static void swrap_mutex_lock(pthread_mutex_t *mutex)
650 {
651         int ret;
652
653         ret = pthread_mutex_lock(mutex);
654         if (ret != 0) {
655                 SWRAP_LOG(SWRAP_LOG_ERROR, "Couldn't lock pthread mutex - %s",
656                           strerror(ret));
657         }
658 }
659
660 static void swrap_mutex_unlock(pthread_mutex_t *mutex)
661 {
662         int ret;
663
664         ret = pthread_mutex_unlock(mutex);
665         if (ret != 0) {
666                 SWRAP_LOG(SWRAP_LOG_ERROR, "Couldn't unlock pthread mutex - %s",
667                           strerror(ret));
668         }
669 }
670
671 /*
672  * These macros have a thread race condition on purpose!
673  *
674  * This is an optimization to avoid locking each time we check if the symbol is
675  * bound.
676  */
677 #define swrap_bind_symbol_libc(sym_name) \
678         if (swrap.libc.symbols._libc_##sym_name.obj == NULL) { \
679                 swrap_mutex_lock(&libc_symbol_binding_mutex); \
680                 if (swrap.libc.symbols._libc_##sym_name.obj == NULL) { \
681                         swrap.libc.symbols._libc_##sym_name.obj = \
682                                 _swrap_bind_symbol(SWRAP_LIBC, #sym_name); \
683                 } \
684                 swrap_mutex_unlock(&libc_symbol_binding_mutex); \
685         }
686
687 #define swrap_bind_symbol_libsocket(sym_name) \
688         if (swrap.libc.symbols._libc_##sym_name.obj == NULL) { \
689                 swrap_mutex_lock(&libc_symbol_binding_mutex); \
690                 if (swrap.libc.symbols._libc_##sym_name.obj == NULL) { \
691                         swrap.libc.symbols._libc_##sym_name.obj = \
692                                 _swrap_bind_symbol(SWRAP_LIBSOCKET, #sym_name); \
693                 } \
694                 swrap_mutex_unlock(&libc_symbol_binding_mutex); \
695         }
696
697 #define swrap_bind_symbol_libnsl(sym_name) \
698         if (swrap.libc.symbols._libc_##sym_name.obj == NULL) { \
699                 swrap_mutex_lock(&libc_symbol_binding_mutex); \
700                 if (swrap.libc.symbols._libc_##sym_name.obj == NULL) { \
701                         swrap.libc.symbols._libc_##sym_name.obj = \
702                                 _swrap_bind_symbol(SWRAP_LIBNSL, #sym_name); \
703                 } \
704                 swrap_mutex_unlock(&libc_symbol_binding_mutex); \
705         }
706
707 /****************************************************************************
708  *                               IMPORTANT
709  ****************************************************************************
710  *
711  * Functions especially from libc need to be loaded individually, you can't
712  * load all at once or gdb will segfault at startup. The same applies to
713  * valgrind and has probably something todo with with the linker.  So we need
714  * load each function at the point it is called the first time.
715  *
716  ****************************************************************************/
717
718 #ifdef HAVE_ACCEPT4
719 static int libc_accept4(int sockfd,
720                         struct sockaddr *addr,
721                         socklen_t *addrlen,
722                         int flags)
723 {
724         swrap_bind_symbol_libsocket(accept4);
725
726         return swrap.libc.symbols._libc_accept4.f(sockfd, addr, addrlen, flags);
727 }
728
729 #else /* HAVE_ACCEPT4 */
730
731 static int libc_accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen)
732 {
733         swrap_bind_symbol_libsocket(accept);
734
735         return swrap.libc.symbols._libc_accept.f(sockfd, addr, addrlen);
736 }
737 #endif /* HAVE_ACCEPT4 */
738
739 static int libc_bind(int sockfd,
740                      const struct sockaddr *addr,
741                      socklen_t addrlen)
742 {
743         swrap_bind_symbol_libsocket(bind);
744
745         return swrap.libc.symbols._libc_bind.f(sockfd, addr, addrlen);
746 }
747
748 static int libc_close(int fd)
749 {
750         swrap_bind_symbol_libc(close);
751
752         return swrap.libc.symbols._libc_close.f(fd);
753 }
754
755 static int libc_connect(int sockfd,
756                         const struct sockaddr *addr,
757                         socklen_t addrlen)
758 {
759         swrap_bind_symbol_libsocket(connect);
760
761         return swrap.libc.symbols._libc_connect.f(sockfd, addr, addrlen);
762 }
763
764 static int libc_dup(int fd)
765 {
766         swrap_bind_symbol_libc(dup);
767
768         return swrap.libc.symbols._libc_dup.f(fd);
769 }
770
771 static int libc_dup2(int oldfd, int newfd)
772 {
773         swrap_bind_symbol_libc(dup2);
774
775         return swrap.libc.symbols._libc_dup2.f(oldfd, newfd);
776 }
777
778 #ifdef HAVE_EVENTFD
779 static int libc_eventfd(int count, int flags)
780 {
781         swrap_bind_symbol_libc(eventfd);
782
783         return swrap.libc.symbols._libc_eventfd.f(count, flags);
784 }
785 #endif
786
787 DO_NOT_SANITIZE_ADDRESS_ATTRIBUTE
788 static int libc_vfcntl(int fd, int cmd, va_list ap)
789 {
790         void *arg;
791         int rc;
792
793         swrap_bind_symbol_libc(fcntl);
794
795         arg = va_arg(ap, void *);
796
797         rc = swrap.libc.symbols._libc_fcntl.f(fd, cmd, arg);
798
799         return rc;
800 }
801
802 static int libc_getpeername(int sockfd,
803                             struct sockaddr *addr,
804                             socklen_t *addrlen)
805 {
806         swrap_bind_symbol_libsocket(getpeername);
807
808         return swrap.libc.symbols._libc_getpeername.f(sockfd, addr, addrlen);
809 }
810
811 static int libc_getsockname(int sockfd,
812                             struct sockaddr *addr,
813                             socklen_t *addrlen)
814 {
815         swrap_bind_symbol_libsocket(getsockname);
816
817         return swrap.libc.symbols._libc_getsockname.f(sockfd, addr, addrlen);
818 }
819
820 static int libc_getsockopt(int sockfd,
821                            int level,
822                            int optname,
823                            void *optval,
824                            socklen_t *optlen)
825 {
826         swrap_bind_symbol_libsocket(getsockopt);
827
828         return swrap.libc.symbols._libc_getsockopt.f(sockfd,
829                                                      level,
830                                                      optname,
831                                                      optval,
832                                                      optlen);
833 }
834
835 DO_NOT_SANITIZE_ADDRESS_ATTRIBUTE
836 static int libc_vioctl(int d, unsigned long int request, va_list ap)
837 {
838         void *arg;
839         int rc;
840
841         swrap_bind_symbol_libc(ioctl);
842
843         arg = va_arg(ap, void *);
844
845         rc = swrap.libc.symbols._libc_ioctl.f(d, request, arg);
846
847         return rc;
848 }
849
850 static int libc_listen(int sockfd, int backlog)
851 {
852         swrap_bind_symbol_libsocket(listen);
853
854         return swrap.libc.symbols._libc_listen.f(sockfd, backlog);
855 }
856
857 static FILE *libc_fopen(const char *name, const char *mode)
858 {
859         swrap_bind_symbol_libc(fopen);
860
861         return swrap.libc.symbols._libc_fopen.f(name, mode);
862 }
863
864 #ifdef HAVE_FOPEN64
865 static FILE *libc_fopen64(const char *name, const char *mode)
866 {
867         swrap_bind_symbol_libc(fopen64);
868
869         return swrap.libc.symbols._libc_fopen64.f(name, mode);
870 }
871 #endif /* HAVE_FOPEN64 */
872
873 static int libc_vopen(const char *pathname, int flags, va_list ap)
874 {
875         int mode = 0;
876         int fd;
877
878         swrap_bind_symbol_libc(open);
879
880         if (flags & O_CREAT) {
881                 mode = va_arg(ap, int);
882         }
883         fd = swrap.libc.symbols._libc_open.f(pathname, flags, (mode_t)mode);
884
885         return fd;
886 }
887
888 static int libc_open(const char *pathname, int flags, ...)
889 {
890         va_list ap;
891         int fd;
892
893         va_start(ap, flags);
894         fd = libc_vopen(pathname, flags, ap);
895         va_end(ap);
896
897         return fd;
898 }
899
900 #ifdef HAVE_OPEN64
901 static int libc_vopen64(const char *pathname, int flags, va_list ap)
902 {
903         int mode = 0;
904         int fd;
905
906         swrap_bind_symbol_libc(open64);
907
908         if (flags & O_CREAT) {
909                 mode = va_arg(ap, int);
910         }
911         fd = swrap.libc.symbols._libc_open64.f(pathname, flags, (mode_t)mode);
912
913         return fd;
914 }
915 #endif /* HAVE_OPEN64 */
916
917 static int libc_vopenat(int dirfd, const char *path, int flags, va_list ap)
918 {
919         int mode = 0;
920         int fd;
921
922         swrap_bind_symbol_libc(openat);
923
924         if (flags & O_CREAT) {
925                 mode = va_arg(ap, int);
926         }
927         fd = swrap.libc.symbols._libc_openat.f(dirfd,
928                                                path,
929                                                flags,
930                                                (mode_t)mode);
931
932         return fd;
933 }
934
935 #if 0
936 static int libc_openat(int dirfd, const char *path, int flags, ...)
937 {
938         va_list ap;
939         int fd;
940
941         va_start(ap, flags);
942         fd = libc_vopenat(dirfd, path, flags, ap);
943         va_end(ap);
944
945         return fd;
946 }
947 #endif
948
949 static int libc_pipe(int pipefd[2])
950 {
951         swrap_bind_symbol_libsocket(pipe);
952
953         return swrap.libc.symbols._libc_pipe.f(pipefd);
954 }
955
956 static int libc_read(int fd, void *buf, size_t count)
957 {
958         swrap_bind_symbol_libc(read);
959
960         return swrap.libc.symbols._libc_read.f(fd, buf, count);
961 }
962
963 static ssize_t libc_readv(int fd, const struct iovec *iov, int iovcnt)
964 {
965         swrap_bind_symbol_libsocket(readv);
966
967         return swrap.libc.symbols._libc_readv.f(fd, iov, iovcnt);
968 }
969
970 static int libc_recv(int sockfd, void *buf, size_t len, int flags)
971 {
972         swrap_bind_symbol_libsocket(recv);
973
974         return swrap.libc.symbols._libc_recv.f(sockfd, buf, len, flags);
975 }
976
977 static int libc_recvfrom(int sockfd,
978                          void *buf,
979                          size_t len,
980                          int flags,
981                          struct sockaddr *src_addr,
982                          socklen_t *addrlen)
983 {
984         swrap_bind_symbol_libsocket(recvfrom);
985
986         return swrap.libc.symbols._libc_recvfrom.f(sockfd,
987                                                    buf,
988                                                    len,
989                                                    flags,
990                                                    src_addr,
991                                                    addrlen);
992 }
993
994 static int libc_recvmsg(int sockfd, struct msghdr *msg, int flags)
995 {
996         swrap_bind_symbol_libsocket(recvmsg);
997
998         return swrap.libc.symbols._libc_recvmsg.f(sockfd, msg, flags);
999 }
1000
1001 static int libc_send(int sockfd, const void *buf, size_t len, int flags)
1002 {
1003         swrap_bind_symbol_libsocket(send);
1004
1005         return swrap.libc.symbols._libc_send.f(sockfd, buf, len, flags);
1006 }
1007
1008 static int libc_sendmsg(int sockfd, const struct msghdr *msg, int flags)
1009 {
1010         swrap_bind_symbol_libsocket(sendmsg);
1011
1012         return swrap.libc.symbols._libc_sendmsg.f(sockfd, msg, flags);
1013 }
1014
1015 static int libc_sendto(int sockfd,
1016                        const void *buf,
1017                        size_t len,
1018                        int flags,
1019                        const  struct sockaddr *dst_addr,
1020                        socklen_t addrlen)
1021 {
1022         swrap_bind_symbol_libsocket(sendto);
1023
1024         return swrap.libc.symbols._libc_sendto.f(sockfd,
1025                                                  buf,
1026                                                  len,
1027                                                  flags,
1028                                                  dst_addr,
1029                                                  addrlen);
1030 }
1031
1032 static int libc_setsockopt(int sockfd,
1033                            int level,
1034                            int optname,
1035                            const void *optval,
1036                            socklen_t optlen)
1037 {
1038         swrap_bind_symbol_libsocket(setsockopt);
1039
1040         return swrap.libc.symbols._libc_setsockopt.f(sockfd,
1041                                                      level,
1042                                                      optname,
1043                                                      optval,
1044                                                      optlen);
1045 }
1046
1047 #ifdef HAVE_SIGNALFD
1048 static int libc_signalfd(int fd, const sigset_t *mask, int flags)
1049 {
1050         swrap_bind_symbol_libsocket(signalfd);
1051
1052         return swrap.libc.symbols._libc_signalfd.f(fd, mask, flags);
1053 }
1054 #endif
1055
1056 static int libc_socket(int domain, int type, int protocol)
1057 {
1058         swrap_bind_symbol_libsocket(socket);
1059
1060         return swrap.libc.symbols._libc_socket.f(domain, type, protocol);
1061 }
1062
1063 static int libc_socketpair(int domain, int type, int protocol, int sv[2])
1064 {
1065         swrap_bind_symbol_libsocket(socketpair);
1066
1067         return swrap.libc.symbols._libc_socketpair.f(domain, type, protocol, sv);
1068 }
1069
1070 #ifdef HAVE_TIMERFD_CREATE
1071 static int libc_timerfd_create(int clockid, int flags)
1072 {
1073         swrap_bind_symbol_libc(timerfd_create);
1074
1075         return swrap.libc.symbols._libc_timerfd_create.f(clockid, flags);
1076 }
1077 #endif
1078
1079 static ssize_t libc_write(int fd, const void *buf, size_t count)
1080 {
1081         swrap_bind_symbol_libc(write);
1082
1083         return swrap.libc.symbols._libc_write.f(fd, buf, count);
1084 }
1085
1086 static ssize_t libc_writev(int fd, const struct iovec *iov, int iovcnt)
1087 {
1088         swrap_bind_symbol_libsocket(writev);
1089
1090         return swrap.libc.symbols._libc_writev.f(fd, iov, iovcnt);
1091 }
1092
1093 /* DO NOT call this function during library initialization! */
1094 static void swrap_bind_symbol_all(void)
1095 {
1096 #ifdef HAVE_ACCEPT4
1097         swrap_bind_symbol_libsocket(accept4);
1098 #else
1099         swrap_bind_symbol_libsocket(accept);
1100 #endif
1101         swrap_bind_symbol_libsocket(bind);
1102         swrap_bind_symbol_libc(close);
1103         swrap_bind_symbol_libsocket(connect);
1104         swrap_bind_symbol_libc(dup);
1105         swrap_bind_symbol_libc(dup2);
1106         swrap_bind_symbol_libc(fcntl);
1107         swrap_bind_symbol_libc(fopen);
1108 #ifdef HAVE_FOPEN64
1109         swrap_bind_symbol_libc(fopen64);
1110 #endif
1111 #ifdef HAVE_EVENTFD
1112         swrap_bind_symbol_libc(eventfd);
1113 #endif
1114         swrap_bind_symbol_libsocket(getpeername);
1115         swrap_bind_symbol_libsocket(getsockname);
1116         swrap_bind_symbol_libsocket(getsockopt);
1117         swrap_bind_symbol_libc(ioctl);
1118         swrap_bind_symbol_libsocket(listen);
1119         swrap_bind_symbol_libc(open);
1120 #ifdef HAVE_OPEN64
1121         swrap_bind_symbol_libc(open64);
1122 #endif
1123         swrap_bind_symbol_libc(openat);
1124         swrap_bind_symbol_libsocket(pipe);
1125         swrap_bind_symbol_libc(read);
1126         swrap_bind_symbol_libsocket(readv);
1127         swrap_bind_symbol_libsocket(recv);
1128         swrap_bind_symbol_libsocket(recvfrom);
1129         swrap_bind_symbol_libsocket(recvmsg);
1130         swrap_bind_symbol_libsocket(send);
1131         swrap_bind_symbol_libsocket(sendmsg);
1132         swrap_bind_symbol_libsocket(sendto);
1133         swrap_bind_symbol_libsocket(setsockopt);
1134 #ifdef HAVE_SIGNALFD
1135         swrap_bind_symbol_libsocket(signalfd);
1136 #endif
1137         swrap_bind_symbol_libsocket(socket);
1138         swrap_bind_symbol_libsocket(socketpair);
1139 #ifdef HAVE_TIMERFD_CREATE
1140         swrap_bind_symbol_libc(timerfd_create);
1141 #endif
1142         swrap_bind_symbol_libc(write);
1143         swrap_bind_symbol_libsocket(writev);
1144 }
1145
1146 /*********************************************************
1147  * SWRAP HELPER FUNCTIONS
1148  *********************************************************/
1149
1150 #ifdef HAVE_IPV6
1151 /*
1152  * FD00::5357:5FXX
1153  */
1154 static const struct in6_addr *swrap_ipv6(void)
1155 {
1156         static struct in6_addr v;
1157         static int initialized;
1158         int ret;
1159
1160         if (initialized) {
1161                 return &v;
1162         }
1163         initialized = 1;
1164
1165         ret = inet_pton(AF_INET6, "FD00::5357:5F00", &v);
1166         if (ret <= 0) {
1167                 abort();
1168         }
1169
1170         return &v;
1171 }
1172 #endif
1173
1174 static void set_port(int family, int prt, struct swrap_address *addr)
1175 {
1176         switch (family) {
1177         case AF_INET:
1178                 addr->sa.in.sin_port = htons(prt);
1179                 break;
1180 #ifdef HAVE_IPV6
1181         case AF_INET6:
1182                 addr->sa.in6.sin6_port = htons(prt);
1183                 break;
1184 #endif
1185         }
1186 }
1187
1188 static size_t socket_length(int family)
1189 {
1190         switch (family) {
1191         case AF_INET:
1192                 return sizeof(struct sockaddr_in);
1193 #ifdef HAVE_IPV6
1194         case AF_INET6:
1195                 return sizeof(struct sockaddr_in6);
1196 #endif
1197         }
1198         return 0;
1199 }
1200
1201 static struct socket_info *swrap_get_socket_info(int si_index)
1202 {
1203         return (struct socket_info *)(&(sockets[si_index].info));
1204 }
1205
1206 static int swrap_get_refcount(struct socket_info *si)
1207 {
1208         struct socket_info_container *sic = SOCKET_INFO_CONTAINER(si);
1209         return sic->meta.refcount;
1210 }
1211
1212 static void swrap_inc_refcount(struct socket_info *si)
1213 {
1214         struct socket_info_container *sic = SOCKET_INFO_CONTAINER(si);
1215
1216         sic->meta.refcount += 1;
1217 }
1218
1219 static void swrap_dec_refcount(struct socket_info *si)
1220 {
1221         struct socket_info_container *sic = SOCKET_INFO_CONTAINER(si);
1222
1223         sic->meta.refcount -= 1;
1224 }
1225
1226 static int swrap_get_next_free(struct socket_info *si)
1227 {
1228         struct socket_info_container *sic = SOCKET_INFO_CONTAINER(si);
1229
1230         return sic->meta.next_free;
1231 }
1232
1233 static void swrap_set_next_free(struct socket_info *si, int next_free)
1234 {
1235         struct socket_info_container *sic = SOCKET_INFO_CONTAINER(si);
1236
1237         sic->meta.next_free = next_free;
1238 }
1239
1240 static const char *socket_wrapper_dir(void)
1241 {
1242         const char *s = getenv("SOCKET_WRAPPER_DIR");
1243         if (s == NULL) {
1244                 return NULL;
1245         }
1246         /* TODO use realpath(3) here, when we add support for threads */
1247         if (strncmp(s, "./", 2) == 0) {
1248                 s += 2;
1249         }
1250
1251         SWRAP_LOG(SWRAP_LOG_TRACE, "socket_wrapper_dir: %s", s);
1252         return s;
1253 }
1254
1255 static unsigned int socket_wrapper_mtu(void)
1256 {
1257         static unsigned int max_mtu = 0;
1258         unsigned int tmp;
1259         const char *s;
1260         char *endp;
1261
1262         swrap_mutex_lock(&mtu_update_mutex);
1263
1264         if (max_mtu != 0) {
1265                 goto done;
1266         }
1267
1268         max_mtu = SOCKET_WRAPPER_MTU_DEFAULT;
1269
1270         s = getenv("SOCKET_WRAPPER_MTU");
1271         if (s == NULL) {
1272                 goto done;
1273         }
1274
1275         tmp = strtol(s, &endp, 10);
1276         if (s == endp) {
1277                 goto done;
1278         }
1279
1280         if (tmp < SOCKET_WRAPPER_MTU_MIN || tmp > SOCKET_WRAPPER_MTU_MAX) {
1281                 goto done;
1282         }
1283         max_mtu = tmp;
1284
1285 done:
1286         swrap_mutex_unlock(&mtu_update_mutex);
1287         return max_mtu;
1288 }
1289
1290 static int socket_wrapper_init_mutex(pthread_mutex_t *m)
1291 {
1292         pthread_mutexattr_t ma;
1293         int ret;
1294
1295         ret = pthread_mutexattr_init(&ma);
1296         if (ret != 0) {
1297                 return ret;
1298         }
1299
1300         ret = pthread_mutexattr_settype(&ma, PTHREAD_MUTEX_ERRORCHECK);
1301         if (ret != 0) {
1302                 goto done;
1303         }
1304
1305         ret = pthread_mutex_init(m, &ma);
1306
1307 done:
1308         pthread_mutexattr_destroy(&ma);
1309
1310         return ret;
1311 }
1312
1313 static size_t socket_wrapper_max_sockets(void)
1314 {
1315         const char *s;
1316         unsigned long tmp;
1317         char *endp;
1318
1319         if (max_sockets != 0) {
1320                 return max_sockets;
1321         }
1322
1323         max_sockets = SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT;
1324
1325         s = getenv("SOCKET_WRAPPER_MAX_SOCKETS");
1326         if (s == NULL || s[0] == '\0') {
1327                 goto done;
1328         }
1329
1330         tmp = strtoul(s, &endp, 10);
1331         if (s == endp) {
1332                 goto done;
1333         }
1334         if (tmp == 0 || tmp > SOCKET_WRAPPER_MAX_SOCKETS_LIMIT) {
1335                 SWRAP_LOG(SWRAP_LOG_ERROR,
1336                           "Invalid number of sockets specified, using default.");
1337                 goto done;
1338         }
1339
1340         max_sockets = tmp;
1341
1342 done:
1343         return max_sockets;
1344 }
1345
1346 static void socket_wrapper_init_fds_idx(void)
1347 {
1348         int *tmp = NULL;
1349         size_t i;
1350
1351         if (socket_fds_idx != NULL) {
1352                 return;
1353         }
1354
1355         tmp = (int *)calloc(SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT, sizeof(int));
1356         if (tmp == NULL) {
1357                 SWRAP_LOG(SWRAP_LOG_ERROR,
1358                           "Failed to allocate socket fds index array: %s",
1359                           strerror(errno));
1360                 exit(-1);
1361         }
1362
1363         for (i = 0; i < SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT; i++) {
1364                 tmp[i] = -1;
1365         }
1366
1367         socket_fds_idx = tmp;
1368 }
1369
1370 static void socket_wrapper_init_sockets(void)
1371 {
1372         size_t i;
1373         int ret;
1374
1375         swrap_mutex_lock(&sockets_mutex);
1376
1377         if (sockets != NULL) {
1378                 swrap_mutex_unlock(&sockets_mutex);
1379                 return;
1380         }
1381
1382         socket_wrapper_init_fds_idx();
1383
1384         max_sockets = socket_wrapper_max_sockets();
1385
1386         sockets = (struct socket_info_container *)calloc(max_sockets,
1387                                         sizeof(struct socket_info_container));
1388
1389         if (sockets == NULL) {
1390                 SWRAP_LOG(SWRAP_LOG_ERROR,
1391                           "Failed to allocate sockets array: %s",
1392                           strerror(errno));
1393                 swrap_mutex_unlock(&sockets_mutex);
1394                 exit(-1);
1395         }
1396
1397         swrap_mutex_lock(&first_free_mutex);
1398
1399         first_free = 0;
1400
1401         for (i = 0; i < max_sockets; i++) {
1402                 swrap_set_next_free(&sockets[i].info, i+1);
1403                 ret = socket_wrapper_init_mutex(&sockets[i].meta.mutex);
1404                 if (ret != 0) {
1405                         SWRAP_LOG(SWRAP_LOG_ERROR,
1406                                   "Failed to initialize pthread mutex");
1407                         goto done;
1408                 }
1409         }
1410
1411         /* mark the end of the free list */
1412         swrap_set_next_free(&sockets[max_sockets-1].info, -1);
1413
1414         ret = socket_wrapper_init_mutex(&autobind_start_mutex);
1415         if (ret != 0) {
1416                 SWRAP_LOG(SWRAP_LOG_ERROR,
1417                           "Failed to initialize pthread mutex");
1418                 goto done;
1419         }
1420
1421         ret = socket_wrapper_init_mutex(&pcap_dump_mutex);
1422         if (ret != 0) {
1423                 SWRAP_LOG(SWRAP_LOG_ERROR,
1424                           "Failed to initialize pthread mutex");
1425                 goto done;
1426         }
1427
1428         ret = socket_wrapper_init_mutex(&mtu_update_mutex);
1429         if (ret != 0) {
1430                 SWRAP_LOG(SWRAP_LOG_ERROR,
1431                           "Failed to initialize pthread mutex");
1432                 goto done;
1433         }
1434
1435 done:
1436         swrap_mutex_unlock(&first_free_mutex);
1437         swrap_mutex_unlock(&sockets_mutex);
1438         if (ret != 0) {
1439                 exit(-1);
1440         }
1441 }
1442
1443 bool socket_wrapper_enabled(void)
1444 {
1445         const char *s = socket_wrapper_dir();
1446
1447         if (s == NULL) {
1448                 return false;
1449         }
1450
1451         socket_wrapper_init_sockets();
1452
1453         return true;
1454 }
1455
1456 static unsigned int socket_wrapper_default_iface(void)
1457 {
1458         const char *s = getenv("SOCKET_WRAPPER_DEFAULT_IFACE");
1459         if (s) {
1460                 unsigned int iface;
1461                 if (sscanf(s, "%u", &iface) == 1) {
1462                         if (iface >= 1 && iface <= MAX_WRAPPED_INTERFACES) {
1463                                 return iface;
1464                         }
1465                 }
1466         }
1467
1468         return 1;/* 127.0.0.1 */
1469 }
1470
1471 static void set_socket_info_index(int fd, int idx)
1472 {
1473         socket_fds_idx[fd] = idx;
1474         /* This builtin issues a full memory barrier. */
1475         __sync_synchronize();
1476 }
1477
1478 static void reset_socket_info_index(int fd)
1479 {
1480         set_socket_info_index(fd, -1);
1481 }
1482
1483 static int find_socket_info_index(int fd)
1484 {
1485         if (fd < 0) {
1486                 return -1;
1487         }
1488
1489         if (socket_fds_idx == NULL) {
1490                 return -1;
1491         }
1492
1493         if (fd >= SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT) {
1494                 SWRAP_LOG(SWRAP_LOG_ERROR,
1495                           "The max socket index limit of %u has been reached, "
1496                           "trying to add %d",
1497                           SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT,
1498                           fd);
1499                 return -1;
1500         }
1501
1502         /* This builtin issues a full memory barrier. */
1503         __sync_synchronize();
1504         return socket_fds_idx[fd];
1505 }
1506
1507 static int swrap_add_socket_info(struct socket_info *si_input)
1508 {
1509         struct socket_info *si = NULL;
1510         int si_index = -1;
1511
1512         if (si_input == NULL) {
1513                 errno = EINVAL;
1514                 return -1;
1515         }
1516
1517         swrap_mutex_lock(&first_free_mutex);
1518         if (first_free == -1) {
1519                 errno = ENFILE;
1520                 goto out;
1521         }
1522
1523         si_index = first_free;
1524         si = swrap_get_socket_info(si_index);
1525
1526         SWRAP_LOCK_SI(si);
1527
1528         first_free = swrap_get_next_free(si);
1529         *si = *si_input;
1530         swrap_inc_refcount(si);
1531
1532         SWRAP_UNLOCK_SI(si);
1533
1534 out:
1535         swrap_mutex_unlock(&first_free_mutex);
1536
1537         return si_index;
1538 }
1539
1540 static int swrap_create_socket(struct socket_info *si, int fd)
1541 {
1542         int idx;
1543
1544         if (fd >= SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT) {
1545                 SWRAP_LOG(SWRAP_LOG_ERROR,
1546                           "The max socket index limit of %u has been reached, "
1547                           "trying to add %d",
1548                           SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT,
1549                           fd);
1550                 return -1;
1551         }
1552
1553         idx = swrap_add_socket_info(si);
1554         if (idx == -1) {
1555                 return -1;
1556         }
1557
1558         set_socket_info_index(fd, idx);
1559
1560         return idx;
1561 }
1562
1563 static int convert_un_in(const struct sockaddr_un *un, struct sockaddr *in, socklen_t *len)
1564 {
1565         unsigned int iface;
1566         unsigned int prt;
1567         const char *p;
1568         char type;
1569
1570         p = strrchr(un->sun_path, '/');
1571         if (p) p++; else p = un->sun_path;
1572
1573         if (sscanf(p, SOCKET_FORMAT, &type, &iface, &prt) != 3) {
1574                 errno = EINVAL;
1575                 return -1;
1576         }
1577
1578         SWRAP_LOG(SWRAP_LOG_TRACE, "type %c iface %u port %u",
1579                         type, iface, prt);
1580
1581         if (iface == 0 || iface > MAX_WRAPPED_INTERFACES) {
1582                 errno = EINVAL;
1583                 return -1;
1584         }
1585
1586         if (prt > 0xFFFF) {
1587                 errno = EINVAL;
1588                 return -1;
1589         }
1590
1591         switch(type) {
1592         case SOCKET_TYPE_CHAR_TCP:
1593         case SOCKET_TYPE_CHAR_UDP: {
1594                 struct sockaddr_in *in2 = (struct sockaddr_in *)(void *)in;
1595
1596                 if ((*len) < sizeof(*in2)) {
1597                     errno = EINVAL;
1598                     return -1;
1599                 }
1600
1601                 memset(in2, 0, sizeof(*in2));
1602                 in2->sin_family = AF_INET;
1603                 in2->sin_addr.s_addr = htonl((127<<24) | iface);
1604                 in2->sin_port = htons(prt);
1605
1606                 *len = sizeof(*in2);
1607                 break;
1608         }
1609 #ifdef HAVE_IPV6
1610         case SOCKET_TYPE_CHAR_TCP_V6:
1611         case SOCKET_TYPE_CHAR_UDP_V6: {
1612                 struct sockaddr_in6 *in2 = (struct sockaddr_in6 *)(void *)in;
1613
1614                 if ((*len) < sizeof(*in2)) {
1615                         errno = EINVAL;
1616                         return -1;
1617                 }
1618
1619                 memset(in2, 0, sizeof(*in2));
1620                 in2->sin6_family = AF_INET6;
1621                 in2->sin6_addr = *swrap_ipv6();
1622                 in2->sin6_addr.s6_addr[15] = iface;
1623                 in2->sin6_port = htons(prt);
1624
1625                 *len = sizeof(*in2);
1626                 break;
1627         }
1628 #endif
1629         default:
1630                 errno = EINVAL;
1631                 return -1;
1632         }
1633
1634         return 0;
1635 }
1636
1637 static int convert_in_un_remote(struct socket_info *si, const struct sockaddr *inaddr, struct sockaddr_un *un,
1638                                 int *bcast)
1639 {
1640         char type = '\0';
1641         unsigned int prt;
1642         unsigned int iface;
1643         int is_bcast = 0;
1644
1645         if (bcast) *bcast = 0;
1646
1647         switch (inaddr->sa_family) {
1648         case AF_INET: {
1649                 const struct sockaddr_in *in =
1650                     (const struct sockaddr_in *)(const void *)inaddr;
1651                 unsigned int addr = ntohl(in->sin_addr.s_addr);
1652                 char u_type = '\0';
1653                 char b_type = '\0';
1654                 char a_type = '\0';
1655
1656                 switch (si->type) {
1657                 case SOCK_STREAM:
1658                         u_type = SOCKET_TYPE_CHAR_TCP;
1659                         break;
1660                 case SOCK_DGRAM:
1661                         u_type = SOCKET_TYPE_CHAR_UDP;
1662                         a_type = SOCKET_TYPE_CHAR_UDP;
1663                         b_type = SOCKET_TYPE_CHAR_UDP;
1664                         break;
1665                 default:
1666                         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown socket type!\n");
1667                         errno = ESOCKTNOSUPPORT;
1668                         return -1;
1669                 }
1670
1671                 prt = ntohs(in->sin_port);
1672                 if (a_type && addr == 0xFFFFFFFF) {
1673                         /* 255.255.255.255 only udp */
1674                         is_bcast = 2;
1675                         type = a_type;
1676                         iface = socket_wrapper_default_iface();
1677                 } else if (b_type && addr == 0x7FFFFFFF) {
1678                         /* 127.255.255.255 only udp */
1679                         is_bcast = 1;
1680                         type = b_type;
1681                         iface = socket_wrapper_default_iface();
1682                 } else if ((addr & 0xFFFFFF00) == 0x7F000000) {
1683                         /* 127.0.0.X */
1684                         is_bcast = 0;
1685                         type = u_type;
1686                         iface = (addr & 0x000000FF);
1687                 } else {
1688                         errno = ENETUNREACH;
1689                         return -1;
1690                 }
1691                 if (bcast) *bcast = is_bcast;
1692                 break;
1693         }
1694 #ifdef HAVE_IPV6
1695         case AF_INET6: {
1696                 const struct sockaddr_in6 *in =
1697                     (const struct sockaddr_in6 *)(const void *)inaddr;
1698                 struct in6_addr cmp1, cmp2;
1699
1700                 switch (si->type) {
1701                 case SOCK_STREAM:
1702                         type = SOCKET_TYPE_CHAR_TCP_V6;
1703                         break;
1704                 case SOCK_DGRAM:
1705                         type = SOCKET_TYPE_CHAR_UDP_V6;
1706                         break;
1707                 default:
1708                         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown socket type!\n");
1709                         errno = ESOCKTNOSUPPORT;
1710                         return -1;
1711                 }
1712
1713                 /* XXX no multicast/broadcast */
1714
1715                 prt = ntohs(in->sin6_port);
1716
1717                 cmp1 = *swrap_ipv6();
1718                 cmp2 = in->sin6_addr;
1719                 cmp2.s6_addr[15] = 0;
1720                 if (IN6_ARE_ADDR_EQUAL(&cmp1, &cmp2)) {
1721                         iface = in->sin6_addr.s6_addr[15];
1722                 } else {
1723                         errno = ENETUNREACH;
1724                         return -1;
1725                 }
1726
1727                 break;
1728         }
1729 #endif
1730         default:
1731                 SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown address family!\n");
1732                 errno = ENETUNREACH;
1733                 return -1;
1734         }
1735
1736         if (prt == 0) {
1737                 SWRAP_LOG(SWRAP_LOG_WARN, "Port not set\n");
1738                 errno = EINVAL;
1739                 return -1;
1740         }
1741
1742         if (is_bcast) {
1743                 snprintf(un->sun_path, sizeof(un->sun_path), "%s/EINVAL",
1744                          socket_wrapper_dir());
1745                 SWRAP_LOG(SWRAP_LOG_DEBUG, "un path [%s]", un->sun_path);
1746                 /* the caller need to do more processing */
1747                 return 0;
1748         }
1749
1750         snprintf(un->sun_path, sizeof(un->sun_path), "%s/"SOCKET_FORMAT,
1751                  socket_wrapper_dir(), type, iface, prt);
1752         SWRAP_LOG(SWRAP_LOG_DEBUG, "un path [%s]", un->sun_path);
1753
1754         return 0;
1755 }
1756
1757 static int convert_in_un_alloc(struct socket_info *si, const struct sockaddr *inaddr, struct sockaddr_un *un,
1758                                int *bcast)
1759 {
1760         char type = '\0';
1761         unsigned int prt;
1762         unsigned int iface;
1763         struct stat st;
1764         int is_bcast = 0;
1765
1766         if (bcast) *bcast = 0;
1767
1768         switch (si->family) {
1769         case AF_INET: {
1770                 const struct sockaddr_in *in =
1771                     (const struct sockaddr_in *)(const void *)inaddr;
1772                 unsigned int addr = ntohl(in->sin_addr.s_addr);
1773                 char u_type = '\0';
1774                 char d_type = '\0';
1775                 char b_type = '\0';
1776                 char a_type = '\0';
1777
1778                 prt = ntohs(in->sin_port);
1779
1780                 switch (si->type) {
1781                 case SOCK_STREAM:
1782                         u_type = SOCKET_TYPE_CHAR_TCP;
1783                         d_type = SOCKET_TYPE_CHAR_TCP;
1784                         break;
1785                 case SOCK_DGRAM:
1786                         u_type = SOCKET_TYPE_CHAR_UDP;
1787                         d_type = SOCKET_TYPE_CHAR_UDP;
1788                         a_type = SOCKET_TYPE_CHAR_UDP;
1789                         b_type = SOCKET_TYPE_CHAR_UDP;
1790                         break;
1791                 default:
1792                         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown socket type!\n");
1793                         errno = ESOCKTNOSUPPORT;
1794                         return -1;
1795                 }
1796
1797                 if (addr == 0) {
1798                         /* 0.0.0.0 */
1799                         is_bcast = 0;
1800                         type = d_type;
1801                         iface = socket_wrapper_default_iface();
1802                 } else if (a_type && addr == 0xFFFFFFFF) {
1803                         /* 255.255.255.255 only udp */
1804                         is_bcast = 2;
1805                         type = a_type;
1806                         iface = socket_wrapper_default_iface();
1807                 } else if (b_type && addr == 0x7FFFFFFF) {
1808                         /* 127.255.255.255 only udp */
1809                         is_bcast = 1;
1810                         type = b_type;
1811                         iface = socket_wrapper_default_iface();
1812                 } else if ((addr & 0xFFFFFF00) == 0x7F000000) {
1813                         /* 127.0.0.X */
1814                         is_bcast = 0;
1815                         type = u_type;
1816                         iface = (addr & 0x000000FF);
1817                 } else {
1818                         errno = EADDRNOTAVAIL;
1819                         return -1;
1820                 }
1821
1822                 /* Store the bind address for connect() */
1823                 if (si->bindname.sa_socklen == 0) {
1824                         struct sockaddr_in bind_in;
1825                         socklen_t blen = sizeof(struct sockaddr_in);
1826
1827                         ZERO_STRUCT(bind_in);
1828                         bind_in.sin_family = in->sin_family;
1829                         bind_in.sin_port = in->sin_port;
1830                         bind_in.sin_addr.s_addr = htonl(0x7F000000 | iface);
1831
1832                         si->bindname.sa_socklen = blen;
1833                         memcpy(&si->bindname.sa.in, &bind_in, blen);
1834                 }
1835
1836                 break;
1837         }
1838 #ifdef HAVE_IPV6
1839         case AF_INET6: {
1840                 const struct sockaddr_in6 *in =
1841                     (const struct sockaddr_in6 *)(const void *)inaddr;
1842                 struct in6_addr cmp1, cmp2;
1843
1844                 switch (si->type) {
1845                 case SOCK_STREAM:
1846                         type = SOCKET_TYPE_CHAR_TCP_V6;
1847                         break;
1848                 case SOCK_DGRAM:
1849                         type = SOCKET_TYPE_CHAR_UDP_V6;
1850                         break;
1851                 default:
1852                         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown socket type!\n");
1853                         errno = ESOCKTNOSUPPORT;
1854                         return -1;
1855                 }
1856
1857                 /* XXX no multicast/broadcast */
1858
1859                 prt = ntohs(in->sin6_port);
1860
1861                 cmp1 = *swrap_ipv6();
1862                 cmp2 = in->sin6_addr;
1863                 cmp2.s6_addr[15] = 0;
1864                 if (IN6_IS_ADDR_UNSPECIFIED(&in->sin6_addr)) {
1865                         iface = socket_wrapper_default_iface();
1866                 } else if (IN6_ARE_ADDR_EQUAL(&cmp1, &cmp2)) {
1867                         iface = in->sin6_addr.s6_addr[15];
1868                 } else {
1869                         errno = EADDRNOTAVAIL;
1870                         return -1;
1871                 }
1872
1873                 /* Store the bind address for connect() */
1874                 if (si->bindname.sa_socklen == 0) {
1875                         struct sockaddr_in6 bind_in;
1876                         socklen_t blen = sizeof(struct sockaddr_in6);
1877
1878                         ZERO_STRUCT(bind_in);
1879                         bind_in.sin6_family = in->sin6_family;
1880                         bind_in.sin6_port = in->sin6_port;
1881
1882                         bind_in.sin6_addr = *swrap_ipv6();
1883                         bind_in.sin6_addr.s6_addr[15] = iface;
1884
1885                         memcpy(&si->bindname.sa.in6, &bind_in, blen);
1886                         si->bindname.sa_socklen = blen;
1887                 }
1888
1889                 break;
1890         }
1891 #endif
1892         default:
1893                 SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown address family\n");
1894                 errno = EADDRNOTAVAIL;
1895                 return -1;
1896         }
1897
1898
1899         if (bcast) *bcast = is_bcast;
1900
1901         if (iface == 0 || iface > MAX_WRAPPED_INTERFACES) {
1902                 errno = EINVAL;
1903                 return -1;
1904         }
1905
1906         if (prt == 0) {
1907                 /* handle auto-allocation of ephemeral ports */
1908                 for (prt = 5001; prt < 10000; prt++) {
1909                         snprintf(un->sun_path, sizeof(un->sun_path), "%s/"SOCKET_FORMAT,
1910                                  socket_wrapper_dir(), type, iface, prt);
1911                         if (stat(un->sun_path, &st) == 0) continue;
1912
1913                         set_port(si->family, prt, &si->myname);
1914                         set_port(si->family, prt, &si->bindname);
1915
1916                         break;
1917                 }
1918                 if (prt == 10000) {
1919                         errno = ENFILE;
1920                         return -1;
1921                 }
1922         }
1923
1924         snprintf(un->sun_path, sizeof(un->sun_path), "%s/"SOCKET_FORMAT,
1925                  socket_wrapper_dir(), type, iface, prt);
1926         SWRAP_LOG(SWRAP_LOG_DEBUG, "un path [%s]", un->sun_path);
1927         return 0;
1928 }
1929
1930 static struct socket_info *find_socket_info(int fd)
1931 {
1932         int idx = find_socket_info_index(fd);
1933
1934         if (idx == -1) {
1935                 return NULL;
1936         }
1937
1938         return swrap_get_socket_info(idx);
1939 }
1940
1941 #if 0 /* FIXME */
1942 static bool check_addr_port_in_use(const struct sockaddr *sa, socklen_t len)
1943 {
1944         struct socket_info_fd *f;
1945         const struct socket_info *last_s = NULL;
1946
1947         /* first catch invalid input */
1948         switch (sa->sa_family) {
1949         case AF_INET:
1950                 if (len < sizeof(struct sockaddr_in)) {
1951                         return false;
1952                 }
1953                 break;
1954 #if HAVE_IPV6
1955         case AF_INET6:
1956                 if (len < sizeof(struct sockaddr_in6)) {
1957                         return false;
1958                 }
1959                 break;
1960 #endif
1961         default:
1962                 return false;
1963                 break;
1964         }
1965
1966         for (f = socket_fds; f; f = f->next) {
1967                 struct socket_info *s = swrap_get_socket_info(f->si_index);
1968
1969                 if (s == last_s) {
1970                         continue;
1971                 }
1972                 last_s = s;
1973
1974                 if (s->myname == NULL) {
1975                         continue;
1976                 }
1977                 if (s->myname->sa_family != sa->sa_family) {
1978                         continue;
1979                 }
1980                 switch (s->myname->sa_family) {
1981                 case AF_INET: {
1982                         struct sockaddr_in *sin1, *sin2;
1983
1984                         sin1 = (struct sockaddr_in *)s->myname;
1985                         sin2 = (struct sockaddr_in *)sa;
1986
1987                         if (sin1->sin_addr.s_addr == htonl(INADDR_ANY)) {
1988                                 continue;
1989                         }
1990                         if (sin1->sin_port != sin2->sin_port) {
1991                                 continue;
1992                         }
1993                         if (sin1->sin_addr.s_addr != sin2->sin_addr.s_addr) {
1994                                 continue;
1995                         }
1996
1997                         /* found */
1998                         return true;
1999                         break;
2000                 }
2001 #if HAVE_IPV6
2002                 case AF_INET6: {
2003                         struct sockaddr_in6 *sin1, *sin2;
2004
2005                         sin1 = (struct sockaddr_in6 *)s->myname;
2006                         sin2 = (struct sockaddr_in6 *)sa;
2007
2008                         if (sin1->sin6_port != sin2->sin6_port) {
2009                                 continue;
2010                         }
2011                         if (!IN6_ARE_ADDR_EQUAL(&sin1->sin6_addr,
2012                                                 &sin2->sin6_addr))
2013                         {
2014                                 continue;
2015                         }
2016
2017                         /* found */
2018                         return true;
2019                         break;
2020                 }
2021 #endif
2022                 default:
2023                         continue;
2024                         break;
2025
2026                 }
2027         }
2028
2029         return false;
2030 }
2031 #endif
2032
2033 static void swrap_remove_stale(int fd)
2034 {
2035         struct socket_info *si;
2036         int si_index;
2037
2038         SWRAP_LOG(SWRAP_LOG_TRACE, "remove stale wrapper for %d", fd);
2039
2040         swrap_mutex_lock(&socket_reset_mutex);
2041
2042         si_index = find_socket_info_index(fd);
2043         if (si_index == -1) {
2044                 swrap_mutex_unlock(&socket_reset_mutex);
2045                 return;
2046         }
2047
2048         reset_socket_info_index(fd);
2049
2050         swrap_mutex_unlock(&socket_reset_mutex);
2051
2052         si = swrap_get_socket_info(si_index);
2053
2054         swrap_mutex_lock(&first_free_mutex);
2055         SWRAP_LOCK_SI(si);
2056
2057         swrap_dec_refcount(si);
2058
2059         if (swrap_get_refcount(si) > 0) {
2060                 goto out;
2061         }
2062
2063         if (si->un_addr.sun_path[0] != '\0') {
2064                 unlink(si->un_addr.sun_path);
2065         }
2066
2067         swrap_set_next_free(si, first_free);
2068         first_free = si_index;
2069
2070 out:
2071         SWRAP_UNLOCK_SI(si);
2072         swrap_mutex_unlock(&first_free_mutex);
2073 }
2074
2075 static int sockaddr_convert_to_un(struct socket_info *si,
2076                                   const struct sockaddr *in_addr,
2077                                   socklen_t in_len,
2078                                   struct sockaddr_un *out_addr,
2079                                   int alloc_sock,
2080                                   int *bcast)
2081 {
2082         struct sockaddr *out = (struct sockaddr *)(void *)out_addr;
2083
2084         (void) in_len; /* unused */
2085
2086         if (out_addr == NULL) {
2087                 return 0;
2088         }
2089
2090         out->sa_family = AF_UNIX;
2091 #ifdef HAVE_STRUCT_SOCKADDR_SA_LEN
2092         out->sa_len = sizeof(*out_addr);
2093 #endif
2094
2095         switch (in_addr->sa_family) {
2096         case AF_UNSPEC: {
2097                 const struct sockaddr_in *sin;
2098                 if (si->family != AF_INET) {
2099                         break;
2100                 }
2101                 if (in_len < sizeof(struct sockaddr_in)) {
2102                         break;
2103                 }
2104                 sin = (const struct sockaddr_in *)(const void *)in_addr;
2105                 if(sin->sin_addr.s_addr != htonl(INADDR_ANY)) {
2106                         break;
2107                 }
2108
2109                 /*
2110                  * Note: in the special case of AF_UNSPEC and INADDR_ANY,
2111                  * AF_UNSPEC is mapped to AF_INET and must be treated here.
2112                  */
2113
2114                 FALL_THROUGH;
2115         }
2116         case AF_INET:
2117 #ifdef HAVE_IPV6
2118         case AF_INET6:
2119 #endif
2120                 switch (si->type) {
2121                 case SOCK_STREAM:
2122                 case SOCK_DGRAM:
2123                         break;
2124                 default:
2125                         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown socket type!\n");
2126                         errno = ESOCKTNOSUPPORT;
2127                         return -1;
2128                 }
2129                 if (alloc_sock) {
2130                         return convert_in_un_alloc(si, in_addr, out_addr, bcast);
2131                 } else {
2132                         return convert_in_un_remote(si, in_addr, out_addr, bcast);
2133                 }
2134         default:
2135                 break;
2136         }
2137
2138         errno = EAFNOSUPPORT;
2139         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown address family\n");
2140         return -1;
2141 }
2142
2143 static int sockaddr_convert_from_un(const struct socket_info *si,
2144                                     const struct sockaddr_un *in_addr,
2145                                     socklen_t un_addrlen,
2146                                     int family,
2147                                     struct sockaddr *out_addr,
2148                                     socklen_t *out_addrlen)
2149 {
2150         int ret;
2151
2152         if (out_addr == NULL || out_addrlen == NULL)
2153                 return 0;
2154
2155         if (un_addrlen == 0) {
2156                 *out_addrlen = 0;
2157                 return 0;
2158         }
2159
2160         switch (family) {
2161         case AF_INET:
2162 #ifdef HAVE_IPV6
2163         case AF_INET6:
2164 #endif
2165                 switch (si->type) {
2166                 case SOCK_STREAM:
2167                 case SOCK_DGRAM:
2168                         break;
2169                 default:
2170                         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown socket type!\n");
2171                         errno = ESOCKTNOSUPPORT;
2172                         return -1;
2173                 }
2174                 ret = convert_un_in(in_addr, out_addr, out_addrlen);
2175 #ifdef HAVE_STRUCT_SOCKADDR_SA_LEN
2176                 out_addr->sa_len = *out_addrlen;
2177 #endif
2178                 return ret;
2179         default:
2180                 break;
2181         }
2182
2183         SWRAP_LOG(SWRAP_LOG_ERROR, "Unknown address family\n");
2184         errno = EAFNOSUPPORT;
2185         return -1;
2186 }
2187
2188 enum swrap_packet_type {
2189         SWRAP_CONNECT_SEND,
2190         SWRAP_CONNECT_UNREACH,
2191         SWRAP_CONNECT_RECV,
2192         SWRAP_CONNECT_ACK,
2193         SWRAP_ACCEPT_SEND,
2194         SWRAP_ACCEPT_RECV,
2195         SWRAP_ACCEPT_ACK,
2196         SWRAP_RECVFROM,
2197         SWRAP_SENDTO,
2198         SWRAP_SENDTO_UNREACH,
2199         SWRAP_PENDING_RST,
2200         SWRAP_RECV,
2201         SWRAP_RECV_RST,
2202         SWRAP_SEND,
2203         SWRAP_SEND_RST,
2204         SWRAP_CLOSE_SEND,
2205         SWRAP_CLOSE_RECV,
2206         SWRAP_CLOSE_ACK,
2207 };
2208
2209 struct swrap_file_hdr {
2210         uint32_t        magic;
2211         uint16_t        version_major;
2212         uint16_t        version_minor;
2213         int32_t         timezone;
2214         uint32_t        sigfigs;
2215         uint32_t        frame_max_len;
2216 #define SWRAP_FRAME_LENGTH_MAX 0xFFFF
2217         uint32_t        link_type;
2218 };
2219 #define SWRAP_FILE_HDR_SIZE 24
2220
2221 struct swrap_packet_frame {
2222         uint32_t seconds;
2223         uint32_t micro_seconds;
2224         uint32_t recorded_length;
2225         uint32_t full_length;
2226 };
2227 #define SWRAP_PACKET_FRAME_SIZE 16
2228
2229 union swrap_packet_ip {
2230         struct {
2231                 uint8_t         ver_hdrlen;
2232                 uint8_t         tos;
2233                 uint16_t        packet_length;
2234                 uint16_t        identification;
2235                 uint8_t         flags;
2236                 uint8_t         fragment;
2237                 uint8_t         ttl;
2238                 uint8_t         protocol;
2239                 uint16_t        hdr_checksum;
2240                 uint32_t        src_addr;
2241                 uint32_t        dest_addr;
2242         } v4;
2243 #define SWRAP_PACKET_IP_V4_SIZE 20
2244         struct {
2245                 uint8_t         ver_prio;
2246                 uint8_t         flow_label_high;
2247                 uint16_t        flow_label_low;
2248                 uint16_t        payload_length;
2249                 uint8_t         next_header;
2250                 uint8_t         hop_limit;
2251                 uint8_t         src_addr[16];
2252                 uint8_t         dest_addr[16];
2253         } v6;
2254 #define SWRAP_PACKET_IP_V6_SIZE 40
2255 };
2256 #define SWRAP_PACKET_IP_SIZE 40
2257
2258 union swrap_packet_payload {
2259         struct {
2260                 uint16_t        source_port;
2261                 uint16_t        dest_port;
2262                 uint32_t        seq_num;
2263                 uint32_t        ack_num;
2264                 uint8_t         hdr_length;
2265                 uint8_t         control;
2266                 uint16_t        window;
2267                 uint16_t        checksum;
2268                 uint16_t        urg;
2269         } tcp;
2270 #define SWRAP_PACKET_PAYLOAD_TCP_SIZE 20
2271         struct {
2272                 uint16_t        source_port;
2273                 uint16_t        dest_port;
2274                 uint16_t        length;
2275                 uint16_t        checksum;
2276         } udp;
2277 #define SWRAP_PACKET_PAYLOAD_UDP_SIZE 8
2278         struct {
2279                 uint8_t         type;
2280                 uint8_t         code;
2281                 uint16_t        checksum;
2282                 uint32_t        unused;
2283         } icmp4;
2284 #define SWRAP_PACKET_PAYLOAD_ICMP4_SIZE 8
2285         struct {
2286                 uint8_t         type;
2287                 uint8_t         code;
2288                 uint16_t        checksum;
2289                 uint32_t        unused;
2290         } icmp6;
2291 #define SWRAP_PACKET_PAYLOAD_ICMP6_SIZE 8
2292 };
2293 #define SWRAP_PACKET_PAYLOAD_SIZE 20
2294
2295 #define SWRAP_PACKET_MIN_ALLOC \
2296         (SWRAP_PACKET_FRAME_SIZE + \
2297          SWRAP_PACKET_IP_SIZE + \
2298          SWRAP_PACKET_PAYLOAD_SIZE)
2299
2300 static const char *swrap_pcap_init_file(void)
2301 {
2302         static int initialized = 0;
2303         static const char *s = NULL;
2304         static const struct swrap_file_hdr h;
2305         static const struct swrap_packet_frame f;
2306         static const union swrap_packet_ip i;
2307         static const union swrap_packet_payload p;
2308
2309         if (initialized == 1) {
2310                 return s;
2311         }
2312         initialized = 1;
2313
2314         /*
2315          * TODO: don't use the structs use plain buffer offsets
2316          *       and PUSH_U8(), PUSH_U16() and PUSH_U32()
2317          *
2318          * for now make sure we disable PCAP support
2319          * if the struct has alignment!
2320          */
2321         if (sizeof(h) != SWRAP_FILE_HDR_SIZE) {
2322                 return NULL;
2323         }
2324         if (sizeof(f) != SWRAP_PACKET_FRAME_SIZE) {
2325                 return NULL;
2326         }
2327         if (sizeof(i) != SWRAP_PACKET_IP_SIZE) {
2328                 return NULL;
2329         }
2330         if (sizeof(i.v4) != SWRAP_PACKET_IP_V4_SIZE) {
2331                 return NULL;
2332         }
2333         if (sizeof(i.v6) != SWRAP_PACKET_IP_V6_SIZE) {
2334                 return NULL;
2335         }
2336         if (sizeof(p) != SWRAP_PACKET_PAYLOAD_SIZE) {
2337                 return NULL;
2338         }
2339         if (sizeof(p.tcp) != SWRAP_PACKET_PAYLOAD_TCP_SIZE) {
2340                 return NULL;
2341         }
2342         if (sizeof(p.udp) != SWRAP_PACKET_PAYLOAD_UDP_SIZE) {
2343                 return NULL;
2344         }
2345         if (sizeof(p.icmp4) != SWRAP_PACKET_PAYLOAD_ICMP4_SIZE) {
2346                 return NULL;
2347         }
2348         if (sizeof(p.icmp6) != SWRAP_PACKET_PAYLOAD_ICMP6_SIZE) {
2349                 return NULL;
2350         }
2351
2352         s = getenv("SOCKET_WRAPPER_PCAP_FILE");
2353         if (s == NULL) {
2354                 return NULL;
2355         }
2356         if (strncmp(s, "./", 2) == 0) {
2357                 s += 2;
2358         }
2359         return s;
2360 }
2361
2362 static uint8_t *swrap_pcap_packet_init(struct timeval *tval,
2363                                        const struct sockaddr *src,
2364                                        const struct sockaddr *dest,
2365                                        int socket_type,
2366                                        const uint8_t *payload,
2367                                        size_t payload_len,
2368                                        unsigned long tcp_seqno,
2369                                        unsigned long tcp_ack,
2370                                        unsigned char tcp_ctl,
2371                                        int unreachable,
2372                                        size_t *_packet_len)
2373 {
2374         uint8_t *base;
2375         uint8_t *buf;
2376         struct swrap_packet_frame *frame;
2377         union swrap_packet_ip *ip;
2378         union swrap_packet_payload *pay;
2379         size_t packet_len;
2380         size_t alloc_len;
2381         size_t nonwire_len = sizeof(*frame);
2382         size_t wire_hdr_len = 0;
2383         size_t wire_len = 0;
2384         size_t ip_hdr_len = 0;
2385         size_t icmp_hdr_len = 0;
2386         size_t icmp_truncate_len = 0;
2387         uint8_t protocol = 0, icmp_protocol = 0;
2388         const struct sockaddr_in *src_in = NULL;
2389         const struct sockaddr_in *dest_in = NULL;
2390 #ifdef HAVE_IPV6
2391         const struct sockaddr_in6 *src_in6 = NULL;
2392         const struct sockaddr_in6 *dest_in6 = NULL;
2393 #endif
2394         uint16_t src_port;
2395         uint16_t dest_port;
2396
2397         switch (src->sa_family) {
2398         case AF_INET:
2399                 src_in = (const struct sockaddr_in *)(const void *)src;
2400                 dest_in = (const struct sockaddr_in *)(const void *)dest;
2401                 src_port = src_in->sin_port;
2402                 dest_port = dest_in->sin_port;
2403                 ip_hdr_len = sizeof(ip->v4);
2404                 break;
2405 #ifdef HAVE_IPV6
2406         case AF_INET6:
2407                 src_in6 = (const struct sockaddr_in6 *)(const void *)src;
2408                 dest_in6 = (const struct sockaddr_in6 *)(const void *)dest;
2409                 src_port = src_in6->sin6_port;
2410                 dest_port = dest_in6->sin6_port;
2411                 ip_hdr_len = sizeof(ip->v6);
2412                 break;
2413 #endif
2414         default:
2415                 return NULL;
2416         }
2417
2418         switch (socket_type) {
2419         case SOCK_STREAM:
2420                 protocol = 0x06; /* TCP */
2421                 wire_hdr_len = ip_hdr_len + sizeof(pay->tcp);
2422                 wire_len = wire_hdr_len + payload_len;
2423                 break;
2424
2425         case SOCK_DGRAM:
2426                 protocol = 0x11; /* UDP */
2427                 wire_hdr_len = ip_hdr_len + sizeof(pay->udp);
2428                 wire_len = wire_hdr_len + payload_len;
2429                 break;
2430
2431         default:
2432                 return NULL;
2433         }
2434
2435         if (unreachable) {
2436                 icmp_protocol = protocol;
2437                 switch (src->sa_family) {
2438                 case AF_INET:
2439                         protocol = 0x01; /* ICMPv4 */
2440                         icmp_hdr_len = ip_hdr_len + sizeof(pay->icmp4);
2441                         break;
2442 #ifdef HAVE_IPV6
2443                 case AF_INET6:
2444                         protocol = 0x3A; /* ICMPv6 */
2445                         icmp_hdr_len = ip_hdr_len + sizeof(pay->icmp6);
2446                         break;
2447 #endif
2448                 }
2449                 if (wire_len > 64 ) {
2450                         icmp_truncate_len = wire_len - 64;
2451                 }
2452                 wire_hdr_len += icmp_hdr_len;
2453                 wire_len += icmp_hdr_len;
2454         }
2455
2456         packet_len = nonwire_len + wire_len;
2457         alloc_len = packet_len;
2458         if (alloc_len < SWRAP_PACKET_MIN_ALLOC) {
2459                 alloc_len = SWRAP_PACKET_MIN_ALLOC;
2460         }
2461
2462         base = (uint8_t *)calloc(1, alloc_len);
2463         if (base == NULL) {
2464                 return NULL;
2465         }
2466
2467         buf = base;
2468
2469         frame = (struct swrap_packet_frame *)(void *)buf;
2470         frame->seconds          = tval->tv_sec;
2471         frame->micro_seconds    = tval->tv_usec;
2472         frame->recorded_length  = wire_len - icmp_truncate_len;
2473         frame->full_length      = wire_len - icmp_truncate_len;
2474         buf += SWRAP_PACKET_FRAME_SIZE;
2475
2476         ip = (union swrap_packet_ip *)(void *)buf;
2477         switch (src->sa_family) {
2478         case AF_INET:
2479                 ip->v4.ver_hdrlen       = 0x45; /* version 4 and 5 * 32 bit words */
2480                 ip->v4.tos              = 0x00;
2481                 ip->v4.packet_length    = htons(wire_len - icmp_truncate_len);
2482                 ip->v4.identification   = htons(0xFFFF);
2483                 ip->v4.flags            = 0x40; /* BIT 1 set - means don't fragment */
2484                 ip->v4.fragment         = htons(0x0000);
2485                 ip->v4.ttl              = 0xFF;
2486                 ip->v4.protocol         = protocol;
2487                 ip->v4.hdr_checksum     = htons(0x0000);
2488                 ip->v4.src_addr         = src_in->sin_addr.s_addr;
2489                 ip->v4.dest_addr        = dest_in->sin_addr.s_addr;
2490                 buf += SWRAP_PACKET_IP_V4_SIZE;
2491                 break;
2492 #ifdef HAVE_IPV6
2493         case AF_INET6:
2494                 ip->v6.ver_prio         = 0x60; /* version 4 and 5 * 32 bit words */
2495                 ip->v6.flow_label_high  = 0x00;
2496                 ip->v6.flow_label_low   = 0x0000;
2497                 ip->v6.payload_length   = htons(wire_len - icmp_truncate_len); /* TODO */
2498                 ip->v6.next_header      = protocol;
2499                 memcpy(ip->v6.src_addr, src_in6->sin6_addr.s6_addr, 16);
2500                 memcpy(ip->v6.dest_addr, dest_in6->sin6_addr.s6_addr, 16);
2501                 buf += SWRAP_PACKET_IP_V6_SIZE;
2502                 break;
2503 #endif
2504         }
2505
2506         if (unreachable) {
2507                 pay = (union swrap_packet_payload *)(void *)buf;
2508                 switch (src->sa_family) {
2509                 case AF_INET:
2510                         pay->icmp4.type         = 0x03; /* destination unreachable */
2511                         pay->icmp4.code         = 0x01; /* host unreachable */
2512                         pay->icmp4.checksum     = htons(0x0000);
2513                         pay->icmp4.unused       = htonl(0x00000000);
2514                         buf += SWRAP_PACKET_PAYLOAD_ICMP4_SIZE;
2515
2516                         /* set the ip header in the ICMP payload */
2517                         ip = (union swrap_packet_ip *)(void *)buf;
2518                         ip->v4.ver_hdrlen       = 0x45; /* version 4 and 5 * 32 bit words */
2519                         ip->v4.tos              = 0x00;
2520                         ip->v4.packet_length    = htons(wire_len - icmp_hdr_len);
2521                         ip->v4.identification   = htons(0xFFFF);
2522                         ip->v4.flags            = 0x40; /* BIT 1 set - means don't fragment */
2523                         ip->v4.fragment         = htons(0x0000);
2524                         ip->v4.ttl              = 0xFF;
2525                         ip->v4.protocol         = icmp_protocol;
2526                         ip->v4.hdr_checksum     = htons(0x0000);
2527                         ip->v4.src_addr         = dest_in->sin_addr.s_addr;
2528                         ip->v4.dest_addr        = src_in->sin_addr.s_addr;
2529                         buf += SWRAP_PACKET_IP_V4_SIZE;
2530
2531                         src_port = dest_in->sin_port;
2532                         dest_port = src_in->sin_port;
2533                         break;
2534 #ifdef HAVE_IPV6
2535                 case AF_INET6:
2536                         pay->icmp6.type         = 0x01; /* destination unreachable */
2537                         pay->icmp6.code         = 0x03; /* address unreachable */
2538                         pay->icmp6.checksum     = htons(0x0000);
2539                         pay->icmp6.unused       = htonl(0x00000000);
2540                         buf += SWRAP_PACKET_PAYLOAD_ICMP6_SIZE;
2541
2542                         /* set the ip header in the ICMP payload */
2543                         ip = (union swrap_packet_ip *)(void *)buf;
2544                         ip->v6.ver_prio         = 0x60; /* version 4 and 5 * 32 bit words */
2545                         ip->v6.flow_label_high  = 0x00;
2546                         ip->v6.flow_label_low   = 0x0000;
2547                         ip->v6.payload_length   = htons(wire_len - icmp_truncate_len); /* TODO */
2548                         ip->v6.next_header      = protocol;
2549                         memcpy(ip->v6.src_addr, dest_in6->sin6_addr.s6_addr, 16);
2550                         memcpy(ip->v6.dest_addr, src_in6->sin6_addr.s6_addr, 16);
2551                         buf += SWRAP_PACKET_IP_V6_SIZE;
2552
2553                         src_port = dest_in6->sin6_port;
2554                         dest_port = src_in6->sin6_port;
2555                         break;
2556 #endif
2557                 }
2558         }
2559
2560         pay = (union swrap_packet_payload *)(void *)buf;
2561
2562         switch (socket_type) {
2563         case SOCK_STREAM:
2564                 pay->tcp.source_port    = src_port;
2565                 pay->tcp.dest_port      = dest_port;
2566                 pay->tcp.seq_num        = htonl(tcp_seqno);
2567                 pay->tcp.ack_num        = htonl(tcp_ack);
2568                 pay->tcp.hdr_length     = 0x50; /* 5 * 32 bit words */
2569                 pay->tcp.control        = tcp_ctl;
2570                 pay->tcp.window         = htons(0x7FFF);
2571                 pay->tcp.checksum       = htons(0x0000);
2572                 pay->tcp.urg            = htons(0x0000);
2573                 buf += SWRAP_PACKET_PAYLOAD_TCP_SIZE;
2574
2575                 break;
2576
2577         case SOCK_DGRAM:
2578                 pay->udp.source_port    = src_port;
2579                 pay->udp.dest_port      = dest_port;
2580                 pay->udp.length         = htons(8 + payload_len);
2581                 pay->udp.checksum       = htons(0x0000);
2582                 buf += SWRAP_PACKET_PAYLOAD_UDP_SIZE;
2583
2584                 break;
2585         }
2586
2587         if (payload && payload_len > 0) {
2588                 memcpy(buf, payload, payload_len);
2589         }
2590
2591         *_packet_len = packet_len - icmp_truncate_len;
2592         return base;
2593 }
2594
2595 static int swrap_pcap_get_fd(const char *fname)
2596 {
2597         static int fd = -1;
2598
2599         if (fd != -1) {
2600                 return fd;
2601         }
2602
2603         fd = libc_open(fname, O_WRONLY|O_CREAT|O_EXCL|O_APPEND, 0644);
2604         if (fd != -1) {
2605                 struct swrap_file_hdr file_hdr;
2606                 file_hdr.magic          = 0xA1B2C3D4;
2607                 file_hdr.version_major  = 0x0002;
2608                 file_hdr.version_minor  = 0x0004;
2609                 file_hdr.timezone       = 0x00000000;
2610                 file_hdr.sigfigs        = 0x00000000;
2611                 file_hdr.frame_max_len  = SWRAP_FRAME_LENGTH_MAX;
2612                 file_hdr.link_type      = 0x0065; /* 101 RAW IP */
2613
2614                 if (write(fd, &file_hdr, sizeof(file_hdr)) != sizeof(file_hdr)) {
2615                         close(fd);
2616                         fd = -1;
2617                 }
2618                 return fd;
2619         }
2620
2621         fd = libc_open(fname, O_WRONLY|O_APPEND, 0644);
2622
2623         return fd;
2624 }
2625
2626 static uint8_t *swrap_pcap_marshall_packet(struct socket_info *si,
2627                                            const struct sockaddr *addr,
2628                                            enum swrap_packet_type type,
2629                                            const void *buf, size_t len,
2630                                            size_t *packet_len)
2631 {
2632         const struct sockaddr *src_addr;
2633         const struct sockaddr *dest_addr;
2634         unsigned long tcp_seqno = 0;
2635         unsigned long tcp_ack = 0;
2636         unsigned char tcp_ctl = 0;
2637         int unreachable = 0;
2638
2639         struct timeval tv;
2640
2641         switch (si->family) {
2642         case AF_INET:
2643                 break;
2644 #ifdef HAVE_IPV6
2645         case AF_INET6:
2646                 break;
2647 #endif
2648         default:
2649                 return NULL;
2650         }
2651
2652         switch (type) {
2653         case SWRAP_CONNECT_SEND:
2654                 if (si->type != SOCK_STREAM) {
2655                         return NULL;
2656                 }
2657
2658                 src_addr  = &si->myname.sa.s;
2659                 dest_addr = addr;
2660
2661                 tcp_seqno = si->io.pck_snd;
2662                 tcp_ack = si->io.pck_rcv;
2663                 tcp_ctl = 0x02; /* SYN */
2664
2665                 si->io.pck_snd += 1;
2666
2667                 break;
2668
2669         case SWRAP_CONNECT_RECV:
2670                 if (si->type != SOCK_STREAM) {
2671                         return NULL;
2672                 }
2673
2674                 dest_addr = &si->myname.sa.s;
2675                 src_addr = addr;
2676
2677                 tcp_seqno = si->io.pck_rcv;
2678                 tcp_ack = si->io.pck_snd;
2679                 tcp_ctl = 0x12; /** SYN,ACK */
2680
2681                 si->io.pck_rcv += 1;
2682
2683                 break;
2684
2685         case SWRAP_CONNECT_UNREACH:
2686                 if (si->type != SOCK_STREAM) {
2687                         return NULL;
2688                 }
2689
2690                 dest_addr = &si->myname.sa.s;
2691                 src_addr  = addr;
2692
2693                 /* Unreachable: resend the data of SWRAP_CONNECT_SEND */
2694                 tcp_seqno = si->io.pck_snd - 1;
2695                 tcp_ack = si->io.pck_rcv;
2696                 tcp_ctl = 0x02; /* SYN */
2697                 unreachable = 1;
2698
2699                 break;
2700
2701         case SWRAP_CONNECT_ACK:
2702                 if (si->type != SOCK_STREAM) {
2703                         return NULL;
2704                 }
2705
2706                 src_addr  = &si->myname.sa.s;
2707                 dest_addr = addr;
2708
2709                 tcp_seqno = si->io.pck_snd;
2710                 tcp_ack = si->io.pck_rcv;
2711                 tcp_ctl = 0x10; /* ACK */
2712
2713                 break;
2714
2715         case SWRAP_ACCEPT_SEND:
2716                 if (si->type != SOCK_STREAM) {
2717                         return NULL;
2718                 }
2719
2720                 dest_addr = &si->myname.sa.s;
2721                 src_addr = addr;
2722
2723                 tcp_seqno = si->io.pck_rcv;
2724                 tcp_ack = si->io.pck_snd;
2725                 tcp_ctl = 0x02; /* SYN */
2726
2727                 si->io.pck_rcv += 1;
2728
2729                 break;
2730
2731         case SWRAP_ACCEPT_RECV:
2732                 if (si->type != SOCK_STREAM) {
2733                         return NULL;
2734                 }
2735
2736                 src_addr = &si->myname.sa.s;
2737                 dest_addr = addr;
2738
2739                 tcp_seqno = si->io.pck_snd;
2740                 tcp_ack = si->io.pck_rcv;
2741                 tcp_ctl = 0x12; /* SYN,ACK */
2742
2743                 si->io.pck_snd += 1;
2744
2745                 break;
2746
2747         case SWRAP_ACCEPT_ACK:
2748                 if (si->type != SOCK_STREAM) {
2749                         return NULL;
2750                 }
2751
2752                 dest_addr = &si->myname.sa.s;
2753                 src_addr = addr;
2754
2755                 tcp_seqno = si->io.pck_rcv;
2756                 tcp_ack = si->io.pck_snd;
2757                 tcp_ctl = 0x10; /* ACK */
2758
2759                 break;
2760
2761         case SWRAP_SEND:
2762                 src_addr  = &si->myname.sa.s;
2763                 dest_addr = &si->peername.sa.s;
2764
2765                 tcp_seqno = si->io.pck_snd;
2766                 tcp_ack = si->io.pck_rcv;
2767                 tcp_ctl = 0x18; /* PSH,ACK */
2768
2769                 si->io.pck_snd += len;
2770
2771                 break;
2772
2773         case SWRAP_SEND_RST:
2774                 dest_addr = &si->myname.sa.s;
2775                 src_addr  = &si->peername.sa.s;
2776
2777                 if (si->type == SOCK_DGRAM) {
2778                         return swrap_pcap_marshall_packet(si,
2779                                                           &si->peername.sa.s,
2780                                                           SWRAP_SENDTO_UNREACH,
2781                                                           buf,
2782                                                           len,
2783                                                           packet_len);
2784                 }
2785
2786                 tcp_seqno = si->io.pck_rcv;
2787                 tcp_ack = si->io.pck_snd;
2788                 tcp_ctl = 0x14; /** RST,ACK */
2789
2790                 break;
2791
2792         case SWRAP_PENDING_RST:
2793                 dest_addr = &si->myname.sa.s;
2794                 src_addr  = &si->peername.sa.s;
2795
2796                 if (si->type == SOCK_DGRAM) {
2797                         return NULL;
2798                 }
2799
2800                 tcp_seqno = si->io.pck_rcv;
2801                 tcp_ack = si->io.pck_snd;
2802                 tcp_ctl = 0x14; /* RST,ACK */
2803
2804                 break;
2805
2806         case SWRAP_RECV:
2807                 dest_addr = &si->myname.sa.s;
2808                 src_addr  = &si->peername.sa.s;
2809
2810                 tcp_seqno = si->io.pck_rcv;
2811                 tcp_ack = si->io.pck_snd;
2812                 tcp_ctl = 0x18; /* PSH,ACK */
2813
2814                 si->io.pck_rcv += len;
2815
2816                 break;
2817
2818         case SWRAP_RECV_RST:
2819                 dest_addr = &si->myname.sa.s;
2820                 src_addr  = &si->peername.sa.s;
2821
2822                 if (si->type == SOCK_DGRAM) {
2823                         return NULL;
2824                 }
2825
2826                 tcp_seqno = si->io.pck_rcv;
2827                 tcp_ack = si->io.pck_snd;
2828                 tcp_ctl = 0x14; /* RST,ACK */
2829
2830                 break;
2831
2832         case SWRAP_SENDTO:
2833                 src_addr = &si->myname.sa.s;
2834                 dest_addr = addr;
2835
2836                 si->io.pck_snd += len;
2837
2838                 break;
2839
2840         case SWRAP_SENDTO_UNREACH:
2841                 dest_addr = &si->myname.sa.s;
2842                 src_addr = addr;
2843
2844                 unreachable = 1;
2845
2846                 break;
2847
2848         case SWRAP_RECVFROM:
2849                 dest_addr = &si->myname.sa.s;
2850                 src_addr = addr;
2851
2852                 si->io.pck_rcv += len;
2853
2854                 break;
2855
2856         case SWRAP_CLOSE_SEND:
2857                 if (si->type != SOCK_STREAM) {
2858                         return NULL;
2859                 }
2860
2861                 src_addr  = &si->myname.sa.s;
2862                 dest_addr = &si->peername.sa.s;
2863
2864                 tcp_seqno = si->io.pck_snd;
2865                 tcp_ack = si->io.pck_rcv;
2866                 tcp_ctl = 0x11; /* FIN, ACK */
2867
2868                 si->io.pck_snd += 1;
2869
2870                 break;
2871
2872         case SWRAP_CLOSE_RECV:
2873                 if (si->type != SOCK_STREAM) {
2874                         return NULL;
2875                 }
2876
2877                 dest_addr = &si->myname.sa.s;
2878                 src_addr  = &si->peername.sa.s;
2879
2880                 tcp_seqno = si->io.pck_rcv;
2881                 tcp_ack = si->io.pck_snd;
2882                 tcp_ctl = 0x11; /* FIN,ACK */
2883
2884                 si->io.pck_rcv += 1;
2885
2886                 break;
2887
2888         case SWRAP_CLOSE_ACK:
2889                 if (si->type != SOCK_STREAM) {
2890                         return NULL;
2891                 }
2892
2893                 src_addr  = &si->myname.sa.s;
2894                 dest_addr = &si->peername.sa.s;
2895
2896                 tcp_seqno = si->io.pck_snd;
2897                 tcp_ack = si->io.pck_rcv;
2898                 tcp_ctl = 0x10; /* ACK */
2899
2900                 break;
2901         default:
2902                 return NULL;
2903         }
2904
2905         swrapGetTimeOfDay(&tv);
2906
2907         return swrap_pcap_packet_init(&tv,
2908                                       src_addr,
2909                                       dest_addr,
2910                                       si->type,
2911                                       (const uint8_t *)buf,
2912                                       len,
2913                                       tcp_seqno,
2914                                       tcp_ack,
2915                                       tcp_ctl,
2916                                       unreachable,
2917                                       packet_len);
2918 }
2919
2920 static void swrap_pcap_dump_packet(struct socket_info *si,
2921                                    const struct sockaddr *addr,
2922                                    enum swrap_packet_type type,
2923                                    const void *buf, size_t len)
2924 {
2925         const char *file_name;
2926         uint8_t *packet;
2927         size_t packet_len = 0;
2928         int fd;
2929
2930         swrap_mutex_lock(&pcap_dump_mutex);
2931
2932         file_name = swrap_pcap_init_file();
2933         if (!file_name) {
2934                 goto done;
2935         }
2936
2937         packet = swrap_pcap_marshall_packet(si,
2938                                             addr,
2939                                             type,
2940                                             buf,
2941                                             len,
2942                                             &packet_len);
2943         if (packet == NULL) {
2944                 goto done;
2945         }
2946
2947         fd = swrap_pcap_get_fd(file_name);
2948         if (fd != -1) {
2949                 if (write(fd, packet, packet_len) != (ssize_t)packet_len) {
2950                         free(packet);
2951                         goto done;
2952                 }
2953         }
2954
2955         free(packet);
2956
2957 done:
2958         swrap_mutex_unlock(&pcap_dump_mutex);
2959 }
2960
2961 /****************************************************************************
2962  *   SIGNALFD
2963  ***************************************************************************/
2964
2965 #ifdef HAVE_SIGNALFD
2966 static int swrap_signalfd(int fd, const sigset_t *mask, int flags)
2967 {
2968         int rc;
2969
2970         rc = libc_signalfd(fd, mask, flags);
2971         if (rc != -1) {
2972                 swrap_remove_stale(fd);
2973         }
2974
2975         return rc;
2976 }
2977
2978 int signalfd(int fd, const sigset_t *mask, int flags)
2979 {
2980         return swrap_signalfd(fd, mask, flags);
2981 }
2982 #endif
2983
2984 /****************************************************************************
2985  *   SOCKET
2986  ***************************************************************************/
2987
2988 static int swrap_socket(int family, int type, int protocol)
2989 {
2990         struct socket_info *si = NULL;
2991         struct socket_info _si = { 0 };
2992         int fd;
2993         int ret;
2994         int real_type = type;
2995
2996         /*
2997          * Remove possible addition flags passed to socket() so
2998          * do not fail checking the type.
2999          * See https://lwn.net/Articles/281965/
3000          */
3001 #ifdef SOCK_CLOEXEC
3002         real_type &= ~SOCK_CLOEXEC;
3003 #endif
3004 #ifdef SOCK_NONBLOCK
3005         real_type &= ~SOCK_NONBLOCK;
3006 #endif
3007
3008         if (!socket_wrapper_enabled()) {
3009                 return libc_socket(family, type, protocol);
3010         }
3011
3012         switch (family) {
3013         case AF_INET:
3014 #ifdef HAVE_IPV6
3015         case AF_INET6:
3016 #endif
3017                 break;
3018 #ifdef AF_NETLINK
3019         case AF_NETLINK:
3020 #endif /* AF_NETLINK */
3021 #ifdef AF_PACKET
3022         case AF_PACKET:
3023 #endif /* AF_PACKET */
3024         case AF_UNIX:
3025                 return libc_socket(family, type, protocol);
3026         default:
3027                 errno = EAFNOSUPPORT;
3028                 return -1;
3029         }
3030
3031         switch (real_type) {
3032         case SOCK_STREAM:
3033                 break;
3034         case SOCK_DGRAM:
3035                 break;
3036         default:
3037                 errno = EPROTONOSUPPORT;
3038                 return -1;
3039         }
3040
3041         switch (protocol) {
3042         case 0:
3043                 break;
3044         case 6:
3045                 if (real_type == SOCK_STREAM) {
3046                         break;
3047                 }
3048                 FALL_THROUGH;
3049         case 17:
3050                 if (real_type == SOCK_DGRAM) {
3051                         break;
3052                 }
3053                 FALL_THROUGH;
3054         default:
3055                 errno = EPROTONOSUPPORT;
3056                 return -1;
3057         }
3058
3059         /*
3060          * We must call libc_socket with type, from the caller, not the version
3061          * we removed SOCK_CLOEXEC and SOCK_NONBLOCK from
3062          */
3063         fd = libc_socket(AF_UNIX, type, 0);
3064
3065         if (fd == -1) {
3066                 return -1;
3067         }
3068
3069         /* Check if we have a stale fd and remove it */
3070         swrap_remove_stale(fd);
3071
3072         si = &_si;
3073         si->family = family;
3074
3075         /* however, the rest of the socket_wrapper code expects just
3076          * the type, not the flags */
3077         si->type = real_type;
3078         si->protocol = protocol;
3079
3080         /*
3081          * Setup myname so getsockname() can succeed to find out the socket
3082          * type.
3083          */
3084         switch(si->family) {
3085         case AF_INET: {
3086                 struct sockaddr_in sin = {
3087                         .sin_family = AF_INET,
3088                 };
3089
3090                 si->myname.sa_socklen = sizeof(struct sockaddr_in);
3091                 memcpy(&si->myname.sa.in, &sin, si->myname.sa_socklen);
3092                 break;
3093         }
3094         case AF_INET6: {
3095                 struct sockaddr_in6 sin6 = {
3096                         .sin6_family = AF_INET6,
3097                 };
3098
3099                 si->myname.sa_socklen = sizeof(struct sockaddr_in6);
3100                 memcpy(&si->myname.sa.in6, &sin6, si->myname.sa_socklen);
3101                 break;
3102         }
3103         default:
3104                 errno = EINVAL;
3105                 return -1;
3106         }
3107
3108         ret = swrap_create_socket(si, fd);
3109         if (ret == -1) {
3110                 return -1;
3111         }
3112
3113         SWRAP_LOG(SWRAP_LOG_TRACE,
3114                   "Created %s socket for protocol %s",
3115                   family == AF_INET ? "IPv4" : "IPv6",
3116                   real_type == SOCK_DGRAM ? "UDP" : "TCP");
3117
3118         return fd;
3119 }
3120
3121 int socket(int family, int type, int protocol)
3122 {
3123         return swrap_socket(family, type, protocol);
3124 }
3125
3126 /****************************************************************************
3127  *   SOCKETPAIR
3128  ***************************************************************************/
3129
3130 static int swrap_socketpair(int family, int type, int protocol, int sv[2])
3131 {
3132         int rc;
3133
3134         rc = libc_socketpair(family, type, protocol, sv);
3135         if (rc != -1) {
3136                 swrap_remove_stale(sv[0]);
3137                 swrap_remove_stale(sv[1]);
3138         }
3139
3140         return rc;
3141 }
3142
3143 int socketpair(int family, int type, int protocol, int sv[2])
3144 {
3145         return swrap_socketpair(family, type, protocol, sv);
3146 }
3147
3148 /****************************************************************************
3149  *   SOCKETPAIR
3150  ***************************************************************************/
3151
3152 #ifdef HAVE_TIMERFD_CREATE
3153 static int swrap_timerfd_create(int clockid, int flags)
3154 {
3155         int fd;
3156
3157         fd = libc_timerfd_create(clockid, flags);
3158         if (fd != -1) {
3159                 swrap_remove_stale(fd);
3160         }
3161
3162         return fd;
3163 }
3164
3165 int timerfd_create(int clockid, int flags)
3166 {
3167         return swrap_timerfd_create(clockid, flags);
3168 }
3169 #endif
3170
3171 /****************************************************************************
3172  *   PIPE
3173  ***************************************************************************/
3174
3175 static int swrap_pipe(int pipefd[2])
3176 {
3177         int rc;
3178
3179         rc = libc_pipe(pipefd);
3180         if (rc != -1) {
3181                 swrap_remove_stale(pipefd[0]);
3182                 swrap_remove_stale(pipefd[1]);
3183         }
3184
3185         return rc;
3186 }
3187
3188 int pipe(int pipefd[2])
3189 {
3190         return swrap_pipe(pipefd);
3191 }
3192
3193 /****************************************************************************
3194  *   ACCEPT
3195  ***************************************************************************/
3196
3197 static int swrap_accept(int s,
3198                         struct sockaddr *addr,
3199                         socklen_t *addrlen,
3200                         int flags)
3201 {
3202         struct socket_info *parent_si, *child_si;
3203         struct socket_info new_si = { 0 };
3204         int fd;
3205         int idx;
3206         struct swrap_address un_addr = {
3207                 .sa_socklen = sizeof(struct sockaddr_un),
3208         };
3209         struct swrap_address un_my_addr = {
3210                 .sa_socklen = sizeof(struct sockaddr_un),
3211         };
3212         struct swrap_address in_addr = {
3213                 .sa_socklen = sizeof(struct sockaddr_storage),
3214         };
3215         struct swrap_address in_my_addr = {
3216                 .sa_socklen = sizeof(struct sockaddr_storage),
3217         };
3218         int ret;
3219
3220         parent_si = find_socket_info(s);
3221         if (!parent_si) {
3222 #ifdef HAVE_ACCEPT4
3223                 return libc_accept4(s, addr, addrlen, flags);
3224 #else
3225                 UNUSED(flags);
3226                 return libc_accept(s, addr, addrlen);
3227 #endif
3228         }
3229
3230
3231         /*
3232          * prevent parent_si from being altered / closed
3233          * while we read it
3234          */
3235         SWRAP_LOCK_SI(parent_si);
3236
3237         /*
3238          * assume out sockaddr have the same size as the in parent
3239          * socket family
3240          */
3241         in_addr.sa_socklen = socket_length(parent_si->family);
3242         if (in_addr.sa_socklen <= 0) {
3243                 SWRAP_UNLOCK_SI(parent_si);
3244                 errno = EINVAL;
3245                 return -1;
3246         }
3247
3248         SWRAP_UNLOCK_SI(parent_si);
3249
3250 #ifdef HAVE_ACCEPT4
3251         ret = libc_accept4(s, &un_addr.sa.s, &un_addr.sa_socklen, flags);
3252 #else
3253         UNUSED(flags);
3254         ret = libc_accept(s, &un_addr.sa.s, &un_addr.sa_socklen);
3255 #endif
3256         if (ret == -1) {
3257                 if (errno == ENOTSOCK) {
3258                         /* Remove stale fds */
3259                         swrap_remove_stale(s);
3260                 }
3261                 return ret;
3262         }
3263
3264         fd = ret;
3265
3266         SWRAP_LOCK_SI(parent_si);
3267
3268         ret = sockaddr_convert_from_un(parent_si,
3269                                        &un_addr.sa.un,
3270                                        un_addr.sa_socklen,
3271                                        parent_si->family,
3272                                        &in_addr.sa.s,
3273                                        &in_addr.sa_socklen);
3274         if (ret == -1) {
3275                 SWRAP_UNLOCK_SI(parent_si);
3276                 close(fd);
3277                 return ret;
3278         }
3279
3280         child_si = &new_si;
3281
3282         child_si->family = parent_si->family;
3283         child_si->type = parent_si->type;
3284         child_si->protocol = parent_si->protocol;
3285         child_si->bound = 1;
3286         child_si->is_server = 1;
3287         child_si->connected = 1;
3288
3289         SWRAP_UNLOCK_SI(parent_si);
3290
3291         child_si->peername = (struct swrap_address) {
3292                 .sa_socklen = in_addr.sa_socklen,
3293         };
3294         memcpy(&child_si->peername.sa.ss, &in_addr.sa.ss, in_addr.sa_socklen);
3295
3296         if (addr != NULL && addrlen != NULL) {
3297                 size_t copy_len = MIN(*addrlen, in_addr.sa_socklen);
3298                 if (copy_len > 0) {
3299                         memcpy(addr, &in_addr.sa.ss, copy_len);
3300                 }
3301                 *addrlen = in_addr.sa_socklen;
3302         }
3303
3304         ret = libc_getsockname(fd,
3305                                &un_my_addr.sa.s,
3306                                &un_my_addr.sa_socklen);
3307         if (ret == -1) {
3308                 close(fd);
3309                 return ret;
3310         }
3311
3312         ret = sockaddr_convert_from_un(child_si,
3313                                        &un_my_addr.sa.un,
3314                                        un_my_addr.sa_socklen,
3315                                        child_si->family,
3316                                        &in_my_addr.sa.s,
3317                                        &in_my_addr.sa_socklen);
3318         if (ret == -1) {
3319                 close(fd);
3320                 return ret;
3321         }
3322
3323         SWRAP_LOG(SWRAP_LOG_TRACE,
3324                   "accept() path=%s, fd=%d",
3325                   un_my_addr.sa.un.sun_path, s);
3326
3327         child_si->myname = (struct swrap_address) {
3328                 .sa_socklen = in_my_addr.sa_socklen,
3329         };
3330         memcpy(&child_si->myname.sa.ss, &in_my_addr.sa.ss, in_my_addr.sa_socklen);
3331
3332         idx = swrap_create_socket(&new_si, fd);
3333         if (idx == -1) {
3334                 close (fd);
3335                 return -1;
3336         }
3337
3338         if (addr != NULL) {
3339                 struct socket_info *si = swrap_get_socket_info(idx);
3340
3341                 SWRAP_LOCK_SI(si);
3342                 swrap_pcap_dump_packet(si, addr, SWRAP_ACCEPT_SEND, NULL, 0);
3343                 swrap_pcap_dump_packet(si, addr, SWRAP_ACCEPT_RECV, NULL, 0);
3344                 swrap_pcap_dump_packet(si, addr, SWRAP_ACCEPT_ACK, NULL, 0);
3345                 SWRAP_UNLOCK_SI(si);
3346         }
3347
3348         return fd;
3349 }
3350
3351 #ifdef HAVE_ACCEPT4
3352 int accept4(int s, struct sockaddr *addr, socklen_t *addrlen, int flags)
3353 {
3354         return swrap_accept(s, addr, (socklen_t *)addrlen, flags);
3355 }
3356 #endif
3357
3358 #ifdef HAVE_ACCEPT_PSOCKLEN_T
3359 int accept(int s, struct sockaddr *addr, Psocklen_t addrlen)
3360 #else
3361 int accept(int s, struct sockaddr *addr, socklen_t *addrlen)
3362 #endif
3363 {
3364         return swrap_accept(s, addr, (socklen_t *)addrlen, 0);
3365 }
3366
3367 static int autobind_start_init;
3368 static int autobind_start;
3369
3370 /* using sendto() or connect() on an unbound socket would give the
3371    recipient no way to reply, as unlike UDP and TCP, a unix domain
3372    socket can't auto-assign ephemeral port numbers, so we need to
3373    assign it here.
3374    Note: this might change the family from ipv6 to ipv4
3375 */
3376 static int swrap_auto_bind(int fd, struct socket_info *si, int family)
3377 {
3378         struct swrap_address un_addr = {
3379                 .sa_socklen = sizeof(struct sockaddr_un),
3380         };
3381         int i;
3382         char type;
3383         int ret;
3384         int port;
3385         struct stat st;
3386
3387         swrap_mutex_lock(&autobind_start_mutex);
3388
3389         if (autobind_start_init != 1) {
3390                 autobind_start_init = 1;
3391                 autobind_start = getpid();
3392                 autobind_start %= 50000;
3393                 autobind_start += 10000;
3394         }
3395
3396         un_addr.sa.un.sun_family = AF_UNIX;
3397
3398         switch (family) {
3399         case AF_INET: {
3400                 struct sockaddr_in in;
3401
3402                 switch (si->type) {
3403                 case SOCK_STREAM:
3404                         type = SOCKET_TYPE_CHAR_TCP;
3405                         break;
3406                 case SOCK_DGRAM:
3407                         type = SOCKET_TYPE_CHAR_UDP;
3408                         break;
3409                 default:
3410                         errno = ESOCKTNOSUPPORT;
3411                         ret = -1;
3412                         goto done;
3413                 }
3414
3415                 memset(&in, 0, sizeof(in));
3416                 in.sin_family = AF_INET;
3417                 in.sin_addr.s_addr = htonl(127<<24 |
3418                                            socket_wrapper_default_iface());
3419
3420                 si->myname = (struct swrap_address) {
3421                         .sa_socklen = sizeof(in),
3422                 };
3423                 memcpy(&si->myname.sa.in, &in, si->myname.sa_socklen);
3424                 break;
3425         }
3426 #ifdef HAVE_IPV6
3427         case AF_INET6: {
3428                 struct sockaddr_in6 in6;
3429
3430                 if (si->family != family) {
3431                         errno = ENETUNREACH;
3432                         ret = -1;
3433                         goto done;
3434                 }
3435
3436                 switch (si->type) {
3437                 case SOCK_STREAM:
3438                         type = SOCKET_TYPE_CHAR_TCP_V6;
3439                         break;
3440                 case SOCK_DGRAM:
3441                         type = SOCKET_TYPE_CHAR_UDP_V6;
3442                         break;
3443                 default:
3444                         errno = ESOCKTNOSUPPORT;
3445                         ret = -1;
3446                         goto done;
3447                 }
3448
3449                 memset(&in6, 0, sizeof(in6));
3450                 in6.sin6_family = AF_INET6;
3451                 in6.sin6_addr = *swrap_ipv6();
3452                 in6.sin6_addr.s6_addr[15] = socket_wrapper_default_iface();
3453
3454                 si->myname = (struct swrap_address) {
3455                         .sa_socklen = sizeof(in6),
3456                 };
3457                 memcpy(&si->myname.sa.in6, &in6, si->myname.sa_socklen);
3458                 break;
3459         }
3460 #endif
3461         default:
3462                 errno = ESOCKTNOSUPPORT;
3463                 ret = -1;
3464                 goto done;
3465         }
3466
3467         if (autobind_start > 60000) {
3468                 autobind_start = 10000;
3469         }
3470
3471         for (i = 0; i < SOCKET_MAX_SOCKETS; i++) {
3472                 port = autobind_start + i;
3473                 snprintf(un_addr.sa.un.sun_path, sizeof(un_addr.sa.un.sun_path),
3474                          "%s/"SOCKET_FORMAT, socket_wrapper_dir(),
3475                          type, socket_wrapper_default_iface(), port);
3476                 if (stat(un_addr.sa.un.sun_path, &st) == 0) continue;
3477
3478                 ret = libc_bind(fd, &un_addr.sa.s, un_addr.sa_socklen);
3479                 if (ret == -1) {
3480                         goto done;
3481                 }
3482
3483                 si->un_addr = un_addr.sa.un;
3484
3485                 si->bound = 1;
3486                 autobind_start = port + 1;
3487                 break;
3488         }
3489         if (i == SOCKET_MAX_SOCKETS) {
3490                 SWRAP_LOG(SWRAP_LOG_ERROR, "Too many open unix sockets (%u) for "
3491                                            "interface "SOCKET_FORMAT,
3492                                            SOCKET_MAX_SOCKETS,
3493                                            type,
3494                                            socket_wrapper_default_iface(),
3495                                            0);
3496                 errno = ENFILE;
3497                 ret = -1;
3498                 goto done;
3499         }
3500
3501         si->family = family;
3502         set_port(si->family, port, &si->myname);
3503
3504         ret = 0;
3505
3506 done:
3507         swrap_mutex_unlock(&autobind_start_mutex);
3508         return ret;
3509 }
3510
3511 /****************************************************************************
3512  *   CONNECT
3513  ***************************************************************************/
3514
3515 static int swrap_connect(int s, const struct sockaddr *serv_addr,
3516                          socklen_t addrlen)
3517 {
3518         int ret;
3519         struct swrap_address un_addr = {
3520                 .sa_socklen = sizeof(struct sockaddr_un),
3521         };
3522         struct socket_info *si = find_socket_info(s);
3523         int bcast = 0;
3524
3525         if (!si) {
3526                 return libc_connect(s, serv_addr, addrlen);
3527         }
3528
3529         SWRAP_LOCK_SI(si);
3530
3531         if (si->bound == 0) {
3532                 ret = swrap_auto_bind(s, si, serv_addr->sa_family);
3533                 if (ret == -1) {
3534                         goto done;
3535                 }
3536         }
3537
3538         if (si->family != serv_addr->sa_family) {
3539                 errno = EINVAL;
3540                 ret = -1;
3541                 goto done;
3542         }
3543
3544         ret = sockaddr_convert_to_un(si, serv_addr,
3545                                      addrlen, &un_addr.sa.un, 0, &bcast);
3546         if (ret == -1) {
3547                 goto done;
3548         }
3549
3550         if (bcast) {
3551                 errno = ENETUNREACH;
3552                 ret = -1;
3553                 goto done;
3554         }
3555
3556         if (si->type == SOCK_DGRAM) {
3557                 si->defer_connect = 1;
3558                 ret = 0;
3559         } else {
3560                 swrap_pcap_dump_packet(si, serv_addr, SWRAP_CONNECT_SEND, NULL, 0);
3561
3562                 ret = libc_connect(s,
3563                                    &un_addr.sa.s,
3564                                    un_addr.sa_socklen);
3565         }
3566
3567         SWRAP_LOG(SWRAP_LOG_TRACE,
3568                   "connect() path=%s, fd=%d",
3569                   un_addr.sa.un.sun_path, s);
3570
3571
3572         /* to give better errors */
3573         if (ret == -1 && errno == ENOENT) {
3574                 errno = EHOSTUNREACH;
3575         }
3576
3577         if (ret == 0) {
3578                 si->peername = (struct swrap_address) {
3579                         .sa_socklen = addrlen,
3580                 };
3581
3582                 memcpy(&si->peername.sa.ss, serv_addr, addrlen);
3583                 si->connected = 1;
3584
3585                 /*
3586                  * When we connect() on a socket than we have to bind the
3587                  * outgoing connection on the interface we use for the
3588                  * transport. We already bound it on the right interface
3589                  * but here we have to update the name so getsockname()
3590                  * returns correct information.
3591                  */
3592                 if (si->bindname.sa_socklen > 0) {
3593                         si->myname = (struct swrap_address) {
3594                                 .sa_socklen = si->bindname.sa_socklen,
3595                         };
3596
3597                         memcpy(&si->myname.sa.ss,
3598                                &si->bindname.sa.ss,
3599                                si->bindname.sa_socklen);
3600
3601                         /* Cleanup bindname */
3602                         si->bindname = (struct swrap_address) {
3603                                 .sa_socklen = 0,
3604                         };
3605                 }
3606
3607                 swrap_pcap_dump_packet(si, serv_addr, SWRAP_CONNECT_RECV, NULL, 0);
3608                 swrap_pcap_dump_packet(si, serv_addr, SWRAP_CONNECT_ACK, NULL, 0);
3609         } else {
3610                 swrap_pcap_dump_packet(si, serv_addr, SWRAP_CONNECT_UNREACH, NULL, 0);
3611         }
3612
3613 done:
3614         SWRAP_UNLOCK_SI(si);
3615         return ret;
3616 }
3617
3618 int connect(int s, const struct sockaddr *serv_addr, socklen_t addrlen)
3619 {
3620         return swrap_connect(s, serv_addr, addrlen);
3621 }
3622
3623 /****************************************************************************
3624  *   BIND
3625  ***************************************************************************/
3626
3627 static int swrap_bind(int s, const struct sockaddr *myaddr, socklen_t addrlen)
3628 {
3629         int ret;
3630         struct swrap_address un_addr = {
3631                 .sa_socklen = sizeof(struct sockaddr_un),
3632         };
3633         struct socket_info *si = find_socket_info(s);
3634         int bind_error = 0;
3635 #if 0 /* FIXME */
3636         bool in_use;
3637 #endif
3638
3639         if (!si) {
3640                 return libc_bind(s, myaddr, addrlen);
3641         }
3642
3643         SWRAP_LOCK_SI(si);
3644
3645         switch (si->family) {
3646         case AF_INET: {
3647                 const struct sockaddr_in *sin;
3648                 if (addrlen < sizeof(struct sockaddr_in)) {
3649                         bind_error = EINVAL;
3650                         break;
3651                 }
3652
3653                 sin = (const struct sockaddr_in *)(const void *)myaddr;
3654
3655                 if (sin->sin_family != AF_INET) {
3656                         bind_error = EAFNOSUPPORT;
3657                 }
3658
3659                 /* special case for AF_UNSPEC */
3660                 if (sin->sin_family == AF_UNSPEC &&
3661                     (sin->sin_addr.s_addr == htonl(INADDR_ANY)))
3662                 {
3663                         bind_error = 0;
3664                 }
3665
3666                 break;
3667         }
3668 #ifdef HAVE_IPV6
3669         case AF_INET6: {
3670                 const struct sockaddr_in6 *sin6;
3671                 if (addrlen < sizeof(struct sockaddr_in6)) {
3672                         bind_error = EINVAL;
3673                         break;
3674                 }
3675
3676                 sin6 = (const struct sockaddr_in6 *)(const void *)myaddr;
3677
3678                 if (sin6->sin6_family != AF_INET6) {
3679                         bind_error = EAFNOSUPPORT;
3680                 }
3681
3682                 break;
3683         }
3684 #endif
3685         default:
3686                 bind_error = EINVAL;
3687                 break;
3688         }
3689
3690         if (bind_error != 0) {
3691                 errno = bind_error;
3692                 ret = -1;
3693                 goto out;
3694         }
3695
3696 #if 0 /* FIXME */
3697         in_use = check_addr_port_in_use(myaddr, addrlen);
3698         if (in_use) {
3699                 errno = EADDRINUSE;
3700                 ret = -1;
3701                 goto out;
3702         }
3703 #endif
3704
3705         si->myname.sa_socklen = addrlen;
3706         memcpy(&si->myname.sa.ss, myaddr, addrlen);
3707
3708         ret = sockaddr_convert_to_un(si,
3709                                      myaddr,
3710                                      addrlen,
3711                                      &un_addr.sa.un,
3712                                      1,
3713                                      &si->bcast);
3714         if (ret == -1) {
3715                 goto out;
3716         }
3717
3718         unlink(un_addr.sa.un.sun_path);
3719
3720         ret = libc_bind(s, &un_addr.sa.s, un_addr.sa_socklen);
3721
3722         SWRAP_LOG(SWRAP_LOG_TRACE,
3723                   "bind() path=%s, fd=%d",
3724                   un_addr.sa.un.sun_path, s);
3725
3726         if (ret == 0) {
3727                 si->bound = 1;
3728         }
3729
3730 out:
3731         SWRAP_UNLOCK_SI(si);
3732
3733         return ret;
3734 }
3735
3736 int bind(int s, const struct sockaddr *myaddr, socklen_t addrlen)
3737 {
3738         return swrap_bind(s, myaddr, addrlen);
3739 }
3740
3741 /****************************************************************************
3742  *   BINDRESVPORT
3743  ***************************************************************************/
3744
3745 #ifdef HAVE_BINDRESVPORT
3746 static int swrap_getsockname(int s, struct sockaddr *name, socklen_t *addrlen);
3747
3748 static int swrap_bindresvport_sa(int sd, struct sockaddr *sa)
3749 {
3750         struct swrap_address myaddr = {
3751                 .sa_socklen = sizeof(struct sockaddr_storage),
3752         };
3753         socklen_t salen;
3754         static uint16_t port;
3755         uint16_t i;
3756         int rc = -1;
3757         int af;
3758
3759 #define SWRAP_STARTPORT 600
3760 #define SWRAP_ENDPORT (IPPORT_RESERVED - 1)
3761 #define SWRAP_NPORTS (SWRAP_ENDPORT - SWRAP_STARTPORT + 1)
3762
3763         if (port == 0) {
3764                 port = (getpid() % SWRAP_NPORTS) + SWRAP_STARTPORT;
3765         }
3766
3767         if (sa == NULL) {
3768                 salen = myaddr.sa_socklen;
3769                 sa = &myaddr.sa.s;
3770
3771                 rc = swrap_getsockname(sd, &myaddr.sa.s, &salen);
3772                 if (rc < 0) {
3773                         return -1;
3774                 }
3775
3776                 af = sa->sa_family;
3777                 memset(&myaddr.sa.ss, 0, salen);
3778         } else {
3779                 af = sa->sa_family;
3780         }
3781
3782         for (i = 0; i < SWRAP_NPORTS; i++, port++) {
3783                 switch(af) {
3784                 case AF_INET: {
3785                         struct sockaddr_in *sinp = (struct sockaddr_in *)(void *)sa;
3786
3787                         salen = sizeof(struct sockaddr_in);
3788                         sinp->sin_port = htons(port);
3789                         break;
3790                 }
3791                 case AF_INET6: {
3792                         struct sockaddr_in6 *sin6p = (struct sockaddr_in6 *)(void *)sa;
3793
3794                         salen = sizeof(struct sockaddr_in6);
3795                         sin6p->sin6_port = htons(port);
3796                         break;
3797                 }
3798                 default:
3799                         errno = EAFNOSUPPORT;
3800                         return -1;
3801                 }
3802                 sa->sa_family = af;
3803
3804                 if (port > SWRAP_ENDPORT) {
3805                         port = SWRAP_STARTPORT;
3806                 }
3807
3808                 rc = swrap_bind(sd, (struct sockaddr *)sa, salen);
3809                 if (rc == 0 || errno != EADDRINUSE) {
3810                         break;
3811                 }
3812         }
3813
3814         return rc;
3815 }
3816
3817 int bindresvport(int sockfd, struct sockaddr_in *sinp)
3818 {
3819         return swrap_bindresvport_sa(sockfd, (struct sockaddr *)sinp);
3820 }
3821 #endif
3822
3823 /****************************************************************************
3824  *   LISTEN
3825  ***************************************************************************/
3826
3827 static int swrap_listen(int s, int backlog)
3828 {
3829         int ret;
3830         struct socket_info *si = find_socket_info(s);
3831
3832         if (!si) {
3833                 return libc_listen(s, backlog);
3834         }
3835
3836         SWRAP_LOCK_SI(si);
3837
3838         if (si->bound == 0) {
3839                 ret = swrap_auto_bind(s, si, si->family);
3840                 if (ret == -1) {
3841                         errno = EADDRINUSE;
3842                         goto out;
3843                 }
3844         }
3845
3846         ret = libc_listen(s, backlog);
3847
3848 out:
3849         SWRAP_UNLOCK_SI(si);
3850
3851         return ret;
3852 }
3853
3854 int listen(int s, int backlog)
3855 {
3856         return swrap_listen(s, backlog);
3857 }
3858
3859 /****************************************************************************
3860  *   FOPEN
3861  ***************************************************************************/
3862
3863 static FILE *swrap_fopen(const char *name, const char *mode)
3864 {
3865         FILE *fp;
3866
3867         fp = libc_fopen(name, mode);
3868         if (fp != NULL) {
3869                 int fd = fileno(fp);
3870
3871                 swrap_remove_stale(fd);
3872         }
3873
3874         return fp;
3875 }
3876
3877 FILE *fopen(const char *name, const char *mode)
3878 {
3879         return swrap_fopen(name, mode);
3880 }
3881
3882 /****************************************************************************
3883  *   FOPEN64
3884  ***************************************************************************/
3885
3886 #ifdef HAVE_FOPEN64
3887 static FILE *swrap_fopen64(const char *name, const char *mode)
3888 {
3889         FILE *fp;
3890
3891         fp = libc_fopen64(name, mode);
3892         if (fp != NULL) {
3893                 int fd = fileno(fp);
3894
3895                 swrap_remove_stale(fd);
3896         }
3897
3898         return fp;
3899 }
3900
3901 FILE *fopen64(const char *name, const char *mode)
3902 {
3903         return swrap_fopen64(name, mode);
3904 }
3905 #endif /* HAVE_FOPEN64 */
3906
3907 /****************************************************************************
3908  *   OPEN
3909  ***************************************************************************/
3910
3911 static int swrap_vopen(const char *pathname, int flags, va_list ap)
3912 {
3913         int ret;
3914
3915         ret = libc_vopen(pathname, flags, ap);
3916         if (ret != -1) {
3917                 /*
3918                  * There are methods for closing descriptors (libc-internal code
3919                  * paths, direct syscalls) which close descriptors in ways that
3920                  * we can't intercept, so try to recover when we notice that
3921                  * that's happened
3922                  */
3923                 swrap_remove_stale(ret);
3924         }
3925         return ret;
3926 }
3927
3928 int open(const char *pathname, int flags, ...)
3929 {
3930         va_list ap;
3931         int fd;
3932
3933         va_start(ap, flags);
3934         fd = swrap_vopen(pathname, flags, ap);
3935         va_end(ap);
3936
3937         return fd;
3938 }
3939
3940 /****************************************************************************
3941  *   OPEN64
3942  ***************************************************************************/
3943
3944 #ifdef HAVE_OPEN64
3945 static int swrap_vopen64(const char *pathname, int flags, va_list ap)
3946 {
3947         int ret;
3948
3949         ret = libc_vopen64(pathname, flags, ap);
3950         if (ret != -1) {
3951                 /*
3952                  * There are methods for closing descriptors (libc-internal code
3953                  * paths, direct syscalls) which close descriptors in ways that
3954                  * we can't intercept, so try to recover when we notice that
3955                  * that's happened
3956                  */
3957                 swrap_remove_stale(ret);
3958         }
3959         return ret;
3960 }
3961
3962 int open64(const char *pathname, int flags, ...)
3963 {
3964         va_list ap;
3965         int fd;
3966
3967         va_start(ap, flags);
3968         fd = swrap_vopen64(pathname, flags, ap);
3969         va_end(ap);
3970
3971         return fd;
3972 }
3973 #endif /* HAVE_OPEN64 */
3974
3975 /****************************************************************************
3976  *   OPENAT
3977  ***************************************************************************/
3978
3979 static int swrap_vopenat(int dirfd, const char *path, int flags, va_list ap)
3980 {
3981         int ret;
3982
3983         ret = libc_vopenat(dirfd, path, flags, ap);
3984         if (ret != -1) {
3985                 /*
3986                  * There are methods for closing descriptors (libc-internal code
3987                  * paths, direct syscalls) which close descriptors in ways that
3988                  * we can't intercept, so try to recover when we notice that
3989                  * that's happened
3990                  */
3991                 swrap_remove_stale(ret);
3992         }
3993
3994         return ret;
3995 }
3996
3997 int openat(int dirfd, const char *path, int flags, ...)
3998 {
3999         va_list ap;
4000         int fd;
4001
4002         va_start(ap, flags);
4003         fd = swrap_vopenat(dirfd, path, flags, ap);
4004         va_end(ap);
4005
4006         return fd;
4007 }
4008
4009 /****************************************************************************
4010  *   GETPEERNAME
4011  ***************************************************************************/
4012
4013 static int swrap_getpeername(int s, struct sockaddr *name, socklen_t *addrlen)
4014 {
4015         struct socket_info *si = find_socket_info(s);
4016         socklen_t len;
4017         int ret = -1;
4018
4019         if (!si) {
4020                 return libc_getpeername(s, name, addrlen);
4021         }
4022
4023         SWRAP_LOCK_SI(si);
4024
4025         if (si->peername.sa_socklen == 0)
4026         {
4027                 errno = ENOTCONN;
4028                 goto out;
4029         }
4030
4031         len = MIN(*addrlen, si->peername.sa_socklen);
4032         if (len == 0) {
4033                 ret = 0;
4034                 goto out;
4035         }
4036
4037         memcpy(name, &si->peername.sa.ss, len);
4038         *addrlen = si->peername.sa_socklen;
4039
4040         ret = 0;
4041 out:
4042         SWRAP_UNLOCK_SI(si);
4043
4044         return ret;
4045 }
4046
4047 #ifdef HAVE_ACCEPT_PSOCKLEN_T
4048 int getpeername(int s, struct sockaddr *name, Psocklen_t addrlen)
4049 #else
4050 int getpeername(int s, struct sockaddr *name, socklen_t *addrlen)
4051 #endif
4052 {
4053         return swrap_getpeername(s, name, (socklen_t *)addrlen);
4054 }
4055
4056 /****************************************************************************
4057  *   GETSOCKNAME
4058  ***************************************************************************/
4059
4060 static int swrap_getsockname(int s, struct sockaddr *name, socklen_t *addrlen)
4061 {
4062         struct socket_info *si = find_socket_info(s);
4063         socklen_t len;
4064         int ret = -1;
4065
4066         if (!si) {
4067                 return libc_getsockname(s, name, addrlen);
4068         }
4069
4070         SWRAP_LOCK_SI(si);
4071
4072         len = MIN(*addrlen, si->myname.sa_socklen);
4073         if (len == 0) {
4074                 ret = 0;
4075                 goto out;
4076         }
4077
4078         memcpy(name, &si->myname.sa.ss, len);
4079         *addrlen = si->myname.sa_socklen;
4080
4081         ret = 0;
4082 out:
4083         SWRAP_UNLOCK_SI(si);
4084
4085         return ret;
4086 }
4087
4088 #ifdef HAVE_ACCEPT_PSOCKLEN_T
4089 int getsockname(int s, struct sockaddr *name, Psocklen_t addrlen)
4090 #else
4091 int getsockname(int s, struct sockaddr *name, socklen_t *addrlen)
4092 #endif
4093 {
4094         return swrap_getsockname(s, name, (socklen_t *)addrlen);
4095 }
4096
4097 /****************************************************************************
4098  *   GETSOCKOPT
4099  ***************************************************************************/
4100
4101 #ifndef SO_PROTOCOL
4102 # ifdef SO_PROTOTYPE /* The Solaris name */
4103 #  define SO_PROTOCOL SO_PROTOTYPE
4104 # endif /* SO_PROTOTYPE */
4105 #endif /* SO_PROTOCOL */
4106
4107 static int swrap_getsockopt(int s, int level, int optname,
4108                             void *optval, socklen_t *optlen)
4109 {
4110         struct socket_info *si = find_socket_info(s);
4111         int ret;
4112
4113         if (!si) {
4114                 return libc_getsockopt(s,
4115                                        level,
4116                                        optname,
4117                                        optval,
4118                                        optlen);
4119         }
4120
4121         SWRAP_LOCK_SI(si);
4122
4123         if (level == SOL_SOCKET) {
4124                 switch (optname) {
4125 #ifdef SO_DOMAIN
4126                 case SO_DOMAIN:
4127                         if (optval == NULL || optlen == NULL ||
4128                             *optlen < (socklen_t)sizeof(int)) {
4129                                 errno = EINVAL;
4130                                 ret = -1;
4131                                 goto done;
4132                         }
4133
4134                         *optlen = sizeof(int);
4135                         *(int *)optval = si->family;
4136                         ret = 0;
4137                         goto done;
4138 #endif /* SO_DOMAIN */
4139
4140 #ifdef SO_PROTOCOL
4141                 case SO_PROTOCOL:
4142                         if (optval == NULL || optlen == NULL ||
4143                             *optlen < (socklen_t)sizeof(int)) {
4144                                 errno = EINVAL;
4145                                 ret = -1;
4146                                 goto done;
4147                         }
4148
4149                         *optlen = sizeof(int);
4150                         *(int *)optval = si->protocol;
4151                         ret = 0;
4152                         goto done;
4153 #endif /* SO_PROTOCOL */
4154                 case SO_TYPE:
4155                         if (optval == NULL || optlen == NULL ||
4156                             *optlen < (socklen_t)sizeof(int)) {
4157                                 errno = EINVAL;
4158                                 ret = -1;
4159                                 goto done;
4160                         }
4161
4162                         *optlen = sizeof(int);
4163                         *(int *)optval = si->type;
4164                         ret = 0;
4165                         goto done;
4166                 default:
4167                         ret = libc_getsockopt(s,
4168                                               level,
4169                                               optname,
4170                                               optval,
4171                                               optlen);
4172                         goto done;
4173                 }
4174         } else if (level == IPPROTO_TCP) {
4175                 switch (optname) {
4176 #ifdef TCP_NODELAY
4177                 case TCP_NODELAY:
4178                         /*
4179                          * This enables sending packets directly out over TCP.
4180                          * As a unix socket is doing that any way, report it as
4181                          * enabled.
4182                          */
4183                         if (optval == NULL || optlen == NULL ||
4184                             *optlen < (socklen_t)sizeof(int)) {
4185                                 errno = EINVAL;
4186                                 ret = -1;
4187                                 goto done;
4188                         }
4189
4190                         *optlen = sizeof(int);
4191                         *(int *)optval = si->tcp_nodelay;
4192
4193                         ret = 0;
4194                         goto done;
4195 #endif /* TCP_NODELAY */
4196                 default:
4197                         break;
4198                 }
4199         }
4200
4201         errno = ENOPROTOOPT;
4202         ret = -1;
4203
4204 done:
4205         SWRAP_UNLOCK_SI(si);
4206         return ret;
4207 }
4208
4209 #ifdef HAVE_ACCEPT_PSOCKLEN_T
4210 int getsockopt(int s, int level, int optname, void *optval, Psocklen_t optlen)
4211 #else
4212 int getsockopt(int s, int level, int optname, void *optval, socklen_t *optlen)
4213 #endif
4214 {
4215         return swrap_getsockopt(s, level, optname, optval, (socklen_t *)optlen);
4216 }
4217
4218 /****************************************************************************
4219  *   SETSOCKOPT
4220  ***************************************************************************/
4221
4222 static int swrap_setsockopt(int s, int level, int optname,
4223                             const void *optval, socklen_t optlen)
4224 {
4225         struct socket_info *si = find_socket_info(s);
4226         int ret;
4227
4228         if (!si) {
4229                 return libc_setsockopt(s,
4230                                        level,
4231                                        optname,
4232                                        optval,
4233                                        optlen);
4234         }
4235
4236         if (level == SOL_SOCKET) {
4237                 return libc_setsockopt(s,
4238                                        level,
4239                                        optname,
4240                                        optval,
4241                                        optlen);
4242         }
4243
4244         SWRAP_LOCK_SI(si);
4245
4246         if (level == IPPROTO_TCP) {
4247                 switch (optname) {
4248 #ifdef TCP_NODELAY
4249                 case TCP_NODELAY: {
4250                         int i;
4251
4252                         /*
4253                          * This enables sending packets directly out over TCP.
4254                          * A unix socket is doing that any way.
4255                          */
4256                         if (optval == NULL || optlen == 0 ||
4257                             optlen < (socklen_t)sizeof(int)) {
4258                                 errno = EINVAL;
4259                                 ret = -1;
4260                                 goto done;
4261                         }
4262
4263                         i = *discard_const_p(int, optval);
4264                         if (i != 0 && i != 1) {
4265                                 errno = EINVAL;
4266                                 ret = -1;
4267                                 goto done;
4268                         }
4269                         si->tcp_nodelay = i;
4270
4271                         ret = 0;
4272                         goto done;
4273                 }
4274 #endif /* TCP_NODELAY */
4275                 default:
4276                         break;
4277                 }
4278         }
4279
4280         switch (si->family) {
4281         case AF_INET:
4282                 if (level == IPPROTO_IP) {
4283 #ifdef IP_PKTINFO
4284                         if (optname == IP_PKTINFO) {
4285                                 si->pktinfo = AF_INET;
4286                         }
4287 #endif /* IP_PKTINFO */
4288                 }
4289                 ret = 0;
4290                 goto done;
4291 #ifdef HAVE_IPV6
4292         case AF_INET6:
4293                 if (level == IPPROTO_IPV6) {
4294 #ifdef IPV6_RECVPKTINFO
4295                         if (optname == IPV6_RECVPKTINFO) {
4296                                 si->pktinfo = AF_INET6;
4297                         }
4298 #endif /* IPV6_PKTINFO */
4299                 }
4300                 ret = 0;
4301                 goto done;
4302 #endif
4303         default:
4304                 errno = ENOPROTOOPT;
4305                 ret = -1;
4306                 goto done;
4307         }
4308
4309 done:
4310         SWRAP_UNLOCK_SI(si);
4311         return ret;
4312 }
4313
4314 int setsockopt(int s, int level, int optname,
4315                const void *optval, socklen_t optlen)
4316 {
4317         return swrap_setsockopt(s, level, optname, optval, optlen);
4318 }
4319
4320 /****************************************************************************
4321  *   IOCTL
4322  ***************************************************************************/
4323
4324 static int swrap_vioctl(int s, unsigned long int r, va_list va)
4325 {
4326         struct socket_info *si = find_socket_info(s);
4327         va_list ap;
4328         int value;
4329         int rc;
4330
4331         if (!si) {
4332                 return libc_vioctl(s, r, va);
4333         }
4334
4335         SWRAP_LOCK_SI(si);
4336
4337         va_copy(ap, va);
4338
4339         rc = libc_vioctl(s, r, va);
4340
4341         switch (r) {
4342         case FIONREAD:
4343                 value = *((int *)va_arg(ap, int *));
4344
4345                 if (rc == -1 && errno != EAGAIN && errno != ENOBUFS) {
4346                         swrap_pcap_dump_packet(si, NULL, SWRAP_PENDING_RST, NULL, 0);
4347                 } else if (value == 0) { /* END OF FILE */
4348                         swrap_pcap_dump_packet(si, NULL, SWRAP_PENDING_RST, NULL, 0);
4349                 }
4350                 break;
4351         }
4352
4353         va_end(ap);
4354
4355         SWRAP_UNLOCK_SI(si);
4356         return rc;
4357 }
4358
4359 #ifdef HAVE_IOCTL_INT
4360 int ioctl(int s, int r, ...)
4361 #else
4362 int ioctl(int s, unsigned long int r, ...)
4363 #endif
4364 {
4365         va_list va;
4366         int rc;
4367
4368         va_start(va, r);
4369
4370         rc = swrap_vioctl(s, (unsigned long int) r, va);
4371
4372         va_end(va);
4373
4374         return rc;
4375 }
4376
4377 /*****************
4378  * CMSG
4379  *****************/
4380
4381 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
4382
4383 #ifndef CMSG_ALIGN
4384 # ifdef _ALIGN /* BSD */
4385 #define CMSG_ALIGN _ALIGN
4386 # else
4387 #define CMSG_ALIGN(len) (((len) + sizeof(size_t) - 1) & ~(sizeof(size_t) - 1))
4388 # endif /* _ALIGN */
4389 #endif /* CMSG_ALIGN */
4390
4391 /**
4392  * @brief Add a cmsghdr to a msghdr.
4393  *
4394  * This is an function to add any type of cmsghdr. It will operate on the
4395  * msg->msg_control and msg->msg_controllen you pass in by adapting them to
4396  * the buffer position after the added cmsg element. Hence, this function is
4397  * intended to be used with an intermediate msghdr and not on the original
4398  * one handed in by the client.
4399  *
4400  * @param[in]  msg      The msghdr to which to add the cmsg.
4401  *
4402  * @param[in]  level    The cmsg level to set.
4403  *
4404  * @param[in]  type     The cmsg type to set.
4405  *
4406  * @param[in]  data     The cmsg data to set.
4407  *
4408  * @param[in]  len      the length of the data to set.
4409  */
4410 static void swrap_msghdr_add_cmsghdr(struct msghdr *msg,
4411                                      int level,
4412                                      int type,
4413                                      const void *data,
4414                                      size_t len)
4415 {
4416         size_t cmlen = CMSG_LEN(len);
4417         size_t cmspace = CMSG_SPACE(len);
4418         uint8_t cmbuf[cmspace];
4419         void *cast_ptr = (void *)cmbuf;
4420         struct cmsghdr *cm = (struct cmsghdr *)cast_ptr;
4421         uint8_t *p;
4422
4423         memset(cmbuf, 0, cmspace);
4424
4425         if (msg->msg_controllen < cmlen) {
4426                 cmlen = msg->msg_controllen;
4427                 msg->msg_flags |= MSG_CTRUNC;
4428         }
4429
4430         if (msg->msg_controllen < cmspace) {
4431                 cmspace = msg->msg_controllen;
4432         }
4433
4434         /*
4435          * We copy the full input data into an intermediate cmsghdr first
4436          * in order to more easily cope with truncation.
4437          */
4438         cm->cmsg_len = cmlen;
4439         cm->cmsg_level = level;
4440         cm->cmsg_type = type;
4441         memcpy(CMSG_DATA(cm), data, len);
4442
4443         /*
4444          * We now copy the possibly truncated buffer.
4445          * We copy cmlen bytes, but consume cmspace bytes,
4446          * leaving the possible padding uninitialiazed.
4447          */
4448         p = (uint8_t *)msg->msg_control;
4449         memcpy(p, cm, cmlen);
4450         p += cmspace;
4451         msg->msg_control = p;
4452         msg->msg_controllen -= cmspace;
4453
4454         return;
4455 }
4456
4457 static int swrap_msghdr_add_pktinfo(struct socket_info *si,
4458                                     struct msghdr *msg)
4459 {
4460         /* Add packet info */
4461         switch (si->pktinfo) {
4462 #if defined(IP_PKTINFO) && (defined(HAVE_STRUCT_IN_PKTINFO) || defined(IP_RECVDSTADDR))
4463         case AF_INET: {
4464                 struct sockaddr_in *sin;
4465 #if defined(HAVE_STRUCT_IN_PKTINFO)
4466                 struct in_pktinfo pkt;
4467 #elif defined(IP_RECVDSTADDR)
4468                 struct in_addr pkt;
4469 #endif
4470
4471                 if (si->bindname.sa_socklen == sizeof(struct sockaddr_in)) {
4472                         sin = &si->bindname.sa.in;
4473                 } else {
4474                         if (si->myname.sa_socklen != sizeof(struct sockaddr_in)) {
4475                                 return 0;
4476                         }
4477                         sin = &si->myname.sa.in;
4478                 }
4479
4480                 ZERO_STRUCT(pkt);
4481
4482 #if defined(HAVE_STRUCT_IN_PKTINFO)
4483                 pkt.ipi_ifindex = socket_wrapper_default_iface();
4484                 pkt.ipi_addr.s_addr = sin->sin_addr.s_addr;
4485 #elif defined(IP_RECVDSTADDR)
4486                 pkt = sin->sin_addr;
4487 #endif
4488
4489                 swrap_msghdr_add_cmsghdr(msg, IPPROTO_IP, IP_PKTINFO,
4490                                          &pkt, sizeof(pkt));
4491
4492                 break;
4493         }
4494 #endif /* IP_PKTINFO */
4495 #if defined(HAVE_IPV6)
4496         case AF_INET6: {
4497 #if defined(IPV6_PKTINFO) && defined(HAVE_STRUCT_IN6_PKTINFO)
4498                 struct sockaddr_in6 *sin6;
4499                 struct in6_pktinfo pkt6;
4500
4501                 if (si->bindname.sa_socklen == sizeof(struct sockaddr_in6)) {
4502                         sin6 = &si->bindname.sa.in6;
4503                 } else {
4504                         if (si->myname.sa_socklen != sizeof(struct sockaddr_in6)) {
4505                                 return 0;
4506                         }
4507                         sin6 = &si->myname.sa.in6;
4508                 }
4509
4510                 ZERO_STRUCT(pkt6);
4511
4512                 pkt6.ipi6_ifindex = socket_wrapper_default_iface();
4513                 pkt6.ipi6_addr = sin6->sin6_addr;
4514
4515                 swrap_msghdr_add_cmsghdr(msg, IPPROTO_IPV6, IPV6_PKTINFO,
4516                                         &pkt6, sizeof(pkt6));
4517 #endif /* HAVE_STRUCT_IN6_PKTINFO */
4518
4519                 break;
4520         }
4521 #endif /* IPV6_PKTINFO */
4522         default:
4523                 return -1;
4524         }
4525
4526         return 0;
4527 }
4528
4529 static int swrap_msghdr_add_socket_info(struct socket_info *si,
4530                                         struct msghdr *omsg)
4531 {
4532         int rc = 0;
4533
4534         if (si->pktinfo > 0) {
4535                 rc = swrap_msghdr_add_pktinfo(si, omsg);
4536         }
4537
4538         return rc;
4539 }
4540
4541 static int swrap_sendmsg_copy_cmsg(struct cmsghdr *cmsg,
4542                                    uint8_t **cm_data,
4543                                    size_t *cm_data_space);
4544 static int swrap_sendmsg_filter_cmsg_socket(struct cmsghdr *cmsg,
4545                                             uint8_t **cm_data,
4546                                             size_t *cm_data_space);
4547
4548 static int swrap_sendmsg_filter_cmsghdr(struct msghdr *msg,
4549                                         uint8_t **cm_data,
4550                                         size_t *cm_data_space) {
4551         struct cmsghdr *cmsg;
4552         int rc = -1;
4553
4554         /* Nothing to do */
4555         if (msg->msg_controllen == 0 || msg->msg_control == NULL) {
4556                 return 0;
4557         }
4558
4559         for (cmsg = CMSG_FIRSTHDR(msg);
4560              cmsg != NULL;
4561              cmsg = CMSG_NXTHDR(msg, cmsg)) {
4562                 switch (cmsg->cmsg_level) {
4563                 case IPPROTO_IP:
4564                         rc = swrap_sendmsg_filter_cmsg_socket(cmsg,
4565                                                               cm_data,
4566                                                               cm_data_space);
4567                         break;
4568                 default:
4569                         rc = swrap_sendmsg_copy_cmsg(cmsg,
4570                                                      cm_data,
4571                                                      cm_data_space);
4572                         break;
4573                 }
4574         }
4575
4576         return rc;
4577 }
4578
4579 static int swrap_sendmsg_copy_cmsg(struct cmsghdr *cmsg,
4580                                    uint8_t **cm_data,
4581                                    size_t *cm_data_space)
4582 {
4583         size_t cmspace;
4584         uint8_t *p;
4585
4586         cmspace = *cm_data_space + CMSG_ALIGN(cmsg->cmsg_len);
4587
4588         p = realloc((*cm_data), cmspace);
4589         if (p == NULL) {
4590                 return -1;
4591         }
4592         (*cm_data) = p;
4593
4594         p = (*cm_data) + (*cm_data_space);
4595         *cm_data_space = cmspace;
4596
4597         memcpy(p, cmsg, cmsg->cmsg_len);
4598
4599         return 0;
4600 }
4601
4602 static int swrap_sendmsg_filter_cmsg_pktinfo(struct cmsghdr *cmsg,
4603                                             uint8_t **cm_data,
4604                                             size_t *cm_data_space);
4605
4606
4607 static int swrap_sendmsg_filter_cmsg_socket(struct cmsghdr *cmsg,
4608                                             uint8_t **cm_data,
4609                                             size_t *cm_data_space)
4610 {
4611         int rc = -1;
4612
4613         switch(cmsg->cmsg_type) {
4614 #ifdef IP_PKTINFO
4615         case IP_PKTINFO:
4616                 rc = swrap_sendmsg_filter_cmsg_pktinfo(cmsg,
4617                                                        cm_data,
4618                                                        cm_data_space);
4619                 break;
4620 #endif
4621 #ifdef IPV6_PKTINFO
4622         case IPV6_PKTINFO:
4623                 rc = swrap_sendmsg_filter_cmsg_pktinfo(cmsg,
4624                                                        cm_data,
4625                                                        cm_data_space);
4626                 break;
4627 #endif
4628         default:
4629                 break;
4630         }
4631
4632         return rc;
4633 }
4634
4635 static int swrap_sendmsg_filter_cmsg_pktinfo(struct cmsghdr *cmsg,
4636                                              uint8_t **cm_data,
4637                                              size_t *cm_data_space)
4638 {
4639         (void)cmsg; /* unused */
4640         (void)cm_data; /* unused */
4641         (void)cm_data_space; /* unused */
4642
4643         /*
4644          * Passing a IP pktinfo to a unix socket might be rejected by the
4645          * Kernel, at least on FreeBSD. So skip this cmsg.
4646          */
4647         return 0;
4648 }
4649 #endif /* HAVE_STRUCT_MSGHDR_MSG_CONTROL */
4650
4651 static ssize_t swrap_sendmsg_before(int fd,
4652                                     struct socket_info *si,
4653                                     struct msghdr *msg,
4654                                     struct iovec *tmp_iov,
4655                                     struct sockaddr_un *tmp_un,
4656                                     const struct sockaddr_un **to_un,
4657                                     const struct sockaddr **to,
4658                                     int *bcast)
4659 {
4660         size_t i, len = 0;
4661         ssize_t ret = -1;
4662
4663         if (to_un) {
4664                 *to_un = NULL;
4665         }
4666         if (to) {
4667                 *to = NULL;
4668         }
4669         if (bcast) {
4670                 *bcast = 0;
4671         }
4672
4673         SWRAP_LOCK_SI(si);
4674
4675         switch (si->type) {
4676         case SOCK_STREAM: {
4677                 unsigned long mtu;
4678
4679                 if (!si->connected) {
4680                         errno = ENOTCONN;
4681                         goto out;
4682                 }
4683
4684                 if (msg->msg_iovlen == 0) {
4685                         break;
4686                 }
4687
4688                 mtu = socket_wrapper_mtu();
4689                 for (i = 0; i < (size_t)msg->msg_iovlen; i++) {
4690                         size_t nlen;
4691                         nlen = len + msg->msg_iov[i].iov_len;
4692                         if (nlen > mtu) {
4693                                 break;
4694                         }
4695                 }
4696                 msg->msg_iovlen = i;
4697                 if (msg->msg_iovlen == 0) {
4698                         *tmp_iov = msg->msg_iov[0];
4699                         tmp_iov->iov_len = MIN((size_t)tmp_iov->iov_len,
4700                                                (size_t)mtu);
4701                         msg->msg_iov = tmp_iov;
4702                         msg->msg_iovlen = 1;
4703                 }
4704                 break;
4705         }
4706         case SOCK_DGRAM:
4707                 if (si->connected) {
4708                         if (msg->msg_name != NULL) {
4709                                 /*
4710                                  * We are dealing with unix sockets and if we
4711                                  * are connected, we should only talk to the
4712                                  * connected unix path. Using the fd to send
4713                                  * to another server would be hard to achieve.
4714                                  */
4715                                 msg->msg_name = NULL;
4716                                 msg->msg_namelen = 0;
4717                         }
4718                 } else {
4719                         const struct sockaddr *msg_name;
4720                         msg_name = (const struct sockaddr *)msg->msg_name;
4721
4722                         if (msg_name == NULL) {
4723                                 errno = ENOTCONN;
4724                                 goto out;
4725                         }
4726
4727
4728                         ret = sockaddr_convert_to_un(si, msg_name, msg->msg_namelen,
4729                                                      tmp_un, 0, bcast);
4730                         if (ret == -1) {
4731                                 goto out;
4732                         }
4733
4734                         if (to_un) {
4735                                 *to_un = tmp_un;
4736                         }
4737                         if (to) {
4738                                 *to = msg_name;
4739                         }
4740                         msg->msg_name = tmp_un;
4741                         msg->msg_namelen = sizeof(*tmp_un);
4742                 }
4743
4744                 if (si->bound == 0) {
4745                         ret = swrap_auto_bind(fd, si, si->family);
4746                         if (ret == -1) {
4747                                 SWRAP_UNLOCK_SI(si);
4748                                 if (errno == ENOTSOCK) {
4749                                         swrap_remove_stale(fd);
4750                                         ret = -ENOTSOCK;
4751                                 } else {
4752                                         SWRAP_LOG(SWRAP_LOG_ERROR, "swrap_sendmsg_before failed");
4753                                 }
4754                                 return ret;
4755                         }
4756                 }
4757
4758                 if (!si->defer_connect) {
4759                         break;
4760                 }
4761
4762                 ret = sockaddr_convert_to_un(si,
4763                                              &si->peername.sa.s,
4764                                              si->peername.sa_socklen,
4765                                              tmp_un,
4766                                              0,
4767                                              NULL);
4768                 if (ret == -1) {
4769                         goto out;
4770                 }
4771
4772                 ret = libc_connect(fd,
4773                                    (struct sockaddr *)(void *)tmp_un,
4774                                    sizeof(*tmp_un));
4775
4776                 /* to give better errors */
4777                 if (ret == -1 && errno == ENOENT) {
4778                         errno = EHOSTUNREACH;
4779                 }
4780
4781                 if (ret == -1) {
4782                         goto out;
4783                 }
4784
4785                 si->defer_connect = 0;
4786                 break;
4787         default:
4788                 errno = EHOSTUNREACH;
4789                 goto out;
4790         }
4791
4792 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
4793         if (msg->msg_controllen > 0 && msg->msg_control != NULL) {
4794                 uint8_t *cmbuf = NULL;
4795                 size_t cmlen = 0;
4796
4797                 ret = swrap_sendmsg_filter_cmsghdr(msg, &cmbuf, &cmlen);
4798                 if (ret < 0) {
4799                         free(cmbuf);
4800                         goto out;
4801                 }
4802
4803                 if (cmlen == 0) {
4804                         msg->msg_controllen = 0;
4805                         msg->msg_control = NULL;
4806                 } else if (cmlen < msg->msg_controllen && cmbuf != NULL) {
4807                         memcpy(msg->msg_control, cmbuf, cmlen);
4808                         msg->msg_controllen = cmlen;
4809                 }
4810                 free(cmbuf);
4811         }
4812 #endif
4813
4814         ret = 0;
4815 out:
4816         SWRAP_UNLOCK_SI(si);
4817
4818         return ret;
4819 }
4820
4821 static void swrap_sendmsg_after(int fd,
4822                                 struct socket_info *si,
4823                                 struct msghdr *msg,
4824                                 const struct sockaddr *to,
4825                                 ssize_t ret)
4826 {
4827         int saved_errno = errno;
4828         size_t i, len = 0;
4829         uint8_t *buf;
4830         off_t ofs = 0;
4831         size_t avail = 0;
4832         size_t remain;
4833
4834         /* to give better errors */
4835         if (ret == -1) {
4836                 if (saved_errno == ENOENT) {
4837                         saved_errno = EHOSTUNREACH;
4838                 } else if (saved_errno == ENOTSOCK) {
4839                         /* If the fd is not a socket, remove it */
4840                         swrap_remove_stale(fd);
4841                 }
4842         }
4843
4844         for (i = 0; i < (size_t)msg->msg_iovlen; i++) {
4845                 avail += msg->msg_iov[i].iov_len;
4846         }
4847
4848         if (ret == -1) {
4849                 remain = MIN(80, avail);
4850         } else {
4851                 remain = ret;
4852         }
4853
4854         /* we capture it as one single packet */
4855         buf = (uint8_t *)malloc(remain);
4856         if (!buf) {
4857                 /* we just not capture the packet */
4858                 errno = saved_errno;
4859                 return;
4860         }
4861
4862         for (i = 0; i < (size_t)msg->msg_iovlen; i++) {
4863                 size_t this_time = MIN(remain, (size_t)msg->msg_iov[i].iov_len);
4864                 memcpy(buf + ofs,
4865                        msg->msg_iov[i].iov_base,
4866                        this_time);
4867                 ofs += this_time;
4868                 remain -= this_time;
4869         }
4870         len = ofs;
4871
4872         SWRAP_LOCK_SI(si);
4873
4874         switch (si->type) {
4875         case SOCK_STREAM:
4876                 if (ret == -1) {
4877                         swrap_pcap_dump_packet(si, NULL, SWRAP_SEND, buf, len);
4878                         swrap_pcap_dump_packet(si, NULL, SWRAP_SEND_RST, NULL, 0);
4879                 } else {
4880                         swrap_pcap_dump_packet(si, NULL, SWRAP_SEND, buf, len);
4881                 }
4882                 break;
4883
4884         case SOCK_DGRAM:
4885                 if (si->connected) {
4886                         to = &si->peername.sa.s;
4887                 }
4888                 if (ret == -1) {
4889                         swrap_pcap_dump_packet(si, to, SWRAP_SENDTO, buf, len);
4890                         swrap_pcap_dump_packet(si, to, SWRAP_SENDTO_UNREACH, buf, len);
4891                 } else {
4892                         swrap_pcap_dump_packet(si, to, SWRAP_SENDTO, buf, len);
4893                 }
4894                 break;
4895         }
4896
4897         SWRAP_UNLOCK_SI(si);
4898
4899         free(buf);
4900         errno = saved_errno;
4901 }
4902
4903 static int swrap_recvmsg_before(int fd,
4904                                 struct socket_info *si,
4905                                 struct msghdr *msg,
4906                                 struct iovec *tmp_iov)
4907 {
4908         size_t i, len = 0;
4909         int ret = -1;
4910
4911         SWRAP_LOCK_SI(si);
4912
4913         (void)fd; /* unused */
4914
4915         switch (si->type) {
4916         case SOCK_STREAM: {
4917                 unsigned int mtu;
4918                 if (!si->connected) {
4919                         errno = ENOTCONN;
4920                         goto out;
4921                 }
4922
4923                 if (msg->msg_iovlen == 0) {
4924                         break;
4925                 }
4926
4927                 mtu = socket_wrapper_mtu();
4928                 for (i = 0; i < (size_t)msg->msg_iovlen; i++) {
4929                         size_t nlen;
4930                         nlen = len + msg->msg_iov[i].iov_len;
4931                         if (nlen > mtu) {
4932                                 break;
4933                         }
4934                 }
4935                 msg->msg_iovlen = i;
4936                 if (msg->msg_iovlen == 0) {
4937                         *tmp_iov = msg->msg_iov[0];
4938                         tmp_iov->iov_len = MIN((size_t)tmp_iov->iov_len,
4939                                                (size_t)mtu);
4940                         msg->msg_iov = tmp_iov;
4941                         msg->msg_iovlen = 1;
4942                 }
4943                 break;
4944         }
4945         case SOCK_DGRAM:
4946                 if (msg->msg_name == NULL) {
4947                         errno = EINVAL;
4948                         goto out;
4949                 }
4950
4951                 if (msg->msg_iovlen == 0) {
4952                         break;
4953                 }
4954
4955                 if (si->bound == 0) {
4956                         ret = swrap_auto_bind(fd, si, si->family);
4957                         if (ret == -1) {
4958                                 SWRAP_UNLOCK_SI(si);
4959                                 /*
4960                                  * When attempting to read or write to a
4961                                  * descriptor, if an underlying autobind fails
4962                                  * because it's not a socket, stop intercepting
4963                                  * uses of that descriptor.
4964                                  */
4965                                 if (errno == ENOTSOCK) {
4966                                         swrap_remove_stale(fd);
4967                                         ret = -ENOTSOCK;
4968                                 } else {
4969                                         SWRAP_LOG(SWRAP_LOG_ERROR,
4970                                                   "swrap_recvmsg_before failed");
4971                                 }
4972                                 return ret;
4973                         }
4974                 }
4975                 break;
4976         default:
4977                 errno = EHOSTUNREACH;
4978                 goto out;
4979         }
4980
4981         ret = 0;
4982 out:
4983         SWRAP_UNLOCK_SI(si);
4984
4985         return ret;
4986 }
4987
4988 static int swrap_recvmsg_after(int fd,
4989                                struct socket_info *si,
4990                                struct msghdr *msg,
4991                                const struct sockaddr_un *un_addr,
4992                                socklen_t un_addrlen,
4993                                ssize_t ret)
4994 {
4995         int saved_errno = errno;
4996         size_t i;
4997         uint8_t *buf = NULL;
4998         off_t ofs = 0;
4999         size_t avail = 0;
5000         size_t remain;
5001         int rc;
5002
5003         /* to give better errors */
5004         if (ret == -1) {
5005                 if (saved_errno == ENOENT) {
5006                         saved_errno = EHOSTUNREACH;
5007                 } else if (saved_errno == ENOTSOCK) {
5008                         /* If the fd is not a socket, remove it */
5009                         swrap_remove_stale(fd);
5010                 }
5011         }
5012
5013         for (i = 0; i < (size_t)msg->msg_iovlen; i++) {
5014                 avail += msg->msg_iov[i].iov_len;
5015         }
5016
5017         SWRAP_LOCK_SI(si);
5018
5019         /* Convert the socket address before we leave */
5020         if (si->type == SOCK_DGRAM && un_addr != NULL) {
5021                 rc = sockaddr_convert_from_un(si,
5022                                               un_addr,
5023                                               un_addrlen,
5024                                               si->family,
5025                                               msg->msg_name,
5026                                               &msg->msg_namelen);
5027                 if (rc == -1) {
5028                         goto done;
5029                 }
5030         }
5031
5032         if (avail == 0) {
5033                 rc = 0;
5034                 goto done;
5035         }
5036
5037         if (ret == -1) {
5038                 remain = MIN(80, avail);
5039         } else {
5040                 remain = ret;
5041         }
5042
5043         /* we capture it as one single packet */
5044         buf = (uint8_t *)malloc(remain);
5045         if (buf == NULL) {
5046                 /* we just not capture the packet */
5047                 SWRAP_UNLOCK_SI(si);
5048                 errno = saved_errno;
5049                 return -1;
5050         }
5051
5052         for (i = 0; i < (size_t)msg->msg_iovlen; i++) {
5053                 size_t this_time = MIN(remain, (size_t)msg->msg_iov[i].iov_len);
5054                 memcpy(buf + ofs,
5055                        msg->msg_iov[i].iov_base,
5056                        this_time);
5057                 ofs += this_time;
5058                 remain -= this_time;
5059         }
5060
5061         switch (si->type) {
5062         case SOCK_STREAM:
5063                 if (ret == -1 && saved_errno != EAGAIN && saved_errno != ENOBUFS) {
5064                         swrap_pcap_dump_packet(si, NULL, SWRAP_RECV_RST, NULL, 0);
5065                 } else if (ret == 0) { /* END OF FILE */
5066                         swrap_pcap_dump_packet(si, NULL, SWRAP_RECV_RST, NULL, 0);
5067                 } else if (ret > 0) {
5068                         swrap_pcap_dump_packet(si, NULL, SWRAP_RECV, buf, ret);
5069                 }
5070                 break;
5071
5072         case SOCK_DGRAM:
5073                 if (ret == -1) {
5074                         break;
5075                 }
5076
5077                 if (un_addr != NULL) {
5078                         swrap_pcap_dump_packet(si,
5079                                           msg->msg_name,
5080                                           SWRAP_RECVFROM,
5081                                           buf,
5082                                           ret);
5083                 } else {
5084                         swrap_pcap_dump_packet(si,
5085                                           msg->msg_name,
5086                                           SWRAP_RECV,
5087                                           buf,
5088                                           ret);
5089                 }
5090
5091                 break;
5092         }
5093
5094         rc = 0;
5095 done:
5096         free(buf);
5097         errno = saved_errno;
5098
5099 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5100         if (rc == 0 &&
5101             msg->msg_controllen > 0 &&
5102             msg->msg_control != NULL) {
5103                 rc = swrap_msghdr_add_socket_info(si, msg);
5104                 if (rc < 0) {
5105                         SWRAP_UNLOCK_SI(si);
5106                         return -1;
5107                 }
5108         }
5109 #endif
5110
5111         SWRAP_UNLOCK_SI(si);
5112         return rc;
5113 }
5114
5115 /****************************************************************************
5116  *   RECVFROM
5117  ***************************************************************************/
5118
5119 static ssize_t swrap_recvfrom(int s, void *buf, size_t len, int flags,
5120                               struct sockaddr *from, socklen_t *fromlen)
5121 {
5122         struct swrap_address from_addr = {
5123                 .sa_socklen = sizeof(struct sockaddr_un),
5124         };
5125         ssize_t ret;
5126         struct socket_info *si = find_socket_info(s);
5127         struct swrap_address saddr = {
5128                 .sa_socklen = sizeof(struct sockaddr_storage),
5129         };
5130         struct msghdr msg;
5131         struct iovec tmp;
5132         int tret;
5133
5134         if (!si) {
5135                 return libc_recvfrom(s,
5136                                      buf,
5137                                      len,
5138                                      flags,
5139                                      from,
5140                                      fromlen);
5141         }
5142
5143         tmp.iov_base = buf;
5144         tmp.iov_len = len;
5145
5146         ZERO_STRUCT(msg);
5147         if (from != NULL && fromlen != NULL) {
5148                 msg.msg_name = from;   /* optional address */
5149                 msg.msg_namelen = *fromlen; /* size of address */
5150         } else {
5151                 msg.msg_name = &saddr.sa.s; /* optional address */
5152                 msg.msg_namelen = saddr.sa_socklen; /* size of address */
5153         }
5154         msg.msg_iov = &tmp;            /* scatter/gather array */
5155         msg.msg_iovlen = 1;            /* # elements in msg_iov */
5156 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5157         msg.msg_control = NULL;        /* ancillary data, see below */
5158         msg.msg_controllen = 0;        /* ancillary data buffer len */
5159         msg.msg_flags = 0;             /* flags on received message */
5160 #endif
5161
5162         tret = swrap_recvmsg_before(s, si, &msg, &tmp);
5163         if (tret < 0) {
5164                 return -1;
5165         }
5166
5167         buf = msg.msg_iov[0].iov_base;
5168         len = msg.msg_iov[0].iov_len;
5169
5170         ret = libc_recvfrom(s,
5171                             buf,
5172                             len,
5173                             flags,
5174                             &from_addr.sa.s,
5175                             &from_addr.sa_socklen);
5176         if (ret == -1) {
5177                 return ret;
5178         }
5179
5180         tret = swrap_recvmsg_after(s,
5181                                    si,
5182                                    &msg,
5183                                    &from_addr.sa.un,
5184                                    from_addr.sa_socklen,
5185                                    ret);
5186         if (tret != 0) {
5187                 return tret;
5188         }
5189
5190         if (from != NULL && fromlen != NULL) {
5191                 *fromlen = msg.msg_namelen;
5192         }
5193
5194         return ret;
5195 }
5196
5197 #ifdef HAVE_ACCEPT_PSOCKLEN_T
5198 ssize_t recvfrom(int s, void *buf, size_t len, int flags,
5199                  struct sockaddr *from, Psocklen_t fromlen)
5200 #else
5201 ssize_t recvfrom(int s, void *buf, size_t len, int flags,
5202                  struct sockaddr *from, socklen_t *fromlen)
5203 #endif
5204 {
5205         return swrap_recvfrom(s, buf, len, flags, from, (socklen_t *)fromlen);
5206 }
5207
5208 /****************************************************************************
5209  *   SENDTO
5210  ***************************************************************************/
5211
5212 static ssize_t swrap_sendto(int s, const void *buf, size_t len, int flags,
5213                             const struct sockaddr *to, socklen_t tolen)
5214 {
5215         struct msghdr msg;
5216         struct iovec tmp;
5217         struct swrap_address un_addr = {
5218                 .sa_socklen = sizeof(struct sockaddr_un),
5219         };
5220         const struct sockaddr_un *to_un = NULL;
5221         ssize_t ret;
5222         int rc;
5223         struct socket_info *si = find_socket_info(s);
5224         int bcast = 0;
5225
5226         if (!si) {
5227                 return libc_sendto(s, buf, len, flags, to, tolen);
5228         }
5229
5230         tmp.iov_base = discard_const_p(char, buf);
5231         tmp.iov_len = len;
5232
5233         ZERO_STRUCT(msg);
5234         msg.msg_name = discard_const_p(struct sockaddr, to); /* optional address */
5235         msg.msg_namelen = tolen;       /* size of address */
5236         msg.msg_iov = &tmp;            /* scatter/gather array */
5237         msg.msg_iovlen = 1;            /* # elements in msg_iov */
5238 #if HAVE_STRUCT_MSGHDR_MSG_CONTROL
5239         msg.msg_control = NULL;        /* ancillary data, see below */
5240         msg.msg_controllen = 0;        /* ancillary data buffer len */
5241         msg.msg_flags = 0;             /* flags on received message */
5242 #endif
5243
5244         rc = swrap_sendmsg_before(s,
5245                                   si,
5246                                   &msg,
5247                                   &tmp,
5248                                   &un_addr.sa.un,
5249                                   &to_un,
5250                                   &to,
5251                                   &bcast);
5252         if (rc < 0) {
5253                 return -1;
5254         }
5255
5256         buf = msg.msg_iov[0].iov_base;
5257         len = msg.msg_iov[0].iov_len;
5258
5259         if (bcast) {
5260                 struct stat st;
5261                 unsigned int iface;
5262                 unsigned int prt = ntohs(((const struct sockaddr_in *)(const void *)to)->sin_port);
5263                 char type;
5264
5265                 type = SOCKET_TYPE_CHAR_UDP;
5266
5267                 for(iface=0; iface <= MAX_WRAPPED_INTERFACES; iface++) {
5268                         snprintf(un_addr.sa.un.sun_path,
5269                                  sizeof(un_addr.sa.un.sun_path),
5270                                  "%s/"SOCKET_FORMAT,
5271                                  socket_wrapper_dir(), type, iface, prt);
5272                         if (stat(un_addr.sa.un.sun_path, &st) != 0) continue;
5273
5274                         /* ignore the any errors in broadcast sends */
5275                         libc_sendto(s,
5276                                     buf,
5277                                     len,
5278                                     flags,
5279                                     &un_addr.sa.s,
5280                                     un_addr.sa_socklen);
5281                 }
5282
5283                 SWRAP_LOCK_SI(si);
5284
5285                 swrap_pcap_dump_packet(si, to, SWRAP_SENDTO, buf, len);
5286
5287                 SWRAP_UNLOCK_SI(si);
5288
5289                 return len;
5290         }
5291
5292         SWRAP_LOCK_SI(si);
5293         /*
5294          * If it is a dgram socket and we are connected, don't include the
5295          * 'to' address.
5296          */
5297         if (si->type == SOCK_DGRAM && si->connected) {
5298                 ret = libc_sendto(s,
5299                                   buf,
5300                                   len,
5301                                   flags,
5302                                   NULL,
5303                                   0);
5304         } else {
5305                 ret = libc_sendto(s,
5306                                   buf,
5307                                   len,
5308                                   flags,
5309                                   (struct sockaddr *)msg.msg_name,
5310                                   msg.msg_namelen);
5311         }
5312
5313         SWRAP_UNLOCK_SI(si);
5314
5315         swrap_sendmsg_after(s, si, &msg, to, ret);
5316
5317         return ret;
5318 }
5319
5320 ssize_t sendto(int s, const void *buf, size_t len, int flags,
5321                const struct sockaddr *to, socklen_t tolen)
5322 {
5323         return swrap_sendto(s, buf, len, flags, to, tolen);
5324 }
5325
5326 /****************************************************************************
5327  *   READV
5328  ***************************************************************************/
5329
5330 static ssize_t swrap_recv(int s, void *buf, size_t len, int flags)
5331 {
5332         struct socket_info *si;
5333         struct msghdr msg;
5334         struct swrap_address saddr = {
5335                 .sa_socklen = sizeof(struct sockaddr_storage),
5336         };
5337         struct iovec tmp;
5338         ssize_t ret;
5339         int tret;
5340
5341         si = find_socket_info(s);
5342         if (si == NULL) {
5343                 return libc_recv(s, buf, len, flags);
5344         }
5345
5346         tmp.iov_base = buf;
5347         tmp.iov_len = len;
5348
5349         ZERO_STRUCT(msg);
5350         msg.msg_name = &saddr.sa.s;    /* optional address */
5351         msg.msg_namelen = saddr.sa_socklen; /* size of address */
5352         msg.msg_iov = &tmp;            /* scatter/gather array */
5353         msg.msg_iovlen = 1;            /* # elements in msg_iov */
5354 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5355         msg.msg_control = NULL;        /* ancillary data, see below */
5356         msg.msg_controllen = 0;        /* ancillary data buffer len */
5357         msg.msg_flags = 0;             /* flags on received message */
5358 #endif
5359
5360         tret = swrap_recvmsg_before(s, si, &msg, &tmp);
5361         if (tret < 0) {
5362                 return -1;
5363         }
5364
5365         buf = msg.msg_iov[0].iov_base;
5366         len = msg.msg_iov[0].iov_len;
5367
5368         ret = libc_recv(s, buf, len, flags);
5369
5370         tret = swrap_recvmsg_after(s, si, &msg, NULL, 0, ret);
5371         if (tret != 0) {
5372                 return tret;
5373         }
5374
5375         return ret;
5376 }
5377
5378 ssize_t recv(int s, void *buf, size_t len, int flags)
5379 {
5380         return swrap_recv(s, buf, len, flags);
5381 }
5382
5383 /****************************************************************************
5384  *   READ
5385  ***************************************************************************/
5386
5387 static ssize_t swrap_read(int s, void *buf, size_t len)
5388 {
5389         struct socket_info *si;
5390         struct msghdr msg;
5391         struct iovec tmp;
5392         struct swrap_address saddr = {
5393                 .sa_socklen = sizeof(struct sockaddr_storage),
5394         };
5395         ssize_t ret;
5396         int tret;
5397
5398         si = find_socket_info(s);
5399         if (si == NULL) {
5400                 return libc_read(s, buf, len);
5401         }
5402
5403         tmp.iov_base = buf;
5404         tmp.iov_len = len;
5405
5406         ZERO_STRUCT(msg);
5407         msg.msg_name = &saddr.sa.ss;   /* optional address */
5408         msg.msg_namelen = saddr.sa_socklen; /* size of address */
5409         msg.msg_iov = &tmp;            /* scatter/gather array */
5410         msg.msg_iovlen = 1;            /* # elements in msg_iov */
5411 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5412         msg.msg_control = NULL;        /* ancillary data, see below */
5413         msg.msg_controllen = 0;        /* ancillary data buffer len */
5414         msg.msg_flags = 0;             /* flags on received message */
5415 #endif
5416
5417         tret = swrap_recvmsg_before(s, si, &msg, &tmp);
5418         if (tret < 0) {
5419                 if (tret == -ENOTSOCK) {
5420                         return libc_read(s, buf, len);
5421                 }
5422                 return -1;
5423         }
5424
5425         buf = msg.msg_iov[0].iov_base;
5426         len = msg.msg_iov[0].iov_len;
5427
5428         ret = libc_read(s, buf, len);
5429
5430         tret = swrap_recvmsg_after(s, si, &msg, NULL, 0, ret);
5431         if (tret != 0) {
5432                 return tret;
5433         }
5434
5435         return ret;
5436 }
5437
5438 ssize_t read(int s, void *buf, size_t len)
5439 {
5440         return swrap_read(s, buf, len);
5441 }
5442
5443 /****************************************************************************
5444  *   WRITE
5445  ***************************************************************************/
5446
5447 static ssize_t swrap_write(int s, const void *buf, size_t len)
5448 {
5449         struct msghdr msg;
5450         struct iovec tmp;
5451         struct sockaddr_un un_addr;
5452         ssize_t ret;
5453         int rc;
5454         struct socket_info *si;
5455
5456         si = find_socket_info(s);
5457         if (si == NULL) {
5458                 return libc_write(s, buf, len);
5459         }
5460
5461         tmp.iov_base = discard_const_p(char, buf);
5462         tmp.iov_len = len;
5463
5464         ZERO_STRUCT(msg);
5465         msg.msg_name = NULL;           /* optional address */
5466         msg.msg_namelen = 0;           /* size of address */
5467         msg.msg_iov = &tmp;            /* scatter/gather array */
5468         msg.msg_iovlen = 1;            /* # elements in msg_iov */
5469 #if HAVE_STRUCT_MSGHDR_MSG_CONTROL
5470         msg.msg_control = NULL;        /* ancillary data, see below */
5471         msg.msg_controllen = 0;        /* ancillary data buffer len */
5472         msg.msg_flags = 0;             /* flags on received message */
5473 #endif
5474
5475         rc = swrap_sendmsg_before(s, si, &msg, &tmp, &un_addr, NULL, NULL, NULL);
5476         if (rc < 0) {
5477                 return -1;
5478         }
5479
5480         buf = msg.msg_iov[0].iov_base;
5481         len = msg.msg_iov[0].iov_len;
5482
5483         ret = libc_write(s, buf, len);
5484
5485         swrap_sendmsg_after(s, si, &msg, NULL, ret);
5486
5487         return ret;
5488 }
5489
5490 ssize_t write(int s, const void *buf, size_t len)
5491 {
5492         return swrap_write(s, buf, len);
5493 }
5494
5495 /****************************************************************************
5496  *   SEND
5497  ***************************************************************************/
5498
5499 static ssize_t swrap_send(int s, const void *buf, size_t len, int flags)
5500 {
5501         struct msghdr msg;
5502         struct iovec tmp;
5503         struct sockaddr_un un_addr;
5504         ssize_t ret;
5505         int rc;
5506         struct socket_info *si = find_socket_info(s);
5507
5508         if (!si) {
5509                 return libc_send(s, buf, len, flags);
5510         }
5511
5512         tmp.iov_base = discard_const_p(char, buf);
5513         tmp.iov_len = len;
5514
5515         ZERO_STRUCT(msg);
5516         msg.msg_name = NULL;           /* optional address */
5517         msg.msg_namelen = 0;           /* size of address */
5518         msg.msg_iov = &tmp;            /* scatter/gather array */
5519         msg.msg_iovlen = 1;            /* # elements in msg_iov */
5520 #if HAVE_STRUCT_MSGHDR_MSG_CONTROL
5521         msg.msg_control = NULL;        /* ancillary data, see below */
5522         msg.msg_controllen = 0;        /* ancillary data buffer len */
5523         msg.msg_flags = 0;             /* flags on received message */
5524 #endif
5525
5526         rc = swrap_sendmsg_before(s, si, &msg, &tmp, &un_addr, NULL, NULL, NULL);
5527         if (rc < 0) {
5528                 return -1;
5529         }
5530
5531         buf = msg.msg_iov[0].iov_base;
5532         len = msg.msg_iov[0].iov_len;
5533
5534         ret = libc_send(s, buf, len, flags);
5535
5536         swrap_sendmsg_after(s, si, &msg, NULL, ret);
5537
5538         return ret;
5539 }
5540
5541 ssize_t send(int s, const void *buf, size_t len, int flags)
5542 {
5543         return swrap_send(s, buf, len, flags);
5544 }
5545
5546 /****************************************************************************
5547  *   RECVMSG
5548  ***************************************************************************/
5549
5550 static ssize_t swrap_recvmsg(int s, struct msghdr *omsg, int flags)
5551 {
5552         struct swrap_address from_addr = {
5553                 .sa_socklen = sizeof(struct sockaddr_un),
5554         };
5555         struct swrap_address convert_addr = {
5556                 .sa_socklen = sizeof(struct sockaddr_storage),
5557         };
5558         struct socket_info *si;
5559         struct msghdr msg;
5560         struct iovec tmp;
5561 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5562         size_t msg_ctrllen_filled;
5563         size_t msg_ctrllen_left;
5564 #endif
5565
5566         ssize_t ret;
5567         int rc;
5568
5569         si = find_socket_info(s);
5570         if (si == NULL) {
5571                 return libc_recvmsg(s, omsg, flags);
5572         }
5573
5574         tmp.iov_base = NULL;
5575         tmp.iov_len = 0;
5576
5577         ZERO_STRUCT(msg);
5578         msg.msg_name = &from_addr.sa;              /* optional address */
5579         msg.msg_namelen = from_addr.sa_socklen;    /* size of address */
5580         msg.msg_iov = omsg->msg_iov;               /* scatter/gather array */
5581         msg.msg_iovlen = omsg->msg_iovlen;         /* # elements in msg_iov */
5582 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5583         msg_ctrllen_filled = 0;
5584         msg_ctrllen_left = omsg->msg_controllen;
5585
5586         msg.msg_control = omsg->msg_control;       /* ancillary data, see below */
5587         msg.msg_controllen = omsg->msg_controllen; /* ancillary data buffer len */
5588         msg.msg_flags = omsg->msg_flags;           /* flags on received message */
5589 #endif
5590
5591         rc = swrap_recvmsg_before(s, si, &msg, &tmp);
5592         if (rc < 0) {
5593                 return -1;
5594         }
5595
5596         ret = libc_recvmsg(s, &msg, flags);
5597
5598 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5599         msg_ctrllen_filled += msg.msg_controllen;
5600         msg_ctrllen_left -= msg.msg_controllen;
5601
5602         if (omsg->msg_control != NULL) {
5603                 uint8_t *p;
5604
5605                 p = omsg->msg_control;
5606                 p += msg_ctrllen_filled;
5607
5608                 msg.msg_control = p;
5609                 msg.msg_controllen = msg_ctrllen_left;
5610         } else {
5611                 msg.msg_control = NULL;
5612                 msg.msg_controllen = 0;
5613         }
5614 #endif
5615
5616         /*
5617          * We convert the unix address to a IP address so we need a buffer
5618          * which can store the address in case of SOCK_DGRAM, see below.
5619          */
5620         msg.msg_name = &convert_addr.sa;
5621         msg.msg_namelen = convert_addr.sa_socklen;
5622
5623         rc = swrap_recvmsg_after(s,
5624                                  si,
5625                                  &msg,
5626                                  &from_addr.sa.un,
5627                                  from_addr.sa_socklen,
5628                                  ret);
5629         if (rc != 0) {
5630                 return rc;
5631         }
5632
5633 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5634         if (omsg->msg_control != NULL) {
5635                 /* msg.msg_controllen = space left */
5636                 msg_ctrllen_left = msg.msg_controllen;
5637                 msg_ctrllen_filled = omsg->msg_controllen - msg_ctrllen_left;
5638         }
5639
5640         /* Update the original message length */
5641         omsg->msg_controllen = msg_ctrllen_filled;
5642         omsg->msg_flags = msg.msg_flags;
5643 #endif
5644         omsg->msg_iovlen = msg.msg_iovlen;
5645
5646         SWRAP_LOCK_SI(si);
5647
5648         /*
5649          * From the manpage:
5650          *
5651          * The  msg_name  field  points  to a caller-allocated buffer that is
5652          * used to return the source address if the socket is unconnected.  The
5653          * caller should set msg_namelen to the size of this buffer before this
5654          * call; upon return from a successful call, msg_name will contain the
5655          * length of the returned address.  If the application  does  not  need
5656          * to know the source address, msg_name can be specified as NULL.
5657          */
5658         if (si->type == SOCK_STREAM) {
5659                 omsg->msg_namelen = 0;
5660         } else if (omsg->msg_name != NULL &&
5661                    omsg->msg_namelen != 0 &&
5662                    omsg->msg_namelen >= msg.msg_namelen) {
5663                 memcpy(omsg->msg_name, msg.msg_name, msg.msg_namelen);
5664                 omsg->msg_namelen = msg.msg_namelen;
5665         }
5666
5667         SWRAP_UNLOCK_SI(si);
5668
5669         return ret;
5670 }
5671
5672 ssize_t recvmsg(int sockfd, struct msghdr *msg, int flags)
5673 {
5674         return swrap_recvmsg(sockfd, msg, flags);
5675 }
5676
5677 /****************************************************************************
5678  *   SENDMSG
5679  ***************************************************************************/
5680
5681 static ssize_t swrap_sendmsg(int s, const struct msghdr *omsg, int flags)
5682 {
5683         struct msghdr msg;
5684         struct iovec tmp;
5685         struct sockaddr_un un_addr;
5686         const struct sockaddr_un *to_un = NULL;
5687         const struct sockaddr *to = NULL;
5688         ssize_t ret;
5689         int rc;
5690         struct socket_info *si = find_socket_info(s);
5691         int bcast = 0;
5692
5693         if (!si) {
5694                 return libc_sendmsg(s, omsg, flags);
5695         }
5696
5697         ZERO_STRUCT(un_addr);
5698
5699         tmp.iov_base = NULL;
5700         tmp.iov_len = 0;
5701
5702         ZERO_STRUCT(msg);
5703
5704         SWRAP_LOCK_SI(si);
5705
5706         if (si->connected == 0) {
5707                 msg.msg_name = omsg->msg_name;             /* optional address */
5708                 msg.msg_namelen = omsg->msg_namelen;       /* size of address */
5709         }
5710         msg.msg_iov = omsg->msg_iov;               /* scatter/gather array */
5711         msg.msg_iovlen = omsg->msg_iovlen;         /* # elements in msg_iov */
5712
5713         SWRAP_UNLOCK_SI(si);
5714
5715 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5716         if (msg.msg_controllen > 0 && msg.msg_control != NULL) {
5717                 /* omsg is a const so use a local buffer for modifications */
5718                 uint8_t cmbuf[omsg->msg_controllen];
5719
5720                 memcpy(cmbuf, omsg->msg_control, omsg->msg_controllen);
5721
5722                 msg.msg_control = cmbuf;       /* ancillary data, see below */
5723                 msg.msg_controllen = omsg->msg_controllen; /* ancillary data buffer len */
5724         }
5725         msg.msg_flags = omsg->msg_flags;           /* flags on received message */
5726 #endif
5727
5728         rc = swrap_sendmsg_before(s, si, &msg, &tmp, &un_addr, &to_un, &to, &bcast);
5729         if (rc < 0) {
5730                 return -1;
5731         }
5732
5733         if (bcast) {
5734                 struct stat st;
5735                 unsigned int iface;
5736                 unsigned int prt = ntohs(((const struct sockaddr_in *)(const void *)to)->sin_port);
5737                 char type;
5738                 size_t i, len = 0;
5739                 uint8_t *buf;
5740                 off_t ofs = 0;
5741                 size_t avail = 0;
5742                 size_t remain;
5743
5744                 for (i = 0; i < (size_t)msg.msg_iovlen; i++) {
5745                         avail += msg.msg_iov[i].iov_len;
5746                 }
5747
5748                 len = avail;
5749                 remain = avail;
5750
5751                 /* we capture it as one single packet */
5752                 buf = (uint8_t *)malloc(remain);
5753                 if (!buf) {
5754                         return -1;
5755                 }
5756
5757                 for (i = 0; i < (size_t)msg.msg_iovlen; i++) {
5758                         size_t this_time = MIN(remain, (size_t)msg.msg_iov[i].iov_len);
5759                         memcpy(buf + ofs,
5760                                msg.msg_iov[i].iov_base,
5761                                this_time);
5762                         ofs += this_time;
5763                         remain -= this_time;
5764                 }
5765
5766                 type = SOCKET_TYPE_CHAR_UDP;
5767
5768                 for(iface=0; iface <= MAX_WRAPPED_INTERFACES; iface++) {
5769                         snprintf(un_addr.sun_path, sizeof(un_addr.sun_path), "%s/"SOCKET_FORMAT,
5770                                  socket_wrapper_dir(), type, iface, prt);
5771                         if (stat(un_addr.sun_path, &st) != 0) continue;
5772
5773                         msg.msg_name = &un_addr;           /* optional address */
5774                         msg.msg_namelen = sizeof(un_addr); /* size of address */
5775
5776                         /* ignore the any errors in broadcast sends */
5777                         libc_sendmsg(s, &msg, flags);
5778                 }
5779
5780                 SWRAP_LOCK_SI(si);
5781
5782                 swrap_pcap_dump_packet(si, to, SWRAP_SENDTO, buf, len);
5783                 free(buf);
5784
5785                 SWRAP_UNLOCK_SI(si);
5786
5787                 return len;
5788         }
5789
5790         ret = libc_sendmsg(s, &msg, flags);
5791
5792         swrap_sendmsg_after(s, si, &msg, to, ret);
5793
5794         return ret;
5795 }
5796
5797 ssize_t sendmsg(int s, const struct msghdr *omsg, int flags)
5798 {
5799         return swrap_sendmsg(s, omsg, flags);
5800 }
5801
5802 /****************************************************************************
5803  *   READV
5804  ***************************************************************************/
5805
5806 static ssize_t swrap_readv(int s, const struct iovec *vector, int count)
5807 {
5808         struct socket_info *si;
5809         struct msghdr msg;
5810         struct iovec tmp;
5811         struct swrap_address saddr = {
5812                 .sa_socklen = sizeof(struct sockaddr_storage)
5813         };
5814         ssize_t ret;
5815         int rc;
5816
5817         si = find_socket_info(s);
5818         if (si == NULL) {
5819                 return libc_readv(s, vector, count);
5820         }
5821
5822         tmp.iov_base = NULL;
5823         tmp.iov_len = 0;
5824
5825         ZERO_STRUCT(msg);
5826         msg.msg_name = &saddr.sa.s; /* optional address */
5827         msg.msg_namelen = saddr.sa_socklen;      /* size of address */
5828         msg.msg_iov = discard_const_p(struct iovec, vector); /* scatter/gather array */
5829         msg.msg_iovlen = count;        /* # elements in msg_iov */
5830 #ifdef HAVE_STRUCT_MSGHDR_MSG_CONTROL
5831         msg.msg_control = NULL;        /* ancillary data, see below */
5832         msg.msg_controllen = 0;        /* ancillary data buffer len */
5833         msg.msg_flags = 0;             /* flags on received message */
5834 #endif
5835
5836         rc = swrap_recvmsg_before(s, si, &msg, &tmp);
5837         if (rc < 0) {
5838                 if (rc == -ENOTSOCK) {
5839                         return libc_readv(s, vector, count);
5840                 }
5841                 return -1;
5842         }
5843
5844         ret = libc_readv(s, msg.msg_iov, msg.msg_iovlen);
5845
5846         rc = swrap_recvmsg_after(s, si, &msg, NULL, 0, ret);
5847         if (rc != 0) {
5848                 return rc;
5849         }
5850
5851         return ret;
5852 }
5853
5854 ssize_t readv(int s, const struct iovec *vector, int count)
5855 {
5856         return swrap_readv(s, vector, count);
5857 }
5858
5859 /****************************************************************************
5860  *   WRITEV
5861  ***************************************************************************/
5862
5863 static ssize_t swrap_writev(int s, const struct iovec *vector, int count)
5864 {
5865         struct msghdr msg;
5866         struct iovec tmp;
5867         struct sockaddr_un un_addr;
5868         ssize_t ret;
5869         int rc;
5870         struct socket_info *si = find_socket_info(s);
5871
5872         if (!si) {
5873                 return libc_writev(s, vector, count);
5874         }
5875
5876         tmp.iov_base = NULL;
5877         tmp.iov_len = 0;
5878
5879         ZERO_STRUCT(msg);
5880         msg.msg_name = NULL;           /* optional address */
5881         msg.msg_namelen = 0;           /* size of address */
5882         msg.msg_iov = discard_const_p(struct iovec, vector); /* scatter/gather array */
5883         msg.msg_iovlen = count;        /* # elements in msg_iov */
5884 #if HAVE_STRUCT_MSGHDR_MSG_CONTROL
5885         msg.msg_control = NULL;        /* ancillary data, see below */
5886         msg.msg_controllen = 0;        /* ancillary data buffer len */
5887         msg.msg_flags = 0;             /* flags on received message */
5888 #endif
5889
5890         rc = swrap_sendmsg_before(s, si, &msg, &tmp, &un_addr, NULL, NULL, NULL);
5891         if (rc < 0) {
5892                 if (rc == -ENOTSOCK) {
5893                         return libc_readv(s, vector, count);
5894                 }
5895                 return -1;
5896         }
5897
5898         ret = libc_writev(s, msg.msg_iov, msg.msg_iovlen);
5899
5900         swrap_sendmsg_after(s, si, &msg, NULL, ret);
5901
5902         return ret;
5903 }
5904
5905 ssize_t writev(int s, const struct iovec *vector, int count)
5906 {
5907         return swrap_writev(s, vector, count);
5908 }
5909
5910 /****************************
5911  * CLOSE
5912  ***************************/
5913
5914 static int swrap_close(int fd)
5915 {
5916         struct socket_info *si = NULL;
5917         int si_index;
5918         int ret;
5919
5920         swrap_mutex_lock(&socket_reset_mutex);
5921
5922         si_index = find_socket_info_index(fd);
5923         if (si_index == -1) {
5924                 swrap_mutex_unlock(&socket_reset_mutex);
5925                 return libc_close(fd);
5926         }
5927
5928         reset_socket_info_index(fd);
5929
5930         swrap_mutex_unlock(&socket_reset_mutex);
5931
5932         si = swrap_get_socket_info(si_index);
5933
5934         swrap_mutex_lock(&first_free_mutex);
5935         SWRAP_LOCK_SI(si);
5936
5937         ret = libc_close(fd);
5938
5939         swrap_dec_refcount(si);
5940
5941         if (swrap_get_refcount(si) > 0) {
5942                 /* there are still references left */
5943                 goto out;
5944         }
5945
5946         if (si->myname.sa_socklen > 0 && si->peername.sa_socklen > 0) {
5947                 swrap_pcap_dump_packet(si, NULL, SWRAP_CLOSE_SEND, NULL, 0);
5948         }
5949
5950         if (si->myname.sa_socklen > 0 && si->peername.sa_socklen > 0) {
5951                 swrap_pcap_dump_packet(si, NULL, SWRAP_CLOSE_RECV, NULL, 0);
5952                 swrap_pcap_dump_packet(si, NULL, SWRAP_CLOSE_ACK, NULL, 0);
5953         }
5954
5955         if (si->un_addr.sun_path[0] != '\0') {
5956                 unlink(si->un_addr.sun_path);
5957         }
5958
5959         swrap_set_next_free(si, first_free);
5960         first_free = si_index;
5961
5962 out:
5963         SWRAP_UNLOCK_SI(si);
5964         swrap_mutex_unlock(&first_free_mutex);
5965
5966         return ret;
5967 }
5968
5969 int close(int fd)
5970 {
5971         return swrap_close(fd);
5972 }
5973
5974 /****************************
5975  * DUP
5976  ***************************/
5977
5978 static int swrap_dup(int fd)
5979 {
5980         struct socket_info *si;
5981         int dup_fd, idx;
5982
5983         idx = find_socket_info_index(fd);
5984         if (idx == -1) {
5985                 return libc_dup(fd);
5986         }
5987
5988         si = swrap_get_socket_info(idx);
5989
5990         dup_fd = libc_dup(fd);
5991         if (dup_fd == -1) {
5992                 int saved_errno = errno;
5993                 errno = saved_errno;
5994                 return -1;
5995         }
5996
5997         SWRAP_LOCK_SI(si);
5998
5999         swrap_inc_refcount(si);
6000
6001         SWRAP_UNLOCK_SI(si);
6002
6003         /* Make sure we don't have an entry for the fd */
6004         swrap_remove_stale(dup_fd);
6005
6006         set_socket_info_index(dup_fd, idx);
6007
6008         return dup_fd;
6009 }
6010
6011 int dup(int fd)
6012 {
6013         return swrap_dup(fd);
6014 }
6015
6016 /****************************
6017  * DUP2
6018  ***************************/
6019
6020 static int swrap_dup2(int fd, int newfd)
6021 {
6022         struct socket_info *si;
6023         int dup_fd, idx;
6024
6025         idx = find_socket_info_index(fd);
6026         if (idx == -1) {
6027                 return libc_dup2(fd, newfd);
6028         }
6029
6030         si = swrap_get_socket_info(idx);
6031
6032         if (fd == newfd) {
6033                 /*
6034                  * According to the manpage:
6035                  *
6036                  * "If oldfd is a valid file descriptor, and newfd has the same
6037                  * value as oldfd, then dup2() does nothing, and returns newfd."
6038                  */
6039                 return newfd;
6040         }
6041
6042         if (find_socket_info(newfd)) {
6043                 /* dup2() does an implicit close of newfd, which we
6044                  * need to emulate */
6045                 swrap_close(newfd);
6046         }
6047
6048         dup_fd = libc_dup2(fd, newfd);
6049         if (dup_fd == -1) {
6050                 int saved_errno = errno;
6051                 errno = saved_errno;
6052                 return -1;
6053         }
6054
6055         SWRAP_LOCK_SI(si);
6056
6057         swrap_inc_refcount(si);
6058
6059         SWRAP_UNLOCK_SI(si);
6060
6061         /* Make sure we don't have an entry for the fd */
6062         swrap_remove_stale(dup_fd);
6063
6064         set_socket_info_index(dup_fd, idx);
6065
6066         return dup_fd;
6067 }
6068
6069 int dup2(int fd, int newfd)
6070 {
6071         return swrap_dup2(fd, newfd);
6072 }
6073
6074 /****************************
6075  * FCNTL
6076  ***************************/
6077
6078 static int swrap_vfcntl(int fd, int cmd, va_list va)
6079 {
6080         struct socket_info *si;
6081         int rc, dup_fd, idx;
6082
6083         idx = find_socket_info_index(fd);
6084         if (idx == -1) {
6085                 return libc_vfcntl(fd, cmd, va);
6086         }
6087
6088         si = swrap_get_socket_info(idx);
6089
6090         switch (cmd) {
6091         case F_DUPFD:
6092                 dup_fd = libc_vfcntl(fd, cmd, va);
6093                 if (dup_fd == -1) {
6094                         int saved_errno = errno;
6095                         errno = saved_errno;
6096                         return -1;
6097                 }
6098
6099                 SWRAP_LOCK_SI(si);
6100
6101                 swrap_inc_refcount(si);
6102
6103                 SWRAP_UNLOCK_SI(si);
6104
6105                 /* Make sure we don't have an entry for the fd */
6106                 swrap_remove_stale(dup_fd);
6107
6108                 set_socket_info_index(dup_fd, idx);
6109
6110                 rc = dup_fd;
6111                 break;
6112         default:
6113                 rc = libc_vfcntl(fd, cmd, va);
6114                 break;
6115         }
6116
6117         return rc;
6118 }
6119
6120 int fcntl(int fd, int cmd, ...)
6121 {
6122         va_list va;
6123         int rc;
6124
6125         va_start(va, cmd);
6126
6127         rc = swrap_vfcntl(fd, cmd, va);
6128
6129         va_end(va);
6130
6131         return rc;
6132 }
6133
6134 /****************************
6135  * EVENTFD
6136  ***************************/
6137
6138 #ifdef HAVE_EVENTFD
6139 static int swrap_eventfd(int count, int flags)
6140 {
6141         int fd;
6142
6143         fd = libc_eventfd(count, flags);
6144         if (fd != -1) {
6145                 swrap_remove_stale(fd);
6146         }
6147
6148         return fd;
6149 }
6150
6151 #ifdef HAVE_EVENTFD_UNSIGNED_INT
6152 int eventfd(unsigned int count, int flags)
6153 #else
6154 int eventfd(int count, int flags)
6155 #endif
6156 {
6157         return swrap_eventfd(count, flags);
6158 }
6159 #endif
6160
6161 #ifdef HAVE_PLEDGE
6162 int pledge(const char *promises, const char *paths[])
6163 {
6164         (void)promises; /* unused */
6165         (void)paths; /* unused */
6166
6167         return 0;
6168 }
6169 #endif /* HAVE_PLEDGE */
6170
6171 static void swrap_thread_prepare(void)
6172 {
6173         /*
6174          * This function should only be called here!!
6175          *
6176          * We bind all symobls to avoid deadlocks of the fork is
6177          * interrupted by a signal handler using a symbol of this
6178          * library.
6179          */
6180         swrap_bind_symbol_all();
6181
6182         SWRAP_LOCK_ALL;
6183 }
6184
6185 static void swrap_thread_parent(void)
6186 {
6187         SWRAP_UNLOCK_ALL;
6188 }
6189
6190 static void swrap_thread_child(void)
6191 {
6192         SWRAP_UNLOCK_ALL;
6193 }
6194
6195 /****************************
6196  * CONSTRUCTOR
6197  ***************************/
6198 void swrap_constructor(void)
6199 {
6200         int ret;
6201
6202         /*
6203         * If we hold a lock and the application forks, then the child
6204         * is not able to unlock the mutex and we are in a deadlock.
6205         * This should prevent such deadlocks.
6206         */
6207         pthread_atfork(&swrap_thread_prepare,
6208                        &swrap_thread_parent,
6209                        &swrap_thread_child);
6210
6211         ret = socket_wrapper_init_mutex(&sockets_mutex);
6212         if (ret != 0) {
6213                 SWRAP_LOG(SWRAP_LOG_ERROR,
6214                           "Failed to initialize pthread mutex");
6215                 exit(-1);
6216         }
6217
6218         ret = socket_wrapper_init_mutex(&socket_reset_mutex);
6219         if (ret != 0) {
6220                 SWRAP_LOG(SWRAP_LOG_ERROR,
6221                           "Failed to initialize pthread mutex");
6222                 exit(-1);
6223         }
6224
6225         ret = socket_wrapper_init_mutex(&first_free_mutex);
6226         if (ret != 0) {
6227                 SWRAP_LOG(SWRAP_LOG_ERROR,
6228                           "Failed to initialize pthread mutex");
6229                 exit(-1);
6230         }
6231 }
6232
6233 /****************************
6234  * DESTRUCTOR
6235  ***************************/
6236
6237 /*
6238  * This function is called when the library is unloaded and makes sure that
6239  * sockets get closed and the unix file for the socket are unlinked.
6240  */
6241 void swrap_destructor(void)
6242 {
6243         size_t i;
6244
6245         if (socket_fds_idx != NULL) {
6246                 for (i = 0; i < SOCKET_WRAPPER_MAX_SOCKETS_DEFAULT; ++i) {
6247                         if (socket_fds_idx[i] != -1) {
6248                                 swrap_close(i);
6249                         }
6250                 }
6251                 SAFE_FREE(socket_fds_idx);
6252         }
6253
6254         SAFE_FREE(sockets);
6255
6256         if (swrap.libc.handle != NULL) {
6257                 dlclose(swrap.libc.handle);
6258         }
6259         if (swrap.libc.socket_handle) {
6260                 dlclose(swrap.libc.socket_handle);
6261         }
6262 }