Re: [PATCH 1/2] hpt366: fix PCI clock detection for HPT374
Alan Cox wrote: + if (chip_type == HPT374 (PCI_FUNC(dev-devfn) 1)) { + struct pci_dev *dev1 = pci_get_slot(dev-bus, +dev-devfn - 1); Can be NULL Not really. This may not be called if it's NULL -- see hpt374_init_setup(). Maybe worth a comment though... + unsigned long io_base = pci_resource_start(dev1, 4); Kaboom That was a dud bomb. ;-) What stops a hot unplug of a 374 from causing that to occur. I don't see Pinned as in pci_get_device()? If so, see setup-ide.c:ide_scan_pcibus(). The IDE core does that for me. where you have the other pci_dev pinned on a hotplug on a box set to scan the devices in reverse order Function 1 will always be skipped, regardless of the scan order. (yes its an extremely obscure case ;)) Security through obscurity. :-) MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/4] it8213/piix/slc90e66: de-couple PIO and UDMA modes
Bartlomiej Zolnierkiewicz wrote: Don't force PIO4 when programming UDMA mode (suggested by Sergei). Not sure if it was worth a separte patvh but well... Signed-off-by: Bartlomiej Zolnierkiewicz [EMAIL PROTECTED] Acked-by: Sergei Shtylyov [EMAIL PROTECTED] MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 2/2] pata_hpt{37x|3x2n}: fix clock reporting (take 2)
Fix several inconsistencies in these drivers WRT reporting the clocks: - when using DPLL mode, 'pata_hpt37x' driver reported the DPLL frequency as the PCI clock -- make it properly report both clocks and add the same ability to the 'pata_hpt3x2n' driver; - both drivers sometimes use pata_hpt3*: and sometimes hpt3*: in the messages -- make them use only the former one; - the message about failed DPLL stablizatios deserves KERN_ERR and a bang. :-) Signed-off-by: Sergei Shtylyov [EMAIL PROTECTED] --- This is against the current Linus tree -- with wording in the header fixed. :-) drivers/ata/pata_hpt37x.c | 10 ++ drivers/ata/pata_hpt3x2n.c |8 +--- 2 files changed, 11 insertions(+), 7 deletions(-) Index: linux-2.6/drivers/ata/pata_hpt37x.c === --- linux-2.6.orig/drivers/ata/pata_hpt37x.c +++ linux-2.6/drivers/ata/pata_hpt37x.c @@ -24,7 +24,7 @@ #include linux/libata.h #define DRV_NAME pata_hpt37x -#define DRV_VERSION0.6.8 +#define DRV_VERSION0.6.9 struct hpt_clock { u8 xfer_speed; @@ -1112,7 +1112,7 @@ static int hpt37x_init_one(struct pci_de pci_write_config_dword(dev, 0x5C, (f_high 16) | f_low | 0x100); } if (adjust == 8) { - printk(KERN_WARNING hpt37x: DPLL did not stabilize.\n); + printk(KERN_ERR pata_hpt37x: DPLL did not stabilize!\n); return -ENODEV; } if (dpll == 3) @@ -1120,7 +1120,8 @@ static int hpt37x_init_one(struct pci_de else private_data = (void *)hpt37x_timings_50; - printk(KERN_INFO hpt37x: Bus clock %dMHz, using DPLL.\n, MHz[dpll]); + printk(KERN_INFO pata_hpt37x: bus clock %dMHz, using %dMHz DPLL.\n, + MHz[clock_slot], MHz[dpll]); } else { private_data = (void *)chip_table-clocks[clock_slot]; /* @@ -1133,7 +1134,8 @@ static int hpt37x_init_one(struct pci_de port = info_hpt370_33; if (clock_slot 2 port == info_hpt370a) port = info_hpt370a_33; - printk(KERN_INFO hpt37x: %s: Bus clock %dMHz.\n, chip_table-name, MHz[clock_slot]); + printk(KERN_INFO pata_hpt37x: %s using %dMHz bus clock.\n, + chip_table-name, MHz[clock_slot]); } /* Now kick off ATA set up */ Index: linux-2.6/drivers/ata/pata_hpt3x2n.c === --- linux-2.6.orig/drivers/ata/pata_hpt3x2n.c +++ linux-2.6/drivers/ata/pata_hpt3x2n.c @@ -8,7 +8,7 @@ * Copyright (C) 1999-2003 Andre Hedrick [EMAIL PROTECTED] * Portions Copyright (C) 2001 Sun Microsystems, Inc. * Portions Copyright (C) 2003 Red Hat Inc - * Portions Copyright (C) 2005-2006MontaVista Software, Inc. + * Portions Copyright (C) 2005-2007MontaVista Software, Inc. * * * TODO @@ -25,7 +25,7 @@ #include linux/libata.h #define DRV_NAME pata_hpt3x2n -#define DRV_VERSION0.3.3 +#define DRV_VERSION0.3.4 enum { HPT_PCI_FAST= (1 31), @@ -579,10 +579,12 @@ static int hpt3x2n_init_one(struct pci_d pci_write_config_dword(dev, 0x5C, (f_high 16) | f_low); } if (adjust == 8) { - printk(KERN_WARNING hpt3x2n: DPLL did not stabilize.\n); + printk(KERN_ERR pata_hpt3x2n: DPLL did not stabilize!\n); return -ENODEV; } + printk(KERN_INFO pata_hpt37x: bus clock %dMHz, using 66MHz DPLL.\n, + pci_mhz); /* Set our private data up. We only need a few flags so we use it directly */ port.private_data = NULL; - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] pata_artop: fix UDMA5 for AEC6280[R] and UDMA6 for AEC6880[R]
Tested on ATP865 (1191:0008 rev 07) in a DS101 box (an ARM-based NAS). Seems to work fine. Its tested fairly hard on several NAS boxes (and still needs a fix for one) However, I'm gettting consistently lower read throughput with pata_artop (13-19 MB/s) than with aec62xx (22 MB/s) on an oldish WD drive, and using pata_artop triggers a WARN_ON(irqs_disabled()) in arch/arm/mm/consistent.c: It would be nice to know why - is the cable detet coming out right on this ? WARNING: at arch/arm/mm/consistent.c:364 dma_free_coherent() ARM has a problem with dma_free_coherent with IRQ disabled. Unfortunately under high load ARM decides to use dma_free_coherent inside dma_unmap_sg(). This as far as I can see is an ARM problem not a libata problem and one you can duplicate with other drivers under high load. If any ARM people can tell me what is going on and help fix it either in ARM or libata that would be great. Alan - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: AMD64 dma_alloc_coherent crashes on non PCI device (was SATA open bugs) II
Not in non platform code, please ... somewhere on the Janitor's list is moving the dma_mask from the bus specific devices into the generic device ... when that happens this quantity will become u64 and they won't know what to do with the NULL check. Ok filed for kernel summit - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/11] it8213/piix/slc90e66: remove {it8213,piix,slc90e66}_dma_2_pio()
Bartlomiej Zolnierkiewicz wrote: Signed-off-by: Bartlomiej Zolnierkiewicz [EMAIL PROTECTED] Sigh... when I was talking about getting rid of that function, I meant that we need to also decouple UltraDMA from PIO -- which is what this patch misses... Addressed in the follow-up patch. That's good, thanks. :-) Actually, I intended to decouple DMA form PIO in this drivers completely but that would be a next step... DMA and PIO timings are shared on these controllers (except when DTE bit is set, then PIO0 timings are always used and DMA timings are independent)...? Yeah, but one do not need to toggle IORDY/prefetch enables for DMA modes -- actually, this is a buglet -- despite what Intel's manuals say... Bart MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: AMD64 dma_alloc_coherent crashes on non PCI device (was SATA open bugs) II
On Fri, 2007-08-10 at 14:54 +0100, Alan Cox wrote: Ok so we do in fact need some kind of proper way to ask if a device is DMA capable ? Right now it seems to be (dev-dma_mask != NULL) I'll follow that path for now then Not in non platform code, please ... somewhere on the Janitor's list is moving the dma_mask from the bus specific devices into the generic device ... when that happens this quantity will become u64 and they won't know what to do with the NULL check. Even today, it's wrong for this to be NULL. It's a bug somewhere in the pcmcia layer. What should happen is that there should be a u64 dma_mask somewhere in struct pcmcia_device where this should be pointing. James - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] pata_artop: fix UDMA5 for AEC6280[R] and UDMA6 for AEC6880[R]
On Thu, 9 Aug 2007 23:19:34 +0200 Bartlomiej Zolnierkiewicz [EMAIL PROTECTED] wrote: Maximum supported UDMA mode for AEC6280[R] is UDMA5 (not UDMA4) and for AEC6880[R] it is UDMA6 (not UDMA5): * Fix the problem by adding missing struct ata_port_info to artop_init_one(). * Use the right naming (s/626/628/). * Bump driver version. Fixes IDE-libata regression, problem was never present in IDE aec62xx driver. Cc: Alan Cox [EMAIL PROTECTED] Signed-off-by: Bartlomiej Zolnierkiewicz [EMAIL PROTECTED] Acked-by: Alan Cox [EMAIL PROTECTED] - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH] hpt366: fix PCI clock detection for HPT374 (take 3)
HPT374 BIOS seems to only save f_CNT register value for the function #0 before re-tuning DPLL (that causes the driver to report obviously distorted f_CNT for the function #1) -- fix this by always reading the saved f_CNT register value from the function #0 in the driver's init_chipset() method. While at it, introduce 'chip_type' for holding the 'struct hpt_info' field of the same name and replace the structure assignment with memcpy()... Signed-off-by: Sergei Shtylyov [EMAIL PROTECTED] --- This is against the current Linus tree -- with wording in the header fixed. Argh! :-( Ignore the previous patch please -- was not fixed enough... :-) drivers/ide/pci/hpt366.c | 41 + 1 files changed, 29 insertions(+), 12 deletions(-) Index: linux-2.6/drivers/ide/pci/hpt366.c === --- linux-2.6.orig/drivers/ide/pci/hpt366.c +++ linux-2.6/drivers/ide/pci/hpt366.c @@ -1,5 +1,5 @@ /* - * linux/drivers/ide/pci/hpt366.c Version 1.10Jun 29, 2007 + * linux/drivers/ide/pci/hpt366.c Version 1.11Aug 9, 2007 * * Copyright (C) 1999-2003 Andre Hedrick [EMAIL PROTECTED] * Portions Copyright (C) 2001 Sun Microsystems, Inc. @@ -981,6 +981,7 @@ static unsigned int __devinit init_chips struct hpt_info *info = kmalloc(sizeof(struct hpt_info), GFP_KERNEL); unsigned long io_base = pci_resource_start(dev, 4); u8 pci_clk, dpll_clk = 0;/* PCI and DPLL clock in MHz */ + u8 chip_type; enum ata_clock clock; if (info == NULL) { @@ -992,7 +993,8 @@ static unsigned int __devinit init_chips * Copy everything from a static template structure * to just allocated per-chip hpt_info structure. */ - *info = *(struct hpt_info *)pci_get_drvdata(dev); + memcpy(info, pci_get_drvdata(dev), sizeof(struct hpt_info)); + chip_type = info-chip_type; pci_write_config_byte(dev, PCI_CACHE_LINE_SIZE, (L1_CACHE_BYTES / 4)); pci_write_config_byte(dev, PCI_LATENCY_TIMER, 0x78); @@ -1002,7 +1004,7 @@ static unsigned int __devinit init_chips /* * First, try to estimate the PCI clock frequency... */ - if (info-chip_type = HPT370) { + if (chip_type = HPT370) { u8 scr1 = 0; u16 f_cnt = 0; u32 temp = 0; @@ -1016,7 +1018,7 @@ static unsigned int __devinit init_chips * HighPoint does this for HPT372A. * NOTE: This register is only writeable via I/O space. */ - if (info-chip_type == HPT372A) + if (chip_type == HPT372A) outb(0x0e, io_base + 0x9c); /* @@ -1034,13 +1036,28 @@ static unsigned int __devinit init_chips * First try reading the register in which the HighPoint BIOS * saves f_CNT value before reprogramming the DPLL from its * default setting (which differs for the various chips). -* NOTE: This register is only accessible via I/O space. * -* In case the signature check fails, we'll have to resort to -* reading the f_CNT register itself in hopes that nobody has -* touched the DPLL yet... +* NOTE: This register is only accessible via I/O space; +* the HPT374 BIOS seems to only set it for the function 0, +* so we always get it from there -- there's no need to check +* result of pci_get_slot() since the function 0 is guaranteed +* to be there by this time (by the IDE core itself)... +*/ + if (chip_type == HPT374 (PCI_FUNC(dev-devfn) 1)) { + struct pci_dev *dev1 = pci_get_slot(dev-bus, +dev-devfn - 1); + unsigned long io_base = pci_resource_start(dev1, 4); + + temp = inl(io_base + 0x90); + pci_dev_put(dev1); + } else + temp = inl(io_base + 0x90); + + /* +* In case the signature check fails, we'll have to +* resort to reading the f_CNT register itself in hopes +* that nobody has touched the DPLL yet... */ - temp = inl(io_base + 0x90); if ((temp 0xF000) != 0xABCDE000) { int i; @@ -1120,7 +1137,7 @@ static unsigned int __devinit init_chips * We also don't like using the DPLL because this causes glitches * on PRST-/SRST- when the state engine gets reset... */ - if (info-chip_type = HPT374 || info-settings[clock] == NULL) { + if (chip_type = HPT374 || info-settings[clock] == NULL) {
Re: [PATCH 2/11] it8213/piix/slc90e66: remove {it8213,piix,slc90e66}_dma_2_pio()
Signed-off-by: Bartlomiej Zolnierkiewicz [EMAIL PROTECTED] Acked-by: Sergei Shtylyov [EMAIL PROTECTED] MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 3/11] au1xxx-ide: use ide_tune_dma()
Bartlomiej Zolnierkiewicz wrote: Good, that's what I lacked for hpt366.c! Were you planning to push it to Linus soon? Not really but if needed I will extract MWDMA filter part and push it sooner. Erm, may I just merge it to my patch (mentioning you of course)? * Add -mdma_filter to ide_hwif_t and use it in ide_get_mode_mask(). Hm, why not mwdma_filter()? That mdma word has unneeded connotation. ;-) Ha! As predicted: -mdma_filter name would make people more ecstatic about the code ;) Nice one. 8-) * Remove needless setting of drive-using_dma from auide_dma_check(). * Split off auide_mdma_filter() from auide_dma_check(). * Use ide_tune_dma() in auide_dma_check(), this fixes following issues: - device's DMA capability bit not being checked - device not being checked against generic DMA blacklist - transfer mode not being set on device/host * Add PIO autotune fallback to auide_dma_check(). Signed-off-by: Bartlomiej Zolnierkiewicz [EMAIL PROTECTED] Index: b/drivers/ide/mips/au1xxx-ide.c === --- a/drivers/ide/mips/au1xxx-ide.c +++ b/drivers/ide/mips/au1xxx-ide.c @@ -351,11 +351,18 @@ static int auide_dma_setup(ide_drive_t * return 0; } -static int auide_dma_check(ide_drive_t *drive) +static u8 auide_mdma_filter(ide_drive_t *drive) { - u8 speed = ide_max_dma_mode(drive); + /* +* FIXME: -white_list and -black_list are based on completely bogus +* -ide_dma_check implementation which didn't set neither the host +* controller timings nor the device for the desired transfer mode. +* +* They should be either removed or 0x00 MWDMA mask should be +* returned for devices on the -black_list. +*/ I don't get it -- why then introduce a method that does nothing? It does something as you've noticed yourself: Yeah, I saw that it does something that shouldn't be done there. :-) The more is the reason to move that method into my recent hpt366 filter patch. - if( dbdma_init_done == 0 ){ + if (dbdma_init_done == 0) { I wonder what this code is doing here at all... auide_hwif.white_list = ide_in_drive_list(drive-id, dma_white_list); auide_hwif.black_list = ide_in_drive_list(drive-id, Why the results of the drive list lockup gets tied to auide_hwif? :-O Yet I was sure I'd typed lookup. Probably a freudian slip. :-) To use results in auide_ddma_init()... (which needs fixing of course). The more interesting questions are: WTF is safe MWDMA mode (tsize == 1, devwidth == 16) and whether -white/black_list is really needed. No time to look into the manuals right now... I planned to cc: AU1XXX platform maintainers on this patch but to my surprise MAINTAINERS lacks AU1XXX entry. It's been solt out to Raza Microelectronics last year and those guys never sent a single patch to linux-mips... Bart MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] pata_hpt37x: actually clock HPT374 by 50 MHz DPLL
Hello. Bartlomiej Zolnierkiewicz wrote: Index: linux-2.6/drivers/ata/pata_hpt37x.c === --- linux-2.6.orig/drivers/ata/pata_hpt37x.c +++ linux-2.6/drivers/ata/pata_hpt37x.c @@ -8,12 +8,10 @@ this driver is lacking author/maintainer info: Why I'm seeing it there then? :-O /* * Libata driver for the highpoint 37x and 30x UDMA66 ATA controllers. They're actually not UDMA66, they are UDMA100/133. MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] pata_artop: fix UDMA5 for AEC6280[R] and UDMA6 for AEC6880[R]
On Fri, 10 Aug 2007 01:45:38 +0200, Bartlomiej Zolnierkiewicz wrote: On Friday 10 August 2007, Alan Cox wrote: On Thu, 9 Aug 2007 23:19:34 +0200 Bartlomiej Zolnierkiewicz [EMAIL PROTECTED] wrote: Maximum supported UDMA mode for AEC6280[R] is UDMA5 (not UDMA4) and for AEC6880[R] it is UDMA6 (not UDMA5): * Fix the problem by adding missing struct ata_port_info to artop_init_one(). * Use the right naming (s/626/628/). * Bump driver version. Fixes IDE-libata regression, problem was never present in IDE aec62xx driver. Have you tested this ?? -ENODEV so no and testing is welcomed. However I went over both drivers to make sure that this change is safe and correct. BTW presence of the above bugs would strongly indicate that pata_artop has never been tested (properly) with AEC6x80[R], otherwise these bugs should have been noticed and fixed much earlier. Tested on ATP865 (1191:0008 rev 07) in a DS101 box (an ARM-based NAS). Seems to work fine. However, I'm gettting consistently lower read throughput with pata_artop (13-19 MB/s) than with aec62xx (22 MB/s) on an oldish WD drive, and using pata_artop triggers a WARN_ON(irqs_disabled()) in arch/arm/mm/consistent.c: WARNING: at arch/arm/mm/consistent.c:364 dma_free_coherent() [c001fe7c] (dump_stack+0x0/0x14) from [c00210ec] (dma_free_coherent+0x38/0x200) [c00210b4] (dma_free_coherent+0x0/0x200) from [c00253a8] (dma_unmap_sg+0x15c/0x198) [c002524c] (dma_unmap_sg+0x0/0x198) from [c0111984] (ata_sg_clean+0xe4/0x1dc) [c01118a0] (ata_sg_clean+0x0/0x1dc) from [c0111ac8] (__ata_qc_complete+0x4c/0xcc) r8:c02eca20 r7:0004 r6:c02ec000 r5:c02ec000 r4:c02eca20 [c0111a7c] (__ata_qc_complete+0x0/0xcc) from [c0111be8] (ata_qc_complete+0xa0/0xe4) r5:c02eca20 r4:c02eca20 [c0111b48] (ata_qc_complete+0x0/0xe4) from [c01121b8] (ata_hsm_qc_complete+0x104/0x10c) r4: [c01120b4] (ata_hsm_qc_complete+0x0/0x10c) from [c01127fc] (ata_hsm_move+0x63c/0x694) r6:c02ec000 r5:0050 r4: [c01121c0] (ata_hsm_move+0x0/0x694) from [c0116628] (ata_interrupt+0x188/0x240) [c01164a0] (ata_interrupt+0x0/0x240) from [c0051b24] (handle_IRQ_event+0x44/0x84) [c0051ae0] (handle_IRQ_event+0x0/0x84) from [c005339c] (handle_level_irq+0xb0/0x108) r7:c02250e8 r6: r5:001c r4:c020e600 [c00532ec] (handle_level_irq+0x0/0x108) from [c001b044] (__exception_text_start+0x44/0x60) r5:c020e600 r4:001c [c001b000] (__exception_text_start+0x0/0x60) from [c001ba44] (__irq_svc+0x24/0x60) Exception stack(0xc0209f64 to 0xc0209fac) 9f60: 0002 c001cfa0 c0208000 c0018de8 9f80: c02250e8 00017570 690541f1 0001746c c0209fc0 c0209fac c0209fac c001cd38 9fa0: c001cfa4 6013 r6:1000 r5:001f r4: [c001cce4] (cpu_idle+0x0/0x8c) from [c018f020] (rest_init+0x48/0x58) r5:c02174d0 r4:c021fa58 [c018efd8] (rest_init+0x0/0x58) from [c0008b7c] (start_kernel+0x238/0x294) [c0008944] (start_kernel+0x0/0x294) from [8038] (0x8038) So far I've only seen this happen when I run hdparm -Tt /dev/sda. So something's still not quite right. aec62xx is perfectly reliable on this box. /Mikael - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] hpt366: UltraDMA filtering for SATA cards
Bartlomiej Zolnierkiewicz wrote: The Marvell bridge chips used on HighPoint SATA cards do not seem to support the UltraDMA modes 1, 2, and 3 (as well as any MWDMA modes), so the driver needs to account for this in the udma_filter() method. In order to achieve that, do the following changes: - install the method for all chips, not only HPT36x/370 (improve code formatting by killing an extra tabs while at it); - add to the end of the 'switch' statement in hpt3xx_udma_filter() case for HPT372[AN] and HPT374 chips upon which the SATA cards are based and check there whether we're dealing with SATA drive (by looking at words 80 and 93 of the drive's identify data), reorder HPT370[A] cases for consistency... Signed-off-by: Sergei Shtylyov [EMAIL PROTECTED] applied but drivers/ide/pci/hpt366.c | 75 ++- 1 files changed, 43 insertions(+), 32 deletions(-) Index: linux-2.6/drivers/ide/pci/hpt366.c === --- linux-2.6.orig/drivers/ide/pci/hpt366.c +++ linux-2.6/drivers/ide/pci/hpt366.c [...] @@ -517,29 +517,17 @@ static int check_in_drive_list(ide_drive } /* - * Note for the future; the SATA hpt37x we must set - * either PIO or UDMA modes 0,4,5 + * The Marvell bridge chips used on the HighPoint SATA cards do not seem + * to support the UltraDMA modes 1, 2, and 3 -- as well as any MWDMA modes + * (that we should start filtering out once the IDE core allows that). */ - static u8 hpt3xx_udma_filter(ide_drive_t *drive) { struct hpt_info *info = pci_get_drvdata(HWIF(drive)-pci_dev); + struct hd_driveid *id = drive-id; u8 mask; switch (info-chip_type) { HPT374/HPT372[NA] case could be added here so re-ordering wouldn't be needed. I did that on purpose -- to keep an alphanumeric ordering. ;-) @@ -551,6 +539,30 @@ static u8 hpt3xx_udma_filter(ide_drive_t check_in_drive_list(drive, bad_ata66_3)) mask = 0x07; break; + case HPT370: + if (!HPT370_ALLOW_ATA100_5 || + check_in_drive_list(drive, bad_ata100_5)) + mask = 0x1f; + else + mask = 0x3f; ATA_UDMA* defines should be used if you insist on re-ordering OK, recasting... + case HPT372 : + case HPT372A: + case HPT372N: + case HPT374 : + /* +* Check for SATA drive by verifying that the word 93 is 0 and +* the drive is ATA-5 or higher compatible. +*/ + if (id-hw_config == 0 (id-major_rev_num 0x7fe0)) Same check as in ide-iops.c::eighty_ninty_three(). Would make sense to add ide_id_is_sata_dev() inline to linux/ide.h. Actually, libata already has ata_id_is_sata() defined in linux/ata.h but it takes const u16 * argument. + return 0x71; + /* fall thru */ default: return 0x7f; HPT371[N]/HPT302[N] will use the default mask which is correct but adds hidden dependency on HPT*_ALLOW_ATA_133 being always defined as 1. No, it doesn't since all this will be AND'ed with hwif-udma_mask... But wait, ide_rate_filter has the different code, it just sets mask to the result of the udma_filter() method... I wonder which code is correct? :-O IMO all HPT*_ALLOW_ATA* defines should just go away... I think it's still worth to keep 'em alive for the possible blacklist additions. Also now that -udma_filter is always present the initial hwif-ultra_mask doesn't matter so as well we may set it to ATA_UDMA6 (0x7f) and cleanup struct hpt_info (by removing max_ultra after fixing init_chipset_hpt366() to use info-chip_type = HPT374 check instead), It's all interesting but you've missed one aspect -- this will make the kernel larger while the current code keeps all this logic in the init.text section. init_setup_hpt366() and hpt366_chipsets[] (by removing udma_mask). I'll think about it in my copious free time (I have plenty of time spent offline now indeed :-)... @@ -1229,25 +1241,24 @@ static unsigned int __devinit init_chips static void __devinit init_hwif_hpt366(ide_hwif_t *hwif) { - struct pci_dev *dev= hwif-pci_dev; - struct hpt_info *info = pci_get_drvdata(dev); - int serialize = HPT_SERIALIZE_IO; - u8 scr1 = 0, ata66 = hwif-channel ? 0x01 : 0x02; - u8 chip_type = info-chip_type; - u8 new_mcr, old_mcr= 0; + struct pci_dev *dev= hwif-pci_dev; + struct hpt_info *info = pci_get_drvdata(dev); + int serialize = HPT_SERIALIZE_IO; + u8 scr1 = 0, ata66 = hwif-channel ? 0x01 : 0x02; + u8 chip_type = info-chip_type; + u8 new_mcr, old_mcr= 0; /* Cache the
Re: AMD64 dma_alloc_coherent crashes on non PCI device (was SATA open bugs) II
Alan Cox [EMAIL PROTECTED] writes: BTW unless I'm misreading the i386 code it'll not fail here, but allocate memory. Surely that will cause failures later if you rely on it failing? If you don't rely on it then changing x86-64 will also not help you. Eww that'll do strange things. In theory I could change i386 too to return NULL in this case (dma_mask == NULL). But I wonder how how many existing PCMCIA drivers I would break this way? Probably needs more testing at least. My current patch is in ftp://ftp.firstfloor.org/pub/ak/x86_64/late-merge/patches/dma-alloc-mask Ok so we do in fact need some kind of proper way to ask if a device is DMA capable ? Right now it seems to be (dev-dma_mask != NULL) -Andi - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] hpt366: fix PCI clock detection for HPT374
On Fri, 10 Aug 2007 19:41:59 +0400 Sergei Shtylyov [EMAIL PROTECTED] wrote: Alan Cox wrote: + if (chip_type == HPT374 (PCI_FUNC(dev-devfn) 1)) { + struct pci_dev *dev1 = pci_get_slot(dev-bus, +dev-devfn - 1); Can be NULL Not really. This may not be called if it's NULL -- see hpt374_init_setup(). Maybe worth a comment though... + unsigned long io_base = pci_resource_start(dev1, 4); Kaboom That was a dud bomb. ;-) What stops a hot unplug of a 374 from causing that to occur. I don't see where you have the other pci_dev pinned on a hotplug on a box set to scan the devices in reverse order (yes its an extremely obscure case ;)) - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] hpt366: fix PCI clock detection for HPT374
Alan Cox wrote: + if (chip_type == HPT374 (PCI_FUNC(dev-devfn) 1)) { + struct pci_dev *dev1 = pci_get_slot(dev-bus, +dev-devfn - 1); Can be NULL Not really. This may not be called if it's NULL -- see hpt374_init_setup(). Maybe worth a comment though... + unsigned long io_base = pci_resource_start(dev1, 4); Kaboom That was a dud bomb. ;-) MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] pata_hpt37x: actually clock HPT374 by 50 MHz DPLL
Bartlomiej Zolnierkiewicz wrote: * This driver is heavily based upon: * * linux/drivers/ide/pci/hpt366.c Version 0.36April 25, 2003 * reference to hpt366 version should also be updated (or removed) Disagree - its not based on the newer hpt366 driver. Its based on the old But this patch has just updated copyright references to match with the new driver while the version still matches the old one! Err... I've updated the copyright to reflect that I've done some changes to these drivers as well... one. Actually by now it bears almost no resemblence any of them Indeed, unfortunately... :-) Bart MBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 16/25] Fix libata warnings with CONFIG_PM=n
From: Gabriel C [EMAIL PROTECTED] drivers/ata/libata-core.c:5993: warning: 'ata_host_disable_link_pm' defined but not used drivers/ata/libata-core.c:6004: warning: 'ata_host_enable_link_pm' defined but not used Signed-off-by: Gabriel Craciunescu [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/libata-core.c |3 ++- 1 files changed, 2 insertions(+), 1 deletion(-) diff -puN drivers/ata/libata-core.c~fix-libata-warnings-with-config_pm=n drivers/ata/libata-core.c --- a/drivers/ata/libata-core.c~fix-libata-warnings-with-config_pm=n +++ a/drivers/ata/libata-core.c @@ -5923,6 +5923,7 @@ int ata_flush_cache(struct ata_device *d return 0; } +#ifdef CONFIG_PM static void ata_host_disable_link_pm(struct ata_host *host) { int i; @@ -5944,7 +5945,7 @@ static void ata_host_enable_link_pm(stru } } -#ifdef CONFIG_PM + static int ata_host_request_pm(struct ata_host *host, pm_message_t mesg, unsigned int action, unsigned int ehi_flags, int wait) _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 21/25] libata: expose AN to user space
From: Kristen Carlson Accardi [EMAIL PROTECTED] If Asynchronous Notification of media change events is supported, pass that information up to the SCSI layer. Signed-off-by: Kristen Carlson Accardi [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: James Bottomley [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/libata-scsi.c |3 +++ 1 files changed, 3 insertions(+) diff -puN drivers/ata/libata-scsi.c~libata-expose-an-to-user-space drivers/ata/libata-scsi.c --- a/drivers/ata/libata-scsi.c~libata-expose-an-to-user-space +++ a/drivers/ata/libata-scsi.c @@ -844,6 +844,9 @@ static void ata_scsi_dev_config(struct s blk_queue_max_hw_segments(q, q-max_hw_segments - 1); } + if (dev-flags ATA_DFLAG_AN) + sdev-media_change_notify = 1; + if (dev-flags ATA_DFLAG_NCQ) { int depth; _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 22/25] libata: send event when AN received
From: Kristen Carlson Accardi [EMAIL PROTECTED] When we get an SDB FIS with the 'N' bit set, we should send an event to user space to indicate that there has been a media change. This will be done via the scsi device. Signed-off-by: Kristen Carlson Accardi [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: James Bottomley [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/ahci.c| 22 ++ drivers/ata/libata-scsi.c | 16 include/linux/libata.h|1 + 3 files changed, 39 insertions(+) diff -puN drivers/ata/ahci.c~libata-send-event-when-an-received drivers/ata/ahci.c --- a/drivers/ata/ahci.c~libata-send-event-when-an-received +++ a/drivers/ata/ahci.c @@ -1529,6 +1529,28 @@ static void ahci_port_intr(struct ata_po return; } + if (status PORT_IRQ_SDB_FIS) { + /* +* if this is an ATAPI device with AN turned on, +* then we should interrogate the device to +* determine the cause of the interrupt +* +* for AN - this we should check the SDB FIS +* and find the I and N bits set +*/ + const u32 *f = pp-rx_fis + RX_FIS_SDB; + + /* check the 'N' bit in word 0 of the FIS */ + if (f[0] (1 15)) { + int port_addr = ((f[0] 0x0f00) 8); + struct ata_device *adev; + if (port_addr ATA_MAX_DEVICES) { + adev = ap-device[port_addr]; + if (adev-flags ATA_DFLAG_AN) + ata_scsi_media_change_notify(adev); + } + } + } if (ap-sactive) qc_active = readl(port_mmio + PORT_SCR_ACT); else diff -puN drivers/ata/libata-scsi.c~libata-send-event-when-an-received drivers/ata/libata-scsi.c --- a/drivers/ata/libata-scsi.c~libata-send-event-when-an-received +++ a/drivers/ata/libata-scsi.c @@ -3218,6 +3218,22 @@ static void ata_scsi_remove_dev(struct a } /** + * ata_scsi_media_change_notify - send media change event + * @atadev: Pointer to the disk device with media change event + * + * Tell the block layer to send a media change notification + * event. + * + * LOCKING: + * interrupt context, may not sleep. + */ +void ata_scsi_media_change_notify(struct ata_device *atadev) +{ + scsi_device_event_notify(atadev-sdev, SDEV_MEDIA_CHANGE); +} +EXPORT_SYMBOL_GPL(ata_scsi_media_change_notify); + +/** * ata_scsi_hotplug - SCSI part of hotplug * @work: Pointer to ATA port to perform SCSI hotplug on * diff -puN include/linux/libata.h~libata-send-event-when-an-received include/linux/libata.h --- a/include/linux/libata.h~libata-send-event-when-an-received +++ a/include/linux/libata.h @@ -761,6 +761,7 @@ extern void ata_host_init(struct ata_hos extern int ata_scsi_detect(struct scsi_host_template *sht); extern int ata_scsi_ioctl(struct scsi_device *dev, int cmd, void __user *arg); extern int ata_scsi_queuecmd(struct scsi_cmnd *cmd, void (*done)(struct scsi_cmnd *)); +extern void ata_scsi_media_change_notify(struct ata_device *atadev); extern void ata_sas_port_destroy(struct ata_port *); extern struct ata_port *ata_sas_port_alloc(struct ata_host *, struct ata_port_info *, struct Scsi_Host *); _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] pata_hpt37x: actually clock HPT374 by 50 MHz DPLL
Hello. Alan Cox wrote: one. Actually by now it bears almost no resemblence any of them Indeed, unfortunately... Oh I think its very fortunate. The original IDE one is 3 semi-related drivers in one file all falling over one another. At least we can now break them individually 8) I'm still thinking that only HPT36x chips were worth moving into another driver -- couldn't help myself not saying that once more. :-) Curse on HighPoint for their stupid chips, device IDs, and drivers. :-Q Alan WBR, Sergei - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: AMD64 dma_alloc_coherent crashes on non PCI device (was SATA open bugs) II
Ok so we do in fact need some kind of proper way to ask if a device is DMA capable ? Right now it seems to be (dev-dma_mask != NULL) I'll follow that path for now then - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 17/25] libata: correct IORDY handling
From: Alan Cox [EMAIL PROTECTED] Debugging a report of a problem with an ancient solid state disk showed up some problems in the IORDY handling 1. We check the wrong bit to see if the device has IORDY 2. Even then some ancient creaking piles of crap don't support SETXFER at all. I think this should go via -mm for a bit. The cases it fixes are obscure and the risk of side effects is slight but possible. This also moves us slightly closer to supporting original MFM/RLL disks with libata but before Jeff panics I have no plans to do that Signed-off-by: Alan Cox [EMAIL PROTECTED] Acked-by: Sergei Shtylyov [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/libata-core.c |6 +- include/linux/ata.h |2 +- 2 files changed, 6 insertions(+), 2 deletions(-) diff -puN drivers/ata/libata-core.c~libata-correct-iordy-handling drivers/ata/libata-core.c --- a/drivers/ata/libata-core.c~libata-correct-iordy-handling +++ a/drivers/ata/libata-core.c @@ -2770,7 +2770,11 @@ static int ata_dev_set_mode(struct ata_d /* Old CFA may refuse this command, which is just fine */ if (dev-xfer_shift == ATA_SHIFT_PIO ata_id_is_cfa(dev-id)) err_mask = ~AC_ERR_DEV; - + /* Some very old devices and some bad newer ones fail any kind of + SET_XFERMODE request but support PIO0-2 timings and no IORDY */ + if (dev-xfer_shift == ATA_SHIFT_PIO !ata_id_has_iordy(dev-id) + dev-pio_mode = XFER_PIO_2) + err_mask = ~AC_ERR_DEV; if (err_mask) { ata_dev_printk(dev, KERN_ERR, failed to set xfermode (err_mask=0x%x)\n, err_mask); diff -puN include/linux/ata.h~libata-correct-iordy-handling include/linux/ata.h --- a/include/linux/ata.h~libata-correct-iordy-handling +++ a/include/linux/ata.h @@ -345,7 +345,7 @@ struct ata_taskfile { #define ata_id_removeable(id) ((id)[0] (1 7)) #define ata_id_has_dword_io(id)((id)[50] (1 0)) #define ata_id_iordy_disable(id) ((id)[49] (1 10)) -#define ata_id_has_iordy(id) ((id)[49] (1 9)) +#define ata_id_has_iordy(id) ((id)[49] (1 11)) #define ata_id_u32(id,n) \ (((u32) (id)[(n) + 1] 16) | ((u32) (id)[(n)])) #define ata_id_u64(id,n) \ _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 18/25] libata: add human-readable error value decoding
From: Robert Hancock [EMAIL PROTECTED] This adds human-readable decoding of the ATA status and error registers (similar to what drivers/ide does) as well as the SATA Serror register to libata error handling output. This prevents the need to pore through standards documents to figure out the meaning of the bits in these registers when looking at error reports. Some bits that drivers/ide decoded are not decoded here, since the bits are either command-dependent or obsolete, and properly parsing them would add too much complexity. Signed-off-by: Robert Hancock [EMAIL PROTECTED] Acked-by: Alan Cox [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/libata-eh.c | 45 ++ include/linux/ata.h |9 +++ 2 files changed, 54 insertions(+) diff -puN drivers/ata/libata-eh.c~libata-add-human-readable-error-value-decoding-v3 drivers/ata/libata-eh.c --- a/drivers/ata/libata-eh.c~libata-add-human-readable-error-value-decoding-v3 +++ a/drivers/ata/libata-eh.c @@ -1698,6 +1698,27 @@ static void ata_eh_report(struct ata_por ata_port_printk(ap, KERN_ERR, %s\n, desc); } + if (ehc-i.serror) + ata_port_printk(ap, KERN_ERR, + SError: {%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s}\n, + ehc-i.serror SERR_DATA_RECOVERED ? RecovData : , + ehc-i.serror SERR_COMM_RECOVERED ? RecovComm : , + ehc-i.serror SERR_DATA ? UnrecovData : , + ehc-i.serror SERR_PERSISTENT ? Persist : , + ehc-i.serror SERR_PROTOCOL ? Proto : , + ehc-i.serror SERR_INTERNAL ? HostInt : , + ehc-i.serror SERR_PHYRDY_CHG ? PHYRdyChg : , + ehc-i.serror SERR_PHY_INT_ERR ? PHYInt : , + ehc-i.serror SERR_COMM_WAKE ? CommWake : , + ehc-i.serror SERR_10B_8B_ERR ? 10B8B : , + ehc-i.serror SERR_DISPARITY ? Dispar : , + ehc-i.serror SERR_CRC ? BadCRC : , + ehc-i.serror SERR_HANDSHAKE ? Handshk : , + ehc-i.serror SERR_LINK_SEQ_ERR ? LinkSeq : , + ehc-i.serror SERR_TRANS_ST_ERROR ? TrStaTrns : , + ehc-i.serror SERR_UNRECOG_FIS ? UnrecFIS : , + ehc-i.serror SERR_DEV_XCHG ? DevExch : ); + for (tag = 0; tag ATA_MAX_QUEUE; tag++) { static const char *dma_str[] = { [DMA_BIDIRECTIONAL] = bidi, @@ -1728,6 +1749,30 @@ static void ata_eh_report(struct ata_por res-hob_lbal, res-hob_lbam, res-hob_lbah, res-device, qc-err_mask, ata_err_string(qc-err_mask), qc-err_mask AC_ERR_NCQ ? F : ); + + if (res-command (ATA_BUSY | ATA_DRDY | ATA_DF | ATA_DRQ | + ATA_ERR) ) { + if (res-command ATA_BUSY) + ata_dev_printk(qc-dev, KERN_ERR, + status: {Busy}\n ); + else + ata_dev_printk(qc-dev, KERN_ERR, + status: {%s%s%s%s}\n, + res-command ATA_DRDY ? DRDY : , + res-command ATA_DF ? DF : , + res-command ATA_DRQ ? DRQ : , + res-command ATA_ERR ? ERR : ); + } + + if (cmd-command != ATA_CMD_PACKET + (res-feature (ATA_ICRC | ATA_UNC | ATA_IDNF | +ATA_ABORTED))) + ata_dev_printk(qc-dev, KERN_ERR, + error: {%s%s%s%s}\n, + res-feature ATA_ICRC ? ICRC : , + res-feature ATA_UNC ? UNC : , + res-feature ATA_IDNF ? IDNF : , + res-feature ATA_ABORTED ? ABRT : ); } } diff -puN include/linux/ata.h~libata-add-human-readable-error-value-decoding-v3 include/linux/ata.h --- a/include/linux/ata.h~libata-add-human-readable-error-value-decoding-v3 +++ a/include/linux/ata.h @@ -268,6 +268,15 @@ enum { SERR_PROTOCOL = (1 10), /* protocol violation */ SERR_INTERNAL = (1 11), /* host internal error */ SERR_PHYRDY_CHG = (1 16), /* PHY RDY changed */ + SERR_PHY_INT_ERR= (1 17), /* PHY internal error */ + SERR_COMM_WAKE = (1 18), /* Comm wake */ + SERR_10B_8B_ERR = (1 19), /* 10b to 8b decode error */ + SERR_DISPARITY = (1 20), /* Disparity */ + SERR_CRC= (1 21), /* CRC error */ + SERR_HANDSHAKE = (1 22), /* Handshake error */ + SERR_LINK_SEQ_ERR =
[patch 25/25] ata_piix: disallow UDMA 133 on ICH5 ICH7
From: Christian Lamparter [EMAIL PROTECTED] There is another outstanding issue with ata_piix.c. Intel has never officially supported anything faster than PATA 100MB/s. But, the ata_piix.c driver define the ICH5 ICH7 as UDMA6 (aka 133MB/s) capable. [ Well, no one has probably noticed it before, because there is bug in do_pata_set_dmamode... Just look at libata_atapiix_enable_real_udma133.patch and you'll see what wrong with it. ] Here are Intel's datasheets for the affected chipsets: ICH5 Datasheet: http://www.intel.com/design/chipsets/datashts/252516.htm (See note on page 183: ... the ICH5 supports reads at the maximum rate of 100MB/s.) ICH7 Datasheet: http://www.intel.com/design/chipsets/datashts/307013.htm (See first note on page 190: ... the ICH7 supports reads at the maximum rate of 100MB/s.) They are two different ways to deal with it: - Either - 1. replace all ich_pata_133 with ich_pata_100. (libata_atapiix_disable_udma6.diff - diff from 2.6.22 ) - Or - 2. keep all ich_pata_133 and fix the bug in do_pata_set_dmamode. (libata_atapiix_enable_real_udma133.patch - diff from 2.6.22) If there are any concerns about the safety of the patch patch: http://lkml.org/lkml/2007/7/6/292 (It was already tested by an Intel employee, but I guess a bit more user input is necessary here... ) This patch implements 1. Cc: Alan Cox [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Signed-off-by: Christian Lamparter [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/ata_piix.c |8 1 files changed, 4 insertions(+), 4 deletions(-) diff -puN drivers/ata/ata_piix.c~ata_piix-disallow-udma-133-on-ich5-ich7 drivers/ata/ata_piix.c --- a/drivers/ata/ata_piix.c~ata_piix-disallow-udma-133-on-ich5-ich7 +++ a/drivers/ata/ata_piix.c @@ -123,7 +123,7 @@ enum { ich_pata_33 = 1,/* ICH up to UDMA 33 only */ ich_pata_66 = 2,/* ICH up to 66 Mhz */ ich_pata_100= 3,/* ICH up to UDMA 100 */ - ich_pata_133= 4,/* ICH up to UDMA 133 */ + /* ICH up to UDMA 133 is not supported */ ich5_sata = 5, ich6_sata = 6, ich6_sata_ahci = 7, @@ -198,7 +198,7 @@ static const struct pci_device_id piix_p { 0x8086, 0x24CA, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, { 0x8086, 0x24CB, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, /* Intel ICH5 */ - { 0x8086, 0x24DB, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_133 }, + { 0x8086, 0x24DB, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, /* C-ICH (i810E2) */ { 0x8086, 0x245B, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, /* ESB (855GME/875P + 6300ESB) UDMA 100 */ @@ -206,7 +206,7 @@ static const struct pci_device_id piix_p /* ICH6 (and 6) (i915) UDMA 100 */ { 0x8086, 0x266F, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, /* ICH7/7-R (i945, i975) UDMA 100*/ - { 0x8086, 0x27DF, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_133 }, + { 0x8086, 0x27DF, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, { 0x8086, 0x269E, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, /* ICH8 Mobile PATA Controller */ { 0x8086, 0x2850, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich_pata_100 }, @@ -489,7 +489,7 @@ static struct ata_port_info piix_port_in .port_ops = ich_pata_ops, }, - /* ich_pata_133: 4 ICH with full UDMA6 */ + /* ich_pata_133: 4 - Not supported - */ { .sht= piix_sht, .flags = PIIX_PATA_FLAGS | PIIX_FLAG_CHECKINTR, _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 15/25] libata: ACPI checks for 80wire cable: use in pata_via
From: Alan Cox [EMAIL PROTECTED] Testing this on the VIA boards fixes several problems with otherwise undetectable SATA bridge chips Signed-off-by: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/pata_via.c |3 +++ 1 files changed, 3 insertions(+) diff -puN drivers/ata/pata_via.c~libata-acpi-checks-for-80wire-cable-use-in-pata_via drivers/ata/pata_via.c --- a/drivers/ata/pata_via.c~libata-acpi-checks-for-80wire-cable-use-in-pata_via +++ a/drivers/ata/pata_via.c @@ -180,6 +180,9 @@ static int via_cable_detect(struct ata_p two drives */ if (ata66 (0x1010 (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)) + return ATA_CBL_PATA80; return ATA_CBL_PATA40; } _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 19/25] libata: check for AN support
From: Kristen Carlson Accardi [EMAIL PROTECTED] Check to see if an ATAPI device supports Asynchronous Notification. If so, enable it. Signed-off-by: Kristen Carlson Accardi [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: James Bottomley [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/ahci.c|5 ++- drivers/ata/libata-core.c | 53 include/linux/ata.h |9 ++ include/linux/libata.h|2 + 4 files changed, 67 insertions(+), 2 deletions(-) diff -puN drivers/ata/ahci.c~libata-check-for-an-support drivers/ata/ahci.c --- a/drivers/ata/ahci.c~libata-check-for-an-support +++ a/drivers/ata/ahci.c @@ -348,14 +348,15 @@ static const struct ata_port_operations static const struct ata_port_info ahci_port_info[] = { /* board_ahci */ { - .flags = AHCI_FLAG_COMMON, + .flags = AHCI_FLAG_COMMON | ATA_FLAG_AN, .pio_mask = 0x1f, /* pio0-4 */ .udma_mask = ATA_UDMA6, .port_ops = ahci_ops, }, /* board_ahci_pi */ { - .flags = AHCI_FLAG_COMMON | AHCI_FLAG_HONOR_PI, + .flags = AHCI_FLAG_COMMON | AHCI_FLAG_HONOR_PI | + ATA_FLAG_AN, .pio_mask = 0x1f, /* pio0-4 */ .udma_mask = ATA_UDMA6, .port_ops = ahci_ops, diff -puN drivers/ata/libata-core.c~libata-check-for-an-support drivers/ata/libata-core.c --- a/drivers/ata/libata-core.c~libata-check-for-an-support +++ a/drivers/ata/libata-core.c @@ -70,6 +70,7 @@ const unsigned long sata_deb_timing_long static unsigned int ata_dev_init_params(struct ata_device *dev, u16 heads, u16 sectors); static unsigned int ata_dev_set_xfermode(struct ata_device *dev); +static unsigned int ata_dev_set_AN(struct ata_device *dev, u8 enable); static void ata_dev_xfermask(struct ata_device *dev); static unsigned long ata_dev_blacklisted(const struct ata_device *dev); @@ -1974,6 +1975,22 @@ int ata_dev_configure(struct ata_device } dev-cdb_len = (unsigned int) rc; + /* +* check to see if this ATAPI device supports +* Asynchronous Notification +*/ + if ((ap-flags ATA_FLAG_AN) ata_id_has_AN(id)) { + int err; + /* issue SET feature command to turn this on */ + err = ata_dev_set_AN(dev, SETFEATURES_SATA_ENABLE); + if (err) + ata_dev_printk(dev, KERN_ERR, + unable to set AN, err %x\n, + err); + else + dev-flags |= ATA_DFLAG_AN; + } + if (ata_id_cdb_intr(dev-id)) { dev-flags |= ATA_DFLAG_CDB_INTR; cdb_intr_string = , CDB intr; @@ -4002,6 +4019,42 @@ static unsigned int ata_dev_set_xfermode } /** + * ata_dev_set_AN - Issue SET FEATURES - SATA FEATURES + * @dev: Device to which command will be sent + * @enable: Whether to enable or disable the feature + * + * Issue SET FEATURES - SATA FEATURES command to device @dev + * on port @ap with sector count set to indicate Asynchronous + * Notification feature + * + * LOCKING: + * PCI/etc. bus probe sem. + * + * RETURNS: + * 0 on success, AC_ERR_* mask otherwise. + */ +static unsigned int ata_dev_set_AN(struct ata_device *dev, u8 enable) +{ + struct ata_taskfile tf; + unsigned int err_mask; + + /* set up set-features taskfile */ + DPRINTK(set features - SATA features\n); + + ata_tf_init(dev, tf); + tf.command = ATA_CMD_SET_FEATURES; + tf.feature = enable; + tf.flags |= ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE; + tf.protocol = ATA_PROT_NODATA; + tf.nsect = SATA_AN; + + err_mask = ata_exec_internal(dev, tf, NULL, DMA_NONE, NULL, 0); + + DPRINTK(EXIT, err_mask=%x\n, err_mask); + return err_mask; +} + +/** * ata_dev_init_params - Issue INIT DEV PARAMS command * @dev: Device to which command will be sent * @heads: Number of heads (taskfile parameter) diff -puN include/linux/ata.h~libata-check-for-an-support include/linux/ata.h --- a/include/linux/ata.h~libata-check-for-an-support +++ a/include/linux/ata.h @@ -217,6 +217,12 @@ enum { SETFEATURES_SPINUP = 0x07, /* Spin-up drive */ + SETFEATURES_SATA_ENABLE = 0x10, /* Enable use of SATA feature */ + SETFEATURES_SATA_DISABLE = 0x90, /* Disable use of SATA feature */ + + /* SETFEATURE Sector counts for SATA features */ + SATA_AN
[patch 09/25] ALPM: increase number of allowable device flags
From: Kristen Carlson Accardi [EMAIL PROTECTED] Signed-off-by: Kristen Carlson Accardi [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- include/linux/libata.h |2 +- 1 files changed, 1 insertion(+), 1 deletion(-) diff -puN include/linux/libata.h~alpm-increase-number-of-allowable-device-flags include/linux/libata.h --- a/include/linux/libata.h~alpm-increase-number-of-allowable-device-flags +++ a/include/linux/libata.h @@ -139,7 +139,7 @@ enum { ATA_DFLAG_FLUSH_EXT = (1 4), /* do FLUSH_EXT instead of FLUSH */ ATA_DFLAG_ACPI_PENDING = (1 5), /* ACPI resume action pending */ ATA_DFLAG_ACPI_FAILED = (1 6), /* ACPI on devcfg has failed */ - ATA_DFLAG_CFG_MASK = (1 8) - 1, + ATA_DFLAG_CFG_MASK = (1 12) - 1, ATA_DFLAG_PIO = (1 8), /* device limited to PIO mode */ ATA_DFLAG_NCQ_OFF = (1 9), /* device limited to non-NCQ mode */ _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 02/25] pata_acpi: rework the ACPI drivers based upon experience of what the BIOS can do
From: Alan Cox [EMAIL PROTECTED] Don't assume the BIOS can validate modes or has any sense at all. Instead use the BIOS timings to deduce the modes. Signed-off-by: Alan Cox [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/pata_acpi.c | 74 +- 1 files changed, 27 insertions(+), 47 deletions(-) diff -puN drivers/ata/pata_acpi.c~pata_acpi-rework-the-acpi-drivers-based-upon-experience drivers/ata/pata_acpi.c --- a/drivers/ata/pata_acpi.c~pata_acpi-rework-the-acpi-drivers-based-upon-experience +++ a/drivers/ata/pata_acpi.c @@ -2,8 +2,6 @@ * ACPI PATA driver * * (c) 2007 Red Hat [EMAIL PROTECTED] - * - * TODO - restore modes after mode_filter chews them up */ #include linux/kernel.h @@ -28,7 +26,7 @@ #include libata-acpi.h #define DRV_NAME pata_acpi -#define DRV_VERSION0.1.1 +#define DRV_VERSION0.2.1 struct pata_acpi { void *handle; @@ -122,59 +120,41 @@ static unsigned long pacpi_discover_mode if (!(probe.flags 0x10)) unit = 0; - - /* In order to generate a valid mode mask as we need cycle through - trying each proposed speed in turn */ + ata_acpi_gtm(ap. acpi-handle, probe); /* Start by scanning for PIO modes */ for (i = 0; i 7; i++) { - probe.drive[unit].pio = pio_cycle[i]; - ata_acpi_stm(ap, acpi-handle, probe); - ata_acpi_gtm(ap, acpi-handle, probe); t = probe.drive[unit].pio; - if (t == 0x || (i t = pio_cycle[i-1])) - mask = ~(1 (i + ATA_SHIFT_PIO)); - } - - /* Select MWDMA */ - probe.flags = ~(1 (2 * unit)); - - /* Scan for MWDMA modes */ - for (i = 0; i 5; i++) { - u32 t; - probe.drive[unit].dma = mwdma_cycle[i]; - ata_acpi_stm(ap, acpi-handle, probe); - ata_acpi_gtm(ap, acpi-handle, probe); - - t = probe.drive[unit].dma; - - if (t == 0x || (i t = mwdma_cycle[i-1])) - mask = ~ (1 (i + ATA_SHIFT_MWDMA)); + if (t = pio_cycle[i]) { + mask |= (2 (ATA_SHIFT_PIO + i)) - 1; + break; + } } - /* Select UDMA */ - probe.flags |= (1 (2 * unit)); - - /* Scan for UDMA modes */ - for (i = 0; i 7; i++) { - u32 t; - probe.drive[unit].dma = udma_cycle[i]; - ata_acpi_stm(ap, acpi-handle, probe); - ata_acpi_gtm(ap, acpi-handle, probe); - - t = probe.drive[unit].dma; - - if (t == 0x || (i t = udma_cycle[i-1])) - mask = ~ (1 (i + ATA_SHIFT_UDMA)); + /* 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)) ap-cbl = ATA_CBL_PATA80; - - /* Restore the programmed timings */ - ata_acpi_stm(ap, acpi-handle, acpi-gtm); - /* And finally we can hand back the list of speeds that actually are - supported by the BIOS */ return mask; } _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: AMD64 dma_alloc_coherent crashes on non PCI device (was SATA open bugs) II
Surely we don't need to wait until then? This is the correct fix, isn't it? (Obviously I'll split it into a generic and a pcmcia specific piece if it looks OK to everyone). It sets the PCMCIA dma_mask up correctly and introduces a DMA_MASK_NONE (I prefer that to DMA_0BIT_MASK but I can add that too if people want) and gives Alan his is_device_dma_capable() API. Patch looks good to me. -Andi - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 03/25] libata: implement ata_wait_after_reset()
From: Tejun Heo [EMAIL PROTECTED] On certain device/controller combination, 0xff status is asserted after reset and doesn't get cleared during 150ms post-reset wait. As 0xff status is interpreted as no device (for good reasons), this can lead to misdetection on such cases. This patch implements ata_wait_after_reset() which replaces the 150ms sleep and waits upto ATA_TMOUT_FF_WAIT if status is 0xff. ATA_TMOUT_FF_WAIT is currently 800ms which is enough for HHD424020F7SV00 to get detected but not enough for Quantum GoVault drive which is known to take upto 2s. Without parallel probing, spending 2s on 0xff port would incur too much delay on ata_piix's which use 0xff to indicate empty port and doesn't have SCR register, so GoVault needs to wait till parallel probing. Signed-off-by: Tejun Heo [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/ahci.c | 11 + drivers/ata/libata-core.c | 67 +++--- drivers/ata/pata_scc.c | 13 +- drivers/ata/sata_inic162x.c |2 - include/linux/libata.h |8 5 files changed, 67 insertions(+), 34 deletions(-) diff -puN drivers/ata/ahci.c~libata-implement-ata_wait_after_reset drivers/ata/ahci.c --- a/drivers/ata/ahci.c~libata-implement-ata_wait_after_reset +++ a/drivers/ata/ahci.c @@ -1085,15 +1085,8 @@ static int ahci_do_softreset(struct ata_ tf.ctl = ~ATA_SRST; ahci_exec_polled_cmd(ap, pmp, tf, 0, 0, 0); - /* spec mandates = 2ms before checking status. -* We wait 150ms, because that was the magic delay used for -* ATAPI devices in Hale Landis's ATADRVR, for the period of time -* between when the ATA command register is written, and then -* status is checked. Because waiting for a while before -* checking status is fine, post SRST, we perform this magic -* delay here as well. -*/ - msleep(150); + /* wait a while before checking status */ + ata_wait_after_reset(ap, deadline); rc = ata_wait_ready(ap, deadline); /* link occupied, -ENODEV too is an error */ diff -puN drivers/ata/libata-core.c~libata-implement-ata_wait_after_reset drivers/ata/libata-core.c --- a/drivers/ata/libata-core.c~libata-implement-ata_wait_after_reset +++ a/drivers/ata/libata-core.c @@ -2982,6 +2982,55 @@ int ata_busy_sleep(struct ata_port *ap, } /** + * ata_wait_after_reset - wait before checking status after reset + * @ap: port containing status register to be polled + * @deadline: deadline jiffies for the operation + * + * After reset, we need to pause a while before reading status. + * Also, certain combination of controller and device report 0xff + * for some duration (e.g. until SATA PHY is up and running) + * which is interpreted as empty port in ATA world. This + * function also waits for such devices to get out of 0xff + * status. + * + * LOCKING: + * Kernel thread context (may sleep). + */ +void ata_wait_after_reset(struct ata_port *ap, unsigned long deadline) +{ + unsigned long until = jiffies + ATA_TMOUT_FF_WAIT; + + if (time_before(until, deadline)) + deadline = until; + + /* Spec mandates = 2ms before checking status. We wait +* 150ms, because that was the magic delay used for ATAPI +* devices in Hale Landis's ATADRVR, for the period of time +* between when the ATA command register is written, and then +* status is checked. Because waiting for a while before +* checking status is fine, post SRST, we perform this magic +* delay here as well. +* +* Old drivers/ide uses the 2mS rule and then waits for ready. +*/ + msleep(150); + + /* Wait for 0xff to clear. Some SATA devices take a long time +* to clear 0xff after reset. For example, HHD424020F7SV00 +* iVDR needs = 800ms while. Quantum GoVault needs even more +* than that. +*/ + while (1) { + u8 status = ata_chk_status(ap); + + if (status != 0xff || time_after(jiffies, deadline)) + return; + + msleep(50); + } +} + +/** * ata_wait_ready - sleep until BSY clears, or timeout * @ap: port containing status register to be polled * @deadline: deadline jiffies for the operation @@ -3097,17 +3146,8 @@ static int ata_bus_softreset(struct ata_ udelay(20); /* FIXME: flush */ iowrite8(ap-ctl, ioaddr-ctl_addr); - /* spec mandates = 2ms before checking status. -* We wait 150ms, because that was the magic delay used for -* ATAPI devices in Hale Landis's ATADRVR, for the period of time -* between when the ATA command register is written, and then -* status is checked. Because waiting for a while before -* checking status is fine, post SRST, we perform this magic -* delay here
[patch 05/25] ata: add the SW NCQ support to sata_nv for MCP51/MCP55/MCP61
From: Kuan Luo [EMAIL PROTECTED] Add the Software NCQ support to sata_nv.c for MCP51/MCP55/MCP61 SATA controller. NCQ function is disable by default, you can enable it with 'swncq=1'. NCQ will be turned off if the drive is Maxtor on MCP51 or MCP55 rev 0xa2 platform. [EMAIL PROTECTED]: build fix] Signed-off-by: Kuan Luo [EMAIL PROTECTED] Signed-off-by: Peer Chen [EMAIL PROTECTED] Cc: Zoltan Boszormenyi [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/sata_nv.c | 860 +++- 1 files changed, 851 insertions(+), 9 deletions(-) diff -puN drivers/ata/sata_nv.c~ata-add-the-sw-ncq-support-to-sata_nv-for-mcp51-mcp55-mcp61 drivers/ata/sata_nv.c --- a/drivers/ata/sata_nv.c~ata-add-the-sw-ncq-support-to-sata_nv-for-mcp51-mcp55-mcp61 +++ a/drivers/ata/sata_nv.c @@ -169,6 +169,35 @@ enum { NV_ADMA_PORT_REGISTER_MODE = (1 0), NV_ADMA_ATAPI_SETUP_COMPLETE= (1 1), + /* MCP55 reg offset */ + NV_CTL_MCP55= 0x400, + NV_INT_STATUS_MCP55 = 0x440, + NV_INT_ENABLE_MCP55 = 0x444, + NV_NCQ_REG_MCP55= 0x448, + + /* MCP55 */ + NV_INT_ALL_MCP55= 0x, + NV_INT_PORT_SHIFT_MCP55 = 16, /* each port occupies 16 bits */ + NV_INT_MASK_MCP55 = NV_INT_ALL_MCP55 0xfffd, + + /* SWNCQ ENABLE BITS*/ + NV_CTL_PRI_SWNCQ= 0x02, + NV_CTL_SEC_SWNCQ= 0x04, + + /* SW NCQ status bits*/ + NV_SWNCQ_IRQ_DEV= (1 0), + NV_SWNCQ_IRQ_PM = (1 1), + NV_SWNCQ_IRQ_ADDED = (1 2), + NV_SWNCQ_IRQ_REMOVED= (1 3), + + NV_SWNCQ_IRQ_BACKOUT= (1 4), + NV_SWNCQ_IRQ_SDBFIS = (1 5), + NV_SWNCQ_IRQ_DHREGFIS = (1 6), + NV_SWNCQ_IRQ_DMASETUP = (1 7), + + NV_SWNCQ_IRQ_HOTPLUG= NV_SWNCQ_IRQ_ADDED | + NV_SWNCQ_IRQ_REMOVED, + }; /* ADMA Physical Region Descriptor - one SG segment */ @@ -226,6 +255,37 @@ struct nv_host_priv { unsigned long type; }; +struct defer_queue { + u32 defer_bits; + unsigned inthead; + unsigned inttail; + unsigned inttag[ATA_MAX_QUEUE]; +}; + +struct nv_swncq_port_priv { + struct ata_prd *prd;/* our SG list */ + dma_addr_t prd_dma; /* and its DMA mapping */ + void __iomem*sactive_block; + void __iomem*irq_block; + void __iomem*tag_block; + u32 qc_active; + unsigned intlast_issue_tag; + spinlock_t lock; + /* fifo circular queue to store deferral command */ + struct defer_queue defer_queue; + + /* for NCQ interrupt analysis */ + u32 dhfis_bits; + u32 dmafis_bits; + u32 sdbfis_bits; + + unsigned intncq_saw_d2h:1; + unsigned intncq_saw_dmas:1; + unsigned intncq_saw_sdb:1; + unsigned intncq_saw_backout:1; +}; + + #define NV_ADMA_CHECK_INTR(GCTL, PORT) ((GCTL) ( 1 (19 + (12 * (PORT) static int nv_init_one (struct pci_dev *pdev, const struct pci_device_id *ent); @@ -263,13 +323,29 @@ static void nv_adma_host_stop(struct ata static void nv_adma_post_internal_cmd(struct ata_queued_cmd *qc); static void nv_adma_tf_read(struct ata_port *ap, struct ata_taskfile *tf); +static void nv_mcp55_thaw(struct ata_port *ap); +static void nv_mcp55_freeze(struct ata_port *ap); +static void nv_swncq_error_handler(struct ata_port *ap); +static int nv_swncq_slave_config(struct scsi_device *sdev); +static int nv_swncq_port_start(struct ata_port *ap); +static void nv_swncq_qc_prep(struct ata_queued_cmd *qc); +static void nv_swncq_fill_sg(struct ata_queued_cmd *qc); +static unsigned int nv_swncq_qc_issue(struct ata_queued_cmd *qc); +static void nv_swncq_irq_clear(struct ata_port *ap, u16 fis); +static irqreturn_t nv_swncq_interrupt(int irq, void *dev_instance); +#ifdef CONFIG_PM +static int nv_swncq_port_suspend(struct ata_port *ap, pm_message_t mesg); +static int nv_swncq_port_resume(struct ata_port *ap); +#endif + enum nv_host_type { GENERIC, NFORCE2, NFORCE3 = NFORCE2, /* NF2 == NF3 as far as sata_nv is concerned */ CK804, - ADMA + ADMA, + SWNCQ }; static const struct pci_device_id nv_pci_tbl[] = { @@ -280,13 +356,13 @@ static const struct pci_device_id nv_pci { PCI_VDEVICE(NVIDIA, PCI_DEVICE_ID_NVIDIA_NFORCE_CK804_SATA2), CK804 }, { PCI_VDEVICE(NVIDIA, PCI_DEVICE_ID_NVIDIA_NFORCE_MCP04_SATA), CK804 }, { PCI_VDEVICE(NVIDIA, PCI_DEVICE_ID_NVIDIA_NFORCE_MCP04_SATA2), CK804 }, - { PCI_VDEVICE(NVIDIA, PCI_DEVICE_ID_NVIDIA_NFORCE_MCP51_SATA), GENERIC }, - { PCI_VDEVICE(NVIDIA,
[patch 04/25] libata-add-irq_flags-to-struct-pata_platform_info-fix
From: Andrew Morton [EMAIL PROTECTED] Remove unneeded, undesirable cast of void*. Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Sonic Zhang [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/pata_platform.c |2 +- 1 files changed, 1 insertion(+), 1 deletion(-) diff -puN drivers/ata/pata_platform.c~libata-add-irq_flags-to-struct-pata_platform_info-fix drivers/ata/pata_platform.c --- a/drivers/ata/pata_platform.c~libata-add-irq_flags-to-struct-pata_platform_info-fix +++ a/drivers/ata/pata_platform.c @@ -209,7 +209,7 @@ static int __devinit pata_platform_probe ap-ioaddr.altstatus_addr = ap-ioaddr.ctl_addr; - pp_info = (struct pata_platform_info *)(pdev-dev.platform_data); + pp_info = pdev-dev.platform_data; pata_platform_setup_port(ap-ioaddr, pp_info); /* activate */ _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 06/25] sata_nv: allow changing queue depth
From: Robert Hancock [EMAIL PROTECTED] The sata_nv driver was missing the change_queue_depth hook in the SCSI host template which the other NCQ-capable libata drivers had. This made it impossible to change the queue depth by user request. Add this in. Signed-off-by: Robert Hancock [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/sata_nv.c |1 + 1 files changed, 1 insertion(+) diff -puN drivers/ata/sata_nv.c~sata_nv-allow-changing-queue-depth drivers/ata/sata_nv.c --- a/drivers/ata/sata_nv.c~sata_nv-allow-changing-queue-depth +++ a/drivers/ata/sata_nv.c @@ -420,6 +420,7 @@ static struct scsi_host_template nv_swnc .name = DRV_NAME, .ioctl = ata_scsi_ioctl, .queuecommand = ata_scsi_queuecmd, + .change_queue_depth = ata_scsi_change_queue_depth, .can_queue = ATA_MAX_QUEUE, .this_id= ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 07/25] libata: adjust libata to ignore errors after spinup
From: Ryan Power [EMAIL PROTECTED] Adjust libata to ignore errors after spinup This patch is to ignore errors from the spinup attempt if the drive is in the standby id state. Signed-off-by: Ryan Power [EMAIL PROTECTED] Acked-by: Mark Lord [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/libata-core.c |2 +- 1 files changed, 1 insertion(+), 1 deletion(-) diff -puN drivers/ata/libata-core.c~libata-adjust-libata-to-ignore-errors-after drivers/ata/libata-core.c --- a/drivers/ata/libata-core.c~libata-adjust-libata-to-ignore-errors-after +++ a/drivers/ata/libata-core.c @@ -1723,7 +1723,7 @@ int ata_dev_read_id(struct ata_device *d tf.protocol = ATA_PROT_NODATA; tf.flags |= ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE; err_mask = ata_exec_internal(dev, tf, NULL, DMA_NONE, NULL, 0); - if (err_mask) { + if (err_mask id[2] != 0x738c) { rc = -EIO; reason = SPINUP failed; goto err_out; _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 12/25] libata: ACPI checks for 80wire cable: headers
From: Alan Cox [EMAIL PROTECTED] We can use the ACPI mode information with several drivers as a hint to cable type. If the ACPI mode set by the BIOS is faster than UDMA33 then we know the BIOS thinks there are 80wire cables. If it doesn't set such a mode or it has no ACPI method then we get no further information and can rely on existing approaches Introduce the function headers needed. Null it out for non ACPI boxes Signed-off-by: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- include/linux/libata.h |6 ++ 1 files changed, 6 insertions(+) diff -puN include/linux/libata.h~libata-acpi-checks-for-80wire-cable-headers include/linux/libata.h --- a/include/linux/libata.h~libata-acpi-checks-for-80wire-cable-headers +++ a/include/linux/libata.h @@ -1053,6 +1053,12 @@ static inline int ata_port_max_devices(c return 1; } +/* libata-acpi.c */ +#ifdef CONFIG_ATA_ACPI +extern int ata_acpi_cbl_80wire(struct ata_port *ap); +#else +static inline int ata_acpi_cbl_80wire(struct ata_port *ap) { return 0; } +#endif static inline u8 ata_chk_status(struct ata_port *ap) { _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 20/25] scsi: expose AN support to user space
From: Kristen Carlson Accardi [EMAIL PROTECTED] If a scsi_device supports async notification for media change, then let user space know this capability exists by creating a new sysfs entry media_change_notify, which will be 1 if it is supported, and 0 if not supported. Create a routine which allows scsi devices to send a uevent when media change events occur. Signed-off-by: Kristen Carlson Accardi [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: James Bottomley [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/scsi/scsi_lib.c| 83 +++ drivers/scsi/scsi_scan.c |1 drivers/scsi/scsi_sysfs.c | 13 + include/scsi/scsi_device.h | 15 +- 4 files changed, 111 insertions(+), 1 deletion(-) diff -puN drivers/scsi/scsi_lib.c~scsi-expose-an-support-to-user-space drivers/scsi/scsi_lib.c --- a/drivers/scsi/scsi_lib.c~scsi-expose-an-support-to-user-space +++ a/drivers/scsi/scsi_lib.c @@ -64,6 +64,11 @@ static struct scsi_host_sg_pool scsi_sg_ }; #undef SP +/* must match scsi_device_event enum in scsi_device.h */ +static char * scsi_device_event_strings[] = { + MEDIA_CHANGE=1, +}; + static void scsi_run_queue(struct request_queue *q); /* @@ -2007,6 +2012,84 @@ scsi_device_set_state(struct scsi_device EXPORT_SYMBOL(scsi_device_set_state); /** + * scsi_device_set_event - Add a new Async event to the event list + * @sdev: scsi_device event occurred on + * @event: the scsi device event + * + * Add a new scsi_device_event_info struct to the scsi_device_event_list + * queue. This may be called from interrupt context. + * + * Returns 0 if successful, -ENOMEM otherwise. + */ +static int +scsi_device_set_event(struct scsi_device *sdev, enum scsi_device_event event) +{ + struct scsi_device_event_info *scsi_event; + unsigned long flags; + + scsi_event = kzalloc(sizeof(*scsi_event), GFP_ATOMIC); + if (!scsi_event) + return -ENOMEM; + INIT_LIST_HEAD(scsi_event-link); + scsi_event-event = event; + spin_lock_irqsave(sdev-list_lock, flags); + list_add_tail(scsi_event-link, sdev-sdev_event_list); + spin_unlock_irqrestore(sdev-list_lock, flags); + return 0; +} + +/** + * scsi_device_event_notify_thread - send a uevent for each scsi event + * @work: work struct for scsi_device + * + * Traverse the queue of scsi device events, dequeue each event and + * send a uevent. Frees event. May not be called from interrupt. + */ +static void scsi_event_notify_thread(struct work_struct *work) +{ + struct scsi_device *sdev; + char *envp[] = { NULL, NULL }; + struct list_head *tmp; + struct list_head *next; + struct scsi_device_event_info *sdev_event; + unsigned long flags; + + sdev = container_of(work, struct scsi_device, ew.work); + list_for_each_safe(tmp, next, sdev-sdev_event_list) { + sdev_event = list_entry(tmp, struct scsi_device_event_info, + link); + spin_lock_irqsave(sdev-list_lock, flags); + list_del(sdev_event-link); + spin_unlock_irqrestore(sdev-list_lock, flags); + envp[0] = scsi_device_event_strings[sdev_event-event-1]; + kobject_uevent_env(sdev-sdev_gendev.kobj, KOBJ_CHANGE, envp); + kfree(sdev_event); + } +} + +/** + * scsi_device_event_notify - store event info and send an event + * @sdev: scsi_device event occurred on + * @event: the scsi device event + * + * Store the event information and then switch process context + * so that the event may be sent to user space. + * This may be called from interrupt context. + * + * Returns 0 if successful, -ENOMEM otherwise. + */ +int scsi_device_event_notify(struct scsi_device *sdev, enum scsi_device_event event) +{ + int rc; + + rc = scsi_device_set_event(sdev, event); + if (!rc) + execute_in_process_context(scsi_event_notify_thread, sdev-ew); + return rc; +} +EXPORT_SYMBOL_GPL(scsi_device_event_notify); + +/** * scsi_device_quiesce - Block user issued commands. * @sdev: scsi device to quiesce. * diff -puN drivers/scsi/scsi_scan.c~scsi-expose-an-support-to-user-space drivers/scsi/scsi_scan.c --- a/drivers/scsi/scsi_scan.c~scsi-expose-an-support-to-user-space +++ a/drivers/scsi/scsi_scan.c @@ -253,6 +253,7 @@ static struct scsi_device *scsi_alloc_sd INIT_LIST_HEAD(sdev-same_target_siblings); INIT_LIST_HEAD(sdev-cmd_list); INIT_LIST_HEAD(sdev-starved_entry); + INIT_LIST_HEAD(sdev-sdev_event_list); spin_lock_init(sdev-list_lock); sdev-sdev_gendev.parent = get_device(starget-dev); diff -puN drivers/scsi/scsi_sysfs.c~scsi-expose-an-support-to-user-space drivers/scsi/scsi_sysfs.c ---
[patch 10/25] ALPM: enable link power management for ata drivers
From: Kristen Carlson Accardi [EMAIL PROTECTED] libata drivers can define a function (enable_pm) that will perform hardware specific actions to enable whatever power management policy the user set up from the scsi sysfs interface if the driver supports it. This power management policy will be activated after all disks have been enumerated and intialized. Drivers should also define disable_pm, which will turn off link power management, but not change link power management policy. Signed-off-by: Kristen Carlson Accardi [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- Documentation/scsi/link_power_management_policy.txt | 19 + drivers/ata/libata-core.c | 41 +++ drivers/ata/libata-eh.c |3 drivers/ata/libata-scsi.c | 118 ++ include/linux/ata.h |6 include/linux/libata.h | 21 + 6 files changed, 206 insertions(+), 2 deletions(-) diff -puN /dev/null Documentation/scsi/link_power_management_policy.txt --- /dev/null +++ a/Documentation/scsi/link_power_management_policy.txt @@ -0,0 +1,19 @@ +This parameter allows the user to set the link (interface) power management. +There are 3 possible options: + +Value Effect + +min_power Tell the controller to try to make the link use the + least possible power when possible. This may + sacrifice some performance due to increased latency + when coming out of lower power states. + +max_performanceGenerally, this means no power management. Tell + the controller to have performance be a priority + over power management. + +medium_power Tell the controller to enter a lower power state + when possible, but do not enter the lowest power + state, thus improving latency over min_power setting. + + diff -puN drivers/ata/libata-core.c~alpm-enable-link-power-management-for-ata-drivers drivers/ata/libata-core.c --- a/drivers/ata/libata-core.c~alpm-enable-link-power-management-for-ata-drivers +++ a/drivers/ata/libata-core.c @@ -1993,6 +1993,9 @@ int ata_dev_configure(struct ata_device if (dev-flags ATA_DFLAG_LBA48) dev-max_sectors = ATA_MAX_SECTORS_LBA48; + if (ata_id_has_hipm(dev-id) || ata_id_has_dipm(dev-id)) + dev-flags |= ATA_DFLAG_IPM; + 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 @@ -2018,6 +2021,13 @@ int ata_dev_configure(struct ata_device dev-max_sectors = min_t(unsigned int, ATA_MAX_SECTORS_128, dev-max_sectors); + if (ata_dev_blacklisted(dev) ATA_HORKAGE_IPM) { + dev-horkage |= ATA_HORKAGE_IPM; + + /* reset link pm_policy for this port to no pm */ + ap-pm_policy = MAX_PERFORMANCE; + } + if (ap-ops-dev_config) ap-ops-dev_config(dev); @@ -5913,6 +5923,27 @@ int ata_flush_cache(struct ata_device *d return 0; } +static void ata_host_disable_link_pm(struct ata_host *host) +{ + int i; + + for (i = 0; i host-n_ports; i++) { + struct ata_port *ap = host-ports[i]; + if (ap-ops-disable_pm) + ap-ops-disable_pm(ap); + } +} + +static void ata_host_enable_link_pm(struct ata_host *host) +{ + int i; + + for (i = 0; i host-n_ports; i++) { + struct ata_port *ap = host-ports[i]; + ata_scsi_set_link_pm_policy(ap, ap-pm_policy); + } +} + #ifdef CONFIG_PM static int ata_host_request_pm(struct ata_host *host, pm_message_t mesg, unsigned int action, unsigned int ehi_flags, @@ -5980,6 +6011,12 @@ int ata_host_suspend(struct ata_host *ho { int rc; + /* +* disable link pm on all ports before requesting +* any pm activity +*/ + ata_host_disable_link_pm(host); + rc = ata_host_request_pm(host, mesg, 0, ATA_EHI_QUIET, 1); if (rc == 0) host-dev-power.power_state = mesg; @@ -6002,6 +6039,9 @@ void ata_host_resume(struct ata_host *ho ata_host_request_pm(host, PMSG_ON, ATA_EH_SOFTRESET, ATA_EHI_NO_AUTOPSY | ATA_EHI_QUIET, 0); host-dev-power.power_state = PMSG_ON; + + /* reenable link pm */ + ata_host_enable_link_pm(host); } #endif @@ -6498,6 +6538,7 @@ int ata_host_register(struct ata_host *h
[patch 23/25] ST340823A, HPA and libata
From: Alan Cox [EMAIL PROTECTED] Ok this is a different approach to handling it - knowing it is an off by one so we can handle the drive if clipped Signed-off-by: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/libata-core.c |7 +++ include/linux/libata.h|1 + 2 files changed, 8 insertions(+) diff -puN drivers/ata/libata-core.c~st340823a-hpa-and-libata drivers/ata/libata-core.c --- a/drivers/ata/libata-core.c~st340823a-hpa-and-libata +++ a/drivers/ata/libata-core.c @@ -988,6 +988,10 @@ static u64 ata_hpa_resize(struct ata_dev else hpa_sectors = ata_read_native_max_address(dev); + /* Reports one sector too many */ + if (hpa_sectors (dev-horkage ATA_HORKAGE_HPA_SIZE)) + hpa_sectors--; + if (hpa_sectors sectors) { ata_dev_printk(dev, KERN_INFO, Host Protected Area detected:\n @@ -3863,6 +3867,9 @@ static const struct ata_blacklist_entry /* Devices with NCQ limits */ + /* Devices which report 1 sector over size HPA */ + { ST340823A, NULL, ATA_HORKAGE_HPA_SIZE, }, + /* End Marker */ { } }; diff -puN include/linux/libata.h~st340823a-hpa-and-libata include/linux/libata.h --- a/include/linux/libata.h~st340823a-hpa-and-libata +++ a/include/linux/libata.h @@ -315,6 +315,7 @@ enum { ATA_HORKAGE_NONCQ = (1 2), /* Don't use NCQ */ ATA_HORKAGE_MAX_SEC_128 = (1 3), /* Limit max sects to 128 */ ATA_HORKAGE_IPM = (1 4), /* LPM problems */ + ATA_HORKAGE_HPA_SIZE= (1 6), /* Reports native size off by one */ }; enum hsm_task_states { _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 11/25] ALPM: enable Aggressive Link Power management for AHCI controllers.
From: Kristen Carlson Accardi [EMAIL PROTECTED] This patch will set the correct bits to turn on Aggressive Link Power Management (ALPM) for the ahci driver. This will cause the controller and disk to negotiate a lower power state for the link when there is no activity (see the AHCI 1.x spec for details). This feature is mutually exclusive with Hot Plug, so when ALPM is enabled, Hot Plug is disabled. ALPM will be enabled by default, but it is settable via the scsi host syfs interface. Possible settings for this feature are: Setting Effect -- min_power ALPM is enabled, and link set to enter lowest power state (SLUMBER) when idle Hot plug not allowed. max_performance ALPM is disabled, Hot Plug is allowed medium_powerALPM is enabled, and link set to enter second lowest power state (PARTIAL) when idle. Hot plug not allowed. Signed-off-by: Kristen Carlson Accardi [EMAIL PROTECTED] Cc: Jeff Garzik [EMAIL PROTECTED] Cc: Tejun Heo [EMAIL PROTECTED] Cc: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/ahci.c | 178 +++ 1 files changed, 178 insertions(+) diff -puN drivers/ata/ahci.c~alpm-enable-aggressive-link-power-management-for-ahci-controllers drivers/ata/ahci.c --- a/drivers/ata/ahci.c~alpm-enable-aggressive-link-power-management-for-ahci-controllers +++ a/drivers/ata/ahci.c @@ -48,6 +48,9 @@ #define DRV_NAME ahci #define DRV_VERSION2.3 +static int ahci_enable_alpm(struct ata_port *ap, + enum link_pm policy); +static int ahci_disable_alpm(struct ata_port *ap); enum { AHCI_PCI_BAR= 5, @@ -98,6 +101,7 @@ enum { /* HOST_CAP bits */ HOST_CAP_SSC= (1 14), /* Slumber capable */ HOST_CAP_CLO= (1 24), /* Command List Override support */ + HOST_CAP_ALPM = (1 26), /* Aggressive Link PM support */ HOST_CAP_SSS= (1 27), /* Staggered Spin-up */ HOST_CAP_SNTF = (1 29), /* SNotification register */ HOST_CAP_NCQ= (1 30), /* Native Command Queueing */ @@ -153,6 +157,8 @@ enum { PORT_IRQ_PIOS_FIS | PORT_IRQ_D2H_REG_FIS, /* PORT_CMD bits */ + PORT_CMD_ASP= (1 27), /* Aggressive Slumber/Partial */ + PORT_CMD_ALPE = (1 26), /* Aggressive Link PM enable */ PORT_CMD_ATAPI = (1 24), /* Device is ATAPI */ PORT_CMD_LIST_ON= (1 15), /* cmd list DMA engine running */ PORT_CMD_FIS_ON = (1 14), /* FIS DMA engine running */ @@ -244,6 +250,11 @@ static int ahci_pci_device_suspend(struc static int ahci_pci_device_resume(struct pci_dev *pdev); #endif +static struct class_device_attribute *ahci_shost_attrs[] = { + class_device_attr_link_power_management_policy, + NULL +}; + static struct scsi_host_template ahci_sht = { .module = THIS_MODULE, .name = DRV_NAME, @@ -261,6 +272,7 @@ static struct scsi_host_template ahci_sh .slave_configure= ata_scsi_slave_config, .slave_destroy = ata_scsi_slave_destroy, .bios_param = ata_std_bios_param, + .shost_attrs= ahci_shost_attrs, }; static const struct ata_port_operations ahci_ops = { @@ -292,6 +304,8 @@ static const struct ata_port_operations .port_suspend = ahci_port_suspend, .port_resume= ahci_port_resume, #endif + .enable_pm = ahci_enable_alpm, + .disable_pm = ahci_disable_alpm, .port_start = ahci_port_start, .port_stop = ahci_port_stop, @@ -778,6 +792,156 @@ static void ahci_power_up(struct ata_por writel(cmd | PORT_CMD_ICC_ACTIVE, port_mmio + PORT_CMD); } +static int ahci_disable_alpm(struct ata_port *ap) +{ + void __iomem *port_mmio = ahci_port_base(ap); + u32 cmd, scontrol; + struct ahci_port_priv *pp = ap-private_data; + + /* +* disable Interface Power Management State Transitions +* This is accomplished by setting bits 8:11 of the +* SATA Control register +*/ + scontrol = readl(port_mmio + PORT_SCR_CTL); + scontrol |= (0x3 8); + writel(scontrol, port_mmio + PORT_SCR_CTL); + + /* get the existing command bits */ + cmd = readl(port_mmio + PORT_CMD); + + /* disable ALPM and ASP */ + cmd = ~PORT_CMD_ASP; + cmd = ~PORT_CMD_ALPE; + + /* force the interface back to active */ + cmd |= PORT_CMD_ICC_ACTIVE; + + /* write out new cmd value */ + writel(cmd, port_mmio + PORT_CMD); + cmd = readl(port_mmio + PORT_CMD); + + /* wait 10ms to be sure we've come out of any low
[patch 14/25] libata: ACPI checks for 80wire cable: use in pata_amd
From: Alan Cox [EMAIL PROTECTED] We can make use of this on the pata_amd driver as many Nvidia devices don't have reliable cable detect. Signed-off-by: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/pata_amd.c |3 +++ 1 files changed, 3 insertions(+) diff -puN drivers/ata/pata_amd.c~libata-acpi-checks-for-80wire-cable-use-in-pata_amd drivers/ata/pata_amd.c --- a/drivers/ata/pata_amd.c~libata-acpi-checks-for-80wire-cable-use-in-pata_amd +++ a/drivers/ata/pata_amd.c @@ -268,6 +268,9 @@ static int nv_cable_detect(struct ata_po 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; } _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 13/25] libata: ACPI checks for 80wire cable: implementation
From: Alan Cox [EMAIL PROTECTED] Provide actual methods for checking if the ACPI support thinks the cable is 80wire, or doesn't know Signed-off-by: Alan Cox [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/libata-acpi.c | 38 1 files changed, 38 insertions(+) diff -puN drivers/ata/libata-acpi.c~libata-acpi-checks-for-80wire-cable-implementation drivers/ata/libata-acpi.c --- a/drivers/ata/libata-acpi.c~libata-acpi-checks-for-80wire-cable-implementation +++ a/drivers/ata/libata-acpi.c @@ -296,6 +296,44 @@ static int ata_dev_get_GTF(struct ata_de } /** + * ata_acpi_cbl_80wire - Check for 80 wire cable + * @ap: Port to check + * + * Return 1 if the ACPI mode data for this port indicates the BIOS selected + * an 80wire mode. + */ + +int ata_acpi_cbl_80wire(struct ata_port *ap) +{ + struct ata_acpi_gtm gtm; + int valid = 0; + + /* No _GTM data, no information */ + if (ata_acpi_gtm(ap, gtm) 0) + return 0; + + /* 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-device[0])) + return 1; + if ((valid 2) ata_dev_enabled(ap-device[1])) + return 1; + return 0; +} + +EXPORT_SYMBOL_GPL(ata_acpi_cbl_80wire); + +/** * taskfile_load_raw - send taskfile registers to host controller * @dev: target ATA device * @gtf: raw ATA taskfile register set (0x1f1 - 0x1f7) _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
[patch 24/25] pata_cmd64x: Set up MWDMA modes properly
From: Alan Cox [EMAIL PROTECTED] Set the MWDMA timing by updating the correct registers. Split the PIO path as this is mostly shared code. Wants testing. Signed-off-by: Alan Cox [EMAIL PROTECTED] Tested-by: Mikael Pettersson [EMAIL PROTECTED] Signed-off-by: Andrew Morton [EMAIL PROTECTED] --- drivers/ata/pata_cmd64x.c | 37 +--- 1 files changed, 26 insertions(+), 11 deletions(-) diff -puN drivers/ata/pata_cmd64x.c~pata_cmd64x-set-up-mwdma-modes-properly drivers/ata/pata_cmd64x.c --- a/drivers/ata/pata_cmd64x.c~pata_cmd64x-set-up-mwdma-modes-properly +++ a/drivers/ata/pata_cmd64x.c @@ -31,7 +31,7 @@ #include linux/libata.h #define DRV_NAME pata_cmd64x -#define DRV_VERSION 0.2.4 +#define DRV_VERSION 0.2.5 /* * CMD64x specific registers definition. @@ -88,14 +88,15 @@ static int cmd648_cable_detect(struct at } /** - * cmd64x_set_piomode - set initial PIO mode data + * cmd64x_set_piomode - set PIO and MWDMA timing * @ap: ATA interface * @adev: ATA device + * @mode: mode * - * Called to do the PIO mode setup. + * Called to do the PIO and MWDMA mode setup. */ -static void cmd64x_set_piomode(struct ata_port *ap, struct ata_device *adev) +static void cmd64x_set_timing(struct ata_port *ap, struct ata_device *adev, u8 mode) { struct pci_dev *pdev = to_pci_dev(ap-host-dev); struct ata_timing t; @@ -117,8 +118,9 @@ static void cmd64x_set_piomode(struct at int arttim = arttim_port[ap-port_no][adev-devno]; int drwtim = drwtim_port[ap-port_no][adev-devno]; - - if (ata_timing_compute(adev, adev-pio_mode, t, T, 0) 0) { + /* ata_timing_compute is smart and will produce timings for MWDMA + that don't violate the drives PIO capabilities. */ + if (ata_timing_compute(adev, mode, t, T, 0) 0) { printk(KERN_ERR DRV_NAME : mode computation failed.\n); return; } @@ -168,6 +170,20 @@ static void cmd64x_set_piomode(struct at } /** + * cmd64x_set_piomode - set initial PIO mode data + * @ap: ATA interface + * @adev: ATA device + * + * Used when configuring the devices ot set the PIO timings. All the + * actual work is done by the PIO/MWDMA setting helper + */ + +static void cmd64x_set_piomode(struct ata_port *ap, struct ata_device *adev) +{ + cmd64x_set_timing(ap, adev, adev-pio_mode); +} + +/** * cmd64x_set_dmamode - set initial DMA mode data * @ap: ATA interface * @adev: ATA device @@ -180,9 +196,6 @@ static void cmd64x_set_dmamode(struct at static const u8 udma_data[] = { 0x30, 0x20, 0x10, 0x20, 0x10, 0x00 }; - static const u8 mwdma_data[] = { - 0x30, 0x20, 0x10 - }; struct pci_dev *pdev = to_pci_dev(ap-host-dev); u8 regU, regD; @@ -208,8 +221,10 @@ static void cmd64x_set_dmamode(struct at regU |= 1 adev-devno; /* UDMA on */ if (adev-dma_mode 2) /* 15nS timing */ regU |= 4 adev-devno; - } else - regD |= mwdma_data[adev-dma_mode - XFER_MW_DMA_0] shift; + } else { + regU = ~ (1 adev-devno); /* UDMA off */ + cmd64x_set_timing(ap, adev, adev-dma_mode); + } regD |= 0x20 adev-devno; _ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 1/2] pata_hpt37x: actually clock HPT374 by 50 MHz DPLL
one. Actually by now it bears almost no resemblence any of them Indeed, unfortunately... Oh I think its very fortunate. The original IDE one is 3 semi-related drivers in one file all falling over one another. At least we can now break them individually 8) Alan - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] pata_artop: fix UDMA5 for AEC6280[R] and UDMA6 for AEC6880[R]
BTW presence of the above bugs would strongly indicate that pata_artop has never been tested (properly) with AEC6x80[R], otherwise these bugs should have been noticed and fixed much earlier. People don't seem to notice minor speed limiting errors, and its a pretty obscure controller too. Not suprised (it took ages for them to notice the CMD64x one too). It has however been tested and works pretty well for most cases. There's one platform where you have to hack both drivers to make them work which I need to investigate further. - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: AMD64 dma_alloc_coherent crashes on non PCI device (was SATA open bugs) II
On Fri, 2007-08-10 at 17:58 +0100, Alan Cox wrote: Not in non platform code, please ... somewhere on the Janitor's list is moving the dma_mask from the bus specific devices into the generic device ... when that happens this quantity will become u64 and they won't know what to do with the NULL check. Ok filed for kernel summit Surely we don't need to wait until then? This is the correct fix, isn't it? (Obviously I'll split it into a generic and a pcmcia specific piece if it looks OK to everyone). It sets the PCMCIA dma_mask up correctly and introduces a DMA_MASK_NONE (I prefer that to DMA_0BIT_MASK but I can add that too if people want) and gives Alan his is_device_dma_capable() API. James diff --git a/drivers/pcmcia/ds.c b/drivers/pcmcia/ds.c index a996071..b3837d3 100644 --- a/drivers/pcmcia/ds.c +++ b/drivers/pcmcia/ds.c @@ -23,6 +23,7 @@ #include linux/crc32.h #include linux/firmware.h #include linux/kref.h +#include linux/dma-mapping.h #define IN_CARD_SERVICES #include pcmcia/cs_types.h @@ -670,6 +671,9 @@ struct pcmcia_device * pcmcia_device_add(struct pcmcia_socket *s, unsigned int f p_dev-dev.bus = pcmcia_bus_type; p_dev-dev.parent = s-dev.parent; p_dev-dev.release = pcmcia_release_dev; + /* by default don't allow DMA */ + p_dev-dma_mask = DMA_MASK_NONE; + p_dev-dev.dma_mask = p_dev-dma_mask; bus_id_len = sprintf (p_dev-dev.bus_id, %d.%d, p_dev-socket-sock, p_dev-device_no); p_dev-devname = kmalloc(6 + bus_id_len + 1, GFP_KERNEL); diff --git a/include/linux/dma-mapping.h b/include/linux/dma-mapping.h index 2dc21cb..0ebfafb 100644 --- a/include/linux/dma-mapping.h +++ b/include/linux/dma-mapping.h @@ -24,6 +24,8 @@ enum dma_data_direction { #define DMA_28BIT_MASK 0x0fffULL #define DMA_24BIT_MASK 0x00ffULL +#define DMA_MASK_NONE 0x0ULL + static inline int valid_dma_direction(int dma_direction) { return ((dma_direction == DMA_BIDIRECTIONAL) || @@ -31,6 +33,11 @@ static inline int valid_dma_direction(int dma_direction) (dma_direction == DMA_FROM_DEVICE)); } +static inline int is_device_dma_capable(struct device *dev) +{ + return dev-dma_mask != NULL *dev-dma_mask != DMA_MASK_NONE; +} + #ifdef CONFIG_HAS_DMA #include asm/dma-mapping.h #else diff --git a/include/pcmcia/ds.h b/include/pcmcia/ds.h index 90ef552..f047a1f 100644 --- a/include/pcmcia/ds.h +++ b/include/pcmcia/ds.h @@ -184,6 +184,7 @@ struct pcmcia_device { char * prod_id[4]; + u64 dma_mask; struct device dev; #ifdef CONFIG_PCMCIA_IOCTL - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] hpt366: UltraDMA filtering for SATA cards
Hi, On Friday 10 August 2007, Sergei Shtylyov wrote: Bartlomiej Zolnierkiewicz wrote: The Marvell bridge chips used on HighPoint SATA cards do not seem to support the UltraDMA modes 1, 2, and 3 (as well as any MWDMA modes), so the driver needs to account for this in the udma_filter() method. In order to achieve that, do the following changes: - install the method for all chips, not only HPT36x/370 (improve code formatting by killing an extra tabs while at it); - add to the end of the 'switch' statement in hpt3xx_udma_filter() case for HPT372[AN] and HPT374 chips upon which the SATA cards are based and check there whether we're dealing with SATA drive (by looking at words 80 and 93 of the drive's identify data), reorder HPT370[A] cases for consistency... Signed-off-by: Sergei Shtylyov [EMAIL PROTECTED] applied but drivers/ide/pci/hpt366.c | 75 ++- 1 files changed, 43 insertions(+), 32 deletions(-) Index: linux-2.6/drivers/ide/pci/hpt366.c === --- linux-2.6.orig/drivers/ide/pci/hpt366.c +++ linux-2.6/drivers/ide/pci/hpt366.c [...] @@ -517,29 +517,17 @@ static int check_in_drive_list(ide_drive } /* - * Note for the future; the SATA hpt37x we must set - * either PIO or UDMA modes 0,4,5 + * The Marvell bridge chips used on the HighPoint SATA cards do not seem + * to support the UltraDMA modes 1, 2, and 3 -- as well as any MWDMA modes + * (that we should start filtering out once the IDE core allows that). */ - static u8 hpt3xx_udma_filter(ide_drive_t *drive) { struct hpt_info *info = pci_get_drvdata(HWIF(drive)-pci_dev); + struct hd_driveid *id = drive-id; u8 mask; switch (info-chip_type) { HPT374/HPT372[NA] case could be added here so re-ordering wouldn't be needed. I did that on purpose -- to keep an alphanumeric ordering. ;-) @@ -551,6 +539,30 @@ static u8 hpt3xx_udma_filter(ide_drive_t check_in_drive_list(drive, bad_ata66_3)) mask = 0x07; break; + case HPT370: + if (!HPT370_ALLOW_ATA100_5 || + check_in_drive_list(drive, bad_ata100_5)) + mask = 0x1f; + else + mask = 0x3f; ATA_UDMA* defines should be used if you insist on re-ordering OK, recasting... + case HPT372 : + case HPT372A: + case HPT372N: + case HPT374 : + /* +* Check for SATA drive by verifying that the word 93 is 0 and +* the drive is ATA-5 or higher compatible. +*/ + if (id-hw_config == 0 (id-major_rev_num 0x7fe0)) Same check as in ide-iops.c::eighty_ninty_three(). Would make sense to add ide_id_is_sata_dev() inline to linux/ide.h. Actually, libata already has ata_id_is_sata() defined in linux/ata.h but it takes const u16 * argument. If we can use this one instead it would be even better. + return 0x71; + /* fall thru */ default: return 0x7f; HPT371[N]/HPT302[N] will use the default mask which is correct but adds hidden dependency on HPT*_ALLOW_ATA_133 being always defined as 1. No, it doesn't since all this will be AND'ed with hwif-udma_mask... But wait, ide_rate_filter has the different code, it just sets mask to the result of the udma_filter() method... I wonder which code is correct? :-O I bet that you are looking at vanilla kernel which currently misses 101 files changed, 1880 insertions(+), 2828 deletions(-) please look at -mm or IDE quilt tree instead. :) ide_rate_filter() happily uses ide_find_dma_mode() nowadays (however this hpt366 patch is for vanilla kernel which doesn't have the needed changes). IMO all HPT*_ALLOW_ATA* defines should just go away... I think it's still worth to keep 'em alive for the possible blacklist additions. No strong feelings about these defines but I think that they actually make the code less readable and also more complex because they control _both_ DPLL used (through controlling max_ultra) and the maximum UDMA mask. Moreover they are _compile_ time options so for testing purposes we may as well ask user to change UDMA mask etc. Also now that -udma_filter is always present the initial hwif-ultra_mask doesn't matter so as well we may set it to ATA_UDMA6 (0x7f) and cleanup struct hpt_info (by removing max_ultra after fixing init_chipset_hpt366() to use info-chip_type = HPT374 check instead), It's all interesting but you've missed one aspect -- this will make the kernel larger while the current code keeps all this logic in the init.text section. We won't be adding a single line of new code: - the current -udma_filter implementation does everything needed already - in init_chipset_hpt366() we simply would replace if (info-max_ultra 6)
Re: [PATCH 1/2] hpt366: fix PCI clock detection for HPT374
On Friday 10 August 2007, Sergei Shtylyov wrote: Alan Cox wrote: + if (chip_type == HPT374 (PCI_FUNC(dev-devfn) 1)) { + struct pci_dev *dev1 = pci_get_slot(dev-bus, + dev-devfn - 1); Can be NULL Not really. This may not be called if it's NULL -- see hpt374_init_setup(). Maybe worth a comment though... + unsigned long io_base = pci_resource_start(dev1, 4); Kaboom That was a dud bomb. ;-) What stops a hot unplug of a 374 from causing that to occur. I don't see Pinned as in pci_get_device()? If so, see setup-ide.c:ide_scan_pcibus(). The IDE core does that for me. ide_scan_pcibus() is used iff IDE is built-in. Moreover pci_get_device() holds reference _only_ to the current PCI device (the reference count to @from PCI device is _always_ decremented). where you have the other pci_dev pinned on a hotplug on a box set to scan the devices in reverse order Function 1 will always be skipped, regardless of the scan order. Yes, but init_chipset_hpt366() will still try to access Function 1 even if earlier init_setup_hpt374() failed to obtain reference to it. (yes its an extremely obscure case ;)) Security through obscurity. :-) Not in this case. :-) Bart - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 3/11] au1xxx-ide: use ide_tune_dma()
On Friday 10 August 2007, Sergei Shtylyov wrote: Bartlomiej Zolnierkiewicz wrote: Good, that's what I lacked for hpt366.c! Were you planning to push it to Linus soon? Not really but if needed I will extract MWDMA filter part and push it sooner. Erm, may I just merge it to my patch (mentioning you of course)? Sure. I planned to cc: AU1XXX platform maintainers on this patch but to my surprise MAINTAINERS lacks AU1XXX entry. It's been solt out to Raza Microelectronics last year and those guys never sent a single patch to linux-mips... Thanks for the info. Bart - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Disk spin down issue on shut down/suspend to disk
Thomas Renninger wrote: On Thu, 2007-08-09 at 15:16 +, Pavel Machek wrote: Hi! firmwarekit-discuss [EMAIL PROTECTED] (added to CC list) see: http://linuxfirmwarekit.org/ But if I understand this problem right, this won't be easy. The ACPI tables are just parsed with system (iasl ...) and syntactical errors/warnings are printed out. I also thought about a test, interpreting the DSDT and read out values of cpufreq tables and sanity check them. AFAIK the linuxfirmwarekit is not designed for that atm. You need to compile in most parts of the acpica code and parse and interpret DSDT/SSDT code yourself in the firmwarekit core or inside a plugin, then do a walk_namespace call or whatever to find the functions/parts you like to examine. This is a lot work and needs a proper design (providing an interface to plugins to let them easily check specific AML/ASL code). Furthermore, we don't really know what we're looking for. How can you tell a given write to an ioport is issuing STANDBYNOW to an ATA disk or trying to power the machine off? Adding to the fun, many modern ATA controller have more than one way to issue a command. Maybe we can match accesses inside regions specified by PCI BARs :-( Hmmm... perhaps we should do it the other way. ACPI is allowed to touch the embedded controller, what else? Maybe we should warn as soon as API touches non-EC I/O port? This is not working... ACPI can and does access all kind of other I/O ports and other resources. Hmm, are the disk accesses done by ACPI via OperationRegion/Field declared variables? I try to get a check for those clashing with native drivers (hopefully this approach is successful for 2.6.24, can't say for sure yet), I wonder whether this one would give a warning like Libata driver is using the same SystemIO/SystemMem resources than ACPI OperationRegion declaration XY. This would not solve the problem, but at least show the need of such a test. Such ACPI vs native driver interference problems are very hard nuts (in identifying and solving). Can someone post an ASL code snippet how ACPI actually access the disk and in which parts/functions, pls. Again, it's not believed that this is being done via AML, but via a BIOS SMM trap on the ACPI sleep state hardware IO port. We have no real ability to find out what the BIOS is doing or prevent it in this case. -- Robert Hancock Saskatoon, SK, Canada To email, remove nospam from [EMAIL PROTECTED] Home Page: http://www.roberthancock.com/ - To unsubscribe from this list: send the line unsubscribe linux-ide in the body of a message to [EMAIL PROTECTED] More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [patch 3/4] Enable link power management for ata drivers
On Thu, 09 Aug 2007 14:24:16 PDT, Kristen Carlson Accardi said: +++ 2.6-git/drivers/ata/libata-scsi.c @@ -2904,6 +2976,52 @@ void ata_scsi_simulate(struct ata_device + if ((dev-horkage ATA_HORKAGE_IPM) || + !(dev-flags ATA_DFLAG_IPM)) { + ata_dev_printk(dev, KERN_ERR, + Unable to set Link PM policy\n); + ap-pm_policy = MAX_PERFORMANCE; + } KERN_INFO please, or KERN_WARNING at the highest, at least until such time as enough drivers support enough hardware that it really *does* qualify for this should not fail status. (OK, so I'm just cranky because I'm tired of seeing a KERN_ERR thrown at every reboot, just because the ata_piix driver doesn't know how to set this stuff up for the DVD?RW drive in my laptop. But when this goes upstream, lots of *other* people are going to get hit by the exact same thing and think there's something actually *wrong* with their hardware.) pgpqy1Uql0IBz.pgp Description: PGP signature