svr4_stream.c revision 263233
1/*- 2 * Copyright (c) 1998 Mark Newton. All rights reserved. 3 * Copyright (c) 1994, 1996 Christos Zoulas. 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. All advertising materials mentioning features or use of this software 14 * must display the following acknowledgement: 15 * This product includes software developed by Christos Zoulas. 16 * 4. The name of the author may not be used to endorse or promote products 17 * derived from this software without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 20 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 21 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 22 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 23 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 24 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 */ 30 31/* 32 * Pretend that we have streams... 33 * Yes, this is gross. 34 * 35 * ToDo: The state machine for getmsg needs re-thinking 36 */ 37 38#include <sys/cdefs.h> 39__FBSDID("$FreeBSD: head/sys/compat/svr4/svr4_stream.c 263233 2014-03-16 10:55:57Z rwatson $"); 40 41#include "opt_compat.h" 42#include "opt_ktrace.h" 43 44#include <sys/param.h> 45#include <sys/systm.h> 46#include <sys/capsicum.h> 47#include <sys/fcntl.h> 48#include <sys/filedesc.h> 49#include <sys/filio.h> 50#include <sys/lock.h> 51#include <sys/malloc.h> 52#include <sys/file.h> /* Must come after sys/malloc.h */ 53#include <sys/mbuf.h> 54#include <sys/mutex.h> 55#include <sys/proc.h> 56#include <sys/protosw.h> 57#include <sys/signal.h> 58#include <sys/signalvar.h> 59#include <sys/socket.h> 60#include <sys/socketvar.h> 61#include <sys/stat.h> 62#include <sys/syscallsubr.h> 63#include <sys/sysproto.h> 64#include <sys/uio.h> 65#include <sys/ktrace.h> /* Must come after sys/uio.h */ 66#include <sys/un.h> 67 68#include <netinet/in.h> 69 70#include <compat/svr4/svr4.h> 71#include <compat/svr4/svr4_types.h> 72#include <compat/svr4/svr4_util.h> 73#include <compat/svr4/svr4_signal.h> 74#include <compat/svr4/svr4_proto.h> 75#include <compat/svr4/svr4_stropts.h> 76#include <compat/svr4/svr4_timod.h> 77#include <compat/svr4/svr4_sockmod.h> 78#include <compat/svr4/svr4_ioctl.h> 79#include <compat/svr4/svr4_socket.h> 80 81/* Utils */ 82static int clean_pipe(struct thread *, char *); 83static void getparm(struct file *, struct svr4_si_sockparms *); 84static int svr4_do_putmsg(struct thread *, struct svr4_sys_putmsg_args *, 85 struct file *); 86static int svr4_do_getmsg(struct thread *, struct svr4_sys_getmsg_args *, 87 struct file *); 88 89/* Address Conversions */ 90static void sockaddr_to_netaddr_in(struct svr4_strmcmd *, 91 const struct sockaddr_in *); 92static void sockaddr_to_netaddr_un(struct svr4_strmcmd *, 93 const struct sockaddr_un *); 94static void netaddr_to_sockaddr_in(struct sockaddr_in *, 95 const struct svr4_strmcmd *); 96static void netaddr_to_sockaddr_un(struct sockaddr_un *, 97 const struct svr4_strmcmd *); 98 99/* stream ioctls */ 100static int i_nread(struct file *, struct thread *, register_t *, int, 101 u_long, caddr_t); 102static int i_fdinsert(struct file *, struct thread *, register_t *, int, 103 u_long, caddr_t); 104static int i_str(struct file *, struct thread *, register_t *, int, 105 u_long, caddr_t); 106static int i_setsig(struct file *, struct thread *, register_t *, int, 107 u_long, caddr_t); 108static int i_getsig(struct file *, struct thread *, register_t *, int, 109 u_long, caddr_t); 110static int _i_bind_rsvd(struct file *, struct thread *, register_t *, int, 111 u_long, caddr_t); 112static int _i_rele_rsvd(struct file *, struct thread *, register_t *, int, 113 u_long, caddr_t); 114 115/* i_str sockmod calls */ 116static int sockmod(struct file *, int, struct svr4_strioctl *, 117 struct thread *); 118static int si_listen(struct file *, int, struct svr4_strioctl *, 119 struct thread *); 120static int si_ogetudata(struct file *, int, struct svr4_strioctl *, 121 struct thread *); 122static int si_sockparams(struct file *, int, struct svr4_strioctl *, 123 struct thread *); 124static int si_shutdown (struct file *, int, struct svr4_strioctl *, 125 struct thread *); 126static int si_getudata(struct file *, int, struct svr4_strioctl *, 127 struct thread *); 128 129/* i_str timod calls */ 130static int timod(struct file *, int, struct svr4_strioctl *, struct thread *); 131static int ti_getinfo(struct file *, int, struct svr4_strioctl *, 132 struct thread *); 133static int ti_bind(struct file *, int, struct svr4_strioctl *, struct thread *); 134 135#ifdef DEBUG_SVR4 136static void bufprint(u_char *, size_t); 137static int show_ioc(const char *, struct svr4_strioctl *); 138static int show_strbuf(struct svr4_strbuf *); 139static void show_msg(const char *, int, struct svr4_strbuf *, 140 struct svr4_strbuf *, int); 141 142static void 143bufprint(buf, len) 144 u_char *buf; 145 size_t len; 146{ 147 size_t i; 148 149 uprintf("\n\t"); 150 for (i = 0; i < len; i++) { 151 uprintf("%x ", buf[i]); 152 if (i && (i % 16) == 0) 153 uprintf("\n\t"); 154 } 155} 156 157static int 158show_ioc(str, ioc) 159 const char *str; 160 struct svr4_strioctl *ioc; 161{ 162 u_char *ptr = NULL; 163 int len; 164 int error; 165 166 len = ioc->len; 167 if (len > 1024) 168 len = 1024; 169 170 if (len > 0) { 171 ptr = (u_char *) malloc(len, M_TEMP, M_WAITOK); 172 if ((error = copyin(ioc->buf, ptr, len)) != 0) { 173 free((char *) ptr, M_TEMP); 174 return error; 175 } 176 } 177 178 uprintf("%s cmd = %ld, timeout = %d, len = %d, buf = %p { ", 179 str, ioc->cmd, ioc->timeout, ioc->len, ioc->buf); 180 181 if (ptr != NULL) 182 bufprint(ptr, len); 183 184 uprintf("}\n"); 185 186 if (ptr != NULL) 187 free((char *) ptr, M_TEMP); 188 return 0; 189} 190 191 192static int 193show_strbuf(str) 194 struct svr4_strbuf *str; 195{ 196 int error; 197 u_char *ptr = NULL; 198 int maxlen = str->maxlen; 199 int len = str->len; 200 201 if (maxlen > 8192) 202 maxlen = 8192; 203 204 if (maxlen < 0) 205 maxlen = 0; 206 207 if (len >= maxlen) 208 len = maxlen; 209 210 if (len > 0) { 211 ptr = (u_char *) malloc(len, M_TEMP, M_WAITOK); 212 213 if ((error = copyin(str->buf, ptr, len)) != 0) { 214 free((char *) ptr, M_TEMP); 215 return error; 216 } 217 } 218 219 uprintf(", { %d, %d, %p=[ ", str->maxlen, str->len, str->buf); 220 221 if (ptr) 222 bufprint(ptr, len); 223 224 uprintf("]}"); 225 226 if (ptr) 227 free((char *) ptr, M_TEMP); 228 229 return 0; 230} 231 232 233static void 234show_msg(str, fd, ctl, dat, flags) 235 const char *str; 236 int fd; 237 struct svr4_strbuf *ctl; 238 struct svr4_strbuf *dat; 239 int flags; 240{ 241 struct svr4_strbuf buf; 242 int error; 243 244 uprintf("%s(%d", str, fd); 245 if (ctl != NULL) { 246 if ((error = copyin(ctl, &buf, sizeof(buf))) != 0) 247 return; 248 show_strbuf(&buf); 249 } 250 else 251 uprintf(", NULL"); 252 253 if (dat != NULL) { 254 if ((error = copyin(dat, &buf, sizeof(buf))) != 0) 255 return; 256 show_strbuf(&buf); 257 } 258 else 259 uprintf(", NULL"); 260 261 uprintf(", %x);\n", flags); 262} 263 264#endif /* DEBUG_SVR4 */ 265 266/* 267 * We are faced with an interesting situation. On svr4 unix sockets 268 * are really pipes. But we really have sockets, and we might as 269 * well use them. At the point where svr4 calls TI_BIND, it has 270 * already created a named pipe for the socket using mknod(2). 271 * We need to create a socket with the same name when we bind, 272 * so we need to remove the pipe before, otherwise we'll get address 273 * already in use. So we *carefully* remove the pipe, to avoid 274 * using this as a random file removal tool. We use system calls 275 * to avoid code duplication. 276 */ 277static int 278clean_pipe(td, path) 279 struct thread *td; 280 char *path; 281{ 282 struct stat st; 283 int error; 284 285 error = kern_lstat(td, path, UIO_SYSSPACE, &st); 286 287 /* 288 * Make sure we are dealing with a mode 0 named pipe. 289 */ 290 if ((st.st_mode & S_IFMT) != S_IFIFO) 291 return (0); 292 293 if ((st.st_mode & ALLPERMS) != 0) 294 return (0); 295 296 error = kern_unlink(td, path, UIO_SYSSPACE); 297 if (error) 298 DPRINTF(("clean_pipe: unlink failed %d\n", error)); 299 return (error); 300} 301 302 303static void 304sockaddr_to_netaddr_in(sc, sain) 305 struct svr4_strmcmd *sc; 306 const struct sockaddr_in *sain; 307{ 308 struct svr4_netaddr_in *na; 309 na = SVR4_ADDROF(sc); 310 311 na->family = sain->sin_family; 312 na->port = sain->sin_port; 313 na->addr = sain->sin_addr.s_addr; 314 DPRINTF(("sockaddr_in -> netaddr %d %d %lx\n", na->family, na->port, 315 na->addr)); 316} 317 318 319static void 320sockaddr_to_netaddr_un(sc, saun) 321 struct svr4_strmcmd *sc; 322 const struct sockaddr_un *saun; 323{ 324 struct svr4_netaddr_un *na; 325 char *dst, *edst = ((char *) sc) + sc->offs + sizeof(na->family) + 1 - 326 sizeof(*sc); 327 const char *src; 328 329 na = SVR4_ADDROF(sc); 330 na->family = saun->sun_family; 331 for (src = saun->sun_path, dst = na->path; (*dst++ = *src++) != '\0'; ) 332 if (dst == edst) 333 break; 334 DPRINTF(("sockaddr_un -> netaddr %d %s\n", na->family, na->path)); 335} 336 337 338static void 339netaddr_to_sockaddr_in(sain, sc) 340 struct sockaddr_in *sain; 341 const struct svr4_strmcmd *sc; 342{ 343 const struct svr4_netaddr_in *na; 344 345 346 na = SVR4_C_ADDROF(sc); 347 memset(sain, 0, sizeof(*sain)); 348 sain->sin_len = sizeof(*sain); 349 sain->sin_family = na->family; 350 sain->sin_port = na->port; 351 sain->sin_addr.s_addr = na->addr; 352 DPRINTF(("netaddr -> sockaddr_in %d %d %x\n", sain->sin_family, 353 sain->sin_port, sain->sin_addr.s_addr)); 354} 355 356 357static void 358netaddr_to_sockaddr_un(saun, sc) 359 struct sockaddr_un *saun; 360 const struct svr4_strmcmd *sc; 361{ 362 const struct svr4_netaddr_un *na; 363 char *dst, *edst = &saun->sun_path[sizeof(saun->sun_path) - 1]; 364 const char *src; 365 366 na = SVR4_C_ADDROF(sc); 367 memset(saun, 0, sizeof(*saun)); 368 saun->sun_family = na->family; 369 for (src = na->path, dst = saun->sun_path; (*dst++ = *src++) != '\0'; ) 370 if (dst == edst) 371 break; 372 saun->sun_len = dst - saun->sun_path; 373 DPRINTF(("netaddr -> sockaddr_un %d %s\n", saun->sun_family, 374 saun->sun_path)); 375} 376 377 378static void 379getparm(fp, pa) 380 struct file *fp; 381 struct svr4_si_sockparms *pa; 382{ 383 struct svr4_strm *st; 384 struct socket *so; 385 386 st = svr4_stream_get(fp); 387 if (st == NULL) 388 return; 389 390 so = fp->f_data; 391 392 pa->family = st->s_family; 393 394 switch (so->so_type) { 395 case SOCK_DGRAM: 396 pa->type = SVR4_T_CLTS; 397 pa->protocol = IPPROTO_UDP; 398 DPRINTF(("getparm(dgram)\n")); 399 return; 400 401 case SOCK_STREAM: 402 pa->type = SVR4_T_COTS; /* What about T_COTS_ORD? XXX */ 403 pa->protocol = IPPROTO_IP; 404 DPRINTF(("getparm(stream)\n")); 405 return; 406 407 case SOCK_RAW: 408 pa->type = SVR4_T_CLTS; 409 pa->protocol = IPPROTO_RAW; 410 DPRINTF(("getparm(raw)\n")); 411 return; 412 413 default: 414 pa->type = 0; 415 pa->protocol = 0; 416 DPRINTF(("getparm(type %d?)\n", so->so_type)); 417 return; 418 } 419} 420 421 422static int 423si_ogetudata(fp, fd, ioc, td) 424 struct file *fp; 425 int fd; 426 struct svr4_strioctl *ioc; 427 struct thread *td; 428{ 429 int error; 430 struct svr4_si_oudata ud; 431 struct svr4_si_sockparms pa; 432 433 if (ioc->len != sizeof(ud) && ioc->len != sizeof(ud) - sizeof(int)) { 434 DPRINTF(("SI_OGETUDATA: Wrong size %d != %d\n", 435 sizeof(ud), ioc->len)); 436 return EINVAL; 437 } 438 439 if ((error = copyin(ioc->buf, &ud, sizeof(ud))) != 0) 440 return error; 441 442 getparm(fp, &pa); 443 444 switch (pa.family) { 445 case AF_INET: 446 ud.tidusize = 16384; 447 ud.addrsize = sizeof(struct svr4_sockaddr_in); 448 if (pa.type == SVR4_SOCK_STREAM) 449 ud.etsdusize = 1; 450 else 451 ud.etsdusize = 0; 452 break; 453 454 case AF_LOCAL: 455 ud.tidusize = 65536; 456 ud.addrsize = 128; 457 ud.etsdusize = 128; 458 break; 459 460 default: 461 DPRINTF(("SI_OGETUDATA: Unsupported address family %d\n", 462 pa.family)); 463 return ENOSYS; 464 } 465 466 /* I have no idea what these should be! */ 467 ud.optsize = 128; 468 ud.tsdusize = 128; 469 470 ud.servtype = pa.type; 471 472 /* XXX: Fixme */ 473 ud.so_state = 0; 474 ud.so_options = 0; 475 return copyout(&ud, ioc->buf, ioc->len); 476} 477 478 479static int 480si_sockparams(fp, fd, ioc, td) 481 struct file *fp; 482 int fd; 483 struct svr4_strioctl *ioc; 484 struct thread *td; 485{ 486 struct svr4_si_sockparms pa; 487 488 getparm(fp, &pa); 489 return copyout(&pa, ioc->buf, sizeof(pa)); 490} 491 492 493static int 494si_listen(fp, fd, ioc, td) 495 struct file *fp; 496 int fd; 497 struct svr4_strioctl *ioc; 498 struct thread *td; 499{ 500 int error; 501 struct svr4_strm *st = svr4_stream_get(fp); 502 struct svr4_strmcmd lst; 503 struct listen_args la; 504 505 if (st == NULL) 506 return EINVAL; 507 508 if (ioc->len < 0 || ioc->len > sizeof(lst)) 509 return EINVAL; 510 511 if ((error = copyin(ioc->buf, &lst, ioc->len)) != 0) 512 return error; 513 514 if (lst.cmd != SVR4_TI_OLD_BIND_REQUEST) { 515 DPRINTF(("si_listen: bad request %ld\n", lst.cmd)); 516 return EINVAL; 517 } 518 519 /* 520 * We are making assumptions again... 521 */ 522 la.s = fd; 523 DPRINTF(("SI_LISTEN: fileno %d backlog = %d\n", fd, 5)); 524 la.backlog = 5; 525 526 if ((error = sys_listen(td, &la)) != 0) { 527 DPRINTF(("SI_LISTEN: listen failed %d\n", error)); 528 return error; 529 } 530 531 st->s_cmd = SVR4_TI__ACCEPT_WAIT; 532 lst.cmd = SVR4_TI_BIND_REPLY; 533 534 switch (st->s_family) { 535 case AF_INET: 536 /* XXX: Fill the length here */ 537 break; 538 539 case AF_LOCAL: 540 lst.len = 140; 541 lst.pad[28] = 0x00000000; /* magic again */ 542 lst.pad[29] = 0x00000800; /* magic again */ 543 lst.pad[30] = 0x80001400; /* magic again */ 544 break; 545 546 default: 547 DPRINTF(("SI_LISTEN: Unsupported address family %d\n", 548 st->s_family)); 549 return ENOSYS; 550 } 551 552 553 if ((error = copyout(&lst, ioc->buf, ioc->len)) != 0) 554 return error; 555 556 return 0; 557} 558 559 560static int 561si_getudata(fp, fd, ioc, td) 562 struct file *fp; 563 int fd; 564 struct svr4_strioctl *ioc; 565 struct thread *td; 566{ 567 int error; 568 struct svr4_si_udata ud; 569 570 if (sizeof(ud) != ioc->len) { 571 DPRINTF(("SI_GETUDATA: Wrong size %d != %d\n", 572 sizeof(ud), ioc->len)); 573 return EINVAL; 574 } 575 576 if ((error = copyin(ioc->buf, &ud, sizeof(ud))) != 0) 577 return error; 578 579 getparm(fp, &ud.sockparms); 580 581 switch (ud.sockparms.family) { 582 case AF_INET: 583 DPRINTF(("getudata_inet\n")); 584 ud.tidusize = 16384; 585 ud.tsdusize = 16384; 586 ud.addrsize = sizeof(struct svr4_sockaddr_in); 587 if (ud.sockparms.type == SVR4_SOCK_STREAM) 588 ud.etsdusize = 1; 589 else 590 ud.etsdusize = 0; 591 ud.optsize = 0; 592 break; 593 594 case AF_LOCAL: 595 DPRINTF(("getudata_local\n")); 596 ud.tidusize = 65536; 597 ud.tsdusize = 128; 598 ud.addrsize = 128; 599 ud.etsdusize = 128; 600 ud.optsize = 128; 601 break; 602 603 default: 604 DPRINTF(("SI_GETUDATA: Unsupported address family %d\n", 605 ud.sockparms.family)); 606 return ENOSYS; 607 } 608 609 610 ud.servtype = ud.sockparms.type; 611 DPRINTF(("ud.servtype = %d\n", ud.servtype)); 612 /* XXX: Fixme */ 613 ud.so_state = 0; 614 ud.so_options = 0; 615 return copyout(&ud, ioc->buf, sizeof(ud)); 616} 617 618 619static int 620si_shutdown(fp, fd, ioc, td) 621 struct file *fp; 622 int fd; 623 struct svr4_strioctl *ioc; 624 struct thread *td; 625{ 626 int error; 627 struct shutdown_args ap; 628 629 if (ioc->len != sizeof(ap.how)) { 630 DPRINTF(("SI_SHUTDOWN: Wrong size %d != %d\n", 631 sizeof(ap.how), ioc->len)); 632 return EINVAL; 633 } 634 635 if ((error = copyin(ioc->buf, &ap.how, ioc->len)) != 0) 636 return error; 637 638 ap.s = fd; 639 640 return sys_shutdown(td, &ap); 641} 642 643 644static int 645sockmod(fp, fd, ioc, td) 646 struct file *fp; 647 int fd; 648 struct svr4_strioctl *ioc; 649 struct thread *td; 650{ 651 switch (ioc->cmd) { 652 case SVR4_SI_OGETUDATA: 653 DPRINTF(("SI_OGETUDATA\n")); 654 return si_ogetudata(fp, fd, ioc, td); 655 656 case SVR4_SI_SHUTDOWN: 657 DPRINTF(("SI_SHUTDOWN\n")); 658 return si_shutdown(fp, fd, ioc, td); 659 660 case SVR4_SI_LISTEN: 661 DPRINTF(("SI_LISTEN\n")); 662 return si_listen(fp, fd, ioc, td); 663 664 case SVR4_SI_SETMYNAME: 665 DPRINTF(("SI_SETMYNAME\n")); 666 return 0; 667 668 case SVR4_SI_SETPEERNAME: 669 DPRINTF(("SI_SETPEERNAME\n")); 670 return 0; 671 672 case SVR4_SI_GETINTRANSIT: 673 DPRINTF(("SI_GETINTRANSIT\n")); 674 return 0; 675 676 case SVR4_SI_TCL_LINK: 677 DPRINTF(("SI_TCL_LINK\n")); 678 return 0; 679 680 case SVR4_SI_TCL_UNLINK: 681 DPRINTF(("SI_TCL_UNLINK\n")); 682 return 0; 683 684 case SVR4_SI_SOCKPARAMS: 685 DPRINTF(("SI_SOCKPARAMS\n")); 686 return si_sockparams(fp, fd, ioc, td); 687 688 case SVR4_SI_GETUDATA: 689 DPRINTF(("SI_GETUDATA\n")); 690 return si_getudata(fp, fd, ioc, td); 691 692 default: 693 DPRINTF(("Unknown sockmod ioctl %lx\n", ioc->cmd)); 694 return 0; 695 696 } 697} 698 699 700static int 701ti_getinfo(fp, fd, ioc, td) 702 struct file *fp; 703 int fd; 704 struct svr4_strioctl *ioc; 705 struct thread *td; 706{ 707 int error; 708 struct svr4_infocmd info; 709 710 memset(&info, 0, sizeof(info)); 711 712 if (ioc->len < 0 || ioc->len > sizeof(info)) 713 return EINVAL; 714 715 if ((error = copyin(ioc->buf, &info, ioc->len)) != 0) 716 return error; 717 718 if (info.cmd != SVR4_TI_INFO_REQUEST) 719 return EINVAL; 720 721 info.cmd = SVR4_TI_INFO_REPLY; 722 info.tsdu = 0; 723 info.etsdu = 1; 724 info.cdata = -2; 725 info.ddata = -2; 726 info.addr = 16; 727 info.opt = -1; 728 info.tidu = 16384; 729 info.serv = 2; 730 info.current = 0; 731 info.provider = 2; 732 733 ioc->len = sizeof(info); 734 if ((error = copyout(&info, ioc->buf, ioc->len)) != 0) 735 return error; 736 737 return 0; 738} 739 740 741static int 742ti_bind(fp, fd, ioc, td) 743 struct file *fp; 744 int fd; 745 struct svr4_strioctl *ioc; 746 struct thread *td; 747{ 748 int error; 749 struct svr4_strm *st = svr4_stream_get(fp); 750 struct sockaddr_in sain; 751 struct sockaddr_un saun; 752 struct sockaddr *skp; 753 int sasize; 754 struct svr4_strmcmd bnd; 755 756 if (st == NULL) { 757 DPRINTF(("ti_bind: bad file descriptor\n")); 758 return EINVAL; 759 } 760 761 if (ioc->len < 0 || ioc->len > sizeof(bnd)) 762 return EINVAL; 763 764 if ((error = copyin(ioc->buf, &bnd, ioc->len)) != 0) 765 return error; 766 767 if (bnd.cmd != SVR4_TI_OLD_BIND_REQUEST) { 768 DPRINTF(("ti_bind: bad request %ld\n", bnd.cmd)); 769 return EINVAL; 770 } 771 772 switch (st->s_family) { 773 case AF_INET: 774 skp = (struct sockaddr *)&sain; 775 sasize = sizeof(sain); 776 777 if (bnd.offs == 0) 778 goto error; 779 780 netaddr_to_sockaddr_in(&sain, &bnd); 781 782 DPRINTF(("TI_BIND: fam %d, port %d, addr %x\n", 783 sain.sin_family, sain.sin_port, 784 sain.sin_addr.s_addr)); 785 break; 786 787 case AF_LOCAL: 788 skp = (struct sockaddr *)&saun; 789 sasize = sizeof(saun); 790 if (bnd.offs == 0) 791 goto error; 792 793 netaddr_to_sockaddr_un(&saun, &bnd); 794 795 if (saun.sun_path[0] == '\0') 796 goto error; 797 798 DPRINTF(("TI_BIND: fam %d, path %s\n", 799 saun.sun_family, saun.sun_path)); 800 801 if ((error = clean_pipe(td, saun.sun_path)) != 0) 802 return error; 803 804 bnd.pad[28] = 0x00001000; /* magic again */ 805 break; 806 807 default: 808 DPRINTF(("TI_BIND: Unsupported address family %d\n", 809 st->s_family)); 810 return ENOSYS; 811 } 812 813 DPRINTF(("TI_BIND: fileno %d\n", fd)); 814 815 if ((error = kern_bind(td, fd, skp)) != 0) { 816 DPRINTF(("TI_BIND: bind failed %d\n", error)); 817 return error; 818 } 819 goto reply; 820 821error: 822 memset(&bnd, 0, sizeof(bnd)); 823 bnd.len = sasize + 4; 824 bnd.offs = 0x10; /* XXX */ 825 826reply: 827 bnd.cmd = SVR4_TI_BIND_REPLY; 828 829 if ((error = copyout(&bnd, ioc->buf, ioc->len)) != 0) 830 return error; 831 832 return 0; 833} 834 835 836static int 837timod(fp, fd, ioc, td) 838 struct file *fp; 839 int fd; 840 struct svr4_strioctl *ioc; 841 struct thread *td; 842{ 843 switch (ioc->cmd) { 844 case SVR4_TI_GETINFO: 845 DPRINTF(("TI_GETINFO\n")); 846 return ti_getinfo(fp, fd, ioc, td); 847 848 case SVR4_TI_OPTMGMT: 849 DPRINTF(("TI_OPTMGMT\n")); 850 return 0; 851 852 case SVR4_TI_BIND: 853 DPRINTF(("TI_BIND\n")); 854 return ti_bind(fp, fd, ioc, td); 855 856 case SVR4_TI_UNBIND: 857 DPRINTF(("TI_UNBIND\n")); 858 return 0; 859 860 default: 861 DPRINTF(("Unknown timod ioctl %lx\n", ioc->cmd)); 862 return 0; 863 } 864} 865 866 867int 868svr4_stream_ti_ioctl(fp, td, retval, fd, cmd, dat) 869 struct file *fp; 870 struct thread *td; 871 register_t *retval; 872 int fd; 873 u_long cmd; 874 caddr_t dat; 875{ 876 struct svr4_strbuf skb, *sub = (struct svr4_strbuf *) dat; 877 struct svr4_strm *st = svr4_stream_get(fp); 878 int error; 879 struct sockaddr *sa; 880 socklen_t sasize, oldsasize; 881 struct svr4_strmcmd sc; 882 883 DPRINTF(("svr4_stream_ti_ioctl\n")); 884 885 if (st == NULL) 886 return EINVAL; 887 888 sc.offs = 0x10; 889 890 if ((error = copyin(sub, &skb, sizeof(skb))) != 0) { 891 DPRINTF(("ti_ioctl: error copying in strbuf\n")); 892 return error; 893 } 894 895 switch (st->s_family) { 896 case AF_INET: 897 sasize = sizeof(struct sockaddr_in); 898 break; 899 900 case AF_LOCAL: 901 sasize = sizeof(struct sockaddr_un); 902 break; 903 904 default: 905 DPRINTF(("ti_ioctl: Unsupported address family %d\n", 906 st->s_family)); 907 return ENOSYS; 908 } 909 oldsasize = sasize; 910 911 switch (cmd) { 912 case SVR4_TI_GETMYNAME: 913 DPRINTF(("TI_GETMYNAME\n")); 914 { 915 error = kern_getsockname(td, fd, &sa, &sasize); 916 if (error) { 917 DPRINTF(("ti_ioctl: getsockname error\n")); 918 return error; 919 } 920 } 921 break; 922 923 case SVR4_TI_GETPEERNAME: 924 DPRINTF(("TI_GETPEERNAME\n")); 925 { 926 error = kern_getpeername(td, fd, &sa, &sasize); 927 if (error) { 928 DPRINTF(("ti_ioctl: getpeername error\n")); 929 return error; 930 } 931 } 932 break; 933 934 case SVR4_TI_SETMYNAME: 935 DPRINTF(("TI_SETMYNAME\n")); 936 return 0; 937 938 case SVR4_TI_SETPEERNAME: 939 DPRINTF(("TI_SETPEERNAME\n")); 940 return 0; 941 default: 942 DPRINTF(("ti_ioctl: Unknown ioctl %lx\n", cmd)); 943 return ENOSYS; 944 } 945 946 if (sasize < 0 || sasize > oldsasize) { 947 free(sa, M_SONAME); 948 return EINVAL; 949 } 950 951 switch (st->s_family) { 952 case AF_INET: 953 sockaddr_to_netaddr_in(&sc, (struct sockaddr_in *)sa); 954 skb.len = sasize; 955 break; 956 957 case AF_LOCAL: 958 sockaddr_to_netaddr_un(&sc, (struct sockaddr_un *)sa); 959 skb.len = sasize + 4; 960 break; 961 962 default: 963 free(sa, M_SONAME); 964 return ENOSYS; 965 } 966 free(sa, M_SONAME); 967 968 if ((error = copyout(SVR4_ADDROF(&sc), skb.buf, sasize)) != 0) { 969 DPRINTF(("ti_ioctl: error copying out socket data\n")); 970 return error; 971 } 972 973 974 if ((error = copyout(&skb, sub, sizeof(skb))) != 0) { 975 DPRINTF(("ti_ioctl: error copying out strbuf\n")); 976 return error; 977 } 978 979 return error; 980} 981 982 983 984 985static int 986i_nread(fp, td, retval, fd, cmd, dat) 987 struct file *fp; 988 struct thread *td; 989 register_t *retval; 990 int fd; 991 u_long cmd; 992 caddr_t dat; 993{ 994 int error; 995 int nread = 0; 996 997 /* 998 * We are supposed to return the message length in nread, and the 999 * number of messages in retval. We don't have the notion of number 1000 * of stream messages, so we just find out if we have any bytes waiting 1001 * for us, and if we do, then we assume that we have at least one 1002 * message waiting for us. 1003 */ 1004 if ((error = fo_ioctl(fp, FIONREAD, (caddr_t) &nread, td->td_ucred, 1005 td)) != 0) 1006 return error; 1007 1008 if (nread != 0) 1009 *retval = 1; 1010 else 1011 *retval = 0; 1012 1013 return copyout(&nread, dat, sizeof(nread)); 1014} 1015 1016static int 1017i_fdinsert(fp, td, retval, fd, cmd, dat) 1018 struct file *fp; 1019 struct thread *td; 1020 register_t *retval; 1021 int fd; 1022 u_long cmd; 1023 caddr_t dat; 1024{ 1025 /* 1026 * Major hack again here. We assume that we are using this to 1027 * implement accept(2). If that is the case, we have already 1028 * called accept, and we have stored the file descriptor in 1029 * afd. We find the file descriptor that the code wants to use 1030 * in fd insert, and then we dup2() our accepted file descriptor 1031 * to it. 1032 */ 1033 int error; 1034 struct svr4_strm *st = svr4_stream_get(fp); 1035 struct svr4_strfdinsert fdi; 1036 struct dup2_args d2p; 1037 1038 if (st == NULL) { 1039 DPRINTF(("fdinsert: bad file type\n")); 1040 return EINVAL; 1041 } 1042 1043 mtx_lock(&Giant); 1044 if (st->s_afd == -1) { 1045 DPRINTF(("fdinsert: accept fd not found\n")); 1046 mtx_unlock(&Giant); 1047 return ENOENT; 1048 } 1049 1050 if ((error = copyin(dat, &fdi, sizeof(fdi))) != 0) { 1051 DPRINTF(("fdinsert: copyin failed %d\n", error)); 1052 mtx_unlock(&Giant); 1053 return error; 1054 } 1055 1056 d2p.from = st->s_afd; 1057 d2p.to = fdi.fd; 1058 1059 if ((error = sys_dup2(td, &d2p)) != 0) { 1060 DPRINTF(("fdinsert: dup2(%d, %d) failed %d\n", 1061 st->s_afd, fdi.fd, error)); 1062 mtx_unlock(&Giant); 1063 return error; 1064 } 1065 1066 if ((error = kern_close(td, st->s_afd)) != 0) { 1067 DPRINTF(("fdinsert: close(%d) failed %d\n", 1068 st->s_afd, error)); 1069 mtx_unlock(&Giant); 1070 return error; 1071 } 1072 1073 st->s_afd = -1; 1074 mtx_unlock(&Giant); 1075 1076 *retval = 0; 1077 return 0; 1078} 1079 1080 1081static int 1082_i_bind_rsvd(fp, td, retval, fd, cmd, dat) 1083 struct file *fp; 1084 struct thread *td; 1085 register_t *retval; 1086 int fd; 1087 u_long cmd; 1088 caddr_t dat; 1089{ 1090 struct mkfifo_args ap; 1091 1092 /* 1093 * This is a supposed to be a kernel and library only ioctl. 1094 * It gets called before ti_bind, when we have a unix 1095 * socket, to physically create the socket transport and 1096 * ``reserve'' it. I don't know how this get reserved inside 1097 * the kernel, but we are going to create it nevertheless. 1098 */ 1099 ap.path = dat; 1100 ap.mode = S_IFIFO; 1101 1102 return sys_mkfifo(td, &ap); 1103} 1104 1105static int 1106_i_rele_rsvd(fp, td, retval, fd, cmd, dat) 1107 struct file *fp; 1108 struct thread *td; 1109 register_t *retval; 1110 int fd; 1111 u_long cmd; 1112 caddr_t dat; 1113{ 1114 struct unlink_args ap; 1115 1116 /* 1117 * This is a supposed to be a kernel and library only ioctl. 1118 * I guess it is supposed to release the socket. 1119 */ 1120 ap.path = dat; 1121 1122 return sys_unlink(td, &ap); 1123} 1124 1125static int 1126i_str(fp, td, retval, fd, cmd, dat) 1127 struct file *fp; 1128 struct thread *td; 1129 register_t *retval; 1130 int fd; 1131 u_long cmd; 1132 caddr_t dat; 1133{ 1134 int error; 1135 struct svr4_strioctl ioc; 1136 1137 if ((error = copyin(dat, &ioc, sizeof(ioc))) != 0) 1138 return error; 1139 1140#ifdef DEBUG_SVR4 1141 if ((error = show_ioc(">", &ioc)) != 0) 1142 return error; 1143#endif /* DEBUG_SVR4 */ 1144 1145 switch (ioc.cmd & 0xff00) { 1146 case SVR4_SIMOD: 1147 if ((error = sockmod(fp, fd, &ioc, td)) != 0) 1148 return error; 1149 break; 1150 1151 case SVR4_TIMOD: 1152 if ((error = timod(fp, fd, &ioc, td)) != 0) 1153 return error; 1154 break; 1155 1156 default: 1157 DPRINTF(("Unimplemented module %c %ld\n", 1158 (char) (cmd >> 8), cmd & 0xff)); 1159 return 0; 1160 } 1161 1162#ifdef DEBUG_SVR4 1163 if ((error = show_ioc("<", &ioc)) != 0) 1164 return error; 1165#endif /* DEBUG_SVR4 */ 1166 return copyout(&ioc, dat, sizeof(ioc)); 1167} 1168 1169static int 1170i_setsig(fp, td, retval, fd, cmd, dat) 1171 struct file *fp; 1172 struct thread *td; 1173 register_t *retval; 1174 int fd; 1175 u_long cmd; 1176 caddr_t dat; 1177{ 1178 /* 1179 * This is the best we can do for now; we cannot generate 1180 * signals only for specific events so the signal mask gets 1181 * ignored; we save it just to pass it to a possible I_GETSIG... 1182 * 1183 * We alse have to fix the O_ASYNC fcntl bit, so the 1184 * process will get SIGPOLLs. 1185 */ 1186 int error; 1187 register_t oflags, flags; 1188 struct svr4_strm *st = svr4_stream_get(fp); 1189 1190 if (st == NULL) { 1191 DPRINTF(("i_setsig: bad file descriptor\n")); 1192 return EINVAL; 1193 } 1194 /* get old status flags */ 1195 error = kern_fcntl(td, fd, F_GETFL, 0); 1196 if (error) 1197 return (error); 1198 1199 oflags = td->td_retval[0]; 1200 1201 /* update the flags */ 1202 mtx_lock(&Giant); 1203 if (dat != NULL) { 1204 int mask; 1205 1206 flags = oflags | O_ASYNC; 1207 if ((error = copyin(dat, &mask, sizeof(mask))) != 0) { 1208 DPRINTF(("i_setsig: bad eventmask pointer\n")); 1209 return error; 1210 } 1211 if (mask & SVR4_S_ALLMASK) { 1212 DPRINTF(("i_setsig: bad eventmask data %x\n", mask)); 1213 return EINVAL; 1214 } 1215 st->s_eventmask = mask; 1216 } 1217 else { 1218 flags = oflags & ~O_ASYNC; 1219 st->s_eventmask = 0; 1220 } 1221 mtx_unlock(&Giant); 1222 1223 /* set the new flags, if changed */ 1224 if (flags != oflags) { 1225 error = kern_fcntl(td, fd, F_SETFL, flags); 1226 if (error) 1227 return (error); 1228 flags = td->td_retval[0]; 1229 } 1230 1231 /* set up SIGIO receiver if needed */ 1232 if (dat != NULL) 1233 return (kern_fcntl(td, fd, F_SETOWN, td->td_proc->p_pid)); 1234 return 0; 1235} 1236 1237static int 1238i_getsig(fp, td, retval, fd, cmd, dat) 1239 struct file *fp; 1240 struct thread *td; 1241 register_t *retval; 1242 int fd; 1243 u_long cmd; 1244 caddr_t dat; 1245{ 1246 int error, eventmask; 1247 1248 if (dat != NULL) { 1249 struct svr4_strm *st = svr4_stream_get(fp); 1250 1251 if (st == NULL) { 1252 DPRINTF(("i_getsig: bad file descriptor\n")); 1253 return EINVAL; 1254 } 1255 mtx_lock(&Giant); 1256 eventmask = st->s_eventmask; 1257 mtx_unlock(&Giant); 1258 if ((error = copyout(&eventmask, dat, 1259 sizeof(eventmask))) != 0) { 1260 DPRINTF(("i_getsig: bad eventmask pointer\n")); 1261 return error; 1262 } 1263 } 1264 return 0; 1265} 1266 1267int 1268svr4_stream_ioctl(fp, td, retval, fd, cmd, dat) 1269 struct file *fp; 1270 struct thread *td; 1271 register_t *retval; 1272 int fd; 1273 u_long cmd; 1274 caddr_t dat; 1275{ 1276 *retval = 0; 1277 1278 /* 1279 * All the following stuff assumes "sockmod" is pushed... 1280 */ 1281 switch (cmd) { 1282 case SVR4_I_NREAD: 1283 DPRINTF(("I_NREAD\n")); 1284 return i_nread(fp, td, retval, fd, cmd, dat); 1285 1286 case SVR4_I_PUSH: 1287 DPRINTF(("I_PUSH %p\n", dat)); 1288#if defined(DEBUG_SVR4) 1289 show_strbuf((struct svr4_strbuf *)dat); 1290#endif 1291 return 0; 1292 1293 case SVR4_I_POP: 1294 DPRINTF(("I_POP\n")); 1295 return 0; 1296 1297 case SVR4_I_LOOK: 1298 DPRINTF(("I_LOOK\n")); 1299 return 0; 1300 1301 case SVR4_I_FLUSH: 1302 DPRINTF(("I_FLUSH\n")); 1303 return 0; 1304 1305 case SVR4_I_SRDOPT: 1306 DPRINTF(("I_SRDOPT\n")); 1307 return 0; 1308 1309 case SVR4_I_GRDOPT: 1310 DPRINTF(("I_GRDOPT\n")); 1311 return 0; 1312 1313 case SVR4_I_STR: 1314 DPRINTF(("I_STR\n")); 1315 return i_str(fp, td, retval, fd, cmd, dat); 1316 1317 case SVR4_I_SETSIG: 1318 DPRINTF(("I_SETSIG\n")); 1319 return i_setsig(fp, td, retval, fd, cmd, dat); 1320 1321 case SVR4_I_GETSIG: 1322 DPRINTF(("I_GETSIG\n")); 1323 return i_getsig(fp, td, retval, fd, cmd, dat); 1324 1325 case SVR4_I_FIND: 1326 DPRINTF(("I_FIND\n")); 1327 /* 1328 * Here we are not pushing modules really, we just 1329 * pretend all are present 1330 */ 1331 *retval = 0; 1332 return 0; 1333 1334 case SVR4_I_LINK: 1335 DPRINTF(("I_LINK\n")); 1336 return 0; 1337 1338 case SVR4_I_UNLINK: 1339 DPRINTF(("I_UNLINK\n")); 1340 return 0; 1341 1342 case SVR4_I_ERECVFD: 1343 DPRINTF(("I_ERECVFD\n")); 1344 return 0; 1345 1346 case SVR4_I_PEEK: 1347 DPRINTF(("I_PEEK\n")); 1348 return 0; 1349 1350 case SVR4_I_FDINSERT: 1351 DPRINTF(("I_FDINSERT\n")); 1352 return i_fdinsert(fp, td, retval, fd, cmd, dat); 1353 1354 case SVR4_I_SENDFD: 1355 DPRINTF(("I_SENDFD\n")); 1356 return 0; 1357 1358 case SVR4_I_RECVFD: 1359 DPRINTF(("I_RECVFD\n")); 1360 return 0; 1361 1362 case SVR4_I_SWROPT: 1363 DPRINTF(("I_SWROPT\n")); 1364 return 0; 1365 1366 case SVR4_I_GWROPT: 1367 DPRINTF(("I_GWROPT\n")); 1368 return 0; 1369 1370 case SVR4_I_LIST: 1371 DPRINTF(("I_LIST\n")); 1372 return 0; 1373 1374 case SVR4_I_PLINK: 1375 DPRINTF(("I_PLINK\n")); 1376 return 0; 1377 1378 case SVR4_I_PUNLINK: 1379 DPRINTF(("I_PUNLINK\n")); 1380 return 0; 1381 1382 case SVR4_I_SETEV: 1383 DPRINTF(("I_SETEV\n")); 1384 return 0; 1385 1386 case SVR4_I_GETEV: 1387 DPRINTF(("I_GETEV\n")); 1388 return 0; 1389 1390 case SVR4_I_STREV: 1391 DPRINTF(("I_STREV\n")); 1392 return 0; 1393 1394 case SVR4_I_UNSTREV: 1395 DPRINTF(("I_UNSTREV\n")); 1396 return 0; 1397 1398 case SVR4_I_FLUSHBAND: 1399 DPRINTF(("I_FLUSHBAND\n")); 1400 return 0; 1401 1402 case SVR4_I_CKBAND: 1403 DPRINTF(("I_CKBAND\n")); 1404 return 0; 1405 1406 case SVR4_I_GETBAND: 1407 DPRINTF(("I_GETBANK\n")); 1408 return 0; 1409 1410 case SVR4_I_ATMARK: 1411 DPRINTF(("I_ATMARK\n")); 1412 return 0; 1413 1414 case SVR4_I_SETCLTIME: 1415 DPRINTF(("I_SETCLTIME\n")); 1416 return 0; 1417 1418 case SVR4_I_GETCLTIME: 1419 DPRINTF(("I_GETCLTIME\n")); 1420 return 0; 1421 1422 case SVR4_I_CANPUT: 1423 DPRINTF(("I_CANPUT\n")); 1424 return 0; 1425 1426 case SVR4__I_BIND_RSVD: 1427 DPRINTF(("_I_BIND_RSVD\n")); 1428 return _i_bind_rsvd(fp, td, retval, fd, cmd, dat); 1429 1430 case SVR4__I_RELE_RSVD: 1431 DPRINTF(("_I_RELE_RSVD\n")); 1432 return _i_rele_rsvd(fp, td, retval, fd, cmd, dat); 1433 1434 default: 1435 DPRINTF(("unimpl cmd = %lx\n", cmd)); 1436 break; 1437 } 1438 1439 return 0; 1440} 1441 1442 1443 1444int 1445svr4_sys_putmsg(td, uap) 1446 struct thread *td; 1447 struct svr4_sys_putmsg_args *uap; 1448{ 1449 cap_rights_t rights; 1450 struct file *fp; 1451 int error; 1452 1453 error = fget(td, uap->fd, cap_rights_init(&rights, CAP_SEND), &fp); 1454 if (error != 0) { 1455#ifdef DEBUG_SVR4 1456 uprintf("putmsg: bad fp\n"); 1457#endif 1458 return EBADF; 1459 } 1460 error = svr4_do_putmsg(td, uap, fp); 1461 fdrop(fp, td); 1462 return (error); 1463} 1464 1465static int 1466svr4_do_putmsg(td, uap, fp) 1467 struct thread *td; 1468 struct svr4_sys_putmsg_args *uap; 1469 struct file *fp; 1470{ 1471 struct svr4_strbuf dat, ctl; 1472 struct svr4_strmcmd sc; 1473 struct sockaddr_in sain; 1474 struct sockaddr_un saun; 1475 struct sockaddr *sa; 1476 int sasize, *retval; 1477 struct svr4_strm *st; 1478 int error; 1479 1480 retval = td->td_retval; 1481 1482#ifdef DEBUG_SVR4 1483 show_msg(">putmsg", uap->fd, uap->ctl, 1484 uap->dat, uap->flags); 1485#endif /* DEBUG_SVR4 */ 1486 1487 if (uap->ctl != NULL) { 1488 if ((error = copyin(uap->ctl, &ctl, sizeof(ctl))) != 0) { 1489#ifdef DEBUG_SVR4 1490 uprintf("putmsg: copyin(): %d\n", error); 1491#endif 1492 return error; 1493 } 1494 } 1495 else 1496 ctl.len = -1; 1497 1498 if (uap->dat != NULL) { 1499 if ((error = copyin(uap->dat, &dat, sizeof(dat))) != 0) { 1500#ifdef DEBUG_SVR4 1501 uprintf("putmsg: copyin(): %d (2)\n", error); 1502#endif 1503 return error; 1504 } 1505 } 1506 else 1507 dat.len = -1; 1508 1509 /* 1510 * Only for sockets for now. 1511 */ 1512 if ((st = svr4_stream_get(fp)) == NULL) { 1513 DPRINTF(("putmsg: bad file type\n")); 1514 return EINVAL; 1515 } 1516 1517 if (ctl.len < 0 || ctl.len > sizeof(sc)) { 1518 DPRINTF(("putmsg: Bad control size %d != %d\n", ctl.len, 1519 sizeof(struct svr4_strmcmd))); 1520 return EINVAL; 1521 } 1522 1523 if ((error = copyin(ctl.buf, &sc, ctl.len)) != 0) 1524 return error; 1525 1526 switch (st->s_family) { 1527 case AF_INET: 1528 if (sc.len != sizeof(sain)) { 1529 if (sc.cmd == SVR4_TI_DATA_REQUEST) { 1530 struct write_args wa; 1531 1532 /* Solaris seems to use sc.cmd = 3 to 1533 * send "expedited" data. telnet uses 1534 * this for options processing, sending EOF, 1535 * etc. I'm sure other things use it too. 1536 * I don't have any documentation 1537 * on it, so I'm making a guess that this 1538 * is how it works. newton@atdot.dotat.org XXX 1539 */ 1540 DPRINTF(("sending expedited data ??\n")); 1541 wa.fd = uap->fd; 1542 wa.buf = dat.buf; 1543 wa.nbyte = dat.len; 1544 return sys_write(td, &wa); 1545 } 1546 DPRINTF(("putmsg: Invalid inet length %ld\n", sc.len)); 1547 return EINVAL; 1548 } 1549 netaddr_to_sockaddr_in(&sain, &sc); 1550 sa = (struct sockaddr *)&sain; 1551 sasize = sizeof(sain); 1552 if (sain.sin_family != st->s_family) 1553 error = EINVAL; 1554 break; 1555 1556 case AF_LOCAL: 1557 if (ctl.len == 8) { 1558 /* We are doing an accept; succeed */ 1559 DPRINTF(("putmsg: Do nothing\n")); 1560 *retval = 0; 1561 return 0; 1562 } 1563 else { 1564 /* Maybe we've been given a device/inode pair */ 1565 dev_t *dev = SVR4_ADDROF(&sc); 1566 ino_t *ino = (ino_t *) &dev[1]; 1567 if (svr4_find_socket(td, fp, *dev, *ino, &saun) != 0) { 1568 /* I guess we have it by name */ 1569 netaddr_to_sockaddr_un(&saun, &sc); 1570 } 1571 sa = (struct sockaddr *)&saun; 1572 sasize = sizeof(saun); 1573 } 1574 break; 1575 1576 default: 1577 DPRINTF(("putmsg: Unsupported address family %d\n", 1578 st->s_family)); 1579 return ENOSYS; 1580 } 1581 1582 mtx_lock(&Giant); 1583 st->s_cmd = sc.cmd; 1584 mtx_unlock(&Giant); 1585 switch (sc.cmd) { 1586 case SVR4_TI_CONNECT_REQUEST: /* connect */ 1587 { 1588 1589 return (kern_connect(td, uap->fd, sa)); 1590 } 1591 1592 case SVR4_TI_SENDTO_REQUEST: /* sendto */ 1593 { 1594 struct msghdr msg; 1595 struct iovec aiov; 1596 1597 msg.msg_name = sa; 1598 msg.msg_namelen = sasize; 1599 msg.msg_iov = &aiov; 1600 msg.msg_iovlen = 1; 1601 msg.msg_control = 0; 1602 msg.msg_flags = 0; 1603 aiov.iov_base = dat.buf; 1604 aiov.iov_len = dat.len; 1605 error = kern_sendit(td, uap->fd, &msg, uap->flags, 1606 NULL, UIO_USERSPACE); 1607 DPRINTF(("sendto_request error: %d\n", error)); 1608 *retval = 0; 1609 return error; 1610 } 1611 1612 default: 1613 DPRINTF(("putmsg: Unimplemented command %lx\n", sc.cmd)); 1614 return ENOSYS; 1615 } 1616} 1617 1618int 1619svr4_sys_getmsg(td, uap) 1620 struct thread *td; 1621 struct svr4_sys_getmsg_args *uap; 1622{ 1623 cap_rights_t rights; 1624 struct file *fp; 1625 int error; 1626 1627 error = fget(td, uap->fd, cap_rights_init(&rights, CAP_RECV), &fp); 1628 if (error != 0) { 1629#ifdef DEBUG_SVR4 1630 uprintf("getmsg: bad fp\n"); 1631#endif 1632 return EBADF; 1633 } 1634 error = svr4_do_getmsg(td, uap, fp); 1635 fdrop(fp, td); 1636 return (error); 1637} 1638 1639int 1640svr4_do_getmsg(td, uap, fp) 1641 struct thread *td; 1642 struct svr4_sys_getmsg_args *uap; 1643 struct file *fp; 1644{ 1645 struct svr4_strbuf dat, ctl; 1646 struct svr4_strmcmd sc; 1647 int error, *retval; 1648 struct msghdr msg; 1649 struct iovec aiov; 1650 struct sockaddr_in sain; 1651 struct sockaddr_un saun; 1652 struct sockaddr *sa; 1653 socklen_t sasize; 1654 struct svr4_strm *st; 1655 struct file *afp; 1656 int fl; 1657 1658 retval = td->td_retval; 1659 error = 0; 1660 afp = NULL; 1661 1662 memset(&sc, 0, sizeof(sc)); 1663 1664#ifdef DEBUG_SVR4 1665 show_msg(">getmsg", uap->fd, uap->ctl, 1666 uap->dat, 0); 1667#endif /* DEBUG_SVR4 */ 1668 1669 if (uap->ctl != NULL) { 1670 if ((error = copyin(uap->ctl, &ctl, sizeof(ctl))) != 0) 1671 return error; 1672 if (ctl.len < 0) 1673 return EINVAL; 1674 } 1675 else { 1676 ctl.len = -1; 1677 ctl.maxlen = 0; 1678 } 1679 1680 if (uap->dat != NULL) { 1681 if ((error = copyin(uap->dat, &dat, sizeof(dat))) != 0) 1682 return error; 1683 } 1684 else { 1685 dat.len = -1; 1686 dat.maxlen = 0; 1687 } 1688 1689 /* 1690 * Only for sockets for now. 1691 */ 1692 if ((st = svr4_stream_get(fp)) == NULL) { 1693 DPRINTF(("getmsg: bad file type\n")); 1694 return EINVAL; 1695 } 1696 1697 if (ctl.maxlen == -1 || dat.maxlen == -1) { 1698 DPRINTF(("getmsg: Cannot handle -1 maxlen (yet)\n")); 1699 return ENOSYS; 1700 } 1701 1702 switch (st->s_family) { 1703 case AF_INET: 1704 sasize = sizeof(sain); 1705 break; 1706 1707 case AF_LOCAL: 1708 sasize = sizeof(saun); 1709 break; 1710 1711 default: 1712 DPRINTF(("getmsg: Unsupported address family %d\n", 1713 st->s_family)); 1714 return ENOSYS; 1715 } 1716 1717 mtx_lock(&Giant); 1718 switch (st->s_cmd) { 1719 case SVR4_TI_CONNECT_REQUEST: 1720 DPRINTF(("getmsg: TI_CONNECT_REQUEST\n")); 1721 /* 1722 * We do the connect in one step, so the putmsg should 1723 * have gotten the error. 1724 */ 1725 sc.cmd = SVR4_TI_OK_REPLY; 1726 sc.len = 0; 1727 1728 ctl.len = 8; 1729 dat.len = -1; 1730 fl = 1; 1731 st->s_cmd = sc.cmd; 1732 break; 1733 1734 case SVR4_TI_OK_REPLY: 1735 DPRINTF(("getmsg: TI_OK_REPLY\n")); 1736 /* 1737 * We are immediately after a connect reply, so we send 1738 * a connect verification. 1739 */ 1740 1741 error = kern_getpeername(td, uap->fd, &sa, &sasize); 1742 if (error) { 1743 mtx_unlock(&Giant); 1744 DPRINTF(("getmsg: getpeername failed %d\n", error)); 1745 return error; 1746 } 1747 1748 sc.cmd = SVR4_TI_CONNECT_REPLY; 1749 sc.pad[0] = 0x4; 1750 sc.offs = 0x18; 1751 sc.pad[1] = 0x14; 1752 sc.pad[2] = 0x04000402; 1753 1754 switch (st->s_family) { 1755 case AF_INET: 1756 sc.len = sasize; 1757 sockaddr_to_netaddr_in(&sc, (struct sockaddr_in *)sa); 1758 break; 1759 1760 case AF_LOCAL: 1761 sc.len = sasize + 4; 1762 sockaddr_to_netaddr_un(&sc, (struct sockaddr_un *)sa); 1763 break; 1764 1765 default: 1766 mtx_unlock(&Giant); 1767 free(sa, M_SONAME); 1768 return ENOSYS; 1769 } 1770 free(sa, M_SONAME); 1771 1772 ctl.len = 40; 1773 dat.len = -1; 1774 fl = 0; 1775 st->s_cmd = sc.cmd; 1776 break; 1777 1778 case SVR4_TI__ACCEPT_OK: 1779 DPRINTF(("getmsg: TI__ACCEPT_OK\n")); 1780 /* 1781 * We do the connect in one step, so the putmsg should 1782 * have gotten the error. 1783 */ 1784 sc.cmd = SVR4_TI_OK_REPLY; 1785 sc.len = 1; 1786 1787 ctl.len = 8; 1788 dat.len = -1; 1789 fl = 1; 1790 st->s_cmd = SVR4_TI__ACCEPT_WAIT; 1791 break; 1792 1793 case SVR4_TI__ACCEPT_WAIT: 1794 DPRINTF(("getmsg: TI__ACCEPT_WAIT\n")); 1795 /* 1796 * We are after a listen, so we try to accept... 1797 */ 1798 1799 error = kern_accept(td, uap->fd, &sa, &sasize, &afp); 1800 if (error) { 1801 mtx_unlock(&Giant); 1802 DPRINTF(("getmsg: accept failed %d\n", error)); 1803 return error; 1804 } 1805 1806 st->s_afd = *retval; 1807 1808 DPRINTF(("getmsg: Accept fd = %d\n", st->s_afd)); 1809 1810 sc.cmd = SVR4_TI_ACCEPT_REPLY; 1811 sc.offs = 0x18; 1812 sc.pad[0] = 0x0; 1813 1814 switch (st->s_family) { 1815 case AF_INET: 1816 sc.pad[1] = 0x28; 1817 sockaddr_to_netaddr_in(&sc, (struct sockaddr_in *)&sa); 1818 ctl.len = 40; 1819 sc.len = sasize; 1820 break; 1821 1822 case AF_LOCAL: 1823 sc.pad[1] = 0x00010000; 1824 sc.pad[2] = 0xf6bcdaa0; /* I don't know what that is */ 1825 sc.pad[3] = 0x00010000; 1826 ctl.len = 134; 1827 sc.len = sasize + 4; 1828 break; 1829 1830 default: 1831 fdclose(td->td_proc->p_fd, afp, st->s_afd, td); 1832 fdrop(afp, td); 1833 st->s_afd = -1; 1834 mtx_unlock(&Giant); 1835 free(sa, M_SONAME); 1836 return ENOSYS; 1837 } 1838 free(sa, M_SONAME); 1839 1840 dat.len = -1; 1841 fl = 0; 1842 st->s_cmd = SVR4_TI__ACCEPT_OK; 1843 break; 1844 1845 case SVR4_TI_SENDTO_REQUEST: 1846 DPRINTF(("getmsg: TI_SENDTO_REQUEST\n")); 1847 if (ctl.maxlen > 36 && ctl.len < 36) 1848 ctl.len = 36; 1849 1850 if (ctl.len > sizeof(sc)) 1851 ctl.len = sizeof(sc); 1852 1853 if ((error = copyin(ctl.buf, &sc, ctl.len)) != 0) { 1854 mtx_unlock(&Giant); 1855 return error; 1856 } 1857 1858 switch (st->s_family) { 1859 case AF_INET: 1860 sa = (struct sockaddr *)&sain; 1861 sockaddr_to_netaddr_in(&sc, &sain); 1862 break; 1863 1864 case AF_LOCAL: 1865 sa = (struct sockaddr *)&saun; 1866 sockaddr_to_netaddr_un(&sc, &saun); 1867 break; 1868 1869 default: 1870 mtx_unlock(&Giant); 1871 return ENOSYS; 1872 } 1873 1874 msg.msg_name = sa; 1875 msg.msg_namelen = sasize; 1876 msg.msg_iov = &aiov; 1877 msg.msg_iovlen = 1; 1878 msg.msg_control = 0; 1879 aiov.iov_base = dat.buf; 1880 aiov.iov_len = dat.maxlen; 1881 msg.msg_flags = 0; 1882 1883 error = kern_recvit(td, uap->fd, &msg, UIO_SYSSPACE, NULL); 1884 1885 if (error) { 1886 mtx_unlock(&Giant); 1887 DPRINTF(("getmsg: recvit failed %d\n", error)); 1888 return error; 1889 } 1890 1891 sc.cmd = SVR4_TI_RECVFROM_IND; 1892 1893 switch (st->s_family) { 1894 case AF_INET: 1895 sc.len = sasize; 1896 sockaddr_to_netaddr_in(&sc, &sain); 1897 break; 1898 1899 case AF_LOCAL: 1900 sc.len = sasize + 4; 1901 sockaddr_to_netaddr_un(&sc, &saun); 1902 break; 1903 1904 default: 1905 mtx_unlock(&Giant); 1906 return ENOSYS; 1907 } 1908 1909 dat.len = *retval; 1910 fl = 0; 1911 st->s_cmd = sc.cmd; 1912 break; 1913 1914 default: 1915 st->s_cmd = sc.cmd; 1916 if (st->s_cmd == SVR4_TI_CONNECT_REQUEST) { 1917 struct read_args ra; 1918 1919 /* More weirdness: Again, I can't find documentation 1920 * to back this up, but when a process does a generic 1921 * "getmsg()" call it seems that the command field is 1922 * zero and the length of the data area is zero. I 1923 * think processes expect getmsg() to fill in dat.len 1924 * after reading at most dat.maxlen octets from the 1925 * stream. Since we're using sockets I can let 1926 * read() look after it and frob return values 1927 * appropriately (or inappropriately :-) 1928 * -- newton@atdot.dotat.org XXX 1929 */ 1930 ra.fd = uap->fd; 1931 ra.buf = dat.buf; 1932 ra.nbyte = dat.maxlen; 1933 if ((error = sys_read(td, &ra)) != 0) { 1934 mtx_unlock(&Giant); 1935 return error; 1936 } 1937 dat.len = *retval; 1938 *retval = 0; 1939 st->s_cmd = SVR4_TI_SENDTO_REQUEST; 1940 break; 1941 } 1942 mtx_unlock(&Giant); 1943 DPRINTF(("getmsg: Unknown state %x\n", st->s_cmd)); 1944 return EINVAL; 1945 } 1946 1947 if (uap->ctl) { 1948 if (ctl.len > sizeof(sc)) 1949 ctl.len = sizeof(sc); 1950 if (ctl.len != -1) 1951 error = copyout(&sc, ctl.buf, ctl.len); 1952 1953 if (error == 0) 1954 error = copyout(&ctl, uap->ctl, sizeof(ctl)); 1955 } 1956 1957 if (uap->dat) { 1958 if (error == 0) 1959 error = copyout(&dat, uap->dat, sizeof(dat)); 1960 } 1961 1962 if (uap->flags) { /* XXX: Need translation */ 1963 if (error == 0) 1964 error = copyout(&fl, uap->flags, sizeof(fl)); 1965 } 1966 1967 if (error) { 1968 if (afp) { 1969 fdclose(td->td_proc->p_fd, afp, st->s_afd, td); 1970 fdrop(afp, td); 1971 st->s_afd = -1; 1972 } 1973 mtx_unlock(&Giant); 1974 return (error); 1975 } 1976 mtx_unlock(&Giant); 1977 if (afp) 1978 fdrop(afp, td); 1979 1980 *retval = 0; 1981 1982#ifdef DEBUG_SVR4 1983 show_msg("<getmsg", uap->fd, uap->ctl, 1984 uap->dat, fl); 1985#endif /* DEBUG_SVR4 */ 1986 return error; 1987} 1988 1989int svr4_sys_send(td, uap) 1990 struct thread *td; 1991 struct svr4_sys_send_args *uap; 1992{ 1993 struct sendto_args sta; 1994 1995 sta.s = uap->s; 1996 sta.buf = uap->buf; 1997 sta.len = uap->len; 1998 sta.flags = uap->flags; 1999 sta.to = NULL; 2000 sta.tolen = 0; 2001 2002 return (sys_sendto(td, &sta)); 2003} 2004 2005int svr4_sys_recv(td, uap) 2006 struct thread *td; 2007 struct svr4_sys_recv_args *uap; 2008{ 2009 struct recvfrom_args rfa; 2010 2011 rfa.s = uap->s; 2012 rfa.buf = uap->buf; 2013 rfa.len = uap->len; 2014 rfa.flags = uap->flags; 2015 rfa.from = NULL; 2016 rfa.fromlenaddr = NULL; 2017 2018 return (sys_recvfrom(td, &rfa)); 2019} 2020 2021/* 2022 * XXX This isn't necessary, but it's handy for inserting debug code into 2023 * sendto(). Let's leave it here for now... 2024 */ 2025int 2026svr4_sys_sendto(td, uap) 2027 struct thread *td; 2028 struct svr4_sys_sendto_args *uap; 2029{ 2030 struct sendto_args sa; 2031 2032 sa.s = uap->s; 2033 sa.buf = uap->buf; 2034 sa.len = uap->len; 2035 sa.flags = uap->flags; 2036 sa.to = (caddr_t)uap->to; 2037 sa.tolen = uap->tolen; 2038 2039 DPRINTF(("calling sendto()\n")); 2040 return sys_sendto(td, &sa); 2041} 2042 2043