aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/scsi/libata-core.c31
-rw-r--r--include/linux/ata.h13
2 files changed, 36 insertions, 8 deletions
diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c
index 175d4646333d..09639e7aaa71 100644
--- a/drivers/scsi/libata-core.c
+++ b/drivers/scsi/libata-core.c
@@ -1082,6 +1082,31 @@ static inline void ata_dump_id(struct ata_device *dev)
1082 dev->id[93]); 1082 dev->id[93]);
1083} 1083}
1084 1084
1085/*
1086 * Compute the PIO modes available for this device. This is not as
1087 * trivial as it seems if we must consider early devices correctly.
1088 *
1089 * FIXME: pre IDE drive timing (do we care ?).
1090 */
1091
1092static unsigned int ata_pio_modes(struct ata_device *adev)
1093{
1094 u16 modes;
1095
1096 /* Usual case. Word 53 indicates word 88 is valid */
1097 if (adev->id[ATA_ID_FIELD_VALID] & (1 << 2)) {
1098 modes = adev->id[ATA_ID_PIO_MODES] & 0x03;
1099 modes <<= 3;
1100 modes |= 0x7;
1101 return modes;
1102 }
1103
1104 /* If word 88 isn't valid then Word 51 holds the PIO timing number
1105 for the maximum. Turn it into a mask and return it */
1106 modes = (2 << (adev->id[ATA_ID_OLD_PIO_MODES] & 0xFF)) - 1 ;
1107 return modes;
1108}
1109
1085/** 1110/**
1086 * ata_dev_identify - obtain IDENTIFY x DEVICE page 1111 * ata_dev_identify - obtain IDENTIFY x DEVICE page
1087 * @ap: port on which device we wish to probe resides 1112 * @ap: port on which device we wish to probe resides
@@ -1215,10 +1240,8 @@ retry:
1215 xfer_modes = dev->id[ATA_ID_UDMA_MODES]; 1240 xfer_modes = dev->id[ATA_ID_UDMA_MODES];
1216 if (!xfer_modes) 1241 if (!xfer_modes)
1217 xfer_modes = (dev->id[ATA_ID_MWDMA_MODES]) << ATA_SHIFT_MWDMA; 1242 xfer_modes = (dev->id[ATA_ID_MWDMA_MODES]) << ATA_SHIFT_MWDMA;
1218 if (!xfer_modes) { 1243 if (!xfer_modes)
1219 xfer_modes = (dev->id[ATA_ID_PIO_MODES]) << (ATA_SHIFT_PIO + 3); 1244 xfer_modes = ata_pio_modes(dev);
1220 xfer_modes |= (0x7 << ATA_SHIFT_PIO);
1221 }
1222 1245
1223 ata_dump_id(dev); 1246 ata_dump_id(dev);
1224 1247
diff --git a/include/linux/ata.h b/include/linux/ata.h
index 630908c9378b..33276d1d05d2 100644
--- a/include/linux/ata.h
+++ b/include/linux/ata.h
@@ -42,13 +42,18 @@ enum {
42 ATA_SECT_SIZE = 512, 42 ATA_SECT_SIZE = 512,
43 43
44 ATA_ID_WORDS = 256, 44 ATA_ID_WORDS = 256,
45 ATA_ID_PROD_OFS = 27,
46 ATA_ID_FW_REV_OFS = 23,
47 ATA_ID_SERNO_OFS = 10, 45 ATA_ID_SERNO_OFS = 10,
48 ATA_ID_MAJOR_VER = 80, 46 ATA_ID_FW_REV_OFS = 23,
49 ATA_ID_PIO_MODES = 64, 47 ATA_ID_PROD_OFS = 27,
48 ATA_ID_OLD_PIO_MODES = 51,
49 ATA_ID_FIELD_VALID = 53,
50 ATA_ID_MWDMA_MODES = 63, 50 ATA_ID_MWDMA_MODES = 63,
51 ATA_ID_PIO_MODES = 64,
52 ATA_ID_EIDE_DMA_MIN = 65,
53 ATA_ID_EIDE_PIO = 67,
54 ATA_ID_EIDE_PIO_IORDY = 68,
51 ATA_ID_UDMA_MODES = 88, 55 ATA_ID_UDMA_MODES = 88,
56 ATA_ID_MAJOR_VER = 80,
52 ATA_ID_PIO4 = (1 << 1), 57 ATA_ID_PIO4 = (1 << 1),
53 58
54 ATA_PCI_CTL_OFS = 2, 59 ATA_PCI_CTL_OFS = 2,