1 /* $NetBSD: kern_descrip.c,v 1.67 2000/05/26 23:10:36 sommerfeld Exp $ */ 2 3 /* 4 * Copyright (c) 1982, 1986, 1989, 1991, 1993 5 * The Regents of the University of California. All rights reserved. 6 * (c) UNIX System Laboratories, Inc. 7 * All or some portions of this file are derived from material licensed 8 * to the University of California by American Telephone and Telegraph 9 * Co. or Unix System Laboratories, Inc. and are reproduced herein with 10 * the permission of UNIX System Laboratories, Inc. 11 * 12 * Redistribution and use in source and binary forms, with or without 13 * modification, are permitted provided that the following conditions 14 * are met: 15 * 1. Redistributions of source code must retain the above copyright 16 * notice, this list of conditions and the following disclaimer. 17 * 2. Redistributions in binary form must reproduce the above copyright 18 * notice, this list of conditions and the following disclaimer in the 19 * documentation and/or other materials provided with the distribution. 20 * 3. All advertising materials mentioning features or use of this software 21 * must display the following acknowledgement: 22 * This product includes software developed by the University of 23 * California, Berkeley and its contributors. 24 * 4. Neither the name of the University nor the names of its contributors 25 * may be used to endorse or promote products derived from this software 26 * without specific prior written permission. 27 * 28 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 29 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 30 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 31 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 32 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 33 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 34 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 35 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 36 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 37 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 38 * SUCH DAMAGE. 39 * 40 * @(#)kern_descrip.c 8.8 (Berkeley) 2/14/95 41 */ 42 43 #include <sys/param.h> 44 #include <sys/systm.h> 45 #include <sys/filedesc.h> 46 #include <sys/kernel.h> 47 #include <sys/vnode.h> 48 #include <sys/proc.h> 49 #include <sys/file.h> 50 #include <sys/socket.h> 51 #include <sys/socketvar.h> 52 #include <sys/stat.h> 53 #include <sys/ioctl.h> 54 #include <sys/fcntl.h> 55 #include <sys/malloc.h> 56 #include <sys/pool.h> 57 #include <sys/syslog.h> 58 #include <sys/unistd.h> 59 #include <sys/resourcevar.h> 60 #include <sys/conf.h> 61 62 #include <sys/mount.h> 63 #include <sys/syscallargs.h> 64 65 #include <vm/vm.h> 66 67 /* 68 * Descriptor management. 69 */ 70 struct filelist filehead; /* head of list of open files */ 71 int nfiles; /* actual number of open files */ 72 struct pool file_pool; /* memory pool for file structures */ 73 struct pool cwdi_pool; /* memory pool for cwdinfo structures */ 74 struct pool filedesc0_pool; /* memory pool for filedesc0 structures */ 75 76 static __inline void fd_used __P((struct filedesc *, int)); 77 static __inline void fd_unused __P((struct filedesc *, int)); 78 int finishdup __P((struct proc *, int, int, register_t *)); 79 80 static __inline void 81 fd_used(fdp, fd) 82 struct filedesc *fdp; 83 int fd; 84 { 85 86 if (fd > fdp->fd_lastfile) 87 fdp->fd_lastfile = fd; 88 } 89 90 static __inline void 91 fd_unused(fdp, fd) 92 struct filedesc *fdp; 93 int fd; 94 { 95 96 if (fd < fdp->fd_freefile) 97 fdp->fd_freefile = fd; 98 #ifdef DIAGNOSTIC 99 if (fd > fdp->fd_lastfile) 100 panic("fd_unused: fd_lastfile inconsistent"); 101 #endif 102 if (fd == fdp->fd_lastfile) { 103 do { 104 fd--; 105 } while (fd >= 0 && fdp->fd_ofiles[fd] == NULL); 106 fdp->fd_lastfile = fd; 107 } 108 } 109 110 /* 111 * System calls on descriptors. 112 */ 113 114 /* 115 * Duplicate a file descriptor. 116 */ 117 /* ARGSUSED */ 118 int 119 sys_dup(p, v, retval) 120 struct proc *p; 121 void *v; 122 register_t *retval; 123 { 124 struct sys_dup_args /* { 125 syscallarg(int) fd; 126 } */ *uap = v; 127 struct file *fp; 128 struct filedesc *fdp = p->p_fd; 129 int old = SCARG(uap, fd); 130 int new; 131 int error; 132 133 if ((u_int)old >= fdp->fd_nfiles || 134 (fp = fdp->fd_ofiles[old]) == NULL || 135 (fp->f_iflags & FIF_WANTCLOSE) != 0) 136 return (EBADF); 137 138 FILE_USE(fp); 139 140 if ((error = fdalloc(p, 0, &new)) != 0) { 141 FILE_UNUSE(fp, p); 142 return (error); 143 } 144 145 /* finishdup() will unuse the descriptors for us */ 146 return (finishdup(p, old, new, retval)); 147 } 148 149 /* 150 * Duplicate a file descriptor to a particular value. 151 */ 152 /* ARGSUSED */ 153 int 154 sys_dup2(p, v, retval) 155 struct proc *p; 156 void *v; 157 register_t *retval; 158 { 159 struct sys_dup2_args /* { 160 syscallarg(int) from; 161 syscallarg(int) to; 162 } */ *uap = v; 163 struct file *fp; 164 struct filedesc *fdp = p->p_fd; 165 int old = SCARG(uap, from), new = SCARG(uap, to); 166 int i, error; 167 168 if ((u_int)old >= fdp->fd_nfiles || 169 (fp = fdp->fd_ofiles[old]) == NULL || 170 (fp->f_iflags & FIF_WANTCLOSE) != 0 || 171 (u_int)new >= p->p_rlimit[RLIMIT_NOFILE].rlim_cur || 172 (u_int)new >= maxfiles) 173 return (EBADF); 174 if (old == new) { 175 *retval = new; 176 return (0); 177 } 178 179 FILE_USE(fp); 180 181 if (new >= fdp->fd_nfiles) { 182 if ((error = fdalloc(p, new, &i)) != 0) { 183 FILE_UNUSE(fp, p); 184 return (error); 185 } 186 if (new != i) 187 panic("dup2: fdalloc"); 188 } else { 189 (void) fdrelease(p, new); 190 } 191 192 /* finishdup() will unuse the descriptors for us */ 193 return (finishdup(p, old, new, retval)); 194 } 195 196 int fcntl_forfs __P((int, struct proc *, int, void *)); 197 198 /* 199 * The file control system call. 200 */ 201 /* ARGSUSED */ 202 int 203 sys_fcntl(p, v, retval) 204 struct proc *p; 205 void *v; 206 register_t *retval; 207 { 208 struct sys_fcntl_args /* { 209 syscallarg(int) fd; 210 syscallarg(int) cmd; 211 syscallarg(void *) arg; 212 } */ *uap = v; 213 int fd = SCARG(uap, fd); 214 struct filedesc *fdp = p->p_fd; 215 struct file *fp; 216 struct vnode *vp; 217 int i, tmp, error = 0, flg = F_POSIX, cmd; 218 struct flock fl; 219 int newmin; 220 221 if ((u_int)fd >= fdp->fd_nfiles || 222 (fp = fdp->fd_ofiles[fd]) == NULL || 223 (fp->f_iflags & FIF_WANTCLOSE) != 0) 224 return (EBADF); 225 226 FILE_USE(fp); 227 228 cmd = SCARG(uap, cmd); 229 if ((cmd & F_FSCTL)) { 230 error = fcntl_forfs(fd, p, cmd, SCARG(uap, arg)); 231 goto out; 232 } 233 234 switch (cmd) { 235 236 case F_DUPFD: 237 newmin = (long)SCARG(uap, arg); 238 if ((u_int)newmin >= p->p_rlimit[RLIMIT_NOFILE].rlim_cur || 239 (u_int)newmin >= maxfiles) { 240 error = EINVAL; 241 goto out; 242 } 243 if ((error = fdalloc(p, newmin, &i)) != 0) 244 goto out; 245 246 /* finishdup() will unuse the descriptors for us */ 247 return (finishdup(p, fd, i, retval)); 248 249 case F_GETFD: 250 *retval = fdp->fd_ofileflags[fd] & UF_EXCLOSE ? 1 : 0; 251 break; 252 253 case F_SETFD: 254 if ((long)SCARG(uap, arg) & 1) 255 fdp->fd_ofileflags[fd] |= UF_EXCLOSE; 256 else 257 fdp->fd_ofileflags[fd] &= ~UF_EXCLOSE; 258 break; 259 260 case F_GETFL: 261 *retval = OFLAGS(fp->f_flag); 262 break; 263 264 case F_SETFL: 265 tmp = FFLAGS((long)SCARG(uap, arg)) & FCNTLFLAGS; 266 error = (*fp->f_ops->fo_fcntl)(fp, F_SETFL, (caddr_t)&tmp, p); 267 if (error) 268 goto out; 269 fp->f_flag &= ~FCNTLFLAGS; 270 fp->f_flag |= tmp; 271 tmp = fp->f_flag & FNONBLOCK; 272 error = (*fp->f_ops->fo_ioctl)(fp, FIONBIO, (caddr_t)&tmp, p); 273 if (error) 274 goto out; 275 tmp = fp->f_flag & FASYNC; 276 error = (*fp->f_ops->fo_ioctl)(fp, FIOASYNC, (caddr_t)&tmp, p); 277 if (error == 0) 278 goto out; 279 fp->f_flag &= ~FNONBLOCK; 280 tmp = 0; 281 (void) (*fp->f_ops->fo_ioctl)(fp, FIONBIO, (caddr_t)&tmp, p); 282 break; 283 284 case F_GETOWN: 285 if (fp->f_type == DTYPE_SOCKET) { 286 *retval = ((struct socket *)fp->f_data)->so_pgid; 287 goto out; 288 } 289 error = (*fp->f_ops->fo_ioctl) 290 (fp, TIOCGPGRP, (caddr_t)retval, p); 291 *retval = -*retval; 292 break; 293 294 case F_SETOWN: 295 if (fp->f_type == DTYPE_SOCKET) { 296 ((struct socket *)fp->f_data)->so_pgid = 297 (long)SCARG(uap, arg); 298 goto out; 299 } 300 if ((long)SCARG(uap, arg) <= 0) { 301 SCARG(uap, arg) = (void *)(-(long)SCARG(uap, arg)); 302 } else { 303 struct proc *p1 = pfind((long)SCARG(uap, arg)); 304 if (p1 == 0) { 305 error = ESRCH; 306 goto out; 307 } 308 SCARG(uap, arg) = (void *)(long)p1->p_pgrp->pg_id; 309 } 310 error = (*fp->f_ops->fo_ioctl) 311 (fp, TIOCSPGRP, (caddr_t)&SCARG(uap, arg), p); 312 break; 313 314 case F_SETLKW: 315 flg |= F_WAIT; 316 /* Fall into F_SETLK */ 317 318 case F_SETLK: 319 if (fp->f_type != DTYPE_VNODE) { 320 error = EINVAL; 321 goto out; 322 } 323 vp = (struct vnode *)fp->f_data; 324 /* Copy in the lock structure */ 325 error = copyin((caddr_t)SCARG(uap, arg), (caddr_t)&fl, 326 sizeof(fl)); 327 if (error) 328 goto out; 329 if (fl.l_whence == SEEK_CUR) 330 fl.l_start += fp->f_offset; 331 switch (fl.l_type) { 332 case F_RDLCK: 333 if ((fp->f_flag & FREAD) == 0) { 334 error = EBADF; 335 goto out; 336 } 337 p->p_flag |= P_ADVLOCK; 338 error = VOP_ADVLOCK(vp, (caddr_t)p, F_SETLK, &fl, flg); 339 goto out; 340 341 case F_WRLCK: 342 if ((fp->f_flag & FWRITE) == 0) { 343 error = EBADF; 344 goto out; 345 } 346 p->p_flag |= P_ADVLOCK; 347 error = VOP_ADVLOCK(vp, (caddr_t)p, F_SETLK, &fl, flg); 348 goto out; 349 350 case F_UNLCK: 351 error = VOP_ADVLOCK(vp, (caddr_t)p, F_UNLCK, &fl, 352 F_POSIX); 353 goto out; 354 355 default: 356 error = EINVAL; 357 goto out; 358 } 359 360 case F_GETLK: 361 if (fp->f_type != DTYPE_VNODE) { 362 error = EINVAL; 363 goto out; 364 } 365 vp = (struct vnode *)fp->f_data; 366 /* Copy in the lock structure */ 367 error = copyin((caddr_t)SCARG(uap, arg), (caddr_t)&fl, 368 sizeof(fl)); 369 if (error) 370 goto out; 371 if (fl.l_whence == SEEK_CUR) 372 fl.l_start += fp->f_offset; 373 if (fl.l_type != F_RDLCK && 374 fl.l_type != F_WRLCK && 375 fl.l_type != F_UNLCK) { 376 error = EINVAL; 377 goto out; 378 } 379 error = VOP_ADVLOCK(vp, (caddr_t)p, F_GETLK, &fl, F_POSIX); 380 if (error) 381 goto out; 382 error = copyout((caddr_t)&fl, (caddr_t)SCARG(uap, arg), 383 sizeof(fl)); 384 break; 385 386 default: 387 error = EINVAL; 388 } 389 390 out: 391 FILE_UNUSE(fp, p); 392 return (error); 393 } 394 395 /* 396 * Common code for dup, dup2, and fcntl(F_DUPFD). 397 */ 398 int 399 finishdup(p, old, new, retval) 400 struct proc *p; 401 int old, new; 402 register_t *retval; 403 { 404 struct filedesc *fdp = p->p_fd; 405 struct file *fp; 406 407 /* 408 * Note: `old' is already used for us. 409 */ 410 411 fp = fdp->fd_ofiles[old]; 412 fdp->fd_ofiles[new] = fp; 413 fdp->fd_ofileflags[new] = fdp->fd_ofileflags[old] &~ UF_EXCLOSE; 414 fp->f_count++; 415 fd_used(fdp, new); 416 *retval = new; 417 FILE_UNUSE(fp, p); 418 return (0); 419 } 420 421 void 422 fdremove(fdp, fd) 423 struct filedesc *fdp; 424 int fd; 425 { 426 427 fdp->fd_ofiles[fd] = NULL; 428 fd_unused(fdp, fd); 429 } 430 431 int 432 fdrelease(p, fd) 433 struct proc *p; 434 int fd; 435 { 436 struct filedesc *fdp = p->p_fd; 437 struct file **fpp, *fp; 438 char *pf; 439 440 fpp = &fdp->fd_ofiles[fd]; 441 fp = *fpp; 442 if (fp == NULL) 443 return (EBADF); 444 445 FILE_USE(fp); 446 447 pf = &fdp->fd_ofileflags[fd]; 448 if (*pf & UF_MAPPED) { 449 /* XXX: USELESS? XXXCDC check it */ 450 p->p_fd->fd_ofileflags[fd] &= ~UF_MAPPED; 451 } 452 *fpp = NULL; 453 *pf = 0; 454 fd_unused(fdp, fd); 455 return (closef(fp, p)); 456 } 457 458 /* 459 * Close a file descriptor. 460 */ 461 /* ARGSUSED */ 462 int 463 sys_close(p, v, retval) 464 struct proc *p; 465 void *v; 466 register_t *retval; 467 { 468 struct sys_close_args /* { 469 syscallarg(int) fd; 470 } */ *uap = v; 471 int fd = SCARG(uap, fd); 472 struct filedesc *fdp = p->p_fd; 473 474 if ((u_int)fd >= fdp->fd_nfiles) 475 return (EBADF); 476 return (fdrelease(p, fd)); 477 } 478 479 /* 480 * Return status information about a file descriptor. 481 */ 482 /* ARGSUSED */ 483 int 484 sys___fstat13(p, v, retval) 485 struct proc *p; 486 void *v; 487 register_t *retval; 488 { 489 struct sys___fstat13_args /* { 490 syscallarg(int) fd; 491 syscallarg(struct stat *) sb; 492 } */ *uap = v; 493 int fd = SCARG(uap, fd); 494 struct filedesc *fdp = p->p_fd; 495 struct file *fp; 496 struct stat ub; 497 int error; 498 499 if ((u_int)fd >= fdp->fd_nfiles || 500 (fp = fdp->fd_ofiles[fd]) == NULL || 501 (fp->f_iflags & FIF_WANTCLOSE) != 0) 502 return (EBADF); 503 504 FILE_USE(fp); 505 506 switch (fp->f_type) { 507 508 case DTYPE_VNODE: 509 error = vn_stat((struct vnode *)fp->f_data, &ub, p); 510 break; 511 512 case DTYPE_SOCKET: 513 error = soo_stat((struct socket *)fp->f_data, &ub); 514 break; 515 516 default: 517 panic("fstat"); 518 /*NOTREACHED*/ 519 } 520 if (error == 0) 521 error = copyout(&ub, SCARG(uap, sb), sizeof(ub)); 522 FILE_UNUSE(fp, p); 523 return (error); 524 } 525 526 /* 527 * Return pathconf information about a file descriptor. 528 */ 529 /* ARGSUSED */ 530 int 531 sys_fpathconf(p, v, retval) 532 struct proc *p; 533 void *v; 534 register_t *retval; 535 { 536 struct sys_fpathconf_args /* { 537 syscallarg(int) fd; 538 syscallarg(int) name; 539 } */ *uap = v; 540 int fd = SCARG(uap, fd); 541 struct filedesc *fdp = p->p_fd; 542 struct file *fp; 543 struct vnode *vp; 544 int error = 0; 545 546 if ((u_int)fd >= fdp->fd_nfiles || 547 (fp = fdp->fd_ofiles[fd]) == NULL || 548 (fp->f_iflags & FIF_WANTCLOSE) != 0) 549 return (EBADF); 550 551 FILE_USE(fp); 552 553 switch (fp->f_type) { 554 555 case DTYPE_SOCKET: 556 if (SCARG(uap, name) != _PC_PIPE_BUF) 557 error = EINVAL; 558 else 559 *retval = PIPE_BUF; 560 break; 561 562 case DTYPE_VNODE: 563 vp = (struct vnode *)fp->f_data; 564 error = VOP_PATHCONF(vp, SCARG(uap, name), retval); 565 break; 566 567 default: 568 panic("fpathconf"); 569 } 570 571 FILE_UNUSE(fp, p); 572 return (error); 573 } 574 575 /* 576 * Allocate a file descriptor for the process. 577 */ 578 int fdexpand; 579 580 int 581 fdalloc(p, want, result) 582 struct proc *p; 583 int want; 584 int *result; 585 { 586 struct filedesc *fdp = p->p_fd; 587 int i; 588 int lim, last, nfiles; 589 struct file **newofile; 590 char *newofileflags; 591 592 /* 593 * Search for a free descriptor starting at the higher 594 * of want or fd_freefile. If that fails, consider 595 * expanding the ofile array. 596 */ 597 lim = min((int)p->p_rlimit[RLIMIT_NOFILE].rlim_cur, maxfiles); 598 for (;;) { 599 last = min(fdp->fd_nfiles, lim); 600 if ((i = want) < fdp->fd_freefile) 601 i = fdp->fd_freefile; 602 for (; i < last; i++) { 603 if (fdp->fd_ofiles[i] == NULL) { 604 fd_used(fdp, i); 605 if (want <= fdp->fd_freefile) 606 fdp->fd_freefile = i; 607 *result = i; 608 return (0); 609 } 610 } 611 612 /* 613 * No space in current array. Expand? 614 */ 615 if (fdp->fd_nfiles >= lim) 616 return (EMFILE); 617 if (fdp->fd_nfiles < NDEXTENT) 618 nfiles = NDEXTENT; 619 else 620 nfiles = 2 * fdp->fd_nfiles; 621 newofile = malloc(nfiles * OFILESIZE, M_FILEDESC, M_WAITOK); 622 newofileflags = (char *) &newofile[nfiles]; 623 /* 624 * Copy the existing ofile and ofileflags arrays 625 * and zero the new portion of each array. 626 */ 627 memcpy(newofile, fdp->fd_ofiles, 628 (i = sizeof(struct file *) * fdp->fd_nfiles)); 629 memset((char *)newofile + i, 0, nfiles * sizeof(struct file *) - i); 630 memcpy(newofileflags, fdp->fd_ofileflags, 631 (i = sizeof(char) * fdp->fd_nfiles)); 632 memset(newofileflags + i, 0, nfiles * sizeof(char) - i); 633 if (fdp->fd_nfiles > NDFILE) 634 free(fdp->fd_ofiles, M_FILEDESC); 635 fdp->fd_ofiles = newofile; 636 fdp->fd_ofileflags = newofileflags; 637 fdp->fd_nfiles = nfiles; 638 fdexpand++; 639 } 640 } 641 642 /* 643 * Check to see whether n user file descriptors 644 * are available to the process p. 645 */ 646 int 647 fdavail(p, n) 648 struct proc *p; 649 int n; 650 { 651 struct filedesc *fdp = p->p_fd; 652 struct file **fpp; 653 int i, lim; 654 655 lim = min((int)p->p_rlimit[RLIMIT_NOFILE].rlim_cur, maxfiles); 656 if ((i = lim - fdp->fd_nfiles) > 0 && (n -= i) <= 0) 657 return (1); 658 fpp = &fdp->fd_ofiles[fdp->fd_freefile]; 659 for (i = min(lim,fdp->fd_nfiles) - fdp->fd_freefile; --i >= 0; fpp++) 660 if (*fpp == NULL && --n <= 0) 661 return (1); 662 return (0); 663 } 664 665 /* 666 * Initialize the data structures necessary for managing files. 667 */ 668 void 669 finit() 670 { 671 672 pool_init(&file_pool, sizeof(struct file), 0, 0, 0, "filepl", 673 0, pool_page_alloc_nointr, pool_page_free_nointr, M_FILE); 674 pool_init(&cwdi_pool, sizeof(struct cwdinfo), 0, 0, 0, "cwdipl", 675 0, pool_page_alloc_nointr, pool_page_free_nointr, M_FILEDESC); 676 pool_init(&filedesc0_pool, sizeof(struct filedesc0), 0, 0, 0, "fdescpl", 677 0, pool_page_alloc_nointr, pool_page_free_nointr, M_FILEDESC); 678 } 679 680 /* 681 * Create a new open file structure and allocate 682 * a file decriptor for the process that refers to it. 683 */ 684 int 685 falloc(p, resultfp, resultfd) 686 struct proc *p; 687 struct file **resultfp; 688 int *resultfd; 689 { 690 struct file *fp, *fq; 691 int error, i; 692 693 if ((error = fdalloc(p, 0, &i)) != 0) 694 return (error); 695 if (nfiles >= maxfiles) { 696 tablefull("file"); 697 return (ENFILE); 698 } 699 /* 700 * Allocate a new file descriptor. 701 * If the process has file descriptor zero open, add to the list 702 * of open files at that point, otherwise put it at the front of 703 * the list of open files. 704 */ 705 nfiles++; 706 fp = pool_get(&file_pool, PR_WAITOK); 707 memset(fp, 0, sizeof(struct file)); 708 if ((fq = p->p_fd->fd_ofiles[0]) != NULL) { 709 LIST_INSERT_AFTER(fq, fp, f_list); 710 } else { 711 LIST_INSERT_HEAD(&filehead, fp, f_list); 712 } 713 p->p_fd->fd_ofiles[i] = fp; 714 fp->f_count = 1; 715 fp->f_cred = p->p_ucred; 716 crhold(fp->f_cred); 717 if (resultfp) { 718 FILE_USE(fp); 719 *resultfp = fp; 720 } 721 if (resultfd) 722 *resultfd = i; 723 return (0); 724 } 725 726 /* 727 * Free a file descriptor. 728 */ 729 void 730 ffree(fp) 731 struct file *fp; 732 { 733 734 #ifdef DIAGNOSTIC 735 if (fp->f_usecount) 736 panic("ffree"); 737 #endif 738 739 LIST_REMOVE(fp, f_list); 740 crfree(fp->f_cred); 741 #ifdef DIAGNOSTIC 742 fp->f_count = 0; 743 #endif 744 nfiles--; 745 pool_put(&file_pool, fp); 746 } 747 748 /* 749 * Create an initial cwdinfo structure, using the same current and root 750 * directories as p. 751 */ 752 struct cwdinfo * 753 cwdinit(p) 754 struct proc *p; 755 { 756 struct cwdinfo *cwdi; 757 758 cwdi = pool_get(&cwdi_pool, PR_WAITOK); 759 760 cwdi->cwdi_cdir = p->p_cwdi->cwdi_cdir; 761 if (cwdi->cwdi_cdir) 762 VREF(cwdi->cwdi_cdir); 763 cwdi->cwdi_rdir = p->p_cwdi->cwdi_rdir; 764 if (cwdi->cwdi_rdir) 765 VREF(cwdi->cwdi_rdir); 766 cwdi->cwdi_cmask = p->p_cwdi->cwdi_cmask; 767 cwdi->cwdi_refcnt = 1; 768 769 return (cwdi); 770 } 771 772 /* 773 * Make p2 share p1's cwdinfo. 774 */ 775 void 776 cwdshare(p1, p2) 777 struct proc *p1, *p2; 778 { 779 780 p2->p_cwdi = p1->p_cwdi; 781 p1->p_cwdi->cwdi_refcnt++; 782 } 783 784 /* 785 * Make this process not share its cwdinfo structure, maintaining 786 * all cwdinfo state. 787 */ 788 void 789 cwdunshare(p) 790 struct proc *p; 791 { 792 struct cwdinfo *newcwdi; 793 794 if (p->p_cwdi->cwdi_refcnt == 1) 795 return; 796 797 newcwdi = cwdinit(p); 798 cwdfree(p); 799 p->p_cwdi = newcwdi; 800 } 801 802 /* 803 * Release a cwdinfo structure. 804 */ 805 void 806 cwdfree(p) 807 struct proc *p; 808 { 809 struct cwdinfo *cwdi = p->p_cwdi; 810 811 if (--cwdi->cwdi_refcnt > 0) 812 return; 813 814 p->p_cwdi = NULL; 815 816 vrele(cwdi->cwdi_cdir); 817 if (cwdi->cwdi_rdir) 818 vrele(cwdi->cwdi_rdir); 819 pool_put(&cwdi_pool, cwdi); 820 } 821 822 /* 823 * Create an initial filedesc structure, using the same current and root 824 * directories as p. 825 */ 826 struct filedesc * 827 fdinit(p) 828 struct proc *p; 829 { 830 struct filedesc0 *newfdp; 831 832 newfdp = pool_get(&filedesc0_pool, PR_WAITOK); 833 memset(newfdp, 0, sizeof(struct filedesc0)); 834 835 fdinit1(newfdp); 836 837 return (&newfdp->fd_fd); 838 } 839 840 /* 841 * Initialize a file descriptor table. 842 */ 843 void 844 fdinit1(newfdp) 845 struct filedesc0 *newfdp; 846 { 847 848 newfdp->fd_fd.fd_refcnt = 1; 849 newfdp->fd_fd.fd_ofiles = newfdp->fd_dfiles; 850 newfdp->fd_fd.fd_ofileflags = newfdp->fd_dfileflags; 851 newfdp->fd_fd.fd_nfiles = NDFILE; 852 } 853 854 /* 855 * Make p2 share p1's filedesc structure. 856 */ 857 void 858 fdshare(p1, p2) 859 struct proc *p1, *p2; 860 { 861 862 p2->p_fd = p1->p_fd; 863 p1->p_fd->fd_refcnt++; 864 } 865 866 /* 867 * Make this process not share its filedesc structure, maintaining 868 * all file descriptor state. 869 */ 870 void 871 fdunshare(p) 872 struct proc *p; 873 { 874 struct filedesc *newfd; 875 876 if (p->p_fd->fd_refcnt == 1) 877 return; 878 879 newfd = fdcopy(p); 880 fdfree(p); 881 p->p_fd = newfd; 882 } 883 884 /* 885 * Clear a process's fd table. 886 */ 887 void 888 fdclear(p) 889 struct proc *p; 890 { 891 struct filedesc *newfd; 892 893 newfd = fdinit(p); 894 fdfree(p); 895 p->p_fd = newfd; 896 } 897 898 /* 899 * Copy a filedesc structure. 900 */ 901 struct filedesc * 902 fdcopy(p) 903 struct proc *p; 904 { 905 struct filedesc *newfdp, *fdp = p->p_fd; 906 struct file **fpp; 907 int i; 908 909 newfdp = pool_get(&filedesc0_pool, PR_WAITOK); 910 memcpy(newfdp, fdp, sizeof(struct filedesc)); 911 newfdp->fd_refcnt = 1; 912 913 /* 914 * If the number of open files fits in the internal arrays 915 * of the open file structure, use them, otherwise allocate 916 * additional memory for the number of descriptors currently 917 * in use. 918 */ 919 if (newfdp->fd_lastfile < NDFILE) { 920 newfdp->fd_ofiles = ((struct filedesc0 *) newfdp)->fd_dfiles; 921 newfdp->fd_ofileflags = 922 ((struct filedesc0 *) newfdp)->fd_dfileflags; 923 i = NDFILE; 924 } else { 925 /* 926 * Compute the smallest multiple of NDEXTENT needed 927 * for the file descriptors currently in use, 928 * allowing the table to shrink. 929 */ 930 i = newfdp->fd_nfiles; 931 while (i >= 2 * NDEXTENT && i > newfdp->fd_lastfile * 2) 932 i /= 2; 933 newfdp->fd_ofiles = malloc(i * OFILESIZE, M_FILEDESC, M_WAITOK); 934 newfdp->fd_ofileflags = (char *) &newfdp->fd_ofiles[i]; 935 } 936 newfdp->fd_nfiles = i; 937 memcpy(newfdp->fd_ofiles, fdp->fd_ofiles, i * sizeof(struct file **)); 938 memcpy(newfdp->fd_ofileflags, fdp->fd_ofileflags, i * sizeof(char)); 939 fpp = newfdp->fd_ofiles; 940 for (i = newfdp->fd_lastfile; i >= 0; i--, fpp++) 941 if (*fpp != NULL) 942 (*fpp)->f_count++; 943 return (newfdp); 944 } 945 946 /* 947 * Release a filedesc structure. 948 */ 949 void 950 fdfree(p) 951 struct proc *p; 952 { 953 struct filedesc *fdp = p->p_fd; 954 struct file **fpp, *fp; 955 int i; 956 957 if (--fdp->fd_refcnt > 0) 958 return; 959 fpp = fdp->fd_ofiles; 960 for (i = fdp->fd_lastfile; i >= 0; i--, fpp++) { 961 fp = *fpp; 962 if (fp != NULL) { 963 *fpp = NULL; 964 FILE_USE(fp); 965 (void) closef(fp, p); 966 } 967 } 968 p->p_fd = NULL; 969 if (fdp->fd_nfiles > NDFILE) 970 free(fdp->fd_ofiles, M_FILEDESC); 971 pool_put(&filedesc0_pool, fdp); 972 } 973 974 /* 975 * Internal form of close. 976 * Decrement reference count on file structure. 977 * Note: p may be NULL when closing a file 978 * that was being passed in a message. 979 * 980 * Note: we expect the caller is holding a usecount, and expects us 981 * to drop it (the caller thinks the file is going away forever). 982 */ 983 int 984 closef(fp, p) 985 struct file *fp; 986 struct proc *p; 987 { 988 struct vnode *vp; 989 struct flock lf; 990 int error; 991 992 if (fp == NULL) 993 return (0); 994 995 /* 996 * POSIX record locking dictates that any close releases ALL 997 * locks owned by this process. This is handled by setting 998 * a flag in the unlock to free ONLY locks obeying POSIX 999 * semantics, and not to free BSD-style file locks. 1000 * If the descriptor was in a message, POSIX-style locks 1001 * aren't passed with the descriptor. 1002 */ 1003 if (p && (p->p_flag & P_ADVLOCK) && fp->f_type == DTYPE_VNODE) { 1004 lf.l_whence = SEEK_SET; 1005 lf.l_start = 0; 1006 lf.l_len = 0; 1007 lf.l_type = F_UNLCK; 1008 vp = (struct vnode *)fp->f_data; 1009 (void) VOP_ADVLOCK(vp, (caddr_t)p, F_UNLCK, &lf, F_POSIX); 1010 } 1011 1012 /* 1013 * If WANTCLOSE is set, then the reference count on the file 1014 * is 0, but there were multiple users of the file. This can 1015 * happen if a filedesc structure is shared by multiple 1016 * processes. 1017 */ 1018 if (fp->f_iflags & FIF_WANTCLOSE) { 1019 /* 1020 * Another user of the file is already closing, and is 1021 * simply waiting for other users of the file to drain. 1022 * Release our usecount, and wake up the closer if it 1023 * is the only remaining use. 1024 */ 1025 #ifdef DIAGNOSTIC 1026 if (fp->f_count != 0) 1027 panic("closef: wantclose and count != 0"); 1028 if (fp->f_usecount < 2) 1029 panic("closef: wantclose and usecount < 2"); 1030 #endif 1031 if (--fp->f_usecount == 1) 1032 wakeup(&fp->f_usecount); 1033 return (0); 1034 } else { 1035 /* 1036 * Decrement the reference count. If we were not the 1037 * last reference, then release our use and just 1038 * return. 1039 */ 1040 if (--fp->f_count > 0) { 1041 #ifdef DIAGNOSTIC 1042 if (fp->f_usecount < 1) 1043 panic("closef: no wantclose and usecount < 1"); 1044 #endif 1045 fp->f_usecount--; 1046 return (0); 1047 } 1048 if (fp->f_count < 0) 1049 panic("closef: count < 0"); 1050 } 1051 1052 /* 1053 * The reference count is now 0. However, there may be 1054 * multiple potential users of this file. This can happen 1055 * if multiple processes shared a single filedesc structure. 1056 * 1057 * Notify these potential users that the file is closing. 1058 * This will prevent them from adding additional uses to 1059 * the file. 1060 */ 1061 fp->f_iflags |= FIF_WANTCLOSE; 1062 1063 /* 1064 * We expect the caller to add a use to the file. So, if we 1065 * are the last user, usecount will be 1. If it is not, we 1066 * must wait for the usecount to drain. When it drains back 1067 * to 1, we will be awakened so that we may proceed with the 1068 * close. 1069 */ 1070 #ifdef DIAGNOSTIC 1071 if (fp->f_usecount < 1) 1072 panic("closef: usecount < 1"); 1073 #endif 1074 while (fp->f_usecount > 1) 1075 (void) tsleep(&fp->f_usecount, PRIBIO, "closef", 0); 1076 #ifdef DIAGNOSTIC 1077 if (fp->f_usecount != 1) 1078 panic("closef: usecount != 1"); 1079 #endif 1080 1081 if ((fp->f_flag & FHASLOCK) && fp->f_type == DTYPE_VNODE) { 1082 lf.l_whence = SEEK_SET; 1083 lf.l_start = 0; 1084 lf.l_len = 0; 1085 lf.l_type = F_UNLCK; 1086 vp = (struct vnode *)fp->f_data; 1087 (void) VOP_ADVLOCK(vp, (caddr_t)fp, F_UNLCK, &lf, F_FLOCK); 1088 } 1089 if (fp->f_ops) 1090 error = (*fp->f_ops->fo_close)(fp, p); 1091 else 1092 error = 0; 1093 1094 /* Nothing references the file now, drop the final use (us). */ 1095 fp->f_usecount--; 1096 1097 ffree(fp); 1098 return (error); 1099 } 1100 1101 /* 1102 * Apply an advisory lock on a file descriptor. 1103 * 1104 * Just attempt to get a record lock of the requested type on 1105 * the entire file (l_whence = SEEK_SET, l_start = 0, l_len = 0). 1106 */ 1107 /* ARGSUSED */ 1108 int 1109 sys_flock(p, v, retval) 1110 struct proc *p; 1111 void *v; 1112 register_t *retval; 1113 { 1114 struct sys_flock_args /* { 1115 syscallarg(int) fd; 1116 syscallarg(int) how; 1117 } */ *uap = v; 1118 int fd = SCARG(uap, fd); 1119 int how = SCARG(uap, how); 1120 struct filedesc *fdp = p->p_fd; 1121 struct file *fp; 1122 struct vnode *vp; 1123 struct flock lf; 1124 int error = 0; 1125 1126 if ((u_int)fd >= fdp->fd_nfiles || 1127 (fp = fdp->fd_ofiles[fd]) == NULL || 1128 (fp->f_iflags & FIF_WANTCLOSE) != 0) 1129 return (EBADF); 1130 1131 FILE_USE(fp); 1132 1133 if (fp->f_type != DTYPE_VNODE) { 1134 error = EOPNOTSUPP; 1135 goto out; 1136 } 1137 1138 vp = (struct vnode *)fp->f_data; 1139 lf.l_whence = SEEK_SET; 1140 lf.l_start = 0; 1141 lf.l_len = 0; 1142 if (how & LOCK_UN) { 1143 lf.l_type = F_UNLCK; 1144 fp->f_flag &= ~FHASLOCK; 1145 error = VOP_ADVLOCK(vp, (caddr_t)fp, F_UNLCK, &lf, F_FLOCK); 1146 goto out; 1147 } 1148 if (how & LOCK_EX) 1149 lf.l_type = F_WRLCK; 1150 else if (how & LOCK_SH) 1151 lf.l_type = F_RDLCK; 1152 else { 1153 error = EINVAL; 1154 goto out; 1155 } 1156 fp->f_flag |= FHASLOCK; 1157 if (how & LOCK_NB) 1158 error = VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, F_FLOCK); 1159 else 1160 error = VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, 1161 F_FLOCK|F_WAIT); 1162 out: 1163 FILE_UNUSE(fp, p); 1164 return (error); 1165 } 1166 1167 /* 1168 * File Descriptor pseudo-device driver (/dev/fd/). 1169 * 1170 * Opening minor device N dup()s the file (if any) connected to file 1171 * descriptor N belonging to the calling process. Note that this driver 1172 * consists of only the ``open()'' routine, because all subsequent 1173 * references to this file will be direct to the other driver. 1174 */ 1175 /* ARGSUSED */ 1176 int 1177 filedescopen(dev, mode, type, p) 1178 dev_t dev; 1179 int mode, type; 1180 struct proc *p; 1181 { 1182 1183 /* 1184 * XXX Kludge: set p->p_dupfd to contain the value of the 1185 * the file descriptor being sought for duplication. The error 1186 * return ensures that the vnode for this device will be released 1187 * by vn_open. Open will detect this special error and take the 1188 * actions in dupfdopen below. Other callers of vn_open or VOP_OPEN 1189 * will simply report the error. 1190 */ 1191 p->p_dupfd = minor(dev); 1192 return (ENODEV); 1193 } 1194 1195 /* 1196 * Duplicate the specified descriptor to a free descriptor. 1197 */ 1198 int 1199 dupfdopen(p, indx, dfd, mode, error) 1200 struct proc *p; 1201 int indx, dfd, mode, error; 1202 { 1203 struct filedesc *fdp = p->p_fd; 1204 struct file *wfp; 1205 struct file *fp; 1206 1207 /* 1208 * If the to-be-dup'd fd number is greater than the allowed number 1209 * of file descriptors, or the fd to be dup'd has already been 1210 * closed, reject. Note, check for new == old is necessary as 1211 * falloc could allocate an already closed to-be-dup'd descriptor 1212 * as the new descriptor. 1213 */ 1214 fp = fdp->fd_ofiles[indx]; 1215 if ((u_int)dfd >= fdp->fd_nfiles || 1216 (wfp = fdp->fd_ofiles[dfd]) == NULL || 1217 (wfp->f_iflags & FIF_WANTCLOSE) != 0 || 1218 fp == wfp) 1219 return (EBADF); 1220 1221 FILE_USE(wfp); 1222 1223 /* 1224 * There are two cases of interest here. 1225 * 1226 * For ENODEV simply dup (dfd) to file descriptor 1227 * (indx) and return. 1228 * 1229 * For ENXIO steal away the file structure from (dfd) and 1230 * store it in (indx). (dfd) is effectively closed by 1231 * this operation. 1232 * 1233 * Any other error code is just returned. 1234 */ 1235 switch (error) { 1236 case ENODEV: 1237 /* 1238 * Check that the mode the file is being opened for is a 1239 * subset of the mode of the existing descriptor. 1240 */ 1241 if (((mode & (FREAD|FWRITE)) | wfp->f_flag) != wfp->f_flag) { 1242 FILE_UNUSE(wfp, p); 1243 return (EACCES); 1244 } 1245 fdp->fd_ofiles[indx] = wfp; 1246 fdp->fd_ofileflags[indx] = fdp->fd_ofileflags[dfd]; 1247 wfp->f_count++; 1248 fd_used(fdp, indx); 1249 FILE_UNUSE(wfp, p); 1250 return (0); 1251 1252 case ENXIO: 1253 /* 1254 * Steal away the file pointer from dfd, and stuff it into indx. 1255 */ 1256 fdp->fd_ofiles[indx] = fdp->fd_ofiles[dfd]; 1257 fdp->fd_ofileflags[indx] = fdp->fd_ofileflags[dfd]; 1258 fdp->fd_ofiles[dfd] = NULL; 1259 fdp->fd_ofileflags[dfd] = 0; 1260 /* 1261 * Complete the clean up of the filedesc structure by 1262 * recomputing the various hints. 1263 */ 1264 fd_used(fdp, indx); 1265 fd_unused(fdp, dfd); 1266 FILE_UNUSE(wfp, p); 1267 return (0); 1268 1269 default: 1270 FILE_UNUSE(wfp, p); 1271 return (error); 1272 } 1273 /* NOTREACHED */ 1274 } 1275 1276 /* 1277 * fcntl call which is being passed to the file's fs. 1278 */ 1279 int 1280 fcntl_forfs(fd, p, cmd, arg) 1281 int fd, cmd; 1282 struct proc *p; 1283 void *arg; 1284 { 1285 struct file *fp; 1286 struct filedesc *fdp; 1287 int error; 1288 u_int size; 1289 caddr_t data, memp; 1290 #define STK_PARAMS 128 1291 char stkbuf[STK_PARAMS]; 1292 1293 /* fd's value was validated in sys_fcntl before calling this routine */ 1294 fdp = p->p_fd; 1295 fp = fdp->fd_ofiles[fd]; 1296 1297 if ((fp->f_flag & (FREAD | FWRITE)) == 0) 1298 return (EBADF); 1299 1300 /* 1301 * Interpret high order word to find amount of data to be 1302 * copied to/from the user's address space. 1303 */ 1304 size = (size_t)F_PARAM_LEN(cmd); 1305 if (size > F_PARAM_MAX) 1306 return (EINVAL); 1307 memp = NULL; 1308 if (size > sizeof(stkbuf)) { 1309 memp = (caddr_t)malloc((u_long)size, M_IOCTLOPS, M_WAITOK); 1310 data = memp; 1311 } else 1312 data = stkbuf; 1313 if (cmd & F_FSIN) { 1314 if (size) { 1315 error = copyin(arg, data, size); 1316 if (error) { 1317 if (memp) 1318 free(memp, M_IOCTLOPS); 1319 return (error); 1320 } 1321 } else 1322 *(caddr_t *)data = arg; 1323 } else if ((cmd & F_FSOUT) && size) 1324 /* 1325 * Zero the buffer so the user always 1326 * gets back something deterministic. 1327 */ 1328 memset(data, 0, size); 1329 else if (cmd & F_FSVOID) 1330 *(caddr_t *)data = arg; 1331 1332 1333 error = (*fp->f_ops->fo_fcntl)(fp, cmd, data, p); 1334 1335 /* 1336 * Copy any data to user, size was 1337 * already set and checked above. 1338 */ 1339 if (error == 0 && (cmd & F_FSOUT) && size) 1340 error = copyout(data, arg, size); 1341 if (memp) 1342 free(memp, M_IOCTLOPS); 1343 return (error); 1344 } 1345 1346 /* 1347 * Close any files on exec? 1348 */ 1349 void 1350 fdcloseexec(p) 1351 struct proc *p; 1352 { 1353 struct filedesc *fdp = p->p_fd; 1354 int fd; 1355 1356 for (fd = 0; fd <= fdp->fd_lastfile; fd++) 1357 if (fdp->fd_ofileflags[fd] & UF_EXCLOSE) 1358 (void) fdrelease(p, fd); 1359 } 1360