linux/drivers/gpu/drm/vc4/vc4_kms.c

// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright (C) 2015 Broadcom
 */

/**
 * DOC: VC4 KMS
 *
 * This is the general code for implementing KMS mode setting that
 * doesn't clearly associate with any of the other objects (plane,
 * crtc, HDMI encoder).
 */

#include <linux/clk.h>
#include <linux/sort.h>

#include <drm/drm_atomic.h>
#include <drm/drm_atomic_helper.h>
#include <drm/drm_crtc.h>
#include <drm/drm_fourcc.h>
#include <drm/drm_gem_framebuffer_helper.h>
#include <drm/drm_probe_helper.h>
#include <drm/drm_vblank.h>

#include "vc4_drv.h"
#include "vc4_regs.h"

struct vc4_ctm_state {};

#define to_vc4_ctm_state(_state)

struct vc4_load_tracker_state {};

#define to_vc4_load_tracker_state(_state)

static struct vc4_ctm_state *vc4_get_ctm_state(struct drm_atomic_state *state,
					       struct drm_private_obj *manager)
{}

static struct drm_private_state *
vc4_ctm_duplicate_state(struct drm_private_obj *obj)
{}

static void vc4_ctm_destroy_state(struct drm_private_obj *obj,
				  struct drm_private_state *state)
{}

static const struct drm_private_state_funcs vc4_ctm_state_funcs =;

static void vc4_ctm_obj_fini(struct drm_device *dev, void *unused)
{}

static int vc4_ctm_obj_init(struct vc4_dev *vc4)
{}

/* Converts a DRM S31.32 value to the HW S0.9 format. */
static u16 vc4_ctm_s31_32_to_s0_9(u64 in)
{}

static void
vc4_ctm_commit(struct vc4_dev *vc4, struct drm_atomic_state *state)
{}

struct vc4_hvs_state *
vc4_hvs_get_new_global_state(const struct drm_atomic_state *state)
{}

struct vc4_hvs_state *
vc4_hvs_get_old_global_state(const struct drm_atomic_state *state)
{}

struct vc4_hvs_state *
vc4_hvs_get_global_state(struct drm_atomic_state *state)
{}

static void vc4_hvs_pv_muxing_commit(struct vc4_dev *vc4,
				     struct drm_atomic_state *state)
{}

static void vc5_hvs_pv_muxing_commit(struct vc4_dev *vc4,
				     struct drm_atomic_state *state)
{}

static void vc4_atomic_commit_tail(struct drm_atomic_state *state)
{}

static int vc4_atomic_commit_setup(struct drm_atomic_state *state)
{}

static struct drm_framebuffer *vc4_fb_create(struct drm_device *dev,
					     struct drm_file *file_priv,
					     const struct drm_mode_fb_cmd2 *mode_cmd)
{}

/* Our CTM has some peculiar limitations: we can only enable it for one CRTC
 * at a time and the HW only supports S0.9 scalars. To account for the latter,
 * we don't allow userland to set a CTM that we have no hope of approximating.
 */
static int
vc4_ctm_atomic_check(struct drm_device *dev, struct drm_atomic_state *state)
{}

static int vc4_load_tracker_atomic_check(struct drm_atomic_state *state)
{}

static struct drm_private_state *
vc4_load_tracker_duplicate_state(struct drm_private_obj *obj)
{}

static void vc4_load_tracker_destroy_state(struct drm_private_obj *obj,
					   struct drm_private_state *state)
{}

static const struct drm_private_state_funcs vc4_load_tracker_state_funcs =;

static void vc4_load_tracker_obj_fini(struct drm_device *dev, void *unused)
{}

static int vc4_load_tracker_obj_init(struct vc4_dev *vc4)
{}

static struct drm_private_state *
vc4_hvs_channels_duplicate_state(struct drm_private_obj *obj)
{}

static void vc4_hvs_channels_destroy_state(struct drm_private_obj *obj,
					   struct drm_private_state *state)
{}

static void vc4_hvs_channels_print_state(struct drm_printer *p,
					 const struct drm_private_state *state)
{}

static const struct drm_private_state_funcs vc4_hvs_state_funcs =;

static void vc4_hvs_channels_obj_fini(struct drm_device *dev, void *unused)
{}

static int vc4_hvs_channels_obj_init(struct vc4_dev *vc4)
{}

static int cmp_vc4_crtc_hvs_output(const void *a, const void *b)
{}

/*
 * The BCM2711 HVS has up to 7 outputs connected to the pixelvalves and
 * the TXP (and therefore all the CRTCs found on that platform).
 *
 * The naive (and our initial) implementation would just iterate over
 * all the active CRTCs, try to find a suitable FIFO, and then remove it
 * from the pool of available FIFOs. However, there are a few corner
 * cases that need to be considered:
 *
 * - When running in a dual-display setup (so with two CRTCs involved),
 *   we can update the state of a single CRTC (for example by changing
 *   its mode using xrandr under X11) without affecting the other. In
 *   this case, the other CRTC wouldn't be in the state at all, so we
 *   need to consider all the running CRTCs in the DRM device to assign
 *   a FIFO, not just the one in the state.
 *
 * - To fix the above, we can't use drm_atomic_get_crtc_state on all
 *   enabled CRTCs to pull their CRTC state into the global state, since
 *   a page flip would start considering their vblank to complete. Since
 *   we don't have a guarantee that they are actually active, that
 *   vblank might never happen, and shouldn't even be considered if we
 *   want to do a page flip on a single CRTC. That can be tested by
 *   doing a modetest -v first on HDMI1 and then on HDMI0.
 *
 * - Since we need the pixelvalve to be disabled and enabled back when
 *   the FIFO is changed, we should keep the FIFO assigned for as long
 *   as the CRTC is enabled, only considering it free again once that
 *   CRTC has been disabled. This can be tested by booting X11 on a
 *   single display, and changing the resolution down and then back up.
 */
static int vc4_pv_muxing_atomic_check(struct drm_device *dev,
				      struct drm_atomic_state *state)
{}

static int
vc4_core_clock_atomic_check(struct drm_atomic_state *state)
{}


static int
vc4_atomic_check(struct drm_device *dev, struct drm_atomic_state *state)
{}

static struct drm_mode_config_helper_funcs vc4_mode_config_helpers =;

static const struct drm_mode_config_funcs vc4_mode_funcs =;

static const struct drm_mode_config_funcs vc5_mode_funcs =;

int vc4_kms_load(struct drm_device *dev)
{}