aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTejun Heo <htejun@gmail.com>2007-10-30 21:17:03 -0400
committerJeff Garzik <jeff@garzik.org>2007-11-03 08:46:54 -0400
commit416dc9ed206bba09807300ee5f155a81cebbd4a1 (patch)
tree483a86db1dbcdb443962f9597531ea0541ef61e6
parentcd955463bb4e96cfec18a0e5b6887c6797fb821d (diff)
libata: cosmetic clean up / reorganization of ata_eh_reset()
Clean up and reorganize ata_eh_reset() to ease further changes. * Cache ARRAY_SIZE(ata_eh_reset_timeouts) in @max_tries. * Cache link->flags in @lflags. * Move failure handling block to the end of the function and unnest both success and failure handling blocks. Signed-off-by: Tejun Heo <htejun@gmail.com> Signed-off-by: Jeff Garzik <jeff@garzik.org>
-rw-r--r--drivers/ata/libata-eh.c112
1 files changed, 56 insertions, 56 deletions
diff --git a/drivers/ata/libata-eh.c b/drivers/ata/libata-eh.c
index 53b2348a364d..dae2174f3877 100644
--- a/drivers/ata/libata-eh.c
+++ b/drivers/ata/libata-eh.c
@@ -2065,16 +2065,19 @@ int ata_eh_reset(struct ata_link *link, int classify,
2065 ata_prereset_fn_t prereset, ata_reset_fn_t softreset, 2065 ata_prereset_fn_t prereset, ata_reset_fn_t softreset,
2066 ata_reset_fn_t hardreset, ata_postreset_fn_t postreset) 2066 ata_reset_fn_t hardreset, ata_postreset_fn_t postreset)
2067{ 2067{
2068 const int max_tries = ARRAY_SIZE(ata_eh_reset_timeouts);
2068 struct ata_port *ap = link->ap; 2069 struct ata_port *ap = link->ap;
2069 struct ata_eh_context *ehc = &link->eh_context; 2070 struct ata_eh_context *ehc = &link->eh_context;
2070 unsigned int *classes = ehc->classes; 2071 unsigned int *classes = ehc->classes;
2072 unsigned int lflags = link->flags;
2071 int verbose = !(ehc->i.flags & ATA_EHI_QUIET); 2073 int verbose = !(ehc->i.flags & ATA_EHI_QUIET);
2072 int try = 0; 2074 int try = 0;
2073 struct ata_device *dev; 2075 struct ata_device *dev;
2074 unsigned long deadline; 2076 unsigned long deadline, now;
2075 unsigned int tmp_action; 2077 unsigned int tmp_action;
2076 ata_reset_fn_t reset; 2078 ata_reset_fn_t reset;
2077 unsigned long flags; 2079 unsigned long flags;
2080 u32 sstatus;
2078 int rc; 2081 int rc;
2079 2082
2080 /* about to reset */ 2083 /* about to reset */
@@ -2106,7 +2109,7 @@ int ata_eh_reset(struct ata_link *link, int classify,
2106 /* Determine which reset to use and record in ehc->i.action. 2109 /* Determine which reset to use and record in ehc->i.action.
2107 * prereset() may examine and modify it. 2110 * prereset() may examine and modify it.
2108 */ 2111 */
2109 if (softreset && (!hardreset || (!(link->flags & ATA_LFLAG_NO_SRST) && 2112 if (softreset && (!hardreset || (!(lflags & ATA_LFLAG_NO_SRST) &&
2110 !sata_set_spd_needed(link) && 2113 !sata_set_spd_needed(link) &&
2111 !(ehc->i.action & ATA_EH_HARDRESET)))) 2114 !(ehc->i.action & ATA_EH_HARDRESET))))
2112 tmp_action = ATA_EH_SOFTRESET; 2115 tmp_action = ATA_EH_SOFTRESET;
@@ -2188,7 +2191,7 @@ int ata_eh_reset(struct ata_link *link, int classify,
2188 rc = ata_do_reset(link, reset, classes, deadline); 2191 rc = ata_do_reset(link, reset, classes, deadline);
2189 2192
2190 if (rc == 0 && classify && classes[0] == ATA_DEV_UNKNOWN && 2193 if (rc == 0 && classify && classes[0] == ATA_DEV_UNKNOWN &&
2191 !(link->flags & ATA_LFLAG_ASSUME_CLASS)) { 2194 !(lflags & ATA_LFLAG_ASSUME_CLASS)) {
2192 ata_link_printk(link, KERN_ERR, 2195 ata_link_printk(link, KERN_ERR,
2193 "classification failed\n"); 2196 "classification failed\n");
2194 rc = -EINVAL; 2197 rc = -EINVAL;
@@ -2196,67 +2199,42 @@ int ata_eh_reset(struct ata_link *link, int classify,
2196 } 2199 }
2197 } 2200 }
2198 2201
2199 /* if we skipped follow-up srst, clear rc */ 2202 /* -EAGAIN can happen if we skipped followup SRST */
2200 if (rc == -EAGAIN) 2203 if (rc && rc != -EAGAIN)
2201 rc = 0; 2204 goto fail;
2202
2203 if (rc && rc != -ERESTART && try < ARRAY_SIZE(ata_eh_reset_timeouts)) {
2204 unsigned long now = jiffies;
2205 2205
2206 if (time_before(now, deadline)) { 2206 ata_link_for_each_dev(dev, link) {
2207 unsigned long delta = deadline - now; 2207 /* After the reset, the device state is PIO 0 and the
2208 2208 * controller state is undefined. Reset also wakes up
2209 ata_link_printk(link, KERN_WARNING, "reset failed " 2209 * drives from sleeping mode.
2210 "(errno=%d), retrying in %u secs\n", 2210 */
2211 rc, (jiffies_to_msecs(delta) + 999) / 1000); 2211 dev->pio_mode = XFER_PIO_0;
2212 dev->flags &= ~ATA_DFLAG_SLEEPING;
2212 2213
2213 while (delta) 2214 if (ata_link_offline(link))
2214 delta = schedule_timeout_uninterruptible(delta); 2215 continue;
2215 }
2216 2216
2217 if (rc == -EPIPE || 2217 /* apply class override and convert UNKNOWN to NONE */
2218 try == ARRAY_SIZE(ata_eh_reset_timeouts) - 1) 2218 if (lflags & ATA_LFLAG_ASSUME_ATA)
2219 sata_down_spd_limit(link); 2219 classes[dev->devno] = ATA_DEV_ATA;
2220 if (hardreset) 2220 else if (lflags & ATA_LFLAG_ASSUME_SEMB)
2221 reset = hardreset; 2221 classes[dev->devno] = ATA_DEV_SEMB_UNSUP; /* not yet */
2222 goto retry; 2222 else if (classes[dev->devno] == ATA_DEV_UNKNOWN)
2223 classes[dev->devno] = ATA_DEV_NONE;
2223 } 2224 }
2224 2225
2225 if (rc == 0) { 2226 /* record current link speed */
2226 u32 sstatus; 2227 if (sata_scr_read(link, SCR_STATUS, &sstatus) == 0)
2227 2228 link->sata_spd = (sstatus >> 4) & 0xf;
2228 ata_link_for_each_dev(dev, link) {
2229 /* After the reset, the device state is PIO 0
2230 * and the controller state is undefined.
2231 * Reset also wakes up drives from sleeping
2232 * mode.
2233 */
2234 dev->pio_mode = XFER_PIO_0;
2235 dev->flags &= ~ATA_DFLAG_SLEEPING;
2236
2237 if (ata_link_offline(link))
2238 continue;
2239
2240 /* apply class override and convert UNKNOWN to NONE */
2241 if (link->flags & ATA_LFLAG_ASSUME_ATA)
2242 classes[dev->devno] = ATA_DEV_ATA;
2243 else if (link->flags & ATA_LFLAG_ASSUME_SEMB)
2244 classes[dev->devno] = ATA_DEV_SEMB_UNSUP; /* not yet */
2245 else if (classes[dev->devno] == ATA_DEV_UNKNOWN)
2246 classes[dev->devno] = ATA_DEV_NONE;
2247 }
2248 2229
2249 /* record current link speed */ 2230 if (postreset)
2250 if (sata_scr_read(link, SCR_STATUS, &sstatus) == 0) 2231 postreset(link, classes);
2251 link->sata_spd = (sstatus >> 4) & 0xf;
2252 2232
2253 if (postreset) 2233 /* reset successful, schedule revalidation */
2254 postreset(link, classes); 2234 ata_eh_done(link, NULL, ehc->i.action & ATA_EH_RESET_MASK);
2235 ehc->i.action |= ATA_EH_REVALIDATE;
2255 2236
2256 /* reset successful, schedule revalidation */ 2237 rc = 0;
2257 ata_eh_done(link, NULL, ehc->i.action & ATA_EH_RESET_MASK);
2258 ehc->i.action |= ATA_EH_REVALIDATE;
2259 }
2260 out: 2238 out:
2261 /* clear hotplug flag */ 2239 /* clear hotplug flag */
2262 ehc->i.flags &= ~ATA_EHI_HOTPLUGGED; 2240 ehc->i.flags &= ~ATA_EHI_HOTPLUGGED;
@@ -2266,6 +2244,28 @@ int ata_eh_reset(struct ata_link *link, int classify,
2266 spin_unlock_irqrestore(ap->lock, flags); 2244 spin_unlock_irqrestore(ap->lock, flags);
2267 2245
2268 return rc; 2246 return rc;
2247
2248 fail:
2249 if (rc == -ERESTART || try >= max_tries)
2250 goto out;
2251
2252 now = jiffies;
2253 if (time_before(now, deadline)) {
2254 unsigned long delta = deadline - now;
2255
2256 ata_link_printk(link, KERN_WARNING, "reset failed "
2257 "(errno=%d), retrying in %u secs\n",
2258 rc, (jiffies_to_msecs(delta) + 999) / 1000);
2259
2260 while (delta)
2261 delta = schedule_timeout_uninterruptible(delta);
2262 }
2263
2264 if (rc == -EPIPE || try == max_tries - 1)
2265 sata_down_spd_limit(link);
2266 if (hardreset)
2267 reset = hardreset;
2268 goto retry;
2269} 2269}
2270 2270
2271static int ata_eh_revalidate_and_attach(struct ata_link *link, 2271static int ata_eh_revalidate_and_attach(struct ata_link *link,