diff options
author | Mark Kettenis <kettenis@cvs.openbsd.org> | 2013-08-06 08:22:38 +0000 |
---|---|---|
committer | Mark Kettenis <kettenis@cvs.openbsd.org> | 2013-08-06 08:22:38 +0000 |
commit | a81c1d8411fd014a2c5dfff5dfc5c16ea68ac1b2 (patch) | |
tree | 955c6400b7ab9b5dea83cf004da4547695195cde /sys | |
parent | 52b25c22978760637c8252452fa8b5d38a9ae81e (diff) |
Make it possible to have multiple clonable devices per major.
Diffstat (limited to 'sys')
-rw-r--r-- | sys/kern/spec_vnops.c | 10 | ||||
-rw-r--r-- | sys/sys/specdev.h | 8 |
2 files changed, 14 insertions, 4 deletions
diff --git a/sys/kern/spec_vnops.c b/sys/kern/spec_vnops.c index 49d301de241..20ce5f2da03 100644 --- a/sys/kern/spec_vnops.c +++ b/sys/kern/spec_vnops.c @@ -1,4 +1,4 @@ -/* $OpenBSD: spec_vnops.c,v 1.75 2013/07/29 18:51:42 kettenis Exp $ */ +/* $OpenBSD: spec_vnops.c,v 1.76 2013/08/06 08:22:37 kettenis Exp $ */ /* $NetBSD: spec_vnops.c,v 1.29 1996/04/22 01:42:38 christos Exp $ */ /* @@ -691,6 +691,9 @@ spec_open_clone(struct vop_open_args *ap) DNPRINTF("cloning vnode\n"); + if (minor(vp->v_rdev) >= (1 << CLONE_SHIFT)) + return (ENXIO); + for (i = 1; i < sizeof(vp->v_specbitmap) * NBBY; i++) if (isclr(vp->v_specbitmap, i)) { setbit(vp->v_specbitmap, i); @@ -700,7 +703,8 @@ spec_open_clone(struct vop_open_args *ap) if (i == sizeof(vp->v_specbitmap) * NBBY) return (EBUSY); /* too many open instances */ - error = cdevvp(makedev(major(vp->v_rdev), i), &cvp); + error = cdevvp(makedev(major(vp->v_rdev), + (i << CLONE_SHIFT) | minor(vp->v_rdev)), &cvp); if (error) { clrbit(vp->v_specbitmap, i); return (error); /* out of vnodes */ @@ -746,7 +750,7 @@ spec_close_clone(struct vop_close_args *ap) return (error); /* device close failed */ pvp = vp->v_specparent; /* get parent device */ - clrbit(pvp->v_specbitmap, minor(vp->v_rdev)); + clrbit(pvp->v_specbitmap, minor(vp->v_rdev) >> CLONE_SHIFT); vrele(pvp); return (0); /* clone closed */ diff --git a/sys/sys/specdev.h b/sys/sys/specdev.h index 4de99ce4ff6..1d21e83530d 100644 --- a/sys/sys/specdev.h +++ b/sys/sys/specdev.h @@ -1,4 +1,4 @@ -/* $OpenBSD: specdev.h,v 1.32 2013/06/11 16:42:18 deraadt Exp $ */ +/* $OpenBSD: specdev.h,v 1.33 2013/08/06 08:22:37 kettenis Exp $ */ /* $NetBSD: specdev.h,v 1.12 1996/02/13 13:13:01 mycroft Exp $ */ /* @@ -67,6 +67,12 @@ struct cloneinfo { #define v_specbitmap v_specinfo->si_ci.ci_bitmap /* + * We use the upper 16 bits of the minor to record the clone instance. + * This gives us 8 bits for encoding the real minor number. + */ +#define CLONE_SHIFT 8 + +/* * Special device management */ #define SPECHSZ 64 |