summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatthew Dempsky <matthew@cvs.openbsd.org>2010-07-01 03:20:40 +0000
committerMatthew Dempsky <matthew@cvs.openbsd.org>2010-07-01 03:20:40 +0000
commitb2735ac78382db6f10e2c1a21582733693b825bb (patch)
treeb8011a9cdd5222b156fe4b36da8358ebf62b031f
parent241672bb6dfbe3c1c24caad5b6dc595bb19ffd59 (diff)
Change scsibus(4)'s scsi_link array to an SLIST to save memory on
sparsely populated buses. ok dlg@, krw@
-rw-r--r--sys/arch/mac68k/mac68k/autoconf.c10
-rw-r--r--sys/arch/macppc/dev/mesh.c4
-rw-r--r--sys/arch/sparc/sparc/autoconf.c6
-rw-r--r--sys/dev/atapiscsi/atapiscsi.c4
-rw-r--r--sys/dev/ic/ami.c8
-rw-r--r--sys/dev/ic/cac.c8
-rw-r--r--sys/dev/ic/ciss.c10
-rw-r--r--sys/dev/ic/mfi.c8
-rw-r--r--sys/dev/ic/mpi.c12
-rw-r--r--sys/dev/pci/arc.c6
-rw-r--r--sys/dev/pci/ips.c9
-rw-r--r--sys/dev/pci/mpii.c10
-rw-r--r--sys/scsi/scsiconf.c87
-rw-r--r--sys/scsi/scsiconf.h12
14 files changed, 106 insertions, 88 deletions
diff --git a/sys/arch/mac68k/mac68k/autoconf.c b/sys/arch/mac68k/mac68k/autoconf.c
index 4e4d1235155..f441a840df0 100644
--- a/sys/arch/mac68k/mac68k/autoconf.c
+++ b/sys/arch/mac68k/mac68k/autoconf.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: autoconf.c,v 1.32 2009/03/15 20:40:25 miod Exp $ */
+/* $OpenBSD: autoconf.c,v 1.33 2010/07/01 03:20:37 matthew Exp $ */
/* $NetBSD: autoconf.c,v 1.38 1996/12/18 05:46:09 scottr Exp $ */
/*
@@ -160,8 +160,8 @@ target_to_unit(bus, target, lun)
if (scsibus_cd.cd_devs[bus]) {
scsi = (struct scsibus_softc *)
scsibus_cd.cd_devs[bus];
- if (scsi->sc_link[target][lun]) {
- sc_link = scsi->sc_link[target][lun];
+ sc_link = scsi_get_link(scsi, target, lun);
+ if (sc_link != NULL) {
sc_dev = (struct device *)
sc_link->device_softc;
return sc_dev->dv_unit;
@@ -176,8 +176,8 @@ target_to_unit(bus, target, lun)
}
if (scsibus_cd.cd_devs[bus]) {
scsi = (struct scsibus_softc *) scsibus_cd.cd_devs[bus];
- if (scsi->sc_link[target][lun]) {
- sc_link = scsi->sc_link[target][lun];
+ sc_link = scsi_get_link(scsi, target, lun);
+ if (sc_link != NULL) {
sc_dev = (struct device *) sc_link->device_softc;
return sc_dev->dv_unit;
}
diff --git a/sys/arch/macppc/dev/mesh.c b/sys/arch/macppc/dev/mesh.c
index e5ac438ecc2..cb7d0031f49 100644
--- a/sys/arch/macppc/dev/mesh.c
+++ b/sys/arch/macppc/dev/mesh.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: mesh.c,v 1.27 2010/06/28 18:31:01 krw Exp $ */
+/* $OpenBSD: mesh.c,v 1.28 2010/07/01 03:20:38 matthew Exp $ */
/* $NetBSD: mesh.c,v 1.1 1999/02/19 13:06:03 tsubai Exp $ */
/*-
@@ -176,8 +176,6 @@ struct mesh_softc {
struct device sc_dev; /* us as a device */
struct scsi_link sc_link;
- struct scsibus_softc *sc_scsibus;
-
u_char *sc_reg; /* MESH base address */
bus_dmamap_t sc_dmamap;
bus_dma_tag_t sc_dmat;
diff --git a/sys/arch/sparc/sparc/autoconf.c b/sys/arch/sparc/sparc/autoconf.c
index 914d857cdc7..5473726a7c3 100644
--- a/sys/arch/sparc/sparc/autoconf.c
+++ b/sys/arch/sparc/sparc/autoconf.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: autoconf.c,v 1.89 2010/06/29 21:28:10 miod Exp $ */
+/* $OpenBSD: autoconf.c,v 1.90 2010/07/01 03:20:38 matthew Exp $ */
/* $NetBSD: autoconf.c,v 1.73 1997/07/29 09:41:53 fair Exp $ */
/*
@@ -1707,14 +1707,14 @@ device_register(struct device *dev, void *aux)
#if defined(SUN4)
if (CPU_ISSUN4 && dev->dv_xname[0] == 's' &&
- target == 0 && sbsc->sc_link[0][0] == NULL) {
+ target == 0 && scsi_get_link(sbsc, 0, 0) == NULL) {
/*
* disk unit 0 is magic: if there is actually no
* target 0 scsi device, the PROM will call
* target 3 `sd0'.
* XXX - what if someone puts a tape at target 0?
*/
- /* Note that sc_link[0][0] will be NULL when we are
+ /* Note that sbsc:0:0 will be NULL when we are
* invoked to match the device for target 0, if it
* exists. But then the attachment args will have
* its own target set to zero. It this case, skip
diff --git a/sys/dev/atapiscsi/atapiscsi.c b/sys/dev/atapiscsi/atapiscsi.c
index d03ecfb5de2..e5a3f7c17b2 100644
--- a/sys/dev/atapiscsi/atapiscsi.c
+++ b/sys/dev/atapiscsi/atapiscsi.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: atapiscsi.c,v 1.91 2010/06/28 18:31:01 krw Exp $ */
+/* $OpenBSD: atapiscsi.c,v 1.92 2010/07/01 03:20:38 matthew Exp $ */
/*
* This code is derived from code with the copyright below.
@@ -284,7 +284,7 @@ atapiscsi_attach(parent, self, aux)
if (child != NULL) {
struct scsibus_softc *scsi = (struct scsibus_softc *)child;
- struct scsi_link *link = scsi->sc_link[0][0];
+ struct scsi_link *link = scsi_get_link(scsi, 0, 0);
if (link) {
strlcpy(drvp->drive_name,
diff --git a/sys/dev/ic/ami.c b/sys/dev/ic/ami.c
index 659a60d01a2..0002797ad1b 100644
--- a/sys/dev/ic/ami.c
+++ b/sys/dev/ic/ami.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ami.c,v 1.211 2010/06/28 18:31:02 krw Exp $ */
+/* $OpenBSD: ami.c,v 1.212 2010/07/01 03:20:38 matthew Exp $ */
/*
* Copyright (c) 2001 Michael Shalayeff
@@ -2352,6 +2352,7 @@ ami_create_sensors(struct ami_softc *sc)
{
struct device *dev;
struct scsibus_softc *ssc = NULL;
+ struct scsi_link *link;
int i;
TAILQ_FOREACH(dev, &alldevs, dv_list) {
@@ -2376,10 +2377,11 @@ ami_create_sensors(struct ami_softc *sc)
sizeof(sc->sc_sensordev.xname));
for (i = 0; i < sc->sc_nunits; i++) {
- if (ssc->sc_link[i][0] == NULL)
+ link = scsi_get_link(ssc, i, 0);
+ if (link == NULL)
goto bad;
- dev = ssc->sc_link[i][0]->device_softc;
+ dev = link->device_softc;
sc->sc_sensors[i].type = SENSOR_DRIVE;
sc->sc_sensors[i].status = SENSOR_S_UNKNOWN;
diff --git a/sys/dev/ic/cac.c b/sys/dev/ic/cac.c
index 090cfb4f10a..b6ab9a51917 100644
--- a/sys/dev/ic/cac.c
+++ b/sys/dev/ic/cac.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: cac.c,v 1.39 2010/06/28 18:31:02 krw Exp $ */
+/* $OpenBSD: cac.c,v 1.40 2010/07/01 03:20:38 matthew Exp $ */
/* $NetBSD: cac.c,v 1.15 2000/11/08 19:20:35 ad Exp $ */
/*
@@ -886,6 +886,7 @@ cac_create_sensors(struct cac_softc *sc)
{
struct device *dev;
struct scsibus_softc *ssc = NULL;
+ struct scsi_link *link;
int i;
TAILQ_FOREACH(dev, &alldevs, dv_list) {
@@ -911,10 +912,11 @@ cac_create_sensors(struct cac_softc *sc)
sizeof(sc->sc_sensordev.xname));
for (i = 0; i < sc->sc_nunits; i++) {
- if (ssc->sc_link[i][0] == NULL)
+ link = scsi_get_link(ssc, i, 0);
+ if (link == NULL)
goto bad;
- dev = ssc->sc_link[i][0]->device_softc;
+ dev = link->device_softc;
sc->sc_sensors[i].type = SENSOR_DRIVE;
sc->sc_sensors[i].status = SENSOR_S_UNKNOWN;
diff --git a/sys/dev/ic/ciss.c b/sys/dev/ic/ciss.c
index 1e8c8782c4a..aa922917119 100644
--- a/sys/dev/ic/ciss.c
+++ b/sys/dev/ic/ciss.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ciss.c,v 1.57 2010/06/28 18:31:02 krw Exp $ */
+/* $OpenBSD: ciss.c,v 1.58 2010/07/01 03:20:38 matthew Exp $ */
/*
* Copyright (c) 2005,2006 Michael Shalayeff
@@ -141,6 +141,7 @@ ciss_attach(struct ciss_softc *sc)
struct ciss_ccb *ccb;
struct ciss_cmd *cmd;
struct ciss_inquiry *inq;
+ struct device *dev;
bus_dma_segment_t seg[1];
int error, i, total, rseg, maxfer;
ciss_lock_t lock;
@@ -401,11 +402,10 @@ ciss_attach(struct ciss_softc *sc)
sensor_attach(&sc->sensordev, &sc->sensors[i++])) {
sc->sensors[i].type = SENSOR_DRIVE;
sc->sensors[i].status = SENSOR_S_UNKNOWN;
- strlcpy(sc->sensors[i].desc, ((struct device *)
- scsibus->sc_link[i][0]->device_softc)->dv_xname,
+ dev = scsi_get_link(scsibus, i, 0)->device_softc;
+ strlcpy(sc->sensors[i].desc, dev->dv_xname,
sizeof(sc->sensors[i].desc));
- strlcpy(sc->sc_lds[i]->xname, ((struct device *)
- scsibus->sc_link[i][0]->device_softc)->dv_xname,
+ strlcpy(sc->sc_lds[i]->xname, dev->dv_xname,
sizeof(sc->sc_lds[i]->xname));
}
if (sensor_task_register(sc, ciss_sensors, 10) == NULL)
diff --git a/sys/dev/ic/mfi.c b/sys/dev/ic/mfi.c
index 6c5453e7a63..9d6359f520a 100644
--- a/sys/dev/ic/mfi.c
+++ b/sys/dev/ic/mfi.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: mfi.c,v 1.108 2010/06/30 19:10:05 mk Exp $ */
+/* $OpenBSD: mfi.c,v 1.109 2010/07/01 03:20:38 matthew Exp $ */
/*
* Copyright (c) 2006 Marco Peereboom <marco@peereboom.us>
*
@@ -1894,6 +1894,7 @@ mfi_create_sensors(struct mfi_softc *sc)
{
struct device *dev;
struct scsibus_softc *ssc = NULL;
+ struct scsi_link *link;
int i;
TAILQ_FOREACH(dev, &alldevs, dv_list) {
@@ -1918,10 +1919,11 @@ mfi_create_sensors(struct mfi_softc *sc)
sizeof(sc->sc_sensordev.xname));
for (i = 0; i < sc->sc_ld_cnt; i++) {
- if (ssc->sc_link[i][0] == NULL)
+ link = scsi_get_link(ssc, i, 0);
+ if (link == NULL)
goto bad;
- dev = ssc->sc_link[i][0]->device_softc;
+ dev = link->device_softc;
sc->sc_sensors[i].type = SENSOR_DRIVE;
sc->sc_sensors[i].status = SENSOR_S_UNKNOWN;
diff --git a/sys/dev/ic/mpi.c b/sys/dev/ic/mpi.c
index e13a4878ff5..d269dde2bd4 100644
--- a/sys/dev/ic/mpi.c
+++ b/sys/dev/ic/mpi.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: mpi.c,v 1.152 2010/06/28 18:31:02 krw Exp $ */
+/* $OpenBSD: mpi.c,v 1.153 2010/07/01 03:20:38 matthew Exp $ */
/*
* Copyright (c) 2005, 2006, 2009 David Gwynne <dlg@openbsd.org>
@@ -462,7 +462,7 @@ mpi_run_ppr(struct mpi_softc *sc)
}
for (i = 0; i < sc->sc_buswidth; i++) {
- link = sc->sc_scsibus->sc_link[i][0];
+ link = scsi_get_link(sc->sc_scsibus, i, 0);
if (link == NULL)
continue;
@@ -3026,7 +3026,7 @@ mpi_ioctl_vol(struct mpi_softc *sc, struct bioc_vol *bv)
bv->bv_nodisk = rpg0->num_phys_disks;
for (i = 0, vol = -1; i < sc->sc_buswidth; i++) {
- link = sc->sc_scsibus->sc_link[i][0];
+ link = scsi_get_link(sc->sc_scsibus, i, 0);
if (link == NULL)
continue;
@@ -3139,7 +3139,7 @@ mpi_create_sensors(struct mpi_softc *sc)
/* count volumes */
for (i = 0, vol = 0; i < sc->sc_buswidth; i++) {
- link = sc->sc_scsibus->sc_link[i][0];
+ link = scsi_get_link(sc->sc_scsibus, i, 0);
if (link == NULL)
continue;
/* skip if not a virtual disk */
@@ -3160,7 +3160,7 @@ mpi_create_sensors(struct mpi_softc *sc)
sizeof(sc->sc_sensordev.xname));
for (i = 0, vol= 0; i < sc->sc_buswidth; i++) {
- link = sc->sc_scsibus->sc_link[i][0];
+ link = scsi_get_link(sc->sc_scsibus, i, 0);
if (link == NULL)
continue;
/* skip if not a virtual disk */
@@ -3200,7 +3200,7 @@ mpi_refresh_sensors(void *arg)
rw_enter_write(&sc->sc_lock);
for (i = 0, vol = 0; i < sc->sc_buswidth; i++) {
- link = sc->sc_scsibus->sc_link[i][0];
+ link = scsi_get_link(sc->sc_scsibus, i, 0);
if (link == NULL)
continue;
/* skip if not a virtual disk */
diff --git a/sys/dev/pci/arc.c b/sys/dev/pci/arc.c
index d600be8d7b8..d8f05d61248 100644
--- a/sys/dev/pci/arc.c
+++ b/sys/dev/pci/arc.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: arc.c,v 1.86 2010/06/28 18:40:51 mk Exp $ */
+/* $OpenBSD: arc.c,v 1.87 2010/07/01 03:20:38 matthew Exp $ */
/*
* Copyright (c) 2006 David Gwynne <dlg@openbsd.org>
@@ -1341,8 +1341,8 @@ arc_bio_vol(struct arc_softc *sc, struct bioc_vol *bv)
}
bv->bv_nodisk = volinfo->member_disks;
- sc_link = sc->sc_scsibus->sc_link[volinfo->scsi_attr.target]
- [volinfo->scsi_attr.lun];
+ sc_link = scsi_get_link(sc->sc_scsibus, volinfo->scsi_attr.target,
+ volinfo->scsi_attr.lun);
if (sc_link != NULL) {
dev = sc_link->device_softc;
strlcpy(bv->bv_dev, dev->dv_xname, sizeof(bv->bv_dev));
diff --git a/sys/dev/pci/ips.c b/sys/dev/pci/ips.c
index 07a39e0d20f..ca76bb7ddf6 100644
--- a/sys/dev/pci/ips.c
+++ b/sys/dev/pci/ips.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ips.c,v 1.100 2010/06/30 19:08:59 mk Exp $ */
+/* $OpenBSD: ips.c,v 1.101 2010/07/01 03:20:38 matthew Exp $ */
/*
* Copyright (c) 2006, 2007, 2009 Alexander Yurchenko <grange@openbsd.org>
@@ -593,6 +593,7 @@ ips_attach(struct device *parent, struct device *self, void *aux)
struct ips_adapterinfo *ai;
struct ips_driveinfo *di;
struct ips_pg5 *pg5;
+ struct device *dev;
pcireg_t maptype;
bus_size_t iosize;
pci_intr_handle_t ih;
@@ -800,8 +801,8 @@ ips_attach(struct device *parent, struct device *self, void *aux)
for (i = 0; i < sc->sc_nunits; i++) {
sc->sc_sensors[i].type = SENSOR_DRIVE;
sc->sc_sensors[i].status = SENSOR_S_UNKNOWN;
- strlcpy(sc->sc_sensors[i].desc, ((struct device *)
- sc->sc_scsibus->sc_link[i][0]->device_softc)->dv_xname,
+ dev = scsi_get_link(sc->sc_scsibus, i, 0)->device_softc;
+ strlcpy(sc->sc_sensors[i].desc, dev->dv_xname,
sizeof(sc->sc_sensors[i].desc));
sensor_attach(&sc->sc_sensordev, &sc->sc_sensors[i]);
}
@@ -1194,7 +1195,7 @@ ips_ioctl_vol(struct ips_softc *sc, struct bioc_vol *bv)
}
}
- dv = sc->sc_scsibus->sc_link[vid][0]->device_softc;
+ dv = scsi_get_link(sc->sc_scsibus, vid, 0)->device_softc;
strlcpy(bv->bv_dev, dv->dv_xname, sizeof(bv->bv_dev));
strlcpy(bv->bv_vendor, "IBM", sizeof(bv->bv_vendor));
diff --git a/sys/dev/pci/mpii.c b/sys/dev/pci/mpii.c
index 92b287de1cb..2c3babae74a 100644
--- a/sys/dev/pci/mpii.c
+++ b/sys/dev/pci/mpii.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: mpii.c,v 1.24 2010/06/28 18:31:02 krw Exp $ */
+/* $OpenBSD: mpii.c,v 1.25 2010/07/01 03:20:38 matthew Exp $ */
/*
* Copyright (c) 2010 Mike Belopuhov <mkb@crypt.org.ru>
* Copyright (c) 2009 James Giannoules
@@ -4667,7 +4667,7 @@ mpii_ioctl_vol(struct mpii_softc *sc, struct bioc_vol *bv)
bv->bv_size = letoh64(vpg->max_lba) * letoh16(vpg->block_size);
- lnk = sc->sc_scsibus->sc_link[bv->bv_volid][0];
+ lnk = scsi_get_link(sc->sc_scsibus, bv->bv_volid, 0);
if (lnk != NULL) {
scdev = lnk->device_softc;
strlcpy(bv->bv_dev, scdev->dv_xname, sizeof(bv->bv_dev));
@@ -4973,6 +4973,7 @@ mpii_create_sensors(struct mpii_softc *sc)
{
struct scsibus_softc *ssc = sc->sc_scsibus;
struct device *dev;
+ struct scsi_link *link;
int i;
sc->sc_sensors = malloc(sizeof(struct ksensor) * sc->sc_vd_count,
@@ -4986,10 +4987,11 @@ mpii_create_sensors(struct mpii_softc *sc)
for (i = sc->sc_vd_id_low; i < sc->sc_vd_id_low + sc->sc_vd_count;
i++) {
- if (ssc->sc_link[i][0] == NULL)
+ link = scsi_get_link(ssc, i, 0);
+ if (link == NULL)
goto bad;
- dev = ssc->sc_link[i][0]->device_softc;
+ dev = link->device_softc;
sc->sc_sensors[i].type = SENSOR_DRIVE;
sc->sc_sensors[i].status = SENSOR_S_UNKNOWN;
diff --git a/sys/scsi/scsiconf.c b/sys/scsi/scsiconf.c
index 740f4f1e61e..8c3c53d25a9 100644
--- a/sys/scsi/scsiconf.c
+++ b/sys/scsi/scsiconf.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: scsiconf.c,v 1.159 2010/06/30 19:23:59 deraadt Exp $ */
+/* $OpenBSD: scsiconf.c,v 1.160 2010/07/01 03:20:39 matthew Exp $ */
/* $NetBSD: scsiconf.c,v 1.57 1996/05/02 01:09:01 neil Exp $ */
/*
@@ -155,7 +155,6 @@ scsibusattach(struct device *parent, struct device *self, void *aux)
struct scsibus_softc *sb = (struct scsibus_softc *)self;
struct scsibus_attach_args *saa = aux;
struct scsi_link *sc_link_proto = saa->saa_sc_link;
- int nbytes, i;
if (!cold)
scsi_autoconf = 0;
@@ -182,16 +181,7 @@ scsibusattach(struct device *parent, struct device *self, void *aux)
/* Initialize shared data. */
scsi_init();
- nbytes = sb->sc_buswidth * sizeof(struct scsi_link **);
- sb->sc_link = malloc(nbytes, M_DEVBUF, M_NOWAIT);
- if (sb->sc_link == NULL)
- panic("scsibusattach: can't allocate target links");
- nbytes = sb->adapter_link->luns * sizeof(struct scsi_link *);
- for (i = 0; i < sb->sc_buswidth; i++) {
- sb->sc_link[i] = malloc(nbytes, M_DEVBUF, M_NOWAIT | M_ZERO);
- if (sb->sc_link[i] == NULL)
- panic("scsibusattach: can't allocate lun links");
- }
+ SLIST_INIT(&sb->sc_link);
#if NBIO > 0
if (bio_register(&sb->sc_dev, scsibus_bioctl) != 0)
@@ -247,9 +237,10 @@ scsi_activate_target(struct scsibus_softc *sc, int target, int act)
void
scsi_activate_lun(struct scsibus_softc *sc, int target, int lun, int act)
{
- struct scsi_link *link = sc->sc_link[target][lun];
+ struct scsi_link *link;
struct device *dev;
+ link = scsi_get_link(sc, target, lun);
if (link == NULL)
return;
@@ -287,7 +278,7 @@ int
scsibusdetach(struct device *dev, int type)
{
struct scsibus_softc *sb = (struct scsibus_softc *)dev;
- int i, error;
+ int error;
#if NBIO > 0
bio_unregister(&sb->sc_dev);
@@ -297,12 +288,7 @@ scsibusdetach(struct device *dev, int type)
if (error != 0)
return (error);
- for (i = 0; i < sb->sc_buswidth; i++) {
- if (sb->sc_link[i] != NULL)
- free(sb->sc_link[i], M_DEVBUF);
- }
-
- free(sb->sc_link, M_DEVBUF);
+ KASSERT(SLIST_EMPTY(&sb->sc_link));
/* Free shared data. */
scsi_deinit();
@@ -391,7 +377,7 @@ scsi_probe_target(struct scsibus_softc *sc, int target)
if (scsi_probe_lun(sc, target, 0) == EINVAL)
return (EINVAL);
- link = sc->sc_link[target][0];
+ link = scsi_get_link(sc, target, 0);
if (link == NULL)
return (ENXIO);
@@ -424,9 +410,9 @@ scsi_probe_target(struct scsibus_softc *sc, int target)
continue;
/* Probe the provided LUN. Don't check LUN 0. */
- sc->sc_link[target][0] = NULL;
+ scsi_remove_link(sc, link);
scsi_probe_lun(sc, target, lun);
- sc->sc_link[target][0] = link;
+ scsi_add_link(sc, link);
}
free(report, M_TEMP);
@@ -480,11 +466,8 @@ scsi_detach_target(struct scsibus_softc *sc, int target, int flags)
target == alink->adapter_target)
return (ENXIO);
- if (sc->sc_link[target] == NULL)
- return (ENXIO);
-
for (i = 0; i < alink->luns; i++) { /* nicer backwards? */
- if (sc->sc_link[target][i] == NULL)
+ if (scsi_get_link(sc, target, i) == NULL)
continue;
err = scsi_detach_lun(sc, target, i, flags);
@@ -507,10 +490,7 @@ scsi_detach_lun(struct scsibus_softc *sc, int target, int lun, int flags)
lun < 0 || lun >= alink->luns)
return (ENXIO);
- if (sc->sc_link[target] == NULL)
- return (ENXIO);
-
- link = sc->sc_link[target][lun];
+ link = scsi_get_link(sc, target, lun);
if (link == NULL)
return (ENXIO);
@@ -541,12 +521,36 @@ scsi_detach_lun(struct scsibus_softc *sc, int target, int lun, int flags)
/* 4. free up its state in the midlayer */
if (link->id != NULL)
devid_free(link->id);
+ scsi_remove_link(sc, link);
free(link, M_DEVBUF);
- sc->sc_link[target][lun] = NULL;
return (0);
}
+struct scsi_link *
+scsi_get_link(struct scsibus_softc *sc, int target, int lun)
+{
+ struct scsi_link *link;
+
+ SLIST_FOREACH(link, &sc->sc_link, bus_list)
+ if (link->target == target && link->lun == lun)
+ return (link);
+
+ return (NULL);
+}
+
+void
+scsi_add_link(struct scsibus_softc *sc, struct scsi_link *link)
+{
+ SLIST_INSERT_HEAD(&sc->sc_link, link, bus_list);
+}
+
+void
+scsi_remove_link(struct scsibus_softc *sc, struct scsi_link *link)
+{
+ SLIST_REMOVE(&sc->sc_link, link, scsi_link, bus_list);
+}
+
void
scsi_strvis(u_char *dst, u_char *src, int len)
{
@@ -846,12 +850,12 @@ scsi_probedev(struct scsibus_softc *scsi, int target, int lun)
const struct scsi_quirk_inquiry_pattern *finger;
struct scsi_inquiry_data *inqbuf;
struct scsi_attach_args sa;
- struct scsi_link *sc_link;
+ struct scsi_link *sc_link, *link0;
struct cfdata *cf;
int priority, rslt = 0;
/* Skip this slot if it is already attached and try the next LUN. */
- if (scsi->sc_link[target][lun] != NULL)
+ if (scsi_get_link(scsi, target, lun) != NULL)
return (0);
sc_link = malloc(sizeof(*sc_link), M_DEVBUF, M_NOWAIT);
@@ -948,15 +952,14 @@ scsi_probedev(struct scsibus_softc *scsi, int target, int lun)
scsi_devid(sc_link);
- if (lun == 0 || scsi->sc_link[target][0] == NULL)
+ link0 = scsi_get_link(scsi, target, 0);
+ if (lun == 0 || link0 == NULL)
;
else if (sc_link->flags & SDEV_UMASS)
;
- else if (sc_link->id != NULL &&
- !DEVID_CMP(scsi->sc_link[target][0]->id, sc_link->id))
+ else if (sc_link->id != NULL && !DEVID_CMP(link0->id, sc_link->id))
;
- else if (memcmp(inqbuf, &scsi->sc_link[target][0]->inqdata,
- sizeof(*inqbuf)) == 0) {
+ else if (memcmp(inqbuf, &link0->inqdata, sizeof(*inqbuf)) == 0) {
/* The device doesn't distinguish between LUNs. */
SC_DEBUG(sc_link, SDEV_DB1, ("IDENTIFY not supported.\n"));
rslt = EINVAL;
@@ -970,7 +973,7 @@ scsi_probedev(struct scsibus_softc *scsi, int target, int lun)
scsibus_printlink(sc_link);
printf("\n");
- scsi->sc_link[target][lun] = sc_link;
+ scsi_add_link(scsi, sc_link);
return (0);
}
#endif /* NMPATH */
@@ -1024,7 +1027,7 @@ scsi_probedev(struct scsibus_softc *scsi, int target, int lun)
* point to prevent such helpfulness before it causes confusion.
*/
if (lun == 0 && (sc_link->flags & SDEV_UMASS) &&
- scsi->sc_link[target][1] == NULL && sc_link->luns > 1) {
+ scsi_get_link(scsi, target, 1) == NULL && sc_link->luns > 1) {
struct scsi_inquiry_data tmpinq;
sc_link->lun = 1;
@@ -1032,7 +1035,7 @@ scsi_probedev(struct scsibus_softc *scsi, int target, int lun)
sc_link->lun = 0;
}
- scsi->sc_link[target][lun] = sc_link;
+ scsi_add_link(scsi, sc_link);
/*
* Generate a TEST_UNIT_READY command. This gives drivers waiting for
diff --git a/sys/scsi/scsiconf.h b/sys/scsi/scsiconf.h
index 6aef1f0888d..0a26745ce76 100644
--- a/sys/scsi/scsiconf.h
+++ b/sys/scsi/scsiconf.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: scsiconf.h,v 1.128 2010/06/27 03:34:29 matthew Exp $ */
+/* $OpenBSD: scsiconf.h,v 1.129 2010/07/01 03:20:39 matthew Exp $ */
/* $NetBSD: scsiconf.h,v 1.35 1997/04/02 02:29:38 mycroft Exp $ */
/*
@@ -380,6 +380,8 @@ struct scsi_xshandler {
* as well.
*/
struct scsi_link {
+ SLIST_ENTRY(scsi_link) bus_list;
+
u_int state;
#define SDEV_S_WAITING (1<<0)
#define SDEV_S_DYING (1<<1)
@@ -458,7 +460,7 @@ struct scsibus_attach_args {
struct scsibus_softc {
struct device sc_dev;
struct scsi_link *adapter_link; /* prototype supplied by adapter */
- struct scsi_link ***sc_link;
+ SLIST_HEAD(, scsi_link) sc_link;
u_int16_t sc_buswidth;
};
@@ -610,6 +612,12 @@ int scsi_req_detach(struct scsibus_softc *, int, int, int);
void scsi_activate(struct scsibus_softc *, int, int, int);
+struct scsi_link * scsi_get_link(struct scsibus_softc *, int, int);
+void scsi_add_link(struct scsibus_softc *,
+ struct scsi_link *);
+void scsi_remove_link(struct scsibus_softc *,
+ struct scsi_link *);
+
extern const u_int8_t version_to_spc[];
#define SCSISPC(x)(version_to_spc[(x) & SID_ANSII])