1 /* 2 * Copyright (C) Jelmer Vernooij 2005 <jelmer@samba.org> 3 * Copyright (C) Stefan Metzmacher 2006 <metze@samba.org> 4 * 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 14 * 2. Redistributions in binary form must reproduce the above copyright 15 * notice, this list of conditions and the following disclaimer in the 16 * documentation and/or other materials provided with the distribution. 17 * 18 * 3. Neither the name of the author nor the names of its contributors 19 * may be used to endorse or promote products derived from this software 20 * without specific prior written permission. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 25 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 26 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 27 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 28 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 29 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 31 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 32 * SUCH DAMAGE. 33 * 34 */ 35 36 /* 37 Socket wrapper library. Passes all socket communication over 38 unix domain sockets if the environment variable SOCKET_WRAPPER_DIR 39 is set. 40 */ 41 42 #define SOCKET_WRAPPER_NOT_REPLACE 43 44 #ifdef _SAMBA_BUILD_ 45 46 #include "includes.h" 47 #include "system/network.h" 48 #include "system/filesys.h" 49 50 #ifdef malloc 51 #undef malloc 52 #endif 53 #ifdef calloc 54 #undef calloc 55 #endif 56 #ifdef strdup 57 #undef strdup 58 #endif 59 60 #else /* _SAMBA_BUILD_ */ 61 62 #include <config.h> 63 #undef SOCKET_WRAPPER_REPLACE 64 65 #include <sys/types.h> 66 #ifdef TIME_WITH_SYS_TIME 67 #include <sys/time.h> 68 #include <time.h> 69 #elif defined(HAVE_SYS_TIME_H) 70 #include <sys/time.h> 71 #else 72 #include <time.h> 73 #endif 74 #include <sys/stat.h> 75 #include <sys/socket.h> 76 #include <sys/ioctl.h> 77 #ifdef HAVE_SYS_FILIO_H 78 #include <sys/filio.h> 79 #endif 80 #include <errno.h> 81 #include <sys/un.h> 82 #include <netinet/in.h> 83 #include <netinet/tcp.h> 84 #include <fcntl.h> 85 #include <stdlib.h> 86 #include <unistd.h> 87 #include <string.h> 88 #include <stdio.h> 89 #include "roken.h" 90 91 #include "socket_wrapper.h" 92 93 #define HAVE_GETTIMEOFDAY_TZ 1 94 95 #define _PUBLIC_ 96 97 #endif 98 99 #define SWRAP_DLIST_ADD(list,item) do { \ 100 if (!(list)) { \ 101 (item)->prev = NULL; \ 102 (item)->next = NULL; \ 103 (list) = (item); \ 104 } else { \ 105 (item)->prev = NULL; \ 106 (item)->next = (list); \ 107 (list)->prev = (item); \ 108 (list) = (item); \ 109 } \ 110 } while (0) 111 112 #define SWRAP_DLIST_REMOVE(list,item) do { \ 113 if ((list) == (item)) { \ 114 (list) = (item)->next; \ 115 if (list) { \ 116 (list)->prev = NULL; \ 117 } \ 118 } else { \ 119 if ((item)->prev) { \ 120 (item)->prev->next = (item)->next; \ 121 } \ 122 if ((item)->next) { \ 123 (item)->next->prev = (item)->prev; \ 124 } \ 125 } \ 126 (item)->prev = NULL; \ 127 (item)->next = NULL; \ 128 } while (0) 129 130 /* LD_PRELOAD doesn't work yet, so REWRITE_CALLS is all we support 131 * for now */ 132 #define REWRITE_CALLS 133 134 #ifdef REWRITE_CALLS 135 #define real_accept accept 136 #define real_connect connect 137 #define real_bind bind 138 #define real_listen listen 139 #define real_getpeername getpeername 140 #define real_getsockname getsockname 141 #define real_getsockopt getsockopt 142 #define real_setsockopt setsockopt 143 #define real_recvfrom recvfrom 144 #define real_sendto sendto 145 #define real_ioctl ioctl 146 #define real_recv recv 147 #define real_send send 148 #define real_socket socket 149 #define real_close close 150 #define real_dup dup 151 #define real_dup2 dup2 152 #endif 153 154 #ifdef HAVE_GETTIMEOFDAY_TZ 155 #define swrapGetTimeOfDay(tval) gettimeofday(tval,NULL) 156 #else 157 #define swrapGetTimeOfDay(tval) gettimeofday(tval) 158 #endif 159 160 /* we need to use a very terse format here as IRIX 6.4 silently 161 truncates names to 16 chars, so if we use a longer name then we 162 can't tell which port a packet came from with recvfrom() 163 164 with this format we have 8 chars left for the directory name 165 */ 166 #define SOCKET_FORMAT "%c%02X%04X" 167 #define SOCKET_TYPE_CHAR_TCP 'T' 168 #define SOCKET_TYPE_CHAR_UDP 'U' 169 #define SOCKET_TYPE_CHAR_TCP_V6 'X' 170 #define SOCKET_TYPE_CHAR_UDP_V6 'Y' 171 172 #define MAX_WRAPPED_INTERFACES 16 173 174 #define SW_IPV6_ADDRESS 1 175 176 static struct sockaddr *sockaddr_dup(const void *data, socklen_t len) 177 { 178 struct sockaddr *ret = (struct sockaddr *)malloc(len); 179 memcpy(ret, data, len); 180 return ret; 181 } 182 183 static void set_port(int family, int prt, struct sockaddr *addr) 184 { 185 switch (family) { 186 case AF_INET: 187 ((struct sockaddr_in *)addr)->sin_port = htons(prt); 188 break; 189 #ifdef HAVE_IPV6 190 case AF_INET6: 191 ((struct sockaddr_in6 *)addr)->sin6_port = htons(prt); 192 break; 193 #endif 194 } 195 } 196 197 static int socket_length(int family) 198 { 199 switch (family) { 200 case AF_INET: 201 return sizeof(struct sockaddr_in); 202 #ifdef HAVE_IPV6 203 case AF_INET6: 204 return sizeof(struct sockaddr_in6); 205 #endif 206 } 207 return -1; 208 } 209 210 211 212 struct socket_info 213 { 214 int fd; 215 216 int family; 217 int type; 218 int protocol; 219 int bound; 220 int bcast; 221 int is_server; 222 223 char *path; 224 char *tmp_path; 225 226 struct sockaddr *myname; 227 socklen_t myname_len; 228 229 struct sockaddr *peername; 230 socklen_t peername_len; 231 232 struct { 233 unsigned long pck_snd; 234 unsigned long pck_rcv; 235 } io; 236 237 struct socket_info *prev, *next; 238 }; 239 240 static struct socket_info *sockets; 241 242 243 static const char *socket_wrapper_dir(void) 244 { 245 const char *s = getenv("SOCKET_WRAPPER_DIR"); 246 if (s == NULL) { 247 return NULL; 248 } 249 if (strncmp(s, "./", 2) == 0) { 250 s += 2; 251 } 252 return s; 253 } 254 255 static unsigned int socket_wrapper_default_iface(void) 256 { 257 const char *s = getenv("SOCKET_WRAPPER_DEFAULT_IFACE"); 258 if (s) { 259 unsigned int iface; 260 if (sscanf(s, "%u", &iface) == 1) { 261 if (iface >= 1 && iface <= MAX_WRAPPED_INTERFACES) { 262 return iface; 263 } 264 } 265 } 266 267 return 1;/* 127.0.0.1 */ 268 } 269 270 static int convert_un_in(const struct sockaddr_un *un, struct sockaddr *in, socklen_t *len) 271 { 272 unsigned int iface; 273 unsigned int prt; 274 const char *p; 275 char type; 276 277 p = strrchr(un->sun_path, '/'); 278 if (p) p++; else p = un->sun_path; 279 280 if (sscanf(p, SOCKET_FORMAT, &type, &iface, &prt) != 3) { 281 errno = EINVAL; 282 return -1; 283 } 284 285 if (iface == 0 || iface > MAX_WRAPPED_INTERFACES) { 286 errno = EINVAL; 287 return -1; 288 } 289 290 if (prt > 0xFFFF) { 291 errno = EINVAL; 292 return -1; 293 } 294 295 switch(type) { 296 case SOCKET_TYPE_CHAR_TCP: 297 case SOCKET_TYPE_CHAR_UDP: { 298 struct sockaddr_in *in2 = (struct sockaddr_in *)in; 299 300 if ((*len) < sizeof(*in2)) { 301 errno = EINVAL; 302 return -1; 303 } 304 305 memset(in2, 0, sizeof(*in2)); 306 in2->sin_family = AF_INET; 307 in2->sin_addr.s_addr = htonl((127<<24) | iface); 308 in2->sin_port = htons(prt); 309 310 *len = sizeof(*in2); 311 break; 312 } 313 #ifdef HAVE_IPV6 314 case SOCKET_TYPE_CHAR_TCP_V6: 315 case SOCKET_TYPE_CHAR_UDP_V6: { 316 struct sockaddr_in6 *in2 = (struct sockaddr_in6 *)in; 317 318 if ((*len) < sizeof(*in2)) { 319 errno = EINVAL; 320 return -1; 321 } 322 323 memset(in2, 0, sizeof(*in2)); 324 in2->sin6_family = AF_INET6; 325 in2->sin6_addr.s6_addr[0] = SW_IPV6_ADDRESS; 326 in2->sin6_port = htons(prt); 327 328 *len = sizeof(*in2); 329 break; 330 } 331 #endif 332 default: 333 errno = EINVAL; 334 return -1; 335 } 336 337 return 0; 338 } 339 340 static int convert_in_un_remote(struct socket_info *si, const struct sockaddr *inaddr, struct sockaddr_un *un, 341 int *bcast) 342 { 343 char type = '\0'; 344 unsigned int prt; 345 unsigned int iface; 346 int is_bcast = 0; 347 348 if (bcast) *bcast = 0; 349 350 switch (si->family) { 351 case AF_INET: { 352 const struct sockaddr_in *in = 353 (const struct sockaddr_in *)inaddr; 354 unsigned int addr = ntohl(in->sin_addr.s_addr); 355 char u_type = '\0'; 356 char b_type = '\0'; 357 char a_type = '\0'; 358 359 switch (si->type) { 360 case SOCK_STREAM: 361 u_type = SOCKET_TYPE_CHAR_TCP; 362 break; 363 case SOCK_DGRAM: 364 u_type = SOCKET_TYPE_CHAR_UDP; 365 a_type = SOCKET_TYPE_CHAR_UDP; 366 b_type = SOCKET_TYPE_CHAR_UDP; 367 break; 368 } 369 370 prt = ntohs(in->sin_port); 371 if (a_type && addr == 0xFFFFFFFF) { 372 /* 255.255.255.255 only udp */ 373 is_bcast = 2; 374 type = a_type; 375 iface = socket_wrapper_default_iface(); 376 } else if (b_type && addr == 0x7FFFFFFF) { 377 /* 127.255.255.255 only udp */ 378 is_bcast = 1; 379 type = b_type; 380 iface = socket_wrapper_default_iface(); 381 } else if ((addr & 0xFFFFFF00) == 0x7F000000) { 382 /* 127.0.0.X */ 383 is_bcast = 0; 384 type = u_type; 385 iface = (addr & 0x000000FF); 386 } else { 387 errno = ENETUNREACH; 388 return -1; 389 } 390 if (bcast) *bcast = is_bcast; 391 break; 392 } 393 #ifdef HAVE_IPV6 394 case AF_INET6: { 395 const struct sockaddr_in6 *in = 396 (const struct sockaddr_in6 *)inaddr; 397 398 switch (si->type) { 399 case SOCK_STREAM: 400 type = SOCKET_TYPE_CHAR_TCP_V6; 401 break; 402 case SOCK_DGRAM: 403 type = SOCKET_TYPE_CHAR_UDP_V6; 404 break; 405 } 406 407 /* XXX no multicast/broadcast */ 408 409 prt = ntohs(in->sin6_port); 410 iface = SW_IPV6_ADDRESS; 411 412 break; 413 } 414 #endif 415 default: 416 errno = ENETUNREACH; 417 return -1; 418 } 419 420 if (prt == 0) { 421 errno = EINVAL; 422 return -1; 423 } 424 425 if (is_bcast) { 426 snprintf(un->sun_path, sizeof(un->sun_path), "%s/EINVAL", 427 socket_wrapper_dir()); 428 /* the caller need to do more processing */ 429 return 0; 430 } 431 432 snprintf(un->sun_path, sizeof(un->sun_path), "%s/"SOCKET_FORMAT, 433 socket_wrapper_dir(), type, iface, prt); 434 435 return 0; 436 } 437 438 static int convert_in_un_alloc(struct socket_info *si, const struct sockaddr *inaddr, struct sockaddr_un *un, 439 int *bcast) 440 { 441 char type = '\0'; 442 unsigned int prt; 443 unsigned int iface; 444 struct stat st; 445 int is_bcast = 0; 446 447 if (bcast) *bcast = 0; 448 449 switch (si->family) { 450 case AF_INET: { 451 const struct sockaddr_in *in = 452 (const struct sockaddr_in *)inaddr; 453 unsigned int addr = ntohl(in->sin_addr.s_addr); 454 char u_type = '\0'; 455 char d_type = '\0'; 456 char b_type = '\0'; 457 char a_type = '\0'; 458 459 prt = ntohs(in->sin_port); 460 461 switch (si->type) { 462 case SOCK_STREAM: 463 u_type = SOCKET_TYPE_CHAR_TCP; 464 d_type = SOCKET_TYPE_CHAR_TCP; 465 break; 466 case SOCK_DGRAM: 467 u_type = SOCKET_TYPE_CHAR_UDP; 468 d_type = SOCKET_TYPE_CHAR_UDP; 469 a_type = SOCKET_TYPE_CHAR_UDP; 470 b_type = SOCKET_TYPE_CHAR_UDP; 471 break; 472 } 473 474 if (addr == 0) { 475 /* 0.0.0.0 */ 476 is_bcast = 0; 477 type = d_type; 478 iface = socket_wrapper_default_iface(); 479 } else if (a_type && addr == 0xFFFFFFFF) { 480 /* 255.255.255.255 only udp */ 481 is_bcast = 2; 482 type = a_type; 483 iface = socket_wrapper_default_iface(); 484 } else if (b_type && addr == 0x7FFFFFFF) { 485 /* 127.255.255.255 only udp */ 486 is_bcast = 1; 487 type = b_type; 488 iface = socket_wrapper_default_iface(); 489 } else if ((addr & 0xFFFFFF00) == 0x7F000000) { 490 /* 127.0.0.X */ 491 is_bcast = 0; 492 type = u_type; 493 iface = (addr & 0x000000FF); 494 } else { 495 errno = EADDRNOTAVAIL; 496 return -1; 497 } 498 break; 499 } 500 #ifdef HAVE_IPV6 501 case AF_INET6: { 502 const struct sockaddr_in6 *in = 503 (const struct sockaddr_in6 *)inaddr; 504 505 switch (si->type) { 506 case SOCK_STREAM: 507 type = SOCKET_TYPE_CHAR_TCP_V6; 508 break; 509 case SOCK_DGRAM: 510 type = SOCKET_TYPE_CHAR_UDP_V6; 511 break; 512 } 513 514 /* XXX no multicast/broadcast */ 515 516 prt = ntohs(in->sin6_port); 517 iface = SW_IPV6_ADDRESS; 518 519 break; 520 } 521 #endif 522 default: 523 errno = ENETUNREACH; 524 return -1; 525 } 526 527 528 if (bcast) *bcast = is_bcast; 529 530 if (prt == 0) { 531 /* handle auto-allocation of ephemeral ports */ 532 for (prt = 5001; prt < 10000; prt++) { 533 snprintf(un->sun_path, sizeof(un->sun_path), "%s/"SOCKET_FORMAT, 534 socket_wrapper_dir(), type, iface, prt); 535 if (stat(un->sun_path, &st) == 0) continue; 536 537 set_port(si->family, prt, si->myname); 538 } 539 } 540 541 snprintf(un->sun_path, sizeof(un->sun_path), "%s/"SOCKET_FORMAT, 542 socket_wrapper_dir(), type, iface, prt); 543 return 0; 544 } 545 546 static struct socket_info *find_socket_info(int fd) 547 { 548 struct socket_info *i; 549 for (i = sockets; i; i = i->next) { 550 if (i->fd == fd) 551 return i; 552 } 553 554 return NULL; 555 } 556 557 static int sockaddr_convert_to_un(struct socket_info *si, const struct sockaddr *in_addr, socklen_t in_len, 558 struct sockaddr_un *out_addr, int alloc_sock, int *bcast) 559 { 560 if (!out_addr) 561 return 0; 562 563 out_addr->sun_family = AF_UNIX; 564 565 switch (in_addr->sa_family) { 566 case AF_INET: 567 #ifdef HAVE_IPV6 568 case AF_INET6: 569 #endif 570 switch (si->type) { 571 case SOCK_STREAM: 572 case SOCK_DGRAM: 573 break; 574 default: 575 errno = ESOCKTNOSUPPORT; 576 return -1; 577 } 578 if (alloc_sock) { 579 return convert_in_un_alloc(si, in_addr, out_addr, bcast); 580 } else { 581 return convert_in_un_remote(si, in_addr, out_addr, bcast); 582 } 583 default: 584 break; 585 } 586 587 errno = EAFNOSUPPORT; 588 return -1; 589 } 590 591 static int sockaddr_convert_from_un(const struct socket_info *si, 592 const struct sockaddr_un *in_addr, 593 socklen_t un_addrlen, 594 int family, 595 struct sockaddr *out_addr, 596 socklen_t *out_addrlen) 597 { 598 if (out_addr == NULL || out_addrlen == NULL) 599 return 0; 600 601 if (un_addrlen == 0) { 602 *out_addrlen = 0; 603 return 0; 604 } 605 606 switch (family) { 607 case AF_INET: 608 #ifdef HAVE_IPV6 609 case AF_INET6: 610 #endif 611 switch (si->type) { 612 case SOCK_STREAM: 613 case SOCK_DGRAM: 614 break; 615 default: 616 errno = ESOCKTNOSUPPORT; 617 return -1; 618 } 619 return convert_un_in(in_addr, out_addr, out_addrlen); 620 default: 621 break; 622 } 623 624 errno = EAFNOSUPPORT; 625 return -1; 626 } 627 628 enum swrap_packet_type { 629 SWRAP_CONNECT_SEND, 630 SWRAP_CONNECT_UNREACH, 631 SWRAP_CONNECT_RECV, 632 SWRAP_CONNECT_ACK, 633 SWRAP_ACCEPT_SEND, 634 SWRAP_ACCEPT_RECV, 635 SWRAP_ACCEPT_ACK, 636 SWRAP_RECVFROM, 637 SWRAP_SENDTO, 638 SWRAP_SENDTO_UNREACH, 639 SWRAP_PENDING_RST, 640 SWRAP_RECV, 641 SWRAP_RECV_RST, 642 SWRAP_SEND, 643 SWRAP_SEND_RST, 644 SWRAP_CLOSE_SEND, 645 SWRAP_CLOSE_RECV, 646 SWRAP_CLOSE_ACK 647 }; 648 649 struct swrap_file_hdr { 650 unsigned long magic; 651 unsigned short version_major; 652 unsigned short version_minor; 653 long timezone; 654 unsigned long sigfigs; 655 unsigned long frame_max_len; 656 #define SWRAP_FRAME_LENGTH_MAX 0xFFFF 657 unsigned long link_type; 658 }; 659 #define SWRAP_FILE_HDR_SIZE 24 660 661 struct swrap_packet { 662 struct { 663 unsigned long seconds; 664 unsigned long micro_seconds; 665 unsigned long recorded_length; 666 unsigned long full_length; 667 } frame; 668 #define SWRAP_PACKET__FRAME_SIZE 16 669 670 struct { 671 struct { 672 unsigned char ver_hdrlen; 673 unsigned char tos; 674 unsigned short packet_length; 675 unsigned short identification; 676 unsigned char flags; 677 unsigned char fragment; 678 unsigned char ttl; 679 unsigned char protocol; 680 unsigned short hdr_checksum; 681 unsigned long src_addr; 682 unsigned long dest_addr; 683 } hdr; 684 #define SWRAP_PACKET__IP_HDR_SIZE 20 685 686 union { 687 struct { 688 unsigned short source_port; 689 unsigned short dest_port; 690 unsigned long seq_num; 691 unsigned long ack_num; 692 unsigned char hdr_length; 693 unsigned char control; 694 unsigned short window; 695 unsigned short checksum; 696 unsigned short urg; 697 } tcp; 698 #define SWRAP_PACKET__IP_P_TCP_SIZE 20 699 struct { 700 unsigned short source_port; 701 unsigned short dest_port; 702 unsigned short length; 703 unsigned short checksum; 704 } udp; 705 #define SWRAP_PACKET__IP_P_UDP_SIZE 8 706 struct { 707 unsigned char type; 708 unsigned char code; 709 unsigned short checksum; 710 unsigned long unused; 711 } icmp; 712 #define SWRAP_PACKET__IP_P_ICMP_SIZE 8 713 } p; 714 } ip; 715 }; 716 #define SWRAP_PACKET_SIZE 56 717 718 static const char *socket_wrapper_pcap_file(void) 719 { 720 static int initialized = 0; 721 static const char *s = NULL; 722 static const struct swrap_file_hdr h; 723 static const struct swrap_packet p; 724 725 if (initialized == 1) { 726 return s; 727 } 728 initialized = 1; 729 730 /* 731 * TODO: don't use the structs use plain buffer offsets 732 * and PUSH_U8(), PUSH_U16() and PUSH_U32() 733 * 734 * for now make sure we disable PCAP support 735 * if the struct has alignment! 736 */ 737 if (sizeof(h) != SWRAP_FILE_HDR_SIZE) { 738 return NULL; 739 } 740 if (sizeof(p) != SWRAP_PACKET_SIZE) { 741 return NULL; 742 } 743 if (sizeof(p.frame) != SWRAP_PACKET__FRAME_SIZE) { 744 return NULL; 745 } 746 if (sizeof(p.ip.hdr) != SWRAP_PACKET__IP_HDR_SIZE) { 747 return NULL; 748 } 749 if (sizeof(p.ip.p.tcp) != SWRAP_PACKET__IP_P_TCP_SIZE) { 750 return NULL; 751 } 752 if (sizeof(p.ip.p.udp) != SWRAP_PACKET__IP_P_UDP_SIZE) { 753 return NULL; 754 } 755 if (sizeof(p.ip.p.icmp) != SWRAP_PACKET__IP_P_ICMP_SIZE) { 756 return NULL; 757 } 758 759 s = getenv("SOCKET_WRAPPER_PCAP_FILE"); 760 if (s == NULL) { 761 return NULL; 762 } 763 if (strncmp(s, "./", 2) == 0) { 764 s += 2; 765 } 766 return s; 767 } 768 769 static struct swrap_packet *swrap_packet_init(struct timeval *tval, 770 const struct sockaddr_in *src_addr, 771 const struct sockaddr_in *dest_addr, 772 int socket_type, 773 const unsigned char *payload, 774 size_t payload_len, 775 unsigned long tcp_seq, 776 unsigned long tcp_ack, 777 unsigned char tcp_ctl, 778 int unreachable, 779 size_t *_packet_len) 780 { 781 struct swrap_packet *ret; 782 struct swrap_packet *packet; 783 size_t packet_len; 784 size_t alloc_len; 785 size_t nonwire_len = sizeof(packet->frame); 786 size_t wire_hdr_len = 0; 787 size_t wire_len = 0; 788 size_t icmp_hdr_len = 0; 789 size_t icmp_truncate_len = 0; 790 unsigned char protocol = 0, icmp_protocol = 0; 791 unsigned short src_port = src_addr->sin_port; 792 unsigned short dest_port = dest_addr->sin_port; 793 794 switch (socket_type) { 795 case SOCK_STREAM: 796 protocol = 0x06; /* TCP */ 797 wire_hdr_len = sizeof(packet->ip.hdr) + sizeof(packet->ip.p.tcp); 798 wire_len = wire_hdr_len + payload_len; 799 break; 800 801 case SOCK_DGRAM: 802 protocol = 0x11; /* UDP */ 803 wire_hdr_len = sizeof(packet->ip.hdr) + sizeof(packet->ip.p.udp); 804 wire_len = wire_hdr_len + payload_len; 805 break; 806 } 807 808 if (unreachable) { 809 icmp_protocol = protocol; 810 protocol = 0x01; /* ICMP */ 811 if (wire_len > 64 ) { 812 icmp_truncate_len = wire_len - 64; 813 } 814 icmp_hdr_len = sizeof(packet->ip.hdr) + sizeof(packet->ip.p.icmp); 815 wire_hdr_len += icmp_hdr_len; 816 wire_len += icmp_hdr_len; 817 } 818 819 packet_len = nonwire_len + wire_len; 820 alloc_len = packet_len; 821 if (alloc_len < sizeof(struct swrap_packet)) { 822 alloc_len = sizeof(struct swrap_packet); 823 } 824 ret = (struct swrap_packet *)malloc(alloc_len); 825 if (!ret) return NULL; 826 827 packet = ret; 828 829 packet->frame.seconds = tval->tv_sec; 830 packet->frame.micro_seconds = tval->tv_usec; 831 packet->frame.recorded_length = wire_len - icmp_truncate_len; 832 packet->frame.full_length = wire_len - icmp_truncate_len; 833 834 packet->ip.hdr.ver_hdrlen = 0x45; /* version 4 and 5 * 32 bit words */ 835 packet->ip.hdr.tos = 0x00; 836 packet->ip.hdr.packet_length = htons(wire_len - icmp_truncate_len); 837 packet->ip.hdr.identification = htons(0xFFFF); 838 packet->ip.hdr.flags = 0x40; /* BIT 1 set - means don't fraqment */ 839 packet->ip.hdr.fragment = htons(0x0000); 840 packet->ip.hdr.ttl = 0xFF; 841 packet->ip.hdr.protocol = protocol; 842 packet->ip.hdr.hdr_checksum = htons(0x0000); 843 packet->ip.hdr.src_addr = src_addr->sin_addr.s_addr; 844 packet->ip.hdr.dest_addr = dest_addr->sin_addr.s_addr; 845 846 if (unreachable) { 847 packet->ip.p.icmp.type = 0x03; /* destination unreachable */ 848 packet->ip.p.icmp.code = 0x01; /* host unreachable */ 849 packet->ip.p.icmp.checksum = htons(0x0000); 850 packet->ip.p.icmp.unused = htonl(0x00000000); 851 852 /* set the ip header in the ICMP payload */ 853 packet = (struct swrap_packet *)(((unsigned char *)ret) + icmp_hdr_len); 854 packet->ip.hdr.ver_hdrlen = 0x45; /* version 4 and 5 * 32 bit words */ 855 packet->ip.hdr.tos = 0x00; 856 packet->ip.hdr.packet_length = htons(wire_len - icmp_hdr_len); 857 packet->ip.hdr.identification = htons(0xFFFF); 858 packet->ip.hdr.flags = 0x40; /* BIT 1 set - means don't fraqment */ 859 packet->ip.hdr.fragment = htons(0x0000); 860 packet->ip.hdr.ttl = 0xFF; 861 packet->ip.hdr.protocol = icmp_protocol; 862 packet->ip.hdr.hdr_checksum = htons(0x0000); 863 packet->ip.hdr.src_addr = dest_addr->sin_addr.s_addr; 864 packet->ip.hdr.dest_addr = src_addr->sin_addr.s_addr; 865 866 src_port = dest_addr->sin_port; 867 dest_port = src_addr->sin_port; 868 } 869 870 switch (socket_type) { 871 case SOCK_STREAM: 872 packet->ip.p.tcp.source_port = src_port; 873 packet->ip.p.tcp.dest_port = dest_port; 874 packet->ip.p.tcp.seq_num = htonl(tcp_seq); 875 packet->ip.p.tcp.ack_num = htonl(tcp_ack); 876 packet->ip.p.tcp.hdr_length = 0x50; /* 5 * 32 bit words */ 877 packet->ip.p.tcp.control = tcp_ctl; 878 packet->ip.p.tcp.window = htons(0x7FFF); 879 packet->ip.p.tcp.checksum = htons(0x0000); 880 packet->ip.p.tcp.urg = htons(0x0000); 881 882 break; 883 884 case SOCK_DGRAM: 885 packet->ip.p.udp.source_port = src_addr->sin_port; 886 packet->ip.p.udp.dest_port = dest_addr->sin_port; 887 packet->ip.p.udp.length = htons(8 + payload_len); 888 packet->ip.p.udp.checksum = htons(0x0000); 889 890 break; 891 } 892 893 if (payload && payload_len > 0) { 894 unsigned char *p = (unsigned char *)ret; 895 p += nonwire_len; 896 p += wire_hdr_len; 897 memcpy(p, payload, payload_len); 898 } 899 900 *_packet_len = packet_len - icmp_truncate_len; 901 return ret; 902 } 903 904 static int swrap_get_pcap_fd(const char *fname) 905 { 906 static int fd = -1; 907 908 if (fd != -1) return fd; 909 910 fd = open(fname, O_WRONLY|O_CREAT|O_EXCL|O_APPEND, 0644); 911 if (fd != -1) { 912 struct swrap_file_hdr file_hdr; 913 file_hdr.magic = 0xA1B2C3D4; 914 file_hdr.version_major = 0x0002; 915 file_hdr.version_minor = 0x0004; 916 file_hdr.timezone = 0x00000000; 917 file_hdr.sigfigs = 0x00000000; 918 file_hdr.frame_max_len = SWRAP_FRAME_LENGTH_MAX; 919 file_hdr.link_type = 0x0065; /* 101 RAW IP */ 920 921 write(fd, &file_hdr, sizeof(file_hdr)); 922 return fd; 923 } 924 925 fd = open(fname, O_WRONLY|O_APPEND, 0644); 926 927 return fd; 928 } 929 930 static void swrap_dump_packet(struct socket_info *si, const struct sockaddr *addr, 931 enum swrap_packet_type type, 932 const void *buf, size_t len) 933 { 934 const struct sockaddr_in *src_addr; 935 const struct sockaddr_in *dest_addr; 936 const char *file_name; 937 unsigned long tcp_seq = 0; 938 unsigned long tcp_ack = 0; 939 unsigned char tcp_ctl = 0; 940 int unreachable = 0; 941 struct timeval tv; 942 struct swrap_packet *packet; 943 size_t packet_len = 0; 944 int fd; 945 946 file_name = socket_wrapper_pcap_file(); 947 if (!file_name) { 948 return; 949 } 950 951 switch (si->family) { 952 case AF_INET: 953 #ifdef HAVE_IPV6 954 case AF_INET6: 955 #endif 956 break; 957 default: 958 return; 959 } 960 961 switch (type) { 962 case SWRAP_CONNECT_SEND: 963 if (si->type != SOCK_STREAM) return; 964 965 src_addr = (const struct sockaddr_in *)si->myname; 966 dest_addr = (const struct sockaddr_in *)addr; 967 968 tcp_seq = si->io.pck_snd; 969 tcp_ack = si->io.pck_rcv; 970 tcp_ctl = 0x02; /* SYN */ 971 972 si->io.pck_snd += 1; 973 974 break; 975 976 case SWRAP_CONNECT_RECV: 977 if (si->type != SOCK_STREAM) return; 978 979 dest_addr = (const struct sockaddr_in *)si->myname; 980 src_addr = (const struct sockaddr_in *)addr; 981 982 tcp_seq = si->io.pck_rcv; 983 tcp_ack = si->io.pck_snd; 984 tcp_ctl = 0x12; /** SYN,ACK */ 985 986 si->io.pck_rcv += 1; 987 988 break; 989 990 case SWRAP_CONNECT_UNREACH: 991 if (si->type != SOCK_STREAM) return; 992 993 dest_addr = (const struct sockaddr_in *)si->myname; 994 src_addr = (const struct sockaddr_in *)addr; 995 996 /* Unreachable: resend the data of SWRAP_CONNECT_SEND */ 997 tcp_seq = si->io.pck_snd - 1; 998 tcp_ack = si->io.pck_rcv; 999 tcp_ctl = 0x02; /* SYN */ 1000 unreachable = 1; 1001 1002 break; 1003 1004 case SWRAP_CONNECT_ACK: 1005 if (si->type != SOCK_STREAM) return; 1006 1007 src_addr = (const struct sockaddr_in *)si->myname; 1008 dest_addr = (const struct sockaddr_in *)addr; 1009 1010 tcp_seq = si->io.pck_snd; 1011 tcp_ack = si->io.pck_rcv; 1012 tcp_ctl = 0x10; /* ACK */ 1013 1014 break; 1015 1016 case SWRAP_ACCEPT_SEND: 1017 if (si->type != SOCK_STREAM) return; 1018 1019 dest_addr = (const struct sockaddr_in *)si->myname; 1020 src_addr = (const struct sockaddr_in *)addr; 1021 1022 tcp_seq = si->io.pck_rcv; 1023 tcp_ack = si->io.pck_snd; 1024 tcp_ctl = 0x02; /* SYN */ 1025 1026 si->io.pck_rcv += 1; 1027 1028 break; 1029 1030 case SWRAP_ACCEPT_RECV: 1031 if (si->type != SOCK_STREAM) return; 1032 1033 src_addr = (const struct sockaddr_in *)si->myname; 1034 dest_addr = (const struct sockaddr_in *)addr; 1035 1036 tcp_seq = si->io.pck_snd; 1037 tcp_ack = si->io.pck_rcv; 1038 tcp_ctl = 0x12; /* SYN,ACK */ 1039 1040 si->io.pck_snd += 1; 1041 1042 break; 1043 1044 case SWRAP_ACCEPT_ACK: 1045 if (si->type != SOCK_STREAM) return; 1046 1047 dest_addr = (const struct sockaddr_in *)si->myname; 1048 src_addr = (const struct sockaddr_in *)addr; 1049 1050 tcp_seq = si->io.pck_rcv; 1051 tcp_ack = si->io.pck_snd; 1052 tcp_ctl = 0x10; /* ACK */ 1053 1054 break; 1055 1056 case SWRAP_SEND: 1057 src_addr = (const struct sockaddr_in *)si->myname; 1058 dest_addr = (const struct sockaddr_in *)si->peername; 1059 1060 tcp_seq = si->io.pck_snd; 1061 tcp_ack = si->io.pck_rcv; 1062 tcp_ctl = 0x18; /* PSH,ACK */ 1063 1064 si->io.pck_snd += len; 1065 1066 break; 1067 1068 case SWRAP_SEND_RST: 1069 dest_addr = (const struct sockaddr_in *)si->myname; 1070 src_addr = (const struct sockaddr_in *)si->peername; 1071 1072 if (si->type == SOCK_DGRAM) { 1073 swrap_dump_packet(si, si->peername, 1074 SWRAP_SENDTO_UNREACH, 1075 buf, len); 1076 return; 1077 } 1078 1079 tcp_seq = si->io.pck_rcv; 1080 tcp_ack = si->io.pck_snd; 1081 tcp_ctl = 0x14; /** RST,ACK */ 1082 1083 break; 1084 1085 case SWRAP_PENDING_RST: 1086 dest_addr = (const struct sockaddr_in *)si->myname; 1087 src_addr = (const struct sockaddr_in *)si->peername; 1088 1089 if (si->type == SOCK_DGRAM) { 1090 return; 1091 } 1092 1093 tcp_seq = si->io.pck_rcv; 1094 tcp_ack = si->io.pck_snd; 1095 tcp_ctl = 0x14; /* RST,ACK */ 1096 1097 break; 1098 1099 case SWRAP_RECV: 1100 dest_addr = (const struct sockaddr_in *)si->myname; 1101 src_addr = (const struct sockaddr_in *)si->peername; 1102 1103 tcp_seq = si->io.pck_rcv; 1104 tcp_ack = si->io.pck_snd; 1105 tcp_ctl = 0x18; /* PSH,ACK */ 1106 1107 si->io.pck_rcv += len; 1108 1109 break; 1110 1111 case SWRAP_RECV_RST: 1112 dest_addr = (const struct sockaddr_in *)si->myname; 1113 src_addr = (const struct sockaddr_in *)si->peername; 1114 1115 if (si->type == SOCK_DGRAM) { 1116 return; 1117 } 1118 1119 tcp_seq = si->io.pck_rcv; 1120 tcp_ack = si->io.pck_snd; 1121 tcp_ctl = 0x14; /* RST,ACK */ 1122 1123 break; 1124 1125 case SWRAP_SENDTO: 1126 src_addr = (const struct sockaddr_in *)si->myname; 1127 dest_addr = (const struct sockaddr_in *)addr; 1128 1129 si->io.pck_snd += len; 1130 1131 break; 1132 1133 case SWRAP_SENDTO_UNREACH: 1134 dest_addr = (const struct sockaddr_in *)si->myname; 1135 src_addr = (const struct sockaddr_in *)addr; 1136 1137 unreachable = 1; 1138 1139 break; 1140 1141 case SWRAP_RECVFROM: 1142 dest_addr = (const struct sockaddr_in *)si->myname; 1143 src_addr = (const struct sockaddr_in *)addr; 1144 1145 si->io.pck_rcv += len; 1146 1147 break; 1148 1149 case SWRAP_CLOSE_SEND: 1150 if (si->type != SOCK_STREAM) return; 1151 1152 src_addr = (const struct sockaddr_in *)si->myname; 1153 dest_addr = (const struct sockaddr_in *)si->peername; 1154 1155 tcp_seq = si->io.pck_snd; 1156 tcp_ack = si->io.pck_rcv; 1157 tcp_ctl = 0x11; /* FIN, ACK */ 1158 1159 si->io.pck_snd += 1; 1160 1161 break; 1162 1163 case SWRAP_CLOSE_RECV: 1164 if (si->type != SOCK_STREAM) return; 1165 1166 dest_addr = (const struct sockaddr_in *)si->myname; 1167 src_addr = (const struct sockaddr_in *)si->peername; 1168 1169 tcp_seq = si->io.pck_rcv; 1170 tcp_ack = si->io.pck_snd; 1171 tcp_ctl = 0x11; /* FIN,ACK */ 1172 1173 si->io.pck_rcv += 1; 1174 1175 break; 1176 1177 case SWRAP_CLOSE_ACK: 1178 if (si->type != SOCK_STREAM) return; 1179 1180 src_addr = (const struct sockaddr_in *)si->myname; 1181 dest_addr = (const struct sockaddr_in *)si->peername; 1182 1183 tcp_seq = si->io.pck_snd; 1184 tcp_ack = si->io.pck_rcv; 1185 tcp_ctl = 0x10; /* ACK */ 1186 1187 break; 1188 default: 1189 return; 1190 } 1191 1192 swrapGetTimeOfDay(&tv); 1193 1194 packet = swrap_packet_init(&tv, src_addr, dest_addr, si->type, 1195 (const unsigned char *)buf, len, 1196 tcp_seq, tcp_ack, tcp_ctl, unreachable, 1197 &packet_len); 1198 if (!packet) { 1199 return; 1200 } 1201 1202 fd = swrap_get_pcap_fd(file_name); 1203 if (fd != -1) { 1204 write(fd, packet, packet_len); 1205 } 1206 1207 free(packet); 1208 } 1209 1210 _PUBLIC_ int swrap_socket(int family, int type, int protocol) 1211 { 1212 struct socket_info *si; 1213 int fd; 1214 1215 if (!socket_wrapper_dir()) { 1216 return real_socket(family, type, protocol); 1217 } 1218 1219 switch (family) { 1220 case AF_INET: 1221 #ifdef HAVE_IPV6 1222 case AF_INET6: 1223 #endif 1224 break; 1225 case AF_UNIX: 1226 return real_socket(family, type, protocol); 1227 default: 1228 errno = EAFNOSUPPORT; 1229 return -1; 1230 } 1231 1232 switch (type) { 1233 case SOCK_STREAM: 1234 break; 1235 case SOCK_DGRAM: 1236 break; 1237 default: 1238 errno = EPROTONOSUPPORT; 1239 return -1; 1240 } 1241 1242 #if 0 1243 switch (protocol) { 1244 case 0: 1245 break; 1246 default: 1247 errno = EPROTONOSUPPORT; 1248 return -1; 1249 } 1250 #endif 1251 1252 fd = real_socket(AF_UNIX, type, 0); 1253 1254 if (fd == -1) return -1; 1255 1256 si = (struct socket_info *)calloc(1, sizeof(struct socket_info)); 1257 1258 si->family = family; 1259 si->type = type; 1260 si->protocol = protocol; 1261 si->fd = fd; 1262 1263 SWRAP_DLIST_ADD(sockets, si); 1264 1265 return si->fd; 1266 } 1267 1268 _PUBLIC_ int swrap_accept(int s, struct sockaddr *addr, socklen_t *addrlen) 1269 { 1270 struct socket_info *parent_si, *child_si; 1271 int fd; 1272 struct sockaddr_un un_addr; 1273 socklen_t un_addrlen = sizeof(un_addr); 1274 struct sockaddr_un un_my_addr; 1275 socklen_t un_my_addrlen = sizeof(un_my_addr); 1276 struct sockaddr *my_addr; 1277 socklen_t my_addrlen, len; 1278 int ret; 1279 1280 parent_si = find_socket_info(s); 1281 if (!parent_si) { 1282 return real_accept(s, addr, addrlen); 1283 } 1284 1285 /* 1286 * assume out sockaddr have the same size as the in parent 1287 * socket family 1288 */ 1289 my_addrlen = socket_length(parent_si->family); 1290 if (my_addrlen < 0) { 1291 errno = EINVAL; 1292 return -1; 1293 } 1294 1295 my_addr = malloc(my_addrlen); 1296 if (my_addr == NULL) { 1297 return -1; 1298 } 1299 1300 memset(&un_addr, 0, sizeof(un_addr)); 1301 memset(&un_my_addr, 0, sizeof(un_my_addr)); 1302 1303 ret = real_accept(s, (struct sockaddr *)&un_addr, &un_addrlen); 1304 if (ret == -1) { 1305 free(my_addr); 1306 return ret; 1307 } 1308 1309 fd = ret; 1310 1311 len = my_addrlen; 1312 ret = sockaddr_convert_from_un(parent_si, &un_addr, un_addrlen, 1313 parent_si->family, my_addr, &len); 1314 if (ret == -1) { 1315 free(my_addr); 1316 close(fd); 1317 return ret; 1318 } 1319 1320 child_si = (struct socket_info *)malloc(sizeof(struct socket_info)); 1321 memset(child_si, 0, sizeof(*child_si)); 1322 1323 child_si->fd = fd; 1324 child_si->family = parent_si->family; 1325 child_si->type = parent_si->type; 1326 child_si->protocol = parent_si->protocol; 1327 child_si->bound = 1; 1328 child_si->is_server = 1; 1329 1330 child_si->peername_len = len; 1331 child_si->peername = sockaddr_dup(my_addr, len); 1332 1333 if (addr != NULL && addrlen != NULL) { 1334 *addrlen = len; 1335 if (*addrlen >= len) 1336 memcpy(addr, my_addr, len); 1337 *addrlen = 0; 1338 } 1339 1340 ret = real_getsockname(fd, (struct sockaddr *)&un_my_addr, &un_my_addrlen); 1341 if (ret == -1) { 1342 free(child_si); 1343 close(fd); 1344 return ret; 1345 } 1346 1347 len = my_addrlen; 1348 ret = sockaddr_convert_from_un(child_si, &un_my_addr, un_my_addrlen, 1349 child_si->family, my_addr, &len); 1350 if (ret == -1) { 1351 free(child_si); 1352 free(my_addr); 1353 close(fd); 1354 return ret; 1355 } 1356 1357 child_si->myname_len = len; 1358 child_si->myname = sockaddr_dup(my_addr, len); 1359 free(my_addr); 1360 1361 SWRAP_DLIST_ADD(sockets, child_si); 1362 1363 swrap_dump_packet(child_si, addr, SWRAP_ACCEPT_SEND, NULL, 0); 1364 swrap_dump_packet(child_si, addr, SWRAP_ACCEPT_RECV, NULL, 0); 1365 swrap_dump_packet(child_si, addr, SWRAP_ACCEPT_ACK, NULL, 0); 1366 1367 return fd; 1368 } 1369 1370 static int autobind_start_init; 1371 static int autobind_start; 1372 1373 /* using sendto() or connect() on an unbound socket would give the 1374 recipient no way to reply, as unlike UDP and TCP, a unix domain 1375 socket can't auto-assign emphemeral port numbers, so we need to 1376 assign it here */ 1377 static int swrap_auto_bind(struct socket_info *si) 1378 { 1379 struct sockaddr_un un_addr; 1380 int i; 1381 char type; 1382 int ret; 1383 int port; 1384 struct stat st; 1385 1386 if (autobind_start_init != 1) { 1387 autobind_start_init = 1; 1388 autobind_start = getpid(); 1389 autobind_start %= 50000; 1390 autobind_start += 10000; 1391 } 1392 1393 un_addr.sun_family = AF_UNIX; 1394 1395 switch (si->family) { 1396 case AF_INET: { 1397 struct sockaddr_in in; 1398 1399 switch (si->type) { 1400 case SOCK_STREAM: 1401 type = SOCKET_TYPE_CHAR_TCP; 1402 break; 1403 case SOCK_DGRAM: 1404 type = SOCKET_TYPE_CHAR_UDP; 1405 break; 1406 default: 1407 errno = ESOCKTNOSUPPORT; 1408 return -1; 1409 } 1410 1411 memset(&in, 0, sizeof(in)); 1412 in.sin_family = AF_INET; 1413 in.sin_addr.s_addr = htonl(127<<24 | 1414 socket_wrapper_default_iface()); 1415 1416 si->myname_len = sizeof(in); 1417 si->myname = sockaddr_dup(&in, si->myname_len); 1418 break; 1419 } 1420 #ifdef HAVE_IPV6 1421 case AF_INET6: { 1422 struct sockaddr_in6 in6; 1423 1424 switch (si->type) { 1425 case SOCK_STREAM: 1426 type = SOCKET_TYPE_CHAR_TCP_V6; 1427 break; 1428 case SOCK_DGRAM: 1429 type = SOCKET_TYPE_CHAR_UDP_V6; 1430 break; 1431 default: 1432 errno = ESOCKTNOSUPPORT; 1433 return -1; 1434 } 1435 1436 memset(&in6, 0, sizeof(in6)); 1437 in6.sin6_family = AF_INET6; 1438 in6.sin6_addr.s6_addr[0] = SW_IPV6_ADDRESS; 1439 si->myname_len = sizeof(in6); 1440 si->myname = sockaddr_dup(&in6, si->myname_len); 1441 break; 1442 } 1443 #endif 1444 default: 1445 errno = ESOCKTNOSUPPORT; 1446 return -1; 1447 } 1448 1449 if (autobind_start > 60000) { 1450 autobind_start = 10000; 1451 } 1452 1453 for (i=0;i<1000;i++) { 1454 port = autobind_start + i; 1455 snprintf(un_addr.sun_path, sizeof(un_addr.sun_path), 1456 "%s/"SOCKET_FORMAT, socket_wrapper_dir(), 1457 type, socket_wrapper_default_iface(), port); 1458 if (stat(un_addr.sun_path, &st) == 0) continue; 1459 1460 ret = real_bind(si->fd, (struct sockaddr *)&un_addr, sizeof(un_addr)); 1461 if (ret == -1) return ret; 1462 1463 si->tmp_path = strdup(un_addr.sun_path); 1464 si->bound = 1; 1465 autobind_start = port + 1; 1466 break; 1467 } 1468 if (i == 1000) { 1469 errno = ENFILE; 1470 return -1; 1471 } 1472 1473 set_port(si->family, port, si->myname); 1474 1475 return 0; 1476 } 1477 1478 1479 _PUBLIC_ int swrap_connect(int s, const struct sockaddr *serv_addr, socklen_t addrlen) 1480 { 1481 int ret; 1482 struct sockaddr_un un_addr; 1483 struct socket_info *si = find_socket_info(s); 1484 1485 if (!si) { 1486 return real_connect(s, serv_addr, addrlen); 1487 } 1488 1489 if (si->bound == 0) { 1490 ret = swrap_auto_bind(si); 1491 if (ret == -1) return -1; 1492 } 1493 1494 if (si->family != serv_addr->sa_family) { 1495 errno = EINVAL; 1496 return -1; 1497 } 1498 1499 ret = sockaddr_convert_to_un(si, (const struct sockaddr *)serv_addr, addrlen, &un_addr, 0, NULL); 1500 if (ret == -1) return -1; 1501 1502 swrap_dump_packet(si, serv_addr, SWRAP_CONNECT_SEND, NULL, 0); 1503 1504 ret = real_connect(s, (struct sockaddr *)&un_addr, 1505 sizeof(struct sockaddr_un)); 1506 1507 /* to give better errors */ 1508 if (ret == -1 && errno == ENOENT) { 1509 errno = EHOSTUNREACH; 1510 } 1511 1512 if (ret == 0) { 1513 si->peername_len = addrlen; 1514 si->peername = sockaddr_dup(serv_addr, addrlen); 1515 1516 swrap_dump_packet(si, serv_addr, SWRAP_CONNECT_RECV, NULL, 0); 1517 swrap_dump_packet(si, serv_addr, SWRAP_CONNECT_ACK, NULL, 0); 1518 } else { 1519 swrap_dump_packet(si, serv_addr, SWRAP_CONNECT_UNREACH, NULL, 0); 1520 } 1521 1522 return ret; 1523 } 1524 1525 _PUBLIC_ int swrap_bind(int s, const struct sockaddr *myaddr, socklen_t addrlen) 1526 { 1527 int ret; 1528 struct sockaddr_un un_addr; 1529 struct socket_info *si = find_socket_info(s); 1530 1531 if (!si) { 1532 return real_bind(s, myaddr, addrlen); 1533 } 1534 1535 si->myname_len = addrlen; 1536 si->myname = sockaddr_dup(myaddr, addrlen); 1537 1538 ret = sockaddr_convert_to_un(si, (const struct sockaddr *)myaddr, addrlen, &un_addr, 1, &si->bcast); 1539 if (ret == -1) return -1; 1540 1541 unlink(un_addr.sun_path); 1542 1543 ret = real_bind(s, (struct sockaddr *)&un_addr, 1544 sizeof(struct sockaddr_un)); 1545 1546 if (ret == 0) { 1547 si->bound = 1; 1548 } 1549 1550 return ret; 1551 } 1552 1553 _PUBLIC_ int swrap_listen(int s, int backlog) 1554 { 1555 int ret; 1556 struct socket_info *si = find_socket_info(s); 1557 1558 if (!si) { 1559 return real_listen(s, backlog); 1560 } 1561 1562 ret = real_listen(s, backlog); 1563 1564 return ret; 1565 } 1566 1567 _PUBLIC_ int swrap_getpeername(int s, struct sockaddr *name, socklen_t *addrlen) 1568 { 1569 struct socket_info *si = find_socket_info(s); 1570 1571 if (!si) { 1572 return real_getpeername(s, name, addrlen); 1573 } 1574 1575 if (!si->peername) 1576 { 1577 errno = ENOTCONN; 1578 return -1; 1579 } 1580 1581 memcpy(name, si->peername, si->peername_len); 1582 *addrlen = si->peername_len; 1583 1584 return 0; 1585 } 1586 1587 _PUBLIC_ int swrap_getsockname(int s, struct sockaddr *name, socklen_t *addrlen) 1588 { 1589 struct socket_info *si = find_socket_info(s); 1590 1591 if (!si) { 1592 return real_getsockname(s, name, addrlen); 1593 } 1594 1595 memcpy(name, si->myname, si->myname_len); 1596 *addrlen = si->myname_len; 1597 1598 return 0; 1599 } 1600 1601 _PUBLIC_ int swrap_getsockopt(int s, int level, int optname, void *optval, socklen_t *optlen) 1602 { 1603 struct socket_info *si = find_socket_info(s); 1604 1605 if (!si) { 1606 return real_getsockopt(s, level, optname, optval, optlen); 1607 } 1608 1609 if (level == SOL_SOCKET) { 1610 return real_getsockopt(s, level, optname, optval, optlen); 1611 } 1612 1613 errno = ENOPROTOOPT; 1614 return -1; 1615 } 1616 1617 _PUBLIC_ int swrap_setsockopt(int s, int level, int optname, const void *optval, socklen_t optlen) 1618 { 1619 struct socket_info *si = find_socket_info(s); 1620 1621 if (!si) { 1622 return real_setsockopt(s, level, optname, optval, optlen); 1623 } 1624 1625 if (level == SOL_SOCKET) { 1626 return real_setsockopt(s, level, optname, optval, optlen); 1627 } 1628 1629 switch (si->family) { 1630 case AF_INET: 1631 return 0; 1632 default: 1633 errno = ENOPROTOOPT; 1634 return -1; 1635 } 1636 } 1637 1638 _PUBLIC_ ssize_t swrap_recvfrom(int s, void *buf, size_t len, int flags, struct sockaddr *from, socklen_t *fromlen) 1639 { 1640 struct sockaddr_un un_addr; 1641 socklen_t un_addrlen = sizeof(un_addr); 1642 int ret; 1643 struct socket_info *si = find_socket_info(s); 1644 1645 if (!si) { 1646 return real_recvfrom(s, buf, len, flags, from, fromlen); 1647 } 1648 1649 /* irix 6.4 forgets to null terminate the sun_path string :-( */ 1650 memset(&un_addr, 0, sizeof(un_addr)); 1651 ret = real_recvfrom(s, buf, len, flags, (struct sockaddr *)&un_addr, &un_addrlen); 1652 if (ret == -1) 1653 return ret; 1654 1655 if (sockaddr_convert_from_un(si, &un_addr, un_addrlen, 1656 si->family, from, fromlen) == -1) { 1657 return -1; 1658 } 1659 1660 swrap_dump_packet(si, from, SWRAP_RECVFROM, buf, ret); 1661 1662 return ret; 1663 } 1664 1665 1666 _PUBLIC_ ssize_t swrap_sendto(int s, const void *buf, size_t len, int flags, const struct sockaddr *to, socklen_t tolen) 1667 { 1668 struct sockaddr_un un_addr; 1669 int ret; 1670 struct socket_info *si = find_socket_info(s); 1671 int bcast = 0; 1672 1673 if (!si) { 1674 return real_sendto(s, buf, len, flags, to, tolen); 1675 } 1676 1677 switch (si->type) { 1678 case SOCK_STREAM: 1679 ret = real_send(s, buf, len, flags); 1680 break; 1681 case SOCK_DGRAM: 1682 if (si->bound == 0) { 1683 ret = swrap_auto_bind(si); 1684 if (ret == -1) return -1; 1685 } 1686 1687 ret = sockaddr_convert_to_un(si, to, tolen, &un_addr, 0, &bcast); 1688 if (ret == -1) return -1; 1689 1690 if (bcast) { 1691 struct stat st; 1692 unsigned int iface; 1693 unsigned int prt = ntohs(((const struct sockaddr_in *)to)->sin_port); 1694 char type; 1695 1696 type = SOCKET_TYPE_CHAR_UDP; 1697 1698 for(iface=0; iface <= MAX_WRAPPED_INTERFACES; iface++) { 1699 snprintf(un_addr.sun_path, sizeof(un_addr.sun_path), "%s/"SOCKET_FORMAT, 1700 socket_wrapper_dir(), type, iface, prt); 1701 if (stat(un_addr.sun_path, &st) != 0) continue; 1702 1703 /* ignore the any errors in broadcast sends */ 1704 real_sendto(s, buf, len, flags, (struct sockaddr *)&un_addr, sizeof(un_addr)); 1705 } 1706 1707 swrap_dump_packet(si, to, SWRAP_SENDTO, buf, len); 1708 1709 return len; 1710 } 1711 1712 ret = real_sendto(s, buf, len, flags, (struct sockaddr *)&un_addr, sizeof(un_addr)); 1713 break; 1714 default: 1715 ret = -1; 1716 errno = EHOSTUNREACH; 1717 break; 1718 } 1719 1720 /* to give better errors */ 1721 if (ret == -1 && errno == ENOENT) { 1722 errno = EHOSTUNREACH; 1723 } 1724 1725 if (ret == -1) { 1726 swrap_dump_packet(si, to, SWRAP_SENDTO, buf, len); 1727 swrap_dump_packet(si, to, SWRAP_SENDTO_UNREACH, buf, len); 1728 } else { 1729 swrap_dump_packet(si, to, SWRAP_SENDTO, buf, ret); 1730 } 1731 1732 return ret; 1733 } 1734 1735 _PUBLIC_ int swrap_ioctl(int s, int r, void *p) 1736 { 1737 int ret; 1738 struct socket_info *si = find_socket_info(s); 1739 int value; 1740 1741 if (!si) { 1742 return real_ioctl(s, r, p); 1743 } 1744 1745 ret = real_ioctl(s, r, p); 1746 1747 switch (r) { 1748 case FIONREAD: 1749 value = *((int *)p); 1750 if (ret == -1 && errno != EAGAIN && errno != ENOBUFS) { 1751 swrap_dump_packet(si, NULL, SWRAP_PENDING_RST, NULL, 0); 1752 } else if (value == 0) { /* END OF FILE */ 1753 swrap_dump_packet(si, NULL, SWRAP_PENDING_RST, NULL, 0); 1754 } 1755 break; 1756 } 1757 1758 return ret; 1759 } 1760 1761 _PUBLIC_ ssize_t swrap_recv(int s, void *buf, size_t len, int flags) 1762 { 1763 int ret; 1764 struct socket_info *si = find_socket_info(s); 1765 1766 if (!si) { 1767 return real_recv(s, buf, len, flags); 1768 } 1769 1770 ret = real_recv(s, buf, len, flags); 1771 if (ret == -1 && errno != EAGAIN && errno != ENOBUFS) { 1772 swrap_dump_packet(si, NULL, SWRAP_RECV_RST, NULL, 0); 1773 } else if (ret == 0) { /* END OF FILE */ 1774 swrap_dump_packet(si, NULL, SWRAP_RECV_RST, NULL, 0); 1775 } else { 1776 swrap_dump_packet(si, NULL, SWRAP_RECV, buf, ret); 1777 } 1778 1779 return ret; 1780 } 1781 1782 1783 _PUBLIC_ ssize_t swrap_send(int s, const void *buf, size_t len, int flags) 1784 { 1785 int ret; 1786 struct socket_info *si = find_socket_info(s); 1787 1788 if (!si) { 1789 return real_send(s, buf, len, flags); 1790 } 1791 1792 ret = real_send(s, buf, len, flags); 1793 1794 if (ret == -1) { 1795 swrap_dump_packet(si, NULL, SWRAP_SEND, buf, len); 1796 swrap_dump_packet(si, NULL, SWRAP_SEND_RST, NULL, 0); 1797 } else { 1798 swrap_dump_packet(si, NULL, SWRAP_SEND, buf, ret); 1799 } 1800 1801 return ret; 1802 } 1803 1804 _PUBLIC_ int swrap_close(int fd) 1805 { 1806 struct socket_info *si = find_socket_info(fd); 1807 int ret; 1808 1809 if (!si) { 1810 return real_close(fd); 1811 } 1812 1813 SWRAP_DLIST_REMOVE(sockets, si); 1814 1815 if (si->myname && si->peername) { 1816 swrap_dump_packet(si, NULL, SWRAP_CLOSE_SEND, NULL, 0); 1817 } 1818 1819 ret = real_close(fd); 1820 1821 if (si->myname && si->peername) { 1822 swrap_dump_packet(si, NULL, SWRAP_CLOSE_RECV, NULL, 0); 1823 swrap_dump_packet(si, NULL, SWRAP_CLOSE_ACK, NULL, 0); 1824 } 1825 1826 if (si->path) free(si->path); 1827 if (si->myname) free(si->myname); 1828 if (si->peername) free(si->peername); 1829 if (si->tmp_path) { 1830 unlink(si->tmp_path); 1831 free(si->tmp_path); 1832 } 1833 free(si); 1834 1835 return ret; 1836 } 1837 1838 static int 1839 dup_internal(const struct socket_info *si_oldd, int fd) 1840 { 1841 struct socket_info *si_newd; 1842 1843 si_newd = (struct socket_info *)calloc(1, sizeof(struct socket_info)); 1844 1845 si_newd->fd = fd; 1846 1847 si_newd->family = si_oldd->family; 1848 si_newd->type = si_oldd->type; 1849 si_newd->protocol = si_oldd->protocol; 1850 si_newd->bound = si_oldd->bound; 1851 si_newd->bcast = si_oldd->bcast; 1852 if (si_oldd->path) 1853 si_newd->path = strdup(si_oldd->path); 1854 if (si_oldd->tmp_path) 1855 si_newd->tmp_path = strdup(si_oldd->tmp_path); 1856 si_newd->myname = 1857 sockaddr_dup(si_oldd->myname, si_oldd->myname_len); 1858 si_newd->myname_len = si_oldd->myname_len; 1859 si_newd->peername = 1860 sockaddr_dup(si_oldd->peername, si_oldd->peername_len); 1861 si_newd->peername_len = si_oldd->peername_len; 1862 1863 si_newd->io = si_oldd->io; 1864 1865 SWRAP_DLIST_ADD(sockets, si_newd); 1866 1867 return fd; 1868 } 1869 1870 1871 _PUBLIC_ int swrap_dup(int oldd) 1872 { 1873 struct socket_info *si; 1874 int fd; 1875 1876 si = find_socket_info(oldd); 1877 if (si == NULL) 1878 return real_dup(oldd); 1879 1880 fd = real_dup(si->fd); 1881 if (fd < 0) 1882 return fd; 1883 1884 return dup_internal(si, fd); 1885 } 1886 1887 1888 _PUBLIC_ int swrap_dup2(int oldd, int newd) 1889 { 1890 struct socket_info *si_newd, *si_oldd; 1891 int fd; 1892 1893 if (newd == oldd) 1894 return newd; 1895 1896 si_oldd = find_socket_info(oldd); 1897 si_newd = find_socket_info(newd); 1898 1899 if (si_oldd == NULL && si_newd == NULL) 1900 return real_dup2(oldd, newd); 1901 1902 fd = real_dup2(si_oldd->fd, newd); 1903 if (fd < 0) 1904 return fd; 1905 1906 /* close new socket first */ 1907 if (si_newd) 1908 swrap_close(newd); 1909 1910 return dup_internal(si_oldd, fd); 1911 } 1912