Skip to content

Commit 5ae0da3

Browse files
committed
drm/i915/dsb: Load LUTs using the DSB during vblank
Loading LUTs with the DSB outside of vblank doesn't really work due to the palette anti-collision logic. Apparently the DSB register writes don't get stalled like CPU mmio writes do and instead we end up corrupting the LUT entries. Disabling the anti-collision logic would allow us to successfully load the LUT outside of vblank, but presumably that risks the LUT reads from the scanout (temporarily) getting corrupted data from the LUT instead. The anti-collision logic isn't active during vblank so that is when we can successfully load the LUT with the DSB. That is what we want to do anyway to avoid tearing. Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com> Link: https://patchwork.freedesktop.org/patch/msgid/20230606191504.18099-13-ville.syrjala@linux.intel.com Reviewed-by: Uma Shankar <uma.shankar@intel.com>
1 parent dd1c3ea commit 5ae0da3

4 files changed

Lines changed: 32 additions & 7 deletions

File tree

drivers/gpu/drm/i915/display/intel_color.c

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1741,12 +1741,6 @@ static void icl_load_luts(const struct intel_crtc_state *crtc_state)
17411741
MISSING_CASE(crtc_state->gamma_mode);
17421742
break;
17431743
}
1744-
1745-
if (crtc_state->dsb) {
1746-
intel_dsb_finish(crtc_state->dsb);
1747-
intel_dsb_commit(crtc_state->dsb, false);
1748-
intel_dsb_wait(crtc_state->dsb);
1749-
}
17501744
}
17511745

17521746
static void vlv_load_luts(const struct intel_crtc_state *crtc_state)
@@ -1853,6 +1847,9 @@ void intel_color_load_luts(const struct intel_crtc_state *crtc_state)
18531847
{
18541848
struct drm_i915_private *i915 = to_i915(crtc_state->uapi.crtc->dev);
18551849

1850+
if (crtc_state->dsb)
1851+
return;
1852+
18561853
i915->display.funcs.color->load_luts(crtc_state);
18571854
}
18581855

@@ -1869,6 +1866,9 @@ void intel_color_commit_arm(const struct intel_crtc_state *crtc_state)
18691866
struct drm_i915_private *i915 = to_i915(crtc_state->uapi.crtc->dev);
18701867

18711868
i915->display.funcs.color->color_commit_arm(crtc_state);
1869+
1870+
if (crtc_state->dsb)
1871+
intel_dsb_commit(crtc_state->dsb, true);
18721872
}
18731873

18741874
void intel_color_post_update(const struct intel_crtc_state *crtc_state)
@@ -1882,6 +1882,7 @@ void intel_color_post_update(const struct intel_crtc_state *crtc_state)
18821882
void intel_color_prepare_commit(struct intel_crtc_state *crtc_state)
18831883
{
18841884
struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc);
1885+
struct drm_i915_private *i915 = to_i915(crtc->base.dev);
18851886

18861887
/* FIXME DSB has issues loading LUTs, disable it for now */
18871888
return;
@@ -1894,6 +1895,12 @@ void intel_color_prepare_commit(struct intel_crtc_state *crtc_state)
18941895
return;
18951896

18961897
crtc_state->dsb = intel_dsb_prepare(crtc, 1024);
1898+
if (!crtc_state->dsb)
1899+
return;
1900+
1901+
i915->display.funcs.color->load_luts(crtc_state);
1902+
1903+
intel_dsb_finish(crtc_state->dsb);
18971904
}
18981905

18991906
void intel_color_cleanup_commit(struct intel_crtc_state *crtc_state)
@@ -1905,6 +1912,17 @@ void intel_color_cleanup_commit(struct intel_crtc_state *crtc_state)
19051912
crtc_state->dsb = NULL;
19061913
}
19071914

1915+
void intel_color_wait_commit(const struct intel_crtc_state *crtc_state)
1916+
{
1917+
if (crtc_state->dsb)
1918+
intel_dsb_wait(crtc_state->dsb);
1919+
}
1920+
1921+
bool intel_color_uses_dsb(const struct intel_crtc_state *crtc_state)
1922+
{
1923+
return crtc_state->dsb;
1924+
}
1925+
19081926
static bool intel_can_preload_luts(const struct intel_crtc_state *new_crtc_state)
19091927
{
19101928
struct intel_crtc *crtc = to_intel_crtc(new_crtc_state->uapi.crtc);

drivers/gpu/drm/i915/display/intel_color.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@ void intel_color_crtc_init(struct intel_crtc *crtc);
1919
int intel_color_check(struct intel_crtc_state *crtc_state);
2020
void intel_color_prepare_commit(struct intel_crtc_state *crtc_state);
2121
void intel_color_cleanup_commit(struct intel_crtc_state *crtc_state);
22+
bool intel_color_uses_dsb(const struct intel_crtc_state *crtc_state);
23+
void intel_color_wait_commit(const struct intel_crtc_state *crtc_state);
2224
void intel_color_commit_noarm(const struct intel_crtc_state *crtc_state);
2325
void intel_color_commit_arm(const struct intel_crtc_state *crtc_state);
2426
void intel_color_post_update(const struct intel_crtc_state *crtc_state);

drivers/gpu/drm/i915/display/intel_crtc.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
#include "intel_display_trace.h"
2525
#include "intel_display_types.h"
2626
#include "intel_drrs.h"
27+
#include "intel_dsb.h"
2728
#include "intel_dsi.h"
2829
#include "intel_fifo_underrun.h"
2930
#include "intel_pipe_crc.h"
@@ -394,7 +395,8 @@ static bool intel_crtc_needs_vblank_work(const struct intel_crtc_state *crtc_sta
394395
return crtc_state->hw.active &&
395396
!intel_crtc_needs_modeset(crtc_state) &&
396397
!crtc_state->preload_luts &&
397-
intel_crtc_needs_color_update(crtc_state);
398+
intel_crtc_needs_color_update(crtc_state) &&
399+
!intel_color_uses_dsb(crtc_state);
398400
}
399401

400402
static void intel_crtc_vblank_work(struct kthread_work *base)

drivers/gpu/drm/i915/display/intel_display.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@
7777
#include "intel_dpll_mgr.h"
7878
#include "intel_dpt.h"
7979
#include "intel_drrs.h"
80+
#include "intel_dsb.h"
8081
#include "intel_dsi.h"
8182
#include "intel_dvo.h"
8283
#include "intel_fb.h"
@@ -7144,6 +7145,8 @@ static void intel_atomic_commit_tail(struct intel_atomic_state *state)
71447145
for_each_new_intel_crtc_in_state(state, crtc, new_crtc_state, i) {
71457146
if (new_crtc_state->do_async_flip)
71467147
intel_crtc_disable_flip_done(state, crtc);
7148+
7149+
intel_color_wait_commit(new_crtc_state);
71477150
}
71487151

71497152
/*

0 commit comments

Comments
 (0)