summaryrefslogtreecommitdiff
path: root/sys/dev/sdmmc/sdmmc_scsi.c
diff options
context:
space:
mode:
authorKenneth R Westerback <krw@cvs.openbsd.org>2010-10-25 10:36:50 +0000
committerKenneth R Westerback <krw@cvs.openbsd.org>2010-10-25 10:36:50 +0000
commitab5b296feb0bec49dfe5ed44f70967ac706e5ec5 (patch)
tree2555aea9f79c90de4e835c8390aeb1a770a9dd43 /sys/dev/sdmmc/sdmmc_scsi.c
parentc3b713c556720a031432324a8ad250a278a14461 (diff)
Iopoolification. Tested by mcbride@, dlg@, and Gabriel Kihlman on tech@.
ok dlg@
Diffstat (limited to 'sys/dev/sdmmc/sdmmc_scsi.c')
-rw-r--r--sys/dev/sdmmc/sdmmc_scsi.c50
1 files changed, 25 insertions, 25 deletions
diff --git a/sys/dev/sdmmc/sdmmc_scsi.c b/sys/dev/sdmmc/sdmmc_scsi.c
index 2393278b082..98256ceab30 100644
--- a/sys/dev/sdmmc/sdmmc_scsi.c
+++ b/sys/dev/sdmmc/sdmmc_scsi.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: sdmmc_scsi.c,v 1.25 2010/08/24 14:52:23 blambert Exp $ */
+/* $OpenBSD: sdmmc_scsi.c,v 1.26 2010/10/25 10:36:49 krw Exp $ */
/*
* Copyright (c) 2006 Uwe Stuehler <uwe@openbsd.org>
@@ -70,12 +70,14 @@ struct sdmmc_scsi_softc {
struct sdmmc_ccb *sc_ccbs; /* allocated ccbs */
struct sdmmc_ccb_list sc_ccb_freeq; /* free ccbs */
struct sdmmc_ccb_list sc_ccb_runq; /* queued ccbs */
+ struct mutex sc_ccb_mtx;
+ struct scsi_iopool sc_iopool;
};
int sdmmc_alloc_ccbs(struct sdmmc_scsi_softc *, int);
void sdmmc_free_ccbs(struct sdmmc_scsi_softc *);
-struct sdmmc_ccb *sdmmc_get_ccb(struct sdmmc_scsi_softc *, int);
-void sdmmc_put_ccb(struct sdmmc_ccb *);
+void *sdmmc_ccb_alloc(void *);
+void sdmmc_ccb_free(void *, void *);
void sdmmc_scsi_cmd(struct scsi_xfer *);
void sdmmc_start_xs(struct sdmmc_softc *, struct sdmmc_ccb *);
@@ -133,6 +135,7 @@ sdmmc_scsi_attach(struct sdmmc_softc *sc)
scbus->sc_link.luns = 1;
scbus->sc_link.openings = 1;
scbus->sc_link.adapter = &scbus->sc_adapter;
+ scbus->sc_link.pool = &scbus->sc_iopool;
bzero(&saa, sizeof(saa));
saa.scsi_link = &scbus->sc_link;
@@ -200,6 +203,9 @@ sdmmc_alloc_ccbs(struct sdmmc_scsi_softc *scbus, int nccbs)
TAILQ_INIT(&scbus->sc_ccb_freeq);
TAILQ_INIT(&scbus->sc_ccb_runq);
+ mtx_init(&scbus->sc_ccb_mtx, IPL_BIO);
+ scsi_iopool_init(&scbus->sc_iopool, scbus, sdmmc_ccb_alloc,
+ sdmmc_ccb_free);
for (i = 0; i < nccbs; i++) {
ccb = &scbus->sc_ccbs[i];
@@ -222,40 +228,42 @@ sdmmc_free_ccbs(struct sdmmc_scsi_softc *scbus)
}
}
-struct sdmmc_ccb *
-sdmmc_get_ccb(struct sdmmc_scsi_softc *scbus, int flags)
+void *
+sdmmc_ccb_alloc(void *xscbus)
{
+ struct sdmmc_scsi_softc *scbus = xscbus;
struct sdmmc_ccb *ccb;
- int s;
- s = splbio();
- while ((ccb = TAILQ_FIRST(&scbus->sc_ccb_freeq)) == NULL &&
- !ISSET(flags, SCSI_NOSLEEP))
- tsleep(&scbus->sc_ccb_freeq, PRIBIO, "getccb", 0);
+ mtx_enter(&scbus->sc_ccb_mtx);
+ ccb = TAILQ_FIRST(&scbus->sc_ccb_freeq);
if (ccb != NULL) {
TAILQ_REMOVE(&scbus->sc_ccb_freeq, ccb, ccb_link);
ccb->ccb_state = SDMMC_CCB_READY;
}
- splx(s);
+ mtx_leave(&scbus->sc_ccb_mtx);
+
return ccb;
}
void
-sdmmc_put_ccb(struct sdmmc_ccb *ccb)
+sdmmc_ccb_free(void *xscbus, void *xccb)
{
- struct sdmmc_scsi_softc *scbus = ccb->ccb_scbus;
+ struct sdmmc_scsi_softc *scbus = xscbus;
+ struct sdmmc_ccb *ccb = xccb;
int s;
s = splbio();
if (ccb->ccb_state == SDMMC_CCB_QUEUED)
TAILQ_REMOVE(&scbus->sc_ccb_runq, ccb, ccb_link);
+ splx(s);
+
ccb->ccb_state = SDMMC_CCB_FREE;
ccb->ccb_flags = 0;
ccb->ccb_xs = NULL;
+
+ mtx_enter(&scbus->sc_ccb_mtx);
TAILQ_INSERT_TAIL(&scbus->sc_ccb_freeq, ccb, ccb_link);
- if (TAILQ_NEXT(ccb, ccb_link) == NULL)
- wakeup(&scbus->sc_ccb_freeq);
- splx(s);
+ mtx_leave(&scbus->sc_ccb_mtx);
}
/*
@@ -366,16 +374,9 @@ sdmmc_scsi_cmd(struct scsi_xfer *xs)
return;
}
- ccb = sdmmc_get_ccb(sc->sc_scsibus, xs->flags);
- if (ccb == NULL) {
- printf("%s: out of ccbs\n", DEVNAME(sc));
- xs->error = XS_DRIVER_STUFFUP;
- scsi_done(xs);
- return;
- }
+ ccb = xs->io;
ccb->ccb_xs = xs;
-
ccb->ccb_blockcnt = blockcnt;
ccb->ccb_blockno = blockno;
@@ -458,7 +459,6 @@ sdmmc_done_xs(struct sdmmc_ccb *ccb)
if (ISSET(ccb->ccb_flags, SDMMC_CCB_F_ERR))
xs->error = XS_DRIVER_STUFFUP;
- sdmmc_put_ccb(ccb);
scsi_done(xs);
}