All of lore.kernel.org
 help / color / mirror / Atom feed
From: Albert Lee <albertcc@tw.ibm.com>
To: Jeff Garzik <jeff@garzik.org>
Cc: Mark Lord <liml@rtr.ca>, Linux IDE <linux-ide@vger.kernel.org>,
	Alan Cox <alan@lxorguk.ukuu.org.uk>, Tejun Heo <htejun@gmail.com>,
	matthieu castet <castet.matthieu@free.fr>,
	Tobias Powalowski <t.powa@gmx.de>
Subject: [PATCH] libata: blacklist for early irq problem
Date: Thu, 30 Nov 2006 17:43:51 +0800	[thread overview]
Message-ID: <456EA7D6.2050101@tw.ibm.com> (raw)
In-Reply-To: <456C8A51.3000605@garzik.org>

Some devices raise irq early before clearing the BSY.
This patch adds blacklist and waits up to 10 microseconds to workaround the early irq problem.

Signed-off-by: Albert Lee <albertcc@tw.ibm.com>
---
Ok, we should not affect the good devices.
Patch revised for your review.
(against the libata-dev tree 6b78c0d20ffbc89acc3c2790f8d7eded05606813).

diff -Nrup 000_libata_dev/drivers/ata/libata-core.c 001_early_irq/drivers/ata/libata-core.c
--- 000_libata_dev/drivers/ata/libata-core.c	2006-11-30 15:53:08.000000000 +0800
+++ 001_early_irq/drivers/ata/libata-core.c	2006-11-30 16:41:23.000000000 +0800
@@ -1610,6 +1610,9 @@ int ata_dev_configure(struct ata_device 
 	if (dev->flags & ATA_DFLAG_LBA48)
 		dev->max_sectors = ATA_MAX_SECTORS_LBA48;
 
+	if (ata_device_blacklisted(dev) & ATA_HORKAGE_EARLY_IRQ)
+		dev->horkage |= ATA_HORKAGE_EARLY_IRQ;
+
 	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
@@ -3184,6 +3187,9 @@ static const struct ata_blacklist_entry 
 
 	/* Devices with NCQ limits */
 
+	/* Devices with early IRQ */
+	{ "CD-ROM 36X/AKW",   NULL,		ATA_HORKAGE_EARLY_IRQ },
+
 	/* End Marker */
 	{ }
 };
@@ -4989,6 +4995,11 @@ inline unsigned int ata_host_intr (struc
 		goto idle_irq;
 	}
 
+	/* some drives raise INTRQ early before clearing BSY */
+	if (unlikely(qc->dev->horkage & ATA_HORKAGE_EARLY_IRQ))
+		/* wait up to 10 microseconds for BSY to clear */
+		ata_busy_wait_alt(ap, ATA_BUSY, ATA_EARLY_IRQ_WAIT);
+
 	/* check altstatus */
 	status = ata_altstatus(ap);
 	if (status & ATA_BUSY)
diff -Nrup 000_libata_dev/include/linux/libata.h 001_early_irq/include/linux/libata.h
--- 000_libata_dev/include/linux/libata.h	2006-11-30 15:53:26.000000000 +0800
+++ 001_early_irq/include/linux/libata.h	2006-11-30 17:04:37.000000000 +0800
@@ -309,6 +309,9 @@ enum {
 	 * most devices.
 	 */
 	ATA_SPINUP_WAIT		= 8000,
+
+	/*  early irq max wait time (for BSY to clear) in usecs */
+	ATA_EARLY_IRQ_WAIT	= 10,
 	
 	/* Horkage types. May be set by libata or controller on drives
 	   (some horkage may be drive/controller pair dependant */
@@ -316,6 +319,7 @@ enum {
 	ATA_HORKAGE_DIAGNOSTIC	= (1 << 0),	/* Failed boot diag */
 	ATA_HORKAGE_NODMA	= (1 << 1),	/* DMA problems */
 	ATA_HORKAGE_NONCQ	= (1 << 2),	/* Don't use NCQ */
+	ATA_HORKAGE_EARLY_IRQ	= (1 << 3),	/* Early IRQ */
 };
 
 enum hsm_task_states {
@@ -1056,6 +1060,30 @@ static inline void ata_pause(struct ata_
 	ndelay(400);
 }
 
+/**
+ *	ata_busy_wait_alt - Wait for a port alt status register
+ *	@ap: Port to wait for.
+ *
+ *	Waits up to max microseconds for the selected bits in the port's
+ *	alt status register to be cleared.
+ *	Returns final value of alt status register.
+ *
+ *	LOCKING:
+ *	Inherited from caller.
+ */
+static inline u8 ata_busy_wait_alt(struct ata_port *ap, unsigned int bits,
+				   unsigned int max)
+{
+	u8 status = ata_altstatus(ap);
+
+	while ((status & bits) && (max > 0)) {
+		udelay(1);
+		status = ata_altstatus(ap);
+		max--;
+	};
+
+	return status;
+}
 
 /**
  *	ata_busy_wait - Wait for a port status register


  reply	other threads:[~2006-11-30  9:44 UTC|newest]

Thread overview: 20+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <200611180759.34622.t.powa@gmx.de>
     [not found] ` <20061118002357.564dbb9d.akpm@osdl.org>
2006-11-18 21:20   ` possibility to merge via_pata fixes to .19 stable series? Jeff Garzik
2006-11-18 22:43     ` Alan
2006-11-19  3:07       ` Andrew Morton
2006-11-19  5:34         ` Tejun Heo
2006-11-19  6:02           ` Andrew Morton
2006-11-28  6:52     ` [PATCH] libata: waits up to 10 microseconds for early irq problem Albert Lee
2006-11-28 10:25       ` Alan
2006-11-28 10:27         ` Tejun Heo
2006-11-28 10:46           ` Alan
2006-11-28 14:00             ` Mark Lord
2006-11-28 14:12               ` Alan
2006-11-28 14:16                 ` Mark Lord
2006-11-28 11:32           ` Albert Lee
2006-11-28 14:17       ` Albert Lee
2006-11-28 14:42         ` Mark Lord
2006-11-28 19:13           ` Jeff Garzik
2006-11-30  9:43             ` Albert Lee [this message]
2006-11-30 11:29               ` [PATCH] libata: blacklist " Alan
2006-11-30 20:37               ` Mark Lord
2006-11-30 20:45               ` Mark Lord

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=456EA7D6.2050101@tw.ibm.com \
    --to=albertcc@tw.ibm.com \
    --cc=alan@lxorguk.ukuu.org.uk \
    --cc=albertl@mail.com \
    --cc=castet.matthieu@free.fr \
    --cc=htejun@gmail.com \
    --cc=jeff@garzik.org \
    --cc=liml@rtr.ca \
    --cc=linux-ide@vger.kernel.org \
    --cc=t.powa@gmx.de \
    /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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.