Merge tag 'defconfig-5.15' of git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc
[linux-2.6-microblaze.git] / drivers / ata / libata-sata.c
index 8adeab7..8f3ff83 100644 (file)
@@ -834,28 +834,46 @@ DEVICE_ATTR(link_power_management_policy, S_IRUGO | S_IWUSR,
            ata_scsi_lpm_show, ata_scsi_lpm_store);
 EXPORT_SYMBOL_GPL(dev_attr_link_power_management_policy);
 
+static ssize_t ata_ncq_prio_supported_show(struct device *device,
+                                          struct device_attribute *attr,
+                                          char *buf)
+{
+       struct scsi_device *sdev = to_scsi_device(device);
+       struct ata_port *ap = ata_shost_to_port(sdev->host);
+       struct ata_device *dev;
+       bool ncq_prio_supported;
+       int rc = 0;
+
+       spin_lock_irq(ap->lock);
+       dev = ata_scsi_find_dev(ap, sdev);
+       if (!dev)
+               rc = -ENODEV;
+       else
+               ncq_prio_supported = dev->flags & ATA_DFLAG_NCQ_PRIO;
+       spin_unlock_irq(ap->lock);
+
+       return rc ? rc : sysfs_emit(buf, "%u\n", ncq_prio_supported);
+}
+
+DEVICE_ATTR(ncq_prio_supported, S_IRUGO, ata_ncq_prio_supported_show, NULL);
+EXPORT_SYMBOL_GPL(dev_attr_ncq_prio_supported);
+
 static ssize_t ata_ncq_prio_enable_show(struct device *device,
                                        struct device_attribute *attr,
                                        char *buf)
 {
        struct scsi_device *sdev = to_scsi_device(device);
-       struct ata_port *ap;
+       struct ata_port *ap = ata_shost_to_port(sdev->host);
        struct ata_device *dev;
        bool ncq_prio_enable;
        int rc = 0;
 
-       ap = ata_shost_to_port(sdev->host);
-
        spin_lock_irq(ap->lock);
        dev = ata_scsi_find_dev(ap, sdev);
-       if (!dev) {
+       if (!dev)
                rc = -ENODEV;
-               goto unlock;
-       }
-
-       ncq_prio_enable = dev->flags & ATA_DFLAG_NCQ_PRIO_ENABLE;
-
-unlock:
+       else
+               ncq_prio_enable = dev->flags & ATA_DFLAG_NCQ_PRIO_ENABLE;
        spin_unlock_irq(ap->lock);
 
        return rc ? rc : snprintf(buf, 20, "%u\n", ncq_prio_enable);
@@ -869,7 +887,7 @@ static ssize_t ata_ncq_prio_enable_store(struct device *device,
        struct ata_port *ap;
        struct ata_device *dev;
        long int input;
-       int rc;
+       int rc = 0;
 
        rc = kstrtol(buf, 10, &input);
        if (rc)
@@ -883,27 +901,20 @@ static ssize_t ata_ncq_prio_enable_store(struct device *device,
                return  -ENODEV;
 
        spin_lock_irq(ap->lock);
+
+       if (!(dev->flags & ATA_DFLAG_NCQ_PRIO)) {
+               rc = -EINVAL;
+               goto unlock;
+       }
+
        if (input)
                dev->flags |= ATA_DFLAG_NCQ_PRIO_ENABLE;
        else
                dev->flags &= ~ATA_DFLAG_NCQ_PRIO_ENABLE;
 
-       dev->link->eh_info.action |= ATA_EH_REVALIDATE;
-       dev->link->eh_info.flags |= ATA_EHI_QUIET;
-       ata_port_schedule_eh(ap);
+unlock:
        spin_unlock_irq(ap->lock);
 
-       ata_port_wait_eh(ap);
-
-       if (input) {
-               spin_lock_irq(ap->lock);
-               if (!(dev->flags & ATA_DFLAG_NCQ_PRIO)) {
-                       dev->flags &= ~ATA_DFLAG_NCQ_PRIO_ENABLE;
-                       rc = -EIO;
-               }
-               spin_unlock_irq(ap->lock);
-       }
-
        return rc ? rc : len;
 }
 
@@ -914,6 +925,7 @@ EXPORT_SYMBOL_GPL(dev_attr_ncq_prio_enable);
 struct device_attribute *ata_ncq_sdev_attrs[] = {
        &dev_attr_unload_heads,
        &dev_attr_ncq_prio_enable,
+       &dev_attr_ncq_prio_supported,
        NULL
 };
 EXPORT_SYMBOL_GPL(ata_ncq_sdev_attrs);