/* SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause) */
/*
 * Copyright (c) 2020 MediaTek Inc.
 */
#ifndef _MTK_TV_DRM_CRTC_H_
#define _MTK_TV_DRM_CRTC_H_

#include "mtk_tv_drm_drv.h"
#include "mtk_tv_drm_plane.h"

#define to_mtk_tv_crtc(x)   container_of(x, struct mtk_tv_drm_crtc, base)

struct mtk_tv_drm_crtc;
struct mtk_tv_drm_crtc_ops {
	void (*enable)(struct mtk_tv_drm_crtc *crtc);
	void (*disable)(struct mtk_tv_drm_crtc *crtc);
	int (*enable_vblank)(struct mtk_tv_drm_crtc *crtc);
	void (*disable_vblank)(struct mtk_tv_drm_crtc *crtc);
	void (*update_plane)(struct mtk_plane_state *state);
	void (*disable_plane)(struct mtk_plane_state *state);
	int (*atomic_set_crtc_property)(struct mtk_tv_drm_crtc *crtc,
		struct drm_crtc_state *state,
		struct drm_property *property,
		uint64_t val);
	int (*atomic_get_crtc_property)(struct mtk_tv_drm_crtc *crtc,
		const struct drm_crtc_state *state,
		struct drm_property *property,
		uint64_t *val);
	int (*atomic_set_plane_property)(struct mtk_drm_plane *mplane,
		struct drm_plane_state *state,
		struct drm_property *property, uint64_t val);
	int (*atomic_get_plane_property)(struct mtk_drm_plane *mplane,
		const struct drm_plane_state *state,
		struct drm_property *property,
		uint64_t *val);
	int (*bootlogo_ctrl)(struct mtk_tv_drm_crtc *crtc,
		unsigned int cmd,
		unsigned int *gop);
	void (*atomic_crtc_begin)(struct mtk_tv_drm_crtc *crtc,
		struct drm_crtc_state *old_crtc_state);
	void (*atomic_crtc_flush)(struct mtk_tv_drm_crtc *crtc,
		struct drm_crtc_state *old_crtc_state);
	int (*check_plane)(struct drm_plane_state *plane_state,
		const struct drm_crtc_state *crtc_state,
		struct mtk_plane_state *state);
	int (*graphic_set_testpattern)(struct mtk_tv_drm_crtc *crtc,
		struct drm_mtk_tv_graphic_testpattern *testpatternInfo);
	int (*set_stub_mode)(struct mtk_tv_drm_crtc *crtc,
		struct drm_mtk_tv_common_stub *stubInfo);
	int (*start_gfx_pqudata)(struct mtk_tv_drm_crtc *crtc,
		struct drm_mtk_tv_gfx_pqudata *pquInfo);
	int (*stop_gfx_pqudata)(struct mtk_tv_drm_crtc *crtc,
		struct drm_mtk_tv_gfx_pqudata *pquInfo);
	int (*get_fence)(struct mtk_tv_drm_crtc *mcrtc,
		struct drm_mtk_tv_fence_info *fenceInfo);
	int (*timeline_inc)(struct mtk_tv_drm_crtc *mcrtc, uint32_t planeIdx);
	int (*set_graphic_pq_buf)(struct mtk_tv_drm_crtc *mcrtc,
		struct drm_mtk_tv_graphic_pq_setting *PqBufInfo);
	int (*get_graphic_roi)(struct drm_mtk_tv_graphic_roi_info *RoiInfo);
	int (*set_graphic_roi)(uint32_t threshold);
	int (*ldm_set_led_check)(struct mtk_tv_drm_crtc *crtc,
		struct drm_mtk_tv_ldm_led_check *ledcheckInfo);
	int (*ldm_set_black_insert_enable)(struct mtk_tv_drm_crtc *crtc,
		struct drm_mtk_tv_ldm_black_insert_enable *blackInsertInfo);
	int (*ldm_set_pq_param)(struct mtk_tv_drm_crtc *crtc,
		struct drm_mtk_tv_ldm_pq_param *ldparamInfo);
};

struct mtk_tv_drm_crtc {
	struct drm_crtc base;
	/**
	 * @event_lock:
	 *
	 * Protects @vblank_event_list and event delivery in
	 * general. See drm_send_event() and drm_send_event_locked().
	 */
	spinlock_t event_lock;
	struct mtk_drm_plane *plane[MTK_DRM_PLANE_TYPE_MAX];
	int plane_count[MTK_DRM_PLANE_TYPE_MAX];
	bool pending_needs_vblank;
	bool active_change;
	struct drm_pending_vblank_event *event;
	const struct mtk_tv_drm_crtc_ops *ops;
	enum drm_mtk_crtc_type mtk_crtc_type;
	void *crtc_private;
};

int mtk_tv_drm_crtc_enable_vblank(struct drm_device *drm, unsigned int pipe);
void mtk_tv_drm_crtc_disable_vblank(struct drm_device *drm, unsigned int pipe);
int mtk_tv_drm_crtc_create(struct drm_device *drm_dev, struct mtk_tv_drm_crtc *mtk_tv_crtc,
	struct drm_plane *plane, struct drm_plane *cursor_plane,
	const struct mtk_tv_drm_crtc_ops *ops);
int mtk_tv_drm_bootlogo_ctrl_ioctl(struct drm_device *dev, void *data, struct drm_file *file_priv);
int mtk_tv_drm_set_graphic_testpattern_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_set_stub_mode_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_start_gfx_pqudata_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_stop_gfx_pqudata_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_get_fence_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_timeline_inc_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_graphic_set_pq_buf_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_graphic_get_roi_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
int mtk_tv_drm_graphic_set_roi_ioctl(struct drm_device *dev, void *data,
						struct drm_file *file_priv);
#endif //_MTK_TV_DRM_CRTC_H_
