[Nouveau] [PATCH 1/2] drm/nouveau: rework bios delays
Pekka Paalanen
pq at iki.fi
Mon Oct 12 11:30:44 PDT 2009
Replace the BIOS_USLEEP() macro with appropriate calls to udelay() and
msleep(). BIOS_USLEEP() was implemented with mdelay(), which is a
busy-wait. msleep() on the other hand can reschedule, so these paths
cannot be called from interrupt or atomic context.
In init_reset(), BIOS_USLEEP(10) was a no-op, since the delay was
rounded off to zero. This was probably a bug in porting the DDX code to
the kernel. The delay is restored.
In init_time(), since the delay is variable with a large range, it is
implemented as a busy-wait for <1ms, and msleep() otherwise rounding
mostly to the next integer milliseconds.
call_lvds_manufacturer_script() contained a bug in the wait: the delay
was executed in microseconds, when it should be milliseconds. Fixed.
Signed-off-by: Pekka Paalanen <pq at iki.fi>
---
drivers/gpu/drm/nouveau/nouveau_bios.c | 20 +++++++++++---------
1 files changed, 11 insertions(+), 9 deletions(-)
diff --git a/drivers/gpu/drm/nouveau/nouveau_bios.c b/drivers/gpu/drm/nouveau/nouveau_bios.c
index 2cf4134..adfd263 100644
--- a/drivers/gpu/drm/nouveau/nouveau_bios.c
+++ b/drivers/gpu/drm/nouveau/nouveau_bios.c
@@ -40,8 +40,6 @@
#define BIOSLOG(sip, fmt, arg...) NV_DEBUG(sip->dev, fmt, ##arg)
#define LOG_OLD_VALUE(x)
-#define BIOS_USLEEP(n) mdelay((n)/1000)
-
#define ROM16(x) le16_to_cpu(*(uint16_t *)&(x))
#define ROM32(x) le32_to_cpu(*(uint32_t *)&(x))
@@ -286,7 +284,7 @@ static void still_alive(void)
{
#if 0
sync();
- BIOS_USLEEP(2000);
+ msleep(2);
#endif
}
@@ -1690,7 +1688,7 @@ init_condition_time(struct nvbios *bios, uint16_t offset,
break;
} else {
BIOSLOG(bios, "0x%04X: Condition not met, sleeping for 20ms\n", offset);
- BIOS_USLEEP(20000);
+ msleep(20);
}
if (!bios_condition_met(bios, offset, cond)) {
@@ -1939,7 +1937,7 @@ init_reset(struct nvbios *bios, uint16_t offset, struct init_exec *iexec)
bios_wr32(bios, NV_PBUS_PCI_NV_19, 0);
bios_wr32(bios, reg, value1);
- BIOS_USLEEP(10);
+ udelay(10);
bios_wr32(bios, reg, value2);
bios_wr32(bios, NV_PBUS_PCI_NV_19, pci_nv_19);
@@ -2339,7 +2337,7 @@ init_time(struct nvbios *bios, uint16_t offset, struct init_exec *iexec)
* Sleep for "time" microseconds.
*/
- uint16_t time = ROM16(bios->data[offset + 1]);
+ unsigned time = ROM16(bios->data[offset + 1]);
if (!iexec->execute)
return true;
@@ -2347,7 +2345,10 @@ init_time(struct nvbios *bios, uint16_t offset, struct init_exec *iexec)
BIOSLOG(bios, "0x%04X: Sleeping for 0x%04X microseconds\n",
offset, time);
- BIOS_USLEEP(time);
+ if (time < 1000)
+ udelay(time);
+ else
+ msleep((time + 900) / 1000);
return true;
}
@@ -3154,9 +3155,10 @@ static int call_lvds_manufacturer_script(struct drm_device *dev, struct dcb_entr
run_digital_op_script(dev, scriptofs, dcbent, head, bios->fp.dual_link);
- if (script == LVDS_PANEL_OFF)
+ if (script == LVDS_PANEL_OFF) {
/* off-on delay in ms */
- BIOS_USLEEP(ROM16(bios->data[bios->fp.xlated_entry + 7]));
+ msleep(ROM16(bios->data[bios->fp.xlated_entry + 7]));
+ }
#ifdef __powerpc__
/* Powerbook specific quirks */
if (script == LVDS_RESET && ((dev->pci_device & 0xffff) == 0x0179 || (dev->pci_device & 0xffff) == 0x0329))
--
1.6.4.4
More information about the Nouveau
mailing list