1 /* 2 * Copyright (c) 1982, 1986, 1989 Regents of the University of California. 3 * All rights reserved. 4 * 5 * %sccs.include.redist.c% 6 * 7 * @(#)ufs_vnops.c 7.64.1.1 (Berkeley) 05/19/91 8 */ 9 10 #include "param.h" 11 #include "systm.h" 12 #include "namei.h" 13 #include "resourcevar.h" 14 #include "kernel.h" 15 #include "file.h" 16 #include "stat.h" 17 #include "buf.h" 18 #include "proc.h" 19 #include "conf.h" 20 #include "mount.h" 21 #include "vnode.h" 22 #include "specdev.h" 23 #include "fifo.h" 24 #include "malloc.h" 25 26 #include "lockf.h" 27 #include "quota.h" 28 #include "inode.h" 29 #include "dir.h" 30 #include "fs.h" 31 32 /* 33 * Create a regular file 34 */ 35 ufs_create(ndp, vap, p) 36 struct nameidata *ndp; 37 struct vattr *vap; 38 struct proc *p; 39 { 40 struct inode *ip; 41 int error; 42 43 if (error = maknode(MAKEIMODE(vap->va_type, vap->va_mode), ndp, &ip)) 44 return (error); 45 ndp->ni_vp = ITOV(ip); 46 return (0); 47 } 48 49 /* 50 * Mknod vnode call 51 */ 52 /* ARGSUSED */ 53 ufs_mknod(ndp, vap, cred, p) 54 struct nameidata *ndp; 55 struct ucred *cred; 56 struct vattr *vap; 57 struct proc *p; 58 { 59 register struct vnode *vp; 60 struct inode *ip; 61 int error; 62 63 if (error = maknode(MAKEIMODE(vap->va_type, vap->va_mode), ndp, &ip)) 64 return (error); 65 ip->i_flag |= IACC|IUPD|ICHG; 66 if (vap->va_rdev != VNOVAL) { 67 /* 68 * Want to be able to use this to make badblock 69 * inodes, so don't truncate the dev number. 70 */ 71 ip->i_rdev = vap->va_rdev; 72 } 73 /* 74 * Remove inode so that it will be reloaded by iget and 75 * checked to see if it is an alias of an existing entry 76 * in the inode cache. 77 */ 78 vp = ITOV(ip); 79 vput(vp); 80 vp->v_type = VNON; 81 vgone(vp); 82 return (0); 83 } 84 85 /* 86 * Open called. 87 * 88 * Nothing to do. 89 */ 90 /* ARGSUSED */ 91 ufs_open(vp, mode, cred, p) 92 struct vnode *vp; 93 int mode; 94 struct ucred *cred; 95 struct proc *p; 96 { 97 98 return (0); 99 } 100 101 /* 102 * Close called 103 * 104 * Update the times on the inode. 105 */ 106 /* ARGSUSED */ 107 ufs_close(vp, fflag, cred, p) 108 struct vnode *vp; 109 int fflag; 110 struct ucred *cred; 111 struct proc *p; 112 { 113 register struct inode *ip = VTOI(vp); 114 115 if (vp->v_usecount > 1 && !(ip->i_flag & ILOCKED)) 116 ITIMES(ip, &time, &time); 117 return (0); 118 } 119 120 /* 121 * Check mode permission on inode pointer. Mode is READ, WRITE or EXEC. 122 * The mode is shifted to select the owner/group/other fields. The 123 * super user is granted all permissions. 124 */ 125 ufs_access(vp, mode, cred, p) 126 struct vnode *vp; 127 register int mode; 128 struct ucred *cred; 129 struct proc *p; 130 { 131 register struct inode *ip = VTOI(vp); 132 register gid_t *gp; 133 int i, error; 134 135 #ifdef DIAGNOSTIC 136 if (!VOP_ISLOCKED(vp)) { 137 vprint("ufs_access: not locked", vp); 138 panic("ufs_access: not locked"); 139 } 140 #endif 141 #ifdef QUOTA 142 if (mode & VWRITE) { 143 switch (vp->v_type) { 144 case VREG: case VDIR: case VLNK: 145 if (error = getinoquota(ip)) 146 return (error); 147 } 148 } 149 #endif /* QUOTA */ 150 /* 151 * If you're the super-user, you always get access. 152 */ 153 if (cred->cr_uid == 0) 154 return (0); 155 /* 156 * Access check is based on only one of owner, group, public. 157 * If not owner, then check group. If not a member of the 158 * group, then check public access. 159 */ 160 if (cred->cr_uid != ip->i_uid) { 161 mode >>= 3; 162 gp = cred->cr_groups; 163 for (i = 0; i < cred->cr_ngroups; i++, gp++) 164 if (ip->i_gid == *gp) 165 goto found; 166 mode >>= 3; 167 found: 168 ; 169 } 170 if ((ip->i_mode & mode) != 0) 171 return (0); 172 return (EACCES); 173 } 174 175 /* ARGSUSED */ 176 ufs_getattr(vp, vap, cred, p) 177 struct vnode *vp; 178 register struct vattr *vap; 179 struct ucred *cred; 180 struct proc *p; 181 { 182 register struct inode *ip = VTOI(vp); 183 184 ITIMES(ip, &time, &time); 185 /* 186 * Copy from inode table 187 */ 188 vap->va_fsid = ip->i_dev; 189 vap->va_fileid = ip->i_number; 190 vap->va_mode = ip->i_mode & ~IFMT; 191 vap->va_nlink = ip->i_nlink; 192 vap->va_uid = ip->i_uid; 193 vap->va_gid = ip->i_gid; 194 vap->va_rdev = (dev_t)ip->i_rdev; 195 #ifdef tahoe 196 vap->va_size = ip->i_size; 197 vap->va_size_rsv = 0; 198 #else 199 vap->va_qsize = ip->i_din.di_qsize; 200 #endif 201 vap->va_atime.tv_sec = ip->i_atime; 202 vap->va_atime.tv_usec = 0; 203 vap->va_mtime.tv_sec = ip->i_mtime; 204 vap->va_mtime.tv_usec = 0; 205 vap->va_ctime.tv_sec = ip->i_ctime; 206 vap->va_ctime.tv_usec = 0; 207 vap->va_flags = ip->i_flags; 208 vap->va_gen = ip->i_gen; 209 /* this doesn't belong here */ 210 if (vp->v_type == VBLK) 211 vap->va_blocksize = BLKDEV_IOSIZE; 212 else if (vp->v_type == VCHR) 213 vap->va_blocksize = MAXBSIZE; 214 else 215 vap->va_blocksize = ip->i_fs->fs_bsize; 216 vap->va_bytes = dbtob(ip->i_blocks); 217 vap->va_bytes_rsv = 0; 218 vap->va_type = vp->v_type; 219 return (0); 220 } 221 222 /* 223 * Set attribute vnode op. called from several syscalls 224 */ 225 ufs_setattr(vp, vap, cred, p) 226 register struct vnode *vp; 227 register struct vattr *vap; 228 register struct ucred *cred; 229 struct proc *p; 230 { 231 register struct inode *ip = VTOI(vp); 232 int error = 0; 233 234 /* 235 * Check for unsetable attributes. 236 */ 237 if ((vap->va_type != VNON) || (vap->va_nlink != VNOVAL) || 238 (vap->va_fsid != VNOVAL) || (vap->va_fileid != VNOVAL) || 239 (vap->va_blocksize != VNOVAL) || (vap->va_rdev != VNOVAL) || 240 ((int)vap->va_bytes != VNOVAL) || (vap->va_gen != VNOVAL)) { 241 return (EINVAL); 242 } 243 /* 244 * Go through the fields and update iff not VNOVAL. 245 */ 246 if (vap->va_uid != (u_short)VNOVAL || vap->va_gid != (u_short)VNOVAL) 247 if (error = chown1(vp, vap->va_uid, vap->va_gid, p)) 248 return (error); 249 if (vap->va_size != VNOVAL) { 250 if (vp->v_type == VDIR) 251 return (EISDIR); 252 if (error = itrunc(ip, vap->va_size, 0)) /* XXX IO_SYNC? */ 253 return (error); 254 } 255 if (vap->va_atime.tv_sec != VNOVAL || vap->va_mtime.tv_sec != VNOVAL) { 256 if (cred->cr_uid != ip->i_uid && 257 (error = suser(cred, &p->p_acflag))) 258 return (error); 259 if (vap->va_atime.tv_sec != VNOVAL) 260 ip->i_flag |= IACC; 261 if (vap->va_mtime.tv_sec != VNOVAL) 262 ip->i_flag |= IUPD; 263 ip->i_flag |= ICHG; 264 if (error = iupdat(ip, &vap->va_atime, &vap->va_mtime, 1)) 265 return (error); 266 } 267 if (vap->va_mode != (u_short)VNOVAL) 268 error = chmod1(vp, (int)vap->va_mode, p); 269 if (vap->va_flags != VNOVAL) { 270 if (cred->cr_uid != ip->i_uid && 271 (error = suser(cred, &p->p_acflag))) 272 return (error); 273 if (cred->cr_uid == 0) { 274 ip->i_flags = vap->va_flags; 275 } else { 276 ip->i_flags &= 0xffff0000; 277 ip->i_flags |= (vap->va_flags & 0xffff); 278 } 279 ip->i_flag |= ICHG; 280 } 281 return (error); 282 } 283 284 /* 285 * Change the mode on a file. 286 * Inode must be locked before calling. 287 */ 288 chmod1(vp, mode, p) 289 register struct vnode *vp; 290 register int mode; 291 struct proc *p; 292 { 293 register struct ucred *cred = p->p_ucred; 294 register struct inode *ip = VTOI(vp); 295 int error; 296 297 if (cred->cr_uid != ip->i_uid && 298 (error = suser(cred, &p->p_acflag))) 299 return (error); 300 if (cred->cr_uid) { 301 if (vp->v_type != VDIR && (mode & ISVTX)) 302 return (EFTYPE); 303 if (!groupmember(ip->i_gid, cred) && (mode & ISGID)) 304 return (EPERM); 305 } 306 ip->i_mode &= ~07777; 307 ip->i_mode |= mode & 07777; 308 ip->i_flag |= ICHG; 309 if ((vp->v_flag & VTEXT) && (ip->i_mode & ISVTX) == 0) 310 (void) vnode_pager_uncache(vp); 311 return (0); 312 } 313 314 /* 315 * Perform chown operation on inode ip; 316 * inode must be locked prior to call. 317 */ 318 chown1(vp, uid, gid, p) 319 register struct vnode *vp; 320 uid_t uid; 321 gid_t gid; 322 struct proc *p; 323 { 324 register struct inode *ip = VTOI(vp); 325 register struct ucred *cred = p->p_ucred; 326 uid_t ouid; 327 gid_t ogid; 328 int error = 0; 329 #ifdef QUOTA 330 register int i; 331 long change; 332 #endif 333 334 if (uid == (u_short)VNOVAL) 335 uid = ip->i_uid; 336 if (gid == (u_short)VNOVAL) 337 gid = ip->i_gid; 338 /* 339 * If we don't own the file, are trying to change the owner 340 * of the file, or are not a member of the target group, 341 * the caller must be superuser or the call fails. 342 */ 343 if ((cred->cr_uid != ip->i_uid || uid != ip->i_uid || 344 !groupmember((gid_t)gid, cred)) && 345 (error = suser(cred, &p->p_acflag))) 346 return (error); 347 ouid = ip->i_uid; 348 ogid = ip->i_gid; 349 #ifdef QUOTA 350 if (error = getinoquota(ip)) 351 return (error); 352 if (ouid == uid) { 353 dqrele(vp, ip->i_dquot[USRQUOTA]); 354 ip->i_dquot[USRQUOTA] = NODQUOT; 355 } 356 if (ogid == gid) { 357 dqrele(vp, ip->i_dquot[GRPQUOTA]); 358 ip->i_dquot[GRPQUOTA] = NODQUOT; 359 } 360 change = ip->i_blocks; 361 (void) chkdq(ip, -change, cred, CHOWN); 362 (void) chkiq(ip, -1, cred, CHOWN); 363 for (i = 0; i < MAXQUOTAS; i++) { 364 dqrele(vp, ip->i_dquot[i]); 365 ip->i_dquot[i] = NODQUOT; 366 } 367 #endif 368 ip->i_uid = uid; 369 ip->i_gid = gid; 370 #ifdef QUOTA 371 if ((error = getinoquota(ip)) == 0) { 372 if (ouid == uid) { 373 dqrele(vp, ip->i_dquot[USRQUOTA]); 374 ip->i_dquot[USRQUOTA] = NODQUOT; 375 } 376 if (ogid == gid) { 377 dqrele(vp, ip->i_dquot[GRPQUOTA]); 378 ip->i_dquot[GRPQUOTA] = NODQUOT; 379 } 380 if ((error = chkdq(ip, change, cred, CHOWN)) == 0) { 381 if ((error = chkiq(ip, 1, cred, CHOWN)) == 0) 382 goto good; 383 else 384 (void) chkdq(ip, -change, cred, CHOWN|FORCE); 385 } 386 for (i = 0; i < MAXQUOTAS; i++) { 387 dqrele(vp, ip->i_dquot[i]); 388 ip->i_dquot[i] = NODQUOT; 389 } 390 } 391 ip->i_uid = ouid; 392 ip->i_gid = ogid; 393 if (getinoquota(ip) == 0) { 394 if (ouid == uid) { 395 dqrele(vp, ip->i_dquot[USRQUOTA]); 396 ip->i_dquot[USRQUOTA] = NODQUOT; 397 } 398 if (ogid == gid) { 399 dqrele(vp, ip->i_dquot[GRPQUOTA]); 400 ip->i_dquot[GRPQUOTA] = NODQUOT; 401 } 402 (void) chkdq(ip, change, cred, FORCE|CHOWN); 403 (void) chkiq(ip, 1, cred, FORCE|CHOWN); 404 (void) getinoquota(ip); 405 } 406 return (error); 407 good: 408 if (getinoquota(ip)) 409 panic("chown: lost quota"); 410 #endif /* QUOTA */ 411 if (ouid != uid || ogid != gid) 412 ip->i_flag |= ICHG; 413 if (ouid != uid && cred->cr_uid != 0) 414 ip->i_mode &= ~ISUID; 415 if (ogid != gid && cred->cr_uid != 0) 416 ip->i_mode &= ~ISGID; 417 return (0); 418 } 419 420 /* 421 * Vnode op for reading. 422 */ 423 /* ARGSUSED */ 424 ufs_read(vp, uio, ioflag, cred) 425 struct vnode *vp; 426 register struct uio *uio; 427 int ioflag; 428 struct ucred *cred; 429 { 430 register struct inode *ip = VTOI(vp); 431 register struct fs *fs; 432 struct buf *bp; 433 daddr_t lbn, bn, rablock; 434 int size, diff, error = 0; 435 long n, on, type; 436 437 #ifdef DIAGNOSTIC 438 if (uio->uio_rw != UIO_READ) 439 panic("ufs_read mode"); 440 type = ip->i_mode & IFMT; 441 if (type != IFDIR && type != IFREG && type != IFLNK) 442 panic("ufs_read type"); 443 #endif 444 if (uio->uio_resid == 0) 445 return (0); 446 if (uio->uio_offset < 0) 447 return (EINVAL); 448 ip->i_flag |= IACC; 449 fs = ip->i_fs; 450 do { 451 lbn = lblkno(fs, uio->uio_offset); 452 on = blkoff(fs, uio->uio_offset); 453 n = MIN((unsigned)(fs->fs_bsize - on), uio->uio_resid); 454 diff = ip->i_size - uio->uio_offset; 455 if (diff <= 0) 456 return (0); 457 if (diff < n) 458 n = diff; 459 size = blksize(fs, ip, lbn); 460 rablock = lbn + 1; 461 if (vp->v_lastr + 1 == lbn && 462 lblktosize(fs, rablock) < ip->i_size) 463 error = breada(ITOV(ip), lbn, size, rablock, 464 blksize(fs, ip, rablock), NOCRED, &bp); 465 else 466 error = bread(ITOV(ip), lbn, size, NOCRED, &bp); 467 vp->v_lastr = lbn; 468 n = MIN(n, size - bp->b_resid); 469 if (error) { 470 brelse(bp); 471 return (error); 472 } 473 error = uiomove(bp->b_un.b_addr + on, (int)n, uio); 474 if (n + on == fs->fs_bsize || uio->uio_offset == ip->i_size) 475 bp->b_flags |= B_AGE; 476 brelse(bp); 477 } while (error == 0 && uio->uio_resid > 0 && n != 0); 478 return (error); 479 } 480 481 /* 482 * Vnode op for writing. 483 */ 484 ufs_write(vp, uio, ioflag, cred) 485 register struct vnode *vp; 486 struct uio *uio; 487 int ioflag; 488 struct ucred *cred; 489 { 490 struct proc *p = uio->uio_procp; 491 register struct inode *ip = VTOI(vp); 492 register struct fs *fs; 493 struct buf *bp; 494 daddr_t lbn, bn; 495 u_long osize; 496 int n, on, flags; 497 int size, resid, error = 0; 498 499 #ifdef DIAGNOSTIC 500 if (uio->uio_rw != UIO_WRITE) 501 panic("ufs_write mode"); 502 #endif 503 switch (vp->v_type) { 504 case VREG: 505 if (ioflag & IO_APPEND) 506 uio->uio_offset = ip->i_size; 507 /* fall through */ 508 case VLNK: 509 break; 510 511 case VDIR: 512 if ((ioflag & IO_SYNC) == 0) 513 panic("ufs_write nonsync dir write"); 514 break; 515 516 default: 517 panic("ufs_write type"); 518 } 519 if (uio->uio_offset < 0) 520 return (EINVAL); 521 if (uio->uio_resid == 0) 522 return (0); 523 /* 524 * Maybe this should be above the vnode op call, but so long as 525 * file servers have no limits, i don't think it matters 526 */ 527 if (vp->v_type == VREG && p && 528 uio->uio_offset + uio->uio_resid > 529 p->p_rlimit[RLIMIT_FSIZE].rlim_cur) { 530 psignal(p, SIGXFSZ); 531 return (EFBIG); 532 } 533 resid = uio->uio_resid; 534 osize = ip->i_size; 535 fs = ip->i_fs; 536 flags = 0; 537 if (ioflag & IO_SYNC) 538 flags = B_SYNC; 539 do { 540 lbn = lblkno(fs, uio->uio_offset); 541 on = blkoff(fs, uio->uio_offset); 542 n = MIN((unsigned)(fs->fs_bsize - on), uio->uio_resid); 543 if (n < fs->fs_bsize) 544 flags |= B_CLRBUF; 545 else 546 flags &= ~B_CLRBUF; 547 if (error = balloc(ip, lbn, (int)(on + n), &bp, flags)) 548 break; 549 bn = bp->b_blkno; 550 if (uio->uio_offset + n > ip->i_size) { 551 ip->i_size = uio->uio_offset + n; 552 vnode_pager_setsize(vp, ip->i_size); 553 } 554 size = blksize(fs, ip, lbn); 555 (void) vnode_pager_uncache(vp); 556 n = MIN(n, size - bp->b_resid); 557 error = uiomove(bp->b_un.b_addr + on, n, uio); 558 if (ioflag & IO_SYNC) 559 (void) bwrite(bp); 560 else if (n + on == fs->fs_bsize) { 561 bp->b_flags |= B_AGE; 562 bawrite(bp); 563 } else 564 bdwrite(bp); 565 ip->i_flag |= IUPD|ICHG; 566 if (cred->cr_uid != 0) 567 ip->i_mode &= ~(ISUID|ISGID); 568 } while (error == 0 && uio->uio_resid > 0 && n != 0); 569 if (error && (ioflag & IO_UNIT)) { 570 (void) itrunc(ip, osize, ioflag & IO_SYNC); 571 uio->uio_offset -= resid - uio->uio_resid; 572 uio->uio_resid = resid; 573 } 574 if (!error && (ioflag & IO_SYNC)) 575 error = iupdat(ip, &time, &time, 1); 576 return (error); 577 } 578 579 /* ARGSUSED */ 580 ufs_ioctl(vp, com, data, fflag, cred, p) 581 struct vnode *vp; 582 int com; 583 caddr_t data; 584 int fflag; 585 struct ucred *cred; 586 struct proc *p; 587 { 588 589 return (ENOTTY); 590 } 591 592 /* ARGSUSED */ 593 ufs_select(vp, which, fflags, cred, p) 594 struct vnode *vp; 595 int which, fflags; 596 struct ucred *cred; 597 struct proc *p; 598 { 599 600 /* 601 * We should really check to see if I/O is possible. 602 */ 603 return (1); 604 } 605 606 /* 607 * Mmap a file 608 * 609 * NB Currently unsupported. 610 */ 611 /* ARGSUSED */ 612 ufs_mmap(vp, fflags, cred, p) 613 struct vnode *vp; 614 int fflags; 615 struct ucred *cred; 616 struct proc *p; 617 { 618 619 return (EINVAL); 620 } 621 622 /* 623 * Synch an open file. 624 */ 625 /* ARGSUSED */ 626 ufs_fsync(vp, fflags, cred, waitfor, p) 627 struct vnode *vp; 628 int fflags; 629 struct ucred *cred; 630 int waitfor; 631 struct proc *p; 632 { 633 struct inode *ip = VTOI(vp); 634 635 if (fflags & FWRITE) 636 ip->i_flag |= ICHG; 637 vflushbuf(vp, waitfor == MNT_WAIT ? B_SYNC : 0); 638 return (iupdat(ip, &time, &time, waitfor == MNT_WAIT)); 639 } 640 641 /* 642 * Seek on a file 643 * 644 * Nothing to do, so just return. 645 */ 646 /* ARGSUSED */ 647 ufs_seek(vp, oldoff, newoff, cred) 648 struct vnode *vp; 649 off_t oldoff, newoff; 650 struct ucred *cred; 651 { 652 653 return (0); 654 } 655 656 /* 657 * ufs remove 658 * Hard to avoid races here, especially 659 * in unlinking directories. 660 */ 661 ufs_remove(ndp, p) 662 struct nameidata *ndp; 663 struct proc *p; 664 { 665 register struct inode *ip, *dp; 666 int error; 667 668 ip = VTOI(ndp->ni_vp); 669 dp = VTOI(ndp->ni_dvp); 670 error = dirremove(ndp); 671 if (!error) { 672 ip->i_nlink--; 673 ip->i_flag |= ICHG; 674 } 675 if (dp == ip) 676 vrele(ITOV(ip)); 677 else 678 iput(ip); 679 iput(dp); 680 return (error); 681 } 682 683 /* 684 * link vnode call 685 */ 686 ufs_link(vp, ndp, p) 687 register struct vnode *vp; 688 register struct nameidata *ndp; 689 struct proc *p; 690 { 691 register struct inode *ip = VTOI(vp); 692 int error; 693 694 #ifdef DIANOSTIC 695 if ((ndp->ni_nameiop & HASBUF) == 0) 696 panic("ufs_link: no name"); 697 #endif 698 if ((unsigned short)ip->i_nlink >= LINK_MAX) { 699 free(ndp->ni_pnbuf, M_NAMEI); 700 return (EMLINK); 701 } 702 if (ndp->ni_dvp != vp) 703 ILOCK(ip); 704 ip->i_nlink++; 705 ip->i_flag |= ICHG; 706 error = iupdat(ip, &time, &time, 1); 707 if (!error) 708 error = direnter(ip, ndp); 709 if (ndp->ni_dvp != vp) 710 IUNLOCK(ip); 711 FREE(ndp->ni_pnbuf, M_NAMEI); 712 vput(ndp->ni_dvp); 713 if (error) { 714 ip->i_nlink--; 715 ip->i_flag |= ICHG; 716 } 717 return (error); 718 } 719 720 /* 721 * Rename system call. 722 * rename("foo", "bar"); 723 * is essentially 724 * unlink("bar"); 725 * link("foo", "bar"); 726 * unlink("foo"); 727 * but ``atomically''. Can't do full commit without saving state in the 728 * inode on disk which isn't feasible at this time. Best we can do is 729 * always guarantee the target exists. 730 * 731 * Basic algorithm is: 732 * 733 * 1) Bump link count on source while we're linking it to the 734 * target. This also ensure the inode won't be deleted out 735 * from underneath us while we work (it may be truncated by 736 * a concurrent `trunc' or `open' for creation). 737 * 2) Link source to destination. If destination already exists, 738 * delete it first. 739 * 3) Unlink source reference to inode if still around. If a 740 * directory was moved and the parent of the destination 741 * is different from the source, patch the ".." entry in the 742 * directory. 743 */ 744 ufs_rename(fndp, tndp, p) 745 register struct nameidata *fndp, *tndp; 746 struct proc *p; 747 { 748 register struct inode *ip, *xp, *dp; 749 struct dirtemplate dirbuf; 750 int doingdirectory = 0, oldparent = 0, newparent = 0; 751 int error = 0; 752 753 #ifdef DIANOSTIC 754 if ((tndp->ni_nameiop & HASBUF) == 0 || 755 (fndp->ni_nameiop & HASBUF) == 0) 756 panic("ufs_rename: no name"); 757 #endif 758 dp = VTOI(fndp->ni_dvp); 759 ip = VTOI(fndp->ni_vp); 760 /* 761 * Check if just deleting a link name. 762 */ 763 if (fndp->ni_vp == tndp->ni_vp) { 764 VOP_ABORTOP(tndp); 765 vput(tndp->ni_dvp); 766 vput(tndp->ni_vp); 767 vrele(fndp->ni_dvp); 768 if ((ip->i_mode&IFMT) == IFDIR) { 769 VOP_ABORTOP(fndp); 770 vrele(fndp->ni_vp); 771 return (EINVAL); 772 } 773 doingdirectory = 0; 774 goto unlinkit; 775 } 776 ILOCK(ip); 777 if ((ip->i_mode&IFMT) == IFDIR) { 778 /* 779 * Avoid ".", "..", and aliases of "." for obvious reasons. 780 */ 781 if ((fndp->ni_namelen == 1 && fndp->ni_ptr[0] == '.') || 782 dp == ip || fndp->ni_isdotdot || (ip->i_flag & IRENAME)) { 783 VOP_ABORTOP(tndp); 784 vput(tndp->ni_dvp); 785 if (tndp->ni_vp) 786 vput(tndp->ni_vp); 787 VOP_ABORTOP(fndp); 788 vrele(fndp->ni_dvp); 789 vput(fndp->ni_vp); 790 return (EINVAL); 791 } 792 ip->i_flag |= IRENAME; 793 oldparent = dp->i_number; 794 doingdirectory++; 795 } 796 vrele(fndp->ni_dvp); 797 798 /* 799 * 1) Bump link count while we're moving stuff 800 * around. If we crash somewhere before 801 * completing our work, the link count 802 * may be wrong, but correctable. 803 */ 804 ip->i_nlink++; 805 ip->i_flag |= ICHG; 806 error = iupdat(ip, &time, &time, 1); 807 IUNLOCK(ip); 808 809 /* 810 * When the target exists, both the directory 811 * and target vnodes are returned locked. 812 */ 813 dp = VTOI(tndp->ni_dvp); 814 xp = NULL; 815 if (tndp->ni_vp) 816 xp = VTOI(tndp->ni_vp); 817 /* 818 * If ".." must be changed (ie the directory gets a new 819 * parent) then the source directory must not be in the 820 * directory heirarchy above the target, as this would 821 * orphan everything below the source directory. Also 822 * the user must have write permission in the source so 823 * as to be able to change "..". We must repeat the call 824 * to namei, as the parent directory is unlocked by the 825 * call to checkpath(). 826 */ 827 if (oldparent != dp->i_number) 828 newparent = dp->i_number; 829 if (doingdirectory && newparent) { 830 VOP_LOCK(fndp->ni_vp); 831 error = ufs_access(fndp->ni_vp, VWRITE, tndp->ni_cred, p); 832 VOP_UNLOCK(fndp->ni_vp); 833 if (error) 834 goto bad; 835 if (xp != NULL) 836 iput(xp); 837 if (error = checkpath(ip, dp, tndp->ni_cred)) 838 goto out; 839 if ((tndp->ni_nameiop & SAVESTART) == 0) 840 panic("ufs_rename: lost to startdir"); 841 p->p_spare[1]--; 842 if (error = lookup(tndp, p)) 843 goto out; 844 dp = VTOI(tndp->ni_dvp); 845 xp = NULL; 846 if (tndp->ni_vp) 847 xp = VTOI(tndp->ni_vp); 848 } 849 /* 850 * 2) If target doesn't exist, link the target 851 * to the source and unlink the source. 852 * Otherwise, rewrite the target directory 853 * entry to reference the source inode and 854 * expunge the original entry's existence. 855 */ 856 if (xp == NULL) { 857 if (dp->i_dev != ip->i_dev) 858 panic("rename: EXDEV"); 859 /* 860 * Account for ".." in new directory. 861 * When source and destination have the same 862 * parent we don't fool with the link count. 863 */ 864 if (doingdirectory && newparent) { 865 if ((unsigned short)dp->i_nlink >= LINK_MAX) { 866 error = EMLINK; 867 goto bad; 868 } 869 dp->i_nlink++; 870 dp->i_flag |= ICHG; 871 if (error = iupdat(dp, &time, &time, 1)) 872 goto bad; 873 } 874 if (error = direnter(ip, tndp)) { 875 if (doingdirectory && newparent) { 876 dp->i_nlink--; 877 dp->i_flag |= ICHG; 878 (void) iupdat(dp, &time, &time, 1); 879 } 880 goto bad; 881 } 882 iput(dp); 883 } else { 884 if (xp->i_dev != dp->i_dev || xp->i_dev != ip->i_dev) 885 panic("rename: EXDEV"); 886 /* 887 * Short circuit rename(foo, foo). 888 */ 889 if (xp->i_number == ip->i_number) 890 panic("rename: same file"); 891 /* 892 * If the parent directory is "sticky", then the user must 893 * own the parent directory, or the destination of the rename, 894 * otherwise the destination may not be changed (except by 895 * root). This implements append-only directories. 896 */ 897 if ((dp->i_mode & ISVTX) && tndp->ni_cred->cr_uid != 0 && 898 tndp->ni_cred->cr_uid != dp->i_uid && 899 xp->i_uid != tndp->ni_cred->cr_uid) { 900 error = EPERM; 901 goto bad; 902 } 903 /* 904 * Target must be empty if a directory and have no links 905 * to it. Also, ensure source and target are compatible 906 * (both directories, or both not directories). 907 */ 908 if ((xp->i_mode&IFMT) == IFDIR) { 909 if (!dirempty(xp, dp->i_number, tndp->ni_cred) || 910 xp->i_nlink > 2) { 911 error = ENOTEMPTY; 912 goto bad; 913 } 914 if (!doingdirectory) { 915 error = ENOTDIR; 916 goto bad; 917 } 918 cache_purge(ITOV(dp)); 919 } else if (doingdirectory) { 920 error = EISDIR; 921 goto bad; 922 } 923 if (error = dirrewrite(dp, ip, tndp)) 924 goto bad; 925 /* 926 * If the target directory is in the same 927 * directory as the source directory, 928 * decrement the link count on the parent 929 * of the target directory. 930 */ 931 if (doingdirectory && !newparent) { 932 dp->i_nlink--; 933 dp->i_flag |= ICHG; 934 } 935 vput(ITOV(dp)); 936 /* 937 * Adjust the link count of the target to 938 * reflect the dirrewrite above. If this is 939 * a directory it is empty and there are 940 * no links to it, so we can squash the inode and 941 * any space associated with it. We disallowed 942 * renaming over top of a directory with links to 943 * it above, as the remaining link would point to 944 * a directory without "." or ".." entries. 945 */ 946 xp->i_nlink--; 947 if (doingdirectory) { 948 if (--xp->i_nlink != 0) 949 panic("rename: linked directory"); 950 error = itrunc(xp, (u_long)0, IO_SYNC); 951 } 952 xp->i_flag |= ICHG; 953 iput(xp); 954 xp = NULL; 955 } 956 957 /* 958 * 3) Unlink the source. 959 */ 960 unlinkit: 961 fndp->ni_nameiop &= ~MODMASK; 962 fndp->ni_nameiop |= LOCKPARENT | LOCKLEAF; 963 if ((fndp->ni_nameiop & SAVESTART) == 0) 964 panic("ufs_rename: lost from startdir"); 965 p->p_spare[1]--; 966 (void) lookup(fndp, p); 967 if (fndp->ni_vp != NULL) { 968 xp = VTOI(fndp->ni_vp); 969 dp = VTOI(fndp->ni_dvp); 970 } else { 971 /* 972 * From name has disappeared. 973 */ 974 if (doingdirectory) 975 panic("rename: lost dir entry"); 976 vrele(ITOV(ip)); 977 return (0); 978 } 979 /* 980 * Ensure that the directory entry still exists and has not 981 * changed while the new name has been entered. If the source is 982 * a file then the entry may have been unlinked or renamed. In 983 * either case there is no further work to be done. If the source 984 * is a directory then it cannot have been rmdir'ed; its link 985 * count of three would cause a rmdir to fail with ENOTEMPTY. 986 * The IRENAME flag ensures that it cannot be moved by another 987 * rename. 988 */ 989 if (xp != ip) { 990 if (doingdirectory) 991 panic("rename: lost dir entry"); 992 } else { 993 /* 994 * If the source is a directory with a 995 * new parent, the link count of the old 996 * parent directory must be decremented 997 * and ".." set to point to the new parent. 998 */ 999 if (doingdirectory && newparent) { 1000 dp->i_nlink--; 1001 dp->i_flag |= ICHG; 1002 error = vn_rdwr(UIO_READ, ITOV(xp), (caddr_t)&dirbuf, 1003 sizeof (struct dirtemplate), (off_t)0, 1004 UIO_SYSSPACE, IO_NODELOCKED, 1005 tndp->ni_cred, (int *)0, (struct proc *)0); 1006 if (error == 0) { 1007 if (dirbuf.dotdot_namlen != 2 || 1008 dirbuf.dotdot_name[0] != '.' || 1009 dirbuf.dotdot_name[1] != '.') { 1010 dirbad(xp, 12, "rename: mangled dir"); 1011 } else { 1012 dirbuf.dotdot_ino = newparent; 1013 (void) vn_rdwr(UIO_WRITE, ITOV(xp), 1014 (caddr_t)&dirbuf, 1015 sizeof (struct dirtemplate), 1016 (off_t)0, UIO_SYSSPACE, 1017 IO_NODELOCKED|IO_SYNC, 1018 tndp->ni_cred, (int *)0, 1019 (struct proc *)0); 1020 cache_purge(ITOV(dp)); 1021 } 1022 } 1023 } 1024 error = dirremove(fndp); 1025 if (!error) { 1026 xp->i_nlink--; 1027 xp->i_flag |= ICHG; 1028 } 1029 xp->i_flag &= ~IRENAME; 1030 } 1031 if (dp) 1032 vput(ITOV(dp)); 1033 if (xp) 1034 vput(ITOV(xp)); 1035 vrele(ITOV(ip)); 1036 return (error); 1037 1038 bad: 1039 if (xp) 1040 vput(ITOV(xp)); 1041 vput(ITOV(dp)); 1042 out: 1043 ip->i_nlink--; 1044 ip->i_flag |= ICHG; 1045 vrele(ITOV(ip)); 1046 return (error); 1047 } 1048 1049 /* 1050 * A virgin directory (no blushing please). 1051 */ 1052 struct dirtemplate mastertemplate = { 1053 0, 12, 1, ".", 1054 0, DIRBLKSIZ - 12, 2, ".." 1055 }; 1056 1057 /* 1058 * Mkdir system call 1059 */ 1060 ufs_mkdir(ndp, vap, p) 1061 struct nameidata *ndp; 1062 struct vattr *vap; 1063 struct proc *p; 1064 { 1065 register struct inode *ip, *dp; 1066 struct inode *tip; 1067 struct vnode *dvp; 1068 struct dirtemplate dirtemplate; 1069 int error; 1070 int dmode; 1071 1072 #ifdef DIANOSTIC 1073 if ((ndp->ni_nameiop & HASBUF) == 0) 1074 panic("ufs_mkdir: no name"); 1075 #endif 1076 dvp = ndp->ni_dvp; 1077 dp = VTOI(dvp); 1078 if ((unsigned short)dp->i_nlink >= LINK_MAX) { 1079 free(ndp->ni_pnbuf, M_NAMEI); 1080 iput(dp); 1081 return (EMLINK); 1082 } 1083 dmode = vap->va_mode&0777; 1084 dmode |= IFDIR; 1085 /* 1086 * Must simulate part of maknode here to acquire the inode, but 1087 * not have it entered in the parent directory. The entry is made 1088 * later after writing "." and ".." entries. 1089 */ 1090 if (error = ialloc(dp, dirpref(dp->i_fs), dmode, ndp->ni_cred, &tip)) { 1091 free(ndp->ni_pnbuf, M_NAMEI); 1092 iput(dp); 1093 return (error); 1094 } 1095 ip = tip; 1096 ip->i_uid = ndp->ni_cred->cr_uid; 1097 ip->i_gid = dp->i_gid; 1098 #ifdef QUOTA 1099 if ((error = getinoquota(ip)) || 1100 (error = chkiq(ip, 1, ndp->ni_cred, 0))) { 1101 free(ndp->ni_pnbuf, M_NAMEI); 1102 ifree(ip, ip->i_number, dmode); 1103 iput(ip); 1104 iput(dp); 1105 return (error); 1106 } 1107 #endif 1108 ip->i_flag |= IACC|IUPD|ICHG; 1109 ip->i_mode = dmode; 1110 ITOV(ip)->v_type = VDIR; /* Rest init'd in iget() */ 1111 ip->i_nlink = 2; 1112 error = iupdat(ip, &time, &time, 1); 1113 1114 /* 1115 * Bump link count in parent directory 1116 * to reflect work done below. Should 1117 * be done before reference is created 1118 * so reparation is possible if we crash. 1119 */ 1120 dp->i_nlink++; 1121 dp->i_flag |= ICHG; 1122 if (error = iupdat(dp, &time, &time, 1)) 1123 goto bad; 1124 1125 /* 1126 * Initialize directory with "." 1127 * and ".." from static template. 1128 */ 1129 dirtemplate = mastertemplate; 1130 dirtemplate.dot_ino = ip->i_number; 1131 dirtemplate.dotdot_ino = dp->i_number; 1132 error = vn_rdwr(UIO_WRITE, ITOV(ip), (caddr_t)&dirtemplate, 1133 sizeof (dirtemplate), (off_t)0, UIO_SYSSPACE, 1134 IO_NODELOCKED|IO_SYNC, ndp->ni_cred, (int *)0, (struct proc *)0); 1135 if (error) { 1136 dp->i_nlink--; 1137 dp->i_flag |= ICHG; 1138 goto bad; 1139 } 1140 if (DIRBLKSIZ > dp->i_fs->fs_fsize) { 1141 panic("mkdir: blksize"); /* XXX - should grow w/balloc() */ 1142 } else { 1143 ip->i_size = DIRBLKSIZ; 1144 ip->i_flag |= ICHG; 1145 } 1146 /* 1147 * Directory all set up, now 1148 * install the entry for it in 1149 * the parent directory. 1150 */ 1151 if (error = direnter(ip, ndp)) { 1152 dp->i_nlink--; 1153 dp->i_flag |= ICHG; 1154 } 1155 bad: 1156 /* 1157 * No need to do an explicit itrunc here, 1158 * vrele will do this for us because we set 1159 * the link count to 0. 1160 */ 1161 if (error) { 1162 ip->i_nlink = 0; 1163 ip->i_flag |= ICHG; 1164 iput(ip); 1165 } else 1166 ndp->ni_vp = ITOV(ip); 1167 FREE(ndp->ni_pnbuf, M_NAMEI); 1168 iput(dp); 1169 return (error); 1170 } 1171 1172 /* 1173 * Rmdir system call. 1174 */ 1175 ufs_rmdir(ndp, p) 1176 register struct nameidata *ndp; 1177 struct proc *p; 1178 { 1179 register struct inode *ip, *dp; 1180 int error = 0; 1181 1182 ip = VTOI(ndp->ni_vp); 1183 dp = VTOI(ndp->ni_dvp); 1184 /* 1185 * No rmdir "." please. 1186 */ 1187 if (dp == ip) { 1188 vrele(ITOV(dp)); 1189 iput(ip); 1190 return (EINVAL); 1191 } 1192 /* 1193 * Verify the directory is empty (and valid). 1194 * (Rmdir ".." won't be valid since 1195 * ".." will contain a reference to 1196 * the current directory and thus be 1197 * non-empty.) 1198 */ 1199 if (ip->i_nlink != 2 || !dirempty(ip, dp->i_number, ndp->ni_cred)) { 1200 error = ENOTEMPTY; 1201 goto out; 1202 } 1203 /* 1204 * Delete reference to directory before purging 1205 * inode. If we crash in between, the directory 1206 * will be reattached to lost+found, 1207 */ 1208 if (error = dirremove(ndp)) 1209 goto out; 1210 dp->i_nlink--; 1211 dp->i_flag |= ICHG; 1212 cache_purge(ITOV(dp)); 1213 iput(dp); 1214 ndp->ni_dvp = NULL; 1215 /* 1216 * Truncate inode. The only stuff left 1217 * in the directory is "." and "..". The 1218 * "." reference is inconsequential since 1219 * we're quashing it. The ".." reference 1220 * has already been adjusted above. We've 1221 * removed the "." reference and the reference 1222 * in the parent directory, but there may be 1223 * other hard links so decrement by 2 and 1224 * worry about them later. 1225 */ 1226 ip->i_nlink -= 2; 1227 error = itrunc(ip, (u_long)0, IO_SYNC); 1228 cache_purge(ITOV(ip)); 1229 out: 1230 if (ndp->ni_dvp) 1231 iput(dp); 1232 iput(ip); 1233 return (error); 1234 } 1235 1236 /* 1237 * symlink -- make a symbolic link 1238 */ 1239 ufs_symlink(ndp, vap, target, p) 1240 struct nameidata *ndp; 1241 struct vattr *vap; 1242 char *target; 1243 struct proc *p; 1244 { 1245 struct inode *ip; 1246 int error; 1247 1248 error = maknode(IFLNK | vap->va_mode, ndp, &ip); 1249 if (error) 1250 return (error); 1251 error = vn_rdwr(UIO_WRITE, ITOV(ip), target, strlen(target), (off_t)0, 1252 UIO_SYSSPACE, IO_NODELOCKED, ndp->ni_cred, (int *)0, 1253 (struct proc *)0); 1254 iput(ip); 1255 return (error); 1256 } 1257 1258 /* 1259 * Vnode op for read and write 1260 */ 1261 ufs_readdir(vp, uio, cred, eofflagp) 1262 struct vnode *vp; 1263 register struct uio *uio; 1264 struct ucred *cred; 1265 int *eofflagp; 1266 { 1267 int count, lost, error; 1268 1269 count = uio->uio_resid; 1270 count &= ~(DIRBLKSIZ - 1); 1271 lost = uio->uio_resid - count; 1272 if (count < DIRBLKSIZ || (uio->uio_offset & (DIRBLKSIZ -1))) 1273 return (EINVAL); 1274 uio->uio_resid = count; 1275 uio->uio_iov->iov_len = count; 1276 error = ufs_read(vp, uio, 0, cred); 1277 uio->uio_resid += lost; 1278 if ((VTOI(vp)->i_size - uio->uio_offset) <= 0) 1279 *eofflagp = 1; 1280 else 1281 *eofflagp = 0; 1282 return (error); 1283 } 1284 1285 /* 1286 * Return target name of a symbolic link 1287 */ 1288 ufs_readlink(vp, uiop, cred) 1289 struct vnode *vp; 1290 struct uio *uiop; 1291 struct ucred *cred; 1292 { 1293 1294 return (ufs_read(vp, uiop, 0, cred)); 1295 } 1296 1297 /* 1298 * Ufs abort op, called after namei() when a CREATE/DELETE isn't actually 1299 * done. If a buffer has been saved in anticipation of a CREATE, delete it. 1300 */ 1301 /* ARGSUSED */ 1302 ufs_abortop(ndp) 1303 struct nameidata *ndp; 1304 { 1305 1306 if ((ndp->ni_nameiop & (HASBUF | SAVESTART)) == HASBUF) 1307 FREE(ndp->ni_pnbuf, M_NAMEI); 1308 return (0); 1309 } 1310 1311 /* 1312 * Lock an inode. 1313 */ 1314 ufs_lock(vp) 1315 struct vnode *vp; 1316 { 1317 register struct inode *ip = VTOI(vp); 1318 1319 ILOCK(ip); 1320 return (0); 1321 } 1322 1323 /* 1324 * Unlock an inode. 1325 */ 1326 ufs_unlock(vp) 1327 struct vnode *vp; 1328 { 1329 register struct inode *ip = VTOI(vp); 1330 1331 if (!(ip->i_flag & ILOCKED)) 1332 panic("ufs_unlock NOT LOCKED"); 1333 IUNLOCK(ip); 1334 return (0); 1335 } 1336 1337 /* 1338 * Check for a locked inode. 1339 */ 1340 ufs_islocked(vp) 1341 struct vnode *vp; 1342 { 1343 1344 if (VTOI(vp)->i_flag & ILOCKED) 1345 return (1); 1346 return (0); 1347 } 1348 1349 /* 1350 * Get access to bmap 1351 */ 1352 ufs_bmap(vp, bn, vpp, bnp) 1353 struct vnode *vp; 1354 daddr_t bn; 1355 struct vnode **vpp; 1356 daddr_t *bnp; 1357 { 1358 struct inode *ip = VTOI(vp); 1359 1360 if (vpp != NULL) 1361 *vpp = ip->i_devvp; 1362 if (bnp == NULL) 1363 return (0); 1364 return (bmap(ip, bn, bnp)); 1365 } 1366 1367 /* 1368 * Calculate the logical to physical mapping if not done already, 1369 * then call the device strategy routine. 1370 */ 1371 int checkoverlap = 0; 1372 1373 ufs_strategy(bp) 1374 register struct buf *bp; 1375 { 1376 register struct inode *ip = VTOI(bp->b_vp); 1377 struct vnode *vp; 1378 int error; 1379 1380 if (bp->b_vp->v_type == VBLK || bp->b_vp->v_type == VCHR) 1381 panic("ufs_strategy: spec"); 1382 if (bp->b_blkno == bp->b_lblkno) { 1383 if (error = bmap(ip, bp->b_lblkno, &bp->b_blkno)) 1384 return (error); 1385 if ((long)bp->b_blkno == -1) 1386 clrbuf(bp); 1387 } 1388 if ((long)bp->b_blkno == -1) { 1389 biodone(bp); 1390 return (0); 1391 } 1392 #ifdef DIAGNOSTIC 1393 if (checkoverlap) { 1394 register struct buf *ep; 1395 struct buf *ebp; 1396 daddr_t start, last; 1397 1398 ebp = &buf[nbuf]; 1399 start = bp->b_blkno; 1400 last = start + btodb(bp->b_bcount) - 1; 1401 for (ep = buf; ep < ebp; ep++) { 1402 if (ep == bp || (ep->b_flags & B_INVAL) || 1403 ep->b_vp == NULLVP) 1404 continue; 1405 if (VOP_BMAP(ep->b_vp, (daddr_t)0, &vp, (daddr_t)0)) 1406 continue; 1407 if (vp != ip->i_devvp) 1408 continue; 1409 /* look for overlap */ 1410 if (ep->b_bcount == 0 || ep->b_blkno > last || 1411 ep->b_blkno + btodb(ep->b_bcount) <= start) 1412 continue; 1413 vprint("Disk overlap", vp); 1414 printf("\tstart %d, end %d overlap start %d, end %d\n", 1415 start, last, ep->b_blkno, 1416 ep->b_blkno + btodb(ep->b_bcount) - 1); 1417 panic("Disk buffer overlap"); 1418 } 1419 } 1420 #endif /* DIAGNOSTIC */ 1421 vp = ip->i_devvp; 1422 bp->b_dev = vp->v_rdev; 1423 (*(vp->v_op->vop_strategy))(bp); 1424 return (0); 1425 } 1426 1427 /* 1428 * Print out the contents of an inode. 1429 */ 1430 ufs_print(vp) 1431 struct vnode *vp; 1432 { 1433 register struct inode *ip = VTOI(vp); 1434 1435 printf("tag VT_UFS, ino %d, on dev %d, %d", ip->i_number, 1436 major(ip->i_dev), minor(ip->i_dev)); 1437 #ifdef FIFO 1438 if (vp->v_type == VFIFO) 1439 fifo_printinfo(vp); 1440 #endif /* FIFO */ 1441 printf("%s\n", (ip->i_flag & ILOCKED) ? " (LOCKED)" : ""); 1442 if (ip->i_spare0 == 0) 1443 return; 1444 printf("\towner pid %d", ip->i_spare0); 1445 if (ip->i_spare1) 1446 printf(" waiting pid %d", ip->i_spare1); 1447 printf("\n"); 1448 } 1449 1450 /* 1451 * Read wrapper for special devices. 1452 */ 1453 ufsspec_read(vp, uio, ioflag, cred) 1454 struct vnode *vp; 1455 struct uio *uio; 1456 int ioflag; 1457 struct ucred *cred; 1458 { 1459 1460 /* 1461 * Set access flag. 1462 */ 1463 VTOI(vp)->i_flag |= IACC; 1464 return (spec_read(vp, uio, ioflag, cred)); 1465 } 1466 1467 /* 1468 * Write wrapper for special devices. 1469 */ 1470 ufsspec_write(vp, uio, ioflag, cred) 1471 struct vnode *vp; 1472 struct uio *uio; 1473 int ioflag; 1474 struct ucred *cred; 1475 { 1476 1477 /* 1478 * Set update and change flags. 1479 */ 1480 VTOI(vp)->i_flag |= IUPD|ICHG; 1481 return (spec_write(vp, uio, ioflag, cred)); 1482 } 1483 1484 /* 1485 * Close wrapper for special devices. 1486 * 1487 * Update the times on the inode then do device close. 1488 */ 1489 ufsspec_close(vp, fflag, cred, p) 1490 struct vnode *vp; 1491 int fflag; 1492 struct ucred *cred; 1493 struct proc *p; 1494 { 1495 register struct inode *ip = VTOI(vp); 1496 1497 if (vp->v_usecount > 1 && !(ip->i_flag & ILOCKED)) 1498 ITIMES(ip, &time, &time); 1499 return (spec_close(vp, fflag, cred, p)); 1500 } 1501 1502 #ifdef FIFO 1503 /* 1504 * Read wrapper for fifo's 1505 */ 1506 ufsfifo_read(vp, uio, ioflag, cred) 1507 struct vnode *vp; 1508 struct uio *uio; 1509 int ioflag; 1510 struct ucred *cred; 1511 { 1512 1513 /* 1514 * Set access flag. 1515 */ 1516 VTOI(vp)->i_flag |= IACC; 1517 return (fifo_read(vp, uio, ioflag, cred)); 1518 } 1519 1520 /* 1521 * Write wrapper for fifo's. 1522 */ 1523 ufsfifo_write(vp, uio, ioflag, cred) 1524 struct vnode *vp; 1525 struct uio *uio; 1526 int ioflag; 1527 struct ucred *cred; 1528 { 1529 1530 /* 1531 * Set update and change flags. 1532 */ 1533 VTOI(vp)->i_flag |= IUPD|ICHG; 1534 return (fifo_write(vp, uio, ioflag, cred)); 1535 } 1536 1537 /* 1538 * Close wrapper for fifo's. 1539 * 1540 * Update the times on the inode then do device close. 1541 */ 1542 ufsfifo_close(vp, fflag, cred, p) 1543 struct vnode *vp; 1544 int fflag; 1545 struct ucred *cred; 1546 struct proc *p; 1547 { 1548 register struct inode *ip = VTOI(vp); 1549 1550 if (vp->v_usecount > 1 && !(ip->i_flag & ILOCKED)) 1551 ITIMES(ip, &time, &time); 1552 return (fifo_close(vp, fflag, cred, p)); 1553 } 1554 #endif /* FIFO */ 1555 1556 /* 1557 * Allocate a new inode. 1558 */ 1559 maknode(mode, ndp, ipp) 1560 int mode; 1561 register struct nameidata *ndp; 1562 struct inode **ipp; 1563 { 1564 register struct inode *ip; 1565 struct inode *tip; 1566 register struct inode *pdir = VTOI(ndp->ni_dvp); 1567 ino_t ipref; 1568 int error; 1569 1570 #ifdef DIANOSTIC 1571 if ((ndp->ni_nameiop & HASBUF) == 0) 1572 panic("maknode: no name"); 1573 #endif 1574 *ipp = 0; 1575 if ((mode & IFMT) == 0) 1576 mode |= IFREG; 1577 if ((mode & IFMT) == IFDIR) 1578 ipref = dirpref(pdir->i_fs); 1579 else 1580 ipref = pdir->i_number; 1581 if (error = ialloc(pdir, ipref, mode, ndp->ni_cred, &tip)) { 1582 free(ndp->ni_pnbuf, M_NAMEI); 1583 iput(pdir); 1584 return (error); 1585 } 1586 ip = tip; 1587 ip->i_uid = ndp->ni_cred->cr_uid; 1588 ip->i_gid = pdir->i_gid; 1589 #ifdef QUOTA 1590 if ((error = getinoquota(ip)) || 1591 (error = chkiq(ip, 1, ndp->ni_cred, 0))) { 1592 free(ndp->ni_pnbuf, M_NAMEI); 1593 ifree(ip, ip->i_number, mode); 1594 iput(ip); 1595 iput(pdir); 1596 return (error); 1597 } 1598 #endif 1599 ip->i_flag |= IACC|IUPD|ICHG; 1600 ip->i_mode = mode; 1601 ITOV(ip)->v_type = IFTOVT(mode); /* Rest init'd in iget() */ 1602 ip->i_nlink = 1; 1603 if ((ip->i_mode & ISGID) && !groupmember(ip->i_gid, ndp->ni_cred) && 1604 suser(ndp->ni_cred, NULL)) 1605 ip->i_mode &= ~ISGID; 1606 1607 /* 1608 * Make sure inode goes to disk before directory entry. 1609 */ 1610 if (error = iupdat(ip, &time, &time, 1)) 1611 goto bad; 1612 if (error = direnter(ip, ndp)) 1613 goto bad; 1614 if ((ndp->ni_nameiop & SAVESTART) == 0) 1615 FREE(ndp->ni_pnbuf, M_NAMEI); 1616 iput(pdir); 1617 *ipp = ip; 1618 return (0); 1619 1620 bad: 1621 /* 1622 * Write error occurred trying to update the inode 1623 * or the directory so must deallocate the inode. 1624 */ 1625 free(ndp->ni_pnbuf, M_NAMEI); 1626 iput(pdir); 1627 ip->i_nlink = 0; 1628 ip->i_flag |= ICHG; 1629 iput(ip); 1630 return (error); 1631 } 1632 1633 /* 1634 * Advisory record locking support 1635 */ 1636 ufs_advlock(vp, id, op, fl, flags) 1637 struct vnode *vp; 1638 caddr_t id; 1639 int op; 1640 register struct flock *fl; 1641 int flags; 1642 { 1643 register struct inode *ip = VTOI(vp); 1644 register struct lockf *lock; 1645 off_t start, end; 1646 int error; 1647 1648 /* 1649 * Avoid the common case of unlocking when inode has no locks. 1650 */ 1651 if (ip->i_lockf == (struct lockf *)0) { 1652 if (op != F_SETLK) { 1653 fl->l_type = F_UNLCK; 1654 return (0); 1655 } 1656 } 1657 /* 1658 * Convert the flock structure into a start and end. 1659 */ 1660 switch (fl->l_whence) { 1661 1662 case SEEK_SET: 1663 case SEEK_CUR: 1664 /* 1665 * Caller is responsible for adding any necessary offset 1666 * when SEEK_CUR is used. 1667 */ 1668 start = fl->l_start; 1669 break; 1670 1671 case SEEK_END: 1672 start = ip->i_size + fl->l_start; 1673 break; 1674 1675 default: 1676 return (EINVAL); 1677 } 1678 if (start < 0) 1679 return (EINVAL); 1680 if (fl->l_len == 0) 1681 end = -1; 1682 else 1683 end = start + fl->l_len - 1; 1684 /* 1685 * Create the lockf structure 1686 */ 1687 MALLOC(lock, struct lockf *, sizeof *lock, M_LOCKF, M_WAITOK); 1688 lock->lf_start = start; 1689 lock->lf_end = end; 1690 lock->lf_id = id; 1691 lock->lf_inode = ip; 1692 lock->lf_type = fl->l_type; 1693 lock->lf_next = (struct lockf *)0; 1694 lock->lf_block = (struct lockf *)0; 1695 lock->lf_flags = flags; 1696 /* 1697 * Do the requested operation. 1698 */ 1699 switch(op) { 1700 case F_SETLK: 1701 return (lf_setlock(lock)); 1702 1703 case F_UNLCK: 1704 error = lf_clearlock(lock); 1705 FREE(lock, M_LOCKF); 1706 return (error); 1707 1708 case F_GETLK: 1709 error = lf_getlock(lock, fl); 1710 FREE(lock, M_LOCKF); 1711 return (error); 1712 1713 default: 1714 free(lock, M_LOCKF); 1715 return (EINVAL); 1716 } 1717 /* NOTREACHED */ 1718 } 1719 1720 /* 1721 * Global vfs data structures for ufs 1722 */ 1723 struct vnodeops ufs_vnodeops = { 1724 ufs_lookup, /* lookup */ 1725 ufs_create, /* create */ 1726 ufs_mknod, /* mknod */ 1727 ufs_open, /* open */ 1728 ufs_close, /* close */ 1729 ufs_access, /* access */ 1730 ufs_getattr, /* getattr */ 1731 ufs_setattr, /* setattr */ 1732 ufs_read, /* read */ 1733 ufs_write, /* write */ 1734 ufs_ioctl, /* ioctl */ 1735 ufs_select, /* select */ 1736 ufs_mmap, /* mmap */ 1737 ufs_fsync, /* fsync */ 1738 ufs_seek, /* seek */ 1739 ufs_remove, /* remove */ 1740 ufs_link, /* link */ 1741 ufs_rename, /* rename */ 1742 ufs_mkdir, /* mkdir */ 1743 ufs_rmdir, /* rmdir */ 1744 ufs_symlink, /* symlink */ 1745 ufs_readdir, /* readdir */ 1746 ufs_readlink, /* readlink */ 1747 ufs_abortop, /* abortop */ 1748 ufs_inactive, /* inactive */ 1749 ufs_reclaim, /* reclaim */ 1750 ufs_lock, /* lock */ 1751 ufs_unlock, /* unlock */ 1752 ufs_bmap, /* bmap */ 1753 ufs_strategy, /* strategy */ 1754 ufs_print, /* print */ 1755 ufs_islocked, /* islocked */ 1756 ufs_advlock, /* advlock */ 1757 }; 1758 1759 struct vnodeops spec_inodeops = { 1760 spec_lookup, /* lookup */ 1761 spec_create, /* create */ 1762 spec_mknod, /* mknod */ 1763 spec_open, /* open */ 1764 ufsspec_close, /* close */ 1765 ufs_access, /* access */ 1766 ufs_getattr, /* getattr */ 1767 ufs_setattr, /* setattr */ 1768 ufsspec_read, /* read */ 1769 ufsspec_write, /* write */ 1770 spec_ioctl, /* ioctl */ 1771 spec_select, /* select */ 1772 spec_mmap, /* mmap */ 1773 spec_fsync, /* fsync */ 1774 spec_seek, /* seek */ 1775 spec_remove, /* remove */ 1776 spec_link, /* link */ 1777 spec_rename, /* rename */ 1778 spec_mkdir, /* mkdir */ 1779 spec_rmdir, /* rmdir */ 1780 spec_symlink, /* symlink */ 1781 spec_readdir, /* readdir */ 1782 spec_readlink, /* readlink */ 1783 spec_abortop, /* abortop */ 1784 ufs_inactive, /* inactive */ 1785 ufs_reclaim, /* reclaim */ 1786 ufs_lock, /* lock */ 1787 ufs_unlock, /* unlock */ 1788 spec_bmap, /* bmap */ 1789 spec_strategy, /* strategy */ 1790 ufs_print, /* print */ 1791 ufs_islocked, /* islocked */ 1792 spec_advlock, /* advlock */ 1793 }; 1794 1795 #ifdef FIFO 1796 struct vnodeops fifo_inodeops = { 1797 fifo_lookup, /* lookup */ 1798 fifo_create, /* create */ 1799 fifo_mknod, /* mknod */ 1800 fifo_open, /* open */ 1801 ufsfifo_close, /* close */ 1802 ufs_access, /* access */ 1803 ufs_getattr, /* getattr */ 1804 ufs_setattr, /* setattr */ 1805 ufsfifo_read, /* read */ 1806 ufsfifo_write, /* write */ 1807 fifo_ioctl, /* ioctl */ 1808 fifo_select, /* select */ 1809 fifo_mmap, /* mmap */ 1810 fifo_fsync, /* fsync */ 1811 fifo_seek, /* seek */ 1812 fifo_remove, /* remove */ 1813 fifo_link, /* link */ 1814 fifo_rename, /* rename */ 1815 fifo_mkdir, /* mkdir */ 1816 fifo_rmdir, /* rmdir */ 1817 fifo_symlink, /* symlink */ 1818 fifo_readdir, /* readdir */ 1819 fifo_readlink, /* readlink */ 1820 fifo_abortop, /* abortop */ 1821 ufs_inactive, /* inactive */ 1822 ufs_reclaim, /* reclaim */ 1823 ufs_lock, /* lock */ 1824 ufs_unlock, /* unlock */ 1825 fifo_bmap, /* bmap */ 1826 fifo_strategy, /* strategy */ 1827 ufs_print, /* print */ 1828 ufs_islocked, /* islocked */ 1829 fifo_advlock, /* advlock */ 1830 }; 1831 #endif /* FIFO */ 1832 1833 enum vtype iftovt_tab[16] = { 1834 VNON, VFIFO, VCHR, VNON, VDIR, VNON, VBLK, VNON, 1835 VREG, VNON, VLNK, VNON, VSOCK, VNON, VNON, VBAD, 1836 }; 1837 int vttoif_tab[9] = { 1838 0, IFREG, IFDIR, IFBLK, IFCHR, IFLNK, IFSOCK, IFIFO, IFMT, 1839 }; 1840