GIT bf00b1fefaace731e28204ea92ceb0102f5fe41b git+ssh://master.kernel.org/pub/scm/linux/kernel/git/jgarzik/libata-dev.git#ALL commit f5d109487004c36fdd92970141e0c2a278a65389 Author: Tejun Heo Date: Sat Nov 24 21:16:07 2007 +0900 ata_piix: separate controller IDs into separate enum Separate controller IDs into a separate enum as Jeff requested. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 3407922a89c56e86ba4ea8c1ad40817826c41c62 Author: Tejun Heo Date: Tue Dec 4 13:33:30 2007 +0900 sata_promise: make pdc_atapi_pkt() use values from qc->tf Make pdc_atapi_pkt() use values from qc->tf instead of creating its own. This is to ease future ATAPI handling changes. Signed-off-by: Tejun Heo Cc: Mikael Pettersson Signed-off-by: Jeff Garzik commit ba515742095612a9835fb939565a3803648f2fe6 Author: Tejun Heo Date: Tue Nov 27 19:43:49 2007 +0900 pata_amd: update mode selection for NV PATAs Cable detection on NV PATA hosts isn't implemented and the CBLID- cable isn't wired according to the sepc either, so both host-side and generic drive-side cable detections are broken. Till now, nv_cable_detect() relied on peeking BIOS and ACPI configurations to upgrade to 80C but this often results in misdetection of 40C cable as 80C. Also, the original implementation was broken in that by the time BIOS configuration is read it has already been cleared by programming PIO0 during reset. This patch reimplements NV mode selection such that... * BIOS configuration value is stored during driver attach and restored on detach. * Cable type is fixed to ATA_CBL_PATA_IGN and mode selection is soley done by nv_mode_filter() which peeks both BIOS and ACPI configurations and filter accordingly. Signed-off-by: Tejun Heo Cc: Alan Cox Signed-off-by: Jeff Garzik commit 8792f7434f36d0bdbb419bcef8ef1d32e6e59321 Author: Tejun Heo Date: Tue Nov 27 19:43:48 2007 +0900 libata: add ATA_CBL_PATA_IGN ATA_CBL_PATA_UNK indicates that the cable type can't be determined from the host side and might be either 80c or 40c. libata applies drive or other generic limit in this case. However, there are controllers where both host and drive side detections are misimplemented and the driver has to rely solely on private method - peeking BIOS or ACPI configuration or using some other private mechanism. This patch adds ATA_CBL_PATA_IGN which tells libata to ignore the cable type completely and just let the LLD determine the transfer mode via host transfer mode masks and ->mode_filter(). Signed-off-by: Tejun Heo Cc: Alan Cox Signed-off-by: Jeff Garzik commit 91d596cfb64190af76c575884c81a7f2a55616f1 Author: Tejun Heo Date: Tue Nov 27 19:43:47 2007 +0900 libata: reimplement ata_acpi_cbl_80wire() using ata_acpi_gtm_xfermask() Reimplement ata_acpi_cbl_80wire() using ata_acpi_gtm_xfermask() and while at it relocate the function below ata_acpi_gtm_xfermask(). New ata_acpi_cbl_80wire() implementation takes @gtm, in both pata_via and pata_amd, use the initial GTM value. Both are trying to peek initial BIOS configuration, so using initial caching value makes sense. This fixes ACPI part of cable detection in pata_amd which previously always returned 0 because configuring PIO0 during reset clears DMA configuration. Signed-off-by: Tejun Heo Cc: Alan Cox Signed-off-by: Jeff Garzik commit 3d688079d91768475c559d058f53f47d59a8e717 Author: Tejun Heo Date: Tue Nov 27 19:43:46 2007 +0900 libata: implement ata_acpi_init_gtm() Add dev->__acpi_init_gtm and store initial GTM values on host initialization. If the field is valid, ata_acpi_init_gtm() returns pointer to the saved GTM structure; otherwise, NULL. This is to remember BIOS/firmware programmed initial timing for later use before reset and mode configuration modify it. The accessor is there to make building w/o ACPI easy dev->__acpi_init doesn't exist if ACPI is not enabled. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit d6896124072e21725500c91bafb8643444cccdc1 Author: Tejun Heo Date: Tue Nov 27 19:43:45 2007 +0900 libata: implement ata_timing_cycle2mode() and use it in libata-acpi and pata_acpi libata-acpi is using separate timing tables for transfer modes although libata-core has the complete ata_timing table. Implement ata_timing_cycle2mode() to look for matching mode given transfer type and cycle duration and use it in libata-acpi and pata_acpi to replace private timing tables. Signed-off-by: Tejun Heo Cc: Alan Cox Signed-off-by: Jeff Garzik commit 9be7fbe2bcf6c1d8388e041e17dae3bcc83ec057 Author: Tejun Heo Date: Tue Nov 27 19:43:44 2007 +0900 libata: fix ata_acpi_gtm_xfermask() ata_acpi_gtm_xfermask() as separated out from pacpi_discover_modes() has various bugs. Fix them. * The wrong comparison operator is used when finding for matching cycle resulting totally bogus result. * With the comparion operator fixed, boundary condtion handling is clumsy. * Setting of any DMA mask bit set all bits in PIO mask. * MWDMA and UDMA blocks are swapped. Signed-off-by: Tejun Heo Cc: Alan Cox Signed-off-by: Jeff Garzik commit 05cf4a6c7e287ed9f6f934139a36293023e18df0 Author: Tejun Heo Date: Tue Nov 27 19:43:43 2007 +0900 libata: separate out ata_acpi_gtm_xfermask() from pacpi_discover_modes() Finding out matching transfer mode from ACPI GTM values is useful for other purposes too. Separate out the function and timing tables from pata_acpi::pacpi_discover_modes(). Other than checking shared-configuration bit after doing ata_acpi_gtm() in pacpi_discover_modes() which should be safe, this patch doesn't introduce any behavior change. Signed-off-by: Tejun Heo Cc: Alan Cox Signed-off-by: Jeff Garzik commit fde75d8d840892f643f5ccde606e05eaf051f211 Author: Tejun Heo Date: Tue Nov 27 19:43:42 2007 +0900 libata: xfer_mask is unsigned long not unsigned int Jeff says xfer_mask is unsigned long not unsigned int. Convert all xfermask fields and handling functions to deal with unsigned longs. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit e84036654384a2b935a9a8217d60fbdc7568afc1 Author: Tejun Heo Date: Tue Nov 27 19:43:41 2007 +0900 libata: kill ata_id_to_dma_mode() ata_id_to_dma_mode() isn't quite generic. The function is basically privately implemented ata_id_xfermask() combined with hardcoded mode printing and configuration which are specific to ata_generic. Kill the function and open code it in generic_set_mode() using generic xfermode handling functions. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 43d5632584a3b2116a08880f156e7a8aab90c46f Author: Tejun Heo Date: Tue Nov 27 19:43:40 2007 +0900 libata: clean up xfermode / PATA timing related stuff * s/ATA_BITS_(PIO|MWDMA|UDMA)/ATA_NR_\1_MODES/g * Consistently use 0xff to indicate invalid transfer mode (0x00 is valid for PIO_SLOW). * Make ata_xfer_mode2mask() return proper mode mask instead of just the highest bit. * Sort ata_timing table in increasing xfermode order and update ata_timing_find_mode() accordingly. This patch doesn't introduce any behavior change. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 638554ec613d4079c146d296790827ecd38fd6de Author: Tejun Heo Date: Tue Nov 27 19:43:39 2007 +0900 libata: export xfermode / PATA timing related functions Export the following xfermode related functions. * ata_pack_xfermask() * ata_unpack_xfermask() * ata_xfer_mask2mode() * ata_xfer_mode2mask() * ata_xfer_mode2shift() * ata_mode_string() * ata_id_xfermask() * ata_timing_find_mode() These functions will be used later by LLD updates. While at it, change unsigned short @speed to u8 @xfer_mode in ata_timing_find_mode() for consistency. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 8f376050be730a704618a70ef1853cb346e64332 Author: Tejun Heo Date: Tue Nov 27 19:43:38 2007 +0900 ata_generic: unindent loop in generic_set_mode() Unindent loop body in generic_set_mode(). This is to ease future change. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 353ceede360cb2d5e61b9f29f08b8362ae8b483c Author: Jeff Garzik Date: Sat Dec 1 18:05:39 2007 -0500 [libata] Build fix WRT ata_is_xxx() new API introduction Signed-off-by: Jeff Garzik commit a72fd05ab7894e1a10b743ccc883d3a44893c63f Author: Tejun Heo Date: Tue Nov 27 19:28:59 2007 +0900 libata: implement fast speed down for unverified data transfer mode It's very likely that the configured data transfer mode is the wrong one if device fails data transfers right after initial data transfer mode configuration (including NCQ on/off and xfermode). libata EH needs to speed down fast before upper layers give up on probing. This patch implement fast speed down rules to handle such cases better. Error occured while data transfer hasn't been verified trigger fast back-to-back speed down actions until data transfer works. This change will make cable mis-detection and other initial configuration problems corrected before partition scanning code gives up. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit bb883607134106770065a766edf770757be82f04 Author: Tejun Heo Date: Tue Nov 27 19:28:58 2007 +0900 libata: implement ATA_DFLAG_DUBIOUS_XFER ATA_DFLAG_DUBIOUS_XFER is set whenever data transfer speed or method changes and gets cleared when data transfer command succeeds in the newly configured transfer mode. This will be used to improve speed down logic. Signed-off-by: Tejun Heo commit c088e0d2c1c0eab7d0d2de62d3ad0cacb1a0a499 Author: Tejun Heo Date: Tue Nov 27 19:28:57 2007 +0900 libata: adjust speed down rules Speed down rules were too conservative. Adjust them a bit. * More than 10 timeouts can't happen in 5 minutes as command timeout is 30secs. Lower the limit for rule #1 to 6. * 10 timeouts is too high for rule #3 too. Lower it to 6. * SATAPI can benefit from falling back to PIO too. Allow SATAPI devices to fall back to PIO. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 2a65191ffb0334ac6f4342559e3bd9a21781c524 Author: Tejun Heo Date: Tue Nov 27 19:28:56 2007 +0900 libata: clean up EH speed down implementation Clean up EH speed down implementation. * is_io boolean variable is replaced eflags. is_io is ATA_EFLAG_IS_IO. * Error categories now have names. * Better comments. * Reorder 5min and 10min rules in ata_eh_speed_down_verdict() * Use local variable @link to cache @dev->link in ata_eh_speed_down() These changes are to improve readability and ease further changes. This patch doesn't introduce any behavior change. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit f2fdc8bed214ca600dba9a61273204e0c2e1652a Author: Tejun Heo Date: Tue Nov 27 19:28:55 2007 +0900 libata: move ata_set_mode() to libata-eh.c Move ata_set_mode() to libata-eh.c. ata_set_mode() is surely an EH action and will be more tightly coupled with the rest of error handling. Move it to libata-eh.c. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 9794bdd7ebf6896dd684110864054802593ce031 Author: Tejun Heo Date: Tue Nov 27 19:28:54 2007 +0900 libata: factor out ata_eh_schedule_probe() Factor out ata_eh_schedule_probe() from ata_eh_handle_dev_fail() and ata_eh_recover(). This is to improve maintainability and make future changes easier. In the previous revision, ata_dev_enabled() test was accidentally dropped while factoring out. This problem was spotted by Bartlomiej. Signed-off-by: Tejun Heo Cc: Bartlomiej Zolnierkiewicz Signed-off-by: Jeff Garzik commit ef14aec8bc358941e47d13db89827a01ac5c4683 Author: Tejun Heo Date: Tue Nov 27 19:28:53 2007 +0900 libata: implement protocol tests Implement protocol tests - ata_is_atapi(), ata_is_nodata(), ata_is_pio(), ata_is_dma(), ata_is_ncq() and ata_is_data() and use them to replace is_atapi_taskfile() and hard coded protocol tests. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 8ca8a084a9ca7b907bce52a9eb12551fca32f838 Author: Tejun Heo Date: Tue Nov 27 19:28:52 2007 +0900 libata: rearrange ATA_DFLAG_* Area for DFLAGs which are cleared on INIT is full. Extend it by 8 bits. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit a44a0af2f01445a7be0fa99655dda8e54256abe2 Author: Jeff Garzik Date: Fri Nov 23 21:12:14 2007 -0500 libata: checkpatch fixes Signed-off-by: Jeff Garzik commit 55119209a5ba0a28d8627ab1bf64edaaf3c6f027 Author: Tejun Heo Date: Mon Nov 19 16:03:44 2007 +0900 ahci: update PCS programming For intel ones, ahci unconditionally OR'd 0xf to PCS. This isn't correct for the following cases. * ich6/7m's which only implement P0 and P2 (0xf works fine tho) * ich8/9's which have six ports and needs 0x3f to enable all ports This patch updates PCS programming such that... * port_map determined by ahci_save_initial_config() is OR'd instead of 0xf * PCS is updated only if necessary (there are turned off enable bits) port_map is determined from PORTS_IMPL PCI register which is implemented as write or write-once register. If the register isn't programmed, ahci automatically generates it from number of ports, which is good enough for PCS programming. ICH6/7M are probably the only ones where non-contiguous enable bits are necessary && PORTS_IMPL isn't programmed properly but they're proven to work reliably with 0xf anyway. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik commit 1faec062c09683ec69faa691462131fd49dc6390 Author: Alan Cox Date: Mon Nov 19 14:45:53 2007 +0000 pata_ninja32: Cardbus ATA initial support Lots of work needed to bring it up to scratch but it does work so you can now use the card. That makes it at least useful, especially as the other cardbus cards are usually INIC162x which aren't yet supported well. Signed-off-by: Alan Cox Signed-off-by: Jeff Garzik commit 7c508b0d3ba19b9b80f65d597bfc78141e4e9cbd Author: Alan Cox Date: Mon Nov 19 14:34:56 2007 +0000 libata-sff: tf_load Jeff said he preferred that the SFF tf_load followed the spec and we documented that anyone who needed different overrode it, rather than it using the ->check_status methods. No driver relies on the current behaviour. Signed-off-by: Alan Cox Signed-off-by: Jeff Garzik commit b198c5f662f3809bad7f0c242984943d58ecb378 Author: Alan Cox Date: Mon Nov 19 14:33:11 2007 +0000 libata: IORDY handling I believe this version meets all Sergei's objections Correct the logic for when we issue a set features for transfer mode - If the device has IORDY and the controller has IORDY - set the mode - If the device has IORDY and the controller does not - turn IORDY off - If neither has IORDY do nothing Signed-off-by: Alan Cox Signed-off-by: Jeff Garzik commit f7c97fdd6de1dde0918dfbcb591d4a668a0ef450 Author: Shaohua Li Date: Fri Nov 2 09:32:38 2007 +0800 libata-acpi: add ACPI _PSx method ACPI spec (ver 3.0a, p289) requires IDE power on/off executes ACPI _PSx methods. As recently most PATA drivers use libata, this patch adds _PSx method support in libata. ACPI spec doesn't mention if SATA requires the same _PSx method. Signed-off-by: Shaohua Li Acked-by: Len Brown Signed-off-by: Jeff Garzik commit 85d4937044be5cf10ef45817c0681376c86b0a16 Author: Alan Cox Date: Sun Nov 4 22:05:49 2007 -0500 libata: Disable ATA8-ACS proposed Trusted Computing features by default Historically word 48 in the identify data was used to mean 32bit I/O was supported for VLB IDE etc. ATA8 reassigns this word to the Trusted Computing Group, where it is used for TCG features. This means that an ATA8 TCG drive is going to trigger 32bit I/O on some systems which will be funny. Anyway we need to sort this out ready for ATA8 so: - Reorder the ata.h header a bit so the ata_version function occurs early in it - Make dword_io check the ATA version - Add an ATA8 version checking TCG presence test While we are at it the current drafts have a flaw where it may not be possible to disable TCG features at boot (and opt out of the trusted model) as TCG intends because it relies on presence of a different optional feature (DCS). Handle this in software by refusing the TCG commands if libata.allow_tpm is not set. (We must make it possible as some environments such as proprietary VDR devices will doubtless want to use it to lock up content) Finally as with CPRM print a warning so that the user knows they may not be able to full access and use the device. Signed-off-by: Alan Cox commit 1bb14e18a6f2db255eeb5ced73f00a19cb07ad6a Author: Alan Cox Date: Thu Oct 25 14:21:16 2007 +0100 libata/pata_it821x: Improve handling of poorly compatible emulations Some it821x RAID firmwares return 0 for the err return off both devices. A similar issue occurs with the slave returning 0 not 1 if you plug a gigabyte sata ramdisk into a controller that fakes two SATA ports as master/slave on an SFF channel. The patch does the following - Allow the 'failed diagnostics' case on both master and slave - Move the HORKAGE_DIAGNOSTIC check after ->dev_config This second change also allows IT821x to fix up a problem where we report drive diagnostic failures when in fact the drive is fine but the microcontroller firmware doesn't appear to get it right. IT821x clears the flag again to avoid giving the user bogus warnings about their disk. The other IT821x change is a bit ugly, we slightly abuse the cable type hook to fiddle with the identify data for the devices. We could add a new hook for this but as we have only one offender and no more seeming likely it seems better to keep libata-core clean. Please let this sit in -mm briefly, just in case the relaxed checking breaks some other emulated interface. Signed-off-by: Alan Cox Signed-off-by: Jeff Garzik commit 400399575978d7deda276bda9df92e35bdf1a94e Author: Alan Cox Date: Mon Oct 15 19:23:13 2007 +0100 libata-core: Don't have screaming fits over DF/ERR combinations Some hardware seems to get this wrong in a non-harmful way, and there are some devices that seem to do it deliberately for various reasons. Just take it as a device error not a catastrophic state machine explosion. Signed-off-by: Alan Cox Signed-off-by: Jeff Garzik commit 5ddcddd4dfeb16a9509dad647f509828d6fee605 Author: Alan Cox Date: Mon Oct 15 20:44:11 2007 +0100 pata_pcmcia: Add support for dumb 8bit IDE emulations Signed-off-by: Alan Cox Signed-off-by: Jeff Garzik commit 589970cd66d50449b3c3807cf0721beb87ca5442 Author: Alan Date: Tue Oct 2 13:53:05 2007 -0700 libata: fix (hopefully) all the remaining problems with devices failing setup/identify Two fixes in this test patch. One of them allows old CF cards to refuse pio mode setting, and one to wait for the drive to settle after a set features changes the speed settings, which is based upon the workarounds used by drivers/ide. Please test and report back if you have an afflicted system. This patch isn't for merging just testing. The CF card fix will still display errors when the card works (got fixes for that once I know the cure works) but should then be found/usable. Not signed off by anyone, not for merging Signed-off-by: Andrew Morton commit d98c11ff26b87a4cf74263c40103230c37d82e32 Author: Jeff Garzik Date: Mon May 28 06:21:45 2007 -0400 [libata] sata_sx4: convert to new EH Signed-off-by: Jeff Garzik drivers/ata/Kconfig | 9 + drivers/ata/Makefile | 1 + drivers/ata/ahci.c | 9 +- drivers/ata/ata_generic.c | 44 +++-- drivers/ata/ata_piix.c | 32 ++-- drivers/ata/libata-acpi.c | 121 ++++++++++--- drivers/ata/libata-core.c | 408 ++++++++++++++++++++++------------------- drivers/ata/libata-eh.c | 289 ++++++++++++++++++++++------- drivers/ata/libata-scsi.c | 18 ++ drivers/ata/libata-sff.c | 6 +- drivers/ata/libata.h | 6 +- drivers/ata/pata_acpi.c | 67 ++------ drivers/ata/pata_ali.c | 2 +- drivers/ata/pata_amd.c | 128 ++++++++++---- drivers/ata/pata_it821x.c | 35 ++++- drivers/ata/pata_ninja32.c | 214 +++++++++++++++++++++ drivers/ata/pata_pcmcia.c | 71 +++++++- drivers/ata/pata_via.c | 3 +- drivers/ata/sata_fsl.c | 2 +- drivers/ata/sata_promise.c | 34 ++-- drivers/ata/sata_sil.c | 10 +- drivers/ata/sata_sil24.c | 26 +--- drivers/ata/sata_sx4.c | 96 ++++++---- drivers/scsi/libsas/sas_ata.c | 2 +- include/linux/ata.h | 100 +++++++++- include/linux/libata.h | 100 ++++++++-- 26 files changed, 1306 insertions(+), 527 deletions(-) diff --git a/drivers/ata/Kconfig b/drivers/ata/Kconfig index ba63619..2478cca 100644 --- a/drivers/ata/Kconfig +++ b/drivers/ata/Kconfig @@ -459,6 +459,15 @@ config PATA_NETCELL If unsure, say N. +config PATA_NINJA32 + tristate "Ninja32/Delkin Cardbus ATA support (Experimental)" + depends on PCI && EXPERIMENTAL + help + This option enables support for the Ninja32, Delkin and + possibly other brands of Cardbus ATA adapter + + If unsure, say N. + config PATA_NS87410 tristate "Nat Semi NS87410 PATA support (Experimental)" depends on PCI && EXPERIMENTAL diff --git a/drivers/ata/Makefile b/drivers/ata/Makefile index b13feb2..82550c1 100644 --- a/drivers/ata/Makefile +++ b/drivers/ata/Makefile @@ -41,6 +41,7 @@ obj-$(CONFIG_PATA_IT821X) += pata_it821x.o obj-$(CONFIG_PATA_IT8213) += pata_it8213.o obj-$(CONFIG_PATA_JMICRON) += pata_jmicron.o obj-$(CONFIG_PATA_NETCELL) += pata_netcell.o +obj-$(CONFIG_PATA_NINJA32) += pata_ninja32.o obj-$(CONFIG_PATA_NS87410) += pata_ns87410.o obj-$(CONFIG_PATA_NS87415) += pata_ns87415.o obj-$(CONFIG_PATA_OPTI) += pata_opti.o diff --git a/drivers/ata/ahci.c b/drivers/ata/ahci.c index 54f38c2..5eee91c 100644 --- a/drivers/ata/ahci.c +++ b/drivers/ata/ahci.c @@ -1036,6 +1036,7 @@ static int ahci_deinit_port(struct ata_port *ap, const char **emsg) static int ahci_reset_controller(struct ata_host *host) { struct pci_dev *pdev = to_pci_dev(host->dev); + struct ahci_host_priv *hpriv = host->private_data; void __iomem *mmio = host->iomap[AHCI_PCI_BAR]; u32 tmp; @@ -1078,8 +1079,10 @@ static int ahci_reset_controller(struct ata_host *host) /* configure PCS */ pci_read_config_word(pdev, 0x92, &tmp16); - tmp16 |= 0xf; - pci_write_config_word(pdev, 0x92, tmp16); + if ((tmp16 & hpriv->port_map) != hpriv->port_map) { + tmp16 |= hpriv->port_map; + pci_write_config_word(pdev, 0x92, tmp16); + } } return 0; @@ -1508,7 +1511,7 @@ static void ahci_qc_prep(struct ata_queued_cmd *qc) { struct ata_port *ap = qc->ap; struct ahci_port_priv *pp = ap->private_data; - int is_atapi = is_atapi_taskfile(&qc->tf); + int is_atapi = ata_is_atapi(qc->tf.protocol); void *cmd_tbl; u32 opts; const u32 cmd_fis_len = 5; /* five dwords */ diff --git a/drivers/ata/ata_generic.c b/drivers/ata/ata_generic.c index 9032998..d11a4f1 100644 --- a/drivers/ata/ata_generic.c +++ b/drivers/ata/ata_generic.c @@ -54,21 +54,37 @@ static int generic_set_mode(struct ata_link *link, struct ata_device **unused) dma_enabled = ioread8(ap->ioaddr.bmdma_addr + ATA_DMA_STATUS); ata_link_for_each_dev(dev, link) { - if (ata_dev_enabled(dev)) { - /* We don't really care */ - dev->pio_mode = XFER_PIO_0; - dev->dma_mode = XFER_MW_DMA_0; - /* We do need the right mode information for DMA or PIO - and this comes from the current configuration flags */ - if (dma_enabled & (1 << (5 + dev->devno))) { - ata_id_to_dma_mode(dev, XFER_MW_DMA_0); - dev->flags &= ~ATA_DFLAG_PIO; - } else { - ata_dev_printk(dev, KERN_INFO, "configured for PIO\n"); - dev->xfer_mode = XFER_PIO_0; - dev->xfer_shift = ATA_SHIFT_PIO; - dev->flags |= ATA_DFLAG_PIO; + if (!ata_dev_enabled(dev)) + continue; + + /* We don't really care */ + dev->pio_mode = XFER_PIO_0; + dev->dma_mode = XFER_MW_DMA_0; + /* We do need the right mode information for DMA or PIO + and this comes from the current configuration flags */ + if (dma_enabled & (1 << (5 + dev->devno))) { + unsigned int xfer_mask = ata_id_xfermask(dev->id); + const char *name; + + if (xfer_mask & (ATA_MASK_MWDMA | ATA_MASK_UDMA)) + name = ata_mode_string(xfer_mask); + else { + /* SWDMA perhaps? */ + name = "DMA"; + xfer_mask |= ata_xfer_mode2mask(XFER_MW_DMA_0); } + + ata_dev_printk(dev, KERN_INFO, "configured for %s\n", + name); + + dev->xfer_mode = ata_xfer_mask2mode(xfer_mask); + dev->xfer_shift = ata_xfer_mode2shift(dev->xfer_mode); + dev->flags &= ~ATA_DFLAG_PIO; + } else { + ata_dev_printk(dev, KERN_INFO, "configured for PIO\n"); + dev->xfer_mode = XFER_PIO_0; + dev->xfer_shift = ATA_SHIFT_PIO; + dev->flags |= ATA_DFLAG_PIO; } } return 0; diff --git a/drivers/ata/ata_piix.c b/drivers/ata/ata_piix.c index bb62a58..3ddbf8b 100644 --- a/drivers/ata/ata_piix.c +++ b/drivers/ata/ata_piix.c @@ -118,21 +118,6 @@ enum { PIIX_80C_PRI = (1 << 5) | (1 << 4), PIIX_80C_SEC = (1 << 7) | (1 << 6), - /* controller IDs */ - piix_pata_mwdma = 0, /* PIIX3 MWDMA only */ - piix_pata_33, /* PIIX4 at 33Mhz */ - ich_pata_33, /* ICH up to UDMA 33 only */ - ich_pata_66, /* ICH up to 66 Mhz */ - ich_pata_100, /* ICH up to UDMA 100 */ - ich5_sata, - ich6_sata, - ich6_sata_ahci, - ich6m_sata_ahci, - ich8_sata_ahci, - ich8_2port_sata, - ich8m_apple_sata_ahci, /* locks up on second port enable */ - tolapai_sata_ahci, - /* constants for mapping table */ P0 = 0, /* port 0 */ P1 = 1, /* port 1 */ @@ -148,6 +133,23 @@ enum { PIIX_HOST_BROKEN_SUSPEND = (1 << 24), }; +enum piix_controller_ids { + /* controller IDs */ + piix_pata_mwdma, /* PIIX3 MWDMA only */ + piix_pata_33, /* PIIX4 at 33Mhz */ + ich_pata_33, /* ICH up to UDMA 33 only */ + ich_pata_66, /* ICH up to 66 Mhz */ + ich_pata_100, /* ICH up to UDMA 100 */ + ich5_sata, + ich6_sata, + ich6_sata_ahci, + ich6m_sata_ahci, + ich8_sata_ahci, + ich8_2port_sata, + ich8m_apple_sata_ahci, /* locks up on second port enable */ + tolapai_sata_ahci, +}; + struct piix_map_db { const u32 mask; const u16 port_enable; diff --git a/drivers/ata/libata-acpi.c b/drivers/ata/libata-acpi.c index 545ea86..5ef2841 100644 --- a/drivers/ata/libata-acpi.c +++ b/drivers/ata/libata-acpi.c @@ -94,6 +94,9 @@ static void ata_acpi_associate_ide_port(struct ata_port *ap) dev->acpi_handle = acpi_get_child(ap->acpi_handle, i); } + + if (ata_acpi_gtm(ap, &ap->__acpi_init_gtm) == 0) + ap->pflags |= ATA_PFLAG_INIT_GTM_VALID; } static void ata_acpi_handle_hotplug(struct ata_port *ap, struct kobject *kobj, @@ -384,41 +387,77 @@ static int ata_dev_get_GTF(struct ata_device *dev, struct ata_acpi_gtf **gtf, } /** + * ata_acpi_gtm_xfermode - determine xfermode from GTM parameter + * @dev: target device + * @gtm: GTM parameter to use + * + * Determine xfermask for @dev from @gtm. + * + * LOCKING: + * None. + * + * RETURNS: + * Determined xfermask. + */ +unsigned long ata_acpi_gtm_xfermask(struct ata_device *dev, + const struct ata_acpi_gtm *gtm) +{ + unsigned long xfer_mask = 0; + unsigned int type; + int unit; + u8 mode; + + /* we always use the 0 slot for crap hardware */ + unit = dev->devno; + if (!(gtm->flags & 0x10)) + unit = 0; + + /* PIO */ + mode = ata_timing_cycle2mode(ATA_SHIFT_PIO, gtm->drive[unit].pio); + xfer_mask |= ata_xfer_mode2mask(mode); + + /* See if we have MWDMA or UDMA data. We don't bother with + * MWDMA if UDMA is available as this means the BIOS set UDMA + * and our error changedown if it works is UDMA to PIO anyway. + */ + if (!(gtm->flags & (1 << (2 * unit)))) + type = ATA_SHIFT_MWDMA; + else + type = ATA_SHIFT_UDMA; + + mode = ata_timing_cycle2mode(type, gtm->drive[unit].dma); + xfer_mask |= ata_xfer_mode2mask(mode); + + return xfer_mask; +} +EXPORT_SYMBOL_GPL(ata_acpi_gtm_xfermask); + +/** * ata_acpi_cbl_80wire - Check for 80 wire cable * @ap: Port to check + * @gtm: GTM data to use * - * Return 1 if the ACPI mode data for this port indicates the BIOS selected - * an 80wire mode. + * Return 1 if the @gtm indicates the BIOS selected an 80wire mode. */ - -int ata_acpi_cbl_80wire(struct ata_port *ap) +int ata_acpi_cbl_80wire(struct ata_port *ap, const struct ata_acpi_gtm *gtm) { - struct ata_acpi_gtm gtm; - int valid = 0; + struct ata_device *dev; - /* No _GTM data, no information */ - if (ata_acpi_gtm(ap, >m) < 0) - return 0; + ata_link_for_each_dev(dev, &ap->link) { + unsigned long xfer_mask, udma_mask; + + if (!ata_dev_enabled(dev)) + continue; + + xfer_mask = ata_acpi_gtm_xfermask(dev, gtm); + ata_unpack_xfermask(xfer_mask, NULL, NULL, &udma_mask); + + if (udma_mask & ~ATA_UDMA_MASK_40C) + return 1; + } - /* Split timing, DMA enabled */ - if ((gtm.flags & 0x11) == 0x11 && gtm.drive[0].dma < 55) - valid |= 1; - if ((gtm.flags & 0x14) == 0x14 && gtm.drive[1].dma < 55) - valid |= 2; - /* Shared timing, DMA enabled */ - if ((gtm.flags & 0x11) == 0x01 && gtm.drive[0].dma < 55) - valid |= 1; - if ((gtm.flags & 0x14) == 0x04 && gtm.drive[0].dma < 55) - valid |= 2; - - /* Drive check */ - if ((valid & 1) && ata_dev_enabled(&ap->link.device[0])) - return 1; - if ((valid & 2) && ata_dev_enabled(&ap->link.device[1])) - return 1; return 0; } - EXPORT_SYMBOL_GPL(ata_acpi_cbl_80wire); /** @@ -646,6 +685,36 @@ void ata_acpi_on_resume(struct ata_port *ap) } /** + * ata_acpi_set_state - set the port power state + * @ap: target ATA port + * @state: state, on/off + * + * This function executes the _PS0/_PS3 ACPI method to set the power state. + * ACPI spec requires _PS0 when IDE power on and _PS3 when power off + */ +void ata_acpi_set_state(struct ata_port *ap, pm_message_t state) +{ + struct ata_device *dev; + + if (!ap->acpi_handle || (ap->flags & ATA_FLAG_ACPI_SATA)) + return; + + /* channel first and then drives for power on and vica versa + for power off */ + if (state.event == PM_EVENT_ON) + acpi_bus_set_power(ap->acpi_handle, ACPI_STATE_D0); + + ata_link_for_each_dev(dev, &ap->link) { + if (dev->acpi_handle && ata_dev_enabled(dev)) + acpi_bus_set_power(dev->acpi_handle, + state.event == PM_EVENT_ON ? + ACPI_STATE_D0 : ACPI_STATE_D3); + } + if (state.event != PM_EVENT_ON) + acpi_bus_set_power(ap->acpi_handle, ACPI_STATE_D3); +} + +/** * ata_acpi_on_devcfg - ATA ACPI hook called on device donfiguration * @dev: target ATA device * diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c index e4dea86..2373ab1 100644 --- a/drivers/ata/libata-core.c +++ b/drivers/ata/libata-core.c @@ -118,6 +118,10 @@ int libata_noacpi = 0; module_param_named(noacpi, libata_noacpi, int, 0444); MODULE_PARM_DESC(noacpi, "Disables the use of ACPI in probe/suspend/resume when set"); +int libata_allow_tpm = 0; +module_param_named(allow_tpm, libata_allow_tpm, int, 0444); +MODULE_PARM_DESC(allow_tpm, "Permit the use of TPM commands"); + MODULE_AUTHOR("Jeff Garzik"); MODULE_DESCRIPTION("Library module for ATA devices"); MODULE_LICENSE("GPL"); @@ -449,9 +453,9 @@ int ata_build_rw_tf(struct ata_taskfile *tf, struct ata_device *dev, * RETURNS: * Packed xfer_mask. */ -static unsigned int ata_pack_xfermask(unsigned int pio_mask, - unsigned int mwdma_mask, - unsigned int udma_mask) +unsigned long ata_pack_xfermask(unsigned long pio_mask, + unsigned long mwdma_mask, + unsigned long udma_mask) { return ((pio_mask << ATA_SHIFT_PIO) & ATA_MASK_PIO) | ((mwdma_mask << ATA_SHIFT_MWDMA) & ATA_MASK_MWDMA) | @@ -468,10 +472,8 @@ static unsigned int ata_pack_xfermask(unsigned int pio_mask, * Unpack @xfer_mask into @pio_mask, @mwdma_mask and @udma_mask. * Any NULL distination masks will be ignored. */ -static void ata_unpack_xfermask(unsigned int xfer_mask, - unsigned int *pio_mask, - unsigned int *mwdma_mask, - unsigned int *udma_mask) +void ata_unpack_xfermask(unsigned long xfer_mask, unsigned long *pio_mask, + unsigned long *mwdma_mask, unsigned long *udma_mask) { if (pio_mask) *pio_mask = (xfer_mask & ATA_MASK_PIO) >> ATA_SHIFT_PIO; @@ -485,9 +487,9 @@ static const struct ata_xfer_ent { int shift, bits; u8 base; } ata_xfer_tbl[] = { - { ATA_SHIFT_PIO, ATA_BITS_PIO, XFER_PIO_0 }, - { ATA_SHIFT_MWDMA, ATA_BITS_MWDMA, XFER_MW_DMA_0 }, - { ATA_SHIFT_UDMA, ATA_BITS_UDMA, XFER_UDMA_0 }, + { ATA_SHIFT_PIO, ATA_NR_PIO_MODES, XFER_PIO_0 }, + { ATA_SHIFT_MWDMA, ATA_NR_MWDMA_MODES, XFER_MW_DMA_0 }, + { ATA_SHIFT_UDMA, ATA_NR_UDMA_MODES, XFER_UDMA_0 }, { -1, }, }; @@ -502,9 +504,9 @@ static const struct ata_xfer_ent { * None. * * RETURNS: - * Matching XFER_* value, 0 if no match found. + * Matching XFER_* value, 0xff if no match found. */ -static u8 ata_xfer_mask2mode(unsigned int xfer_mask) +u8 ata_xfer_mask2mode(unsigned long xfer_mask) { int highbit = fls(xfer_mask) - 1; const struct ata_xfer_ent *ent; @@ -512,7 +514,7 @@ static u8 ata_xfer_mask2mode(unsigned int xfer_mask) for (ent = ata_xfer_tbl; ent->shift >= 0; ent++) if (highbit >= ent->shift && highbit < ent->shift + ent->bits) return ent->base + highbit - ent->shift; - return 0; + return 0xff; } /** @@ -527,13 +529,14 @@ static u8 ata_xfer_mask2mode(unsigned int xfer_mask) * RETURNS: * Matching xfer_mask, 0 if no match found. */ -static unsigned int ata_xfer_mode2mask(u8 xfer_mode) +unsigned long ata_xfer_mode2mask(u8 xfer_mode) { const struct ata_xfer_ent *ent; for (ent = ata_xfer_tbl; ent->shift >= 0; ent++) if (xfer_mode >= ent->base && xfer_mode < ent->base + ent->bits) - return 1 << (ent->shift + xfer_mode - ent->base); + return ((2 << (ent->shift + xfer_mode - ent->base)) - 1) + & ~((1 << ent->shift) - 1); return 0; } @@ -549,7 +552,7 @@ static unsigned int ata_xfer_mode2mask(u8 xfer_mode) * RETURNS: * Matching xfer_shift, -1 if no match found. */ -static int ata_xfer_mode2shift(unsigned int xfer_mode) +int ata_xfer_mode2shift(unsigned long xfer_mode) { const struct ata_xfer_ent *ent; @@ -573,7 +576,7 @@ static int ata_xfer_mode2shift(unsigned int xfer_mode) * Constant C string representing highest speed listed in * @mode_mask, or the constant C string "". */ -static const char *ata_mode_string(unsigned int xfer_mask) +const char *ata_mode_string(unsigned long xfer_mask) { static const char * const xfer_mode_str[] = { "PIO0", @@ -945,8 +948,8 @@ unsigned int ata_dev_try_classify(struct ata_device *dev, int present, if (r_err) *r_err = err; - /* see if device passed diags: if master then continue and warn later */ - if (err == 0 && dev->devno == 0) + /* see if device passed diags: continue and warn later */ + if (err == 0) /* diagnostic fail : do nothing _YET_ */ dev->horkage |= ATA_HORKAGE_DIAGNOSTIC; else if (err == 1) @@ -1284,48 +1287,6 @@ static int ata_hpa_resize(struct ata_device *dev) } /** - * ata_id_to_dma_mode - Identify DMA mode from id block - * @dev: device to identify - * @unknown: mode to assume if we cannot tell - * - * Set up the timing values for the device based upon the identify - * reported values for the DMA mode. This function is used by drivers - * which rely upon firmware configured modes, but wish to report the - * mode correctly when possible. - * - * In addition we emit similarly formatted messages to the default - * ata_dev_set_mode handler, in order to provide consistency of - * presentation. - */ - -void ata_id_to_dma_mode(struct ata_device *dev, u8 unknown) -{ - unsigned int mask; - u8 mode; - - /* Pack the DMA modes */ - mask = ((dev->id[63] >> 8) << ATA_SHIFT_MWDMA) & ATA_MASK_MWDMA; - if (dev->id[53] & 0x04) - mask |= ((dev->id[88] >> 8) << ATA_SHIFT_UDMA) & ATA_MASK_UDMA; - - /* Select the mode in use */ - mode = ata_xfer_mask2mode(mask); - - if (mode != 0) { - ata_dev_printk(dev, KERN_INFO, "configured for %s\n", - ata_mode_string(mask)); - } else { - /* SWDMA perhaps ? */ - mode = unknown; - ata_dev_printk(dev, KERN_INFO, "configured for DMA\n"); - } - - /* Configure the device reporting */ - dev->xfer_mode = mode; - dev->xfer_shift = ata_xfer_mode2shift(mode); -} - -/** * ata_noop_dev_select - Select device 0/1 on ATA bus * @ap: ATA channel to manipulate * @device: ATA device (numbered from zero) to select @@ -1462,9 +1423,9 @@ static inline void ata_dump_id(const u16 *id) * RETURNS: * Computed xfermask */ -static unsigned int ata_id_xfermask(const u16 *id) +unsigned long ata_id_xfermask(const u16 *id) { - unsigned int pio_mask, mwdma_mask, udma_mask; + unsigned long pio_mask, mwdma_mask, udma_mask; /* Usual case. Word 53 indicates word 64 is valid */ if (id[ATA_ID_FIELD_VALID] & (1 << 1)) { @@ -2088,7 +2049,7 @@ int ata_dev_configure(struct ata_device *dev) struct ata_eh_context *ehc = &dev->link->eh_context; int print_info = ehc->i.flags & ATA_EHI_PRINTINFO; const u16 *id = dev->id; - unsigned int xfer_mask; + unsigned long xfer_mask; char revbuf[7]; /* XYZ-99\0 */ char fwrevbuf[ATA_ID_FW_REV_LEN+1]; char modelbuf[ATA_ID_PROD_LEN+1]; @@ -2159,8 +2120,14 @@ int ata_dev_configure(struct ata_device *dev) "supports DRM functions and may " "not be fully accessable.\n"); snprintf(revbuf, 7, "CFA"); - } else + } else { snprintf(revbuf, 7, "ATA-%d", ata_id_major_version(id)); + /* Warn the user if the device has TPM extensions */ + if (ata_id_has_tpm(id)) + ata_dev_printk(dev, KERN_WARNING, + "supports DRM functions and may " + "not be fully accessable.\n"); + } dev->n_sectors = ata_id_n_sectors(id); @@ -2293,19 +2260,8 @@ int ata_dev_configure(struct ata_device *dev) dev->flags |= ATA_DFLAG_DIPM; } - if (dev->horkage & ATA_HORKAGE_DIAGNOSTIC) { - /* Let the user know. We don't want to disallow opens for - rescue purposes, or in case the vendor is just a blithering - idiot */ - if (print_info) { - ata_dev_printk(dev, KERN_WARNING, -"Drive reports diagnostics failure. This may indicate a drive\n"); - ata_dev_printk(dev, KERN_WARNING, -"fault or invalid emulation. Contact drive vendor for information.\n"); - } - } - - /* limit bridge transfers to udma5, 200 sectors */ + /* Limit PATA drive on SATA cable bridge transfers to udma5, + 200 sectors */ if (ata_dev_knobble(dev)) { if (ata_msg_drv(ap) && print_info) ata_dev_printk(dev, KERN_INFO, @@ -2334,6 +2290,21 @@ int ata_dev_configure(struct ata_device *dev) if (ap->ops->dev_config) ap->ops->dev_config(dev); + if (dev->horkage & ATA_HORKAGE_DIAGNOSTIC) { + /* Let the user know. We don't want to disallow opens for + rescue purposes, or in case the vendor is just a blithering + idiot. Do this after the dev_config call as some controllers + with buggy firmware may want to avoid reporting false device + bugs */ + + if (print_info) { + ata_dev_printk(dev, KERN_WARNING, +"Drive reports diagnostics failure. This may indicate a drive\n"); + ata_dev_printk(dev, KERN_WARNING, +"fault or invalid emulation. Contact drive vendor for information.\n"); + } + } + if (ata_msg_probe(ap)) ata_dev_printk(dev, KERN_DEBUG, "%s: EXIT, drv_stat = 0x%x\n", __FUNCTION__, ata_chk_status(ap)); @@ -2385,6 +2356,18 @@ int ata_cable_unknown(struct ata_port *ap) } /** + * ata_cable_ignore - return ignored PATA cable. + * @ap: port + * + * Helper method for drivers which don't use cable type to limit + * transfer mode. + */ +int ata_cable_ignore(struct ata_port *ap) +{ + return ATA_CBL_PATA_IGN; +} + +/** * ata_cable_sata - return SATA cable type * @ap: port * @@ -2779,38 +2762,33 @@ int sata_set_spd(struct ata_link *link) */ static const struct ata_timing ata_timing[] = { +/* { XFER_PIO_SLOW, 120, 290, 240, 960, 290, 240, 960, 0 }, */ + { XFER_PIO_0, 70, 290, 240, 600, 165, 150, 600, 0 }, + { XFER_PIO_1, 50, 290, 93, 383, 125, 100, 383, 0 }, + { XFER_PIO_2, 30, 290, 40, 330, 100, 90, 240, 0 }, + { XFER_PIO_3, 30, 80, 70, 180, 80, 70, 180, 0 }, + { XFER_PIO_4, 25, 70, 25, 120, 70, 25, 120, 0 }, + { XFER_PIO_5, 15, 65, 25, 100, 65, 25, 100, 0 }, + { XFER_PIO_6, 10, 55, 20, 80, 55, 20, 80, 0 }, - { XFER_UDMA_6, 0, 0, 0, 0, 0, 0, 0, 15 }, - { XFER_UDMA_5, 0, 0, 0, 0, 0, 0, 0, 20 }, - { XFER_UDMA_4, 0, 0, 0, 0, 0, 0, 0, 30 }, - { XFER_UDMA_3, 0, 0, 0, 0, 0, 0, 0, 45 }, + { XFER_SW_DMA_0, 120, 0, 0, 0, 480, 480, 960, 0 }, + { XFER_SW_DMA_1, 90, 0, 0, 0, 240, 240, 480, 0 }, + { XFER_SW_DMA_2, 60, 0, 0, 0, 120, 120, 240, 0 }, - { XFER_MW_DMA_4, 25, 0, 0, 0, 55, 20, 80, 0 }, + { XFER_MW_DMA_0, 60, 0, 0, 0, 215, 215, 480, 0 }, + { XFER_MW_DMA_1, 45, 0, 0, 0, 80, 50, 150, 0 }, + { XFER_MW_DMA_2, 25, 0, 0, 0, 70, 25, 120, 0 }, { XFER_MW_DMA_3, 25, 0, 0, 0, 65, 25, 100, 0 }, - { XFER_UDMA_2, 0, 0, 0, 0, 0, 0, 0, 60 }, - { XFER_UDMA_1, 0, 0, 0, 0, 0, 0, 0, 80 }, - { XFER_UDMA_0, 0, 0, 0, 0, 0, 0, 0, 120 }, + { XFER_MW_DMA_4, 25, 0, 0, 0, 55, 20, 80, 0 }, /* { XFER_UDMA_SLOW, 0, 0, 0, 0, 0, 0, 0, 150 }, */ - - { XFER_MW_DMA_2, 25, 0, 0, 0, 70, 25, 120, 0 }, - { XFER_MW_DMA_1, 45, 0, 0, 0, 80, 50, 150, 0 }, - { XFER_MW_DMA_0, 60, 0, 0, 0, 215, 215, 480, 0 }, - - { XFER_SW_DMA_2, 60, 0, 0, 0, 120, 120, 240, 0 }, - { XFER_SW_DMA_1, 90, 0, 0, 0, 240, 240, 480, 0 }, - { XFER_SW_DMA_0, 120, 0, 0, 0, 480, 480, 960, 0 }, - - { XFER_PIO_6, 10, 55, 20, 80, 55, 20, 80, 0 }, - { XFER_PIO_5, 15, 65, 25, 100, 65, 25, 100, 0 }, - { XFER_PIO_4, 25, 70, 25, 120, 70, 25, 120, 0 }, - { XFER_PIO_3, 30, 80, 70, 180, 80, 70, 180, 0 }, - - { XFER_PIO_2, 30, 290, 40, 330, 100, 90, 240, 0 }, - { XFER_PIO_1, 50, 290, 93, 383, 125, 100, 383, 0 }, - { XFER_PIO_0, 70, 290, 240, 600, 165, 150, 600, 0 }, - -/* { XFER_PIO_SLOW, 120, 290, 240, 960, 290, 240, 960, 0 }, */ + { XFER_UDMA_0, 0, 0, 0, 0, 0, 0, 0, 120 }, + { XFER_UDMA_1, 0, 0, 0, 0, 0, 0, 0, 80 }, + { XFER_UDMA_2, 0, 0, 0, 0, 0, 0, 0, 60 }, + { XFER_UDMA_3, 0, 0, 0, 0, 0, 0, 0, 45 }, + { XFER_UDMA_4, 0, 0, 0, 0, 0, 0, 0, 30 }, + { XFER_UDMA_5, 0, 0, 0, 0, 0, 0, 0, 20 }, + { XFER_UDMA_6, 0, 0, 0, 0, 0, 0, 0, 15 }, { 0xFF } }; @@ -2843,14 +2821,16 @@ void ata_timing_merge(const struct ata_timing *a, const struct ata_timing *b, if (what & ATA_TIMING_UDMA ) m->udma = max(a->udma, b->udma); } -static const struct ata_timing *ata_timing_find_mode(unsigned short speed) +const struct ata_timing *ata_timing_find_mode(u8 xfer_mode) { - const struct ata_timing *t; + const struct ata_timing *t = ata_timing; + + while (xfer_mode > t->mode) + t++; - for (t = ata_timing; t->mode != speed; t++) - if (t->mode == 0xFF) - return NULL; - return t; + if (xfer_mode == t->mode) + return t; + return NULL; } int ata_timing_compute(struct ata_device *adev, unsigned short speed, @@ -2925,6 +2905,57 @@ int ata_timing_compute(struct ata_device *adev, unsigned short speed, } /** + * ata_timing_cycle2mode - find xfer mode for the specified cycle duration + * @xfer_shift: ATA_SHIFT_* value for transfer type to examine. + * @cycle: cycle duration in ns + * + * Return matching xfer mode for @cycle. The returned mode is of + * the transfer type specified by @xfer_shift. If @cycle is too + * slow for @xfer_shift, 0xff is returned. If @cycle is faster + * than the fastest known mode, the fasted mode is returned. + * + * LOCKING: + * None. + * + * RETURNS: + * Matching xfer_mode, 0xff if no match found. + */ +u8 ata_timing_cycle2mode(unsigned int xfer_shift, int cycle) +{ + u8 base_mode = 0xff, last_mode = 0xff; + const struct ata_xfer_ent *ent; + const struct ata_timing *t; + + for (ent = ata_xfer_tbl; ent->shift >= 0; ent++) + if (ent->shift == xfer_shift) + base_mode = ent->base; + + for (t = ata_timing_find_mode(base_mode); + t && ata_xfer_mode2shift(t->mode) == xfer_shift; t++) { + unsigned short this_cycle; + + switch (xfer_shift) { + case ATA_SHIFT_PIO: + case ATA_SHIFT_MWDMA: + this_cycle = t->cycle; + break; + case ATA_SHIFT_UDMA: + this_cycle = t->udma; + break; + default: + return 0xff; + } + + if (cycle > this_cycle) + break; + + last_mode = t->mode; + } + + return last_mode; +} + +/** * ata_down_xfermask_limit - adjust dev xfer masks downward * @dev: Device to adjust xfer masks * @sel: ATA_DNXFER_* selector @@ -2942,8 +2973,8 @@ int ata_timing_compute(struct ata_device *adev, unsigned short speed, int ata_down_xfermask_limit(struct ata_device *dev, unsigned int sel) { char buf[32]; - unsigned int orig_mask, xfer_mask; - unsigned int pio_mask, mwdma_mask, udma_mask; + unsigned long orig_mask, xfer_mask; + unsigned long pio_mask, mwdma_mask, udma_mask; int quiet, highbit; quiet = !!(sel & ATA_DNXFER_QUIET); @@ -3037,7 +3068,7 @@ static int ata_dev_set_mode(struct ata_device *dev) /* Early MWDMA devices do DMA but don't allow DMA mode setting. Don't fail an MWDMA0 set IFF the device indicates it is in MWDMA0 */ - if (dev->xfer_shift == ATA_SHIFT_MWDMA && + if (dev->xfer_shift == ATA_SHIFT_MWDMA && dev->dma_mode == XFER_MW_DMA_0 && (dev->id[63] >> 8) & 1) err_mask &= ~AC_ERR_DEV; @@ -3087,7 +3118,7 @@ int ata_do_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) /* step 1: calculate xfer_mask */ ata_link_for_each_dev(dev, link) { - unsigned int pio_mask, dma_mask; + unsigned long pio_mask, dma_mask; unsigned int mode_mask; if (!ata_dev_enabled(dev)) @@ -3113,7 +3144,7 @@ int ata_do_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) dev->dma_mode = ata_xfer_mask2mode(dma_mask); found = 1; - if (dev->dma_mode) + if (dev->dma_mode != 0xff) used_dma = 1; } if (!found) @@ -3124,7 +3155,7 @@ int ata_do_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) if (!ata_dev_enabled(dev)) continue; - if (!dev->pio_mode) { + if (dev->pio_mode == 0xff) { ata_dev_printk(dev, KERN_WARNING, "no PIO support\n"); rc = -EINVAL; goto out; @@ -3138,7 +3169,7 @@ int ata_do_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) /* step 3: set host DMA timings */ ata_link_for_each_dev(dev, link) { - if (!ata_dev_enabled(dev) || !dev->dma_mode) + if (!ata_dev_enabled(dev) || dev->dma_mode == 0xff) continue; dev->xfer_mode = dev->dma_mode; @@ -3171,31 +3202,6 @@ int ata_do_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) } /** - * ata_set_mode - Program timings and issue SET FEATURES - XFER - * @link: link on which timings will be programmed - * @r_failed_dev: out paramter for failed device - * - * Set ATA device disk transfer mode (PIO3, UDMA6, etc.). If - * ata_set_mode() fails, pointer to the failing device is - * returned in @r_failed_dev. - * - * LOCKING: - * PCI/etc. bus probe sem. - * - * RETURNS: - * 0 on success, negative errno otherwise - */ -int ata_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) -{ - struct ata_port *ap = link->ap; - - /* has private set_mode? */ - if (ap->ops->set_mode) - return ap->ops->set_mode(link, r_failed_dev); - return ata_do_set_mode(link, r_failed_dev); -} - -/** * ata_tf_to_host - issue ATA taskfile to host controller * @ap: port to which command is being issued * @tf: ATA taskfile register set @@ -4359,7 +4365,14 @@ static unsigned int ata_dev_set_xfermode(struct ata_device *dev) tf.feature = SETFEATURES_XFER; tf.flags |= ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE | ATA_TFLAG_POLLING; tf.protocol = ATA_PROT_NODATA; - tf.nsect = dev->xfer_mode; + /* If we are using IORDY we must send the mode setting command */ + if (ata_pio_need_iordy(dev)) + tf.nsect = dev->xfer_mode; + /* If the device has IORDY and the controller does not - turn it off */ + else if (ata_id_has_iordy(dev->id)) + tf.nsect = 0x01; + else /* In the ancient relic department - skip all of this */ + return 0; err_mask = ata_exec_internal(dev, &tf, NULL, DMA_NONE, NULL, 0, 0); @@ -5295,7 +5308,7 @@ static inline int ata_hsm_ok_in_wq(struct ata_port *ap, struct ata_queued_cmd *q (qc->tf.flags & ATA_TFLAG_WRITE)) return 1; - if (is_atapi_taskfile(&qc->tf) && + if (ata_is_atapi(qc->tf.protocol) && !(qc->dev->flags & ATA_DFLAG_CDB_INTR)) return 1; } @@ -5412,19 +5425,19 @@ fsm_start: * let the EH abort the command or reset the device. */ if (unlikely(status & (ATA_ERR | ATA_DF))) { - /* Some ATAPI tape drives forget to clear the ERR bit - * when doing the next command (mostly request sense). - * We ignore ERR here to workaround and proceed sending - * the CDB. - */ - if (!(qc->dev->horkage & ATA_HORKAGE_STUCK_ERR)) { - ata_port_printk(ap, KERN_WARNING, - "DRQ=1 with device error, " - "dev_stat 0x%X\n", status); - qc->err_mask |= AC_ERR_HSM; - ap->hsm_task_state = HSM_ST_ERR; - goto fsm_start; - } + ata_port_printk(ap, KERN_WARNING, "DRQ=1 with device " + "error, dev_stat 0x%X\n", status); + /* Some devices muck this up. Some follow an ATA + non-standard that permits the damaged sector to + be retrieved at this point. The ATA spec says + we should jump up and down on DRQ + ERR, reality + says we should be a little more relaxed. + + Rather than an HSM error, take it as a device + error */ + qc->err_mask |= AC_ERR_DEV; + ap->hsm_task_state = HSM_ST_ERR; + goto fsm_start; } /* Send the CDB (atapi) or the first data block (ata pio out). @@ -5759,6 +5772,22 @@ static void fill_result_tf(struct ata_queued_cmd *qc) ap->ops->tf_read(ap, &qc->result_tf); } +static void ata_verify_xfer(struct ata_queued_cmd *qc) +{ + struct ata_device *dev = qc->dev; + + if (ata_tag_internal(qc->tag)) + return; + + if (ata_is_nodata(qc->tf.protocol)) + return; + + if ((dev->mwdma_mask || dev->udma_mask) && ata_is_pio(qc->tf.protocol)) + return; + + dev->flags &= ~ATA_DFLAG_DUBIOUS_XFER; +} + /** * ata_qc_complete - Complete an active ATA command * @qc: Command to complete @@ -5830,6 +5859,9 @@ void ata_qc_complete(struct ata_queued_cmd *qc) break; } + if (unlikely(dev->flags & ATA_DFLAG_DUBIOUS_XFER)) + ata_verify_xfer(qc); + __ata_qc_complete(qc); } else { if (qc->flags & ATA_QCFLAG_EH_SCHEDULED) @@ -5892,30 +5924,6 @@ int ata_qc_complete_multiple(struct ata_port *ap, u32 qc_active, return nr_done; } -static inline int ata_should_dma_map(struct ata_queued_cmd *qc) -{ - struct ata_port *ap = qc->ap; - - switch (qc->tf.protocol) { - case ATA_PROT_NCQ: - case ATA_PROT_DMA: - case ATA_PROT_ATAPI_DMA: - return 1; - - case ATA_PROT_ATAPI: - case ATA_PROT_PIO: - if (ap->flags & ATA_FLAG_PIO_DMA) - return 1; - - /* fall through */ - - default: - return 0; - } - - /* never reached */ -} - /** * ata_qc_issue - issue taskfile to device * @qc: command to issue to device @@ -5932,6 +5940,7 @@ void ata_qc_issue(struct ata_queued_cmd *qc) { struct ata_port *ap = qc->ap; struct ata_link *link = qc->dev->link; + u8 prot = qc->tf.protocol; /* Make sure only one non-NCQ command is outstanding. The * check is skipped for old EH because it reuses active qc to @@ -5939,7 +5948,7 @@ void ata_qc_issue(struct ata_queued_cmd *qc) */ WARN_ON(ap->ops->error_handler && ata_tag_valid(link->active_tag)); - if (qc->tf.protocol == ATA_PROT_NCQ) { + if (prot == ATA_PROT_NCQ) { WARN_ON(link->sactive & (1 << qc->tag)); if (!link->sactive) @@ -5955,7 +5964,8 @@ void ata_qc_issue(struct ata_queued_cmd *qc) qc->flags |= ATA_QCFLAG_ACTIVE; ap->qc_active |= 1 << qc->tag; - if (ata_should_dma_map(qc)) { + if (ata_is_dma(prot) || (ata_is_pio(prot) && + (ap->flags & ATA_FLAG_PIO_DMA))) { if (qc->flags & ATA_QCFLAG_SG) { if (ata_sg_setup(qc)) goto sg_err; @@ -6142,6 +6152,7 @@ inline unsigned int ata_host_intr(struct ata_port *ap, { struct ata_eh_info *ehi = &ap->link.eh_info; u8 status, host_stat = 0; + int i; VPRINTK("ata%u: protocol %d task_state %d\n", ap->print_id, qc->tf.protocol, ap->hsm_task_state); @@ -6154,8 +6165,8 @@ inline unsigned int ata_host_intr(struct ata_port *ap, */ /* Check the ATA_DFLAG_CDB_INTR flag is enough here. - * The flag was turned on only for atapi devices. - * No need to check is_atapi_taskfile(&qc->tf) again. + * The flag was turned on only for atapi devices. No + * need to check ata_is_atapi(qc->tf.protocol) again. */ if (!(qc->dev->flags & ATA_DFLAG_CDB_INTR)) goto idle_irq; @@ -6198,6 +6209,20 @@ inline unsigned int ata_host_intr(struct ata_port *ap, if (unlikely(status & ATA_BUSY)) goto idle_irq; + if (unlikely(qc->tf.command == ATA_CMD_SET_FEATURES && + qc->tf.feature == SETFEATURES_XFER)) { + /* Let the timings change settle and the drive catch up as + some hardware needs up to 10uS to get its brain back in + gear. Taken from the workarounds in drivers/ide done by + Matthew Faupel/Niccolo Rigacci */ + for (i = 0; i < 10; i++) { + if ((status & (ATA_BUSY | ATA_DRQ | ATA_ERR)) == 0) + break; + udelay(1); + status = ata_chk_status(ap); + } + } + /* ack bmdma irq events */ ap->ops->irq_clear(ap); @@ -7554,6 +7579,13 @@ EXPORT_SYMBOL_GPL(ata_std_dev_select); EXPORT_SYMBOL_GPL(sata_print_link_status); EXPORT_SYMBOL_GPL(ata_tf_to_fis); EXPORT_SYMBOL_GPL(ata_tf_from_fis); +EXPORT_SYMBOL_GPL(ata_pack_xfermask); +EXPORT_SYMBOL_GPL(ata_unpack_xfermask); +EXPORT_SYMBOL_GPL(ata_xfer_mask2mode); +EXPORT_SYMBOL_GPL(ata_xfer_mode2mask); +EXPORT_SYMBOL_GPL(ata_xfer_mode2shift); +EXPORT_SYMBOL_GPL(ata_mode_string); +EXPORT_SYMBOL_GPL(ata_id_xfermask); EXPORT_SYMBOL_GPL(ata_check_status); EXPORT_SYMBOL_GPL(ata_altstatus); EXPORT_SYMBOL_GPL(ata_exec_command); @@ -7615,12 +7647,13 @@ EXPORT_SYMBOL_GPL(ata_host_resume); #endif /* CONFIG_PM */ EXPORT_SYMBOL_GPL(ata_id_string); EXPORT_SYMBOL_GPL(ata_id_c_string); -EXPORT_SYMBOL_GPL(ata_id_to_dma_mode); EXPORT_SYMBOL_GPL(ata_scsi_simulate); EXPORT_SYMBOL_GPL(ata_pio_need_iordy); +EXPORT_SYMBOL_GPL(ata_timing_find_mode); EXPORT_SYMBOL_GPL(ata_timing_compute); EXPORT_SYMBOL_GPL(ata_timing_merge); +EXPORT_SYMBOL_GPL(ata_timing_cycle2mode); #ifdef CONFIG_PCI EXPORT_SYMBOL_GPL(pci_test_config_bits); @@ -7668,4 +7701,5 @@ EXPORT_SYMBOL_GPL(ata_dev_try_classify); EXPORT_SYMBOL_GPL(ata_cable_40wire); EXPORT_SYMBOL_GPL(ata_cable_80wire); EXPORT_SYMBOL_GPL(ata_cable_unknown); +EXPORT_SYMBOL_GPL(ata_cable_ignore); EXPORT_SYMBOL_GPL(ata_cable_sata); diff --git a/drivers/ata/libata-eh.c b/drivers/ata/libata-eh.c index e6605f0..228a225 100644 --- a/drivers/ata/libata-eh.c +++ b/drivers/ata/libata-eh.c @@ -46,9 +46,27 @@ #include "libata.h" enum { + /* speed down verdicts */ ATA_EH_SPDN_NCQ_OFF = (1 << 0), ATA_EH_SPDN_SPEED_DOWN = (1 << 1), ATA_EH_SPDN_FALLBACK_TO_PIO = (1 << 2), + ATA_EH_SPDN_KEEP_ERRORS = (1 << 3), + + /* error flags */ + ATA_EFLAG_IS_IO = (1 << 0), + ATA_EFLAG_DUBIOUS_XFER = (1 << 1), + + /* error categories */ + ATA_ECAT_NONE = 0, + ATA_ECAT_ATA_BUS = 1, + ATA_ECAT_TOUT_HSM = 2, + ATA_ECAT_UNK_DEV = 3, + ATA_ECAT_DUBIOUS_ATA_BUS = 4, + ATA_ECAT_DUBIOUS_TOUT_HSM = 5, + ATA_ECAT_DUBIOUS_UNK_DEV = 6, + ATA_ECAT_NR = 7, + + ATA_ECAT_DUBIOUS_BASE = ATA_ECAT_DUBIOUS_ATA_BUS, }; /* Waiting in ->prereset can never be reliable. It's sometimes nice @@ -218,7 +236,7 @@ void ata_port_pbar_desc(struct ata_port *ap, int bar, ssize_t offset, #endif /* CONFIG_PCI */ -static void ata_ering_record(struct ata_ering *ering, int is_io, +static void ata_ering_record(struct ata_ering *ering, unsigned int eflags, unsigned int err_mask) { struct ata_ering_entry *ent; @@ -229,11 +247,20 @@ static void ata_ering_record(struct ata_ering *ering, int is_io, ering->cursor %= ATA_ERING_SIZE; ent = &ering->ring[ering->cursor]; - ent->is_io = is_io; + ent->eflags = eflags; ent->err_mask = err_mask; ent->timestamp = get_jiffies_64(); } +static struct ata_ering_entry *ata_ering_top(struct ata_ering *ering) +{ + struct ata_ering_entry *ent = &ering->ring[ering->cursor]; + + if (ent->err_mask) + return ent; + return NULL; +} + static void ata_ering_clear(struct ata_ering *ering) { memset(ering, 0, sizeof(*ering)); @@ -445,9 +472,20 @@ void ata_scsi_error(struct Scsi_Host *host) spin_lock_irqsave(ap->lock, flags); __ata_port_for_each_link(link, ap) { + struct ata_eh_context *ehc = &link->eh_context; + struct ata_device *dev; + memset(&link->eh_context, 0, sizeof(link->eh_context)); link->eh_context.i = link->eh_info; memset(&link->eh_info, 0, sizeof(link->eh_info)); + + ata_link_for_each_dev(dev, link) { + int devno = dev->devno; + + ehc->saved_xfer_mode[devno] = dev->xfer_mode; + if (ata_ncq_enabled(dev)) + ehc->saved_ncq_enabled |= 1 << devno; + } } ap->pflags |= ATA_PFLAG_EH_IN_PROGRESS; @@ -1451,20 +1489,29 @@ static unsigned int ata_eh_analyze_tf(struct ata_queued_cmd *qc, return action; } -static int ata_eh_categorize_error(int is_io, unsigned int err_mask) +static int ata_eh_categorize_error(unsigned int eflags, unsigned int err_mask, + int *xfer_ok) { + int base = 0; + + if (!(eflags & ATA_EFLAG_DUBIOUS_XFER)) + *xfer_ok = 1; + + if (!*xfer_ok) + base = ATA_ECAT_DUBIOUS_BASE; + if (err_mask & AC_ERR_ATA_BUS) - return 1; + return base + ATA_ECAT_ATA_BUS; if (err_mask & AC_ERR_TIMEOUT) - return 2; + return base + ATA_ECAT_TOUT_HSM; - if (is_io) { + if (eflags & ATA_EFLAG_IS_IO) { if (err_mask & AC_ERR_HSM) - return 2; + return base + ATA_ECAT_TOUT_HSM; if ((err_mask & (AC_ERR_DEV|AC_ERR_MEDIA|AC_ERR_INVALID)) == AC_ERR_DEV) - return 3; + return base + ATA_ECAT_UNK_DEV; } return 0; @@ -1472,18 +1519,22 @@ static int ata_eh_categorize_error(int is_io, unsigned int err_mask) struct speed_down_verdict_arg { u64 since; - int nr_errors[4]; + int xfer_ok; + int nr_errors[ATA_ECAT_NR]; }; static int speed_down_verdict_cb(struct ata_ering_entry *ent, void *void_arg) { struct speed_down_verdict_arg *arg = void_arg; - int cat = ata_eh_categorize_error(ent->is_io, ent->err_mask); + int cat; if (ent->timestamp < arg->since) return -1; + cat = ata_eh_categorize_error(ent->eflags, ent->err_mask, + &arg->xfer_ok); arg->nr_errors[cat]++; + return 0; } @@ -1495,22 +1546,48 @@ static int speed_down_verdict_cb(struct ata_ering_entry *ent, void *void_arg) * whether NCQ needs to be turned off, transfer speed should be * stepped down, or falling back to PIO is necessary. * - * Cat-1 is ATA_BUS error for any command. + * ECAT_ATA_BUS : ATA_BUS error for any command + * + * ECAT_TOUT_HSM : TIMEOUT for any command or HSM violation for + * IO commands + * + * ECAT_UNK_DEV : Unknown DEV error for IO commands + * + * ECAT_DUBIOUS_* : Identical to above three but occurred while + * data transfer hasn't been verified. + * + * Verdicts are + * + * NCQ_OFF : Turn off NCQ. + * + * SPEED_DOWN : Speed down transfer speed but don't fall back + * to PIO. + * + * FALLBACK_TO_PIO : Fall back to PIO. + * + * Even if multiple verdicts are returned, only one action is + * taken per error. An action triggered by non-DUBIOUS errors + * clears ering, while one triggered by DUBIOUS_* errors doesn't. + * This is to expedite speed down decisions right after device is + * initially configured. * - * Cat-2 is TIMEOUT for any command or HSM violation for known - * supported commands. + * The followings are speed down rules. #1 and #2 deal with + * DUBIOUS errors. * - * Cat-3 is is unclassified DEV error for known supported - * command. + * 1. If more than one DUBIOUS_ATA_BUS or DUBIOUS_TOUT_HSM errors + * occurred during last 5 mins, SPEED_DOWN and FALLBACK_TO_PIO. * - * NCQ needs to be turned off if there have been more than 3 - * Cat-2 + Cat-3 errors during last 10 minutes. + * 2. If more than one DUBIOUS_TOUT_HSM or DUBIOUS_UNK_DEV errors + * occurred during last 5 mins, NCQ_OFF. * - * Speed down is necessary if there have been more than 3 Cat-1 + - * Cat-2 errors or 10 Cat-3 errors during last 10 minutes. + * 3. If more than 8 ATA_BUS, TOUT_HSM or UNK_DEV errors + * ocurred during last 5 mins, FALLBACK_TO_PIO * - * Falling back to PIO mode is necessary if there have been more - * than 10 Cat-1 + Cat-2 + Cat-3 errors during last 5 minutes. + * 4. If more than 3 TOUT_HSM or UNK_DEV errors occurred + * during last 10 mins, NCQ_OFF. + * + * 5. If more than 3 ATA_BUS or TOUT_HSM errors, or more than 6 + * UNK_DEV errors occurred during last 10 mins, SPEED_DOWN. * * LOCKING: * Inherited from caller. @@ -1525,23 +1602,38 @@ static unsigned int ata_eh_speed_down_verdict(struct ata_device *dev) struct speed_down_verdict_arg arg; unsigned int verdict = 0; - /* scan past 10 mins of error history */ + /* scan past 5 mins of error history */ memset(&arg, 0, sizeof(arg)); - arg.since = j64 - min(j64, j10mins); + arg.since = j64 - min(j64, j5mins); ata_ering_map(&dev->ering, speed_down_verdict_cb, &arg); - if (arg.nr_errors[2] + arg.nr_errors[3] > 3) - verdict |= ATA_EH_SPDN_NCQ_OFF; - if (arg.nr_errors[1] + arg.nr_errors[2] > 3 || arg.nr_errors[3] > 10) - verdict |= ATA_EH_SPDN_SPEED_DOWN; + if (arg.nr_errors[ATA_ECAT_DUBIOUS_ATA_BUS] + + arg.nr_errors[ATA_ECAT_DUBIOUS_TOUT_HSM] > 1) + verdict |= ATA_EH_SPDN_SPEED_DOWN | + ATA_EH_SPDN_FALLBACK_TO_PIO | ATA_EH_SPDN_KEEP_ERRORS; - /* scan past 3 mins of error history */ + if (arg.nr_errors[ATA_ECAT_DUBIOUS_TOUT_HSM] + + arg.nr_errors[ATA_ECAT_DUBIOUS_UNK_DEV] > 1) + verdict |= ATA_EH_SPDN_NCQ_OFF | ATA_EH_SPDN_KEEP_ERRORS; + + if (arg.nr_errors[ATA_ECAT_ATA_BUS] + + arg.nr_errors[ATA_ECAT_TOUT_HSM] + + arg.nr_errors[ATA_ECAT_UNK_DEV] > 6) + verdict |= ATA_EH_SPDN_FALLBACK_TO_PIO; + + /* scan past 10 mins of error history */ memset(&arg, 0, sizeof(arg)); - arg.since = j64 - min(j64, j5mins); + arg.since = j64 - min(j64, j10mins); ata_ering_map(&dev->ering, speed_down_verdict_cb, &arg); - if (arg.nr_errors[1] + arg.nr_errors[2] + arg.nr_errors[3] > 10) - verdict |= ATA_EH_SPDN_FALLBACK_TO_PIO; + if (arg.nr_errors[ATA_ECAT_TOUT_HSM] + + arg.nr_errors[ATA_ECAT_UNK_DEV] > 3) + verdict |= ATA_EH_SPDN_NCQ_OFF; + + if (arg.nr_errors[ATA_ECAT_ATA_BUS] + + arg.nr_errors[ATA_ECAT_TOUT_HSM] > 3 || + arg.nr_errors[ATA_ECAT_UNK_DEV] > 6) + verdict |= ATA_EH_SPDN_SPEED_DOWN; return verdict; } @@ -1549,7 +1641,7 @@ static unsigned int ata_eh_speed_down_verdict(struct ata_device *dev) /** * ata_eh_speed_down - record error and speed down if necessary * @dev: Failed device - * @is_io: Did the device fail during normal IO? + * @eflags: mask of ATA_EFLAG_* flags * @err_mask: err_mask of the error * * Record error and examine error history to determine whether @@ -1563,18 +1655,20 @@ static unsigned int ata_eh_speed_down_verdict(struct ata_device *dev) * RETURNS: * Determined recovery action. */ -static unsigned int ata_eh_speed_down(struct ata_device *dev, int is_io, - unsigned int err_mask) +static unsigned int ata_eh_speed_down(struct ata_device *dev, + unsigned int eflags, unsigned int err_mask) { + struct ata_link *link = dev->link; + int xfer_ok = 0; unsigned int verdict; unsigned int action = 0; /* don't bother if Cat-0 error */ - if (ata_eh_categorize_error(is_io, err_mask) == 0) + if (ata_eh_categorize_error(eflags, err_mask, &xfer_ok) == 0) return 0; /* record error and determine whether speed down is necessary */ - ata_ering_record(&dev->ering, is_io, err_mask); + ata_ering_record(&dev->ering, eflags, err_mask); verdict = ata_eh_speed_down_verdict(dev); /* turn off NCQ? */ @@ -1590,7 +1684,7 @@ static unsigned int ata_eh_speed_down(struct ata_device *dev, int is_io, /* speed down? */ if (verdict & ATA_EH_SPDN_SPEED_DOWN) { /* speed down SATA link speed if possible */ - if (sata_down_spd_limit(dev->link) == 0) { + if (sata_down_spd_limit(link) == 0) { action |= ATA_EH_HARDRESET; goto done; } @@ -1618,10 +1712,10 @@ static unsigned int ata_eh_speed_down(struct ata_device *dev, int is_io, } /* Fall back to PIO? Slowing down to PIO is meaningless for - * SATA. Consider it only for PATA. + * SATA ATA devices. Consider it only for PATA and SATAPI. */ if ((verdict & ATA_EH_SPDN_FALLBACK_TO_PIO) && (dev->spdn_cnt >= 2) && - (dev->link->ap->cbl != ATA_CBL_SATA) && + (link->ap->cbl != ATA_CBL_SATA || dev->class == ATA_DEV_ATAPI) && (dev->xfer_shift != ATA_SHIFT_PIO)) { if (ata_down_xfermask_limit(dev, ATA_DNXFER_FORCE_PIO) == 0) { dev->spdn_cnt = 0; @@ -1633,7 +1727,8 @@ static unsigned int ata_eh_speed_down(struct ata_device *dev, int is_io, return 0; done: /* device has been slowed down, blow error history */ - ata_ering_clear(&dev->ering); + if (!(verdict & ATA_EH_SPDN_KEEP_ERRORS)) + ata_ering_clear(&dev->ering); return action; } @@ -1653,8 +1748,8 @@ static void ata_eh_link_autopsy(struct ata_link *link) struct ata_port *ap = link->ap; struct ata_eh_context *ehc = &link->eh_context; struct ata_device *dev; - unsigned int all_err_mask = 0; - int tag, is_io = 0; + unsigned int all_err_mask = 0, eflags = 0; + int tag; u32 serror; int rc; @@ -1713,15 +1808,15 @@ static void ata_eh_link_autopsy(struct ata_link *link) ehc->i.dev = qc->dev; all_err_mask |= qc->err_mask; if (qc->flags & ATA_QCFLAG_IO) - is_io = 1; + eflags |= ATA_EFLAG_IS_IO; } /* enforce default EH actions */ if (ap->pflags & ATA_PFLAG_FROZEN || all_err_mask & (AC_ERR_HSM | AC_ERR_TIMEOUT)) ehc->i.action |= ATA_EH_SOFTRESET; - else if ((is_io && all_err_mask) || - (!is_io && (all_err_mask & ~AC_ERR_DEV))) + else if (((eflags & ATA_EFLAG_IS_IO) && all_err_mask) || + (!(eflags & ATA_EFLAG_IS_IO) && (all_err_mask & ~AC_ERR_DEV))) ehc->i.action |= ATA_EH_REVALIDATE; /* If we have offending qcs and the associated failed device, @@ -1739,8 +1834,11 @@ static void ata_eh_link_autopsy(struct ata_link *link) ata_dev_enabled(link->device)) dev = link->device; - if (dev) - ehc->i.action |= ata_eh_speed_down(dev, is_io, all_err_mask); + if (dev) { + if (dev->flags & ATA_DFLAG_DUBIOUS_XFER) + eflags |= ATA_EFLAG_DUBIOUS_XFER; + ehc->i.action |= ata_eh_speed_down(dev, eflags, all_err_mask); + } DPRINTK("EXIT\n"); } @@ -1879,7 +1977,7 @@ static void ata_eh_link_report(struct ata_link *link) dma_str[qc->dma_dir]); } - if (is_atapi_taskfile(&qc->tf)) + if (ata_is_atapi(qc->tf.protocol)) snprintf(cdb_buf, sizeof(cdb_buf), "cdb %02x %02x %02x %02x %02x %02x %02x %02x " "%02x %02x %02x %02x %02x %02x %02x %02x\n ", @@ -2321,6 +2419,58 @@ static int ata_eh_revalidate_and_attach(struct ata_link *link, return rc; } +/** + * ata_set_mode - Program timings and issue SET FEATURES - XFER + * @link: link on which timings will be programmed + * @r_failed_dev: out paramter for failed device + * + * Set ATA device disk transfer mode (PIO3, UDMA6, etc.). If + * ata_set_mode() fails, pointer to the failing device is + * returned in @r_failed_dev. + * + * LOCKING: + * PCI/etc. bus probe sem. + * + * RETURNS: + * 0 on success, negative errno otherwise + */ +int ata_set_mode(struct ata_link *link, struct ata_device **r_failed_dev) +{ + struct ata_port *ap = link->ap; + struct ata_device *dev; + int rc; + + /* if data transfer is verified, clear DUBIOUS_XFER on ering top */ + ata_link_for_each_dev(dev, link) { + if (!(dev->flags & ATA_DFLAG_DUBIOUS_XFER)) { + struct ata_ering_entry *ent; + + ent = ata_ering_top(&dev->ering); + if (ent) + ent->eflags &= ~ATA_EFLAG_DUBIOUS_XFER; + } + } + + /* has private set_mode? */ + if (ap->ops->set_mode) + rc = ap->ops->set_mode(link, r_failed_dev); + else + rc = ata_do_set_mode(link, r_failed_dev); + + /* if transfer mode has changed, set DUBIOUS_XFER on device */ + ata_link_for_each_dev(dev, link) { + struct ata_eh_context *ehc = &link->eh_context; + u8 saved_xfer_mode = ehc->saved_xfer_mode[dev->devno]; + u8 saved_ncq = !!(ehc->saved_ncq_enabled & (1 << dev->devno)); + + if (dev->xfer_mode != saved_xfer_mode || + ata_ncq_enabled(dev) != saved_ncq) + dev->flags |= ATA_DFLAG_DUBIOUS_XFER; + } + + return rc; +} + static int ata_link_nr_enabled(struct ata_link *link) { struct ata_device *dev; @@ -2367,6 +2517,24 @@ static int ata_eh_skip_recovery(struct ata_link *link) return 1; } +static int ata_eh_schedule_probe(struct ata_device *dev) +{ + struct ata_eh_context *ehc = &dev->link->eh_context; + + if (!(ehc->i.probe_mask & (1 << dev->devno)) || + (ehc->did_probe_mask & (1 << dev->devno))) + return 0; + + ata_eh_detach_dev(dev); + ata_dev_init(dev); + ehc->did_probe_mask |= (1 << dev->devno); + ehc->i.action |= ATA_EH_SOFTRESET; + ehc->saved_xfer_mode[dev->devno] = 0; + ehc->saved_ncq_enabled &= ~(1 << dev->devno); + + return 1; +} + static int ata_eh_handle_dev_fail(struct ata_device *dev, int err) { struct ata_eh_context *ehc = &dev->link->eh_context; @@ -2398,16 +2566,9 @@ static int ata_eh_handle_dev_fail(struct ata_device *dev, int err) if (ata_link_offline(dev->link)) ata_eh_detach_dev(dev); - /* probe if requested */ - if ((ehc->i.probe_mask & (1 << dev->devno)) && - !(ehc->did_probe_mask & (1 << dev->devno))) { - ata_eh_detach_dev(dev); - ata_dev_init(dev); - + /* schedule probe if necessary */ + if (ata_eh_schedule_probe(dev)) ehc->tries[dev->devno] = ATA_EH_DEV_TRIES; - ehc->did_probe_mask |= (1 << dev->devno); - ehc->i.action |= ATA_EH_SOFTRESET; - } return 1; } else { @@ -2484,14 +2645,9 @@ int ata_eh_recover(struct ata_port *ap, ata_prereset_fn_t prereset, if (dev->flags & ATA_DFLAG_DETACH) ata_eh_detach_dev(dev); - if (!ata_dev_enabled(dev) && - ((ehc->i.probe_mask & (1 << dev->devno)) && - !(ehc->did_probe_mask & (1 << dev->devno)))) { - ata_eh_detach_dev(dev); - ata_dev_init(dev); - ehc->did_probe_mask |= (1 << dev->devno); - ehc->i.action |= ATA_EH_SOFTRESET; - } + /* schedule probe if necessary */ + if (!ata_dev_enabled(dev)) + ata_eh_schedule_probe(dev); } } @@ -2739,6 +2895,7 @@ static void ata_eh_handle_port_suspend(struct ata_port *ap) if (ap->ops->port_suspend) rc = ap->ops->port_suspend(ap, ap->pm_mesg); + ata_acpi_set_state(ap, PMSG_SUSPEND); out: /* report result */ spin_lock_irqsave(ap->lock, flags); @@ -2784,6 +2941,8 @@ static void ata_eh_handle_port_resume(struct ata_port *ap) WARN_ON(!(ap->pflags & ATA_PFLAG_SUSPENDED)); + ata_acpi_set_state(ap, PMSG_ON); + if (ap->ops->port_resume) rc = ap->ops->port_resume(ap); diff --git a/drivers/ata/libata-scsi.c b/drivers/ata/libata-scsi.c index a883bb0..a1ec970 100644 --- a/drivers/ata/libata-scsi.c +++ b/drivers/ata/libata-scsi.c @@ -2689,6 +2689,24 @@ static unsigned int ata_scsi_pass_thru(struct ata_queued_cmd *qc) if ((tf->protocol = ata_scsi_map_proto(cdb[1])) == ATA_PROT_UNKNOWN) goto invalid_fld; + /* + * Filter TPM commands by default. These provide an + * essentially uncontrolled encrypted "back door" between + * applications and the disk. Set libata.allow_tpm=1 if you + * have a real reason for wanting to use them. This ensures + * that installed software cannot easily mess stuff up without + * user intent. DVR type users will probably ship with this enabled + * for movie content management. + * + * Note that for ATA8 we can issue a DCS change and DCS freeze lock + * for this and should do in future but that it is not sufficient as + * DCS is an optional feature set. Thus we also do the software filter + * so that we comply with the TC consortium stated goal that the user + * can turn off TC features of their system. + */ + if (tf->command >= 0x5C && tf->command <= 0x5F && !libata_allow_tpm) + goto invalid_fld; + /* We may not issue DMA commands if no DMA mode is set */ if (tf->protocol == ATA_PROT_DMA && dev->dma_mode == 0) goto invalid_fld; diff --git a/drivers/ata/libata-sff.c b/drivers/ata/libata-sff.c index 48acc09..fb69476 100644 --- a/drivers/ata/libata-sff.c +++ b/drivers/ata/libata-sff.c @@ -147,7 +147,9 @@ void ata_exec_command(struct ata_port *ap, const struct ata_taskfile *tf) * @tf: ATA taskfile register set for storing input * * Reads ATA taskfile registers for currently-selected device - * into @tf. + * into @tf. Assumes the device has a fully SFF compliant task file + * layout and behaviour. If you device does not (eg has a different + * status method) then you will need to provide a replacement tf_read * * LOCKING: * Inherited from caller. @@ -156,7 +158,7 @@ void ata_tf_read(struct ata_port *ap, struct ata_taskfile *tf) { struct ata_ioports *ioaddr = &ap->ioaddr; - tf->command = ata_chk_status(ap); + tf->command = ata_check_status(ap); tf->feature = ioread8(ioaddr->error_addr); tf->nsect = ioread8(ioaddr->nsect_addr); tf->lbal = ioread8(ioaddr->lbal_addr); diff --git a/drivers/ata/libata.h b/drivers/ata/libata.h index 0e6cf3a..f8ab11e 100644 --- a/drivers/ata/libata.h +++ b/drivers/ata/libata.h @@ -60,6 +60,7 @@ extern int atapi_dmadir; extern int atapi_passthru16; extern int libata_fua; extern int libata_noacpi; +extern int libata_allow_tpm; extern struct ata_queued_cmd *ata_qc_new_init(struct ata_device *dev); extern int ata_build_rw_tf(struct ata_taskfile *tf, struct ata_device *dev, u64 block, u32 n_block, unsigned int tf_flags, @@ -85,7 +86,6 @@ extern int ata_dev_configure(struct ata_device *dev); extern int sata_down_spd_limit(struct ata_link *link); extern int sata_set_spd_needed(struct ata_link *link); extern int ata_down_xfermask_limit(struct ata_device *dev, unsigned int sel); -extern int ata_set_mode(struct ata_link *link, struct ata_device **r_failed_dev); extern void ata_sg_clean(struct ata_queued_cmd *qc); extern void ata_qc_free(struct ata_queued_cmd *qc); extern void ata_qc_issue(struct ata_queued_cmd *qc); @@ -111,12 +111,15 @@ extern void ata_acpi_associate(struct ata_host *host); extern int ata_acpi_on_suspend(struct ata_port *ap); extern void ata_acpi_on_resume(struct ata_port *ap); extern int ata_acpi_on_devcfg(struct ata_device *adev); +extern void ata_acpi_set_state(struct ata_port *ap, pm_message_t state); #else static inline void ata_acpi_associate_sata_port(struct ata_port *ap) { } static inline void ata_acpi_associate(struct ata_host *host) { } static inline int ata_acpi_on_suspend(struct ata_port *ap) { return 0; } static inline void ata_acpi_on_resume(struct ata_port *ap) { } static inline int ata_acpi_on_devcfg(struct ata_device *adev) { return 0; } +static inline void ata_acpi_set_state(struct ata_port *ap, + pm_message_t state) { } #endif /* libata-scsi.c */ @@ -179,6 +182,7 @@ extern void ata_eh_report(struct ata_port *ap); extern int ata_eh_reset(struct ata_link *link, int classify, ata_prereset_fn_t prereset, ata_reset_fn_t softreset, ata_reset_fn_t hardreset, ata_postreset_fn_t postreset); +extern int ata_set_mode(struct ata_link *link, struct ata_device **r_failed_dev); extern int ata_eh_recover(struct ata_port *ap, ata_prereset_fn_t prereset, ata_reset_fn_t softreset, ata_reset_fn_t hardreset, ata_postreset_fn_t postreset, diff --git a/drivers/ata/pata_acpi.c b/drivers/ata/pata_acpi.c index e4542ab..244098a 100644 --- a/drivers/ata/pata_acpi.c +++ b/drivers/ata/pata_acpi.c @@ -81,17 +81,6 @@ static void pacpi_error_handler(struct ata_port *ap) NULL, ata_std_postreset); } -/* Welcome to ACPI, bring a bucket */ -static const unsigned int pio_cycle[7] = { - 600, 383, 240, 180, 120, 100, 80 -}; -static const unsigned int mwdma_cycle[5] = { - 480, 150, 120, 100, 80 -}; -static const unsigned int udma_cycle[7] = { - 120, 80, 60, 45, 30, 20, 15 -}; - /** * pacpi_discover_modes - filter non ACPI modes * @adev: ATA device @@ -103,56 +92,20 @@ static const unsigned int udma_cycle[7] = { static unsigned long pacpi_discover_modes(struct ata_port *ap, struct ata_device *adev) { - int unit = adev->devno; struct pata_acpi *acpi = ap->private_data; - int i; - u32 t; - unsigned long mask = (0x7f << ATA_SHIFT_UDMA) | (0x7 << ATA_SHIFT_MWDMA) | (0x1F << ATA_SHIFT_PIO); - struct ata_acpi_gtm probe; + unsigned int xfer_mask; probe = acpi->gtm; - /* We always use the 0 slot for crap hardware */ - if (!(probe.flags & 0x10)) - unit = 0; - ata_acpi_gtm(ap, &probe); - /* Start by scanning for PIO modes */ - for (i = 0; i < 7; i++) { - t = probe.drive[unit].pio; - if (t <= pio_cycle[i]) { - mask |= (2 << (ATA_SHIFT_PIO + i)) - 1; - break; - } - } + xfer_mask = ata_acpi_gtm_xfermask(adev, &probe); - /* See if we have MWDMA or UDMA data. We don't bother with MWDMA - if UDMA is availabe as this means the BIOS set UDMA and our - error changedown if it works is UDMA to PIO anyway */ - if (probe.flags & (1 << (2 * unit))) { - /* MWDMA */ - for (i = 0; i < 5; i++) { - t = probe.drive[unit].dma; - if (t <= mwdma_cycle[i]) { - mask |= (2 << (ATA_SHIFT_MWDMA + i)) - 1; - break; - } - } - } else { - /* UDMA */ - for (i = 0; i < 7; i++) { - t = probe.drive[unit].dma; - if (t <= udma_cycle[i]) { - mask |= (2 << (ATA_SHIFT_UDMA + i)) - 1; - break; - } - } - } - if (mask & (0xF8 << ATA_SHIFT_UDMA)) + if (xfer_mask & (0xF8 << ATA_SHIFT_UDMA)) ap->cbl = ATA_CBL_PATA80; - return mask; + + return xfer_mask; } /** @@ -180,12 +133,14 @@ static void pacpi_set_piomode(struct ata_port *ap, struct ata_device *adev) { int unit = adev->devno; struct pata_acpi *acpi = ap->private_data; + const struct ata_timing *t; if (!(acpi->gtm.flags & 0x10)) unit = 0; /* Now stuff the nS values into the structure */ - acpi->gtm.drive[unit].pio = pio_cycle[adev->pio_mode - XFER_PIO_0]; + t = ata_timing_find_mode(adev->pio_mode); + acpi->gtm.drive[unit].pio = t->cycle; ata_acpi_stm(ap, &acpi->gtm); /* See what mode we actually got */ ata_acpi_gtm(ap, &acpi->gtm); @@ -201,16 +156,18 @@ static void pacpi_set_dmamode(struct ata_port *ap, struct ata_device *adev) { int unit = adev->devno; struct pata_acpi *acpi = ap->private_data; + const struct ata_timing *t; if (!(acpi->gtm.flags & 0x10)) unit = 0; /* Now stuff the nS values into the structure */ + t = ata_timing_find_mode(adev->dma_mode); if (adev->dma_mode >= XFER_UDMA_0) { - acpi->gtm.drive[unit].dma = udma_cycle[adev->dma_mode - XFER_UDMA_0]; + acpi->gtm.drive[unit].dma = t->udma; acpi->gtm.flags |= (1 << (2 * unit)); } else { - acpi->gtm.drive[unit].dma = mwdma_cycle[adev->dma_mode - XFER_MW_DMA_0]; + acpi->gtm.drive[unit].dma = t->cycle; acpi->gtm.flags &= ~(1 << (2 * unit)); } ata_acpi_stm(ap, &acpi->gtm); diff --git a/drivers/ata/pata_ali.c b/drivers/ata/pata_ali.c index 8caf9af..7e68edf 100644 --- a/drivers/ata/pata_ali.c +++ b/drivers/ata/pata_ali.c @@ -64,7 +64,7 @@ static int ali_cable_override(struct pci_dev *pdev) if (pdev->subsystem_vendor == 0x10CF && pdev->subsystem_device == 0x10AF) return 1; /* Mitac 8317 (Winbook-A) and relatives */ - if (pdev->subsystem_vendor == 0x1071 && pdev->subsystem_device == 0x8317) + if (pdev->subsystem_vendor == 0x1071 && pdev->subsystem_device == 0x8317) return 1; /* Systems by DMI */ if (dmi_check_system(cable_dmi_table)) diff --git a/drivers/ata/pata_amd.c b/drivers/ata/pata_amd.c index 3cc27b5..761a666 100644 --- a/drivers/ata/pata_amd.c +++ b/drivers/ata/pata_amd.c @@ -220,6 +220,62 @@ static void amd133_set_dmamode(struct ata_port *ap, struct ata_device *adev) timing_setup(ap, adev, 0x40, adev->dma_mode, 4); } +/* Both host-side and drive-side detection results are worthless on NV + * PATAs. Ignore them and just follow what BIOS configured. Both the + * current configuration in PCI config reg and ACPI GTM result are + * cached during driver attach and are consulted to select transfer + * mode. + */ +static unsigned long nv_mode_filter(struct ata_device *dev, + unsigned long xfer_mask) +{ + static const unsigned int udma_mask_map[] = + { ATA_UDMA2, ATA_UDMA1, ATA_UDMA0, 0, + ATA_UDMA3, ATA_UDMA4, ATA_UDMA5, ATA_UDMA6 }; + struct ata_port *ap = dev->link->ap; + char acpi_str[32] = ""; + u32 saved_udma, udma; + const struct ata_acpi_gtm *gtm; + unsigned long bios_limit = 0, acpi_limit = 0, limit; + + /* find out what BIOS configured */ + udma = saved_udma = (unsigned long)ap->host->private_data; + + if (ap->port_no == 0) + udma >>= 16; + if (dev->devno == 0) + udma >>= 8; + + if ((udma & 0xc0) == 0xc0) + bios_limit = ata_pack_xfermask(0, 0, udma_mask_map[udma & 0x7]); + + /* consult ACPI GTM too */ + gtm = ata_acpi_init_gtm(ap); + if (gtm) { + acpi_limit = ata_acpi_gtm_xfermask(dev, gtm); + + snprintf(acpi_str, sizeof(acpi_str), " (%u:%u:0x%x)", + gtm->drive[0].dma, gtm->drive[1].dma, gtm->flags); + } + + /* be optimistic, EH can take care of things if something goes wrong */ + limit = bios_limit | acpi_limit; + + /* If PIO or DMA isn't configured at all, don't limit. Let EH + * handle it. + */ + if (!(limit & ATA_MASK_PIO)) + limit |= ATA_MASK_PIO; + if (!(limit & (ATA_MASK_MWDMA | ATA_MASK_UDMA))) + limit |= ATA_MASK_MWDMA | ATA_MASK_UDMA; + + ata_port_printk(ap, KERN_DEBUG, "nv_mode_filter: 0x%lx&0x%lx->0x%lx, " + "BIOS=0x%lx (0x%x) ACPI=0x%lx%s\n", + xfer_mask, limit, xfer_mask & limit, bios_limit, + saved_udma, acpi_limit, acpi_str); + + return xfer_mask & limit; +} /** * nv_probe_init - cable detection @@ -252,31 +308,6 @@ static void nv_error_handler(struct ata_port *ap) ata_std_postreset); } -static int nv_cable_detect(struct ata_port *ap) -{ - static const u8 bitmask[2] = {0x03, 0x0C}; - struct pci_dev *pdev = to_pci_dev(ap->host->dev); - u8 ata66; - u16 udma; - int cbl; - - pci_read_config_byte(pdev, 0x52, &ata66); - if (ata66 & bitmask[ap->port_no]) - cbl = ATA_CBL_PATA80; - else - cbl = ATA_CBL_PATA40; - - /* We now have to double check because the Nvidia boxes BIOS - doesn't always set the cable bits but does set mode bits */ - pci_read_config_word(pdev, 0x62 - 2 * ap->port_no, &udma); - if ((udma & 0xC4) == 0xC4 || (udma & 0xC400) == 0xC400) - cbl = ATA_CBL_PATA80; - /* And a triple check across suspend/resume with ACPI around */ - if (ata_acpi_cbl_80wire(ap)) - cbl = ATA_CBL_PATA80; - return cbl; -} - /** * nv100_set_piomode - set initial PIO mode data * @ap: ATA interface @@ -314,6 +345,14 @@ static void nv133_set_dmamode(struct ata_port *ap, struct ata_device *adev) timing_setup(ap, adev, 0x50, adev->dma_mode, 4); } +static void nv_host_stop(struct ata_host *host) +{ + u32 udma = (unsigned long)host->private_data; + + /* restore PCI config register 0x60 */ + pci_write_config_dword(to_pci_dev(host->dev), 0x60, udma); +} + static struct scsi_host_template amd_sht = { .module = THIS_MODULE, .name = DRV_NAME, @@ -478,7 +517,8 @@ static struct ata_port_operations nv100_port_ops = { .thaw = ata_bmdma_thaw, .error_handler = nv_error_handler, .post_internal_cmd = ata_bmdma_post_internal_cmd, - .cable_detect = nv_cable_detect, + .cable_detect = ata_cable_ignore, + .mode_filter = nv_mode_filter, .bmdma_setup = ata_bmdma_setup, .bmdma_start = ata_bmdma_start, @@ -495,6 +535,7 @@ static struct ata_port_operations nv100_port_ops = { .irq_on = ata_irq_on, .port_start = ata_sff_port_start, + .host_stop = nv_host_stop, }; static struct ata_port_operations nv133_port_ops = { @@ -511,7 +552,8 @@ static struct ata_port_operations nv133_port_ops = { .thaw = ata_bmdma_thaw, .error_handler = nv_error_handler, .post_internal_cmd = ata_bmdma_post_internal_cmd, - .cable_detect = nv_cable_detect, + .cable_detect = ata_cable_ignore, + .mode_filter = nv_mode_filter, .bmdma_setup = ata_bmdma_setup, .bmdma_start = ata_bmdma_start, @@ -528,6 +570,7 @@ static struct ata_port_operations nv133_port_ops = { .irq_on = ata_irq_on, .port_start = ata_sff_port_start, + .host_stop = nv_host_stop, }; static int amd_init_one(struct pci_dev *pdev, const struct pci_device_id *id) @@ -614,7 +657,8 @@ static int amd_init_one(struct pci_dev *pdev, const struct pci_device_id *id) .port_ops = &amd100_port_ops } }; - const struct ata_port_info *ppi[] = { NULL, NULL }; + struct ata_port_info pi; + const struct ata_port_info *ppi[] = { &pi, NULL }; static int printed_version; int type = id->driver_data; u8 fifo; @@ -628,6 +672,19 @@ static int amd_init_one(struct pci_dev *pdev, const struct pci_device_id *id) if (type == 1 && pdev->revision > 0x7) type = 2; + /* Serenade ? */ + if (type == 5 && pdev->subsystem_vendor == PCI_VENDOR_ID_AMD && + pdev->subsystem_device == PCI_DEVICE_ID_AMD_SERENADE) + type = 6; /* UDMA 100 only */ + + /* + * Okay, type is determined now. Apply type-specific workarounds. + */ + pi = info[type]; + + if (type < 3) + ata_pci_clear_simplex(pdev); + /* Check for AMD7411 */ if (type == 3) /* FIFO is broken */ @@ -635,16 +692,17 @@ static int amd_init_one(struct pci_dev *pdev, const struct pci_device_id *id) else pci_write_config_byte(pdev, 0x41, fifo | 0xF0); - /* Serenade ? */ - if (type == 5 && pdev->subsystem_vendor == PCI_VENDOR_ID_AMD && - pdev->subsystem_device == PCI_DEVICE_ID_AMD_SERENADE) - type = 6; /* UDMA 100 only */ + /* Cable detection on Nvidia chips doesn't work too well, + * cache BIOS programmed UDMA mode. + */ + if (type == 7 || type == 8) { + u32 udma; - if (type < 3) - ata_pci_clear_simplex(pdev); + pci_read_config_dword(pdev, 0x60, &udma); + pi.private_data = (void *)(unsigned long)udma; + } /* And fire it up */ - ppi[0] = &info[type]; return ata_pci_init_one(pdev, ppi); } diff --git a/drivers/ata/pata_it821x.c b/drivers/ata/pata_it821x.c index ca9aae0..109ddd4 100644 --- a/drivers/ata/pata_it821x.c +++ b/drivers/ata/pata_it821x.c @@ -430,7 +430,7 @@ static unsigned int it821x_smart_qc_issue_prot(struct ata_queued_cmd *qc) return ata_qc_issue_prot(qc); } printk(KERN_DEBUG "it821x: can't process command 0x%02X\n", qc->tf.command); - return AC_ERR_INVALID; + return AC_ERR_DEV; } /** @@ -516,6 +516,37 @@ static void it821x_dev_config(struct ata_device *adev) printk("(%dK stripe)", adev->id[146]); printk(".\n"); } + /* This is a controller firmware triggered funny, don't + report the drive faulty! */ + adev->horkage &= ~ATA_HORKAGE_DIAGNOSTIC; +} + +/** + * it821x_ident_hack - Hack identify data up + * @ap: Port + * + * Walk the devices on this firmware driven port and slightly + * mash the identify data to stop us and common tools trying to + * use features not firmware supported. The firmware itself does + * some masking (eg SMART) but not enough. + * + * This is a bit of an abuse of the cable method, but it is the + * only method called at the right time. We could modify the libata + * core specifically for ident hacking but while we have one offender + * it seems better to keep the fallout localised. + */ + +static int it821x_ident_hack(struct ata_port *ap) +{ + struct ata_device *adev; + ata_link_for_each_dev(adev, &ap->link) { + if (ata_dev_enabled(adev)) { + adev->id[84] &= ~(1 << 6); /* No FUA */ + adev->id[85] &= ~(1 << 10); /* No HPA */ + adev->id[76] = 0; /* No NCQ/AN etc */ + } + } + return ata_cable_unknown(ap); } @@ -634,7 +665,7 @@ static struct ata_port_operations it821x_smart_port_ops = { .thaw = ata_bmdma_thaw, .error_handler = ata_bmdma_error_handler, .post_internal_cmd = ata_bmdma_post_internal_cmd, - .cable_detect = ata_cable_unknown, + .cable_detect = it821x_ident_hack, .bmdma_setup = ata_bmdma_setup, .bmdma_start = ata_bmdma_start, diff --git a/drivers/ata/pata_ninja32.c b/drivers/ata/pata_ninja32.c new file mode 100644 index 0000000..1c1b835 --- /dev/null +++ b/drivers/ata/pata_ninja32.c @@ -0,0 +1,214 @@ +/* + * pata_ninja32.c - Ninja32 PATA for new ATA layer + * (C) 2007 Red Hat Inc + * Alan Cox + * + * Note: The controller like many controllers has shared timings for + * PIO and DMA. We thus flip to the DMA timings in dma_start and flip back + * in the dma_stop function. Thus we actually don't need a set_dmamode + * method as the PIO method is always called and will set the right PIO + * timing parameters. + * + * The Ninja32 Cardbus is not a generic SFF controller. Instead it is + * laid out as follows off BAR 0. This is based upon Mark Lord's delkin + * driver and the extensive analysis done by the BSD developers, notably + * ITOH Yasufumi. + * + * Base + 0x00 IRQ Status + * Base + 0x01 IRQ control + * Base + 0x02 Chipset control + * Base + 0x04 VDMA and reset control + wait bits + * Base + 0x08 BMIMBA + * Base + 0x0C DMA Length + * Base + 0x10 Taskfile + * Base + 0x18 BMDMA Status ? + * Base + 0x1C + * Base + 0x1D Bus master control + * bit 0 = enable + * bit 1 = 0 write/1 read + * bit 2 = 1 sgtable + * bit 3 = go + * bit 4-6 wait bits + * bit 7 = done + * Base + 0x1E AltStatus + * Base + 0x1F timing register + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#define DRV_NAME "pata_ninja32" +#define DRV_VERSION "0.0.1" + + +/** + * ninja32_set_piomode - set initial PIO mode data + * @ap: ATA interface + * @adev: ATA device + * + * Called to do the PIO mode setup. Our timing registers are shared + * but we want to set the PIO timing by default. + */ + +static void ninja32_set_piomode(struct ata_port *ap, struct ata_device *adev) +{ + static u16 pio_timing[5] = { + 0xd6, 0x85, 0x44, 0x33, 0x13 + }; + iowrite8(pio_timing[adev->pio_mode - XFER_PIO_0], + ap->ioaddr.bmdma_addr + 0x1f); + ap->private_data = adev; +} + + +static void ninja32_dev_select(struct ata_port *ap, unsigned int device) +{ + struct ata_device *adev = &ap->link.device[device]; + if (ap->private_data != adev) { + iowrite8(0xd6, ap->ioaddr.bmdma_addr + 0x1f); + ata_std_dev_select(ap, device); + ninja32_set_piomode(ap, adev); + } +} + +static struct scsi_host_template ninja32_sht = { + .module = THIS_MODULE, + .name = DRV_NAME, + .ioctl = ata_scsi_ioctl, + .queuecommand = ata_scsi_queuecmd, + .can_queue = ATA_DEF_QUEUE, + .this_id = ATA_SHT_THIS_ID, + .sg_tablesize = LIBATA_MAX_PRD, + .cmd_per_lun = ATA_SHT_CMD_PER_LUN, + .emulated = ATA_SHT_EMULATED, + .use_clustering = ATA_SHT_USE_CLUSTERING, + .proc_name = DRV_NAME, + .dma_boundary = ATA_DMA_BOUNDARY, + .slave_configure = ata_scsi_slave_config, + .slave_destroy = ata_scsi_slave_destroy, + .bios_param = ata_std_bios_param, +}; + +static struct ata_port_operations ninja32_port_ops = { + .set_piomode = ninja32_set_piomode, + .mode_filter = ata_pci_default_filter, + + .tf_load = ata_tf_load, + .tf_read = ata_tf_read, + .check_status = ata_check_status, + .exec_command = ata_exec_command, + .dev_select = ninja32_dev_select, + + .freeze = ata_bmdma_freeze, + .thaw = ata_bmdma_thaw, + .error_handler = ata_bmdma_error_handler, + .post_internal_cmd = ata_bmdma_post_internal_cmd, + .cable_detect = ata_cable_40wire, + + .bmdma_setup = ata_bmdma_setup, + .bmdma_start = ata_bmdma_start, + .bmdma_stop = ata_bmdma_stop, + .bmdma_status = ata_bmdma_status, + + .qc_prep = ata_qc_prep, + .qc_issue = ata_qc_issue_prot, + + .data_xfer = ata_data_xfer, + + .irq_handler = ata_interrupt, + .irq_clear = ata_bmdma_irq_clear, + .irq_on = ata_irq_on, + + .port_start = ata_sff_port_start, +}; + +static int ninja32_init_one(struct pci_dev *dev, const struct pci_device_id *id) +{ + struct ata_host *host; + struct ata_port *ap; + void __iomem *base; + int rc; + + host = ata_host_alloc(&dev->dev, 1); + if (!host) + return -ENOMEM; + ap = host->ports[0]; + + /* Set up the PCI device */ + rc = pcim_enable_device(dev); + if (rc) + return rc; + rc = pcim_iomap_regions(dev, 1 << 0, DRV_NAME); + if (rc == -EBUSY) + pcim_pin_device(dev); + if (rc) + return rc; + + host->iomap = pcim_iomap_table(dev); + rc = pci_set_dma_mask(dev, ATA_DMA_MASK); + if (rc) + return rc; + rc = pci_set_consistent_dma_mask(dev, ATA_DMA_MASK); + if (rc) + return rc; + pci_set_master(dev); + + /* Set up the register mappings */ + base = host->iomap[0]; + if (!base) + return -ENOMEM; + ap->ops = &ninja32_port_ops; + ap->pio_mask = 0x1F; + ap->flags |= ATA_FLAG_SLAVE_POSS; + + ap->ioaddr.cmd_addr = base + 0x10; + ap->ioaddr.ctl_addr = base + 0x1E; + ap->ioaddr.altstatus_addr = base + 0x1E; + ap->ioaddr.bmdma_addr = base; + ata_std_ports(&ap->ioaddr); + + iowrite8(0x05, base + 0x01); /* Enable interrupt lines */ + iowrite8(0xB3, base + 0x02); /* Burst, ?? setup */ + iowrite8(0x00, base + 0x04); /* WAIT0 ? */ + /* FIXME: Should we disable them at remove ? */ + return ata_host_activate(host, dev->irq, ata_interrupt, + IRQF_SHARED, &ninja32_sht); +} + +static const struct pci_device_id ninja32[] = { + { 0x1145, 0xf021, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 }, + { 0x1145, 0xf024, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 }, + { }, +}; + +static struct pci_driver ninja32_pci_driver = { + .name = DRV_NAME, + .id_table = ninja32, + .probe = ninja32_init_one, + .remove = ata_pci_remove_one +}; + +static int __init ninja32_init(void) +{ + return pci_register_driver(&ninja32_pci_driver); +} + +static void __exit ninja32_exit(void) +{ + pci_unregister_driver(&ninja32_pci_driver); +} + +MODULE_AUTHOR("Alan Cox"); +MODULE_DESCRIPTION("low-level driver for Ninja32 ATA"); +MODULE_LICENSE("GPL"); +MODULE_DEVICE_TABLE(pci, ninja32); +MODULE_VERSION(DRV_VERSION); + +module_init(ninja32_init); +module_exit(ninja32_exit); diff --git a/drivers/ata/pata_pcmcia.c b/drivers/ata/pata_pcmcia.c index fd36099..bbd4d70 100644 --- a/drivers/ata/pata_pcmcia.c +++ b/drivers/ata/pata_pcmcia.c @@ -86,6 +86,44 @@ static int pcmcia_set_mode(struct ata_link *link, struct ata_device **r_failed_d return ata_do_set_mode(link, r_failed_dev); } +/** + * pcmcia_set_mode_8bit - PCMCIA specific mode setup + * @link: link + * @r_failed_dev: Return pointer for failed device + * + * For the simple emulated 8bit stuff the less we do the better. + */ + +static int pcmcia_set_mode_8bit(struct ata_link *link, + struct ata_device **r_failed_dev) +{ + return 0; +} + +/** + * ata_data_xfer_8bit - Transfer data by 8bit PIO + * @adev: device to target + * @buf: data buffer + * @buflen: buffer length + * @write_data: read/write + * + * Transfer data from/to the device data register by 8 bit PIO. + * + * LOCKING: + * Inherited from caller. + */ + +static void ata_data_xfer_8bit(struct ata_device *adev, unsigned char *buf, + unsigned int buflen, int write_data) +{ + struct ata_port *ap = adev->link->ap; + if (write_data) + iowrite8_rep(ap->ioaddr.data_addr, buf, buflen); + else + ioread8_rep(ap->ioaddr.data_addr, buf, buflen); +} + + static struct scsi_host_template pcmcia_sht = { .module = THIS_MODULE, .name = DRV_NAME, @@ -129,12 +167,38 @@ static struct ata_port_operations pcmcia_port_ops = { .port_start = ata_sff_port_start, }; +static struct ata_port_operations pcmcia_8bit_port_ops = { + .set_mode = pcmcia_set_mode_8bit, + .tf_load = ata_tf_load, + .tf_read = ata_tf_read, + .check_status = ata_check_status, + .exec_command = ata_exec_command, + .dev_select = ata_std_dev_select, + + .freeze = ata_bmdma_freeze, + .thaw = ata_bmdma_thaw, + .error_handler = ata_bmdma_error_handler, + .post_internal_cmd = ata_bmdma_post_internal_cmd, + .cable_detect = ata_cable_40wire, + + .qc_prep = ata_qc_prep, + .qc_issue = ata_qc_issue_prot, + + .data_xfer = ata_data_xfer_8bit, + + .irq_clear = ata_bmdma_irq_clear, + .irq_on = ata_irq_on, + + .port_start = ata_sff_port_start, +}; + #define CS_CHECK(fn, ret) \ do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) /** * pcmcia_init_one - attach a PCMCIA interface * @pdev: pcmcia device + * @ops: operations for this device * * Register a PCMCIA IDE interface. Such interfaces are PIO 0 and * shared IRQ. @@ -157,6 +221,8 @@ static int pcmcia_init_one(struct pcmcia_device *pdev) unsigned long io_base, ctl_base; void __iomem *io_addr, *ctl_addr; + struct ata_port_operations *ops = &pcmcia_port_ops; + info = kzalloc(sizeof(*info), GFP_KERNEL); if (info == NULL) return -ENOMEM; @@ -284,6 +350,8 @@ next_entry: if (pdev->io.NumPorts1 >= 0x20) printk(KERN_WARNING DRV_NAME ": second channel not yet supported.\n"); + if (pdev->manf_id == 0x0097 && pdev->card_id == 0x1620) + ops = &pcmcia_8bit_port_ops; /* * Having done the PCMCIA plumbing the ATA side is relatively * sane. @@ -294,7 +362,7 @@ next_entry: goto failed; ap = host->ports[0]; - ap->ops = &pcmcia_port_ops; + ap->ops = ops; ap->pio_mask = 1; /* ISA so PIO 0 cycles */ ap->flags |= ATA_FLAG_SLAVE_POSS; ap->ioaddr.cmd_addr = io_addr; @@ -360,6 +428,7 @@ static struct pcmcia_device_id pcmcia_devices[] = { PCMCIA_DEVICE_MANF_CARD(0x0032, 0x0704), PCMCIA_DEVICE_MANF_CARD(0x0032, 0x2904), PCMCIA_DEVICE_MANF_CARD(0x0045, 0x0401), /* SanDisk CFA */ + PCMCIA_DEVICE_MANF_CARD(0x0097, 0x1620), /* TI emulated */ PCMCIA_DEVICE_MANF_CARD(0x0098, 0x0000), /* Toshiba */ PCMCIA_DEVICE_MANF_CARD(0x00a4, 0x002d), PCMCIA_DEVICE_MANF_CARD(0x00ce, 0x0000), /* Samsung */ diff --git a/drivers/ata/pata_via.c b/drivers/ata/pata_via.c index 453d72b..39627ab 100644 --- a/drivers/ata/pata_via.c +++ b/drivers/ata/pata_via.c @@ -185,7 +185,8 @@ static int via_cable_detect(struct ata_port *ap) { if (ata66 & (0x10100000 >> (16 * ap->port_no))) return ATA_CBL_PATA80; /* Check with ACPI so we can spot BIOS reported SATA bridges */ - if (ata_acpi_cbl_80wire(ap)) + if (ata_acpi_init_gtm(ap) && + ata_acpi_cbl_80wire(ap, ata_acpi_init_gtm(ap))) return ATA_CBL_PATA80; return ATA_CBL_PATA40; } diff --git a/drivers/ata/sata_fsl.c b/drivers/ata/sata_fsl.c index d015b4a..a3c33f1 100644 --- a/drivers/ata/sata_fsl.c +++ b/drivers/ata/sata_fsl.c @@ -417,7 +417,7 @@ static void sata_fsl_qc_prep(struct ata_queued_cmd *qc) } /* setup "ACMD - atapi command" in cmd. desc. if this is ATAPI cmd */ - if (is_atapi_taskfile(&qc->tf)) { + if (ata_is_atapi(qc->tf.protocol)) { desc_info |= ATAPI_CMD; memset((void *)&cd->acmd, 0, 32); memcpy((void *)&cd->acmd, qc->cdb, qc->dev->cdb_len); diff --git a/drivers/ata/sata_promise.c b/drivers/ata/sata_promise.c index 7914def..9638faa 100644 --- a/drivers/ata/sata_promise.c +++ b/drivers/ata/sata_promise.c @@ -450,7 +450,7 @@ static void pdc_atapi_pkt(struct ata_queued_cmd *qc) struct pdc_port_priv *pp = ap->private_data; u8 *buf = pp->pkt; u32 *buf32 = (u32 *) buf; - unsigned int dev_sel, feature, nbytes; + unsigned int dev_sel, feature; /* set control bits (byte 0), zero delay seq id (byte 3), * and seq id (byte 2) @@ -473,45 +473,37 @@ static void pdc_atapi_pkt(struct ata_queued_cmd *qc) buf32[2] = 0; /* no next-packet */ /* select drive */ - if (sata_scr_valid(&ap->link)) { + if (sata_scr_valid(&ap->link)) dev_sel = PDC_DEVICE_SATA; - } else { - dev_sel = ATA_DEVICE_OBS; - if (qc->dev->devno != 0) - dev_sel |= ATA_DEV1; - } + else + dev_sel = qc->tf.device; + buf[12] = (1 << 5) | ATA_REG_DEVICE; buf[13] = dev_sel; buf[14] = (1 << 5) | ATA_REG_DEVICE | PDC_PKT_CLEAR_BSY; buf[15] = dev_sel; /* once more, waiting for BSY to clear */ buf[16] = (1 << 5) | ATA_REG_NSECT; - buf[17] = 0x00; + buf[17] = qc->tf.nsect; buf[18] = (1 << 5) | ATA_REG_LBAL; - buf[19] = 0x00; + buf[19] = qc->tf.lbal; /* set feature and byte counter registers */ - if (qc->tf.protocol != ATA_PROT_ATAPI_DMA) { + if (qc->tf.protocol != ATA_PROT_ATAPI_DMA) feature = PDC_FEATURE_ATAPI_PIO; - /* set byte counter register to real transfer byte count */ - nbytes = qc->nbytes; - if (nbytes > 0xffff) - nbytes = 0xffff; - } else { + else feature = PDC_FEATURE_ATAPI_DMA; - /* set byte counter register to 0 */ - nbytes = 0; - } + buf[20] = (1 << 5) | ATA_REG_FEATURE; buf[21] = feature; buf[22] = (1 << 5) | ATA_REG_BYTEL; - buf[23] = nbytes & 0xFF; + buf[23] = qc->tf.lbam; buf[24] = (1 << 5) | ATA_REG_BYTEH; - buf[25] = (nbytes >> 8) & 0xFF; + buf[25] = qc->tf.lbah; /* send ATAPI packet command 0xA0 */ buf[26] = (1 << 5) | ATA_REG_CMD; - buf[27] = ATA_CMD_PACKET; + buf[27] = qc->tf.command; /* select drive and check DRQ */ buf[28] = (1 << 5) | ATA_REG_DEVICE | PDC_PKT_WAIT_DRDY; diff --git a/drivers/ata/sata_sil.c b/drivers/ata/sata_sil.c index 4e6e381..4f31481 100644 --- a/drivers/ata/sata_sil.c +++ b/drivers/ata/sata_sil.c @@ -420,15 +420,14 @@ static void sil_host_intr(struct ata_port *ap, u32 bmdma2) */ /* Check the ATA_DFLAG_CDB_INTR flag is enough here. - * The flag was turned on only for atapi devices. - * No need to check is_atapi_taskfile(&qc->tf) again. + * The flag was turned on only for atapi devices. No + * need to check ata_is_atapi(qc->tf.protocol) again. */ if (!(qc->dev->flags & ATA_DFLAG_CDB_INTR)) goto err_hsm; break; case HSM_ST_LAST: - if (qc->tf.protocol == ATA_PROT_DMA || - qc->tf.protocol == ATA_PROT_ATAPI_DMA) { + if (ata_is_dma(qc->tf.protocol)) { /* clear DMA-Start bit */ ap->ops->bmdma_stop(qc); @@ -455,8 +454,7 @@ static void sil_host_intr(struct ata_port *ap, u32 bmdma2) /* kick HSM in the ass */ ata_hsm_move(ap, qc, status, 0); - if (unlikely(qc->err_mask) && (qc->tf.protocol == ATA_PROT_DMA || - qc->tf.protocol == ATA_PROT_ATAPI_DMA)) + if (unlikely(qc->err_mask) && ata_is_dma(qc->tf.protocol)) ata_ehi_push_desc(ehi, "BMDMA2 stat 0x%x", bmdma2); return; diff --git a/drivers/ata/sata_sil24.c b/drivers/ata/sata_sil24.c index 96fd526..4f25209 100644 --- a/drivers/ata/sata_sil24.c +++ b/drivers/ata/sata_sil24.c @@ -831,10 +831,6 @@ static int sil24_qc_defer(struct ata_queued_cmd *qc) { struct ata_link *link = qc->dev->link; struct ata_port *ap = link->ap; - u8 prot = qc->tf.protocol; - int is_atapi = (prot == ATA_PROT_ATAPI || - prot == ATA_PROT_ATAPI_NODATA || - prot == ATA_PROT_ATAPI_DMA); /* ATAPI commands completing with CHECK_SENSE cause various * weird problems if other commands are active. PMP DMA CS @@ -849,7 +845,7 @@ static int sil24_qc_defer(struct ata_queued_cmd *qc) qc->flags |= ATA_QCFLAG_CLEAR_EXCL; } else return ATA_DEFER_PORT; - } else if (unlikely(is_atapi)) { + } else if (unlikely(ata_is_atapi(qc->tf.protocol))) { ap->excl_link = link; if (ap->nr_active_links) return ATA_DEFER_PORT; @@ -870,35 +866,21 @@ static void sil24_qc_prep(struct ata_queued_cmd *qc) cb = &pp->cmd_block[sil24_tag(qc->tag)]; - switch (qc->tf.protocol) { - case ATA_PROT_PIO: - case ATA_PROT_DMA: - case ATA_PROT_NCQ: - case ATA_PROT_NODATA: + if (!ata_is_atapi(qc->tf.protocol)) { prb = &cb->ata.prb; sge = cb->ata.sge; - break; - - case ATA_PROT_ATAPI: - case ATA_PROT_ATAPI_DMA: - case ATA_PROT_ATAPI_NODATA: + } else { prb = &cb->atapi.prb; sge = cb->atapi.sge; memset(cb->atapi.cdb, 0, 32); memcpy(cb->atapi.cdb, qc->cdb, qc->dev->cdb_len); - if (qc->tf.protocol != ATA_PROT_ATAPI_NODATA) { + if (ata_is_data(qc->tf.protocol)) { if (qc->tf.flags & ATA_TFLAG_WRITE) ctrl = PRB_CTRL_PACKET_WRITE; else ctrl = PRB_CTRL_PACKET_READ; } - break; - - default: - prb = NULL; /* shut up, gcc */ - sge = NULL; - BUG(); } prb->ctrl = cpu_to_le16(ctrl); diff --git a/drivers/ata/sata_sx4.c b/drivers/ata/sata_sx4.c index 4d85718..187bdcf 100644 --- a/drivers/ata/sata_sx4.c +++ b/drivers/ata/sata_sx4.c @@ -213,8 +213,9 @@ struct pdc_host_priv { static int pdc_sata_init_one(struct pci_dev *pdev, const struct pci_device_id *ent); -static void pdc_eng_timeout(struct ata_port *ap); -static void pdc_20621_phy_reset(struct ata_port *ap); +static void pdc_error_handler(struct ata_port *ap); +static void pdc_freeze(struct ata_port *ap); +static void pdc_thaw(struct ata_port *ap); static int pdc_port_start(struct ata_port *ap); static void pdc20621_qc_prep(struct ata_queued_cmd *qc); static void pdc_tf_load_mmio(struct ata_port *ap, const struct ata_taskfile *tf); @@ -259,11 +260,12 @@ static const struct ata_port_operations pdc_20621_ops = { .check_status = ata_check_status, .exec_command = pdc_exec_command_mmio, .dev_select = ata_std_dev_select, - .phy_reset = pdc_20621_phy_reset, .qc_prep = pdc20621_qc_prep, .qc_issue = pdc20621_qc_issue_prot, .data_xfer = ata_data_xfer, - .eng_timeout = pdc_eng_timeout, + .freeze = pdc_freeze, + .thaw = pdc_thaw, + .error_handler = pdc_error_handler, .irq_clear = pdc20621_irq_clear, .irq_on = ata_irq_on, .port_start = pdc_port_start, @@ -320,14 +322,6 @@ static int pdc_port_start(struct ata_port *ap) return 0; } -static void pdc_20621_phy_reset(struct ata_port *ap) -{ - VPRINTK("ENTER\n"); - ap->cbl = ATA_CBL_SATA; - ata_port_probe(ap); - ata_bus_reset(ap); -} - static inline void pdc20621_ata_sg(struct ata_taskfile *tf, u8 *buf, unsigned int portno, unsigned int total_len) @@ -868,40 +862,70 @@ static irqreturn_t pdc20621_interrupt(int irq, void *dev_instance) return IRQ_RETVAL(handled); } -static void pdc_eng_timeout(struct ata_port *ap) +static void pdc_freeze(struct ata_port *ap) { - u8 drv_stat; - struct ata_host *host = ap->host; - struct ata_queued_cmd *qc; - unsigned long flags; + void __iomem *mmio = ap->ioaddr.cmd_addr; + u32 tmp; - DPRINTK("ENTER\n"); + /* FIXME: this should handle HDMA copy engine freezing */ - spin_lock_irqsave(&host->lock, flags); + tmp = readl(mmio + PDC_CTLSTAT); + tmp |= PDC_MASK_INT; + tmp &= ~PDC_DMA_ENABLE; + writel(tmp, mmio + PDC_CTLSTAT); + readl(mmio + PDC_CTLSTAT); /* flush */ +} - qc = ata_qc_from_tag(ap, ap->link.active_tag); +static void pdc_thaw(struct ata_port *ap) +{ + void __iomem *mmio = ap->ioaddr.cmd_addr; + void __iomem *mmio_base; + u32 tmp; - switch (qc->tf.protocol) { - case ATA_PROT_DMA: - case ATA_PROT_NODATA: - ata_port_printk(ap, KERN_ERR, "command timeout\n"); - qc->err_mask |= __ac_err_mask(ata_wait_idle(ap)); - break; + /* FIXME: this should handle HDMA copy engine thawing */ - default: - drv_stat = ata_busy_wait(ap, ATA_BUSY | ATA_DRQ, 1000); + /* reading SEQ mask register clears IRQ */ + mmio_base = ap->host->iomap[PDC_MMIO_BAR] + PDC_CHIP0_OFS; + readl(mmio_base + PDC_20621_SEQMASK); - ata_port_printk(ap, KERN_ERR, - "unknown timeout, cmd 0x%x stat 0x%x\n", - qc->tf.command, drv_stat); + /* turn IRQ back on */ + tmp = readl(mmio + PDC_CTLSTAT); + tmp &= ~PDC_MASK_INT; + writel(tmp, mmio + PDC_CTLSTAT); + readl(mmio + PDC_CTLSTAT); /* flush */ +} - qc->err_mask |= ac_err_mask(drv_stat); - break; +static void pdc_reset_port(struct ata_port *ap) +{ + void __iomem *mmio = ap->ioaddr.cmd_addr + PDC_CTLSTAT; + unsigned int i; + u32 tmp; + + /* FIXME: handle HDMA copy engine */ + + for (i = 11; i > 0; i--) { + tmp = readl(mmio); + if (tmp & PDC_RESET) + break; + + udelay(100); + + tmp |= PDC_RESET; + writel(tmp, mmio); } - spin_unlock_irqrestore(&host->lock, flags); - ata_eh_qc_complete(qc); - DPRINTK("EXIT\n"); + tmp &= ~PDC_RESET; + writel(tmp, mmio); + readl(mmio); /* flush */ +} + +static void pdc_error_handler(struct ata_port *ap) +{ + if (!(ap->pflags & ATA_PFLAG_FROZEN)) + pdc_reset_port(ap); + + ata_do_eh(ap, ata_std_prereset, ata_std_softreset, NULL, + ata_std_postreset); } static void pdc_tf_load_mmio(struct ata_port *ap, const struct ata_taskfile *tf) diff --git a/drivers/scsi/libsas/sas_ata.c b/drivers/scsi/libsas/sas_ata.c index 0829b55..831294d 100644 --- a/drivers/scsi/libsas/sas_ata.c +++ b/drivers/scsi/libsas/sas_ata.c @@ -176,7 +176,7 @@ static unsigned int sas_ata_qc_issue(struct ata_queued_cmd *qc) ata_tf_to_fis(&qc->tf, 1, 0, (u8*)&task->ata_task.fis); task->uldd_task = qc; - if (is_atapi_taskfile(&qc->tf)) { + if (ata_is_atapi(qc->tf.protocol)) { memcpy(task->ata_task.atapi_packet, qc->cdb, qc->dev->cdb_len); task->total_xfer_len = qc->nbytes + qc->pad_len; task->num_scatter = qc->pad_len ? qc->n_elem + 1 : qc->n_elem; diff --git a/include/linux/ata.h b/include/linux/ata.h index 5c4e54a..3992557 100644 --- a/include/linux/ata.h +++ b/include/linux/ata.h @@ -271,9 +271,10 @@ enum { ATA_CBL_NONE = 0, ATA_CBL_PATA40 = 1, ATA_CBL_PATA80 = 2, - ATA_CBL_PATA40_SHORT = 3, /* 40 wire cable to high UDMA spec */ - ATA_CBL_PATA_UNK = 4, - ATA_CBL_SATA = 5, + ATA_CBL_PATA40_SHORT = 3, /* 40 wire cable to high UDMA spec */ + ATA_CBL_PATA_UNK = 4, /* don't know, maybe 80c? */ + ATA_CBL_PATA_IGN = 5, /* don't know, ignore cable handling */ + ATA_CBL_SATA = 6, /* SATA Status and Control Registers */ SCR_STATUS = 0, @@ -309,6 +310,13 @@ enum { 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 { @@ -358,13 +366,69 @@ struct ata_taskfile { 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 ATA_PROT_ATAPI_NODATA: + return ATA_PROT_FLAG_ATAPI; + case ATA_PROT_ATAPI: + return ATA_PROT_FLAG_ATAPI | ATA_PROT_FLAG_PIO; + case ATA_PROT_ATAPI_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 + */ #define ata_id_is_ata(id) (((id)[0] & (1 << 15)) == 0) #define ata_id_has_lba(id) ((id)[49] & (1 << 9)) #define ata_id_has_dma(id) ((id)[49] & (1 << 8)) #define ata_id_has_ncq(id) ((id)[76] & (1 << 8)) #define ata_id_queue_depth(id) (((id)[75] & 0x1f) + 1) #define ata_id_removeable(id) ((id)[0] & (1 << 7)) -#define ata_id_has_dword_io(id) ((id)[48] & (1 << 0)) #define ata_id_has_atapi_AN(id) \ ( (((id)[76] != 0x0000) && ((id)[76] != 0xffff)) && \ ((id)[78] & (1 << 5)) ) @@ -400,6 +464,7 @@ static inline bool ata_id_has_dipm(const u16 *id) return val & (1 << 3); } + static inline int ata_id_has_fua(const u16 *id) { if ((id[84] & 0xC000) != 0x4000) @@ -504,6 +569,26 @@ static inline int ata_id_is_sata(const u16 *id) return ata_id_major_version(id) >= 5 && id[93] == 0; } +static inline int ata_id_has_tpm(const u16 *id) +{ + /* The TPM bits are only valid on ATA8 */ + if (ata_id_major_version(id) < 8) + return 0; + if ((id[48] & 0xC000) != 0x4000) + return 0; + return id[48] & (1 << 0); +} + +static inline int ata_id_has_dword_io(const u16 *id) +{ + /* ATA 8 reuses this flag for "trusted" computing */ + if (ata_id_major_version(id) > 7) + return 0; + if (id[48] & (1 << 0)) + return 1; + return 0; +} + static inline int ata_id_current_chs_valid(const u16 *id) { /* For ATA-1 devices, if the INITIALIZE DEVICE PARAMETERS command @@ -561,13 +646,6 @@ static inline int atapi_command_packet_set(const u16 *dev_id) return (dev_id[0] >> 8) & 0x1f; } -static inline int is_atapi_taskfile(const struct ata_taskfile *tf) -{ - return (tf->protocol == ATA_PROT_ATAPI) || - (tf->protocol == ATA_PROT_ATAPI_NODATA) || - (tf->protocol == ATA_PROT_ATAPI_DMA); -} - static inline int is_multi_taskfile(struct ata_taskfile *tf) { return (tf->command == ATA_CMD_READ_MULTI) || diff --git a/include/linux/libata.h b/include/linux/libata.h index ef52a07..62d09c8 100644 --- a/include/linux/libata.h +++ b/include/linux/libata.h @@ -141,10 +141,11 @@ enum { ATA_DFLAG_NCQ_OFF = (1 << 13), /* device limited to non-NCQ mode */ ATA_DFLAG_SPUNDOWN = (1 << 14), /* XXX: for spindown_compat */ ATA_DFLAG_SLEEPING = (1 << 15), /* device is sleeping */ - ATA_DFLAG_INIT_MASK = (1 << 16) - 1, + ATA_DFLAG_DUBIOUS_XFER = (1 << 16), /* data transfer not verified */ + ATA_DFLAG_INIT_MASK = (1 << 24) - 1, - ATA_DFLAG_DETACH = (1 << 16), - ATA_DFLAG_DETACHED = (1 << 17), + ATA_DFLAG_DETACH = (1 << 24), + ATA_DFLAG_DETACHED = (1 << 25), ATA_DEV_UNKNOWN = 0, /* unknown device */ ATA_DEV_ATA = 1, /* ATA device */ @@ -212,6 +213,7 @@ enum { ATA_PFLAG_SUSPENDED = (1 << 17), /* port is suspended (power) */ ATA_PFLAG_PM_PENDING = (1 << 18), /* PM operation pending */ ATA_PFLAG_GTM_VALID = (1 << 19), /* acpi_gtm data valid */ + ATA_PFLAG_INIT_GTM_VALID = (1 << 20), /* initial gtm data valid */ /* struct ata_queued_cmd flags */ ATA_QCFLAG_ACTIVE = (1 << 0), /* cmd not yet ack'd to scsi lyer */ @@ -264,19 +266,15 @@ enum { PORT_DISABLED = 2, /* encoding various smaller bitmaps into a single - * unsigned int bitmap + * unsigned long bitmap */ - ATA_BITS_PIO = 7, - ATA_BITS_MWDMA = 5, - ATA_BITS_UDMA = 8, + ATA_NR_PIO_MODES = 7, + ATA_NR_MWDMA_MODES = 5, + ATA_NR_UDMA_MODES = 8, ATA_SHIFT_PIO = 0, - ATA_SHIFT_MWDMA = ATA_SHIFT_PIO + ATA_BITS_PIO, - ATA_SHIFT_UDMA = ATA_SHIFT_MWDMA + ATA_BITS_MWDMA, - - ATA_MASK_PIO = ((1 << ATA_BITS_PIO) - 1) << ATA_SHIFT_PIO, - ATA_MASK_MWDMA = ((1 << ATA_BITS_MWDMA) - 1) << ATA_SHIFT_MWDMA, - ATA_MASK_UDMA = ((1 << ATA_BITS_UDMA) - 1) << ATA_SHIFT_UDMA, + ATA_SHIFT_MWDMA = ATA_SHIFT_PIO + ATA_NR_PIO_MODES, + ATA_SHIFT_UDMA = ATA_SHIFT_MWDMA + ATA_NR_MWDMA_MODES, /* size of buffer to pad xfers ending on unaligned boundaries */ ATA_DMA_PAD_SZ = 4, @@ -349,6 +347,15 @@ enum { ATA_DMA_MASK_CFA = (1 << 2), /* DMA on CF Card */ }; +enum ata_xfer_mask { + ATA_MASK_PIO = ((1LU << ATA_NR_PIO_MODES) - 1) + << ATA_SHIFT_PIO, + ATA_MASK_MWDMA = ((1LU << ATA_NR_MWDMA_MODES) - 1) + << ATA_SHIFT_MWDMA, + ATA_MASK_UDMA = ((1LU << ATA_NR_UDMA_MODES) - 1) + << ATA_SHIFT_UDMA, +}; + enum hsm_task_states { HSM_ST_IDLE, /* no command on going */ HSM_ST_FIRST, /* (waiting the device to) @@ -480,7 +487,7 @@ struct ata_port_stats { }; struct ata_ering_entry { - int is_io; + unsigned int eflags; unsigned int err_mask; u64 timestamp; }; @@ -519,9 +526,9 @@ struct ata_device { unsigned int cdb_len; /* per-dev xfer mask */ - unsigned int pio_mask; - unsigned int mwdma_mask; - unsigned int udma_mask; + unsigned long pio_mask; + unsigned long mwdma_mask; + unsigned long udma_mask; /* for CHS addressing */ u16 cylinders; /* Number of cylinders */ @@ -557,6 +564,8 @@ struct ata_eh_context { int tries[ATA_MAX_DEVICES]; unsigned int classes[ATA_MAX_DEVICES]; unsigned int did_probe_mask; + unsigned int saved_ncq_enabled; + u8 saved_xfer_mode[ATA_MAX_DEVICES]; }; struct ata_acpi_drive @@ -654,6 +663,7 @@ struct ata_port { #ifdef CONFIG_ATA_ACPI acpi_handle acpi_handle; struct ata_acpi_gtm acpi_gtm; + struct ata_acpi_gtm __acpi_init_gtm; /* use ata_acpi_init_gtm() */ #endif u8 sector_buf[ATA_SECT_SIZE]; /* owned by EH */ }; @@ -845,6 +855,16 @@ extern void ata_tf_read(struct ata_port *ap, struct ata_taskfile *tf); extern void ata_tf_to_fis(const struct ata_taskfile *tf, u8 pmp, int is_cmd, u8 *fis); extern void ata_tf_from_fis(const u8 *fis, struct ata_taskfile *tf); +extern unsigned long ata_pack_xfermask(unsigned long pio_mask, + unsigned long mwdma_mask, unsigned long udma_mask); +extern void ata_unpack_xfermask(unsigned long xfer_mask, + unsigned long *pio_mask, unsigned long *mwdma_mask, + unsigned long *udma_mask); +extern u8 ata_xfer_mask2mode(unsigned long xfer_mask); +extern unsigned long ata_xfer_mode2mask(u8 xfer_mode); +extern int ata_xfer_mode2shift(unsigned long xfer_mode); +extern const char *ata_mode_string(unsigned long xfer_mask); +extern unsigned long ata_id_xfermask(const u16 *id); extern void ata_noop_dev_select(struct ata_port *ap, unsigned int device); extern void ata_std_dev_select(struct ata_port *ap, unsigned int device); extern u8 ata_check_status(struct ata_port *ap); @@ -872,7 +892,6 @@ extern void ata_id_string(const u16 *id, unsigned char *s, unsigned int ofs, unsigned int len); extern void ata_id_c_string(const u16 *id, unsigned char *s, unsigned int ofs, unsigned int len); -extern void ata_id_to_dma_mode(struct ata_device *dev, u8 unknown); extern void ata_bmdma_setup(struct ata_queued_cmd *qc); extern void ata_bmdma_start(struct ata_queued_cmd *qc); extern void ata_bmdma_stop(struct ata_queued_cmd *qc); @@ -907,6 +926,7 @@ extern u8 ata_irq_on(struct ata_port *ap); extern int ata_cable_40wire(struct ata_port *ap); extern int ata_cable_80wire(struct ata_port *ap); extern int ata_cable_sata(struct ata_port *ap); +extern int ata_cable_ignore(struct ata_port *ap); extern int ata_cable_unknown(struct ata_port *ap); /* @@ -914,11 +934,13 @@ extern int ata_cable_unknown(struct ata_port *ap); */ extern unsigned int ata_pio_need_iordy(const struct ata_device *); +extern const struct ata_timing *ata_timing_find_mode(u8 xfer_mode); extern int ata_timing_compute(struct ata_device *, unsigned short, struct ata_timing *, int, int); extern void ata_timing_merge(const struct ata_timing *, const struct ata_timing *, struct ata_timing *, unsigned int); +extern u8 ata_timing_cycle2mode(unsigned int xfer_shift, int cycle); enum { ATA_TIMING_SETUP = (1 << 0), @@ -939,11 +961,46 @@ enum { /* libata-acpi.c */ #ifdef CONFIG_ATA_ACPI -extern int ata_acpi_cbl_80wire(struct ata_port *ap); +static inline const struct ata_acpi_gtm *ata_acpi_init_gtm(struct ata_port *ap) +{ + if (ap->pflags & ATA_PFLAG_INIT_GTM_VALID) + return &ap->__acpi_init_gtm; + return NULL; +} int ata_acpi_stm(const struct ata_port *ap, struct ata_acpi_gtm *stm); int ata_acpi_gtm(const 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); +int ata_acpi_cbl_80wire(struct ata_port *ap, const struct ata_acpi_gtm *gtm); #else -static inline int ata_acpi_cbl_80wire(struct ata_port *ap) { return 0; } +static inline const struct ata_acpi_gtm *ata_acpi_init_gtm(struct ata_port *ap) +{ + return NULL; +} + +static inline int ata_acpi_stm(const struct ata_port *ap, + struct ata_acpi_gtm *stm) +{ + return -ENOSYS; +} + +static inline int ata_acpi_gtm(const struct ata_port *ap, + struct ata_acpi_gtm *stm) +{ + return -ENOSYS; +} + +static inline unsigned int ata_acpi_gtm_xfermask(struct ata_device *dev, + const struct ata_acpi_gtm *gtm) +{ + return 0; +} + +static inline int ata_acpi_cbl_80wire(struct ata_port *ap, + const struct ata_acpi_gtm *gtm) +{ + return 0; +} #endif #ifdef CONFIG_PCI @@ -973,7 +1030,8 @@ extern int ata_pci_prepare_sff_host(struct pci_dev *pdev, const struct ata_port_info * const * ppi, struct ata_host **r_host); extern int pci_test_config_bits(struct pci_dev *pdev, const struct pci_bits *bits); -extern unsigned long ata_pci_default_filter(struct ata_device *, unsigned long); +extern unsigned long ata_pci_default_filter(struct ata_device *dev, + unsigned long xfer_mask); #endif /* CONFIG_PCI */ /*