From dd5d2d841e954134a06ea6b6e414b90b9b80b4e5 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Mon, 13 Oct 2008 19:21:28 -0400 Subject: [PATCH] libata: always do follow-up SRST if hardreset returned -EAGAIN commit 5dbfc9cb59d4ad75199949d7dd8a8c6d7bc518df upstream As an optimization, follow-up SRST used to be skipped if classification wasn't requested even when hardreset requested it via -EAGAIN. However, some hardresets can't wait for device readiness and skipping SRST can cause timeout or other failures during revalidation. Always perform follow-up SRST if hardreset returns -EAGAIN. This makes reset paths more predictable and thus less error-prone. While at it, move hardreset error checking such that it's done right after hardreset is finished. This simplifies followup SRST condition check a bit and makes the reset path easier to modify. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik Cc: Chuck Ebbert Signed-off-by: Greg Kroah-Hartman --- drivers/ata/libata-eh.c | 20 ++++++-------------- 1 file changed, 6 insertions(+), 14 deletions(-) diff --git a/drivers/ata/libata-eh.c b/drivers/ata/libata-eh.c index 7894d83ea1eb..4b0f24fc89f7 100644 --- a/drivers/ata/libata-eh.c +++ b/drivers/ata/libata-eh.c @@ -2050,18 +2050,12 @@ static int ata_do_reset(struct ata_link *link, ata_reset_fn_t reset, } static int ata_eh_followup_srst_needed(struct ata_link *link, - int rc, int classify, - const unsigned int *classes) + int rc, const unsigned int *classes) { if ((link->flags & ATA_LFLAG_NO_SRST) || ata_link_offline(link)) return 0; - if (rc == -EAGAIN) { - if (classify) - return 1; - rc = 0; - } - if (rc != 0) - return 0; + if (rc == -EAGAIN) + return 1; if (sata_pmp_supported(link->ap) && ata_is_host_link(link)) return 1; return 0; @@ -2174,9 +2168,11 @@ int ata_eh_reset(struct ata_link *link, int classify, ehc->i.flags |= ATA_EHI_DID_SOFTRESET; rc = ata_do_reset(link, reset, classes, deadline); + if (rc && rc != -EAGAIN) + goto fail; if (reset == hardreset && - ata_eh_followup_srst_needed(link, rc, classify, classes)) { + ata_eh_followup_srst_needed(link, rc, classes)) { /* okay, let's do follow-up softreset */ reset = softreset; @@ -2191,10 +2187,6 @@ int ata_eh_reset(struct ata_link *link, int classify, ata_eh_about_to_do(link, NULL, ATA_EH_RESET); rc = ata_do_reset(link, reset, classes, deadline); } - - /* -EAGAIN can happen if we skipped followup SRST */ - if (rc && rc != -EAGAIN) - goto fail; } else { if (verbose) ata_link_printk(link, KERN_INFO, "no reset method " -- 2.39.5