diff options
Diffstat (limited to 'drivers/gpu/drm/nouveau/nv50_display.c')
-rw-r--r-- | drivers/gpu/drm/nouveau/nv50_display.c | 551 |
1 files changed, 234 insertions, 317 deletions
diff --git a/drivers/gpu/drm/nouveau/nv50_display.c b/drivers/gpu/drm/nouveau/nv50_display.c index f868a13e5c2d..f97b42cbb6bb 100644 --- a/drivers/gpu/drm/nouveau/nv50_display.c +++ b/drivers/gpu/drm/nouveau/nv50_display.c | |||
@@ -24,28 +24,30 @@ | |||
24 | * | 24 | * |
25 | */ | 25 | */ |
26 | 26 | ||
27 | #define NOUVEAU_DMA_DEBUG (nouveau_reg_debug & NOUVEAU_REG_DEBUG_EVO) | 27 | #include "nouveau_drm.h" |
28 | #include "nouveau_dma.h" | ||
29 | |||
28 | #include "nv50_display.h" | 30 | #include "nv50_display.h" |
29 | #include "nouveau_crtc.h" | 31 | #include "nouveau_crtc.h" |
30 | #include "nouveau_encoder.h" | 32 | #include "nouveau_encoder.h" |
31 | #include "nouveau_connector.h" | 33 | #include "nouveau_connector.h" |
32 | #include "nouveau_fb.h" | ||
33 | #include "nouveau_fbcon.h" | 34 | #include "nouveau_fbcon.h" |
34 | #include "nouveau_ramht.h" | ||
35 | #include "nouveau_software.h" | ||
36 | #include <drm/drm_crtc_helper.h> | 35 | #include <drm/drm_crtc_helper.h> |
36 | #include "nouveau_fence.h" | ||
37 | |||
38 | #include <core/gpuobj.h> | ||
39 | #include <subdev/timer.h> | ||
37 | 40 | ||
38 | static void nv50_display_isr(struct drm_device *); | ||
39 | static void nv50_display_bh(unsigned long); | 41 | static void nv50_display_bh(unsigned long); |
40 | 42 | ||
41 | static inline int | 43 | static inline int |
42 | nv50_sor_nr(struct drm_device *dev) | 44 | nv50_sor_nr(struct drm_device *dev) |
43 | { | 45 | { |
44 | struct drm_nouveau_private *dev_priv = dev->dev_private; | 46 | struct nouveau_device *device = nouveau_dev(dev); |
45 | 47 | ||
46 | if (dev_priv->chipset < 0x90 || | 48 | if (device->chipset < 0x90 || |
47 | dev_priv->chipset == 0x92 || | 49 | device->chipset == 0x92 || |
48 | dev_priv->chipset == 0xa0) | 50 | device->chipset == 0xa0) |
49 | return 2; | 51 | return 2; |
50 | 52 | ||
51 | return 4; | 53 | return 4; |
@@ -54,73 +56,29 @@ nv50_sor_nr(struct drm_device *dev) | |||
54 | u32 | 56 | u32 |
55 | nv50_display_active_crtcs(struct drm_device *dev) | 57 | nv50_display_active_crtcs(struct drm_device *dev) |
56 | { | 58 | { |
57 | struct drm_nouveau_private *dev_priv = dev->dev_private; | 59 | struct nouveau_device *device = nouveau_dev(dev); |
58 | u32 mask = 0; | 60 | u32 mask = 0; |
59 | int i; | 61 | int i; |
60 | 62 | ||
61 | if (dev_priv->chipset < 0x90 || | 63 | if (device->chipset < 0x90 || |
62 | dev_priv->chipset == 0x92 || | 64 | device->chipset == 0x92 || |
63 | dev_priv->chipset == 0xa0) { | 65 | device->chipset == 0xa0) { |
64 | for (i = 0; i < 2; i++) | 66 | for (i = 0; i < 2; i++) |
65 | mask |= nv_rd32(dev, NV50_PDISPLAY_SOR_MODE_CTRL_C(i)); | 67 | mask |= nv_rd32(device, NV50_PDISPLAY_SOR_MODE_CTRL_C(i)); |
66 | } else { | 68 | } else { |
67 | for (i = 0; i < 4; i++) | 69 | for (i = 0; i < 4; i++) |
68 | mask |= nv_rd32(dev, NV90_PDISPLAY_SOR_MODE_CTRL_C(i)); | 70 | mask |= nv_rd32(device, NV90_PDISPLAY_SOR_MODE_CTRL_C(i)); |
69 | } | 71 | } |
70 | 72 | ||
71 | for (i = 0; i < 3; i++) | 73 | for (i = 0; i < 3; i++) |
72 | mask |= nv_rd32(dev, NV50_PDISPLAY_DAC_MODE_CTRL_C(i)); | 74 | mask |= nv_rd32(device, NV50_PDISPLAY_DAC_MODE_CTRL_C(i)); |
73 | 75 | ||
74 | return mask & 3; | 76 | return mask & 3; |
75 | } | 77 | } |
76 | 78 | ||
77 | static int | ||
78 | evo_icmd(struct drm_device *dev, int ch, u32 mthd, u32 data) | ||
79 | { | ||
80 | int ret = 0; | ||
81 | nv_mask(dev, 0x610300 + (ch * 0x08), 0x00000001, 0x00000001); | ||
82 | nv_wr32(dev, 0x610304 + (ch * 0x08), data); | ||
83 | nv_wr32(dev, 0x610300 + (ch * 0x08), 0x80000001 | mthd); | ||
84 | if (!nv_wait(dev, 0x610300 + (ch * 0x08), 0x80000000, 0x00000000)) | ||
85 | ret = -EBUSY; | ||
86 | if (ret || (nouveau_reg_debug & NOUVEAU_REG_DEBUG_EVO)) | ||
87 | NV_INFO(dev, "EvoPIO: %d 0x%04x 0x%08x\n", ch, mthd, data); | ||
88 | nv_mask(dev, 0x610300 + (ch * 0x08), 0x00000001, 0x00000000); | ||
89 | return ret; | ||
90 | } | ||
91 | |||
92 | int | 79 | int |
93 | nv50_display_early_init(struct drm_device *dev) | 80 | nv50_display_early_init(struct drm_device *dev) |
94 | { | 81 | { |
95 | u32 ctrl = nv_rd32(dev, 0x610200); | ||
96 | int i; | ||
97 | |||
98 | /* check if master evo channel is already active, a good a sign as any | ||
99 | * that the display engine is in a weird state (hibernate/kexec), if | ||
100 | * it is, do our best to reset the display engine... | ||
101 | */ | ||
102 | if ((ctrl & 0x00000003) == 0x00000003) { | ||
103 | NV_INFO(dev, "PDISP: EVO(0) 0x%08x, resetting...\n", ctrl); | ||
104 | |||
105 | /* deactivate both heads first, PDISP will disappear forever | ||
106 | * (well, until you power cycle) on some boards as soon as | ||
107 | * PMC_ENABLE is hit unless they are.. | ||
108 | */ | ||
109 | for (i = 0; i < 2; i++) { | ||
110 | evo_icmd(dev, 0, 0x0880 + (i * 0x400), 0x05000000); | ||
111 | evo_icmd(dev, 0, 0x089c + (i * 0x400), 0); | ||
112 | evo_icmd(dev, 0, 0x0840 + (i * 0x400), 0); | ||
113 | evo_icmd(dev, 0, 0x0844 + (i * 0x400), 0); | ||
114 | evo_icmd(dev, 0, 0x085c + (i * 0x400), 0); | ||
115 | evo_icmd(dev, 0, 0x0874 + (i * 0x400), 0); | ||
116 | } | ||
117 | evo_icmd(dev, 0, 0x0080, 0); | ||
118 | |||
119 | /* reset PDISP */ | ||
120 | nv_mask(dev, 0x000200, 0x40000000, 0x00000000); | ||
121 | nv_mask(dev, 0x000200, 0x40000000, 0x40000000); | ||
122 | } | ||
123 | |||
124 | return 0; | 82 | return 0; |
125 | } | 83 | } |
126 | 84 | ||
@@ -132,11 +90,8 @@ nv50_display_late_takedown(struct drm_device *dev) | |||
132 | int | 90 | int |
133 | nv50_display_sync(struct drm_device *dev) | 91 | nv50_display_sync(struct drm_device *dev) |
134 | { | 92 | { |
135 | struct drm_nouveau_private *dev_priv = dev->dev_private; | ||
136 | struct nouveau_timer_engine *ptimer = &dev_priv->engine.timer; | ||
137 | struct nv50_display *disp = nv50_display(dev); | 93 | struct nv50_display *disp = nv50_display(dev); |
138 | struct nouveau_channel *evo = disp->master; | 94 | struct nouveau_channel *evo = disp->master; |
139 | u64 start; | ||
140 | int ret; | 95 | int ret; |
141 | 96 | ||
142 | ret = RING_SPACE(evo, 6); | 97 | ret = RING_SPACE(evo, 6); |
@@ -148,29 +103,28 @@ nv50_display_sync(struct drm_device *dev) | |||
148 | BEGIN_NV04(evo, 0, 0x0084, 1); | 103 | BEGIN_NV04(evo, 0, 0x0084, 1); |
149 | OUT_RING (evo, 0x00000000); | 104 | OUT_RING (evo, 0x00000000); |
150 | 105 | ||
151 | nv_wo32(disp->ntfy, 0x000, 0x00000000); | 106 | nv_wo32(disp->ramin, 0x2000, 0x00000000); |
152 | FIRE_RING (evo); | 107 | FIRE_RING (evo); |
153 | 108 | ||
154 | start = ptimer->read(dev); | 109 | if (nv_wait_ne(disp->ramin, 0x2000, 0xffffffff, 0x00000000)) |
155 | do { | 110 | return 0; |
156 | if (nv_ro32(disp->ntfy, 0x000)) | ||
157 | return 0; | ||
158 | } while (ptimer->read(dev) - start < 2000000000ULL); | ||
159 | } | 111 | } |
160 | 112 | ||
161 | return -EBUSY; | 113 | return 0; |
162 | } | 114 | } |
163 | 115 | ||
164 | int | 116 | int |
165 | nv50_display_init(struct drm_device *dev) | 117 | nv50_display_init(struct drm_device *dev) |
166 | { | 118 | { |
119 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
120 | struct nouveau_device *device = nouveau_dev(dev); | ||
167 | struct nouveau_channel *evo; | 121 | struct nouveau_channel *evo; |
168 | int ret, i; | 122 | int ret, i; |
169 | u32 val; | 123 | u32 val; |
170 | 124 | ||
171 | NV_DEBUG_KMS(dev, "\n"); | 125 | NV_DEBUG(drm, "\n"); |
172 | 126 | ||
173 | nv_wr32(dev, 0x00610184, nv_rd32(dev, 0x00614004)); | 127 | nv_wr32(device, 0x00610184, nv_rd32(device, 0x00614004)); |
174 | 128 | ||
175 | /* | 129 | /* |
176 | * I think the 0x006101XX range is some kind of main control area | 130 | * I think the 0x006101XX range is some kind of main control area |
@@ -178,82 +132,82 @@ nv50_display_init(struct drm_device *dev) | |||
178 | */ | 132 | */ |
179 | /* CRTC? */ | 133 | /* CRTC? */ |
180 | for (i = 0; i < 2; i++) { | 134 | for (i = 0; i < 2; i++) { |
181 | val = nv_rd32(dev, 0x00616100 + (i * 0x800)); | 135 | val = nv_rd32(device, 0x00616100 + (i * 0x800)); |
182 | nv_wr32(dev, 0x00610190 + (i * 0x10), val); | 136 | nv_wr32(device, 0x00610190 + (i * 0x10), val); |
183 | val = nv_rd32(dev, 0x00616104 + (i * 0x800)); | 137 | val = nv_rd32(device, 0x00616104 + (i * 0x800)); |
184 | nv_wr32(dev, 0x00610194 + (i * 0x10), val); | 138 | nv_wr32(device, 0x00610194 + (i * 0x10), val); |
185 | val = nv_rd32(dev, 0x00616108 + (i * 0x800)); | 139 | val = nv_rd32(device, 0x00616108 + (i * 0x800)); |
186 | nv_wr32(dev, 0x00610198 + (i * 0x10), val); | 140 | nv_wr32(device, 0x00610198 + (i * 0x10), val); |
187 | val = nv_rd32(dev, 0x0061610c + (i * 0x800)); | 141 | val = nv_rd32(device, 0x0061610c + (i * 0x800)); |
188 | nv_wr32(dev, 0x0061019c + (i * 0x10), val); | 142 | nv_wr32(device, 0x0061019c + (i * 0x10), val); |
189 | } | 143 | } |
190 | 144 | ||
191 | /* DAC */ | 145 | /* DAC */ |
192 | for (i = 0; i < 3; i++) { | 146 | for (i = 0; i < 3; i++) { |
193 | val = nv_rd32(dev, 0x0061a000 + (i * 0x800)); | 147 | val = nv_rd32(device, 0x0061a000 + (i * 0x800)); |
194 | nv_wr32(dev, 0x006101d0 + (i * 0x04), val); | 148 | nv_wr32(device, 0x006101d0 + (i * 0x04), val); |
195 | } | 149 | } |
196 | 150 | ||
197 | /* SOR */ | 151 | /* SOR */ |
198 | for (i = 0; i < nv50_sor_nr(dev); i++) { | 152 | for (i = 0; i < nv50_sor_nr(dev); i++) { |
199 | val = nv_rd32(dev, 0x0061c000 + (i * 0x800)); | 153 | val = nv_rd32(device, 0x0061c000 + (i * 0x800)); |
200 | nv_wr32(dev, 0x006101e0 + (i * 0x04), val); | 154 | nv_wr32(device, 0x006101e0 + (i * 0x04), val); |
201 | } | 155 | } |
202 | 156 | ||
203 | /* EXT */ | 157 | /* EXT */ |
204 | for (i = 0; i < 3; i++) { | 158 | for (i = 0; i < 3; i++) { |
205 | val = nv_rd32(dev, 0x0061e000 + (i * 0x800)); | 159 | val = nv_rd32(device, 0x0061e000 + (i * 0x800)); |
206 | nv_wr32(dev, 0x006101f0 + (i * 0x04), val); | 160 | nv_wr32(device, 0x006101f0 + (i * 0x04), val); |
207 | } | 161 | } |
208 | 162 | ||
209 | for (i = 0; i < 3; i++) { | 163 | for (i = 0; i < 3; i++) { |
210 | nv_wr32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(i), 0x00550000 | | 164 | nv_wr32(device, NV50_PDISPLAY_DAC_DPMS_CTRL(i), 0x00550000 | |
211 | NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING); | 165 | NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING); |
212 | nv_wr32(dev, NV50_PDISPLAY_DAC_CLK_CTRL1(i), 0x00000001); | 166 | nv_wr32(device, NV50_PDISPLAY_DAC_CLK_CTRL1(i), 0x00000001); |
213 | } | 167 | } |
214 | 168 | ||
215 | /* The precise purpose is unknown, i suspect it has something to do | 169 | /* The precise purpose is unknown, i suspect it has something to do |
216 | * with text mode. | 170 | * with text mode. |
217 | */ | 171 | */ |
218 | if (nv_rd32(dev, NV50_PDISPLAY_INTR_1) & 0x100) { | 172 | if (nv_rd32(device, NV50_PDISPLAY_INTR_1) & 0x100) { |
219 | nv_wr32(dev, NV50_PDISPLAY_INTR_1, 0x100); | 173 | nv_wr32(device, NV50_PDISPLAY_INTR_1, 0x100); |
220 | nv_wr32(dev, 0x006194e8, nv_rd32(dev, 0x006194e8) & ~1); | 174 | nv_wr32(device, 0x006194e8, nv_rd32(device, 0x006194e8) & ~1); |
221 | if (!nv_wait(dev, 0x006194e8, 2, 0)) { | 175 | if (!nv_wait(device, 0x006194e8, 2, 0)) { |
222 | NV_ERROR(dev, "timeout: (0x6194e8 & 2) != 0\n"); | 176 | NV_ERROR(drm, "timeout: (0x6194e8 & 2) != 0\n"); |
223 | NV_ERROR(dev, "0x6194e8 = 0x%08x\n", | 177 | NV_ERROR(drm, "0x6194e8 = 0x%08x\n", |
224 | nv_rd32(dev, 0x6194e8)); | 178 | nv_rd32(device, 0x6194e8)); |
225 | return -EBUSY; | 179 | return -EBUSY; |
226 | } | 180 | } |
227 | } | 181 | } |
228 | 182 | ||
229 | for (i = 0; i < 2; i++) { | 183 | for (i = 0; i < 2; i++) { |
230 | nv_wr32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), 0x2000); | 184 | nv_wr32(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), 0x2000); |
231 | if (!nv_wait(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), | 185 | if (!nv_wait(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), |
232 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, 0)) { | 186 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, 0)) { |
233 | NV_ERROR(dev, "timeout: CURSOR_CTRL2_STATUS == 0\n"); | 187 | NV_ERROR(drm, "timeout: CURSOR_CTRL2_STATUS == 0\n"); |
234 | NV_ERROR(dev, "CURSOR_CTRL2 = 0x%08x\n", | 188 | NV_ERROR(drm, "CURSOR_CTRL2 = 0x%08x\n", |
235 | nv_rd32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); | 189 | nv_rd32(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); |
236 | return -EBUSY; | 190 | return -EBUSY; |
237 | } | 191 | } |
238 | 192 | ||
239 | nv_wr32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), | 193 | nv_wr32(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), |
240 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_ON); | 194 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_ON); |
241 | if (!nv_wait(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), | 195 | if (!nv_wait(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), |
242 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, | 196 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, |
243 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS_ACTIVE)) { | 197 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS_ACTIVE)) { |
244 | NV_ERROR(dev, "timeout: " | 198 | NV_ERROR(drm, "timeout: " |
245 | "CURSOR_CTRL2_STATUS_ACTIVE(%d)\n", i); | 199 | "CURSOR_CTRL2_STATUS_ACTIVE(%d)\n", i); |
246 | NV_ERROR(dev, "CURSOR_CTRL2(%d) = 0x%08x\n", i, | 200 | NV_ERROR(drm, "CURSOR_CTRL2(%d) = 0x%08x\n", i, |
247 | nv_rd32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); | 201 | nv_rd32(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); |
248 | return -EBUSY; | 202 | return -EBUSY; |
249 | } | 203 | } |
250 | } | 204 | } |
251 | 205 | ||
252 | nv_wr32(dev, NV50_PDISPLAY_PIO_CTRL, 0x00000000); | 206 | nv_wr32(device, NV50_PDISPLAY_PIO_CTRL, 0x00000000); |
253 | nv_mask(dev, NV50_PDISPLAY_INTR_0, 0x00000000, 0x00000000); | 207 | nv_mask(device, NV50_PDISPLAY_INTR_0, 0x00000000, 0x00000000); |
254 | nv_wr32(dev, NV50_PDISPLAY_INTR_EN_0, 0x00000000); | 208 | nv_wr32(device, NV50_PDISPLAY_INTR_EN_0, 0x00000000); |
255 | nv_mask(dev, NV50_PDISPLAY_INTR_1, 0x00000000, 0x00000000); | 209 | nv_mask(device, NV50_PDISPLAY_INTR_1, 0x00000000, 0x00000000); |
256 | nv_wr32(dev, NV50_PDISPLAY_INTR_EN_1, | 210 | nv_wr32(device, NV50_PDISPLAY_INTR_EN_1, |
257 | NV50_PDISPLAY_INTR_EN_1_CLK_UNK10 | | 211 | NV50_PDISPLAY_INTR_EN_1_CLK_UNK10 | |
258 | NV50_PDISPLAY_INTR_EN_1_CLK_UNK20 | | 212 | NV50_PDISPLAY_INTR_EN_1_CLK_UNK20 | |
259 | NV50_PDISPLAY_INTR_EN_1_CLK_UNK40); | 213 | NV50_PDISPLAY_INTR_EN_1_CLK_UNK40); |
@@ -263,7 +217,7 @@ nv50_display_init(struct drm_device *dev) | |||
263 | return ret; | 217 | return ret; |
264 | evo = nv50_display(dev)->master; | 218 | evo = nv50_display(dev)->master; |
265 | 219 | ||
266 | nv_wr32(dev, NV50_PDISPLAY_OBJECTS, (evo->ramin->vinst >> 8) | 9); | 220 | nv_wr32(device, NV50_PDISPLAY_OBJECTS, (nv50_display(dev)->ramin->addr >> 8) | 9); |
267 | 221 | ||
268 | ret = RING_SPACE(evo, 3); | 222 | ret = RING_SPACE(evo, 3); |
269 | if (ret) | 223 | if (ret) |
@@ -278,12 +232,14 @@ nv50_display_init(struct drm_device *dev) | |||
278 | void | 232 | void |
279 | nv50_display_fini(struct drm_device *dev) | 233 | nv50_display_fini(struct drm_device *dev) |
280 | { | 234 | { |
235 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
236 | struct nouveau_device *device = nouveau_dev(dev); | ||
281 | struct nv50_display *disp = nv50_display(dev); | 237 | struct nv50_display *disp = nv50_display(dev); |
282 | struct nouveau_channel *evo = disp->master; | 238 | struct nouveau_channel *evo = disp->master; |
283 | struct drm_crtc *drm_crtc; | 239 | struct drm_crtc *drm_crtc; |
284 | int ret, i; | 240 | int ret, i; |
285 | 241 | ||
286 | NV_DEBUG_KMS(dev, "\n"); | 242 | NV_DEBUG(drm, "\n"); |
287 | 243 | ||
288 | list_for_each_entry(drm_crtc, &dev->mode_config.crtc_list, head) { | 244 | list_for_each_entry(drm_crtc, &dev->mode_config.crtc_list, head) { |
289 | struct nouveau_crtc *crtc = nouveau_crtc(drm_crtc); | 245 | struct nouveau_crtc *crtc = nouveau_crtc(drm_crtc); |
@@ -308,55 +264,59 @@ nv50_display_fini(struct drm_device *dev) | |||
308 | if (!crtc->base.enabled) | 264 | if (!crtc->base.enabled) |
309 | continue; | 265 | continue; |
310 | 266 | ||
311 | nv_wr32(dev, NV50_PDISPLAY_INTR_1, mask); | 267 | nv_wr32(device, NV50_PDISPLAY_INTR_1, mask); |
312 | if (!nv_wait(dev, NV50_PDISPLAY_INTR_1, mask, mask)) { | 268 | if (!nv_wait(device, NV50_PDISPLAY_INTR_1, mask, mask)) { |
313 | NV_ERROR(dev, "timeout: (0x610024 & 0x%08x) == " | 269 | NV_ERROR(drm, "timeout: (0x610024 & 0x%08x) == " |
314 | "0x%08x\n", mask, mask); | 270 | "0x%08x\n", mask, mask); |
315 | NV_ERROR(dev, "0x610024 = 0x%08x\n", | 271 | NV_ERROR(drm, "0x610024 = 0x%08x\n", |
316 | nv_rd32(dev, NV50_PDISPLAY_INTR_1)); | 272 | nv_rd32(device, NV50_PDISPLAY_INTR_1)); |
317 | } | 273 | } |
318 | } | 274 | } |
319 | 275 | ||
320 | for (i = 0; i < 2; i++) { | 276 | for (i = 0; i < 2; i++) { |
321 | nv_wr32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), 0); | 277 | nv_wr32(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), 0); |
322 | if (!nv_wait(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), | 278 | if (!nv_wait(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), |
323 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, 0)) { | 279 | NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, 0)) { |
324 | NV_ERROR(dev, "timeout: CURSOR_CTRL2_STATUS == 0\n"); | 280 | NV_ERROR(drm, "timeout: CURSOR_CTRL2_STATUS == 0\n"); |
325 | NV_ERROR(dev, "CURSOR_CTRL2 = 0x%08x\n", | 281 | NV_ERROR(drm, "CURSOR_CTRL2 = 0x%08x\n", |
326 | nv_rd32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); | 282 | nv_rd32(device, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); |
327 | } | 283 | } |
328 | } | 284 | } |
329 | 285 | ||
330 | nv50_evo_fini(dev); | 286 | nv50_evo_fini(dev); |
331 | 287 | ||
332 | for (i = 0; i < 3; i++) { | 288 | for (i = 0; i < 3; i++) { |
333 | if (!nv_wait(dev, NV50_PDISPLAY_SOR_DPMS_STATE(i), | 289 | if (!nv_wait(device, NV50_PDISPLAY_SOR_DPMS_STATE(i), |
334 | NV50_PDISPLAY_SOR_DPMS_STATE_WAIT, 0)) { | 290 | NV50_PDISPLAY_SOR_DPMS_STATE_WAIT, 0)) { |
335 | NV_ERROR(dev, "timeout: SOR_DPMS_STATE_WAIT(%d) == 0\n", i); | 291 | NV_ERROR(drm, "timeout: SOR_DPMS_STATE_WAIT(%d) == 0\n", i); |
336 | NV_ERROR(dev, "SOR_DPMS_STATE(%d) = 0x%08x\n", i, | 292 | NV_ERROR(drm, "SOR_DPMS_STATE(%d) = 0x%08x\n", i, |
337 | nv_rd32(dev, NV50_PDISPLAY_SOR_DPMS_STATE(i))); | 293 | nv_rd32(device, NV50_PDISPLAY_SOR_DPMS_STATE(i))); |
338 | } | 294 | } |
339 | } | 295 | } |
340 | 296 | ||
341 | /* disable interrupts. */ | 297 | /* disable interrupts. */ |
342 | nv_wr32(dev, NV50_PDISPLAY_INTR_EN_1, 0x00000000); | 298 | nv_wr32(device, NV50_PDISPLAY_INTR_EN_1, 0x00000000); |
343 | } | 299 | } |
344 | 300 | ||
345 | int | 301 | int |
346 | nv50_display_create(struct drm_device *dev) | 302 | nv50_display_create(struct drm_device *dev) |
347 | { | 303 | { |
348 | struct drm_nouveau_private *dev_priv = dev->dev_private; | 304 | struct nouveau_drm *drm = nouveau_drm(dev); |
349 | struct dcb_table *dcb = &dev_priv->vbios.dcb; | 305 | struct dcb_table *dcb = &drm->vbios.dcb; |
350 | struct drm_connector *connector, *ct; | 306 | struct drm_connector *connector, *ct; |
351 | struct nv50_display *priv; | 307 | struct nv50_display *priv; |
352 | int ret, i; | 308 | int ret, i; |
353 | 309 | ||
354 | NV_DEBUG_KMS(dev, "\n"); | 310 | NV_DEBUG(drm, "\n"); |
355 | 311 | ||
356 | priv = kzalloc(sizeof(*priv), GFP_KERNEL); | 312 | priv = kzalloc(sizeof(*priv), GFP_KERNEL); |
357 | if (!priv) | 313 | if (!priv) |
358 | return -ENOMEM; | 314 | return -ENOMEM; |
359 | dev_priv->engine.display.priv = priv; | 315 | |
316 | nouveau_display(dev)->priv = priv; | ||
317 | nouveau_display(dev)->dtor = nv50_display_destroy; | ||
318 | nouveau_display(dev)->init = nv50_display_init; | ||
319 | nouveau_display(dev)->fini = nv50_display_fini; | ||
360 | 320 | ||
361 | /* Create CRTC objects */ | 321 | /* Create CRTC objects */ |
362 | for (i = 0; i < 2; i++) { | 322 | for (i = 0; i < 2; i++) { |
@@ -367,10 +327,10 @@ nv50_display_create(struct drm_device *dev) | |||
367 | 327 | ||
368 | /* We setup the encoders from the BIOS table */ | 328 | /* We setup the encoders from the BIOS table */ |
369 | for (i = 0 ; i < dcb->entries; i++) { | 329 | for (i = 0 ; i < dcb->entries; i++) { |
370 | struct dcb_entry *entry = &dcb->entry[i]; | 330 | struct dcb_output *entry = &dcb->entry[i]; |
371 | 331 | ||
372 | if (entry->location != DCB_LOC_ON_CHIP) { | 332 | if (entry->location != DCB_LOC_ON_CHIP) { |
373 | NV_WARN(dev, "Off-chip encoder %d/%d unsupported\n", | 333 | NV_WARN(drm, "Off-chip encoder %d/%d unsupported\n", |
374 | entry->type, ffs(entry->or) - 1); | 334 | entry->type, ffs(entry->or) - 1); |
375 | continue; | 335 | continue; |
376 | } | 336 | } |
@@ -380,16 +340,16 @@ nv50_display_create(struct drm_device *dev) | |||
380 | continue; | 340 | continue; |
381 | 341 | ||
382 | switch (entry->type) { | 342 | switch (entry->type) { |
383 | case OUTPUT_TMDS: | 343 | case DCB_OUTPUT_TMDS: |
384 | case OUTPUT_LVDS: | 344 | case DCB_OUTPUT_LVDS: |
385 | case OUTPUT_DP: | 345 | case DCB_OUTPUT_DP: |
386 | nv50_sor_create(connector, entry); | 346 | nv50_sor_create(connector, entry); |
387 | break; | 347 | break; |
388 | case OUTPUT_ANALOG: | 348 | case DCB_OUTPUT_ANALOG: |
389 | nv50_dac_create(connector, entry); | 349 | nv50_dac_create(connector, entry); |
390 | break; | 350 | break; |
391 | default: | 351 | default: |
392 | NV_WARN(dev, "DCB encoder %d unknown\n", entry->type); | 352 | NV_WARN(drm, "DCB encoder %d unknown\n", entry->type); |
393 | continue; | 353 | continue; |
394 | } | 354 | } |
395 | } | 355 | } |
@@ -397,14 +357,13 @@ nv50_display_create(struct drm_device *dev) | |||
397 | list_for_each_entry_safe(connector, ct, | 357 | list_for_each_entry_safe(connector, ct, |
398 | &dev->mode_config.connector_list, head) { | 358 | &dev->mode_config.connector_list, head) { |
399 | if (!connector->encoder_ids[0]) { | 359 | if (!connector->encoder_ids[0]) { |
400 | NV_WARN(dev, "%s has no encoders, removing\n", | 360 | NV_WARN(drm, "%s has no encoders, removing\n", |
401 | drm_get_connector_name(connector)); | 361 | drm_get_connector_name(connector)); |
402 | connector->funcs->destroy(connector); | 362 | connector->funcs->destroy(connector); |
403 | } | 363 | } |
404 | } | 364 | } |
405 | 365 | ||
406 | tasklet_init(&priv->tasklet, nv50_display_bh, (unsigned long)dev); | 366 | tasklet_init(&priv->tasklet, nv50_display_bh, (unsigned long)dev); |
407 | nouveau_irq_register(dev, 26, nv50_display_isr); | ||
408 | 367 | ||
409 | ret = nv50_evo_create(dev); | 368 | ret = nv50_evo_create(dev); |
410 | if (ret) { | 369 | if (ret) { |
@@ -420,13 +379,16 @@ nv50_display_destroy(struct drm_device *dev) | |||
420 | { | 379 | { |
421 | struct nv50_display *disp = nv50_display(dev); | 380 | struct nv50_display *disp = nv50_display(dev); |
422 | 381 | ||
423 | NV_DEBUG_KMS(dev, "\n"); | ||
424 | |||
425 | nv50_evo_destroy(dev); | 382 | nv50_evo_destroy(dev); |
426 | nouveau_irq_unregister(dev, 26); | ||
427 | kfree(disp); | 383 | kfree(disp); |
428 | } | 384 | } |
429 | 385 | ||
386 | struct nouveau_bo * | ||
387 | nv50_display_crtc_sema(struct drm_device *dev, int crtc) | ||
388 | { | ||
389 | return nv50_display(dev)->crtc[crtc].sem.bo; | ||
390 | } | ||
391 | |||
430 | void | 392 | void |
431 | nv50_display_flip_stop(struct drm_crtc *crtc) | 393 | nv50_display_flip_stop(struct drm_crtc *crtc) |
432 | { | 394 | { |
@@ -457,7 +419,7 @@ int | |||
457 | nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb, | 419 | nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb, |
458 | struct nouveau_channel *chan) | 420 | struct nouveau_channel *chan) |
459 | { | 421 | { |
460 | struct drm_nouveau_private *dev_priv = crtc->dev->dev_private; | 422 | struct nouveau_drm *drm = nouveau_drm(crtc->dev); |
461 | struct nouveau_framebuffer *nv_fb = nouveau_framebuffer(fb); | 423 | struct nouveau_framebuffer *nv_fb = nouveau_framebuffer(fb); |
462 | struct nv50_display *disp = nv50_display(crtc->dev); | 424 | struct nv50_display *disp = nv50_display(crtc->dev); |
463 | struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); | 425 | struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); |
@@ -477,7 +439,7 @@ nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb, | |||
477 | return ret; | 439 | return ret; |
478 | } | 440 | } |
479 | 441 | ||
480 | if (dev_priv->chipset < 0xc0) { | 442 | if (nv_device(drm->device)->chipset < 0xc0) { |
481 | BEGIN_NV04(chan, 0, 0x0060, 2); | 443 | BEGIN_NV04(chan, 0, 0x0060, 2); |
482 | OUT_RING (chan, NvEvoSema0 + nv_crtc->index); | 444 | OUT_RING (chan, NvEvoSema0 + nv_crtc->index); |
483 | OUT_RING (chan, dispc->sem.offset); | 445 | OUT_RING (chan, dispc->sem.offset); |
@@ -487,12 +449,12 @@ nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb, | |||
487 | OUT_RING (chan, dispc->sem.offset ^ 0x10); | 449 | OUT_RING (chan, dispc->sem.offset ^ 0x10); |
488 | OUT_RING (chan, 0x74b1e000); | 450 | OUT_RING (chan, 0x74b1e000); |
489 | BEGIN_NV04(chan, 0, 0x0060, 1); | 451 | BEGIN_NV04(chan, 0, 0x0060, 1); |
490 | if (dev_priv->chipset < 0x84) | 452 | if (nv_device(drm->device)->chipset < 0x84) |
491 | OUT_RING (chan, NvSema); | 453 | OUT_RING (chan, NvSema); |
492 | else | 454 | else |
493 | OUT_RING (chan, chan->vram_handle); | 455 | OUT_RING (chan, chan->vram); |
494 | } else { | 456 | } else { |
495 | u64 offset = nvc0_software_crtc(chan, nv_crtc->index); | 457 | u64 offset = nvc0_fence_crtc(chan, nv_crtc->index); |
496 | offset += dispc->sem.offset; | 458 | offset += dispc->sem.offset; |
497 | BEGIN_NVC0(chan, 0, 0x0010, 4); | 459 | BEGIN_NVC0(chan, 0, 0x0010, 4); |
498 | OUT_RING (chan, upper_32_bits(offset)); | 460 | OUT_RING (chan, upper_32_bits(offset)); |
@@ -555,13 +517,13 @@ nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb, | |||
555 | } | 517 | } |
556 | 518 | ||
557 | static u16 | 519 | static u16 |
558 | nv50_display_script_select(struct drm_device *dev, struct dcb_entry *dcb, | 520 | nv50_display_script_select(struct drm_device *dev, struct dcb_output *dcb, |
559 | u32 mc, int pxclk) | 521 | u32 mc, int pxclk) |
560 | { | 522 | { |
561 | struct drm_nouveau_private *dev_priv = dev->dev_private; | 523 | struct nouveau_drm *drm = nouveau_drm(dev); |
562 | struct nouveau_connector *nv_connector = NULL; | 524 | struct nouveau_connector *nv_connector = NULL; |
563 | struct drm_encoder *encoder; | 525 | struct drm_encoder *encoder; |
564 | struct nvbios *bios = &dev_priv->vbios; | 526 | struct nvbios *bios = &drm->vbios; |
565 | u32 script = 0, or; | 527 | u32 script = 0, or; |
566 | 528 | ||
567 | list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { | 529 | list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { |
@@ -576,7 +538,7 @@ nv50_display_script_select(struct drm_device *dev, struct dcb_entry *dcb, | |||
576 | 538 | ||
577 | or = ffs(dcb->or) - 1; | 539 | or = ffs(dcb->or) - 1; |
578 | switch (dcb->type) { | 540 | switch (dcb->type) { |
579 | case OUTPUT_LVDS: | 541 | case DCB_OUTPUT_LVDS: |
580 | script = (mc >> 8) & 0xf; | 542 | script = (mc >> 8) & 0xf; |
581 | if (bios->fp_no_ddc) { | 543 | if (bios->fp_no_ddc) { |
582 | if (bios->fp.dual_link) | 544 | if (bios->fp.dual_link) |
@@ -609,34 +571,20 @@ nv50_display_script_select(struct drm_device *dev, struct dcb_entry *dcb, | |||
609 | (nv_connector->edid->input & 0x70) >= 0x20) | 571 | (nv_connector->edid->input & 0x70) >= 0x20) |
610 | script |= 0x0200; | 572 | script |= 0x0200; |
611 | } | 573 | } |
612 | |||
613 | if (nouveau_uscript_lvds >= 0) { | ||
614 | NV_INFO(dev, "override script 0x%04x with 0x%04x " | ||
615 | "for output LVDS-%d\n", script, | ||
616 | nouveau_uscript_lvds, or); | ||
617 | script = nouveau_uscript_lvds; | ||
618 | } | ||
619 | break; | 574 | break; |
620 | case OUTPUT_TMDS: | 575 | case DCB_OUTPUT_TMDS: |
621 | script = (mc >> 8) & 0xf; | 576 | script = (mc >> 8) & 0xf; |
622 | if (pxclk >= 165000) | 577 | if (pxclk >= 165000) |
623 | script |= 0x0100; | 578 | script |= 0x0100; |
624 | |||
625 | if (nouveau_uscript_tmds >= 0) { | ||
626 | NV_INFO(dev, "override script 0x%04x with 0x%04x " | ||
627 | "for output TMDS-%d\n", script, | ||
628 | nouveau_uscript_tmds, or); | ||
629 | script = nouveau_uscript_tmds; | ||
630 | } | ||
631 | break; | 579 | break; |
632 | case OUTPUT_DP: | 580 | case DCB_OUTPUT_DP: |
633 | script = (mc >> 8) & 0xf; | 581 | script = (mc >> 8) & 0xf; |
634 | break; | 582 | break; |
635 | case OUTPUT_ANALOG: | 583 | case DCB_OUTPUT_ANALOG: |
636 | script = 0xff; | 584 | script = 0xff; |
637 | break; | 585 | break; |
638 | default: | 586 | default: |
639 | NV_ERROR(dev, "modeset on unsupported output type!\n"); | 587 | NV_ERROR(drm, "modeset on unsupported output type!\n"); |
640 | break; | 588 | break; |
641 | } | 589 | } |
642 | 590 | ||
@@ -644,59 +592,18 @@ nv50_display_script_select(struct drm_device *dev, struct dcb_entry *dcb, | |||
644 | } | 592 | } |
645 | 593 | ||
646 | static void | 594 | static void |
647 | nv50_display_vblank_crtc_handler(struct drm_device *dev, int crtc) | ||
648 | { | ||
649 | struct drm_nouveau_private *dev_priv = dev->dev_private; | ||
650 | struct nouveau_software_priv *psw = nv_engine(dev, NVOBJ_ENGINE_SW); | ||
651 | struct nouveau_software_chan *pch, *tmp; | ||
652 | |||
653 | list_for_each_entry_safe(pch, tmp, &psw->vblank, vblank.list) { | ||
654 | if (pch->vblank.head != crtc) | ||
655 | continue; | ||
656 | |||
657 | spin_lock(&psw->peephole_lock); | ||
658 | nv_wr32(dev, 0x001704, pch->vblank.channel); | ||
659 | nv_wr32(dev, 0x001710, 0x80000000 | pch->vblank.ctxdma); | ||
660 | if (dev_priv->chipset == 0x50) { | ||
661 | nv_wr32(dev, 0x001570, pch->vblank.offset); | ||
662 | nv_wr32(dev, 0x001574, pch->vblank.value); | ||
663 | } else { | ||
664 | nv_wr32(dev, 0x060010, pch->vblank.offset); | ||
665 | nv_wr32(dev, 0x060014, pch->vblank.value); | ||
666 | } | ||
667 | spin_unlock(&psw->peephole_lock); | ||
668 | |||
669 | list_del(&pch->vblank.list); | ||
670 | drm_vblank_put(dev, crtc); | ||
671 | } | ||
672 | |||
673 | drm_handle_vblank(dev, crtc); | ||
674 | } | ||
675 | |||
676 | static void | ||
677 | nv50_display_vblank_handler(struct drm_device *dev, uint32_t intr) | ||
678 | { | ||
679 | if (intr & NV50_PDISPLAY_INTR_1_VBLANK_CRTC_0) | ||
680 | nv50_display_vblank_crtc_handler(dev, 0); | ||
681 | |||
682 | if (intr & NV50_PDISPLAY_INTR_1_VBLANK_CRTC_1) | ||
683 | nv50_display_vblank_crtc_handler(dev, 1); | ||
684 | |||
685 | nv_wr32(dev, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_VBLANK_CRTC); | ||
686 | } | ||
687 | |||
688 | static void | ||
689 | nv50_display_unk10_handler(struct drm_device *dev) | 595 | nv50_display_unk10_handler(struct drm_device *dev) |
690 | { | 596 | { |
691 | struct drm_nouveau_private *dev_priv = dev->dev_private; | 597 | struct nouveau_device *device = nouveau_dev(dev); |
598 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
692 | struct nv50_display *disp = nv50_display(dev); | 599 | struct nv50_display *disp = nv50_display(dev); |
693 | u32 unk30 = nv_rd32(dev, 0x610030), mc; | 600 | u32 unk30 = nv_rd32(device, 0x610030), mc; |
694 | int i, crtc, or = 0, type = OUTPUT_ANY; | 601 | int i, crtc, or = 0, type = DCB_OUTPUT_ANY; |
695 | 602 | ||
696 | NV_DEBUG_KMS(dev, "0x610030: 0x%08x\n", unk30); | 603 | NV_DEBUG(drm, "0x610030: 0x%08x\n", unk30); |
697 | disp->irq.dcb = NULL; | 604 | disp->irq.dcb = NULL; |
698 | 605 | ||
699 | nv_wr32(dev, 0x619494, nv_rd32(dev, 0x619494) & ~8); | 606 | nv_wr32(device, 0x619494, nv_rd32(device, 0x619494) & ~8); |
700 | 607 | ||
701 | /* Determine which CRTC we're dealing with, only 1 ever will be | 608 | /* Determine which CRTC we're dealing with, only 1 ever will be |
702 | * signalled at the same time with the current nouveau code. | 609 | * signalled at the same time with the current nouveau code. |
@@ -711,44 +618,44 @@ nv50_display_unk10_handler(struct drm_device *dev) | |||
711 | goto ack; | 618 | goto ack; |
712 | 619 | ||
713 | /* Find which encoder was connected to the CRTC */ | 620 | /* Find which encoder was connected to the CRTC */ |
714 | for (i = 0; type == OUTPUT_ANY && i < 3; i++) { | 621 | for (i = 0; type == DCB_OUTPUT_ANY && i < 3; i++) { |
715 | mc = nv_rd32(dev, NV50_PDISPLAY_DAC_MODE_CTRL_C(i)); | 622 | mc = nv_rd32(device, NV50_PDISPLAY_DAC_MODE_CTRL_C(i)); |
716 | NV_DEBUG_KMS(dev, "DAC-%d mc: 0x%08x\n", i, mc); | 623 | NV_DEBUG(drm, "DAC-%d mc: 0x%08x\n", i, mc); |
717 | if (!(mc & (1 << crtc))) | 624 | if (!(mc & (1 << crtc))) |
718 | continue; | 625 | continue; |
719 | 626 | ||
720 | switch ((mc & 0x00000f00) >> 8) { | 627 | switch ((mc & 0x00000f00) >> 8) { |
721 | case 0: type = OUTPUT_ANALOG; break; | 628 | case 0: type = DCB_OUTPUT_ANALOG; break; |
722 | case 1: type = OUTPUT_TV; break; | 629 | case 1: type = DCB_OUTPUT_TV; break; |
723 | default: | 630 | default: |
724 | NV_ERROR(dev, "invalid mc, DAC-%d: 0x%08x\n", i, mc); | 631 | NV_ERROR(drm, "invalid mc, DAC-%d: 0x%08x\n", i, mc); |
725 | goto ack; | 632 | goto ack; |
726 | } | 633 | } |
727 | 634 | ||
728 | or = i; | 635 | or = i; |
729 | } | 636 | } |
730 | 637 | ||
731 | for (i = 0; type == OUTPUT_ANY && i < nv50_sor_nr(dev); i++) { | 638 | for (i = 0; type == DCB_OUTPUT_ANY && i < nv50_sor_nr(dev); i++) { |
732 | if (dev_priv->chipset < 0x90 || | 639 | if (nv_device(drm->device)->chipset < 0x90 || |
733 | dev_priv->chipset == 0x92 || | 640 | nv_device(drm->device)->chipset == 0x92 || |
734 | dev_priv->chipset == 0xa0) | 641 | nv_device(drm->device)->chipset == 0xa0) |
735 | mc = nv_rd32(dev, NV50_PDISPLAY_SOR_MODE_CTRL_C(i)); | 642 | mc = nv_rd32(device, NV50_PDISPLAY_SOR_MODE_CTRL_C(i)); |
736 | else | 643 | else |
737 | mc = nv_rd32(dev, NV90_PDISPLAY_SOR_MODE_CTRL_C(i)); | 644 | mc = nv_rd32(device, NV90_PDISPLAY_SOR_MODE_CTRL_C(i)); |
738 | 645 | ||
739 | NV_DEBUG_KMS(dev, "SOR-%d mc: 0x%08x\n", i, mc); | 646 | NV_DEBUG(drm, "SOR-%d mc: 0x%08x\n", i, mc); |
740 | if (!(mc & (1 << crtc))) | 647 | if (!(mc & (1 << crtc))) |
741 | continue; | 648 | continue; |
742 | 649 | ||
743 | switch ((mc & 0x00000f00) >> 8) { | 650 | switch ((mc & 0x00000f00) >> 8) { |
744 | case 0: type = OUTPUT_LVDS; break; | 651 | case 0: type = DCB_OUTPUT_LVDS; break; |
745 | case 1: type = OUTPUT_TMDS; break; | 652 | case 1: type = DCB_OUTPUT_TMDS; break; |
746 | case 2: type = OUTPUT_TMDS; break; | 653 | case 2: type = DCB_OUTPUT_TMDS; break; |
747 | case 5: type = OUTPUT_TMDS; break; | 654 | case 5: type = DCB_OUTPUT_TMDS; break; |
748 | case 8: type = OUTPUT_DP; break; | 655 | case 8: type = DCB_OUTPUT_DP; break; |
749 | case 9: type = OUTPUT_DP; break; | 656 | case 9: type = DCB_OUTPUT_DP; break; |
750 | default: | 657 | default: |
751 | NV_ERROR(dev, "invalid mc, SOR-%d: 0x%08x\n", i, mc); | 658 | NV_ERROR(drm, "invalid mc, SOR-%d: 0x%08x\n", i, mc); |
752 | goto ack; | 659 | goto ack; |
753 | } | 660 | } |
754 | 661 | ||
@@ -756,12 +663,12 @@ nv50_display_unk10_handler(struct drm_device *dev) | |||
756 | } | 663 | } |
757 | 664 | ||
758 | /* There was no encoder to disable */ | 665 | /* There was no encoder to disable */ |
759 | if (type == OUTPUT_ANY) | 666 | if (type == DCB_OUTPUT_ANY) |
760 | goto ack; | 667 | goto ack; |
761 | 668 | ||
762 | /* Disable the encoder */ | 669 | /* Disable the encoder */ |
763 | for (i = 0; i < dev_priv->vbios.dcb.entries; i++) { | 670 | for (i = 0; i < drm->vbios.dcb.entries; i++) { |
764 | struct dcb_entry *dcb = &dev_priv->vbios.dcb.entry[i]; | 671 | struct dcb_output *dcb = &drm->vbios.dcb.entry[i]; |
765 | 672 | ||
766 | if (dcb->type == type && (dcb->or & (1 << or))) { | 673 | if (dcb->type == type && (dcb->or & (1 << or))) { |
767 | nouveau_bios_run_display_table(dev, 0, -1, dcb, -1); | 674 | nouveau_bios_run_display_table(dev, 0, -1, dcb, -1); |
@@ -770,22 +677,23 @@ nv50_display_unk10_handler(struct drm_device *dev) | |||
770 | } | 677 | } |
771 | } | 678 | } |
772 | 679 | ||
773 | NV_ERROR(dev, "no dcb for %d %d 0x%08x\n", or, type, mc); | 680 | NV_ERROR(drm, "no dcb for %d %d 0x%08x\n", or, type, mc); |
774 | ack: | 681 | ack: |
775 | nv_wr32(dev, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK10); | 682 | nv_wr32(device, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK10); |
776 | nv_wr32(dev, 0x610030, 0x80000000); | 683 | nv_wr32(device, 0x610030, 0x80000000); |
777 | } | 684 | } |
778 | 685 | ||
779 | static void | 686 | static void |
780 | nv50_display_unk20_handler(struct drm_device *dev) | 687 | nv50_display_unk20_handler(struct drm_device *dev) |
781 | { | 688 | { |
782 | struct drm_nouveau_private *dev_priv = dev->dev_private; | 689 | struct nouveau_device *device = nouveau_dev(dev); |
690 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
783 | struct nv50_display *disp = nv50_display(dev); | 691 | struct nv50_display *disp = nv50_display(dev); |
784 | u32 unk30 = nv_rd32(dev, 0x610030), tmp, pclk, script, mc = 0; | 692 | u32 unk30 = nv_rd32(device, 0x610030), tmp, pclk, script, mc = 0; |
785 | struct dcb_entry *dcb; | 693 | struct dcb_output *dcb; |
786 | int i, crtc, or = 0, type = OUTPUT_ANY; | 694 | int i, crtc, or = 0, type = DCB_OUTPUT_ANY; |
787 | 695 | ||
788 | NV_DEBUG_KMS(dev, "0x610030: 0x%08x\n", unk30); | 696 | NV_DEBUG(drm, "0x610030: 0x%08x\n", unk30); |
789 | dcb = disp->irq.dcb; | 697 | dcb = disp->irq.dcb; |
790 | if (dcb) { | 698 | if (dcb) { |
791 | nouveau_bios_run_display_table(dev, 0, -2, dcb, -1); | 699 | nouveau_bios_run_display_table(dev, 0, -2, dcb, -1); |
@@ -795,86 +703,86 @@ nv50_display_unk20_handler(struct drm_device *dev) | |||
795 | /* CRTC clock change requested? */ | 703 | /* CRTC clock change requested? */ |
796 | crtc = ffs((unk30 & 0x00000600) >> 9) - 1; | 704 | crtc = ffs((unk30 & 0x00000600) >> 9) - 1; |
797 | if (crtc >= 0) { | 705 | if (crtc >= 0) { |
798 | pclk = nv_rd32(dev, NV50_PDISPLAY_CRTC_P(crtc, CLOCK)); | 706 | pclk = nv_rd32(device, NV50_PDISPLAY_CRTC_P(crtc, CLOCK)); |
799 | pclk &= 0x003fffff; | 707 | pclk &= 0x003fffff; |
800 | if (pclk) | 708 | if (pclk) |
801 | nv50_crtc_set_clock(dev, crtc, pclk); | 709 | nv50_crtc_set_clock(dev, crtc, pclk); |
802 | 710 | ||
803 | tmp = nv_rd32(dev, NV50_PDISPLAY_CRTC_CLK_CTRL2(crtc)); | 711 | tmp = nv_rd32(device, NV50_PDISPLAY_CRTC_CLK_CTRL2(crtc)); |
804 | tmp &= ~0x000000f; | 712 | tmp &= ~0x000000f; |
805 | nv_wr32(dev, NV50_PDISPLAY_CRTC_CLK_CTRL2(crtc), tmp); | 713 | nv_wr32(device, NV50_PDISPLAY_CRTC_CLK_CTRL2(crtc), tmp); |
806 | } | 714 | } |
807 | 715 | ||
808 | /* Nothing needs to be done for the encoder */ | 716 | /* Nothing needs to be done for the encoder */ |
809 | crtc = ffs((unk30 & 0x00000180) >> 7) - 1; | 717 | crtc = ffs((unk30 & 0x00000180) >> 7) - 1; |
810 | if (crtc < 0) | 718 | if (crtc < 0) |
811 | goto ack; | 719 | goto ack; |
812 | pclk = nv_rd32(dev, NV50_PDISPLAY_CRTC_P(crtc, CLOCK)) & 0x003fffff; | 720 | pclk = nv_rd32(device, NV50_PDISPLAY_CRTC_P(crtc, CLOCK)) & 0x003fffff; |
813 | 721 | ||
814 | /* Find which encoder is connected to the CRTC */ | 722 | /* Find which encoder is connected to the CRTC */ |
815 | for (i = 0; type == OUTPUT_ANY && i < 3; i++) { | 723 | for (i = 0; type == DCB_OUTPUT_ANY && i < 3; i++) { |
816 | mc = nv_rd32(dev, NV50_PDISPLAY_DAC_MODE_CTRL_P(i)); | 724 | mc = nv_rd32(device, NV50_PDISPLAY_DAC_MODE_CTRL_P(i)); |
817 | NV_DEBUG_KMS(dev, "DAC-%d mc: 0x%08x\n", i, mc); | 725 | NV_DEBUG(drm, "DAC-%d mc: 0x%08x\n", i, mc); |
818 | if (!(mc & (1 << crtc))) | 726 | if (!(mc & (1 << crtc))) |
819 | continue; | 727 | continue; |
820 | 728 | ||
821 | switch ((mc & 0x00000f00) >> 8) { | 729 | switch ((mc & 0x00000f00) >> 8) { |
822 | case 0: type = OUTPUT_ANALOG; break; | 730 | case 0: type = DCB_OUTPUT_ANALOG; break; |
823 | case 1: type = OUTPUT_TV; break; | 731 | case 1: type = DCB_OUTPUT_TV; break; |
824 | default: | 732 | default: |
825 | NV_ERROR(dev, "invalid mc, DAC-%d: 0x%08x\n", i, mc); | 733 | NV_ERROR(drm, "invalid mc, DAC-%d: 0x%08x\n", i, mc); |
826 | goto ack; | 734 | goto ack; |
827 | } | 735 | } |
828 | 736 | ||
829 | or = i; | 737 | or = i; |
830 | } | 738 | } |
831 | 739 | ||
832 | for (i = 0; type == OUTPUT_ANY && i < nv50_sor_nr(dev); i++) { | 740 | for (i = 0; type == DCB_OUTPUT_ANY && i < nv50_sor_nr(dev); i++) { |
833 | if (dev_priv->chipset < 0x90 || | 741 | if (nv_device(drm->device)->chipset < 0x90 || |
834 | dev_priv->chipset == 0x92 || | 742 | nv_device(drm->device)->chipset == 0x92 || |
835 | dev_priv->chipset == 0xa0) | 743 | nv_device(drm->device)->chipset == 0xa0) |
836 | mc = nv_rd32(dev, NV50_PDISPLAY_SOR_MODE_CTRL_P(i)); | 744 | mc = nv_rd32(device, NV50_PDISPLAY_SOR_MODE_CTRL_P(i)); |
837 | else | 745 | else |
838 | mc = nv_rd32(dev, NV90_PDISPLAY_SOR_MODE_CTRL_P(i)); | 746 | mc = nv_rd32(device, NV90_PDISPLAY_SOR_MODE_CTRL_P(i)); |
839 | 747 | ||
840 | NV_DEBUG_KMS(dev, "SOR-%d mc: 0x%08x\n", i, mc); | 748 | NV_DEBUG(drm, "SOR-%d mc: 0x%08x\n", i, mc); |
841 | if (!(mc & (1 << crtc))) | 749 | if (!(mc & (1 << crtc))) |
842 | continue; | 750 | continue; |
843 | 751 | ||
844 | switch ((mc & 0x00000f00) >> 8) { | 752 | switch ((mc & 0x00000f00) >> 8) { |
845 | case 0: type = OUTPUT_LVDS; break; | 753 | case 0: type = DCB_OUTPUT_LVDS; break; |
846 | case 1: type = OUTPUT_TMDS; break; | 754 | case 1: type = DCB_OUTPUT_TMDS; break; |
847 | case 2: type = OUTPUT_TMDS; break; | 755 | case 2: type = DCB_OUTPUT_TMDS; break; |
848 | case 5: type = OUTPUT_TMDS; break; | 756 | case 5: type = DCB_OUTPUT_TMDS; break; |
849 | case 8: type = OUTPUT_DP; break; | 757 | case 8: type = DCB_OUTPUT_DP; break; |
850 | case 9: type = OUTPUT_DP; break; | 758 | case 9: type = DCB_OUTPUT_DP; break; |
851 | default: | 759 | default: |
852 | NV_ERROR(dev, "invalid mc, SOR-%d: 0x%08x\n", i, mc); | 760 | NV_ERROR(drm, "invalid mc, SOR-%d: 0x%08x\n", i, mc); |
853 | goto ack; | 761 | goto ack; |
854 | } | 762 | } |
855 | 763 | ||
856 | or = i; | 764 | or = i; |
857 | } | 765 | } |
858 | 766 | ||
859 | if (type == OUTPUT_ANY) | 767 | if (type == DCB_OUTPUT_ANY) |
860 | goto ack; | 768 | goto ack; |
861 | 769 | ||
862 | /* Enable the encoder */ | 770 | /* Enable the encoder */ |
863 | for (i = 0; i < dev_priv->vbios.dcb.entries; i++) { | 771 | for (i = 0; i < drm->vbios.dcb.entries; i++) { |
864 | dcb = &dev_priv->vbios.dcb.entry[i]; | 772 | dcb = &drm->vbios.dcb.entry[i]; |
865 | if (dcb->type == type && (dcb->or & (1 << or))) | 773 | if (dcb->type == type && (dcb->or & (1 << or))) |
866 | break; | 774 | break; |
867 | } | 775 | } |
868 | 776 | ||
869 | if (i == dev_priv->vbios.dcb.entries) { | 777 | if (i == drm->vbios.dcb.entries) { |
870 | NV_ERROR(dev, "no dcb for %d %d 0x%08x\n", or, type, mc); | 778 | NV_ERROR(drm, "no dcb for %d %d 0x%08x\n", or, type, mc); |
871 | goto ack; | 779 | goto ack; |
872 | } | 780 | } |
873 | 781 | ||
874 | script = nv50_display_script_select(dev, dcb, mc, pclk); | 782 | script = nv50_display_script_select(dev, dcb, mc, pclk); |
875 | nouveau_bios_run_display_table(dev, script, pclk, dcb, -1); | 783 | nouveau_bios_run_display_table(dev, script, pclk, dcb, -1); |
876 | 784 | ||
877 | if (type == OUTPUT_DP) { | 785 | if (type == DCB_OUTPUT_DP) { |
878 | int link = !(dcb->dpconf.sor.link & 1); | 786 | int link = !(dcb->dpconf.sor.link & 1); |
879 | if ((mc & 0x000f0000) == 0x00020000) | 787 | if ((mc & 0x000f0000) == 0x00020000) |
880 | nv50_sor_dp_calc_tu(dev, or, link, pclk, 18); | 788 | nv50_sor_dp_calc_tu(dev, or, link, pclk, 18); |
@@ -882,14 +790,14 @@ nv50_display_unk20_handler(struct drm_device *dev) | |||
882 | nv50_sor_dp_calc_tu(dev, or, link, pclk, 24); | 790 | nv50_sor_dp_calc_tu(dev, or, link, pclk, 24); |
883 | } | 791 | } |
884 | 792 | ||
885 | if (dcb->type != OUTPUT_ANALOG) { | 793 | if (dcb->type != DCB_OUTPUT_ANALOG) { |
886 | tmp = nv_rd32(dev, NV50_PDISPLAY_SOR_CLK_CTRL2(or)); | 794 | tmp = nv_rd32(device, NV50_PDISPLAY_SOR_CLK_CTRL2(or)); |
887 | tmp &= ~0x00000f0f; | 795 | tmp &= ~0x00000f0f; |
888 | if (script & 0x0100) | 796 | if (script & 0x0100) |
889 | tmp |= 0x00000101; | 797 | tmp |= 0x00000101; |
890 | nv_wr32(dev, NV50_PDISPLAY_SOR_CLK_CTRL2(or), tmp); | 798 | nv_wr32(device, NV50_PDISPLAY_SOR_CLK_CTRL2(or), tmp); |
891 | } else { | 799 | } else { |
892 | nv_wr32(dev, NV50_PDISPLAY_DAC_CLK_CTRL2(or), 0); | 800 | nv_wr32(device, NV50_PDISPLAY_DAC_CLK_CTRL2(or), 0); |
893 | } | 801 | } |
894 | 802 | ||
895 | disp->irq.dcb = dcb; | 803 | disp->irq.dcb = dcb; |
@@ -897,8 +805,8 @@ nv50_display_unk20_handler(struct drm_device *dev) | |||
897 | disp->irq.script = script; | 805 | disp->irq.script = script; |
898 | 806 | ||
899 | ack: | 807 | ack: |
900 | nv_wr32(dev, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK20); | 808 | nv_wr32(device, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK20); |
901 | nv_wr32(dev, 0x610030, 0x80000000); | 809 | nv_wr32(device, 0x610030, 0x80000000); |
902 | } | 810 | } |
903 | 811 | ||
904 | /* If programming a TMDS output on a SOR that can also be configured for | 812 | /* If programming a TMDS output on a SOR that can also be configured for |
@@ -910,23 +818,24 @@ ack: | |||
910 | * programmed for DisplayPort. | 818 | * programmed for DisplayPort. |
911 | */ | 819 | */ |
912 | static void | 820 | static void |
913 | nv50_display_unk40_dp_set_tmds(struct drm_device *dev, struct dcb_entry *dcb) | 821 | nv50_display_unk40_dp_set_tmds(struct drm_device *dev, struct dcb_output *dcb) |
914 | { | 822 | { |
823 | struct nouveau_device *device = nouveau_dev(dev); | ||
915 | int or = ffs(dcb->or) - 1, link = !(dcb->dpconf.sor.link & 1); | 824 | int or = ffs(dcb->or) - 1, link = !(dcb->dpconf.sor.link & 1); |
916 | struct drm_encoder *encoder; | 825 | struct drm_encoder *encoder; |
917 | u32 tmp; | 826 | u32 tmp; |
918 | 827 | ||
919 | if (dcb->type != OUTPUT_TMDS) | 828 | if (dcb->type != DCB_OUTPUT_TMDS) |
920 | return; | 829 | return; |
921 | 830 | ||
922 | list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { | 831 | list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { |
923 | struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); | 832 | struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); |
924 | 833 | ||
925 | if (nv_encoder->dcb->type == OUTPUT_DP && | 834 | if (nv_encoder->dcb->type == DCB_OUTPUT_DP && |
926 | nv_encoder->dcb->or & (1 << or)) { | 835 | nv_encoder->dcb->or & (1 << or)) { |
927 | tmp = nv_rd32(dev, NV50_SOR_DP_CTRL(or, link)); | 836 | tmp = nv_rd32(device, NV50_SOR_DP_CTRL(or, link)); |
928 | tmp &= ~NV50_SOR_DP_CTRL_ENABLED; | 837 | tmp &= ~NV50_SOR_DP_CTRL_ENABLED; |
929 | nv_wr32(dev, NV50_SOR_DP_CTRL(or, link), tmp); | 838 | nv_wr32(device, NV50_SOR_DP_CTRL(or, link), tmp); |
930 | break; | 839 | break; |
931 | } | 840 | } |
932 | } | 841 | } |
@@ -935,12 +844,14 @@ nv50_display_unk40_dp_set_tmds(struct drm_device *dev, struct dcb_entry *dcb) | |||
935 | static void | 844 | static void |
936 | nv50_display_unk40_handler(struct drm_device *dev) | 845 | nv50_display_unk40_handler(struct drm_device *dev) |
937 | { | 846 | { |
847 | struct nouveau_device *device = nouveau_dev(dev); | ||
848 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
938 | struct nv50_display *disp = nv50_display(dev); | 849 | struct nv50_display *disp = nv50_display(dev); |
939 | struct dcb_entry *dcb = disp->irq.dcb; | 850 | struct dcb_output *dcb = disp->irq.dcb; |
940 | u16 script = disp->irq.script; | 851 | u16 script = disp->irq.script; |
941 | u32 unk30 = nv_rd32(dev, 0x610030), pclk = disp->irq.pclk; | 852 | u32 unk30 = nv_rd32(device, 0x610030), pclk = disp->irq.pclk; |
942 | 853 | ||
943 | NV_DEBUG_KMS(dev, "0x610030: 0x%08x\n", unk30); | 854 | NV_DEBUG(drm, "0x610030: 0x%08x\n", unk30); |
944 | disp->irq.dcb = NULL; | 855 | disp->irq.dcb = NULL; |
945 | if (!dcb) | 856 | if (!dcb) |
946 | goto ack; | 857 | goto ack; |
@@ -949,21 +860,23 @@ nv50_display_unk40_handler(struct drm_device *dev) | |||
949 | nv50_display_unk40_dp_set_tmds(dev, dcb); | 860 | nv50_display_unk40_dp_set_tmds(dev, dcb); |
950 | 861 | ||
951 | ack: | 862 | ack: |
952 | nv_wr32(dev, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK40); | 863 | nv_wr32(device, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK40); |
953 | nv_wr32(dev, 0x610030, 0x80000000); | 864 | nv_wr32(device, 0x610030, 0x80000000); |
954 | nv_wr32(dev, 0x619494, nv_rd32(dev, 0x619494) | 8); | 865 | nv_wr32(device, 0x619494, nv_rd32(device, 0x619494) | 8); |
955 | } | 866 | } |
956 | 867 | ||
957 | static void | 868 | static void |
958 | nv50_display_bh(unsigned long data) | 869 | nv50_display_bh(unsigned long data) |
959 | { | 870 | { |
960 | struct drm_device *dev = (struct drm_device *)data; | 871 | struct drm_device *dev = (struct drm_device *)data; |
872 | struct nouveau_device *device = nouveau_dev(dev); | ||
873 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
961 | 874 | ||
962 | for (;;) { | 875 | for (;;) { |
963 | uint32_t intr0 = nv_rd32(dev, NV50_PDISPLAY_INTR_0); | 876 | uint32_t intr0 = nv_rd32(device, NV50_PDISPLAY_INTR_0); |
964 | uint32_t intr1 = nv_rd32(dev, NV50_PDISPLAY_INTR_1); | 877 | uint32_t intr1 = nv_rd32(device, NV50_PDISPLAY_INTR_1); |
965 | 878 | ||
966 | NV_DEBUG_KMS(dev, "PDISPLAY_INTR_BH 0x%08x 0x%08x\n", intr0, intr1); | 879 | NV_DEBUG(drm, "PDISPLAY_INTR_BH 0x%08x 0x%08x\n", intr0, intr1); |
967 | 880 | ||
968 | if (intr1 & NV50_PDISPLAY_INTR_1_CLK_UNK10) | 881 | if (intr1 & NV50_PDISPLAY_INTR_1_CLK_UNK10) |
969 | nv50_display_unk10_handler(dev); | 882 | nv50_display_unk10_handler(dev); |
@@ -977,13 +890,15 @@ nv50_display_bh(unsigned long data) | |||
977 | break; | 890 | break; |
978 | } | 891 | } |
979 | 892 | ||
980 | nv_wr32(dev, NV03_PMC_INTR_EN_0, 1); | 893 | nv_wr32(device, NV03_PMC_INTR_EN_0, 1); |
981 | } | 894 | } |
982 | 895 | ||
983 | static void | 896 | static void |
984 | nv50_display_error_handler(struct drm_device *dev) | 897 | nv50_display_error_handler(struct drm_device *dev) |
985 | { | 898 | { |
986 | u32 channels = (nv_rd32(dev, NV50_PDISPLAY_INTR_0) & 0x001f0000) >> 16; | 899 | struct nouveau_device *device = nouveau_dev(dev); |
900 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
901 | u32 channels = (nv_rd32(device, NV50_PDISPLAY_INTR_0) & 0x001f0000) >> 16; | ||
987 | u32 addr, data; | 902 | u32 addr, data; |
988 | int chid; | 903 | int chid; |
989 | 904 | ||
@@ -991,29 +906,31 @@ nv50_display_error_handler(struct drm_device *dev) | |||
991 | if (!(channels & (1 << chid))) | 906 | if (!(channels & (1 << chid))) |
992 | continue; | 907 | continue; |
993 | 908 | ||
994 | nv_wr32(dev, NV50_PDISPLAY_INTR_0, 0x00010000 << chid); | 909 | nv_wr32(device, NV50_PDISPLAY_INTR_0, 0x00010000 << chid); |
995 | addr = nv_rd32(dev, NV50_PDISPLAY_TRAPPED_ADDR(chid)); | 910 | addr = nv_rd32(device, NV50_PDISPLAY_TRAPPED_ADDR(chid)); |
996 | data = nv_rd32(dev, NV50_PDISPLAY_TRAPPED_DATA(chid)); | 911 | data = nv_rd32(device, NV50_PDISPLAY_TRAPPED_DATA(chid)); |
997 | NV_ERROR(dev, "EvoCh %d Mthd 0x%04x Data 0x%08x " | 912 | NV_ERROR(drm, "EvoCh %d Mthd 0x%04x Data 0x%08x " |
998 | "(0x%04x 0x%02x)\n", chid, | 913 | "(0x%04x 0x%02x)\n", chid, |
999 | addr & 0xffc, data, addr >> 16, (addr >> 12) & 0xf); | 914 | addr & 0xffc, data, addr >> 16, (addr >> 12) & 0xf); |
1000 | 915 | ||
1001 | nv_wr32(dev, NV50_PDISPLAY_TRAPPED_ADDR(chid), 0x90000000); | 916 | nv_wr32(device, NV50_PDISPLAY_TRAPPED_ADDR(chid), 0x90000000); |
1002 | } | 917 | } |
1003 | } | 918 | } |
1004 | 919 | ||
1005 | static void | 920 | void |
1006 | nv50_display_isr(struct drm_device *dev) | 921 | nv50_display_intr(struct drm_device *dev) |
1007 | { | 922 | { |
923 | struct nouveau_device *device = nouveau_dev(dev); | ||
924 | struct nouveau_drm *drm = nouveau_drm(dev); | ||
1008 | struct nv50_display *disp = nv50_display(dev); | 925 | struct nv50_display *disp = nv50_display(dev); |
1009 | uint32_t delayed = 0; | 926 | uint32_t delayed = 0; |
1010 | 927 | ||
1011 | while (nv_rd32(dev, NV50_PMC_INTR_0) & NV50_PMC_INTR_0_DISPLAY) { | 928 | while (nv_rd32(device, NV50_PMC_INTR_0) & NV50_PMC_INTR_0_DISPLAY) { |
1012 | uint32_t intr0 = nv_rd32(dev, NV50_PDISPLAY_INTR_0); | 929 | uint32_t intr0 = nv_rd32(device, NV50_PDISPLAY_INTR_0); |
1013 | uint32_t intr1 = nv_rd32(dev, NV50_PDISPLAY_INTR_1); | 930 | uint32_t intr1 = nv_rd32(device, NV50_PDISPLAY_INTR_1); |
1014 | uint32_t clock; | 931 | uint32_t clock; |
1015 | 932 | ||
1016 | NV_DEBUG_KMS(dev, "PDISPLAY_INTR 0x%08x 0x%08x\n", intr0, intr1); | 933 | NV_DEBUG(drm, "PDISPLAY_INTR 0x%08x 0x%08x\n", intr0, intr1); |
1017 | 934 | ||
1018 | if (!intr0 && !(intr1 & ~delayed)) | 935 | if (!intr0 && !(intr1 & ~delayed)) |
1019 | break; | 936 | break; |
@@ -1024,29 +941,29 @@ nv50_display_isr(struct drm_device *dev) | |||
1024 | } | 941 | } |
1025 | 942 | ||
1026 | if (intr1 & NV50_PDISPLAY_INTR_1_VBLANK_CRTC) { | 943 | if (intr1 & NV50_PDISPLAY_INTR_1_VBLANK_CRTC) { |
1027 | nv50_display_vblank_handler(dev, intr1); | ||
1028 | intr1 &= ~NV50_PDISPLAY_INTR_1_VBLANK_CRTC; | 944 | intr1 &= ~NV50_PDISPLAY_INTR_1_VBLANK_CRTC; |
945 | delayed |= NV50_PDISPLAY_INTR_1_VBLANK_CRTC; | ||
1029 | } | 946 | } |
1030 | 947 | ||
1031 | clock = (intr1 & (NV50_PDISPLAY_INTR_1_CLK_UNK10 | | 948 | clock = (intr1 & (NV50_PDISPLAY_INTR_1_CLK_UNK10 | |
1032 | NV50_PDISPLAY_INTR_1_CLK_UNK20 | | 949 | NV50_PDISPLAY_INTR_1_CLK_UNK20 | |
1033 | NV50_PDISPLAY_INTR_1_CLK_UNK40)); | 950 | NV50_PDISPLAY_INTR_1_CLK_UNK40)); |
1034 | if (clock) { | 951 | if (clock) { |
1035 | nv_wr32(dev, NV03_PMC_INTR_EN_0, 0); | 952 | nv_wr32(device, NV03_PMC_INTR_EN_0, 0); |
1036 | tasklet_schedule(&disp->tasklet); | 953 | tasklet_schedule(&disp->tasklet); |
1037 | delayed |= clock; | 954 | delayed |= clock; |
1038 | intr1 &= ~clock; | 955 | intr1 &= ~clock; |
1039 | } | 956 | } |
1040 | 957 | ||
1041 | if (intr0) { | 958 | if (intr0) { |
1042 | NV_ERROR(dev, "unknown PDISPLAY_INTR_0: 0x%08x\n", intr0); | 959 | NV_ERROR(drm, "unknown PDISPLAY_INTR_0: 0x%08x\n", intr0); |
1043 | nv_wr32(dev, NV50_PDISPLAY_INTR_0, intr0); | 960 | nv_wr32(device, NV50_PDISPLAY_INTR_0, intr0); |
1044 | } | 961 | } |
1045 | 962 | ||
1046 | if (intr1) { | 963 | if (intr1) { |
1047 | NV_ERROR(dev, | 964 | NV_ERROR(drm, |
1048 | "unknown PDISPLAY_INTR_1: 0x%08x\n", intr1); | 965 | "unknown PDISPLAY_INTR_1: 0x%08x\n", intr1); |
1049 | nv_wr32(dev, NV50_PDISPLAY_INTR_1, intr1); | 966 | nv_wr32(device, NV50_PDISPLAY_INTR_1, intr1); |
1050 | } | 967 | } |
1051 | } | 968 | } |
1052 | } | 969 | } |