1 /* 2 * inet and unix socket functions for qemu 3 * 4 * (c) 2008 Gerd Hoffmann <kraxel@redhat.com> 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation; under version 2 of the License. 9 * 10 * This program is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU General Public License for more details. 14 * 15 * Contributions after 2012-01-13 are licensed under the terms of the 16 * GNU GPL, version 2 or (at your option) any later version. 17 */ 18 #include "qemu/osdep.h" 19 20 #ifdef CONFIG_AF_VSOCK 21 #include <linux/vm_sockets.h> 22 #endif /* CONFIG_AF_VSOCK */ 23 24 #include "monitor/monitor.h" 25 #include "qapi/clone-visitor.h" 26 #include "qapi/error.h" 27 #include "qapi/qapi-visit-sockets.h" 28 #include "qemu/sockets.h" 29 #include "qemu/main-loop.h" 30 #include "qapi/qobject-input-visitor.h" 31 #include "qapi/qobject-output-visitor.h" 32 #include "qemu/cutils.h" 33 #include "qemu/option.h" 34 #include "trace.h" 35 36 #ifndef AI_ADDRCONFIG 37 # define AI_ADDRCONFIG 0 38 #endif 39 40 #ifndef AI_V4MAPPED 41 # define AI_V4MAPPED 0 42 #endif 43 44 #ifndef AI_NUMERICSERV 45 # define AI_NUMERICSERV 0 46 #endif 47 48 /* 49 * On macOS TCP_KEEPIDLE is available under a different name, TCP_KEEPALIVE. 50 * https://github.com/apple/darwin-xnu/blob/xnu-4570.1.46/bsd/man/man4/tcp.4#L172 51 */ 52 #if defined(TCP_KEEPALIVE) && !defined(TCP_KEEPIDLE) 53 # define TCP_KEEPIDLE TCP_KEEPALIVE 54 #endif 55 56 57 static int inet_getport(struct addrinfo *e) 58 { 59 struct sockaddr_in *i4; 60 struct sockaddr_in6 *i6; 61 62 switch (e->ai_family) { 63 case PF_INET6: 64 i6 = (void*)e->ai_addr; 65 return ntohs(i6->sin6_port); 66 case PF_INET: 67 i4 = (void*)e->ai_addr; 68 return ntohs(i4->sin_port); 69 default: 70 return 0; 71 } 72 } 73 74 static void inet_setport(struct addrinfo *e, int port) 75 { 76 struct sockaddr_in *i4; 77 struct sockaddr_in6 *i6; 78 79 switch (e->ai_family) { 80 case PF_INET6: 81 i6 = (void*)e->ai_addr; 82 i6->sin6_port = htons(port); 83 break; 84 case PF_INET: 85 i4 = (void*)e->ai_addr; 86 i4->sin_port = htons(port); 87 break; 88 } 89 } 90 91 NetworkAddressFamily inet_netfamily(int family) 92 { 93 switch (family) { 94 case PF_INET6: return NETWORK_ADDRESS_FAMILY_IPV6; 95 case PF_INET: return NETWORK_ADDRESS_FAMILY_IPV4; 96 case PF_UNIX: return NETWORK_ADDRESS_FAMILY_UNIX; 97 #ifdef CONFIG_AF_VSOCK 98 case PF_VSOCK: return NETWORK_ADDRESS_FAMILY_VSOCK; 99 #endif /* CONFIG_AF_VSOCK */ 100 } 101 return NETWORK_ADDRESS_FAMILY_UNKNOWN; 102 } 103 104 bool fd_is_socket(int fd) 105 { 106 int optval; 107 socklen_t optlen = sizeof(optval); 108 return !getsockopt(fd, SOL_SOCKET, SO_TYPE, &optval, &optlen); 109 } 110 111 112 /* 113 * Matrix we're trying to apply 114 * 115 * ipv4 ipv6 family 116 * - - PF_UNSPEC 117 * - f PF_INET 118 * - t PF_INET6 119 * f - PF_INET6 120 * f f <error> 121 * f t PF_INET6 122 * t - PF_INET 123 * t f PF_INET 124 * t t PF_INET6/PF_UNSPEC 125 * 126 * NB, this matrix is only about getting the necessary results 127 * from getaddrinfo(). Some of the cases require further work 128 * after reading results from getaddrinfo in order to fully 129 * apply the logic the end user wants. 130 * 131 * In the first and last cases, we must set IPV6_V6ONLY=0 132 * when binding, to allow a single listener to potentially 133 * accept both IPv4+6 addresses. 134 */ 135 int inet_ai_family_from_address(InetSocketAddress *addr, 136 Error **errp) 137 { 138 if (addr->has_ipv6 && addr->has_ipv4 && 139 !addr->ipv6 && !addr->ipv4) { 140 error_setg(errp, "Cannot disable IPv4 and IPv6 at same time"); 141 return PF_UNSPEC; 142 } 143 if ((addr->has_ipv6 && addr->ipv6) && (addr->has_ipv4 && addr->ipv4)) { 144 /* 145 * Some backends can only do a single listener. In that case 146 * we want empty hostname to resolve to "::" and then use the 147 * flag IPV6_V6ONLY==0 to get both protocols on 1 socket. This 148 * doesn't work for addresses other than "", so they're just 149 * inevitably broken until multiple listeners can be used, 150 * and thus we honour getaddrinfo automatic protocol detection 151 * Once all backends do multi-listener, remove the PF_INET6 152 * branch entirely. 153 */ 154 if (!addr->host || g_str_equal(addr->host, "")) { 155 return PF_INET6; 156 } else { 157 return PF_UNSPEC; 158 } 159 } 160 if ((addr->has_ipv6 && addr->ipv6) || (addr->has_ipv4 && !addr->ipv4)) { 161 return PF_INET6; 162 } 163 if ((addr->has_ipv4 && addr->ipv4) || (addr->has_ipv6 && !addr->ipv6)) { 164 return PF_INET; 165 } 166 return PF_UNSPEC; 167 } 168 169 static int create_fast_reuse_socket(struct addrinfo *e) 170 { 171 int slisten = qemu_socket(e->ai_family, e->ai_socktype, e->ai_protocol); 172 if (slisten < 0) { 173 return -1; 174 } 175 socket_set_fast_reuse(slisten); 176 return slisten; 177 } 178 179 static int try_bind(int socket, InetSocketAddress *saddr, struct addrinfo *e) 180 { 181 #ifndef IPV6_V6ONLY 182 return bind(socket, e->ai_addr, e->ai_addrlen); 183 #else 184 /* 185 * Deals with first & last cases in matrix in comment 186 * for inet_ai_family_from_address(). 187 */ 188 int v6only = 189 ((!saddr->has_ipv4 && !saddr->has_ipv6) || 190 (saddr->has_ipv4 && saddr->ipv4 && 191 saddr->has_ipv6 && saddr->ipv6)) ? 0 : 1; 192 int stat; 193 194 rebind: 195 if (e->ai_family == PF_INET6) { 196 setsockopt(socket, IPPROTO_IPV6, IPV6_V6ONLY, &v6only, 197 sizeof(v6only)); 198 } 199 200 stat = bind(socket, e->ai_addr, e->ai_addrlen); 201 if (!stat) { 202 return 0; 203 } 204 205 /* If we got EADDRINUSE from an IPv6 bind & v6only is unset, 206 * it could be that the IPv4 port is already claimed, so retry 207 * with v6only set 208 */ 209 if (e->ai_family == PF_INET6 && errno == EADDRINUSE && !v6only) { 210 v6only = 1; 211 goto rebind; 212 } 213 return stat; 214 #endif 215 } 216 217 static int inet_set_sockopts(int sock, InetSocketAddress *saddr, Error **errp) 218 { 219 if (saddr->keep_alive) { 220 int keep_alive = 1; 221 int ret = setsockopt(sock, SOL_SOCKET, SO_KEEPALIVE, 222 &keep_alive, sizeof(keep_alive)); 223 224 if (ret < 0) { 225 error_setg_errno(errp, errno, 226 "Unable to set keep-alive option on socket"); 227 return -1; 228 } 229 #ifdef HAVE_TCP_KEEPCNT 230 if (saddr->has_keep_alive_count && saddr->keep_alive_count) { 231 int keep_count = saddr->keep_alive_count; 232 ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPCNT, &keep_count, 233 sizeof(keep_count)); 234 if (ret < 0) { 235 error_setg_errno(errp, errno, 236 "Unable to set TCP keep-alive count option on socket"); 237 return -1; 238 } 239 } 240 #endif 241 #ifdef HAVE_TCP_KEEPIDLE 242 if (saddr->has_keep_alive_idle && saddr->keep_alive_idle) { 243 int keep_idle = saddr->keep_alive_idle; 244 ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPIDLE, &keep_idle, 245 sizeof(keep_idle)); 246 if (ret < 0) { 247 error_setg_errno(errp, errno, 248 "Unable to set TCP keep-alive idle option on socket"); 249 return -1; 250 } 251 } 252 #endif 253 #ifdef HAVE_TCP_KEEPINTVL 254 if (saddr->has_keep_alive_interval && saddr->keep_alive_interval) { 255 int keep_interval = saddr->keep_alive_interval; 256 ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPINTVL, &keep_interval, 257 sizeof(keep_interval)); 258 if (ret < 0) { 259 error_setg_errno(errp, errno, 260 "Unable to set TCP keep-alive interval option on socket"); 261 return -1; 262 } 263 } 264 #endif 265 } 266 return 0; 267 } 268 269 static int inet_listen_saddr(InetSocketAddress *saddr, 270 int port_offset, 271 int num, 272 Error **errp) 273 { 274 ERRP_GUARD(); 275 struct addrinfo ai, *res, *e; 276 char port[33]; 277 char uaddr[INET6_ADDRSTRLEN+1]; 278 char uport[33]; 279 int rc, port_min, port_max, p; 280 int slisten = -1; 281 int saved_errno = 0; 282 bool socket_created = false; 283 284 memset(&ai,0, sizeof(ai)); 285 ai.ai_flags = AI_PASSIVE; 286 if (saddr->has_numeric && saddr->numeric) { 287 ai.ai_flags |= AI_NUMERICHOST | AI_NUMERICSERV; 288 } 289 ai.ai_socktype = SOCK_STREAM; 290 ai.ai_family = inet_ai_family_from_address(saddr, errp); 291 if (*errp) { 292 return -1; 293 } 294 295 if (saddr->host == NULL) { 296 error_setg(errp, "host not specified"); 297 return -1; 298 } 299 if (saddr->port != NULL) { 300 pstrcpy(port, sizeof(port), saddr->port); 301 } else { 302 port[0] = '\0'; 303 } 304 305 /* lookup */ 306 if (port_offset) { 307 uint64_t baseport; 308 if (strlen(port) == 0) { 309 error_setg(errp, "port not specified"); 310 return -1; 311 } 312 if (parse_uint_full(port, 10, &baseport) < 0) { 313 error_setg(errp, "can't convert to a number: %s", port); 314 return -1; 315 } 316 if (baseport > 65535 || 317 baseport + port_offset > 65535) { 318 error_setg(errp, "port %s out of range", port); 319 return -1; 320 } 321 snprintf(port, sizeof(port), "%d", (int)baseport + port_offset); 322 } 323 rc = getaddrinfo(strlen(saddr->host) ? saddr->host : NULL, 324 strlen(port) ? port : NULL, &ai, &res); 325 if (rc != 0) { 326 error_setg(errp, "address resolution failed for %s:%s: %s", 327 saddr->host, port, gai_strerror(rc)); 328 return -1; 329 } 330 331 /* create socket + bind/listen */ 332 for (e = res; e != NULL; e = e->ai_next) { 333 #ifdef HAVE_IPPROTO_MPTCP 334 if (saddr->has_mptcp && saddr->mptcp) { 335 e->ai_protocol = IPPROTO_MPTCP; 336 } 337 #endif 338 getnameinfo((struct sockaddr*)e->ai_addr,e->ai_addrlen, 339 uaddr,INET6_ADDRSTRLEN,uport,32, 340 NI_NUMERICHOST | NI_NUMERICSERV); 341 342 port_min = inet_getport(e); 343 port_max = saddr->has_to ? saddr->to + port_offset : port_min; 344 for (p = port_min; p <= port_max; p++) { 345 if (slisten >= 0) { 346 /* 347 * We have a socket we tried with the previous port. It cannot 348 * be rebound, we need to close it and create a new one. 349 */ 350 close(slisten); 351 slisten = -1; 352 } 353 inet_setport(e, p); 354 355 slisten = create_fast_reuse_socket(e); 356 if (slisten < 0) { 357 /* 358 * First time we expect we might fail to create the socket 359 * eg if 'e' has AF_INET6 but ipv6 kmod is not loaded. 360 * Later iterations should always succeed if first iteration 361 * worked though, so treat that as fatal. 362 */ 363 if (p == port_min) { 364 continue; 365 } else { 366 error_setg_errno(errp, errno, 367 "Failed to recreate failed listening socket"); 368 goto fail; 369 } 370 } 371 socket_created = true; 372 373 rc = try_bind(slisten, saddr, e); 374 if (rc < 0) { 375 if (errno == EADDRINUSE) { 376 /* This port is already used, try the next one */ 377 continue; 378 } 379 error_setg_errno(errp, errno, "Failed to bind socket"); 380 goto fail; 381 } 382 if (listen(slisten, num)) { 383 if (errno == EADDRINUSE) { 384 /* This port is already used, try the next one */ 385 continue; 386 } 387 error_setg_errno(errp, errno, "Failed to listen on socket"); 388 goto fail; 389 } 390 /* We have a listening socket */ 391 if (inet_set_sockopts(slisten, saddr, errp) < 0) { 392 goto fail; 393 } 394 freeaddrinfo(res); 395 return slisten; 396 } 397 } 398 error_setg_errno(errp, errno, 399 socket_created ? 400 "Failed to find an available port" : 401 "Failed to create a socket"); 402 fail: 403 saved_errno = errno; 404 if (slisten >= 0) { 405 close(slisten); 406 } 407 freeaddrinfo(res); 408 errno = saved_errno; 409 return -1; 410 } 411 412 #ifdef _WIN32 413 #define QEMU_SOCKET_RC_INPROGRESS(rc) \ 414 ((rc) == -EINPROGRESS || (rc) == -EWOULDBLOCK || (rc) == -WSAEALREADY) 415 #else 416 #define QEMU_SOCKET_RC_INPROGRESS(rc) \ 417 ((rc) == -EINPROGRESS) 418 #endif 419 420 static int inet_connect_addr(const InetSocketAddress *saddr, 421 struct addrinfo *addr, Error **errp) 422 { 423 int sock, rc; 424 425 sock = qemu_socket(addr->ai_family, addr->ai_socktype, addr->ai_protocol); 426 if (sock < 0) { 427 error_setg_errno(errp, errno, "Failed to create socket family %d", 428 addr->ai_family); 429 return -1; 430 } 431 432 /* connect to peer */ 433 do { 434 rc = 0; 435 if (connect(sock, addr->ai_addr, addr->ai_addrlen) < 0) { 436 rc = -errno; 437 } 438 } while (rc == -EINTR); 439 440 if (rc < 0) { 441 error_setg_errno(errp, errno, "Failed to connect to '%s:%s'", 442 saddr->host, saddr->port); 443 close(sock); 444 return -1; 445 } 446 447 return sock; 448 } 449 450 static struct addrinfo *inet_parse_connect_saddr(InetSocketAddress *saddr, 451 Error **errp) 452 { 453 ERRP_GUARD(); 454 struct addrinfo ai, *res; 455 int rc; 456 static int useV4Mapped = 1; 457 458 memset(&ai, 0, sizeof(ai)); 459 460 ai.ai_flags = AI_CANONNAME | AI_ADDRCONFIG; 461 if (qatomic_read(&useV4Mapped)) { 462 ai.ai_flags |= AI_V4MAPPED; 463 } 464 ai.ai_socktype = SOCK_STREAM; 465 ai.ai_family = inet_ai_family_from_address(saddr, errp); 466 if (*errp) { 467 return NULL; 468 } 469 470 if (saddr->host == NULL || saddr->port == NULL) { 471 error_setg(errp, "host and/or port not specified"); 472 return NULL; 473 } 474 475 /* lookup */ 476 rc = getaddrinfo(saddr->host, saddr->port, &ai, &res); 477 478 /* At least FreeBSD and OS-X 10.6 declare AI_V4MAPPED but 479 * then don't implement it in their getaddrinfo(). Detect 480 * this and retry without the flag since that's preferable 481 * to a fatal error 482 */ 483 if (rc == EAI_BADFLAGS && 484 (ai.ai_flags & AI_V4MAPPED)) { 485 qatomic_set(&useV4Mapped, 0); 486 ai.ai_flags &= ~AI_V4MAPPED; 487 rc = getaddrinfo(saddr->host, saddr->port, &ai, &res); 488 } 489 if (rc != 0) { 490 error_setg(errp, "address resolution failed for %s:%s: %s", 491 saddr->host, saddr->port, gai_strerror(rc)); 492 return NULL; 493 } 494 return res; 495 } 496 497 /** 498 * Create a socket and connect it to an address. 499 * 500 * @saddr: Inet socket address specification 501 * @errp: set on error 502 * 503 * Returns: -1 on error, file descriptor on success. 504 */ 505 int inet_connect_saddr(InetSocketAddress *saddr, Error **errp) 506 { 507 Error *local_err = NULL; 508 struct addrinfo *res, *e; 509 int sock = -1; 510 511 res = inet_parse_connect_saddr(saddr, errp); 512 if (!res) { 513 return -1; 514 } 515 516 for (e = res; e != NULL; e = e->ai_next) { 517 error_free(local_err); 518 local_err = NULL; 519 520 #ifdef HAVE_IPPROTO_MPTCP 521 if (saddr->has_mptcp && saddr->mptcp) { 522 e->ai_protocol = IPPROTO_MPTCP; 523 } 524 #endif 525 526 sock = inet_connect_addr(saddr, e, &local_err); 527 if (sock >= 0) { 528 break; 529 } 530 } 531 532 freeaddrinfo(res); 533 534 if (sock < 0) { 535 error_propagate(errp, local_err); 536 return sock; 537 } 538 539 if (inet_set_sockopts(sock, saddr, errp) < 0) { 540 close(sock); 541 return -1; 542 } 543 544 return sock; 545 } 546 547 static int inet_dgram_saddr(InetSocketAddress *sraddr, 548 InetSocketAddress *sladdr, 549 Error **errp) 550 { 551 ERRP_GUARD(); 552 struct addrinfo ai, *peer = NULL, *local = NULL; 553 const char *addr; 554 const char *port; 555 int sock = -1, rc; 556 557 /* lookup peer addr */ 558 memset(&ai,0, sizeof(ai)); 559 ai.ai_flags = AI_CANONNAME | AI_V4MAPPED | AI_ADDRCONFIG; 560 ai.ai_socktype = SOCK_DGRAM; 561 ai.ai_family = inet_ai_family_from_address(sraddr, errp); 562 if (*errp) { 563 goto err; 564 } 565 566 addr = sraddr->host; 567 port = sraddr->port; 568 if (addr == NULL || strlen(addr) == 0) { 569 addr = "localhost"; 570 } 571 if (port == NULL || strlen(port) == 0) { 572 error_setg(errp, "remote port not specified"); 573 goto err; 574 } 575 576 if ((rc = getaddrinfo(addr, port, &ai, &peer)) != 0) { 577 error_setg(errp, "address resolution failed for %s:%s: %s", addr, port, 578 gai_strerror(rc)); 579 goto err; 580 } 581 582 /* lookup local addr */ 583 memset(&ai,0, sizeof(ai)); 584 ai.ai_flags = AI_PASSIVE; 585 ai.ai_family = peer->ai_family; 586 ai.ai_socktype = SOCK_DGRAM; 587 588 if (sladdr) { 589 addr = sladdr->host; 590 port = sladdr->port; 591 if (addr == NULL || strlen(addr) == 0) { 592 addr = NULL; 593 } 594 if (!port || strlen(port) == 0) { 595 port = "0"; 596 } 597 } else { 598 addr = NULL; 599 port = "0"; 600 } 601 602 if ((rc = getaddrinfo(addr, port, &ai, &local)) != 0) { 603 error_setg(errp, "address resolution failed for %s:%s: %s", addr, port, 604 gai_strerror(rc)); 605 goto err; 606 } 607 608 /* create socket */ 609 sock = qemu_socket(peer->ai_family, peer->ai_socktype, peer->ai_protocol); 610 if (sock < 0) { 611 error_setg_errno(errp, errno, "Failed to create socket family %d", 612 peer->ai_family); 613 goto err; 614 } 615 socket_set_fast_reuse(sock); 616 617 /* bind socket */ 618 if (bind(sock, local->ai_addr, local->ai_addrlen) < 0) { 619 error_setg_errno(errp, errno, "Failed to bind socket"); 620 goto err; 621 } 622 623 /* connect to peer */ 624 if (connect(sock,peer->ai_addr,peer->ai_addrlen) < 0) { 625 error_setg_errno(errp, errno, "Failed to connect to '%s:%s'", 626 addr, port); 627 goto err; 628 } 629 630 freeaddrinfo(local); 631 freeaddrinfo(peer); 632 return sock; 633 634 err: 635 if (sock != -1) { 636 close(sock); 637 } 638 if (local) { 639 freeaddrinfo(local); 640 } 641 if (peer) { 642 freeaddrinfo(peer); 643 } 644 645 return -1; 646 } 647 648 static QemuOptsList inet_opts = { 649 .name = "InetSocketAddress", 650 .head = QTAILQ_HEAD_INITIALIZER(inet_opts.head), 651 .implied_opt_name = "addr", 652 .desc = { 653 { 654 .name = "addr", 655 .type = QEMU_OPT_STRING, 656 }, 657 { 658 .name = "numeric", 659 .type = QEMU_OPT_BOOL, 660 }, 661 { 662 .name = "to", 663 .type = QEMU_OPT_NUMBER, 664 }, 665 { 666 .name = "ipv4", 667 .type = QEMU_OPT_BOOL, 668 }, 669 { 670 .name = "ipv6", 671 .type = QEMU_OPT_BOOL, 672 }, 673 { 674 .name = "keep-alive", 675 .type = QEMU_OPT_BOOL, 676 }, 677 #ifdef HAVE_TCP_KEEPCNT 678 { 679 .name = "keep-alive-count", 680 .type = QEMU_OPT_NUMBER, 681 }, 682 #endif 683 #ifdef HAVE_TCP_KEEPIDLE 684 { 685 .name = "keep-alive-idle", 686 .type = QEMU_OPT_NUMBER, 687 }, 688 #endif 689 #ifdef HAVE_TCP_KEEPINTVL 690 { 691 .name = "keep-alive-interval", 692 .type = QEMU_OPT_NUMBER, 693 }, 694 #endif 695 #ifdef HAVE_IPPROTO_MPTCP 696 { 697 .name = "mptcp", 698 .type = QEMU_OPT_BOOL, 699 }, 700 #endif 701 { /* end of list */ } 702 }, 703 }; 704 705 int inet_parse(InetSocketAddress *addr, const char *str, Error **errp) 706 { 707 QemuOpts *opts = qemu_opts_parse(&inet_opts, str, true, errp); 708 if (!opts) { 709 return -1; 710 } 711 memset(addr, 0, sizeof(*addr)); 712 713 /* parse address */ 714 const char *addr_str = qemu_opt_get(opts, "addr"); 715 if (!addr_str) { 716 error_setg(errp, "error parsing address ''"); 717 return -1; 718 } 719 if (str[0] == '[') { 720 /* IPv6 addr */ 721 const char *ip_end = strstr(addr_str, "]:"); 722 if (!ip_end || ip_end - addr_str < 2 || strlen(ip_end) < 3) { 723 error_setg(errp, "error parsing IPv6 address '%s'", addr_str); 724 return -1; 725 } 726 addr->host = g_strndup(addr_str + 1, ip_end - addr_str - 1); 727 addr->port = g_strdup(ip_end + 2); 728 } else { 729 /* no host, hostname or IPv4 addr */ 730 const char *port = strchr(addr_str, ':'); 731 if (!port || strlen(port) < 2) { 732 error_setg(errp, "error parsing address '%s'", addr_str); 733 return -1; 734 } 735 addr->host = g_strndup(addr_str, port - addr_str); 736 addr->port = g_strdup(port + 1); 737 } 738 739 /* parse options */ 740 if (qemu_opt_find(opts, "numeric")) { 741 addr->has_numeric = true, 742 addr->numeric = qemu_opt_get_bool(opts, "numeric", false); 743 } 744 if (qemu_opt_find(opts, "to")) { 745 addr->has_to = true; 746 addr->to = qemu_opt_get_number(opts, "to", 0); 747 } 748 if (qemu_opt_find(opts, "ipv4")) { 749 addr->has_ipv4 = true; 750 addr->ipv4 = qemu_opt_get_bool(opts, "ipv4", false); 751 } 752 if (qemu_opt_find(opts, "ipv6")) { 753 addr->has_ipv6 = true; 754 addr->ipv6 = qemu_opt_get_bool(opts, "ipv6", false); 755 } 756 if (qemu_opt_find(opts, "keep-alive")) { 757 addr->has_keep_alive = true; 758 addr->keep_alive = qemu_opt_get_bool(opts, "keep-alive", false); 759 } 760 #ifdef HAVE_TCP_KEEPCNT 761 if (qemu_opt_find(opts, "keep-alive-count")) { 762 addr->has_keep_alive_count = true; 763 addr->keep_alive_count = qemu_opt_get_number(opts, "keep-alive-count", 0); 764 } 765 #endif 766 #ifdef HAVE_TCP_KEEPIDLE 767 if (qemu_opt_find(opts, "keep-alive-idle")) { 768 addr->has_keep_alive_idle = true; 769 addr->keep_alive_idle = qemu_opt_get_number(opts, "keep-alive-idle", 0); 770 } 771 #endif 772 #ifdef HAVE_TCP_KEEPINTVL 773 if (qemu_opt_find(opts, "keep-alive-interval")) { 774 addr->has_keep_alive_interval = true; 775 addr->keep_alive_interval = qemu_opt_get_number(opts, "keep-alive-interval", 0); 776 } 777 #endif 778 #ifdef HAVE_IPPROTO_MPTCP 779 if (qemu_opt_find(opts, "mptcp")) { 780 addr->has_mptcp = true; 781 addr->mptcp = qemu_opt_get_bool(opts, "mptcp", 0); 782 } 783 #endif 784 return 0; 785 } 786 787 788 #ifdef CONFIG_AF_VSOCK 789 static bool vsock_parse_vaddr_to_sockaddr(const VsockSocketAddress *vaddr, 790 struct sockaddr_vm *svm, 791 Error **errp) 792 { 793 uint64_t val; 794 795 memset(svm, 0, sizeof(*svm)); 796 svm->svm_family = AF_VSOCK; 797 798 if (parse_uint_full(vaddr->cid, 10, &val) < 0 || 799 val > UINT32_MAX) { 800 error_setg(errp, "Failed to parse cid '%s'", vaddr->cid); 801 return false; 802 } 803 svm->svm_cid = val; 804 805 if (parse_uint_full(vaddr->port, 10, &val) < 0 || 806 val > UINT32_MAX) { 807 error_setg(errp, "Failed to parse port '%s'", vaddr->port); 808 return false; 809 } 810 svm->svm_port = val; 811 812 return true; 813 } 814 815 static int vsock_connect_addr(const VsockSocketAddress *vaddr, 816 const struct sockaddr_vm *svm, Error **errp) 817 { 818 int sock, rc; 819 820 sock = qemu_socket(AF_VSOCK, SOCK_STREAM, 0); 821 if (sock < 0) { 822 error_setg_errno(errp, errno, "Failed to create socket family %d", 823 AF_VSOCK); 824 return -1; 825 } 826 827 /* connect to peer */ 828 do { 829 rc = 0; 830 if (connect(sock, (const struct sockaddr *)svm, sizeof(*svm)) < 0) { 831 rc = -errno; 832 } 833 } while (rc == -EINTR); 834 835 if (rc < 0) { 836 error_setg_errno(errp, errno, "Failed to connect to '%s:%s'", 837 vaddr->cid, vaddr->port); 838 close(sock); 839 return -1; 840 } 841 842 return sock; 843 } 844 845 static int vsock_connect_saddr(VsockSocketAddress *vaddr, Error **errp) 846 { 847 struct sockaddr_vm svm; 848 849 if (!vsock_parse_vaddr_to_sockaddr(vaddr, &svm, errp)) { 850 return -1; 851 } 852 853 return vsock_connect_addr(vaddr, &svm, errp); 854 } 855 856 static int vsock_listen_saddr(VsockSocketAddress *vaddr, 857 int num, 858 Error **errp) 859 { 860 struct sockaddr_vm svm; 861 int slisten; 862 863 if (!vsock_parse_vaddr_to_sockaddr(vaddr, &svm, errp)) { 864 return -1; 865 } 866 867 slisten = qemu_socket(AF_VSOCK, SOCK_STREAM, 0); 868 if (slisten < 0) { 869 error_setg_errno(errp, errno, "Failed to create socket"); 870 return -1; 871 } 872 873 if (bind(slisten, (const struct sockaddr *)&svm, sizeof(svm)) != 0) { 874 error_setg_errno(errp, errno, "Failed to bind socket"); 875 close(slisten); 876 return -1; 877 } 878 879 if (listen(slisten, num) != 0) { 880 error_setg_errno(errp, errno, "Failed to listen on socket"); 881 close(slisten); 882 return -1; 883 } 884 return slisten; 885 } 886 887 static int vsock_parse(VsockSocketAddress *addr, const char *str, 888 Error **errp) 889 { 890 char cid[33]; 891 char port[33]; 892 int n; 893 894 if (sscanf(str, "%32[^:]:%32[^,]%n", cid, port, &n) != 2) { 895 error_setg(errp, "error parsing address '%s'", str); 896 return -1; 897 } 898 if (str[n] != '\0') { 899 error_setg(errp, "trailing characters in address '%s'", str); 900 return -1; 901 } 902 903 addr->cid = g_strdup(cid); 904 addr->port = g_strdup(port); 905 return 0; 906 } 907 #else 908 static void vsock_unsupported(Error **errp) 909 { 910 error_setg(errp, "socket family AF_VSOCK unsupported"); 911 } 912 913 static int vsock_connect_saddr(VsockSocketAddress *vaddr, Error **errp) 914 { 915 vsock_unsupported(errp); 916 return -1; 917 } 918 919 static int vsock_listen_saddr(VsockSocketAddress *vaddr, 920 int num, 921 Error **errp) 922 { 923 vsock_unsupported(errp); 924 return -1; 925 } 926 927 static int vsock_parse(VsockSocketAddress *addr, const char *str, 928 Error **errp) 929 { 930 vsock_unsupported(errp); 931 return -1; 932 } 933 #endif /* CONFIG_AF_VSOCK */ 934 935 static bool saddr_is_abstract(UnixSocketAddress *saddr) 936 { 937 #ifdef CONFIG_LINUX 938 return saddr->abstract; 939 #else 940 return false; 941 #endif 942 } 943 944 static bool saddr_is_tight(UnixSocketAddress *saddr) 945 { 946 #ifdef CONFIG_LINUX 947 return !saddr->has_tight || saddr->tight; 948 #else 949 return false; 950 #endif 951 } 952 953 static int unix_listen_saddr(UnixSocketAddress *saddr, 954 int num, 955 Error **errp) 956 { 957 bool abstract = saddr_is_abstract(saddr); 958 struct sockaddr_un un; 959 int sock, fd; 960 char *pathbuf = NULL; 961 const char *path; 962 size_t pathlen; 963 size_t addrlen; 964 965 sock = qemu_socket(PF_UNIX, SOCK_STREAM, 0); 966 if (sock < 0) { 967 error_setg_errno(errp, errno, "Failed to create Unix socket"); 968 return -1; 969 } 970 971 if (saddr->path[0] || abstract) { 972 path = saddr->path; 973 } else { 974 path = pathbuf = g_strdup_printf("%s/qemu-socket-XXXXXX", 975 g_get_tmp_dir()); 976 } 977 978 pathlen = strlen(path); 979 if (pathlen > sizeof(un.sun_path) || 980 (abstract && pathlen > (sizeof(un.sun_path) - 1))) { 981 error_setg(errp, "UNIX socket path '%s' is too long", path); 982 error_append_hint(errp, "Path must be less than %zu bytes\n", 983 abstract ? sizeof(un.sun_path) - 1 : 984 sizeof(un.sun_path)); 985 goto err; 986 } 987 988 if (pathbuf != NULL) { 989 /* 990 * This dummy fd usage silences the mktemp() insecure warning. 991 * Using mkstemp() doesn't make things more secure here 992 * though. bind() complains about existing files, so we have 993 * to unlink first and thus re-open the race window. The 994 * worst case possible is bind() failing, i.e. a DoS attack. 995 */ 996 fd = mkstemp(pathbuf); 997 if (fd < 0) { 998 error_setg_errno(errp, errno, 999 "Failed to make a temporary socket %s", pathbuf); 1000 goto err; 1001 } 1002 close(fd); 1003 } 1004 1005 if (!abstract && unlink(path) < 0 && errno != ENOENT) { 1006 error_setg_errno(errp, errno, 1007 "Failed to unlink socket %s", path); 1008 goto err; 1009 } 1010 1011 memset(&un, 0, sizeof(un)); 1012 un.sun_family = AF_UNIX; 1013 addrlen = sizeof(un); 1014 1015 if (abstract) { 1016 un.sun_path[0] = '\0'; 1017 memcpy(&un.sun_path[1], path, pathlen); 1018 if (saddr_is_tight(saddr)) { 1019 addrlen = offsetof(struct sockaddr_un, sun_path) + 1 + pathlen; 1020 } 1021 } else { 1022 memcpy(un.sun_path, path, pathlen); 1023 } 1024 1025 if (bind(sock, (struct sockaddr *) &un, addrlen) < 0) { 1026 error_setg_errno(errp, errno, "Failed to bind socket to %s", path); 1027 goto err; 1028 } 1029 if (listen(sock, num) < 0) { 1030 error_setg_errno(errp, errno, "Failed to listen on socket"); 1031 goto err; 1032 } 1033 1034 g_free(pathbuf); 1035 return sock; 1036 1037 err: 1038 g_free(pathbuf); 1039 close(sock); 1040 return -1; 1041 } 1042 1043 static int unix_connect_saddr(UnixSocketAddress *saddr, Error **errp) 1044 { 1045 bool abstract = saddr_is_abstract(saddr); 1046 struct sockaddr_un un; 1047 int sock, rc; 1048 size_t pathlen; 1049 size_t addrlen; 1050 1051 if (saddr->path == NULL) { 1052 error_setg(errp, "unix connect: no path specified"); 1053 return -1; 1054 } 1055 1056 sock = qemu_socket(PF_UNIX, SOCK_STREAM, 0); 1057 if (sock < 0) { 1058 error_setg_errno(errp, errno, "Failed to create socket"); 1059 return -1; 1060 } 1061 1062 pathlen = strlen(saddr->path); 1063 if (pathlen > sizeof(un.sun_path) || 1064 (abstract && pathlen > (sizeof(un.sun_path) - 1))) { 1065 error_setg(errp, "UNIX socket path '%s' is too long", saddr->path); 1066 error_append_hint(errp, "Path must be less than %zu bytes\n", 1067 abstract ? sizeof(un.sun_path) - 1 : 1068 sizeof(un.sun_path)); 1069 goto err; 1070 } 1071 1072 memset(&un, 0, sizeof(un)); 1073 un.sun_family = AF_UNIX; 1074 addrlen = sizeof(un); 1075 1076 if (abstract) { 1077 un.sun_path[0] = '\0'; 1078 memcpy(&un.sun_path[1], saddr->path, pathlen); 1079 if (saddr_is_tight(saddr)) { 1080 addrlen = offsetof(struct sockaddr_un, sun_path) + 1 + pathlen; 1081 } 1082 } else { 1083 memcpy(un.sun_path, saddr->path, pathlen); 1084 } 1085 /* connect to peer */ 1086 do { 1087 rc = 0; 1088 if (connect(sock, (struct sockaddr *) &un, addrlen) < 0) { 1089 rc = -errno; 1090 } 1091 } while (rc == -EINTR); 1092 1093 if (rc < 0) { 1094 error_setg_errno(errp, -rc, "Failed to connect to '%s'", 1095 saddr->path); 1096 goto err; 1097 } 1098 1099 return sock; 1100 1101 err: 1102 close(sock); 1103 return -1; 1104 } 1105 1106 /* compatibility wrapper */ 1107 int unix_listen(const char *str, Error **errp) 1108 { 1109 UnixSocketAddress *saddr; 1110 int sock; 1111 1112 saddr = g_new0(UnixSocketAddress, 1); 1113 saddr->path = g_strdup(str); 1114 sock = unix_listen_saddr(saddr, 1, errp); 1115 qapi_free_UnixSocketAddress(saddr); 1116 return sock; 1117 } 1118 1119 int unix_connect(const char *path, Error **errp) 1120 { 1121 UnixSocketAddress *saddr; 1122 int sock; 1123 1124 saddr = g_new0(UnixSocketAddress, 1); 1125 saddr->path = g_strdup(path); 1126 sock = unix_connect_saddr(saddr, errp); 1127 qapi_free_UnixSocketAddress(saddr); 1128 return sock; 1129 } 1130 1131 char *socket_uri(SocketAddress *addr) 1132 { 1133 switch (addr->type) { 1134 case SOCKET_ADDRESS_TYPE_INET: 1135 return g_strdup_printf("tcp:%s:%s", 1136 addr->u.inet.host, 1137 addr->u.inet.port); 1138 case SOCKET_ADDRESS_TYPE_UNIX: 1139 return g_strdup_printf("unix:%s", 1140 addr->u.q_unix.path); 1141 case SOCKET_ADDRESS_TYPE_FD: 1142 return g_strdup_printf("fd:%s", addr->u.fd.str); 1143 case SOCKET_ADDRESS_TYPE_VSOCK: 1144 return g_strdup_printf("vsock:%s:%s", 1145 addr->u.vsock.cid, 1146 addr->u.vsock.port); 1147 default: 1148 return g_strdup("unknown address type"); 1149 } 1150 } 1151 1152 SocketAddress *socket_parse(const char *str, Error **errp) 1153 { 1154 SocketAddress *addr; 1155 1156 addr = g_new0(SocketAddress, 1); 1157 if (strstart(str, "unix:", NULL)) { 1158 if (str[5] == '\0') { 1159 error_setg(errp, "invalid Unix socket address"); 1160 goto fail; 1161 } else { 1162 addr->type = SOCKET_ADDRESS_TYPE_UNIX; 1163 addr->u.q_unix.path = g_strdup(str + 5); 1164 } 1165 } else if (strstart(str, "fd:", NULL)) { 1166 if (str[3] == '\0') { 1167 error_setg(errp, "invalid file descriptor address"); 1168 goto fail; 1169 } else { 1170 addr->type = SOCKET_ADDRESS_TYPE_FD; 1171 addr->u.fd.str = g_strdup(str + 3); 1172 } 1173 } else if (strstart(str, "vsock:", NULL)) { 1174 addr->type = SOCKET_ADDRESS_TYPE_VSOCK; 1175 if (vsock_parse(&addr->u.vsock, str + strlen("vsock:"), errp)) { 1176 goto fail; 1177 } 1178 } else if (strstart(str, "tcp:", NULL)) { 1179 addr->type = SOCKET_ADDRESS_TYPE_INET; 1180 if (inet_parse(&addr->u.inet, str + strlen("tcp:"), errp)) { 1181 goto fail; 1182 } 1183 } else { 1184 addr->type = SOCKET_ADDRESS_TYPE_INET; 1185 if (inet_parse(&addr->u.inet, str, errp)) { 1186 goto fail; 1187 } 1188 } 1189 return addr; 1190 1191 fail: 1192 qapi_free_SocketAddress(addr); 1193 return NULL; 1194 } 1195 1196 static int socket_get_fd(const char *fdstr, Error **errp) 1197 { 1198 Monitor *cur_mon = monitor_cur(); 1199 int fd; 1200 if (cur_mon) { 1201 fd = monitor_get_fd(cur_mon, fdstr, errp); 1202 if (fd < 0) { 1203 return -1; 1204 } 1205 } else { 1206 if (qemu_strtoi(fdstr, NULL, 10, &fd) < 0) { 1207 error_setg_errno(errp, errno, 1208 "Unable to parse FD number %s", 1209 fdstr); 1210 return -1; 1211 } 1212 } 1213 if (!fd_is_socket(fd)) { 1214 error_setg(errp, "File descriptor '%s' is not a socket", fdstr); 1215 close(fd); 1216 return -1; 1217 } 1218 return fd; 1219 } 1220 1221 int socket_address_parse_named_fd(SocketAddress *addr, Error **errp) 1222 { 1223 int fd; 1224 1225 if (addr->type != SOCKET_ADDRESS_TYPE_FD) { 1226 return 0; 1227 } 1228 1229 fd = socket_get_fd(addr->u.fd.str, errp); 1230 if (fd < 0) { 1231 return fd; 1232 } 1233 1234 g_free(addr->u.fd.str); 1235 addr->u.fd.str = g_strdup_printf("%d", fd); 1236 1237 return 0; 1238 } 1239 1240 int socket_connect(SocketAddress *addr, Error **errp) 1241 { 1242 int fd; 1243 1244 switch (addr->type) { 1245 case SOCKET_ADDRESS_TYPE_INET: 1246 fd = inet_connect_saddr(&addr->u.inet, errp); 1247 break; 1248 1249 case SOCKET_ADDRESS_TYPE_UNIX: 1250 fd = unix_connect_saddr(&addr->u.q_unix, errp); 1251 break; 1252 1253 case SOCKET_ADDRESS_TYPE_FD: 1254 fd = socket_get_fd(addr->u.fd.str, errp); 1255 break; 1256 1257 case SOCKET_ADDRESS_TYPE_VSOCK: 1258 fd = vsock_connect_saddr(&addr->u.vsock, errp); 1259 break; 1260 1261 default: 1262 abort(); 1263 } 1264 return fd; 1265 } 1266 1267 int socket_listen(SocketAddress *addr, int num, Error **errp) 1268 { 1269 int fd; 1270 1271 trace_socket_listen(num); 1272 switch (addr->type) { 1273 case SOCKET_ADDRESS_TYPE_INET: 1274 fd = inet_listen_saddr(&addr->u.inet, 0, num, errp); 1275 break; 1276 1277 case SOCKET_ADDRESS_TYPE_UNIX: 1278 fd = unix_listen_saddr(&addr->u.q_unix, num, errp); 1279 break; 1280 1281 case SOCKET_ADDRESS_TYPE_FD: 1282 fd = socket_get_fd(addr->u.fd.str, errp); 1283 if (fd < 0) { 1284 return -1; 1285 } 1286 1287 /* 1288 * If the socket is not yet in the listen state, then transition it to 1289 * the listen state now. 1290 * 1291 * If it's already listening then this updates the backlog value as 1292 * requested. 1293 * 1294 * If this socket cannot listen because it's already in another state 1295 * (e.g. unbound or connected) then we'll catch the error here. 1296 */ 1297 if (listen(fd, num) != 0) { 1298 error_setg_errno(errp, errno, "Failed to listen on fd socket"); 1299 close(fd); 1300 return -1; 1301 } 1302 break; 1303 1304 case SOCKET_ADDRESS_TYPE_VSOCK: 1305 fd = vsock_listen_saddr(&addr->u.vsock, num, errp); 1306 break; 1307 1308 default: 1309 abort(); 1310 } 1311 return fd; 1312 } 1313 1314 void socket_listen_cleanup(int fd, Error **errp) 1315 { 1316 SocketAddress *addr; 1317 1318 addr = socket_local_address(fd, errp); 1319 if (!addr) { 1320 return; 1321 } 1322 1323 if (addr->type == SOCKET_ADDRESS_TYPE_UNIX 1324 && addr->u.q_unix.path) { 1325 if (unlink(addr->u.q_unix.path) < 0 && errno != ENOENT) { 1326 error_setg_errno(errp, errno, 1327 "Failed to unlink socket %s", 1328 addr->u.q_unix.path); 1329 } 1330 } 1331 1332 qapi_free_SocketAddress(addr); 1333 } 1334 1335 int socket_dgram(SocketAddress *remote, SocketAddress *local, Error **errp) 1336 { 1337 int fd; 1338 1339 /* 1340 * TODO SOCKET_ADDRESS_TYPE_FD when fd is AF_INET or AF_INET6 1341 * (although other address families can do SOCK_DGRAM, too) 1342 */ 1343 switch (remote->type) { 1344 case SOCKET_ADDRESS_TYPE_INET: 1345 fd = inet_dgram_saddr(&remote->u.inet, 1346 local ? &local->u.inet : NULL, errp); 1347 break; 1348 1349 default: 1350 error_setg(errp, "socket type unsupported for datagram"); 1351 fd = -1; 1352 } 1353 return fd; 1354 } 1355 1356 1357 static SocketAddress * 1358 socket_sockaddr_to_address_inet(struct sockaddr_storage *sa, 1359 socklen_t salen, 1360 Error **errp) 1361 { 1362 char host[NI_MAXHOST]; 1363 char serv[NI_MAXSERV]; 1364 SocketAddress *addr; 1365 InetSocketAddress *inet; 1366 int ret; 1367 1368 ret = getnameinfo((struct sockaddr *)sa, salen, 1369 host, sizeof(host), 1370 serv, sizeof(serv), 1371 NI_NUMERICHOST | NI_NUMERICSERV); 1372 if (ret != 0) { 1373 error_setg(errp, "Cannot format numeric socket address: %s", 1374 gai_strerror(ret)); 1375 return NULL; 1376 } 1377 1378 addr = g_new0(SocketAddress, 1); 1379 addr->type = SOCKET_ADDRESS_TYPE_INET; 1380 inet = &addr->u.inet; 1381 inet->host = g_strdup(host); 1382 inet->port = g_strdup(serv); 1383 if (sa->ss_family == AF_INET) { 1384 inet->has_ipv4 = inet->ipv4 = true; 1385 } else { 1386 inet->has_ipv6 = inet->ipv6 = true; 1387 } 1388 1389 return addr; 1390 } 1391 1392 1393 static SocketAddress * 1394 socket_sockaddr_to_address_unix(struct sockaddr_storage *sa, 1395 socklen_t salen, 1396 Error **errp) 1397 { 1398 SocketAddress *addr; 1399 struct sockaddr_un *su = (struct sockaddr_un *)sa; 1400 1401 addr = g_new0(SocketAddress, 1); 1402 addr->type = SOCKET_ADDRESS_TYPE_UNIX; 1403 salen -= offsetof(struct sockaddr_un, sun_path); 1404 #ifdef CONFIG_LINUX 1405 if (salen > 0 && !su->sun_path[0]) { 1406 /* Linux abstract socket */ 1407 addr->u.q_unix.path = g_strndup(su->sun_path + 1, salen - 1); 1408 addr->u.q_unix.has_abstract = true; 1409 addr->u.q_unix.abstract = true; 1410 addr->u.q_unix.has_tight = true; 1411 addr->u.q_unix.tight = salen < sizeof(su->sun_path); 1412 return addr; 1413 } 1414 #endif 1415 1416 addr->u.q_unix.path = g_strndup(su->sun_path, salen); 1417 return addr; 1418 } 1419 1420 #ifdef CONFIG_AF_VSOCK 1421 static SocketAddress * 1422 socket_sockaddr_to_address_vsock(struct sockaddr_storage *sa, 1423 socklen_t salen, 1424 Error **errp) 1425 { 1426 SocketAddress *addr; 1427 VsockSocketAddress *vaddr; 1428 struct sockaddr_vm *svm = (struct sockaddr_vm *)sa; 1429 1430 addr = g_new0(SocketAddress, 1); 1431 addr->type = SOCKET_ADDRESS_TYPE_VSOCK; 1432 vaddr = &addr->u.vsock; 1433 vaddr->cid = g_strdup_printf("%u", svm->svm_cid); 1434 vaddr->port = g_strdup_printf("%u", svm->svm_port); 1435 1436 return addr; 1437 } 1438 #endif /* CONFIG_AF_VSOCK */ 1439 1440 SocketAddress * 1441 socket_sockaddr_to_address(struct sockaddr_storage *sa, 1442 socklen_t salen, 1443 Error **errp) 1444 { 1445 switch (sa->ss_family) { 1446 case AF_INET: 1447 case AF_INET6: 1448 return socket_sockaddr_to_address_inet(sa, salen, errp); 1449 1450 case AF_UNIX: 1451 return socket_sockaddr_to_address_unix(sa, salen, errp); 1452 1453 #ifdef CONFIG_AF_VSOCK 1454 case AF_VSOCK: 1455 return socket_sockaddr_to_address_vsock(sa, salen, errp); 1456 #endif 1457 1458 default: 1459 error_setg(errp, "socket family %d unsupported", 1460 sa->ss_family); 1461 return NULL; 1462 } 1463 return 0; 1464 } 1465 1466 1467 SocketAddress *socket_local_address(int fd, Error **errp) 1468 { 1469 struct sockaddr_storage ss; 1470 socklen_t sslen = sizeof(ss); 1471 1472 if (getsockname(fd, (struct sockaddr *)&ss, &sslen) < 0) { 1473 error_setg_errno(errp, errno, "%s", 1474 "Unable to query local socket address"); 1475 return NULL; 1476 } 1477 1478 return socket_sockaddr_to_address(&ss, sslen, errp); 1479 } 1480 1481 1482 SocketAddress *socket_address_flatten(SocketAddressLegacy *addr_legacy) 1483 { 1484 SocketAddress *addr; 1485 1486 if (!addr_legacy) { 1487 return NULL; 1488 } 1489 1490 addr = g_new(SocketAddress, 1); 1491 1492 switch (addr_legacy->type) { 1493 case SOCKET_ADDRESS_TYPE_INET: 1494 addr->type = SOCKET_ADDRESS_TYPE_INET; 1495 QAPI_CLONE_MEMBERS(InetSocketAddress, &addr->u.inet, 1496 addr_legacy->u.inet.data); 1497 break; 1498 case SOCKET_ADDRESS_TYPE_UNIX: 1499 addr->type = SOCKET_ADDRESS_TYPE_UNIX; 1500 QAPI_CLONE_MEMBERS(UnixSocketAddress, &addr->u.q_unix, 1501 addr_legacy->u.q_unix.data); 1502 break; 1503 case SOCKET_ADDRESS_TYPE_VSOCK: 1504 addr->type = SOCKET_ADDRESS_TYPE_VSOCK; 1505 QAPI_CLONE_MEMBERS(VsockSocketAddress, &addr->u.vsock, 1506 addr_legacy->u.vsock.data); 1507 break; 1508 case SOCKET_ADDRESS_TYPE_FD: 1509 addr->type = SOCKET_ADDRESS_TYPE_FD; 1510 QAPI_CLONE_MEMBERS(FdSocketAddress, &addr->u.fd, 1511 addr_legacy->u.fd.data); 1512 break; 1513 default: 1514 abort(); 1515 } 1516 1517 return addr; 1518 } 1519