]> www.pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - drivers/ide/pci/aec62xx.c
aec62xx: kill speedproc() method wrapper (take 2)
[linux-2.6-omap-h63xx.git] / drivers / ide / pci / aec62xx.c
index b173bc66ce1e19ae25efef18e8361864c850a877..794ac40ec90f11c059c9a6fb5dfe6bffddebc591 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * linux/drivers/ide/pci/aec62xx.c             Version 0.21    Apr 21, 2007
+ * linux/drivers/ide/pci/aec62xx.c             Version 0.24    May 24, 2007
  *
  * Copyright (C) 1999-2002     Andre Hedrick <andre@linux-ide.org>
  * Copyright (C) 2007          MontaVista Software, Inc. <source@mvista.com>
@@ -140,25 +140,10 @@ static int aec6260_tune_chipset (ide_drive_t *drive, u8 xferspeed)
        return(ide_config_drive_speed(drive, speed));
 }
 
-static int aec62xx_tune_chipset (ide_drive_t *drive, u8 speed)
-{
-       switch (HWIF(drive)->pci_dev->device) {
-               case PCI_DEVICE_ID_ARTOP_ATP865:
-               case PCI_DEVICE_ID_ARTOP_ATP865R:
-               case PCI_DEVICE_ID_ARTOP_ATP860:
-               case PCI_DEVICE_ID_ARTOP_ATP860R:
-                       return ((int) aec6260_tune_chipset(drive, speed));
-               case PCI_DEVICE_ID_ARTOP_ATP850UF:
-                       return ((int) aec6210_tune_chipset(drive, speed));
-               default:
-                       return -1;
-       }
-}
-
 static void aec62xx_tune_drive (ide_drive_t *drive, u8 pio)
 {
        pio = ide_get_best_pio_mode(drive, pio, 4, NULL);
-       (void) aec62xx_tune_chipset(drive, pio + XFER_PIO_0);
+       (void) HWIF(drive)->speedproc(drive, pio + XFER_PIO_0);
 }
 
 static int aec62xx_config_drive_xfer_rate (ide_drive_t *drive)
@@ -172,12 +157,9 @@ static int aec62xx_config_drive_xfer_rate (ide_drive_t *drive)
        return -1;
 }
 
-static int aec62xx_irq_timeout (ide_drive_t *drive)
+static void aec62xx_dma_lost_irq (ide_drive_t *drive)
 {
-       ide_hwif_t *hwif        = HWIF(drive);
-       struct pci_dev *dev     = hwif->pci_dev;
-
-       switch(dev->device) {
+       switch (HWIF(drive)->pci_dev->device) {
                case PCI_DEVICE_ID_ARTOP_ATP860:
                case PCI_DEVICE_ID_ARTOP_ATP860R:
                case PCI_DEVICE_ID_ARTOP_ATP865:
@@ -186,7 +168,6 @@ static int aec62xx_irq_timeout (ide_drive_t *drive)
                default:
                        break;
        }
-       return 0;
 }
 
 static unsigned int __devinit init_chipset_aec62xx(struct pci_dev *dev, const char *name)
@@ -224,64 +205,45 @@ 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;
+       struct pci_dev *dev     = hwif->pci_dev;
+       u8 reg54 = 0,  mask     = hwif->channel ? 0xf0 : 0x0f;
+       unsigned long flags;
 
-       hwif->autodma = 0;
        hwif->tuneproc = &aec62xx_tune_drive;
-       hwif->speedproc = &aec62xx_tune_chipset;
-
-       if (dev->device == PCI_DEVICE_ID_ARTOP_ATP850UF)
-               hwif->serialized = hwif->channel;
 
-       if (hwif->mate)
-               hwif->mate->serialized = hwif->serialized;
+       if (dev->device == PCI_DEVICE_ID_ARTOP_ATP850UF) {
+               if(hwif->mate)
+                       hwif->mate->serialized = hwif->serialized = 1;
+               hwif->speedproc = &aec6210_tune_chipset;
+       } else
+               hwif->speedproc = &aec6260_tune_chipset;
 
        if (!hwif->dma_base) {
-               hwif->drives[0].autotune = 1;
-               hwif->drives[1].autotune = 1;
+               hwif->drives[0].autotune = hwif->drives[1].autotune = 1;
                return;
        }
 
        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;
-       hwif->ide_dma_lostirq   = &aec62xx_irq_timeout;
-
-       if (!noautodma)
-               hwif->autodma = 1;
-       hwif->drives[0].autodma = hwif->autodma;
-       hwif->drives[1].autodma = hwif->autodma;
-}
-
-static void __devinit init_dma_aec62xx(ide_hwif_t *hwif, unsigned long dmabase)
-{
-       struct pci_dev *dev     = hwif->pci_dev;
+       hwif->dma_lost_irq      = &aec62xx_dma_lost_irq;
 
        if (dev->device == PCI_DEVICE_ID_ARTOP_ATP850UF) {
-               u8 reg54h = 0;
-               unsigned long flags;
-
                spin_lock_irqsave(&ide_lock, flags);
-               pci_read_config_byte(dev, 0x54, &reg54h);
-               pci_write_config_byte(dev, 0x54, reg54h & ~(hwif->channel ? 0xF0 : 0x0F));
+               pci_read_config_byte (dev, 0x54, &reg54);
+               pci_write_config_byte(dev, 0x54, (reg54 & ~mask));
                spin_unlock_irqrestore(&ide_lock, flags);
-       } else {
-               u8 ata66        = 0;
+       } else if (!hwif->udma_four) {
+               u8 ata66 = 0, mask = hwif->channel ? 0x02 : 0x01;
+
                pci_read_config_byte(hwif->pci_dev, 0x49, &ata66);
-               if (!(hwif->udma_four))
-                       hwif->udma_four = (ata66&(hwif->channel?0x02:0x01))?0:1;
+               hwif->udma_four = (ata66 & mask) ? 0 : 1;
        }
 
-       ide_setup_dma(hwif, dmabase, 8);
+       if (!noautodma)
+               hwif->autodma = 1;
+       hwif->drives[0].autodma = hwif->drives[1].autodma = hwif->autodma;
 }
 
 static int __devinit init_setup_aec62xx(struct pci_dev *dev, ide_pci_device_t *d)
@@ -291,16 +253,12 @@ static int __devinit init_setup_aec62xx(struct pci_dev *dev, ide_pci_device_t *d
 
 static int __devinit init_setup_aec6x80(struct pci_dev *dev, ide_pci_device_t *d)
 {
-       unsigned long bar4reg = pci_resource_start(dev, 4);
-
-       if (inb(bar4reg+2) & 0x10) {
-               strcpy(d->name, "AEC6880");
-               if (dev->device == PCI_DEVICE_ID_ARTOP_ATP865R)
-                       strcpy(d->name, "AEC6880R");
-       } else {
-               strcpy(d->name, "AEC6280");
-               if (dev->device == PCI_DEVICE_ID_ARTOP_ATP865R)
-                       strcpy(d->name, "AEC6280R");
+       unsigned long dma_base = pci_resource_start(dev, 4);
+
+       if (inb(dma_base + 2) & 0x10) {
+               d->name = (dev->device == PCI_DEVICE_ID_ARTOP_ATP865R) ?
+                         "AEC6880R" : "AEC6880";
+               d->udma_mask = 0x7f; /* udma0-6 */
        }
 
        return ide_setup_pci_device(dev, d);
@@ -312,7 +270,6 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .init_setup     = init_setup_aec62xx,
                .init_chipset   = init_chipset_aec62xx,
                .init_hwif      = init_hwif_aec62xx,
-               .init_dma       = init_dma_aec62xx,
                .channels       = 2,
                .autodma        = AUTODMA,
                .enablebits     = {{0x4a,0x02,0x02}, {0x4a,0x04,0x04}},
@@ -323,7 +280,6 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .init_setup     = init_setup_aec62xx,
                .init_chipset   = init_chipset_aec62xx,
                .init_hwif      = init_hwif_aec62xx,
-               .init_dma       = init_dma_aec62xx,
                .channels       = 2,
                .autodma        = NOAUTODMA,
                .bootable       = OFF_BOARD,
@@ -333,28 +289,25 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
                .init_setup     = init_setup_aec62xx,
                .init_chipset   = init_chipset_aec62xx,
                .init_hwif      = init_hwif_aec62xx,
-               .init_dma       = init_dma_aec62xx,
                .channels       = 2,
                .autodma        = AUTODMA,
                .enablebits     = {{0x4a,0x02,0x02}, {0x4a,0x04,0x04}},
                .bootable       = NEVER_BOARD,
                .udma_mask      = 0x1f, /* udma0-4 */
        },{     /* 3 */
-               .name           = "AEC6X80",
+               .name           = "AEC6280",
                .init_setup     = init_setup_aec6x80,
                .init_chipset   = init_chipset_aec62xx,
                .init_hwif      = init_hwif_aec62xx,
-               .init_dma       = init_dma_aec62xx,
                .channels       = 2,
                .autodma        = AUTODMA,
                .bootable       = OFF_BOARD,
                .udma_mask      = 0x3f, /* udma0-5 */
        },{     /* 4 */
-               .name           = "AEC6X80R",
+               .name           = "AEC6280R",
                .init_setup     = init_setup_aec6x80,
                .init_chipset   = init_chipset_aec62xx,
                .init_hwif      = init_hwif_aec62xx,
-               .init_dma       = init_dma_aec62xx,
                .channels       = 2,
                .autodma        = AUTODMA,
                .enablebits     = {{0x4a,0x02,0x02}, {0x4a,0x04,0x04}},
@@ -370,13 +323,16 @@ static ide_pci_device_t aec62xx_chipsets[] __devinitdata = {
  *
  *     Called when the PCI registration layer (or the IDE initialization)
  *     finds a device matching our IDE device tables.
+ *
+ *     NOTE: since we're going to modify the 'name' field for AEC-6[26]80[R]
+ *     chips, pass a local copy of 'struct pci_device_id' down the call chain.
  */
  
 static int __devinit aec62xx_init_one(struct pci_dev *dev, const struct pci_device_id *id)
 {
-       ide_pci_device_t *d = &aec62xx_chipsets[id->driver_data];
+       ide_pci_device_t d = aec62xx_chipsets[id->driver_data];
 
-       return d->init_setup(dev, d);
+       return d.init_setup(dev, &d);
 }
 
 static struct pci_device_id aec62xx_pci_tbl[] = {