update from rk29 server
[firefly-linux-kernel-4.4.55.git] / drivers / ata / ata_piix.c
index 9ac4e378992ef60d71634121379b91479c8660f2..c33591d3a5999a4e624578132b53eea00d820a98 100644 (file)
@@ -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