diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2013-09-03 18:19:53 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2013-09-03 18:19:53 -0700 |
commit | 357397a14117f0c2eeafcac06a1f8412a02aa6af (patch) | |
tree | 8420d5aab6b80fc211979d894174462c9806b26e | |
parent | 9ee52a1633a77961cb7b7fb5bd40be682f8412c7 (diff) | |
parent | 86a565e61bcb9574bae3b622799682fef2d855bb (diff) | |
download | linux-357397a14117f0c2eeafcac06a1f8412a02aa6af.tar.bz2 |
Merge branch 'for-3.12' of git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata
Pull libata changes from Tejun Heo:
"Two interesting changes.
- libata acpi handling has been restructured so that the association
between ata devices and ACPI handles are less convoluted. This
change shouldn't change visible behavior.
- Queued TRIM support, which enables sending TRIM to the device
without draining in-flight RW commands, is added. Currently only
enabled for ahci (and likely to stay that way for the foreseeable
future).
Other changes are driver-specific updates / fixes"
* 'for-3.12' of git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata:
libata: bugfix: Remove __le32 in ata_tf_to_fis()
libata: acpi: Remove ata_dev_acpi_handle stub in libata.h
libata: Add support for queued DSM TRIM
libata: Add support for SEND/RECEIVE FPDMA QUEUED
libata: Add H2D FIS "auxiliary" port flag
libata: Populate host-to-device FIS "auxiliary" field
ata: acpi: rework the ata acpi bind support
sata, highbank: send extra clock cycles in SGPIO patterns
sata, highbank: set tx_atten override bits
devicetree: create a separate binding description for sata_highbank
drivers/ata/sata_rcar.c: simplify use of devm_ioremap_resource
sata highbank: enable 64-bit DMA mask when using LPAE
ata: pata_samsung_cf: add missing __iomem annotation
ata: pata_arasan: Staticize local symbols
sata_mv: Remove unneeded CONFIG_HAVE_CLK ifdefs
ata: use dev_get_platdata()
sata_mv: Remove unneeded forward declaration
libata: acpi: remove dead code for ata_acpi_(un)bind
libata: move 'struct ata_taskfile' and friends from ata.h to libata.h
-rw-r--r-- | Documentation/devicetree/bindings/ata/ahci-platform.txt | 18 | ||||
-rw-r--r-- | Documentation/devicetree/bindings/ata/sata_highbank.txt | 44 | ||||
-rw-r--r-- | drivers/ata/ahci.c | 8 | ||||
-rw-r--r-- | drivers/ata/libata-acpi.c | 278 | ||||
-rw-r--r-- | drivers/ata/libata-core.c | 29 | ||||
-rw-r--r-- | drivers/ata/libata-scsi.c | 38 | ||||
-rw-r--r-- | drivers/ata/libata-transport.c | 2 | ||||
-rw-r--r-- | drivers/ata/libata-zpodd.c | 12 | ||||
-rw-r--r-- | drivers/ata/libata.h | 19 | ||||
-rw-r--r-- | drivers/ata/pata_acpi.c | 4 | ||||
-rw-r--r-- | drivers/ata/pata_arasan_cf.c | 4 | ||||
-rw-r--r-- | drivers/ata/pata_at32.c | 2 | ||||
-rw-r--r-- | drivers/ata/pata_at91.c | 2 | ||||
-rw-r--r-- | drivers/ata/pata_ixp4xx_cf.c | 4 | ||||
-rw-r--r-- | drivers/ata/pata_octeon_cf.c | 2 | ||||
-rw-r--r-- | drivers/ata/pata_platform.c | 2 | ||||
-rw-r--r-- | drivers/ata/pata_pxa.c | 2 | ||||
-rw-r--r-- | drivers/ata/pata_samsung_cf.c | 10 | ||||
-rw-r--r-- | drivers/ata/sata_highbank.c | 74 | ||||
-rw-r--r-- | drivers/ata/sata_mv.c | 26 | ||||
-rw-r--r-- | drivers/ata/sata_rcar.c | 5 | ||||
-rw-r--r-- | drivers/scsi/scsi_lib.c | 22 | ||||
-rw-r--r-- | include/linux/ata.h | 123 | ||||
-rw-r--r-- | include/linux/libata.h | 120 |
24 files changed, 423 insertions, 427 deletions
diff --git a/Documentation/devicetree/bindings/ata/ahci-platform.txt b/Documentation/devicetree/bindings/ata/ahci-platform.txt index 3ec0c5c4f0e9..89de1564950c 100644 --- a/Documentation/devicetree/bindings/ata/ahci-platform.txt +++ b/Documentation/devicetree/bindings/ata/ahci-platform.txt @@ -4,27 +4,17 @@ SATA nodes are defined to describe on-chip Serial ATA controllers. Each SATA controller should have its own node. Required properties: -- compatible : compatible list, contains "calxeda,hb-ahci" or "snps,spear-ahci" +- compatible : compatible list, contains "snps,spear-ahci" - interrupts : <interrupt mapping for SATA IRQ> - reg : <registers mapping> Optional properties: -- calxeda,port-phys: phandle-combophy and lane assignment, which maps each - SATA port to a combophy and a lane within that - combophy -- calxeda,sgpio-gpio: phandle-gpio bank, bit offset, and default on or off, - which indicates that the driver supports SGPIO - indicator lights using the indicated GPIOs -- calxeda,led-order : a u32 array that map port numbers to offsets within the - SGPIO bitstream. - dma-coherent : Present if dma operations are coherent Example: sata@ffe08000 { - compatible = "calxeda,hb-ahci"; - reg = <0xffe08000 0x1000>; - interrupts = <115>; - calxeda,port-phys = <&combophy5 0 &combophy0 0 &combophy0 1 - &combophy0 2 &combophy0 3>; + compatible = "snps,spear-ahci"; + reg = <0xffe08000 0x1000>; + interrupts = <115>; }; diff --git a/Documentation/devicetree/bindings/ata/sata_highbank.txt b/Documentation/devicetree/bindings/ata/sata_highbank.txt new file mode 100644 index 000000000000..aa83407cb7a4 --- /dev/null +++ b/Documentation/devicetree/bindings/ata/sata_highbank.txt @@ -0,0 +1,44 @@ +* Calxeda AHCI SATA Controller + +SATA nodes are defined to describe on-chip Serial ATA controllers. +The Calxeda SATA controller mostly conforms to the AHCI interface +with some special extensions to add functionality. +Each SATA controller should have its own node. + +Required properties: +- compatible : compatible list, contains "calxeda,hb-ahci" +- interrupts : <interrupt mapping for SATA IRQ> +- reg : <registers mapping> + +Optional properties: +- dma-coherent : Present if dma operations are coherent +- calxeda,port-phys : phandle-combophy and lane assignment, which maps each + SATA port to a combophy and a lane within that + combophy +- calxeda,sgpio-gpio: phandle-gpio bank, bit offset, and default on or off, + which indicates that the driver supports SGPIO + indicator lights using the indicated GPIOs +- calxeda,led-order : a u32 array that map port numbers to offsets within the + SGPIO bitstream. +- calxeda,tx-atten : a u32 array that contains TX attenuation override + codes, one per port. The upper 3 bytes are always + 0 and thus ignored. +- calxeda,pre-clocks : a u32 that indicates the number of additional clock + cycles to transmit before sending an SGPIO pattern +- calxeda,post-clocks: a u32 that indicates the number of additional clock + cycles to transmit after sending an SGPIO pattern + +Example: + sata@ffe08000 { + compatible = "calxeda,hb-ahci"; + reg = <0xffe08000 0x1000>; + interrupts = <115>; + dma-coherent; + calxeda,port-phys = <&combophy5 0 &combophy0 0 &combophy0 1 + &combophy0 2 &combophy0 3>; + calxeda,sgpio-gpio =<&gpioh 5 1 &gpioh 6 1 &gpioh 7 1>; + calxeda,led-order = <4 0 1 2 3>; + calxeda,tx-atten = <0xff 22 0xff 0xff 23>; + calxeda,pre-clocks = <10>; + calxeda,post-clocks = <0>; + }; diff --git a/drivers/ata/ahci.c b/drivers/ata/ahci.c index db4380d70031..9d715ae5ff6b 100644 --- a/drivers/ata/ahci.c +++ b/drivers/ata/ahci.c @@ -1295,6 +1295,14 @@ static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) */ if (!(hpriv->flags & AHCI_HFLAG_NO_FPDMA_AA)) pi.flags |= ATA_FLAG_FPDMA_AA; + + /* + * All AHCI controllers should be forward-compatible + * with the new auxiliary field. This code should be + * conditionalized if any buggy AHCI controllers are + * encountered. + */ + pi.flags |= ATA_FLAG_FPDMA_AUX; } if (hpriv->cap & HOST_CAP_PMP) diff --git a/drivers/ata/libata-acpi.c b/drivers/ata/libata-acpi.c index da8170dfc90f..4ba8b0405572 100644 --- a/drivers/ata/libata-acpi.c +++ b/drivers/ata/libata-acpi.c @@ -34,14 +34,6 @@ struct ata_acpi_gtf { u8 tf[REGS_PER_GTF]; /* regs. 0x1f1 - 0x1f7 */ } __packed; -/* - * Helper - belongs in the PCI layer somewhere eventually - */ -static int is_pci_dev(struct device *dev) -{ - return (dev->bus == &pci_bus_type); -} - static void ata_acpi_clear_gtf(struct ata_device *dev) { kfree(dev->gtf_cache); @@ -49,47 +41,18 @@ static void ata_acpi_clear_gtf(struct ata_device *dev) } /** - * ata_ap_acpi_handle - provide the acpi_handle for an ata_port - * @ap: the acpi_handle returned will correspond to this port - * - * Returns the acpi_handle for the ACPI namespace object corresponding to - * the ata_port passed into the function, or NULL if no such object exists - */ -acpi_handle ata_ap_acpi_handle(struct ata_port *ap) -{ - if (ap->flags & ATA_FLAG_ACPI_SATA) - return NULL; - - return ap->scsi_host ? - DEVICE_ACPI_HANDLE(&ap->scsi_host->shost_gendev) : NULL; -} -EXPORT_SYMBOL(ata_ap_acpi_handle); - -/** * ata_dev_acpi_handle - provide the acpi_handle for an ata_device - * @dev: the acpi_device returned will correspond to this port + * @dev: the acpi_handle returned will correspond to this device * * Returns the acpi_handle for the ACPI namespace object corresponding to * the ata_device passed into the function, or NULL if no such object exists + * or ACPI is disabled for this device due to consecutive errors. */ acpi_handle ata_dev_acpi_handle(struct ata_device *dev) { - acpi_integer adr; - struct ata_port *ap = dev->link->ap; - - if (libata_noacpi || dev->flags & ATA_DFLAG_ACPI_DISABLED) - return NULL; - - if (ap->flags & ATA_FLAG_ACPI_SATA) { - if (!sata_pmp_attached(ap)) - adr = SATA_ADR(ap->port_no, NO_PORT_MULT); - else - adr = SATA_ADR(ap->port_no, dev->link->pmp); - return acpi_get_child(DEVICE_ACPI_HANDLE(ap->host->dev), adr); - } else - return acpi_get_child(ata_ap_acpi_handle(ap), dev->devno); + return dev->flags & ATA_DFLAG_ACPI_DISABLED ? + NULL : ACPI_HANDLE(&dev->tdev); } -EXPORT_SYMBOL(ata_dev_acpi_handle); /* @ap and @dev are the same as ata_acpi_handle_hotplug() */ static void ata_acpi_detach_device(struct ata_port *ap, struct ata_device *dev) @@ -156,10 +119,8 @@ static void ata_acpi_handle_hotplug(struct ata_port *ap, struct ata_device *dev, spin_unlock_irqrestore(ap->lock, flags); - if (wait) { + if (wait) ata_port_wait_eh(ap); - flush_work(&ap->hotplug_task.work); - } } static void ata_acpi_dev_notify_dock(acpi_handle handle, u32 event, void *data) @@ -216,37 +177,55 @@ static const struct acpi_dock_ops ata_acpi_ap_dock_ops = { .uevent = ata_acpi_ap_uevent, }; -void ata_acpi_hotplug_init(struct ata_host *host) +/* bind acpi handle to pata port */ +void ata_acpi_bind_port(struct ata_port *ap) { - int i; + acpi_handle host_handle = ACPI_HANDLE(ap->host->dev); - for (i = 0; i < host->n_ports; i++) { - struct ata_port *ap = host->ports[i]; - acpi_handle handle; - struct ata_device *dev; + if (libata_noacpi || ap->flags & ATA_FLAG_ACPI_SATA || !host_handle) + return; - if (!ap) - continue; + ACPI_HANDLE_SET(&ap->tdev, acpi_get_child(host_handle, ap->port_no)); - handle = ata_ap_acpi_handle(ap); - if (handle) { - /* we might be on a docking station */ - register_hotplug_dock_device(handle, - &ata_acpi_ap_dock_ops, ap, - NULL, NULL); - } + if (ata_acpi_gtm(ap, &ap->__acpi_init_gtm) == 0) + ap->pflags |= ATA_PFLAG_INIT_GTM_VALID; - ata_for_each_dev(dev, &ap->link, ALL) { - handle = ata_dev_acpi_handle(dev); - if (!handle) - continue; + /* we might be on a docking station */ + register_hotplug_dock_device(ACPI_HANDLE(&ap->tdev), + &ata_acpi_ap_dock_ops, ap, NULL, NULL); +} - /* we might be on a docking station */ - register_hotplug_dock_device(handle, - &ata_acpi_dev_dock_ops, - dev, NULL, NULL); - } +void ata_acpi_bind_dev(struct ata_device *dev) +{ + struct ata_port *ap = dev->link->ap; + acpi_handle port_handle = ACPI_HANDLE(&ap->tdev); + acpi_handle host_handle = ACPI_HANDLE(ap->host->dev); + acpi_handle parent_handle; + u64 adr; + + /* + * For both sata/pata devices, host handle is required. + * For pata device, port handle is also required. + */ + if (libata_noacpi || !host_handle || + (!(ap->flags & ATA_FLAG_ACPI_SATA) && !port_handle)) + return; + + if (ap->flags & ATA_FLAG_ACPI_SATA) { + if (!sata_pmp_attached(ap)) + adr = SATA_ADR(ap->port_no, NO_PORT_MULT); + else + adr = SATA_ADR(ap->port_no, dev->link->pmp); + parent_handle = host_handle; + } else { + adr = dev->devno; + parent_handle = port_handle; } + + ACPI_HANDLE_SET(&dev->tdev, acpi_get_child(parent_handle, adr)); + + register_hotplug_dock_device(ata_dev_acpi_handle(dev), + &ata_acpi_dev_dock_ops, dev, NULL, NULL); } /** @@ -270,18 +249,34 @@ void ata_acpi_dissociate(struct ata_host *host) struct ata_port *ap = host->ports[i]; const struct ata_acpi_gtm *gtm = ata_acpi_init_gtm(ap); - if (ata_ap_acpi_handle(ap) && gtm) + if (ACPI_HANDLE(&ap->tdev) && gtm) ata_acpi_stm(ap, gtm); } } -static int __ata_acpi_gtm(struct ata_port *ap, acpi_handle handle, - struct ata_acpi_gtm *gtm) +/** + * ata_acpi_gtm - execute _GTM + * @ap: target ATA port + * @gtm: out parameter for _GTM result + * + * Evaluate _GTM and store the result in @gtm. + * + * LOCKING: + * EH context. + * + * RETURNS: + * 0 on success, -ENOENT if _GTM doesn't exist, -errno on failure. + */ +int ata_acpi_gtm(struct ata_port *ap, struct ata_acpi_gtm *gtm) { struct acpi_buffer output = { .length = ACPI_ALLOCATE_BUFFER }; union acpi_object *out_obj; acpi_status status; int rc = 0; + acpi_handle handle = ACPI_HANDLE(&ap->tdev); + + if (!handle) + return -EINVAL; status = acpi_evaluate_object(handle, "_GTM", NULL, &output); @@ -317,27 +312,6 @@ static int __ata_acpi_gtm(struct ata_port *ap, acpi_handle handle, return rc; } -/** - * ata_acpi_gtm - execute _GTM - * @ap: target ATA port - * @gtm: out parameter for _GTM result - * - * Evaluate _GTM and store the result in @gtm. - * - * LOCKING: - * EH context. - * - * RETURNS: - * 0 on success, -ENOENT if _GTM doesn't exist, -errno on failure. - */ -int ata_acpi_gtm(struct ata_port *ap, struct ata_acpi_gtm *gtm) -{ - if (ata_ap_acpi_handle(ap)) - return __ata_acpi_gtm(ap, ata_ap_acpi_handle(ap), gtm); - else - return -EINVAL; -} - EXPORT_SYMBOL_GPL(ata_acpi_gtm); /** @@ -374,8 +348,8 @@ int ata_acpi_stm(struct ata_port *ap, const struct ata_acpi_gtm *stm) input.count = 3; input.pointer = in_params; - status = acpi_evaluate_object(ata_ap_acpi_handle(ap), "_STM", &input, - NULL); + status = acpi_evaluate_object(ACPI_HANDLE(&ap->tdev), "_STM", + &input, NULL); if (status == AE_NOT_FOUND) return -ENOENT; @@ -850,7 +824,7 @@ void ata_acpi_on_resume(struct ata_port *ap) const struct ata_acpi_gtm *gtm = ata_acpi_init_gtm(ap); struct ata_device *dev; - if (ata_ap_acpi_handle(ap) && gtm) { + if (ACPI_HANDLE(&ap->tdev) && gtm) { /* _GTM valid */ /* restore timing parameters */ @@ -894,8 +868,7 @@ static int ata_acpi_choose_suspend_state(struct ata_device *dev, bool runtime) d_max_in = ACPI_STATE_D3_HOT; out: - return acpi_pm_device_sleep_state(&dev->sdev->sdev_gendev, - NULL, d_max_in); + return acpi_pm_device_sleep_state(&dev->tdev, NULL, d_max_in); } static void sata_acpi_set_state(struct ata_port *ap, pm_message_t state) @@ -932,7 +905,7 @@ static void pata_acpi_set_state(struct ata_port *ap, pm_message_t state) struct ata_device *dev; acpi_handle port_handle; - port_handle = ata_ap_acpi_handle(ap); + port_handle = ACPI_HANDLE(&ap->tdev); if (!port_handle) return; @@ -1063,109 +1036,16 @@ void ata_acpi_on_disable(struct ata_device *dev) ata_acpi_clear_gtf(dev); } -static int compat_pci_ata(struct ata_port *ap) -{ - struct device *dev = ap->tdev.parent; - struct pci_dev *pdev; - - if (!is_pci_dev(dev)) - return 0; - - pdev = to_pci_dev(dev); - - if ((pdev->class >> 8) != PCI_CLASS_STORAGE_SATA && - (pdev->class >> 8) != PCI_CLASS_STORAGE_IDE) - return 0; - - return 1; -} - -static int ata_acpi_bind_host(struct ata_port *ap, acpi_handle *handle) -{ - if (libata_noacpi || ap->flags & ATA_FLAG_ACPI_SATA) - return -ENODEV; - - *handle = acpi_get_child(DEVICE_ACPI_HANDLE(ap->tdev.parent), - ap->port_no); - - if (!*handle) - return -ENODEV; - - if (__ata_acpi_gtm(ap, *handle, &ap->__acpi_init_gtm) == 0) - ap->pflags |= ATA_PFLAG_INIT_GTM_VALID; - - return 0; -} - -static int ata_acpi_bind_device(struct ata_port *ap, struct scsi_device *sdev, - acpi_handle *handle) -{ - struct ata_device *ata_dev; - - if (ap->flags & ATA_FLAG_ACPI_SATA) { - if (!sata_pmp_attached(ap)) - ata_dev = &ap->link.device[sdev->id]; - else - ata_dev = &ap->pmp_link[sdev->channel].device[sdev->id]; - } - else { - ata_dev = &ap->link.device[sdev->id]; - } - - *handle = ata_dev_acpi_handle(ata_dev); - - if (!*handle) - return -ENODEV; - - return 0; -} - -static int is_ata_port(const struct device *dev) -{ - return dev->type == &ata_port_type; -} - -static struct ata_port *dev_to_ata_port(struct device *dev) -{ - while (!is_ata_port(dev)) { - if (!dev->parent) - return NULL; - dev = dev->parent; - } - return to_ata_port(dev); -} - -static int ata_acpi_find_device(struct device *dev, acpi_handle *handle) -{ - struct ata_port *ap = dev_to_ata_port(dev); - - if (!ap) - return -ENODEV; - - if (!compat_pci_ata(ap)) - return -ENODEV; - - if (scsi_is_host_device(dev)) - return ata_acpi_bind_host(ap, handle); - else if (scsi_is_sdev_device(dev)) { - struct scsi_device *sdev = to_scsi_device(dev); - - return ata_acpi_bind_device(ap, sdev, handle); - } else - return -ENODEV; -} - -static struct acpi_bus_type ata_acpi_bus = { - .name = "ATA", - .find_device = ata_acpi_find_device, -}; - -int ata_acpi_register(void) +void ata_scsi_acpi_bind(struct ata_device *dev) { - return scsi_register_acpi_bus_type(&ata_acpi_bus); + acpi_handle handle = ata_dev_acpi_handle(dev); + if (handle) + acpi_dev_pm_add_dependent(handle, &dev->sdev->sdev_gendev); } -void ata_acpi_unregister(void) +void ata_scsi_acpi_unbind(struct ata_device *dev) { - scsi_unregister_acpi_bus_type(&ata_acpi_bus); + acpi_handle handle = ata_dev_acpi_handle(dev); + if (handle) + acpi_dev_pm_remove_dependent(handle, &dev->sdev->sdev_gendev); } diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c index c24354d44f3d..83b1a9fb2d44 100644 --- a/drivers/ata/libata-core.c +++ b/drivers/ata/libata-core.c @@ -569,10 +569,10 @@ void ata_tf_to_fis(const struct ata_taskfile *tf, u8 pmp, int is_cmd, u8 *fis) fis[14] = 0; fis[15] = tf->ctl; - fis[16] = 0; - fis[17] = 0; - fis[18] = 0; - fis[19] = 0; + fis[16] = tf->auxiliary & 0xff; + fis[17] = (tf->auxiliary >> 8) & 0xff; + fis[18] = (tf->auxiliary >> 16) & 0xff; + fis[19] = (tf->auxiliary >> 24) & 0xff; } /** @@ -2139,6 +2139,22 @@ static int ata_dev_config_ncq(struct ata_device *dev, else snprintf(desc, desc_sz, "NCQ (depth %d/%d)%s", hdepth, ddepth, aa_desc); + + if ((ap->flags & ATA_FLAG_FPDMA_AUX) && + ata_id_has_ncq_send_and_recv(dev->id)) { + err_mask = ata_read_log_page(dev, ATA_LOG_NCQ_SEND_RECV, + 0, ap->sector_buf, 1); + if (err_mask) { + ata_dev_dbg(dev, + "failed to get NCQ Send/Recv Log Emask 0x%x\n", + err_mask); + } else { + dev->flags |= ATA_DFLAG_NCQ_SEND_RECV; + memcpy(dev->ncq_send_recv_cmds, ap->sector_buf, + ATA_LOG_NCQ_SEND_RECV_SIZE); + } + } + return 0; } @@ -6150,8 +6166,6 @@ int ata_host_register(struct ata_host *host, struct scsi_host_template *sht) if (rc) goto err_tadd; - ata_acpi_hotplug_init(host); - /* set cable, sata_spd_limit and report */ for (i = 0; i < host->n_ports; i++) { struct ata_port *ap = host->ports[i]; @@ -6632,8 +6646,6 @@ static int __init ata_init(void) ata_parse_force_param(); - ata_acpi_register(); - rc = ata_sff_init(); if (rc) { kfree(ata_force_tbl); @@ -6660,7 +6672,6 @@ static void __exit ata_exit(void) ata_release_transport(ata_scsi_transport_template); libata_transport_exit(); ata_sff_exit(); - ata_acpi_unregister(); kfree(ata_force_tbl); } diff --git a/drivers/ata/libata-scsi.c b/drivers/ata/libata-scsi.c index b1e880a3c3da..97a0cef12959 100644 --- a/drivers/ata/libata-scsi.c +++ b/drivers/ata/libata-scsi.c @@ -49,7 +49,6 @@ #include <linux/hdreg.h> #include <linux/uaccess.h> #include <linux/suspend.h> -#include <linux/pm_qos.h> #include <asm/unaligned.h> #include "libata.h" @@ -3100,12 +3099,25 @@ static unsigned int ata_scsi_write_same_xlat(struct ata_queued_cmd *qc) buf = page_address(sg_page(scsi_sglist(scmd))); size = ata_set_lba_range_entries(buf, 512, block, n_block); - tf->protocol = ATA_PROT_DMA; - tf->hob_feature = 0; - tf->feature = ATA_DSM_TRIM; - tf->hob_nsect = (size / 512) >> 8; - tf->nsect = size / 512; - tf->command = ATA_CMD_DSM; + if (ata_ncq_enabled(dev) && ata_fpdma_dsm_supported(dev)) { + /* Newer devices support queued TRIM commands */ + tf->protocol = ATA_PROT_NCQ; + tf->command = ATA_CMD_FPDMA_SEND; + tf->hob_nsect = ATA_SUBCMD_FPDMA_SEND_DSM & 0x1f; + tf->nsect = qc->tag << 3; + tf->hob_feature = (size / 512) >> 8; + tf->feature = size / 512; + + tf->auxiliary = 1; + } else { + tf->protocol = ATA_PROT_DMA; + tf->hob_feature = 0; + tf->feature = ATA_DSM_TRIM; + tf->hob_nsect = (size / 512) >> 8; + tf->nsect = size / 512; + tf->command = ATA_CMD_DSM; + } + tf->flags |= ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE | ATA_TFLAG_LBA48 | ATA_TFLAG_WRITE; @@ -3667,9 +3679,7 @@ void ata_scsi_scan_host(struct ata_port *ap, int sync) if (!IS_ERR(sdev)) { dev->sdev = sdev; scsi_device_put(sdev); - if (zpodd_dev_enabled(dev)) - dev_pm_qos_expose_flags( - &sdev->sdev_gendev, 0); + ata_scsi_acpi_bind(dev); } else { dev->sdev = NULL; } @@ -3757,6 +3767,8 @@ static void ata_scsi_remove_dev(struct ata_device *dev) struct scsi_device *sdev; unsigned long flags; + ata_scsi_acpi_unbind(dev); + /* Alas, we need to grab scan_mutex to ensure SCSI device * state doesn't change underneath us and thus * scsi_device_get() always succeeds. The mutex locking can @@ -3766,9 +3778,6 @@ static void ata_scsi_remove_dev(struct ata_device *dev) mutex_lock(&ap->scsi_host->scan_mutex); spin_lock_irqsave(ap->lock, flags); - if (zpodd_dev_enabled(dev)) - zpodd_exit(dev); - /* clearing dev->sdev is protected by host lock */ sdev = dev->sdev; dev->sdev = NULL; @@ -3818,6 +3827,9 @@ static void ata_scsi_handle_link_detach(struct ata_link *link) dev->flags &= ~ATA_DFLAG_DETACHED; spin_unlock_irqrestore(ap->lock, flags); + if (zpodd_dev_enabled(dev)) + zpodd_exit(dev); + ata_scsi_remove_dev(dev); } } diff --git a/drivers/ata/libata-transport.c b/drivers/ata/libata-transport.c index 077a856f5fd0..150a917f0c3c 100644 --- a/drivers/ata/libata-transport.c +++ b/drivers/ata/libata-transport.c @@ -287,6 +287,7 @@ int ata_tport_add(struct device *parent, dev->release = ata_tport_release; dev_set_name(dev, "ata%d", ap->print_id); transport_setup_device(dev); + ata_acpi_bind_port(ap); error = device_add(dev); if (error) { goto tport_err; @@ -644,6 +645,7 @@ static int ata_tdev_add(struct ata_device *ata_dev) dev_set_name(dev, "dev%d.%d.0", ap->print_id, link->pmp); transport_setup_device(dev); + ata_acpi_bind_dev(ata_dev); error = device_add(dev); if (error) { ata_tdev_free(ata_dev); diff --git a/drivers/ata/libata-zpodd.c b/drivers/ata/libata-zpodd.c index cd8daf47188b..68f9e3293e9c 100644 --- a/drivers/ata/libata-zpodd.c +++ b/drivers/ata/libata-zpodd.c @@ -2,6 +2,7 @@ #include <linux/cdrom.h> #include <linux/pm_runtime.h> #include <linux/module.h> +#include <linux/pm_qos.h> #include <scsi/scsi_device.h> #include "libata.h" @@ -190,8 +191,8 @@ void zpodd_enable_run_wake(struct ata_device *dev) sdev_disable_disk_events(dev->sdev); zpodd->powered_off = true; - device_set_run_wake(&dev->sdev->sdev_gendev, true); - acpi_pm_device_run_wake(&dev->sdev->sdev_gendev, true); + device_set_run_wake(&dev->tdev, true); + acpi_pm_device_run_wake(&dev->tdev, true); } /* Disable runtime wake capability if it is enabled */ @@ -200,8 +201,8 @@ void zpodd_disable_run_wake(struct ata_device *dev) struct zpodd *zpodd = dev->zpodd; if (zpodd->powered_off) { - acpi_pm_device_run_wake(&dev->sdev->sdev_gendev, false); - device_set_run_wake(&dev->sdev->sdev_gendev, false); + acpi_pm_device_run_wake(&dev->tdev, false); + device_set_run_wake(&dev->tdev, false); } } @@ -262,7 +263,7 @@ static void ata_acpi_add_pm_notifier(struct ata_device *dev) static void ata_acpi_remove_pm_notifier(struct ata_device *dev) { - acpi_handle handle = DEVICE_ACPI_HANDLE(&dev->sdev->sdev_gendev); + acpi_handle handle = ata_dev_acpi_handle(dev); acpi_remove_notify_handler(handle, ACPI_SYSTEM_NOTIFY, zpodd_wake_dev); } @@ -290,6 +291,7 @@ void zpodd_init(struct ata_device *dev) ata_acpi_add_pm_notifier(dev); zpodd->dev = dev; dev->zpodd = zpodd; + dev_pm_qos_expose_flags(&dev->tdev, 0); } void zpodd_exit(struct ata_device *dev) diff --git a/drivers/ata/libata.h b/drivers/ata/libata.h index 577d902bc4de..eeeb77845d48 100644 --- a/drivers/ata/libata.h +++ b/drivers/ata/libata.h @@ -118,11 +118,11 @@ extern void ata_acpi_on_resume(struct ata_port *ap); extern int ata_acpi_on_devcfg(struct ata_device *dev); extern void ata_acpi_on_disable(struct ata_device *dev); extern void ata_acpi_set_state(struct ata_port *ap, pm_message_t state); -extern int ata_acpi_register(void); -extern void ata_acpi_unregister(void); -extern void ata_acpi_bind(struct ata_device *dev); -extern void ata_acpi_unbind(struct ata_device *dev); -extern void ata_acpi_hotplug_init(struct ata_host *host); +extern void ata_acpi_bind_port(struct ata_port *ap); +extern void ata_acpi_bind_dev(struct ata_device *dev); +extern acpi_handle ata_dev_acpi_handle(struct ata_device *dev); +extern void ata_scsi_acpi_bind(struct ata_device *dev); +extern void ata_scsi_acpi_unbind(struct ata_device *dev); #else static inline void ata_acpi_dissociate(struct ata_host *host) { } static inline int ata_acpi_on_suspend(struct ata_port *ap) { return 0; } @@ -131,11 +131,10 @@ static inline int ata_acpi_on_devcfg(struct ata_device *dev) { return 0; } static inline void ata_acpi_on_disable(struct ata_device *dev) { } static inline void ata_acpi_set_state(struct ata_port *ap, pm_message_t state) { } -static inline int ata_acpi_register(void) { return 0; } -static inline void ata_acpi_unregister(void) { } -static inline void ata_acpi_bind(struct ata_device *dev) { } -static inline void ata_acpi_unbind(struct ata_device *dev) { } -static inline void ata_acpi_hotplug_init(struct ata_host *host) {} +static inline void ata_acpi_bind_port(struct ata_port *ap) {} +static inline void ata_acpi_bind_dev(struct ata_device *dev) {} +static inline void ata_scsi_acpi_bind(struct ata_device *dev) {} +static inline void ata_scsi_acpi_unbind(struct ata_device *dev) {} #endif /* libata-scsi.c */ diff --git a/drivers/ata/pata_acpi.c b/drivers/ata/pata_acpi.c index 09723b76beac..73212c9c6d5b 100644 --- a/drivers/ata/pata_acpi.c +++ b/drivers/ata/pata_acpi.c @@ -39,7 +39,7 @@ static int pacpi_pre_reset(struct ata_link *link, unsigned long deadline) { struct ata_port *ap = link->ap; struct pata_acpi *acpi = ap->private_data; - if (ata_ap_acpi_handle(ap) == NULL || ata_acpi_gtm(ap, &acpi->gtm) < 0) + if (ACPI_HANDLE(&ap->tdev) == NULL || ata_acpi_gtm(ap, &acpi->gtm) < 0) return -ENODEV; return ata_sff_prereset(link, deadline); @@ -195,7 +195,7 @@ static int pacpi_port_start(struct ata_port *ap) struct pci_dev *pdev = to_pci_dev(ap->host->dev); struct pata_acpi *acpi; - if (ata_ap_acpi_handle(ap) == NULL) + if (ACPI_HANDLE(&ap->tdev) == NULL) return -ENODEV; acpi = ap->private_data = devm_kzalloc(&pdev->dev, sizeof(struct pata_acpi), GFP_KERNEL); diff --git a/drivers/ata/pata_arasan_cf.c b/drivers/ata/pata_arasan_cf.c index 848ed3254ddd..853f610af28f 100644 --- a/drivers/ata/pata_arasan_cf.c +++ b/drivers/ata/pata_arasan_cf.c @@ -654,7 +654,7 @@ static void arasan_cf_freeze(struct ata_port *ap) ata_sff_freeze(ap); } -void arasan_cf_error_handler(struct ata_port *ap) +static void arasan_cf_error_handler(struct ata_port *ap) { struct arasan_cf_dev *acdev = ap->host->private_data; @@ -683,7 +683,7 @@ static void arasan_cf_dma_start(struct arasan_cf_dev *acdev) ata_sff_queue_work(&acdev->work); } -unsigned int arasan_cf_qc_issue(struct ata_queued_cmd *qc) +static unsigned int arasan_cf_qc_issue(struct ata_queued_cmd *qc) { struct ata_port *ap = qc->ap; struct arasan_cf_dev *acdev = ap->host->private_data; diff --git a/drivers/ata/pata_at32.c b/drivers/ata/pata_at32.c index 8d493b4a0961..d59d5239405f 100644 --- a/drivers/ata/pata_at32.c +++ b/drivers/ata/pata_at32.c @@ -271,7 +271,7 @@ static int __init pata_at32_probe(struct platform_device *pdev) struct device *dev = &pdev->dev; struct at32_ide_info *info; - struct ide_platform_data *board = pdev->dev.platform_data; + struct ide_platform_data *board = dev_get_platdata(&pdev->dev); struct resource *res; int irq; diff --git a/drivers/ata/pata_at91.c b/drivers/ata/pata_at91.c index 5364f97b42c6..d63ee8f41a4f 100644 --- a/drivers/ata/pata_at91.c +++ b/drivers/ata/pata_at91.c @@ -315,7 +315,7 @@ static struct ata_port_operations pata_at91_port_ops = { static int pata_at91_probe(struct platform_device *pdev) { - struct at91_cf_data *board = pdev->dev.platform_data; + struct at91_cf_data *board = dev_get_platdata(&pdev->dev); struct device *dev = &pdev->dev; struct at91_ide_info *info; struct resource *mem_res; diff --git a/drivers/ata/pata_ixp4xx_cf.c b/drivers/ata/pata_ixp4xx_cf.c index dcc6b243e525..1ec53f8ca96f 100644 --- a/drivers/ata/pata_ixp4xx_cf.c +++ b/drivers/ata/pata_ixp4xx_cf.c @@ -48,7 +48,7 @@ static unsigned int ixp4xx_mmio_data_xfer(struct ata_device *dev, u16 *buf16 = (u16 *) buf; struct ata_port *ap = dev->link->ap; void __iomem *mmio = ap->ioaddr.data_addr; - struct ixp4xx_pata_data *data = ap->host->dev->platform_data; + struct ixp4xx_pata_data *data = dev_get_platdata(ap->host->dev); /* set the expansion bus in 16bit mode and restore * 8 bit mode after the transaction. @@ -143,7 +143,7 @@ static int ixp4xx_pata_probe(struct platform_device *pdev) struct resource *cs0, *cs1; struct ata_host *host; struct ata_port *ap; - struct ixp4xx_pata_data *data = pdev->dev.platform_data; + struct ixp4xx_pata_data *data = dev_get_platdata(&pdev->dev); cs0 = platform_get_resource(pdev, IORESOURCE_MEM, 0); cs1 = platform_get_resource(pdev, IORESOURCE_MEM, 1); diff --git a/drivers/ata/pata_octeon_cf.c b/drivers/ata/pata_octeon_cf.c index e73bef3093d2..c51bbb9ea8e8 100644 --- a/drivers/ata/pata_octeon_cf.c +++ b/drivers/ata/pata_octeon_cf.c @@ -1037,7 +1037,7 @@ static void octeon_cf_shutdown(struct device *dev) union cvmx_mio_boot_dma_cfgx dma_cfg; union cvmx_mio_boot_dma_intx dma_int; - struct octeon_cf_port *cf_port = dev->platform_data; + struct octeon_cf_port *cf_port = dev_get_platdata(dev); if (cf_port->dma_base) { /* Stop and clear the dma engine. */ diff --git a/drivers/ata/pata_platform.c b/drivers/ata/pata_platform.c index 71e093767f4e..02794885de10 100644 --- a/drivers/ata/pata_platform.c +++ b/drivers/ata/pata_platform.c @@ -180,7 +180,7 @@ static int pata_platform_probe(struct platform_device *pdev) struct resource *io_res; struct resource *ctl_res; struct resource *irq_res; - struct pata_platform_info *pp_info = pdev->dev.platform_data; + struct pata_platform_info *pp_info = dev_get_platdata(&pdev->dev); /* * Simple resource validation .. diff --git a/drivers/ata/pata_pxa.c b/drivers/ata/pata_pxa.c index 942ef94b29e6..a6f05acad61e 100644 --- a/drivers/ata/pata_pxa.c +++ b/drivers/ata/pata_pxa.c @@ -238,7 +238,7 @@ static int pxa_ata_probe(struct platform_device *pdev) struct resource *ctl_res; struct resource *dma_res; struct resource *irq_res; - struct pata_pxa_pdata *pdata = pdev->dev.platform_data; + struct pata_pxa_pdata *pdata = dev_get_platdata(&pdev->dev); int ret = 0; /* diff --git a/drivers/ata/pata_samsung_cf.c b/drivers/ata/pata_samsung_cf.c index 6ef27e98c508..898e544a7ae8 100644 --- a/drivers/ata/pata_samsung_cf.c +++ b/drivers/ata/pata_samsung_cf.c @@ -241,8 +241,8 @@ static u8 pata_s3c_check_altstatus(struct ata_port *ap) /* * pata_s3c_data_xfer - Transfer data by PIO */ -unsigned int pata_s3c_data_xfer(struct ata_device *dev, unsigned char *buf, - unsigned int buflen, int rw) +static unsigned int pata_s3c_data_xfer(struct ata_device *dev, + unsigned char *buf, unsigned int buflen, int rw) { struct ata_port *ap = dev->link->ap; struct s3c_ide_info *info = ap->host->private_data; @@ -418,7 +418,7 @@ static struct ata_port_operations pata_s5p_port_ops = { .set_piomode = pata_s3c_set_piomode, }; -static void pata_s3c_enable(void *s3c_ide_regbase, bool state) +static void pata_s3c_enable(void __iomem *s3c_ide_regbase, bool state) { u32 temp = readl(s3c_ide_regbase + S3C_ATA_CTRL); temp = state ? (temp | 1) : (temp & ~1); @@ -475,7 +475,7 @@ static void pata_s3c_hwinit(struct s3c_ide_info *info, static int __init pata_s3c_probe(struct platform_device *pdev) { - struct s3c_ide_platdata *pdata = pdev->dev.platform_data; + struct s3c_ide_platdata *pdata = dev_get_platdata(&pdev->dev); struct device *dev = &pdev->dev; struct s3c_ide_info *info; struct resource *res; @@ -617,7 +617,7 @@ static int pata_s3c_resume(struct device *dev) { struct platform_device *pdev = to_platform_device(dev); struct ata_host *host = platform_get_drvdata(pdev); - struct s3c_ide_platdata *pdata = pdev->dev.platform_data; + struct s3c_ide_platdata *pdata = dev_get_platdata(&pdev->dev); struct s3c_ide_info *info = host->private_data; pata_s3c_hwinit(info, pdata); diff --git a/drivers/ata/sata_highbank.c b/drivers/ata/sata_highbank.c index e9a4f46d962e..7f5e5d96327f 100644 --- a/drivers/ata/sata_highbank.c +++ b/drivers/ata/sata_highbank.c @@ -46,14 +46,19 @@ #define CR_BUSY 0x0001 #define CR_START 0x0001 #define CR_WR_RDN 0x0002 +#define CPHY_TX_INPUT_STS 0x2001 #define CPHY_RX_INPUT_STS 0x2002 -#define CPHY_SATA_OVERRIDE 0x4000 -#define CPHY_OVERRIDE 0x2005 +#define CPHY_SATA_TX_OVERRIDE 0x8000 +#define CPHY_SATA_RX_OVERRIDE 0x4000 +#define CPHY_TX_OVERRIDE 0x2004 +#define CPHY_RX_OVERRIDE 0x2005 #define SPHY_LANE 0x100 #define SPHY_HALF_RATE 0x0001 #define CPHY_SATA_DPLL_MODE 0x0700 #define CPHY_SATA_DPLL_SHIFT 8 #define CPHY_SATA_DPLL_RESET (1 << 11) +#define CPHY_SATA_TX_ATTEN 0x1c00 +#define CPHY_SATA_TX_ATTEN_SHIFT 10 #define CPHY_PHY_COUNT 6 #define CPHY_LANE_COUNT 4 #define CPHY_PORT_COUNT (CPHY_PHY_COUNT * CPHY_LANE_COUNT) @@ -66,6 +71,7 @@ struct phy_lane_info { void __iomem *phy_base; u8 lane_mapping; u8 phy_devs; + u8 tx_atten; }; static struct phy_lane_info port_data[CPHY_PORT_COUNT]; @@ -76,9 +82,11 @@ static DEFINE_SPINLOCK(sgpio_lock); #define SGPIO_PINS 3 #define SGPIO_PORTS 8 -/* can be cast as an ahci_host_priv for compatibility with most functions */ struct ecx_plat_data { u32 n_ports; + /* number of extra clocks that the SGPIO PIC controller expects */ + u32 pre_clocks; + u32 post_clocks; unsigned sgpio_gpio[SGPIO_PINS]; u32 sgpio_pattern; u32 port_to_sgpio[SGPIO_PORTS]; @@ -155,6 +163,9 @@ static ssize_t ecx_transmit_led_message(struct ata_port *ap, u32 state, spin_lock_irqsave(&sgpio_lock, flags); ecx_parse_sgpio(pdata, ap->port_no, state); sgpio_out = pdata->sgpio_pattern; + for (i = 0; i < pdata->pre_clocks; i++) + ecx_led_cycle_clock(pdata); + gpio_set_value(pdata->sgpio_gpio[SLOAD], 1); ecx_led_cycle_clock(pdata); gpio_set_value(pdata->sgpio_gpio[SLOAD], 0); @@ -167,6 +178,8 @@ static ssize_t ecx_transmit_led_message(struct ata_port *ap, u32 state, sgpio_out >>= 1; ecx_led_cycle_clock(pdata); } + for (i = 0; i < pdata->post_clocks; i++) + ecx_led_cycle_clock(pdata); /* save off new led state for port/slot */ emp->led_state = state; @@ -201,6 +214,11 @@ static void highbank_set_em_messages(struct device *dev, of_property_read_u32_array(np, "calxeda,led-order", pdata->port_to_sgpio, pdata->n_ports); + if (of_property_read_u32(np, "calxeda,pre-clocks", &pdata->pre_clocks)) + pdata->pre_clocks = 0; + if (of_property_read_u32(np, "calxeda,post-clocks", + &pdata->post_clocks)) + pdata->post_clocks = 0; /* store em_loc */ hpriv->em_loc = 0; @@ -259,8 +277,27 @@ static void highbank_cphy_disable_overrides(u8 sata_port) if (unlikely(port_data[sata_port].phy_base == NULL)) return; tmp = combo_phy_read(sata_port, CPHY_RX_INPUT_STS + lane * SPHY_LANE); - tmp &= ~CPHY_SATA_OVERRIDE; - combo_phy_write(sata_port, CPHY_OVERRIDE + lane * SPHY_LANE, tmp); + tmp &= ~CPHY_SATA_RX_OVERRIDE; + combo_phy_write(sata_port, CPHY_RX_OVERRIDE + lane * SPHY_LANE, tmp); +} + +static void cphy_override_tx_attenuation(u8 sata_port, u32 val) +{ + u8 lane = port_data[sata_port].lane_mapping; + u32 tmp; + + if (val & 0x8) + return; + + tmp = combo_phy_read(sata_port, CPHY_TX_INPUT_STS + lane * SPHY_LANE); + tmp &= ~CPHY_SATA_TX_OVERRIDE; + combo_phy_write(sata_port, CPHY_TX_OVERRIDE + lane * SPHY_LANE, tmp); + + tmp |= CPHY_SATA_TX_OVERRIDE; + combo_phy_write(sata_port, CPHY_TX_OVERRIDE + lane * SPHY_LANE, tmp); + + tmp |= (val << CPHY_SATA_TX_ATTEN_SHIFT) & CPHY_SATA_TX_ATTEN; + combo_phy_write(sata_port, CPHY_TX_OVERRIDE + lane * SPHY_LANE, tmp); } static void cphy_override_rx_mode(u8 sata_port, u32 val) @@ -268,21 +305,21 @@ static void cphy_override_rx_mode(u8 sata_port, u32 val) u8 lane = port_data[sata_port].lane_mapping; u32 tmp; tmp = combo_phy_read(sata_port, CPHY_RX_INPUT_STS + lane * SPHY_LANE); - tmp &= ~CPHY_SATA_OVERRIDE; - combo_phy_write(sata_port, CPHY_OVERRIDE + lane * SPHY_LANE, tmp); + tmp &= ~CPHY_SATA_RX_OVERRIDE; + combo_phy_write(sata_port, CPHY_RX_OVERRIDE + lane * SPHY_LANE, tmp); - tmp |= CPHY_SATA_OVERRIDE; - combo_phy_write(sata_port, CPHY_OVERRIDE + lane * SPHY_LANE, tmp); + tmp |= CPHY_SATA_RX_OVERRIDE; + combo_phy_write(sata_port, CPHY_RX_OVERRIDE + lane * SPHY_LANE, tmp); tmp &= ~CPHY_SATA_DPLL_MODE; tmp |= val << CPHY_SATA_DPLL_SHIFT; - combo_phy_write(sata_port, CPHY_OVERRIDE + lane * SPHY_LANE, tmp); + combo_phy_write(sata_port, CPHY_RX_OVERRIDE + lane * SPHY_LANE, tmp); tmp |= CPHY_SATA_DPLL_RESET; - combo_phy_write(sata_port, CPHY_OVERRIDE + lane * SPHY_LANE, tmp); + combo_phy_write(sata_port, CPHY_RX_OVERRIDE + lane * SPHY_LANE, tmp); tmp &= ~CPHY_SATA_DPLL_RESET; - combo_phy_write(sata_port, CPHY_OVERRIDE + lane * SPHY_LANE, tmp); + combo_phy_write(sata_port, CPHY_RX_OVERRIDE + lane * SPHY_LANE, tmp); msleep(15); } @@ -299,16 +336,20 @@ static void highbank_cphy_override_lane(u8 sata_port) lane * SPHY_LANE); } while ((tmp & SPHY_HALF_RATE) && (k++ < 1000)); cphy_override_rx_mode(sata_port, 3); + cphy_override_tx_attenuation(sata_port, port_data[sata_port].tx_atten); } static int highbank_initialize_phys(struct device *dev, void __iomem *addr) { struct device_node *sata_node = dev->of_node; - int phy_count = 0, phy, port = 0; + int phy_count = 0, phy, port = 0, i; void __iomem *cphy_base[CPHY_PHY_COUNT]; struct device_node *phy_nodes[CPHY_PHY_COUNT]; + u32 tx_atten[CPHY_PORT_COUNT]; + memset(port_data, 0, sizeof(struct phy_lane_info) * CPHY_PORT_COUNT); memset(phy_nodes, 0, sizeof(struct device_node*) * CPHY_PHY_COUNT); + memset(tx_atten, 0xff, CPHY_PORT_COUNT); do { u32 tmp; @@ -336,6 +377,10 @@ static int highbank_initialize_phys(struct device *dev, void __iomem *addr) of_node_put(phy_data.np); port += 1; } while (port < CPHY_PORT_COUNT); + of_property_read_u32_array(sata_node, "calxeda,tx-atten", + tx_atten, port); + for (i = 0; i < port; i++) + port_data[i].tx_atten = (u8) tx_atten[i]; return 0; } @@ -479,6 +524,9 @@ static int ahci_highbank_probe(struct platform_device *pdev) if (hpriv->cap & HOST_CAP_PMP) pi.flags |= ATA_FLAG_PMP; + if (hpriv->cap & HOST_CAP_64) + dma_set_coherent_mask(dev, DMA_BIT_MASK(64)); + /* CAP.NP sometimes indicate the index of the last enabled * port, at other times, that of the last possible port, so * determining the maximum port number requires looking at diff --git a/drivers/ata/sata_mv.c b/drivers/ata/sata_mv.c index 35c6b6d09c27..56be31819897 100644 --- a/drivers/ata/sata_mv.c +++ b/drivers/ata/sata_mv.c @@ -553,10 +553,15 @@ struct mv_host_priv { u32 irq_mask_offset; u32 unmask_all_irqs; -#if defined(CONFIG_HAVE_CLK) + /* + * Needed on some devices that require their clocks to be enabled. + * These are optional: if the platform device does not have any + * clocks, they won't be used. Also, if the underlying hardware + * does not support the common clock framework (CONFIG_HAVE_CLK=n), + * all the clock operations become no-ops (see clk.h). + */ struct clk *clk; struct clk **port_clks; -#endif /* * These consistent DMA memory pools give us guaranteed * alignment for hardware-accessed data structures, @@ -4032,9 +4037,7 @@ static int mv_platform_probe(struct platform_device *pdev) struct resource *res; int n_ports = 0, irq = 0; int rc; -#if defined(CONFIG_HAVE_CLK) int port; -#endif ata_print_version_once(&pdev->dev, DRV_VERSION); @@ -4058,7 +4061,7 @@ static int mv_platform_probe(struct platform_device *pdev) of_property_read_u32(pdev->dev.of_node, "nr-ports", &n_ports); irq = irq_of_parse_and_map(pdev->dev.of_node, 0); } else { - mv_platform_data = pdev->dev.platform_data; + mv_platform_data = dev_get_platdata(&pdev->dev); n_ports = mv_platform_data->n_ports; irq = platform_get_irq(pdev, 0); } @@ -4068,13 +4071,11 @@ static int mv_platform_probe(struct platform_device *pdev) if (!host || !hpriv) return -ENOMEM; -#if defined(CONFIG_HAVE_CLK) hpriv->port_clks = devm_kzalloc(&pdev->dev, sizeof(struct clk *) * n_ports, GFP_KERNEL); if (!hpriv->port_clks) return -ENOMEM; -#endif host->private_data = hpriv; hpriv->n_ports = n_ports; hpriv->board_idx = chip_soc; @@ -4084,7 +4085,6 @@ static int mv_platform_probe(struct platform_device *pdev) resource_size(res)); hpriv->base -= SATAHC0_REG_BASE; -#if defined(CONFIG_HAVE_CLK) hpriv->clk = clk_get(&pdev->dev, NULL); if (IS_ERR(hpriv->clk)) dev_notice(&pdev->dev, "cannot get optional clkdev\n"); @@ -4098,7 +4098,6 @@ static int mv_platform_probe(struct platform_device *pdev) if (!IS_ERR(hpriv->port_clks[port])) clk_prepare_enable(hpriv->port_clks[port]); } -#endif /* * (Re-)program MBUS remapping windows if we are asked to. @@ -4124,7 +4123,6 @@ static int mv_platform_probe(struct platform_device *pdev) return 0; err: -#if defined(CONFIG_HAVE_CLK) if (!IS_ERR(hpriv->clk)) { clk_disable_unprepare(hpriv->clk); clk_put(hpriv->clk); @@ -4135,7 +4133,6 @@ err: clk_put(hpriv->port_clks[port]); } } -#endif return rc; } @@ -4151,13 +4148,10 @@ err: static int mv_platform_remove(struct platform_device *pdev) { struct ata_host *host = platform_get_drvdata(pdev); -#if defined(CONFIG_HAVE_CLK) struct mv_host_priv *hpriv = host->private_data; int port; -#endif ata_host_detach(host); -#if defined(CONFIG_HAVE_CLK) if (!IS_ERR(hpriv->clk)) { clk_disable_unprepare(hpriv->clk); clk_put(hpriv->clk); @@ -4168,7 +4162,6 @@ static int mv_platform_remove(struct platform_device *pdev) clk_put(hpriv->port_clks[port]); } } -#endif return 0; } @@ -4428,9 +4421,6 @@ static int mv_pci_device_resume(struct pci_dev *pdev) #endif #endif -static int mv_platform_probe(struct platform_device *pdev); -static int mv_platform_remove(struct platform_device *pdev); - static int __init mv_init(void) { int rc = -ENODEV; diff --git a/drivers/ata/sata_rcar.c b/drivers/ata/sata_rcar.c index 8108eb065444..c2d95e9fb971 100644 --- a/drivers/ata/sata_rcar.c +++ b/drivers/ata/sata_rcar.c @@ -778,10 +778,6 @@ static int sata_rcar_probe(struct platform_device *pdev) int irq; int ret = 0; - mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (mem == NULL) - return -EINVAL; - irq = platform_get_irq(pdev, 0); if (irq <= 0) return -EINVAL; @@ -807,6 +803,7 @@ static int sata_rcar_probe(struct platform_device *pdev) host->private_data = priv; + mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); priv->base = devm_ioremap_resource(&pdev->dev, mem); if (IS_ERR(priv->base)) { ret = PTR_ERR(priv->base); diff --git a/drivers/scsi/scsi_lib.c b/drivers/scsi/scsi_lib.c index d545931c85eb..d1549b74e2d1 100644 --- a/drivers/scsi/scsi_lib.c +++ b/drivers/scsi/scsi_lib.c @@ -68,28 +68,6 @@ static struct scsi_host_sg_pool scsi_sg_pools[] = { struct kmem_cache *scsi_sdb_cache; -#ifdef CONFIG_ACPI -#include <acpi/acpi_bus.h> - -static bool acpi_scsi_bus_match(struct device *dev) -{ - return dev->bus == &scsi_bus_type; -} - -int scsi_register_acpi_bus_type(struct acpi_bus_type *bus) -{ - bus->match = acpi_scsi_bus_match; - return register_acpi_bus_type(bus); -} -EXPORT_SYMBOL_GPL(scsi_register_acpi_bus_type); - -void scsi_unregister_acpi_bus_type(struct acpi_bus_type *bus) -{ - unregister_acpi_bus_type(bus); -} -EXPORT_SYMBOL_GPL(scsi_unregister_acpi_bus_type); -#endif - /* * When to reinvoke queueing after a resource shortage. It's 3 msecs to * not change behaviour from the previous unplug mechanism, experimentation diff --git a/include/linux/ata.h b/include/linux/ata.h index ee0bd9524055..bf4c69ca76df 100644 --- a/include/linux/ata.h +++ b/include/linux/ata.h @@ -239,6 +239,8 @@ enum { ATA_CMD_WRITE_QUEUED_FUA_EXT = 0x3E, ATA_CMD_FPDMA_READ = 0x60, ATA_CMD_FPDMA_WRITE = 0x61, + ATA_CMD_FPDMA_SEND = 0x64, + ATA_CMD_FPDMA_RECV = 0x65, ATA_CMD_PIO_READ = 0x20, ATA_CMD_PIO_READ_EXT = 0x24, ATA_CMD_PIO_WRITE = 0x30, @@ -293,8 +295,13 @@ enum { /* marked obsolete in the ATA/ATAPI-7 spec */ ATA_CMD_RESTORE = 0x10, + /* Subcmds for ATA_CMD_FPDMA_SEND */ + ATA_SUBCMD_FPDMA_SEND_DSM = 0x00, + ATA_SUBCMD_FPDMA_SEND_WR_LOG_DMA_EXT = 0x02, + /* READ_LOG_EXT pages */ ATA_LOG_SATA_NCQ = 0x10, + ATA_LOG_NCQ_SEND_RECV = 0x13, ATA_LOG_SATA_ID_DEV_DATA = 0x30, ATA_LOG_SATA_SETTINGS = 0x08, ATA_LOG_DEVSLP_OFFSET = 0x30, @@ -305,6 +312,15 @@ enum { ATA_LOG_DEVSLP_VALID = 0x07, ATA_LOG_DEVSLP_VALID_MASK = 0x80, + /* NCQ send and receive log */ + ATA_LOG_NCQ_SEND_RECV_SUBCMDS_OFFSET = 0x00, + ATA_LOG_NCQ_SEND_RECV_SUBCMDS_DSM = (1 << 0), + ATA_LOG_NCQ_SEND_RECV_DSM_OFFSET = 0x04, + ATA_LOG_NCQ_SEND_RECV_DSM_TRIM = (1 << 0), + ATA_LOG_NCQ_SEND_RECV_RD_LOG_OFFSET = 0x08, + ATA_LOG_NCQ_SEND_RECV_WR_LOG_OFFSET = 0x0C, + ATA_LOG_NCQ_SEND_RECV_SIZE = 0x10, + /* READ/WRITE LONG (obsolete) */ ATA_CMD_READ_LONG = 0x22, ATA_CMD_READ_LONG_ONCE = 0x23, @@ -446,22 +462,6 @@ enum { SERR_TRANS_ST_ERROR = (1 << 24), /* Transport state trans. error */ SERR_UNRECOG_FIS = (1 << 25), /* Unrecognized FIS */ SERR_DEV_XCHG = (1 << 26), /* device exchanged */ - - /* struct ata_taskfile flags */ - ATA_TFLAG_LBA48 = (1 << 0), /* enable 48-bit LBA and "HOB" */ - ATA_TFLAG_ISADDR = (1 << 1), /* enable r/w to nsect/lba regs */ - ATA_TFLAG_DEVICE = (1 << 2), /* enable r/w to device reg */ - ATA_TFLAG_WRITE = (1 << 3), /* data dir: host->dev==1 (write) */ - ATA_TFLAG_LBA = (1 << 4), /* enable LBA */ - ATA_TFLAG_FUA = (1 << 5), /* enable FUA */ - ATA_TFLAG_POLLING = (1 << 6), /* set nIEN to 1 and use polling */ - - /* protocol flags */ - ATA_PROT_FLAG_PIO = (1 << 0), /* is PIO */ - ATA_PROT_FLAG_DMA = (1 << 1), /* is DMA */ - ATA_PROT_FLAG_DATA = ATA_PROT_FLAG_PIO | ATA_PROT_FLAG_DMA, - ATA_PROT_FLAG_NCQ = (1 << 2), /* is NCQ */ - ATA_PROT_FLAG_ATAPI = (1 << 3), /* is ATAPI */ }; enum ata_tf_protocols { @@ -488,83 +488,6 @@ struct ata_bmdma_prd { __le32 flags_len; }; -struct ata_taskfile { - unsigned long flags; /* ATA_TFLAG_xxx */ - u8 protocol; /* ATA_PROT_xxx */ - - u8 ctl; /* control reg */ - - u8 hob_feature; /* additional data */ - u8 hob_nsect; /* to support LBA48 */ - u8 hob_lbal; - u8 hob_lbam; - u8 hob_lbah; - - u8 feature; - u8 nsect; - u8 lbal; - u8 lbam; - u8 lbah; - - u8 device; - - u8 command; /* IO operation */ -}; - -/* - * protocol tests - */ -static inline unsigned int ata_prot_flags(u8 prot) -{ - switch (prot) { - case ATA_PROT_NODATA: - return 0; - case ATA_PROT_PIO: - return ATA_PROT_FLAG_PIO; - case ATA_PROT_DMA: - return ATA_PROT_FLAG_DMA; - case ATA_PROT_NCQ: - return ATA_PROT_FLAG_DMA | ATA_PROT_FLAG_NCQ; - case ATAPI_PROT_NODATA: - return ATA_PROT_FLAG_ATAPI; - case ATAPI_PROT_PIO: - return ATA_PROT_FLAG_ATAPI | ATA_PROT_FLAG_PIO; - case ATAPI_PROT_DMA: - return ATA_PROT_FLAG_ATAPI | ATA_PROT_FLAG_DMA; - } - return 0; -} - -static inline int ata_is_atapi(u8 prot) -{ - return ata_prot_flags(prot) & ATA_PROT_FLAG_ATAPI; -} - -static inline int ata_is_nodata(u8 prot) -{ - return !(ata_prot_flags(prot) & ATA_PROT_FLAG_DATA); -} - -static inline int ata_is_pio(u8 prot) -{ - return ata_prot_flags(prot) & ATA_PROT_FLAG_PIO; -} - -static inline int ata_is_dma(u8 prot) -{ - return ata_prot_flags(prot) & ATA_PROT_FLAG_DMA; -} - -static inline int ata_is_ncq(u8 prot) -{ - return ata_prot_flags(prot) & ATA_PROT_FLAG_NCQ; -} - -static inline int ata_is_data(u8 prot) -{ - return ata_prot_flags(prot) & ATA_PROT_FLAG_DATA; -} - /* * id tests */ @@ -865,6 +788,11 @@ static inline int ata_id_rotation_rate(const u16 *id) return val; } +static inline bool ata_id_has_ncq_send_and_recv(const u16 *id) +{ + return id[ATA_ID_SATA_CAPABILITY_2] & BIT(6); +} + static inline bool ata_id_has_trim(const u16 *id) { if (ata_id_major_version(id) >= 7 && @@ -1060,15 +988,6 @@ static inline unsigned ata_set_lba_range_entries(void *_buffer, return used_bytes; } -static inline int is_multi_taskfile(struct ata_taskfile *tf) -{ - return (tf->command == ATA_CMD_READ_MULTI) || - (tf->command == ATA_CMD_WRITE_MULTI) || - (tf->command == ATA_CMD_READ_MULTI_EXT) || - (tf->command == ATA_CMD_WRITE_MULTI_EXT) || - (tf->command == ATA_CMD_WRITE_MULTI_FUA_EXT); -} - static inline bool ata_ok(u8 status) { return ((status & (ATA_BUSY | ATA_DRDY | ATA_DF | ATA_DRQ | ATA_ERR)) diff --git a/include/linux/libata.h b/include/linux/libata.h index 4ea55bb45deb..0e23c26485f4 100644 --- a/include/linux/libata.h +++ b/include/linux/libata.h @@ -138,6 +138,22 @@ enum { ATA_SHT_THIS_ID = -1, ATA_SHT_USE_CLUSTERING = 1, + /* struct ata_taskfile flags */ + ATA_TFLAG_LBA48 = (1 << 0), /* enable 48-bit LBA and "HOB" */ + ATA_TFLAG_ISADDR = (1 << 1), /* enable r/w to nsect/lba regs */ + ATA_TFLAG_DEVICE = (1 << 2), /* enable r/w to device reg */ + ATA_TFLAG_WRITE = (1 << 3), /* data dir: host->dev==1 (write) */ + ATA_TFLAG_LBA = (1 << 4), /* enable LBA */ + ATA_TFLAG_FUA = (1 << 5), /* enable FUA */ + ATA_TFLAG_POLLING = (1 << 6), /* set nIEN to 1 and use polling */ + + /* protocol flags */ + ATA_PROT_FLAG_PIO = (1 << 0), /* is PIO */ + ATA_PROT_FLAG_DMA = (1 << 1), /* is DMA */ + ATA_PROT_FLAG_DATA = ATA_PROT_FLAG_PIO | ATA_PROT_FLAG_DMA, + ATA_PROT_FLAG_NCQ = (1 << 2), /* is NCQ */ + ATA_PROT_FLAG_ATAPI = (1 << 3), /* is ATAPI */ + /* struct ata_device stuff */ ATA_DFLAG_LBA = (1 << 0), /* device supports LBA */ ATA_DFLAG_LBA48 = (1 << 1), /* device supports LBA48 */ @@ -156,6 +172,7 @@ enum { ATA_DFLAG_DUBIOUS_XFER = (1 << 16), /* data transfer not verified */ ATA_DFLAG_NO_UNLOAD = (1 << 17), /* device doesn't support unload */ ATA_DFLAG_UNLOCK_HPA = (1 << 18), /* unlock HPA */ + ATA_DFLAG_NCQ_SEND_RECV = (1 << 19), /* device supports NCQ SEND and RECV */ ATA_DFLAG_INIT_MASK = (1 << 24) - 1, ATA_DFLAG_DETACH = (1 << 24), @@ -207,6 +224,7 @@ enum { ATA_FLAG_ACPI_SATA = (1 << 17), /* need native SATA ACPI layout */ ATA_FLAG_AN = (1 << 18), /* controller supports AN */ ATA_FLAG_PMP = (1 << 19), /* controller supports PMP */ + ATA_FLAG_FPDMA_AUX = (1 << 20), /* controller supports H2DFIS aux field */ ATA_FLAG_EM = (1 << 21), /* driver supports enclosure * management */ ATA_FLAG_SW_ACTIVITY = (1 << 22), /* driver supports sw activity @@ -518,6 +536,33 @@ enum sw_activity { BLINK_OFF, }; +struct ata_taskfile { + unsigned long flags; /* ATA_TFLAG_xxx */ + u8 protocol; /* ATA_PROT_xxx */ + + u8 ctl; /* control reg */ + + u8 hob_feature; /* additional data */ + u8 hob_nsect; /* to support LBA48 */ + u8 hob_lbal; + u8 hob_lbam; + u8 hob_lbah; + + u8 feature; + u8 nsect; + u8 lbal; + u8 lbam; + u8 lbah; + + u8 device; + + u8 command; /* IO operation */ + + u32 auxiliary; /* auxiliary field */ + /* from SATA 3.1 and */ + /* ATA-8 ACS-3 */ +}; + #ifdef CONFIG_ATA_SFF struct ata_ioports { void __iomem *cmd_addr; @@ -660,6 +705,9 @@ struct ata_device { /* DEVSLP Timing Variables from Identify Device Data Log */ u8 devslp_timing[ATA_LOG_DEVSLP_SIZE]; + /* NCQ send and receive log subcommand support */ + u8 ncq_send_recv_cmds[ATA_LOG_NCQ_SEND_RECV_SIZE]; + /* error history */ int spdn_cnt; /* ering is CLEAR_END, read comment above CLEAR_END */ @@ -959,6 +1007,69 @@ extern const unsigned long sata_deb_timing_long[]; extern struct ata_port_operations ata_dummy_port_ops; extern const struct ata_port_info ata_dummy_port_info; +/* + * protocol tests + */ +static inline unsigned int ata_prot_flags(u8 prot) +{ + switch (prot) { + case ATA_PROT_NODATA: + return 0; + case ATA_PROT_PIO: + return ATA_PROT_FLAG_PIO; + case ATA_PROT_DMA: + return ATA_PROT_FLAG_DMA; + case ATA_PROT_NCQ: + return ATA_PROT_FLAG_DMA | ATA_PROT_FLAG_NCQ; + case ATAPI_PROT_NODATA: + return ATA_PROT_FLAG_ATAPI; + case ATAPI_PROT_PIO: + return ATA_PROT_FLAG_ATAPI | ATA_PROT_FLAG_PIO; + case ATAPI_PROT_DMA: + return ATA_PROT_FLAG_ATAPI | ATA_PROT_FLAG_DMA; + } + return 0; +} + +static inline int ata_is_atapi(u8 prot) +{ + return ata_prot_flags(prot) & ATA_PROT_FLAG_ATAPI; +} + +static inline int ata_is_nodata(u8 prot) +{ + return !(ata_prot_flags(prot) & ATA_PROT_FLAG_DATA); +} + +static inline int ata_is_pio(u8 prot) +{ + return ata_prot_flags(prot) & ATA_PROT_FLAG_PIO; +} + +static inline int ata_is_dma(u8 prot) +{ + return ata_prot_flags(prot) & ATA_PROT_FLAG_DMA; +} + +static inline int ata_is_ncq(u8 prot) +{ + return ata_prot_flags(prot) & ATA_PROT_FLAG_NCQ; +} + +static inline int ata_is_data(u8 prot) +{ + return ata_prot_flags(prot) & ATA_PROT_FLAG_DATA; +} + +static inline int is_multi_taskfile(struct ata_taskfile *tf) +{ + return (tf->command == ATA_CMD_READ_MULTI) || + (tf->command == ATA_CMD_WRITE_MULTI) || + (tf->command == ATA_CMD_READ_MULTI_EXT) || + (tf->command == ATA_CMD_WRITE_MULTI_EXT) || + (tf->command == ATA_CMD_WRITE_MULTI_FUA_EXT); +} + static inline const unsigned long * sata_ehc_deb_timing(struct ata_eh_context *ehc) { @@ -1142,8 +1253,6 @@ int ata_acpi_stm(struct ata_port *ap, const struct ata_acpi_gtm *stm); int ata_acpi_gtm(struct ata_port *ap, struct ata_acpi_gtm *stm); unsigned long ata_acpi_gtm_xfermask(struct ata_device *dev, const struct ata_acpi_gtm *gtm); -acpi_handle ata_ap_acpi_handle(struct ata_port *ap); -acpi_handle ata_dev_acpi_handle(struct ata_device *dev); int ata_acpi_cbl_80wire(struct ata_port *ap, const struct ata_acpi_gtm *gtm); #else static inline const struct ata_acpi_gtm *ata_acpi_init_gtm(struct ata_port *ap) @@ -1497,6 +1606,13 @@ static inline int ata_ncq_enabled(struct ata_device *dev) ATA_DFLAG_NCQ)) == ATA_DFLAG_NCQ; } +static inline bool ata_fpdma_dsm_supported(struct ata_device *dev) +{ + return (dev->flags & ATA_DFLAG_NCQ_SEND_RECV) && + (dev->ncq_send_recv_cmds[ATA_LOG_NCQ_SEND_RECV_DSM_OFFSET] & + ATA_LOG_NCQ_SEND_RECV_DSM_TRIM); +} + static inline void ata_qc_set_polling(struct ata_queued_cmd *qc) { qc->tf.ctl |= ATA_NIEN; |