From: Tejun Heo <htejun@gmail.com>
To: jgarzik@pobox.com, alan@lxorguk.ukuu.org.uk, axboe@suse.de,
albertcc@tw.ibm.com, forrest.zhao@intel.com, efalk@google.com,
linux-ide@vger.kernel.org
Cc: Tejun Heo <htejun@gmail.com>
Subject: [PATCH 06/11] libata-eh-fw: implement ata_port_schedule_eh() and ata_port_abort()
Date: Thu, 11 May 2006 21:27:24 +0900 [thread overview]
Message-ID: <11473504442652-git-send-email-htejun@gmail.com> (raw)
In-Reply-To: <11473504433328-git-send-email-htejun@gmail.com>
ata_port_schedule_eh() directly schedules EH for @ap without
associated qc. Once EH scheduled, no further qc is allowed and EH
kicks in as soon as all currently active qc's are drained.
ata_port_abort() schedules all currently active commands for EH by
qc_completing them with ATA_QCFLAG_FAILED set. If ata_port_abort()
doesn't find any qc to abort, it directly schedule EH using
ata_port_schedule_eh().
These two functions provide ways to invoke EH for conditions which
aren't directly related to any specfic qc.
Signed-off-by: Tejun Heo <htejun@gmail.com>
---
drivers/scsi/libata-core.c | 2 ++
drivers/scsi/libata-eh.c | 54 ++++++++++++++++++++++++++++++++++++++++++++
drivers/scsi/libata-scsi.c | 23 +++++++++++++++++++
drivers/scsi/libata.h | 1 +
include/linux/libata.h | 4 +++
5 files changed, 84 insertions(+), 0 deletions(-)
8bf0da935c2cc87ba065a10866fdf212cc0abe37
diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c
index 2b18033..7483518 100644
--- a/drivers/scsi/libata-core.c
+++ b/drivers/scsi/libata-core.c
@@ -5382,5 +5382,7 @@ EXPORT_SYMBOL_GPL(ata_scsi_device_suspen
EXPORT_SYMBOL_GPL(ata_scsi_device_resume);
EXPORT_SYMBOL_GPL(ata_eng_timeout);
+EXPORT_SYMBOL_GPL(ata_port_schedule_eh);
+EXPORT_SYMBOL_GPL(ata_port_abort);
EXPORT_SYMBOL_GPL(ata_eh_qc_complete);
EXPORT_SYMBOL_GPL(ata_eh_qc_retry);
diff --git a/drivers/scsi/libata-eh.c b/drivers/scsi/libata-eh.c
index 471846f..037a561 100644
--- a/drivers/scsi/libata-eh.c
+++ b/drivers/scsi/libata-eh.c
@@ -237,6 +237,60 @@ void ata_qc_schedule_eh(struct ata_queue
scsi_req_abort_cmd(qc->scsicmd);
}
+/**
+ * ata_port_schedule_eh - schedule error handling without a qc
+ * @ap: ATA port to schedule EH for
+ *
+ * Schedule error handling for @ap. EH will kick in as soon as
+ * all commands are drained.
+ *
+ * LOCKING:
+ * spin_lock_irqsave(host_set lock)
+ */
+void ata_port_schedule_eh(struct ata_port *ap)
+{
+ WARN_ON(!ap->ops->error_handler);
+
+ ap->flags |= ATA_FLAG_EH_PENDING;
+ ata_schedule_scsi_eh(ap->host);
+
+ DPRINTK("port EH scheduled\n");
+}
+
+/**
+ * ata_port_abort - abort all qc's on the port
+ * @ap: ATA port to abort qc's for
+ *
+ * Abort all active qc's of @ap and schedule EH.
+ *
+ * LOCKING:
+ * spin_lock_irqsave(host_set lock)
+ *
+ * RETURNS:
+ * Number of aborted qc's.
+ */
+int ata_port_abort(struct ata_port *ap)
+{
+ int tag, nr_aborted = 0;
+
+ WARN_ON(!ap->ops->error_handler);
+
+ for (tag = 0; tag < ATA_MAX_QUEUE; tag++) {
+ struct ata_queued_cmd *qc = ata_qc_from_tag(ap, tag);
+
+ if (qc) {
+ qc->flags |= ATA_QCFLAG_FAILED;
+ ata_qc_complete(qc);
+ nr_aborted++;
+ }
+ }
+
+ if (!nr_aborted)
+ ata_port_schedule_eh(ap);
+
+ return nr_aborted;
+}
+
static void ata_eh_scsidone(struct scsi_cmnd *scmd)
{
/* nada */
diff --git a/drivers/scsi/libata-scsi.c b/drivers/scsi/libata-scsi.c
index a9b4083..fd7064b 100644
--- a/drivers/scsi/libata-scsi.c
+++ b/drivers/scsi/libata-scsi.c
@@ -2596,3 +2596,26 @@ void ata_scsi_scan_host(struct ata_port
}
}
+/**
+ * ata_schedule_scsi_eh - schedule EH for SCSI host
+ * @shost: SCSI host to invoke error handling on.
+ *
+ * Schedule SCSI EH without scmd. This is a hack.
+ *
+ * LOCKING:
+ * spin_lock_irqsave(host_set lock)
+ **/
+void ata_schedule_scsi_eh(struct Scsi_Host *shost)
+{
+ unsigned long flags;
+
+ spin_lock_irqsave(shost->host_lock, flags);
+
+ if (scsi_host_set_state(shost, SHOST_RECOVERY) == 0 ||
+ scsi_host_set_state(shost, SHOST_CANCEL_RECOVERY) == 0) {
+ shost->host_eh_scheduled++;
+ scsi_eh_wakeup(shost);
+ }
+
+ spin_unlock_irqrestore(shost->host_lock, flags);
+}
diff --git a/drivers/scsi/libata.h b/drivers/scsi/libata.h
index 1e81c37..e2bbddf 100644
--- a/drivers/scsi/libata.h
+++ b/drivers/scsi/libata.h
@@ -98,6 +98,7 @@ extern void ata_scsi_set_sense(struct sc
extern void ata_scsi_rbuf_fill(struct ata_scsi_args *args,
unsigned int (*actor) (struct ata_scsi_args *args,
u8 *rbuf, unsigned int buflen));
+extern void ata_schedule_scsi_eh(struct Scsi_Host *shost);
/* libata-eh.c */
extern enum scsi_eh_timer_return ata_scsi_timed_out(struct scsi_cmnd *cmd);
diff --git a/include/linux/libata.h b/include/linux/libata.h
index fbabfb6..4221d7a 100644
--- a/include/linux/libata.h
+++ b/include/linux/libata.h
@@ -662,6 +662,10 @@ extern unsigned long ata_pci_default_fil
* EH
*/
extern void ata_eng_timeout(struct ata_port *ap);
+
+extern void ata_port_schedule_eh(struct ata_port *ap);
+extern int ata_port_abort(struct ata_port *ap);
+
extern void ata_eh_qc_complete(struct ata_queued_cmd *qc);
extern void ata_eh_qc_retry(struct ata_queued_cmd *qc);
--
1.2.4
next prev parent reply other threads:[~2006-05-11 12:27 UTC|newest]
Thread overview: 20+ messages / expand[flat|nested] mbox.gz Atom feed top
2006-05-11 12:27 [PATCHSET 02/11] new EH framework, take 3 Tejun Heo
2006-05-11 12:27 ` [PATCH 03/11] libata-eh-fw: use special reserved tag and qc for internal commands Tejun Heo
2006-05-11 12:27 ` [PATCH 02/11] libata-eh-fw: clear SError in ata_std_postreset() Tejun Heo
2006-05-11 12:27 ` [PATCH 01/11] libata-eh-fw: add flags and operations for new EH Tejun Heo
2006-05-11 12:27 ` [PATCH 04/11] libata-eh-fw: update ata_qc_from_tag() to enforce normal/EH qc ownership Tejun Heo
2006-05-11 12:27 ` [PATCH 11/11] libata-eh-fw: update SCSI command completion path for new EH Tejun Heo
2006-05-11 12:27 ` [PATCH 07/11] libata-eh-fw: implement freeze/thaw Tejun Heo
2006-05-16 10:15 ` Albert Lee
2006-05-16 10:30 ` Tejun Heo
2006-05-16 10:43 ` Albert Lee
2006-05-16 11:17 ` Albert Lee
2006-05-11 12:27 ` [PATCH 05/11] libata-eh-fw: implement new EH scheduling via error completion Tejun Heo
2006-05-11 12:27 ` [PATCH 09/11] libata-eh-fw: update ata_scsi_error() for new EH Tejun Heo
2006-05-11 12:27 ` [PATCH 10/11] libata-eh-fw: update ata_exec_internal() " Tejun Heo
2006-05-11 12:27 ` [PATCH 08/11] libata-eh-fw: implement new EH scheduling from PIO Tejun Heo
2006-05-18 10:42 ` Albert Lee
2006-05-18 11:49 ` Tejun Heo
2006-05-19 7:31 ` Albert Lee
2006-05-11 12:27 ` Tejun Heo [this message]
2006-05-13 22:01 ` [PATCHSET 02/11] new EH framework, take 3 Jeff Garzik
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=11473504442652-git-send-email-htejun@gmail.com \
--to=htejun@gmail.com \
--cc=alan@lxorguk.ukuu.org.uk \
--cc=albertcc@tw.ibm.com \
--cc=axboe@suse.de \
--cc=efalk@google.com \
--cc=forrest.zhao@intel.com \
--cc=jgarzik@pobox.com \
--cc=linux-ide@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.