1 /*- 2 * Copyright (c) 1982, 1986, 1989, 1990, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. Neither the name of the University nor the names of its contributors 14 * may be used to endorse or promote products derived from this software 15 * without specific prior written permission. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27 * SUCH DAMAGE. 28 * 29 * @(#)uipc_syscalls.c 8.4 (Berkeley) 2/21/94 30 */ 31 32 #include <sys/cdefs.h> 33 __FBSDID("$FreeBSD$"); 34 35 #include "opt_capsicum.h" 36 #include "opt_inet.h" 37 #include "opt_inet6.h" 38 #include "opt_compat.h" 39 #include "opt_ktrace.h" 40 41 #include <sys/param.h> 42 #include <sys/systm.h> 43 #include <sys/capsicum.h> 44 #include <sys/kernel.h> 45 #include <sys/lock.h> 46 #include <sys/mutex.h> 47 #include <sys/sysproto.h> 48 #include <sys/malloc.h> 49 #include <sys/filedesc.h> 50 #include <sys/proc.h> 51 #include <sys/filio.h> 52 #include <sys/jail.h> 53 #include <sys/mbuf.h> 54 #include <sys/protosw.h> 55 #include <sys/rwlock.h> 56 #include <sys/socket.h> 57 #include <sys/socketvar.h> 58 #include <sys/syscallsubr.h> 59 #ifdef KTRACE 60 #include <sys/ktrace.h> 61 #endif 62 #ifdef COMPAT_FREEBSD32 63 #include <compat/freebsd32/freebsd32_util.h> 64 #endif 65 66 #include <net/vnet.h> 67 68 #include <security/audit/audit.h> 69 #include <security/mac/mac_framework.h> 70 71 /* 72 * Flags for accept1() and kern_accept4(), in addition to SOCK_CLOEXEC 73 * and SOCK_NONBLOCK. 74 */ 75 #define ACCEPT4_INHERIT 0x1 76 #define ACCEPT4_COMPAT 0x2 77 78 static int sendit(struct thread *td, int s, struct msghdr *mp, int flags); 79 static int recvit(struct thread *td, int s, struct msghdr *mp, void *namelenp); 80 81 static int accept1(struct thread *td, int s, struct sockaddr *uname, 82 socklen_t *anamelen, int flags); 83 static int getsockname1(struct thread *td, struct getsockname_args *uap, 84 int compat); 85 static int getpeername1(struct thread *td, struct getpeername_args *uap, 86 int compat); 87 static int sockargs(struct mbuf **, char *, socklen_t, int); 88 89 /* 90 * Convert a user file descriptor to a kernel file entry and check if required 91 * capability rights are present. 92 * If required copy of current set of capability rights is returned. 93 * A reference on the file entry is held upon returning. 94 */ 95 int 96 getsock_cap(struct thread *td, int fd, cap_rights_t *rightsp, 97 struct file **fpp, u_int *fflagp, struct filecaps *havecapsp) 98 { 99 struct file *fp; 100 int error; 101 102 error = fget_cap(td, fd, rightsp, &fp, havecapsp); 103 if (error != 0) 104 return (error); 105 if (fp->f_type != DTYPE_SOCKET) { 106 fdrop(fp, td); 107 if (havecapsp != NULL) 108 filecaps_free(havecapsp); 109 return (ENOTSOCK); 110 } 111 if (fflagp != NULL) 112 *fflagp = fp->f_flag; 113 *fpp = fp; 114 return (0); 115 } 116 117 /* 118 * System call interface to the socket abstraction. 119 */ 120 #if defined(COMPAT_43) 121 #define COMPAT_OLDSOCK 122 #endif 123 124 int 125 sys_socket(struct thread *td, struct socket_args *uap) 126 { 127 struct socket *so; 128 struct file *fp; 129 int fd, error, type, oflag, fflag; 130 131 AUDIT_ARG_SOCKET(uap->domain, uap->type, uap->protocol); 132 133 type = uap->type; 134 oflag = 0; 135 fflag = 0; 136 if ((type & SOCK_CLOEXEC) != 0) { 137 type &= ~SOCK_CLOEXEC; 138 oflag |= O_CLOEXEC; 139 } 140 if ((type & SOCK_NONBLOCK) != 0) { 141 type &= ~SOCK_NONBLOCK; 142 fflag |= FNONBLOCK; 143 } 144 145 #ifdef MAC 146 error = mac_socket_check_create(td->td_ucred, uap->domain, type, 147 uap->protocol); 148 if (error != 0) 149 return (error); 150 #endif 151 error = falloc(td, &fp, &fd, oflag); 152 if (error != 0) 153 return (error); 154 /* An extra reference on `fp' has been held for us by falloc(). */ 155 error = socreate(uap->domain, &so, type, uap->protocol, 156 td->td_ucred, td); 157 if (error != 0) { 158 fdclose(td, fp, fd); 159 } else { 160 finit(fp, FREAD | FWRITE | fflag, DTYPE_SOCKET, so, &socketops); 161 if ((fflag & FNONBLOCK) != 0) 162 (void) fo_ioctl(fp, FIONBIO, &fflag, td->td_ucred, td); 163 td->td_retval[0] = fd; 164 } 165 fdrop(fp, td); 166 return (error); 167 } 168 169 int 170 sys_bind(struct thread *td, struct bind_args *uap) 171 { 172 struct sockaddr *sa; 173 int error; 174 175 error = getsockaddr(&sa, uap->name, uap->namelen); 176 if (error == 0) { 177 error = kern_bindat(td, AT_FDCWD, uap->s, sa); 178 free(sa, M_SONAME); 179 } 180 return (error); 181 } 182 183 int 184 kern_bindat(struct thread *td, int dirfd, int fd, struct sockaddr *sa) 185 { 186 struct socket *so; 187 struct file *fp; 188 cap_rights_t rights; 189 int error; 190 191 AUDIT_ARG_FD(fd); 192 AUDIT_ARG_SOCKADDR(td, dirfd, sa); 193 error = getsock_cap(td, fd, cap_rights_init(&rights, CAP_BIND), 194 &fp, NULL, NULL); 195 if (error != 0) 196 return (error); 197 so = fp->f_data; 198 #ifdef KTRACE 199 if (KTRPOINT(td, KTR_STRUCT)) 200 ktrsockaddr(sa); 201 #endif 202 #ifdef MAC 203 error = mac_socket_check_bind(td->td_ucred, so, sa); 204 if (error == 0) { 205 #endif 206 if (dirfd == AT_FDCWD) 207 error = sobind(so, sa, td); 208 else 209 error = sobindat(dirfd, so, sa, td); 210 #ifdef MAC 211 } 212 #endif 213 fdrop(fp, td); 214 return (error); 215 } 216 217 int 218 sys_bindat(struct thread *td, struct bindat_args *uap) 219 { 220 struct sockaddr *sa; 221 int error; 222 223 error = getsockaddr(&sa, uap->name, uap->namelen); 224 if (error == 0) { 225 error = kern_bindat(td, uap->fd, uap->s, sa); 226 free(sa, M_SONAME); 227 } 228 return (error); 229 } 230 231 int 232 sys_listen(struct thread *td, struct listen_args *uap) 233 { 234 struct socket *so; 235 struct file *fp; 236 cap_rights_t rights; 237 int error; 238 239 AUDIT_ARG_FD(uap->s); 240 error = getsock_cap(td, uap->s, cap_rights_init(&rights, CAP_LISTEN), 241 &fp, NULL, NULL); 242 if (error == 0) { 243 so = fp->f_data; 244 #ifdef MAC 245 error = mac_socket_check_listen(td->td_ucred, so); 246 if (error == 0) 247 #endif 248 error = solisten(so, uap->backlog, td); 249 fdrop(fp, td); 250 } 251 return(error); 252 } 253 254 /* 255 * accept1() 256 */ 257 static int 258 accept1(td, s, uname, anamelen, flags) 259 struct thread *td; 260 int s; 261 struct sockaddr *uname; 262 socklen_t *anamelen; 263 int flags; 264 { 265 struct sockaddr *name; 266 socklen_t namelen; 267 struct file *fp; 268 int error; 269 270 if (uname == NULL) 271 return (kern_accept4(td, s, NULL, NULL, flags, NULL)); 272 273 error = copyin(anamelen, &namelen, sizeof (namelen)); 274 if (error != 0) 275 return (error); 276 277 error = kern_accept4(td, s, &name, &namelen, flags, &fp); 278 279 if (error != 0) 280 return (error); 281 282 if (error == 0 && uname != NULL) { 283 #ifdef COMPAT_OLDSOCK 284 if (flags & ACCEPT4_COMPAT) 285 ((struct osockaddr *)name)->sa_family = 286 name->sa_family; 287 #endif 288 error = copyout(name, uname, namelen); 289 } 290 if (error == 0) 291 error = copyout(&namelen, anamelen, 292 sizeof(namelen)); 293 if (error != 0) 294 fdclose(td, fp, td->td_retval[0]); 295 fdrop(fp, td); 296 free(name, M_SONAME); 297 return (error); 298 } 299 300 int 301 kern_accept(struct thread *td, int s, struct sockaddr **name, 302 socklen_t *namelen, struct file **fp) 303 { 304 return (kern_accept4(td, s, name, namelen, ACCEPT4_INHERIT, fp)); 305 } 306 307 int 308 kern_accept4(struct thread *td, int s, struct sockaddr **name, 309 socklen_t *namelen, int flags, struct file **fp) 310 { 311 struct file *headfp, *nfp = NULL; 312 struct sockaddr *sa = NULL; 313 struct socket *head, *so; 314 struct filecaps fcaps; 315 cap_rights_t rights; 316 u_int fflag; 317 pid_t pgid; 318 int error, fd, tmp; 319 320 if (name != NULL) 321 *name = NULL; 322 323 AUDIT_ARG_FD(s); 324 error = getsock_cap(td, s, cap_rights_init(&rights, CAP_ACCEPT), 325 &headfp, &fflag, &fcaps); 326 if (error != 0) 327 return (error); 328 head = headfp->f_data; 329 if ((head->so_options & SO_ACCEPTCONN) == 0) { 330 error = EINVAL; 331 goto done; 332 } 333 #ifdef MAC 334 error = mac_socket_check_accept(td->td_ucred, head); 335 if (error != 0) 336 goto done; 337 #endif 338 error = falloc_caps(td, &nfp, &fd, 339 (flags & SOCK_CLOEXEC) ? O_CLOEXEC : 0, &fcaps); 340 if (error != 0) 341 goto done; 342 ACCEPT_LOCK(); 343 if ((head->so_state & SS_NBIO) && TAILQ_EMPTY(&head->so_comp)) { 344 ACCEPT_UNLOCK(); 345 error = EWOULDBLOCK; 346 goto noconnection; 347 } 348 while (TAILQ_EMPTY(&head->so_comp) && head->so_error == 0) { 349 if (head->so_rcv.sb_state & SBS_CANTRCVMORE) { 350 head->so_error = ECONNABORTED; 351 break; 352 } 353 error = msleep(&head->so_timeo, &accept_mtx, PSOCK | PCATCH, 354 "accept", 0); 355 if (error != 0) { 356 ACCEPT_UNLOCK(); 357 goto noconnection; 358 } 359 } 360 if (head->so_error) { 361 error = head->so_error; 362 head->so_error = 0; 363 ACCEPT_UNLOCK(); 364 goto noconnection; 365 } 366 so = TAILQ_FIRST(&head->so_comp); 367 KASSERT(!(so->so_qstate & SQ_INCOMP), ("accept1: so SQ_INCOMP")); 368 KASSERT(so->so_qstate & SQ_COMP, ("accept1: so not SQ_COMP")); 369 370 /* 371 * Before changing the flags on the socket, we have to bump the 372 * reference count. Otherwise, if the protocol calls sofree(), 373 * the socket will be released due to a zero refcount. 374 */ 375 SOCK_LOCK(so); /* soref() and so_state update */ 376 soref(so); /* file descriptor reference */ 377 378 TAILQ_REMOVE(&head->so_comp, so, so_list); 379 head->so_qlen--; 380 if (flags & ACCEPT4_INHERIT) 381 so->so_state |= (head->so_state & SS_NBIO); 382 else 383 so->so_state |= (flags & SOCK_NONBLOCK) ? SS_NBIO : 0; 384 so->so_qstate &= ~SQ_COMP; 385 so->so_head = NULL; 386 387 SOCK_UNLOCK(so); 388 ACCEPT_UNLOCK(); 389 390 /* An extra reference on `nfp' has been held for us by falloc(). */ 391 td->td_retval[0] = fd; 392 393 /* connection has been removed from the listen queue */ 394 KNOTE_UNLOCKED(&head->so_rcv.sb_sel.si_note, 0); 395 396 if (flags & ACCEPT4_INHERIT) { 397 pgid = fgetown(&head->so_sigio); 398 if (pgid != 0) 399 fsetown(pgid, &so->so_sigio); 400 } else { 401 fflag &= ~(FNONBLOCK | FASYNC); 402 if (flags & SOCK_NONBLOCK) 403 fflag |= FNONBLOCK; 404 } 405 406 finit(nfp, fflag, DTYPE_SOCKET, so, &socketops); 407 /* Sync socket nonblocking/async state with file flags */ 408 tmp = fflag & FNONBLOCK; 409 (void) fo_ioctl(nfp, FIONBIO, &tmp, td->td_ucred, td); 410 tmp = fflag & FASYNC; 411 (void) fo_ioctl(nfp, FIOASYNC, &tmp, td->td_ucred, td); 412 sa = NULL; 413 error = soaccept(so, &sa); 414 if (error != 0) 415 goto noconnection; 416 if (sa == NULL) { 417 if (name) 418 *namelen = 0; 419 goto done; 420 } 421 AUDIT_ARG_SOCKADDR(td, AT_FDCWD, sa); 422 if (name) { 423 /* check sa_len before it is destroyed */ 424 if (*namelen > sa->sa_len) 425 *namelen = sa->sa_len; 426 #ifdef KTRACE 427 if (KTRPOINT(td, KTR_STRUCT)) 428 ktrsockaddr(sa); 429 #endif 430 *name = sa; 431 sa = NULL; 432 } 433 noconnection: 434 free(sa, M_SONAME); 435 436 /* 437 * close the new descriptor, assuming someone hasn't ripped it 438 * out from under us. 439 */ 440 if (error != 0) 441 fdclose(td, nfp, fd); 442 443 /* 444 * Release explicitly held references before returning. We return 445 * a reference on nfp to the caller on success if they request it. 446 */ 447 done: 448 if (nfp == NULL) 449 filecaps_free(&fcaps); 450 if (fp != NULL) { 451 if (error == 0) { 452 *fp = nfp; 453 nfp = NULL; 454 } else 455 *fp = NULL; 456 } 457 if (nfp != NULL) 458 fdrop(nfp, td); 459 fdrop(headfp, td); 460 return (error); 461 } 462 463 int 464 sys_accept(td, uap) 465 struct thread *td; 466 struct accept_args *uap; 467 { 468 469 return (accept1(td, uap->s, uap->name, uap->anamelen, ACCEPT4_INHERIT)); 470 } 471 472 int 473 sys_accept4(td, uap) 474 struct thread *td; 475 struct accept4_args *uap; 476 { 477 478 if (uap->flags & ~(SOCK_CLOEXEC | SOCK_NONBLOCK)) 479 return (EINVAL); 480 481 return (accept1(td, uap->s, uap->name, uap->anamelen, uap->flags)); 482 } 483 484 #ifdef COMPAT_OLDSOCK 485 int 486 oaccept(td, uap) 487 struct thread *td; 488 struct accept_args *uap; 489 { 490 491 return (accept1(td, uap->s, uap->name, uap->anamelen, 492 ACCEPT4_INHERIT | ACCEPT4_COMPAT)); 493 } 494 #endif /* COMPAT_OLDSOCK */ 495 496 int 497 sys_connect(struct thread *td, struct connect_args *uap) 498 { 499 struct sockaddr *sa; 500 int error; 501 502 error = getsockaddr(&sa, uap->name, uap->namelen); 503 if (error == 0) { 504 error = kern_connectat(td, AT_FDCWD, uap->s, sa); 505 free(sa, M_SONAME); 506 } 507 return (error); 508 } 509 510 int 511 kern_connectat(struct thread *td, int dirfd, int fd, struct sockaddr *sa) 512 { 513 struct socket *so; 514 struct file *fp; 515 cap_rights_t rights; 516 int error, interrupted = 0; 517 518 AUDIT_ARG_FD(fd); 519 AUDIT_ARG_SOCKADDR(td, dirfd, sa); 520 error = getsock_cap(td, fd, cap_rights_init(&rights, CAP_CONNECT), 521 &fp, NULL, NULL); 522 if (error != 0) 523 return (error); 524 so = fp->f_data; 525 if (so->so_state & SS_ISCONNECTING) { 526 error = EALREADY; 527 goto done1; 528 } 529 #ifdef KTRACE 530 if (KTRPOINT(td, KTR_STRUCT)) 531 ktrsockaddr(sa); 532 #endif 533 #ifdef MAC 534 error = mac_socket_check_connect(td->td_ucred, so, sa); 535 if (error != 0) 536 goto bad; 537 #endif 538 if (dirfd == AT_FDCWD) 539 error = soconnect(so, sa, td); 540 else 541 error = soconnectat(dirfd, so, sa, td); 542 if (error != 0) 543 goto bad; 544 if ((so->so_state & SS_NBIO) && (so->so_state & SS_ISCONNECTING)) { 545 error = EINPROGRESS; 546 goto done1; 547 } 548 SOCK_LOCK(so); 549 while ((so->so_state & SS_ISCONNECTING) && so->so_error == 0) { 550 error = msleep(&so->so_timeo, SOCK_MTX(so), PSOCK | PCATCH, 551 "connec", 0); 552 if (error != 0) { 553 if (error == EINTR || error == ERESTART) 554 interrupted = 1; 555 break; 556 } 557 } 558 if (error == 0) { 559 error = so->so_error; 560 so->so_error = 0; 561 } 562 SOCK_UNLOCK(so); 563 bad: 564 if (!interrupted) 565 so->so_state &= ~SS_ISCONNECTING; 566 if (error == ERESTART) 567 error = EINTR; 568 done1: 569 fdrop(fp, td); 570 return (error); 571 } 572 573 int 574 sys_connectat(struct thread *td, struct connectat_args *uap) 575 { 576 struct sockaddr *sa; 577 int error; 578 579 error = getsockaddr(&sa, uap->name, uap->namelen); 580 if (error == 0) { 581 error = kern_connectat(td, uap->fd, uap->s, sa); 582 free(sa, M_SONAME); 583 } 584 return (error); 585 } 586 587 int 588 kern_socketpair(struct thread *td, int domain, int type, int protocol, 589 int *rsv) 590 { 591 struct file *fp1, *fp2; 592 struct socket *so1, *so2; 593 int fd, error, oflag, fflag; 594 595 AUDIT_ARG_SOCKET(domain, type, protocol); 596 597 oflag = 0; 598 fflag = 0; 599 if ((type & SOCK_CLOEXEC) != 0) { 600 type &= ~SOCK_CLOEXEC; 601 oflag |= O_CLOEXEC; 602 } 603 if ((type & SOCK_NONBLOCK) != 0) { 604 type &= ~SOCK_NONBLOCK; 605 fflag |= FNONBLOCK; 606 } 607 #ifdef MAC 608 /* We might want to have a separate check for socket pairs. */ 609 error = mac_socket_check_create(td->td_ucred, domain, type, 610 protocol); 611 if (error != 0) 612 return (error); 613 #endif 614 error = socreate(domain, &so1, type, protocol, td->td_ucred, td); 615 if (error != 0) 616 return (error); 617 error = socreate(domain, &so2, type, protocol, td->td_ucred, td); 618 if (error != 0) 619 goto free1; 620 /* On success extra reference to `fp1' and 'fp2' is set by falloc. */ 621 error = falloc(td, &fp1, &fd, oflag); 622 if (error != 0) 623 goto free2; 624 rsv[0] = fd; 625 fp1->f_data = so1; /* so1 already has ref count */ 626 error = falloc(td, &fp2, &fd, oflag); 627 if (error != 0) 628 goto free3; 629 fp2->f_data = so2; /* so2 already has ref count */ 630 rsv[1] = fd; 631 error = soconnect2(so1, so2); 632 if (error != 0) 633 goto free4; 634 if (type == SOCK_DGRAM) { 635 /* 636 * Datagram socket connection is asymmetric. 637 */ 638 error = soconnect2(so2, so1); 639 if (error != 0) 640 goto free4; 641 } 642 finit(fp1, FREAD | FWRITE | fflag, DTYPE_SOCKET, fp1->f_data, 643 &socketops); 644 finit(fp2, FREAD | FWRITE | fflag, DTYPE_SOCKET, fp2->f_data, 645 &socketops); 646 if ((fflag & FNONBLOCK) != 0) { 647 (void) fo_ioctl(fp1, FIONBIO, &fflag, td->td_ucred, td); 648 (void) fo_ioctl(fp2, FIONBIO, &fflag, td->td_ucred, td); 649 } 650 fdrop(fp1, td); 651 fdrop(fp2, td); 652 return (0); 653 free4: 654 fdclose(td, fp2, rsv[1]); 655 fdrop(fp2, td); 656 free3: 657 fdclose(td, fp1, rsv[0]); 658 fdrop(fp1, td); 659 free2: 660 if (so2 != NULL) 661 (void)soclose(so2); 662 free1: 663 if (so1 != NULL) 664 (void)soclose(so1); 665 return (error); 666 } 667 668 int 669 sys_socketpair(struct thread *td, struct socketpair_args *uap) 670 { 671 int error, sv[2]; 672 673 error = kern_socketpair(td, uap->domain, uap->type, 674 uap->protocol, sv); 675 if (error != 0) 676 return (error); 677 error = copyout(sv, uap->rsv, 2 * sizeof(int)); 678 if (error != 0) { 679 (void)kern_close(td, sv[0]); 680 (void)kern_close(td, sv[1]); 681 } 682 return (error); 683 } 684 685 static int 686 sendit(struct thread *td, int s, struct msghdr *mp, int flags) 687 { 688 struct mbuf *control; 689 struct sockaddr *to; 690 int error; 691 692 #ifdef CAPABILITY_MODE 693 if (IN_CAPABILITY_MODE(td) && (mp->msg_name != NULL)) 694 return (ECAPMODE); 695 #endif 696 697 if (mp->msg_name != NULL) { 698 error = getsockaddr(&to, mp->msg_name, mp->msg_namelen); 699 if (error != 0) { 700 to = NULL; 701 goto bad; 702 } 703 mp->msg_name = to; 704 } else { 705 to = NULL; 706 } 707 708 if (mp->msg_control) { 709 if (mp->msg_controllen < sizeof(struct cmsghdr) 710 #ifdef COMPAT_OLDSOCK 711 && mp->msg_flags != MSG_COMPAT 712 #endif 713 ) { 714 error = EINVAL; 715 goto bad; 716 } 717 error = sockargs(&control, mp->msg_control, 718 mp->msg_controllen, MT_CONTROL); 719 if (error != 0) 720 goto bad; 721 #ifdef COMPAT_OLDSOCK 722 if (mp->msg_flags == MSG_COMPAT) { 723 struct cmsghdr *cm; 724 725 M_PREPEND(control, sizeof(*cm), M_WAITOK); 726 cm = mtod(control, struct cmsghdr *); 727 cm->cmsg_len = control->m_len; 728 cm->cmsg_level = SOL_SOCKET; 729 cm->cmsg_type = SCM_RIGHTS; 730 } 731 #endif 732 } else { 733 control = NULL; 734 } 735 736 error = kern_sendit(td, s, mp, flags, control, UIO_USERSPACE); 737 738 bad: 739 free(to, M_SONAME); 740 return (error); 741 } 742 743 int 744 kern_sendit(struct thread *td, int s, struct msghdr *mp, int flags, 745 struct mbuf *control, enum uio_seg segflg) 746 { 747 struct file *fp; 748 struct uio auio; 749 struct iovec *iov; 750 struct socket *so; 751 cap_rights_t rights; 752 #ifdef KTRACE 753 struct uio *ktruio = NULL; 754 #endif 755 ssize_t len; 756 int i, error; 757 758 AUDIT_ARG_FD(s); 759 cap_rights_init(&rights, CAP_SEND); 760 if (mp->msg_name != NULL) { 761 AUDIT_ARG_SOCKADDR(td, AT_FDCWD, mp->msg_name); 762 cap_rights_set(&rights, CAP_CONNECT); 763 } 764 error = getsock_cap(td, s, &rights, &fp, NULL, NULL); 765 if (error != 0) { 766 m_freem(control); 767 return (error); 768 } 769 so = (struct socket *)fp->f_data; 770 771 #ifdef KTRACE 772 if (mp->msg_name != NULL && KTRPOINT(td, KTR_STRUCT)) 773 ktrsockaddr(mp->msg_name); 774 #endif 775 #ifdef MAC 776 if (mp->msg_name != NULL) { 777 error = mac_socket_check_connect(td->td_ucred, so, 778 mp->msg_name); 779 if (error != 0) { 780 m_freem(control); 781 goto bad; 782 } 783 } 784 error = mac_socket_check_send(td->td_ucred, so); 785 if (error != 0) { 786 m_freem(control); 787 goto bad; 788 } 789 #endif 790 791 auio.uio_iov = mp->msg_iov; 792 auio.uio_iovcnt = mp->msg_iovlen; 793 auio.uio_segflg = segflg; 794 auio.uio_rw = UIO_WRITE; 795 auio.uio_td = td; 796 auio.uio_offset = 0; /* XXX */ 797 auio.uio_resid = 0; 798 iov = mp->msg_iov; 799 for (i = 0; i < mp->msg_iovlen; i++, iov++) { 800 if ((auio.uio_resid += iov->iov_len) < 0) { 801 error = EINVAL; 802 m_freem(control); 803 goto bad; 804 } 805 } 806 #ifdef KTRACE 807 if (KTRPOINT(td, KTR_GENIO)) 808 ktruio = cloneuio(&auio); 809 #endif 810 len = auio.uio_resid; 811 error = sosend(so, mp->msg_name, &auio, 0, control, flags, td); 812 if (error != 0) { 813 if (auio.uio_resid != len && (error == ERESTART || 814 error == EINTR || error == EWOULDBLOCK)) 815 error = 0; 816 /* Generation of SIGPIPE can be controlled per socket */ 817 if (error == EPIPE && !(so->so_options & SO_NOSIGPIPE) && 818 !(flags & MSG_NOSIGNAL)) { 819 PROC_LOCK(td->td_proc); 820 tdsignal(td, SIGPIPE); 821 PROC_UNLOCK(td->td_proc); 822 } 823 } 824 if (error == 0) 825 td->td_retval[0] = len - auio.uio_resid; 826 #ifdef KTRACE 827 if (ktruio != NULL) { 828 ktruio->uio_resid = td->td_retval[0]; 829 ktrgenio(s, UIO_WRITE, ktruio, error); 830 } 831 #endif 832 bad: 833 fdrop(fp, td); 834 return (error); 835 } 836 837 int 838 sys_sendto(struct thread *td, struct sendto_args *uap) 839 { 840 struct msghdr msg; 841 struct iovec aiov; 842 843 msg.msg_name = uap->to; 844 msg.msg_namelen = uap->tolen; 845 msg.msg_iov = &aiov; 846 msg.msg_iovlen = 1; 847 msg.msg_control = 0; 848 #ifdef COMPAT_OLDSOCK 849 msg.msg_flags = 0; 850 #endif 851 aiov.iov_base = uap->buf; 852 aiov.iov_len = uap->len; 853 return (sendit(td, uap->s, &msg, uap->flags)); 854 } 855 856 #ifdef COMPAT_OLDSOCK 857 int 858 osend(struct thread *td, struct osend_args *uap) 859 { 860 struct msghdr msg; 861 struct iovec aiov; 862 863 msg.msg_name = 0; 864 msg.msg_namelen = 0; 865 msg.msg_iov = &aiov; 866 msg.msg_iovlen = 1; 867 aiov.iov_base = uap->buf; 868 aiov.iov_len = uap->len; 869 msg.msg_control = 0; 870 msg.msg_flags = 0; 871 return (sendit(td, uap->s, &msg, uap->flags)); 872 } 873 874 int 875 osendmsg(struct thread *td, struct osendmsg_args *uap) 876 { 877 struct msghdr msg; 878 struct iovec *iov; 879 int error; 880 881 error = copyin(uap->msg, &msg, sizeof (struct omsghdr)); 882 if (error != 0) 883 return (error); 884 error = copyiniov(msg.msg_iov, msg.msg_iovlen, &iov, EMSGSIZE); 885 if (error != 0) 886 return (error); 887 msg.msg_iov = iov; 888 msg.msg_flags = MSG_COMPAT; 889 error = sendit(td, uap->s, &msg, uap->flags); 890 free(iov, M_IOV); 891 return (error); 892 } 893 #endif 894 895 int 896 sys_sendmsg(struct thread *td, struct sendmsg_args *uap) 897 { 898 struct msghdr msg; 899 struct iovec *iov; 900 int error; 901 902 error = copyin(uap->msg, &msg, sizeof (msg)); 903 if (error != 0) 904 return (error); 905 error = copyiniov(msg.msg_iov, msg.msg_iovlen, &iov, EMSGSIZE); 906 if (error != 0) 907 return (error); 908 msg.msg_iov = iov; 909 #ifdef COMPAT_OLDSOCK 910 msg.msg_flags = 0; 911 #endif 912 error = sendit(td, uap->s, &msg, uap->flags); 913 free(iov, M_IOV); 914 return (error); 915 } 916 917 int 918 kern_recvit(struct thread *td, int s, struct msghdr *mp, enum uio_seg fromseg, 919 struct mbuf **controlp) 920 { 921 struct uio auio; 922 struct iovec *iov; 923 struct mbuf *m, *control = NULL; 924 caddr_t ctlbuf; 925 struct file *fp; 926 struct socket *so; 927 struct sockaddr *fromsa = NULL; 928 cap_rights_t rights; 929 #ifdef KTRACE 930 struct uio *ktruio = NULL; 931 #endif 932 ssize_t len; 933 int error, i; 934 935 if (controlp != NULL) 936 *controlp = NULL; 937 938 AUDIT_ARG_FD(s); 939 error = getsock_cap(td, s, cap_rights_init(&rights, CAP_RECV), 940 &fp, NULL, NULL); 941 if (error != 0) 942 return (error); 943 so = fp->f_data; 944 945 #ifdef MAC 946 error = mac_socket_check_receive(td->td_ucred, so); 947 if (error != 0) { 948 fdrop(fp, td); 949 return (error); 950 } 951 #endif 952 953 auio.uio_iov = mp->msg_iov; 954 auio.uio_iovcnt = mp->msg_iovlen; 955 auio.uio_segflg = UIO_USERSPACE; 956 auio.uio_rw = UIO_READ; 957 auio.uio_td = td; 958 auio.uio_offset = 0; /* XXX */ 959 auio.uio_resid = 0; 960 iov = mp->msg_iov; 961 for (i = 0; i < mp->msg_iovlen; i++, iov++) { 962 if ((auio.uio_resid += iov->iov_len) < 0) { 963 fdrop(fp, td); 964 return (EINVAL); 965 } 966 } 967 #ifdef KTRACE 968 if (KTRPOINT(td, KTR_GENIO)) 969 ktruio = cloneuio(&auio); 970 #endif 971 len = auio.uio_resid; 972 error = soreceive(so, &fromsa, &auio, NULL, 973 (mp->msg_control || controlp) ? &control : NULL, 974 &mp->msg_flags); 975 if (error != 0) { 976 if (auio.uio_resid != len && (error == ERESTART || 977 error == EINTR || error == EWOULDBLOCK)) 978 error = 0; 979 } 980 if (fromsa != NULL) 981 AUDIT_ARG_SOCKADDR(td, AT_FDCWD, fromsa); 982 #ifdef KTRACE 983 if (ktruio != NULL) { 984 ktruio->uio_resid = len - auio.uio_resid; 985 ktrgenio(s, UIO_READ, ktruio, error); 986 } 987 #endif 988 if (error != 0) 989 goto out; 990 td->td_retval[0] = len - auio.uio_resid; 991 if (mp->msg_name) { 992 len = mp->msg_namelen; 993 if (len <= 0 || fromsa == NULL) 994 len = 0; 995 else { 996 /* save sa_len before it is destroyed by MSG_COMPAT */ 997 len = MIN(len, fromsa->sa_len); 998 #ifdef COMPAT_OLDSOCK 999 if (mp->msg_flags & MSG_COMPAT) 1000 ((struct osockaddr *)fromsa)->sa_family = 1001 fromsa->sa_family; 1002 #endif 1003 if (fromseg == UIO_USERSPACE) { 1004 error = copyout(fromsa, mp->msg_name, 1005 (unsigned)len); 1006 if (error != 0) 1007 goto out; 1008 } else 1009 bcopy(fromsa, mp->msg_name, len); 1010 } 1011 mp->msg_namelen = len; 1012 } 1013 if (mp->msg_control && controlp == NULL) { 1014 #ifdef COMPAT_OLDSOCK 1015 /* 1016 * We assume that old recvmsg calls won't receive access 1017 * rights and other control info, esp. as control info 1018 * is always optional and those options didn't exist in 4.3. 1019 * If we receive rights, trim the cmsghdr; anything else 1020 * is tossed. 1021 */ 1022 if (control && mp->msg_flags & MSG_COMPAT) { 1023 if (mtod(control, struct cmsghdr *)->cmsg_level != 1024 SOL_SOCKET || 1025 mtod(control, struct cmsghdr *)->cmsg_type != 1026 SCM_RIGHTS) { 1027 mp->msg_controllen = 0; 1028 goto out; 1029 } 1030 control->m_len -= sizeof (struct cmsghdr); 1031 control->m_data += sizeof (struct cmsghdr); 1032 } 1033 #endif 1034 len = mp->msg_controllen; 1035 m = control; 1036 mp->msg_controllen = 0; 1037 ctlbuf = mp->msg_control; 1038 1039 while (m && len > 0) { 1040 unsigned int tocopy; 1041 1042 if (len >= m->m_len) 1043 tocopy = m->m_len; 1044 else { 1045 mp->msg_flags |= MSG_CTRUNC; 1046 tocopy = len; 1047 } 1048 1049 if ((error = copyout(mtod(m, caddr_t), 1050 ctlbuf, tocopy)) != 0) 1051 goto out; 1052 1053 ctlbuf += tocopy; 1054 len -= tocopy; 1055 m = m->m_next; 1056 } 1057 mp->msg_controllen = ctlbuf - (caddr_t)mp->msg_control; 1058 } 1059 out: 1060 fdrop(fp, td); 1061 #ifdef KTRACE 1062 if (fromsa && KTRPOINT(td, KTR_STRUCT)) 1063 ktrsockaddr(fromsa); 1064 #endif 1065 free(fromsa, M_SONAME); 1066 1067 if (error == 0 && controlp != NULL) 1068 *controlp = control; 1069 else if (control) 1070 m_freem(control); 1071 1072 return (error); 1073 } 1074 1075 static int 1076 recvit(struct thread *td, int s, struct msghdr *mp, void *namelenp) 1077 { 1078 int error; 1079 1080 error = kern_recvit(td, s, mp, UIO_USERSPACE, NULL); 1081 if (error != 0) 1082 return (error); 1083 if (namelenp != NULL) { 1084 error = copyout(&mp->msg_namelen, namelenp, sizeof (socklen_t)); 1085 #ifdef COMPAT_OLDSOCK 1086 if (mp->msg_flags & MSG_COMPAT) 1087 error = 0; /* old recvfrom didn't check */ 1088 #endif 1089 } 1090 return (error); 1091 } 1092 1093 int 1094 sys_recvfrom(struct thread *td, struct recvfrom_args *uap) 1095 { 1096 struct msghdr msg; 1097 struct iovec aiov; 1098 int error; 1099 1100 if (uap->fromlenaddr) { 1101 error = copyin(uap->fromlenaddr, 1102 &msg.msg_namelen, sizeof (msg.msg_namelen)); 1103 if (error != 0) 1104 goto done2; 1105 } else { 1106 msg.msg_namelen = 0; 1107 } 1108 msg.msg_name = uap->from; 1109 msg.msg_iov = &aiov; 1110 msg.msg_iovlen = 1; 1111 aiov.iov_base = uap->buf; 1112 aiov.iov_len = uap->len; 1113 msg.msg_control = 0; 1114 msg.msg_flags = uap->flags; 1115 error = recvit(td, uap->s, &msg, uap->fromlenaddr); 1116 done2: 1117 return (error); 1118 } 1119 1120 #ifdef COMPAT_OLDSOCK 1121 int 1122 orecvfrom(struct thread *td, struct recvfrom_args *uap) 1123 { 1124 1125 uap->flags |= MSG_COMPAT; 1126 return (sys_recvfrom(td, uap)); 1127 } 1128 #endif 1129 1130 #ifdef COMPAT_OLDSOCK 1131 int 1132 orecv(struct thread *td, struct orecv_args *uap) 1133 { 1134 struct msghdr msg; 1135 struct iovec aiov; 1136 1137 msg.msg_name = 0; 1138 msg.msg_namelen = 0; 1139 msg.msg_iov = &aiov; 1140 msg.msg_iovlen = 1; 1141 aiov.iov_base = uap->buf; 1142 aiov.iov_len = uap->len; 1143 msg.msg_control = 0; 1144 msg.msg_flags = uap->flags; 1145 return (recvit(td, uap->s, &msg, NULL)); 1146 } 1147 1148 /* 1149 * Old recvmsg. This code takes advantage of the fact that the old msghdr 1150 * overlays the new one, missing only the flags, and with the (old) access 1151 * rights where the control fields are now. 1152 */ 1153 int 1154 orecvmsg(struct thread *td, struct orecvmsg_args *uap) 1155 { 1156 struct msghdr msg; 1157 struct iovec *iov; 1158 int error; 1159 1160 error = copyin(uap->msg, &msg, sizeof (struct omsghdr)); 1161 if (error != 0) 1162 return (error); 1163 error = copyiniov(msg.msg_iov, msg.msg_iovlen, &iov, EMSGSIZE); 1164 if (error != 0) 1165 return (error); 1166 msg.msg_flags = uap->flags | MSG_COMPAT; 1167 msg.msg_iov = iov; 1168 error = recvit(td, uap->s, &msg, &uap->msg->msg_namelen); 1169 if (msg.msg_controllen && error == 0) 1170 error = copyout(&msg.msg_controllen, 1171 &uap->msg->msg_accrightslen, sizeof (int)); 1172 free(iov, M_IOV); 1173 return (error); 1174 } 1175 #endif 1176 1177 int 1178 sys_recvmsg(struct thread *td, struct recvmsg_args *uap) 1179 { 1180 struct msghdr msg; 1181 struct iovec *uiov, *iov; 1182 int error; 1183 1184 error = copyin(uap->msg, &msg, sizeof (msg)); 1185 if (error != 0) 1186 return (error); 1187 error = copyiniov(msg.msg_iov, msg.msg_iovlen, &iov, EMSGSIZE); 1188 if (error != 0) 1189 return (error); 1190 msg.msg_flags = uap->flags; 1191 #ifdef COMPAT_OLDSOCK 1192 msg.msg_flags &= ~MSG_COMPAT; 1193 #endif 1194 uiov = msg.msg_iov; 1195 msg.msg_iov = iov; 1196 error = recvit(td, uap->s, &msg, NULL); 1197 if (error == 0) { 1198 msg.msg_iov = uiov; 1199 error = copyout(&msg, uap->msg, sizeof(msg)); 1200 } 1201 free(iov, M_IOV); 1202 return (error); 1203 } 1204 1205 int 1206 sys_shutdown(struct thread *td, struct shutdown_args *uap) 1207 { 1208 struct socket *so; 1209 struct file *fp; 1210 cap_rights_t rights; 1211 int error; 1212 1213 AUDIT_ARG_FD(uap->s); 1214 error = getsock_cap(td, uap->s, cap_rights_init(&rights, CAP_SHUTDOWN), 1215 &fp, NULL, NULL); 1216 if (error == 0) { 1217 so = fp->f_data; 1218 error = soshutdown(so, uap->how); 1219 /* 1220 * Previous versions did not return ENOTCONN, but 0 in 1221 * case the socket was not connected. Some important 1222 * programs like syslogd up to r279016, 2015-02-19, 1223 * still depend on this behavior. 1224 */ 1225 if (error == ENOTCONN && 1226 td->td_proc->p_osrel < P_OSREL_SHUTDOWN_ENOTCONN) 1227 error = 0; 1228 fdrop(fp, td); 1229 } 1230 return (error); 1231 } 1232 1233 int 1234 sys_setsockopt(struct thread *td, struct setsockopt_args *uap) 1235 { 1236 1237 return (kern_setsockopt(td, uap->s, uap->level, uap->name, 1238 uap->val, UIO_USERSPACE, uap->valsize)); 1239 } 1240 1241 int 1242 kern_setsockopt(struct thread *td, int s, int level, int name, void *val, 1243 enum uio_seg valseg, socklen_t valsize) 1244 { 1245 struct socket *so; 1246 struct file *fp; 1247 struct sockopt sopt; 1248 cap_rights_t rights; 1249 int error; 1250 1251 if (val == NULL && valsize != 0) 1252 return (EFAULT); 1253 if ((int)valsize < 0) 1254 return (EINVAL); 1255 1256 sopt.sopt_dir = SOPT_SET; 1257 sopt.sopt_level = level; 1258 sopt.sopt_name = name; 1259 sopt.sopt_val = val; 1260 sopt.sopt_valsize = valsize; 1261 switch (valseg) { 1262 case UIO_USERSPACE: 1263 sopt.sopt_td = td; 1264 break; 1265 case UIO_SYSSPACE: 1266 sopt.sopt_td = NULL; 1267 break; 1268 default: 1269 panic("kern_setsockopt called with bad valseg"); 1270 } 1271 1272 AUDIT_ARG_FD(s); 1273 error = getsock_cap(td, s, cap_rights_init(&rights, CAP_SETSOCKOPT), 1274 &fp, NULL, NULL); 1275 if (error == 0) { 1276 so = fp->f_data; 1277 error = sosetopt(so, &sopt); 1278 fdrop(fp, td); 1279 } 1280 return(error); 1281 } 1282 1283 int 1284 sys_getsockopt(struct thread *td, struct getsockopt_args *uap) 1285 { 1286 socklen_t valsize; 1287 int error; 1288 1289 if (uap->val) { 1290 error = copyin(uap->avalsize, &valsize, sizeof (valsize)); 1291 if (error != 0) 1292 return (error); 1293 } 1294 1295 error = kern_getsockopt(td, uap->s, uap->level, uap->name, 1296 uap->val, UIO_USERSPACE, &valsize); 1297 1298 if (error == 0) 1299 error = copyout(&valsize, uap->avalsize, sizeof (valsize)); 1300 return (error); 1301 } 1302 1303 /* 1304 * Kernel version of getsockopt. 1305 * optval can be a userland or userspace. optlen is always a kernel pointer. 1306 */ 1307 int 1308 kern_getsockopt(struct thread *td, int s, int level, int name, void *val, 1309 enum uio_seg valseg, socklen_t *valsize) 1310 { 1311 struct socket *so; 1312 struct file *fp; 1313 struct sockopt sopt; 1314 cap_rights_t rights; 1315 int error; 1316 1317 if (val == NULL) 1318 *valsize = 0; 1319 if ((int)*valsize < 0) 1320 return (EINVAL); 1321 1322 sopt.sopt_dir = SOPT_GET; 1323 sopt.sopt_level = level; 1324 sopt.sopt_name = name; 1325 sopt.sopt_val = val; 1326 sopt.sopt_valsize = (size_t)*valsize; /* checked non-negative above */ 1327 switch (valseg) { 1328 case UIO_USERSPACE: 1329 sopt.sopt_td = td; 1330 break; 1331 case UIO_SYSSPACE: 1332 sopt.sopt_td = NULL; 1333 break; 1334 default: 1335 panic("kern_getsockopt called with bad valseg"); 1336 } 1337 1338 AUDIT_ARG_FD(s); 1339 error = getsock_cap(td, s, cap_rights_init(&rights, CAP_GETSOCKOPT), 1340 &fp, NULL, NULL); 1341 if (error == 0) { 1342 so = fp->f_data; 1343 error = sogetopt(so, &sopt); 1344 *valsize = sopt.sopt_valsize; 1345 fdrop(fp, td); 1346 } 1347 return (error); 1348 } 1349 1350 /* 1351 * getsockname1() - Get socket name. 1352 */ 1353 static int 1354 getsockname1(struct thread *td, struct getsockname_args *uap, int compat) 1355 { 1356 struct sockaddr *sa; 1357 socklen_t len; 1358 int error; 1359 1360 error = copyin(uap->alen, &len, sizeof(len)); 1361 if (error != 0) 1362 return (error); 1363 1364 error = kern_getsockname(td, uap->fdes, &sa, &len); 1365 if (error != 0) 1366 return (error); 1367 1368 if (len != 0) { 1369 #ifdef COMPAT_OLDSOCK 1370 if (compat) 1371 ((struct osockaddr *)sa)->sa_family = sa->sa_family; 1372 #endif 1373 error = copyout(sa, uap->asa, (u_int)len); 1374 } 1375 free(sa, M_SONAME); 1376 if (error == 0) 1377 error = copyout(&len, uap->alen, sizeof(len)); 1378 return (error); 1379 } 1380 1381 int 1382 kern_getsockname(struct thread *td, int fd, struct sockaddr **sa, 1383 socklen_t *alen) 1384 { 1385 struct socket *so; 1386 struct file *fp; 1387 cap_rights_t rights; 1388 socklen_t len; 1389 int error; 1390 1391 AUDIT_ARG_FD(fd); 1392 error = getsock_cap(td, fd, cap_rights_init(&rights, CAP_GETSOCKNAME), 1393 &fp, NULL, NULL); 1394 if (error != 0) 1395 return (error); 1396 so = fp->f_data; 1397 *sa = NULL; 1398 CURVNET_SET(so->so_vnet); 1399 error = (*so->so_proto->pr_usrreqs->pru_sockaddr)(so, sa); 1400 CURVNET_RESTORE(); 1401 if (error != 0) 1402 goto bad; 1403 if (*sa == NULL) 1404 len = 0; 1405 else 1406 len = MIN(*alen, (*sa)->sa_len); 1407 *alen = len; 1408 #ifdef KTRACE 1409 if (KTRPOINT(td, KTR_STRUCT)) 1410 ktrsockaddr(*sa); 1411 #endif 1412 bad: 1413 fdrop(fp, td); 1414 if (error != 0 && *sa != NULL) { 1415 free(*sa, M_SONAME); 1416 *sa = NULL; 1417 } 1418 return (error); 1419 } 1420 1421 int 1422 sys_getsockname(struct thread *td, struct getsockname_args *uap) 1423 { 1424 1425 return (getsockname1(td, uap, 0)); 1426 } 1427 1428 #ifdef COMPAT_OLDSOCK 1429 int 1430 ogetsockname(struct thread *td, struct getsockname_args *uap) 1431 { 1432 1433 return (getsockname1(td, uap, 1)); 1434 } 1435 #endif /* COMPAT_OLDSOCK */ 1436 1437 /* 1438 * getpeername1() - Get name of peer for connected socket. 1439 */ 1440 static int 1441 getpeername1(struct thread *td, struct getpeername_args *uap, int compat) 1442 { 1443 struct sockaddr *sa; 1444 socklen_t len; 1445 int error; 1446 1447 error = copyin(uap->alen, &len, sizeof (len)); 1448 if (error != 0) 1449 return (error); 1450 1451 error = kern_getpeername(td, uap->fdes, &sa, &len); 1452 if (error != 0) 1453 return (error); 1454 1455 if (len != 0) { 1456 #ifdef COMPAT_OLDSOCK 1457 if (compat) 1458 ((struct osockaddr *)sa)->sa_family = sa->sa_family; 1459 #endif 1460 error = copyout(sa, uap->asa, (u_int)len); 1461 } 1462 free(sa, M_SONAME); 1463 if (error == 0) 1464 error = copyout(&len, uap->alen, sizeof(len)); 1465 return (error); 1466 } 1467 1468 int 1469 kern_getpeername(struct thread *td, int fd, struct sockaddr **sa, 1470 socklen_t *alen) 1471 { 1472 struct socket *so; 1473 struct file *fp; 1474 cap_rights_t rights; 1475 socklen_t len; 1476 int error; 1477 1478 AUDIT_ARG_FD(fd); 1479 error = getsock_cap(td, fd, cap_rights_init(&rights, CAP_GETPEERNAME), 1480 &fp, NULL, NULL); 1481 if (error != 0) 1482 return (error); 1483 so = fp->f_data; 1484 if ((so->so_state & (SS_ISCONNECTED|SS_ISCONFIRMING)) == 0) { 1485 error = ENOTCONN; 1486 goto done; 1487 } 1488 *sa = NULL; 1489 CURVNET_SET(so->so_vnet); 1490 error = (*so->so_proto->pr_usrreqs->pru_peeraddr)(so, sa); 1491 CURVNET_RESTORE(); 1492 if (error != 0) 1493 goto bad; 1494 if (*sa == NULL) 1495 len = 0; 1496 else 1497 len = MIN(*alen, (*sa)->sa_len); 1498 *alen = len; 1499 #ifdef KTRACE 1500 if (KTRPOINT(td, KTR_STRUCT)) 1501 ktrsockaddr(*sa); 1502 #endif 1503 bad: 1504 if (error != 0 && *sa != NULL) { 1505 free(*sa, M_SONAME); 1506 *sa = NULL; 1507 } 1508 done: 1509 fdrop(fp, td); 1510 return (error); 1511 } 1512 1513 int 1514 sys_getpeername(struct thread *td, struct getpeername_args *uap) 1515 { 1516 1517 return (getpeername1(td, uap, 0)); 1518 } 1519 1520 #ifdef COMPAT_OLDSOCK 1521 int 1522 ogetpeername(struct thread *td, struct ogetpeername_args *uap) 1523 { 1524 1525 /* XXX uap should have type `getpeername_args *' to begin with. */ 1526 return (getpeername1(td, (struct getpeername_args *)uap, 1)); 1527 } 1528 #endif /* COMPAT_OLDSOCK */ 1529 1530 static int 1531 sockargs(struct mbuf **mp, char *buf, socklen_t buflen, int type) 1532 { 1533 struct sockaddr *sa; 1534 struct mbuf *m; 1535 int error; 1536 1537 if (buflen > MLEN) { 1538 #ifdef COMPAT_OLDSOCK 1539 if (type == MT_SONAME && buflen <= 112) 1540 buflen = MLEN; /* unix domain compat. hack */ 1541 else 1542 #endif 1543 if (buflen > MCLBYTES) 1544 return (EINVAL); 1545 } 1546 m = m_get2(buflen, M_WAITOK, type, 0); 1547 m->m_len = buflen; 1548 error = copyin(buf, mtod(m, void *), buflen); 1549 if (error != 0) 1550 (void) m_free(m); 1551 else { 1552 *mp = m; 1553 if (type == MT_SONAME) { 1554 sa = mtod(m, struct sockaddr *); 1555 1556 #if defined(COMPAT_OLDSOCK) && BYTE_ORDER != BIG_ENDIAN 1557 if (sa->sa_family == 0 && sa->sa_len < AF_MAX) 1558 sa->sa_family = sa->sa_len; 1559 #endif 1560 sa->sa_len = buflen; 1561 } 1562 } 1563 return (error); 1564 } 1565 1566 int 1567 getsockaddr(struct sockaddr **namp, caddr_t uaddr, size_t len) 1568 { 1569 struct sockaddr *sa; 1570 int error; 1571 1572 if (len > SOCK_MAXADDRLEN) 1573 return (ENAMETOOLONG); 1574 if (len < offsetof(struct sockaddr, sa_data[0])) 1575 return (EINVAL); 1576 sa = malloc(len, M_SONAME, M_WAITOK); 1577 error = copyin(uaddr, sa, len); 1578 if (error != 0) { 1579 free(sa, M_SONAME); 1580 } else { 1581 #if defined(COMPAT_OLDSOCK) && BYTE_ORDER != BIG_ENDIAN 1582 if (sa->sa_family == 0 && sa->sa_len < AF_MAX) 1583 sa->sa_family = sa->sa_len; 1584 #endif 1585 sa->sa_len = len; 1586 *namp = sa; 1587 } 1588 return (error); 1589 } 1590