summaryrefslogtreecommitdiff
path: root/drivers/ata/ata_piix.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/ata/ata_piix.c')
-rw-r--r--drivers/ata/ata_piix.c22
1 files changed, 19 insertions, 3 deletions
diff --git a/drivers/ata/ata_piix.c b/drivers/ata/ata_piix.c
index 9ac4e378992e..c33591d3a599 100644
--- a/drivers/ata/ata_piix.c
+++ b/drivers/ata/ata_piix.c
@@ -157,6 +157,7 @@ struct piix_map_db {
struct piix_host_priv {
const int *map;
u32 saved_iocfg;
+ spinlock_t sidpr_lock; /* FIXME: remove once locking in EH is fixed */
void __iomem *sidpr;
};
@@ -291,6 +292,14 @@ static const struct pci_device_id piix_pci_tbl[] = {
{ 0x8086, 0x3b2d, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata },
/* SATA Controller IDE (PCH) */
{ 0x8086, 0x3b2e, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata },
+ /* SATA Controller IDE (CPT) */
+ { 0x8086, 0x1c00, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata },
+ /* SATA Controller IDE (CPT) */
+ { 0x8086, 0x1c01, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata },
+ /* SATA Controller IDE (CPT) */
+ { 0x8086, 0x1c08, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata },
+ /* SATA Controller IDE (CPT) */
+ { 0x8086, 0x1c09, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata },
{ } /* terminate list */
};
@@ -869,10 +878,10 @@ static void do_pata_set_dmamode(struct ata_port *ap, struct ata_device *adev, in
(timings[pio][1] << 8);
}
- if (ap->udma_mask) {
+ if (ap->udma_mask)
udma_enable &= ~(1 << devid);
- pci_write_config_word(dev, master_port, master_data);
- }
+
+ pci_write_config_word(dev, master_port, master_data);
}
/* Don't scribble on 0x48 if the controller does not support UDMA */
if (ap->udma_mask)
@@ -940,12 +949,15 @@ static int piix_sidpr_scr_read(struct ata_link *link,
unsigned int reg, u32 *val)
{
struct piix_host_priv *hpriv = link->ap->host->private_data;
+ unsigned long flags;
if (reg >= ARRAY_SIZE(piix_sidx_map))
return -EINVAL;
+ spin_lock_irqsave(&hpriv->sidpr_lock, flags);
piix_sidpr_sel(link, reg);
*val = ioread32(hpriv->sidpr + PIIX_SIDPR_DATA);
+ spin_unlock_irqrestore(&hpriv->sidpr_lock, flags);
return 0;
}
@@ -953,12 +965,15 @@ static int piix_sidpr_scr_write(struct ata_link *link,
unsigned int reg, u32 val)
{
struct piix_host_priv *hpriv = link->ap->host->private_data;
+ unsigned long flags;
if (reg >= ARRAY_SIZE(piix_sidx_map))
return -EINVAL;
+ spin_lock_irqsave(&hpriv->sidpr_lock, flags);
piix_sidpr_sel(link, reg);
iowrite32(val, hpriv->sidpr + PIIX_SIDPR_DATA);
+ spin_unlock_irqrestore(&hpriv->sidpr_lock, flags);
return 0;
}
@@ -1547,6 +1562,7 @@ static int __devinit piix_init_one(struct pci_dev *pdev,
hpriv = devm_kzalloc(dev, sizeof(*hpriv), GFP_KERNEL);
if (!hpriv)
return -ENOMEM;
+ spin_lock_init(&hpriv->sidpr_lock);
/* Save IOCFG, this will be used for cable detection, quirk
* detection and restoration on detach. This is necessary