#include <sys/signal2.h>
#include <sys/vnode.h>
#include <sys/malloc.h>
+#include <sys/sysproto.h>
+#include <sys/mman.h>
#include <sys/linker.h>
#include <sys/fcntl.h>
+#include <sys/nlookup.h>
+#include <sys/devfs.h>
#include <vm/vm.h>
#include <vm/vm_object.h>
#include <vm/vm_page.h>
#include <vm/vm_pager.h>
#include <vm/vnode_pager.h>
+#include <vm/vm_extern.h>
#include <sys/buf2.h>
#include <sys/thread2.h>
MALLOC_DEFINE(M_MFSNODE, "MFS node", "MFS vnode private part");
-extern struct vop_ops *mfs_vnode_vops_p;
-
static int mfs_mount (struct mount *mp,
char *path, caddr_t data, struct ucred *td);
static int mfs_start (struct mount *mp, int flags);
static int mfs_statfs (struct mount *mp, struct statfs *sbp,
struct ucred *cred);
static int mfs_init (struct vfsconf *);
+static void mfs_doio(struct bio *bio, struct mfsnode *mfsp);
d_open_t mfsopen;
d_close_t mfsclose;
{
cdev_t dev = ap->a_head.a_dev;
+#if 0
if (ap->a_oflags & FWRITE)
return(EROFS);
+#endif
if (dev->si_drv1)
return(0);
return(ENXIO);
int
mfsclose(struct dev_close_args *ap)
{
+ cdev_t dev = ap->a_head.a_dev;
+ struct mfsnode *mfsp;
+
+ if ((mfsp = dev->si_drv1) == NULL)
+ return(0);
+ mfsp->mfs_active = 0;
+ wakeup((caddr_t)mfsp);
return(0);
}
/*
* Initiate I/O
*/
- bioq_insert_tail(&mfsp->bio_queue, bio);
- wakeup((caddr_t)mfsp);
+ if (mfsp->mfs_td == curthread) {
+ mfs_doio(bio, mfsp);
+ } else {
+ bioq_insert_tail(&mfsp->bio_queue, bio);
+ wakeup((caddr_t)mfsp);
+ }
return(0);
/*
struct ufsmount *ump;
struct fs *fs;
struct mfsnode *mfsp;
+ struct nlookupdata nd;
size_t size;
- int flags, err;
+ char devname[16];
+ int flags;
int minnum;
+ int error;
cdev_t dev;
/*
panic("mfs_mount: mount MFS as root: not configured!");
}
+ mfsp = NULL;
+
/*
***
* Mounting non-root file system or updating a file system
*/
/* copy in user arguments*/
- if ((err = copyin(data, (caddr_t)&args, sizeof (struct mfs_args))) != 0)
+ error = copyin(data, (caddr_t)&args, sizeof (struct mfs_args));
+ if (error)
goto error_1;
/*
flags = WRITECLOSE;
if (mp->mnt_flag & MNT_FORCE)
flags |= FORCECLOSE;
- err = ffs_flushfiles(mp, flags);
- if (err)
+ error = ffs_flushfiles(mp, flags);
+ if (error)
goto error_1;
}
if (fs->fs_ronly && (mp->mnt_kern_flag & MNTK_WANTRDWR)) {
* Process export requests. Jumping to "success"
* will return the vfs_export() error code.
*/
- err = vfs_export(mp, &ump->um_export, &args.export);
+ error = vfs_export(mp, &ump->um_export, &args.export);
goto success;
}
/* XXX MFS does not support name updating*/
goto success;
}
+
/*
- * Do the MALLOC before the getnewvnode since doing so afterward
+ * Do the MALLOC before the make_dev since doing so afterward
* might cause a bogus v_data pointer to get dereferenced
* elsewhere if MALLOC should block.
*/
- MALLOC(mfsp, struct mfsnode *, sizeof *mfsp, M_MFSNODE, M_WAITOK);
-
- err = getspecialvnode(VT_MFS, NULL, &mfs_vnode_vops_p, &devvp, 0, 0);
- if (err) {
- FREE(mfsp, M_MFSNODE);
- goto error_1;
- }
+ MALLOC(mfsp, struct mfsnode *, sizeof *mfsp, M_MFSNODE,
+ M_WAITOK|M_ZERO);
- minnum = (curproc->p_pid & 0xFF) |
- ((curproc->p_pid & ~0xFF) << 8);
+ minnum = (int)curproc->p_pid;
- devvp->v_type = VCHR;
dev = make_dev(&mfs_ops, minnum, UID_ROOT, GID_WHEEL, 0600,
- "MFS%d", minnum >> 16);
+ "mfs%d", minnum);
/* It is not clear that these will get initialized otherwise */
dev->si_bsize_phys = DEV_BSIZE;
dev->si_iosize_max = DFLTPHYS;
dev->si_drv1 = mfsp;
- addaliasu(devvp, mfs_ops.head.maj, minnum);
- devvp->v_data = mfsp;
mfsp->mfs_baseoff = args.base;
mfsp->mfs_size = args.size;
- mfsp->mfs_vnode = devvp;
- mfsp->mfs_dev = reference_dev(dev);
+ mfsp->mfs_dev = dev;
mfsp->mfs_td = curthread;
mfsp->mfs_active = 1;
bioq_init(&mfsp->bio_queue);
+ devfs_config(); /* sync devfs work */
+ ksnprintf(devname, sizeof(devname), "/dev/mfs%d", minnum);
+ nlookup_init(&nd, devname, UIO_SYSSPACE, 0);
+ devvp = NULL;
+ error = nlookup(&nd);
+ if (error == 0) {
+ devvp = nd.nl_nch.ncp->nc_vp;
+ if (devvp == NULL)
+ error = ENOENT;
+ error = vget(devvp, LK_SHARED);
+ }
+ nlookup_done(&nd);
+
+ if (error)
+ goto error_1;
+ vn_unlock(devvp);
+
/*
* Our 'block' device must be backed by a VM object. Theoretically
* we could use the anonymous memory VM object supplied by userland,
* being referenced externally. We have to undo the refs for
* the self reference between vnode and object.
*/
- vnode_pager_alloc(devvp, args.size, 0, 0);
- vrele(devvp);
- --devvp->v_object->ref_count;
+ vnode_pager_setsize(devvp, args.size);
/* Save "mounted from" info for mount point (NULL pad)*/
- copyinstr( args.fspec, /* device name*/
- mp->mnt_stat.f_mntfromname, /* save area*/
- MNAMELEN - 1, /* max size*/
- &size); /* real size*/
- bzero( mp->mnt_stat.f_mntfromname + size, MNAMELEN - size);
-
- vx_unlock(devvp);
- if ((err = ffs_mountfs(devvp, mp, M_MFSNODE)) != 0) {
+ copyinstr(args.fspec, /* device name*/
+ mp->mnt_stat.f_mntfromname, /* save area*/
+ MNAMELEN - 1, /* max size*/
+ &size); /* real size*/
+ bzero(mp->mnt_stat.f_mntfromname + size, MNAMELEN - size);
+ /* vref is eaten by mount? */
+
+ error = ffs_mountfs(devvp, mp, M_MFSNODE);
+ if (error) {
mfsp->mfs_active = 0;
goto error_2;
}
goto success;
error_2: /* error with devvp held*/
-
- /* release devvp before failing*/
vrele(devvp);
error_1: /* no state to back out*/
+ if (mfsp) {
+ if (mfsp->mfs_dev) {
+ destroy_dev(mfsp->mfs_dev);
+ mfsp->mfs_dev = NULL;
+ }
+ FREE(mfsp, M_MFSNODE);
+ }
success:
- return( err);
+ return(error);
}
/*
mfs_start(struct mount *mp, int flags)
{
struct vnode *vp = VFSTOUFS(mp)->um_devvp;
- struct mfsnode *mfsp = VTOMFS(vp);
+ struct mfsnode *mfsp = vp->v_rdev->si_drv1;
struct bio *bio;
struct buf *bp;
int gotsig = 0, sig;
gotsig++; /* try to unmount in next pass */
}
PRELE(curproc);
- v_release_rdev(vp); /* hack because we do not implement CLOSE */
- /* XXX destroy/release devvp */
+ if (mfsp->mfs_dev) {
+ destroy_dev(mfsp->mfs_dev);
+ mfsp->mfs_dev = NULL;
+ }
+ FREE(mfsp, M_MFSNODE);
return (0);
}
{
return (0);
}
+
+/*
+ * Memory file system I/O.
+ *
+ * Trivial on the HP since buffer has already been mapping into KVA space.
+ *
+ * Read and Write are handled with a simple copyin and copyout.
+ *
+ * We also partially support VOP_FREEBLKS(). We can't implement
+ * completely -- for example, on fragments or inode metadata, but we can
+ * implement it for page-aligned requests.
+ */
+static void
+mfs_doio(struct bio *bio, struct mfsnode *mfsp)
+{
+ struct buf *bp = bio->bio_buf;
+ caddr_t base = mfsp->mfs_baseoff + bio->bio_offset;
+ int bytes;
+
+ switch(bp->b_cmd) {
+ case BUF_CMD_FREEBLKS:
+ /*
+ * Implement FREEBLKS, which allows the filesystem to tell
+ * a block device when blocks are no longer needed (like when
+ * a file is deleted). We use the hook to MADV_FREE the VM.
+ * This makes an MFS filesystem work as well or better then
+ * a sun-style swap-mounted filesystem.
+ */
+ bytes = bp->b_bcount;
+
+ if ((vm_offset_t)base & PAGE_MASK) {
+ int n = PAGE_SIZE - ((vm_offset_t)base & PAGE_MASK);
+ bytes -= n;
+ base += n;
+ }
+ if (bytes > 0) {
+ struct madvise_args uap;
+
+ bytes &= ~PAGE_MASK;
+ if (bytes != 0) {
+ bzero(&uap, sizeof(uap));
+ uap.addr = base;
+ uap.len = bytes;
+ uap.behav = MADV_FREE;
+ sys_madvise(&uap);
+ }
+ }
+ bp->b_error = 0;
+ break;
+ case BUF_CMD_READ:
+ /*
+ * Read data from our 'memory' disk
+ */
+ bp->b_error = copyin(base, bp->b_data, bp->b_bcount);
+ break;
+ case BUF_CMD_WRITE:
+ /*
+ * Write data to our 'memory' disk
+ */
+ bp->b_error = copyout(bp->b_data, base, bp->b_bcount);
+ break;
+ default:
+ panic("mfs: bad b_cmd %d\n", bp->b_cmd);
+ }
+ if (bp->b_error)
+ bp->b_flags |= B_ERROR;
+ biodone(bio);
+}
+++ /dev/null
-/*
- * Copyright (c) 1989, 1993
- * The Regents of the University of California. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. All advertising materials mentioning features or use of this software
- * must display the following acknowledgement:
- * This product includes software developed by the University of
- * California, Berkeley and its contributors.
- * 4. Neither the name of the University nor the names of its contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
- * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
- * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
- * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- *
- * @(#)mfs_vnops.c 8.11 (Berkeley) 5/22/95
- * $FreeBSD: src/sys/ufs/mfs/mfs_vnops.c,v 1.47.2.1 2001/05/22 02:06:43 bp Exp $
- * $DragonFly: src/sys/vfs/mfs/mfs_vnops.c,v 1.37 2007/08/13 17:31:56 dillon Exp $
- */
-
-#include <sys/param.h>
-#include <sys/systm.h>
-#include <sys/kernel.h>
-#include <sys/proc.h>
-#include <sys/buf.h>
-#include <sys/vnode.h>
-#include <sys/malloc.h>
-#include <sys/sysproto.h>
-#include <sys/mman.h>
-#include <sys/conf.h>
-
-#include <vm/vm.h>
-#include <vm/vm_object.h>
-#include <vm/vm_page.h>
-#include <vm/vm_pager.h>
-#include <vm/vnode_pager.h>
-
-#include <sys/buf2.h>
-#include <sys/thread2.h>
-
-#include "mfsnode.h"
-#include "mfs_extern.h"
-
-static int mfs_badop (struct vop_generic_args *);
-static int mfs_bmap (struct vop_bmap_args *);
-static int mfs_close (struct vop_close_args *);
-static int mfs_fsync (struct vop_fsync_args *);
-static int mfs_freeblks (struct vop_freeblks_args *);
-static int mfs_inactive (struct vop_inactive_args *); /* XXX */
-static int mfs_open (struct vop_open_args *);
-static int mfs_reclaim (struct vop_reclaim_args *); /* XXX */
-static int mfs_print (struct vop_print_args *); /* XXX */
-static int mfs_strategy (struct vop_strategy_args *); /* XXX */
-/*
- * mfs vnode operations. Note: the vops here are used for the MFS block
- * device, not for operations on files (MFS calls the ffs mount code for that)
- */
-static struct vop_ops mfs_vnode_vops = {
- .vop_default = mfs_badop,
- .vop_bmap = mfs_bmap,
- .vop_close = mfs_close,
- .vop_freeblks = mfs_freeblks,
- .vop_fsync = mfs_fsync,
- .vop_inactive = mfs_inactive,
- .vop_ioctl = (void *)vop_enotty,
- .vop_open = mfs_open,
- .vop_print = mfs_print,
- .vop_reclaim = mfs_reclaim,
- .vop_strategy = mfs_strategy,
-};
-
-struct vop_ops *mfs_vnode_vops_p = &mfs_vnode_vops;
-
-VNODEOP_SET(mfs_vnode_vops);
-
-/*
- * Vnode Operations.
- *
- * Open called to allow memory filesystem to initialize and
- * validate before actual IO. Record our process identifier
- * so we can tell when we are doing I/O to ourself.
- *
- * NOTE: new device sequencing. mounts check the device reference count
- * before calling open, so we must associate the device in open and
- * disassociate it in close rather then faking it when we created the vnode.
- *
- * mfs_open(struct vnode *a_vp, int a_mode, struct ucred *a_cred,
- * struct file *a_fp)
- */
-/* ARGSUSED */
-static int
-mfs_open(struct vop_open_args *ap)
-{
- struct vnode *vp = ap->a_vp;
- struct mfsnode *mfsp = VTOMFS(vp);
-
- if (vp->v_type != VCHR)
- panic("mfs_open not VCHR");
- if (vp->v_rdev == NULL)
- v_associate_rdev(vp, mfsp->mfs_dev);
- return (vop_stdopen(ap));
-}
-
-static int
-mfs_fsync(struct vop_fsync_args *ap)
-{
- return (0);
-}
-
-/*
- * mfs_freeblks() - hook to allow us to free physical memory.
- *
- * We implement the BUF_CMD_FREEBLKS strategy. We can't just madvise()
- * here because we have to do it in the correct order vs other bio
- * requests, so we queue it.
- *
- * Note: geteblk() sets B_INVAL. We leave it set to guarentee buffer
- * throw-away on brelse()? XXX
- *
- * mfs_freeblks(struct vnode *a_vp, daddr_t a_addr, daddr_t a_length)
- */
-static int
-mfs_freeblks(struct vop_freeblks_args *ap)
-{
- struct buf *bp;
- struct vnode *vp = ap->a_vp;
-
- bp = geteblk(ap->a_length);
- bp->b_cmd = BUF_CMD_FREEBLKS;
- bp->b_bio1.bio_offset = ap->a_offset;
- bp->b_bcount = ap->a_length;
- BUF_KERNPROC(bp);
- vn_strategy(vp, &bp->b_bio1);
- return(0);
-}
-
-/*
- * Pass I/O requests to the memory filesystem process.
- *
- * mfs_strategy(struct vnode *a_vp, struct bio *a_bio)
- */
-static int
-mfs_strategy(struct vop_strategy_args *ap)
-{
- struct bio *bio = ap->a_bio;
- struct buf *bp = bio->bio_buf;
- struct mfsnode *mfsp;
- struct thread *td = curthread; /* XXX */
-
- mfsp = ap->a_vp->v_rdev->si_drv1;
- if (mfsp == NULL) {
- bp->b_error = ENXIO;
- bp->b_flags |= B_ERROR;
- biodone(bio);
- return(0);
- }
-
- /*
- * splbio required for queueing/dequeueing, in case of forwarded
- * BPs from bio interrupts (?). It may not be necessary.
- */
-
- crit_enter();
-
- if (mfsp->mfs_td == NULL) {
- /*
- * mini-root. Note: BUF_CMD_FREEBLKS not supported at the
- * moment, since we do not know what kind of dataspace
- * b_data is in.
- */
- caddr_t base;
-
- base = mfsp->mfs_baseoff + bio->bio_offset;
- switch(bp->b_cmd) {
- case BUF_CMD_FREEBLKS:
- break;
- case BUF_CMD_READ:
- bcopy(base, bp->b_data, bp->b_bcount);
- break;
- case BUF_CMD_WRITE:
- bcopy(bp->b_data, base, bp->b_bcount);
- break;
- default:
- panic("mfs: bad b_cmd %d\n", bp->b_cmd);
- }
- biodone(bio);
- } else if (mfsp->mfs_td == td) {
- /*
- * VOP to self
- */
- crit_exit();
- mfs_doio(bio, mfsp);
- crit_enter();
- } else {
- /*
- * VOP from some other process, queue to MFS process and
- * wake it up.
- */
- bioq_insert_tail(&mfsp->bio_queue, bio);
- wakeup((caddr_t)mfsp);
- }
- crit_exit();
- return (0);
-}
-
-/*
- * Memory file system I/O.
- *
- * Trivial on the HP since buffer has already been mapping into KVA space.
- *
- * Read and Write are handled with a simple copyin and copyout.
- *
- * We also partially support VOP_FREEBLKS(). We can't implement
- * completely -- for example, on fragments or inode metadata, but we can
- * implement it for page-aligned requests.
- */
-void
-mfs_doio(struct bio *bio, struct mfsnode *mfsp)
-{
- struct buf *bp = bio->bio_buf;
- caddr_t base = mfsp->mfs_baseoff + bio->bio_offset;
- int bytes;
-
- switch(bp->b_cmd) {
- case BUF_CMD_FREEBLKS:
- /*
- * Implement FREEBLKS, which allows the filesystem to tell
- * a block device when blocks are no longer needed (like when
- * a file is deleted). We use the hook to MADV_FREE the VM.
- * This makes an MFS filesystem work as well or better then
- * a sun-style swap-mounted filesystem.
- */
- bytes = bp->b_bcount;
-
- if ((vm_offset_t)base & PAGE_MASK) {
- int n = PAGE_SIZE - ((vm_offset_t)base & PAGE_MASK);
- bytes -= n;
- base += n;
- }
- if (bytes > 0) {
- struct madvise_args uap;
-
- bytes &= ~PAGE_MASK;
- if (bytes != 0) {
- bzero(&uap, sizeof(uap));
- uap.addr = base;
- uap.len = bytes;
- uap.behav = MADV_FREE;
- sys_madvise(&uap);
- }
- }
- bp->b_error = 0;
- break;
- case BUF_CMD_READ:
- /*
- * Read data from our 'memory' disk
- */
- bp->b_error = copyin(base, bp->b_data, bp->b_bcount);
- break;
- case BUF_CMD_WRITE:
- /*
- * Write data to our 'memory' disk
- */
- bp->b_error = copyout(bp->b_data, base, bp->b_bcount);
- break;
- default:
- panic("mfs: bad b_cmd %d\n", bp->b_cmd);
- }
- if (bp->b_error)
- bp->b_flags |= B_ERROR;
- biodone(bio);
-}
-
-/*
- * This is a noop, simply returning what one has been given.
- *
- * mfs_bmap(struct vnode *a_vp, off_t a_loffset,
- * off_t *a_doffsetp, int *a_runp, int *a_runb)
- */
-static int
-mfs_bmap(struct vop_bmap_args *ap)
-{
- if (ap->a_doffsetp != NULL)
- *ap->a_doffsetp = ap->a_loffset;
- if (ap->a_runp != NULL)
- *ap->a_runp = 0;
- if (ap->a_runb != NULL)
- *ap->a_runb = 0;
- return (0);
-}
-
-/*
- * Memory filesystem close routine
- *
- * mfs_close(struct vnode *a_vp, int a_fflag)
- */
-/* ARGSUSED */
-static int
-mfs_close(struct vop_close_args *ap)
-{
- struct vnode *vp = ap->a_vp;
- struct mfsnode *mfsp = VTOMFS(vp);
- struct bio *bio;
- int error = 0;
-
- /*
- * Finish any pending I/O requests.
- */
- while ((bio = bioq_first(&mfsp->bio_queue)) != NULL) {
- bioq_remove(&mfsp->bio_queue, bio);
- mfs_doio(bio, mfsp);
- wakeup((caddr_t)bio->bio_buf);
- }
-
- /*
- * We really only care about the last close
- */
- if (vp->v_opencount > 1)
- goto done;
-
- /*
- * Synchronize any remaining buffers and then destroy them.
- */
- if ((error = vinvalbuf(vp, V_SAVE, 0, 0)) != 0)
- goto done;
-
- /*
- * Get rid of the pseudo-backing object. Since the object is
- * not directly memory mapped, we don't have to worry about
- * synchronizing it.
- */
- if (vp->v_object)
- vm_pager_deallocate(vp->v_object);
-
- /*
- * There should be no way to have any more uses of this
- * vnode, so if we find any other uses, it is a panic.
- */
- if (vp->v_sysref.refcnt > 1)
- kprintf("mfs_close: ref count %d > 1\n", vp->v_sysref.refcnt);
- if (vp->v_sysref.refcnt > 1 || (bioq_first(&mfsp->bio_queue) != NULL))
- panic("mfs_close");
- /*
- * Send a request to the filesystem server to exit.
- */
- mfsp->mfs_active = 0;
- v_release_rdev(vp);
- if (mfsp->mfs_dev) {
- destroy_dev(mfsp->mfs_dev);
- mfsp->mfs_dev = NULL;
- }
- wakeup((caddr_t)mfsp);
-done:
- vop_stdclose(ap);
- return (error);
-}
-
-/*
- * Memory filesystem inactive routine
- *
- * mfs_inactive(struct vnode *a_vp)
- */
-/* ARGSUSED */
-static int
-mfs_inactive(struct vop_inactive_args *ap)
-{
- struct vnode *vp = ap->a_vp;
- struct mfsnode *mfsp = VTOMFS(vp);
-
- if (bioq_first(&mfsp->bio_queue) != NULL)
- panic("mfs_inactive: not inactive (next buffer %p)",
- bioq_first(&mfsp->bio_queue));
- return (0);
-}
-
-/*
- * Reclaim a memory filesystem devvp so that it can be reused.
- *
- * mfs_reclaim(struct vnode *a_vp)
- */
-static int
-mfs_reclaim(struct vop_reclaim_args *ap)
-{
- struct vnode *vp = ap->a_vp;
-
- FREE(vp->v_data, M_MFSNODE);
- vp->v_data = NULL;
- return (0);
-}
-
-/*
- * Print out the contents of an mfsnode.
- *
- * mfs_print(struct vnode *a_vp)
- */
-static int
-mfs_print(struct vop_print_args *ap)
-{
- struct mfsnode *mfsp = VTOMFS(ap->a_vp);
-
- kprintf("tag VT_MFS, td %p, base %p, size %ld\n",
- mfsp->mfs_td, (void *)mfsp->mfs_baseoff, mfsp->mfs_size);
- return (0);
-}
-
-/*
- * Block device bad operation
- */
-static int
-mfs_badop(struct vop_generic_args *ap)
-{
- int i;
-
- kprintf("mfs_badop[%s]\n", ap->a_desc->sd_name);
- i = vop_defaultop(ap);
- kprintf("mfs_badop[%s] = %d\n", ap->a_desc->sd_name, i);
- return (i);
-}
-