Commit e7d4e143 authored by Tobias Jakobi's avatar Tobias Jakobi Committed by Alex Deucher
Browse files

drm/amd/display: handle nulled pipe context in DCE110's set_drr()

As set_drr() is called from IRQ context, it can happen that the
pipe context has been nulled by dc_state_destruct().

Apply the same protection here that is already present for
dcn35_set_drr() and dcn10_set_drr(). I.e. fetch the tg pointer
first (to avoid a race with dc_state_destruct()), and then
check the local copy before using it.

Closes: https://gitlab.freedesktop.org/drm/amd/-/issues/3142


Fixes: 06ad7e16 ("drm/amd/display: Destroy DC context while keeping DML and DML2")
Acked-by: default avatarAlex Deucher <alexander.deucher@amd.com>
Signed-off-by: default avatarTobias Jakobi <tjakobi@math.uni-bielefeld.de>
Signed-off-by: default avatarAlex Deucher <alexander.deucher@amd.com>
parent 375b035f
Loading
Loading
Loading
Loading
+14 −7
Original line number Diff line number Diff line
@@ -2096,13 +2096,20 @@ static void set_drr(struct pipe_ctx **pipe_ctx,
	 * as well.
	 */
	for (i = 0; i < num_pipes; i++) {
		pipe_ctx[i]->stream_res.tg->funcs->set_drr(
			pipe_ctx[i]->stream_res.tg, &params);
		/* dc_state_destruct() might null the stream resources, so fetch tg
		 * here first to avoid a race condition. The lifetime of the pointee
		 * itself (the timing_generator object) is not a problem here.
		 */
		struct timing_generator *tg = pipe_ctx[i]->stream_res.tg;

		if ((tg != NULL) && tg->funcs) {
			if (tg->funcs->set_drr)
				tg->funcs->set_drr(tg, &params);
			if (adjust.v_total_max != 0 && adjust.v_total_min != 0)
			pipe_ctx[i]->stream_res.tg->funcs->set_static_screen_control(
					pipe_ctx[i]->stream_res.tg,
					event_triggers, num_frames);
				if (tg->funcs->set_static_screen_control)
					tg->funcs->set_static_screen_control(
						tg, event_triggers, num_frames);
		}
	}
}