Please apply the attached patch over 2.6.20.1 and report how it works. Thanks. -- tejun
diff --git a/drivers/ata/ahci.c b/drivers/ata/ahci.c index 6d93240..2d7d97d 100644 --- a/drivers/ata/ahci.c +++ b/drivers/ata/ahci.c @@ -80,6 +80,7 @@ enum { board_ahci_pi = 1, board_ahci_vt8251 = 2, board_ahci_ign_iferr = 3, + board_ahci_ign_interr = 4, /* global controller registers */ HOST_CAP = 0x00, /* host capabilities */ @@ -168,6 +169,7 @@ enum { AHCI_FLAG_NO_NCQ = (1 << 24), AHCI_FLAG_IGN_IRQ_IF_ERR = (1 << 25), /* ignore IRQ_IF_ERR */ AHCI_FLAG_HONOR_PI = (1 << 26), /* honor PORTS_IMPL */ + AHCI_FLAG_IGN_SERR_INTERNAL = (1 << 27), /* ignore SERR_INTERNAL */ }; struct ahci_cmd_hdr { @@ -353,6 +355,17 @@ static const struct ata_port_info ahci_port_info[] = { .udma_mask = 0x7f, /* udma0-6 ; FIXME */ .port_ops = &ahci_ops, }, + /* board_ahci_ign_interr */ + { + .sht = &ahci_sht, + .flags = ATA_FLAG_SATA | ATA_FLAG_NO_LEGACY | + ATA_FLAG_MMIO | ATA_FLAG_PIO_DMA | + ATA_FLAG_SKIP_D2H_BSY | + AHCI_FLAG_IGN_SERR_INTERNAL, + .pio_mask = 0x1f, /* pio0-4 */ + .udma_mask = 0x7f, /* udma0-6 ; FIXME */ + .port_ops = &ahci_ops, + }, }; static const struct pci_device_id ahci_pci_tbl[] = { @@ -392,8 +405,8 @@ static const struct pci_device_id ahci_pci_tbl[] = { { PCI_VDEVICE(JMICRON, 0x2366), board_ahci_ign_iferr }, /* JMB366 */ /* ATI */ - { PCI_VDEVICE(ATI, 0x4380), board_ahci }, /* ATI SB600 non-raid */ - { PCI_VDEVICE(ATI, 0x4381), board_ahci }, /* ATI SB600 raid */ + { PCI_VDEVICE(ATI, 0x4380), board_ahci_ign_interr }, /* SB600 non-raid */ + { PCI_VDEVICE(ATI, 0x4381), board_ahci_ign_interr }, /* SB600 raid */ /* VIA */ { PCI_VDEVICE(VIA, 0x3349), board_ahci_vt8251 }, /* VIA VT8251 */ @@ -454,9 +467,10 @@ static inline void __iomem *ahci_port_base(void __iomem *base, return base + 0x100 + (port * 0x80); } -static u32 ahci_scr_read (struct ata_port *ap, unsigned int sc_reg_in) +static u32 ahci_scr_read(struct ata_port *ap, unsigned int sc_reg_in) { unsigned int sc_reg; + u32 serr; switch (sc_reg_in) { case SCR_STATUS: sc_reg = 0; break; @@ -467,12 +481,13 @@ static u32 ahci_scr_read (struct ata_port *ap, unsigned int sc_reg_in) return 0xffffffffU; } - return readl(ap->ioaddr.scr_addr + (sc_reg * 4)); + serr = readl(ap->ioaddr.scr_addr + (sc_reg * 4)); + if (ap->flags & AHCI_FLAG_IGN_SERR_INTERNAL) + serr &= ~SERR_INTERNAL; + return serr; } - -static void ahci_scr_write (struct ata_port *ap, unsigned int sc_reg_in, - u32 val) +static void ahci_scr_write(struct ata_port *ap, unsigned int sc_reg_in, u32 val) { unsigned int sc_reg;