Module Name: src
Committed By: nat
Date: Mon Oct 28 14:36:43 UTC 2024
Modified Files:
src/sys/dev/ic: ncr5380sbc.c
src/sys/dev/scsipi: scsipi_base.c scsipiconf.h
Log Message:
Introduce scsipi_done_once.
This allows for transfers to be sucessfully aborted on the ncr5380sbc(4).
This may be usefull in future for other scsi controllers.
Callers of scsipi_done are not affected by this change.
Part of kern/58452.
As posted to tech-kern:
https://mail-index.netbsd.org/tech-kern/2024/08/02/msg029652.html
Ok thorpej@.
To generate a diff of this commit:
cvs rdiff -u -r1.71 -r1.72 src/sys/dev/ic/ncr5380sbc.c
cvs rdiff -u -r1.190 -r1.191 src/sys/dev/scsipi/scsipi_base.c
cvs rdiff -u -r1.131 -r1.132 src/sys/dev/scsipi/scsipiconf.h
Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.
Modified files:
Index: src/sys/dev/ic/ncr5380sbc.c
diff -u src/sys/dev/ic/ncr5380sbc.c:1.71 src/sys/dev/ic/ncr5380sbc.c:1.72
--- src/sys/dev/ic/ncr5380sbc.c:1.71 Mon Oct 28 14:32:04 2024
+++ src/sys/dev/ic/ncr5380sbc.c Mon Oct 28 14:36:43 2024
@@ -1,4 +1,4 @@
-/* $NetBSD: ncr5380sbc.c,v 1.71 2024/10/28 14:32:04 nat Exp $ */
+/* $NetBSD: ncr5380sbc.c,v 1.72 2024/10/28 14:36:43 nat Exp $ */
/*
* Copyright (c) 1995 David Jones, Gordon W. Ross
@@ -71,7 +71,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: ncr5380sbc.c,v 1.71 2024/10/28 14:32:04 nat Exp $");
+__KERNEL_RCSID(0, "$NetBSD: ncr5380sbc.c,v 1.72 2024/10/28 14:36:43 nat Exp $");
#include "opt_ddb.h"
@@ -808,10 +808,13 @@ finish:
sc->sc_ncmds--;
/* Tell common SCSI code it is done. */
- scsipi_done(xs);
+ scsipi_done_once(xs);
sc->sc_state = NCR_IDLE;
/* Now ncr5380_sched() may be called again. */
+
+ /* Check the queue. */
+ scsipi_channel_thaw(&sc->sc_channel, 0);
}
Index: src/sys/dev/scsipi/scsipi_base.c
diff -u src/sys/dev/scsipi/scsipi_base.c:1.190 src/sys/dev/scsipi/scsipi_base.c:1.191
--- src/sys/dev/scsipi/scsipi_base.c:1.190 Fri Jun 14 18:44:18 2024
+++ src/sys/dev/scsipi/scsipi_base.c Mon Oct 28 14:36:43 2024
@@ -1,4 +1,4 @@
-/* $NetBSD: scsipi_base.c,v 1.190 2024/06/14 18:44:18 kardel Exp $ */
+/* $NetBSD: scsipi_base.c,v 1.191 2024/10/28 14:36:43 nat Exp $ */
/*-
* Copyright (c) 1998, 1999, 2000, 2002, 2003, 2004 The NetBSD Foundation, Inc.
@@ -31,7 +31,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: scsipi_base.c,v 1.190 2024/06/14 18:44:18 kardel Exp $");
+__KERNEL_RCSID(0, "$NetBSD: scsipi_base.c,v 1.191 2024/10/28 14:36:43 nat Exp $");
#ifdef _KERNEL_OPT
#include "opt_scsi.h"
@@ -96,6 +96,8 @@ SDT_PROBE_DEFINE1(scsi, base, xfer, rest
SDT_PROBE_DEFINE1(scsi, base, xfer, free, "struct scsipi_xfer *"/*xs*/);
static int scsipi_complete(struct scsipi_xfer *);
+static struct scsipi_channel*
+ scsipi_done_internal(struct scsipi_xfer *, bool);
static void scsipi_request_sense(struct scsipi_xfer *);
static int scsipi_enqueue(struct scsipi_xfer *);
static void scsipi_run_queue(struct scsipi_channel *chan);
@@ -1597,6 +1599,28 @@ scsipi_free_opcodeinfo(struct scsipi_per
void
scsipi_done(struct scsipi_xfer *xs)
{
+ struct scsipi_channel *chan;
+ /*
+ * If there are more xfers on the channel's queue, attempt to
+ * run them.
+ */
+ if ((chan = scsipi_done_internal(xs, true)) != NULL)
+ scsipi_run_queue(chan);
+}
+
+/*
+ * Just like scsipi_done(), but no recursion. Useful if aborting the current
+ * transfer.
+ */
+void
+scsipi_done_once(struct scsipi_xfer *xs)
+{
+ (void)scsipi_done_internal(xs, false);
+}
+
+static struct scsipi_channel*
+scsipi_done_internal(struct scsipi_xfer *xs, bool more)
+{
struct scsipi_periph *periph = xs->xs_periph;
struct scsipi_channel *chan = periph->periph_channel;
int freezecnt;
@@ -1685,7 +1709,7 @@ scsipi_done(struct scsipi_xfer *xs)
*/
if (xs->xs_control & XS_CTL_POLL) {
mutex_exit(chan_mtx(chan));
- return;
+ return NULL;
}
cv_broadcast(xs_cv(xs));
mutex_exit(chan_mtx(chan));
@@ -1697,7 +1721,7 @@ scsipi_done(struct scsipi_xfer *xs)
* without error; no use in taking a context switch
* if we can handle it in interrupt context.
*/
- if (xs->error == XS_NOERROR) {
+ if (xs->error == XS_NOERROR && more == true) {
mutex_exit(chan_mtx(chan));
(void) scsipi_complete(xs);
goto out;
@@ -1712,11 +1736,7 @@ scsipi_done(struct scsipi_xfer *xs)
mutex_exit(chan_mtx(chan));
out:
- /*
- * If there are more xfers on the channel's queue, attempt to
- * run them.
- */
- scsipi_run_queue(chan);
+ return chan;
}
/*
Index: src/sys/dev/scsipi/scsipiconf.h
diff -u src/sys/dev/scsipi/scsipiconf.h:1.131 src/sys/dev/scsipi/scsipiconf.h:1.132
--- src/sys/dev/scsipi/scsipiconf.h:1.131 Sat Jun 22 10:07:46 2024
+++ src/sys/dev/scsipi/scsipiconf.h Mon Oct 28 14:36:43 2024
@@ -1,4 +1,4 @@
-/* $NetBSD: scsipiconf.h,v 1.131 2024/06/22 10:07:46 palle Exp $ */
+/* $NetBSD: scsipiconf.h,v 1.132 2024/10/28 14:36:43 nat Exp $ */
/*-
* Copyright (c) 1998, 1999, 2000, 2004 The NetBSD Foundation, Inc.
@@ -702,6 +702,7 @@ int scsipi_mode_sense_big(struct scsipi_
struct scsi_mode_parameter_header_10 *, int, int, int, int);
int scsipi_start(struct scsipi_periph *, int, int);
void scsipi_done(struct scsipi_xfer *);
+void scsipi_done_once(struct scsipi_xfer *);
void scsipi_user_done(struct scsipi_xfer *);
int scsipi_interpret_sense(struct scsipi_xfer *);
void scsipi_wait_drain(struct scsipi_periph *);