]> err.no Git - linux-2.6/blobdiff - drivers/ata/libata-core.c
Merge branch 'semaphore' of git://git.kernel.org/pub/scm/linux/kernel/git/willy/misc
[linux-2.6] / drivers / ata / libata-core.c
index 3401248180c9d2bea36a2fa67cab7f5ec4667684..b0b00af90d0e18314782fec05cdd136cbd41eff1 100644 (file)
@@ -61,7 +61,6 @@
 #include <scsi/scsi_cmnd.h>
 #include <scsi/scsi_host.h>
 #include <linux/libata.h>
-#include <asm/semaphore.h>
 #include <asm/byteorder.h>
 #include <linux/cdrom.h>
 
@@ -3132,16 +3131,21 @@ static int ata_dev_set_mode(struct ata_device *dev)
        if (rc)
                return rc;
 
-       /* Old CFA may refuse this command, which is just fine */
-       if (dev->xfer_shift == ATA_SHIFT_PIO && ata_id_is_cfa(dev->id))
-               ign_dev_err = 1;
-
-       /* Some very old devices and some bad newer ones fail any kind of
-          SET_XFERMODE request but support PIO0-2 timings and no IORDY */
-       if (dev->xfer_shift == ATA_SHIFT_PIO && !ata_id_has_iordy(dev->id) &&
-                       dev->pio_mode <= XFER_PIO_2)
-               ign_dev_err = 1;
-
+       if (dev->xfer_shift == ATA_SHIFT_PIO) {
+               /* Old CFA may refuse this command, which is just fine */
+               if (ata_id_is_cfa(dev->id))
+                       ign_dev_err = 1;
+               /* Catch several broken garbage emulations plus some pre
+                  ATA devices */
+               if (ata_id_major_version(dev->id) == 0 &&
+                                       dev->pio_mode <= XFER_PIO_2)
+                       ign_dev_err = 1;
+               /* Some very old devices and some bad newer ones fail
+                  any kind of SET_XFERMODE request but support PIO0-2
+                  timings and no IORDY */
+               if (!ata_id_has_iordy(dev->id) && dev->pio_mode <= XFER_PIO_2)
+                       ign_dev_err = 1;
+       }
        /* Early MWDMA devices do DMA but don't allow DMA mode setting.
           Don't fail an MWDMA0 set IFF the device indicates it is in MWDMA0 */
        if (dev->xfer_shift == ATA_SHIFT_MWDMA &&
@@ -3541,6 +3545,10 @@ int ata_std_prereset(struct ata_link *link, unsigned long deadline)
                                        "link for reset (errno=%d)\n", rc);
        }
 
+       /* no point in trying softreset on offline link */
+       if (ata_link_offline(link))
+               ehc->i.action &= ~ATA_EH_SOFTRESET;
+
        return 0;
 }
 
@@ -4029,6 +4037,10 @@ static int cable_is_40wire(struct ata_port *ap)
        /* If the controller thinks we are 80 wire, we are */
        if (ap->cbl == ATA_CBL_PATA80 || ap->cbl == ATA_CBL_SATA)
                return 0;
+       /* If the system is known to be 40 wire short cable (eg laptop),
+          then we allow 80 wire modes even if the drive isn't sure */
+       if (ap->cbl == ATA_CBL_PATA40_SHORT)
+               return 0;
        /* If the controller doesn't know we scan
 
           - Note: We look for all 40 wire detects at this point.