Remove the SLICE code.
This clearly needs alot more thought, and we dont need this to hunt us down in 3.0-RELEASE.
This commit is contained in:
parent
355150a489
commit
d024c95599
@ -34,7 +34,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)autoconf.c 7.1 (Berkeley) 5/9/91
|
||||
* $Id: autoconf.c,v 1.103 1998/08/23 14:17:52 des Exp $
|
||||
* $Id: autoconf.c,v 1.104 1998/09/03 20:59:28 nsouch Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -45,7 +45,6 @@
|
||||
* devices are determined (from possibilities mentioned in ioconf.c),
|
||||
* and the drivers are initialized.
|
||||
*/
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
#include "opt_bootp.h"
|
||||
#include "opt_ffs.h"
|
||||
#include "opt_cd9660.h"
|
||||
@ -111,7 +110,6 @@ SYSINIT(configure, SI_SUB_CONFIGURE, SI_ORDER_FIRST, configure, NULL)
|
||||
static void configure_finish __P((void));
|
||||
static void configure_start __P((void));
|
||||
static int setdumpdev __P((dev_t dev));
|
||||
#ifndef SLICE
|
||||
static void setroot __P((void));
|
||||
|
||||
#ifdef CD9660
|
||||
@ -175,7 +173,6 @@ find_cdrom_root()
|
||||
return EINVAL;
|
||||
}
|
||||
#endif /* CD9660 */
|
||||
#endif /* !SLICE */
|
||||
|
||||
static void
|
||||
configure_start()
|
||||
@ -309,7 +306,6 @@ configure(dummy)
|
||||
cold = 0;
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
void
|
||||
cpu_rootconf()
|
||||
@ -388,7 +384,6 @@ cpu_rootconf()
|
||||
setconf();
|
||||
}
|
||||
|
||||
#endif /* !SLICE */
|
||||
|
||||
void
|
||||
cpu_dumpconf()
|
||||
@ -431,7 +426,6 @@ setdumpdev(dev)
|
||||
return (0);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
u_long bootdev = 0; /* not a dev_t - encoding is different */
|
||||
|
||||
@ -501,7 +495,6 @@ setroot()
|
||||
sprintf(rootdevnames[1], "%s%s", sname, partname);
|
||||
}
|
||||
|
||||
#endif /* !SLICE */
|
||||
|
||||
static int
|
||||
sysctl_kern_dumpdev SYSCTL_HANDLER_ARGS
|
||||
|
@ -2,7 +2,7 @@
|
||||
# LINT -- config file for checking all the sources, tries to pull in
|
||||
# as much of the source tree as it can.
|
||||
#
|
||||
# $Id: LINT,v 1.461 1998/09/10 11:23:08 sos Exp $
|
||||
# $Id: LINT,v 1.462 1998/09/11 18:50:16 rvb Exp $
|
||||
#
|
||||
# NB: You probably don't want to try running a kernel built from this
|
||||
# file. Instead, you should start from GENERIC, and add options from
|
||||
@ -476,10 +476,7 @@ options UNION #Union filesystem
|
||||
options "CD9660_ROOT" #CD-ROM usable as root device
|
||||
options FFS_ROOT #FFS usable as root device
|
||||
options NFS_ROOT #NFS usable as root device
|
||||
# DEVFS and SLICE are experimental but work.
|
||||
# SLICE disables too much old code so enabling it in LINT would be bad
|
||||
options DEVFS #devices filesystem
|
||||
#options SLICE #devfs based disk handling
|
||||
|
||||
# Allow the FFS to use Softupdates technology.
|
||||
# To do this you need to copy the two files
|
||||
|
@ -1,4 +1,4 @@
|
||||
# $Id: options,v 1.94 1998/08/31 18:37:19 sos Exp $
|
||||
# $Id: options,v 1.95 1998/09/11 18:50:15 rvb Exp $
|
||||
#
|
||||
# On the handling of kernel options
|
||||
#
|
||||
@ -41,7 +41,6 @@ GDB_REMOTE_CHAT opt_ddb.h
|
||||
DB_KLD_SYMBOLS opt_ddb.h
|
||||
DB_ELF_SYMBOLS opt_ddb.h
|
||||
DEVFS
|
||||
SLICE opt_devfs.h
|
||||
FAILSAFE
|
||||
HW_WDOG
|
||||
KTRACE
|
||||
|
@ -43,7 +43,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)fd.c 7.4 (Berkeley) 5/25/91
|
||||
* $Id: fd.c,v 1.119 1998/07/18 03:15:33 bde Exp $
|
||||
* $Id: fd.c,v 1.120 1998/07/29 13:00:40 bde Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
@ -84,10 +84,6 @@
|
||||
#endif
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
|
||||
/* misuse a flag to identify format operation */
|
||||
@ -184,21 +180,8 @@ static struct fd_data {
|
||||
struct callout_handle toffhandle;
|
||||
struct callout_handle tohandle;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
int unit; /* as in fd0 */
|
||||
void *bdevs[MAXPARTITIONS];
|
||||
void *cdevs[MAXPARTITIONS];
|
||||
struct subdev{
|
||||
struct slice *slice;
|
||||
int minor;
|
||||
struct fd_data *drive;
|
||||
struct slicelimits limit;
|
||||
}subdevs[16];
|
||||
struct intr_config_hook ich;
|
||||
#else /* SLICE */
|
||||
void *bdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
void *cdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
} fd_data[NFD];
|
||||
|
||||
@ -244,9 +227,7 @@ static timeout_t fd_iotimeout;
|
||||
static timeout_t fd_pseudointr;
|
||||
static int fdstate(fdcu_t, fdc_p);
|
||||
static int retrier(fdcu_t);
|
||||
#ifndef SLICE
|
||||
static int fdformat(dev_t, struct fd_formb *, struct proc *);
|
||||
#endif
|
||||
|
||||
static int enable_fifo(fdc_p fdc);
|
||||
|
||||
@ -322,30 +303,6 @@ static struct cdevsw fd_cdevsw = {
|
||||
|
||||
static struct isa_device *fdcdevs[NFDC];
|
||||
|
||||
#ifdef SLICE
|
||||
static sl_h_IO_req_t fdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t fdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t fdsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t fdsclose; */ /* downwards travelling close */
|
||||
static void fdsinit(void *);
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"floppy",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&fdsIOreq,
|
||||
&fdsioctl,
|
||||
&fdsopen,
|
||||
/*&fdsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
NULL /* dump */
|
||||
};
|
||||
#endif /* SLICE */
|
||||
|
||||
static int
|
||||
fdc_err(fdcu_t fdcu, const char *s)
|
||||
@ -582,12 +539,8 @@ fdattach(struct isa_device *dev)
|
||||
struct isa_device *fdup;
|
||||
int ic_type = 0;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
char namebuf[64];
|
||||
#else
|
||||
int mynor;
|
||||
int typemynor;
|
||||
#endif /* SLICE */
|
||||
int typesize;
|
||||
#endif
|
||||
|
||||
@ -739,9 +692,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
|
||||
fd->track = FD_NO_TRACK;
|
||||
#ifdef SLICE
|
||||
fd->unit = fdu;
|
||||
#endif
|
||||
fd->fdc = fdc;
|
||||
fd->fdsu = fdsu;
|
||||
fd->options = 0;
|
||||
@ -781,29 +731,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
}
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d",fdu);
|
||||
fd->subdevs[0].minor = 0;
|
||||
fd->subdevs[0].drive = fd;
|
||||
fd->subdevs[0].limit.blksize =
|
||||
128 << (fd_types[fd->type - 1].secsize);
|
||||
fd->subdevs[0].limit.slicesize =
|
||||
fd_types[fd->type - 1].size
|
||||
* fd->subdevs[0].limit.blksize;
|
||||
fd->ft = fd_types + (fd->type - 1); /* default value */
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[0],
|
||||
&fd->subdevs[0].limit,
|
||||
&fd->subdevs[0].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[0].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[0].slice->probeinfo.type = NULL;
|
||||
|
||||
fd->ich.ich_func = fdsinit;
|
||||
fd->ich.ich_arg = &fd->subdevs[0];
|
||||
config_intrhook_establish(&fd->ich);
|
||||
#else /* SLICE */
|
||||
mynor = fdu << 6;
|
||||
fd->bdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_BLK,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
@ -811,7 +738,6 @@ fdattach(struct isa_device *dev)
|
||||
fd->cdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_CHR,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
"rfd%d", fdu);
|
||||
#endif /* SLICE */
|
||||
for (i = 1; i < 1 + NUMDENS; i++) {
|
||||
/*
|
||||
* XXX this and the lookup in Fdopen() should be
|
||||
@ -848,25 +774,6 @@ fdattach(struct isa_device *dev)
|
||||
typesize = 1480;
|
||||
if (typesize == 1722)
|
||||
typesize = 1720;
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d.%d",fdu,typesize);
|
||||
fd->subdevs[i].minor = i;
|
||||
fd->subdevs[i].drive = fd;
|
||||
fd->subdevs[i].limit.blksize =
|
||||
128 << (fd_types[i - 1].secsize);
|
||||
fd->subdevs[i].limit.slicesize =
|
||||
fd_types[i - 1].size
|
||||
* fd->subdevs[i].limit.blksize;
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[i],
|
||||
&fd->subdevs[i].limit,
|
||||
&fd->subdevs[i].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[i].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[i].slice->probeinfo.type = NO_SUBPART;
|
||||
}
|
||||
#else /* SLICE */
|
||||
typemynor = mynor | i;
|
||||
fd->bdevs[i] =
|
||||
devfs_add_devswf(&fd_cdevsw, typemynor, DV_BLK,
|
||||
@ -885,7 +792,6 @@ fdattach(struct isa_device *dev)
|
||||
devfs_link(fd->cdevs[0],
|
||||
"rfd%d%c", fdu, 'a' + i);
|
||||
}
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
#ifdef notyet
|
||||
if (dk_ndrive < DK_NDRIVE) {
|
||||
@ -905,19 +811,6 @@ fdattach(struct isa_device *dev)
|
||||
}
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static void
|
||||
fdsinit(void *arg)
|
||||
{
|
||||
struct subdev *sd = arg;
|
||||
sh_p tp;
|
||||
|
||||
slice_start_probe(sd->slice);
|
||||
config_intrhook_disestablish(&sd->drive->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/****************************************************************************/
|
||||
/* motor control stuff */
|
||||
@ -1317,48 +1210,6 @@ fdstrategy(struct buf *bp)
|
||||
biodone(bp);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
/****************************************************************************/
|
||||
/* fdsIOreq */
|
||||
/****************************************************************************/
|
||||
static void
|
||||
fdsIOreq(void *private ,struct buf *bp)
|
||||
{
|
||||
unsigned nblocks, blknum, cando;
|
||||
int s;
|
||||
fdcu_t fdcu;
|
||||
fdu_t fdu;
|
||||
fdc_p fdc;
|
||||
fd_p fd;
|
||||
size_t fdblk;
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
fdc = fd->fdc;
|
||||
fdcu = fdc->fdcu;
|
||||
|
||||
/* check for controller already busy with tape */
|
||||
if (fdc->flags & FDC_TAPE_BUSY) {
|
||||
bp->b_error = EBUSY;
|
||||
bp->b_flags |= B_ERROR;
|
||||
goto bad;
|
||||
}
|
||||
bp->b_driver1 = sd; /* squirrel away which device.. */
|
||||
bp->b_resid = 0;
|
||||
s = splbio();
|
||||
bufqdisksort(&fdc->head, bp);
|
||||
untimeout(fd_turnoff, (caddr_t)fdu, fd->toffhandle); /* a good idea */
|
||||
fdstart(fdcu);
|
||||
splx(s);
|
||||
return;
|
||||
|
||||
bad:
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/***************************************************************\
|
||||
* fdstart *
|
||||
@ -1477,14 +1328,8 @@ fdstate(fdcu_t fdcu, fdc_p fdc)
|
||||
TRACE1("[fdc%d IDLE]", fdcu);
|
||||
return(0);
|
||||
}
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(bp->b_dev));
|
||||
fd = fd_data + fdu;
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
if (fdc->fd && (fd != fdc->fd))
|
||||
{
|
||||
@ -1898,23 +1743,11 @@ retrier(fdcu)
|
||||
struct subdev *sd;
|
||||
fdc_p fdc = fdc_data + fdcu;
|
||||
register struct buf *bp;
|
||||
#ifdef SLICE
|
||||
struct fd_data *fd;
|
||||
int fdu;
|
||||
#endif
|
||||
|
||||
bp = bufq_first(&fdc->head);
|
||||
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
if(fd->options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#else
|
||||
if(fd_data[FDUNIT(minor(bp->b_dev))].options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#endif
|
||||
switch(fdc->retry)
|
||||
{
|
||||
case 0: case 1: case 2:
|
||||
@ -1931,10 +1764,6 @@ retrier(fdcu)
|
||||
default:
|
||||
fail:
|
||||
{
|
||||
#ifdef SLICE
|
||||
printf("fd%d: hard error, block %d ", fdu,
|
||||
fd->skip / DEV_BSIZE);
|
||||
#else
|
||||
dev_t sav_b_dev = bp->b_dev;
|
||||
/* Trick diskerr */
|
||||
bp->b_dev = makedev(major(bp->b_dev),
|
||||
@ -1943,7 +1772,6 @@ retrier(fdcu)
|
||||
fdc->fd->skip / DEV_BSIZE,
|
||||
(struct disklabel *)NULL);
|
||||
bp->b_dev = sav_b_dev;
|
||||
#endif /* !SLICE */
|
||||
if (fdc->flags & FDC_STAT_VALID)
|
||||
{
|
||||
printf(
|
||||
@ -1973,16 +1801,11 @@ retrier(fdcu)
|
||||
return(1);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdformat( struct subdev *sd, struct fd_formb *finfo, struct proc *p)
|
||||
#else /* !SLICE */
|
||||
static int
|
||||
fdformat(dev, finfo, p)
|
||||
dev_t dev;
|
||||
struct fd_formb *finfo;
|
||||
struct proc *p;
|
||||
#endif /* !SLICE */
|
||||
{
|
||||
fdu_t fdu;
|
||||
fd_p fd;
|
||||
@ -1991,13 +1814,8 @@ fdformat(dev, finfo, p)
|
||||
int rv = 0, s;
|
||||
size_t fdblk;
|
||||
|
||||
#ifdef SLICE
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(dev));
|
||||
fd = &fd_data[fdu];
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
/* set up a buffer header for fdstrategy() */
|
||||
@ -2023,13 +1841,8 @@ fdformat(dev, finfo, p)
|
||||
bp->b_data = (caddr_t)finfo;
|
||||
|
||||
/* now do the format */
|
||||
#ifdef SLICE
|
||||
bp->b_driver1 = sd;
|
||||
fdsIOreq(sd, bp);
|
||||
#else /* !SLICE */
|
||||
bp->b_dev = dev;
|
||||
fdstrategy(bp);
|
||||
#endif /* !SLICE */
|
||||
|
||||
/* ...and wait for it to complete */
|
||||
s = splbio();
|
||||
@ -2085,33 +1898,10 @@ fdioctl(dev, cmd, addr, flag, p)
|
||||
return ftioctl(dev, cmd, addr, flag, p);
|
||||
#endif
|
||||
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* if SLICE is defined then only ft accesses come here
|
||||
* so break the rest off to another function for SLICE access.
|
||||
*/
|
||||
return (ENOTTY);
|
||||
}
|
||||
|
||||
/*
|
||||
* Slice ioctls come here
|
||||
*/
|
||||
static int
|
||||
fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
struct subdev *sd = private;
|
||||
fd_p fd = sd->drive;
|
||||
fdu_t fdu = fd->unit;
|
||||
fdc_p fdc = fd->fdc;
|
||||
fdcu_t fdcu = fdc->fdcu;
|
||||
size_t fdblk;
|
||||
int error = 0;
|
||||
#endif /* SLICE */
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
#ifndef SLICE
|
||||
case DIOCGDINFO:
|
||||
bzero(buffer, sizeof (buffer));
|
||||
dl = (struct disklabel *)buffer;
|
||||
@ -2155,7 +1945,6 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
error = writedisklabel(dev, fdstrategy,
|
||||
(struct disklabel *)buffer);
|
||||
break;
|
||||
#endif /* !SLICE */
|
||||
case FD_FORM:
|
||||
if((flag & FWRITE) == 0)
|
||||
error = EBADF; /* must be opened for writing */
|
||||
@ -2163,11 +1952,7 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
FD_FORMAT_VERSION)
|
||||
error = EINVAL; /* wrong version of formatting prog */
|
||||
else
|
||||
#ifdef SLICE
|
||||
error = fdformat(sd, (struct fd_formb *)addr, p);
|
||||
#else
|
||||
error = fdformat(dev, (struct fd_formb *)addr, p);
|
||||
#endif
|
||||
break;
|
||||
|
||||
case FD_GTYPE: /* get drive type */
|
||||
@ -2211,35 +1996,6 @@ static void fd_drvinit(void *notused )
|
||||
SYSINIT(fddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,fd_drvinit,NULL)
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
if((flags & (FREAD|FWRITE)) != 0) {
|
||||
return(Fdopen(makedev(0,sd->minor), flags , mode, p));
|
||||
} else {
|
||||
return(fdclose(makedev(0,sd->minor), 0 , mode, p));
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
fdsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
fdclose(makedev(0,sd->minor), 0 , 0, p);
|
||||
return ;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -1,799 +0,0 @@
|
||||
/*-
|
||||
* Copyright (C) 1997,1998 Julian Elischer. All rights reserved.
|
||||
* julian@freebsd.org
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER ``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 HOLDER 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.
|
||||
*
|
||||
* $Id: disklabel.c,v 1.7 1998/07/13 08:22:54 julian Exp $
|
||||
*/
|
||||
#define BAD144
|
||||
#undef BAD144
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/kernel.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/buf.h>
|
||||
#include <sys/fcntl.h>
|
||||
#include <sys/disklabel.h>
|
||||
#include <sys/diskslice.h>
|
||||
#include <sys/dkstat.h>
|
||||
#ifdef BAD144
|
||||
#include <sys/dkbad.h>
|
||||
#endif
|
||||
#include <sys/malloc.h>
|
||||
#include <dev/slice/slice.h>
|
||||
|
||||
#include <sys/conf.h>
|
||||
#include <sys/sliceio.h>
|
||||
#include <sys/syslog.h>
|
||||
|
||||
|
||||
struct private_data {
|
||||
u_int32_t flags;
|
||||
u_int8_t rflags;
|
||||
u_int8_t wflags;
|
||||
int savedoflags;
|
||||
struct slice *slice_down;
|
||||
struct disklabel disklabel;
|
||||
struct subdev {
|
||||
int part;
|
||||
struct slice *slice;
|
||||
struct slicelimits limit;
|
||||
struct private_data *pd;
|
||||
u_int32_t offset; /* all disklabel supports */
|
||||
} subdevs[MAXPARTITIONS];
|
||||
#ifdef BAD144
|
||||
struct dkbad_intern *bad;
|
||||
#endif
|
||||
};
|
||||
|
||||
static sl_h_IO_req_t dkl_IOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t dkl_ioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t dkl_open; /* downwards travelling open */
|
||||
/*static sl_h_close_t dkl_close; */ /* downwards travelling close */
|
||||
static sl_h_claim_t dkl_claim; /* upwards travelling claim */
|
||||
static sl_h_revoke_t dkl_revoke;/* upwards travelling revokation */
|
||||
static sl_h_verify_t dkl_verify;/* things changed, are we stil valid? */
|
||||
static sl_h_upconfig_t dkl_upconfig;/* config requests from below */
|
||||
static sl_h_dump_t dkl_dump; /* core dump req downward */
|
||||
static sl_h_done_t dkl_done; /* callback after async request */
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"disklabel",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
&dkl_done,
|
||||
&dkl_IOreq,
|
||||
&dkl_ioctl,
|
||||
&dkl_open,
|
||||
/*&dkl_close*/NULL,
|
||||
&dkl_revoke, /* revoke */
|
||||
&dkl_claim, /* claim */
|
||||
&dkl_verify, /* verify */
|
||||
&dkl_upconfig, /* subslice manipulation */
|
||||
&dkl_dump
|
||||
};
|
||||
|
||||
static void
|
||||
sd_drvinit(void *unused)
|
||||
{
|
||||
sl_newtype(&slicetype);
|
||||
}
|
||||
|
||||
SYSINIT(sddev, SI_SUB_DRIVERS, SI_ORDER_MIDDLE, sd_drvinit, NULL);
|
||||
|
||||
/*
|
||||
* Allocate and the private data.
|
||||
*/
|
||||
static int
|
||||
dklallocprivate(sl_p slice)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
|
||||
pd = malloc(sizeof(*pd), M_DEVBUF, M_NOWAIT);
|
||||
if (pd == NULL) {
|
||||
printf("dkl: failed malloc\n");
|
||||
return (ENOMEM);
|
||||
}
|
||||
bzero(pd, sizeof(*pd));
|
||||
pd->slice_down = slice;
|
||||
slice->refs++;
|
||||
slice->handler_up = &slicetype;
|
||||
slice->private_up = pd;
|
||||
slicetype.refs++;
|
||||
return (0);
|
||||
}
|
||||
|
||||
static int
|
||||
dkl_claim(sl_p slice)
|
||||
{
|
||||
int error = 0;
|
||||
/*
|
||||
* Don't even BOTHER if it's not 512 byte sectors
|
||||
*/
|
||||
if (slice->limits.blksize != 512)
|
||||
return (EINVAL);
|
||||
if (slice->private_up == NULL) {
|
||||
if ((error = dklallocprivate(slice))) {
|
||||
return (error);
|
||||
}
|
||||
}
|
||||
if ((error = slice_request_block(slice, LABELSECTOR))) {
|
||||
dkl_revoke(slice->private_up);
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
static int
|
||||
dkl_verify(sl_p slice)
|
||||
{
|
||||
int error = 0;
|
||||
/*
|
||||
* Don't even BOTHER if it's not 512 byte sectors
|
||||
*/
|
||||
if (slice->limits.blksize != 512)
|
||||
return (EINVAL);
|
||||
if ((error = slice_request_block(slice, LABELSECTOR))) {
|
||||
dkl_revoke(slice->private_up);
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* called with an argument of a bp when it is completed
|
||||
*/
|
||||
static int
|
||||
dkl_done(sl_p slice, struct buf *bp)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
struct disklabel label;
|
||||
struct disklabel *lp, *dlp, *dl;
|
||||
struct partition *dp0, *dp, *dp2;
|
||||
int part;
|
||||
int found = 0;
|
||||
int i;
|
||||
char name[64];
|
||||
int slice_offset;
|
||||
int error = 0;
|
||||
|
||||
|
||||
RR;
|
||||
/*
|
||||
* Discover whether the IO was successful.
|
||||
*/
|
||||
pd = slice->private_up;
|
||||
if ( bp->b_flags & B_ERROR ) {
|
||||
error = bp->b_error;
|
||||
goto nope;
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
* Step through the block looking for the label.
|
||||
* It may not be at the front (Though I have never seen this).
|
||||
* When found, copy it to the destination supplied.
|
||||
*/
|
||||
for (dlp = (struct disklabel *) bp->b_data;
|
||||
dlp <= (struct disklabel *) ((char *) bp->b_data
|
||||
+ slice->limits.blksize
|
||||
- sizeof(*dlp));
|
||||
dlp = (struct disklabel *) (((char *) dlp) + sizeof(long))) {
|
||||
if ((dlp->d_magic == DISKMAGIC) &&
|
||||
(dlp->d_magic2 == DISKMAGIC) &&
|
||||
(dlp->d_npartitions <= MAXPARTITIONS) &&
|
||||
(dkcksum(dlp) == 0)) {
|
||||
found = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (! found) {
|
||||
goto nope;
|
||||
}
|
||||
|
||||
/* copy the table out of the buf and release it. */
|
||||
bcopy(dlp, &label, sizeof(label));
|
||||
bp->b_flags |= B_INVAL | B_AGE;
|
||||
brelse(bp);
|
||||
|
||||
/*
|
||||
* Disklabels are done relative to the base of the disk,
|
||||
* rather than the local partition, (DUH!)
|
||||
* so use partition 2 (c) to get the base,
|
||||
* and subtract it from all non-0 offsets.
|
||||
*/
|
||||
dp = label.d_partitions;
|
||||
slice_offset = dp[2].p_offset;
|
||||
for (part = 0; part < MAXPARTITIONS; part++, dp++) {
|
||||
/*
|
||||
* We could be reloading, in which case skip
|
||||
* entries already set up.
|
||||
*/
|
||||
if (dp->p_size == 0)
|
||||
continue;
|
||||
if ( dp->p_offset < slice_offset ) {
|
||||
printf("slice before 'c'\n");
|
||||
dp->p_size = 0;
|
||||
continue;
|
||||
}
|
||||
dp->p_offset -= slice_offset;
|
||||
}
|
||||
|
||||
|
||||
/*-
|
||||
* Handle the case when we are being asked to reevaluate
|
||||
* an already loaded disklabel.
|
||||
* We've already handled the case when it's completely vanished.
|
||||
*
|
||||
* Look at a slice that USED to be ours.
|
||||
* Decide if any sub-slices need to be revoked.
|
||||
* For each existing subslice, check that the basic size
|
||||
* and position has not changed. Also check the TYPE.
|
||||
* If not then at least ask them to verify themselves.
|
||||
* It is possible we should allow a slice to grow.
|
||||
*/
|
||||
dl = &(pd->disklabel);
|
||||
dp = dl->d_partitions;
|
||||
dp2 = label.d_partitions;
|
||||
for (part = 0; part < MAXPARTITIONS; part++, dp++, dp2++) {
|
||||
if (pd->subdevs[part].slice) {
|
||||
if ((dp2->p_offset != dp->p_offset)
|
||||
|| (dp2->p_size != dp->p_size)) {
|
||||
sl_rmslice(pd->subdevs[part].slice);
|
||||
pd->subdevs[part].slice = NULL;
|
||||
} else if (pd->subdevs[part].slice->handler_up) {
|
||||
(*pd->subdevs[part].slice->handler_up->verify)
|
||||
(pd->subdevs[part].slice);
|
||||
}
|
||||
}
|
||||
}
|
||||
/*- having got rid of changing slices, replace
|
||||
* the old table with the new one, and
|
||||
* handle any new slices by calling the constructor.
|
||||
*/
|
||||
bcopy(&label, dl, sizeof(label));
|
||||
|
||||
#ifdef BAD144
|
||||
#if 0
|
||||
/* place holder:
|
||||
remember to add some state machine to handle bad144 loading */
|
||||
|
||||
if (pd->disklabel.d_flags & D_BADSECT) {
|
||||
if ((error = dkl_readbad144(pd))) {
|
||||
free(pd, M_DEVBUF);
|
||||
return (error);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
dp0 = dl->d_partitions;
|
||||
|
||||
/*-
|
||||
* Handle each of the partitions.
|
||||
* We should check that each makes sence and is legal.
|
||||
* 1/ it should not already have a slice.
|
||||
* 2/ should not be 0 length.
|
||||
* 3/ should not go past end of our slice.
|
||||
* 4/ should not overlap other slices.
|
||||
* It can include sector 0 (unfortunatly)
|
||||
*/
|
||||
dp = dp0;
|
||||
for (part = 0; part < MAXPARTITIONS; part++, dp++) {
|
||||
int i;
|
||||
if ( part == 2 )
|
||||
continue; /* XXX skip the 'c' partition */
|
||||
/*
|
||||
* We could be reloading, in which case skip
|
||||
* entries already set up.
|
||||
*/
|
||||
if (pd->subdevs[part].slice != NULL)
|
||||
breakout: continue;
|
||||
/*
|
||||
* also skip partitions not present
|
||||
*/
|
||||
if (dp->p_size == 0)
|
||||
continue;
|
||||
printf(" part %c, start=%d, size=%d\n", part + 'a', dp->p_offset, dp->p_size);
|
||||
|
||||
if ((dp->p_offset + dp->p_size) >
|
||||
(slice->limits.slicesize / slice->limits.blksize)) {
|
||||
printf("dkl: slice %d too big ", part);
|
||||
printf("(%x > %x:%x )\n",
|
||||
(dp->p_offset + dp->p_size),
|
||||
(slice->limits.slicesize / slice->limits.blksize) );
|
||||
continue;
|
||||
}
|
||||
/* check for overlaps with existing slices */
|
||||
for (i = 0; i < MAXPARTITIONS; i++) {
|
||||
/* skip empty slots (including this one) */
|
||||
if (pd->subdevs[i].slice == NULL)
|
||||
continue;
|
||||
if ((dp0[i].p_offset < (dp->p_offset + dp->p_size))
|
||||
&& ((dp0[i].p_offset + dp0[i].p_size) > dp->p_offset))
|
||||
{
|
||||
printf("dkl: slice %d overlaps slice %d\n",
|
||||
part, i);
|
||||
goto breakout;
|
||||
}
|
||||
}
|
||||
/*-
|
||||
* the slice seems to make sense. Use it.
|
||||
*/
|
||||
pd->subdevs[part].part = part;
|
||||
pd->subdevs[part].pd = pd;
|
||||
pd->subdevs[part].offset = dp->p_offset;
|
||||
pd->subdevs[part].limit.blksize
|
||||
= slice->limits.blksize;
|
||||
pd->subdevs[part].limit.slicesize
|
||||
= (slice->limits.blksize * (u_int64_t)dp->p_size);
|
||||
|
||||
sprintf(name, "%s%c", slice->name, (char )('a' + part));
|
||||
sl_make_slice(&slicetype,
|
||||
&pd->subdevs[part],
|
||||
&pd->subdevs[part].limit,
|
||||
&pd->subdevs[part].slice,
|
||||
name);
|
||||
pd->subdevs[part].slice->probeinfo.typespecific = &dp->p_fstype;
|
||||
switch (dp->p_fstype) {
|
||||
case FS_UNUSED:
|
||||
/* allow unuseed to be further split */
|
||||
pd->subdevs[part].slice->probeinfo.type = NULL;
|
||||
break;
|
||||
case FS_V6:
|
||||
case FS_V7:
|
||||
case FS_SYSV:
|
||||
case FS_V71K:
|
||||
case FS_V8:
|
||||
case FS_MSDOS:
|
||||
case FS_BSDLFS:
|
||||
case FS_OTHER:
|
||||
case FS_HPFS:
|
||||
case FS_ISO9660:
|
||||
case FS_BOOT :
|
||||
#if 0
|
||||
printf("%s: type %d. Leaving\n",
|
||||
pd->subdevs[part].slice->name,
|
||||
(u_int)dp->p_fstype);
|
||||
#endif
|
||||
case FS_SWAP:
|
||||
case FS_BSDFFS:
|
||||
pd->subdevs[part].slice->probeinfo.type = NO_SUBPART;
|
||||
break;
|
||||
default:
|
||||
pd->subdevs[part].slice->probeinfo.type = NULL;
|
||||
}
|
||||
/*
|
||||
* Dont allow further breakup of slices that
|
||||
* cover our disklabel (that would recurse forever)
|
||||
*/
|
||||
if (dp->p_offset < 16) {
|
||||
#if 0
|
||||
printf("%s: covers disklabel. Leaving\n",
|
||||
pd->subdevs[part].slice->name);
|
||||
#endif
|
||||
pd->subdevs[part].slice->probeinfo.type = NO_SUBPART;
|
||||
}
|
||||
slice_start_probe(pd->subdevs[part].slice);
|
||||
}
|
||||
return (0);
|
||||
nope:
|
||||
printf(" .. nope\n");
|
||||
dkl_revoke(pd);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#if 0
|
||||
/*-
|
||||
* This is a special HACK function for the IDE driver.
|
||||
* It is here because everything it need is in scope here,
|
||||
* but it is not really part of the SLICE code.
|
||||
* Because old ESDI drives could not tell their geometry, They need
|
||||
* to get it from the MBR or the disklabel. This is the disklabel bit.
|
||||
*/
|
||||
int
|
||||
dkl_geom_hack(struct slice * slice, struct ide_geom *geom)
|
||||
{
|
||||
struct disklabel disklabel;
|
||||
struct disklabel *dl, *dl0;
|
||||
int error;
|
||||
RR;
|
||||
|
||||
/* first check it's a disklabel*/
|
||||
if ((error = dkl_claim (slice)))
|
||||
return (error);
|
||||
/*-
|
||||
* Try load a valid disklabel table.
|
||||
* This is wasteful but never called on new (< 5 YO ) drives.
|
||||
*/
|
||||
if ((error = dkl_extract_table(slice, &disklabel)) != 0) {
|
||||
return (error);
|
||||
}
|
||||
geom->secpertrack = disklabel. d_nsectors;
|
||||
geom->trackpercyl = disklabel.d_ntracks;
|
||||
geom->cyls = disklabel.d_ncylinders;
|
||||
return (0);
|
||||
}
|
||||
#endif
|
||||
|
||||
/*-
|
||||
* Invalidate all subslices, and free resources for this handler instance.
|
||||
*/
|
||||
static int
|
||||
dkl_revoke(void *private)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
register struct slice *slice;
|
||||
int part;
|
||||
|
||||
RR;
|
||||
pd = private;
|
||||
slice = pd->slice_down;
|
||||
for (part = 0; part < MAXPARTITIONS; part++) {
|
||||
if (pd->subdevs[part].slice) {
|
||||
sl_rmslice(pd->subdevs[part].slice);
|
||||
}
|
||||
}
|
||||
/*-
|
||||
* remove ourself as a handler
|
||||
*/
|
||||
slice->handler_up = NULL;
|
||||
slice->private_up = NULL;
|
||||
slicetype.refs--;
|
||||
#ifdef BAD144
|
||||
if (pd->bad)
|
||||
free(pd->bad, M_DEVBUF);
|
||||
#endif
|
||||
free(pd, M_DEVBUF);
|
||||
sl_unref(slice);
|
||||
return (0);
|
||||
}
|
||||
|
||||
#ifdef BAD144
|
||||
#if 0
|
||||
bucket= blknum >> 4; /* set 16 blocks to the same bucket */
|
||||
bucket ^= (bucket>>16); /* combine bytes 1+3, 2+4 */
|
||||
bucket ^= (bucket>>8); /* combine bytes 1+3+2+4 */
|
||||
bucket &= 0x7F; /* AND 128 entries */
|
||||
#endif
|
||||
/*
|
||||
* Given a bad144 table, load the values into ram.
|
||||
* eventually we should hash them so we can do forwards lookups.
|
||||
* Probably should hash on (blknum >> 4) to minimise
|
||||
* lookups for a clustered IO. (see above)
|
||||
*/
|
||||
static int
|
||||
dkl_internbad144(struct private_data *pd, struct dkbad *btp, int flag)
|
||||
{
|
||||
struct disklabel *lp = &pd->disklabel;
|
||||
struct dkbad_intern *bip = pd->bad;
|
||||
int i;
|
||||
|
||||
if (bip == NULL) {
|
||||
bip = malloc(sizeof *bip, M_DEVBUF, flag);
|
||||
if (bip == NULL)
|
||||
return (ENOMEM);
|
||||
pd->bad = bip;
|
||||
}
|
||||
/*
|
||||
* Spare sectors are allocated beginning with the last sector of
|
||||
* the second last track of the disk (the last track is used for
|
||||
* the bad sector list).
|
||||
*/
|
||||
bip->bi_maxspare = lp->d_secperunit - lp->d_nsectors - 1;
|
||||
bip->bi_nbad = DKBAD_MAXBAD;
|
||||
for (i=0; i < DKBAD_MAXBAD && btp->bt_bad[i].bt_cyl != DKBAD_NOCYL; i++)
|
||||
bip->bi_bad[i] = btp->bt_bad[i].bt_cyl * lp->d_secpercyl
|
||||
+ (btp->bt_bad[i].bt_trksec >> 8)
|
||||
* lp->d_nsectors
|
||||
+ (btp->bt_bad[i].bt_trksec & 0x00ff);
|
||||
bip->bi_bad[i] = -1;
|
||||
#if 1
|
||||
for (i = 0; i < DKBAD_MAXBAD && bip->bi_bad[i] != -1; i++)
|
||||
printf(" %8d => %8d\n", bip->bi_bad[i],
|
||||
bip->bi_maxspare - i);
|
||||
#endif
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Hunt in the last cylinder for the bad144 table
|
||||
* this needs to be turned around to be made into a state operation
|
||||
* driven by IO completion of the read.
|
||||
*/
|
||||
static int
|
||||
dkl_readbad144(struct private_data *pd)
|
||||
{
|
||||
sl_p slice = pd->slice_down;
|
||||
struct disklabel *lp = &pd->disklabel;
|
||||
struct dkbad *db;
|
||||
struct buf *bp;
|
||||
int blkno, i, error;
|
||||
|
||||
for (i = 0; i < min(10, lp->d_nsectors); i += 2) {
|
||||
blkno = lp->d_secperunit - lp->d_nsectors + i;
|
||||
if (lp->d_secsize > slice->limits.blksize)
|
||||
blkno *= lp->d_secsize / slice->limits.blksize;
|
||||
else
|
||||
blkno /= slice->limits.blksize / lp->d_secsize;
|
||||
error = slice_readblock(slice, blkno, &bp);
|
||||
if (error)
|
||||
return (error);
|
||||
bp->b_flags |= B_INVAL | B_AGE;
|
||||
db = (struct dkbad *)bp->b_data;
|
||||
if (db->bt_mbz == 0 && db->bt_flag == DKBAD_MAGIC) {
|
||||
printf(" bad144 table found at block %d\n", blkno);
|
||||
error = dkl_internbad144(pd, db, M_NOWAIT);
|
||||
brelse(bp);
|
||||
return (error);
|
||||
}
|
||||
brelse(bp);
|
||||
}
|
||||
return (EINVAL);
|
||||
}
|
||||
|
||||
static __inline daddr_t
|
||||
dkl_transbad144(struct private_data *pd, daddr_t blkno)
|
||||
{
|
||||
return transbad144(pd->bad, blkno);
|
||||
}
|
||||
#endif
|
||||
|
||||
/*-
|
||||
* shift the appropriate IO by the offset for that slice.
|
||||
*/
|
||||
static void
|
||||
dkl_IOreq(void *private, struct buf * bp)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
bp->b_pblkno += sdp->offset; /* add the offset for that slice */
|
||||
sliceio(slice, bp, SLW_ABOVE);
|
||||
}
|
||||
|
||||
static int
|
||||
dkl_open(void *private, int flags, int mode, struct proc * p)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
int error;
|
||||
u_int8_t newrflags = 0;
|
||||
u_int8_t newwflags = 0;
|
||||
int newoflags;
|
||||
int part;
|
||||
u_int8_t partbit;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
part = sdp->part;
|
||||
partbit = (1 << part);
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
|
||||
/*
|
||||
* Calculate the change to to over-all picture here.
|
||||
* Notice that this might result in LESS open bits
|
||||
* if that was what was passed from above.
|
||||
* (Prelude to 'mode-change' instead of open/close.)
|
||||
*/
|
||||
/* work out what our stored flags will be if this succeeds */
|
||||
newwflags &= ~ (partbit);
|
||||
newrflags &= ~ (partbit);
|
||||
newwflags |= (flags & FWRITE) ? (partbit) : 0;
|
||||
newrflags |= (flags & FREAD) ? (partbit) : 0;
|
||||
|
||||
/* work out what we want to pass down this time */
|
||||
newoflags = newwflags ? FWRITE : 0;
|
||||
newoflags |= newrflags ? FREAD : 0;
|
||||
|
||||
/*
|
||||
* If the agregate flags we used last time are the same as
|
||||
* the agregate flags we would use this time, then don't
|
||||
* bother re-doing the command.
|
||||
*/
|
||||
if (newoflags != pd->savedoflags) {
|
||||
if (error = sliceopen(slice, newoflags, mode, p, SLW_ABOVE)) {
|
||||
return (error);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Now that we know it succeeded, commit, by replacing the old
|
||||
* flags with the new ones.
|
||||
*/
|
||||
pd->rflags = newrflags;
|
||||
pd->wflags = newwflags;
|
||||
pd->savedoflags = newoflags;
|
||||
return (0);
|
||||
}
|
||||
|
||||
static int
|
||||
dkl_ioctl(void *private, u_long cmd, caddr_t addr, int flag, struct proc * p)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
struct disklabel *lp;
|
||||
int error;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
lp = &pd->disklabel;
|
||||
switch (cmd) {
|
||||
case DIOCGDINFO:
|
||||
*(struct disklabel *)addr = *lp;
|
||||
return (0);
|
||||
|
||||
case DIOCGPART:
|
||||
if (lp == NULL)
|
||||
return (EINVAL);
|
||||
((struct partinfo *)addr)->disklab = lp;
|
||||
((struct partinfo *)addr)->part = lp->d_partitions + sdp->part;
|
||||
return (0);
|
||||
|
||||
#ifdef BAD144
|
||||
case DIOCSBAD:
|
||||
if (!(flag & FWRITE))
|
||||
return (EBADF);
|
||||
return (dkl_internbad144(pd, (struct dkbad *)addr, M_WAITOK));
|
||||
#endif
|
||||
|
||||
/* These don't really make sense. keep the headers for a reminder */
|
||||
case DIOCSDINFO:
|
||||
case DIOCSYNCSLICEINFO:
|
||||
case DIOCWDINFO:
|
||||
case DIOCWLABEL:
|
||||
return (ENOIOCTL);
|
||||
}
|
||||
|
||||
return ((*slice->handler_down->ioctl) (slice->private_down,
|
||||
cmd, addr, flag, p));
|
||||
}
|
||||
|
||||
static int
|
||||
dkl_upconfig(struct slice *slice, int cmd, caddr_t addr, int flag, struct proc * p)
|
||||
{
|
||||
RR;
|
||||
switch (cmd) {
|
||||
case SLCIOCRESET:
|
||||
return (0);
|
||||
|
||||
#ifdef BAD144
|
||||
case SLCIOCTRANSBAD:
|
||||
{
|
||||
struct private_data *pd;
|
||||
daddr_t blkno;
|
||||
|
||||
pd = slice->private_up;
|
||||
if (pd->bad)
|
||||
*(daddr_t*)addr = dkl_transbad144(pd, *(daddr_t*)addr);
|
||||
return (0);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* These don't really make sense. keep the headers for a reminder */
|
||||
default:
|
||||
return (ENOIOCTL);
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
|
||||
static struct disklabel static_label;
|
||||
/*
|
||||
* This is a hack routine called from the slice generic code to produce a dummy
|
||||
* disklabel when given a slice descriptor. It's in here because this code
|
||||
* knows about disklabels.
|
||||
*/
|
||||
int
|
||||
dkl_dummy_ioctl(struct slice *slice, u_long cmd, caddr_t addr,
|
||||
int flag, struct proc * p)
|
||||
{
|
||||
struct disklabel *lp = &static_label;
|
||||
|
||||
switch (cmd) {
|
||||
case DIOCGDINFO:
|
||||
case DIOCGPART:
|
||||
bzero(lp, sizeof(static_label));
|
||||
lp->d_magic = DISKMAGIC;
|
||||
lp->d_magic2 = DISKMAGIC;
|
||||
lp->d_secsize = slice->limits.blksize;
|
||||
lp->d_nsectors = 1;
|
||||
lp->d_ntracks = 1;
|
||||
lp->d_secpercyl = 1;
|
||||
lp->d_ncylinders =
|
||||
lp->d_secperunit = slice->limits.slicesize
|
||||
/ slice->limits.blksize;
|
||||
lp->d_npartitions = RAW_PART + 1;
|
||||
lp->d_partitions[RAW_PART].p_size = lp->d_secperunit;
|
||||
lp->d_partitions[RAW_PART].p_offset = 0;
|
||||
break;
|
||||
default:
|
||||
return (ENOIOCTL);
|
||||
}
|
||||
lp->d_checksum = dkcksum(lp);
|
||||
|
||||
switch (cmd) {
|
||||
case DIOCGDINFO:
|
||||
*(struct disklabel *)addr = *lp;
|
||||
break;
|
||||
case DIOCGPART:
|
||||
/* XXX hack alert.
|
||||
* This is a hack as this information is consumed immediatly
|
||||
* otherwise the use of a static buffer would be dangerous.
|
||||
*/
|
||||
((struct partinfo *)addr)->disklab = lp;
|
||||
((struct partinfo *)addr)->part = lp->d_partitions + RAW_PART;
|
||||
}
|
||||
|
||||
return (0);
|
||||
|
||||
}
|
||||
|
||||
#if 0 /* use the existing one for now */
|
||||
/*-
|
||||
* Compute checksum for disk label.
|
||||
*/
|
||||
u_int
|
||||
dkcksum(lp)
|
||||
register struct disklabel *lp;
|
||||
{
|
||||
register u_short *start, *end;
|
||||
register u_short sum = 0;
|
||||
|
||||
start = (u_short *) lp;
|
||||
end = (u_short *) & lp->d_partitions[lp->d_npartitions];
|
||||
while (start < end)
|
||||
sum ^= *start++;
|
||||
return (sum);
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
/*
|
||||
* pass down a dump request.
|
||||
* make sure it's offset by the right amount.
|
||||
*/
|
||||
static int
|
||||
dkl_dump(void *private, int32_t blkoff, int32_t blkcnt)
|
||||
{
|
||||
struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
blkoff += sdp->offset;
|
||||
if (slice->handler_down->dump) {
|
||||
return (*slice->handler_down->dump)(slice->private_down,
|
||||
blkoff, blkcnt);
|
||||
}
|
||||
return(ENXIO);
|
||||
}
|
@ -1,725 +0,0 @@
|
||||
/*-
|
||||
* Copyright (C) 1997,1998 Julian Elischer. All rights reserved.
|
||||
* julian@freebsd.org
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER ``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 HOLDER 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.
|
||||
*
|
||||
* $Id: mbr.c,v 1.8 1998/07/20 04:12:39 julian Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/kernel.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/buf.h>
|
||||
#include <sys/fcntl.h>
|
||||
#include <sys/disklabel.h>
|
||||
#include <sys/dkstat.h>
|
||||
#include <sys/malloc.h>
|
||||
#include <sys/sliceio.h>
|
||||
#include <dev/slice/slice.h>
|
||||
|
||||
|
||||
struct private_data {
|
||||
u_int32_t flags;
|
||||
struct slice *slice_down;
|
||||
int savedoflags;
|
||||
/* struct buf *bp; */
|
||||
u_int32_t table_offset;
|
||||
struct dos_partition dos_table[NDOSPART];
|
||||
struct subdev {
|
||||
int part;
|
||||
struct slice *slice;
|
||||
struct slicelimits limit;
|
||||
struct private_data *pd;
|
||||
u_int32_t offset; /* Fdisk only has 32 bits */
|
||||
} subdevs[NDOSPART];
|
||||
};
|
||||
/*
|
||||
* Bits in the mbr private data flag word
|
||||
*/
|
||||
#define MBRF_OPEN_RBIT 0x01
|
||||
#define MBRF_S1_OPEN_RD 0x01
|
||||
#define MBRF_S2_OPEN_RD 0x02
|
||||
#define MBRF_S3_OPEN_RD 0x04
|
||||
#define MBRF_S4_OPEN_RD 0x08
|
||||
#define MBRF_MSK_RD 0x0F
|
||||
#define MBRF_OPEN_WBIT 0x10
|
||||
#define MBRF_S1_OPEN_WR 0x10
|
||||
#define MBRF_S2_OPEN_WR 0x20
|
||||
#define MBRF_S3_OPEN_WR 0x40
|
||||
#define MBRF_S4_OPEN_WR 0x80
|
||||
#define MBRF_MSK_WR 0xF0
|
||||
#define MBRF_MSK_OPEN 0xFF
|
||||
|
||||
#define DOSPTYP_ONTRACK 84
|
||||
|
||||
static sl_h_IO_req_t mbr_IOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t mbr_ioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t mbr_open; /* downwards travelling open */
|
||||
/*static sl_h_close_t mbr_close; */ /* downwards travelling close */
|
||||
static sl_h_claim_t mbr_claim; /* upwards travelling claim */
|
||||
static sl_h_revoke_t mbr_revoke;/* upwards travelling revokation */
|
||||
static sl_h_verify_t mbr_verify;/* things changed, are we stil valid? */
|
||||
static sl_h_upconfig_t mbr_upconfig;/* config request from below */
|
||||
static sl_h_dump_t mbr_dump; /* core dump req downward */
|
||||
static sl_h_done_t mbr_done; /* callback after async request */
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"MBR",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
&mbr_done,
|
||||
&mbr_IOreq,
|
||||
&mbr_ioctl,
|
||||
&mbr_open,
|
||||
/*&mbr_close*/NULL,
|
||||
&mbr_revoke, /* revoke */
|
||||
&mbr_claim, /* claim */
|
||||
&mbr_verify, /* verify */
|
||||
&mbr_upconfig, /* config from below */
|
||||
&mbr_dump
|
||||
};
|
||||
|
||||
static void
|
||||
sd_drvinit(void *unused)
|
||||
{
|
||||
sl_newtype(&slicetype);
|
||||
}
|
||||
|
||||
SYSINIT(sddev, SI_SUB_DRIVERS, SI_ORDER_MIDDLE, sd_drvinit, NULL);
|
||||
|
||||
/*
|
||||
* Allocate and the private data.
|
||||
*/
|
||||
static int
|
||||
mbrallocprivate(sl_p slice)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
|
||||
pd = malloc(sizeof(*pd), M_DEVBUF, M_NOWAIT);
|
||||
if (pd == NULL) {
|
||||
printf("mbr: failed malloc\n");
|
||||
return (ENOMEM);
|
||||
}
|
||||
bzero(pd, sizeof(*pd));
|
||||
pd->slice_down = slice;
|
||||
slice->refs++;
|
||||
slice->handler_up = &slicetype;
|
||||
slice->private_up = pd;
|
||||
slicetype.refs++;
|
||||
return (0);
|
||||
}
|
||||
|
||||
static int
|
||||
mbr_claim(sl_p slice)
|
||||
{
|
||||
int error = 0;
|
||||
/*
|
||||
* Don't even BOTHER if it's not 512 byte sectors
|
||||
*/
|
||||
if (slice->limits.blksize != 512)
|
||||
return (EINVAL);
|
||||
if (slice->private_up == NULL) {
|
||||
if ((error = mbrallocprivate(slice))) {
|
||||
return (error);
|
||||
}
|
||||
}
|
||||
if ((error = slice_request_block(slice, 0))) {
|
||||
mbr_revoke(slice->private_up);
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
static int
|
||||
mbr_verify(sl_p slice)
|
||||
{
|
||||
int error = 0;
|
||||
/*
|
||||
* Don't even BOTHER if it's not 512 byte sectors
|
||||
*/
|
||||
if (slice->limits.blksize != 512)
|
||||
return (EINVAL);
|
||||
if ((error = slice_request_block(slice, 0))) {
|
||||
mbr_revoke(slice->private_up);
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* called with an argument of a bp when it is completed
|
||||
*/
|
||||
static int
|
||||
mbr_done(sl_p slice, struct buf *bp)
|
||||
{
|
||||
struct private_data *pd;
|
||||
struct dos_partition table[NDOSPART];
|
||||
struct dos_partition *dp0, *dp, *dp2;
|
||||
u_int8_t *cp;
|
||||
int part;
|
||||
int numactive = 0;
|
||||
int i;
|
||||
char name[64];
|
||||
int error = 0;
|
||||
|
||||
RR;
|
||||
/*
|
||||
* Discover whether the IO was successful.
|
||||
*/
|
||||
pd = slice->private_up;
|
||||
if ( bp->b_flags & B_ERROR ) {
|
||||
error = bp->b_error;
|
||||
bp->b_flags |= B_INVAL | B_AGE;
|
||||
brelse(bp);
|
||||
if (bootverbose)
|
||||
printf ("failed.. IO error ");
|
||||
goto nope;
|
||||
}
|
||||
cp = bp->b_data;
|
||||
if (cp[0x1FE] != 0x55 || cp[0x1FF] != 0xAA) {
|
||||
bp->b_flags |= B_INVAL | B_AGE;
|
||||
brelse(bp);
|
||||
if (bootverbose)
|
||||
printf ("rejected.. bad magic ");
|
||||
goto nope;
|
||||
}
|
||||
dp0 = (struct dos_partition *) (cp + DOSPARTOFF);
|
||||
|
||||
/* copy the table out of the buf and release it. */
|
||||
bcopy(dp0, table, sizeof(table));
|
||||
bp->b_flags |= B_INVAL | B_AGE;
|
||||
brelse(bp);
|
||||
|
||||
/*
|
||||
* Check for "Ontrack Diskmanager". Note that if the geometry is
|
||||
* still needed then we probably won't be able to read a DiskManager
|
||||
* MBR because we will fail to read sector 63. The very act of
|
||||
* finding a Disk Manager might however have given us the info we
|
||||
* need if the disk manager set's its partition up correctly.
|
||||
* XXX not true with interrupt driven probes.
|
||||
*/
|
||||
if (pd->table_offset == 0) {
|
||||
for (part = 0, dp = table;
|
||||
part < NDOSPART; part++, dp++) {
|
||||
if (dp->dp_typ == DOSPTYP_ONTRACK) {
|
||||
#ifdef MAYBE
|
||||
/*
|
||||
* It's not known if this should always 63 or
|
||||
* if this is just the start of the 2nd
|
||||
* track.
|
||||
*/
|
||||
pd->table_offset = dp->dp_start;
|
||||
#else
|
||||
pd->table_offset = 63;
|
||||
#endif
|
||||
if (bootverbose)
|
||||
printf("Found \"Ontrack Disk Manager\"\n");
|
||||
slice_request_block(slice, pd->table_offset);
|
||||
return (0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* The first block of the dos code is marked like a valid MBR.
|
||||
* Try to distinguish this case by doing a sanity check on the table.
|
||||
* Check:
|
||||
* Flag byte can only be 0 or 0x80.
|
||||
* At most one active partition.
|
||||
* -Other tests to be added here-
|
||||
*/
|
||||
for (part = 0, dp = table; part < NDOSPART; part++, dp++) {
|
||||
if (dp->dp_flag & 0x7f) {
|
||||
if (bootverbose)
|
||||
printf ("rejected.. bad flag ");
|
||||
goto nope;
|
||||
}
|
||||
if ((dp->dp_typ) && (dp->dp_size) && (dp->dp_start == 0)) {
|
||||
if (bootverbose)
|
||||
printf("rejected.. Slice includes MBR ");
|
||||
goto nope;
|
||||
}
|
||||
if (dp->dp_flag == 0x80)
|
||||
numactive++;
|
||||
}
|
||||
if (numactive > 1) {
|
||||
if (bootverbose)
|
||||
printf ("rejected.. multiple active ");
|
||||
goto nope;
|
||||
}
|
||||
/*-
|
||||
* Handle the case when we are being asked to reevaluate
|
||||
* an already loaded mbr table.
|
||||
* We've already handled the case when it's completely vanished.
|
||||
*
|
||||
* Look at a slice that USED to be ours.
|
||||
* Decide if any sub-slices need to be revoked.
|
||||
* For each existing subslice, check that the basic size
|
||||
* and position has not changed. Also check the TYPE.
|
||||
* If not then at least ask them to verify themselves.
|
||||
* It is possible we should allow a slice to grow.
|
||||
*/
|
||||
dp = pd->dos_table;
|
||||
dp0 = pd->dos_table;
|
||||
dp2 = table;
|
||||
for (part = 0; part < NDOSPART; part++, dp++, dp2++) {
|
||||
if (pd->subdevs[part].slice) {
|
||||
if ((dp2->dp_start != dp->dp_start)
|
||||
|| (dp2->dp_size != dp->dp_size)
|
||||
|| (dp2->dp_typ != dp->dp_typ) ) {
|
||||
sl_rmslice(pd->subdevs[part].slice);
|
||||
pd->subdevs[part].slice = NULL;
|
||||
} else if (pd->subdevs[part].slice->handler_up) {
|
||||
(*pd->subdevs[part].slice->handler_up->verify)
|
||||
(pd->subdevs[part].slice);
|
||||
}
|
||||
}
|
||||
}
|
||||
/*
|
||||
* Having got rid of changing slices, replace
|
||||
* the old table with the new one.
|
||||
*/
|
||||
bcopy( table, pd->dos_table, sizeof(table));
|
||||
|
||||
/*
|
||||
* Handle each of the partitions.
|
||||
* We should check that each makes sense and is legal.
|
||||
* 1/ it should not already have a slice.
|
||||
* 2/ should not be 0 length.
|
||||
* 3/ should not go past end of our slice.
|
||||
* 4/ should not include sector 0.
|
||||
* 5/ should not overlap other slices.
|
||||
*
|
||||
* Be aware that this may queue up one (or more) IO requests
|
||||
* for each subslice created.
|
||||
*/
|
||||
if (bootverbose)
|
||||
printf("yep \n");
|
||||
dp = dp0;
|
||||
for (part = 0; part < NDOSPART; part++, dp++) {
|
||||
int i;
|
||||
if (pd->subdevs[part].slice != NULL)
|
||||
breakout: continue;
|
||||
if (dp->dp_size == 0)
|
||||
continue;
|
||||
if (dp->dp_start < 1)
|
||||
continue;
|
||||
printf(" part %d, start=%d, size=%d\n", part + 1, dp->dp_start, dp->dp_size);
|
||||
|
||||
if ((dp->dp_start + dp->dp_size) >
|
||||
(slice->limits.slicesize/slice->limits.blksize)) {
|
||||
printf("mbr: slice %d too big ", part);
|
||||
printf("(%x > %x:%x )\n",
|
||||
(dp->dp_start + dp->dp_size),
|
||||
(slice->limits.slicesize / slice->limits.blksize) );
|
||||
continue;
|
||||
}
|
||||
/* check for overlaps with existing slices */
|
||||
for (i = 0; i < NDOSPART; i++) {
|
||||
/* skip empty slots (including this one) */
|
||||
if (pd->subdevs[i].slice == NULL )
|
||||
continue;
|
||||
if ((dp0[i].dp_start < (dp->dp_start + dp->dp_size))
|
||||
&& ((dp0[i].dp_start + dp0[i].dp_size) > dp->dp_start))
|
||||
{
|
||||
printf("mbr: new slice %d overlaps slice %d\n",
|
||||
part, i);
|
||||
goto breakout;
|
||||
}
|
||||
}
|
||||
/*
|
||||
* the slice seems to make sense. Use it.
|
||||
*/
|
||||
pd->subdevs[part].part = part;
|
||||
pd->subdevs[part].pd = pd;
|
||||
pd->subdevs[part].offset = dp->dp_start;
|
||||
pd->subdevs[part].limit.blksize
|
||||
= slice->limits.blksize;
|
||||
pd->subdevs[part].limit.slicesize
|
||||
= (slice->limits.blksize * (u_int64_t)dp->dp_size);
|
||||
|
||||
sprintf(name, "%ss%d", slice->name, part + 1);
|
||||
sl_make_slice(&slicetype,
|
||||
&pd->subdevs[part],
|
||||
&pd->subdevs[part].limit,
|
||||
&pd->subdevs[part].slice,
|
||||
name);
|
||||
pd->subdevs[part].slice->probeinfo.typespecific = &dp->dp_typ;
|
||||
switch (dp->dp_typ) { /* list stolen from fdisk */
|
||||
case 0x00: /* "unused" */
|
||||
case 0x01: /* "Primary DOS with 12 bit FAT" */
|
||||
case 0x02: /* "XENIX / filesystem" */
|
||||
case 0x03: /* "XENIX /usr filesystem" */
|
||||
case 0x04: /* "Primary DOS with 16 bit FAT" */
|
||||
case 0x05: /* "Extended DOS" */
|
||||
case 0x06: /* "Primary 'big' DOS (> 32MB)" */
|
||||
case 0x07: /* "OS/2 HPFS, QNX or Advanced UNIX" */
|
||||
case 0x08: /* "AIX filesystem" */
|
||||
case 0x09: /* "AIX boot partition or Coherent" */
|
||||
case 0x0A: /* "OS/2 Boot Manager or OPUS" */
|
||||
case 0x10: /* "OPUS" */
|
||||
case 0x40: /* "VENIX 286" */
|
||||
case 0x50: /* "DM" */
|
||||
case 0x51: /* "DM" */
|
||||
case 0x52: /* "CP/M or Microport SysV/AT" */
|
||||
case 0x56: /* "GB" */
|
||||
case 0x61: /* "Speed" */
|
||||
case 0x63: /* "ISC UNIX, System V/386, GNU HURD or Mach" */
|
||||
case 0x64: /* "Novell Netware 2.xx" */
|
||||
case 0x65: /* "Novell Netware 3.xx" */
|
||||
case 0x75: /* "PCIX" */
|
||||
case 0x80: /* "Minix 1.1 ... 1.4a" */
|
||||
case 0x81: /* "Minix 1.4b ... 1.5.10" */
|
||||
case 0x82: /* "Linux swap" */
|
||||
case 0x83: /* "Linux filesystem" */
|
||||
case 0x93: /* "Amoeba filesystem" */
|
||||
case 0x94: /* "Amoeba bad block table" */
|
||||
case 0xA6: /* "OpenBSD" */
|
||||
case 0xA7: /* "NEXTSTEP" */
|
||||
case 0xB7: /* "BSDI BSD/386 filesystem" */
|
||||
case 0xB8: /* "BSDI BSD/386 swap" */
|
||||
case 0xDB: /* "Concurrent CPM or C.DOS or CTOS" */
|
||||
case 0xE1: /* "Speed" */
|
||||
case 0xE3: /* "Speed" */
|
||||
case 0xE4: /* "Speed" */
|
||||
case 0xF1: /* "Speed" */
|
||||
case 0xF2: /* "DOS 3.3+ Secondary" */
|
||||
case 0xF4: /* "Speed" */
|
||||
case 0xFF: /* "BBT (Bad Blocks Table)" */
|
||||
printf("%s: type %d. Leaving\n",
|
||||
pd->subdevs[part].slice->name,
|
||||
(u_int)dp->dp_typ);
|
||||
pd->subdevs[part].slice->probeinfo.type = NO_SUBPART;
|
||||
break;
|
||||
case DOSPTYP_386BSD: /* 0xA5 "FreeBSD/NetBSD/386BSD" */
|
||||
pd->subdevs[part].slice->probeinfo.type = "disklabel";
|
||||
break;
|
||||
default:
|
||||
pd->subdevs[part].slice->probeinfo.type = NULL;
|
||||
}
|
||||
slice_start_probe(pd->subdevs[part].slice);
|
||||
}
|
||||
return (0);
|
||||
nope:
|
||||
printf("nope\n");
|
||||
mbr_revoke(pd);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* This routine tries to guess the geometry for
|
||||
* old disk drivers that need the MBR code to set it. Bits taken from
|
||||
* diskslice_machdep.c which itself evolved from earlier code.
|
||||
* This is not part of the SLICE code per-se, but just a convenient place to
|
||||
* put this HACK because everything is in scope. Only called by the IDE driver.
|
||||
* At the moment I don't know when it could be called from wd.c
|
||||
* Possibly it might call the claim function itself so it may be called instead of
|
||||
* the claim. It would have to inhibit the claim from calling the disklabel
|
||||
* claim till after the correct values were assigned. possibbly this
|
||||
* might be broken into two parts, the first of which hangs a struct off the
|
||||
* private data, and the second of which fills it in after the mbr has been loaded.
|
||||
*/
|
||||
int
|
||||
mbr_geom_hack(struct slice * slice, struct ide_geom *geom)
|
||||
{
|
||||
struct dos_partition table[NDOSPART];
|
||||
struct dos_partition *dp, *dp0;
|
||||
struct private_data *pd;
|
||||
int part;
|
||||
int error;
|
||||
int max_ncyls;
|
||||
int max_nsectors;
|
||||
int max_ntracks;
|
||||
u_int32_t secpercyl;
|
||||
RR;
|
||||
|
||||
if (slice->handler_up != &slicetype)
|
||||
return (ENXIO);
|
||||
pd = slice->private_up; /* XXX */
|
||||
if (pd == NULL)
|
||||
return (ENXIO);
|
||||
dp0 = pd->dos_table;
|
||||
/*
|
||||
* Guess the geometry. For some old drives (ESDI, st506) the
|
||||
* driver below us may not yet know the geometry, but needs
|
||||
* to before it can access blocks out of the first track.
|
||||
* This hack is to use information in the MBR to "deduce"
|
||||
* this information and pass it back.
|
||||
*/
|
||||
max_ncyls = 0;
|
||||
max_nsectors = 0;
|
||||
max_ntracks = 0;
|
||||
for (part = 0, dp = dp0; part < NDOSPART; part++, dp++) {
|
||||
int ncyls;
|
||||
int nsectors;
|
||||
int ntracks;
|
||||
|
||||
if (dp->dp_size == 0)
|
||||
continue;
|
||||
ncyls = DPCYL(dp->dp_ecyl, dp->dp_esect) + 1;
|
||||
if (max_ncyls < ncyls)
|
||||
max_ncyls = ncyls;
|
||||
nsectors = DPSECT(dp->dp_esect);
|
||||
if (max_nsectors < nsectors)
|
||||
max_nsectors = nsectors;
|
||||
ntracks = dp->dp_ehd + 1;
|
||||
if (max_ntracks < ntracks)
|
||||
max_ntracks = ntracks;
|
||||
}
|
||||
if ((max_ncyls == 0)
|
||||
&& (max_nsectors == 0)
|
||||
&& (max_ntracks == 0)) {
|
||||
/* we've gained nought, so just return */
|
||||
return (EINVAL);
|
||||
}
|
||||
secpercyl = (u_long) max_nsectors *max_ntracks;
|
||||
printf("s=%d, h=%d, c=%d\n", max_nsectors, max_ntracks, max_ncyls);
|
||||
/*
|
||||
* Check that we have guessed the geometry right by checking
|
||||
* the partition entries.
|
||||
*/
|
||||
error = 0;
|
||||
for (part = 0, dp = dp0; part < NDOSPART; part++, dp++) {
|
||||
int cyl;
|
||||
int sector;
|
||||
int track;
|
||||
int secpercyl;
|
||||
|
||||
if (dp->dp_size == 0)
|
||||
continue;
|
||||
cyl = DPCYL(dp->dp_scyl, dp->dp_ssect);
|
||||
track = dp->dp_shd;
|
||||
sector = DPSECT(dp->dp_ssect) - 1;
|
||||
secpercyl = max_nsectors * max_ntracks;
|
||||
/*
|
||||
* If the geometry doesn't work for any partition
|
||||
* start then don't accept it.
|
||||
*/
|
||||
if (((((dp->dp_start / secpercyl) % 1024) != cyl)
|
||||
&& (cyl != 1023))
|
||||
|| (((dp->dp_start % secpercyl)
|
||||
/ max_nsectors) != track)
|
||||
|| (((dp->dp_start % secpercyl)
|
||||
% max_nsectors) != sector)) {
|
||||
printf("Can't get disk geometry from MBR\n");
|
||||
return (EINVAL);
|
||||
}
|
||||
if ((dp->dp_start / secpercyl) > 1023) {
|
||||
printf("part %d above BIOS reach\n", part);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Set our newely hypothesised numbers into the geometry
|
||||
* slots in the supplied SLICE.
|
||||
*/
|
||||
geom->secpertrack = max_nsectors;
|
||||
geom->trackpercyl = max_ntracks;
|
||||
geom->cyls = max_ncyls;
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Invalidate all subslices, and free resources for this handler instance.
|
||||
*/
|
||||
static int
|
||||
mbr_revoke(void *private)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
register struct slice *slice;
|
||||
int part;
|
||||
|
||||
RR;
|
||||
pd = private;
|
||||
slice = pd->slice_down;
|
||||
for (part = 0; part < NDOSPART; part++) {
|
||||
if (pd->subdevs[part].slice) {
|
||||
sl_rmslice(pd->subdevs[part].slice);
|
||||
}
|
||||
}
|
||||
/*
|
||||
* remove ourself as a handler
|
||||
*/
|
||||
slice->handler_up = NULL;
|
||||
slice->private_up = NULL;
|
||||
slicetype.refs--;
|
||||
free(pd,M_DEVBUF);
|
||||
sl_unref(slice);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* shift the appropriate IO by the offset for that slice.
|
||||
*/
|
||||
static void
|
||||
mbr_IOreq(void *private, struct buf * bp)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
bp->b_pblkno += sdp->offset; /* add the offset for that slice */
|
||||
sliceio(slice, bp, SLW_ABOVE);
|
||||
}
|
||||
|
||||
static int
|
||||
mbr_open(void *private, int flags, int mode, struct proc * p)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
int part;
|
||||
int error;
|
||||
int newflags = 0;
|
||||
int oldoflags = 0;
|
||||
int newoflags = 0;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
part = sdp->part;
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
|
||||
/*
|
||||
* Calculate the change to to over-all picture here.
|
||||
* Notice that this might result in LESS open bits
|
||||
* if that was what was passed from above.
|
||||
* (Prelude to 'mode-change' instead of open/close.)
|
||||
*/
|
||||
/* work out what our stored flags will be if this succeeds */
|
||||
newflags = pd->flags & ~((MBRF_OPEN_WBIT|MBRF_OPEN_RBIT) << part);
|
||||
newflags |= (flags & FWRITE) ? (MBRF_OPEN_WBIT << part) : 0;
|
||||
newflags |= (flags & FREAD) ? (MBRF_OPEN_RBIT << part) : 0;
|
||||
|
||||
/* work out what we want to pass down this time */
|
||||
newoflags = (newflags & MBRF_MSK_WR) ? FWRITE : 0;
|
||||
newoflags |= (newflags & MBRF_MSK_RD) ? FREAD : 0;
|
||||
|
||||
/*
|
||||
* If the agregate flags we used last time are the same as
|
||||
* the agregate flags we would use this time, then don't
|
||||
* bother re-doing the command.
|
||||
*/
|
||||
if (newoflags != pd->savedoflags) {
|
||||
if (error = sliceopen(slice, newoflags, mode, p, SLW_ABOVE)) {
|
||||
return (error);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Now that we know it succeeded, commit, by replacing the old
|
||||
* flags with the new ones.
|
||||
*/
|
||||
pd->flags &= ~MBRF_MSK_OPEN;
|
||||
pd->flags |= newflags;
|
||||
pd->savedoflags = newoflags;
|
||||
return (0);
|
||||
}
|
||||
|
||||
static int
|
||||
mbr_ioctl(void *private, u_long cmd, caddr_t addr, int flag, struct proc * p)
|
||||
{
|
||||
register struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
int error;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
|
||||
return ((*slice->handler_down->ioctl) (slice->private_down,
|
||||
cmd, addr, flag, p));
|
||||
}
|
||||
|
||||
static int
|
||||
mbr_upconfig(struct slice *slice, int cmd, caddr_t addr,
|
||||
int flag, struct proc * p)
|
||||
{
|
||||
int error;
|
||||
|
||||
RR;
|
||||
switch (cmd) {
|
||||
case SLCIOCRESET:
|
||||
return (0);
|
||||
|
||||
case SLCIOCTRANSBAD:
|
||||
{
|
||||
struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
daddr_t blkno;
|
||||
int part;
|
||||
|
||||
if (!slice->handler_up)
|
||||
return (0);
|
||||
blkno = *(daddr_t *)addr;
|
||||
pd = slice->private_up;
|
||||
sdp = pd->subdevs;
|
||||
for (part = 0; part < NDOSPART; part++, sdp++) {
|
||||
if (!sdp->slice)
|
||||
continue;
|
||||
if (blkno < sdp->offset)
|
||||
continue;
|
||||
if (blkno >= sdp->offset +
|
||||
sdp->limit.slicesize / sdp->limit.blksize)
|
||||
continue;
|
||||
blkno -= sdp->offset;
|
||||
slice = sdp->slice;
|
||||
error = (*slice->handler_up->upconf)(slice, cmd,
|
||||
(caddr_t)&blkno, flag, p);
|
||||
if (!error)
|
||||
*(daddr_t *)addr = blkno + sdp->offset;
|
||||
return (error);
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
|
||||
/* These don't really make sense. keep the headers for a reminder */
|
||||
default:
|
||||
return (ENOIOCTL);
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
|
||||
static int
|
||||
mbr_dump(void *private, int32_t blkoff, int32_t blkcnt)
|
||||
{
|
||||
struct private_data *pd;
|
||||
struct subdev *sdp;
|
||||
register struct slice *slice;
|
||||
|
||||
RR;
|
||||
sdp = private;
|
||||
pd = sdp->pd;
|
||||
slice = pd->slice_down;
|
||||
blkoff += sdp->offset;
|
||||
if (slice->handler_down->dump) {
|
||||
return (*slice->handler_down->dump)(slice->private_down,
|
||||
blkoff, blkcnt);
|
||||
}
|
||||
return(ENXIO);
|
||||
}
|
@ -1,152 +0,0 @@
|
||||
yes I know this is not in mandoc format..
|
||||
|
||||
The slices are stackable..
|
||||
With alternating layers of handler(driver)/slice/handler/slice/handler/slice
|
||||
The "Slice" is implemented as a common structure shared between three
|
||||
pieces of code. Each slice in the stack can be thought of in OO terms as
|
||||
an instance of the 'slice' object. Methods include all the 'device' node
|
||||
methods exported via the cdevsw[], bdevsw[] and devfs interfaces. Thus
|
||||
whenever a handler exports a slice object, a unique node is made available
|
||||
to the users via the device system, to access that slice, as if it were a
|
||||
disk in it's own right. Since the interface is implemented by the same
|
||||
code no matter where in the stack it occurs, all partitions and devices
|
||||
which are exported by the slice code, exhibit almost identical behavior.
|
||||
Theoretically, it should be possible to treat a partition of a device, as
|
||||
if it were a separate device, as it should exhibit the same behavior as
|
||||
the device itself (except for size).
|
||||
|
||||
The diagram below exhibits the form of one layer of the stack. Each handler
|
||||
can decide how many slices to export on the upper side, and
|
||||
how many slices to connect to on the lower side. If A slice can not be
|
||||
further subdivided, there may not be an upper handler.
|
||||
|
||||
[upper handler] (optional)
|
||||
^
|
||||
|
|
||||
|
|
||||
v |------ raw (char) device
|
||||
[common slice information]<---------->[slice device]
|
||||
^ |------ block device
|
||||
|
|
||||
|
|
||||
v
|
||||
[lower handler] (may be a device driver)
|
||||
|
||||
Each of these 3 items share some knowledge of the internal structure and
|
||||
contents of the slice structure. They also know each other's published
|
||||
interfaces. This may change as the design settles down and it becomes more
|
||||
obvious which parts can be hidden.
|
||||
|
||||
The slices are created bottom up.
|
||||
When the driver decides that there is media that should be made available,
|
||||
it creates a 'slice' object to represent it. This slice object comes with a
|
||||
set of methods for exporting and implementing a device. The action of creating
|
||||
a slice therefor creates the interface through which a user can access that
|
||||
device. A driver might even export such slice before the media is present,
|
||||
in order to make a device node available to the user. (e.g. the floppy
|
||||
driver would make /dev/rfd0 available even if there was no media present,
|
||||
simply because it has no way of detecting that the media has been added.
|
||||
Attempts to open or access that node would result in the usual EIO
|
||||
errors.
|
||||
|
||||
i.e. the device probes, and creates a static 'slice' that is associated with
|
||||
the device.. The static slice can't be removed unless the driver does so,
|
||||
thought if the media is changed the size of the slice may change.
|
||||
|
||||
|
||||
Some time after the media has been detected, or deduced to be present,
|
||||
the driver would ask the system to try interpret the contents of the
|
||||
media. It does this by passing the slice to the generic code. The generic
|
||||
code will ask all the possible handlers to see if that slice (or virtual
|
||||
disk) has the structure it requires. Sometimes the driver (or lower handler,
|
||||
for that is what the driver is from the point of view of the slice) Will 'seed'
|
||||
the slice with a 'hint' which will make the generic code narrow it's requests
|
||||
to a particular handler, or group of handlers.
|
||||
|
||||
When a slice object attaches an handler to one of it's slices, that handler
|
||||
might elect to further export more slices, each representing some different
|
||||
view of the slice. This could result on a multi layer stack of slices and
|
||||
handlers, depending on the contents of the device. Whether a handler will
|
||||
elect to further divide a slice given to it is solely up to that handler. No
|
||||
other code has jurisdiction over that decision.
|
||||
|
||||
Because a device may need to know that it is being used, it is important
|
||||
that open() events be cascaded down towards the device. Handlers that
|
||||
export multiple slices upwards must pass down the union of all the open
|
||||
states of those slices.
|
||||
|
||||
A lower level handler can decide that the slices it has exported are no
|
||||
longer valid. This can occur for several reasons. For example a write to a
|
||||
low level slice might change the structures defining a higher level slice,
|
||||
or a driver (the lowest level handler) might notice that the media on which
|
||||
a slice is based, has been removed, or in some other way become
|
||||
unavailable. The handler must be able to invalidate the slice(es) affected,
|
||||
and know that the system will cascade that invalidation upwards as needed.
|
||||
A higher handler may decide to no pass on the invalidation if it calculates
|
||||
that higher level services can still be provided without the particular
|
||||
lower slice being present, (e.g. a RAID handler).
|
||||
|
||||
Access to various layers is controlled by a strict protocol to avoid
|
||||
accidental system damage. There is a single sysctl variable that can
|
||||
disable the enforcement of this protocol, however it should ony be used
|
||||
in special (e.g. system instalation) circumstances. The basic protocol
|
||||
is that a higher level device cannot be opened while one of it's lower
|
||||
layers is open for writing. Similarly, a lower layer cannot be openned for
|
||||
writing while an upper layer is open at all. Two devices at different
|
||||
layers can be openned at the same time if there is no direct
|
||||
decendancy between the two. In an analogue, we might say that 'cousins'
|
||||
can be openned independantly, but anscestors and descendents cannot.
|
||||
The sysctl variable kern.slicexclusive has 3 values.
|
||||
0 disables the checks metioned above. 1 enables them, and 2
|
||||
enables eve more draconian rules in which even READ opens are disabled.
|
||||
|
||||
Further rules govern the interaction of the block and raw versions of a
|
||||
slice. For example, if a block device is open for read/write, it's raw
|
||||
device can not be written to (in mode 1)
|
||||
|
||||
[think about upwards permission inherritance for subslices]
|
||||
|
||||
|
||||
[setting up new configurations]
|
||||
A disk exports simply a raw slice. It has no preference as to what goes on it..
|
||||
(preferences are stored in the slice's probehints structure.)
|
||||
To slice it into fdisk type:
|
||||
1/ set the hints to "mbr", through an ioctl on that device. (e.g. rsd0)
|
||||
2/ Run the "mbr" code's constructor. this will initialise the slice.
|
||||
The "mbr" code will actually write an mbr to the slice,
|
||||
with default values. (so it will recognise it in the future).
|
||||
(this is why the claim is separate from the constructor). The claim()
|
||||
is nondestructive. The constructor KNOWS it owns the slice.
|
||||
3/ Send ioctls to the device that are redirected UP to the new handler.
|
||||
These ioctls allow "type specific templates" and manipulation
|
||||
of slice tables. Each hander interprets these to suit it's own table
|
||||
format. This uses the sl_h_upconfig() method, which is basically an
|
||||
ioctl entrypoint, but which is not automatically cascaded up.
|
||||
|
||||
|
||||
rc should have the following added to it to make the system 'safe'
|
||||
when multi-user mode is entered.
|
||||
|
||||
*** /etc/rc.orig Sat Apr 18 14:34:48 1998
|
||||
--- /etc/rc Sat Apr 18 14:38:32 1998
|
||||
***************
|
||||
*** 82,87 ****
|
||||
--- 82,96 ----
|
||||
exit 1
|
||||
fi
|
||||
|
||||
+ ###DEVFS
|
||||
+ # put the storage slices into safe mode.
|
||||
+ # 0 == unsafe. One char, one blk and one subslice can all be openned R/W.
|
||||
+ # 1 = readonly. If a subslice is open, a blk and chr can be openned R/O.
|
||||
+ # If a slice is open R/W, subslices cannot be openned.
|
||||
+ # 2 = exclusive. If a subslice is open, a blk or chr cannot be openned.
|
||||
+ # and visa versa.
|
||||
+ sysctl -w kern.slicexclusive=1
|
||||
+
|
||||
# If there is a global system configuration file, suck it in.
|
||||
if [ -f /etc/rc.conf ]; then
|
||||
. /etc/rc.conf
|
||||
|
||||
|
||||
|
@ -1,207 +0,0 @@
|
||||
/*-
|
||||
* Copyright (C) 1997,1998 Julian Elischer. All rights reserved.
|
||||
* julian@freebsd.org
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER ``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 HOLDER 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.
|
||||
*
|
||||
* $Id: slice.h,v 1.4 1998/07/13 08:22:55 julian Exp $
|
||||
*/
|
||||
|
||||
typedef struct slice_handler *sh_p;
|
||||
typedef struct slice *sl_p;
|
||||
|
||||
struct slicelimits {
|
||||
u_int32_t blksize; /* IN BYTES */
|
||||
u_int64_t slicesize; /* IN BYTES */
|
||||
};
|
||||
typedef struct slicelimits *slmt_p;
|
||||
|
||||
/*
|
||||
* This struct is only used by the IDE geometry guessing hack in
|
||||
* the MBR and disklabel code, when talked to by the IDE driver with a VERY
|
||||
* OLD DISK
|
||||
*/
|
||||
struct ide_geom {
|
||||
u_int32_t secpertrack; /* set to 0 if geom not known */
|
||||
u_int16_t trackpercyl;
|
||||
u_int32_t cyls;
|
||||
};
|
||||
|
||||
/*
|
||||
* The probehints are set by the lower handler, to give direction as to
|
||||
* what handler is probably required above. If a slice is repartitioned,
|
||||
* these may change e.g. mbr may set 165 meaning "FreeBSD slice" or 4 "DOS".
|
||||
* -type: a string for the type that should be used.
|
||||
* if it's a null string ("") then don't even try find a sub handler.
|
||||
* defined as NO_SUBPART
|
||||
* if it's a NULL pointer (NULL) then probe all known types.
|
||||
* -typespecific: A pointer to SOMETHING that the lower handler thinks
|
||||
* may be of interest to the higher hamdlers. The "something" is dependent
|
||||
* on the type of the lower handler so the upper handler must know of
|
||||
* this in advance. The type of this should be specified in an
|
||||
* include file associated with the lower type. This is probably rarely
|
||||
* needed.
|
||||
*/
|
||||
struct probehints {
|
||||
sh_p trial_handler; /* methods of handler being probed */
|
||||
char *type; /* don't probe, just use this type */
|
||||
void *typespecific; /* the lower layer specifies this */
|
||||
};
|
||||
#define NO_SUBPART ""
|
||||
/*
|
||||
* The common slice structure with data, methods and linkages.
|
||||
*/
|
||||
struct slice {
|
||||
/* Per slice data */
|
||||
char *name; /* e.g. sd0 wd0s1, wd0s1a ?? */
|
||||
struct probehints probeinfo; /* how we should probe this */
|
||||
u_int32_t flags; /* this device open, etc. */
|
||||
u_int16_t refs; /* active references, free if 1->0 */
|
||||
u_int16_t opencount; /* actual count of opens if allowed */
|
||||
struct slicelimits limits; /* limits on this slice */
|
||||
sh_p handler_up; /* type methods etc. */
|
||||
void *private_up; /* data for the slice type */
|
||||
sh_p handler_down; /* type methods etc. */
|
||||
void *private_down; /* data for the slice type */
|
||||
/*------- fields for the slice device driver -------*/
|
||||
LIST_ENTRY(slice) hash_list; /* next slice in this bucket */
|
||||
u_int32_t minor; /* the key for finding us */
|
||||
void *devfs_btoken;
|
||||
void *devfs_ctoken;
|
||||
};
|
||||
|
||||
/* bit definitions for the slice flags */
|
||||
#define SLF_CLOSED 0x00000000 /* slice not open */
|
||||
#define SLF_OPEN_BLK_RD 0x00000001 /* blk slice readable */
|
||||
#define SLF_OPEN_BLK_WR 0x00000002 /* blk slice writeable */
|
||||
#define SLF_OPEN_BLK (SLF_OPEN_BLK_RD|SLF_OPEN_BLK_WR)
|
||||
#define SLF_OPEN_CHR_RD 0x00000004 /* raw slice readable */
|
||||
#define SLF_OPEN_CHR_WR 0x00000008 /* raw slice writeable */
|
||||
#define SLF_OPEN_CHR (SLF_OPEN_CHR_RD|SLF_OPEN_CHR_WR)
|
||||
#define SLF_OPEN_DEV_RD (SLF_OPEN_CHR_RD|SLF_OPEN_BLK_RD)
|
||||
#define SLF_OPEN_DEV_WR (SLF_OPEN_CHR_WR|SLF_OPEN_BLK_WR)
|
||||
#define SLF_OPEN_DEV (SLF_OPEN_DEV_RD|SLF_OPEN_DEV_WR)
|
||||
#define SLF_OPEN_UP_RD 0x00000010 /* upper layer is readable */
|
||||
#define SLF_OPEN_UP_WR 0x00000020 /* upper layer is writable */
|
||||
#define SLF_OPEN_UP 0x00000030 /* upper layer is open */
|
||||
#define SLF_OPEN_WR (SLF_OPEN_UP_WR|SLF_OPEN_DEV_WR)
|
||||
#define SLF_OPEN_RD (SLF_OPEN_UP_RD|SLF_OPEN_DEV_RD)
|
||||
#define SLF_OPEN_STATE (SLF_OPEN_WR|SLF_OPEN_RD) /* Mask open state */
|
||||
|
||||
#define SLF_INVALID 0x00000100 /* Everything aborts */
|
||||
#define SLF_LOCKED 0x00000200 /* Hold off, It's busy */
|
||||
#define SLF_WANTED 0x00000400 /* I held off, wake me up */
|
||||
#define SLF_PROBING 0x00000800 /* Probe state machine active */
|
||||
#define SLF_PROBE_SEL 0x00001000 /* Probe selecting */
|
||||
#define SLF_DONT_ARGUE 0x00002000 /* an assign, not a probe */
|
||||
|
||||
#define SLF_WAIT_READ 0x00008000 /* waiting for a probe read */
|
||||
#define SLF_WAIT_WRITE 0x0000C000 /* waiting for a probe read */
|
||||
#define SLF_PROBE_STATE 0x0000C000 /* Present probe state */
|
||||
|
||||
/*
|
||||
* prototypes for slice methods
|
||||
*/
|
||||
typedef void sl_h_IO_req_t(void *private, struct buf * buf);
|
||||
typedef int sl_h_ioctl_t(void *private, u_long cmd, caddr_t data,
|
||||
int fflag, struct proc * p);
|
||||
typedef int sl_h_done_t(sl_p slice, struct buf *bp);
|
||||
typedef int sl_h_open_t(void *private, int flags, int mode, struct proc * p);
|
||||
typedef void sl_h_close_t(void *private, int flags, int mode, struct proc * p);
|
||||
typedef int sl_h_revoke_t(void *private);
|
||||
typedef int sl_h_claim_t(struct slice * slice);
|
||||
typedef int sl_h_verify_t(struct slice *slice);
|
||||
typedef int sl_h_upconfig_t(struct slice *slice, int cmd, caddr_t data,
|
||||
int fflag, struct proc *p);
|
||||
typedef int sl_h_dump_t(void *private, int32_t blkoff, int32_t blkcnt);
|
||||
|
||||
struct slice_handler {
|
||||
char *name;
|
||||
int version;/* the version of this handler */
|
||||
struct slice_handler *next; /* next registered type */
|
||||
int refs; /* references to this type */
|
||||
sl_h_done_t *done; /* return after async request */
|
||||
sl_h_IO_req_t *IOreq; /* IO req downward (to device) */
|
||||
sl_h_ioctl_t *ioctl; /* ioctl downward (to device) */
|
||||
sl_h_open_t *open; /* downwards travelling open */
|
||||
sl_h_close_t *close; /* downwards travelling close */
|
||||
sl_h_revoke_t *revoke; /* revoke upwards (towards user ) */
|
||||
sl_h_claim_t *claim; /* claim a new slice */
|
||||
sl_h_verify_t *verify; /* verify that a slice as it was before */
|
||||
sl_h_upconfig_t *upconf; /* config requests from slice below */
|
||||
sl_h_dump_t *dump; /* dump the core */
|
||||
};
|
||||
|
||||
/*
|
||||
* general routines that handlers need.
|
||||
*/
|
||||
int sl_make_slice(sh_p handler_down, void *private_down,
|
||||
struct slicelimits *limits,
|
||||
sl_p *slicepp, char *name);
|
||||
void sl_rmslice(sl_p slice);
|
||||
int sl_newtype(sh_p tp);
|
||||
sh_p sl_findtype(char *type);
|
||||
void slice_start_probe(sl_p slice);
|
||||
int slice_lock(sl_p slice);
|
||||
int slice_unlock(sl_p slice);
|
||||
int slice_request_block(struct slice *slice, int blkno);
|
||||
int slice_writeblock(struct slice * slice, int blkno,
|
||||
void (*iodone )(struct buf *),
|
||||
caddr_t data, int len);
|
||||
void slice_probe_next(sl_p slice);
|
||||
|
||||
/*
|
||||
* Definitions for "SLICE" utilities. (handler or device acting on a slice).
|
||||
*/
|
||||
enum slc_who { SLW_ABOVE, SLW_DEVICE }; /* helps to know who's calling */
|
||||
|
||||
void sliceio(sl_p slice, struct buf * bp, enum slc_who who);
|
||||
int sliceopen(sl_p slice, int flags, int mode,
|
||||
struct proc * p, enum slc_who who);
|
||||
void sliceclose(sl_p slice, int flags, int mode,
|
||||
struct proc * p, enum slc_who who);
|
||||
|
||||
void sl_unref(sl_p slice);
|
||||
void slice_add_device(sl_p slice);
|
||||
void slice_remove_device(sl_p slice);
|
||||
|
||||
/*
|
||||
* The geometry guessing HACK functions
|
||||
*/
|
||||
int mbr_geom_hack(struct slice * slice, struct ide_geom *geom);
|
||||
int dkl_geom_hack(struct slice * slice, struct ide_geom *geom);
|
||||
/*
|
||||
* The routine to produce a dummy disklabel from a slice.
|
||||
* Lives in disklabel.c because that's where everyhting is in scope,
|
||||
* but is used in slice_device.c. XXX hack.
|
||||
*/
|
||||
int dkl_dummy_ioctl(struct slice *slice, u_long cmd, caddr_t addr,
|
||||
int flag, struct proc * p);
|
||||
|
||||
/*
|
||||
* debugging
|
||||
*/
|
||||
#if 0
|
||||
#define RR printf(__FUNCTION__ " called\n")
|
||||
#else
|
||||
#define RR /* nothing */
|
||||
#endif
|
@ -1,826 +0,0 @@
|
||||
/*-
|
||||
* Copyright (C) 1997,1998 Julian Elischer. All rights reserved.
|
||||
* julian@freebsd.org
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER ``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 HOLDER 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.
|
||||
*
|
||||
* $Id: slice_base.c,v 1.5 1998/07/13 08:22:56 julian Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/kernel.h> /* SYSINIT stuff */
|
||||
#include <sys/fcntl.h> /* FREAD/FWRITE */
|
||||
#include <sys/conf.h> /* cdevsw stuff */
|
||||
#include <sys/malloc.h> /* malloc region definitions */
|
||||
#include <sys/buf.h> /* buffers for IO */
|
||||
#include <sys/queue.h> /* linked lists etc. */
|
||||
#include <sys/stat.h> /* S_IFCHR, S_IFBLK */
|
||||
#include <sys/sysctl.h> /* the sysctl for shooting self in foot */
|
||||
/*#include <sys/devfsext.h> */ /* DEVFS defintitions */
|
||||
#include <dev/slice/slice.h> /* temporary location */
|
||||
|
||||
#define SLICESPL() splbio()
|
||||
|
||||
static void sl_async_done(struct buf *bp);
|
||||
|
||||
|
||||
static int slicexclusive = 0; /* default value == "foot shootable" */
|
||||
|
||||
/*
|
||||
* Make a new type available. Just link it in, but first make sure there is
|
||||
* no name collision.
|
||||
*/
|
||||
|
||||
static sh_p types;
|
||||
|
||||
int
|
||||
sl_newtype(sh_p tp)
|
||||
{
|
||||
if (sl_findtype(tp->name)) {
|
||||
return (EEXIST);
|
||||
}
|
||||
tp->next = types;
|
||||
types = tp;
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Look for a type of the name given.
|
||||
*/
|
||||
sh_p
|
||||
sl_findtype(char *type)
|
||||
{
|
||||
sh_p tp;
|
||||
|
||||
tp = types;
|
||||
while (tp) {
|
||||
if (strcmp(tp->name, type) == 0)
|
||||
return (tp);
|
||||
tp = tp->next;
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
* Make a handler instantiation of the requested type.
|
||||
* don't take no for an answer.
|
||||
* force it to mark it's new territory.
|
||||
* Must be called from a within a user context.
|
||||
*
|
||||
*/
|
||||
static int
|
||||
sl_make_handler(sl_p slice, char *type)
|
||||
{
|
||||
sh_p handler_up;
|
||||
|
||||
/*
|
||||
* check that the type makes sense.
|
||||
*/
|
||||
if (type == NULL) {
|
||||
return (EINVAL);
|
||||
}
|
||||
handler_up = sl_findtype(type);
|
||||
if (handler_up == NULL) {
|
||||
return (ENXIO);
|
||||
}
|
||||
|
||||
/*
|
||||
* and call the constructor
|
||||
*/
|
||||
slice->flags |= SLF_DONT_ARGUE;
|
||||
return( (*handler_up->claim) (slice));
|
||||
}
|
||||
|
||||
/*
|
||||
* lock and unlock Slices while doing operations such as open().
|
||||
* gets a reference on the slice..
|
||||
* XXX This doesn't work for SMP.
|
||||
*/
|
||||
int
|
||||
slice_lock(struct slice *slice)
|
||||
{
|
||||
int s = SLICESPL();
|
||||
slice->refs++;
|
||||
while ( slice->flags & (SLF_LOCKED | SLF_INVALID)) {
|
||||
if (slice->flags & SLF_INVALID) {
|
||||
sl_unref(slice);
|
||||
splx(s);
|
||||
return (ENXIO);
|
||||
}
|
||||
slice->flags |= SLF_WANTED;
|
||||
tsleep(slice, PRIBIO, "slice_lock", 0);
|
||||
}
|
||||
slice->flags |= SLF_LOCKED;
|
||||
splx(s);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Releases a slice
|
||||
* Assumes that if we had it locked, no-one else could invalidate it.
|
||||
* We can still hold a reference on it.
|
||||
*/
|
||||
int
|
||||
slice_unlock(struct slice *slice)
|
||||
{
|
||||
int s = SLICESPL();
|
||||
slice->flags &= ~SLF_LOCKED;
|
||||
if ( slice->flags & SLF_WANTED) {
|
||||
slice->flags &= ~SLF_WANTED;
|
||||
wakeup(slice);
|
||||
}
|
||||
splx(s);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* create a new slice. Link it into the structures.
|
||||
* As of yet it has no upper handler.
|
||||
*/
|
||||
int
|
||||
sl_make_slice(sh_p handler_down, void *private_down,
|
||||
struct slicelimits * limits,
|
||||
sl_p * slicepp, char *name)
|
||||
{
|
||||
sl_p slice;
|
||||
|
||||
/*
|
||||
* Allocate storage for this instance .
|
||||
*/
|
||||
slice = malloc(sizeof(*slice), M_DEVBUF, M_NOWAIT);
|
||||
if (slice == NULL) {
|
||||
printf("slice failed to allocate driver storage\n");
|
||||
return (ENOMEM);
|
||||
}
|
||||
bzero(slice, sizeof(*slice));
|
||||
if (name) {
|
||||
slice->name = malloc(strlen(name) + 1, M_DEVBUF, M_NOWAIT);
|
||||
if (slice->name == NULL) {
|
||||
printf("slice failed name storage\n");
|
||||
free(slice, M_DEVBUF);
|
||||
return (ENOMEM);
|
||||
}
|
||||
strcpy(slice->name, name);
|
||||
}
|
||||
slice->handler_down = handler_down;
|
||||
slice->private_down = private_down;
|
||||
handler_down->refs++;
|
||||
slice->limits = *limits;
|
||||
slice_add_device(slice);
|
||||
slice->refs = 1; /* one for our downward creator */
|
||||
*slicepp = slice;
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Forceably start a shutdown process on a slice. Either call it's shutdown
|
||||
* method, or do the default shutdown if there is no type-specific method.
|
||||
* XXX Really should say who called us.
|
||||
* Should be called at SLICESPL (splbio)
|
||||
*/
|
||||
void
|
||||
sl_rmslice(sl_p slice)
|
||||
{
|
||||
RR;
|
||||
/*
|
||||
* An extra reference so it doesn't go away while we are not looking.
|
||||
*/
|
||||
slice->refs++;
|
||||
|
||||
if (slice->flags & SLF_INVALID) {
|
||||
/*
|
||||
* If it's already shutting down, let it die without further
|
||||
* taunting. "go away or I'll taunt you a second time, you
|
||||
* silly eenglish pig-dog"
|
||||
*/
|
||||
sl_unref(slice);/* possibly the last reference */
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* Mark it as invalid so any newcomers know not to try use it.
|
||||
* No real need to LOCK it.
|
||||
*/
|
||||
slice->flags &= ~SLF_OPEN_STATE;
|
||||
slice->flags |= SLF_INVALID;
|
||||
|
||||
/*
|
||||
* remove the device appendages.
|
||||
* Any open vnodes SHOULD go to deadfs.
|
||||
*/
|
||||
slice_remove_device(slice);
|
||||
|
||||
/*
|
||||
* Propogate the damage upwards.
|
||||
* Note that the revoke method is not optional.
|
||||
* The upper handler releases it's reference so refs--.
|
||||
*/
|
||||
if (slice->handler_up) {
|
||||
(*slice->handler_up->revoke) (slice->private_up);
|
||||
}
|
||||
sl_unref(slice); /* One for the lower handler that called us */
|
||||
sl_unref(slice); /* possibly the last reference */
|
||||
}
|
||||
|
||||
|
||||
|
||||
void
|
||||
sl_unref(sl_p slice)
|
||||
{
|
||||
if ((--(slice->refs)) == 0) {
|
||||
FREE(slice, M_DEVBUF);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
* Handler probing state machine support.
|
||||
***********************************************************************/
|
||||
|
||||
/*
|
||||
* Ask all known handler types if a given slice is handled by them.
|
||||
* If the slice specifies a type, then just find that.
|
||||
* This will be done asynchronously. The claim operation may simply
|
||||
* queue the work to be done. When this item has been rejected,
|
||||
* control will pass to slice_probe_next().
|
||||
* This starts up the generic probeing state machine, which
|
||||
* will start up the probing state machine for each handler in turn,
|
||||
* until one has claimed the device, or there are no more handlers.
|
||||
*
|
||||
*/
|
||||
void
|
||||
slice_start_probe(sl_p slice)
|
||||
{
|
||||
sh_p tp = types;
|
||||
|
||||
if (slice->probeinfo.type == NULL) {
|
||||
if(slice->handler_up == NULL) {
|
||||
slice->probeinfo.trial_handler = tp;
|
||||
slice->flags |= SLF_PROBING;
|
||||
printf("%s: probing for %s.. ",slice->name, tp->name);
|
||||
(*tp->claim) (slice);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* Null string ("") means "don't even try". Caller probably
|
||||
* should pre-trap such cases but we'll check here too.
|
||||
* Notice that the PROBING bit is not set.
|
||||
* This means that we should not do a full probe,
|
||||
* but just this one handler.
|
||||
*/
|
||||
if (slice->probeinfo.type[0]) {
|
||||
tp = sl_findtype(slice->probeinfo.type);
|
||||
if (tp) {
|
||||
printf("%s: attaching %s..\n", slice->name, tp->name);
|
||||
(*tp->claim) (slice);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Move the slice probe type, on to the next type
|
||||
* and call that. Called from failed probes.
|
||||
* Don't do anything if the PROBING flag has been cleared.
|
||||
*/
|
||||
void
|
||||
slice_probe_next(sl_p slice)
|
||||
{
|
||||
sh_p tp = slice->probeinfo.trial_handler;
|
||||
|
||||
if ((slice->flags & SLF_PROBING) == 0)
|
||||
return;
|
||||
if (tp != NULL) {
|
||||
if (slice->probeinfo.trial_handler = tp = tp->next) {
|
||||
printf("%s: probing for %s.. ",slice->name, tp->name);
|
||||
(*tp->claim) (slice);
|
||||
return;
|
||||
}
|
||||
}
|
||||
slice->flags &= ~SLF_PROBING;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Given a slice, launch an IOrequest for information
|
||||
* This is not a bulk IO routine but meant for probes etc.
|
||||
* This routine may be called at interrupt time. It schedules an
|
||||
* IO that will be completed asynchronously. On completion the
|
||||
* Block IO system will call sl_async_done, which will trigger
|
||||
* a completion event for the handler's probe state machine.
|
||||
*/
|
||||
int
|
||||
slice_request_block(sl_p slice, int blknum)
|
||||
{
|
||||
struct buf *bp;
|
||||
int s;
|
||||
|
||||
RR;
|
||||
s = splbio();
|
||||
#ifdef PARANOID
|
||||
if ( slice->private_up == NULL) {
|
||||
panic("slice_request_block: no pd");
|
||||
}
|
||||
if (slice->flags & SLF_PROBE_STATE) {
|
||||
panic("slice_request_block: 2nd IO");
|
||||
}
|
||||
#endif /* PARANOID */
|
||||
bp = geteblk((int) slice->limits.blksize);
|
||||
if (bp == NULL) {
|
||||
return (ENOMEM);
|
||||
}
|
||||
slice->flags |= SLF_WAIT_READ;
|
||||
bp->b_iodone = &sl_async_done;
|
||||
bp->b_flags |= B_CALL;
|
||||
bp->b_dev = (dev_t)slice; /* XXX HACK ALERT! */
|
||||
bp->b_pblkno = bp->b_blkno = blknum;
|
||||
bp->b_bcount = slice->limits.blksize;
|
||||
bp->b_flags |= B_BUSY | B_READ;
|
||||
sliceio(slice, bp, SLW_ABOVE);
|
||||
splx(s);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Write a block on behalf of a handler.
|
||||
* This is not a bulk IO routine but meant for probes etc.
|
||||
* I think that perhaps it should attempt to do sliceopen()
|
||||
* calls on the slice first. (XXX?) no, they may block?
|
||||
*/
|
||||
int
|
||||
slice_writeblock(struct slice * slice, int blkno,
|
||||
void (*iodone )(struct buf *),
|
||||
caddr_t data, int len)
|
||||
{
|
||||
struct buf *bp;
|
||||
int error = 0;
|
||||
|
||||
#ifdef PARANOID
|
||||
if ( slice->handler_up == NULL) {
|
||||
panic("slice_writeblock: no handler");
|
||||
}
|
||||
if (slice->flags & SLF_PROBE_STATE) {
|
||||
panic("slice_writeblock: 2nd IO");
|
||||
}
|
||||
#endif /* PARANOID */
|
||||
if (len > slice->limits.blksize)
|
||||
return (EINVAL);
|
||||
bp = geteblk((int) slice->limits.blksize);
|
||||
if (bp == NULL) {
|
||||
return (ENOMEM);
|
||||
}
|
||||
slice->flags |= SLF_WAIT_WRITE;
|
||||
bcopy(data, bp->b_data, len);
|
||||
bp->b_iodone = sl_async_done;
|
||||
bp->b_flags |= B_CALL;
|
||||
bp->b_dev = (dev_t)slice; /* XXX HACK ALERT! */
|
||||
bp->b_pblkno = bp->b_blkno = blkno;
|
||||
bp->b_bcount = slice->limits.blksize;
|
||||
bp->b_flags |= B_BUSY | B_WRITE;
|
||||
sliceio(slice, bp, SLW_ABOVE);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* called with an argument of a bp when it is completed.
|
||||
* Th eslice is extracted from the operation and the completion event
|
||||
* is used to trigger that slice's state machine to make the next move.
|
||||
*/
|
||||
static void
|
||||
sl_async_done(struct buf *bp)
|
||||
{
|
||||
sl_p slice;
|
||||
int error;
|
||||
|
||||
RR;
|
||||
if (bp->b_dev < 0xf0000000)
|
||||
panic ("b_dev used in SLICE code");
|
||||
slice = (struct slice *)bp->b_dev; /* XXX HACK! */
|
||||
|
||||
#ifdef PARANOID
|
||||
if ( slice->handler_up == NULL) {
|
||||
panic("sl_async_done: no pd");
|
||||
}
|
||||
if (bp->b_flags & B_READ) {
|
||||
if ((slice->flags & SLF_PROBE_STATE) != SLF_WAIT_READ)
|
||||
panic("sl_async_done: unexpected read completion");
|
||||
} else {
|
||||
if ((slice->flags & SLF_PROBE_STATE) != SLF_WAIT_WRITE)
|
||||
panic("sl_async_done: unexpected write completion");
|
||||
}
|
||||
#endif /* PARANOID */
|
||||
|
||||
/*
|
||||
* if the IO failed, then abandon the probes and
|
||||
* return. Possibly ask the lower layer to try again later?
|
||||
* It's assumed that a a revoke will abort the state machine.
|
||||
* XXX Maybe we should call the done() routine anyhow
|
||||
* and let each handler detect the failure..
|
||||
*/
|
||||
if (bp->b_flags & B_ERROR) {
|
||||
(* slice->handler_up->revoke)(slice->private_up);
|
||||
|
||||
/* (* slice->handler_down->SOMETHING) (slice->private_down); */
|
||||
|
||||
bp->b_flags |= B_INVAL | B_AGE;
|
||||
brelse(bp);
|
||||
slice->flags &= ~SLF_PROBING;
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* Call the handler's done() routine. This will
|
||||
* examine the result of the probe and do whatever is needed.
|
||||
* Check for abnormal error conditions. (return value non 0)
|
||||
* Not claiming the slice is not an error condition.
|
||||
*/
|
||||
if ( (* slice->handler_up->done)(slice, bp)) {
|
||||
slice->flags &= ~SLF_PROBING;
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* If the handler has left itself there, or cleared
|
||||
* the PROBING bit, then consider
|
||||
* probing to have come to a close. So just return.
|
||||
* XXX An IO error would be a great hint to abandon probing as well.
|
||||
* we catch that on the way up but we might want to give
|
||||
* the handler a chance to clean up state?
|
||||
*/
|
||||
if (slice->handler_up || ((slice->flags & SLF_PROBING) == 0)) {
|
||||
slice->flags &= ~SLF_PROBING;
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* The handler didn't claim it. Nor did it abort the
|
||||
* probing sequence.
|
||||
* Ok, so we should try the next handler to probe.
|
||||
*/
|
||||
slice_probe_next(slice);
|
||||
}
|
||||
|
||||
/*
|
||||
* functions that are used to call the next level down.
|
||||
*/
|
||||
void
|
||||
sliceio(sl_p slice, struct buf * bp, enum slc_who who)
|
||||
{
|
||||
/* XXX do shortcuts here */
|
||||
|
||||
if (slice->flags & SLF_INVALID) {
|
||||
bp->b_error = ENXIO;
|
||||
goto bad;
|
||||
}
|
||||
/*
|
||||
* if it's from above, assume it hasn't
|
||||
* broken it's agreement about read/write.
|
||||
* A higher level slice would have caught it.
|
||||
* Make no such assumption if it's this device.
|
||||
*/
|
||||
if (who == SLW_DEVICE) {
|
||||
if (((slice->flags & SLF_OPEN_DEV_WR) == 0) &&
|
||||
( (bp->b_flags & B_READ) == B_WRITE )) {
|
||||
bp->b_error = EROFS;
|
||||
goto bad;
|
||||
}
|
||||
}
|
||||
(*slice->handler_down->IOreq) (slice->private_down, bp);
|
||||
return;
|
||||
bad:
|
||||
bp->b_flags |= B_ERROR;
|
||||
/* toss transfer, we're done early */
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* Try open a slice.
|
||||
* don't forget to say if we are above (1) or the dev (0).
|
||||
*
|
||||
* We really need to add a lot of support for CHANGING
|
||||
* what we have openned.. i.e if we have ABOVE open R/W
|
||||
* and DEVICE open R/O, then closing the device
|
||||
* should downgrade our open to those items below us to R/O.
|
||||
* This would need support in both open and close routines in both
|
||||
* slice and handler code.
|
||||
*
|
||||
* ((*) == Illegal state.. (how did we get here?))
|
||||
* (must have been in "shoot foot mode").
|
||||
* A bit already set can be set again. (may represent part of an upgrade)
|
||||
* This may not hold true if we are in an 'illegal state'.
|
||||
* Some such opens will fail in an attempt to revert to a legal state.
|
||||
* success = ((request & allowed[state]) == request)
|
||||
*/
|
||||
#define UP_RDWR SLF_OPEN_UP
|
||||
#define CHR_RDWR SLF_OPEN_CHR
|
||||
#define CHR_RD SLF_OPEN_CHR_RD
|
||||
#define BLK_RDWR SLF_OPEN_BLK
|
||||
#define BLK_RD SLF_OPEN_BLK_RD
|
||||
static u_char allowed[64] = {
|
||||
/* Present state | requested states allowed */
|
||||
/* UP CHR BLK | UP CHR BLK */
|
||||
/* R W R W R W | R W R W R W */
|
||||
/* 0 0 0 0 0 0 1 1 1 1 1 1 */( UP_RDWR|CHR_RDWR|BLK_RDWR ),
|
||||
/* 0 0 0 0 0 1 0 0 1 0 1 1 */( CHR_RD|BLK_RDWR ),
|
||||
/* 0 0 0 0 1 0 1 1 1 1 1 1 */( UP_RDWR|CHR_RDWR|BLK_RDWR ),
|
||||
/* 0 0 0 0 1 1 0 0 1 0 1 1 */( CHR_RD|BLK_RDWR ),
|
||||
/* 0 0 0 1 0 0 0 0 1 1 1 0 */( CHR_RDWR|BLK_RD ),
|
||||
/* 0 0 0 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 0 0 1 1 0 0 0 1 1 1 0 */( CHR_RDWR|BLK_RD ),
|
||||
/* 0 0 0 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 0 1 0 0 0 1 1 1 1 1 1 */( UP_RDWR|CHR_RDWR|BLK_RDWR ),
|
||||
/* 0 0 1 0 0 1 0 0 1 0 1 1 */( CHR_RD|BLK_RDWR ),
|
||||
/* 0 0 1 0 1 0 1 1 1 1 1 1 */( UP_RDWR|CHR_RDWR|BLK_RDWR ),
|
||||
/* 0 0 1 0 1 1 0 0 1 0 1 1 */( CHR_RD|BLK_RDWR ),
|
||||
/* 0 0 1 1 0 0 0 0 1 1 1 0 */( CHR_RDWR|BLK_RD ),
|
||||
/* 0 0 1 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 0 1 1 1 0 0 0 1 1 1 0 */( CHR_RDWR|BLK_RD ),
|
||||
/* 0 0 1 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 0 0 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 0 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 0 1 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 0 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 1 0 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 1 1 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 0 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 0 0 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 0 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 0 1 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 0 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 1 0 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 1 1 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 0 1 1 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 0 0 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 0 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 0 1 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 0 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 1 0 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 1 1 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 0 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 0 0 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 0 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 0 1 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 0 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 1 0 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 1 1 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 0 1 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 0 0 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 0 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 0 1 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 0 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 1 0 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 1 1 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 0 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 0 0 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 0 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 0 1 0 1 1 1 0 1 0 */( UP_RDWR|CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 0 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 1 0 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 1 0 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 1 1 0 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ),
|
||||
/* 1 1 1 1 1 1 0 0 1 0 1 0 (*) */( CHR_RD|BLK_RD ) };
|
||||
|
||||
int
|
||||
sliceopen(struct slice *slice, int flags, int mode,
|
||||
struct proc * p, enum slc_who who)
|
||||
{
|
||||
int s;
|
||||
int error;
|
||||
int sl_flags = slice->flags & SLF_OPEN_STATE;
|
||||
int or_flags;
|
||||
int and_flags;
|
||||
int dn_flags;
|
||||
int odn_flags;
|
||||
|
||||
|
||||
if (slice->flags & SLF_INVALID)
|
||||
return (ENXIO);
|
||||
/*
|
||||
* Firstly, don't allow re-opens of what is already open
|
||||
*/
|
||||
if (error = slice_lock(slice))
|
||||
return (error);
|
||||
error = EBUSY; /* default answer */
|
||||
switch (who) {
|
||||
case SLW_ABOVE:
|
||||
or_flags = ((flags & FREAD) ? SLF_OPEN_UP_RD : 0);
|
||||
or_flags |= ((flags & FWRITE) ? SLF_OPEN_UP_WR : 0);
|
||||
and_flags = ~SLF_OPEN_UP;
|
||||
break;
|
||||
case SLW_DEVICE:
|
||||
switch (mode & S_IFMT) {
|
||||
case S_IFCHR:
|
||||
or_flags = ((flags & FREAD) ? SLF_OPEN_CHR_RD : 0);
|
||||
or_flags |= ((flags & FWRITE) ? SLF_OPEN_CHR_WR : 0);
|
||||
and_flags = ~SLF_OPEN_CHR;
|
||||
break;
|
||||
case S_IFBLK:
|
||||
or_flags = ((flags & FREAD) ? SLF_OPEN_BLK_RD : 0);
|
||||
or_flags |= ((flags & FWRITE) ? SLF_OPEN_BLK_WR : 0);
|
||||
and_flags = ~SLF_OPEN_BLK;
|
||||
break;
|
||||
default:
|
||||
panic("slice: bad open type");
|
||||
}
|
||||
/* XXX only accumulate flags as we don't know about all closes */
|
||||
/* XXX */ if ( or_flags )
|
||||
/* XXX */ and_flags = ~0;
|
||||
break;
|
||||
default:
|
||||
panic("slice: bad request source");
|
||||
}
|
||||
/*
|
||||
* Be appropriatly paranoid depending on the system mode.
|
||||
* This is also probably wrong XXX
|
||||
*/
|
||||
switch(slicexclusive) {
|
||||
case 2:
|
||||
/*
|
||||
* if any one path has it open, we forbid any other
|
||||
* paths. Only allow an upgrade/downgrade from
|
||||
* the same source as the present openner.
|
||||
*/
|
||||
if ( sl_flags & and_flags)
|
||||
goto reject;
|
||||
case 1: /*
|
||||
* The behaviour is encoded into the state array given above.
|
||||
*/
|
||||
if ((or_flags & allowed[sl_flags]) != or_flags)
|
||||
goto reject;
|
||||
break;
|
||||
case 0: /*
|
||||
* Permission is granted to shoot self in foot.
|
||||
* All three of UPPER, CHAR and BLK can be open at once.
|
||||
*/
|
||||
break;
|
||||
}
|
||||
/*
|
||||
* Get the old open mode and the new open mode.
|
||||
* If we already have it open in this way, don't do it again.
|
||||
*
|
||||
* XXX More thought needed for the locking and open-flags.
|
||||
* For now ignore the existance of flags other than FWRITE & FREAD.
|
||||
*/
|
||||
odn_flags = (sl_flags & SLF_OPEN_WR) ? FWRITE : 0;
|
||||
odn_flags |= (sl_flags & SLF_OPEN_RD) ? FREAD : 0;
|
||||
sl_flags &= and_flags;
|
||||
sl_flags |= or_flags;
|
||||
dn_flags = (sl_flags & SLF_OPEN_WR) ? FWRITE : 0;
|
||||
dn_flags |= (sl_flags & SLF_OPEN_RD) ? FREAD : 0;
|
||||
error = 0;
|
||||
if (dn_flags != odn_flags) {
|
||||
if ((error = (*slice->handler_down->open) (slice->private_down,
|
||||
dn_flags, mode, p)) != 0) {
|
||||
goto reject;
|
||||
}
|
||||
}
|
||||
slice->flags &= ~SLF_OPEN_STATE;
|
||||
slice->flags |= sl_flags;
|
||||
#if 1 /* it was basically a close */
|
||||
if ((slice->flags & SLF_OPEN_STATE) == SLF_CLOSED) {
|
||||
sh_p tp;
|
||||
|
||||
/*
|
||||
* If we had an upper handler, ask it to check if it's still
|
||||
* valid. it may decide to self destruct.
|
||||
*/
|
||||
if (slice->handler_up) {
|
||||
(*slice->handler_up->verify)(slice);
|
||||
}
|
||||
/*
|
||||
* If we don't have an upper handler, check if
|
||||
* maybe there is now a suitable environment for one.
|
||||
* We may end up with a different handler
|
||||
* from what we had above. Maybe we should clear the hint?
|
||||
* Maybe we should ask the lower one to re-issue the request?
|
||||
*/
|
||||
if (slice->handler_up == NULL) {
|
||||
slice_start_probe(slice);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
reject:
|
||||
slice_unlock(slice);
|
||||
if ((slice->flags & SLF_INVALID) == SLF_INVALID)
|
||||
error = ENODEV; /* we've been zapped while down there! */
|
||||
sl_unref(slice); /* slice_lock gave us a ref.*/
|
||||
return (error);
|
||||
}
|
||||
|
||||
#if 0
|
||||
void
|
||||
sliceclose(struct slice *slice, int flags, int mode,
|
||||
struct proc * p, enum slc_who who)
|
||||
{
|
||||
sh_p tp;
|
||||
|
||||
if (slice->flags & SLF_INVALID)
|
||||
return ;
|
||||
if (slice_lock(slice))
|
||||
return ;
|
||||
switch (who) {
|
||||
case SLW_ABOVE:
|
||||
slice->flags &= ~SLF_OPEN_UP;
|
||||
break;
|
||||
case SLW_DEVICE:
|
||||
switch (mode & S_IFMT) {
|
||||
case S_IFCHR:
|
||||
slice->flags &= ~SLF_OPEN_CHR;
|
||||
break;
|
||||
case S_IFBLK:
|
||||
slice->flags &= ~SLF_OPEN_BLK;
|
||||
break;
|
||||
default:
|
||||
panic("slice: bad open type");
|
||||
}
|
||||
/*
|
||||
* If we had an upper handler, ask it to check if it's still
|
||||
* valid. it may decide to self destruct.
|
||||
*/
|
||||
if (slice->handler_up) {
|
||||
(*slice->handler_up->verify)(slice);
|
||||
}
|
||||
/*
|
||||
* If we don't have an upper handler, check if
|
||||
* maybe there is now a suitable environment for one.
|
||||
* We may end up with a different handler
|
||||
* from what we had above. Maybe we should clear the hint?
|
||||
* Maybe we should ask the lower one to re-issue the request?
|
||||
*/
|
||||
if (slice->handler_up == NULL) {
|
||||
if ((tp = slice_start_probe(slice)) != NULL) {
|
||||
(*tp->constructor)(slice);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
/*
|
||||
* Last-close semantics strike again
|
||||
* This may refine to a downgrade if we closed (say) the last writer
|
||||
* but there are still readers.
|
||||
* probably open/close should merge to one 'mode-change' function.
|
||||
* (except for a vnode reference with no mode)
|
||||
*/
|
||||
if ( (slice->flags & SLF_OPEN_STATE) == 0)
|
||||
(*slice->handler_down->close) (slice->private_down,
|
||||
flags, mode, p);
|
||||
slice_unlock(slice);
|
||||
sl_unref(slice);
|
||||
return ;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
/*
|
||||
* control behaviour of slices WRT sharing:
|
||||
* 2 = no sharing
|
||||
* 1 = read on a device already mounted (or parent of) is ok. No writes.
|
||||
* 0 = go ahead.. shoot yourself in the foot.
|
||||
*/
|
||||
static int
|
||||
sysctl_kern_slicexclusive SYSCTL_HANDLER_ARGS
|
||||
{
|
||||
int error;
|
||||
int new_val = slicexclusive;
|
||||
|
||||
error = sysctl_handle_int(oidp, &new_val, 0, req);
|
||||
if (error == 0) {
|
||||
if ((new_val >= 0) && (new_val < 3)) {
|
||||
slicexclusive = new_val;
|
||||
} else {
|
||||
error = EINVAL;
|
||||
}
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
SYSCTL_PROC(_kern, OID_AUTO, slicexclusive, CTLTYPE_INT|CTLFLAG_RW,
|
||||
0, sizeof slicexclusive, sysctl_kern_slicexclusive, "I", "");
|
||||
|
@ -1,403 +0,0 @@
|
||||
/*-
|
||||
* Copyright (C) 1997,1998 Julian Elischer. All rights reserved.
|
||||
* julian@freebsd.org
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER ``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 HOLDER 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.
|
||||
*
|
||||
* $Id: slice_device.c,v 1.6 1998/06/07 18:44:03 sos Exp $
|
||||
*/
|
||||
#define DIAGNOSTIC 1
|
||||
#include "opt_hw_wdog.h"
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/kernel.h> /* SYSINIT stuff */
|
||||
#include <sys/conf.h> /* cdevsw stuff */
|
||||
#include <sys/malloc.h> /* malloc region definitions */
|
||||
#include <sys/buf.h> /* bufs for describing IO */
|
||||
#include <sys/fcntl.h> /* file open modes etc. */
|
||||
#include <sys/queue.h> /* standard queue macros */
|
||||
#include <sys/stat.h> /* S_IFBLK, S_IFMT etc. */
|
||||
#include <sys/devfsext.h> /* DEVFS defintitions */
|
||||
#include <dev/slice/slice.h> /* temporary location */
|
||||
|
||||
#include <vm/vm_param.h>
|
||||
#include <machine/md_var.h>
|
||||
#include <i386/i386/cons.h>
|
||||
|
||||
/* Function prototypes (these should all be static except for slicenew()) */
|
||||
static d_open_t slcdevopen;
|
||||
static d_read_t slcdevread;
|
||||
static d_write_t slcdevwrite;
|
||||
static d_close_t slcdevclose;
|
||||
static d_ioctl_t slcdevioctl;
|
||||
static d_dump_t slcdevdump;
|
||||
static d_psize_t slcdevsize;
|
||||
static d_strategy_t slcdevstrategy;
|
||||
|
||||
#define BDEV_MAJOR 14
|
||||
#define CDEV_MAJOR 20
|
||||
|
||||
static struct cdevsw slice_cdevsw = {
|
||||
slcdevopen, slcdevclose, slcdevread, slcdevwrite,
|
||||
slcdevioctl, nostop, nullreset, nodevtotty,
|
||||
seltrue, nommap, slcdevstrategy, "slice",
|
||||
NULL, -1, slcdevdump, slcdevsize,
|
||||
D_DISK, 0, -1 };
|
||||
|
||||
|
||||
#define UNIT_HASH_SIZE 64
|
||||
LIST_HEAD(slice_bucket, slice) hash_table[UNIT_HASH_SIZE - 1];
|
||||
|
||||
/*
|
||||
* Now for some driver initialisation. Occurs ONCE during boot (very early).
|
||||
*/
|
||||
static void
|
||||
slice_drvinit(void *unused)
|
||||
{
|
||||
int i;
|
||||
|
||||
/*
|
||||
* add bdevsw and cdevsw entries
|
||||
*/
|
||||
cdevsw_add_generic(BDEV_MAJOR, CDEV_MAJOR, &slice_cdevsw);
|
||||
|
||||
/*
|
||||
* clear out the hash table
|
||||
*/
|
||||
for (i = 0; i < UNIT_HASH_SIZE; i++) {
|
||||
LIST_INIT(hash_table + i);
|
||||
}
|
||||
}
|
||||
|
||||
SYSINIT(slicedev, SI_SUB_DRIVERS, SI_ORDER_MIDDLE + CDEV_MAJOR,
|
||||
slice_drvinit, NULL);
|
||||
|
||||
static int nextunit = 0;
|
||||
|
||||
void
|
||||
slice_add_device(sl_p slice)
|
||||
{
|
||||
int unit = nextunit++;
|
||||
char *name = slice->name;
|
||||
RR;
|
||||
slice->minor = makedev(0,
|
||||
(((unit << 8) & 0xffff0000) | (unit & 0x000000ff)));
|
||||
/*
|
||||
* put it on the hash chain for it's bucket so we can find it again
|
||||
* later.
|
||||
*/
|
||||
LIST_INSERT_HEAD(hash_table + (slice->minor % UNIT_HASH_SIZE),
|
||||
slice, hash_list);
|
||||
/*
|
||||
* Add an entry in the devfs for it. Possibly should happen later.
|
||||
*/
|
||||
slice->devfs_ctoken = devfs_add_devswf(&slice_cdevsw, unit, DV_CHR,
|
||||
UID_ROOT, GID_OPERATOR, 0600, "r%s", name ? name : "-");
|
||||
slice->devfs_btoken = devfs_add_devswf(&slice_cdevsw, unit, DV_BLK,
|
||||
UID_ROOT, GID_OPERATOR, 0600, "%s", name ? name : "-");
|
||||
/* XXX link this node into upper list of caller */
|
||||
}
|
||||
|
||||
/*
|
||||
* Given a minor number, find the slice which the operations are destined.
|
||||
* When DEVFS DDEV devices are enabled this is bypassed entirely.
|
||||
*/
|
||||
static struct slice *
|
||||
minor_to_slice(unsigned int minor)
|
||||
{
|
||||
int hash = minor % UNIT_HASH_SIZE;
|
||||
struct slice *slice;
|
||||
|
||||
slice = (hash_table + hash)->lh_first;
|
||||
while (slice) {
|
||||
if (slice->minor == minor) {
|
||||
return (slice);
|
||||
}
|
||||
slice = slice->hash_list.le_next;
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
|
||||
|
||||
int
|
||||
slcdevioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc * p)
|
||||
{
|
||||
sl_p slice = minor_to_slice(minor(dev));
|
||||
int error = 0;
|
||||
|
||||
RR;
|
||||
|
||||
/*
|
||||
* Look for only some generic "inherrited" ioctls that apply to all
|
||||
* disk-like devices otherwise pass it down to the previous handler
|
||||
*/
|
||||
|
||||
switch (cmd) {
|
||||
/*
|
||||
* At present there are none, but eventually there would be
|
||||
* something that returns the basic partition parameters.
|
||||
* Whether this would be in the form of a disklabel or
|
||||
* similar I have not yet decided.
|
||||
*/
|
||||
default:
|
||||
if (slice->handler_down->ioctl) {
|
||||
error = (*slice->handler_down->ioctl)
|
||||
(slice->private_down, cmd, data, flag, p);
|
||||
} else {
|
||||
error = ENOTTY;
|
||||
}
|
||||
if (error) {
|
||||
/*
|
||||
* If no disklabel was returned, let's make
|
||||
* up something that will satisfy the system's
|
||||
* need for a disklabel to mount an ffs on.
|
||||
* Don't overwrite error unless we get a dummy.
|
||||
* let the called routine decide
|
||||
* if it can handle any ioctl.
|
||||
*/
|
||||
if (dkl_dummy_ioctl(slice, cmd, data, flag, p) == 0) {
|
||||
error = 0;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* You also need read, write, open, close routines. This should get you
|
||||
* started.
|
||||
* The open MIGHT allow the caller to proceed if it is a READ
|
||||
* mode, and it is open at a higher layer.
|
||||
* All Accesses would have to be checked for READ
|
||||
* as the system doesn't enforce this at this time.
|
||||
*/
|
||||
static int
|
||||
slcdevopen(dev_t dev, int flags, int mode, struct proc * p)
|
||||
{
|
||||
sl_p slice = minor_to_slice(minor(dev));
|
||||
int error;
|
||||
|
||||
RR;
|
||||
if (slice == NULL)
|
||||
return (ENXIO);
|
||||
#if 1 /* the hack */
|
||||
if ((mode & S_IFMT) == S_IFBLK) {
|
||||
/*
|
||||
* XXX Because a mount -u does not re-open the device
|
||||
* The hack here, is to always open block devices
|
||||
* in full read/write mode. Eventually, if DEVFS
|
||||
* becomes ubiquitous, VOP to do a file upgrade
|
||||
* might be implemented. Other Filesystems need
|
||||
* not implement it..
|
||||
* THIS SHOULD BE DONE IN slice_device.c
|
||||
*/
|
||||
flags |= FWRITE;
|
||||
}
|
||||
#endif /* the hack */
|
||||
return (sliceopen(slice, flags, mode, p, SLW_DEVICE));
|
||||
}
|
||||
|
||||
static int
|
||||
slcdevclose(dev_t dev, int flags, int mode, struct proc * p)
|
||||
{
|
||||
sl_p slice = minor_to_slice(minor(dev));
|
||||
RR;
|
||||
#ifdef DIAGNOSTICX
|
||||
if ((flags & (FWRITE | FREAD)) != 0) {
|
||||
printf("sliceclose called with non 0 flags\n");
|
||||
}
|
||||
#endif
|
||||
/*
|
||||
* Close is just an open for non-read/nonwrite in this context.
|
||||
*/
|
||||
sliceopen(slice, 0, mode, p, SLW_DEVICE);
|
||||
return(0);
|
||||
}
|
||||
|
||||
static int
|
||||
slcdevsize(dev_t dev)
|
||||
{
|
||||
sl_p slice = minor_to_slice(minor(dev));
|
||||
|
||||
RR;
|
||||
if (slice == NULL)
|
||||
return (-1);
|
||||
|
||||
#if 0
|
||||
return (slice->limits.slicesize / slice->limits.blksize);
|
||||
#else
|
||||
return (slice->limits.slicesize / 512);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
slcdevread(dev_t dev, struct uio *uio, int ioflag)
|
||||
{
|
||||
return (physio(slcdevstrategy, NULL, dev, 1, minphys, uio));
|
||||
}
|
||||
|
||||
static int
|
||||
slcdevwrite(dev_t dev, struct uio *uio, int ioflag)
|
||||
{
|
||||
return (physio(slcdevstrategy, NULL, dev, 0, minphys, uio));
|
||||
}
|
||||
static dev_t cdevnum, bdevnum;
|
||||
/*
|
||||
* Read/write routine for a buffer. Finds the proper unit, range checks
|
||||
* arguments, and schedules the transfer. Does not wait for the transfer to
|
||||
* complete. Multi-page transfers are supported. All I/O requests must be a
|
||||
* multiple of a sector in length.
|
||||
*/
|
||||
void
|
||||
slcdevstrategy(struct buf * bp)
|
||||
{
|
||||
sl_p slice = minor_to_slice(minor(bp->b_dev));
|
||||
u_int64_t start, end;
|
||||
u_int32_t blksize;
|
||||
daddr_t blkno;
|
||||
int s;
|
||||
|
||||
RR;
|
||||
if (slice == NULL) {
|
||||
bp->b_error = ENXIO;
|
||||
goto bad;
|
||||
}
|
||||
blksize = slice->limits.blksize;
|
||||
/* Check we are going to be able to do this kind of transfer */
|
||||
/* Check the start point too if DEV_BSIZE != reallity */
|
||||
if (bp->b_blkno < 0) {
|
||||
Debugger("Slice code got negative blocknumber");
|
||||
bp->b_error = EINVAL;
|
||||
goto bad;
|
||||
}
|
||||
start = (u_int64_t)bp->b_blkno * DEV_BSIZE;
|
||||
if (blksize != DEV_BSIZE) {
|
||||
if ((start % blksize) != 0) {
|
||||
Debugger("slice: request not on block boundary.");
|
||||
bp->b_error = EINVAL;
|
||||
goto bad;
|
||||
}
|
||||
blkno = start / blksize;
|
||||
} else {
|
||||
blkno = bp->b_blkno;
|
||||
}
|
||||
|
||||
if ((bp->b_bcount % blksize) != 0) {
|
||||
printf("bcount = %d, blksize= %d(%d)\n",
|
||||
bp->b_bcount, blksize,
|
||||
slice->limits.blksize);
|
||||
Debugger("slice: request not multile of blocksize.");
|
||||
bp->b_error = EINVAL;
|
||||
goto bad;
|
||||
}
|
||||
/*
|
||||
* Do bounds checking, adjust transfer, and set b_pblkno.
|
||||
*/
|
||||
bp->b_pblkno = blkno;
|
||||
end = start + (u_int64_t)bp->b_bcount; /* first byte BEYOND the IO */
|
||||
|
||||
/*
|
||||
* Handle the cases near or beyond the end of the slice. Assumes IO
|
||||
* is < 2^63 bytes long. (pretty safe)
|
||||
*/
|
||||
if (end > slice->limits.slicesize) {
|
||||
int64_t size;
|
||||
size = slice->limits.slicesize - start;
|
||||
/*
|
||||
* if exactly on end of slice, return EOF
|
||||
*/
|
||||
if ((size == 0) && (bp->b_flags & B_READ)) {
|
||||
printf("slice: at end of slice.");
|
||||
bp->b_resid = bp->b_bcount;
|
||||
goto done;
|
||||
}
|
||||
if (size <= 0) {
|
||||
printf("slice: beyond end of slice.");
|
||||
bp->b_error = EINVAL;
|
||||
goto bad;
|
||||
}
|
||||
bp->b_bcount = size;
|
||||
}
|
||||
sliceio(slice, bp, SLW_DEVICE);
|
||||
return;
|
||||
|
||||
done:
|
||||
s = splbio();
|
||||
/* toss transfer, we're done early */
|
||||
biodone(bp);
|
||||
splx(s);
|
||||
return;
|
||||
bad:
|
||||
bp->b_flags |= B_ERROR;
|
||||
goto done;
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
slice_remove_device(sl_p slice)
|
||||
{
|
||||
/*
|
||||
* Remove the devfs entry, which revokes the vnode etc. XXX if
|
||||
* handler has madde more, we should tell it too. e.g. floppy driver
|
||||
* does this.
|
||||
*/
|
||||
RR;
|
||||
devfs_remove_dev(slice->devfs_btoken);
|
||||
devfs_remove_dev(slice->devfs_ctoken);
|
||||
|
||||
/*
|
||||
* Remove it from the hashtable.
|
||||
*/
|
||||
LIST_REMOVE(slice, hash_list);
|
||||
}
|
||||
|
||||
static int
|
||||
slcdevdump(dev_t dev)
|
||||
{
|
||||
sl_p slice = minor_to_slice(minor(dev));
|
||||
static int slcdoingdump = 0;
|
||||
int32_t num, nblocks, lo;
|
||||
RR;
|
||||
if (!slice || !(slice->flags & SLF_OPEN_DEV_WR) ||
|
||||
!slice->handler_down->dump)
|
||||
return (ENXIO);
|
||||
|
||||
/* Toss any characters present prior to dump. */
|
||||
while (cncheckc() != -1)
|
||||
;
|
||||
|
||||
if (slcdoingdump)
|
||||
return (EFAULT);
|
||||
|
||||
num = (int32_t)(Maxmem * PAGE_SIZE / slice->limits.blksize);
|
||||
nblocks = (int32_t)(slice->limits.slicesize / slice->limits.blksize);
|
||||
lo = dumplo * DEV_BSIZE / slice->limits.blksize;
|
||||
if (lo < 0 || lo + num > nblocks)
|
||||
return (EINVAL);
|
||||
|
||||
slcdoingdump = 1;
|
||||
return (*slice->handler_down->dump)(slice->private_down, lo, num);
|
||||
}
|
@ -1,124 +0,0 @@
|
||||
Original notes on how this might be implememented.. may not reflect
|
||||
the final code very much.
|
||||
======================================================[JRE]
|
||||
|
||||
the slices are 'kinda' stackable..
|
||||
With alternating layers of handler(driver)/slice/handler/slice/handler/slice
|
||||
The "Slice" is a common structure shared between three pieces of code.
|
||||
1/ the lower handler
|
||||
2/ the upper handler
|
||||
3/ the generic slice code, which implements the device nodes etc.
|
||||
Each of these 3 items share a knowledge of the internal struture and
|
||||
contents of the slice structure. they also know each other's published
|
||||
interfaces.
|
||||
|
||||
Each layer is much like the previous..
|
||||
Each layer has similar characteristics..
|
||||
The slices are created bottom up..
|
||||
i.e. the device probes, and creates a static 'slice' that is
|
||||
assiciated with the device.. The static slice
|
||||
can't be altered, unless the media is changed..
|
||||
|
||||
A translation method, which might be NULL, in which case
|
||||
it is a simple case of offset addition.
|
||||
Possibly the offset might be already added..
|
||||
possibly this might be achieved by specifying a default method set.
|
||||
|
||||
Each disk slice has a structure associated with it..
|
||||
When a slice is 'loaded' there must be some way of deciding if it has
|
||||
a subslice structure. if it does, then that structure must
|
||||
be loaded to create mode slices..
|
||||
this is recursive.
|
||||
|
||||
The structuring must be such that it can recognise an attempt to change
|
||||
higer level structuring..
|
||||
This suggests a recursive 'open' count.. for open subslices.
|
||||
|
||||
The idea would be to pass the following operations through methods.
|
||||
|
||||
translation to (possibly more than one) io operation
|
||||
open count passing..
|
||||
interpretation of subslicing and other slicing operations.
|
||||
possibly there might be permissions inherritance.
|
||||
open a slice...
|
||||
create a slice.. methods are supplied by the disk driver..
|
||||
|
||||
upward methods:
|
||||
force close
|
||||
|
||||
identify slice type.. slice type modules each asked
|
||||
to identify..
|
||||
|
||||
to do IO
|
||||
|
||||
1/ find apropriate slice (hash)
|
||||
LIST_HEAD(slice_bucket, slice) hash_table[UNIT_HASH_SIZE - 1];
|
||||
|
||||
in the init,
|
||||
for ( i = 0; i < UNIT_HASH_SIZE; i++) {
|
||||
LIST_INIT(hash_table + i)
|
||||
}
|
||||
|
||||
struct slice *minor_to_slice(unsigned int minor)
|
||||
{
|
||||
int hash = minor % UNIT_HASH_SIZE;
|
||||
struct slice *slice;
|
||||
|
||||
slice = (hash_table + hash)->lh_first;
|
||||
while (slice) {
|
||||
if (slice->minor == minor) {
|
||||
return (slice);
|
||||
}
|
||||
slice = slice->hashlist.le_next
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
2/
|
||||
if IO method,
|
||||
do IO method..
|
||||
return
|
||||
check bounds
|
||||
adjust offset
|
||||
follow slice-parent link and loop to top
|
||||
IO methods are supplied by drivers
|
||||
drivers including concatination drivers etc.
|
||||
|
||||
concatination must be seen as a slice type
|
||||
|
||||
once all parts of a concatinated slice are created, then
|
||||
the new 'concatinated slice' appears in the devfs.
|
||||
a concatinated slice has a 'label' that identifies it's volume
|
||||
and it's part (e.g. part 3 out of 5)
|
||||
'slice's in ram are either Primary or slave slices in a concatinated slice..
|
||||
|
||||
|
||||
to set up a slice call slice_add() which:
|
||||
1/ If (slice type not known)
|
||||
Identify the type (call all type probe routines in turn)
|
||||
2/ call the succeeding type attach routine
|
||||
3/ the attach routine calls slice_add() for each sub slice
|
||||
The probe and attach may merge.
|
||||
|
||||
|
||||
the type of a slice must be detirmined taking into account the type of the
|
||||
parent slice.. It is conceivable that the parent slice
|
||||
might TELL the slice_add() routine what to make the slice..
|
||||
Possibly the parent set's a CONTEXT which might be helpful
|
||||
in identifying a slice
|
||||
|
||||
|
||||
disk:
|
||||
set up Method struct:
|
||||
IO points to disk strategy
|
||||
set size to whole disk
|
||||
set offset to 0
|
||||
set context to RAW
|
||||
call slice_add
|
||||
|
||||
|
||||
slice_add()
|
||||
called when we know about a slice..possibly we should fill out a slice
|
||||
struct before calling it.
|
||||
The slice struct is all that is needed to be able to do IO
|
||||
to the slice. slice_add, will then link the slice into
|
||||
the system as needed.
|
326
sys/dev/vn/vn.c
326
sys/dev/vn/vn.c
@ -38,7 +38,7 @@
|
||||
* from: Utah Hdr: vn.c 1.13 94/04/02
|
||||
*
|
||||
* from: @(#)vn.c 8.6 (Berkeley) 4/1/94
|
||||
* $Id: vn.c,v 1.69 1998/08/23 20:16:28 phk Exp $
|
||||
* $Id: vn.c,v 1.70 1998/09/12 18:46:06 sos Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -84,10 +84,6 @@
|
||||
#include <sys/diskslice.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/conf.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#endif /*DEVFS*/
|
||||
@ -95,7 +91,6 @@
|
||||
#include <sys/vnioctl.h>
|
||||
|
||||
static d_ioctl_t vnioctl;
|
||||
#ifndef SLICE
|
||||
static d_open_t vnopen;
|
||||
static d_read_t vnread;
|
||||
static d_write_t vnwrite;
|
||||
@ -115,31 +110,6 @@ static struct cdevsw vn_cdevsw = {
|
||||
NULL, -1, vndump, vnsize,
|
||||
D_DISK|D_NOCLUSTERRW, 0, -1 };
|
||||
|
||||
#else /* SLICE */
|
||||
|
||||
static sl_h_IO_req_t nvsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t nvsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t nvsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t nvsclose; */ /* downwards travelling close */
|
||||
static sl_h_dump_t nvsdump; /* core dump req downward */
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"vn",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&nvsIOreq,
|
||||
&nvsioctl,
|
||||
&nvsopen,
|
||||
/*&nvsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
&nvsdump
|
||||
};
|
||||
#endif
|
||||
|
||||
#define vnunit(dev) dkunit(dev)
|
||||
|
||||
@ -152,14 +122,7 @@ static struct slice_handler slicetype = {
|
||||
struct vn_softc {
|
||||
int sc_flags; /* flags */
|
||||
size_t sc_size; /* size of vn */
|
||||
#ifdef SLICE
|
||||
struct slice *slice;
|
||||
struct slicelimits limit;
|
||||
int mynor;
|
||||
int unit;
|
||||
#else
|
||||
struct diskslices *sc_slices;
|
||||
#endif /* SLICE */
|
||||
struct vnode *sc_vp; /* vnode */
|
||||
struct ucred *sc_cred; /* credentials */
|
||||
int sc_maxactive; /* max # of active requests */
|
||||
@ -184,7 +147,6 @@ static int vnsetcred (struct vn_softc *vn, struct ucred *cred);
|
||||
static void vnshutdown (int, void *);
|
||||
static void vnclear (struct vn_softc *vn);
|
||||
|
||||
#ifndef SLICE
|
||||
static int
|
||||
vnclose(dev_t dev, int flags, int mode, struct proc *p)
|
||||
{
|
||||
@ -453,181 +415,6 @@ vnstrategy(struct buf *bp)
|
||||
}
|
||||
}
|
||||
|
||||
#else /* SLICE */
|
||||
static void
|
||||
nvsIOreq(void *private ,struct buf *bp)
|
||||
{
|
||||
struct vn_softc *vn = private;
|
||||
u_int32_t unit = vn->unit;
|
||||
register daddr_t bn;
|
||||
int error;
|
||||
int isvplocked = 0;
|
||||
long sz;
|
||||
struct uio auio;
|
||||
struct iovec aiov;
|
||||
|
||||
IFOPT(vn, VN_DEBUG)
|
||||
printf("vnstrategy(%p): unit %d\n", bp, unit);
|
||||
|
||||
if ((vn->sc_flags & VNF_INITED) == 0) {
|
||||
bp->b_error = ENXIO;
|
||||
bp->b_flags |= B_ERROR;
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
bn = bp->b_pblkno;
|
||||
bp->b_resid = bp->b_bcount;/* XXX best place to set this? */
|
||||
sz = howmany(bp->b_bcount, DEV_BSIZE);
|
||||
if (bn < 0 || bn + sz > vn->sc_size) {
|
||||
if (bn != vn->sc_size) {
|
||||
bp->b_error = EINVAL;
|
||||
bp->b_flags |= B_ERROR;
|
||||
}
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
|
||||
if( (bp->b_flags & B_PAGING) == 0) {
|
||||
aiov.iov_base = bp->b_data;
|
||||
aiov.iov_len = bp->b_bcount;
|
||||
auio.uio_iov = &aiov;
|
||||
auio.uio_iovcnt = 1;
|
||||
auio.uio_offset = dbtob(bn);
|
||||
auio.uio_segflg = UIO_SYSSPACE;
|
||||
if( bp->b_flags & B_READ)
|
||||
auio.uio_rw = UIO_READ;
|
||||
else
|
||||
auio.uio_rw = UIO_WRITE;
|
||||
auio.uio_resid = bp->b_bcount;
|
||||
auio.uio_procp = curproc;
|
||||
if (!VOP_ISLOCKED(vn->sc_vp)) {
|
||||
isvplocked = 1;
|
||||
vn_lock(vn->sc_vp, LK_EXCLUSIVE | LK_RETRY, curproc);
|
||||
}
|
||||
if( bp->b_flags & B_READ)
|
||||
error = VOP_READ(vn->sc_vp, &auio, 0, vn->sc_cred);
|
||||
else
|
||||
error = VOP_WRITE(vn->sc_vp, &auio, 0, vn->sc_cred);
|
||||
if (isvplocked) {
|
||||
VOP_UNLOCK(vn->sc_vp, 0, curproc);
|
||||
isvplocked = 0;
|
||||
}
|
||||
bp->b_resid = auio.uio_resid;
|
||||
|
||||
if( error )
|
||||
bp->b_flags |= B_ERROR;
|
||||
biodone(bp);
|
||||
} else {
|
||||
long bsize, resid;
|
||||
off_t byten;
|
||||
int flags;
|
||||
caddr_t addr;
|
||||
struct buf *nbp;
|
||||
|
||||
nbp = getvnbuf();
|
||||
bzero(nbp, sizeof(struct buf));
|
||||
LIST_INIT(&nbp->b_dep);
|
||||
byten = dbtob(bn);
|
||||
/* This is probably the only time this is RIGHT */
|
||||
bsize = vn->sc_vp->v_mount->mnt_stat.f_iosize;
|
||||
addr = bp->b_data;
|
||||
flags = bp->b_flags | B_CALL;
|
||||
for (resid = bp->b_resid; resid; ) {
|
||||
struct vnode *vp;
|
||||
daddr_t nbn;
|
||||
int off, s, nra;
|
||||
|
||||
nra = 0;
|
||||
if (!VOP_ISLOCKED(vn->sc_vp)) {
|
||||
isvplocked = 1;
|
||||
vn_lock(vn->sc_vp, LK_EXCLUSIVE | LK_RETRY, curproc);
|
||||
}
|
||||
error = VOP_BMAP(vn->sc_vp, (daddr_t)(byten / bsize),
|
||||
&vp, &nbn, &nra, NULL);
|
||||
if (isvplocked) {
|
||||
VOP_UNLOCK(vn->sc_vp, 0, curproc);
|
||||
isvplocked = 0;
|
||||
}
|
||||
if (error == 0 && nbn == -1)
|
||||
error = EIO;
|
||||
|
||||
IFOPT(vn, VN_DONTCLUSTER)
|
||||
nra = 0;
|
||||
|
||||
off = byten % bsize;
|
||||
if (off)
|
||||
sz = bsize - off;
|
||||
else
|
||||
sz = (1 + nra) * bsize;
|
||||
if (resid < sz)
|
||||
sz = resid;
|
||||
|
||||
if (error) {
|
||||
bp->b_resid -= (resid - sz);
|
||||
bp->b_flags |= B_ERROR;
|
||||
biodone(bp);
|
||||
putvnbuf(nbp);
|
||||
return;
|
||||
}
|
||||
|
||||
IFOPT(vn,VN_IO)
|
||||
printf(
|
||||
/* XXX no %qx in kernel. Synthesize it. */
|
||||
"vnstrategy: vp %p/%p bn 0x%lx%08lx/0x%lx sz 0x%lx\n",
|
||||
(void *)vn->sc_vp, (void *)vp,
|
||||
(u_long)(byten >> 32), (u_long)byten,
|
||||
(u_long)nbn, sz);
|
||||
|
||||
nbp->b_flags = flags;
|
||||
nbp->b_bcount = sz;
|
||||
nbp->b_bufsize = sz;
|
||||
nbp->b_error = 0;
|
||||
if (vp->v_type == VBLK || vp->v_type == VCHR)
|
||||
nbp->b_dev = vp->v_rdev;
|
||||
else
|
||||
nbp->b_dev = NODEV;
|
||||
nbp->b_data = addr;
|
||||
nbp->b_blkno = nbn + btodb(off);
|
||||
nbp->b_offset = dbtob(nbn) + off;
|
||||
nbp->b_proc = bp->b_proc;
|
||||
nbp->b_iodone = vniodone;
|
||||
nbp->b_vp = vp;
|
||||
nbp->b_rcred = vn->sc_cred; /* XXX crdup? */
|
||||
nbp->b_wcred = vn->sc_cred; /* XXX crdup? */
|
||||
nbp->b_dirtyoff = bp->b_dirtyoff;
|
||||
nbp->b_dirtyend = bp->b_dirtyend;
|
||||
nbp->b_validoff = bp->b_validoff;
|
||||
nbp->b_validend = bp->b_validend;
|
||||
|
||||
if ((nbp->b_flags & B_READ) == 0)
|
||||
nbp->b_vp->v_numoutput++;
|
||||
|
||||
VOP_STRATEGY(vp, nbp);
|
||||
|
||||
s = splbio();
|
||||
while ((nbp->b_flags & B_DONE) == 0) {
|
||||
nbp->b_flags |= B_WANTED;
|
||||
tsleep(nbp, PRIBIO, "vnwait", 0);
|
||||
}
|
||||
splx(s);
|
||||
|
||||
if( nbp->b_flags & B_ERROR) {
|
||||
bp->b_flags |= B_ERROR;
|
||||
bp->b_resid -= (resid - sz);
|
||||
biodone(bp);
|
||||
putvnbuf(nbp);
|
||||
return;
|
||||
}
|
||||
|
||||
byten += sz;
|
||||
addr += sz;
|
||||
resid -= sz;
|
||||
}
|
||||
biodone(bp);
|
||||
putvnbuf(nbp);
|
||||
}
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
void
|
||||
vniodone( struct buf *bp) {
|
||||
@ -645,9 +432,6 @@ vnioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
|
||||
struct nameidata nd;
|
||||
int error;
|
||||
u_long *f;
|
||||
#ifdef SLICE
|
||||
sh_p tp;
|
||||
#endif
|
||||
|
||||
IFOPT(vn,VN_FOLLOW)
|
||||
printf("vnioctl(0x%lx, 0x%lx, %p, 0x%x, %p): unit %d\n",
|
||||
@ -663,7 +447,6 @@ vnioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
|
||||
case VNIOCUCLEAR:
|
||||
goto vn_specific;
|
||||
}
|
||||
#ifndef SLICE
|
||||
|
||||
IFOPT(vn,VN_LABELS) {
|
||||
if (vn->sc_slices != NULL) {
|
||||
@ -678,7 +461,6 @@ vnioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
|
||||
return (ENOTTY);
|
||||
}
|
||||
|
||||
#endif
|
||||
vn_specific:
|
||||
|
||||
error = suser(p->p_ucred, &p->p_acflag);
|
||||
@ -718,26 +500,6 @@ vnioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
|
||||
}
|
||||
vio->vn_size = dbtob(vn->sc_size);
|
||||
vn->sc_flags |= VNF_INITED;
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* XXX The filesystem blocksize will say 1024
|
||||
* for a 8K filesystem. don't know yet how to deal with this,
|
||||
* so lie for now.. say 512.
|
||||
*/
|
||||
#if 0
|
||||
vn->limit.blksize = vn->sc_vp->v_mount->mnt_stat.f_bsize;
|
||||
#else
|
||||
vn->limit.blksize = DEV_BSIZE;
|
||||
#endif
|
||||
vn->slice->limits.blksize = vn->limit.blksize;
|
||||
vn->limit.slicesize = vattr.va_size;
|
||||
vn->slice->limits.slicesize = vattr.va_size;
|
||||
/*
|
||||
* We have a media to read/write.
|
||||
* Try identify it.
|
||||
*/
|
||||
slice_start_probe(vn->slice); /* this happens asynchronously */
|
||||
#else
|
||||
IFOPT(vn, VN_LABELS) {
|
||||
/*
|
||||
* Reopen so that `ds' knows which devices are open.
|
||||
@ -750,7 +512,6 @@ vnioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
|
||||
if (error)
|
||||
vnclear(vn);
|
||||
}
|
||||
#endif
|
||||
IFOPT(vn, VN_FOLLOW)
|
||||
printf("vnioctl: SET vp %p size %x\n",
|
||||
vn->sc_vp, vn->sc_size);
|
||||
@ -850,14 +611,8 @@ vnclear(struct vn_softc *vn)
|
||||
|
||||
IFOPT(vn, VN_FOLLOW)
|
||||
printf("vnclear(%p): vp=%p\n", vn, vp);
|
||||
#ifdef SLICE
|
||||
if (vn->slice->handler_up) {
|
||||
(*(vn->slice->handler_up->revoke)) (vn->slice->private_up);
|
||||
}
|
||||
#else /* SLICE */
|
||||
if (vn->sc_slices != NULL)
|
||||
dsgone(&vn->sc_slices);
|
||||
#endif
|
||||
vn->sc_flags &= ~VNF_INITED;
|
||||
if (vp == (struct vnode *)0)
|
||||
panic("vnclear: null vp");
|
||||
@ -868,7 +623,6 @@ vnclear(struct vn_softc *vn)
|
||||
vn->sc_size = 0;
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
static int
|
||||
vnsize(dev_t dev)
|
||||
{
|
||||
@ -887,7 +641,6 @@ vndump(dev_t dev)
|
||||
}
|
||||
|
||||
static vn_devsw_installed = 0;
|
||||
#endif /* !SLICE */
|
||||
|
||||
static void
|
||||
vn_drvinit(void *unused)
|
||||
@ -895,7 +648,6 @@ vn_drvinit(void *unused)
|
||||
#ifdef DEVFS
|
||||
int unit;
|
||||
#endif
|
||||
#ifndef SLICE
|
||||
if(!vn_devsw_installed ) {
|
||||
if (at_shutdown(&vnshutdown, NULL, SHUTDOWN_POST_SYNC)) {
|
||||
printf("vn: could not install shutdown hook\n");
|
||||
@ -925,84 +677,8 @@ vn_drvinit(void *unused)
|
||||
"vn%d", unit);
|
||||
}
|
||||
#endif
|
||||
#else /* SLICE */
|
||||
int mynor;
|
||||
int unit;
|
||||
struct vn_softc *vn;
|
||||
char namebuf[64];
|
||||
if (at_shutdown(&vnshutdown, NULL, SHUTDOWN_POST_SYNC)) {
|
||||
printf("vn: could not install shutdown hook\n");
|
||||
return;
|
||||
}
|
||||
for (unit = 0; unit < NVN; unit++) {
|
||||
vn = malloc(sizeof *vn, M_DEVBUF, M_NOWAIT);
|
||||
if (!vn)
|
||||
return;
|
||||
bzero(vn, sizeof *vn);
|
||||
vn_softc[unit] = vn;
|
||||
vn->unit = unit;
|
||||
sprintf(namebuf,"vn%d",vn->unit);
|
||||
vn->mynor = dkmakeminor(unit, WHOLE_DISK_SLICE,
|
||||
RAW_PART);
|
||||
vn->limit.blksize = DEV_BSIZE;
|
||||
vn->limit.slicesize = ((u_int64_t)vn->sc_size * DEV_BSIZE);
|
||||
sl_make_slice(&slicetype,
|
||||
vn,
|
||||
&vn->limit,
|
||||
&vn->slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
vn->slice->probeinfo.typespecific = NULL;
|
||||
vn->slice->probeinfo.type = NULL;
|
||||
}
|
||||
#endif /* SLICE */
|
||||
}
|
||||
|
||||
SYSINIT(vndev, SI_SUB_DRIVERS, SI_ORDER_ANY, vn_drvinit, NULL)
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static int
|
||||
nvsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct vn_softc *vn;
|
||||
|
||||
vn = private;
|
||||
|
||||
IFOPT(vn, VN_FOLLOW)
|
||||
printf("vnopen(0x%lx, 0x%x, 0x%x, %p)\n",
|
||||
makedev(0,vn->mynor) , flags, mode, p);
|
||||
return (0);
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
nvsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct vn_softc *vn;
|
||||
|
||||
vn = private;
|
||||
IFOPT(vn, VN_FOLLOW)
|
||||
printf("vnclose(0x%lx, 0x%x, 0x%x, %p)\n",
|
||||
makedev(0,vn->mynor) , flags, mode, p);
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int
|
||||
nvsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
struct vn_softc *vn;
|
||||
|
||||
vn = private;
|
||||
|
||||
return(vnioctl(makedev(0,vn->mynor), cmd, addr, flag, p));
|
||||
}
|
||||
|
||||
static int
|
||||
nvsdump(void *private, int32_t blkoff, int32_t blkcnt)
|
||||
{
|
||||
return (ENODEV);
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
@ -36,7 +36,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)cd9660_vfsops.c 8.18 (Berkeley) 5/22/95
|
||||
* $Id: cd9660_vfsops.c,v 1.42 1998/09/07 07:20:30 guido Exp $
|
||||
* $Id: cd9660_vfsops.c,v 1.43 1998/09/07 13:17:00 bde Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
@ -143,10 +143,6 @@ iso_get_ssector(dev, p)
|
||||
|
||||
#ifndef VFS_LKM /* mount root makes no sense to an LKM */
|
||||
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
#ifdef SLICE
|
||||
extern struct vnode *root_device_vnode;
|
||||
#endif
|
||||
static int iso_mountroot __P((struct mount *mp, struct proc *p));
|
||||
|
||||
static int
|
||||
@ -157,18 +153,10 @@ iso_mountroot(mp, p)
|
||||
struct iso_args args;
|
||||
int error;
|
||||
|
||||
#ifdef SLICE
|
||||
rootvp = root_device_vnode;
|
||||
if (rootvp == NULL) {
|
||||
printf("cd9660_mountroot: rootvp not set");
|
||||
return (EINVAL);
|
||||
}
|
||||
#else
|
||||
if ((error = bdevvp(rootdev, &rootvp))) {
|
||||
printf("iso_mountroot: can't find rootvp");
|
||||
return (error);
|
||||
}
|
||||
#endif
|
||||
args.flags = ISOFSMNT_ROOT;
|
||||
args.ssector = iso_get_ssector(rootdev, p);
|
||||
if (bootverbose)
|
||||
|
@ -2,7 +2,7 @@
|
||||
# LINT -- config file for checking all the sources, tries to pull in
|
||||
# as much of the source tree as it can.
|
||||
#
|
||||
# $Id: LINT,v 1.461 1998/09/10 11:23:08 sos Exp $
|
||||
# $Id: LINT,v 1.462 1998/09/11 18:50:16 rvb Exp $
|
||||
#
|
||||
# NB: You probably don't want to try running a kernel built from this
|
||||
# file. Instead, you should start from GENERIC, and add options from
|
||||
@ -476,10 +476,7 @@ options UNION #Union filesystem
|
||||
options "CD9660_ROOT" #CD-ROM usable as root device
|
||||
options FFS_ROOT #FFS usable as root device
|
||||
options NFS_ROOT #NFS usable as root device
|
||||
# DEVFS and SLICE are experimental but work.
|
||||
# SLICE disables too much old code so enabling it in LINT would be bad
|
||||
options DEVFS #devices filesystem
|
||||
#options SLICE #devfs based disk handling
|
||||
|
||||
# Allow the FFS to use Softupdates technology.
|
||||
# To do this you need to copy the two files
|
||||
|
@ -2,7 +2,7 @@
|
||||
# LINT -- config file for checking all the sources, tries to pull in
|
||||
# as much of the source tree as it can.
|
||||
#
|
||||
# $Id: LINT,v 1.461 1998/09/10 11:23:08 sos Exp $
|
||||
# $Id: LINT,v 1.462 1998/09/11 18:50:16 rvb Exp $
|
||||
#
|
||||
# NB: You probably don't want to try running a kernel built from this
|
||||
# file. Instead, you should start from GENERIC, and add options from
|
||||
@ -476,10 +476,7 @@ options UNION #Union filesystem
|
||||
options "CD9660_ROOT" #CD-ROM usable as root device
|
||||
options FFS_ROOT #FFS usable as root device
|
||||
options NFS_ROOT #NFS usable as root device
|
||||
# DEVFS and SLICE are experimental but work.
|
||||
# SLICE disables too much old code so enabling it in LINT would be bad
|
||||
options DEVFS #devices filesystem
|
||||
#options SLICE #devfs based disk handling
|
||||
|
||||
# Allow the FFS to use Softupdates technology.
|
||||
# To do this you need to copy the two files
|
||||
|
@ -34,7 +34,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)autoconf.c 7.1 (Berkeley) 5/9/91
|
||||
* $Id: autoconf.c,v 1.103 1998/08/23 14:17:52 des Exp $
|
||||
* $Id: autoconf.c,v 1.104 1998/09/03 20:59:28 nsouch Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -45,7 +45,6 @@
|
||||
* devices are determined (from possibilities mentioned in ioconf.c),
|
||||
* and the drivers are initialized.
|
||||
*/
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
#include "opt_bootp.h"
|
||||
#include "opt_ffs.h"
|
||||
#include "opt_cd9660.h"
|
||||
@ -111,7 +110,6 @@ SYSINIT(configure, SI_SUB_CONFIGURE, SI_ORDER_FIRST, configure, NULL)
|
||||
static void configure_finish __P((void));
|
||||
static void configure_start __P((void));
|
||||
static int setdumpdev __P((dev_t dev));
|
||||
#ifndef SLICE
|
||||
static void setroot __P((void));
|
||||
|
||||
#ifdef CD9660
|
||||
@ -175,7 +173,6 @@ find_cdrom_root()
|
||||
return EINVAL;
|
||||
}
|
||||
#endif /* CD9660 */
|
||||
#endif /* !SLICE */
|
||||
|
||||
static void
|
||||
configure_start()
|
||||
@ -309,7 +306,6 @@ configure(dummy)
|
||||
cold = 0;
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
void
|
||||
cpu_rootconf()
|
||||
@ -388,7 +384,6 @@ cpu_rootconf()
|
||||
setconf();
|
||||
}
|
||||
|
||||
#endif /* !SLICE */
|
||||
|
||||
void
|
||||
cpu_dumpconf()
|
||||
@ -431,7 +426,6 @@ setdumpdev(dev)
|
||||
return (0);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
u_long bootdev = 0; /* not a dev_t - encoding is different */
|
||||
|
||||
@ -501,7 +495,6 @@ setroot()
|
||||
sprintf(rootdevnames[1], "%s%s", sname, partname);
|
||||
}
|
||||
|
||||
#endif /* !SLICE */
|
||||
|
||||
static int
|
||||
sysctl_kern_dumpdev SYSCTL_HANDLER_ARGS
|
||||
|
@ -43,7 +43,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)fd.c 7.4 (Berkeley) 5/25/91
|
||||
* $Id: fd.c,v 1.119 1998/07/18 03:15:33 bde Exp $
|
||||
* $Id: fd.c,v 1.120 1998/07/29 13:00:40 bde Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
@ -84,10 +84,6 @@
|
||||
#endif
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
|
||||
/* misuse a flag to identify format operation */
|
||||
@ -184,21 +180,8 @@ static struct fd_data {
|
||||
struct callout_handle toffhandle;
|
||||
struct callout_handle tohandle;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
int unit; /* as in fd0 */
|
||||
void *bdevs[MAXPARTITIONS];
|
||||
void *cdevs[MAXPARTITIONS];
|
||||
struct subdev{
|
||||
struct slice *slice;
|
||||
int minor;
|
||||
struct fd_data *drive;
|
||||
struct slicelimits limit;
|
||||
}subdevs[16];
|
||||
struct intr_config_hook ich;
|
||||
#else /* SLICE */
|
||||
void *bdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
void *cdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
} fd_data[NFD];
|
||||
|
||||
@ -244,9 +227,7 @@ static timeout_t fd_iotimeout;
|
||||
static timeout_t fd_pseudointr;
|
||||
static int fdstate(fdcu_t, fdc_p);
|
||||
static int retrier(fdcu_t);
|
||||
#ifndef SLICE
|
||||
static int fdformat(dev_t, struct fd_formb *, struct proc *);
|
||||
#endif
|
||||
|
||||
static int enable_fifo(fdc_p fdc);
|
||||
|
||||
@ -322,30 +303,6 @@ static struct cdevsw fd_cdevsw = {
|
||||
|
||||
static struct isa_device *fdcdevs[NFDC];
|
||||
|
||||
#ifdef SLICE
|
||||
static sl_h_IO_req_t fdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t fdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t fdsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t fdsclose; */ /* downwards travelling close */
|
||||
static void fdsinit(void *);
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"floppy",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&fdsIOreq,
|
||||
&fdsioctl,
|
||||
&fdsopen,
|
||||
/*&fdsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
NULL /* dump */
|
||||
};
|
||||
#endif /* SLICE */
|
||||
|
||||
static int
|
||||
fdc_err(fdcu_t fdcu, const char *s)
|
||||
@ -582,12 +539,8 @@ fdattach(struct isa_device *dev)
|
||||
struct isa_device *fdup;
|
||||
int ic_type = 0;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
char namebuf[64];
|
||||
#else
|
||||
int mynor;
|
||||
int typemynor;
|
||||
#endif /* SLICE */
|
||||
int typesize;
|
||||
#endif
|
||||
|
||||
@ -739,9 +692,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
|
||||
fd->track = FD_NO_TRACK;
|
||||
#ifdef SLICE
|
||||
fd->unit = fdu;
|
||||
#endif
|
||||
fd->fdc = fdc;
|
||||
fd->fdsu = fdsu;
|
||||
fd->options = 0;
|
||||
@ -781,29 +731,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
}
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d",fdu);
|
||||
fd->subdevs[0].minor = 0;
|
||||
fd->subdevs[0].drive = fd;
|
||||
fd->subdevs[0].limit.blksize =
|
||||
128 << (fd_types[fd->type - 1].secsize);
|
||||
fd->subdevs[0].limit.slicesize =
|
||||
fd_types[fd->type - 1].size
|
||||
* fd->subdevs[0].limit.blksize;
|
||||
fd->ft = fd_types + (fd->type - 1); /* default value */
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[0],
|
||||
&fd->subdevs[0].limit,
|
||||
&fd->subdevs[0].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[0].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[0].slice->probeinfo.type = NULL;
|
||||
|
||||
fd->ich.ich_func = fdsinit;
|
||||
fd->ich.ich_arg = &fd->subdevs[0];
|
||||
config_intrhook_establish(&fd->ich);
|
||||
#else /* SLICE */
|
||||
mynor = fdu << 6;
|
||||
fd->bdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_BLK,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
@ -811,7 +738,6 @@ fdattach(struct isa_device *dev)
|
||||
fd->cdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_CHR,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
"rfd%d", fdu);
|
||||
#endif /* SLICE */
|
||||
for (i = 1; i < 1 + NUMDENS; i++) {
|
||||
/*
|
||||
* XXX this and the lookup in Fdopen() should be
|
||||
@ -848,25 +774,6 @@ fdattach(struct isa_device *dev)
|
||||
typesize = 1480;
|
||||
if (typesize == 1722)
|
||||
typesize = 1720;
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d.%d",fdu,typesize);
|
||||
fd->subdevs[i].minor = i;
|
||||
fd->subdevs[i].drive = fd;
|
||||
fd->subdevs[i].limit.blksize =
|
||||
128 << (fd_types[i - 1].secsize);
|
||||
fd->subdevs[i].limit.slicesize =
|
||||
fd_types[i - 1].size
|
||||
* fd->subdevs[i].limit.blksize;
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[i],
|
||||
&fd->subdevs[i].limit,
|
||||
&fd->subdevs[i].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[i].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[i].slice->probeinfo.type = NO_SUBPART;
|
||||
}
|
||||
#else /* SLICE */
|
||||
typemynor = mynor | i;
|
||||
fd->bdevs[i] =
|
||||
devfs_add_devswf(&fd_cdevsw, typemynor, DV_BLK,
|
||||
@ -885,7 +792,6 @@ fdattach(struct isa_device *dev)
|
||||
devfs_link(fd->cdevs[0],
|
||||
"rfd%d%c", fdu, 'a' + i);
|
||||
}
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
#ifdef notyet
|
||||
if (dk_ndrive < DK_NDRIVE) {
|
||||
@ -905,19 +811,6 @@ fdattach(struct isa_device *dev)
|
||||
}
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static void
|
||||
fdsinit(void *arg)
|
||||
{
|
||||
struct subdev *sd = arg;
|
||||
sh_p tp;
|
||||
|
||||
slice_start_probe(sd->slice);
|
||||
config_intrhook_disestablish(&sd->drive->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/****************************************************************************/
|
||||
/* motor control stuff */
|
||||
@ -1317,48 +1210,6 @@ fdstrategy(struct buf *bp)
|
||||
biodone(bp);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
/****************************************************************************/
|
||||
/* fdsIOreq */
|
||||
/****************************************************************************/
|
||||
static void
|
||||
fdsIOreq(void *private ,struct buf *bp)
|
||||
{
|
||||
unsigned nblocks, blknum, cando;
|
||||
int s;
|
||||
fdcu_t fdcu;
|
||||
fdu_t fdu;
|
||||
fdc_p fdc;
|
||||
fd_p fd;
|
||||
size_t fdblk;
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
fdc = fd->fdc;
|
||||
fdcu = fdc->fdcu;
|
||||
|
||||
/* check for controller already busy with tape */
|
||||
if (fdc->flags & FDC_TAPE_BUSY) {
|
||||
bp->b_error = EBUSY;
|
||||
bp->b_flags |= B_ERROR;
|
||||
goto bad;
|
||||
}
|
||||
bp->b_driver1 = sd; /* squirrel away which device.. */
|
||||
bp->b_resid = 0;
|
||||
s = splbio();
|
||||
bufqdisksort(&fdc->head, bp);
|
||||
untimeout(fd_turnoff, (caddr_t)fdu, fd->toffhandle); /* a good idea */
|
||||
fdstart(fdcu);
|
||||
splx(s);
|
||||
return;
|
||||
|
||||
bad:
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/***************************************************************\
|
||||
* fdstart *
|
||||
@ -1477,14 +1328,8 @@ fdstate(fdcu_t fdcu, fdc_p fdc)
|
||||
TRACE1("[fdc%d IDLE]", fdcu);
|
||||
return(0);
|
||||
}
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(bp->b_dev));
|
||||
fd = fd_data + fdu;
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
if (fdc->fd && (fd != fdc->fd))
|
||||
{
|
||||
@ -1898,23 +1743,11 @@ retrier(fdcu)
|
||||
struct subdev *sd;
|
||||
fdc_p fdc = fdc_data + fdcu;
|
||||
register struct buf *bp;
|
||||
#ifdef SLICE
|
||||
struct fd_data *fd;
|
||||
int fdu;
|
||||
#endif
|
||||
|
||||
bp = bufq_first(&fdc->head);
|
||||
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
if(fd->options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#else
|
||||
if(fd_data[FDUNIT(minor(bp->b_dev))].options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#endif
|
||||
switch(fdc->retry)
|
||||
{
|
||||
case 0: case 1: case 2:
|
||||
@ -1931,10 +1764,6 @@ retrier(fdcu)
|
||||
default:
|
||||
fail:
|
||||
{
|
||||
#ifdef SLICE
|
||||
printf("fd%d: hard error, block %d ", fdu,
|
||||
fd->skip / DEV_BSIZE);
|
||||
#else
|
||||
dev_t sav_b_dev = bp->b_dev;
|
||||
/* Trick diskerr */
|
||||
bp->b_dev = makedev(major(bp->b_dev),
|
||||
@ -1943,7 +1772,6 @@ retrier(fdcu)
|
||||
fdc->fd->skip / DEV_BSIZE,
|
||||
(struct disklabel *)NULL);
|
||||
bp->b_dev = sav_b_dev;
|
||||
#endif /* !SLICE */
|
||||
if (fdc->flags & FDC_STAT_VALID)
|
||||
{
|
||||
printf(
|
||||
@ -1973,16 +1801,11 @@ retrier(fdcu)
|
||||
return(1);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdformat( struct subdev *sd, struct fd_formb *finfo, struct proc *p)
|
||||
#else /* !SLICE */
|
||||
static int
|
||||
fdformat(dev, finfo, p)
|
||||
dev_t dev;
|
||||
struct fd_formb *finfo;
|
||||
struct proc *p;
|
||||
#endif /* !SLICE */
|
||||
{
|
||||
fdu_t fdu;
|
||||
fd_p fd;
|
||||
@ -1991,13 +1814,8 @@ fdformat(dev, finfo, p)
|
||||
int rv = 0, s;
|
||||
size_t fdblk;
|
||||
|
||||
#ifdef SLICE
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(dev));
|
||||
fd = &fd_data[fdu];
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
/* set up a buffer header for fdstrategy() */
|
||||
@ -2023,13 +1841,8 @@ fdformat(dev, finfo, p)
|
||||
bp->b_data = (caddr_t)finfo;
|
||||
|
||||
/* now do the format */
|
||||
#ifdef SLICE
|
||||
bp->b_driver1 = sd;
|
||||
fdsIOreq(sd, bp);
|
||||
#else /* !SLICE */
|
||||
bp->b_dev = dev;
|
||||
fdstrategy(bp);
|
||||
#endif /* !SLICE */
|
||||
|
||||
/* ...and wait for it to complete */
|
||||
s = splbio();
|
||||
@ -2085,33 +1898,10 @@ fdioctl(dev, cmd, addr, flag, p)
|
||||
return ftioctl(dev, cmd, addr, flag, p);
|
||||
#endif
|
||||
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* if SLICE is defined then only ft accesses come here
|
||||
* so break the rest off to another function for SLICE access.
|
||||
*/
|
||||
return (ENOTTY);
|
||||
}
|
||||
|
||||
/*
|
||||
* Slice ioctls come here
|
||||
*/
|
||||
static int
|
||||
fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
struct subdev *sd = private;
|
||||
fd_p fd = sd->drive;
|
||||
fdu_t fdu = fd->unit;
|
||||
fdc_p fdc = fd->fdc;
|
||||
fdcu_t fdcu = fdc->fdcu;
|
||||
size_t fdblk;
|
||||
int error = 0;
|
||||
#endif /* SLICE */
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
#ifndef SLICE
|
||||
case DIOCGDINFO:
|
||||
bzero(buffer, sizeof (buffer));
|
||||
dl = (struct disklabel *)buffer;
|
||||
@ -2155,7 +1945,6 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
error = writedisklabel(dev, fdstrategy,
|
||||
(struct disklabel *)buffer);
|
||||
break;
|
||||
#endif /* !SLICE */
|
||||
case FD_FORM:
|
||||
if((flag & FWRITE) == 0)
|
||||
error = EBADF; /* must be opened for writing */
|
||||
@ -2163,11 +1952,7 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
FD_FORMAT_VERSION)
|
||||
error = EINVAL; /* wrong version of formatting prog */
|
||||
else
|
||||
#ifdef SLICE
|
||||
error = fdformat(sd, (struct fd_formb *)addr, p);
|
||||
#else
|
||||
error = fdformat(dev, (struct fd_formb *)addr, p);
|
||||
#endif
|
||||
break;
|
||||
|
||||
case FD_GTYPE: /* get drive type */
|
||||
@ -2211,35 +1996,6 @@ static void fd_drvinit(void *notused )
|
||||
SYSINIT(fddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,fd_drvinit,NULL)
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
if((flags & (FREAD|FWRITE)) != 0) {
|
||||
return(Fdopen(makedev(0,sd->minor), flags , mode, p));
|
||||
} else {
|
||||
return(fdclose(makedev(0,sd->minor), 0 , mode, p));
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
fdsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
fdclose(makedev(0,sd->minor), 0 , 0, p);
|
||||
return ;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -34,7 +34,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)wd.c 7.2 (Berkeley) 5/9/91
|
||||
* $Id: wd.c,v 1.173 1998/07/30 15:16:04 bde Exp $
|
||||
* $Id: wd.c,v 1.174 1998/08/23 20:16:34 phk Exp $
|
||||
*/
|
||||
|
||||
/* TODO:
|
||||
@ -80,14 +80,7 @@
|
||||
#include <sys/buf.h>
|
||||
#include <sys/malloc.h>
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <sys/fcntl.h>
|
||||
#include <sys/sliceio.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#else
|
||||
#include <sys/devfsext.h>
|
||||
#endif /*SLICE*/
|
||||
#endif /*DEVFS*/
|
||||
#include <machine/bootinfo.h>
|
||||
#include <machine/clock.h>
|
||||
@ -177,15 +170,8 @@ struct disk {
|
||||
u_int32_t dk_port; /* i/o port base */
|
||||
u_int32_t dk_altport; /* altstatus port base */
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
struct slice *slice;
|
||||
int minor;
|
||||
struct slicelimits limit;
|
||||
struct intr_config_hook ich;
|
||||
#else
|
||||
void *dk_bdev; /* devfs token for whole disk */
|
||||
void *dk_cdev; /* devfs token for raw whole disk */
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
u_long cfg_flags; /* configured characteristics */
|
||||
short dk_flags; /* drive characteristics found */
|
||||
@ -248,9 +234,7 @@ static void wderror(struct buf *bp, struct disk *du, char *mesg);
|
||||
static void wdflushirq(struct disk *du, int old_ipl);
|
||||
static int wdreset(struct disk *du);
|
||||
static void wdsleep(int ctrlr, char *wmesg);
|
||||
#ifndef SLICE
|
||||
static void wdstrategy1(struct buf *bp);
|
||||
#endif
|
||||
static timeout_t wdtimeout;
|
||||
static int wdunwedge(struct disk *du);
|
||||
static int wdwait(struct disk *du, u_char bits_wanted, int timeout);
|
||||
@ -259,34 +243,7 @@ struct isa_driver wdcdriver = {
|
||||
wdprobe, wdattach, "wdc",
|
||||
};
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static sl_h_IO_req_t wdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t wdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t wdsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t wdsclose; */ /* downwards travelling close */
|
||||
static sl_h_dump_t wddump; /* core dump req downward */
|
||||
static void wds_init(void*);
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"IDE",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&wdsIOreq,
|
||||
&wdsioctl,
|
||||
&wdsopen,
|
||||
/*&wdsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
&wddump
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
static d_open_t wdopen;
|
||||
static d_read_t wdread;
|
||||
@ -308,7 +265,6 @@ static struct cdevsw wd_cdevsw = {
|
||||
NULL, -1, wddump, wdsize,
|
||||
D_DISK, 0, -1 };
|
||||
|
||||
#endif /* !SLICE */
|
||||
|
||||
#ifdef CMD640
|
||||
static int atapictrlr;
|
||||
@ -457,7 +413,7 @@ wdprobe(struct isa_device *dvp)
|
||||
static int
|
||||
wdattach(struct isa_device *dvp)
|
||||
{
|
||||
#if defined(DEVFS) && ! defined(SLICE)
|
||||
#if defined(DEVFS)
|
||||
int mynor;
|
||||
#endif
|
||||
u_int unit, lunit;
|
||||
@ -538,12 +494,6 @@ wdattach(struct isa_device *dvp)
|
||||
if (du->cfg_flags & WDOPT_SLEEPHACK)
|
||||
printf(", sleep-hack");
|
||||
printf("\n");
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* Here we somehow schedule the geometry HACK fro later and print
|
||||
* something meaningful.
|
||||
*/
|
||||
#endif
|
||||
if (du->dk_params.wdp_heads == 0)
|
||||
printf("wd%d: size unknown, using %s values\n",
|
||||
lunit, du->dk_dd.d_secperunit > 17
|
||||
@ -578,35 +528,6 @@ wdattach(struct isa_device *dvp)
|
||||
wdtimeout(du);
|
||||
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
{
|
||||
char namebuf[64];
|
||||
sprintf(namebuf,"wd%d",lunit);
|
||||
du->minor = dkmakeminor(lunit,
|
||||
WHOLE_DISK_SLICE, RAW_PART);
|
||||
du->limit.blksize = du->dk_dd.d_secsize;
|
||||
du->limit.slicesize =
|
||||
(u_int64_t)du->dk_dd.d_secsize *
|
||||
du->dk_dd.d_secperunit;
|
||||
/*
|
||||
* Fill in the 3 geometry entries
|
||||
* to tell the mbr code
|
||||
* we already know it, so that it
|
||||
* doesn't try deduce it.
|
||||
*/
|
||||
sl_make_slice(&slicetype,
|
||||
du,
|
||||
&du->limit,
|
||||
&du->slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
du->slice->probeinfo.typespecific = NULL;
|
||||
du->slice->probeinfo.type = NULL;
|
||||
}
|
||||
du->ich.ich_func = wds_init;
|
||||
du->ich.ich_arg = du;
|
||||
config_intrhook_establish(&du->ich);
|
||||
#else
|
||||
mynor = dkmakeminor(lunit, WHOLE_DISK_SLICE, RAW_PART);
|
||||
du->dk_bdev = devfs_add_devswf(&wd_cdevsw, mynor,
|
||||
DV_BLK, UID_ROOT,
|
||||
@ -616,7 +537,6 @@ wdattach(struct isa_device *dvp)
|
||||
DV_CHR, UID_ROOT,
|
||||
GID_OPERATOR, 0640,
|
||||
"rwd%d", lunit);
|
||||
#endif
|
||||
#endif
|
||||
|
||||
if (dk_ndrive < DK_NDRIVE) {
|
||||
@ -673,50 +593,7 @@ next: ;
|
||||
return (1);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
extern struct proc *curproc;
|
||||
static void
|
||||
wds_init(void *arg)
|
||||
{
|
||||
struct disk *du = arg;
|
||||
sh_p tp;
|
||||
int err = 0;
|
||||
struct ide_geom geom;
|
||||
|
||||
if ((err = wdsopen(du, FREAD, 0, curproc))) {
|
||||
printf("wd open failed with %d", err);
|
||||
return;
|
||||
}
|
||||
/*
|
||||
* If we still don't have geometry,
|
||||
* Then call the IDE geometry HACK functions.
|
||||
*/
|
||||
#if 0
|
||||
if ( ?? ) { /* how do we know? */
|
||||
bzero (&geom, sizeof(geom));
|
||||
if (mbr_geom_hack(du->slice)) && (dkl_geom_hack(du->slice)) {
|
||||
printf("We really have no geometry\n");
|
||||
} else {
|
||||
du->dk_dd.d_secperunit = (geom.cyls *
|
||||
geom.trackpercyl * geom.secpertrack);
|
||||
du->dk_dd.d_ncylinders = geom.cyls;
|
||||
du->dk_dd.d_ntracks = geom.trackpercyl;
|
||||
du->dk_dd.d_nsectors = geom.secpertrack;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
slice_start_probe(du->slice);
|
||||
config_intrhook_disestablish(&du->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
#if 0
|
||||
wdsclose(du, 0, 0, curproc);
|
||||
#else
|
||||
wdsopen(du, 0, 0, curproc); /* open to 0 flags == close */
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
static int
|
||||
wdread(dev_t dev, struct uio *uio, int ioflag)
|
||||
@ -842,7 +719,6 @@ wdstrategy1(struct buf *bp)
|
||||
*/
|
||||
wdstrategy(bp);
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* Routine to queue a command to the controller. The unit's
|
||||
@ -935,13 +811,8 @@ wdstart(int ctrlr)
|
||||
}
|
||||
|
||||
/* obtain controller and drive information */
|
||||
#ifdef SLICE
|
||||
du = bp->b_driver1;
|
||||
lunit = du->dk_lunit;
|
||||
#else /* !SLICE */
|
||||
lunit = dkunit(bp->b_dev);
|
||||
du = wddrives[lunit];
|
||||
#endif /* !SLICE */
|
||||
|
||||
/* if not really a transfer, do control operations specially */
|
||||
if (du->dk_state < OPEN) {
|
||||
@ -981,7 +852,6 @@ wdstart(int ctrlr)
|
||||
du->dk_flags |= DKFL_SINGLE;
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
if (du->dk_flags & DKFL_SINGLE
|
||||
&& dsgetbad(bp->b_dev, du->dk_slices) != NULL) {
|
||||
/* XXX */
|
||||
@ -991,12 +861,6 @@ wdstart(int ctrlr)
|
||||
blknum = transbad144(dsgetbad(bp->b_dev, du->dk_slices),
|
||||
blknum - ds_offset) + ds_offset;
|
||||
}
|
||||
#else
|
||||
if (du->dk_flags & DKFL_SINGLE && du->slice->handler_up) {
|
||||
(void) (*du->slice->handler_up->upconf)(du->slice,
|
||||
SLCIOCTRANSBAD, (caddr_t)&blknum, 0, 0);
|
||||
}
|
||||
#endif
|
||||
|
||||
wdtab[ctrlr].b_active = 1; /* mark controller active */
|
||||
|
||||
@ -1243,11 +1107,7 @@ wdintr(int unit)
|
||||
}
|
||||
#endif
|
||||
bp = bufq_first(&wdtab[unit].controller_queue);
|
||||
#ifdef SLICE
|
||||
du = bp->b_driver1;
|
||||
#else /* !SLICE */
|
||||
du = wddrives[dkunit(bp->b_dev)];
|
||||
#endif /* !SLICE */
|
||||
|
||||
/* finish off DMA */
|
||||
if (du->dk_flags & (DKFL_DMA|DKFL_USEDMA)) {
|
||||
@ -1454,7 +1314,6 @@ done: ;
|
||||
wdstart(unit);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
/*
|
||||
* Initialize a drive.
|
||||
*/
|
||||
@ -1631,7 +1490,6 @@ wdopen(dev_t dev, int flags, int fmt, struct proc *p)
|
||||
return (0);
|
||||
#endif
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* Implement operations other than read/write.
|
||||
@ -1645,11 +1503,7 @@ wdcontrol(register struct buf *bp)
|
||||
register struct disk *du;
|
||||
int ctrlr;
|
||||
|
||||
#ifdef SLICE
|
||||
du = bp->b_driver1;
|
||||
#else /* !SLICE */
|
||||
du = wddrives[dkunit(bp->b_dev)];
|
||||
#endif /* !SLICE */
|
||||
#ifdef CMD640
|
||||
ctrlr = du->dk_ctrlr_cmd640;
|
||||
#else
|
||||
@ -2136,7 +1990,6 @@ wdgetctlr(struct disk *du)
|
||||
return (0);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
int
|
||||
wdclose(dev_t dev, int flags, int fmt, struct proc *p)
|
||||
{
|
||||
@ -2158,12 +2011,10 @@ wdioctl(dev_t dev, u_long cmd, caddr_t addr, int flags, struct proc *p)
|
||||
|
||||
du = wddrives[lunit];
|
||||
wdsleep(du->dk_ctrlr, "wdioct");
|
||||
#ifndef SLICE
|
||||
error = dsioctl("wd", dev, cmd, addr, flags, &du->dk_slices,
|
||||
wdstrategy1, (ds_setgeom_t *)NULL);
|
||||
if (error != ENOIOCTL)
|
||||
return (error);
|
||||
#endif /* SLICE */
|
||||
switch (cmd) {
|
||||
case DIOCSBADSCAN:
|
||||
if (*(int *)addr)
|
||||
@ -2226,18 +2077,11 @@ wdsize(dev_t dev)
|
||||
return (-1);
|
||||
return (dssize(dev, &du->dk_slices, wdopen, wdclose));
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
#ifndef SLICE
|
||||
int
|
||||
wddump(dev_t dev)
|
||||
#else
|
||||
static int
|
||||
wddump(void *private, int32_t start, int32_t num)
|
||||
#endif /* SLICE */
|
||||
{
|
||||
register struct disk *du;
|
||||
#ifndef SLICE
|
||||
struct disklabel *lp;
|
||||
long num; /* number of sectors to write */
|
||||
int lunit, part;
|
||||
@ -2246,14 +2090,10 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
u_long ds_offset;
|
||||
u_long nblocks;
|
||||
static int wddoingadump = 0;
|
||||
#else
|
||||
long blknum, blkchk, blkcnt, blknext;
|
||||
#endif /* SLICE */
|
||||
long cylin, head, sector;
|
||||
long secpertrk, secpercyl;
|
||||
char *addr;
|
||||
|
||||
#ifndef SLICE
|
||||
/* Toss any characters present prior to dump. */
|
||||
while (cncheckc() != -1)
|
||||
;
|
||||
@ -2297,14 +2137,6 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
wdtab[du->dk_ctrlr].b_active = 1;
|
||||
#endif
|
||||
wddoingadump = 1;
|
||||
#else
|
||||
du = private;
|
||||
if (du->dk_state < OPEN)
|
||||
return (ENXIO);
|
||||
|
||||
secpertrk = du->dk_dd.d_nsectors;
|
||||
secpercyl = du->dk_dd.d_secpercyl;
|
||||
#endif /* SLICE */
|
||||
|
||||
/* Recalibrate the drive. */
|
||||
DELAY(5); /* ATA spec XXX NOT */
|
||||
@ -2317,11 +2149,7 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
|
||||
du->dk_flags |= DKFL_SINGLE;
|
||||
addr = (char *) 0;
|
||||
#ifndef SLICE
|
||||
blknum = dumplo + blkoff;
|
||||
#else
|
||||
blknum = start;
|
||||
#endif /* SLICE */
|
||||
while (num > 0) {
|
||||
blkcnt = num;
|
||||
if (blkcnt > MAXTRANSFER)
|
||||
@ -2338,20 +2166,12 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
* sector is bad, then reduce reduce the transfer to
|
||||
* avoid any bad sectors.
|
||||
*/
|
||||
#ifndef SLICE
|
||||
if (du->dk_flags & DKFL_SINGLE
|
||||
&& dsgetbad(dev, du->dk_slices) != NULL) {
|
||||
for (blkchk = blknum; blkchk < blknum + blkcnt; blkchk++) {
|
||||
daddr_t blknew;
|
||||
blknew = transbad144(dsgetbad(dev, du->dk_slices),
|
||||
blkchk - ds_offset) + ds_offset;
|
||||
#else
|
||||
if (du->dk_flags & DKFL_SINGLE && du->slice->handler_up) {
|
||||
for (blkchk = blknum; blkchk < blknum + blkcnt; blkchk++) {
|
||||
daddr_t blknew = blkchk;
|
||||
(void) (*du->slice->handler_up->upconf)(du->slice,
|
||||
SLCIOCTRANSBAD, (caddr_t)&blknew, 0, 0);
|
||||
#endif /* SLICE */
|
||||
if (blknew != blkchk) {
|
||||
/* Found bad block. */
|
||||
blkcnt = blkchk - blknum;
|
||||
@ -2459,15 +2279,11 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
static void
|
||||
wderror(struct buf *bp, struct disk *du, char *mesg)
|
||||
{
|
||||
#ifdef SLICE
|
||||
printf("wd%d: %s:\n", du->dk_lunit, mesg);
|
||||
#else /* !SLICE */
|
||||
if (bp == NULL)
|
||||
printf("wd%d: %s:\n", du->dk_lunit, mesg);
|
||||
else
|
||||
diskerr(bp, "wd", mesg, LOG_PRINTF, du->dk_skip,
|
||||
dsgetlabel(bp->b_dev, du->dk_slices));
|
||||
#endif /* !SLICE */
|
||||
printf("wd%d: status %b error %b\n", du->dk_lunit,
|
||||
du->dk_status, WDCS_BITS, du->dk_error, WDERR_BITS);
|
||||
}
|
||||
@ -2690,7 +2506,6 @@ wdwait(struct disk *du, u_char bits_wanted, int timeout)
|
||||
return (-1);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
static wd_devsw_installed = 0;
|
||||
|
||||
static void wd_drvinit(void *unused)
|
||||
@ -2705,134 +2520,7 @@ static void wd_drvinit(void *unused)
|
||||
}
|
||||
|
||||
SYSINIT(wddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,wd_drvinit,NULL)
|
||||
#endif /* !SLICE */
|
||||
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* Read/write routine for a buffer. Finds the proper unit, range checks
|
||||
* arguments, and schedules the transfer. Does not wait for the transfer
|
||||
* to complete. Multi-page transfers are supported. All I/O requests must
|
||||
* be a multiple of a sector in length.
|
||||
*/
|
||||
static void
|
||||
wdsIOreq(void *private, struct buf *bp)
|
||||
{
|
||||
struct disk *du = private;
|
||||
int s;
|
||||
int lunit = du->dk_lunit;
|
||||
|
||||
/* queue transfer on drive, activate drive and controller if idle */
|
||||
s = splbio();
|
||||
|
||||
bufqdisksort(&drive_queue[lunit], bp);
|
||||
|
||||
/*
|
||||
* Move the head of the drive queue to the controller queue.
|
||||
*/
|
||||
if (wdutab[lunit].b_active == 0)
|
||||
wdustart(du);
|
||||
|
||||
/*
|
||||
* Kick off the controller if there is anything for IT to do.
|
||||
*/
|
||||
#ifdef CMD640
|
||||
if (wdtab[du->dk_ctrlr_cmd640].b_active == 0)
|
||||
#else
|
||||
if (wdtab[du->dk_ctrlr].b_active == 0)
|
||||
#endif
|
||||
wdstart(du->dk_ctrlr); /* start controller */
|
||||
|
||||
splx(s);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialize a drive.
|
||||
*/
|
||||
static int
|
||||
wdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
register struct disk *du;
|
||||
int error = 0;
|
||||
|
||||
du = private;
|
||||
|
||||
if ((flags & (FREAD|FWRITE)) != 0) {
|
||||
/* Finish flushing IRQs left over from wdattach(). */
|
||||
#ifdef CMD640
|
||||
if (wdtab[du->dk_ctrlr_cmd640].b_active == 2)
|
||||
wdtab[du->dk_ctrlr_cmd640].b_active = 0;
|
||||
#else
|
||||
if (wdtab[du->dk_ctrlr].b_active == 2)
|
||||
wdtab[du->dk_ctrlr].b_active = 0;
|
||||
#endif
|
||||
|
||||
du->dk_state = OPEN;
|
||||
du->dk_flags &= ~DKFL_BADSCAN;
|
||||
} else {
|
||||
/* <luoqi@watermarkgroup.com> suggests I remove this */
|
||||
/* du->dk_state = CLOSED;*/
|
||||
/* du->dk_state = WANTOPEN; */ /* maybe this? */
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
wdsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
register struct disk *du;
|
||||
|
||||
du = private;
|
||||
du->dk_state = CLOSED;
|
||||
return;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
static int
|
||||
wdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
register struct disk *du = private;
|
||||
#ifdef notyet
|
||||
int error;
|
||||
#endif
|
||||
|
||||
wdsleep(du->dk_ctrlr, "wdioct");
|
||||
switch (cmd) {
|
||||
case DIOCSBADSCAN:
|
||||
if (*(int *)addr)
|
||||
du->dk_flags |= DKFL_BADSCAN;
|
||||
else
|
||||
du->dk_flags &= ~DKFL_BADSCAN;
|
||||
return (0);
|
||||
#ifdef notyet
|
||||
case DIOCWFORMAT:
|
||||
if (!(flag & FWRITE))
|
||||
return (EBADF);
|
||||
fop = (struct format_op *)addr;
|
||||
aiov.iov_base = fop->df_buf;
|
||||
aiov.iov_len = fop->df_count;
|
||||
auio.uio_iov = &aiov;
|
||||
auio.uio_iovcnt = 1;
|
||||
auio.uio_resid = fop->df_count;
|
||||
auio.uio_segflg = 0;
|
||||
auio.uio_offset = fop->df_startblk * du->dk_dd.d_secsize;
|
||||
#error /* XXX the 386BSD interface is different */
|
||||
error = physio(wdformat, &rwdbuf[lunit], 0, dev, B_WRITE,
|
||||
minphys, &auio);
|
||||
fop->df_count -= auio.uio_resid;
|
||||
fop->df_reg[0] = du->dk_status;
|
||||
fop->df_reg[1] = du->dk_error;
|
||||
return (error);
|
||||
#endif
|
||||
|
||||
default:
|
||||
return (ENOTTY);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* SLICE */
|
||||
#endif /* NWDC > 0 */
|
||||
|
246
sys/isa/fd.c
246
sys/isa/fd.c
@ -43,7 +43,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)fd.c 7.4 (Berkeley) 5/25/91
|
||||
* $Id: fd.c,v 1.119 1998/07/18 03:15:33 bde Exp $
|
||||
* $Id: fd.c,v 1.120 1998/07/29 13:00:40 bde Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
@ -84,10 +84,6 @@
|
||||
#endif
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
|
||||
/* misuse a flag to identify format operation */
|
||||
@ -184,21 +180,8 @@ static struct fd_data {
|
||||
struct callout_handle toffhandle;
|
||||
struct callout_handle tohandle;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
int unit; /* as in fd0 */
|
||||
void *bdevs[MAXPARTITIONS];
|
||||
void *cdevs[MAXPARTITIONS];
|
||||
struct subdev{
|
||||
struct slice *slice;
|
||||
int minor;
|
||||
struct fd_data *drive;
|
||||
struct slicelimits limit;
|
||||
}subdevs[16];
|
||||
struct intr_config_hook ich;
|
||||
#else /* SLICE */
|
||||
void *bdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
void *cdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
} fd_data[NFD];
|
||||
|
||||
@ -244,9 +227,7 @@ static timeout_t fd_iotimeout;
|
||||
static timeout_t fd_pseudointr;
|
||||
static int fdstate(fdcu_t, fdc_p);
|
||||
static int retrier(fdcu_t);
|
||||
#ifndef SLICE
|
||||
static int fdformat(dev_t, struct fd_formb *, struct proc *);
|
||||
#endif
|
||||
|
||||
static int enable_fifo(fdc_p fdc);
|
||||
|
||||
@ -322,30 +303,6 @@ static struct cdevsw fd_cdevsw = {
|
||||
|
||||
static struct isa_device *fdcdevs[NFDC];
|
||||
|
||||
#ifdef SLICE
|
||||
static sl_h_IO_req_t fdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t fdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t fdsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t fdsclose; */ /* downwards travelling close */
|
||||
static void fdsinit(void *);
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"floppy",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&fdsIOreq,
|
||||
&fdsioctl,
|
||||
&fdsopen,
|
||||
/*&fdsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
NULL /* dump */
|
||||
};
|
||||
#endif /* SLICE */
|
||||
|
||||
static int
|
||||
fdc_err(fdcu_t fdcu, const char *s)
|
||||
@ -582,12 +539,8 @@ fdattach(struct isa_device *dev)
|
||||
struct isa_device *fdup;
|
||||
int ic_type = 0;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
char namebuf[64];
|
||||
#else
|
||||
int mynor;
|
||||
int typemynor;
|
||||
#endif /* SLICE */
|
||||
int typesize;
|
||||
#endif
|
||||
|
||||
@ -739,9 +692,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
|
||||
fd->track = FD_NO_TRACK;
|
||||
#ifdef SLICE
|
||||
fd->unit = fdu;
|
||||
#endif
|
||||
fd->fdc = fdc;
|
||||
fd->fdsu = fdsu;
|
||||
fd->options = 0;
|
||||
@ -781,29 +731,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
}
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d",fdu);
|
||||
fd->subdevs[0].minor = 0;
|
||||
fd->subdevs[0].drive = fd;
|
||||
fd->subdevs[0].limit.blksize =
|
||||
128 << (fd_types[fd->type - 1].secsize);
|
||||
fd->subdevs[0].limit.slicesize =
|
||||
fd_types[fd->type - 1].size
|
||||
* fd->subdevs[0].limit.blksize;
|
||||
fd->ft = fd_types + (fd->type - 1); /* default value */
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[0],
|
||||
&fd->subdevs[0].limit,
|
||||
&fd->subdevs[0].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[0].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[0].slice->probeinfo.type = NULL;
|
||||
|
||||
fd->ich.ich_func = fdsinit;
|
||||
fd->ich.ich_arg = &fd->subdevs[0];
|
||||
config_intrhook_establish(&fd->ich);
|
||||
#else /* SLICE */
|
||||
mynor = fdu << 6;
|
||||
fd->bdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_BLK,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
@ -811,7 +738,6 @@ fdattach(struct isa_device *dev)
|
||||
fd->cdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_CHR,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
"rfd%d", fdu);
|
||||
#endif /* SLICE */
|
||||
for (i = 1; i < 1 + NUMDENS; i++) {
|
||||
/*
|
||||
* XXX this and the lookup in Fdopen() should be
|
||||
@ -848,25 +774,6 @@ fdattach(struct isa_device *dev)
|
||||
typesize = 1480;
|
||||
if (typesize == 1722)
|
||||
typesize = 1720;
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d.%d",fdu,typesize);
|
||||
fd->subdevs[i].minor = i;
|
||||
fd->subdevs[i].drive = fd;
|
||||
fd->subdevs[i].limit.blksize =
|
||||
128 << (fd_types[i - 1].secsize);
|
||||
fd->subdevs[i].limit.slicesize =
|
||||
fd_types[i - 1].size
|
||||
* fd->subdevs[i].limit.blksize;
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[i],
|
||||
&fd->subdevs[i].limit,
|
||||
&fd->subdevs[i].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[i].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[i].slice->probeinfo.type = NO_SUBPART;
|
||||
}
|
||||
#else /* SLICE */
|
||||
typemynor = mynor | i;
|
||||
fd->bdevs[i] =
|
||||
devfs_add_devswf(&fd_cdevsw, typemynor, DV_BLK,
|
||||
@ -885,7 +792,6 @@ fdattach(struct isa_device *dev)
|
||||
devfs_link(fd->cdevs[0],
|
||||
"rfd%d%c", fdu, 'a' + i);
|
||||
}
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
#ifdef notyet
|
||||
if (dk_ndrive < DK_NDRIVE) {
|
||||
@ -905,19 +811,6 @@ fdattach(struct isa_device *dev)
|
||||
}
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static void
|
||||
fdsinit(void *arg)
|
||||
{
|
||||
struct subdev *sd = arg;
|
||||
sh_p tp;
|
||||
|
||||
slice_start_probe(sd->slice);
|
||||
config_intrhook_disestablish(&sd->drive->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/****************************************************************************/
|
||||
/* motor control stuff */
|
||||
@ -1317,48 +1210,6 @@ fdstrategy(struct buf *bp)
|
||||
biodone(bp);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
/****************************************************************************/
|
||||
/* fdsIOreq */
|
||||
/****************************************************************************/
|
||||
static void
|
||||
fdsIOreq(void *private ,struct buf *bp)
|
||||
{
|
||||
unsigned nblocks, blknum, cando;
|
||||
int s;
|
||||
fdcu_t fdcu;
|
||||
fdu_t fdu;
|
||||
fdc_p fdc;
|
||||
fd_p fd;
|
||||
size_t fdblk;
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
fdc = fd->fdc;
|
||||
fdcu = fdc->fdcu;
|
||||
|
||||
/* check for controller already busy with tape */
|
||||
if (fdc->flags & FDC_TAPE_BUSY) {
|
||||
bp->b_error = EBUSY;
|
||||
bp->b_flags |= B_ERROR;
|
||||
goto bad;
|
||||
}
|
||||
bp->b_driver1 = sd; /* squirrel away which device.. */
|
||||
bp->b_resid = 0;
|
||||
s = splbio();
|
||||
bufqdisksort(&fdc->head, bp);
|
||||
untimeout(fd_turnoff, (caddr_t)fdu, fd->toffhandle); /* a good idea */
|
||||
fdstart(fdcu);
|
||||
splx(s);
|
||||
return;
|
||||
|
||||
bad:
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/***************************************************************\
|
||||
* fdstart *
|
||||
@ -1477,14 +1328,8 @@ fdstate(fdcu_t fdcu, fdc_p fdc)
|
||||
TRACE1("[fdc%d IDLE]", fdcu);
|
||||
return(0);
|
||||
}
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(bp->b_dev));
|
||||
fd = fd_data + fdu;
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
if (fdc->fd && (fd != fdc->fd))
|
||||
{
|
||||
@ -1898,23 +1743,11 @@ retrier(fdcu)
|
||||
struct subdev *sd;
|
||||
fdc_p fdc = fdc_data + fdcu;
|
||||
register struct buf *bp;
|
||||
#ifdef SLICE
|
||||
struct fd_data *fd;
|
||||
int fdu;
|
||||
#endif
|
||||
|
||||
bp = bufq_first(&fdc->head);
|
||||
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
if(fd->options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#else
|
||||
if(fd_data[FDUNIT(minor(bp->b_dev))].options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#endif
|
||||
switch(fdc->retry)
|
||||
{
|
||||
case 0: case 1: case 2:
|
||||
@ -1931,10 +1764,6 @@ retrier(fdcu)
|
||||
default:
|
||||
fail:
|
||||
{
|
||||
#ifdef SLICE
|
||||
printf("fd%d: hard error, block %d ", fdu,
|
||||
fd->skip / DEV_BSIZE);
|
||||
#else
|
||||
dev_t sav_b_dev = bp->b_dev;
|
||||
/* Trick diskerr */
|
||||
bp->b_dev = makedev(major(bp->b_dev),
|
||||
@ -1943,7 +1772,6 @@ retrier(fdcu)
|
||||
fdc->fd->skip / DEV_BSIZE,
|
||||
(struct disklabel *)NULL);
|
||||
bp->b_dev = sav_b_dev;
|
||||
#endif /* !SLICE */
|
||||
if (fdc->flags & FDC_STAT_VALID)
|
||||
{
|
||||
printf(
|
||||
@ -1973,16 +1801,11 @@ retrier(fdcu)
|
||||
return(1);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdformat( struct subdev *sd, struct fd_formb *finfo, struct proc *p)
|
||||
#else /* !SLICE */
|
||||
static int
|
||||
fdformat(dev, finfo, p)
|
||||
dev_t dev;
|
||||
struct fd_formb *finfo;
|
||||
struct proc *p;
|
||||
#endif /* !SLICE */
|
||||
{
|
||||
fdu_t fdu;
|
||||
fd_p fd;
|
||||
@ -1991,13 +1814,8 @@ fdformat(dev, finfo, p)
|
||||
int rv = 0, s;
|
||||
size_t fdblk;
|
||||
|
||||
#ifdef SLICE
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(dev));
|
||||
fd = &fd_data[fdu];
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
/* set up a buffer header for fdstrategy() */
|
||||
@ -2023,13 +1841,8 @@ fdformat(dev, finfo, p)
|
||||
bp->b_data = (caddr_t)finfo;
|
||||
|
||||
/* now do the format */
|
||||
#ifdef SLICE
|
||||
bp->b_driver1 = sd;
|
||||
fdsIOreq(sd, bp);
|
||||
#else /* !SLICE */
|
||||
bp->b_dev = dev;
|
||||
fdstrategy(bp);
|
||||
#endif /* !SLICE */
|
||||
|
||||
/* ...and wait for it to complete */
|
||||
s = splbio();
|
||||
@ -2085,33 +1898,10 @@ fdioctl(dev, cmd, addr, flag, p)
|
||||
return ftioctl(dev, cmd, addr, flag, p);
|
||||
#endif
|
||||
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* if SLICE is defined then only ft accesses come here
|
||||
* so break the rest off to another function for SLICE access.
|
||||
*/
|
||||
return (ENOTTY);
|
||||
}
|
||||
|
||||
/*
|
||||
* Slice ioctls come here
|
||||
*/
|
||||
static int
|
||||
fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
struct subdev *sd = private;
|
||||
fd_p fd = sd->drive;
|
||||
fdu_t fdu = fd->unit;
|
||||
fdc_p fdc = fd->fdc;
|
||||
fdcu_t fdcu = fdc->fdcu;
|
||||
size_t fdblk;
|
||||
int error = 0;
|
||||
#endif /* SLICE */
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
#ifndef SLICE
|
||||
case DIOCGDINFO:
|
||||
bzero(buffer, sizeof (buffer));
|
||||
dl = (struct disklabel *)buffer;
|
||||
@ -2155,7 +1945,6 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
error = writedisklabel(dev, fdstrategy,
|
||||
(struct disklabel *)buffer);
|
||||
break;
|
||||
#endif /* !SLICE */
|
||||
case FD_FORM:
|
||||
if((flag & FWRITE) == 0)
|
||||
error = EBADF; /* must be opened for writing */
|
||||
@ -2163,11 +1952,7 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
FD_FORMAT_VERSION)
|
||||
error = EINVAL; /* wrong version of formatting prog */
|
||||
else
|
||||
#ifdef SLICE
|
||||
error = fdformat(sd, (struct fd_formb *)addr, p);
|
||||
#else
|
||||
error = fdformat(dev, (struct fd_formb *)addr, p);
|
||||
#endif
|
||||
break;
|
||||
|
||||
case FD_GTYPE: /* get drive type */
|
||||
@ -2211,35 +1996,6 @@ static void fd_drvinit(void *notused )
|
||||
SYSINIT(fddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,fd_drvinit,NULL)
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
if((flags & (FREAD|FWRITE)) != 0) {
|
||||
return(Fdopen(makedev(0,sd->minor), flags , mode, p));
|
||||
} else {
|
||||
return(fdclose(makedev(0,sd->minor), 0 , mode, p));
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
fdsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
fdclose(makedev(0,sd->minor), 0 , 0, p);
|
||||
return ;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -36,7 +36,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)cd9660_vfsops.c 8.18 (Berkeley) 5/22/95
|
||||
* $Id: cd9660_vfsops.c,v 1.42 1998/09/07 07:20:30 guido Exp $
|
||||
* $Id: cd9660_vfsops.c,v 1.43 1998/09/07 13:17:00 bde Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
@ -143,10 +143,6 @@ iso_get_ssector(dev, p)
|
||||
|
||||
#ifndef VFS_LKM /* mount root makes no sense to an LKM */
|
||||
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
#ifdef SLICE
|
||||
extern struct vnode *root_device_vnode;
|
||||
#endif
|
||||
static int iso_mountroot __P((struct mount *mp, struct proc *p));
|
||||
|
||||
static int
|
||||
@ -157,18 +153,10 @@ iso_mountroot(mp, p)
|
||||
struct iso_args args;
|
||||
int error;
|
||||
|
||||
#ifdef SLICE
|
||||
rootvp = root_device_vnode;
|
||||
if (rootvp == NULL) {
|
||||
printf("cd9660_mountroot: rootvp not set");
|
||||
return (EINVAL);
|
||||
}
|
||||
#else
|
||||
if ((error = bdevvp(rootdev, &rootvp))) {
|
||||
printf("iso_mountroot: can't find rootvp");
|
||||
return (error);
|
||||
}
|
||||
#endif
|
||||
args.flags = ISOFSMNT_ROOT;
|
||||
args.ssector = iso_get_ssector(rootdev, p);
|
||||
if (bootverbose)
|
||||
|
@ -39,7 +39,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)init_main.c 8.9 (Berkeley) 1/21/94
|
||||
* $Id: init_main.c,v 1.94 1998/06/07 17:11:32 dfr Exp $
|
||||
* $Id: init_main.c,v 1.95 1998/07/15 05:21:48 bde Exp $
|
||||
*/
|
||||
|
||||
#include "opt_devfs.h"
|
||||
@ -585,11 +585,6 @@ start_init(p)
|
||||
(void)subyte(--ucp, 'C');
|
||||
options = 1;
|
||||
#endif
|
||||
|
||||
#if defined(DEVFS) && defined(SLICE)
|
||||
(void)subyte(--ucp, 'd');
|
||||
options = 1;
|
||||
#endif
|
||||
if (options == 0)
|
||||
(void)subyte(--ucp, '-');
|
||||
(void)subyte(--ucp, '-'); /* leading hyphen */
|
||||
|
@ -32,7 +32,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)vfs_conf.c 8.8 (Berkeley) 3/31/94
|
||||
* $Id: vfs_conf.c,v 1.24 1998/04/20 03:57:30 julian Exp $
|
||||
* $Id: vfs_conf.c,v 1.25 1998/06/09 12:52:33 bde Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -51,7 +51,6 @@
|
||||
* as an aid to conversion for kernel multithreading
|
||||
* on SMP reentrancy
|
||||
*/
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
#include "opt_bootp.h"
|
||||
|
||||
#include <sys/param.h> /* dev_t (types.h)*/
|
||||
@ -75,9 +74,6 @@ dev_t rootdevs[] = { NODEV, NODEV };
|
||||
char *rootdevnames[2];
|
||||
struct vnode *rootvnode;
|
||||
char *mountrootfsname;
|
||||
#ifdef SLICE
|
||||
char rootdevice[32];
|
||||
#endif
|
||||
#ifdef BOOTP
|
||||
extern void bootpc_init __P((void));
|
||||
#endif
|
||||
|
@ -36,7 +36,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)vfs_subr.c 8.31 (Berkeley) 5/26/95
|
||||
* $Id: vfs_subr.c,v 1.161 1998/08/29 13:13:10 bde Exp $
|
||||
* $Id: vfs_subr.c,v 1.162 1998/09/05 15:17:33 bde Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -1113,7 +1113,6 @@ reassignbuf(bp, newvp)
|
||||
splx(s);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
/*
|
||||
* Create a vnode for a block device.
|
||||
* Used for mounting the root file system.
|
||||
@ -1143,7 +1142,6 @@ bdevvp(dev, vpp)
|
||||
*vpp = vp;
|
||||
return (0);
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* Check to see if the new vnode represents a special device
|
||||
|
@ -32,7 +32,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)vfs_conf.c 8.8 (Berkeley) 3/31/94
|
||||
* $Id: vfs_conf.c,v 1.24 1998/04/20 03:57:30 julian Exp $
|
||||
* $Id: vfs_conf.c,v 1.25 1998/06/09 12:52:33 bde Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -51,7 +51,6 @@
|
||||
* as an aid to conversion for kernel multithreading
|
||||
* on SMP reentrancy
|
||||
*/
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
#include "opt_bootp.h"
|
||||
|
||||
#include <sys/param.h> /* dev_t (types.h)*/
|
||||
@ -75,9 +74,6 @@ dev_t rootdevs[] = { NODEV, NODEV };
|
||||
char *rootdevnames[2];
|
||||
struct vnode *rootvnode;
|
||||
char *mountrootfsname;
|
||||
#ifdef SLICE
|
||||
char rootdevice[32];
|
||||
#endif
|
||||
#ifdef BOOTP
|
||||
extern void bootpc_init __P((void));
|
||||
#endif
|
||||
|
@ -36,7 +36,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)vfs_subr.c 8.31 (Berkeley) 5/26/95
|
||||
* $Id: vfs_subr.c,v 1.161 1998/08/29 13:13:10 bde Exp $
|
||||
* $Id: vfs_subr.c,v 1.162 1998/09/05 15:17:33 bde Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
@ -1113,7 +1113,6 @@ reassignbuf(bp, newvp)
|
||||
splx(s);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
/*
|
||||
* Create a vnode for a block device.
|
||||
* Used for mounting the root file system.
|
||||
@ -1143,7 +1142,6 @@ bdevvp(dev, vpp)
|
||||
*vpp = vp;
|
||||
return (0);
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* Check to see if the new vnode represents a special device
|
||||
|
@ -43,7 +43,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)fd.c 7.4 (Berkeley) 5/25/91
|
||||
* $Id: fd.c,v 1.37 1998/07/19 15:03:49 kato Exp $
|
||||
* $Id: fd.c,v 1.38 1998/07/30 09:01:12 kato Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
@ -92,10 +92,6 @@
|
||||
#endif
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
|
||||
/* misuse a flag to identify format operation */
|
||||
@ -221,21 +217,8 @@ static struct fd_data {
|
||||
struct callout_handle toffhandle;
|
||||
struct callout_handle tohandle;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
int unit; /* as in fd0 */
|
||||
void *bdevs[MAXPARTITIONS];
|
||||
void *cdevs[MAXPARTITIONS];
|
||||
struct subdev{
|
||||
struct slice *slice;
|
||||
int minor;
|
||||
struct fd_data *drive;
|
||||
struct slicelimits limit;
|
||||
}subdevs[16];
|
||||
struct intr_config_hook ich;
|
||||
#else /* SLICE */
|
||||
void *bdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
void *cdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
#ifdef PC98
|
||||
int pc98_trans;
|
||||
@ -339,9 +322,7 @@ static timeout_t fd_iotimeout;
|
||||
static timeout_t fd_pseudointr;
|
||||
static int fdstate(fdcu_t, fdc_p);
|
||||
static int retrier(fdcu_t);
|
||||
#ifndef SLICE
|
||||
static int fdformat(dev_t, struct fd_formb *, struct proc *);
|
||||
#endif
|
||||
|
||||
static int enable_fifo(fdc_p fdc);
|
||||
|
||||
@ -417,30 +398,6 @@ static struct cdevsw fd_cdevsw = {
|
||||
|
||||
static struct isa_device *fdcdevs[NFDC];
|
||||
|
||||
#ifdef SLICE
|
||||
static sl_h_IO_req_t fdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t fdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t fdsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t fdsclose; */ /* downwards travelling close */
|
||||
static void fdsinit(void *);
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"floppy",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&fdsIOreq,
|
||||
&fdsioctl,
|
||||
&fdsopen,
|
||||
/*&fdsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
NULL /* dump */
|
||||
};
|
||||
#endif /* SLICE */
|
||||
|
||||
static int
|
||||
fdc_err(fdcu_t fdcu, const char *s)
|
||||
@ -765,12 +722,8 @@ fdattach(struct isa_device *dev)
|
||||
struct isa_device *fdup;
|
||||
int ic_type = 0;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
char namebuf[64];
|
||||
#else
|
||||
int mynor;
|
||||
int typemynor;
|
||||
#endif /* SLICE */
|
||||
int typesize;
|
||||
#endif
|
||||
|
||||
@ -979,9 +932,6 @@ fdattach(struct isa_device *dev)
|
||||
#endif
|
||||
|
||||
fd->track = FD_NO_TRACK;
|
||||
#ifdef SLICE
|
||||
fd->unit = fdu;
|
||||
#endif
|
||||
fd->fdc = fdc;
|
||||
fd->fdsu = fdsu;
|
||||
fd->options = 0;
|
||||
@ -1043,29 +993,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
}
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d",fdu);
|
||||
fd->subdevs[0].minor = 0;
|
||||
fd->subdevs[0].drive = fd;
|
||||
fd->subdevs[0].limit.blksize =
|
||||
128 << (fd_types[fd->type - 1].secsize);
|
||||
fd->subdevs[0].limit.slicesize =
|
||||
fd_types[fd->type - 1].size
|
||||
* fd->subdevs[0].limit.blksize;
|
||||
fd->ft = fd_types + (fd->type - 1); /* default value */
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[0],
|
||||
&fd->subdevs[0].limit,
|
||||
&fd->subdevs[0].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[0].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[0].slice->probeinfo.type = NULL;
|
||||
|
||||
fd->ich.ich_func = fdsinit;
|
||||
fd->ich.ich_arg = &fd->subdevs[0];
|
||||
config_intrhook_establish(&fd->ich);
|
||||
#else /* SLICE */
|
||||
mynor = fdu << 6;
|
||||
fd->bdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_BLK,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
@ -1073,7 +1000,6 @@ fdattach(struct isa_device *dev)
|
||||
fd->cdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_CHR,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
"rfd%d", fdu);
|
||||
#endif /* SLICE */
|
||||
for (i = 1; i < 1 + NUMDENS; i++) {
|
||||
/*
|
||||
* XXX this and the lookup in Fdopen() should be
|
||||
@ -1133,25 +1059,6 @@ fdattach(struct isa_device *dev)
|
||||
if (typesize == 1722)
|
||||
typesize = 1720;
|
||||
#endif
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d.%d",fdu,typesize);
|
||||
fd->subdevs[i].minor = i;
|
||||
fd->subdevs[i].drive = fd;
|
||||
fd->subdevs[i].limit.blksize =
|
||||
128 << (fd_types[i - 1].secsize);
|
||||
fd->subdevs[i].limit.slicesize =
|
||||
fd_types[i - 1].size
|
||||
* fd->subdevs[i].limit.blksize;
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[i],
|
||||
&fd->subdevs[i].limit,
|
||||
&fd->subdevs[i].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[i].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[i].slice->probeinfo.type = NO_SUBPART;
|
||||
}
|
||||
#else /* SLICE */
|
||||
typemynor = mynor | i;
|
||||
fd->bdevs[i] =
|
||||
devfs_add_devswf(&fd_cdevsw, typemynor, DV_BLK,
|
||||
@ -1170,7 +1077,6 @@ fdattach(struct isa_device *dev)
|
||||
devfs_link(fd->cdevs[0],
|
||||
"rfd%d%c", fdu, 'a' + i);
|
||||
}
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
#ifdef notyet
|
||||
if (dk_ndrive < DK_NDRIVE) {
|
||||
@ -1190,19 +1096,6 @@ fdattach(struct isa_device *dev)
|
||||
}
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static void
|
||||
fdsinit(void *arg)
|
||||
{
|
||||
struct subdev *sd = arg;
|
||||
sh_p tp;
|
||||
|
||||
slice_start_probe(sd->slice);
|
||||
config_intrhook_disestablish(&sd->drive->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/****************************************************************************/
|
||||
/* motor control stuff */
|
||||
@ -1647,48 +1540,6 @@ fdstrategy(struct buf *bp)
|
||||
biodone(bp);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
/****************************************************************************/
|
||||
/* fdsIOreq */
|
||||
/****************************************************************************/
|
||||
static void
|
||||
fdsIOreq(void *private ,struct buf *bp)
|
||||
{
|
||||
unsigned nblocks, blknum, cando;
|
||||
int s;
|
||||
fdcu_t fdcu;
|
||||
fdu_t fdu;
|
||||
fdc_p fdc;
|
||||
fd_p fd;
|
||||
size_t fdblk;
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
fdc = fd->fdc;
|
||||
fdcu = fdc->fdcu;
|
||||
|
||||
/* check for controller already busy with tape */
|
||||
if (fdc->flags & FDC_TAPE_BUSY) {
|
||||
bp->b_error = EBUSY;
|
||||
bp->b_flags |= B_ERROR;
|
||||
goto bad;
|
||||
}
|
||||
bp->b_driver1 = sd; /* squirrel away which device.. */
|
||||
bp->b_resid = 0;
|
||||
s = splbio();
|
||||
bufqdisksort(&fdc->head, bp);
|
||||
untimeout(fd_turnoff, (caddr_t)fdu, fd->toffhandle); /* a good idea */
|
||||
fdstart(fdcu);
|
||||
splx(s);
|
||||
return;
|
||||
|
||||
bad:
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/***************************************************************\
|
||||
* fdstart *
|
||||
@ -1807,14 +1658,8 @@ fdstate(fdcu_t fdcu, fdc_p fdc)
|
||||
TRACE1("[fdc%d IDLE]", fdcu);
|
||||
return(0);
|
||||
}
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(bp->b_dev));
|
||||
fd = fd_data + fdu;
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
if (fdc->fd && (fd != fdc->fd))
|
||||
{
|
||||
@ -2327,23 +2172,11 @@ retrier(fdcu)
|
||||
struct subdev *sd;
|
||||
fdc_p fdc = fdc_data + fdcu;
|
||||
register struct buf *bp;
|
||||
#ifdef SLICE
|
||||
struct fd_data *fd;
|
||||
int fdu;
|
||||
#endif
|
||||
|
||||
bp = bufq_first(&fdc->head);
|
||||
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
if(fd->options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#else
|
||||
if(fd_data[FDUNIT(minor(bp->b_dev))].options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#endif
|
||||
switch(fdc->retry)
|
||||
{
|
||||
case 0: case 1: case 2:
|
||||
@ -2360,10 +2193,6 @@ retrier(fdcu)
|
||||
default:
|
||||
fail:
|
||||
{
|
||||
#ifdef SLICE
|
||||
printf("fd%d: hard error, block %d ", fdu,
|
||||
fd->skip / DEV_BSIZE);
|
||||
#else
|
||||
dev_t sav_b_dev = bp->b_dev;
|
||||
/* Trick diskerr */
|
||||
bp->b_dev = makedev(major(bp->b_dev),
|
||||
@ -2372,7 +2201,6 @@ retrier(fdcu)
|
||||
fdc->fd->skip / DEV_BSIZE,
|
||||
(struct disklabel *)NULL);
|
||||
bp->b_dev = sav_b_dev;
|
||||
#endif /* !SLICE */
|
||||
if (fdc->flags & FDC_STAT_VALID)
|
||||
{
|
||||
printf(
|
||||
@ -2402,16 +2230,11 @@ retrier(fdcu)
|
||||
return(1);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdformat( struct subdev *sd, struct fd_formb *finfo, struct proc *p)
|
||||
#else /* !SLICE */
|
||||
static int
|
||||
fdformat(dev, finfo, p)
|
||||
dev_t dev;
|
||||
struct fd_formb *finfo;
|
||||
struct proc *p;
|
||||
#endif /* !SLICE */
|
||||
{
|
||||
fdu_t fdu;
|
||||
fd_p fd;
|
||||
@ -2420,13 +2243,8 @@ fdformat(dev, finfo, p)
|
||||
int rv = 0, s;
|
||||
size_t fdblk;
|
||||
|
||||
#ifdef SLICE
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(dev));
|
||||
fd = &fd_data[fdu];
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
/* set up a buffer header for fdstrategy() */
|
||||
@ -2452,13 +2270,8 @@ fdformat(dev, finfo, p)
|
||||
bp->b_data = (caddr_t)finfo;
|
||||
|
||||
/* now do the format */
|
||||
#ifdef SLICE
|
||||
bp->b_driver1 = sd;
|
||||
fdsIOreq(sd, bp);
|
||||
#else /* !SLICE */
|
||||
bp->b_dev = dev;
|
||||
fdstrategy(bp);
|
||||
#endif /* !SLICE */
|
||||
|
||||
/* ...and wait for it to complete */
|
||||
s = splbio();
|
||||
@ -2514,28 +2327,6 @@ fdioctl(dev, cmd, addr, flag, p)
|
||||
return ftioctl(dev, cmd, addr, flag, p);
|
||||
#endif
|
||||
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* if SLICE is defined then only ft accesses come here
|
||||
* so break the rest off to another function for SLICE access.
|
||||
*/
|
||||
return (ENOTTY);
|
||||
}
|
||||
|
||||
/*
|
||||
* Slice ioctls come here
|
||||
*/
|
||||
static int
|
||||
fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
struct subdev *sd = private;
|
||||
fd_p fd = sd->drive;
|
||||
fdu_t fdu = fd->unit;
|
||||
fdc_p fdc = fd->fdc;
|
||||
fdcu_t fdcu = fdc->fdcu;
|
||||
size_t fdblk;
|
||||
int error = 0;
|
||||
#endif /* SLICE */
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
#ifdef PC98
|
||||
@ -2543,7 +2334,6 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
#endif
|
||||
switch (cmd)
|
||||
{
|
||||
#ifndef SLICE
|
||||
case DIOCGDINFO:
|
||||
bzero(buffer, sizeof (buffer));
|
||||
dl = (struct disklabel *)buffer;
|
||||
@ -2587,7 +2377,6 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
error = writedisklabel(dev, fdstrategy,
|
||||
(struct disklabel *)buffer);
|
||||
break;
|
||||
#endif /* !SLICE */
|
||||
case FD_FORM:
|
||||
if((flag & FWRITE) == 0)
|
||||
error = EBADF; /* must be opened for writing */
|
||||
@ -2595,11 +2384,7 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
FD_FORMAT_VERSION)
|
||||
error = EINVAL; /* wrong version of formatting prog */
|
||||
else
|
||||
#ifdef SLICE
|
||||
error = fdformat(sd, (struct fd_formb *)addr, p);
|
||||
#else
|
||||
error = fdformat(dev, (struct fd_formb *)addr, p);
|
||||
#endif
|
||||
break;
|
||||
|
||||
case FD_GTYPE: /* get drive type */
|
||||
@ -2643,35 +2428,6 @@ static void fd_drvinit(void *notused )
|
||||
SYSINIT(fddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,fd_drvinit,NULL)
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
if((flags & (FREAD|FWRITE)) != 0) {
|
||||
return(Fdopen(makedev(0,sd->minor), flags , mode, p));
|
||||
} else {
|
||||
return(fdclose(makedev(0,sd->minor), 0 , mode, p));
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
fdsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
fdclose(makedev(0,sd->minor), 0 , 0, p);
|
||||
return ;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -43,7 +43,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)fd.c 7.4 (Berkeley) 5/25/91
|
||||
* $Id: fd.c,v 1.37 1998/07/19 15:03:49 kato Exp $
|
||||
* $Id: fd.c,v 1.38 1998/07/30 09:01:12 kato Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
@ -92,10 +92,6 @@
|
||||
#endif
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
|
||||
/* misuse a flag to identify format operation */
|
||||
@ -221,21 +217,8 @@ static struct fd_data {
|
||||
struct callout_handle toffhandle;
|
||||
struct callout_handle tohandle;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
int unit; /* as in fd0 */
|
||||
void *bdevs[MAXPARTITIONS];
|
||||
void *cdevs[MAXPARTITIONS];
|
||||
struct subdev{
|
||||
struct slice *slice;
|
||||
int minor;
|
||||
struct fd_data *drive;
|
||||
struct slicelimits limit;
|
||||
}subdevs[16];
|
||||
struct intr_config_hook ich;
|
||||
#else /* SLICE */
|
||||
void *bdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
void *cdevs[1 + NUMDENS + MAXPARTITIONS];
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
#ifdef PC98
|
||||
int pc98_trans;
|
||||
@ -339,9 +322,7 @@ static timeout_t fd_iotimeout;
|
||||
static timeout_t fd_pseudointr;
|
||||
static int fdstate(fdcu_t, fdc_p);
|
||||
static int retrier(fdcu_t);
|
||||
#ifndef SLICE
|
||||
static int fdformat(dev_t, struct fd_formb *, struct proc *);
|
||||
#endif
|
||||
|
||||
static int enable_fifo(fdc_p fdc);
|
||||
|
||||
@ -417,30 +398,6 @@ static struct cdevsw fd_cdevsw = {
|
||||
|
||||
static struct isa_device *fdcdevs[NFDC];
|
||||
|
||||
#ifdef SLICE
|
||||
static sl_h_IO_req_t fdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t fdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t fdsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t fdsclose; */ /* downwards travelling close */
|
||||
static void fdsinit(void *);
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"floppy",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&fdsIOreq,
|
||||
&fdsioctl,
|
||||
&fdsopen,
|
||||
/*&fdsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
NULL /* dump */
|
||||
};
|
||||
#endif /* SLICE */
|
||||
|
||||
static int
|
||||
fdc_err(fdcu_t fdcu, const char *s)
|
||||
@ -765,12 +722,8 @@ fdattach(struct isa_device *dev)
|
||||
struct isa_device *fdup;
|
||||
int ic_type = 0;
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
char namebuf[64];
|
||||
#else
|
||||
int mynor;
|
||||
int typemynor;
|
||||
#endif /* SLICE */
|
||||
int typesize;
|
||||
#endif
|
||||
|
||||
@ -979,9 +932,6 @@ fdattach(struct isa_device *dev)
|
||||
#endif
|
||||
|
||||
fd->track = FD_NO_TRACK;
|
||||
#ifdef SLICE
|
||||
fd->unit = fdu;
|
||||
#endif
|
||||
fd->fdc = fdc;
|
||||
fd->fdsu = fdsu;
|
||||
fd->options = 0;
|
||||
@ -1043,29 +993,6 @@ fdattach(struct isa_device *dev)
|
||||
continue;
|
||||
}
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d",fdu);
|
||||
fd->subdevs[0].minor = 0;
|
||||
fd->subdevs[0].drive = fd;
|
||||
fd->subdevs[0].limit.blksize =
|
||||
128 << (fd_types[fd->type - 1].secsize);
|
||||
fd->subdevs[0].limit.slicesize =
|
||||
fd_types[fd->type - 1].size
|
||||
* fd->subdevs[0].limit.blksize;
|
||||
fd->ft = fd_types + (fd->type - 1); /* default value */
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[0],
|
||||
&fd->subdevs[0].limit,
|
||||
&fd->subdevs[0].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[0].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[0].slice->probeinfo.type = NULL;
|
||||
|
||||
fd->ich.ich_func = fdsinit;
|
||||
fd->ich.ich_arg = &fd->subdevs[0];
|
||||
config_intrhook_establish(&fd->ich);
|
||||
#else /* SLICE */
|
||||
mynor = fdu << 6;
|
||||
fd->bdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_BLK,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
@ -1073,7 +1000,6 @@ fdattach(struct isa_device *dev)
|
||||
fd->cdevs[0] = devfs_add_devswf(&fd_cdevsw, mynor, DV_CHR,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
"rfd%d", fdu);
|
||||
#endif /* SLICE */
|
||||
for (i = 1; i < 1 + NUMDENS; i++) {
|
||||
/*
|
||||
* XXX this and the lookup in Fdopen() should be
|
||||
@ -1133,25 +1059,6 @@ fdattach(struct isa_device *dev)
|
||||
if (typesize == 1722)
|
||||
typesize = 1720;
|
||||
#endif
|
||||
#ifdef SLICE
|
||||
sprintf(namebuf,"fd%d.%d",fdu,typesize);
|
||||
fd->subdevs[i].minor = i;
|
||||
fd->subdevs[i].drive = fd;
|
||||
fd->subdevs[i].limit.blksize =
|
||||
128 << (fd_types[i - 1].secsize);
|
||||
fd->subdevs[i].limit.slicesize =
|
||||
fd_types[i - 1].size
|
||||
* fd->subdevs[i].limit.blksize;
|
||||
sl_make_slice(&slicetype,
|
||||
&fd->subdevs[i],
|
||||
&fd->subdevs[i].limit,
|
||||
&fd->subdevs[i].slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
fd->subdevs[i].slice->probeinfo.typespecific = NULL;
|
||||
fd->subdevs[i].slice->probeinfo.type = NO_SUBPART;
|
||||
}
|
||||
#else /* SLICE */
|
||||
typemynor = mynor | i;
|
||||
fd->bdevs[i] =
|
||||
devfs_add_devswf(&fd_cdevsw, typemynor, DV_BLK,
|
||||
@ -1170,7 +1077,6 @@ fdattach(struct isa_device *dev)
|
||||
devfs_link(fd->cdevs[0],
|
||||
"rfd%d%c", fdu, 'a' + i);
|
||||
}
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
#ifdef notyet
|
||||
if (dk_ndrive < DK_NDRIVE) {
|
||||
@ -1190,19 +1096,6 @@ fdattach(struct isa_device *dev)
|
||||
}
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static void
|
||||
fdsinit(void *arg)
|
||||
{
|
||||
struct subdev *sd = arg;
|
||||
sh_p tp;
|
||||
|
||||
slice_start_probe(sd->slice);
|
||||
config_intrhook_disestablish(&sd->drive->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/****************************************************************************/
|
||||
/* motor control stuff */
|
||||
@ -1647,48 +1540,6 @@ fdstrategy(struct buf *bp)
|
||||
biodone(bp);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
/****************************************************************************/
|
||||
/* fdsIOreq */
|
||||
/****************************************************************************/
|
||||
static void
|
||||
fdsIOreq(void *private ,struct buf *bp)
|
||||
{
|
||||
unsigned nblocks, blknum, cando;
|
||||
int s;
|
||||
fdcu_t fdcu;
|
||||
fdu_t fdu;
|
||||
fdc_p fdc;
|
||||
fd_p fd;
|
||||
size_t fdblk;
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
fdc = fd->fdc;
|
||||
fdcu = fdc->fdcu;
|
||||
|
||||
/* check for controller already busy with tape */
|
||||
if (fdc->flags & FDC_TAPE_BUSY) {
|
||||
bp->b_error = EBUSY;
|
||||
bp->b_flags |= B_ERROR;
|
||||
goto bad;
|
||||
}
|
||||
bp->b_driver1 = sd; /* squirrel away which device.. */
|
||||
bp->b_resid = 0;
|
||||
s = splbio();
|
||||
bufqdisksort(&fdc->head, bp);
|
||||
untimeout(fd_turnoff, (caddr_t)fdu, fd->toffhandle); /* a good idea */
|
||||
fdstart(fdcu);
|
||||
splx(s);
|
||||
return;
|
||||
|
||||
bad:
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/***************************************************************\
|
||||
* fdstart *
|
||||
@ -1807,14 +1658,8 @@ fdstate(fdcu_t fdcu, fdc_p fdc)
|
||||
TRACE1("[fdc%d IDLE]", fdcu);
|
||||
return(0);
|
||||
}
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(bp->b_dev));
|
||||
fd = fd_data + fdu;
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
if (fdc->fd && (fd != fdc->fd))
|
||||
{
|
||||
@ -2327,23 +2172,11 @@ retrier(fdcu)
|
||||
struct subdev *sd;
|
||||
fdc_p fdc = fdc_data + fdcu;
|
||||
register struct buf *bp;
|
||||
#ifdef SLICE
|
||||
struct fd_data *fd;
|
||||
int fdu;
|
||||
#endif
|
||||
|
||||
bp = bufq_first(&fdc->head);
|
||||
|
||||
#ifdef SLICE
|
||||
sd = bp->b_driver1;
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
if(fd->options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#else
|
||||
if(fd_data[FDUNIT(minor(bp->b_dev))].options & FDOPT_NORETRY)
|
||||
goto fail;
|
||||
#endif
|
||||
switch(fdc->retry)
|
||||
{
|
||||
case 0: case 1: case 2:
|
||||
@ -2360,10 +2193,6 @@ retrier(fdcu)
|
||||
default:
|
||||
fail:
|
||||
{
|
||||
#ifdef SLICE
|
||||
printf("fd%d: hard error, block %d ", fdu,
|
||||
fd->skip / DEV_BSIZE);
|
||||
#else
|
||||
dev_t sav_b_dev = bp->b_dev;
|
||||
/* Trick diskerr */
|
||||
bp->b_dev = makedev(major(bp->b_dev),
|
||||
@ -2372,7 +2201,6 @@ retrier(fdcu)
|
||||
fdc->fd->skip / DEV_BSIZE,
|
||||
(struct disklabel *)NULL);
|
||||
bp->b_dev = sav_b_dev;
|
||||
#endif /* !SLICE */
|
||||
if (fdc->flags & FDC_STAT_VALID)
|
||||
{
|
||||
printf(
|
||||
@ -2402,16 +2230,11 @@ retrier(fdcu)
|
||||
return(1);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdformat( struct subdev *sd, struct fd_formb *finfo, struct proc *p)
|
||||
#else /* !SLICE */
|
||||
static int
|
||||
fdformat(dev, finfo, p)
|
||||
dev_t dev;
|
||||
struct fd_formb *finfo;
|
||||
struct proc *p;
|
||||
#endif /* !SLICE */
|
||||
{
|
||||
fdu_t fdu;
|
||||
fd_p fd;
|
||||
@ -2420,13 +2243,8 @@ fdformat(dev, finfo, p)
|
||||
int rv = 0, s;
|
||||
size_t fdblk;
|
||||
|
||||
#ifdef SLICE
|
||||
fd = sd->drive;
|
||||
fdu = fd->unit;
|
||||
#else
|
||||
fdu = FDUNIT(minor(dev));
|
||||
fd = &fd_data[fdu];
|
||||
#endif
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
/* set up a buffer header for fdstrategy() */
|
||||
@ -2452,13 +2270,8 @@ fdformat(dev, finfo, p)
|
||||
bp->b_data = (caddr_t)finfo;
|
||||
|
||||
/* now do the format */
|
||||
#ifdef SLICE
|
||||
bp->b_driver1 = sd;
|
||||
fdsIOreq(sd, bp);
|
||||
#else /* !SLICE */
|
||||
bp->b_dev = dev;
|
||||
fdstrategy(bp);
|
||||
#endif /* !SLICE */
|
||||
|
||||
/* ...and wait for it to complete */
|
||||
s = splbio();
|
||||
@ -2514,28 +2327,6 @@ fdioctl(dev, cmd, addr, flag, p)
|
||||
return ftioctl(dev, cmd, addr, flag, p);
|
||||
#endif
|
||||
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* if SLICE is defined then only ft accesses come here
|
||||
* so break the rest off to another function for SLICE access.
|
||||
*/
|
||||
return (ENOTTY);
|
||||
}
|
||||
|
||||
/*
|
||||
* Slice ioctls come here
|
||||
*/
|
||||
static int
|
||||
fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
struct subdev *sd = private;
|
||||
fd_p fd = sd->drive;
|
||||
fdu_t fdu = fd->unit;
|
||||
fdc_p fdc = fd->fdc;
|
||||
fdcu_t fdcu = fdc->fdcu;
|
||||
size_t fdblk;
|
||||
int error = 0;
|
||||
#endif /* SLICE */
|
||||
fdblk = 128 << fd->ft->secsize;
|
||||
|
||||
#ifdef PC98
|
||||
@ -2543,7 +2334,6 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
#endif
|
||||
switch (cmd)
|
||||
{
|
||||
#ifndef SLICE
|
||||
case DIOCGDINFO:
|
||||
bzero(buffer, sizeof (buffer));
|
||||
dl = (struct disklabel *)buffer;
|
||||
@ -2587,7 +2377,6 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
error = writedisklabel(dev, fdstrategy,
|
||||
(struct disklabel *)buffer);
|
||||
break;
|
||||
#endif /* !SLICE */
|
||||
case FD_FORM:
|
||||
if((flag & FWRITE) == 0)
|
||||
error = EBADF; /* must be opened for writing */
|
||||
@ -2595,11 +2384,7 @@ fdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
FD_FORMAT_VERSION)
|
||||
error = EINVAL; /* wrong version of formatting prog */
|
||||
else
|
||||
#ifdef SLICE
|
||||
error = fdformat(sd, (struct fd_formb *)addr, p);
|
||||
#else
|
||||
error = fdformat(dev, (struct fd_formb *)addr, p);
|
||||
#endif
|
||||
break;
|
||||
|
||||
case FD_GTYPE: /* get drive type */
|
||||
@ -2643,35 +2428,6 @@ static void fd_drvinit(void *notused )
|
||||
SYSINIT(fddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,fd_drvinit,NULL)
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
static int
|
||||
fdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
if((flags & (FREAD|FWRITE)) != 0) {
|
||||
return(Fdopen(makedev(0,sd->minor), flags , mode, p));
|
||||
} else {
|
||||
return(fdclose(makedev(0,sd->minor), 0 , mode, p));
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
fdsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
struct subdev *sd;
|
||||
|
||||
sd = private;
|
||||
|
||||
fdclose(makedev(0,sd->minor), 0 , 0, p);
|
||||
return ;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -34,7 +34,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)wd.c 7.2 (Berkeley) 5/9/91
|
||||
* $Id: wd.c,v 1.60 1998/07/30 15:16:05 bde Exp $
|
||||
* $Id: wd.c,v 1.61 1998/08/23 20:16:34 phk Exp $
|
||||
*/
|
||||
|
||||
/* TODO:
|
||||
@ -80,14 +80,7 @@
|
||||
#include <sys/buf.h>
|
||||
#include <sys/malloc.h>
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <sys/fcntl.h>
|
||||
#include <sys/sliceio.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#else
|
||||
#include <sys/devfsext.h>
|
||||
#endif /*SLICE*/
|
||||
#endif /*DEVFS*/
|
||||
#include <machine/bootinfo.h>
|
||||
#include <machine/clock.h>
|
||||
@ -196,15 +189,8 @@ struct disk {
|
||||
u_int32_t dk_port; /* i/o port base */
|
||||
u_int32_t dk_altport; /* altstatus port base */
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
struct slice *slice;
|
||||
int minor;
|
||||
struct slicelimits limit;
|
||||
struct intr_config_hook ich;
|
||||
#else
|
||||
void *dk_bdev; /* devfs token for whole disk */
|
||||
void *dk_cdev; /* devfs token for raw whole disk */
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
u_long cfg_flags; /* configured characteristics */
|
||||
short dk_flags; /* drive characteristics found */
|
||||
@ -274,9 +260,7 @@ static void wderror(struct buf *bp, struct disk *du, char *mesg);
|
||||
static void wdflushirq(struct disk *du, int old_ipl);
|
||||
static int wdreset(struct disk *du);
|
||||
static void wdsleep(int ctrlr, char *wmesg);
|
||||
#ifndef SLICE
|
||||
static void wdstrategy1(struct buf *bp);
|
||||
#endif
|
||||
static timeout_t wdtimeout;
|
||||
static int wdunwedge(struct disk *du);
|
||||
static int wdwait(struct disk *du, u_char bits_wanted, int timeout);
|
||||
@ -285,34 +269,7 @@ struct isa_driver wdcdriver = {
|
||||
wdprobe, wdattach, "wdc",
|
||||
};
|
||||
|
||||
#ifdef SLICE
|
||||
|
||||
static sl_h_IO_req_t wdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t wdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t wdsopen; /* downwards travelling open */
|
||||
/*static sl_h_close_t wdsclose; */ /* downwards travelling close */
|
||||
static sl_h_dump_t wddump; /* core dump req downward */
|
||||
static void wds_init(void*);
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"IDE",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&wdsIOreq,
|
||||
&wdsioctl,
|
||||
&wdsopen,
|
||||
/*&wdsclose*/NULL,
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
&wddump
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
static d_open_t wdopen;
|
||||
static d_read_t wdread;
|
||||
@ -334,7 +291,6 @@ static struct cdevsw wd_cdevsw = {
|
||||
NULL, -1, wddump, wdsize,
|
||||
D_DISK, 0, -1 };
|
||||
|
||||
#endif /* !SLICE */
|
||||
|
||||
#ifdef CMD640
|
||||
static int atapictrlr;
|
||||
@ -521,7 +477,7 @@ wdprobe(struct isa_device *dvp)
|
||||
static int
|
||||
wdattach(struct isa_device *dvp)
|
||||
{
|
||||
#if defined(DEVFS) && ! defined(SLICE)
|
||||
#if defined(DEVFS)
|
||||
int mynor;
|
||||
#endif
|
||||
u_int unit, lunit;
|
||||
@ -611,12 +567,6 @@ wdattach(struct isa_device *dvp)
|
||||
if (du->cfg_flags & WDOPT_SLEEPHACK)
|
||||
printf(", sleep-hack");
|
||||
printf("\n");
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* Here we somehow schedule the geometry HACK fro later and print
|
||||
* something meaningful.
|
||||
*/
|
||||
#endif
|
||||
if (du->dk_params.wdp_heads == 0)
|
||||
printf("wd%d: size unknown, using %s values\n",
|
||||
lunit, du->dk_dd.d_secperunit > 17
|
||||
@ -651,35 +601,6 @@ wdattach(struct isa_device *dvp)
|
||||
wdtimeout(du);
|
||||
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
{
|
||||
char namebuf[64];
|
||||
sprintf(namebuf,"wd%d",lunit);
|
||||
du->minor = dkmakeminor(lunit,
|
||||
WHOLE_DISK_SLICE, RAW_PART);
|
||||
du->limit.blksize = du->dk_dd.d_secsize;
|
||||
du->limit.slicesize =
|
||||
(u_int64_t)du->dk_dd.d_secsize *
|
||||
du->dk_dd.d_secperunit;
|
||||
/*
|
||||
* Fill in the 3 geometry entries
|
||||
* to tell the mbr code
|
||||
* we already know it, so that it
|
||||
* doesn't try deduce it.
|
||||
*/
|
||||
sl_make_slice(&slicetype,
|
||||
du,
|
||||
&du->limit,
|
||||
&du->slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
du->slice->probeinfo.typespecific = NULL;
|
||||
du->slice->probeinfo.type = NULL;
|
||||
}
|
||||
du->ich.ich_func = wds_init;
|
||||
du->ich.ich_arg = du;
|
||||
config_intrhook_establish(&du->ich);
|
||||
#else
|
||||
mynor = dkmakeminor(lunit, WHOLE_DISK_SLICE, RAW_PART);
|
||||
du->dk_bdev = devfs_add_devswf(&wd_cdevsw, mynor,
|
||||
DV_BLK, UID_ROOT,
|
||||
@ -689,7 +610,6 @@ wdattach(struct isa_device *dvp)
|
||||
DV_CHR, UID_ROOT,
|
||||
GID_OPERATOR, 0640,
|
||||
"rwd%d", lunit);
|
||||
#endif
|
||||
#endif
|
||||
|
||||
if (dk_ndrive < DK_NDRIVE) {
|
||||
@ -755,50 +675,7 @@ next: ;
|
||||
return (1);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
extern struct proc *curproc;
|
||||
static void
|
||||
wds_init(void *arg)
|
||||
{
|
||||
struct disk *du = arg;
|
||||
sh_p tp;
|
||||
int err = 0;
|
||||
struct ide_geom geom;
|
||||
|
||||
if ((err = wdsopen(du, FREAD, 0, curproc))) {
|
||||
printf("wd open failed with %d", err);
|
||||
return;
|
||||
}
|
||||
/*
|
||||
* If we still don't have geometry,
|
||||
* Then call the IDE geometry HACK functions.
|
||||
*/
|
||||
#if 0
|
||||
if ( ?? ) { /* how do we know? */
|
||||
bzero (&geom, sizeof(geom));
|
||||
if (mbr_geom_hack(du->slice)) && (dkl_geom_hack(du->slice)) {
|
||||
printf("We really have no geometry\n");
|
||||
} else {
|
||||
du->dk_dd.d_secperunit = (geom.cyls *
|
||||
geom.trackpercyl * geom.secpertrack);
|
||||
du->dk_dd.d_ncylinders = geom.cyls;
|
||||
du->dk_dd.d_ntracks = geom.trackpercyl;
|
||||
du->dk_dd.d_nsectors = geom.secpertrack;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
slice_start_probe(du->slice);
|
||||
config_intrhook_disestablish(&du->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
#if 0
|
||||
wdsclose(du, 0, 0, curproc);
|
||||
#else
|
||||
wdsopen(du, 0, 0, curproc); /* open to 0 flags == close */
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
static int
|
||||
wdread(dev_t dev, struct uio *uio, int ioflag)
|
||||
@ -928,7 +805,6 @@ wdstrategy1(struct buf *bp)
|
||||
*/
|
||||
wdstrategy(bp);
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* Routine to queue a command to the controller. The unit's
|
||||
@ -1024,13 +900,8 @@ wdstart(int ctrlr)
|
||||
}
|
||||
|
||||
/* obtain controller and drive information */
|
||||
#ifdef SLICE
|
||||
du = bp->b_driver1;
|
||||
lunit = du->dk_lunit;
|
||||
#else /* !SLICE */
|
||||
lunit = dkunit(bp->b_dev);
|
||||
du = wddrives[lunit];
|
||||
#endif /* !SLICE */
|
||||
|
||||
#ifdef PC98
|
||||
outb(0x432,(du->dk_unit)%2);
|
||||
@ -1081,7 +952,6 @@ wdstart(int ctrlr)
|
||||
du->dk_flags |= DKFL_SINGLE;
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
if (du->dk_flags & DKFL_SINGLE
|
||||
&& dsgetbad(bp->b_dev, du->dk_slices) != NULL) {
|
||||
/* XXX */
|
||||
@ -1091,12 +961,6 @@ wdstart(int ctrlr)
|
||||
blknum = transbad144(dsgetbad(bp->b_dev, du->dk_slices),
|
||||
blknum - ds_offset) + ds_offset;
|
||||
}
|
||||
#else
|
||||
if (du->dk_flags & DKFL_SINGLE && du->slice->handler_up) {
|
||||
(void) (*du->slice->handler_up->upconf)(du->slice,
|
||||
SLCIOCTRANSBAD, (caddr_t)&blknum, 0, 0);
|
||||
}
|
||||
#endif
|
||||
|
||||
wdtab[ctrlr].b_active = 1; /* mark controller active */
|
||||
|
||||
@ -1354,11 +1218,7 @@ wdintr(int unit)
|
||||
}
|
||||
#endif
|
||||
bp = bufq_first(&wdtab[unit].controller_queue);
|
||||
#ifdef SLICE
|
||||
du = bp->b_driver1;
|
||||
#else /* !SLICE */
|
||||
du = wddrives[dkunit(bp->b_dev)];
|
||||
#endif /* !SLICE */
|
||||
|
||||
#ifdef PC98
|
||||
outb(0x432,(du->dk_unit)%2);
|
||||
@ -1568,7 +1428,6 @@ done: ;
|
||||
wdstart(unit);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
/*
|
||||
* Initialize a drive.
|
||||
*/
|
||||
@ -1749,7 +1608,6 @@ wdopen(dev_t dev, int flags, int fmt, struct proc *p)
|
||||
return (0);
|
||||
#endif
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* Implement operations other than read/write.
|
||||
@ -1763,11 +1621,7 @@ wdcontrol(register struct buf *bp)
|
||||
register struct disk *du;
|
||||
int ctrlr;
|
||||
|
||||
#ifdef SLICE
|
||||
du = bp->b_driver1;
|
||||
#else /* !SLICE */
|
||||
du = wddrives[dkunit(bp->b_dev)];
|
||||
#endif /* !SLICE */
|
||||
#ifdef CMD640
|
||||
ctrlr = du->dk_ctrlr_cmd640;
|
||||
#else
|
||||
@ -2348,7 +2202,6 @@ wdgetctlr(struct disk *du)
|
||||
return (0);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
int
|
||||
wdclose(dev_t dev, int flags, int fmt, struct proc *p)
|
||||
{
|
||||
@ -2370,12 +2223,10 @@ wdioctl(dev_t dev, u_long cmd, caddr_t addr, int flags, struct proc *p)
|
||||
|
||||
du = wddrives[lunit];
|
||||
wdsleep(du->dk_ctrlr, "wdioct");
|
||||
#ifndef SLICE
|
||||
error = dsioctl("wd", dev, cmd, addr, flags, &du->dk_slices,
|
||||
wdstrategy1, (ds_setgeom_t *)NULL);
|
||||
if (error != ENOIOCTL)
|
||||
return (error);
|
||||
#endif /* SLICE */
|
||||
#ifdef PC98
|
||||
outb(0x432,(du->dk_unit)%2);
|
||||
#endif
|
||||
@ -2444,15 +2295,9 @@ wdsize(dev_t dev)
|
||||
#endif
|
||||
return (dssize(dev, &du->dk_slices, wdopen, wdclose));
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
#ifndef SLICE
|
||||
int
|
||||
wddump(dev_t dev)
|
||||
#else
|
||||
static int
|
||||
wddump(void *private, int32_t start, int32_t num)
|
||||
#endif /* SLICE */
|
||||
{
|
||||
#ifdef PC98
|
||||
/* do nothing */
|
||||
@ -2460,7 +2305,6 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
return(0);
|
||||
#else
|
||||
register struct disk *du;
|
||||
#ifndef SLICE
|
||||
struct disklabel *lp;
|
||||
long num; /* number of sectors to write */
|
||||
int lunit, part;
|
||||
@ -2469,14 +2313,10 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
u_long ds_offset;
|
||||
u_long nblocks;
|
||||
static int wddoingadump = 0;
|
||||
#else
|
||||
long blknum, blkchk, blkcnt, blknext;
|
||||
#endif /* SLICE */
|
||||
long cylin, head, sector;
|
||||
long secpertrk, secpercyl;
|
||||
char *addr;
|
||||
|
||||
#ifndef SLICE
|
||||
/* Toss any characters present prior to dump. */
|
||||
while (cncheckc() != -1)
|
||||
;
|
||||
@ -2523,14 +2363,6 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
wdtab[du->dk_ctrlr].b_active = 1;
|
||||
#endif
|
||||
wddoingadump = 1;
|
||||
#else
|
||||
du = private;
|
||||
if (du->dk_state < OPEN)
|
||||
return (ENXIO);
|
||||
|
||||
secpertrk = du->dk_dd.d_nsectors;
|
||||
secpercyl = du->dk_dd.d_secpercyl;
|
||||
#endif /* SLICE */
|
||||
|
||||
/* Recalibrate the drive. */
|
||||
DELAY(5); /* ATA spec XXX NOT */
|
||||
@ -2543,11 +2375,7 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
|
||||
du->dk_flags |= DKFL_SINGLE;
|
||||
addr = (char *) 0;
|
||||
#ifndef SLICE
|
||||
blknum = dumplo + blkoff;
|
||||
#else
|
||||
blknum = start;
|
||||
#endif /* SLICE */
|
||||
while (num > 0) {
|
||||
blkcnt = num;
|
||||
if (blkcnt > MAXTRANSFER)
|
||||
@ -2564,20 +2392,12 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
* sector is bad, then reduce reduce the transfer to
|
||||
* avoid any bad sectors.
|
||||
*/
|
||||
#ifndef SLICE
|
||||
if (du->dk_flags & DKFL_SINGLE
|
||||
&& dsgetbad(dev, du->dk_slices) != NULL) {
|
||||
for (blkchk = blknum; blkchk < blknum + blkcnt; blkchk++) {
|
||||
daddr_t blknew;
|
||||
blknew = transbad144(dsgetbad(dev, du->dk_slices),
|
||||
blkchk - ds_offset) + ds_offset;
|
||||
#else
|
||||
if (du->dk_flags & DKFL_SINGLE && du->slice->handler_up) {
|
||||
for (blkchk = blknum; blkchk < blknum + blkcnt; blkchk++) {
|
||||
daddr_t blknew = blkchk;
|
||||
(void) (*du->slice->handler_up->upconf)(du->slice,
|
||||
SLCIOCTRANSBAD, (caddr_t)&blknew, 0, 0);
|
||||
#endif /* SLICE */
|
||||
if (blknew != blkchk) {
|
||||
/* Found bad block. */
|
||||
blkcnt = blkchk - blknum;
|
||||
@ -2686,15 +2506,11 @@ wddump(void *private, int32_t start, int32_t num)
|
||||
static void
|
||||
wderror(struct buf *bp, struct disk *du, char *mesg)
|
||||
{
|
||||
#ifdef SLICE
|
||||
printf("wd%d: %s:\n", du->dk_lunit, mesg);
|
||||
#else /* !SLICE */
|
||||
if (bp == NULL)
|
||||
printf("wd%d: %s:\n", du->dk_lunit, mesg);
|
||||
else
|
||||
diskerr(bp, "wd", mesg, LOG_PRINTF, du->dk_skip,
|
||||
dsgetlabel(bp->b_dev, du->dk_slices));
|
||||
#endif /* !SLICE */
|
||||
printf("wd%d: status %b error %b\n", du->dk_lunit,
|
||||
du->dk_status, WDCS_BITS, du->dk_error, WDERR_BITS);
|
||||
}
|
||||
@ -2953,7 +2769,6 @@ wdwait(struct disk *du, u_char bits_wanted, int timeout)
|
||||
return (-1);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
static wd_devsw_installed = 0;
|
||||
|
||||
static void wd_drvinit(void *unused)
|
||||
@ -2968,134 +2783,7 @@ static void wd_drvinit(void *unused)
|
||||
}
|
||||
|
||||
SYSINIT(wddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,wd_drvinit,NULL)
|
||||
#endif /* !SLICE */
|
||||
|
||||
|
||||
|
||||
#ifdef SLICE
|
||||
/*
|
||||
* Read/write routine for a buffer. Finds the proper unit, range checks
|
||||
* arguments, and schedules the transfer. Does not wait for the transfer
|
||||
* to complete. Multi-page transfers are supported. All I/O requests must
|
||||
* be a multiple of a sector in length.
|
||||
*/
|
||||
static void
|
||||
wdsIOreq(void *private, struct buf *bp)
|
||||
{
|
||||
struct disk *du = private;
|
||||
int s;
|
||||
int lunit = du->dk_lunit;
|
||||
|
||||
/* queue transfer on drive, activate drive and controller if idle */
|
||||
s = splbio();
|
||||
|
||||
bufqdisksort(&drive_queue[lunit], bp);
|
||||
|
||||
/*
|
||||
* Move the head of the drive queue to the controller queue.
|
||||
*/
|
||||
if (wdutab[lunit].b_active == 0)
|
||||
wdustart(du);
|
||||
|
||||
/*
|
||||
* Kick off the controller if there is anything for IT to do.
|
||||
*/
|
||||
#ifdef CMD640
|
||||
if (wdtab[du->dk_ctrlr_cmd640].b_active == 0)
|
||||
#else
|
||||
if (wdtab[du->dk_ctrlr].b_active == 0)
|
||||
#endif
|
||||
wdstart(du->dk_ctrlr); /* start controller */
|
||||
|
||||
splx(s);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
* Initialize a drive.
|
||||
*/
|
||||
static int
|
||||
wdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
register struct disk *du;
|
||||
int error = 0;
|
||||
|
||||
du = private;
|
||||
|
||||
if ((flags & (FREAD|FWRITE)) != 0) {
|
||||
/* Finish flushing IRQs left over from wdattach(). */
|
||||
#ifdef CMD640
|
||||
if (wdtab[du->dk_ctrlr_cmd640].b_active == 2)
|
||||
wdtab[du->dk_ctrlr_cmd640].b_active = 0;
|
||||
#else
|
||||
if (wdtab[du->dk_ctrlr].b_active == 2)
|
||||
wdtab[du->dk_ctrlr].b_active = 0;
|
||||
#endif
|
||||
|
||||
du->dk_state = OPEN;
|
||||
du->dk_flags &= ~DKFL_BADSCAN;
|
||||
} else {
|
||||
/* <luoqi@watermarkgroup.com> suggests I remove this */
|
||||
/* du->dk_state = CLOSED;*/
|
||||
/* du->dk_state = WANTOPEN; */ /* maybe this? */
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void
|
||||
wdsclose(void *private, int flags, int mode, struct proc *p)
|
||||
{
|
||||
register struct disk *du;
|
||||
|
||||
du = private;
|
||||
du->dk_state = CLOSED;
|
||||
return;
|
||||
}
|
||||
#endif /* 0 */
|
||||
|
||||
static int
|
||||
wdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
{
|
||||
register struct disk *du = private;
|
||||
#ifdef notyet
|
||||
int error;
|
||||
#endif
|
||||
|
||||
wdsleep(du->dk_ctrlr, "wdioct");
|
||||
switch (cmd) {
|
||||
case DIOCSBADSCAN:
|
||||
if (*(int *)addr)
|
||||
du->dk_flags |= DKFL_BADSCAN;
|
||||
else
|
||||
du->dk_flags &= ~DKFL_BADSCAN;
|
||||
return (0);
|
||||
#ifdef notyet
|
||||
case DIOCWFORMAT:
|
||||
if (!(flag & FWRITE))
|
||||
return (EBADF);
|
||||
fop = (struct format_op *)addr;
|
||||
aiov.iov_base = fop->df_buf;
|
||||
aiov.iov_len = fop->df_count;
|
||||
auio.uio_iov = &aiov;
|
||||
auio.uio_iovcnt = 1;
|
||||
auio.uio_resid = fop->df_count;
|
||||
auio.uio_segflg = 0;
|
||||
auio.uio_offset = fop->df_startblk * du->dk_dd.d_secsize;
|
||||
#error /* XXX the 386BSD interface is different */
|
||||
error = physio(wdformat, &rwdbuf[lunit], 0, dev, B_WRITE,
|
||||
minphys, &auio);
|
||||
fop->df_count -= auio.uio_resid;
|
||||
fop->df_reg[0] = du->dk_status;
|
||||
fop->df_reg[1] = du->dk_error;
|
||||
return (error);
|
||||
#endif
|
||||
|
||||
default:
|
||||
return (ENOTTY);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* SLICE */
|
||||
#endif /* NWDC > 0 */
|
||||
|
260
sys/scsi/sd.c
260
sys/scsi/sd.c
@ -14,7 +14,7 @@
|
||||
*
|
||||
* Ported to run under 386BSD by Julian Elischer (julian@dialix.oz.au) Sept 1992
|
||||
*
|
||||
* $Id: sd.c,v 1.138 1998/07/30 15:16:05 bde Exp $
|
||||
* $Id: sd.c,v 1.139 1998/08/23 20:16:35 phk Exp $
|
||||
*/
|
||||
|
||||
#include "opt_bounce.h"
|
||||
@ -34,11 +34,6 @@
|
||||
#include <sys/conf.h>
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <sys/fcntl.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#endif /* DEVFS */
|
||||
|
||||
#include <scsi/scsi_disk.h>
|
||||
@ -99,23 +94,13 @@ struct scsi_data {
|
||||
struct buf_queue_head buf_queue;
|
||||
int dkunit; /* disk stats unit number */
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
struct slice *slice;
|
||||
int mynor;
|
||||
struct slicelimits limit;
|
||||
struct scsi_link *sc_link;
|
||||
int unit;
|
||||
struct intr_config_hook ich;
|
||||
#else /* SLICE */
|
||||
void *b_devfs_token;
|
||||
void *c_devfs_token;
|
||||
#endif /* SLICE */
|
||||
void *ctl_devfs_token;
|
||||
#endif
|
||||
};
|
||||
|
||||
|
||||
#ifndef SLICE
|
||||
static int sdunit(dev_t dev) { return SDUNIT(dev); }
|
||||
static dev_t sdsetunit(dev_t dev, int unit) { return SDSETUNIT(dev, unit); }
|
||||
static errval sd_open __P((dev_t dev, int mode, int fmt, struct proc *p,
|
||||
@ -145,36 +130,8 @@ static struct cdevsw sd_cdevsw = {
|
||||
NULL, -1, sddump, sdsize,
|
||||
D_DISK, 0, -1 };
|
||||
|
||||
#else /* ! SLICE */
|
||||
|
||||
static errval sdattach(struct scsi_link *sc_link);
|
||||
static sl_h_IO_req_t sdsIOreq; /* IO req downward (to device) */
|
||||
static sl_h_ioctl_t sdsioctl; /* ioctl req downward (to device) */
|
||||
static sl_h_open_t sdsopen; /* downwards travelling open */
|
||||
static sl_h_close_t sdsclose; /* downwards travelling close */
|
||||
static void sds_init (void *arg);
|
||||
static sl_h_dump_t sdsdump; /* core dump req downward */
|
||||
|
||||
static struct slice_handler slicetype = {
|
||||
"scsidisk",
|
||||
0,
|
||||
NULL,
|
||||
0,
|
||||
NULL, /* constructor */
|
||||
&sdsIOreq,
|
||||
&sdsioctl,
|
||||
&sdsopen,
|
||||
NULL, /* was close, now free */
|
||||
NULL, /* revoke */
|
||||
NULL, /* claim */
|
||||
NULL, /* verify */
|
||||
NULL, /* upconfig */
|
||||
&sdsdump
|
||||
};
|
||||
#endif
|
||||
|
||||
|
||||
#ifndef SLICE
|
||||
|
||||
SCSI_DEVICE_ENTRIES(sd)
|
||||
|
||||
@ -200,39 +157,6 @@ static struct scsi_device sd_switch =
|
||||
sd_close,
|
||||
sd_strategy,
|
||||
};
|
||||
#else /* SLICE */
|
||||
static struct scsi_device sd_switch =
|
||||
{
|
||||
sd_sense_handler,
|
||||
sdstart, /* have a queue, served by this */
|
||||
NULL, /* have no async handler */
|
||||
NULL, /* Use default 'done' routine */
|
||||
"sd",
|
||||
0,
|
||||
{0, 0},
|
||||
0, /* Link flags */
|
||||
sdattach,
|
||||
"Direct-Access",
|
||||
NULL,
|
||||
sizeof(struct scsi_data),
|
||||
T_DIRECT,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
};
|
||||
|
||||
|
||||
/* this should be called by the SYSINIT (?!) */
|
||||
void
|
||||
sdinit(void)
|
||||
{
|
||||
scsi_device_register(&sd_switch);
|
||||
}
|
||||
|
||||
#endif /* SLICE */
|
||||
static struct scsi_xfer sx;
|
||||
|
||||
|
||||
@ -308,30 +232,6 @@ sdattach(struct scsi_link *sc_link)
|
||||
sd_registerdev(unit);
|
||||
|
||||
#ifdef DEVFS
|
||||
#ifdef SLICE
|
||||
{
|
||||
char namebuf[64];
|
||||
sd->unit = unit;
|
||||
sd->sc_link = sc_link;
|
||||
sprintf(namebuf,"sd%d",sd->unit);
|
||||
sd->mynor = dkmakeminor(unit, WHOLE_DISK_SLICE, RAW_PART);
|
||||
sd->limit.blksize = sd->params.secsiz;
|
||||
/* need to cast to avoid overflow! */
|
||||
sd->limit.slicesize =
|
||||
(u_int64_t)sd->params.secsiz * sd->params.disksize;
|
||||
sl_make_slice(&slicetype,
|
||||
sd,
|
||||
&sd->limit,
|
||||
&sd->slice,
|
||||
namebuf);
|
||||
/* Allow full probing */
|
||||
sd->slice->probeinfo.typespecific = NULL;
|
||||
sd->slice->probeinfo.type = NULL;
|
||||
}
|
||||
sd->ich.ich_func = sds_init;
|
||||
sd->ich.ich_arg = sd;
|
||||
config_intrhook_establish(&sd->ich);
|
||||
#else /* SLICE */
|
||||
mynor = dkmakeminor(unit, WHOLE_DISK_SLICE, RAW_PART);
|
||||
sd->b_devfs_token = devfs_add_devswf(&sd_cdevsw, mynor, DV_BLK,
|
||||
UID_ROOT, GID_OPERATOR, 0640,
|
||||
@ -345,54 +245,17 @@ sdattach(struct scsi_link *sc_link)
|
||||
DV_CHR,
|
||||
UID_ROOT, GID_WHEEL, 0600,
|
||||
"rsd%d.ctl", unit);
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
/* run a LOT later */
|
||||
static void
|
||||
sds_init(void *arg)
|
||||
{
|
||||
struct scsi_data *sd = arg;
|
||||
sh_p tp;
|
||||
|
||||
slice_start_probe(sd->slice);
|
||||
config_intrhook_disestablish(&sd->ich);
|
||||
DELAY(2000000); /* XXX */
|
||||
}
|
||||
#endif /* SLICE */
|
||||
|
||||
/*
|
||||
* open the device. Make sure the partition info is a up-to-date as can be.
|
||||
*/
|
||||
#ifdef SLICE
|
||||
static int
|
||||
sdsopen(void *private, int flags, int mode, struct proc *p)
|
||||
#else /* !SLICE */
|
||||
static errval
|
||||
sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
#endif
|
||||
{
|
||||
#ifdef SLICE
|
||||
errval errcode = 0;
|
||||
struct scsi_data *sd = private;
|
||||
struct scsi_link *sc_link = sd->sc_link;
|
||||
u_int32_t unit = sd->unit;
|
||||
|
||||
if ((flags & (FREAD|FWRITE)) == 0) {
|
||||
/* Mode chenge to mode 0 (closed) */
|
||||
errcode = scsi_device_lock(sc_link);
|
||||
if (errcode) {
|
||||
return errcode; /* how can close fail? */
|
||||
}
|
||||
scsi_prevent(sc_link, PR_ALLOW, SCSI_SILENT | SCSI_ERR_OK);
|
||||
sc_link->flags &= ~SDEV_OPEN;
|
||||
scsi_device_unlock(sc_link);
|
||||
return (0);
|
||||
}
|
||||
#else /* !SLICE */
|
||||
errval errcode = 0;
|
||||
u_int32_t unit;
|
||||
struct disklabel label;
|
||||
@ -400,7 +263,6 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
|
||||
unit = SDUNIT(dev);
|
||||
sd = sc_link->sd;
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* Make sure the disk has been initialised
|
||||
@ -411,13 +273,9 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
return (ENXIO);
|
||||
}
|
||||
|
||||
#ifdef SLICE
|
||||
SC_DEBUG(sc_link, SDEV_DB1, ("sdsopen: (unit %ld)\n", unit));
|
||||
#else /* !SLICE */
|
||||
SC_DEBUG(sc_link, SDEV_DB1,
|
||||
("sd_open: dev=0x%lx (unit %lu, partition %d)\n",
|
||||
(u_long)dev, (u_long)unit, PARTITION(dev)));
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* "unit attention" errors should occur here if the
|
||||
@ -437,7 +295,6 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
*/
|
||||
sc_link->flags |= SDEV_OPEN; /* unit attn becomes an err now */
|
||||
if (!(sc_link->flags & SDEV_MEDIA_LOADED) && sd->dk_slices != NULL) {
|
||||
#ifndef SLICE
|
||||
/*
|
||||
* If somebody still has it open, then forbid re-entry.
|
||||
*/
|
||||
@ -447,7 +304,6 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
}
|
||||
|
||||
dsgone(&sd->dk_slices);
|
||||
#endif /* !SLICE */
|
||||
}
|
||||
|
||||
/*
|
||||
@ -471,7 +327,6 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
/* Lock the pack in. */
|
||||
scsi_prevent(sc_link, PR_PREVENT, SCSI_ERR_OK | SCSI_SILENT);
|
||||
|
||||
#ifndef SLICE
|
||||
/* Build label for whole disk. */
|
||||
bzero(&label, sizeof label);
|
||||
label.d_type = DTYPE_SCSI;
|
||||
@ -490,7 +345,6 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
(ds_setgeom_t *)NULL, &sd_cdevsw);
|
||||
if (errcode != 0)
|
||||
goto close;
|
||||
#endif /* !SLICE */
|
||||
SC_DEBUG(sc_link, SDEV_DB3, ("Slice tables initialized "));
|
||||
|
||||
SC_DEBUG(sc_link, SDEV_DB3, ("open %lu %lu\n",
|
||||
@ -500,11 +354,7 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
return 0;
|
||||
|
||||
close:
|
||||
#ifndef SLICE
|
||||
if (!dsisopen(sd->dk_slices))
|
||||
#else
|
||||
if((sd->slice->flags & SLF_OPEN_STATE) == SLF_CLOSED)
|
||||
#endif
|
||||
{
|
||||
scsi_prevent(sc_link, PR_ALLOW, SCSI_ERR_OK | SCSI_SILENT);
|
||||
sc_link->flags &= ~SDEV_OPEN;
|
||||
@ -513,7 +363,6 @@ sd_open(dev_t dev, int mode, int fmt, struct proc *p, struct scsi_link *sc_link)
|
||||
return errcode;
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
/*
|
||||
* close the device.. only called if we are the LAST occurence of an open
|
||||
* device. Convenient now but usually a pain.
|
||||
@ -631,7 +480,6 @@ sdstrategy1(struct buf *bp)
|
||||
sdstrategy(bp);
|
||||
}
|
||||
|
||||
#endif /* ! SLICE */
|
||||
/*
|
||||
* sdstart looks to see if there is a buf waiting for the device
|
||||
* and that the device is not already busy. If both are true,
|
||||
@ -747,24 +595,12 @@ sdstart(u_int32_t unit, u_int32_t flags)
|
||||
* Perform special action on behalf of the user
|
||||
* Knows about the internals of this device
|
||||
*/
|
||||
#ifdef SLICE
|
||||
static int
|
||||
sdsioctl( void *private, u_long cmd, caddr_t addr, int flag, struct proc *p)
|
||||
#else /* SLICE */
|
||||
static errval
|
||||
sd_ioctl(dev_t dev, u_long cmd, caddr_t addr, int flag, struct proc *p,
|
||||
struct scsi_link *sc_link)
|
||||
#endif /* !SLICE */
|
||||
{
|
||||
#ifdef SLICE
|
||||
struct scsi_data *sd = private;
|
||||
struct scsi_link *sc_link = sd->sc_link;
|
||||
dev_t dev = makedev(0,sd->mynor);
|
||||
|
||||
#else /* SLICE */
|
||||
errval error;
|
||||
struct scsi_data *sd = sc_link->sd;
|
||||
#endif /* !SLICE */
|
||||
SC_DEBUG(sc_link, SDEV_DB1, ("sdioctl (0x%lx)", cmd));
|
||||
|
||||
#if 0
|
||||
@ -782,7 +618,6 @@ sd_ioctl(dev_t dev, u_long cmd, caddr_t addr, int flag, struct proc *p,
|
||||
if (cmd == DIOCSBAD)
|
||||
return (EINVAL); /* XXX */
|
||||
|
||||
#ifndef SLICE
|
||||
error = scsi_device_lock(sc_link);
|
||||
if (error)
|
||||
return error;
|
||||
@ -793,7 +628,6 @@ sd_ioctl(dev_t dev, u_long cmd, caddr_t addr, int flag, struct proc *p,
|
||||
return (error);
|
||||
if (PARTITION(dev) != RAW_PART)
|
||||
return (ENOTTY);
|
||||
#endif /* ! SLICE */ /* really only take this from the ctl device XXX */
|
||||
return (scsi_do_ioctl(dev, cmd, addr, flag, p, sc_link));
|
||||
}
|
||||
|
||||
@ -1009,7 +843,6 @@ sd_get_parms(int unit, int flags)
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
static int
|
||||
sdsize(dev_t dev)
|
||||
{
|
||||
@ -1021,7 +854,6 @@ sdsize(dev_t dev)
|
||||
return (dssize(dev, &sd->dk_slices, sdopen, sdclose));
|
||||
}
|
||||
|
||||
#endif /* ! SLICE */
|
||||
/*
|
||||
* sense handler: Called to determine what to do when the
|
||||
* device returns a CHECK CONDITION.
|
||||
@ -1080,22 +912,15 @@ sd_sense_handler(struct scsi_xfer *xs)
|
||||
* at offset 'dumplo' into the partition.
|
||||
* XXX for SLICE starts at argument 'start'.
|
||||
*/
|
||||
#ifndef SLICE
|
||||
static errval
|
||||
sddump(dev_t dev)
|
||||
#else
|
||||
static int
|
||||
sdsdump(void *private, int32_t start, int32_t num)
|
||||
#endif /* SLICE */
|
||||
{ /* dump core after a system crash */
|
||||
#ifndef SLICE
|
||||
struct disklabel *lp;
|
||||
int32_t num; /* number of sectors to write */
|
||||
u_int32_t unit, part;
|
||||
int32_t nblocks;
|
||||
int32_t blkoff;
|
||||
static int sddoingadump = 0;
|
||||
#endif /* SLICE */
|
||||
register struct scsi_data *sd; /* disk unit to do the IO */
|
||||
struct scsi_link *sc_link;
|
||||
int32_t blknum, blkcnt = MAXTRANSFER;
|
||||
@ -1106,7 +931,6 @@ sdsdump(void *private, int32_t start, int32_t num)
|
||||
|
||||
addr = (char *) 0; /* starting address */
|
||||
|
||||
#ifndef SLICE
|
||||
/* toss any characters present prior to dump */
|
||||
while (cncheckc() != -1) ;
|
||||
|
||||
@ -1121,17 +945,12 @@ sdsdump(void *private, int32_t start, int32_t num)
|
||||
return ENXIO;
|
||||
|
||||
sd = sc_link->sd;
|
||||
#else
|
||||
sd = private;
|
||||
sc_link = sd->sc_link;
|
||||
#endif /* SLICE */
|
||||
|
||||
/* was it ever initialized etc. ? */
|
||||
if (!(sd->flags & SDINIT))
|
||||
return (ENXIO);
|
||||
if ((sc_link->flags & SDEV_MEDIA_LOADED) != SDEV_MEDIA_LOADED)
|
||||
return (ENXIO);
|
||||
#ifndef SLICE
|
||||
if (sd->dk_slices == NULL)
|
||||
Debugger("sddump: no slices");
|
||||
if ((lp = dsgetlabel(dev, sd->dk_slices)) == NULL)
|
||||
@ -1157,9 +976,6 @@ sdsdump(void *private, int32_t start, int32_t num)
|
||||
sddoingadump = 1;
|
||||
|
||||
blknum = dumplo + blkoff;
|
||||
#else
|
||||
blknum = start;
|
||||
#endif /* SLICE */
|
||||
while (num > 0) {
|
||||
if (is_physical_memory((vm_offset_t)addr))
|
||||
pmap_enter(kernel_pmap, (vm_offset_t)CADDR1,
|
||||
@ -1234,7 +1050,6 @@ sdsdump(void *private, int32_t start, int32_t num)
|
||||
return (0);
|
||||
}
|
||||
|
||||
#ifndef SLICE
|
||||
static sd_devsw_installed = 0;
|
||||
|
||||
static void sd_drvinit(void *unused)
|
||||
@ -1248,76 +1063,3 @@ static void sd_drvinit(void *unused)
|
||||
|
||||
SYSINIT(sddev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,sd_drvinit,NULL)
|
||||
|
||||
#endif /* !SLICE */
|
||||
#ifdef SLICE
|
||||
|
||||
/*
|
||||
* arguments, and schedules the transfer. Does not wait for the transfer
|
||||
* to complete. Multi-page transfers are supported. All I/O requests must
|
||||
* be a multiple of a sector in length.
|
||||
scsi_strategy(bp, &sd_switch);
|
||||
*/
|
||||
static void
|
||||
sdsIOreq(void *private ,struct buf *bp)
|
||||
{
|
||||
struct scsi_data *sd = private;
|
||||
u_int32_t opri;
|
||||
u_int32_t unit = sd->unit;
|
||||
struct scsi_link *sc_link = sd->sc_link;
|
||||
|
||||
SC_DEBUG(sc_link, SDEV_DB2, ("sdIOreq\n"));
|
||||
SC_DEBUG(sc_link, SDEV_DB1, ("%ld bytes @ blk%ld\n",
|
||||
bp->b_bcount, bp->b_pblkno));
|
||||
|
||||
bp->b_resid = 0;
|
||||
bp->b_error = 0;
|
||||
|
||||
(*sc_link->adapter->scsi_minphys)(bp);
|
||||
|
||||
sdstrats++;
|
||||
/*
|
||||
* If the device has been made invalid, error out
|
||||
*/
|
||||
if (!(sc_link->flags & SDEV_MEDIA_LOADED)) {
|
||||
bp->b_error = EIO;
|
||||
goto bad;
|
||||
}
|
||||
|
||||
/*
|
||||
* check it's not too big a transfer for our adapter
|
||||
*/
|
||||
/*scsi_minphys(bp,&sd_switch);*/
|
||||
|
||||
opri = SPLSD();
|
||||
/*
|
||||
* Use a bounce buffer if necessary
|
||||
*/
|
||||
#ifdef BOUNCE_BUFFERS
|
||||
if (sc_link->flags & SDEV_BOUNCE)
|
||||
vm_bounce_alloc(bp);
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Place it in the queue of disk activities for this disk
|
||||
*/
|
||||
#ifdef SDDISKSORT
|
||||
bufq_disksort(&sd->buf_queue, bp);
|
||||
#else
|
||||
bufq_insert_tail(&sd->buf_queue, bp);
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Tell the device to get going on the transfer if it's
|
||||
* not doing anything, otherwise just wait for completion
|
||||
*/
|
||||
sdstart(unit, 0);
|
||||
|
||||
splx(opri);
|
||||
return;
|
||||
bad:
|
||||
bp->b_flags |= B_ERROR;
|
||||
bp->b_resid = bp->b_bcount;
|
||||
biodone(bp);
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
@ -40,7 +40,7 @@
|
||||
*/
|
||||
|
||||
|
||||
#ident "$Id: dpt.h,v 1.3 1998/06/02 00:32:37 eivind Exp $"
|
||||
#ident "$Id: dpt.h,v 1.4 1998/08/05 00:54:37 eivind Exp $"
|
||||
|
||||
#ifndef _DPT_H
|
||||
#define _DPT_H
|
||||
@ -49,10 +49,6 @@
|
||||
|
||||
#ifdef DEVFS
|
||||
#include <sys/devfsext.h>
|
||||
#ifdef SLICE
|
||||
#include <sys/device.h>
|
||||
#include <dev/slice/slice.h>
|
||||
#endif /* SLICE */
|
||||
#endif
|
||||
|
||||
#define DPT_CDEV_MAJOR 88
|
||||
|
@ -31,10 +31,9 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)ffs_vfsops.c 8.31 (Berkeley) 5/20/95
|
||||
* $Id: ffs_vfsops.c,v 1.85 1998/08/17 19:09:36 bde Exp $
|
||||
* $Id: ffs_vfsops.c,v 1.86 1998/09/07 13:17:06 bde Exp $
|
||||
*/
|
||||
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
#include "opt_quota.h"
|
||||
|
||||
#include <sys/param.h>
|
||||
@ -126,9 +125,6 @@ VFS_SET(ufs_vfsops, ufs, 0);
|
||||
* system call will fail with EFAULT in copyinstr in
|
||||
* namei() if it is a genuine NULL from the user.
|
||||
*/
|
||||
#ifdef SLICE
|
||||
extern struct vnode *root_device_vnode;
|
||||
#endif
|
||||
static int
|
||||
ffs_mount( mp, path, data, ndp, p)
|
||||
struct mount *mp; /* mount struct pointer*/
|
||||
@ -158,13 +154,6 @@ ffs_mount( mp, path, data, ndp, p)
|
||||
***
|
||||
*/
|
||||
|
||||
#ifdef SLICE
|
||||
rootvp = root_device_vnode;
|
||||
if (rootvp == NULL) {
|
||||
printf("ffs_mountroot: rootvp not set");
|
||||
return (EINVAL);
|
||||
}
|
||||
#else /* !SLICE */
|
||||
if ((err = bdevvp(rootdev, &rootvp))) {
|
||||
printf("ffs_mountroot: can't find rootvp");
|
||||
return (err);
|
||||
@ -174,7 +163,6 @@ ffs_mount( mp, path, data, ndp, p)
|
||||
mp->mnt_flag |= MNT_NOCLUSTERR;
|
||||
if (bdevsw[major(rootdev)]->d_flags & D_NOCLUSTERW)
|
||||
mp->mnt_flag |= MNT_NOCLUSTERW;
|
||||
#endif /* !SLICE */
|
||||
if( ( err = ffs_mountfs(rootvp, mp, p, M_FFSNODE)) != 0) {
|
||||
/* fs specific cleanup (if any)*/
|
||||
goto error_1;
|
||||
|
@ -31,12 +31,11 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)mfs_vfsops.c 8.11 (Berkeley) 6/19/95
|
||||
* $Id: mfs_vfsops.c,v 1.43 1998/05/11 19:27:18 julian Exp $
|
||||
* $Id: mfs_vfsops.c,v 1.44 1998/09/07 13:17:06 bde Exp $
|
||||
*/
|
||||
|
||||
|
||||
#include "opt_mfs.h"
|
||||
#include "opt_devfs.h" /* for SLICE */
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
@ -104,9 +103,6 @@ static struct vfsops mfs_vfsops = {
|
||||
|
||||
VFS_SET(mfs_vfsops, mfs, 0);
|
||||
|
||||
#ifdef SLICE
|
||||
extern struct vnode *root_device_vnode;
|
||||
#endif /* SLICE */
|
||||
#ifdef MFS_ROOT
|
||||
|
||||
static u_char mfs_root[MFS_ROOT*1024] = "MFS Filesystem goes here";
|
||||
@ -281,14 +277,10 @@ mfs_mount(mp, path, data, ndp, p)
|
||||
rootdev = makedev(255, mfs_minor++);
|
||||
printf("rootfs is %ld Kbyte compiled in MFS\n",
|
||||
mfs_rootsize/1024);
|
||||
#ifdef SLICE
|
||||
rootvp=root_device_vnode;
|
||||
#else /* !SLICE */
|
||||
if ((err = bdevvp(rootdev, &rootvp))) {
|
||||
printf("mfs_mountroot: can't find rootvp");
|
||||
return (err);
|
||||
}
|
||||
#endif /* !SLICE */
|
||||
|
||||
/*
|
||||
* FS specific handling
|
||||
|
Loading…
Reference in New Issue
Block a user