xref: /linux/drivers/gpu/drm/nouveau/dispnv04/disp.h (revision c771600c6af14749609b49565ffb4cac2959710d)
1b7019ac5SIlia Mirkin /* SPDX-License-Identifier: MIT */
2017e6e29SBen Skeggs #ifndef __NV04_DISPLAY_H__
3017e6e29SBen Skeggs #define __NV04_DISPLAY_H__
44dc28134SBen Skeggs #include <subdev/bios.h>
551a3d342SBen Skeggs #include <subdev/bios/pll.h>
651a3d342SBen Skeggs 
777145f1cSBen Skeggs #include "nouveau_display.h"
877145f1cSBen Skeggs 
9801bc858SBen Skeggs #include <nvif/event.h>
10801bc858SBen Skeggs 
1109838c4eSLyude Paul struct nouveau_encoder;
1209838c4eSLyude Paul 
13017e6e29SBen Skeggs enum nv04_fp_display_regs {
14017e6e29SBen Skeggs 	FP_DISPLAY_END,
15017e6e29SBen Skeggs 	FP_TOTAL,
16017e6e29SBen Skeggs 	FP_CRTC,
17017e6e29SBen Skeggs 	FP_SYNC_START,
18017e6e29SBen Skeggs 	FP_SYNC_END,
19017e6e29SBen Skeggs 	FP_VALID_START,
20017e6e29SBen Skeggs 	FP_VALID_END
21017e6e29SBen Skeggs };
22017e6e29SBen Skeggs 
23017e6e29SBen Skeggs struct nv04_crtc_reg {
24017e6e29SBen Skeggs 	unsigned char MiscOutReg;
25017e6e29SBen Skeggs 	uint8_t CRTC[0xa0];
26017e6e29SBen Skeggs 	uint8_t CR58[0x10];
27017e6e29SBen Skeggs 	uint8_t Sequencer[5];
28017e6e29SBen Skeggs 	uint8_t Graphics[9];
29017e6e29SBen Skeggs 	uint8_t Attribute[21];
30017e6e29SBen Skeggs 	unsigned char DAC[768];
31017e6e29SBen Skeggs 
32017e6e29SBen Skeggs 	/* PCRTC regs */
33017e6e29SBen Skeggs 	uint32_t fb_start;
34017e6e29SBen Skeggs 	uint32_t crtc_cfg;
35017e6e29SBen Skeggs 	uint32_t cursor_cfg;
36017e6e29SBen Skeggs 	uint32_t gpio_ext;
37017e6e29SBen Skeggs 	uint32_t crtc_830;
38017e6e29SBen Skeggs 	uint32_t crtc_834;
39017e6e29SBen Skeggs 	uint32_t crtc_850;
40017e6e29SBen Skeggs 	uint32_t crtc_eng_ctrl;
41017e6e29SBen Skeggs 
42017e6e29SBen Skeggs 	/* PRAMDAC regs */
43017e6e29SBen Skeggs 	uint32_t nv10_cursync;
44be83cd4eSBen Skeggs 	struct nvkm_pll_vals pllvals;
45017e6e29SBen Skeggs 	uint32_t ramdac_gen_ctrl;
46017e6e29SBen Skeggs 	uint32_t ramdac_630;
47017e6e29SBen Skeggs 	uint32_t ramdac_634;
48017e6e29SBen Skeggs 	uint32_t tv_setup;
49017e6e29SBen Skeggs 	uint32_t tv_vtotal;
50017e6e29SBen Skeggs 	uint32_t tv_vskew;
51017e6e29SBen Skeggs 	uint32_t tv_vsync_delay;
52017e6e29SBen Skeggs 	uint32_t tv_htotal;
53017e6e29SBen Skeggs 	uint32_t tv_hskew;
54017e6e29SBen Skeggs 	uint32_t tv_hsync_delay;
55017e6e29SBen Skeggs 	uint32_t tv_hsync_delay2;
56017e6e29SBen Skeggs 	uint32_t fp_horiz_regs[7];
57017e6e29SBen Skeggs 	uint32_t fp_vert_regs[7];
58017e6e29SBen Skeggs 	uint32_t dither;
59017e6e29SBen Skeggs 	uint32_t fp_control;
60017e6e29SBen Skeggs 	uint32_t dither_regs[6];
61017e6e29SBen Skeggs 	uint32_t fp_debug_0;
62017e6e29SBen Skeggs 	uint32_t fp_debug_1;
63017e6e29SBen Skeggs 	uint32_t fp_debug_2;
64017e6e29SBen Skeggs 	uint32_t fp_margin_color;
65017e6e29SBen Skeggs 	uint32_t ramdac_8c0;
66017e6e29SBen Skeggs 	uint32_t ramdac_a20;
67017e6e29SBen Skeggs 	uint32_t ramdac_a24;
68017e6e29SBen Skeggs 	uint32_t ramdac_a34;
69017e6e29SBen Skeggs 	uint32_t ctv_regs[38];
70017e6e29SBen Skeggs };
71017e6e29SBen Skeggs 
72017e6e29SBen Skeggs struct nv04_output_reg {
73017e6e29SBen Skeggs 	uint32_t output;
74017e6e29SBen Skeggs 	int head;
75017e6e29SBen Skeggs };
76017e6e29SBen Skeggs 
77017e6e29SBen Skeggs struct nv04_mode_state {
78017e6e29SBen Skeggs 	struct nv04_crtc_reg crtc_reg[2];
79017e6e29SBen Skeggs 	uint32_t pllsel;
80017e6e29SBen Skeggs 	uint32_t sel_clk;
81017e6e29SBen Skeggs };
82017e6e29SBen Skeggs 
83017e6e29SBen Skeggs struct nv04_display {
84017e6e29SBen Skeggs 	struct nv04_mode_state mode_reg;
85017e6e29SBen Skeggs 	struct nv04_mode_state saved_reg;
86017e6e29SBen Skeggs 	uint32_t saved_vga_font[4][16384];
87017e6e29SBen Skeggs 	uint32_t dac_users[4];
8878ae0ad4SBen Skeggs 	struct nouveau_bo *image[2];
89801bc858SBen Skeggs 	struct nvif_event flip;
90801bc858SBen Skeggs 	struct nouveau_drm *drm;
91017e6e29SBen Skeggs };
92017e6e29SBen Skeggs 
9377145f1cSBen Skeggs static inline struct nv04_display *
nv04_display(struct drm_device * dev)9477145f1cSBen Skeggs nv04_display(struct drm_device *dev)
9577145f1cSBen Skeggs {
9677145f1cSBen Skeggs 	return nouveau_display(dev)->priv;
9777145f1cSBen Skeggs }
9877145f1cSBen Skeggs 
99017e6e29SBen Skeggs /* nv04_display.c */
100017e6e29SBen Skeggs int nv04_display_create(struct drm_device *);
10109838c4eSLyude Paul struct nouveau_connector *
10209838c4eSLyude Paul nv04_encoder_get_connector(struct nouveau_encoder *nv_encoder);
103017e6e29SBen Skeggs 
104017e6e29SBen Skeggs /* nv04_crtc.c */
105017e6e29SBen Skeggs int nv04_crtc_create(struct drm_device *, int index);
106017e6e29SBen Skeggs 
107017e6e29SBen Skeggs /* nv04_dac.c */
108017e6e29SBen Skeggs int nv04_dac_create(struct drm_connector *, struct dcb_output *);
109017e6e29SBen Skeggs uint32_t nv17_dac_sample_load(struct drm_encoder *encoder);
110017e6e29SBen Skeggs int nv04_dac_output_offset(struct drm_encoder *encoder);
111017e6e29SBen Skeggs void nv04_dac_update_dacclk(struct drm_encoder *encoder, bool enable);
112017e6e29SBen Skeggs bool nv04_dac_in_use(struct drm_encoder *encoder);
113017e6e29SBen Skeggs 
114017e6e29SBen Skeggs /* nv04_dfp.c */
115017e6e29SBen Skeggs int nv04_dfp_create(struct drm_connector *, struct dcb_output *);
116017e6e29SBen Skeggs int nv04_dfp_get_bound_head(struct drm_device *dev, struct dcb_output *dcbent);
117017e6e29SBen Skeggs void nv04_dfp_bind_head(struct drm_device *dev, struct dcb_output *dcbent,
118017e6e29SBen Skeggs 			       int head, bool dl);
119017e6e29SBen Skeggs void nv04_dfp_disable(struct drm_device *dev, int head);
120017e6e29SBen Skeggs void nv04_dfp_update_fp_control(struct drm_encoder *encoder, int mode);
121017e6e29SBen Skeggs 
122017e6e29SBen Skeggs /* nv04_tv.c */
123017e6e29SBen Skeggs int nv04_tv_identify(struct drm_device *dev, int i2c_index);
124017e6e29SBen Skeggs int nv04_tv_create(struct drm_connector *, struct dcb_output *);
125017e6e29SBen Skeggs 
126017e6e29SBen Skeggs /* nv17_tv.c */
127017e6e29SBen Skeggs int nv17_tv_create(struct drm_connector *, struct dcb_output *);
128017e6e29SBen Skeggs 
129515de6b2SIlia Mirkin /* overlay.c */
130515de6b2SIlia Mirkin void nouveau_overlay_init(struct drm_device *dev);
131515de6b2SIlia Mirkin 
13277145f1cSBen Skeggs static inline bool
nv_two_heads(struct drm_device * dev)13377145f1cSBen Skeggs nv_two_heads(struct drm_device *dev)
13477145f1cSBen Skeggs {
13577145f1cSBen Skeggs 	struct nouveau_drm *drm = nouveau_drm(dev);
1364c0d42f7SThomas Zimmermann 	const int impl = to_pci_dev(dev->dev)->device & 0x0ff0;
13777145f1cSBen Skeggs 
1381167c6bcSBen Skeggs 	if (drm->client.device.info.family >= NV_DEVICE_INFO_V0_CELSIUS && impl != 0x0100 &&
13977145f1cSBen Skeggs 	    impl != 0x0150 && impl != 0x01a0 && impl != 0x0200)
14077145f1cSBen Skeggs 		return true;
14177145f1cSBen Skeggs 
14277145f1cSBen Skeggs 	return false;
14377145f1cSBen Skeggs }
14477145f1cSBen Skeggs 
14577145f1cSBen Skeggs static inline bool
nv_gf4_disp_arch(struct drm_device * dev)14677145f1cSBen Skeggs nv_gf4_disp_arch(struct drm_device *dev)
14777145f1cSBen Skeggs {
1484c0d42f7SThomas Zimmermann 	return nv_two_heads(dev) && (to_pci_dev(dev->dev)->device & 0x0ff0) != 0x0110;
14977145f1cSBen Skeggs }
15077145f1cSBen Skeggs 
15177145f1cSBen Skeggs static inline bool
nv_two_reg_pll(struct drm_device * dev)15277145f1cSBen Skeggs nv_two_reg_pll(struct drm_device *dev)
15377145f1cSBen Skeggs {
15477145f1cSBen Skeggs 	struct nouveau_drm *drm = nouveau_drm(dev);
1554c0d42f7SThomas Zimmermann 	const int impl = to_pci_dev(dev->dev)->device & 0x0ff0;
15677145f1cSBen Skeggs 
1571167c6bcSBen Skeggs 	if (impl == 0x0310 || impl == 0x0340 || drm->client.device.info.family >= NV_DEVICE_INFO_V0_CURIE)
15877145f1cSBen Skeggs 		return true;
15977145f1cSBen Skeggs 	return false;
16077145f1cSBen Skeggs }
16177145f1cSBen Skeggs 
16277145f1cSBen Skeggs static inline bool
nv_match_device(struct drm_device * dev,unsigned device,unsigned sub_vendor,unsigned sub_device)16377145f1cSBen Skeggs nv_match_device(struct drm_device *dev, unsigned device,
16477145f1cSBen Skeggs 		unsigned sub_vendor, unsigned sub_device)
16577145f1cSBen Skeggs {
1664c0d42f7SThomas Zimmermann 	struct pci_dev *pdev = to_pci_dev(dev->dev);
1674c0d42f7SThomas Zimmermann 
1684c0d42f7SThomas Zimmermann 	return pdev->device == device &&
1694c0d42f7SThomas Zimmermann 		pdev->subsystem_vendor == sub_vendor &&
1704c0d42f7SThomas Zimmermann 		pdev->subsystem_device == sub_device;
17177145f1cSBen Skeggs }
17277145f1cSBen Skeggs 
17377145f1cSBen Skeggs #include <subdev/bios/init.h>
17477145f1cSBen Skeggs 
17577145f1cSBen Skeggs static inline void
nouveau_bios_run_init_table(struct drm_device * dev,u16 table,struct dcb_output * outp,int crtc)17677145f1cSBen Skeggs nouveau_bios_run_init_table(struct drm_device *dev, u16 table,
17777145f1cSBen Skeggs 			    struct dcb_output *outp, int crtc)
17877145f1cSBen Skeggs {
1796901f1d6SBen Skeggs 	nvbios_init(&nvxx_bios(nouveau_drm(dev))->subdev, table,
180639d72e2SBen Skeggs 		init.outp = outp;
181639d72e2SBen Skeggs 		init.head = crtc;
182639d72e2SBen Skeggs 	);
18377145f1cSBen Skeggs }
18477145f1cSBen Skeggs 
185801bc858SBen Skeggs int nv04_flip_complete(struct nvif_event *, void *, u32);
186017e6e29SBen Skeggs #endif
187