diff options
Diffstat (limited to 'drivers/ide/ppc')
-rw-r--r-- | drivers/ide/ppc/mpc8xx.c | 58 | ||||
-rw-r--r-- | drivers/ide/ppc/pmac.c | 90 |
2 files changed, 92 insertions, 56 deletions
diff --git a/drivers/ide/ppc/mpc8xx.c b/drivers/ide/ppc/mpc8xx.c index a784a97ca7ec..467656f06ccc 100644 --- a/drivers/ide/ppc/mpc8xx.c +++ b/drivers/ide/ppc/mpc8xx.c @@ -36,6 +36,8 @@ #include <asm/machdep.h> #include <asm/irq.h> +#define DRV_NAME "ide-mpc8xx" + static int identify (volatile u8 *p); static void print_fixed (volatile u8 *p); static void print_funcid (int func); @@ -127,7 +129,7 @@ static int pcmcia_schlvl = PCMCIA_SCHLVL; * MPC8xx's internal PCMCIA interface */ #if defined(CONFIG_IDE_8xx_PCCARD) || defined(CONFIG_IDE_8xx_DIRECT) -static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) +static int __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) { unsigned long *p = hw->io_ports; int i; @@ -182,6 +184,13 @@ static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) pcmcia_phy_base, pcmcia_phy_end, pcmcia_phy_end - pcmcia_phy_base); + if (!request_mem_region(pcmcia_phy_base, + pcmcia_phy_end - pcmcia_phy_base, + DRV_NAME)) { + printk(KERN_ERR "%s: resources busy\n", DRV_NAME); + return -EBUSY; + } + pcmcia_base=(unsigned long)ioremap(pcmcia_phy_base, pcmcia_phy_end-pcmcia_phy_base); @@ -236,7 +245,7 @@ static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) if (pcmp->pcmc_pipr & (M8XX_PCMCIA_CD1(_slot_)|M8XX_PCMCIA_CD2(_slot_))) { printk ("No card in slot %c: PIPR=%08x\n", 'A' + _slot_, (u32) pcmp->pcmc_pipr); - return; /* No card in slot */ + return -ENODEV; /* No card in slot */ } check_ide_device (pcmcia_base); @@ -279,9 +288,6 @@ static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) } #endif /* CONFIG_IDE_8xx_PCCARD */ - ide_hwifs[data_port].pio_mask = ATA_PIO4; - ide_hwifs[data_port].set_pio_mode = m8xx_ide_set_pio_mode; - /* Enable Harddisk Interrupt, * and make it edge sensitive */ @@ -296,6 +302,8 @@ static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) /* Enable falling edge irq */ pcmp->pcmc_per = 0x100000 >> (16 * _slot_); #endif /* CONFIG_IDE_8xx_PCCARD */ + + return 0; } #endif /* CONFIG_IDE_8xx_PCCARD || CONFIG_IDE_8xx_DIRECT */ @@ -304,7 +312,7 @@ static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) * MPC8xx's internal PCMCIA interface */ #if defined(CONFIG_IDE_EXT_DIRECT) -static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) +static int __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) { unsigned long *p = hw->io_ports; int i; @@ -327,7 +335,12 @@ static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) printk ("IDE phys mem : %08x...%08x (size %08x)\n", ide_phy_base, ide_phy_end, ide_phy_end - ide_phy_base); - + + if (!request_mem_region(ide_phy_base, 0x200, DRV_NAME)) { + printk(KERN_ERR "%s: resources busy\n", DRV_NAME); + return -EBUSY; + } + ide_base=(unsigned long)ioremap(ide_phy_base, ide_phy_end-ide_phy_base); @@ -357,15 +370,14 @@ static void __init m8xx_ide_init_ports(hw_regs_t *hw, unsigned long data_port) hw->irq = ioport_dsc[data_port].irq; hw->ack_intr = (ide_ack_intr_t *)ide_interrupt_ack; - ide_hwifs[data_port].pio_mask = ATA_PIO4; - ide_hwifs[data_port].set_pio_mode = m8xx_ide_set_pio_mode; - /* Enable Harddisk Interrupt, * and make it edge sensitive */ /* (11-18) Set edge detect for irq, no wakeup from low power mode */ ((immap_t *) IMAP_ADDR)->im_siu_conf.sc_siel |= (0x80000000 >> ioport_dsc[data_port].irq); + + return 0; } #endif /* CONFIG_IDE_8xx_DIRECT */ @@ -794,14 +806,28 @@ static int __init mpc8xx_ide_probe(void) #ifdef IDE0_BASE_OFFSET memset(&hw, 0, sizeof(hw)); - m8xx_ide_init_ports(&hw, 0); - ide_init_port_hw(&ide_hwifs[0], &hw); - idx[0] = 0; + if (!m8xx_ide_init_ports(&hw, 0)) { + ide_hwif_t *hwif = &ide_hwifs[0]; + + ide_init_port_hw(hwif, &hw); + hwif->mmio = 1; + hwif->pio_mask = ATA_PIO4; + hwif->set_pio_mode = m8xx_ide_set_pio_mode; + + idx[0] = 0; + } #ifdef IDE1_BASE_OFFSET memset(&hw, 0, sizeof(hw)); - m8xx_ide_init_ports(&hw, 1); - ide_init_port_hw(&ide_hwifs[1], &hw); - idx[1] = 1; + if (!m8xx_ide_init_ports(&hw, 1)) { + ide_hwif_t *mate = &ide_hwifs[1]; + + ide_init_port_hw(mate, &hw); + mate->mmio = 1; + mate->pio_mask = ATA_PIO4; + mate->set_pio_mode = m8xx_ide_set_pio_mode; + + idx[1] = 1; + } #endif #endif diff --git a/drivers/ide/ppc/pmac.c b/drivers/ide/ppc/pmac.c index 88619b50d9ef..177961edc430 100644 --- a/drivers/ide/ppc/pmac.c +++ b/drivers/ide/ppc/pmac.c @@ -79,8 +79,6 @@ typedef struct pmac_ide_hwif { } pmac_ide_hwif_t; -static pmac_ide_hwif_t pmac_ide[MAX_HWIFS]; - enum { controller_ohare, /* OHare based */ controller_heathrow, /* Heathrow/Paddington */ @@ -923,7 +921,6 @@ pmac_ide_do_resume(ide_hwif_t *hwif) static const struct ide_port_info pmac_port_info = { .chipset = ide_pmac, .host_flags = IDE_HFLAG_SET_PIO_MODE_KEEP_DMA | - IDE_HFLAG_PIO_NO_DOWNGRADE | IDE_HFLAG_POST_SET_MODE | IDE_HFLAG_NO_DMA | /* no SFF-style DMA */ IDE_HFLAG_UNMASK_IRQS, @@ -1088,35 +1085,36 @@ pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_device_id *match) { void __iomem *base; unsigned long regbase; - int irq; ide_hwif_t *hwif; pmac_ide_hwif_t *pmif; - int i, rc; + int irq, rc; hw_regs_t hw; - i = 0; - while (i < MAX_HWIFS && (ide_hwifs[i].io_ports[IDE_DATA_OFFSET] != 0 - || pmac_ide[i].node != NULL)) - ++i; - if (i >= MAX_HWIFS) { + pmif = kzalloc(sizeof(*pmif), GFP_KERNEL); + if (pmif == NULL) + return -ENOMEM; + + hwif = ide_find_port(); + if (hwif == NULL) { printk(KERN_ERR "ide-pmac: MacIO interface attach with no slot\n"); printk(KERN_ERR " %s\n", mdev->ofdev.node->full_name); - return -ENODEV; + rc = -ENODEV; + goto out_free_pmif; } - pmif = &pmac_ide[i]; - hwif = &ide_hwifs[i]; - if (macio_resource_count(mdev) == 0) { - printk(KERN_WARNING "ide%d: no address for %s\n", - i, mdev->ofdev.node->full_name); - return -ENXIO; + printk(KERN_WARNING "ide-pmac: no address for %s\n", + mdev->ofdev.node->full_name); + rc = -ENXIO; + goto out_free_pmif; } /* Request memory resource for IO ports */ if (macio_request_resource(mdev, 0, "ide-pmac (ports)")) { - printk(KERN_ERR "ide%d: can't request mmio resource !\n", i); - return -EBUSY; + printk(KERN_ERR "ide-pmac: can't request MMIO resource for " + "%s!\n", mdev->ofdev.node->full_name); + rc = -EBUSY; + goto out_free_pmif; } /* XXX This is bogus. Should be fixed in the registry by checking @@ -1125,8 +1123,8 @@ pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_device_id *match) * where that happens though... */ if (macio_irq_count(mdev) == 0) { - printk(KERN_WARNING "ide%d: no intrs for device %s, using 13\n", - i, mdev->ofdev.node->full_name); + printk(KERN_WARNING "ide-pmac: no intrs for device %s, using " + "13\n", mdev->ofdev.node->full_name); irq = irq_create_mapping(NULL, 13); } else irq = macio_irq(mdev, 0); @@ -1144,7 +1142,9 @@ pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_device_id *match) #ifdef CONFIG_BLK_DEV_IDEDMA_PMAC if (macio_resource_count(mdev) >= 2) { if (macio_request_resource(mdev, 1, "ide-pmac (dma)")) - printk(KERN_WARNING "ide%d: can't request DMA resource !\n", i); + printk(KERN_WARNING "ide-pmac: can't request DMA " + "resource for %s!\n", + mdev->ofdev.node->full_name); else pmif->dma_regs = ioremap(macio_resource_start(mdev, 1), 0x1000); } else @@ -1166,11 +1166,15 @@ pmac_ide_macio_attach(struct macio_dev *mdev, const struct of_device_id *match) iounmap(pmif->dma_regs); macio_release_resource(mdev, 1); } - memset(pmif, 0, sizeof(*pmif)); macio_release_resource(mdev, 0); + kfree(pmif); } return rc; + +out_free_pmif: + kfree(pmif); + return rc; } static int @@ -1215,7 +1219,7 @@ pmac_ide_pci_attach(struct pci_dev *pdev, const struct pci_device_id *id) pmac_ide_hwif_t *pmif; void __iomem *base; unsigned long rbase, rlen; - int i, rc; + int rc; hw_regs_t hw; np = pci_device_to_OF_node(pdev); @@ -1223,30 +1227,32 @@ pmac_ide_pci_attach(struct pci_dev *pdev, const struct pci_device_id *id) printk(KERN_ERR "ide-pmac: cannot find MacIO node for Kauai ATA interface\n"); return -ENODEV; } - i = 0; - while (i < MAX_HWIFS && (ide_hwifs[i].io_ports[IDE_DATA_OFFSET] != 0 - || pmac_ide[i].node != NULL)) - ++i; - if (i >= MAX_HWIFS) { + + pmif = kzalloc(sizeof(*pmif), GFP_KERNEL); + if (pmif == NULL) + return -ENOMEM; + + hwif = ide_find_port(); + if (hwif == NULL) { printk(KERN_ERR "ide-pmac: PCI interface attach with no slot\n"); printk(KERN_ERR " %s\n", np->full_name); - return -ENODEV; + rc = -ENODEV; + goto out_free_pmif; } - pmif = &pmac_ide[i]; - hwif = &ide_hwifs[i]; - if (pci_enable_device(pdev)) { - printk(KERN_WARNING "ide%i: Can't enable PCI device for %s\n", - i, np->full_name); - return -ENXIO; + printk(KERN_WARNING "ide-pmac: Can't enable PCI device for " + "%s\n", np->full_name); + rc = -ENXIO; + goto out_free_pmif; } pci_set_master(pdev); if (pci_request_regions(pdev, "Kauai ATA")) { - printk(KERN_ERR "ide%d: Cannot obtain PCI resources for %s\n", - i, np->full_name); - return -ENXIO; + printk(KERN_ERR "ide-pmac: Cannot obtain PCI resources for " + "%s\n", np->full_name); + rc = -ENXIO; + goto out_free_pmif; } hwif->dev = &pdev->dev; @@ -1276,11 +1282,15 @@ pmac_ide_pci_attach(struct pci_dev *pdev, const struct pci_device_id *id) /* The inteface is released to the common IDE layer */ pci_set_drvdata(pdev, NULL); iounmap(base); - memset(pmif, 0, sizeof(*pmif)); pci_release_regions(pdev); + kfree(pmif); } return rc; + +out_free_pmif: + kfree(pmif); + return rc; } static int |