mirror of
git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-08-05 16:54:27 +00:00

Provide the lower level code for PIPEDMC based flip queue. We'll use the so called semi-full flip queue mode where the PIPEDMC will start the provided DSB on a scanline a little ahead of the vblank. We need to program the triggering scanline early enough so that the DSB has enough time to complete writing all the double buffered registers before they get latched (at start of vblank). The firmware implements several queues: - 3 "plane queues" which execute a single DSB per entry - 1 "general queue" which can apparently execute 2 DSBs per entry - 1 vestigial "fast queue" that replaced the "simple flip queue" on ADL+, but this isn't supposed to be used due to issues. But we only need a single plane queue really, and we won't actually use it as a real queue because we don't allow queueing multiple commits ahead of time. So the whole thing is perhaps useless. I suppose there migth be some power saving benefits if we would get the flip scheduled by userspace early and then could keep some hardware powered off a bit longer until the DMC kicks off the flipq programming. But that is pure speculation at this time and needs to be proven. The code to hook up the flip queue into the actual atomic commit path will follow later. TODO: need to think how to do the "wait for DMC firmware load" nicely need to think about VRR and PSR etc. v2: Don't write DMC_FQ_W2_PTS_CFG_SEL on pre-lnl Don't oops at flipq init if there is no dmc v3: Adapt to PTL+ flipq changes (different queue entry layout, different trigger event, need VRR TG) Use the actual CDCLK frequency Ask the DSB code how long things are expected to take v3: Adjust the cdclk rounding (docs are 100% vague, Windows rounds like this) Initialize some undocumented magic DMC variables on PTL v4: Use PIPEDMC_FQ_STATUS for busy check (the busy bit in PIPEDMC_FQ_CTRL is apparently gone on LNL+) Based the preempt timeout on the max exec time Preempt before disabling the flip queue Order the PIPEDMC_SCANLINECMP* writes a bit more carefully Fix some typos v5: Try to deal with some clang-20 div-by-zero false positive (Nathan) Add some docs (Jani) Cc: Nathan Chancellor <nathan@kernel.org> Reviewed-by: Uma Shankar <uma.shankar@intel.com> Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com> epr Link: https://patchwork.freedesktop.org/patch/msgid/20250624170049.27284-5-ville.syrjala@linux.intel.com
51 lines
1.9 KiB
C
51 lines
1.9 KiB
C
/* SPDX-License-Identifier: MIT */
|
|
/*
|
|
* Copyright © 2019 Intel Corporation
|
|
*/
|
|
|
|
#ifndef __INTEL_DMC_H__
|
|
#define __INTEL_DMC_H__
|
|
|
|
#include <linux/types.h>
|
|
|
|
enum pipe;
|
|
enum pipedmc_event_id;
|
|
struct drm_printer;
|
|
struct intel_crtc;
|
|
struct intel_crtc_state;
|
|
struct intel_display;
|
|
struct intel_dmc_snapshot;
|
|
|
|
void intel_dmc_init(struct intel_display *display);
|
|
void intel_dmc_load_program(struct intel_display *display);
|
|
void intel_dmc_wait_fw_load(struct intel_display *display);
|
|
void intel_dmc_disable_program(struct intel_display *display);
|
|
void intel_dmc_enable_pipe(const struct intel_crtc_state *crtc_state);
|
|
void intel_dmc_disable_pipe(const struct intel_crtc_state *crtc_state);
|
|
void intel_dmc_block_pkgc(struct intel_display *display, enum pipe pipe,
|
|
bool block);
|
|
void intel_dmc_start_pkgc_exit_at_start_of_undelayed_vblank(struct intel_display *display,
|
|
enum pipe pipe, bool enable);
|
|
void intel_dmc_fini(struct intel_display *display);
|
|
void intel_dmc_suspend(struct intel_display *display);
|
|
void intel_dmc_resume(struct intel_display *display);
|
|
bool intel_dmc_has_payload(struct intel_display *display);
|
|
void intel_dmc_debugfs_register(struct intel_display *display);
|
|
|
|
struct intel_dmc_snapshot *intel_dmc_snapshot_capture(struct intel_display *display);
|
|
void intel_dmc_snapshot_print(const struct intel_dmc_snapshot *snapshot, struct drm_printer *p);
|
|
void intel_dmc_update_dc6_allowed_count(struct intel_display *display, bool start_tracking);
|
|
|
|
void assert_main_dmc_loaded(struct intel_display *display);
|
|
|
|
void intel_pipedmc_irq_handler(struct intel_display *display, enum pipe pipe);
|
|
|
|
u32 intel_pipedmc_start_mmioaddr(struct intel_crtc *crtc);
|
|
void intel_pipedmc_enable_event(struct intel_crtc *crtc,
|
|
enum pipedmc_event_id event);
|
|
void intel_pipedmc_disable_event(struct intel_crtc *crtc,
|
|
enum pipedmc_event_id event);
|
|
|
|
void intel_pipedmc_irq_handler(struct intel_display *display, enum pipe pipe);
|
|
|
|
#endif /* __INTEL_DMC_H__ */
|