From: Tejun Heo <htejun@gmail.com>
To: Matthew Stapleton <matthew4196@gmail.com>
Cc: linux-ide@vger.kernel.org
Subject: Re: ICH7m problem using libata
Date: Wed, 03 Jan 2007 12:44:25 +0900 [thread overview]
Message-ID: <459B2699.8090506@gmail.com> (raw)
In-Reply-To: <200701031307.23024.matthew4196@gmail.com>
[-- Attachment #1: Type: text/plain, Size: 1653 bytes --]
Matthew Stapleton wrote:
> Tejun Heo wrote:
>> Please apply the attached patch over 2.6.19 and report what the kernel says.
>>
>> Thanks.
>>
>
> I got the following errors during the timeout when running hald:
>
> ata1.01: exception Emask 0x0 SAct 0x0 SErr 0x0 action 0x2 frozen
> ata1.01: cmd a0/00:00:00:00:20/00:00:00:00:00/b0 tag 0 cdb 0x1e data 0 in
> res 40/00:03:00:00:00/00:00:00:00:00/b0 Emask 0x4 (timeout)
> ata1.01: CDB: 1e:00:00:00:00:00:00:00 00:00:00:00:00:00:00:00 p=6
>
> ata1.01: exception Emask 0x0 SAct 0x0 SErr 0x0 action 0x2 frozen
> ata1.01: (BMDMA stat 0x64)
> ata1.01: cmd a0/01:00:00:00:00/00:00:00:00:00/b0 tag 0 cdb 0x25 data 8 in
> res 40/00:03:00:00:00/00:00:00:00:00/b0 Emask 0x4 (timeout)
> ata1.01: CDB: 25:00:00:00:00:00:00:00 00:00:00:00:00:00:00:00 p=7
>
> With my test program that opens and closes the cdrom drive every second, I got
> the following errors during the timeout:
>
> ata1.01: exception Emask 0x0 SAct 0x0 SErr 0x0 action 0x2 frozen
> ata1.01: (BMDMA stat 0x64)
> ata1.01: cmd a0/01:00:00:00:00/00:00:00:00:00/b0 tag 0 cdb 0x43 data 12 in
> res 40/00:03:00:00:00/00:00:00:00:00/b0 Emask 0x4 (timeout)
> ata1.01: CDB: 43:00:00:00:00:00:00:00 0c:40:00:00:00:00:00:00 p=7
>
> ata1.01: exception Emask 0x0 SAct 0x0 SErr 0x0 action 0x2 frozen
> ata1.01: (BMDMA stat 0x4)
> ata1.01: cmd a0/01:00:00:00:00/00:00:00:00:00/b0 tag 0 cdb 0x25 data 8 in
> res 40/00:03:00:00:00/00:00:00:00:00/b0 Emask 0x4 (timeout)
> ata1.01: CDB: 25:00:00:00:00:00:00:00 00:00:00:00:00:00:00:00 p=7
Can you try the attached patch over 2.6.19 and report full dmesg? Thanks.
--
tejun
[-- Attachment #2: cocktail-2.6.19.patch --]
[-- Type: text/x-patch, Size: 8082 bytes --]
Index: work/drivers/ata/libata-core.c
===================================================================
--- work.orig/drivers/ata/libata-core.c 2007-01-03 12:33:36.000000000 +0900
+++ work/drivers/ata/libata-core.c 2007-01-03 12:36:28.000000000 +0900
@@ -59,6 +59,10 @@
#include "libata.h"
+enum {
+ ATA_MODE_STRING_MAX = 16,
+};
+
/* debounce timing parameters in msecs { interval, duration, timeout } */
const unsigned long sata_deb_timing_normal[] = { 5, 100, 2000 };
const unsigned long sata_deb_timing_hotplug[] = { 25, 500, 2000 };
@@ -367,6 +371,7 @@ static int ata_xfer_mode2shift(unsigned
/**
* ata_mode_string - convert xfer_mask to string
* @xfer_mask: mask of bits supported; only highest bit counts.
+ * @buf: buffer of ATA_MODE_STRING_MAX bytes
*
* Determine string which represents the highest speed
* (highest bit in @modemask).
@@ -375,10 +380,10 @@ static int ata_xfer_mode2shift(unsigned
* None.
*
* RETURNS:
- * Constant C string representing highest speed listed in
- * @mode_mask, or the constant C string "<n/a>".
+ * Pointer to @buf which contains C string representing highest
+ * DMA and PIO speeds listed in @mode_mask.
*/
-static const char *ata_mode_string(unsigned int xfer_mask)
+static const char *ata_mode_string(unsigned int xfer_mask, char *buf)
{
static const char * const xfer_mode_str[] = {
"PIO0",
@@ -403,11 +408,24 @@ static const char *ata_mode_string(unsig
"UDMA7",
};
int highbit;
+ const char *str, *pio_str;
+
+ str = pio_str = "<n/a>";
highbit = fls(xfer_mask) - 1;
if (highbit >= 0 && highbit < ARRAY_SIZE(xfer_mode_str))
- return xfer_mode_str[highbit];
- return "<n/a>";
+ str = xfer_mode_str[highbit];
+
+ highbit = fls(xfer_mask & ATA_MASK_PIO) - 1;
+ if (highbit >= 0 && highbit < ARRAY_SIZE(xfer_mode_str))
+ pio_str = xfer_mode_str[highbit];
+
+ if (str != pio_str)
+ snprintf(buf, ATA_MODE_STRING_MAX, "%s:%s", str, pio_str);
+ else
+ snprintf(buf, ATA_MODE_STRING_MAX, "%s", str);
+
+ return buf;
}
static const char *sata_spd_string(unsigned int spd)
@@ -1389,7 +1407,7 @@ int ata_dev_configure(struct ata_device
{
struct ata_port *ap = dev->ap;
const u16 *id = dev->id;
- unsigned int xfer_mask;
+ char xfer_buf[ATA_MODE_STRING_MAX];
char revbuf[7]; /* XYZ-99\0 */
int rc;
@@ -1427,7 +1445,7 @@ int ata_dev_configure(struct ata_device
*/
/* find max transfer mode; for printk only */
- xfer_mask = ata_id_xfermask(id);
+ ata_mode_string(ata_id_xfermask(id), xfer_buf);
if (ata_msg_probe(ap))
ata_dump_id(id);
@@ -1463,8 +1481,7 @@ int ata_dev_configure(struct ata_device
if (ata_msg_drv(ap) && print_info)
ata_dev_printk(dev, KERN_INFO, "%s, "
"max %s, %Lu sectors: %s %s\n",
- revbuf,
- ata_mode_string(xfer_mask),
+ revbuf, xfer_buf,
(unsigned long long)dev->n_sectors,
lba_desc, ncq_desc);
} else {
@@ -1486,8 +1503,7 @@ int ata_dev_configure(struct ata_device
if (ata_msg_drv(ap) && print_info)
ata_dev_printk(dev, KERN_INFO, "%s, "
"max %s, %Lu sectors: CHS %u/%u/%u\n",
- revbuf,
- ata_mode_string(xfer_mask),
+ revbuf, xfer_buf,
(unsigned long long)dev->n_sectors,
dev->cylinders, dev->heads,
dev->sectors);
@@ -1526,8 +1542,7 @@ int ata_dev_configure(struct ata_device
/* print device info to dmesg */
if (ata_msg_drv(ap) && print_info)
ata_dev_printk(dev, KERN_INFO, "ATAPI, max %s%s\n",
- ata_mode_string(xfer_mask),
- cdb_intr_string);
+ xfer_buf, cdb_intr_string);
}
if (dev->horkage & ATA_HORKAGE_DIAGNOSTIC) {
@@ -2121,6 +2136,7 @@ int ata_timing_compute(struct ata_device
int ata_down_xfermask_limit(struct ata_device *dev, int force_pio0)
{
unsigned long xfer_mask;
+ char xfer_buf[ATA_MODE_STRING_MAX];
int highbit;
xfer_mask = ata_pack_xfermask(dev->pio_mask, dev->mwdma_mask,
@@ -2143,7 +2159,7 @@ int ata_down_xfermask_limit(struct ata_d
&dev->udma_mask);
ata_dev_printk(dev, KERN_WARNING, "limiting speed to %s\n",
- ata_mode_string(xfer_mask));
+ ata_mode_string(xfer_mask, xfer_buf));
return 0;
@@ -2154,6 +2170,7 @@ int ata_down_xfermask_limit(struct ata_d
static int ata_dev_set_mode(struct ata_device *dev)
{
unsigned int err_mask;
+ char xfer_buf[ATA_MODE_STRING_MAX];
int rc;
dev->flags &= ~ATA_DFLAG_PIO;
@@ -2174,8 +2191,10 @@ static int ata_dev_set_mode(struct ata_d
DPRINTK("xfer_shift=%u, xfer_mode=0x%x\n",
dev->xfer_shift, (int)dev->xfer_mode);
- ata_dev_printk(dev, KERN_INFO, "configured for %s\n",
- ata_mode_string(ata_xfer_mode2mask(dev->xfer_mode)));
+ ata_mode_string(ata_xfer_mode2mask(dev->xfer_mode) |
+ ata_xfer_mode2mask(dev->pio_mode), xfer_buf);
+ ata_dev_printk(dev, KERN_INFO, "configured for %s\n", xfer_buf);
+
return 0;
}
@@ -2227,6 +2246,9 @@ int ata_set_mode(struct ata_port *ap, st
pio_mask = ata_pack_xfermask(dev->pio_mask, 0, 0);
dma_mask = ata_pack_xfermask(0, dev->mwdma_mask, dev->udma_mask);
dev->pio_mode = ata_xfer_mask2mode(pio_mask);
+ /* XXX - debug */
+ if (dev->pio_mode)
+ dev->pio_mode = XFER_PIO_0;
dev->dma_mode = ata_xfer_mask2mode(dma_mask);
found = 1;
@@ -3109,6 +3131,7 @@ static void ata_dev_xfermask(struct ata_
struct ata_port *ap = dev->ap;
struct ata_host *host = ap->host;
unsigned long xfer_mask;
+ int i;
/* controller modes available */
xfer_mask = ata_pack_xfermask(ap->pio_mask,
@@ -3120,10 +3143,27 @@ static void ata_dev_xfermask(struct ata_
if (ap->cbl == ATA_CBL_PATA40)
xfer_mask &= ~(0xF8 << ATA_SHIFT_UDMA);
+ /* apply xfermask limits of this device */
xfer_mask &= ata_pack_xfermask(dev->pio_mask,
dev->mwdma_mask, dev->udma_mask);
xfer_mask &= ata_id_xfermask(dev->id);
+ /* PIO xfermask limits are shared by all devices on the same
+ * channel to avoid violating device selection timing.
+ */
+ for (i = 0; i < ATA_MAX_DEVICES; i++) {
+ struct ata_device *d = &ap->device[i];
+ unsigned int pio_mask;
+
+ if (ata_dev_absent(d))
+ continue;
+
+ ata_unpack_xfermask(ata_id_xfermask(d->id),
+ &pio_mask, NULL, NULL);
+ pio_mask &= d->pio_mask;
+ xfer_mask &= ata_pack_xfermask(pio_mask, UINT_MAX, UINT_MAX);
+ }
+
/*
* CFA Advanced TrueIDE timings are not allowed on a shared
* cable
@@ -5479,7 +5519,7 @@ int ata_device_add(const struct ata_prob
/* register each port bound to this device */
for (i = 0; i < host->n_ports; i++) {
struct ata_port *ap;
- unsigned long xfer_mode_mask;
+ char xfer_buf[ATA_MODE_STRING_MAX];
int irq_line = ent->irq;
ap = ata_port_add(ent, host, i);
@@ -5506,18 +5546,16 @@ int ata_device_add(const struct ata_prob
if (i == 1 && ent->irq2)
irq_line = ent->irq2;
- xfer_mode_mask =(ap->udma_mask << ATA_SHIFT_UDMA) |
- (ap->mwdma_mask << ATA_SHIFT_MWDMA) |
- (ap->pio_mask << ATA_SHIFT_PIO);
+ ata_mode_string(ap->udma_mask << ATA_SHIFT_UDMA |
+ ap->mwdma_mask << ATA_SHIFT_MWDMA |
+ ap->pio_mask << ATA_SHIFT_PIO, xfer_buf);
/* print per-port info to dmesg */
ata_port_printk(ap, KERN_INFO, "%cATA max %s cmd 0x%lX "
"ctl 0x%lX bmdma 0x%lX irq %d\n",
ap->flags & ATA_FLAG_SATA ? 'S' : 'P',
- ata_mode_string(xfer_mode_mask),
- ap->ioaddr.cmd_addr,
- ap->ioaddr.ctl_addr,
- ap->ioaddr.bmdma_addr,
+ xfer_buf, ap->ioaddr.cmd_addr,
+ ap->ioaddr.ctl_addr, ap->ioaddr.bmdma_addr,
irq_line);
ata_chk_status(ap);
Index: work/drivers/ata/libata-sff.c
===================================================================
--- work.orig/drivers/ata/libata-sff.c 2007-01-03 12:33:36.000000000 +0900
+++ work/drivers/ata/libata-sff.c 2007-01-03 12:36:19.000000000 +0900
@@ -662,6 +662,7 @@ void ata_bmdma_stop(struct ata_queued_cm
*/
void ata_bmdma_freeze(struct ata_port *ap)
{
+#if 0
struct ata_ioports *ioaddr = &ap->ioaddr;
ap->ctl |= ATA_NIEN;
@@ -671,6 +672,7 @@ void ata_bmdma_freeze(struct ata_port *a
writeb(ap->ctl, (void __iomem *)ioaddr->ctl_addr);
else
outb(ap->ctl, ioaddr->ctl_addr);
+#endif
}
/**
next prev parent reply other threads:[~2007-01-03 3:44 UTC|newest]
Thread overview: 18+ messages / expand[flat|nested] mbox.gz Atom feed top
2006-12-04 17:36 ICH7m problem using libata Jan Gutter
2006-12-20 0:18 ` Tejun Heo
2007-01-03 3:07 ` Matthew Stapleton
2007-01-03 3:44 ` Tejun Heo [this message]
2007-01-09 22:17 ` Matthew Stapleton
2007-01-15 5:20 ` Tejun Heo
2007-01-15 23:58 ` Matthew Stapleton
2007-01-16 8:56 ` Tejun Heo
2007-01-16 11:31 ` Jan Gutter
2007-01-16 11:42 ` Tejun Heo
2007-01-16 13:53 ` Jan Gutter
2007-01-17 5:11 ` Tejun Heo
2007-01-17 13:25 ` Jan Gutter
2007-01-17 13:41 ` Tejun Heo
2007-01-18 2:13 ` Matthew Stapleton
-- strict thread matches above, loose matches on Subject: below --
2006-12-19 0:40 Matthew Stapleton
2007-01-16 14:11 Mikael Pettersson
2007-01-16 14:51 ` Jan Gutter
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=459B2699.8090506@gmail.com \
--to=htejun@gmail.com \
--cc=linux-ide@vger.kernel.org \
--cc=matthew4196@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).