1 | // SPDX-License-Identifier: MIT |
2 | /* |
3 | * Copyright © 2023 Intel Corporation |
4 | */ |
5 | |
6 | #include "gt/intel_rps.h" |
7 | #include "i915_drv.h" |
8 | #include "i915_irq.h" |
9 | #include "i915_reg.h" |
10 | #include "icl_dsi_regs.h" |
11 | #include "intel_crtc.h" |
12 | #include "intel_de.h" |
13 | #include "intel_display_irq.h" |
14 | #include "intel_display_trace.h" |
15 | #include "intel_display_types.h" |
16 | #include "intel_dp_aux.h" |
17 | #include "intel_fdi_regs.h" |
18 | #include "intel_fifo_underrun.h" |
19 | #include "intel_gmbus.h" |
20 | #include "intel_hotplug_irq.h" |
21 | #include "intel_pmdemand.h" |
22 | #include "intel_psr.h" |
23 | #include "intel_psr_regs.h" |
24 | |
25 | static void |
26 | intel_handle_vblank(struct drm_i915_private *dev_priv, enum pipe pipe) |
27 | { |
28 | struct intel_crtc *crtc = intel_crtc_for_pipe(i915: dev_priv, pipe); |
29 | |
30 | drm_crtc_handle_vblank(crtc: &crtc->base); |
31 | } |
32 | |
33 | /** |
34 | * ilk_update_display_irq - update DEIMR |
35 | * @dev_priv: driver private |
36 | * @interrupt_mask: mask of interrupt bits to update |
37 | * @enabled_irq_mask: mask of interrupt bits to enable |
38 | */ |
39 | void ilk_update_display_irq(struct drm_i915_private *dev_priv, |
40 | u32 interrupt_mask, u32 enabled_irq_mask) |
41 | { |
42 | u32 new_val; |
43 | |
44 | lockdep_assert_held(&dev_priv->irq_lock); |
45 | drm_WARN_ON(&dev_priv->drm, enabled_irq_mask & ~interrupt_mask); |
46 | |
47 | new_val = dev_priv->irq_mask; |
48 | new_val &= ~interrupt_mask; |
49 | new_val |= (~enabled_irq_mask & interrupt_mask); |
50 | |
51 | if (new_val != dev_priv->irq_mask && |
52 | !drm_WARN_ON(&dev_priv->drm, !intel_irqs_enabled(dev_priv))) { |
53 | dev_priv->irq_mask = new_val; |
54 | intel_uncore_write(uncore: &dev_priv->uncore, DEIMR, val: dev_priv->irq_mask); |
55 | intel_uncore_posting_read(&dev_priv->uncore, DEIMR); |
56 | } |
57 | } |
58 | |
59 | void ilk_enable_display_irq(struct drm_i915_private *i915, u32 bits) |
60 | { |
61 | ilk_update_display_irq(dev_priv: i915, interrupt_mask: bits, enabled_irq_mask: bits); |
62 | } |
63 | |
64 | void ilk_disable_display_irq(struct drm_i915_private *i915, u32 bits) |
65 | { |
66 | ilk_update_display_irq(dev_priv: i915, interrupt_mask: bits, enabled_irq_mask: 0); |
67 | } |
68 | |
69 | /** |
70 | * bdw_update_port_irq - update DE port interrupt |
71 | * @dev_priv: driver private |
72 | * @interrupt_mask: mask of interrupt bits to update |
73 | * @enabled_irq_mask: mask of interrupt bits to enable |
74 | */ |
75 | void bdw_update_port_irq(struct drm_i915_private *dev_priv, |
76 | u32 interrupt_mask, u32 enabled_irq_mask) |
77 | { |
78 | u32 new_val; |
79 | u32 old_val; |
80 | |
81 | lockdep_assert_held(&dev_priv->irq_lock); |
82 | |
83 | drm_WARN_ON(&dev_priv->drm, enabled_irq_mask & ~interrupt_mask); |
84 | |
85 | if (drm_WARN_ON(&dev_priv->drm, !intel_irqs_enabled(dev_priv))) |
86 | return; |
87 | |
88 | old_val = intel_uncore_read(uncore: &dev_priv->uncore, GEN8_DE_PORT_IMR); |
89 | |
90 | new_val = old_val; |
91 | new_val &= ~interrupt_mask; |
92 | new_val |= (~enabled_irq_mask & interrupt_mask); |
93 | |
94 | if (new_val != old_val) { |
95 | intel_uncore_write(uncore: &dev_priv->uncore, GEN8_DE_PORT_IMR, val: new_val); |
96 | intel_uncore_posting_read(&dev_priv->uncore, GEN8_DE_PORT_IMR); |
97 | } |
98 | } |
99 | |
100 | /** |
101 | * bdw_update_pipe_irq - update DE pipe interrupt |
102 | * @dev_priv: driver private |
103 | * @pipe: pipe whose interrupt to update |
104 | * @interrupt_mask: mask of interrupt bits to update |
105 | * @enabled_irq_mask: mask of interrupt bits to enable |
106 | */ |
107 | static void bdw_update_pipe_irq(struct drm_i915_private *dev_priv, |
108 | enum pipe pipe, u32 interrupt_mask, |
109 | u32 enabled_irq_mask) |
110 | { |
111 | u32 new_val; |
112 | |
113 | lockdep_assert_held(&dev_priv->irq_lock); |
114 | |
115 | drm_WARN_ON(&dev_priv->drm, enabled_irq_mask & ~interrupt_mask); |
116 | |
117 | if (drm_WARN_ON(&dev_priv->drm, !intel_irqs_enabled(dev_priv))) |
118 | return; |
119 | |
120 | new_val = dev_priv->de_irq_mask[pipe]; |
121 | new_val &= ~interrupt_mask; |
122 | new_val |= (~enabled_irq_mask & interrupt_mask); |
123 | |
124 | if (new_val != dev_priv->de_irq_mask[pipe]) { |
125 | dev_priv->de_irq_mask[pipe] = new_val; |
126 | intel_uncore_write(uncore: &dev_priv->uncore, GEN8_DE_PIPE_IMR(pipe), val: dev_priv->de_irq_mask[pipe]); |
127 | intel_uncore_posting_read(&dev_priv->uncore, GEN8_DE_PIPE_IMR(pipe)); |
128 | } |
129 | } |
130 | |
131 | void bdw_enable_pipe_irq(struct drm_i915_private *i915, |
132 | enum pipe pipe, u32 bits) |
133 | { |
134 | bdw_update_pipe_irq(dev_priv: i915, pipe, interrupt_mask: bits, enabled_irq_mask: bits); |
135 | } |
136 | |
137 | void bdw_disable_pipe_irq(struct drm_i915_private *i915, |
138 | enum pipe pipe, u32 bits) |
139 | { |
140 | bdw_update_pipe_irq(dev_priv: i915, pipe, interrupt_mask: bits, enabled_irq_mask: 0); |
141 | } |
142 | |
143 | /** |
144 | * ibx_display_interrupt_update - update SDEIMR |
145 | * @dev_priv: driver private |
146 | * @interrupt_mask: mask of interrupt bits to update |
147 | * @enabled_irq_mask: mask of interrupt bits to enable |
148 | */ |
149 | void ibx_display_interrupt_update(struct drm_i915_private *dev_priv, |
150 | u32 interrupt_mask, |
151 | u32 enabled_irq_mask) |
152 | { |
153 | u32 sdeimr = intel_uncore_read(uncore: &dev_priv->uncore, SDEIMR); |
154 | |
155 | sdeimr &= ~interrupt_mask; |
156 | sdeimr |= (~enabled_irq_mask & interrupt_mask); |
157 | |
158 | drm_WARN_ON(&dev_priv->drm, enabled_irq_mask & ~interrupt_mask); |
159 | |
160 | lockdep_assert_held(&dev_priv->irq_lock); |
161 | |
162 | if (drm_WARN_ON(&dev_priv->drm, !intel_irqs_enabled(dev_priv))) |
163 | return; |
164 | |
165 | intel_uncore_write(uncore: &dev_priv->uncore, SDEIMR, val: sdeimr); |
166 | intel_uncore_posting_read(&dev_priv->uncore, SDEIMR); |
167 | } |
168 | |
169 | void ibx_enable_display_interrupt(struct drm_i915_private *i915, u32 bits) |
170 | { |
171 | ibx_display_interrupt_update(dev_priv: i915, interrupt_mask: bits, enabled_irq_mask: bits); |
172 | } |
173 | |
174 | void ibx_disable_display_interrupt(struct drm_i915_private *i915, u32 bits) |
175 | { |
176 | ibx_display_interrupt_update(dev_priv: i915, interrupt_mask: bits, enabled_irq_mask: 0); |
177 | } |
178 | |
179 | u32 i915_pipestat_enable_mask(struct drm_i915_private *dev_priv, |
180 | enum pipe pipe) |
181 | { |
182 | u32 status_mask = dev_priv->pipestat_irq_mask[pipe]; |
183 | u32 enable_mask = status_mask << 16; |
184 | |
185 | lockdep_assert_held(&dev_priv->irq_lock); |
186 | |
187 | if (DISPLAY_VER(dev_priv) < 5) |
188 | goto out; |
189 | |
190 | /* |
191 | * On pipe A we don't support the PSR interrupt yet, |
192 | * on pipe B and C the same bit MBZ. |
193 | */ |
194 | if (drm_WARN_ON_ONCE(&dev_priv->drm, |
195 | status_mask & PIPE_A_PSR_STATUS_VLV)) |
196 | return 0; |
197 | /* |
198 | * On pipe B and C we don't support the PSR interrupt yet, on pipe |
199 | * A the same bit is for perf counters which we don't use either. |
200 | */ |
201 | if (drm_WARN_ON_ONCE(&dev_priv->drm, |
202 | status_mask & PIPE_B_PSR_STATUS_VLV)) |
203 | return 0; |
204 | |
205 | enable_mask &= ~(PIPE_FIFO_UNDERRUN_STATUS | |
206 | SPRITE0_FLIP_DONE_INT_EN_VLV | |
207 | SPRITE1_FLIP_DONE_INT_EN_VLV); |
208 | if (status_mask & SPRITE0_FLIP_DONE_INT_STATUS_VLV) |
209 | enable_mask |= SPRITE0_FLIP_DONE_INT_EN_VLV; |
210 | if (status_mask & SPRITE1_FLIP_DONE_INT_STATUS_VLV) |
211 | enable_mask |= SPRITE1_FLIP_DONE_INT_EN_VLV; |
212 | |
213 | out: |
214 | drm_WARN_ONCE(&dev_priv->drm, |
215 | enable_mask & ~PIPESTAT_INT_ENABLE_MASK || |
216 | status_mask & ~PIPESTAT_INT_STATUS_MASK, |
217 | "pipe %c: enable_mask=0x%x, status_mask=0x%x\n" , |
218 | pipe_name(pipe), enable_mask, status_mask); |
219 | |
220 | return enable_mask; |
221 | } |
222 | |
223 | void i915_enable_pipestat(struct drm_i915_private *dev_priv, |
224 | enum pipe pipe, u32 status_mask) |
225 | { |
226 | i915_reg_t reg = PIPESTAT(pipe); |
227 | u32 enable_mask; |
228 | |
229 | drm_WARN_ONCE(&dev_priv->drm, status_mask & ~PIPESTAT_INT_STATUS_MASK, |
230 | "pipe %c: status_mask=0x%x\n" , |
231 | pipe_name(pipe), status_mask); |
232 | |
233 | lockdep_assert_held(&dev_priv->irq_lock); |
234 | drm_WARN_ON(&dev_priv->drm, !intel_irqs_enabled(dev_priv)); |
235 | |
236 | if ((dev_priv->pipestat_irq_mask[pipe] & status_mask) == status_mask) |
237 | return; |
238 | |
239 | dev_priv->pipestat_irq_mask[pipe] |= status_mask; |
240 | enable_mask = i915_pipestat_enable_mask(dev_priv, pipe); |
241 | |
242 | intel_uncore_write(uncore: &dev_priv->uncore, reg, val: enable_mask | status_mask); |
243 | intel_uncore_posting_read(&dev_priv->uncore, reg); |
244 | } |
245 | |
246 | void i915_disable_pipestat(struct drm_i915_private *dev_priv, |
247 | enum pipe pipe, u32 status_mask) |
248 | { |
249 | i915_reg_t reg = PIPESTAT(pipe); |
250 | u32 enable_mask; |
251 | |
252 | drm_WARN_ONCE(&dev_priv->drm, status_mask & ~PIPESTAT_INT_STATUS_MASK, |
253 | "pipe %c: status_mask=0x%x\n" , |
254 | pipe_name(pipe), status_mask); |
255 | |
256 | lockdep_assert_held(&dev_priv->irq_lock); |
257 | drm_WARN_ON(&dev_priv->drm, !intel_irqs_enabled(dev_priv)); |
258 | |
259 | if ((dev_priv->pipestat_irq_mask[pipe] & status_mask) == 0) |
260 | return; |
261 | |
262 | dev_priv->pipestat_irq_mask[pipe] &= ~status_mask; |
263 | enable_mask = i915_pipestat_enable_mask(dev_priv, pipe); |
264 | |
265 | intel_uncore_write(uncore: &dev_priv->uncore, reg, val: enable_mask | status_mask); |
266 | intel_uncore_posting_read(&dev_priv->uncore, reg); |
267 | } |
268 | |
269 | static bool i915_has_asle(struct drm_i915_private *i915) |
270 | { |
271 | if (!IS_PINEVIEW(i915) && !IS_MOBILE(i915)) |
272 | return false; |
273 | |
274 | return intel_opregion_asle_present(i915); |
275 | } |
276 | |
277 | /** |
278 | * i915_enable_asle_pipestat - enable ASLE pipestat for OpRegion |
279 | * @dev_priv: i915 device private |
280 | */ |
281 | void i915_enable_asle_pipestat(struct drm_i915_private *dev_priv) |
282 | { |
283 | if (!i915_has_asle(i915: dev_priv)) |
284 | return; |
285 | |
286 | spin_lock_irq(lock: &dev_priv->irq_lock); |
287 | |
288 | i915_enable_pipestat(dev_priv, pipe: PIPE_B, PIPE_LEGACY_BLC_EVENT_STATUS); |
289 | if (DISPLAY_VER(dev_priv) >= 4) |
290 | i915_enable_pipestat(dev_priv, pipe: PIPE_A, |
291 | PIPE_LEGACY_BLC_EVENT_STATUS); |
292 | |
293 | spin_unlock_irq(lock: &dev_priv->irq_lock); |
294 | } |
295 | |
296 | #if defined(CONFIG_DEBUG_FS) |
297 | static void display_pipe_crc_irq_handler(struct drm_i915_private *dev_priv, |
298 | enum pipe pipe, |
299 | u32 crc0, u32 crc1, |
300 | u32 crc2, u32 crc3, |
301 | u32 crc4) |
302 | { |
303 | struct intel_crtc *crtc = intel_crtc_for_pipe(i915: dev_priv, pipe); |
304 | struct intel_pipe_crc *pipe_crc = &crtc->pipe_crc; |
305 | u32 crcs[5] = { crc0, crc1, crc2, crc3, crc4 }; |
306 | |
307 | trace_intel_pipe_crc(crtc, crcs); |
308 | |
309 | spin_lock(lock: &pipe_crc->lock); |
310 | /* |
311 | * For some not yet identified reason, the first CRC is |
312 | * bonkers. So let's just wait for the next vblank and read |
313 | * out the buggy result. |
314 | * |
315 | * On GEN8+ sometimes the second CRC is bonkers as well, so |
316 | * don't trust that one either. |
317 | */ |
318 | if (pipe_crc->skipped <= 0 || |
319 | (DISPLAY_VER(dev_priv) >= 8 && pipe_crc->skipped == 1)) { |
320 | pipe_crc->skipped++; |
321 | spin_unlock(lock: &pipe_crc->lock); |
322 | return; |
323 | } |
324 | spin_unlock(lock: &pipe_crc->lock); |
325 | |
326 | drm_crtc_add_crc_entry(crtc: &crtc->base, has_frame: true, |
327 | frame: drm_crtc_accurate_vblank_count(crtc: &crtc->base), |
328 | crcs); |
329 | } |
330 | #else |
331 | static inline void |
332 | display_pipe_crc_irq_handler(struct drm_i915_private *dev_priv, |
333 | enum pipe pipe, |
334 | u32 crc0, u32 crc1, |
335 | u32 crc2, u32 crc3, |
336 | u32 crc4) {} |
337 | #endif |
338 | |
339 | static void flip_done_handler(struct drm_i915_private *i915, |
340 | enum pipe pipe) |
341 | { |
342 | struct intel_crtc *crtc = intel_crtc_for_pipe(i915, pipe); |
343 | |
344 | spin_lock(lock: &i915->drm.event_lock); |
345 | |
346 | if (crtc->flip_done_event) { |
347 | drm_crtc_send_vblank_event(crtc: &crtc->base, e: crtc->flip_done_event); |
348 | crtc->flip_done_event = NULL; |
349 | } |
350 | |
351 | spin_unlock(lock: &i915->drm.event_lock); |
352 | } |
353 | |
354 | static void hsw_pipe_crc_irq_handler(struct drm_i915_private *dev_priv, |
355 | enum pipe pipe) |
356 | { |
357 | display_pipe_crc_irq_handler(dev_priv, pipe, |
358 | crc0: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_1_IVB(pipe)), |
359 | crc1: 0, crc2: 0, crc3: 0, crc4: 0); |
360 | } |
361 | |
362 | static void ivb_pipe_crc_irq_handler(struct drm_i915_private *dev_priv, |
363 | enum pipe pipe) |
364 | { |
365 | display_pipe_crc_irq_handler(dev_priv, pipe, |
366 | crc0: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_1_IVB(pipe)), |
367 | crc1: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_2_IVB(pipe)), |
368 | crc2: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_3_IVB(pipe)), |
369 | crc3: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_4_IVB(pipe)), |
370 | crc4: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_5_IVB(pipe))); |
371 | } |
372 | |
373 | static void i9xx_pipe_crc_irq_handler(struct drm_i915_private *dev_priv, |
374 | enum pipe pipe) |
375 | { |
376 | u32 res1, res2; |
377 | |
378 | if (DISPLAY_VER(dev_priv) >= 3) |
379 | res1 = intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_RES1_I915(pipe)); |
380 | else |
381 | res1 = 0; |
382 | |
383 | if (DISPLAY_VER(dev_priv) >= 5 || IS_G4X(dev_priv)) |
384 | res2 = intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_RES2_G4X(pipe)); |
385 | else |
386 | res2 = 0; |
387 | |
388 | display_pipe_crc_irq_handler(dev_priv, pipe, |
389 | crc0: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_RED(pipe)), |
390 | crc1: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_GREEN(pipe)), |
391 | crc2: intel_uncore_read(uncore: &dev_priv->uncore, PIPE_CRC_RES_BLUE(pipe)), |
392 | crc3: res1, crc4: res2); |
393 | } |
394 | |
395 | void i9xx_pipestat_irq_reset(struct drm_i915_private *dev_priv) |
396 | { |
397 | enum pipe pipe; |
398 | |
399 | for_each_pipe(dev_priv, pipe) { |
400 | intel_uncore_write(uncore: &dev_priv->uncore, PIPESTAT(pipe), |
401 | PIPESTAT_INT_STATUS_MASK | |
402 | PIPE_FIFO_UNDERRUN_STATUS); |
403 | |
404 | dev_priv->pipestat_irq_mask[pipe] = 0; |
405 | } |
406 | } |
407 | |
408 | void i9xx_pipestat_irq_ack(struct drm_i915_private *dev_priv, |
409 | u32 iir, u32 pipe_stats[I915_MAX_PIPES]) |
410 | { |
411 | enum pipe pipe; |
412 | |
413 | spin_lock(lock: &dev_priv->irq_lock); |
414 | |
415 | if (!dev_priv->display_irqs_enabled) { |
416 | spin_unlock(lock: &dev_priv->irq_lock); |
417 | return; |
418 | } |
419 | |
420 | for_each_pipe(dev_priv, pipe) { |
421 | i915_reg_t reg; |
422 | u32 status_mask, enable_mask, iir_bit = 0; |
423 | |
424 | /* |
425 | * PIPESTAT bits get signalled even when the interrupt is |
426 | * disabled with the mask bits, and some of the status bits do |
427 | * not generate interrupts at all (like the underrun bit). Hence |
428 | * we need to be careful that we only handle what we want to |
429 | * handle. |
430 | */ |
431 | |
432 | /* fifo underruns are filterered in the underrun handler. */ |
433 | status_mask = PIPE_FIFO_UNDERRUN_STATUS; |
434 | |
435 | switch (pipe) { |
436 | default: |
437 | case PIPE_A: |
438 | iir_bit = I915_DISPLAY_PIPE_A_EVENT_INTERRUPT; |
439 | break; |
440 | case PIPE_B: |
441 | iir_bit = I915_DISPLAY_PIPE_B_EVENT_INTERRUPT; |
442 | break; |
443 | case PIPE_C: |
444 | iir_bit = I915_DISPLAY_PIPE_C_EVENT_INTERRUPT; |
445 | break; |
446 | } |
447 | if (iir & iir_bit) |
448 | status_mask |= dev_priv->pipestat_irq_mask[pipe]; |
449 | |
450 | if (!status_mask) |
451 | continue; |
452 | |
453 | reg = PIPESTAT(pipe); |
454 | pipe_stats[pipe] = intel_uncore_read(uncore: &dev_priv->uncore, reg) & status_mask; |
455 | enable_mask = i915_pipestat_enable_mask(dev_priv, pipe); |
456 | |
457 | /* |
458 | * Clear the PIPE*STAT regs before the IIR |
459 | * |
460 | * Toggle the enable bits to make sure we get an |
461 | * edge in the ISR pipe event bit if we don't clear |
462 | * all the enabled status bits. Otherwise the edge |
463 | * triggered IIR on i965/g4x wouldn't notice that |
464 | * an interrupt is still pending. |
465 | */ |
466 | if (pipe_stats[pipe]) { |
467 | intel_uncore_write(uncore: &dev_priv->uncore, reg, val: pipe_stats[pipe]); |
468 | intel_uncore_write(uncore: &dev_priv->uncore, reg, val: enable_mask); |
469 | } |
470 | } |
471 | spin_unlock(lock: &dev_priv->irq_lock); |
472 | } |
473 | |
474 | void i8xx_pipestat_irq_handler(struct drm_i915_private *dev_priv, |
475 | u16 iir, u32 pipe_stats[I915_MAX_PIPES]) |
476 | { |
477 | enum pipe pipe; |
478 | |
479 | for_each_pipe(dev_priv, pipe) { |
480 | if (pipe_stats[pipe] & PIPE_VBLANK_INTERRUPT_STATUS) |
481 | intel_handle_vblank(dev_priv, pipe); |
482 | |
483 | if (pipe_stats[pipe] & PIPE_CRC_DONE_INTERRUPT_STATUS) |
484 | i9xx_pipe_crc_irq_handler(dev_priv, pipe); |
485 | |
486 | if (pipe_stats[pipe] & PIPE_FIFO_UNDERRUN_STATUS) |
487 | intel_cpu_fifo_underrun_irq_handler(dev_priv, pipe); |
488 | } |
489 | } |
490 | |
491 | void i915_pipestat_irq_handler(struct drm_i915_private *dev_priv, |
492 | u32 iir, u32 pipe_stats[I915_MAX_PIPES]) |
493 | { |
494 | bool blc_event = false; |
495 | enum pipe pipe; |
496 | |
497 | for_each_pipe(dev_priv, pipe) { |
498 | if (pipe_stats[pipe] & PIPE_VBLANK_INTERRUPT_STATUS) |
499 | intel_handle_vblank(dev_priv, pipe); |
500 | |
501 | if (pipe_stats[pipe] & PIPE_LEGACY_BLC_EVENT_STATUS) |
502 | blc_event = true; |
503 | |
504 | if (pipe_stats[pipe] & PIPE_CRC_DONE_INTERRUPT_STATUS) |
505 | i9xx_pipe_crc_irq_handler(dev_priv, pipe); |
506 | |
507 | if (pipe_stats[pipe] & PIPE_FIFO_UNDERRUN_STATUS) |
508 | intel_cpu_fifo_underrun_irq_handler(dev_priv, pipe); |
509 | } |
510 | |
511 | if (blc_event || (iir & I915_ASLE_INTERRUPT)) |
512 | intel_opregion_asle_intr(dev_priv); |
513 | } |
514 | |
515 | void i965_pipestat_irq_handler(struct drm_i915_private *dev_priv, |
516 | u32 iir, u32 pipe_stats[I915_MAX_PIPES]) |
517 | { |
518 | bool blc_event = false; |
519 | enum pipe pipe; |
520 | |
521 | for_each_pipe(dev_priv, pipe) { |
522 | if (pipe_stats[pipe] & PIPE_START_VBLANK_INTERRUPT_STATUS) |
523 | intel_handle_vblank(dev_priv, pipe); |
524 | |
525 | if (pipe_stats[pipe] & PIPE_LEGACY_BLC_EVENT_STATUS) |
526 | blc_event = true; |
527 | |
528 | if (pipe_stats[pipe] & PIPE_CRC_DONE_INTERRUPT_STATUS) |
529 | i9xx_pipe_crc_irq_handler(dev_priv, pipe); |
530 | |
531 | if (pipe_stats[pipe] & PIPE_FIFO_UNDERRUN_STATUS) |
532 | intel_cpu_fifo_underrun_irq_handler(dev_priv, pipe); |
533 | } |
534 | |
535 | if (blc_event || (iir & I915_ASLE_INTERRUPT)) |
536 | intel_opregion_asle_intr(dev_priv); |
537 | |
538 | if (pipe_stats[0] & PIPE_GMBUS_INTERRUPT_STATUS) |
539 | intel_gmbus_irq_handler(i915: dev_priv); |
540 | } |
541 | |
542 | void valleyview_pipestat_irq_handler(struct drm_i915_private *dev_priv, |
543 | u32 pipe_stats[I915_MAX_PIPES]) |
544 | { |
545 | enum pipe pipe; |
546 | |
547 | for_each_pipe(dev_priv, pipe) { |
548 | if (pipe_stats[pipe] & PIPE_START_VBLANK_INTERRUPT_STATUS) |
549 | intel_handle_vblank(dev_priv, pipe); |
550 | |
551 | if (pipe_stats[pipe] & PLANE_FLIP_DONE_INT_STATUS_VLV) |
552 | flip_done_handler(i915: dev_priv, pipe); |
553 | |
554 | if (pipe_stats[pipe] & PIPE_CRC_DONE_INTERRUPT_STATUS) |
555 | i9xx_pipe_crc_irq_handler(dev_priv, pipe); |
556 | |
557 | if (pipe_stats[pipe] & PIPE_FIFO_UNDERRUN_STATUS) |
558 | intel_cpu_fifo_underrun_irq_handler(dev_priv, pipe); |
559 | } |
560 | |
561 | if (pipe_stats[0] & PIPE_GMBUS_INTERRUPT_STATUS) |
562 | intel_gmbus_irq_handler(i915: dev_priv); |
563 | } |
564 | |
565 | static void ibx_irq_handler(struct drm_i915_private *dev_priv, u32 pch_iir) |
566 | { |
567 | enum pipe pipe; |
568 | u32 hotplug_trigger = pch_iir & SDE_HOTPLUG_MASK; |
569 | |
570 | ibx_hpd_irq_handler(i915: dev_priv, hotplug_trigger); |
571 | |
572 | if (pch_iir & SDE_AUDIO_POWER_MASK) { |
573 | int port = ffs((pch_iir & SDE_AUDIO_POWER_MASK) >> |
574 | SDE_AUDIO_POWER_SHIFT); |
575 | drm_dbg(&dev_priv->drm, "PCH audio power change on port %d\n" , |
576 | port_name(port)); |
577 | } |
578 | |
579 | if (pch_iir & SDE_AUX_MASK) |
580 | intel_dp_aux_irq_handler(i915: dev_priv); |
581 | |
582 | if (pch_iir & SDE_GMBUS) |
583 | intel_gmbus_irq_handler(i915: dev_priv); |
584 | |
585 | if (pch_iir & SDE_AUDIO_HDCP_MASK) |
586 | drm_dbg(&dev_priv->drm, "PCH HDCP audio interrupt\n" ); |
587 | |
588 | if (pch_iir & SDE_AUDIO_TRANS_MASK) |
589 | drm_dbg(&dev_priv->drm, "PCH transcoder audio interrupt\n" ); |
590 | |
591 | if (pch_iir & SDE_POISON) |
592 | drm_err(&dev_priv->drm, "PCH poison interrupt\n" ); |
593 | |
594 | if (pch_iir & SDE_FDI_MASK) { |
595 | for_each_pipe(dev_priv, pipe) |
596 | drm_dbg(&dev_priv->drm, " pipe %c FDI IIR: 0x%08x\n" , |
597 | pipe_name(pipe), |
598 | intel_uncore_read(&dev_priv->uncore, FDI_RX_IIR(pipe))); |
599 | } |
600 | |
601 | if (pch_iir & (SDE_TRANSB_CRC_DONE | SDE_TRANSA_CRC_DONE)) |
602 | drm_dbg(&dev_priv->drm, "PCH transcoder CRC done interrupt\n" ); |
603 | |
604 | if (pch_iir & (SDE_TRANSB_CRC_ERR | SDE_TRANSA_CRC_ERR)) |
605 | drm_dbg(&dev_priv->drm, |
606 | "PCH transcoder CRC error interrupt\n" ); |
607 | |
608 | if (pch_iir & SDE_TRANSA_FIFO_UNDER) |
609 | intel_pch_fifo_underrun_irq_handler(dev_priv, pch_transcoder: PIPE_A); |
610 | |
611 | if (pch_iir & SDE_TRANSB_FIFO_UNDER) |
612 | intel_pch_fifo_underrun_irq_handler(dev_priv, pch_transcoder: PIPE_B); |
613 | } |
614 | |
615 | static void ivb_err_int_handler(struct drm_i915_private *dev_priv) |
616 | { |
617 | u32 err_int = intel_uncore_read(uncore: &dev_priv->uncore, GEN7_ERR_INT); |
618 | enum pipe pipe; |
619 | |
620 | if (err_int & ERR_INT_POISON) |
621 | drm_err(&dev_priv->drm, "Poison interrupt\n" ); |
622 | |
623 | for_each_pipe(dev_priv, pipe) { |
624 | if (err_int & ERR_INT_FIFO_UNDERRUN(pipe)) |
625 | intel_cpu_fifo_underrun_irq_handler(dev_priv, pipe); |
626 | |
627 | if (err_int & ERR_INT_PIPE_CRC_DONE(pipe)) { |
628 | if (IS_IVYBRIDGE(dev_priv)) |
629 | ivb_pipe_crc_irq_handler(dev_priv, pipe); |
630 | else |
631 | hsw_pipe_crc_irq_handler(dev_priv, pipe); |
632 | } |
633 | } |
634 | |
635 | intel_uncore_write(uncore: &dev_priv->uncore, GEN7_ERR_INT, val: err_int); |
636 | } |
637 | |
638 | static void cpt_serr_int_handler(struct drm_i915_private *dev_priv) |
639 | { |
640 | u32 serr_int = intel_uncore_read(uncore: &dev_priv->uncore, SERR_INT); |
641 | enum pipe pipe; |
642 | |
643 | if (serr_int & SERR_INT_POISON) |
644 | drm_err(&dev_priv->drm, "PCH poison interrupt\n" ); |
645 | |
646 | for_each_pipe(dev_priv, pipe) |
647 | if (serr_int & SERR_INT_TRANS_FIFO_UNDERRUN(pipe)) |
648 | intel_pch_fifo_underrun_irq_handler(dev_priv, pch_transcoder: pipe); |
649 | |
650 | intel_uncore_write(uncore: &dev_priv->uncore, SERR_INT, val: serr_int); |
651 | } |
652 | |
653 | static void cpt_irq_handler(struct drm_i915_private *dev_priv, u32 pch_iir) |
654 | { |
655 | enum pipe pipe; |
656 | u32 hotplug_trigger = pch_iir & SDE_HOTPLUG_MASK_CPT; |
657 | |
658 | ibx_hpd_irq_handler(i915: dev_priv, hotplug_trigger); |
659 | |
660 | if (pch_iir & SDE_AUDIO_POWER_MASK_CPT) { |
661 | int port = ffs((pch_iir & SDE_AUDIO_POWER_MASK_CPT) >> |
662 | SDE_AUDIO_POWER_SHIFT_CPT); |
663 | drm_dbg(&dev_priv->drm, "PCH audio power change on port %c\n" , |
664 | port_name(port)); |
665 | } |
666 | |
667 | if (pch_iir & SDE_AUX_MASK_CPT) |
668 | intel_dp_aux_irq_handler(i915: dev_priv); |
669 | |
670 | if (pch_iir & SDE_GMBUS_CPT) |
671 | intel_gmbus_irq_handler(i915: dev_priv); |
672 | |
673 | if (pch_iir & SDE_AUDIO_CP_REQ_CPT) |
674 | drm_dbg(&dev_priv->drm, "Audio CP request interrupt\n" ); |
675 | |
676 | if (pch_iir & SDE_AUDIO_CP_CHG_CPT) |
677 | drm_dbg(&dev_priv->drm, "Audio CP change interrupt\n" ); |
678 | |
679 | if (pch_iir & SDE_FDI_MASK_CPT) { |
680 | for_each_pipe(dev_priv, pipe) |
681 | drm_dbg(&dev_priv->drm, " pipe %c FDI IIR: 0x%08x\n" , |
682 | pipe_name(pipe), |
683 | intel_uncore_read(&dev_priv->uncore, FDI_RX_IIR(pipe))); |
684 | } |
685 | |
686 | if (pch_iir & SDE_ERROR_CPT) |
687 | cpt_serr_int_handler(dev_priv); |
688 | } |
689 | |
690 | void ilk_display_irq_handler(struct drm_i915_private *dev_priv, u32 de_iir) |
691 | { |
692 | enum pipe pipe; |
693 | u32 hotplug_trigger = de_iir & DE_DP_A_HOTPLUG; |
694 | |
695 | if (hotplug_trigger) |
696 | ilk_hpd_irq_handler(i915: dev_priv, hotplug_trigger); |
697 | |
698 | if (de_iir & DE_AUX_CHANNEL_A) |
699 | intel_dp_aux_irq_handler(i915: dev_priv); |
700 | |
701 | if (de_iir & DE_GSE) |
702 | intel_opregion_asle_intr(dev_priv); |
703 | |
704 | if (de_iir & DE_POISON) |
705 | drm_err(&dev_priv->drm, "Poison interrupt\n" ); |
706 | |
707 | for_each_pipe(dev_priv, pipe) { |
708 | if (de_iir & DE_PIPE_VBLANK(pipe)) |
709 | intel_handle_vblank(dev_priv, pipe); |
710 | |
711 | if (de_iir & DE_PLANE_FLIP_DONE(pipe)) |
712 | flip_done_handler(i915: dev_priv, pipe); |
713 | |
714 | if (de_iir & DE_PIPE_FIFO_UNDERRUN(pipe)) |
715 | intel_cpu_fifo_underrun_irq_handler(dev_priv, pipe); |
716 | |
717 | if (de_iir & DE_PIPE_CRC_DONE(pipe)) |
718 | i9xx_pipe_crc_irq_handler(dev_priv, pipe); |
719 | } |
720 | |
721 | /* check event from PCH */ |
722 | if (de_iir & DE_PCH_EVENT) { |
723 | u32 pch_iir = intel_uncore_read(uncore: &dev_priv->uncore, SDEIIR); |
724 | |
725 | if (HAS_PCH_CPT(dev_priv)) |
726 | cpt_irq_handler(dev_priv, pch_iir); |
727 | else |
728 | ibx_irq_handler(dev_priv, pch_iir); |
729 | |
730 | /* should clear PCH hotplug event before clear CPU irq */ |
731 | intel_uncore_write(uncore: &dev_priv->uncore, SDEIIR, val: pch_iir); |
732 | } |
733 | |
734 | if (DISPLAY_VER(dev_priv) == 5 && de_iir & DE_PCU_EVENT) |
735 | gen5_rps_irq_handler(rps: &to_gt(i915: dev_priv)->rps); |
736 | } |
737 | |
738 | void ivb_display_irq_handler(struct drm_i915_private *dev_priv, u32 de_iir) |
739 | { |
740 | enum pipe pipe; |
741 | u32 hotplug_trigger = de_iir & DE_DP_A_HOTPLUG_IVB; |
742 | |
743 | if (hotplug_trigger) |
744 | ilk_hpd_irq_handler(i915: dev_priv, hotplug_trigger); |
745 | |
746 | if (de_iir & DE_ERR_INT_IVB) |
747 | ivb_err_int_handler(dev_priv); |
748 | |
749 | if (de_iir & DE_EDP_PSR_INT_HSW) { |
750 | struct intel_encoder *encoder; |
751 | |
752 | for_each_intel_encoder_with_psr(&dev_priv->drm, encoder) { |
753 | struct intel_dp *intel_dp = enc_to_intel_dp(encoder); |
754 | u32 psr_iir; |
755 | |
756 | psr_iir = intel_uncore_rmw(uncore: &dev_priv->uncore, |
757 | EDP_PSR_IIR, clear: 0, set: 0); |
758 | intel_psr_irq_handler(intel_dp, psr_iir); |
759 | break; |
760 | } |
761 | } |
762 | |
763 | if (de_iir & DE_AUX_CHANNEL_A_IVB) |
764 | intel_dp_aux_irq_handler(i915: dev_priv); |
765 | |
766 | if (de_iir & DE_GSE_IVB) |
767 | intel_opregion_asle_intr(dev_priv); |
768 | |
769 | for_each_pipe(dev_priv, pipe) { |
770 | if (de_iir & DE_PIPE_VBLANK_IVB(pipe)) |
771 | intel_handle_vblank(dev_priv, pipe); |
772 | |
773 | if (de_iir & DE_PLANE_FLIP_DONE_IVB(pipe)) |
774 | flip_done_handler(i915: dev_priv, pipe); |
775 | } |
776 | |
777 | /* check event from PCH */ |
778 | if (!HAS_PCH_NOP(dev_priv) && (de_iir & DE_PCH_EVENT_IVB)) { |
779 | u32 pch_iir = intel_uncore_read(uncore: &dev_priv->uncore, SDEIIR); |
780 | |
781 | cpt_irq_handler(dev_priv, pch_iir); |
782 | |
783 | /* clear PCH hotplug event before clear CPU irq */ |
784 | intel_uncore_write(uncore: &dev_priv->uncore, SDEIIR, val: pch_iir); |
785 | } |
786 | } |
787 | |
788 | static u32 gen8_de_port_aux_mask(struct drm_i915_private *dev_priv) |
789 | { |
790 | u32 mask; |
791 | |
792 | if (DISPLAY_VER(dev_priv) >= 20) |
793 | return 0; |
794 | else if (DISPLAY_VER(dev_priv) >= 14) |
795 | return TGL_DE_PORT_AUX_DDIA | |
796 | TGL_DE_PORT_AUX_DDIB; |
797 | else if (DISPLAY_VER(dev_priv) >= 13) |
798 | return TGL_DE_PORT_AUX_DDIA | |
799 | TGL_DE_PORT_AUX_DDIB | |
800 | TGL_DE_PORT_AUX_DDIC | |
801 | XELPD_DE_PORT_AUX_DDID | |
802 | XELPD_DE_PORT_AUX_DDIE | |
803 | TGL_DE_PORT_AUX_USBC1 | |
804 | TGL_DE_PORT_AUX_USBC2 | |
805 | TGL_DE_PORT_AUX_USBC3 | |
806 | TGL_DE_PORT_AUX_USBC4; |
807 | else if (DISPLAY_VER(dev_priv) >= 12) |
808 | return TGL_DE_PORT_AUX_DDIA | |
809 | TGL_DE_PORT_AUX_DDIB | |
810 | TGL_DE_PORT_AUX_DDIC | |
811 | TGL_DE_PORT_AUX_USBC1 | |
812 | TGL_DE_PORT_AUX_USBC2 | |
813 | TGL_DE_PORT_AUX_USBC3 | |
814 | TGL_DE_PORT_AUX_USBC4 | |
815 | TGL_DE_PORT_AUX_USBC5 | |
816 | TGL_DE_PORT_AUX_USBC6; |
817 | |
818 | mask = GEN8_AUX_CHANNEL_A; |
819 | if (DISPLAY_VER(dev_priv) >= 9) |
820 | mask |= GEN9_AUX_CHANNEL_B | |
821 | GEN9_AUX_CHANNEL_C | |
822 | GEN9_AUX_CHANNEL_D; |
823 | |
824 | if (DISPLAY_VER(dev_priv) == 11) { |
825 | mask |= ICL_AUX_CHANNEL_F; |
826 | mask |= ICL_AUX_CHANNEL_E; |
827 | } |
828 | |
829 | return mask; |
830 | } |
831 | |
832 | static u32 gen8_de_pipe_fault_mask(struct drm_i915_private *dev_priv) |
833 | { |
834 | if (DISPLAY_VER(dev_priv) >= 13 || HAS_D12_PLANE_MINIMIZATION(dev_priv)) |
835 | return RKL_DE_PIPE_IRQ_FAULT_ERRORS; |
836 | else if (DISPLAY_VER(dev_priv) >= 11) |
837 | return GEN11_DE_PIPE_IRQ_FAULT_ERRORS; |
838 | else if (DISPLAY_VER(dev_priv) >= 9) |
839 | return GEN9_DE_PIPE_IRQ_FAULT_ERRORS; |
840 | else |
841 | return GEN8_DE_PIPE_IRQ_FAULT_ERRORS; |
842 | } |
843 | |
844 | static void intel_pmdemand_irq_handler(struct drm_i915_private *dev_priv) |
845 | { |
846 | wake_up_all(&dev_priv->display.pmdemand.waitqueue); |
847 | } |
848 | |
849 | static void |
850 | gen8_de_misc_irq_handler(struct drm_i915_private *dev_priv, u32 iir) |
851 | { |
852 | bool found = false; |
853 | |
854 | if (DISPLAY_VER(dev_priv) >= 14) { |
855 | if (iir & (XELPDP_PMDEMAND_RSP | |
856 | XELPDP_PMDEMAND_RSPTOUT_ERR)) { |
857 | if (iir & XELPDP_PMDEMAND_RSPTOUT_ERR) |
858 | drm_dbg(&dev_priv->drm, |
859 | "Error waiting for Punit PM Demand Response\n" ); |
860 | |
861 | intel_pmdemand_irq_handler(dev_priv); |
862 | found = true; |
863 | } |
864 | } else if (iir & GEN8_DE_MISC_GSE) { |
865 | intel_opregion_asle_intr(dev_priv); |
866 | found = true; |
867 | } |
868 | |
869 | if (iir & GEN8_DE_EDP_PSR) { |
870 | struct intel_encoder *encoder; |
871 | u32 psr_iir; |
872 | i915_reg_t iir_reg; |
873 | |
874 | for_each_intel_encoder_with_psr(&dev_priv->drm, encoder) { |
875 | struct intel_dp *intel_dp = enc_to_intel_dp(encoder); |
876 | |
877 | if (DISPLAY_VER(dev_priv) >= 12) |
878 | iir_reg = TRANS_PSR_IIR(intel_dp->psr.transcoder); |
879 | else |
880 | iir_reg = EDP_PSR_IIR; |
881 | |
882 | psr_iir = intel_uncore_rmw(uncore: &dev_priv->uncore, reg: iir_reg, clear: 0, set: 0); |
883 | |
884 | if (psr_iir) |
885 | found = true; |
886 | |
887 | intel_psr_irq_handler(intel_dp, psr_iir); |
888 | |
889 | /* prior GEN12 only have one EDP PSR */ |
890 | if (DISPLAY_VER(dev_priv) < 12) |
891 | break; |
892 | } |
893 | } |
894 | |
895 | if (!found) |
896 | drm_err(&dev_priv->drm, "Unexpected DE Misc interrupt: 0x%08x\n" , iir); |
897 | } |
898 | |
899 | static void gen11_dsi_te_interrupt_handler(struct drm_i915_private *dev_priv, |
900 | u32 te_trigger) |
901 | { |
902 | enum pipe pipe = INVALID_PIPE; |
903 | enum transcoder dsi_trans; |
904 | enum port port; |
905 | u32 val; |
906 | |
907 | /* |
908 | * Incase of dual link, TE comes from DSI_1 |
909 | * this is to check if dual link is enabled |
910 | */ |
911 | val = intel_uncore_read(uncore: &dev_priv->uncore, TRANS_DDI_FUNC_CTL2(TRANSCODER_DSI_0)); |
912 | val &= PORT_SYNC_MODE_ENABLE; |
913 | |
914 | /* |
915 | * if dual link is enabled, then read DSI_0 |
916 | * transcoder registers |
917 | */ |
918 | port = ((te_trigger & DSI1_TE && val) || (te_trigger & DSI0_TE)) ? |
919 | PORT_A : PORT_B; |
920 | dsi_trans = (port == PORT_A) ? TRANSCODER_DSI_0 : TRANSCODER_DSI_1; |
921 | |
922 | /* Check if DSI configured in command mode */ |
923 | val = intel_uncore_read(uncore: &dev_priv->uncore, DSI_TRANS_FUNC_CONF(dsi_trans)); |
924 | val = val & OP_MODE_MASK; |
925 | |
926 | if (val != CMD_MODE_NO_GATE && val != CMD_MODE_TE_GATE) { |
927 | drm_err(&dev_priv->drm, "DSI trancoder not configured in command mode\n" ); |
928 | return; |
929 | } |
930 | |
931 | /* Get PIPE for handling VBLANK event */ |
932 | val = intel_uncore_read(uncore: &dev_priv->uncore, TRANS_DDI_FUNC_CTL(dsi_trans)); |
933 | switch (val & TRANS_DDI_EDP_INPUT_MASK) { |
934 | case TRANS_DDI_EDP_INPUT_A_ON: |
935 | pipe = PIPE_A; |
936 | break; |
937 | case TRANS_DDI_EDP_INPUT_B_ONOFF: |
938 | pipe = PIPE_B; |
939 | break; |
940 | case TRANS_DDI_EDP_INPUT_C_ONOFF: |
941 | pipe = PIPE_C; |
942 | break; |
943 | default: |
944 | drm_err(&dev_priv->drm, "Invalid PIPE\n" ); |
945 | return; |
946 | } |
947 | |
948 | intel_handle_vblank(dev_priv, pipe); |
949 | |
950 | /* clear TE in dsi IIR */ |
951 | port = (te_trigger & DSI1_TE) ? PORT_B : PORT_A; |
952 | intel_uncore_rmw(uncore: &dev_priv->uncore, DSI_INTR_IDENT_REG(port), clear: 0, set: 0); |
953 | } |
954 | |
955 | static u32 gen8_de_pipe_flip_done_mask(struct drm_i915_private *i915) |
956 | { |
957 | if (DISPLAY_VER(i915) >= 9) |
958 | return GEN9_PIPE_PLANE1_FLIP_DONE; |
959 | else |
960 | return GEN8_PIPE_PRIMARY_FLIP_DONE; |
961 | } |
962 | |
963 | u32 gen8_de_pipe_underrun_mask(struct drm_i915_private *dev_priv) |
964 | { |
965 | u32 mask = GEN8_PIPE_FIFO_UNDERRUN; |
966 | |
967 | if (DISPLAY_VER(dev_priv) >= 13) |
968 | mask |= XELPD_PIPE_SOFT_UNDERRUN | |
969 | XELPD_PIPE_HARD_UNDERRUN; |
970 | |
971 | return mask; |
972 | } |
973 | |
974 | static void gen8_read_and_ack_pch_irqs(struct drm_i915_private *i915, u32 *pch_iir, u32 *pica_iir) |
975 | { |
976 | u32 pica_ier = 0; |
977 | |
978 | *pica_iir = 0; |
979 | *pch_iir = intel_de_read(i915, SDEIIR); |
980 | if (!*pch_iir) |
981 | return; |
982 | |
983 | /** |
984 | * PICA IER must be disabled/re-enabled around clearing PICA IIR and |
985 | * SDEIIR, to avoid losing PICA IRQs and to ensure that such IRQs set |
986 | * their flags both in the PICA and SDE IIR. |
987 | */ |
988 | if (*pch_iir & SDE_PICAINTERRUPT) { |
989 | drm_WARN_ON(&i915->drm, INTEL_PCH_TYPE(i915) < PCH_MTL); |
990 | |
991 | pica_ier = intel_de_rmw(i915, PICAINTERRUPT_IER, clear: ~0, set: 0); |
992 | *pica_iir = intel_de_read(i915, PICAINTERRUPT_IIR); |
993 | intel_de_write(i915, PICAINTERRUPT_IIR, val: *pica_iir); |
994 | } |
995 | |
996 | intel_de_write(i915, SDEIIR, val: *pch_iir); |
997 | |
998 | if (pica_ier) |
999 | intel_de_write(i915, PICAINTERRUPT_IER, val: pica_ier); |
1000 | } |
1001 | |
1002 | void gen8_de_irq_handler(struct drm_i915_private *dev_priv, u32 master_ctl) |
1003 | { |
1004 | u32 iir; |
1005 | enum pipe pipe; |
1006 | |
1007 | drm_WARN_ON_ONCE(&dev_priv->drm, !HAS_DISPLAY(dev_priv)); |
1008 | |
1009 | if (master_ctl & GEN8_DE_MISC_IRQ) { |
1010 | iir = intel_uncore_read(uncore: &dev_priv->uncore, GEN8_DE_MISC_IIR); |
1011 | if (iir) { |
1012 | intel_uncore_write(uncore: &dev_priv->uncore, GEN8_DE_MISC_IIR, val: iir); |
1013 | gen8_de_misc_irq_handler(dev_priv, iir); |
1014 | } else { |
1015 | drm_err_ratelimited(&dev_priv->drm, |
1016 | "The master control interrupt lied (DE MISC)!\n" ); |
1017 | } |
1018 | } |
1019 | |
1020 | if (DISPLAY_VER(dev_priv) >= 11 && (master_ctl & GEN11_DE_HPD_IRQ)) { |
1021 | iir = intel_uncore_read(uncore: &dev_priv->uncore, GEN11_DE_HPD_IIR); |
1022 | if (iir) { |
1023 | intel_uncore_write(uncore: &dev_priv->uncore, GEN11_DE_HPD_IIR, val: iir); |
1024 | gen11_hpd_irq_handler(i915: dev_priv, iir); |
1025 | } else { |
1026 | drm_err_ratelimited(&dev_priv->drm, |
1027 | "The master control interrupt lied, (DE HPD)!\n" ); |
1028 | } |
1029 | } |
1030 | |
1031 | if (master_ctl & GEN8_DE_PORT_IRQ) { |
1032 | iir = intel_uncore_read(uncore: &dev_priv->uncore, GEN8_DE_PORT_IIR); |
1033 | if (iir) { |
1034 | bool found = false; |
1035 | |
1036 | intel_uncore_write(uncore: &dev_priv->uncore, GEN8_DE_PORT_IIR, val: iir); |
1037 | |
1038 | if (iir & gen8_de_port_aux_mask(dev_priv)) { |
1039 | intel_dp_aux_irq_handler(i915: dev_priv); |
1040 | found = true; |
1041 | } |
1042 | |
1043 | if (IS_GEMINILAKE(dev_priv) || IS_BROXTON(dev_priv)) { |
1044 | u32 hotplug_trigger = iir & BXT_DE_PORT_HOTPLUG_MASK; |
1045 | |
1046 | if (hotplug_trigger) { |
1047 | bxt_hpd_irq_handler(i915: dev_priv, hotplug_trigger); |
1048 | found = true; |
1049 | } |
1050 | } else if (IS_BROADWELL(dev_priv)) { |
1051 | u32 hotplug_trigger = iir & BDW_DE_PORT_HOTPLUG_MASK; |
1052 | |
1053 | if (hotplug_trigger) { |
1054 | ilk_hpd_irq_handler(i915: dev_priv, hotplug_trigger); |
1055 | found = true; |
1056 | } |
1057 | } |
1058 | |
1059 | if ((IS_GEMINILAKE(dev_priv) || IS_BROXTON(dev_priv)) && |
1060 | (iir & BXT_DE_PORT_GMBUS)) { |
1061 | intel_gmbus_irq_handler(i915: dev_priv); |
1062 | found = true; |
1063 | } |
1064 | |
1065 | if (DISPLAY_VER(dev_priv) >= 11) { |
1066 | u32 te_trigger = iir & (DSI0_TE | DSI1_TE); |
1067 | |
1068 | if (te_trigger) { |
1069 | gen11_dsi_te_interrupt_handler(dev_priv, te_trigger); |
1070 | found = true; |
1071 | } |
1072 | } |
1073 | |
1074 | if (!found) |
1075 | drm_err_ratelimited(&dev_priv->drm, |
1076 | "Unexpected DE Port interrupt\n" ); |
1077 | } else { |
1078 | drm_err_ratelimited(&dev_priv->drm, |
1079 | "The master control interrupt lied (DE PORT)!\n" ); |
1080 | } |
1081 | } |
1082 | |
1083 | for_each_pipe(dev_priv, pipe) { |
1084 | u32 fault_errors; |
1085 | |
1086 | if (!(master_ctl & GEN8_DE_PIPE_IRQ(pipe))) |
1087 | continue; |
1088 | |
1089 | iir = intel_uncore_read(uncore: &dev_priv->uncore, GEN8_DE_PIPE_IIR(pipe)); |
1090 | if (!iir) { |
1091 | drm_err_ratelimited(&dev_priv->drm, |
1092 | "The master control interrupt lied (DE PIPE)!\n" ); |
1093 | continue; |
1094 | } |
1095 | |
1096 | intel_uncore_write(uncore: &dev_priv->uncore, GEN8_DE_PIPE_IIR(pipe), val: iir); |
1097 | |
1098 | if (iir & GEN8_PIPE_VBLANK) |
1099 | intel_handle_vblank(dev_priv, pipe); |
1100 | |
1101 | if (iir & gen8_de_pipe_flip_done_mask(i915: dev_priv)) |
1102 | flip_done_handler(i915: dev_priv, pipe); |
1103 | |
1104 | if (iir & GEN8_PIPE_CDCLK_CRC_DONE) |
1105 | hsw_pipe_crc_irq_handler(dev_priv, pipe); |
1106 | |
1107 | if (iir & gen8_de_pipe_underrun_mask(dev_priv)) |
1108 | intel_cpu_fifo_underrun_irq_handler(dev_priv, pipe); |
1109 | |
1110 | fault_errors = iir & gen8_de_pipe_fault_mask(dev_priv); |
1111 | if (fault_errors) |
1112 | drm_err_ratelimited(&dev_priv->drm, |
1113 | "Fault errors on pipe %c: 0x%08x\n" , |
1114 | pipe_name(pipe), |
1115 | fault_errors); |
1116 | } |
1117 | |
1118 | if (HAS_PCH_SPLIT(dev_priv) && !HAS_PCH_NOP(dev_priv) && |
1119 | master_ctl & GEN8_DE_PCH_IRQ) { |
1120 | u32 pica_iir; |
1121 | |
1122 | /* |
1123 | * FIXME(BDW): Assume for now that the new interrupt handling |
1124 | * scheme also closed the SDE interrupt handling race we've seen |
1125 | * on older pch-split platforms. But this needs testing. |
1126 | */ |
1127 | gen8_read_and_ack_pch_irqs(i915: dev_priv, pch_iir: &iir, pica_iir: &pica_iir); |
1128 | if (iir) { |
1129 | if (pica_iir) |
1130 | xelpdp_pica_irq_handler(i915: dev_priv, iir: pica_iir); |
1131 | |
1132 | if (INTEL_PCH_TYPE(dev_priv) >= PCH_ICP) |
1133 | icp_irq_handler(i915: dev_priv, pch_iir: iir); |
1134 | else if (INTEL_PCH_TYPE(dev_priv) >= PCH_SPT) |
1135 | spt_irq_handler(i915: dev_priv, pch_iir: iir); |
1136 | else |
1137 | cpt_irq_handler(dev_priv, pch_iir: iir); |
1138 | } else { |
1139 | /* |
1140 | * Like on previous PCH there seems to be something |
1141 | * fishy going on with forwarding PCH interrupts. |
1142 | */ |
1143 | drm_dbg(&dev_priv->drm, |
1144 | "The master control interrupt lied (SDE)!\n" ); |
1145 | } |
1146 | } |
1147 | } |
1148 | |
1149 | u32 gen11_gu_misc_irq_ack(struct drm_i915_private *i915, const u32 master_ctl) |
1150 | { |
1151 | void __iomem * const regs = intel_uncore_regs(uncore: &i915->uncore); |
1152 | u32 iir; |
1153 | |
1154 | if (!(master_ctl & GEN11_GU_MISC_IRQ)) |
1155 | return 0; |
1156 | |
1157 | iir = raw_reg_read(regs, GEN11_GU_MISC_IIR); |
1158 | if (likely(iir)) |
1159 | raw_reg_write(regs, GEN11_GU_MISC_IIR, iir); |
1160 | |
1161 | return iir; |
1162 | } |
1163 | |
1164 | void gen11_gu_misc_irq_handler(struct drm_i915_private *i915, const u32 iir) |
1165 | { |
1166 | if (iir & GEN11_GU_MISC_GSE) |
1167 | intel_opregion_asle_intr(dev_priv: i915); |
1168 | } |
1169 | |
1170 | void gen11_display_irq_handler(struct drm_i915_private *i915) |
1171 | { |
1172 | void __iomem * const regs = intel_uncore_regs(uncore: &i915->uncore); |
1173 | const u32 disp_ctl = raw_reg_read(regs, GEN11_DISPLAY_INT_CTL); |
1174 | |
1175 | disable_rpm_wakeref_asserts(rpm: &i915->runtime_pm); |
1176 | /* |
1177 | * GEN11_DISPLAY_INT_CTL has same format as GEN8_MASTER_IRQ |
1178 | * for the display related bits. |
1179 | */ |
1180 | raw_reg_write(regs, GEN11_DISPLAY_INT_CTL, 0x0); |
1181 | gen8_de_irq_handler(dev_priv: i915, master_ctl: disp_ctl); |
1182 | raw_reg_write(regs, GEN11_DISPLAY_INT_CTL, |
1183 | GEN11_DISPLAY_IRQ_ENABLE); |
1184 | |
1185 | enable_rpm_wakeref_asserts(rpm: &i915->runtime_pm); |
1186 | } |
1187 | |
1188 | /* Called from drm generic code, passed 'crtc' which |
1189 | * we use as a pipe index |
1190 | */ |
1191 | int i8xx_enable_vblank(struct drm_crtc *crtc) |
1192 | { |
1193 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1194 | enum pipe pipe = to_intel_crtc(crtc)->pipe; |
1195 | unsigned long irqflags; |
1196 | |
1197 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1198 | i915_enable_pipestat(dev_priv, pipe, PIPE_VBLANK_INTERRUPT_STATUS); |
1199 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1200 | |
1201 | return 0; |
1202 | } |
1203 | |
1204 | int i915gm_enable_vblank(struct drm_crtc *crtc) |
1205 | { |
1206 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1207 | |
1208 | /* |
1209 | * Vblank interrupts fail to wake the device up from C2+. |
1210 | * Disabling render clock gating during C-states avoids |
1211 | * the problem. There is a small power cost so we do this |
1212 | * only when vblank interrupts are actually enabled. |
1213 | */ |
1214 | if (dev_priv->vblank_enabled++ == 0) |
1215 | intel_uncore_write(uncore: &dev_priv->uncore, SCPD0, _MASKED_BIT_ENABLE(CSTATE_RENDER_CLOCK_GATE_DISABLE)); |
1216 | |
1217 | return i8xx_enable_vblank(crtc); |
1218 | } |
1219 | |
1220 | int i965_enable_vblank(struct drm_crtc *crtc) |
1221 | { |
1222 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1223 | enum pipe pipe = to_intel_crtc(crtc)->pipe; |
1224 | unsigned long irqflags; |
1225 | |
1226 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1227 | i915_enable_pipestat(dev_priv, pipe, |
1228 | PIPE_START_VBLANK_INTERRUPT_STATUS); |
1229 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1230 | |
1231 | return 0; |
1232 | } |
1233 | |
1234 | int ilk_enable_vblank(struct drm_crtc *crtc) |
1235 | { |
1236 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1237 | enum pipe pipe = to_intel_crtc(crtc)->pipe; |
1238 | unsigned long irqflags; |
1239 | u32 bit = DISPLAY_VER(dev_priv) >= 7 ? |
1240 | DE_PIPE_VBLANK_IVB(pipe) : DE_PIPE_VBLANK(pipe); |
1241 | |
1242 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1243 | ilk_enable_display_irq(i915: dev_priv, bits: bit); |
1244 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1245 | |
1246 | /* Even though there is no DMC, frame counter can get stuck when |
1247 | * PSR is active as no frames are generated. |
1248 | */ |
1249 | if (HAS_PSR(dev_priv)) |
1250 | drm_crtc_vblank_restore(crtc); |
1251 | |
1252 | return 0; |
1253 | } |
1254 | |
1255 | static bool gen11_dsi_configure_te(struct intel_crtc *intel_crtc, |
1256 | bool enable) |
1257 | { |
1258 | struct drm_i915_private *dev_priv = to_i915(dev: intel_crtc->base.dev); |
1259 | enum port port; |
1260 | |
1261 | if (!(intel_crtc->mode_flags & |
1262 | (I915_MODE_FLAG_DSI_USE_TE1 | I915_MODE_FLAG_DSI_USE_TE0))) |
1263 | return false; |
1264 | |
1265 | /* for dual link cases we consider TE from slave */ |
1266 | if (intel_crtc->mode_flags & I915_MODE_FLAG_DSI_USE_TE1) |
1267 | port = PORT_B; |
1268 | else |
1269 | port = PORT_A; |
1270 | |
1271 | intel_uncore_rmw(uncore: &dev_priv->uncore, DSI_INTR_MASK_REG(port), DSI_TE_EVENT, |
1272 | set: enable ? 0 : DSI_TE_EVENT); |
1273 | |
1274 | intel_uncore_rmw(uncore: &dev_priv->uncore, DSI_INTR_IDENT_REG(port), clear: 0, set: 0); |
1275 | |
1276 | return true; |
1277 | } |
1278 | |
1279 | int bdw_enable_vblank(struct drm_crtc *_crtc) |
1280 | { |
1281 | struct intel_crtc *crtc = to_intel_crtc(_crtc); |
1282 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->base.dev); |
1283 | enum pipe pipe = crtc->pipe; |
1284 | unsigned long irqflags; |
1285 | |
1286 | if (gen11_dsi_configure_te(intel_crtc: crtc, enable: true)) |
1287 | return 0; |
1288 | |
1289 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1290 | bdw_enable_pipe_irq(i915: dev_priv, pipe, GEN8_PIPE_VBLANK); |
1291 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1292 | |
1293 | /* Even if there is no DMC, frame counter can get stuck when |
1294 | * PSR is active as no frames are generated, so check only for PSR. |
1295 | */ |
1296 | if (HAS_PSR(dev_priv)) |
1297 | drm_crtc_vblank_restore(crtc: &crtc->base); |
1298 | |
1299 | return 0; |
1300 | } |
1301 | |
1302 | /* Called from drm generic code, passed 'crtc' which |
1303 | * we use as a pipe index |
1304 | */ |
1305 | void i8xx_disable_vblank(struct drm_crtc *crtc) |
1306 | { |
1307 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1308 | enum pipe pipe = to_intel_crtc(crtc)->pipe; |
1309 | unsigned long irqflags; |
1310 | |
1311 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1312 | i915_disable_pipestat(dev_priv, pipe, PIPE_VBLANK_INTERRUPT_STATUS); |
1313 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1314 | } |
1315 | |
1316 | void i915gm_disable_vblank(struct drm_crtc *crtc) |
1317 | { |
1318 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1319 | |
1320 | i8xx_disable_vblank(crtc); |
1321 | |
1322 | if (--dev_priv->vblank_enabled == 0) |
1323 | intel_uncore_write(uncore: &dev_priv->uncore, SCPD0, _MASKED_BIT_DISABLE(CSTATE_RENDER_CLOCK_GATE_DISABLE)); |
1324 | } |
1325 | |
1326 | void i965_disable_vblank(struct drm_crtc *crtc) |
1327 | { |
1328 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1329 | enum pipe pipe = to_intel_crtc(crtc)->pipe; |
1330 | unsigned long irqflags; |
1331 | |
1332 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1333 | i915_disable_pipestat(dev_priv, pipe, |
1334 | PIPE_START_VBLANK_INTERRUPT_STATUS); |
1335 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1336 | } |
1337 | |
1338 | void ilk_disable_vblank(struct drm_crtc *crtc) |
1339 | { |
1340 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->dev); |
1341 | enum pipe pipe = to_intel_crtc(crtc)->pipe; |
1342 | unsigned long irqflags; |
1343 | u32 bit = DISPLAY_VER(dev_priv) >= 7 ? |
1344 | DE_PIPE_VBLANK_IVB(pipe) : DE_PIPE_VBLANK(pipe); |
1345 | |
1346 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1347 | ilk_disable_display_irq(i915: dev_priv, bits: bit); |
1348 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1349 | } |
1350 | |
1351 | void bdw_disable_vblank(struct drm_crtc *_crtc) |
1352 | { |
1353 | struct intel_crtc *crtc = to_intel_crtc(_crtc); |
1354 | struct drm_i915_private *dev_priv = to_i915(dev: crtc->base.dev); |
1355 | enum pipe pipe = crtc->pipe; |
1356 | unsigned long irqflags; |
1357 | |
1358 | if (gen11_dsi_configure_te(intel_crtc: crtc, enable: false)) |
1359 | return; |
1360 | |
1361 | spin_lock_irqsave(&dev_priv->irq_lock, irqflags); |
1362 | bdw_disable_pipe_irq(i915: dev_priv, pipe, GEN8_PIPE_VBLANK); |
1363 | spin_unlock_irqrestore(lock: &dev_priv->irq_lock, flags: irqflags); |
1364 | } |
1365 | |
1366 | void vlv_display_irq_reset(struct drm_i915_private *dev_priv) |
1367 | { |
1368 | struct intel_uncore *uncore = &dev_priv->uncore; |
1369 | |
1370 | if (IS_CHERRYVIEW(dev_priv)) |
1371 | intel_uncore_write(uncore, DPINVGTT, DPINVGTT_STATUS_MASK_CHV); |
1372 | else |
1373 | intel_uncore_write(uncore, DPINVGTT, DPINVGTT_STATUS_MASK_VLV); |
1374 | |
1375 | i915_hotplug_interrupt_update_locked(i915: dev_priv, mask: 0xffffffff, bits: 0); |
1376 | intel_uncore_rmw(uncore, PORT_HOTPLUG_STAT, clear: 0, set: 0); |
1377 | |
1378 | i9xx_pipestat_irq_reset(dev_priv); |
1379 | |
1380 | GEN3_IRQ_RESET(uncore, VLV_); |
1381 | dev_priv->irq_mask = ~0u; |
1382 | } |
1383 | |
1384 | void vlv_display_irq_postinstall(struct drm_i915_private *dev_priv) |
1385 | { |
1386 | struct intel_uncore *uncore = &dev_priv->uncore; |
1387 | |
1388 | u32 pipestat_mask; |
1389 | u32 enable_mask; |
1390 | enum pipe pipe; |
1391 | |
1392 | pipestat_mask = PIPE_CRC_DONE_INTERRUPT_STATUS; |
1393 | |
1394 | i915_enable_pipestat(dev_priv, pipe: PIPE_A, PIPE_GMBUS_INTERRUPT_STATUS); |
1395 | for_each_pipe(dev_priv, pipe) |
1396 | i915_enable_pipestat(dev_priv, pipe, status_mask: pipestat_mask); |
1397 | |
1398 | enable_mask = I915_DISPLAY_PORT_INTERRUPT | |
1399 | I915_DISPLAY_PIPE_A_EVENT_INTERRUPT | |
1400 | I915_DISPLAY_PIPE_B_EVENT_INTERRUPT | |
1401 | I915_LPE_PIPE_A_INTERRUPT | |
1402 | I915_LPE_PIPE_B_INTERRUPT; |
1403 | |
1404 | if (IS_CHERRYVIEW(dev_priv)) |
1405 | enable_mask |= I915_DISPLAY_PIPE_C_EVENT_INTERRUPT | |
1406 | I915_LPE_PIPE_C_INTERRUPT; |
1407 | |
1408 | drm_WARN_ON(&dev_priv->drm, dev_priv->irq_mask != ~0u); |
1409 | |
1410 | dev_priv->irq_mask = ~enable_mask; |
1411 | |
1412 | GEN3_IRQ_INIT(uncore, VLV_, dev_priv->irq_mask, enable_mask); |
1413 | } |
1414 | |
1415 | void gen8_display_irq_reset(struct drm_i915_private *dev_priv) |
1416 | { |
1417 | struct intel_uncore *uncore = &dev_priv->uncore; |
1418 | enum pipe pipe; |
1419 | |
1420 | if (!HAS_DISPLAY(dev_priv)) |
1421 | return; |
1422 | |
1423 | intel_uncore_write(uncore, EDP_PSR_IMR, val: 0xffffffff); |
1424 | intel_uncore_write(uncore, EDP_PSR_IIR, val: 0xffffffff); |
1425 | |
1426 | for_each_pipe(dev_priv, pipe) |
1427 | if (intel_display_power_is_enabled(dev_priv, |
1428 | POWER_DOMAIN_PIPE(pipe))) |
1429 | GEN8_IRQ_RESET_NDX(uncore, DE_PIPE, pipe); |
1430 | |
1431 | GEN3_IRQ_RESET(uncore, GEN8_DE_PORT_); |
1432 | GEN3_IRQ_RESET(uncore, GEN8_DE_MISC_); |
1433 | } |
1434 | |
1435 | void gen11_display_irq_reset(struct drm_i915_private *dev_priv) |
1436 | { |
1437 | struct intel_uncore *uncore = &dev_priv->uncore; |
1438 | enum pipe pipe; |
1439 | u32 trans_mask = BIT(TRANSCODER_A) | BIT(TRANSCODER_B) | |
1440 | BIT(TRANSCODER_C) | BIT(TRANSCODER_D); |
1441 | |
1442 | if (!HAS_DISPLAY(dev_priv)) |
1443 | return; |
1444 | |
1445 | intel_uncore_write(uncore, GEN11_DISPLAY_INT_CTL, val: 0); |
1446 | |
1447 | if (DISPLAY_VER(dev_priv) >= 12) { |
1448 | enum transcoder trans; |
1449 | |
1450 | for_each_cpu_transcoder_masked(dev_priv, trans, trans_mask) { |
1451 | enum intel_display_power_domain domain; |
1452 | |
1453 | domain = POWER_DOMAIN_TRANSCODER(trans); |
1454 | if (!intel_display_power_is_enabled(dev_priv, domain)) |
1455 | continue; |
1456 | |
1457 | intel_uncore_write(uncore, TRANS_PSR_IMR(trans), val: 0xffffffff); |
1458 | intel_uncore_write(uncore, TRANS_PSR_IIR(trans), val: 0xffffffff); |
1459 | } |
1460 | } else { |
1461 | intel_uncore_write(uncore, EDP_PSR_IMR, val: 0xffffffff); |
1462 | intel_uncore_write(uncore, EDP_PSR_IIR, val: 0xffffffff); |
1463 | } |
1464 | |
1465 | for_each_pipe(dev_priv, pipe) |
1466 | if (intel_display_power_is_enabled(dev_priv, |
1467 | POWER_DOMAIN_PIPE(pipe))) |
1468 | GEN8_IRQ_RESET_NDX(uncore, DE_PIPE, pipe); |
1469 | |
1470 | GEN3_IRQ_RESET(uncore, GEN8_DE_PORT_); |
1471 | GEN3_IRQ_RESET(uncore, GEN8_DE_MISC_); |
1472 | |
1473 | if (DISPLAY_VER(dev_priv) >= 14) |
1474 | GEN3_IRQ_RESET(uncore, PICAINTERRUPT_); |
1475 | else |
1476 | GEN3_IRQ_RESET(uncore, GEN11_DE_HPD_); |
1477 | |
1478 | if (INTEL_PCH_TYPE(dev_priv) >= PCH_ICP) |
1479 | GEN3_IRQ_RESET(uncore, SDE); |
1480 | } |
1481 | |
1482 | void gen8_irq_power_well_post_enable(struct drm_i915_private *dev_priv, |
1483 | u8 pipe_mask) |
1484 | { |
1485 | struct intel_uncore *uncore = &dev_priv->uncore; |
1486 | u32 = GEN8_PIPE_VBLANK | |
1487 | gen8_de_pipe_underrun_mask(dev_priv) | |
1488 | gen8_de_pipe_flip_done_mask(i915: dev_priv); |
1489 | enum pipe pipe; |
1490 | |
1491 | spin_lock_irq(lock: &dev_priv->irq_lock); |
1492 | |
1493 | if (!intel_irqs_enabled(dev_priv)) { |
1494 | spin_unlock_irq(lock: &dev_priv->irq_lock); |
1495 | return; |
1496 | } |
1497 | |
1498 | for_each_pipe_masked(dev_priv, pipe, pipe_mask) |
1499 | GEN8_IRQ_INIT_NDX(uncore, DE_PIPE, pipe, |
1500 | dev_priv->de_irq_mask[pipe], |
1501 | ~dev_priv->de_irq_mask[pipe] | extra_ier); |
1502 | |
1503 | spin_unlock_irq(lock: &dev_priv->irq_lock); |
1504 | } |
1505 | |
1506 | void gen8_irq_power_well_pre_disable(struct drm_i915_private *dev_priv, |
1507 | u8 pipe_mask) |
1508 | { |
1509 | struct intel_uncore *uncore = &dev_priv->uncore; |
1510 | enum pipe pipe; |
1511 | |
1512 | spin_lock_irq(lock: &dev_priv->irq_lock); |
1513 | |
1514 | if (!intel_irqs_enabled(dev_priv)) { |
1515 | spin_unlock_irq(lock: &dev_priv->irq_lock); |
1516 | return; |
1517 | } |
1518 | |
1519 | for_each_pipe_masked(dev_priv, pipe, pipe_mask) |
1520 | GEN8_IRQ_RESET_NDX(uncore, DE_PIPE, pipe); |
1521 | |
1522 | spin_unlock_irq(lock: &dev_priv->irq_lock); |
1523 | |
1524 | /* make sure we're done processing display irqs */ |
1525 | intel_synchronize_irq(i915: dev_priv); |
1526 | } |
1527 | |
1528 | /* |
1529 | * SDEIER is also touched by the interrupt handler to work around missed PCH |
1530 | * interrupts. Hence we can't update it after the interrupt handler is enabled - |
1531 | * instead we unconditionally enable all PCH interrupt sources here, but then |
1532 | * only unmask them as needed with SDEIMR. |
1533 | * |
1534 | * Note that we currently do this after installing the interrupt handler, |
1535 | * but before we enable the master interrupt. That should be sufficient |
1536 | * to avoid races with the irq handler, assuming we have MSI. Shared legacy |
1537 | * interrupts could still race. |
1538 | */ |
1539 | static void ibx_irq_postinstall(struct drm_i915_private *dev_priv) |
1540 | { |
1541 | struct intel_uncore *uncore = &dev_priv->uncore; |
1542 | u32 mask; |
1543 | |
1544 | if (HAS_PCH_NOP(dev_priv)) |
1545 | return; |
1546 | |
1547 | if (HAS_PCH_IBX(dev_priv)) |
1548 | mask = SDE_GMBUS | SDE_AUX_MASK | SDE_POISON; |
1549 | else if (HAS_PCH_CPT(dev_priv) || HAS_PCH_LPT(dev_priv)) |
1550 | mask = SDE_GMBUS_CPT | SDE_AUX_MASK_CPT; |
1551 | else |
1552 | mask = SDE_GMBUS_CPT; |
1553 | |
1554 | GEN3_IRQ_INIT(uncore, SDE, ~mask, 0xffffffff); |
1555 | } |
1556 | |
1557 | void valleyview_enable_display_irqs(struct drm_i915_private *dev_priv) |
1558 | { |
1559 | lockdep_assert_held(&dev_priv->irq_lock); |
1560 | |
1561 | if (dev_priv->display_irqs_enabled) |
1562 | return; |
1563 | |
1564 | dev_priv->display_irqs_enabled = true; |
1565 | |
1566 | if (intel_irqs_enabled(dev_priv)) { |
1567 | vlv_display_irq_reset(dev_priv); |
1568 | vlv_display_irq_postinstall(dev_priv); |
1569 | } |
1570 | } |
1571 | |
1572 | void valleyview_disable_display_irqs(struct drm_i915_private *dev_priv) |
1573 | { |
1574 | lockdep_assert_held(&dev_priv->irq_lock); |
1575 | |
1576 | if (!dev_priv->display_irqs_enabled) |
1577 | return; |
1578 | |
1579 | dev_priv->display_irqs_enabled = false; |
1580 | |
1581 | if (intel_irqs_enabled(dev_priv)) |
1582 | vlv_display_irq_reset(dev_priv); |
1583 | } |
1584 | |
1585 | void ilk_de_irq_postinstall(struct drm_i915_private *i915) |
1586 | { |
1587 | struct intel_uncore *uncore = &i915->uncore; |
1588 | u32 display_mask, ; |
1589 | |
1590 | if (DISPLAY_VER(i915) >= 7) { |
1591 | display_mask = (DE_MASTER_IRQ_CONTROL | DE_GSE_IVB | |
1592 | DE_PCH_EVENT_IVB | DE_AUX_CHANNEL_A_IVB); |
1593 | extra_mask = (DE_PIPEC_VBLANK_IVB | DE_PIPEB_VBLANK_IVB | |
1594 | DE_PIPEA_VBLANK_IVB | DE_ERR_INT_IVB | |
1595 | DE_PLANE_FLIP_DONE_IVB(PLANE_C) | |
1596 | DE_PLANE_FLIP_DONE_IVB(PLANE_B) | |
1597 | DE_PLANE_FLIP_DONE_IVB(PLANE_A) | |
1598 | DE_DP_A_HOTPLUG_IVB); |
1599 | } else { |
1600 | display_mask = (DE_MASTER_IRQ_CONTROL | DE_GSE | DE_PCH_EVENT | |
1601 | DE_AUX_CHANNEL_A | DE_PIPEB_CRC_DONE | |
1602 | DE_PIPEA_CRC_DONE | DE_POISON); |
1603 | extra_mask = (DE_PIPEA_VBLANK | DE_PIPEB_VBLANK | |
1604 | DE_PIPEB_FIFO_UNDERRUN | DE_PIPEA_FIFO_UNDERRUN | |
1605 | DE_PLANE_FLIP_DONE(PLANE_A) | |
1606 | DE_PLANE_FLIP_DONE(PLANE_B) | |
1607 | DE_DP_A_HOTPLUG); |
1608 | } |
1609 | |
1610 | if (IS_HASWELL(i915)) { |
1611 | gen3_assert_iir_is_zero(uncore, EDP_PSR_IIR); |
1612 | display_mask |= DE_EDP_PSR_INT_HSW; |
1613 | } |
1614 | |
1615 | if (IS_IRONLAKE_M(i915)) |
1616 | extra_mask |= DE_PCU_EVENT; |
1617 | |
1618 | i915->irq_mask = ~display_mask; |
1619 | |
1620 | ibx_irq_postinstall(dev_priv: i915); |
1621 | |
1622 | GEN3_IRQ_INIT(uncore, DE, i915->irq_mask, |
1623 | display_mask | extra_mask); |
1624 | } |
1625 | |
1626 | static void mtp_irq_postinstall(struct drm_i915_private *i915); |
1627 | static void icp_irq_postinstall(struct drm_i915_private *i915); |
1628 | |
1629 | void gen8_de_irq_postinstall(struct drm_i915_private *dev_priv) |
1630 | { |
1631 | struct intel_uncore *uncore = &dev_priv->uncore; |
1632 | |
1633 | u32 de_pipe_masked = gen8_de_pipe_fault_mask(dev_priv) | |
1634 | GEN8_PIPE_CDCLK_CRC_DONE; |
1635 | u32 de_pipe_enables; |
1636 | u32 de_port_masked = gen8_de_port_aux_mask(dev_priv); |
1637 | u32 de_port_enables; |
1638 | u32 de_misc_masked = GEN8_DE_EDP_PSR; |
1639 | u32 trans_mask = BIT(TRANSCODER_A) | BIT(TRANSCODER_B) | |
1640 | BIT(TRANSCODER_C) | BIT(TRANSCODER_D); |
1641 | enum pipe pipe; |
1642 | |
1643 | if (!HAS_DISPLAY(dev_priv)) |
1644 | return; |
1645 | |
1646 | if (DISPLAY_VER(dev_priv) >= 14) |
1647 | mtp_irq_postinstall(i915: dev_priv); |
1648 | else if (INTEL_PCH_TYPE(dev_priv) >= PCH_ICP) |
1649 | icp_irq_postinstall(i915: dev_priv); |
1650 | else if (HAS_PCH_SPLIT(dev_priv)) |
1651 | ibx_irq_postinstall(dev_priv); |
1652 | |
1653 | if (DISPLAY_VER(dev_priv) < 11) |
1654 | de_misc_masked |= GEN8_DE_MISC_GSE; |
1655 | |
1656 | if (IS_GEMINILAKE(dev_priv) || IS_BROXTON(dev_priv)) |
1657 | de_port_masked |= BXT_DE_PORT_GMBUS; |
1658 | |
1659 | if (DISPLAY_VER(dev_priv) >= 14) { |
1660 | de_misc_masked |= XELPDP_PMDEMAND_RSPTOUT_ERR | |
1661 | XELPDP_PMDEMAND_RSP; |
1662 | } else if (DISPLAY_VER(dev_priv) >= 11) { |
1663 | enum port port; |
1664 | |
1665 | if (intel_bios_is_dsi_present(dev_priv, port: &port)) |
1666 | de_port_masked |= DSI0_TE | DSI1_TE; |
1667 | } |
1668 | |
1669 | de_pipe_enables = de_pipe_masked | |
1670 | GEN8_PIPE_VBLANK | |
1671 | gen8_de_pipe_underrun_mask(dev_priv) | |
1672 | gen8_de_pipe_flip_done_mask(i915: dev_priv); |
1673 | |
1674 | de_port_enables = de_port_masked; |
1675 | if (IS_GEMINILAKE(dev_priv) || IS_BROXTON(dev_priv)) |
1676 | de_port_enables |= BXT_DE_PORT_HOTPLUG_MASK; |
1677 | else if (IS_BROADWELL(dev_priv)) |
1678 | de_port_enables |= BDW_DE_PORT_HOTPLUG_MASK; |
1679 | |
1680 | if (DISPLAY_VER(dev_priv) >= 12) { |
1681 | enum transcoder trans; |
1682 | |
1683 | for_each_cpu_transcoder_masked(dev_priv, trans, trans_mask) { |
1684 | enum intel_display_power_domain domain; |
1685 | |
1686 | domain = POWER_DOMAIN_TRANSCODER(trans); |
1687 | if (!intel_display_power_is_enabled(dev_priv, domain)) |
1688 | continue; |
1689 | |
1690 | gen3_assert_iir_is_zero(uncore, TRANS_PSR_IIR(trans)); |
1691 | } |
1692 | } else { |
1693 | gen3_assert_iir_is_zero(uncore, EDP_PSR_IIR); |
1694 | } |
1695 | |
1696 | for_each_pipe(dev_priv, pipe) { |
1697 | dev_priv->de_irq_mask[pipe] = ~de_pipe_masked; |
1698 | |
1699 | if (intel_display_power_is_enabled(dev_priv, |
1700 | POWER_DOMAIN_PIPE(pipe))) |
1701 | GEN8_IRQ_INIT_NDX(uncore, DE_PIPE, pipe, |
1702 | dev_priv->de_irq_mask[pipe], |
1703 | de_pipe_enables); |
1704 | } |
1705 | |
1706 | GEN3_IRQ_INIT(uncore, GEN8_DE_PORT_, ~de_port_masked, de_port_enables); |
1707 | GEN3_IRQ_INIT(uncore, GEN8_DE_MISC_, ~de_misc_masked, de_misc_masked); |
1708 | |
1709 | if (IS_DISPLAY_VER(dev_priv, 11, 13)) { |
1710 | u32 de_hpd_masked = 0; |
1711 | u32 de_hpd_enables = GEN11_DE_TC_HOTPLUG_MASK | |
1712 | GEN11_DE_TBT_HOTPLUG_MASK; |
1713 | |
1714 | GEN3_IRQ_INIT(uncore, GEN11_DE_HPD_, ~de_hpd_masked, |
1715 | de_hpd_enables); |
1716 | } |
1717 | } |
1718 | |
1719 | static void mtp_irq_postinstall(struct drm_i915_private *i915) |
1720 | { |
1721 | struct intel_uncore *uncore = &i915->uncore; |
1722 | u32 sde_mask = SDE_GMBUS_ICP | SDE_PICAINTERRUPT; |
1723 | u32 de_hpd_mask = XELPDP_AUX_TC_MASK; |
1724 | u32 de_hpd_enables = de_hpd_mask | XELPDP_DP_ALT_HOTPLUG_MASK | |
1725 | XELPDP_TBT_HOTPLUG_MASK; |
1726 | |
1727 | GEN3_IRQ_INIT(uncore, PICAINTERRUPT_, ~de_hpd_mask, |
1728 | de_hpd_enables); |
1729 | |
1730 | GEN3_IRQ_INIT(uncore, SDE, ~sde_mask, 0xffffffff); |
1731 | } |
1732 | |
1733 | static void icp_irq_postinstall(struct drm_i915_private *dev_priv) |
1734 | { |
1735 | struct intel_uncore *uncore = &dev_priv->uncore; |
1736 | u32 mask = SDE_GMBUS_ICP; |
1737 | |
1738 | GEN3_IRQ_INIT(uncore, SDE, ~mask, 0xffffffff); |
1739 | } |
1740 | |
1741 | void gen11_de_irq_postinstall(struct drm_i915_private *dev_priv) |
1742 | { |
1743 | if (!HAS_DISPLAY(dev_priv)) |
1744 | return; |
1745 | |
1746 | gen8_de_irq_postinstall(dev_priv); |
1747 | |
1748 | intel_uncore_write(uncore: &dev_priv->uncore, GEN11_DISPLAY_INT_CTL, |
1749 | GEN11_DISPLAY_IRQ_ENABLE); |
1750 | } |
1751 | |
1752 | void dg1_de_irq_postinstall(struct drm_i915_private *i915) |
1753 | { |
1754 | if (!HAS_DISPLAY(i915)) |
1755 | return; |
1756 | |
1757 | gen8_de_irq_postinstall(dev_priv: i915); |
1758 | intel_uncore_write(uncore: &i915->uncore, GEN11_DISPLAY_INT_CTL, |
1759 | GEN11_DISPLAY_IRQ_ENABLE); |
1760 | } |
1761 | |
1762 | void intel_display_irq_init(struct drm_i915_private *i915) |
1763 | { |
1764 | i915->drm.vblank_disable_immediate = true; |
1765 | |
1766 | /* |
1767 | * Most platforms treat the display irq block as an always-on power |
1768 | * domain. vlv/chv can disable it at runtime and need special care to |
1769 | * avoid writing any of the display block registers outside of the power |
1770 | * domain. We defer setting up the display irqs in this case to the |
1771 | * runtime pm. |
1772 | */ |
1773 | i915->display_irqs_enabled = true; |
1774 | if (IS_VALLEYVIEW(i915) || IS_CHERRYVIEW(i915)) |
1775 | i915->display_irqs_enabled = false; |
1776 | |
1777 | intel_hotplug_irq_init(i915); |
1778 | } |
1779 | |