[PATCH] libata: implement ata_tf_read_block()
[linux-2.6.git] / drivers / ata / libata-core.c
index 1c93154..3fd7c79 100644 (file)
@@ -240,6 +240,49 @@ int ata_rwcmd_protocol(struct ata_queued_cmd *qc)
 }
 
 /**
+ *     ata_tf_read_block - Read block address from ATA taskfile
+ *     @tf: ATA taskfile of interest
+ *     @dev: ATA device @tf belongs to
+ *
+ *     LOCKING:
+ *     None.
+ *
+ *     Read block address from @tf.  This function can handle all
+ *     three address formats - LBA, LBA48 and CHS.  tf->protocol and
+ *     flags select the address format to use.
+ *
+ *     RETURNS:
+ *     Block address read from @tf.
+ */
+u64 ata_tf_read_block(struct ata_taskfile *tf, struct ata_device *dev)
+{
+       u64 block = 0;
+
+       if (tf->flags & ATA_TFLAG_LBA) {
+               if (tf->flags & ATA_TFLAG_LBA48) {
+                       block |= (u64)tf->hob_lbah << 40;
+                       block |= (u64)tf->hob_lbam << 32;
+                       block |= tf->hob_lbal << 24;
+               } else
+                       block |= (tf->device & 0xf) << 24;
+
+               block |= tf->lbah << 16;
+               block |= tf->lbam << 8;
+               block |= tf->lbal;
+       } else {
+               u32 cyl, head, sect;
+
+               cyl = tf->lbam | (tf->lbah << 8);
+               head = tf->device & 0xf;
+               sect = tf->lbal;
+
+               block = (cyl * dev->heads + head) * dev->sectors + sect;
+       }
+
+       return block;
+}
+
+/**
  *     ata_pack_xfermask - Pack pio, mwdma and udma masks into xfer_mask
  *     @pio_mask: pio_mask
  *     @mwdma_mask: mwdma_mask
@@ -616,8 +659,11 @@ ata_dev_try_classify(struct ata_port *ap, unsigned int device, u8 *r_err)
        if (r_err)
                *r_err = err;
 
-       /* see if device passed diags */
-       if (err == 1)
+       /* see if device passed diags: if master then continue and warn later */
+       if (err == 0 && device == 0)
+               /* diagnostic fail : do nothing _YET_ */
+               ap->device[device].horkage |= ATA_HORKAGE_DIAGNOSTIC;
+       else if (err == 1)
                /* do nothing */ ;
        else if ((device == 0) && (err == 0x81))
                /* do nothing */ ;
@@ -867,7 +913,11 @@ static unsigned int ata_id_xfermask(const u16 *id)
                 * the PIO timing number for the maximum. Turn it into
                 * a mask.
                 */
-               pio_mask = (2 << (id[ATA_ID_OLD_PIO_MODES] & 0xFF)) - 1 ;
+               u8 mode = id[ATA_ID_OLD_PIO_MODES] & 0xFF;
+               if (mode < 5)   /* Valid PIO range */
+                       pio_mask = (2 << mode) - 1;
+               else
+                       pio_mask = 1;
 
                /* But wait.. there's more. Design your standards by
                 * committee and you too can get a free iordy field to
@@ -1217,7 +1267,7 @@ unsigned int ata_pio_need_iordy(const struct ata_device *adev)
  *     ata_dev_read_id - Read ID data from the specified device
  *     @dev: target device
  *     @p_class: pointer to class of the target device (may be changed)
- *     @post_reset: is this read ID post-reset?
+ *     @flags: ATA_READID_* flags
  *     @id: buffer to read IDENTIFY data into
  *
  *     Read ID data from the specified device.  ATA_CMD_ID_ATA is
@@ -1232,7 +1282,7 @@ unsigned int ata_pio_need_iordy(const struct ata_device *adev)
  *     0 on success, -errno otherwise.
  */
 int ata_dev_read_id(struct ata_device *dev, unsigned int *p_class,
-                   int post_reset, u16 *id)
+                   unsigned int flags, u16 *id)
 {
        struct ata_port *ap = dev->ap;
        unsigned int class = *p_class;
@@ -1265,9 +1315,20 @@ int ata_dev_read_id(struct ata_device *dev, unsigned int *p_class,
 
        tf.protocol = ATA_PROT_PIO;
 
+       /* presence detection using polling IDENTIFY? */
+       if (flags & ATA_READID_DETECT)
+               tf.flags |= ATA_TFLAG_POLLING;
+
        err_mask = ata_exec_internal(dev, &tf, NULL, DMA_FROM_DEVICE,
                                     id, sizeof(id[0]) * ATA_ID_WORDS);
        if (err_mask) {
+               if ((flags & ATA_READID_DETECT) &&
+                   (err_mask & AC_ERR_NODEV_HINT)) {
+                       DPRINTK("ata%u.%d: NODEV after polling detection\n",
+                               ap->id, dev->devno);
+                       return -ENOENT;
+               }
+
                rc = -EIO;
                reason = "I/O error";
                goto err_out;
@@ -1276,13 +1337,18 @@ int ata_dev_read_id(struct ata_device *dev, unsigned int *p_class,
        swap_buf_le16(id, ATA_ID_WORDS);
 
        /* sanity check */
-       if ((class == ATA_DEV_ATA) != (ata_id_is_ata(id) | ata_id_is_cfa(id))) {
-               rc = -EINVAL;
-               reason = "device reports illegal type";
-               goto err_out;
+       rc = -EINVAL;
+       reason = "device reports illegal type";
+
+       if (class == ATA_DEV_ATA) {
+               if (!ata_id_is_ata(id) && !ata_id_is_cfa(id))
+                       goto err_out;
+       } else {
+               if (ata_id_is_ata(id))
+                       goto err_out;
        }
 
-       if (post_reset && class == ATA_DEV_ATA) {
+       if ((flags & ATA_READID_POSTRESET) && class == ATA_DEV_ATA) {
                /*
                 * The exact sequence expected by certain pre-ATA4 drives is:
                 * SRST RESET
@@ -1302,7 +1368,7 @@ int ata_dev_read_id(struct ata_device *dev, unsigned int *p_class,
                        /* current CHS translation info (id[53-58]) might be
                         * changed. reread the identify device info.
                         */
-                       post_reset = 0;
+                       flags &= ~ATA_READID_POSTRESET;
                        goto retry;
                }
        }
@@ -1333,7 +1399,10 @@ static void ata_dev_config_ncq(struct ata_device *dev,
                desc[0] = '\0';
                return;
        }
-
+       if (ata_device_blacklisted(dev) & ATA_HORKAGE_NONCQ) {
+               snprintf(desc, desc_sz, "NCQ (not used)");
+               return;
+       }
        if (ap->flags & ATA_FLAG_NCQ) {
                hdepth = min(ap->scsi_host->can_queue, ATA_MAX_QUEUE - 1);
                dev->flags |= ATA_DFLAG_NCQ;
@@ -1362,7 +1431,6 @@ static void ata_set_port_max_cmd_len(struct ata_port *ap)
 /**
  *     ata_dev_configure - Configure the specified ATA/ATAPI device
  *     @dev: Target device to configure
- *     @print_info: Enable device info printout
  *
  *     Configure @dev according to @dev->id.  Generic and low-level
  *     driver specific fixups are also applied.
@@ -1373,9 +1441,10 @@ static void ata_set_port_max_cmd_len(struct ata_port *ap)
  *     RETURNS:
  *     0 on success, -errno otherwise
  */
-int ata_dev_configure(struct ata_device *dev, int print_info)
+int ata_dev_configure(struct ata_device *dev)
 {
        struct ata_port *ap = dev->ap;
+       int print_info = ap->eh_context.i.flags & ATA_EHI_PRINTINFO;
        const u16 *id = dev->id;
        unsigned int xfer_mask;
        char revbuf[7];         /* XYZ-99\0 */
@@ -1442,6 +1511,10 @@ int ata_dev_configure(struct ata_device *dev, int print_info)
                        if (ata_id_has_lba48(id)) {
                                dev->flags |= ATA_DFLAG_LBA48;
                                lba_desc = "LBA48";
+
+                               if (dev->n_sectors >= (1UL << 28) &&
+                                   ata_id_has_flush_ext(id))
+                                       dev->flags |= ATA_DFLAG_FLUSH_EXT;
                        }
 
                        /* config NCQ */
@@ -1518,6 +1591,23 @@ int ata_dev_configure(struct ata_device *dev, int print_info)
                                       cdb_intr_string);
        }
 
+       /* determine max_sectors */
+       dev->max_sectors = ATA_MAX_SECTORS;
+       if (dev->flags & ATA_DFLAG_LBA48)
+               dev->max_sectors = ATA_MAX_SECTORS_LBA48;
+
+       if (dev->horkage & ATA_HORKAGE_DIAGNOSTIC) {
+               /* Let the user know. We don't want to disallow opens for
+                  rescue purposes, or in case the vendor is just a blithering
+                  idiot */
+                if (print_info) {
+                       ata_dev_printk(dev, KERN_WARNING,
+"Drive reports diagnostics failure. This may indicate a drive\n");
+                       ata_dev_printk(dev, KERN_WARNING,
+"fault or invalid emulation. Contact drive vendor for information.\n");
+               }
+       }
+
        ata_set_port_max_cmd_len(ap);
 
        /* limit bridge transfers to udma5, 200 sectors */
@@ -1607,11 +1697,14 @@ int ata_bus_probe(struct ata_port *ap)
                if (!ata_dev_enabled(dev))
                        continue;
 
-               rc = ata_dev_read_id(dev, &dev->class, 1, dev->id);
+               rc = ata_dev_read_id(dev, &dev->class, ATA_READID_POSTRESET,
+                                    dev->id);
                if (rc)
                        goto fail;
 
-               rc = ata_dev_configure(dev, 1);
+               ap->eh_context.i.flags |= ATA_EHI_PRINTINFO;
+               rc = ata_dev_configure(dev);
+               ap->eh_context.i.flags &= ~ATA_EHI_PRINTINFO;
                if (rc)
                        goto fail;
        }
@@ -2129,6 +2222,7 @@ int ata_down_xfermask_limit(struct ata_device *dev, int force_pio0)
 
 static int ata_dev_set_mode(struct ata_device *dev)
 {
+       struct ata_eh_context *ehc = &dev->ap->eh_context;
        unsigned int err_mask;
        int rc;
 
@@ -2143,7 +2237,9 @@ static int ata_dev_set_mode(struct ata_device *dev)
                return -EIO;
        }
 
+       ehc->i.flags |= ATA_EHI_POST_SETMODE;
        rc = ata_dev_revalidate(dev, 0);
+       ehc->i.flags &= ~ATA_EHI_POST_SETMODE;
        if (rc)
                return rc;
 
@@ -2301,11 +2397,14 @@ static inline void ata_tf_to_host(struct ata_port *ap,
  *     Sleep until ATA Status register bit BSY clears,
  *     or a timeout occurs.
  *
- *     LOCKING: None.
+ *     LOCKING:
+ *     Kernel thread context (may sleep).
+ *
+ *     RETURNS:
+ *     0 on success, -errno otherwise.
  */
-
-unsigned int ata_busy_sleep (struct ata_port *ap,
-                            unsigned long tmout_pat, unsigned long tmout)
+int ata_busy_sleep(struct ata_port *ap,
+                  unsigned long tmout_pat, unsigned long tmout)
 {
        unsigned long timer_start, timeout;
        u8 status;
@@ -2313,25 +2412,32 @@ unsigned int ata_busy_sleep (struct ata_port *ap,
        status = ata_busy_wait(ap, ATA_BUSY, 300);
        timer_start = jiffies;
        timeout = timer_start + tmout_pat;
-       while ((status & ATA_BUSY) && (time_before(jiffies, timeout))) {
+       while (status != 0xff && (status & ATA_BUSY) &&
+              time_before(jiffies, timeout)) {
                msleep(50);
                status = ata_busy_wait(ap, ATA_BUSY, 3);
        }
 
-       if (status & ATA_BUSY)
+       if (status != 0xff && (status & ATA_BUSY))
                ata_port_printk(ap, KERN_WARNING,
-                               "port is slow to respond, please be patient\n");
+                               "port is slow to respond, please be patient "
+                               "(Status 0x%x)\n", status);
 
        timeout = timer_start + tmout;
-       while ((status & ATA_BUSY) && (time_before(jiffies, timeout))) {
+       while (status != 0xff && (status & ATA_BUSY) &&
+              time_before(jiffies, timeout)) {
                msleep(50);
                status = ata_chk_status(ap);
        }
 
+       if (status == 0xff)
+               return -ENODEV;
+
        if (status & ATA_BUSY) {
                ata_port_printk(ap, KERN_ERR, "port failed to respond "
-                               "(%lu secs)\n", tmout / HZ);
-               return 1;
+                               "(%lu secs, Status 0x%x)\n",
+                               tmout / HZ, status);
+               return -EBUSY;
        }
 
        return 0;
@@ -2422,10 +2528,8 @@ static unsigned int ata_bus_softreset(struct ata_port *ap,
         * the bus shows 0xFF because the odd clown forgets the D7
         * pulldown resistor.
         */
-       if (ata_check_status(ap) == 0xFF) {
-               ata_port_printk(ap, KERN_ERR, "SRST failed (status 0xFF)\n");
-               return AC_ERR_OTHER;
-       }
+       if (ata_check_status(ap) == 0xFF)
+               return 0;
 
        ata_bus_post_reset(ap, devmask);
 
@@ -2751,9 +2855,9 @@ int ata_std_softreset(struct ata_port *ap, unsigned int *classes)
 }
 
 /**
- *     sata_std_hardreset - reset host port via SATA phy reset
+ *     sata_port_hardreset - reset port via SATA phy reset
  *     @ap: port to reset
- *     @class: resulting class of attached device
+ *     @timing: timing parameters { interval, duratinon, timeout } in msec
  *
  *     SATA phy-reset host port using DET bits of SControl register.
  *
@@ -2763,10 +2867,8 @@ int ata_std_softreset(struct ata_port *ap, unsigned int *classes)
  *     RETURNS:
  *     0 on success, -errno otherwise.
  */
-int sata_std_hardreset(struct ata_port *ap, unsigned int *class)
+int sata_port_hardreset(struct ata_port *ap, const unsigned long *timing)
 {
-       struct ata_eh_context *ehc = &ap->eh_context;
-       const unsigned long *timing = sata_ehc_deb_timing(ehc);
        u32 scontrol;
        int rc;
 
@@ -2779,24 +2881,24 @@ int sata_std_hardreset(struct ata_port *ap, unsigned int *class)
                 * and Sil3124.
                 */
                if ((rc = sata_scr_read(ap, SCR_CONTROL, &scontrol)))
-                       return rc;
+                       goto out;
 
                scontrol = (scontrol & 0x0f0) | 0x304;
 
                if ((rc = sata_scr_write(ap, SCR_CONTROL, scontrol)))
-                       return rc;
+                       goto out;
 
                sata_set_spd(ap);
        }
 
        /* issue phy wake/reset */
        if ((rc = sata_scr_read(ap, SCR_CONTROL, &scontrol)))
-               return rc;
+               goto out;
 
        scontrol = (scontrol & 0x0f0) | 0x301;
 
        if ((rc = sata_scr_write_flush(ap, SCR_CONTROL, scontrol)))
-               return rc;
+               goto out;
 
        /* Couldn't find anything in SATA I/II specs, but AHCI-1.1
         * 10.4.2 says at least 1 ms.
@@ -2804,7 +2906,40 @@ int sata_std_hardreset(struct ata_port *ap, unsigned int *class)
        msleep(1);
 
        /* bring phy back */
-       sata_phy_resume(ap, timing);
+       rc = sata_phy_resume(ap, timing);
+ out:
+       DPRINTK("EXIT, rc=%d\n", rc);
+       return rc;
+}
+
+/**
+ *     sata_std_hardreset - reset host port via SATA phy reset
+ *     @ap: port to reset
+ *     @class: resulting class of attached device
+ *
+ *     SATA phy-reset host port using DET bits of SControl register,
+ *     wait for !BSY and classify the attached device.
+ *
+ *     LOCKING:
+ *     Kernel thread context (may sleep)
+ *
+ *     RETURNS:
+ *     0 on success, -errno otherwise.
+ */
+int sata_std_hardreset(struct ata_port *ap, unsigned int *class)
+{
+       const unsigned long *timing = sata_ehc_deb_timing(&ap->eh_context);
+       int rc;
+
+       DPRINTK("ENTER\n");
+
+       /* do hardreset */
+       rc = sata_port_hardreset(ap, timing);
+       if (rc) {
+               ata_port_printk(ap, KERN_ERR,
+                               "COMRESET failed (errno=%d)\n", rc);
+               return rc;
+       }
 
        /* TODO: phy layer with polling, timeouts, etc. */
        if (ata_port_offline(ap)) {
@@ -2943,7 +3078,7 @@ static int ata_dev_same_device(struct ata_device *dev, unsigned int new_class,
 /**
  *     ata_dev_revalidate - Revalidate ATA device
  *     @dev: device to revalidate
- *     @post_reset: is this revalidation after reset?
+ *     @readid_flags: read ID flags
  *
  *     Re-read IDENTIFY page and make sure @dev is still attached to
  *     the port.
@@ -2954,7 +3089,7 @@ static int ata_dev_same_device(struct ata_device *dev, unsigned int new_class,
  *     RETURNS:
  *     0 on success, negative errno otherwise
  */
-int ata_dev_revalidate(struct ata_device *dev, int post_reset)
+int ata_dev_revalidate(struct ata_device *dev, unsigned int readid_flags)
 {
        unsigned int class = dev->class;
        u16 *id = (void *)dev->ap->sector_buf;
@@ -2966,7 +3101,7 @@ int ata_dev_revalidate(struct ata_device *dev, int post_reset)
        }
 
        /* read ID data */
-       rc = ata_dev_read_id(dev, &class, post_reset, id);
+       rc = ata_dev_read_id(dev, &class, readid_flags, id);
        if (rc)
                goto fail;
 
@@ -2979,7 +3114,7 @@ int ata_dev_revalidate(struct ata_device *dev, int post_reset)
        memcpy(dev->id, id, sizeof(id[0]) * ATA_ID_WORDS);
 
        /* configure device according to the new ID */
-       rc = ata_dev_configure(dev, 0);
+       rc = ata_dev_configure(dev);
        if (rc == 0)
                return 0;
 
@@ -2988,37 +3123,55 @@ int ata_dev_revalidate(struct ata_device *dev, int post_reset)
        return rc;
 }
 
-static const char * const ata_dma_blacklist [] = {
-       "WDC AC11000H", NULL,
-       "WDC AC22100H", NULL,
-       "WDC AC32500H", NULL,
-       "WDC AC33100H", NULL,
-       "WDC AC31600H", NULL,
-       "WDC AC32100H", "24.09P07",
-       "WDC AC23200L", "21.10N21",
-       "Compaq CRD-8241B",  NULL,
-       "CRD-8400B", NULL,
-       "CRD-8480B", NULL,
-       "CRD-8482B", NULL,
-       "CRD-84", NULL,
-       "SanDisk SDP3B", NULL,
-       "SanDisk SDP3B-64", NULL,
-       "SANYO CD-ROM CRD", NULL,
-       "HITACHI CDR-8", NULL,
-       "HITACHI CDR-8335", NULL,
-       "HITACHI CDR-8435", NULL,
-       "Toshiba CD-ROM XM-6202B", NULL,
-       "TOSHIBA CD-ROM XM-1702BC", NULL,
-       "CD-532E-A", NULL,
-       "E-IDE CD-ROM CR-840", NULL,
-       "CD-ROM Drive/F5A", NULL,
-       "WPI CDD-820", NULL,
-       "SAMSUNG CD-ROM SC-148C", NULL,
-       "SAMSUNG CD-ROM SC", NULL,
-       "SanDisk SDP3B-64", NULL,
-       "ATAPI CD-ROM DRIVE 40X MAXIMUM",NULL,
-       "_NEC DV5800A", NULL,
-       "SAMSUNG CD-ROM SN-124", "N001"
+struct ata_blacklist_entry {
+       const char *model_num;
+       const char *model_rev;
+       unsigned long horkage;
+};
+
+static const struct ata_blacklist_entry ata_device_blacklist [] = {
+       /* Devices with DMA related problems under Linux */
+       { "WDC AC11000H",       NULL,           ATA_HORKAGE_NODMA },
+       { "WDC AC22100H",       NULL,           ATA_HORKAGE_NODMA },
+       { "WDC AC32500H",       NULL,           ATA_HORKAGE_NODMA },
+       { "WDC AC33100H",       NULL,           ATA_HORKAGE_NODMA },
+       { "WDC AC31600H",       NULL,           ATA_HORKAGE_NODMA },
+       { "WDC AC32100H",       "24.09P07",     ATA_HORKAGE_NODMA },
+       { "WDC AC23200L",       "21.10N21",     ATA_HORKAGE_NODMA },
+       { "Compaq CRD-8241B",   NULL,           ATA_HORKAGE_NODMA },
+       { "CRD-8400B",          NULL,           ATA_HORKAGE_NODMA },
+       { "CRD-8480B",          NULL,           ATA_HORKAGE_NODMA },
+       { "CRD-8482B",          NULL,           ATA_HORKAGE_NODMA },
+       { "CRD-84",             NULL,           ATA_HORKAGE_NODMA },
+       { "SanDisk SDP3B",      NULL,           ATA_HORKAGE_NODMA },
+       { "SanDisk SDP3B-64",   NULL,           ATA_HORKAGE_NODMA },
+       { "SANYO CD-ROM CRD",   NULL,           ATA_HORKAGE_NODMA },
+       { "HITACHI CDR-8",      NULL,           ATA_HORKAGE_NODMA },
+       { "HITACHI CDR-8335",   NULL,           ATA_HORKAGE_NODMA },
+       { "HITACHI CDR-8435",   NULL,           ATA_HORKAGE_NODMA },
+       { "Toshiba CD-ROM XM-6202B", NULL,      ATA_HORKAGE_NODMA },
+       { "TOSHIBA CD-ROM XM-1702BC", NULL,     ATA_HORKAGE_NODMA },
+       { "CD-532E-A",          NULL,           ATA_HORKAGE_NODMA },
+       { "E-IDE CD-ROM CR-840",NULL,           ATA_HORKAGE_NODMA },
+       { "CD-ROM Drive/F5A",   NULL,           ATA_HORKAGE_NODMA },
+       { "WPI CDD-820",        NULL,           ATA_HORKAGE_NODMA },
+       { "SAMSUNG CD-ROM SC-148C", NULL,       ATA_HORKAGE_NODMA },
+       { "SAMSUNG CD-ROM SC",  NULL,           ATA_HORKAGE_NODMA },
+       { "SanDisk SDP3B-64",   NULL,           ATA_HORKAGE_NODMA },
+       { "ATAPI CD-ROM DRIVE 40X MAXIMUM",NULL,ATA_HORKAGE_NODMA },
+       { "_NEC DV5800A",       NULL,           ATA_HORKAGE_NODMA },
+       { "SAMSUNG CD-ROM SN-124","N001",       ATA_HORKAGE_NODMA },
+
+       /* Devices we expect to fail diagnostics */
+
+       /* Devices where NCQ should be avoided */
+       /* NCQ is slow */
+        { "WDC WD740ADFD-00",   NULL,          ATA_HORKAGE_NONCQ },
+
+       /* Devices with NCQ limits */
+
+       /* End Marker */
+       { }
 };
 
 static int ata_strim(char *s, size_t len)
@@ -3033,20 +3186,12 @@ static int ata_strim(char *s, size_t len)
        return len;
 }
 
-static int ata_dma_blacklisted(const struct ata_device *dev)
+unsigned long ata_device_blacklisted(const struct ata_device *dev)
 {
        unsigned char model_num[40];
        unsigned char model_rev[16];
        unsigned int nlen, rlen;
-       int i;
-
-       /* We don't support polling DMA.
-        * DMA blacklist those ATAPI devices with CDB-intr (and use PIO)
-        * if the LLDD handles only interrupts in the HSM_ST_LAST state.
-        */
-       if ((dev->ap->flags & ATA_FLAG_PIO_POLLING) &&
-           (dev->flags & ATA_DFLAG_CDB_INTR))
-               return 1;
+       const struct ata_blacklist_entry *ad = ata_device_blacklist;
 
        ata_id_string(dev->id, model_num, ATA_ID_PROD_OFS,
                          sizeof(model_num));
@@ -3055,17 +3200,30 @@ static int ata_dma_blacklisted(const struct ata_device *dev)
        nlen = ata_strim(model_num, sizeof(model_num));
        rlen = ata_strim(model_rev, sizeof(model_rev));
 
-       for (i = 0; i < ARRAY_SIZE(ata_dma_blacklist); i += 2) {
-               if (!strncmp(ata_dma_blacklist[i], model_num, nlen)) {
-                       if (ata_dma_blacklist[i+1] == NULL)
-                               return 1;
-                       if (!strncmp(ata_dma_blacklist[i], model_rev, rlen))
-                               return 1;
+       while (ad->model_num) {
+               if (!strncmp(ad->model_num, model_num, nlen)) {
+                       if (ad->model_rev == NULL)
+                               return ad->horkage;
+                       if (!strncmp(ad->model_rev, model_rev, rlen))
+                               return ad->horkage;
                }
+               ad++;
        }
        return 0;
 }
 
+static int ata_dma_blacklisted(const struct ata_device *dev)
+{
+       /* We don't support polling DMA.
+        * DMA blacklist those ATAPI devices with CDB-intr (and use PIO)
+        * if the LLDD handles only interrupts in the HSM_ST_LAST state.
+        */
+       if ((dev->ap->flags & ATA_FLAG_PIO_POLLING) &&
+           (dev->flags & ATA_DFLAG_CDB_INTR))
+               return 1;
+       return (ata_device_blacklisted(dev) & ATA_HORKAGE_NODMA) ? 1 : 0;
+}
+
 /**
  *     ata_dev_xfermask - Compute supported xfermask of the given device
  *     @dev: Device to compute xfermask for
@@ -3093,6 +3251,13 @@ static void ata_dev_xfermask(struct ata_device *dev)
         */
        if (ap->cbl == ATA_CBL_PATA40)
                xfer_mask &= ~(0xF8 << ATA_SHIFT_UDMA);
+       /* Apply drive side cable rule. Unknown or 80 pin cables reported
+        * host side are checked drive side as well. Cases where we know a
+        * 40wire cable is used safely for 80 are not checked here.
+        */
+        if (ata_drive_40wire(dev->id) && (ap->cbl == ATA_CBL_PATA_UNK || ap->cbl == ATA_CBL_PATA80))
+               xfer_mask &= ~(0xF8 << ATA_SHIFT_UDMA);
+
 
        xfer_mask &= ata_pack_xfermask(dev->pio_mask,
                                       dev->mwdma_mask, dev->udma_mask);
@@ -3369,19 +3534,15 @@ void ata_noop_qc_prep(struct ata_queued_cmd *qc) { }
 
 void ata_sg_init_one(struct ata_queued_cmd *qc, void *buf, unsigned int buflen)
 {
-       struct scatterlist *sg;
-
        qc->flags |= ATA_QCFLAG_SINGLE;
 
-       memset(&qc->sgent, 0, sizeof(qc->sgent));
        qc->__sg = &qc->sgent;
        qc->n_elem = 1;
        qc->orig_n_elem = 1;
        qc->buf_virt = buf;
        qc->nbytes = buflen;
 
-       sg = qc->__sg;
-       sg_init_one(sg, buf, buflen);
+       sg_init_one(&qc->sgent, buf, buflen);
 }
 
 /**
@@ -4174,8 +4335,12 @@ fsm_start:
                                        /* device stops HSM for abort/error */
                                        qc->err_mask |= AC_ERR_DEV;
                                else
-                                       /* HSM violation. Let EH handle this */
-                                       qc->err_mask |= AC_ERR_HSM;
+                                       /* HSM violation. Let EH handle this.
+                                        * Phantom devices also trigger this
+                                        * condition.  Mark hint.
+                                        */
+                                       qc->err_mask |= AC_ERR_HSM |
+                                                       AC_ERR_NODEV_HINT;
 
                                ap->hsm_task_state = HSM_ST_ERR;
                                goto fsm_start;
@@ -4414,6 +4579,14 @@ void __ata_qc_complete(struct ata_queued_cmd *qc)
        qc->complete_fn(qc);
 }
 
+static void fill_result_tf(struct ata_queued_cmd *qc)
+{
+       struct ata_port *ap = qc->ap;
+
+       ap->ops->tf_read(ap, &qc->result_tf);
+       qc->result_tf.flags = qc->tf.flags;
+}
+
 /**
  *     ata_qc_complete - Complete an active ATA command
  *     @qc: Command to complete
@@ -4451,7 +4624,7 @@ void ata_qc_complete(struct ata_queued_cmd *qc)
                if (unlikely(qc->flags & ATA_QCFLAG_FAILED)) {
                        if (!ata_tag_internal(qc->tag)) {
                                /* always fill result TF for failed qc */
-                               ap->ops->tf_read(ap, &qc->result_tf);
+                               fill_result_tf(qc);
                                ata_qc_schedule_eh(qc);
                                return;
                        }
@@ -4459,7 +4632,7 @@ void ata_qc_complete(struct ata_queued_cmd *qc)
 
                /* read result TF if requested */
                if (qc->flags & ATA_QCFLAG_RESULT_TF)
-                       ap->ops->tf_read(ap, &qc->result_tf);
+                       fill_result_tf(qc);
 
                __ata_qc_complete(qc);
        } else {
@@ -4468,7 +4641,7 @@ void ata_qc_complete(struct ata_queued_cmd *qc)
 
                /* read result TF if failed or requested */
                if (qc->err_mask || qc->flags & ATA_QCFLAG_RESULT_TF)
-                       ap->ops->tf_read(ap, &qc->result_tf);
+                       fill_result_tf(qc);
 
                __ata_qc_complete(qc);
        }
@@ -4835,7 +5008,6 @@ idle_irq:
  *     ata_interrupt - Default ATA host interrupt handler
  *     @irq: irq line (unused)
  *     @dev_instance: pointer to our ata_host information structure
- *     @regs: unused
  *
  *     Default interrupt handler for PCI IDE devices.  Calls
  *     ata_host_intr() for each port that is not disabled.
@@ -4847,7 +5019,7 @@ idle_irq:
  *     IRQ_NONE or IRQ_HANDLED.
  */
 
-irqreturn_t ata_interrupt (int irq, void *dev_instance, struct pt_regs *regs)
+irqreturn_t ata_interrupt (int irq, void *dev_instance)
 {
        struct ata_host *host = dev_instance;
        unsigned int i;
@@ -5023,7 +5195,7 @@ int ata_flush_cache(struct ata_device *dev)
        if (!ata_try_flush_cache(dev))
                return 0;
 
-       if (ata_id_has_flush_ext(dev->id))
+       if (dev->flags & ATA_DFLAG_FLUSH_EXT)
                cmd = ATA_CMD_FLUSH_EXT;
        else
                cmd = ATA_CMD_FLUSH;
@@ -5269,11 +5441,19 @@ void ata_port_init(struct ata_port *ap, struct ata_host *host,
        ap->host = host;
        ap->dev = ent->dev;
        ap->port_no = port_no;
-       ap->pio_mask = ent->pio_mask;
-       ap->mwdma_mask = ent->mwdma_mask;
-       ap->udma_mask = ent->udma_mask;
-       ap->flags |= ent->port_flags;
-       ap->ops = ent->port_ops;
+       if (port_no == 1 && ent->pinfo2) {
+               ap->pio_mask = ent->pinfo2->pio_mask;
+               ap->mwdma_mask = ent->pinfo2->mwdma_mask;
+               ap->udma_mask = ent->pinfo2->udma_mask;
+               ap->flags |= ent->pinfo2->flags;
+               ap->ops = ent->pinfo2->port_ops;
+       } else {
+               ap->pio_mask = ent->pio_mask;
+               ap->mwdma_mask = ent->mwdma_mask;
+               ap->udma_mask = ent->udma_mask;
+               ap->flags |= ent->port_flags;
+               ap->ops = ent->port_ops;
+       }
        ap->hw_sata_spd_limit = UINT_MAX;
        ap->active_tag = ATA_TAG_POISON;
        ap->last_ctl = 0xFF;
@@ -5425,6 +5605,11 @@ int ata_device_add(const struct ata_probe_ent *ent)
        int rc;
 
        DPRINTK("ENTER\n");
+       
+       if (ent->irq == 0) {
+               dev_printk(KERN_ERR, dev, "is not available: No interrupt assigned.\n");
+               return 0;
+       }
        /* alloc a container for our list of ATA ports (buses) */
        host = kzalloc(sizeof(struct ata_host) +
                       (ent->n_ports * sizeof(void *)), GFP_KERNEL);
@@ -5445,11 +5630,10 @@ int ata_device_add(const struct ata_probe_ent *ent)
                int irq_line = ent->irq;
 
                ap = ata_port_add(ent, host, i);
+               host->ports[i] = ap;
                if (!ap)
                        goto err_out;
 
-               host->ports[i] = ap;
-
                /* dummy? */
                if (ent->dummy_port_mask & (1 << i)) {
                        ata_port_printk(ap, KERN_INFO, "DUMMY\n");
@@ -5707,7 +5891,7 @@ void ata_host_remove(struct ata_host *host)
 
 /**
  *     ata_scsi_release - SCSI layer callback hook for host unload
- *     @host: libata host to be unloaded
+ *     @shost: libata host to be unloaded
  *
  *     Performs all duties necessary to shut down a libata port...
  *     Kill port kthread, disable port, and release resources.
@@ -5753,6 +5937,7 @@ ata_probe_ent_alloc(struct device *dev, const struct ata_port_info *port)
        probe_ent->mwdma_mask = port->mwdma_mask;
        probe_ent->udma_mask = port->udma_mask;
        probe_ent->port_ops = port->port_ops;
+       probe_ent->private_data = port->private_data;
 
        return probe_ent;
 }
@@ -5919,7 +6104,7 @@ static void __exit ata_exit(void)
        destroy_workqueue(ata_aux_wq);
 }
 
-module_init(ata_init);
+subsys_initcall(ata_init);
 module_exit(ata_exit);
 
 static unsigned long ratelimit_time;
@@ -6082,9 +6267,9 @@ EXPORT_SYMBOL_GPL(__sata_phy_reset);
 EXPORT_SYMBOL_GPL(ata_bus_reset);
 EXPORT_SYMBOL_GPL(ata_std_prereset);
 EXPORT_SYMBOL_GPL(ata_std_softreset);
+EXPORT_SYMBOL_GPL(sata_port_hardreset);
 EXPORT_SYMBOL_GPL(sata_std_hardreset);
 EXPORT_SYMBOL_GPL(ata_std_postreset);
-EXPORT_SYMBOL_GPL(ata_dev_revalidate);
 EXPORT_SYMBOL_GPL(ata_dev_classify);
 EXPORT_SYMBOL_GPL(ata_dev_pair);
 EXPORT_SYMBOL_GPL(ata_port_disable);
@@ -6109,6 +6294,7 @@ EXPORT_SYMBOL_GPL(ata_host_suspend);
 EXPORT_SYMBOL_GPL(ata_host_resume);
 EXPORT_SYMBOL_GPL(ata_id_string);
 EXPORT_SYMBOL_GPL(ata_id_c_string);
+EXPORT_SYMBOL_GPL(ata_device_blacklisted);
 EXPORT_SYMBOL_GPL(ata_scsi_simulate);
 
 EXPORT_SYMBOL_GPL(ata_pio_need_iordy);