ide: fix UDMA/MWDMA/SWDMA masks (v3)
authorBartlomiej Zolnierkiewicz <bzolnier@gmail.com>
Wed, 9 May 2007 22:01:07 +0000 (00:01 +0200)
committerBartlomiej Zolnierkiewicz <bzolnier@gmail.com>
Wed, 9 May 2007 22:01:07 +0000 (00:01 +0200)
* use 0x00 instead of 0x80 to disable ->{ultra,mwdma,swdma}_mask
* add udma_mask field to ide_pci_device_t and use it to initialize
  ->ultra_mask in aec62xx, cmd64x, pdc202xx_{new,old} and piix drivers
* fix UDMA masks to match with chipset specific *_ratemask()
  (alim15x3, hpt366, serverworks and siimage drivers need UDMA mask
   filtering method - done in the next patch)

v2:
* piix: fix cable detection for 82801AA_1 and 82372FB_1
  [ Noticed by Sergei Shtylyov <sshtylyov@ru.mvista.com>. ]
* cmd64x: use hwif->cds->udma_mask
  [ Suggested by Sergei Shtylyov <sshtylyov@ru.mvista.com>. ]
* aec62xx: fix newly introduced bug - check DMA status not command register
  [ Noticed by Sergei Shtylyov <sshtylyov@ru.mvista.com>. ]

v3:
* piix: use hwif->cds->udma_mask
  [ Suggested by Sergei Shtylyov <sshtylyov@ru.mvista.com>. ]

Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
drivers/ide/ide.c
drivers/ide/pci/aec62xx.c
drivers/ide/pci/alim15x3.c
drivers/ide/pci/cmd64x.c
drivers/ide/pci/pdc202xx_new.c
drivers/ide/pci/pdc202xx_old.c
drivers/ide/pci/piix.c
drivers/ide/pci/sis5513.c
include/linux/ide.h

index ae5bf2b..c06424f 100644 (file)
@@ -216,9 +216,6 @@ static void init_hwif_data(ide_hwif_t *hwif, unsigned int index)
        hwif->bus_state = BUSSTATE_ON;
 
        hwif->atapi_dma = 0;            /* disable all atapi dma */ 
-       hwif->ultra_mask = 0x80;        /* disable all ultra */
-       hwif->mwdma_mask = 0x80;        /* disable all mwdma */
-       hwif->swdma_mask = 0x80;        /* disable all swdma */
 
        init_completion(&hwif->gendev_rel_comp);
 
index 73bdf64..abe0b1b 100644 (file)
@@ -261,11 +261,13 @@ static unsigned int __devinit init_chipset_aec62xx(struct pci_dev *dev, const ch
 
 static void __devinit init_hwif_aec62xx(ide_hwif_t *hwif)
 {
+       struct pci_dev *dev = hwif->pci_dev;
+
        hwif->autodma = 0;
        hwif->tuneproc = &aec62xx_tune_drive;
        hwif->speedproc = &aec62xx_tune_chipset;
 
-       if (hwif->pci_dev->device == PCI_DEVICE_ID_ARTOP_ATP850UF)
+       if (dev->device == PCI_DEVICE_ID_ARTOP_ATP850UF)
                hwif->serialized = hwif->channel;
 
        if (hwif->mate)
@@ -277,7 +279,15 @@ static void __devinit init_hwif_aec62xx(ide_hwif_t *hwif)
                return;
        }
 
-       hwif->ultra_mask = 0x7f;
+       hwif->ultra_mask = hwif->cds->udma_mask;
+
+       /* atp865 and atp865r */
+       if (hwif->ultra_mask == 0x3f) {
+               /* check bit 0x10 of DMA status register */
+               if (inb(pci_resource_start(dev, 4) + 2) & 0x10)
+                       hwif->ultra_mask = 0x7f; /* udma0-6 */
+       }
+
        hwif->mwdma_mask = 0x07;
 
        hwif->ide_dma_check     = &aec62xx_config_drive_xfer_rate;
@@ -344,6 +354,7 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .enablebits     = {{0x4a,0x02,0x02}, {0x4a,0x04,0x04}},
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x07, /* udma0-2 */
        },{     /* 1 */
                .name           = "AEC6260",
                .init_setup     = init_setup_aec62xx,
@@ -353,6 +364,7 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = NOAUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x1f, /* udma0-4 */
        },{     /* 2 */
                .name           = "AEC6260R",
                .init_setup     = init_setup_aec62xx,
@@ -363,6 +375,7 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .enablebits     = {{0x4a,0x02,0x02}, {0x4a,0x04,0x04}},
                .bootable       = NEVER_BOARD,
+               .udma_mask      = 0x1f, /* udma0-4 */
        },{     /* 3 */
                .name           = "AEC6X80",
                .init_setup     = init_setup_aec6x80,
@@ -372,6 +385,7 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x3f, /* udma0-5 */
        },{     /* 4 */
                .name           = "AEC6X80R",
                .init_setup     = init_setup_aec6x80,
@@ -382,6 +396,7 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .enablebits     = {{0x4a,0x02,0x02}, {0x4a,0x04,0x04}},
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x3f, /* udma0-5 */
        }
 };
 
index 946a127..26c27d9 100644 (file)
@@ -783,8 +783,17 @@ static void __devinit init_hwif_common_ali15x3 (ide_hwif_t *hwif)
 
        hwif->atapi_dma = 1;
 
-       if (m5229_revision > 0x20)
-               hwif->ultra_mask = 0x7f;
+       if (m5229_revision <= 0x20)
+               hwif->ultra_mask = 0x00; /* no udma */
+       else if (m5229_revision < 0xC2)
+               hwif->ultra_mask = 0x07; /* udma0-2 */
+       else if (m5229_revision == 0xC2 || m5229_revision == 0xC3)
+               hwif->ultra_mask = 0x1f; /* udma0-4 */
+       else if (m5229_revision == 0xC4)
+               hwif->ultra_mask = 0x3f; /* udma0-5 */
+       else
+               hwif->ultra_mask = 0x7f; /* udma0-6 */
+
        hwif->mwdma_mask = 0x07;
        hwif->swdma_mask = 0x07;
 
index 77f51ab..610c45f 100644 (file)
@@ -644,15 +644,12 @@ static void __devinit init_hwif_cmd64x(ide_hwif_t *hwif)
 
        hwif->atapi_dma = 1;
 
-       hwif->ultra_mask = 0x3f;
-       hwif->mwdma_mask = 0x07;
+       hwif->ultra_mask = hwif->cds->udma_mask;
+
+       if (dev->device == PCI_DEVICE_ID_CMD_646 && class_rev < 5)
+               hwif->ultra_mask = 0x00;
 
-       if (dev->device == PCI_DEVICE_ID_CMD_643)
-               hwif->ultra_mask = 0x80;
-       if (dev->device == PCI_DEVICE_ID_CMD_646)
-               hwif->ultra_mask = (class_rev > 0x04) ? 0x07 : 0x80;
-       if (dev->device == PCI_DEVICE_ID_CMD_648)
-               hwif->ultra_mask = 0x1f;
+       hwif->mwdma_mask = 0x07;
 
        hwif->ide_dma_check = &cmd64x_config_drive_for_dma;
        if (!(hwif->udma_four))
@@ -716,6 +713,7 @@ static ide_pci_device_t cmd64x_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .enablebits     = {{0x00,0x00,0x00}, {0x51,0x08,0x08}},
                .bootable       = ON_BOARD,
+               .udma_mask      = 0x00, /* no udma */
        },{     /* 1 */
                .name           = "CMD646",
                .init_setup     = init_setup_cmd646,
@@ -725,6 +723,7 @@ static ide_pci_device_t cmd64x_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .enablebits     = {{0x51,0x04,0x04}, {0x51,0x08,0x08}},
                .bootable       = ON_BOARD,
+               .udma_mask      = 0x07, /* udma0-2 */
        },{     /* 2 */
                .name           = "CMD648",
                .init_setup     = init_setup_cmd64x,
@@ -734,6 +733,7 @@ static ide_pci_device_t cmd64x_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .enablebits     = {{0x51,0x04,0x04}, {0x51,0x08,0x08}},
                .bootable       = ON_BOARD,
+               .udma_mask      = 0x1f, /* udma0-4 */
        },{     /* 3 */
                .name           = "CMD649",
                .init_setup     = init_setup_cmd64x,
@@ -743,6 +743,7 @@ static ide_pci_device_t cmd64x_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .enablebits     = {{0x51,0x04,0x04}, {0x51,0x08,0x08}},
                .bootable       = ON_BOARD,
+               .udma_mask      = 0x3f, /* udma0-5 */
        }
 };
 
index 2cdd629..a238534 100644 (file)
@@ -543,7 +543,8 @@ static void __devinit init_hwif_pdc202new(ide_hwif_t *hwif)
        hwif->drives[0].autotune = hwif->drives[1].autotune = 1;
 
        hwif->atapi_dma  = 1;
-       hwif->ultra_mask = 0x7f;
+
+       hwif->ultra_mask = hwif->cds->udma_mask;
        hwif->mwdma_mask = 0x07;
 
        hwif->err_stops_fifo = 1;
@@ -619,6 +620,7 @@ static ide_pci_device_t pdcnew_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x3f, /* udma0-5 */
        },{     /* 1 */
                .name           = "PDC20269",
                .init_setup     = init_setup_pdcnew,
@@ -627,6 +629,7 @@ static ide_pci_device_t pdcnew_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x7f, /* udma0-6*/
        },{     /* 2 */
                .name           = "PDC20270",
                .init_setup     = init_setup_pdc20270,
@@ -635,6 +638,7 @@ static ide_pci_device_t pdcnew_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x3f, /* udma0-5 */
        },{     /* 3 */
                .name           = "PDC20271",
                .init_setup     = init_setup_pdcnew,
@@ -643,6 +647,7 @@ static ide_pci_device_t pdcnew_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x7f, /* udma0-6*/
        },{     /* 4 */
                .name           = "PDC20275",
                .init_setup     = init_setup_pdcnew,
@@ -651,6 +656,7 @@ static ide_pci_device_t pdcnew_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x7f, /* udma0-6*/
        },{     /* 5 */
                .name           = "PDC20276",
                .init_setup     = init_setup_pdc20276,
@@ -659,6 +665,7 @@ static ide_pci_device_t pdcnew_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x7f, /* udma0-6*/
        },{     /* 6 */
                .name           = "PDC20277",
                .init_setup     = init_setup_pdcnew,
@@ -667,6 +674,7 @@ static ide_pci_device_t pdcnew_chipsets[] __devinitdata = {
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
+               .udma_mask      = 0x7f, /* udma0-6*/
        }
 };
 
index a7a639f..d7a3806 100644 (file)
@@ -478,7 +478,7 @@ static void __devinit init_hwif_pdc202xx(ide_hwif_t *hwif)
 
        hwif->drives[0].autotune = hwif->drives[1].autotune = 1;
 
-       hwif->ultra_mask = 0x3f;
+       hwif->ultra_mask = hwif->cds->udma_mask;
        hwif->mwdma_mask = 0x07;
        hwif->swdma_mask = 0x07;
        hwif->atapi_dma = 1;
@@ -587,6 +587,7 @@ static ide_pci_device_t pdc202xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .extra          = 16,
+               .udma_mask      = 0x07, /* udma0-2 */
        },{     /* 1 */
                .name           = "PDC20262",
                .init_setup     = init_setup_pdc202ata4,
@@ -597,6 +598,7 @@ static ide_pci_device_t pdc202xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .extra          = 48,
+               .udma_mask      = 0x1f, /* udma0-4 */
        },{     /* 2 */
                .name           = "PDC20263",
                .init_setup     = init_setup_pdc202ata4,
@@ -607,6 +609,7 @@ static ide_pci_device_t pdc202xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .extra          = 48,
+               .udma_mask      = 0x1f, /* udma0-4 */
        },{     /* 3 */
                .name           = "PDC20265",
                .init_setup     = init_setup_pdc20265,
@@ -617,6 +620,7 @@ static ide_pci_device_t pdc202xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .extra          = 48,
+               .udma_mask      = 0x3f, /* udma0-5 */
        },{     /* 4 */
                .name           = "PDC20267",
                .init_setup     = init_setup_pdc202xx,
@@ -627,6 +631,7 @@ static ide_pci_device_t pdc202xx_chipsets[] __devinitdata = {
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .extra          = 48,
+               .udma_mask      = 0x3f, /* udma0-5 */
        }
 };
 
index 061d300..17ea44e 100644 (file)
@@ -524,26 +524,14 @@ static void __devinit init_hwif_piix(ide_hwif_t *hwif)
                hwif->ide_dma_clear_irq = &piix_dma_clear_irq;
 
        hwif->atapi_dma = 1;
-       hwif->ultra_mask = 0x3f;
+
+       hwif->ultra_mask = hwif->cds->udma_mask;
        hwif->mwdma_mask = 0x06;
        hwif->swdma_mask = 0x04;
 
-       switch(hwif->pci_dev->device) {
-               case PCI_DEVICE_ID_INTEL_82371FB_0:
-               case PCI_DEVICE_ID_INTEL_82371FB_1:
-               case PCI_DEVICE_ID_INTEL_82371SB_1:
-                       hwif->ultra_mask = 0x80;
-                       break;
-               case PCI_DEVICE_ID_INTEL_82371AB:
-               case PCI_DEVICE_ID_INTEL_82443MX_1:
-               case PCI_DEVICE_ID_INTEL_82451NX:
-               case PCI_DEVICE_ID_INTEL_82801AB_1:
-                       hwif->ultra_mask = 0x07;
-                       break;
-               default:
-                       if (!hwif->udma_four)
-                               hwif->udma_four = piix_cable_detect(hwif);
-                       break;
+       if (hwif->ultra_mask & 0x78) {
+               if (!hwif->udma_four)
+                       hwif->udma_four = piix_cable_detect(hwif);
        }
 
        if (no_piix_dma)
@@ -557,7 +545,7 @@ static void __devinit init_hwif_piix(ide_hwif_t *hwif)
        hwif->drives[0].autodma = hwif->autodma;
 }
 
-#define DECLARE_PIIX_DEV(name_str) \
+#define DECLARE_PIIX_DEV(name_str, udma) \
        {                                               \
                .name           = name_str,             \
                .init_chipset   = init_chipset_piix,    \
@@ -566,11 +554,12 @@ static void __devinit init_hwif_piix(ide_hwif_t *hwif)
                .autodma        = AUTODMA,              \
                .enablebits     = {{0x41,0x80,0x80}, {0x43,0x80,0x80}}, \
                .bootable       = ON_BOARD,             \
+               .udma_mask      = udma,                 \
        }
 
 static ide_pci_device_t piix_pci_info[] __devinitdata = {
-       /*  0 */ DECLARE_PIIX_DEV("PIIXa"),
-       /*  1 */ DECLARE_PIIX_DEV("PIIXb"),
+       /*  0 */ DECLARE_PIIX_DEV("PIIXa", 0x00),       /* no udma */
+       /*  1 */ DECLARE_PIIX_DEV("PIIXb", 0x00),       /* no udma */
 
        /*  2 */
        {       /*
@@ -587,28 +576,28 @@ static ide_pci_device_t piix_pci_info[] __devinitdata = {
                .flags          = IDEPCI_FLAG_ISA_PORTS
        },
 
-       /*  3 */ DECLARE_PIIX_DEV("PIIX3"),
-       /*  4 */ DECLARE_PIIX_DEV("PIIX4"),
-       /*  5 */ DECLARE_PIIX_DEV("ICH0"),
-       /*  6 */ DECLARE_PIIX_DEV("PIIX4"),
-       /*  7 */ DECLARE_PIIX_DEV("ICH"),
-       /*  8 */ DECLARE_PIIX_DEV("PIIX4"),
-       /*  9 */ DECLARE_PIIX_DEV("PIIX4"),
-       /* 10 */ DECLARE_PIIX_DEV("ICH2"),
-       /* 11 */ DECLARE_PIIX_DEV("ICH2M"),
-       /* 12 */ DECLARE_PIIX_DEV("ICH3M"),
-       /* 13 */ DECLARE_PIIX_DEV("ICH3"),
-       /* 14 */ DECLARE_PIIX_DEV("ICH4"),
-       /* 15 */ DECLARE_PIIX_DEV("ICH5"),
-       /* 16 */ DECLARE_PIIX_DEV("C-ICH"),
-       /* 17 */ DECLARE_PIIX_DEV("ICH4"),
-       /* 18 */ DECLARE_PIIX_DEV("ICH5-SATA"),
-       /* 19 */ DECLARE_PIIX_DEV("ICH5"),
-       /* 20 */ DECLARE_PIIX_DEV("ICH6"),
-       /* 21 */ DECLARE_PIIX_DEV("ICH7"),
-       /* 22 */ DECLARE_PIIX_DEV("ICH4"),
-       /* 23 */ DECLARE_PIIX_DEV("ESB2"),
-       /* 24 */ DECLARE_PIIX_DEV("ICH8M"),
+       /*  3 */ DECLARE_PIIX_DEV("PIIX3", 0x00),       /* no udma */
+       /*  4 */ DECLARE_PIIX_DEV("PIIX4", 0x07),       /* udma0-2 */
+       /*  5 */ DECLARE_PIIX_DEV("ICH0",  0x07),       /* udma0-2 */
+       /*  6 */ DECLARE_PIIX_DEV("PIIX4", 0x07),       /* udma0-2 */
+       /*  7 */ DECLARE_PIIX_DEV("ICH",   0x1f),       /* udma0-4 */
+       /*  8 */ DECLARE_PIIX_DEV("PIIX4", 0x1f),       /* udma0-4 */
+       /*  9 */ DECLARE_PIIX_DEV("PIIX4", 0x07),       /* udma0-2 */
+       /* 10 */ DECLARE_PIIX_DEV("ICH2",  0x3f),       /* udma0-5 */
+       /* 11 */ DECLARE_PIIX_DEV("ICH2M", 0x3f),       /* udma0-5 */
+       /* 12 */ DECLARE_PIIX_DEV("ICH3M", 0x3f),       /* udma0-5 */
+       /* 13 */ DECLARE_PIIX_DEV("ICH3",  0x3f),       /* udma0-5 */
+       /* 14 */ DECLARE_PIIX_DEV("ICH4",  0x3f),       /* udma0-5 */
+       /* 15 */ DECLARE_PIIX_DEV("ICH5",  0x3f),       /* udma0-5 */
+       /* 16 */ DECLARE_PIIX_DEV("C-ICH", 0x3f),       /* udma0-5 */
+       /* 17 */ DECLARE_PIIX_DEV("ICH4",  0x3f),       /* udma0-5 */
+       /* 18 */ DECLARE_PIIX_DEV("ICH5-SATA", 0x3f),   /* udma0-5 */
+       /* 19 */ DECLARE_PIIX_DEV("ICH5",  0x3f),       /* udma0-5 */
+       /* 20 */ DECLARE_PIIX_DEV("ICH6",  0x3f),       /* udma0-5 */
+       /* 21 */ DECLARE_PIIX_DEV("ICH7",  0x3f),       /* udma0-5 */
+       /* 22 */ DECLARE_PIIX_DEV("ICH4",  0x3f),       /* udma0-5 */
+       /* 23 */ DECLARE_PIIX_DEV("ESB2",  0x3f),       /* udma0-5 */
+       /* 24 */ DECLARE_PIIX_DEV("ICH8M", 0x3f),       /* udma0-5 */
 };
 
 /**
index 2ba0669..6fe4ecb 100644 (file)
@@ -858,6 +858,8 @@ static unsigned int __devinit ata66_sis5513 (ide_hwif_t *hwif)
 
 static void __devinit init_hwif_sis5513 (ide_hwif_t *hwif)
 {
+       u8 udma_rates[] = { 0x00, 0x00, 0x07, 0x1f, 0x3f, 0x3f, 0x7f, 0x7f };
+
        hwif->autodma = 0;
 
        if (!hwif->irq)
@@ -873,7 +875,8 @@ static void __devinit init_hwif_sis5513 (ide_hwif_t *hwif)
        }
 
        hwif->atapi_dma = 1;
-       hwif->ultra_mask = 0x7f;
+
+       hwif->ultra_mask = udma_rates[chipset_family];
        hwif->mwdma_mask = 0x07;
        hwif->swdma_mask = 0x07;
 
index 418dfb5..c9375c8 100644 (file)
@@ -1257,6 +1257,7 @@ typedef struct ide_pci_device_s {
        unsigned int            extra;
        struct ide_pci_device_s *next;
        u8                      flags;
+       u8                      udma_mask;
 } ide_pci_device_t;
 
 extern int ide_setup_pci_device(struct pci_dev *, ide_pci_device_t *);