Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

drm/i915/psr: Consider SCL lines when validating vblank for wake latency

Panel Replay and PSR2 selective update require sufficient vblank duration
to accommodate wake latencies. However, the current
wake_lines_fit_into_vblank() logic does not account for the minimum
Set Context Latency (SCL) lines.

Separate out _intel_psr_min_set_context_latency() to compute the minimum
SCL requirement based on platform and feature usage.

The alpm_config_valid() helper is updated to pass the necessary context for
determining whether Panel Replay or PSR2 selective update is enabled.

v2: While calling alpm_config_valid() for selective_update use false flag
instead of has_panel_replay. (Jouni)
v3: Correct ordering of the panel_replay, sel_update flags. (Jouni)

Signed-off-by: Ankit Nautiyal <ankit.k.nautiyal@intel.com>
Cc: Animesh Manna <animesh.manna@intel.com>
Cc: Jouni Högander <jouni.hogander@intel.com>
Reviewed-by: Jouni Högander <jouni.hogander@intel.com>
Link: https://lore.kernel.org/r/20251016055415.2101347-6-ankit.k.nautiyal@intel.com

+61 -41
+61 -41
drivers/gpu/drm/i915/display/intel_psr.c
··· 1361 1361 return entry_setup_frames; 1362 1362 } 1363 1363 1364 + static 1365 + int _intel_psr_min_set_context_latency(const struct intel_crtc_state *crtc_state, 1366 + bool needs_panel_replay, 1367 + bool needs_sel_update) 1368 + { 1369 + struct intel_display *display = to_intel_display(crtc_state); 1370 + 1371 + if (!crtc_state->has_psr) 1372 + return 0; 1373 + 1374 + /* Wa_14015401596 */ 1375 + if (intel_vrr_possible(crtc_state) && IS_DISPLAY_VER(display, 13, 14)) 1376 + return 1; 1377 + 1378 + /* Rest is for SRD_STATUS needed on LunarLake and onwards */ 1379 + if (DISPLAY_VER(display) < 20) 1380 + return 0; 1381 + 1382 + /* 1383 + * Comment on SRD_STATUS register in Bspec for LunarLake and onwards: 1384 + * 1385 + * To deterministically capture the transition of the state machine 1386 + * going from SRDOFFACK to IDLE, the delayed V. Blank should be at least 1387 + * one line after the non-delayed V. Blank. 1388 + * 1389 + * Legacy TG: TRANS_SET_CONTEXT_LATENCY > 0 1390 + * VRR TG: TRANS_VRR_CTL[ VRR Guardband ] < (TRANS_VRR_VMAX[ VRR Vmax ] 1391 + * - TRANS_VTOTAL[ Vertical Active ]) 1392 + * 1393 + * SRD_STATUS is used only by PSR1 on PantherLake. 1394 + * SRD_STATUS is used by PSR1 and Panel Replay DP on LunarLake. 1395 + */ 1396 + 1397 + if (DISPLAY_VER(display) >= 30 && (needs_panel_replay || 1398 + needs_sel_update)) 1399 + return 0; 1400 + else if (DISPLAY_VER(display) < 30 && (needs_sel_update || 1401 + intel_crtc_has_type(crtc_state, 1402 + INTEL_OUTPUT_EDP))) 1403 + return 0; 1404 + else 1405 + return 1; 1406 + } 1407 + 1364 1408 static bool wake_lines_fit_into_vblank(struct intel_dp *intel_dp, 1365 1409 const struct intel_crtc_state *crtc_state, 1366 - bool aux_less) 1410 + bool aux_less, 1411 + bool needs_panel_replay, 1412 + bool needs_sel_update) 1367 1413 { 1368 1414 struct intel_display *display = to_intel_display(intel_dp); 1369 1415 int vblank = crtc_state->hw.adjusted_mode.crtc_vblank_end - 1370 1416 crtc_state->hw.adjusted_mode.crtc_vblank_start; 1371 1417 int wake_lines; 1418 + int scl = _intel_psr_min_set_context_latency(crtc_state, 1419 + needs_panel_replay, 1420 + needs_sel_update); 1421 + vblank -= scl; 1372 1422 1373 1423 if (aux_less) 1374 1424 wake_lines = crtc_state->alpm_state.aux_less_wake_lines; ··· 1440 1390 1441 1391 static bool alpm_config_valid(struct intel_dp *intel_dp, 1442 1392 struct intel_crtc_state *crtc_state, 1443 - bool aux_less) 1393 + bool aux_less, 1394 + bool needs_panel_replay, 1395 + bool needs_sel_update) 1444 1396 { 1445 1397 struct intel_display *display = to_intel_display(intel_dp); 1446 1398 ··· 1452 1400 return false; 1453 1401 } 1454 1402 1455 - if (!wake_lines_fit_into_vblank(intel_dp, crtc_state, aux_less)) { 1403 + if (!wake_lines_fit_into_vblank(intel_dp, crtc_state, aux_less, 1404 + needs_panel_replay, needs_sel_update)) { 1456 1405 drm_dbg_kms(display->drm, 1457 1406 "PSR2/Panel Replay not enabled, too short vblank time\n"); 1458 1407 return false; ··· 1545 1492 return false; 1546 1493 } 1547 1494 1548 - if (!alpm_config_valid(intel_dp, crtc_state, false)) 1495 + if (!alpm_config_valid(intel_dp, crtc_state, false, false, true)) 1549 1496 return false; 1550 1497 1551 1498 if (!crtc_state->enable_psr2_sel_fetch && ··· 1696 1643 return false; 1697 1644 } 1698 1645 1699 - if (!alpm_config_valid(intel_dp, crtc_state, true)) 1646 + if (!alpm_config_valid(intel_dp, crtc_state, true, true, false)) 1700 1647 return false; 1701 1648 1702 1649 return true; ··· 2424 2371 */ 2425 2372 int intel_psr_min_set_context_latency(const struct intel_crtc_state *crtc_state) 2426 2373 { 2427 - struct intel_display *display = to_intel_display(crtc_state); 2428 2374 2429 - if (!crtc_state->has_psr) 2430 - return 0; 2431 - 2432 - /* Wa_14015401596 */ 2433 - if (intel_vrr_possible(crtc_state) && IS_DISPLAY_VER(display, 13, 14)) 2434 - return 1; 2435 - 2436 - /* Rest is for SRD_STATUS needed on LunarLake and onwards */ 2437 - if (DISPLAY_VER(display) < 20) 2438 - return 0; 2439 - 2440 - /* 2441 - * Comment on SRD_STATUS register in Bspec for LunarLake and onwards: 2442 - * 2443 - * To deterministically capture the transition of the state machine 2444 - * going from SRDOFFACK to IDLE, the delayed V. Blank should be at least 2445 - * one line after the non-delayed V. Blank. 2446 - * 2447 - * Legacy TG: TRANS_SET_CONTEXT_LATENCY > 0 2448 - * VRR TG: TRANS_VRR_CTL[ VRR Guardband ] < (TRANS_VRR_VMAX[ VRR Vmax ] 2449 - * - TRANS_VTOTAL[ Vertical Active ]) 2450 - * 2451 - * SRD_STATUS is used only by PSR1 on PantherLake. 2452 - * SRD_STATUS is used by PSR1 and Panel Replay DP on LunarLake. 2453 - */ 2454 - 2455 - if (DISPLAY_VER(display) >= 30 && (crtc_state->has_panel_replay || 2456 - crtc_state->has_sel_update)) 2457 - return 0; 2458 - else if (DISPLAY_VER(display) < 30 && (crtc_state->has_sel_update || 2459 - intel_crtc_has_type(crtc_state, 2460 - INTEL_OUTPUT_EDP))) 2461 - return 0; 2462 - else 2463 - return 1; 2375 + return _intel_psr_min_set_context_latency(crtc_state, 2376 + crtc_state->has_panel_replay, 2377 + crtc_state->has_sel_update); 2464 2378 } 2465 2379 2466 2380 static u32 man_trk_ctl_enable_bit_get(struct intel_display *display)