diff options
| author | Linus Torvalds <torvalds@linux-foundation.org> | 2008-05-19 19:29:29 -0400 |
|---|---|---|
| committer | Linus Torvalds <torvalds@linux-foundation.org> | 2008-05-19 19:29:29 -0400 |
| commit | 88e6c9499f959cdac9ef120a1a1e857da5944052 (patch) | |
| tree | 282eaabe299f084db582668a16b2f86e0cfbdfec | |
| parent | 8c4bab3a1aadaf4e38b2bfaf557eab74322a9fd4 (diff) | |
| parent | c85665ffa8e351a5b38f8e4ceaec527d8783c970 (diff) | |
Merge branch 'upstream-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jgarzik/libata-dev
* 'upstream-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jgarzik/libata-dev: (28 commits)
drivers/ata: trim trailing whitespace
Fixups to ATA ACPI hotplug
libata: ignore SIMG4726 config pseudo device
sata_sil24: don't use NCQ if marvell 4140 PMP is attached
libata: don't schedule LPM action seperately during probing
libata: make sure PMP notification is turned off during recovery
libata: increase PMP register access timeout to 3s
libata: ignore recovered PHY errors
libata: kill hotplug related race condition
libata: move reset freeze/thaw handling into ata_eh_reset()
libata: reorganize ata_eh_reset() no reset method path
libata: fix sata_link_hardreset() @online out parameter handling
sata_promise: other cleanups
sata_promise: mmio access cleanups
sata_promise: fix irq clearing buglets
ata: remove FIT() macro
sata_mv: ensure empty request queue for FBS-NCQ EH
sata_mv: cache main_irq_mask register in hpriv
sata_mv: disregard masked irqs
sata_mv: fix pmp drives not found
...
| -rw-r--r-- | drivers/ata/libata-acpi.c | 75 | ||||
| -rw-r--r-- | drivers/ata/libata-core.c | 40 | ||||
| -rw-r--r-- | drivers/ata/libata-eh.c | 207 | ||||
| -rw-r--r-- | drivers/ata/libata-pmp.c | 44 | ||||
| -rw-r--r-- | drivers/ata/libata-scsi.c | 6 | ||||
| -rw-r--r-- | drivers/ata/pata_ali.c | 10 | ||||
| -rw-r--r-- | drivers/ata/pata_amd.c | 14 | ||||
| -rw-r--r-- | drivers/ata/pata_at32.c | 2 | ||||
| -rw-r--r-- | drivers/ata/pata_bf54x.c | 5 | ||||
| -rw-r--r-- | drivers/ata/pata_cypress.c | 8 | ||||
| -rw-r--r-- | drivers/ata/pata_legacy.c | 50 | ||||
| -rw-r--r-- | drivers/ata/pata_ns87410.c | 6 | ||||
| -rw-r--r-- | drivers/ata/pata_ns87415.c | 4 | ||||
| -rw-r--r-- | drivers/ata/pata_qdi.c | 16 | ||||
| -rw-r--r-- | drivers/ata/pata_sl82c105.c | 2 | ||||
| -rw-r--r-- | drivers/ata/pata_via.c | 14 | ||||
| -rw-r--r-- | drivers/ata/pata_winbond.c | 6 | ||||
| -rw-r--r-- | drivers/ata/sata_mv.c | 163 | ||||
| -rw-r--r-- | drivers/ata/sata_promise.c | 148 | ||||
| -rw-r--r-- | drivers/ata/sata_sil24.c | 11 | ||||
| -rw-r--r-- | include/linux/libata.h | 6 |
21 files changed, 453 insertions, 384 deletions
diff --git a/drivers/ata/libata-acpi.c b/drivers/ata/libata-acpi.c index 70b77e0899a8..dbf6ca781f66 100644 --- a/drivers/ata/libata-acpi.c +++ b/drivers/ata/libata-acpi.c | |||
| @@ -118,8 +118,8 @@ static void ata_acpi_associate_ide_port(struct ata_port *ap) | |||
| 118 | ap->pflags |= ATA_PFLAG_INIT_GTM_VALID; | 118 | ap->pflags |= ATA_PFLAG_INIT_GTM_VALID; |
| 119 | } | 119 | } |
| 120 | 120 | ||
| 121 | static void ata_acpi_handle_hotplug(struct ata_port *ap, struct ata_device *dev, | 121 | static void ata_acpi_handle_hotplug(struct ata_port *ap, struct ata_device |
| 122 | u32 event) | 122 | *dev, u32 event) |
| 123 | { | 123 | { |
| 124 | char event_string[12]; | 124 | char event_string[12]; |
| 125 | char *envp[] = { event_string, NULL }; | 125 | char *envp[] = { event_string, NULL }; |
| @@ -127,6 +127,9 @@ static void ata_acpi_handle_hotplug(struct ata_port *ap, struct ata_device *dev, | |||
| 127 | struct kobject *kobj = NULL; | 127 | struct kobject *kobj = NULL; |
| 128 | int wait = 0; | 128 | int wait = 0; |
| 129 | unsigned long flags; | 129 | unsigned long flags; |
| 130 | acpi_handle handle, tmphandle; | ||
| 131 | unsigned long sta; | ||
| 132 | acpi_status status; | ||
| 130 | 133 | ||
| 131 | if (!ap) | 134 | if (!ap) |
| 132 | ap = dev->link->ap; | 135 | ap = dev->link->ap; |
| @@ -134,32 +137,57 @@ static void ata_acpi_handle_hotplug(struct ata_port *ap, struct ata_device *dev, | |||
| 134 | 137 | ||
| 135 | spin_lock_irqsave(ap->lock, flags); | 138 | spin_lock_irqsave(ap->lock, flags); |
| 136 | 139 | ||
| 140 | if (dev) | ||
| 141 | handle = dev->acpi_handle; | ||
| 142 | else | ||
| 143 | handle = ap->acpi_handle; | ||
| 144 | |||
| 145 | status = acpi_get_handle(handle, "_EJ0", &tmphandle); | ||
| 146 | if (ACPI_FAILURE(status)) { | ||
| 147 | /* This device is not ejectable */ | ||
| 148 | spin_unlock_irqrestore(ap->lock, flags); | ||
| 149 | return; | ||
| 150 | } | ||
| 151 | |||
| 152 | status = acpi_evaluate_integer(handle, "_STA", NULL, &sta); | ||
| 153 | if (ACPI_FAILURE(status)) { | ||
| 154 | printk ("Unable to determine bay status\n"); | ||
| 155 | spin_unlock_irqrestore(ap->lock, flags); | ||
| 156 | return; | ||
| 157 | } | ||
| 158 | |||
| 137 | switch (event) { | 159 | switch (event) { |
| 138 | case ACPI_NOTIFY_BUS_CHECK: | 160 | case ACPI_NOTIFY_BUS_CHECK: |
| 139 | case ACPI_NOTIFY_DEVICE_CHECK: | 161 | case ACPI_NOTIFY_DEVICE_CHECK: |
| 140 | ata_ehi_push_desc(ehi, "ACPI event"); | 162 | ata_ehi_push_desc(ehi, "ACPI event"); |
| 141 | ata_ehi_hotplugged(ehi); | 163 | if (!sta) { |
| 142 | ata_port_freeze(ap); | 164 | /* Device has been unplugged */ |
| 143 | break; | 165 | if (dev) |
| 144 | 166 | dev->flags |= ATA_DFLAG_DETACH; | |
| 145 | case ACPI_NOTIFY_EJECT_REQUEST: | 167 | else { |
| 146 | ata_ehi_push_desc(ehi, "ACPI event"); | 168 | struct ata_link *tlink; |
| 147 | if (dev) | 169 | struct ata_device *tdev; |
| 148 | dev->flags |= ATA_DFLAG_DETACH; | 170 | |
| 149 | else { | 171 | ata_port_for_each_link(tlink, ap) { |
| 150 | struct ata_link *tlink; | 172 | ata_link_for_each_dev(tdev, tlink) { |
| 151 | struct ata_device *tdev; | 173 | tdev->flags |= |
| 152 | 174 | ATA_DFLAG_DETACH; | |
| 153 | ata_port_for_each_link(tlink, ap) | 175 | } |
| 154 | ata_link_for_each_dev(tdev, tlink) | 176 | } |
| 155 | tdev->flags |= ATA_DFLAG_DETACH; | 177 | } |
| 178 | ata_port_schedule_eh(ap); | ||
| 179 | wait = 1; | ||
| 180 | } else { | ||
| 181 | ata_ehi_hotplugged(ehi); | ||
| 182 | ata_port_freeze(ap); | ||
| 156 | } | 183 | } |
| 157 | |||
| 158 | ata_port_schedule_eh(ap); | ||
| 159 | wait = 1; | ||
| 160 | break; | ||
| 161 | } | 184 | } |
| 162 | 185 | ||
| 186 | spin_unlock_irqrestore(ap->lock, flags); | ||
| 187 | |||
| 188 | if (wait) | ||
| 189 | ata_port_wait_eh(ap); | ||
| 190 | |||
| 163 | if (dev) { | 191 | if (dev) { |
| 164 | if (dev->sdev) | 192 | if (dev->sdev) |
| 165 | kobj = &dev->sdev->sdev_gendev.kobj; | 193 | kobj = &dev->sdev->sdev_gendev.kobj; |
| @@ -170,11 +198,6 @@ static void ata_acpi_handle_hotplug(struct ata_port *ap, struct ata_device *dev, | |||
| 170 | sprintf(event_string, "BAY_EVENT=%d", event); | 198 | sprintf(event_string, "BAY_EVENT=%d", event); |
| 171 | kobject_uevent_env(kobj, KOBJ_CHANGE, envp); | 199 | kobject_uevent_env(kobj, KOBJ_CHANGE, envp); |
| 172 | } | 200 | } |
| 173 | |||
| 174 | spin_unlock_irqrestore(ap->lock, flags); | ||
| 175 | |||
| 176 | if (wait) | ||
| 177 | ata_port_wait_eh(ap); | ||
| 178 | } | 201 | } |
| 179 | 202 | ||
| 180 | static void ata_acpi_dev_notify(acpi_handle handle, u32 event, void *data) | 203 | static void ata_acpi_dev_notify(acpi_handle handle, u32 event, void *data) |
diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c index 927b692d723c..3c89f205c83f 100644 --- a/drivers/ata/libata-core.c +++ b/drivers/ata/libata-core.c | |||
| @@ -2126,6 +2126,13 @@ int ata_dev_configure(struct ata_device *dev) | |||
| 2126 | dev->horkage |= ata_dev_blacklisted(dev); | 2126 | dev->horkage |= ata_dev_blacklisted(dev); |
| 2127 | ata_force_horkage(dev); | 2127 | ata_force_horkage(dev); |
| 2128 | 2128 | ||
| 2129 | if (dev->horkage & ATA_HORKAGE_DISABLE) { | ||
| 2130 | ata_dev_printk(dev, KERN_INFO, | ||
| 2131 | "unsupported device, disabling\n"); | ||
| 2132 | ata_dev_disable(dev); | ||
| 2133 | return 0; | ||
| 2134 | } | ||
| 2135 | |||
| 2129 | /* let ACPI work its magic */ | 2136 | /* let ACPI work its magic */ |
| 2130 | rc = ata_acpi_on_devcfg(dev); | 2137 | rc = ata_acpi_on_devcfg(dev); |
| 2131 | if (rc) | 2138 | if (rc) |
| @@ -3490,22 +3497,11 @@ int sata_link_resume(struct ata_link *link, const unsigned long *params, | |||
| 3490 | if ((rc = sata_link_debounce(link, params, deadline))) | 3497 | if ((rc = sata_link_debounce(link, params, deadline))) |
| 3491 | return rc; | 3498 | return rc; |
| 3492 | 3499 | ||
| 3493 | /* Clear SError. PMP and some host PHYs require this to | 3500 | /* clear SError, some PHYs require this even for SRST to work */ |
| 3494 | * operate and clearing should be done before checking PHY | ||
| 3495 | * online status to avoid race condition (hotplugging between | ||
| 3496 | * link resume and status check). | ||
| 3497 | */ | ||
| 3498 | if (!(rc = sata_scr_read(link, SCR_ERROR, &serror))) | 3501 | if (!(rc = sata_scr_read(link, SCR_ERROR, &serror))) |
| 3499 | rc = sata_scr_write(link, SCR_ERROR, serror); | 3502 | rc = sata_scr_write(link, SCR_ERROR, serror); |
| 3500 | if (rc == 0 || rc == -EINVAL) { | ||
| 3501 | unsigned long flags; | ||
| 3502 | 3503 | ||
| 3503 | spin_lock_irqsave(link->ap->lock, flags); | 3504 | return rc != -EINVAL ? rc : 0; |
| 3504 | link->eh_info.serror = 0; | ||
| 3505 | spin_unlock_irqrestore(link->ap->lock, flags); | ||
