aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/char/agp
diff options
context:
space:
mode:
authorDave Jones <davej@redhat.com>2005-09-23 15:59:37 -0700
committerDave Jones <davej@redhat.com>2005-09-23 15:59:37 -0700
commit0ff541dafdcb9bc8933e7e4881e5924a408b5335 (patch)
tree8467dffd0c09b5a32085b72a4a348af5adafa62d /drivers/char/agp
parent[PATCH] pci: only call pci_restore_bars at boot (diff)
downloadlinux-dev-0ff541dafdcb9bc8933e7e4881e5924a408b5335.tar.xz
linux-dev-0ff541dafdcb9bc8933e7e4881e5924a408b5335.zip
[AGPGART] Fix serverworks TLB flush.
Go back to what 2.4 kernels used to do here, as if this hits, the kernel just hangs indefinitly. Actually an improvement over 2.4 - we now break; out of the loop instead of just printing messages on timeouts. Signed-off-by: Dave Jones <davej@redhat.com>
Diffstat (limited to 'drivers/char/agp')
-rw-r--r--drivers/char/agp/sworks-agp.c18
1 files changed, 16 insertions, 2 deletions
diff --git a/drivers/char/agp/sworks-agp.c b/drivers/char/agp/sworks-agp.c
index a9fb12c20eb7..53968973f890 100644
--- a/drivers/char/agp/sworks-agp.c
+++ b/drivers/char/agp/sworks-agp.c
@@ -242,13 +242,27 @@ static int serverworks_fetch_size(void)
*/
static void serverworks_tlbflush(struct agp_memory *temp)
{
+ unsigned long timeout;
+
writeb(1, serverworks_private.registers+SVWRKS_POSTFLUSH);
- while (readb(serverworks_private.registers+SVWRKS_POSTFLUSH) == 1)
+ timeout = jiffies + 3*HZ;
+ while (readb(serverworks_private.registers+SVWRKS_POSTFLUSH) == 1) {
cpu_relax();
+ if (time_after(jiffies, timeout)) {
+ printk(KERN_ERR PFX "TLB post flush took more than 3 seconds\n");
+ break;
+ }
+ }
writel(1, serverworks_private.registers+SVWRKS_DIRFLUSH);
- while(readl(serverworks_private.registers+SVWRKS_DIRFLUSH) == 1)
+ timeout = jiffies + 3*HZ;
+ while (readl(serverworks_private.registers+SVWRKS_DIRFLUSH) == 1) {
cpu_relax();
+ if (time_after(jiffies, timeout)) {
+ printk(KERN_ERR PFX "TLB Dir flush took more than 3 seconds\n");
+ break;
+ }
+ }
}
static int serverworks_configure(void)