summaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
authorDavid Gwynne <dlg@cvs.openbsd.org>2006-03-17 13:34:24 +0000
committerDavid Gwynne <dlg@cvs.openbsd.org>2006-03-17 13:34:24 +0000
commit5ebc1b8cd4ac1770d6a9909fa3632d0299144620 (patch)
treea73d12f0f38e6ec790bd1faf336b549256f59890 /sys
parent6a057bae05c6ce0405bde047dc35a2d059a1d692 (diff)
split the completion path up. its now the responsibility of the the path
that sets the command up to say how its should be completed. this means we dont have to complicate a generic handler to cope with all the different setup paths. however, at the moment we're using the generic complicated one :)
Diffstat (limited to 'sys')
-rw-r--r--sys/dev/ic/ami.c28
-rw-r--r--sys/dev/ic/amivar.h4
2 files changed, 26 insertions, 6 deletions
diff --git a/sys/dev/ic/ami.c b/sys/dev/ic/ami.c
index a854fed92df..be8c3e38432 100644
--- a/sys/dev/ic/ami.c
+++ b/sys/dev/ic/ami.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ami.c,v 1.120 2006/03/17 10:49:12 dlg Exp $ */
+/* $OpenBSD: ami.c,v 1.121 2006/03/17 13:34:23 dlg Exp $ */
/*
* Copyright (c) 2001 Michael Shalayeff
@@ -130,6 +130,7 @@ int ami_cmd(struct ami_ccb *, int, int);
int ami_start(struct ami_softc *, struct ami_ccb *);
int ami_poll(struct ami_softc *, struct ami_ccb *);
int ami_done(struct ami_softc *, int);
+int ami_done_ccb(struct ami_softc *, struct ami_ccb *);
void ami_copy_internal_data(struct scsi_xfer *, void *, size_t);
int ami_inquire(struct ami_softc *, u_int8_t);
@@ -1112,7 +1113,6 @@ int
ami_done(struct ami_softc *sc, int idx)
{
struct ami_ccb *ccb = &sc->sc_ccbs[idx - 1];
- struct scsi_xfer *xs = ccb->ccb_xs;
int s;
AMI_DPRINTF(AMI_D_CMD, ("done(%d) ", ccb->ccb_cmd.acc_id));
@@ -1126,6 +1126,18 @@ ami_done(struct ami_softc *sc, int idx)
s = splbio();
ccb->ccb_state = AMI_CCB_READY;
TAILQ_REMOVE(&sc->sc_ccbq, ccb, ccb_link);
+ splx(s);
+
+ ccb->ccb_done(sc, ccb);
+
+ return (0);
+}
+
+int
+ami_done_ccb(struct ami_softc *sc, struct ami_ccb *ccb)
+{
+ struct scsi_xfer *xs = ccb->ccb_xs;
+ int s;
if (ccb->ccb_data != NULL) {
bus_dmamap_sync(sc->sc_dmat, ccb->ccb_dmamap, 0,
@@ -1143,8 +1155,11 @@ ami_done(struct ami_softc *sc, int idx)
if (ccb->ccb_wakeup) {
ccb->ccb_wakeup = 0;
wakeup(ccb);
- } else
+ } else {
+ s = splbio();
ami_put_ccb(ccb);
+ splx(s);
+ }
if (xs) {
timeout_del(&xs->stimeout);
@@ -1154,8 +1169,6 @@ ami_done(struct ami_softc *sc, int idx)
scsi_done(xs);
}
- splx(s);
-
return (0);
}
@@ -1229,6 +1242,7 @@ ami_scsi_raw_cmd(struct scsi_xfer *xs)
ccb->ccb_len = xs->datalen;
ccb->ccb_data = xs->data;
ccb->ccb_dir = (xs->flags & SCSI_DATA_IN) ? AMI_CCB_IN : AMI_CCB_OUT;
+ ccb->ccb_done = ami_done_ccb;
ccb->ccb_cmd.acc_cmd = AMI_PASSTHRU;
ccb->ccb_cmd.acc_passthru.apt_data = ccb->ccb_ptpa;
@@ -1384,6 +1398,7 @@ ami_scsi_cmd(struct scsi_xfer *xs)
}
ccb->ccb_xs = xs;
+ ccb->ccb_done = ami_done_ccb;
if (xs->timeout < 30000)
xs->timeout = 30000; /* at least 30sec */
@@ -1502,6 +1517,7 @@ ami_scsi_cmd(struct scsi_xfer *xs)
ccb->ccb_len = xs->datalen;
ccb->ccb_data = xs->data;
ccb->ccb_dir = (xs->flags & SCSI_DATA_IN) ? AMI_CCB_IN : AMI_CCB_OUT;
+ ccb->ccb_done = ami_done_ccb;
cmd = &ccb->ccb_cmd;
cmd->acc_cmd = (xs->flags & SCSI_DATA_IN) ? AMI_READ : AMI_WRITE;
@@ -1686,6 +1702,7 @@ ami_drv_inq(struct ami_softc *sc, u_int8_t ch, u_int8_t tg, u_int8_t page,
ccb->ccb_data = inqbuf;
ccb->ccb_len = sizeof(struct scsi_inquiry_data);
ccb->ccb_dir = AMI_CCB_IN;
+ ccb->ccb_done = ami_done_ccb;
ccb->ccb_cmd.acc_cmd = AMI_PASSTHRU;
ccb->ccb_cmd.acc_passthru.apt_data = ccb->ccb_ptpa;
@@ -1757,6 +1774,7 @@ ami_mgmt(struct ami_softc *sc, u_int8_t opcode, u_int8_t par1, u_int8_t par2,
}
ccb->ccb_data = NULL;
+ ccb->ccb_done = ami_done_ccb;
ccb->ccb_wakeup = 1;
cmd = &ccb->ccb_cmd;
diff --git a/sys/dev/ic/amivar.h b/sys/dev/ic/amivar.h
index e079c08c531..9b1027c139e 100644
--- a/sys/dev/ic/amivar.h
+++ b/sys/dev/ic/amivar.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: amivar.h,v 1.38 2006/03/17 10:49:12 dlg Exp $ */
+/* $OpenBSD: amivar.h,v 1.39 2006/03/17 13:34:23 dlg Exp $ */
/*
* Copyright (c) 2001 Michael Shalayeff
@@ -64,6 +64,8 @@ struct ami_ccb {
AMI_CCB_OUT
} ccb_dir;
bus_dmamap_t ccb_dmamap;
+ int (*ccb_done)(struct ami_softc *sc,
+ struct ami_ccb *ccb);
volatile int ccb_wakeup;