On Sun, Aug 24, 2008 at 6:04 AM, Lennert Buytenhek <buytenh@xxxxxxxxxxxxxx> wrote: > For some reason, sata_mv doesn't clear interrupt status during init > when it's running on an SoC host adapter. If the bootloader has > touched the SATA controller before starting Linux, Linux can end up > enabling the SATA interrupt with events pending, which will cause the > interrupt to be marked as spurious and then be disabled, which then > breaks all further accesses to the controller. > > This patch makes the SoC path clear interrupt status on init like in > the non-SoC case. > > Signed-off-by: Lennert Buytenhek <buytenh@xxxxxxxxxxx> > --- > drivers/ata/sata_mv.c | 21 ++++++++++----------- > 1 files changed, 10 insertions(+), 11 deletions(-) > > diff --git a/drivers/ata/sata_mv.c b/drivers/ata/sata_mv.c > index ad169ff..e829a3a 100644 > --- a/drivers/ata/sata_mv.c > +++ b/drivers/ata/sata_mv.c > @@ -3131,19 +3131,18 @@ static int mv_init_host(struct ata_host *host, unsigned int board_idx) > writelfl(0, hc_mmio + HC_IRQ_CAUSE_OFS); > } > > - if (!IS_SOC(hpriv)) { > - /* Clear any currently outstanding host interrupt conditions */ > - writelfl(0, mmio + hpriv->irq_cause_ofs); > + /* Clear any currently outstanding host interrupt conditions */ > + writelfl(0, mmio + hpriv->irq_cause_ofs); > > - /* and unmask interrupt generation for host regs */ > - writelfl(hpriv->unmask_all_irqs, mmio + hpriv->irq_mask_ofs); > + /* and unmask interrupt generation for host regs */ > + writelfl(hpriv->unmask_all_irqs, mmio + hpriv->irq_mask_ofs); > + > + /* > + * enable only global host interrupts for now. > + * The per-port interrupts get done later as ports are set up. > + */ > + mv_set_main_irq_mask(host, 0, PCI_ERR); > > - /* > - * enable only global host interrupts for now. > - * The per-port interrupts get done later as ports are set up. > - */ > - mv_set_main_irq_mask(host, 0, PCI_ERR); > - } > done: > return rc; > } The patch looks fine. Mark, I think that all the code that clears the cause registers should be moved from mv_init_host to the reset_hc functions, which already clears some of those register. for example, register 0x14 (host controller cause register) get cleared twice, the first time at mv5_reset_one_hc. also, the reset_hc functions better use the register define instead of a hardcoded number when possible. saeed -- To unsubscribe from this list: send the line "unsubscribe linux-ide" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html