示例#1
0
/*
 * Perform a synchronous indirect write of the given block number
 * on the given device, using the given fbuf.  Upon return the fbp
 * is invalid.
 */
int
fbiwrite(struct fbuf *fbp, vnode_t *devvp, daddr_t bn, int bsize)
{
	struct buf *bp;
	int error, fberror;

	/*
	 * Allocate a temp bp using pageio_setup, but then use it
	 * for physio to the area mapped by fbuf which is currently
	 * all locked down in place.
	 *
	 * XXX - need to have a generalized bp header facility
	 * which we build up pageio_setup on top of.  Other places
	 * (like here and in device drivers for the raw I/O case)
	 * could then use these new facilities in a more straight
	 * forward fashion instead of playing all these games.
	 */
	bp = pageio_setup((struct page *)NULL, fbp->fb_count, devvp, B_WRITE);
	bp->b_flags &= ~B_PAGEIO;		/* XXX */
	bp->b_un.b_addr = fbp->fb_addr;

	bp->b_blkno = bn * btod(bsize);
	bp->b_dev = cmpdev(devvp->v_rdev);	/* store in old dev format */
	bp->b_edev = devvp->v_rdev;
	bp->b_proc = NULL;			/* i.e. the kernel */

	(void) bdev_strategy(bp);
	error = biowait(bp);
	pageio_done(bp);

	/*CSTYLED*/
	FBCOMMON(fbp, S_OTHER, 0, fberror = )

	return (error ? error : fberror);
}
示例#2
0
static int
auto_getattr(
	vnode_t *vp,
	vattr_t *vap,
	int flags,
	cred_t *cred,
	caller_context_t *ct)
{
	fnnode_t *fnp = vntofn(vp);
	vnode_t *newvp;
	vfs_t *vfsp;
	int error;

	AUTOFS_DPRINT((4, "auto_getattr vp %p\n", (void *)vp));

	if (flags & ATTR_TRIGGER) {
		/*
		 * Pre-trigger the mount
		 */
		error = auto_trigger_mount(vp, cred, &newvp);
		if (error)
			return (error);

		if (newvp == NULL)
			goto defattr;

		if (error = vn_vfsrlock_wait(vp)) {
			VN_RELE(newvp);
			return (error);
		}

		vfsp = newvp->v_vfsp;
		VN_RELE(newvp);
	} else {
		/*
		 * Recursive auto_getattr/mount; go to the vfsp == NULL
		 * case.
		 */
		if (vn_vfswlock_held(vp))
			goto defattr;

		if (error = vn_vfsrlock_wait(vp))
			return (error);

		vfsp = vn_mountedvfs(vp);
	}

	if (vfsp != NULL) {
		/*
		 * Node is mounted on.
		 */
		error = VFS_ROOT(vfsp, &newvp);
		vn_vfsunlock(vp);
		if (error)
			return (error);
		mutex_enter(&fnp->fn_lock);
		if (fnp->fn_seen == newvp && fnp->fn_thread == curthread) {
			/*
			 * Recursive auto_getattr(); just release newvp and drop
			 * into the vfsp == NULL case.
			 */
			mutex_exit(&fnp->fn_lock);
			VN_RELE(newvp);
		} else {
			while (fnp->fn_thread && fnp->fn_thread != curthread) {
				fnp->fn_flags |= MF_ATTR_WAIT;
				cv_wait(&fnp->fn_cv_mount, &fnp->fn_lock);
			}
			fnp->fn_thread = curthread;
			fnp->fn_seen = newvp;
			mutex_exit(&fnp->fn_lock);
			error = VOP_GETATTR(newvp, vap, flags, cred, ct);
			VN_RELE(newvp);
			mutex_enter(&fnp->fn_lock);
			fnp->fn_seen = 0;
			fnp->fn_thread = 0;
			if (fnp->fn_flags & MF_ATTR_WAIT) {
				fnp->fn_flags &= ~MF_ATTR_WAIT;
				cv_broadcast(&fnp->fn_cv_mount);
			}
			mutex_exit(&fnp->fn_lock);
			return (error);
		}
	} else {
		vn_vfsunlock(vp);
	}

defattr:
	ASSERT(vp->v_type == VDIR || vp->v_type == VLNK);
	vap->va_uid	= 0;
	vap->va_gid	= 0;
	vap->va_nlink	= fnp->fn_linkcnt;
	vap->va_nodeid	= (u_longlong_t)fnp->fn_nodeid;
	vap->va_size	= fnp->fn_size;
	vap->va_atime	= fnp->fn_atime;
	vap->va_mtime	= fnp->fn_mtime;
	vap->va_ctime	= fnp->fn_ctime;
	vap->va_type	= vp->v_type;
	vap->va_mode	= fnp->fn_mode;
	vap->va_fsid	= vp->v_vfsp->vfs_dev;
	vap->va_rdev	= 0;
	vap->va_blksize	= MAXBSIZE;
	vap->va_nblocks	= (fsblkcnt64_t)btod(vap->va_size);
	vap->va_seq	= 0;

	return (0);
}
示例#3
0
/* ARGSUSED */
int
socket_vop_getattr(struct vnode *vp, struct vattr *vap, int flags,
    struct cred *cr, caller_context_t *ct)
{
	dev_t		fsid;
	struct sonode 	*so;
	static int	sonode_shift = 0;

	/*
	 * Calculate the amount of bitshift to a sonode pointer which will
	 * still keep it unique.  See below.
	 */
	if (sonode_shift == 0)
		sonode_shift = highbit(sizeof (struct sonode));
	ASSERT(sonode_shift > 0);

	so = VTOSO(vp);
	fsid = sockdev;

	if (so->so_version == SOV_STREAM) {
		/*
		 * The imaginary "sockmod" has been popped - act
		 * as a stream
		 */
		vap->va_type = VCHR;
		vap->va_mode = 0;
	} else {
		vap->va_type = vp->v_type;
		vap->va_mode = S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|
		    S_IROTH|S_IWOTH;
	}
	vap->va_uid = vap->va_gid = 0;
	vap->va_fsid = fsid;
	/*
	 * If the va_nodeid is > MAX_USHORT, then i386 stats might fail.
	 * So we shift down the sonode pointer to try and get the most
	 * uniqueness into 16-bits.
	 */
	vap->va_nodeid = ((ino_t)so >> sonode_shift) & 0xFFFF;
	vap->va_nlink = 0;
	vap->va_size = 0;

	/*
	 * We need to zero out the va_rdev to avoid some fstats getting
	 * EOVERFLOW.  This also mimics SunOS 4.x and BSD behavior.
	 */
	vap->va_rdev = (dev_t)0;
	vap->va_blksize = MAXBSIZE;
	vap->va_nblocks = btod(vap->va_size);

	if (!SOCK_IS_NONSTR(so)) {
		sotpi_info_t *sti = SOTOTPI(so);

		mutex_enter(&so->so_lock);
		vap->va_atime.tv_sec = sti->sti_atime;
		vap->va_mtime.tv_sec = sti->sti_mtime;
		vap->va_ctime.tv_sec = sti->sti_ctime;
		mutex_exit(&so->so_lock);
	} else {
		vap->va_atime.tv_sec = 0;
		vap->va_mtime.tv_sec = 0;
		vap->va_ctime.tv_sec = 0;
	}

	vap->va_atime.tv_nsec = 0;
	vap->va_mtime.tv_nsec = 0;
	vap->va_ctime.tv_nsec = 0;
	vap->va_seq = 0;

	return (0);
}
示例#4
0
/*
 * return statefile offset in DEV_BSIZE units
 */
int
cpr_statefile_offset(void)
{
	return (cprconfig.cf_type != CFT_UFS ? btod(CPR_SPEC_OFFSET) : 0);
}
示例#5
0
/*
 * return statefile offset in DEV_BSIZE units
 */
int
cpr_statefile_offset(void)
{
	return (cpr_statefile_is_spec() ? btod(CPR_SPEC_OFFSET) : 0);
}