diff options
author | Emil Velikov <emil.l.velikov@gmail.com> | 2013-08-23 13:43:42 -0400 |
---|---|---|
committer | Ben Skeggs <bskeggs@redhat.com> | 2013-09-03 23:47:02 -0400 |
commit | 5087f51da805f53cba7366f70d596e7bde2a5486 (patch) | |
tree | e73d10135fb529dfb5cfc863b697e3c692e60f99 | |
parent | c865534f1e5b5b4ef03f4a55cf4730f4b70dd75b (diff) |
drm/nv50/disp: prevent false output detection on the original nv50
Commit ea9197cc323839ef3d5280c0453b2c622caa6bc7 effectively enabled the
use of an improved DAC detection code, but introduced a regression on
the original nv50 chipset, causing a ghost monitor to be detected.
v2 (Ben Skeggs): the offending line was likely a thinko, removed it for
all chipsets (tested nv50 and nve6 to cover entire range) and added
some additional debugging.
Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=67382
Tested-by: Martin Peres <martin.peres@labri.fr>
Signed-off-by: Emil Velikov <emil.l.velikov@gmail.com>
Cc: <stable@vger.kernel.org> # 3.9+
Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
-rw-r--r-- | drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c | 15 |
1 files changed, 10 insertions, 5 deletions
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c b/drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c index f02fd9f443ff..a66b27c0fcab 100644 --- a/drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c +++ b/drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c | |||
@@ -49,18 +49,23 @@ int | |||
49 | nv50_dac_sense(struct nv50_disp_priv *priv, int or, u32 loadval) | 49 | nv50_dac_sense(struct nv50_disp_priv *priv, int or, u32 loadval) |
50 | { | 50 | { |
51 | const u32 doff = (or * 0x800); | 51 | const u32 doff = (or * 0x800); |
52 | int load = -EINVAL; | 52 | |
53 | nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80150000); | 53 | nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80150000); |
54 | nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000); | 54 | nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000); |
55 | |||
55 | nv_wr32(priv, 0x61a00c + doff, 0x00100000 | loadval); | 56 | nv_wr32(priv, 0x61a00c + doff, 0x00100000 | loadval); |
56 | mdelay(9); | 57 | mdelay(9); |
57 | udelay(500); | 58 | udelay(500); |
58 | nv_wr32(priv, 0x61a00c + doff, 0x80000000); | 59 | loadval = nv_mask(priv, 0x61a00c + doff, 0xffffffff, 0x00000000); |
59 | load = (nv_rd32(priv, 0x61a00c + doff) & 0x38000000) >> 27; | 60 | |
60 | nv_wr32(priv, 0x61a00c + doff, 0x00000000); | ||
61 | nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80550000); | 61 | nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80550000); |
62 | nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000); | 62 | nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000); |
63 | return load; | 63 | |
64 | nv_debug(priv, "DAC%d sense: 0x%08x\n", or, loadval); | ||
65 | if (!(loadval & 0x80000000)) | ||
66 | return -ETIMEDOUT; | ||
67 | |||
68 | return (loadval & 0x38000000) >> 27; | ||
64 | } | 69 | } |
65 | 70 | ||
66 | int | 71 | int |