xref: /original-bsd/sys/kern/vfs_syscalls.c (revision be1f24e8)
1 /*
2  * Copyright (c) 1989 The Regents of the University of California.
3  * All rights reserved.
4  *
5  * %sccs.include.redist.c%
6  *
7  *	@(#)vfs_syscalls.c	7.100 (Berkeley) 10/11/92
8  */
9 
10 #include <sys/param.h>
11 #include <sys/systm.h>
12 #include <sys/namei.h>
13 #include <sys/filedesc.h>
14 #include <sys/kernel.h>
15 #include <sys/file.h>
16 #include <sys/stat.h>
17 #include <sys/vnode.h>
18 #include <sys/mount.h>
19 #include <sys/proc.h>
20 #include <sys/uio.h>
21 #include <sys/malloc.h>
22 #include <sys/dirent.h>
23 
24 #include <vm/vm.h>
25 
26 /*
27  * Virtual File System System Calls
28  */
29 
30 /*
31  * Mount system call.
32  */
33 struct mount_args {
34 	int	type;
35 	char	*dir;
36 	int	flags;
37 	caddr_t	data;
38 };
39 /* ARGSUSED */
40 mount(p, uap, retval)
41 	struct proc *p;
42 	register struct mount_args *uap;
43 	int *retval;
44 {
45 	register struct vnode *vp;
46 	register struct mount *mp;
47 	int error, flag;
48 	struct nameidata nd;
49 
50 	/*
51 	 * Must be super user
52 	 */
53 	if (error = suser(p->p_ucred, &p->p_acflag))
54 		return (error);
55 	/*
56 	 * Get vnode to be covered
57 	 */
58 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->dir, p);
59 	if (error = namei(&nd))
60 		return (error);
61 	vp = nd.ni_vp;
62 	if (uap->flags & MNT_UPDATE) {
63 		if ((vp->v_flag & VROOT) == 0) {
64 			vput(vp);
65 			return (EINVAL);
66 		}
67 		mp = vp->v_mount;
68 		/*
69 		 * We allow going from read-only to read-write,
70 		 * but not from read-write to read-only.
71 		 */
72 		if ((mp->mnt_flag & MNT_RDONLY) == 0 &&
73 		    (uap->flags & MNT_RDONLY) != 0) {
74 			vput(vp);
75 			return (EOPNOTSUPP);	/* Needs translation */
76 		}
77 		flag = mp->mnt_flag;
78 		mp->mnt_flag |= MNT_UPDATE;
79 		VOP_UNLOCK(vp);
80 		goto update;
81 	}
82 	if (vp->v_usecount != 1 && (uap->flags & MNT_UNION) == 0) {
83 		vput(vp);
84 		return (EBUSY);
85 	}
86 	if (error = vinvalbuf(vp, V_SAVE, p->p_ucred, p))
87 		return (error);
88 	if (vp->v_type != VDIR) {
89 		vput(vp);
90 		return (ENOTDIR);
91 	}
92 	if ((unsigned long)uap->type > MOUNT_MAXTYPE ||
93 	    vfssw[uap->type] == (struct vfsops *)0) {
94 		vput(vp);
95 		return (ENODEV);
96 	}
97 
98 	/*
99 	 * Allocate and initialize the file system.
100 	 */
101 	mp = (struct mount *)malloc((u_long)sizeof(struct mount),
102 		M_MOUNT, M_WAITOK);
103 	bzero((char *)mp, (u_long)sizeof(struct mount));
104 	mp->mnt_op = vfssw[uap->type];
105 	if (error = vfs_lock(mp)) {
106 		free((caddr_t)mp, M_MOUNT);
107 		vput(vp);
108 		return (error);
109 	}
110 	if (vp->v_mountedhere != (struct mount *)0) {
111 		vfs_unlock(mp);
112 		free((caddr_t)mp, M_MOUNT);
113 		vput(vp);
114 		return (EBUSY);
115 	}
116 	vp->v_mountedhere = mp;
117 	mp->mnt_vnodecovered = vp;
118 update:
119 	/*
120 	 * Set the mount level flags.
121 	 */
122 	if (uap->flags & MNT_RDONLY)
123 		mp->mnt_flag |= MNT_RDONLY;
124 	else
125 		mp->mnt_flag &= ~MNT_RDONLY;
126 	if (uap->flags & MNT_NOSUID)
127 		mp->mnt_flag |= MNT_NOSUID;
128 	else
129 		mp->mnt_flag &= ~MNT_NOSUID;
130 	if (uap->flags & MNT_NOEXEC)
131 		mp->mnt_flag |= MNT_NOEXEC;
132 	else
133 		mp->mnt_flag &= ~MNT_NOEXEC;
134 	if (uap->flags & MNT_NODEV)
135 		mp->mnt_flag |= MNT_NODEV;
136 	else
137 		mp->mnt_flag &= ~MNT_NODEV;
138 	if (uap->flags & MNT_SYNCHRONOUS)
139 		mp->mnt_flag |= MNT_SYNCHRONOUS;
140 	else
141 		mp->mnt_flag &= ~MNT_SYNCHRONOUS;
142 	if (uap->flags & MNT_UNION)
143 		mp->mnt_flag |= MNT_UNION;
144 	else
145 		mp->mnt_flag &= ~MNT_UNION;
146 	/*
147 	 * Mount the filesystem.
148 	 */
149 	error = VFS_MOUNT(mp, uap->dir, uap->data, &nd, p);
150 	if (mp->mnt_flag & MNT_UPDATE) {
151 		mp->mnt_flag &= ~MNT_UPDATE;
152 		vrele(vp);
153 		if (error)
154 			mp->mnt_flag = flag;
155 		return (error);
156 	}
157 	/*
158 	 * Put the new filesystem on the mount list after root.
159 	 */
160 	mp->mnt_next = rootfs->mnt_next;
161 	mp->mnt_prev = rootfs;
162 	rootfs->mnt_next = mp;
163 	mp->mnt_next->mnt_prev = mp;
164 	cache_purge(vp);
165 	if (!error) {
166 		VOP_UNLOCK(vp);
167 		vfs_unlock(mp);
168 		error = VFS_START(mp, 0, p);
169 	} else {
170 		vfs_remove(mp);
171 		free((caddr_t)mp, M_MOUNT);
172 		vput(vp);
173 	}
174 	return (error);
175 }
176 
177 /*
178  * Unmount system call.
179  *
180  * Note: unmount takes a path to the vnode mounted on as argument,
181  * not special file (as before).
182  */
183 struct unmount_args {
184 	char	*pathp;
185 	int	flags;
186 };
187 /* ARGSUSED */
188 unmount(p, uap, retval)
189 	struct proc *p;
190 	register struct unmount_args *uap;
191 	int *retval;
192 {
193 	register struct vnode *vp;
194 	struct mount *mp;
195 	int error;
196 	struct nameidata nd;
197 
198 	/*
199 	 * Must be super user
200 	 */
201 	if (error = suser(p->p_ucred, &p->p_acflag))
202 		return (error);
203 
204 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->pathp, p);
205 	if (error = namei(&nd))
206 		return (error);
207 	vp = nd.ni_vp;
208 	/*
209 	 * Must be the root of the filesystem
210 	 */
211 	if ((vp->v_flag & VROOT) == 0) {
212 		vput(vp);
213 		return (EINVAL);
214 	}
215 	mp = vp->v_mount;
216 	vput(vp);
217 	return (dounmount(mp, uap->flags, p));
218 }
219 
220 /*
221  * Do an unmount.
222  */
223 dounmount(mp, flags, p)
224 	register struct mount *mp;
225 	int flags;
226 	struct proc *p;
227 {
228 	struct vnode *coveredvp;
229 	int error;
230 
231 	coveredvp = mp->mnt_vnodecovered;
232 	if (vfs_busy(mp))
233 		return (EBUSY);
234 	mp->mnt_flag |= MNT_UNMOUNT;
235 	if (error = vfs_lock(mp))
236 		return (error);
237 
238 	vnode_pager_umount(mp);	/* release cached vnodes */
239 	cache_purgevfs(mp);	/* remove cache entries for this file sys */
240 	if ((error = VFS_SYNC(mp, MNT_WAIT, p->p_ucred, p)) == 0 ||
241 	    (flags & MNT_FORCE))
242 		error = VFS_UNMOUNT(mp, flags, p);
243 	mp->mnt_flag &= ~MNT_UNMOUNT;
244 	vfs_unbusy(mp);
245 	if (error) {
246 		vfs_unlock(mp);
247 	} else {
248 		vrele(coveredvp);
249 		vfs_remove(mp);
250 		if (mp->mnt_mounth != NULL)
251 			panic("unmount: dangling vnode");
252 		free((caddr_t)mp, M_MOUNT);
253 	}
254 	return (error);
255 }
256 
257 /*
258  * Sync system call.
259  * Sync each mounted filesystem.
260  */
261 #ifdef DIAGNOSTIC
262 int syncprt = 0;
263 #endif
264 
265 struct sync_args {
266 	int	dummy;
267 };
268 /* ARGSUSED */
269 sync(p, uap, retval)
270 	struct proc *p;
271 	struct sync_args *uap;
272 	int *retval;
273 {
274 	register struct mount *mp;
275 	struct mount *omp;
276 
277 	mp = rootfs;
278 	do {
279 		/*
280 		 * The lock check below is to avoid races with mount
281 		 * and unmount.
282 		 */
283 		if ((mp->mnt_flag & (MNT_MLOCK|MNT_RDONLY|MNT_MPBUSY)) == 0 &&
284 		    !vfs_busy(mp)) {
285 			VFS_SYNC(mp, MNT_NOWAIT, p->p_ucred, p);
286 			omp = mp;
287 			mp = mp->mnt_next;
288 			vfs_unbusy(omp);
289 		} else
290 			mp = mp->mnt_next;
291 	} while (mp != rootfs);
292 #ifdef DIAGNOSTIC
293 	if (syncprt)
294 		vfs_bufstats();
295 #endif /* DIAGNOSTIC */
296 	return (0);
297 }
298 
299 /*
300  * Operate on filesystem quotas.
301  */
302 struct quotactl_args {
303 	char *path;
304 	int cmd;
305 	int uid;
306 	caddr_t arg;
307 };
308 /* ARGSUSED */
309 quotactl(p, uap, retval)
310 	struct proc *p;
311 	register struct quotactl_args *uap;
312 	int *retval;
313 {
314 	register struct mount *mp;
315 	int error;
316 	struct nameidata nd;
317 
318 	NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, uap->path, p);
319 	if (error = namei(&nd))
320 		return (error);
321 	mp = nd.ni_vp->v_mount;
322 	vrele(nd.ni_vp);
323 	return (VFS_QUOTACTL(mp, uap->cmd, uap->uid, uap->arg, p));
324 }
325 
326 /*
327  * Get filesystem statistics.
328  */
329 struct statfs_args {
330 	char *path;
331 	struct statfs *buf;
332 };
333 /* ARGSUSED */
334 statfs(p, uap, retval)
335 	struct proc *p;
336 	register struct statfs_args *uap;
337 	int *retval;
338 {
339 	register struct mount *mp;
340 	register struct statfs *sp;
341 	int error;
342 	struct nameidata nd;
343 
344 	NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, uap->path, p);
345 	if (error = namei(&nd))
346 		return (error);
347 	mp = nd.ni_vp->v_mount;
348 	sp = &mp->mnt_stat;
349 	vrele(nd.ni_vp);
350 	if (error = VFS_STATFS(mp, sp, p))
351 		return (error);
352 	sp->f_flags = mp->mnt_flag & MNT_VISFLAGMASK;
353 	return (copyout((caddr_t)sp, (caddr_t)uap->buf, sizeof(*sp)));
354 }
355 
356 /*
357  * Get filesystem statistics.
358  */
359 struct fstatfs_args {
360 	int fd;
361 	struct statfs *buf;
362 };
363 /* ARGSUSED */
364 fstatfs(p, uap, retval)
365 	struct proc *p;
366 	register struct fstatfs_args *uap;
367 	int *retval;
368 {
369 	struct file *fp;
370 	struct mount *mp;
371 	register struct statfs *sp;
372 	int error;
373 
374 	if (error = getvnode(p->p_fd, uap->fd, &fp))
375 		return (error);
376 	mp = ((struct vnode *)fp->f_data)->v_mount;
377 	sp = &mp->mnt_stat;
378 	if (error = VFS_STATFS(mp, sp, p))
379 		return (error);
380 	sp->f_flags = mp->mnt_flag & MNT_VISFLAGMASK;
381 	return (copyout((caddr_t)sp, (caddr_t)uap->buf, sizeof(*sp)));
382 }
383 
384 /*
385  * Get statistics on all filesystems.
386  */
387 struct getfsstat_args {
388 	struct statfs *buf;
389 	long bufsize;
390 	int flags;
391 };
392 getfsstat(p, uap, retval)
393 	struct proc *p;
394 	register struct getfsstat_args *uap;
395 	int *retval;
396 {
397 	register struct mount *mp;
398 	register struct statfs *sp;
399 	caddr_t sfsp;
400 	long count, maxcount, error;
401 
402 	maxcount = uap->bufsize / sizeof(struct statfs);
403 	sfsp = (caddr_t)uap->buf;
404 	mp = rootfs;
405 	count = 0;
406 	do {
407 		if (sfsp && count < maxcount &&
408 		    ((mp->mnt_flag & MNT_MLOCK) == 0)) {
409 			sp = &mp->mnt_stat;
410 			/*
411 			 * If MNT_NOWAIT is specified, do not refresh the
412 			 * fsstat cache. MNT_WAIT overrides MNT_NOWAIT.
413 			 */
414 			if (((uap->flags & MNT_NOWAIT) == 0 ||
415 			    (uap->flags & MNT_WAIT)) &&
416 			    (error = VFS_STATFS(mp, sp, p))) {
417 				mp = mp->mnt_prev;
418 				continue;
419 			}
420 			sp->f_flags = mp->mnt_flag & MNT_VISFLAGMASK;
421 			if (error = copyout((caddr_t)sp, sfsp, sizeof(*sp)))
422 				return (error);
423 			sfsp += sizeof(*sp);
424 		}
425 		count++;
426 		mp = mp->mnt_prev;
427 	} while (mp != rootfs);
428 	if (sfsp && count > maxcount)
429 		*retval = maxcount;
430 	else
431 		*retval = count;
432 	return (0);
433 }
434 
435 /*
436  * Change current working directory to a given file descriptor.
437  */
438 struct fchdir_args {
439 	int	fd;
440 };
441 /* ARGSUSED */
442 fchdir(p, uap, retval)
443 	struct proc *p;
444 	struct fchdir_args *uap;
445 	int *retval;
446 {
447 	register struct filedesc *fdp = p->p_fd;
448 	register struct vnode *vp;
449 	struct file *fp;
450 	int error;
451 
452 	if (error = getvnode(fdp, uap->fd, &fp))
453 		return (error);
454 	vp = (struct vnode *)fp->f_data;
455 	VOP_LOCK(vp);
456 	if (vp->v_type != VDIR)
457 		error = ENOTDIR;
458 	else
459 		error = VOP_ACCESS(vp, VEXEC, p->p_ucred, p);
460 	VOP_UNLOCK(vp);
461 	if (error)
462 		return (error);
463 	VREF(vp);
464 	vrele(fdp->fd_cdir);
465 	fdp->fd_cdir = vp;
466 	return (0);
467 }
468 
469 /*
470  * Change current working directory (``.'').
471  */
472 struct chdir_args {
473 	char	*fname;
474 };
475 /* ARGSUSED */
476 chdir(p, uap, retval)
477 	struct proc *p;
478 	struct chdir_args *uap;
479 	int *retval;
480 {
481 	register struct filedesc *fdp = p->p_fd;
482 	int error;
483 	struct nameidata nd;
484 
485 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
486 	if (error = chdirec(&nd, p))
487 		return (error);
488 	vrele(fdp->fd_cdir);
489 	fdp->fd_cdir = nd.ni_vp;
490 	return (0);
491 }
492 
493 /*
494  * Change notion of root (``/'') directory.
495  */
496 struct chroot_args {
497 	char	*fname;
498 };
499 /* ARGSUSED */
500 chroot(p, uap, retval)
501 	struct proc *p;
502 	struct chroot_args *uap;
503 	int *retval;
504 {
505 	register struct filedesc *fdp = p->p_fd;
506 	int error;
507 	struct nameidata nd;
508 
509 	if (error = suser(p->p_ucred, &p->p_acflag))
510 		return (error);
511 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
512 	if (error = chdirec(&nd, p))
513 		return (error);
514 	if (fdp->fd_rdir != NULL)
515 		vrele(fdp->fd_rdir);
516 	fdp->fd_rdir = nd.ni_vp;
517 	return (0);
518 }
519 
520 /*
521  * Common routine for chroot and chdir.
522  */
523 chdirec(ndp, p)
524 	register struct nameidata *ndp;
525 	struct proc *p;
526 {
527 	struct vnode *vp;
528 	int error;
529 
530 	if (error = namei(ndp))
531 		return (error);
532 	vp = ndp->ni_vp;
533 	if (vp->v_type != VDIR)
534 		error = ENOTDIR;
535 	else
536 		error = VOP_ACCESS(vp, VEXEC, p->p_ucred, p);
537 	VOP_UNLOCK(vp);
538 	if (error)
539 		vrele(vp);
540 	return (error);
541 }
542 
543 /*
544  * Open system call.
545  * Check permissions, allocate an open file structure,
546  * and call the device open routine if any.
547  */
548 struct open_args {
549 	char	*fname;
550 	int	mode;
551 	int	crtmode;
552 };
553 open(p, uap, retval)
554 	struct proc *p;
555 	register struct open_args *uap;
556 	int *retval;
557 {
558 	register struct filedesc *fdp = p->p_fd;
559 	register struct file *fp;
560 	register struct vnode *vp;
561 	int fmode, cmode;
562 	struct file *nfp;
563 	int type, indx, error;
564 	struct flock lf;
565 	struct nameidata nd;
566 	extern struct fileops vnops;
567 
568 	if (error = falloc(p, &nfp, &indx))
569 		return (error);
570 	fp = nfp;
571 	fmode = FFLAGS(uap->mode);
572 	cmode = ((uap->crtmode &~ fdp->fd_cmask) & 07777) &~ S_ISVTX;
573 	NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, uap->fname, p);
574 	p->p_dupfd = -indx - 1;			/* XXX check for fdopen */
575 	if (error = vn_open(&nd, fmode, cmode)) {
576 		ffree(fp);
577 		if ((error == ENODEV || error == ENXIO) &&
578 		    p->p_dupfd >= 0 && 			/* XXX from fdopen */
579 		    (error = dupfdopen(fdp, indx, p->p_dupfd,
580 					fmode, error)) == 0) {
581 			*retval = indx;
582 			return (0);
583 		}
584 		if (error == ERESTART)
585 			error = EINTR;
586 		fdp->fd_ofiles[indx] = NULL;
587 		return (error);
588 	}
589 	p->p_dupfd = 0;
590 	vp = nd.ni_vp;
591 	fp->f_flag = fmode & FMASK;
592 	fp->f_type = DTYPE_VNODE;
593 	fp->f_ops = &vnops;
594 	fp->f_data = (caddr_t)vp;
595 	if (fmode & (O_EXLOCK | O_SHLOCK)) {
596 		lf.l_whence = SEEK_SET;
597 		lf.l_start = 0;
598 		lf.l_len = 0;
599 		if (fmode & O_EXLOCK)
600 			lf.l_type = F_WRLCK;
601 		else
602 			lf.l_type = F_RDLCK;
603 		type = F_FLOCK;
604 		if ((fmode & FNONBLOCK) == 0)
605 			type |= F_WAIT;
606 		if (error = VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, type)) {
607 			VOP_UNLOCK(vp);
608 			(void) vn_close(vp, fp->f_flag, fp->f_cred, p);
609 			ffree(fp);
610 			fdp->fd_ofiles[indx] = NULL;
611 			return (error);
612 		}
613 		fp->f_flag |= FHASLOCK;
614 	}
615 	VOP_UNLOCK(vp);
616 	*retval = indx;
617 	return (0);
618 }
619 
620 #ifdef COMPAT_43
621 /*
622  * Creat system call.
623  */
624 struct ocreat_args {
625 	char	*fname;
626 	int	fmode;
627 };
628 ocreat(p, uap, retval)
629 	struct proc *p;
630 	register struct ocreat_args *uap;
631 	int *retval;
632 {
633 	struct open_args openuap;
634 
635 	openuap.fname = uap->fname;
636 	openuap.crtmode = uap->fmode;
637 	openuap.mode = O_WRONLY | O_CREAT | O_TRUNC;
638 	return (open(p, &openuap, retval));
639 }
640 #endif /* COMPAT_43 */
641 
642 /*
643  * Mknod system call.
644  */
645 struct mknod_args {
646 	char	*fname;
647 	int	fmode;
648 	int	dev;
649 };
650 /* ARGSUSED */
651 mknod(p, uap, retval)
652 	struct proc *p;
653 	register struct mknod_args *uap;
654 	int *retval;
655 {
656 	register struct vnode *vp;
657 	struct vattr vattr;
658 	int error;
659 	struct nameidata nd;
660 
661 	if (error = suser(p->p_ucred, &p->p_acflag))
662 		return (error);
663 	NDINIT(&nd, CREATE, LOCKPARENT, UIO_USERSPACE, uap->fname, p);
664 	if (error = namei(&nd))
665 		return (error);
666 	vp = nd.ni_vp;
667 	if (vp != NULL) {
668 		error = EEXIST;
669 		goto out;
670 	}
671 	VATTR_NULL(&vattr);
672 	switch (uap->fmode & S_IFMT) {
673 
674 	case S_IFMT:	/* used by badsect to flag bad sectors */
675 		vattr.va_type = VBAD;
676 		break;
677 	case S_IFCHR:
678 		vattr.va_type = VCHR;
679 		break;
680 	case S_IFBLK:
681 		vattr.va_type = VBLK;
682 		break;
683 	default:
684 		error = EINVAL;
685 		goto out;
686 	}
687 	vattr.va_mode = (uap->fmode & 07777) &~ p->p_fd->fd_cmask;
688 	vattr.va_rdev = uap->dev;
689 out:
690 	if (!error) {
691 		LEASE_CHECK(nd.ni_dvp, p, p->p_ucred, LEASE_WRITE);
692 		error = VOP_MKNOD(nd.ni_dvp, &nd.ni_vp, &nd.ni_cnd, &vattr);
693 	} else {
694 		VOP_ABORTOP(nd.ni_dvp, &nd.ni_cnd);
695 		if (nd.ni_dvp == vp)
696 			vrele(nd.ni_dvp);
697 		else
698 			vput(nd.ni_dvp);
699 		if (vp)
700 			vrele(vp);
701 	}
702 	return (error);
703 }
704 
705 /*
706  * Mkfifo system call.
707  */
708 struct mkfifo_args {
709 	char	*fname;
710 	int	fmode;
711 };
712 /* ARGSUSED */
713 mkfifo(p, uap, retval)
714 	struct proc *p;
715 	register struct mkfifo_args *uap;
716 	int *retval;
717 {
718 	struct vattr vattr;
719 	int error;
720 	struct nameidata nd;
721 
722 #ifndef FIFO
723 	return (EOPNOTSUPP);
724 #else
725 	NDINIT(&nd, CREATE, LOCKPARENT, UIO_USERSPACE, uap->fname, p);
726 	if (error = namei(&nd))
727 		return (error);
728 	if (nd.ni_vp != NULL) {
729 		VOP_ABORTOP(nd.ni_dvp, &nd.ni_cnd);
730 		if (nd.ni_dvp == nd.ni_vp)
731 			vrele(nd.ni_dvp);
732 		else
733 			vput(nd.ni_dvp);
734 		vrele(nd.ni_vp);
735 		return (EEXIST);
736 	}
737 	VATTR_NULL(&vattr);
738 	vattr.va_type = VFIFO;
739 	vattr.va_mode = (uap->fmode & 07777) &~ p->p_fd->fd_cmask;
740 	LEASE_CHECK(nd.ni_dvp, p, p->p_ucred, LEASE_WRITE);
741 	return (VOP_MKNOD(nd.ni_dvp, &nd.ni_vp, &nd.ni_cnd, &vattr));
742 #endif /* FIFO */
743 }
744 
745 /*
746  * Link system call.
747  */
748 struct link_args {
749 	char	*target;
750 	char	*linkname;
751 };
752 /* ARGSUSED */
753 link(p, uap, retval)
754 	struct proc *p;
755 	register struct link_args *uap;
756 	int *retval;
757 {
758 	register struct vnode *vp, *xp;
759 	int error;
760 	struct nameidata nd;
761 
762 	NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, uap->target, p);
763 	if (error = namei(&nd))
764 		return (error);
765 	vp = nd.ni_vp;
766 	if (vp->v_type == VDIR &&
767 	    (error = suser(p->p_ucred, &p->p_acflag)))
768 		goto out1;
769 	nd.ni_cnd.cn_nameiop = CREATE;
770 	nd.ni_cnd.cn_flags = LOCKPARENT;
771 	nd.ni_dirp = (caddr_t)uap->linkname;
772 	if (error = namei(&nd))
773 		goto out1;
774 	xp = nd.ni_vp;
775 	if (xp != NULL) {
776 		error = EEXIST;
777 		goto out;
778 	}
779 	xp = nd.ni_dvp;
780 out:
781 	if (!error) {
782 		LEASE_CHECK(xp, p, p->p_ucred, LEASE_WRITE);
783 		LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
784 		error = VOP_LINK(nd.ni_dvp, vp, &nd.ni_cnd);
785 	} else {
786 		VOP_ABORTOP(nd.ni_dvp, &nd.ni_cnd);
787 		if (nd.ni_dvp == nd.ni_vp)
788 			vrele(nd.ni_dvp);
789 		else
790 			vput(nd.ni_dvp);
791 		if (nd.ni_vp)
792 			vrele(nd.ni_vp);
793 	}
794 out1:
795 	vrele(vp);
796 	return (error);
797 }
798 
799 /*
800  * Make a symbolic link.
801  */
802 struct symlink_args {
803 	char	*target;
804 	char	*linkname;
805 };
806 /* ARGSUSED */
807 symlink(p, uap, retval)
808 	struct proc *p;
809 	register struct symlink_args *uap;
810 	int *retval;
811 {
812 	struct vattr vattr;
813 	char *target;
814 	int error;
815 	struct nameidata nd;
816 
817 	MALLOC(target, char *, MAXPATHLEN, M_NAMEI, M_WAITOK);
818 	if (error = copyinstr(uap->target, target, MAXPATHLEN, (u_int *)0))
819 		goto out;
820 	NDINIT(&nd, CREATE, LOCKPARENT, UIO_USERSPACE, uap->linkname, p);
821 	if (error = namei(&nd))
822 		goto out;
823 	if (nd.ni_vp) {
824 		VOP_ABORTOP(nd.ni_dvp, &nd.ni_cnd);
825 		if (nd.ni_dvp == nd.ni_vp)
826 			vrele(nd.ni_dvp);
827 		else
828 			vput(nd.ni_dvp);
829 		vrele(nd.ni_vp);
830 		error = EEXIST;
831 		goto out;
832 	}
833 	VATTR_NULL(&vattr);
834 	vattr.va_mode = 0777 &~ p->p_fd->fd_cmask;
835 	LEASE_CHECK(nd.ni_dvp, p, p->p_ucred, LEASE_WRITE);
836 	error = VOP_SYMLINK(nd.ni_dvp, &nd.ni_vp, &nd.ni_cnd, &vattr, target);
837 out:
838 	FREE(target, M_NAMEI);
839 	return (error);
840 }
841 
842 /*
843  * Delete a name from the filesystem.
844  */
845 struct unlink_args {
846 	char	*name;
847 };
848 /* ARGSUSED */
849 unlink(p, uap, retval)
850 	struct proc *p;
851 	struct unlink_args *uap;
852 	int *retval;
853 {
854 	register struct vnode *vp;
855 	int error;
856 	struct nameidata nd;
857 
858 	NDINIT(&nd, DELETE, LOCKPARENT | LOCKLEAF, UIO_USERSPACE, uap->name, p);
859 	if (error = namei(&nd))
860 		return (error);
861 	vp = nd.ni_vp;
862 	if (vp->v_type == VDIR &&
863 	    (error = suser(p->p_ucred, &p->p_acflag)))
864 		goto out;
865 	/*
866 	 * The root of a mounted filesystem cannot be deleted.
867 	 */
868 	if (vp->v_flag & VROOT) {
869 		error = EBUSY;
870 		goto out;
871 	}
872 	(void) vnode_pager_uncache(vp);
873 out:
874 	if (!error) {
875 		LEASE_CHECK(nd.ni_dvp, p, p->p_ucred, LEASE_WRITE);
876 		LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
877 		error = VOP_REMOVE(nd.ni_dvp, nd.ni_vp, &nd.ni_cnd);
878 	} else {
879 		VOP_ABORTOP(nd.ni_dvp, &nd.ni_cnd);
880 		if (nd.ni_dvp == vp)
881 			vrele(nd.ni_dvp);
882 		else
883 			vput(nd.ni_dvp);
884 		vput(vp);
885 	}
886 	return (error);
887 }
888 
889 struct __lseek_args {
890 	int	fdes;
891 	int	pad;
892 	off_t	off;
893 	int	sbase;
894 };
895 
896 #if defined(COMPAT_43) || defined(COMPAT_SUNOS)
897 /*
898  * Seek system call.
899  */
900 struct lseek_args {
901 	int	fdes;
902 	long	off;
903 	int	sbase;
904 };
905 lseek(p, uap, retval)
906 	struct proc *p;
907 	register struct lseek_args *uap;
908 	int *retval;
909 {
910 	struct __lseek_args nuap;
911 	off_t qret;
912 	int error;
913 
914 	nuap.fdes = uap->fdes;
915 	nuap.off = uap->off;
916 	nuap.sbase = uap->sbase;
917 	error = __lseek(p, &nuap, &qret);
918 	*(long *)retval = qret;
919 	return (error);
920 }
921 #endif /* COMPAT_43 || COMPAT_SUNOS */
922 
923 /*
924  * Seek system call.
925  */
926 __lseek(p, uap, retval)
927 	struct proc *p;
928 	register struct __lseek_args *uap;
929 	int *retval;
930 {
931 	struct ucred *cred = p->p_ucred;
932 	register struct filedesc *fdp = p->p_fd;
933 	register struct file *fp;
934 	struct vattr vattr;
935 	int error;
936 
937 	if ((unsigned)uap->fdes >= fdp->fd_nfiles ||
938 	    (fp = fdp->fd_ofiles[uap->fdes]) == NULL)
939 		return (EBADF);
940 	if (fp->f_type != DTYPE_VNODE)
941 		return (ESPIPE);
942 	switch (uap->sbase) {
943 
944 	case L_INCR:
945 		fp->f_offset += uap->off;
946 		break;
947 
948 	case L_XTND:
949 		if (error = VOP_GETATTR((struct vnode *)fp->f_data,
950 		    &vattr, cred, p))
951 			return (error);
952 		fp->f_offset = uap->off + vattr.va_size;
953 		break;
954 
955 	case L_SET:
956 		fp->f_offset = uap->off;
957 		break;
958 
959 	default:
960 		return (EINVAL);
961 	}
962 	*(off_t *)retval = fp->f_offset;
963 	return (0);
964 }
965 
966 /*
967  * Check access permissions.
968  */
969 struct saccess_args {
970 	char	*fname;
971 	int	fmode;
972 };
973 /* ARGSUSED */
974 saccess(p, uap, retval)
975 	struct proc *p;
976 	register struct saccess_args *uap;
977 	int *retval;
978 {
979 	register struct ucred *cred = p->p_ucred;
980 	register struct vnode *vp;
981 	int error, mode, svuid, svgid;
982 	struct nameidata nd;
983 
984 	svuid = cred->cr_uid;
985 	svgid = cred->cr_groups[0];
986 	cred->cr_uid = p->p_cred->p_ruid;
987 	cred->cr_groups[0] = p->p_cred->p_rgid;
988 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
989 	if (error = namei(&nd))
990 		goto out1;
991 	vp = nd.ni_vp;
992 	/*
993 	 * fmode == 0 means only check for exist
994 	 */
995 	if (uap->fmode) {
996 		mode = 0;
997 		if (uap->fmode & R_OK)
998 			mode |= VREAD;
999 		if (uap->fmode & W_OK)
1000 			mode |= VWRITE;
1001 		if (uap->fmode & X_OK)
1002 			mode |= VEXEC;
1003 		if ((mode & VWRITE) == 0 || (error = vn_writechk(vp)) == 0)
1004 			error = VOP_ACCESS(vp, mode, cred, p);
1005 	}
1006 	vput(vp);
1007 out1:
1008 	cred->cr_uid = svuid;
1009 	cred->cr_groups[0] = svgid;
1010 	return (error);
1011 }
1012 
1013 #if defined(COMPAT_43) || defined(COMPAT_SUNOS)
1014 /*
1015  * Stat system call.
1016  * This version follows links.
1017  */
1018 struct ostat_args {
1019 	char	*fname;
1020 	struct ostat *ub;
1021 };
1022 /* ARGSUSED */
1023 ostat(p, uap, retval)
1024 	struct proc *p;
1025 	register struct ostat_args *uap;
1026 	int *retval;
1027 {
1028 	struct stat sb;
1029 	struct ostat osb;
1030 	int error;
1031 	struct nameidata nd;
1032 
1033 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1034 	if (error = namei(&nd))
1035 		return (error);
1036 	error = vn_stat(nd.ni_vp, &sb, p);
1037 	vput(nd.ni_vp);
1038 	if (error)
1039 		return (error);
1040 	cvtstat(&sb, &osb);
1041 	error = copyout((caddr_t)&osb, (caddr_t)uap->ub, sizeof (osb));
1042 	return (error);
1043 }
1044 
1045 /*
1046  * Lstat system call.
1047  * This version does not follow links.
1048  */
1049 struct olstat_args {
1050 	char	*fname;
1051 	struct ostat *ub;
1052 };
1053 /* ARGSUSED */
1054 olstat(p, uap, retval)
1055 	struct proc *p;
1056 	register struct olstat_args *uap;
1057 	int *retval;
1058 {
1059 	struct stat sb;
1060 	struct ostat osb;
1061 	int error;
1062 	struct nameidata nd;
1063 
1064 	NDINIT(&nd, LOOKUP, NOFOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1065 	if (error = namei(&nd))
1066 		return (error);
1067 	error = vn_stat(nd.ni_vp, &sb, p);
1068 	vput(nd.ni_vp);
1069 	if (error)
1070 		return (error);
1071 	cvtstat(&sb, &osb);
1072 	error = copyout((caddr_t)&osb, (caddr_t)uap->ub, sizeof (osb));
1073 	return (error);
1074 }
1075 
1076 /*
1077  * convert from an old to a new stat structure.
1078  */
1079 cvtstat(st, ost)
1080 	struct stat *st;
1081 	struct ostat *ost;
1082 {
1083 
1084 	ost->st_dev = st->st_dev;
1085 	ost->st_ino = st->st_ino;
1086 	ost->st_mode = st->st_mode;
1087 	ost->st_nlink = st->st_nlink;
1088 	ost->st_uid = st->st_uid;
1089 	ost->st_gid = st->st_gid;
1090 	ost->st_rdev = st->st_rdev;
1091 	if (st->st_size < (quad_t)1 << 32)
1092 		ost->st_size = st->st_size;
1093 	else
1094 		ost->st_size = -2;
1095 	ost->st_atime = st->st_atime;
1096 	ost->st_mtime = st->st_mtime;
1097 	ost->st_ctime = st->st_ctime;
1098 	ost->st_blksize = st->st_blksize;
1099 	ost->st_blocks = st->st_blocks;
1100 	ost->st_flags = st->st_flags;
1101 	ost->st_gen = st->st_gen;
1102 }
1103 #endif /* COMPAT_43 || COMPAT_SUNOS */
1104 
1105 /*
1106  * Stat system call.
1107  * This version follows links.
1108  */
1109 struct stat_args {
1110 	char	*fname;
1111 	struct stat *ub;
1112 };
1113 /* ARGSUSED */
1114 stat(p, uap, retval)
1115 	struct proc *p;
1116 	register struct stat_args *uap;
1117 	int *retval;
1118 {
1119 	struct stat sb;
1120 	int error;
1121 	struct nameidata nd;
1122 
1123 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1124 	if (error = namei(&nd))
1125 		return (error);
1126 	error = vn_stat(nd.ni_vp, &sb, p);
1127 	vput(nd.ni_vp);
1128 	if (error)
1129 		return (error);
1130 	error = copyout((caddr_t)&sb, (caddr_t)uap->ub, sizeof (sb));
1131 	return (error);
1132 }
1133 
1134 /*
1135  * Lstat system call.
1136  * This version does not follow links.
1137  */
1138 struct lstat_args {
1139 	char	*fname;
1140 	struct stat *ub;
1141 };
1142 /* ARGSUSED */
1143 lstat(p, uap, retval)
1144 	struct proc *p;
1145 	register struct lstat_args *uap;
1146 	int *retval;
1147 {
1148 	struct stat sb;
1149 	int error;
1150 	struct nameidata nd;
1151 
1152 	NDINIT(&nd, LOOKUP, NOFOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1153 	if (error = namei(&nd))
1154 		return (error);
1155 	error = vn_stat(nd.ni_vp, &sb, p);
1156 	vput(nd.ni_vp);
1157 	if (error)
1158 		return (error);
1159 	error = copyout((caddr_t)&sb, (caddr_t)uap->ub, sizeof (sb));
1160 	return (error);
1161 }
1162 
1163 /*
1164  * Return target name of a symbolic link.
1165  */
1166 struct readlink_args {
1167 	char	*name;
1168 	char	*buf;
1169 	int	count;
1170 };
1171 /* ARGSUSED */
1172 readlink(p, uap, retval)
1173 	struct proc *p;
1174 	register struct readlink_args *uap;
1175 	int *retval;
1176 {
1177 	register struct vnode *vp;
1178 	struct iovec aiov;
1179 	struct uio auio;
1180 	int error;
1181 	struct nameidata nd;
1182 
1183 	NDINIT(&nd, LOOKUP, NOFOLLOW | LOCKLEAF, UIO_USERSPACE, uap->name, p);
1184 	if (error = namei(&nd))
1185 		return (error);
1186 	vp = nd.ni_vp;
1187 	if (vp->v_type != VLNK) {
1188 		error = EINVAL;
1189 		goto out;
1190 	}
1191 	aiov.iov_base = uap->buf;
1192 	aiov.iov_len = uap->count;
1193 	auio.uio_iov = &aiov;
1194 	auio.uio_iovcnt = 1;
1195 	auio.uio_offset = 0;
1196 	auio.uio_rw = UIO_READ;
1197 	auio.uio_segflg = UIO_USERSPACE;
1198 	auio.uio_procp = p;
1199 	auio.uio_resid = uap->count;
1200 	error = VOP_READLINK(vp, &auio, p->p_ucred);
1201 out:
1202 	vput(vp);
1203 	*retval = uap->count - auio.uio_resid;
1204 	return (error);
1205 }
1206 
1207 /*
1208  * Change flags of a file given path name.
1209  */
1210 struct chflags_args {
1211 	char	*fname;
1212 	int	flags;
1213 };
1214 /* ARGSUSED */
1215 chflags(p, uap, retval)
1216 	struct proc *p;
1217 	register struct chflags_args *uap;
1218 	int *retval;
1219 {
1220 	register struct vnode *vp;
1221 	struct vattr vattr;
1222 	int error;
1223 	struct nameidata nd;
1224 
1225 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1226 	if (error = namei(&nd))
1227 		return (error);
1228 	vp = nd.ni_vp;
1229 	if (vp->v_mount->mnt_flag & MNT_RDONLY) {
1230 		error = EROFS;
1231 		goto out;
1232 	}
1233 	VATTR_NULL(&vattr);
1234 	vattr.va_flags = uap->flags;
1235 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1236 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1237 out:
1238 	vput(vp);
1239 	return (error);
1240 }
1241 
1242 /*
1243  * Change flags of a file given a file descriptor.
1244  */
1245 struct fchflags_args {
1246 	int	fd;
1247 	int	flags;
1248 };
1249 /* ARGSUSED */
1250 fchflags(p, uap, retval)
1251 	struct proc *p;
1252 	register struct fchflags_args *uap;
1253 	int *retval;
1254 {
1255 	struct vattr vattr;
1256 	struct vnode *vp;
1257 	struct file *fp;
1258 	int error;
1259 
1260 	if (error = getvnode(p->p_fd, uap->fd, &fp))
1261 		return (error);
1262 	vp = (struct vnode *)fp->f_data;
1263 	VOP_LOCK(vp);
1264 	if (vp->v_mount->mnt_flag & MNT_RDONLY) {
1265 		error = EROFS;
1266 		goto out;
1267 	}
1268 	VATTR_NULL(&vattr);
1269 	vattr.va_flags = uap->flags;
1270 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1271 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1272 out:
1273 	VOP_UNLOCK(vp);
1274 	return (error);
1275 }
1276 
1277 /*
1278  * Change mode of a file given path name.
1279  */
1280 struct chmod_args {
1281 	char	*fname;
1282 	int	fmode;
1283 };
1284 /* ARGSUSED */
1285 chmod(p, uap, retval)
1286 	struct proc *p;
1287 	register struct chmod_args *uap;
1288 	int *retval;
1289 {
1290 	register struct vnode *vp;
1291 	struct vattr vattr;
1292 	int error;
1293 	struct nameidata nd;
1294 
1295 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1296 	if (error = namei(&nd))
1297 		return (error);
1298 	vp = nd.ni_vp;
1299 	if (vp->v_mount->mnt_flag & MNT_RDONLY) {
1300 		error = EROFS;
1301 		goto out;
1302 	}
1303 	VATTR_NULL(&vattr);
1304 	vattr.va_mode = uap->fmode & 07777;
1305 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1306 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1307 out:
1308 	vput(vp);
1309 	return (error);
1310 }
1311 
1312 /*
1313  * Change mode of a file given a file descriptor.
1314  */
1315 struct fchmod_args {
1316 	int	fd;
1317 	int	fmode;
1318 };
1319 /* ARGSUSED */
1320 fchmod(p, uap, retval)
1321 	struct proc *p;
1322 	register struct fchmod_args *uap;
1323 	int *retval;
1324 {
1325 	struct vattr vattr;
1326 	struct vnode *vp;
1327 	struct file *fp;
1328 	int error;
1329 
1330 	if (error = getvnode(p->p_fd, uap->fd, &fp))
1331 		return (error);
1332 	vp = (struct vnode *)fp->f_data;
1333 	VOP_LOCK(vp);
1334 	if (vp->v_mount->mnt_flag & MNT_RDONLY) {
1335 		error = EROFS;
1336 		goto out;
1337 	}
1338 	VATTR_NULL(&vattr);
1339 	vattr.va_mode = uap->fmode & 07777;
1340 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1341 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1342 out:
1343 	VOP_UNLOCK(vp);
1344 	return (error);
1345 }
1346 
1347 /*
1348  * Set ownership given a path name.
1349  */
1350 struct chown_args {
1351 	char	*fname;
1352 	int	uid;
1353 	int	gid;
1354 };
1355 /* ARGSUSED */
1356 chown(p, uap, retval)
1357 	struct proc *p;
1358 	register struct chown_args *uap;
1359 	int *retval;
1360 {
1361 	register struct vnode *vp;
1362 	struct vattr vattr;
1363 	int error;
1364 	struct nameidata nd;
1365 
1366 	NDINIT(&nd, LOOKUP, NOFOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1367 	if (error = namei(&nd))
1368 		return (error);
1369 	vp = nd.ni_vp;
1370 	if (vp->v_mount->mnt_flag & MNT_RDONLY) {
1371 		error = EROFS;
1372 		goto out;
1373 	}
1374 	VATTR_NULL(&vattr);
1375 	vattr.va_uid = uap->uid;
1376 	vattr.va_gid = uap->gid;
1377 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1378 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1379 out:
1380 	vput(vp);
1381 	return (error);
1382 }
1383 
1384 /*
1385  * Set ownership given a file descriptor.
1386  */
1387 struct fchown_args {
1388 	int	fd;
1389 	int	uid;
1390 	int	gid;
1391 };
1392 /* ARGSUSED */
1393 fchown(p, uap, retval)
1394 	struct proc *p;
1395 	register struct fchown_args *uap;
1396 	int *retval;
1397 {
1398 	struct vattr vattr;
1399 	struct vnode *vp;
1400 	struct file *fp;
1401 	int error;
1402 
1403 	if (error = getvnode(p->p_fd, uap->fd, &fp))
1404 		return (error);
1405 	vp = (struct vnode *)fp->f_data;
1406 	VOP_LOCK(vp);
1407 	if (vp->v_mount->mnt_flag & MNT_RDONLY) {
1408 		error = EROFS;
1409 		goto out;
1410 	}
1411 	VATTR_NULL(&vattr);
1412 	vattr.va_uid = uap->uid;
1413 	vattr.va_gid = uap->gid;
1414 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1415 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1416 out:
1417 	VOP_UNLOCK(vp);
1418 	return (error);
1419 }
1420 
1421 /*
1422  * Set the access and modification times of a file.
1423  */
1424 struct utimes_args {
1425 	char	*fname;
1426 	struct	timeval *tptr;
1427 };
1428 /* ARGSUSED */
1429 utimes(p, uap, retval)
1430 	struct proc *p;
1431 	register struct utimes_args *uap;
1432 	int *retval;
1433 {
1434 	register struct vnode *vp;
1435 	struct timeval tv[2];
1436 	struct vattr vattr;
1437 	int error;
1438 	struct nameidata nd;
1439 
1440 	if (error = copyin((caddr_t)uap->tptr, (caddr_t)tv, sizeof (tv)))
1441 		return (error);
1442 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1443 	if (error = namei(&nd))
1444 		return (error);
1445 	vp = nd.ni_vp;
1446 	if (vp->v_mount->mnt_flag & MNT_RDONLY) {
1447 		error = EROFS;
1448 		goto out;
1449 	}
1450 	VATTR_NULL(&vattr);
1451 	vattr.va_atime.ts_sec = tv[0].tv_sec;
1452 	vattr.va_atime.ts_nsec = tv[0].tv_usec * 1000;
1453 	vattr.va_mtime.ts_sec = tv[1].tv_sec;
1454 	vattr.va_mtime.ts_nsec = tv[1].tv_usec * 1000;
1455 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1456 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1457 out:
1458 	vput(vp);
1459 	return (error);
1460 }
1461 
1462 struct __truncate_args {
1463 	char	*fname;
1464 	int	pad;
1465 	off_t	length;
1466 };
1467 
1468 /*
1469  * Truncate a file given its path name.
1470  */
1471 /* ARGSUSED */
1472 __truncate(p, uap, retval)
1473 	struct proc *p;
1474 	register struct __truncate_args *uap;
1475 	int *retval;
1476 {
1477 	register struct vnode *vp;
1478 	struct vattr vattr;
1479 	int error;
1480 	struct nameidata nd;
1481 
1482 	NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, uap->fname, p);
1483 	if (error = namei(&nd))
1484 		return (error);
1485 	vp = nd.ni_vp;
1486 	if (vp->v_type == VDIR) {
1487 		error = EISDIR;
1488 		goto out;
1489 	}
1490 	if ((error = vn_writechk(vp)) ||
1491 	    (error = VOP_ACCESS(vp, VWRITE, p->p_ucred, p)))
1492 		goto out;
1493 	VATTR_NULL(&vattr);
1494 	vattr.va_size = uap->length;
1495 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1496 	error = VOP_SETATTR(vp, &vattr, p->p_ucred, p);
1497 out:
1498 	vput(vp);
1499 	return (error);
1500 }
1501 
1502 struct __ftruncate_args {
1503 	int	fd;
1504 	int	pad;
1505 	off_t	length;
1506 };
1507 
1508 /*
1509  * Truncate a file given a file descriptor.
1510  */
1511 /* ARGSUSED */
1512 __ftruncate(p, uap, retval)
1513 	struct proc *p;
1514 	register struct __ftruncate_args *uap;
1515 	int *retval;
1516 {
1517 	struct vattr vattr;
1518 	struct vnode *vp;
1519 	struct file *fp;
1520 	int error;
1521 
1522 	if (error = getvnode(p->p_fd, uap->fd, &fp))
1523 		return (error);
1524 	if ((fp->f_flag & FWRITE) == 0)
1525 		return (EINVAL);
1526 	vp = (struct vnode *)fp->f_data;
1527 	VOP_LOCK(vp);
1528 	if (vp->v_type == VDIR) {
1529 		error = EISDIR;
1530 		goto out;
1531 	}
1532 	if (error = vn_writechk(vp))
1533 		goto out;
1534 	VATTR_NULL(&vattr);
1535 	vattr.va_size = uap->length;
1536 	LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1537 	error = VOP_SETATTR(vp, &vattr, fp->f_cred, p);
1538 out:
1539 	VOP_UNLOCK(vp);
1540 	return (error);
1541 }
1542 
1543 #if defined(COMPAT_43) || defined(COMPAT_SUNOS)
1544 /*
1545  * Truncate a file given its path name.
1546  */
1547 struct truncate_args {
1548 	char	*fname;
1549 	long	length;
1550 };
1551 /* ARGSUSED */
1552 truncate(p, uap, retval)
1553 	struct proc *p;
1554 	register struct truncate_args *uap;
1555 	int *retval;
1556 {
1557 	struct __truncate_args nuap;
1558 
1559 	nuap.fname = uap->fname;
1560 	nuap.length = uap->length;
1561 	return (__truncate(p, &nuap, retval));
1562 }
1563 
1564 /*
1565  * Truncate a file given a file descriptor.
1566  */
1567 struct ftruncate_args {
1568 	int	fd;
1569 	long	length;
1570 };
1571 /* ARGSUSED */
1572 ftruncate(p, uap, retval)
1573 	struct proc *p;
1574 	register struct ftruncate_args *uap;
1575 	int *retval;
1576 {
1577 	struct __ftruncate_args nuap;
1578 
1579 	nuap.fd = uap->fd;
1580 	nuap.length = uap->length;
1581 	return (__ftruncate(p, &nuap, retval));
1582 }
1583 #endif /* COMPAT_43 || COMPAT_SUNOS */
1584 
1585 /*
1586  * Synch an open file.
1587  */
1588 struct fsync_args {
1589 	int	fd;
1590 };
1591 /* ARGSUSED */
1592 fsync(p, uap, retval)
1593 	struct proc *p;
1594 	struct fsync_args *uap;
1595 	int *retval;
1596 {
1597 	register struct vnode *vp;
1598 	struct file *fp;
1599 	int error;
1600 
1601 	if (error = getvnode(p->p_fd, uap->fd, &fp))
1602 		return (error);
1603 	vp = (struct vnode *)fp->f_data;
1604 	VOP_LOCK(vp);
1605 	error = VOP_FSYNC(vp, fp->f_cred, MNT_WAIT, p);
1606 	VOP_UNLOCK(vp);
1607 	return (error);
1608 }
1609 
1610 /*
1611  * Rename system call.
1612  *
1613  * Source and destination must either both be directories, or both
1614  * not be directories.  If target is a directory, it must be empty.
1615  */
1616 struct rename_args {
1617 	char	*from;
1618 	char	*to;
1619 };
1620 /* ARGSUSED */
1621 rename(p, uap, retval)
1622 	struct proc *p;
1623 	register struct rename_args *uap;
1624 	int *retval;
1625 {
1626 	register struct vnode *tvp, *fvp, *tdvp;
1627 	struct nameidata fromnd, tond;
1628 	int error;
1629 
1630 	NDINIT(&fromnd, DELETE, WANTPARENT | SAVESTART, UIO_USERSPACE,
1631 		uap->from, p);
1632 	if (error = namei(&fromnd))
1633 		return (error);
1634 	fvp = fromnd.ni_vp;
1635 	NDINIT(&tond, RENAME, LOCKPARENT | LOCKLEAF | NOCACHE | SAVESTART,
1636 		UIO_USERSPACE, uap->to, p);
1637 	if (error = namei(&tond)) {
1638 		VOP_ABORTOP(fromnd.ni_dvp, &fromnd.ni_cnd);
1639 		vrele(fromnd.ni_dvp);
1640 		vrele(fvp);
1641 		goto out1;
1642 	}
1643 	tdvp = tond.ni_dvp;
1644 	tvp = tond.ni_vp;
1645 	if (tvp != NULL) {
1646 		if (fvp->v_type == VDIR && tvp->v_type != VDIR) {
1647 			error = ENOTDIR;
1648 			goto out;
1649 		} else if (fvp->v_type != VDIR && tvp->v_type == VDIR) {
1650 			error = EISDIR;
1651 			goto out;
1652 		}
1653 	}
1654 	if (fvp == tdvp)
1655 		error = EINVAL;
1656 	/*
1657 	 * If source is the same as the destination (that is the
1658 	 * same inode number with the same name in the same directory),
1659 	 * then there is nothing to do.
1660 	 */
1661 	if (fvp == tvp && fromnd.ni_dvp == tdvp &&
1662 	    fromnd.ni_cnd.cn_namelen == tond.ni_cnd.cn_namelen &&
1663 	    !bcmp(fromnd.ni_cnd.cn_nameptr, tond.ni_cnd.cn_nameptr,
1664 	      fromnd.ni_cnd.cn_namelen))
1665 		error = -1;
1666 out:
1667 	if (!error) {
1668 		LEASE_CHECK(tdvp, p, p->p_ucred, LEASE_WRITE);
1669 		if (fromnd.ni_dvp != tdvp)
1670 			LEASE_CHECK(fromnd.ni_dvp, p, p->p_ucred, LEASE_WRITE);
1671 		if (tvp)
1672 			LEASE_CHECK(tvp, p, p->p_ucred, LEASE_WRITE);
1673 		error = VOP_RENAME(fromnd.ni_dvp, fromnd.ni_vp, &fromnd.ni_cnd,
1674 				   tond.ni_dvp, tond.ni_vp, &tond.ni_cnd);
1675 	} else {
1676 		VOP_ABORTOP(tond.ni_dvp, &tond.ni_cnd);
1677 		if (tdvp == tvp)
1678 			vrele(tdvp);
1679 		else
1680 			vput(tdvp);
1681 		if (tvp)
1682 			vput(tvp);
1683 		VOP_ABORTOP(fromnd.ni_dvp, &fromnd.ni_cnd);
1684 		vrele(fromnd.ni_dvp);
1685 		vrele(fvp);
1686 	}
1687 	vrele(tond.ni_startdir);
1688 	FREE(tond.ni_cnd.cn_pnbuf, M_NAMEI);
1689 out1:
1690 	vrele(fromnd.ni_startdir);
1691 	FREE(fromnd.ni_cnd.cn_pnbuf, M_NAMEI);
1692 	if (error == -1)
1693 		return (0);
1694 	return (error);
1695 }
1696 
1697 /*
1698  * Mkdir system call.
1699  */
1700 struct mkdir_args {
1701 	char	*name;
1702 	int	dmode;
1703 };
1704 /* ARGSUSED */
1705 mkdir(p, uap, retval)
1706 	struct proc *p;
1707 	register struct mkdir_args *uap;
1708 	int *retval;
1709 {
1710 	register struct vnode *vp;
1711 	struct vattr vattr;
1712 	int error;
1713 	struct nameidata nd;
1714 
1715 	NDINIT(&nd, CREATE, LOCKPARENT, UIO_USERSPACE, uap->name, p);
1716 	if (error = namei(&nd))
1717 		return (error);
1718 	vp = nd.ni_vp;
1719 	if (vp != NULL) {
1720 		VOP_ABORTOP(nd.ni_dvp, &nd.ni_cnd);
1721 		if (nd.ni_dvp == vp)
1722 			vrele(nd.ni_dvp);
1723 		else
1724 			vput(nd.ni_dvp);
1725 		vrele(vp);
1726 		return (EEXIST);
1727 	}
1728 	VATTR_NULL(&vattr);
1729 	vattr.va_type = VDIR;
1730 	vattr.va_mode = (uap->dmode & 0777) &~ p->p_fd->fd_cmask;
1731 	LEASE_CHECK(nd.ni_dvp, p, p->p_ucred, LEASE_WRITE);
1732 	error = VOP_MKDIR(nd.ni_dvp, &nd.ni_vp, &nd.ni_cnd, &vattr);
1733 	if (!error)
1734 		vput(nd.ni_vp);
1735 	return (error);
1736 }
1737 
1738 /*
1739  * Rmdir system call.
1740  */
1741 struct rmdir_args {
1742 	char	*name;
1743 };
1744 /* ARGSUSED */
1745 rmdir(p, uap, retval)
1746 	struct proc *p;
1747 	struct rmdir_args *uap;
1748 	int *retval;
1749 {
1750 	register struct vnode *vp;
1751 	int error;
1752 	struct nameidata nd;
1753 
1754 	NDINIT(&nd, DELETE, LOCKPARENT | LOCKLEAF, UIO_USERSPACE, uap->name, p);
1755 	if (error = namei(&nd))
1756 		return (error);
1757 	vp = nd.ni_vp;
1758 	if (vp->v_type != VDIR) {
1759 		error = ENOTDIR;
1760 		goto out;
1761 	}
1762 	/*
1763 	 * No rmdir "." please.
1764 	 */
1765 	if (nd.ni_dvp == vp) {
1766 		error = EINVAL;
1767 		goto out;
1768 	}
1769 	/*
1770 	 * The root of a mounted filesystem cannot be deleted.
1771 	 */
1772 	if (vp->v_flag & VROOT)
1773 		error = EBUSY;
1774 out:
1775 	if (!error) {
1776 		LEASE_CHECK(nd.ni_dvp, p, p->p_ucred, LEASE_WRITE);
1777 		LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE);
1778 		error = VOP_RMDIR(nd.ni_dvp, nd.ni_vp, &nd.ni_cnd);
1779 	} else {
1780 		VOP_ABORTOP(nd.ni_dvp, &nd.ni_cnd);
1781 		if (nd.ni_dvp == vp)
1782 			vrele(nd.ni_dvp);
1783 		else
1784 			vput(nd.ni_dvp);
1785 		vput(vp);
1786 	}
1787 	return (error);
1788 }
1789 
1790 #ifdef COMPAT_43
1791 /*
1792  * Read a block of directory entries in a file system independent format.
1793  */
1794 struct ogetdirentries_args {
1795 	int	fd;
1796 	char	*buf;
1797 	unsigned count;
1798 	long	*basep;
1799 };
1800 ogetdirentries(p, uap, retval)
1801 	struct proc *p;
1802 	register struct ogetdirentries_args *uap;
1803 	int *retval;
1804 {
1805 	register struct vnode *vp;
1806 	struct file *fp;
1807 	struct uio auio, kuio;
1808 	struct iovec aiov, kiov;
1809 	struct dirent *dp, *edp;
1810 	caddr_t dirbuf;
1811 	int error, readcnt;
1812 	long loff;
1813 
1814 	if (error = getvnode(p->p_fd, uap->fd, &fp))
1815 		return (error);
1816 	if ((fp->f_flag & FREAD) == 0)
1817 		return (EBADF);
1818 	vp = (struct vnode *)fp->f_data;
1819 	if (vp->v_type != VDIR)
1820 		return (EINVAL);
1821 	aiov.iov_base = uap->buf;
1822 	aiov.iov_len = uap->count;
1823 	auio.uio_iov = &aiov;
1824 	auio.uio_iovcnt = 1;
1825 	auio.uio_rw = UIO_READ;
1826 	auio.uio_segflg = UIO_USERSPACE;
1827 	auio.uio_procp = p;
1828 	auio.uio_resid = uap->count;
1829 	VOP_LOCK(vp);
1830 	loff = auio.uio_offset = fp->f_offset;
1831 #	if (BYTE_ORDER != LITTLE_ENDIAN)
1832 		if (vp->v_mount->mnt_maxsymlinklen <= 0) {
1833 			error = VOP_READDIR(vp, &auio, fp->f_cred);
1834 			fp->f_offset = auio.uio_offset;
1835 		} else
1836 #	endif
1837 	{
1838 		kuio = auio;
1839 		kuio.uio_iov = &kiov;
1840 		kuio.uio_segflg = UIO_SYSSPACE;
1841 		kiov.iov_len = uap->count;
1842 		MALLOC(dirbuf, caddr_t, uap->count, M_TEMP, M_WAITOK);
1843 		kiov.iov_base = dirbuf;
1844 		error = VOP_READDIR(vp, &kuio, fp->f_cred);
1845 		fp->f_offset = kuio.uio_offset;
1846 		if (error == 0) {
1847 			readcnt = uap->count - kuio.uio_resid;
1848 			edp = (struct dirent *)&dirbuf[readcnt];
1849 			for (dp = (struct dirent *)dirbuf; dp < edp; ) {
1850 #				if (BYTE_ORDER == LITTLE_ENDIAN)
1851 					/*
1852 					 * The expected low byte of
1853 					 * dp->d_namlen is our dp->d_type.
1854 					 * The high MBZ byte of dp->d_namlen
1855 					 * is our dp->d_namlen.
1856 					 */
1857 					dp->d_type = dp->d_namlen;
1858 					dp->d_namlen = 0;
1859 #				else
1860 					/*
1861 					 * The dp->d_type is the high byte
1862 					 * of the expected dp->d_namlen,
1863 					 * so must be zero'ed.
1864 					 */
1865 					dp->d_type = 0;
1866 #				endif
1867 				if (dp->d_reclen > 0) {
1868 					dp = (struct dirent *)
1869 					    ((char *)dp + dp->d_reclen);
1870 				} else {
1871 					error = EIO;
1872 					break;
1873 				}
1874 			}
1875 			if (dp >= edp)
1876 				error = uiomove(dirbuf, readcnt, &auio);
1877 		}
1878 		FREE(dirbuf, M_TEMP);
1879 	}
1880 	VOP_UNLOCK(vp);
1881 	if (error)
1882 		return (error);
1883 	error = copyout((caddr_t)&loff, (caddr_t)uap->basep, sizeof(long));
1884 	*retval = uap->count - auio.uio_resid;
1885 	return (error);
1886 }
1887 #endif
1888 
1889 /*
1890  * Read a block of directory entries in a file system independent format.
1891  */
1892 struct getdirentries_args {
1893 	int	fd;
1894 	char	*buf;
1895 	unsigned count;
1896 	long	*basep;
1897 };
1898 getdirentries(p, uap, retval)
1899 	struct proc *p;
1900 	register struct getdirentries_args *uap;
1901 	int *retval;
1902 {
1903 	register struct vnode *vp;
1904 	struct file *fp;
1905 	struct uio auio;
1906 	struct iovec aiov;
1907 	long loff;
1908 	int error;
1909 
1910 	if (error = getvnode(p->p_fd, uap->fd, &fp))
1911 		return (error);
1912 	if ((fp->f_flag & FREAD) == 0)
1913 		return (EBADF);
1914 	vp = (struct vnode *)fp->f_data;
1915 unionread:
1916 	if (vp->v_type != VDIR)
1917 		return (EINVAL);
1918 	aiov.iov_base = uap->buf;
1919 	aiov.iov_len = uap->count;
1920 	auio.uio_iov = &aiov;
1921 	auio.uio_iovcnt = 1;
1922 	auio.uio_rw = UIO_READ;
1923 	auio.uio_segflg = UIO_USERSPACE;
1924 	auio.uio_procp = p;
1925 	auio.uio_resid = uap->count;
1926 	VOP_LOCK(vp);
1927 	loff = auio.uio_offset = fp->f_offset;
1928 	error = VOP_READDIR(vp, &auio, fp->f_cred);
1929 	fp->f_offset = auio.uio_offset;
1930 	VOP_UNLOCK(vp);
1931 	if (error)
1932 		return (error);
1933 	if ((uap->count == auio.uio_resid) &&
1934 	    (vp->v_flag & VROOT) &&
1935 	    (vp->v_mount->mnt_flag & MNT_UNION)) {
1936 		struct vnode *tvp = vp;
1937 		vp = vp->v_mount->mnt_vnodecovered;
1938 		VREF(vp);
1939 		fp->f_data = (caddr_t) vp;
1940 		fp->f_offset = 0;
1941 		vrele(tvp);
1942 		goto unionread;
1943 	}
1944 	error = copyout((caddr_t)&loff, (caddr_t)uap->basep, sizeof(long));
1945 	*retval = uap->count - auio.uio_resid;
1946 	return (error);
1947 }
1948 
1949 /*
1950  * Set the mode mask for creation of filesystem nodes.
1951  */
1952 struct umask_args {
1953 	int	mask;
1954 };
1955 mode_t				/* XXX */
1956 umask(p, uap, retval)
1957 	struct proc *p;
1958 	struct umask_args *uap;
1959 	int *retval;
1960 {
1961 	register struct filedesc *fdp = p->p_fd;
1962 
1963 	*retval = fdp->fd_cmask;
1964 	fdp->fd_cmask = uap->mask & 07777;
1965 	return (0);
1966 }
1967 
1968 /*
1969  * Void all references to file by ripping underlying filesystem
1970  * away from vnode.
1971  */
1972 struct revoke_args {
1973 	char	*fname;
1974 };
1975 /* ARGSUSED */
1976 revoke(p, uap, retval)
1977 	struct proc *p;
1978 	register struct revoke_args *uap;
1979 	int *retval;
1980 {
1981 	register struct vnode *vp;
1982 	struct vattr vattr;
1983 	int error;
1984 	struct nameidata nd;
1985 
1986 	NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, uap->fname, p);
1987 	if (error = namei(&nd))
1988 		return (error);
1989 	vp = nd.ni_vp;
1990 	if (vp->v_type != VCHR && vp->v_type != VBLK) {
1991 		error = EINVAL;
1992 		goto out;
1993 	}
1994 	if (error = VOP_GETATTR(vp, &vattr, p->p_ucred, p))
1995 		goto out;
1996 	if (p->p_ucred->cr_uid != vattr.va_uid &&
1997 	    (error = suser(p->p_ucred, &p->p_acflag)))
1998 		goto out;
1999 	if (vp->v_usecount > 1 || (vp->v_flag & VALIASED))
2000 		vgoneall(vp);
2001 out:
2002 	vrele(vp);
2003 	return (error);
2004 }
2005 
2006 /*
2007  * Convert a user file descriptor to a kernel file entry.
2008  */
2009 getvnode(fdp, fdes, fpp)
2010 	struct filedesc *fdp;
2011 	struct file **fpp;
2012 	int fdes;
2013 {
2014 	struct file *fp;
2015 
2016 	if ((unsigned)fdes >= fdp->fd_nfiles ||
2017 	    (fp = fdp->fd_ofiles[fdes]) == NULL)
2018 		return (EBADF);
2019 	if (fp->f_type != DTYPE_VNODE)
2020 		return (EINVAL);
2021 	*fpp = fp;
2022 	return (0);
2023 }
2024