Linux Audio

Check our new training course

Loading...
v4.6
 
  1/*
  2 * Copyright (c) 2016, The Linux Foundation. All rights reserved.
  3 *
  4 * This program is free software; you can redistribute it and/or modify
  5 * it under the terms of the GNU General Public License version 2 and
  6 * only version 2 as published by the Free Software Foundation.
  7 *
  8 * This program is distributed in the hope that it will be useful,
  9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 11 * GNU General Public License for more details.
 12 */
 13
 14#include <linux/clk-provider.h>
 
 15
 16#include "hdmi.h"
 17
 18#define HDMI_VCO_MAX_FREQ			12000000000UL
 19#define HDMI_VCO_MIN_FREQ			8000000000UL
 20
 21#define HDMI_PCLK_MAX_FREQ			600000000
 22#define HDMI_PCLK_MIN_FREQ			25000000
 23
 24#define HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD	3400000000UL
 25#define HDMI_DIG_FREQ_BIT_CLK_THRESHOLD		1500000000UL
 26#define HDMI_MID_FREQ_BIT_CLK_THRESHOLD		750000000UL
 27#define HDMI_CORECLK_DIV			5
 28#define HDMI_DEFAULT_REF_CLOCK			19200000
 29#define HDMI_PLL_CMP_CNT			1024
 30
 31#define HDMI_PLL_POLL_MAX_READS			100
 32#define HDMI_PLL_POLL_TIMEOUT_US		150
 33
 34#define HDMI_NUM_TX_CHANNEL			4
 35
 36struct hdmi_pll_8996 {
 37	struct platform_device *pdev;
 38	struct clk_hw clk_hw;
 39
 40	/* pll mmio base */
 41	void __iomem *mmio_qserdes_com;
 42	/* tx channel base */
 43	void __iomem *mmio_qserdes_tx[HDMI_NUM_TX_CHANNEL];
 44};
 45
 46#define hw_clk_to_pll(x) container_of(x, struct hdmi_pll_8996, clk_hw)
 47
 48struct hdmi_8996_phy_pll_reg_cfg {
 49	u32 tx_lx_lane_mode[HDMI_NUM_TX_CHANNEL];
 50	u32 tx_lx_tx_band[HDMI_NUM_TX_CHANNEL];
 51	u32 com_svs_mode_clk_sel;
 52	u32 com_hsclk_sel;
 53	u32 com_pll_cctrl_mode0;
 54	u32 com_pll_rctrl_mode0;
 55	u32 com_cp_ctrl_mode0;
 56	u32 com_dec_start_mode0;
 57	u32 com_div_frac_start1_mode0;
 58	u32 com_div_frac_start2_mode0;
 59	u32 com_div_frac_start3_mode0;
 60	u32 com_integloop_gain0_mode0;
 61	u32 com_integloop_gain1_mode0;
 62	u32 com_lock_cmp_en;
 63	u32 com_lock_cmp1_mode0;
 64	u32 com_lock_cmp2_mode0;
 65	u32 com_lock_cmp3_mode0;
 66	u32 com_core_clk_en;
 67	u32 com_coreclk_div;
 68	u32 com_vco_tune_ctrl;
 69
 70	u32 tx_lx_tx_drv_lvl[HDMI_NUM_TX_CHANNEL];
 71	u32 tx_lx_tx_emp_post1_lvl[HDMI_NUM_TX_CHANNEL];
 72	u32 tx_lx_vmode_ctrl1[HDMI_NUM_TX_CHANNEL];
 73	u32 tx_lx_vmode_ctrl2[HDMI_NUM_TX_CHANNEL];
 74	u32 tx_lx_res_code_lane_tx[HDMI_NUM_TX_CHANNEL];
 75	u32 tx_lx_hp_pd_enables[HDMI_NUM_TX_CHANNEL];
 76
 77	u32 phy_mode;
 78};
 79
 80struct hdmi_8996_post_divider {
 81	u64 vco_freq;
 82	int hsclk_divsel;
 83	int vco_ratio;
 84	int tx_band_sel;
 85	int half_rate_mode;
 86};
 87
 88static inline struct hdmi_phy *pll_get_phy(struct hdmi_pll_8996 *pll)
 89{
 90	return platform_get_drvdata(pll->pdev);
 91}
 92
 93static inline void hdmi_pll_write(struct hdmi_pll_8996 *pll, int offset,
 94				  u32 data)
 95{
 96	msm_writel(data, pll->mmio_qserdes_com + offset);
 97}
 98
 99static inline u32 hdmi_pll_read(struct hdmi_pll_8996 *pll, int offset)
100{
101	return msm_readl(pll->mmio_qserdes_com + offset);
102}
103
104static inline void hdmi_tx_chan_write(struct hdmi_pll_8996 *pll, int channel,
105				      int offset, int data)
106{
107	 msm_writel(data, pll->mmio_qserdes_tx[channel] + offset);
108}
109
110static inline u32 pll_get_cpctrl(u64 frac_start, unsigned long ref_clk,
111				 bool gen_ssc)
112{
113	if ((frac_start != 0) || gen_ssc)
114		return (11000000 / (ref_clk / 20));
115
116	return 0x23;
117}
118
119static inline u32 pll_get_rctrl(u64 frac_start, bool gen_ssc)
120{
121	if ((frac_start != 0) || gen_ssc)
122		return 0x16;
123
124	return 0x10;
125}
126
127static inline u32 pll_get_cctrl(u64 frac_start, bool gen_ssc)
128{
129	if ((frac_start != 0) || gen_ssc)
130		return 0x28;
131
132	return 0x1;
133}
134
135static inline u32 pll_get_integloop_gain(u64 frac_start, u64 bclk, u32 ref_clk,
136					 bool gen_ssc)
137{
138	int digclk_divsel = bclk >= HDMI_DIG_FREQ_BIT_CLK_THRESHOLD ? 1 : 2;
139	u64 base;
140
141	if ((frac_start != 0) || gen_ssc)
142		base = (64 * ref_clk) / HDMI_DEFAULT_REF_CLOCK;
143	else
144		base = (1022 * ref_clk) / 100;
145
146	base <<= digclk_divsel;
147
148	return (base <= 2046 ? base : 2046);
149}
150
151static inline u32 pll_get_pll_cmp(u64 fdata, unsigned long ref_clk)
152{
153	u64 dividend = HDMI_PLL_CMP_CNT * fdata;
154	u32 divisor = ref_clk * 10;
155	u32 rem;
156
157	rem = do_div(dividend, divisor);
158	if (rem > (divisor >> 1))
159		dividend++;
160
161	return dividend - 1;
162}
163
164static inline u64 pll_cmp_to_fdata(u32 pll_cmp, unsigned long ref_clk)
165{
166	u64 fdata = ((u64)pll_cmp) * ref_clk * 10;
167
168	do_div(fdata, HDMI_PLL_CMP_CNT);
169
170	return fdata;
171}
172
173static int pll_get_post_div(struct hdmi_8996_post_divider *pd, u64 bclk)
174{
175	int ratio[] = { 2, 3, 4, 5, 6, 9, 10, 12, 14, 15, 20, 21, 25, 28, 35 };
176	int hs_divsel[] = { 0, 4, 8, 12, 1, 5, 2, 9, 3, 13, 10, 7, 14, 11, 15 };
177	int tx_band_sel[] = { 0, 1, 2, 3 };
178	u64 vco_freq[60];
179	u64 vco, vco_optimal;
180	int half_rate_mode = 0;
181	int vco_optimal_index, vco_freq_index;
182	int i, j;
183
184retry:
185	vco_optimal = HDMI_VCO_MAX_FREQ;
186	vco_optimal_index = -1;
187	vco_freq_index = 0;
188	for (i = 0; i < 15; i++) {
189		for (j = 0; j < 4; j++) {
190			u32 ratio_mult = ratio[i] << tx_band_sel[j];
191
192			vco = bclk >> half_rate_mode;
193			vco *= ratio_mult;
194			vco_freq[vco_freq_index++] = vco;
195		}
196	}
197
198	for (i = 0; i < 60; i++) {
199		u64 vco_tmp = vco_freq[i];
200
201		if ((vco_tmp >= HDMI_VCO_MIN_FREQ) &&
202		    (vco_tmp <= vco_optimal)) {
203			vco_optimal = vco_tmp;
204			vco_optimal_index = i;
205		}
206	}
207
208	if (vco_optimal_index == -1) {
209		if (!half_rate_mode) {
210			half_rate_mode = 1;
211			goto retry;
212		}
213	} else {
214		pd->vco_freq = vco_optimal;
215		pd->tx_band_sel = tx_band_sel[vco_optimal_index % 4];
216		pd->vco_ratio = ratio[vco_optimal_index / 4];
217		pd->hsclk_divsel = hs_divsel[vco_optimal_index / 4];
218
219		return 0;
220	}
221
222	return -EINVAL;
223}
224
225static int pll_calculate(unsigned long pix_clk, unsigned long ref_clk,
226			 struct hdmi_8996_phy_pll_reg_cfg *cfg)
227{
228	struct hdmi_8996_post_divider pd;
229	u64 bclk;
230	u64 tmds_clk;
231	u64 dec_start;
232	u64 frac_start;
233	u64 fdata;
234	u32 pll_divisor;
235	u32 rem;
236	u32 cpctrl;
237	u32 rctrl;
238	u32 cctrl;
239	u32 integloop_gain;
240	u32 pll_cmp;
241	int i, ret;
242
243	/* bit clk = 10 * pix_clk */
244	bclk = ((u64)pix_clk) * 10;
245
246	if (bclk > HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD)
247		tmds_clk = pix_clk >> 2;
248	else
249		tmds_clk = pix_clk;
250
251	ret = pll_get_post_div(&pd, bclk);
252	if (ret)
253		return ret;
254
255	dec_start = pd.vco_freq;
256	pll_divisor = 4 * ref_clk;
257	do_div(dec_start, pll_divisor);
258
259	frac_start = pd.vco_freq * (1 << 20);
260
261	rem = do_div(frac_start, pll_divisor);
262	frac_start -= dec_start * (1 << 20);
263	if (rem > (pll_divisor >> 1))
264		frac_start++;
265
266	cpctrl = pll_get_cpctrl(frac_start, ref_clk, false);
267	rctrl = pll_get_rctrl(frac_start, false);
268	cctrl = pll_get_cctrl(frac_start, false);
269	integloop_gain = pll_get_integloop_gain(frac_start, bclk,
270						ref_clk, false);
271
272	fdata = pd.vco_freq;
273	do_div(fdata, pd.vco_ratio);
274
275	pll_cmp = pll_get_pll_cmp(fdata, ref_clk);
276
277	DBG("VCO freq: %llu", pd.vco_freq);
278	DBG("fdata: %llu", fdata);
279	DBG("pix_clk: %lu", pix_clk);
280	DBG("tmds clk: %llu", tmds_clk);
281	DBG("HSCLK_SEL: %d", pd.hsclk_divsel);
282	DBG("DEC_START: %llu", dec_start);
283	DBG("DIV_FRAC_START: %llu", frac_start);
284	DBG("PLL_CPCTRL: %u", cpctrl);
285	DBG("PLL_RCTRL: %u", rctrl);
286	DBG("PLL_CCTRL: %u", cctrl);
287	DBG("INTEGLOOP_GAIN: %u", integloop_gain);
288	DBG("TX_BAND: %d", pd.tx_band_sel);
289	DBG("PLL_CMP: %u", pll_cmp);
290
291	/* Convert these values to register specific values */
292	if (bclk > HDMI_DIG_FREQ_BIT_CLK_THRESHOLD)
293		cfg->com_svs_mode_clk_sel = 1;
294	else
295		cfg->com_svs_mode_clk_sel = 2;
296
297	cfg->com_hsclk_sel = (0x20 | pd.hsclk_divsel);
298	cfg->com_pll_cctrl_mode0 = cctrl;
299	cfg->com_pll_rctrl_mode0 = rctrl;
300	cfg->com_cp_ctrl_mode0 = cpctrl;
301	cfg->com_dec_start_mode0 = dec_start;
302	cfg->com_div_frac_start1_mode0 = (frac_start & 0xff);
303	cfg->com_div_frac_start2_mode0 = ((frac_start & 0xff00) >> 8);
304	cfg->com_div_frac_start3_mode0 = ((frac_start & 0xf0000) >> 16);
305	cfg->com_integloop_gain0_mode0 = (integloop_gain & 0xff);
306	cfg->com_integloop_gain1_mode0 = ((integloop_gain & 0xf00) >> 8);
307	cfg->com_lock_cmp1_mode0 = (pll_cmp & 0xff);
308	cfg->com_lock_cmp2_mode0 = ((pll_cmp & 0xff00) >> 8);
309	cfg->com_lock_cmp3_mode0 = ((pll_cmp & 0x30000) >> 16);
310	cfg->com_lock_cmp_en = 0x0;
311	cfg->com_core_clk_en = 0x2c;
312	cfg->com_coreclk_div = HDMI_CORECLK_DIV;
313	cfg->phy_mode = (bclk > HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD) ? 0x10 : 0x0;
314	cfg->com_vco_tune_ctrl = 0x0;
315
316	cfg->tx_lx_lane_mode[0] =
317		cfg->tx_lx_lane_mode[2] = 0x43;
318
319	cfg->tx_lx_hp_pd_enables[0] =
320		cfg->tx_lx_hp_pd_enables[1] =
321		cfg->tx_lx_hp_pd_enables[2] = 0x0c;
322	cfg->tx_lx_hp_pd_enables[3] = 0x3;
323
324	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++)
325		cfg->tx_lx_tx_band[i] = pd.tx_band_sel + 4;
326
327	if (bclk > HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD) {
328		cfg->tx_lx_tx_drv_lvl[0] =
329			cfg->tx_lx_tx_drv_lvl[1] =
330			cfg->tx_lx_tx_drv_lvl[2] = 0x25;
331		cfg->tx_lx_tx_drv_lvl[3] = 0x22;
332
333		cfg->tx_lx_tx_emp_post1_lvl[0] =
334			cfg->tx_lx_tx_emp_post1_lvl[1] =
335			cfg->tx_lx_tx_emp_post1_lvl[2] = 0x23;
336		cfg->tx_lx_tx_emp_post1_lvl[3] = 0x27;
337
338		cfg->tx_lx_vmode_ctrl1[0] =
339			cfg->tx_lx_vmode_ctrl1[1] =
340			cfg->tx_lx_vmode_ctrl1[2] =
341			cfg->tx_lx_vmode_ctrl1[3] = 0x00;
342
343		cfg->tx_lx_vmode_ctrl2[0] =
344			cfg->tx_lx_vmode_ctrl2[1] =
345			cfg->tx_lx_vmode_ctrl2[2] = 0x0D;
346
347		cfg->tx_lx_vmode_ctrl2[3] = 0x00;
348	} else if (bclk > HDMI_MID_FREQ_BIT_CLK_THRESHOLD) {
349		for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
350			cfg->tx_lx_tx_drv_lvl[i] = 0x25;
351			cfg->tx_lx_tx_emp_post1_lvl[i] = 0x23;
352			cfg->tx_lx_vmode_ctrl1[i] = 0x00;
353		}
354
355		cfg->tx_lx_vmode_ctrl2[0] =
356			cfg->tx_lx_vmode_ctrl2[1] =
357			cfg->tx_lx_vmode_ctrl2[2] = 0x0D;
358		cfg->tx_lx_vmode_ctrl2[3] = 0x00;
359	} else {
360		for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
361			cfg->tx_lx_tx_drv_lvl[i] = 0x20;
362			cfg->tx_lx_tx_emp_post1_lvl[i] = 0x20;
363			cfg->tx_lx_vmode_ctrl1[i] = 0x00;
364			cfg->tx_lx_vmode_ctrl2[i] = 0x0E;
365		}
366	}
367
368	DBG("com_svs_mode_clk_sel = 0x%x", cfg->com_svs_mode_clk_sel);
369	DBG("com_hsclk_sel = 0x%x", cfg->com_hsclk_sel);
370	DBG("com_lock_cmp_en = 0x%x", cfg->com_lock_cmp_en);
371	DBG("com_pll_cctrl_mode0 = 0x%x", cfg->com_pll_cctrl_mode0);
372	DBG("com_pll_rctrl_mode0 = 0x%x", cfg->com_pll_rctrl_mode0);
373	DBG("com_cp_ctrl_mode0 = 0x%x", cfg->com_cp_ctrl_mode0);
374	DBG("com_dec_start_mode0 = 0x%x", cfg->com_dec_start_mode0);
375	DBG("com_div_frac_start1_mode0 = 0x%x", cfg->com_div_frac_start1_mode0);
376	DBG("com_div_frac_start2_mode0 = 0x%x", cfg->com_div_frac_start2_mode0);
377	DBG("com_div_frac_start3_mode0 = 0x%x", cfg->com_div_frac_start3_mode0);
378	DBG("com_integloop_gain0_mode0 = 0x%x", cfg->com_integloop_gain0_mode0);
379	DBG("com_integloop_gain1_mode0 = 0x%x", cfg->com_integloop_gain1_mode0);
380	DBG("com_lock_cmp1_mode0 = 0x%x", cfg->com_lock_cmp1_mode0);
381	DBG("com_lock_cmp2_mode0 = 0x%x", cfg->com_lock_cmp2_mode0);
382	DBG("com_lock_cmp3_mode0 = 0x%x", cfg->com_lock_cmp3_mode0);
383	DBG("com_core_clk_en = 0x%x", cfg->com_core_clk_en);
384	DBG("com_coreclk_div = 0x%x", cfg->com_coreclk_div);
385	DBG("phy_mode = 0x%x", cfg->phy_mode);
386
387	DBG("tx_l0_lane_mode = 0x%x", cfg->tx_lx_lane_mode[0]);
388	DBG("tx_l2_lane_mode = 0x%x", cfg->tx_lx_lane_mode[2]);
389
390	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
391		DBG("tx_l%d_tx_band = 0x%x", i, cfg->tx_lx_tx_band[i]);
392		DBG("tx_l%d_tx_drv_lvl = 0x%x", i, cfg->tx_lx_tx_drv_lvl[i]);
393		DBG("tx_l%d_tx_emp_post1_lvl = 0x%x", i,
394		    cfg->tx_lx_tx_emp_post1_lvl[i]);
395		DBG("tx_l%d_vmode_ctrl1 = 0x%x", i, cfg->tx_lx_vmode_ctrl1[i]);
396		DBG("tx_l%d_vmode_ctrl2 = 0x%x", i, cfg->tx_lx_vmode_ctrl2[i]);
397	}
398
399	return 0;
400}
401
402static int hdmi_8996_pll_set_clk_rate(struct clk_hw *hw, unsigned long rate,
403				      unsigned long parent_rate)
404{
405	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
406	struct hdmi_phy *phy = pll_get_phy(pll);
407	struct hdmi_8996_phy_pll_reg_cfg cfg;
408	int i, ret;
409
410	memset(&cfg, 0x00, sizeof(cfg));
411
412	ret = pll_calculate(rate, parent_rate, &cfg);
413	if (ret) {
414		DRM_ERROR("PLL calculation failed\n");
415		return ret;
416	}
417
418	/* Initially shut down PHY */
419	DBG("Disabling PHY");
420	hdmi_phy_write(phy, REG_HDMI_8996_PHY_PD_CTL, 0x0);
421	udelay(500);
422
423	/* Power up sequence */
424	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BG_CTRL, 0x04);
425
426	hdmi_phy_write(phy, REG_HDMI_8996_PHY_PD_CTL, 0x1);
427	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_RESETSM_CNTRL, 0x20);
428	hdmi_phy_write(phy, REG_HDMI_8996_PHY_TX0_TX1_LANE_CTL, 0x0F);
429	hdmi_phy_write(phy, REG_HDMI_8996_PHY_TX2_TX3_LANE_CTL, 0x0F);
430
431	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
432		hdmi_tx_chan_write(pll, i,
433				   REG_HDMI_PHY_QSERDES_TX_LX_CLKBUF_ENABLE,
434				   0x03);
435		hdmi_tx_chan_write(pll, i,
436				   REG_HDMI_PHY_QSERDES_TX_LX_TX_BAND,
437				   cfg.tx_lx_tx_band[i]);
438		hdmi_tx_chan_write(pll, i,
439				   REG_HDMI_PHY_QSERDES_TX_LX_RESET_TSYNC_EN,
440				   0x03);
441	}
442
443	hdmi_tx_chan_write(pll, 0, REG_HDMI_PHY_QSERDES_TX_LX_LANE_MODE,
444			   cfg.tx_lx_lane_mode[0]);
445	hdmi_tx_chan_write(pll, 2, REG_HDMI_PHY_QSERDES_TX_LX_LANE_MODE,
446			   cfg.tx_lx_lane_mode[2]);
447
448	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SYSCLK_BUF_ENABLE, 0x1E);
449	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BIAS_EN_CLKBUFLR_EN, 0x07);
450	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SYSCLK_EN_SEL, 0x37);
451	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SYS_CLK_CTRL, 0x02);
452	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CLK_ENABLE1, 0x0E);
453
454	/* Bypass VCO calibration */
455	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SVS_MODE_CLK_SEL,
456		       cfg.com_svs_mode_clk_sel);
457
458	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BG_TRIM, 0x0F);
459	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_PLL_IVCO, 0x0F);
460	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_VCO_TUNE_CTRL,
461		       cfg.com_vco_tune_ctrl);
462
463	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BG_CTRL, 0x06);
464
465	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CLK_SELECT, 0x30);
466	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_HSCLK_SEL,
467		       cfg.com_hsclk_sel);
468	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP_EN,
469		       cfg.com_lock_cmp_en);
470
471	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_PLL_CCTRL_MODE0,
472		       cfg.com_pll_cctrl_mode0);
473	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_PLL_RCTRL_MODE0,
474		       cfg.com_pll_rctrl_mode0);
475	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CP_CTRL_MODE0,
476		       cfg.com_cp_ctrl_mode0);
477	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DEC_START_MODE0,
478		       cfg.com_dec_start_mode0);
479	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DIV_FRAC_START1_MODE0,
480		       cfg.com_div_frac_start1_mode0);
481	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DIV_FRAC_START2_MODE0,
482		       cfg.com_div_frac_start2_mode0);
483	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DIV_FRAC_START3_MODE0,
484		       cfg.com_div_frac_start3_mode0);
485
486	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_INTEGLOOP_GAIN0_MODE0,
487		       cfg.com_integloop_gain0_mode0);
488	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_INTEGLOOP_GAIN1_MODE0,
489		       cfg.com_integloop_gain1_mode0);
490
491	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP1_MODE0,
492		       cfg.com_lock_cmp1_mode0);
493	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP2_MODE0,
494		       cfg.com_lock_cmp2_mode0);
495	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP3_MODE0,
496		       cfg.com_lock_cmp3_mode0);
497
498	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_VCO_TUNE_MAP, 0x00);
499	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CORE_CLK_EN,
500		       cfg.com_core_clk_en);
501	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CORECLK_DIV,
502		       cfg.com_coreclk_div);
503	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CMN_CONFIG, 0x02);
504
505	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_RESCODE_DIV_NUM, 0x15);
506
507	/* TX lanes setup (TX 0/1/2/3) */
508	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
509		hdmi_tx_chan_write(pll, i,
510				   REG_HDMI_PHY_QSERDES_TX_LX_TX_DRV_LVL,
511				   cfg.tx_lx_tx_drv_lvl[i]);
512		hdmi_tx_chan_write(pll, i,
513				   REG_HDMI_PHY_QSERDES_TX_LX_TX_EMP_POST1_LVL,
514				   cfg.tx_lx_tx_emp_post1_lvl[i]);
515		hdmi_tx_chan_write(pll, i,
516				   REG_HDMI_PHY_QSERDES_TX_LX_VMODE_CTRL1,
517				   cfg.tx_lx_vmode_ctrl1[i]);
518		hdmi_tx_chan_write(pll, i,
519				   REG_HDMI_PHY_QSERDES_TX_LX_VMODE_CTRL2,
520				   cfg.tx_lx_vmode_ctrl2[i]);
521		hdmi_tx_chan_write(pll, i,
522				   REG_HDMI_PHY_QSERDES_TX_LX_TX_DRV_LVL_OFFSET,
523				   0x00);
524		hdmi_tx_chan_write(pll, i,
525			REG_HDMI_PHY_QSERDES_TX_LX_RES_CODE_LANE_OFFSET,
526			0x00);
527		hdmi_tx_chan_write(pll, i,
528			REG_HDMI_PHY_QSERDES_TX_LX_TRAN_DRVR_EMP_EN,
529			0x03);
530		hdmi_tx_chan_write(pll, i,
531			REG_HDMI_PHY_QSERDES_TX_LX_PARRATE_REC_DETECT_IDLE_EN,
532			0x40);
533		hdmi_tx_chan_write(pll, i,
534				   REG_HDMI_PHY_QSERDES_TX_LX_HP_PD_ENABLES,
535				   cfg.tx_lx_hp_pd_enables[i]);
536	}
537
538	hdmi_phy_write(phy, REG_HDMI_8996_PHY_MODE, cfg.phy_mode);
539	hdmi_phy_write(phy, REG_HDMI_8996_PHY_PD_CTL, 0x1F);
540
541	/*
542	 * Ensure that vco configuration gets flushed to hardware before
543	 * enabling the PLL
544	 */
545	wmb();
546
547	return 0;
548}
549
550static int hdmi_8996_phy_ready_status(struct hdmi_phy *phy)
551{
552	u32 nb_tries = HDMI_PLL_POLL_MAX_READS;
553	unsigned long timeout = HDMI_PLL_POLL_TIMEOUT_US;
554	u32 status;
555	int phy_ready = 0;
556
557	DBG("Waiting for PHY ready");
558
559	while (nb_tries--) {
560		status = hdmi_phy_read(phy, REG_HDMI_8996_PHY_STATUS);
561		phy_ready = status & BIT(0);
562
563		if (phy_ready)
564			break;
565
566		udelay(timeout);
567	}
568
569	DBG("PHY is %sready", phy_ready ? "" : "*not* ");
570
571	return phy_ready;
572}
573
574static int hdmi_8996_pll_lock_status(struct hdmi_pll_8996 *pll)
575{
576	u32 status;
577	int nb_tries = HDMI_PLL_POLL_MAX_READS;
578	unsigned long timeout = HDMI_PLL_POLL_TIMEOUT_US;
579	int pll_locked = 0;
580
581	DBG("Waiting for PLL lock");
582
583	while (nb_tries--) {
584		status = hdmi_pll_read(pll,
585				       REG_HDMI_PHY_QSERDES_COM_C_READY_STATUS);
586		pll_locked = status & BIT(0);
587
588		if (pll_locked)
589			break;
590
591		udelay(timeout);
592	}
593
594	DBG("HDMI PLL is %slocked", pll_locked ? "" : "*not* ");
595
596	return pll_locked;
597}
598
599static int hdmi_8996_pll_prepare(struct clk_hw *hw)
600{
601	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
602	struct hdmi_phy *phy = pll_get_phy(pll);
603	int i, ret = 0;
604
605	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x1);
606	udelay(100);
607
608	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x19);
609	udelay(100);
610
611	ret = hdmi_8996_pll_lock_status(pll);
612	if (!ret)
613		return ret;
614
615	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++)
616		hdmi_tx_chan_write(pll, i,
617			REG_HDMI_PHY_QSERDES_TX_LX_HIGHZ_TRANSCEIVEREN_BIAS_DRVR_EN,
618			0x6F);
619
620	/* Disable SSC */
621	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_PER1, 0x0);
622	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_PER2, 0x0);
623	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_STEP_SIZE1, 0x0);
624	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_STEP_SIZE2, 0x0);
625	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_EN_CENTER, 0x2);
626
627	ret = hdmi_8996_phy_ready_status(phy);
628	if (!ret)
629		return ret;
630
631	/* Restart the retiming buffer */
632	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x18);
633	udelay(1);
634	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x19);
635
636	return 0;
637}
638
639static long hdmi_8996_pll_round_rate(struct clk_hw *hw,
640				     unsigned long rate,
641				     unsigned long *parent_rate)
642{
643	if (rate < HDMI_PCLK_MIN_FREQ)
644		return HDMI_PCLK_MIN_FREQ;
645	else if (rate > HDMI_PCLK_MAX_FREQ)
646		return HDMI_PCLK_MAX_FREQ;
647	else
648		return rate;
649}
650
651static unsigned long hdmi_8996_pll_recalc_rate(struct clk_hw *hw,
652					       unsigned long parent_rate)
653{
654	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
655	u64 fdata;
656	u32 cmp1, cmp2, cmp3, pll_cmp;
657
658	cmp1 = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP1_MODE0);
659	cmp2 = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP2_MODE0);
660	cmp3 = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP3_MODE0);
661
662	pll_cmp = cmp1 | (cmp2 << 8) | (cmp3 << 16);
663
664	fdata = pll_cmp_to_fdata(pll_cmp + 1, parent_rate);
665
666	do_div(fdata, 10);
667
668	return fdata;
669}
670
671static void hdmi_8996_pll_unprepare(struct clk_hw *hw)
672{
 
 
 
 
 
673}
674
675static int hdmi_8996_pll_is_enabled(struct clk_hw *hw)
676{
677	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
678	u32 status;
679	int pll_locked;
680
681	status = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_C_READY_STATUS);
682	pll_locked = status & BIT(0);
683
684	return pll_locked;
685}
686
687static struct clk_ops hdmi_8996_pll_ops = {
688	.set_rate = hdmi_8996_pll_set_clk_rate,
689	.round_rate = hdmi_8996_pll_round_rate,
690	.recalc_rate = hdmi_8996_pll_recalc_rate,
691	.prepare = hdmi_8996_pll_prepare,
692	.unprepare = hdmi_8996_pll_unprepare,
693	.is_enabled = hdmi_8996_pll_is_enabled,
694};
695
696static const char * const hdmi_pll_parents[] = {
697	"xo",
698};
699
700static struct clk_init_data pll_init = {
701	.name = "hdmipll",
702	.ops = &hdmi_8996_pll_ops,
703	.parent_names = hdmi_pll_parents,
704	.num_parents = ARRAY_SIZE(hdmi_pll_parents),
 
 
 
705};
706
707int msm_hdmi_pll_8996_init(struct platform_device *pdev)
708{
709	struct device *dev = &pdev->dev;
710	struct hdmi_pll_8996 *pll;
711	struct clk *clk;
712	int i;
713
714	pll = devm_kzalloc(dev, sizeof(*pll), GFP_KERNEL);
715	if (!pll)
716		return -ENOMEM;
717
718	pll->pdev = pdev;
719
720	pll->mmio_qserdes_com = msm_ioremap(pdev, "hdmi_pll", "HDMI_PLL");
721	if (IS_ERR(pll->mmio_qserdes_com)) {
722		dev_err(dev, "failed to map pll base\n");
723		return -ENOMEM;
724	}
725
726	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
727		char name[32], label[32];
728
729		snprintf(name, sizeof(name), "hdmi_tx_l%d", i);
730		snprintf(label, sizeof(label), "HDMI_TX_L%d", i);
731
732		pll->mmio_qserdes_tx[i] = msm_ioremap(pdev, name, label);
733		if (IS_ERR(pll->mmio_qserdes_tx[i])) {
734			dev_err(dev, "failed to map pll base\n");
735			return -ENOMEM;
736		}
737	}
738	pll->clk_hw.init = &pll_init;
739
740	clk = devm_clk_register(dev, &pll->clk_hw);
741	if (IS_ERR(clk)) {
742		dev_err(dev, "failed to register pll clock\n");
743		return -EINVAL;
 
 
 
 
 
 
744	}
745
746	return 0;
747}
748
749static const char * const hdmi_phy_8996_reg_names[] = {
750	"vddio",
751	"vcca",
752};
753
754static const char * const hdmi_phy_8996_clk_names[] = {
755	"mmagic_iface_clk",
756	"iface_clk",
757	"ref_clk",
758};
759
760const struct hdmi_phy_cfg msm_hdmi_phy_8996_cfg = {
761	.type = MSM_HDMI_PHY_8996,
762	.reg_names = hdmi_phy_8996_reg_names,
763	.num_regs = ARRAY_SIZE(hdmi_phy_8996_reg_names),
764	.clk_names = hdmi_phy_8996_clk_names,
765	.num_clks = ARRAY_SIZE(hdmi_phy_8996_clk_names),
766};
v6.2
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Copyright (c) 2016, The Linux Foundation. All rights reserved.
 
 
 
 
 
 
 
 
 
  4 */
  5
  6#include <linux/clk-provider.h>
  7#include <linux/delay.h>
  8
  9#include "hdmi.h"
 10
 11#define HDMI_VCO_MAX_FREQ			12000000000UL
 12#define HDMI_VCO_MIN_FREQ			8000000000UL
 13
 14#define HDMI_PCLK_MAX_FREQ			600000000
 15#define HDMI_PCLK_MIN_FREQ			25000000
 16
 17#define HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD	3400000000UL
 18#define HDMI_DIG_FREQ_BIT_CLK_THRESHOLD		1500000000UL
 19#define HDMI_MID_FREQ_BIT_CLK_THRESHOLD		750000000UL
 20#define HDMI_CORECLK_DIV			5
 21#define HDMI_DEFAULT_REF_CLOCK			19200000
 22#define HDMI_PLL_CMP_CNT			1024
 23
 24#define HDMI_PLL_POLL_MAX_READS			100
 25#define HDMI_PLL_POLL_TIMEOUT_US		150
 26
 27#define HDMI_NUM_TX_CHANNEL			4
 28
 29struct hdmi_pll_8996 {
 30	struct platform_device *pdev;
 31	struct clk_hw clk_hw;
 32
 33	/* pll mmio base */
 34	void __iomem *mmio_qserdes_com;
 35	/* tx channel base */
 36	void __iomem *mmio_qserdes_tx[HDMI_NUM_TX_CHANNEL];
 37};
 38
 39#define hw_clk_to_pll(x) container_of(x, struct hdmi_pll_8996, clk_hw)
 40
 41struct hdmi_8996_phy_pll_reg_cfg {
 42	u32 tx_lx_lane_mode[HDMI_NUM_TX_CHANNEL];
 43	u32 tx_lx_tx_band[HDMI_NUM_TX_CHANNEL];
 44	u32 com_svs_mode_clk_sel;
 45	u32 com_hsclk_sel;
 46	u32 com_pll_cctrl_mode0;
 47	u32 com_pll_rctrl_mode0;
 48	u32 com_cp_ctrl_mode0;
 49	u32 com_dec_start_mode0;
 50	u32 com_div_frac_start1_mode0;
 51	u32 com_div_frac_start2_mode0;
 52	u32 com_div_frac_start3_mode0;
 53	u32 com_integloop_gain0_mode0;
 54	u32 com_integloop_gain1_mode0;
 55	u32 com_lock_cmp_en;
 56	u32 com_lock_cmp1_mode0;
 57	u32 com_lock_cmp2_mode0;
 58	u32 com_lock_cmp3_mode0;
 59	u32 com_core_clk_en;
 60	u32 com_coreclk_div;
 61	u32 com_vco_tune_ctrl;
 62
 63	u32 tx_lx_tx_drv_lvl[HDMI_NUM_TX_CHANNEL];
 64	u32 tx_lx_tx_emp_post1_lvl[HDMI_NUM_TX_CHANNEL];
 65	u32 tx_lx_vmode_ctrl1[HDMI_NUM_TX_CHANNEL];
 66	u32 tx_lx_vmode_ctrl2[HDMI_NUM_TX_CHANNEL];
 67	u32 tx_lx_res_code_lane_tx[HDMI_NUM_TX_CHANNEL];
 68	u32 tx_lx_hp_pd_enables[HDMI_NUM_TX_CHANNEL];
 69
 70	u32 phy_mode;
 71};
 72
 73struct hdmi_8996_post_divider {
 74	u64 vco_freq;
 75	int hsclk_divsel;
 76	int vco_ratio;
 77	int tx_band_sel;
 78	int half_rate_mode;
 79};
 80
 81static inline struct hdmi_phy *pll_get_phy(struct hdmi_pll_8996 *pll)
 82{
 83	return platform_get_drvdata(pll->pdev);
 84}
 85
 86static inline void hdmi_pll_write(struct hdmi_pll_8996 *pll, int offset,
 87				  u32 data)
 88{
 89	msm_writel(data, pll->mmio_qserdes_com + offset);
 90}
 91
 92static inline u32 hdmi_pll_read(struct hdmi_pll_8996 *pll, int offset)
 93{
 94	return msm_readl(pll->mmio_qserdes_com + offset);
 95}
 96
 97static inline void hdmi_tx_chan_write(struct hdmi_pll_8996 *pll, int channel,
 98				      int offset, int data)
 99{
100	 msm_writel(data, pll->mmio_qserdes_tx[channel] + offset);
101}
102
103static inline u32 pll_get_cpctrl(u64 frac_start, unsigned long ref_clk,
104				 bool gen_ssc)
105{
106	if ((frac_start != 0) || gen_ssc)
107		return (11000000 / (ref_clk / 20));
108
109	return 0x23;
110}
111
112static inline u32 pll_get_rctrl(u64 frac_start, bool gen_ssc)
113{
114	if ((frac_start != 0) || gen_ssc)
115		return 0x16;
116
117	return 0x10;
118}
119
120static inline u32 pll_get_cctrl(u64 frac_start, bool gen_ssc)
121{
122	if ((frac_start != 0) || gen_ssc)
123		return 0x28;
124
125	return 0x1;
126}
127
128static inline u32 pll_get_integloop_gain(u64 frac_start, u64 bclk, u32 ref_clk,
129					 bool gen_ssc)
130{
131	int digclk_divsel = bclk >= HDMI_DIG_FREQ_BIT_CLK_THRESHOLD ? 1 : 2;
132	u64 base;
133
134	if ((frac_start != 0) || gen_ssc)
135		base = (64 * ref_clk) / HDMI_DEFAULT_REF_CLOCK;
136	else
137		base = (1022 * ref_clk) / 100;
138
139	base <<= digclk_divsel;
140
141	return (base <= 2046 ? base : 2046);
142}
143
144static inline u32 pll_get_pll_cmp(u64 fdata, unsigned long ref_clk)
145{
146	u64 dividend = HDMI_PLL_CMP_CNT * fdata;
147	u32 divisor = ref_clk * 10;
148	u32 rem;
149
150	rem = do_div(dividend, divisor);
151	if (rem > (divisor >> 1))
152		dividend++;
153
154	return dividend - 1;
155}
156
157static inline u64 pll_cmp_to_fdata(u32 pll_cmp, unsigned long ref_clk)
158{
159	u64 fdata = ((u64)pll_cmp) * ref_clk * 10;
160
161	do_div(fdata, HDMI_PLL_CMP_CNT);
162
163	return fdata;
164}
165
166static int pll_get_post_div(struct hdmi_8996_post_divider *pd, u64 bclk)
167{
168	int ratio[] = { 2, 3, 4, 5, 6, 9, 10, 12, 14, 15, 20, 21, 25, 28, 35 };
169	int hs_divsel[] = { 0, 4, 8, 12, 1, 5, 2, 9, 3, 13, 10, 7, 14, 11, 15 };
170	int tx_band_sel[] = { 0, 1, 2, 3 };
171	u64 vco_freq[60];
172	u64 vco, vco_optimal;
173	int half_rate_mode = 0;
174	int vco_optimal_index, vco_freq_index;
175	int i, j;
176
177retry:
178	vco_optimal = HDMI_VCO_MAX_FREQ;
179	vco_optimal_index = -1;
180	vco_freq_index = 0;
181	for (i = 0; i < 15; i++) {
182		for (j = 0; j < 4; j++) {
183			u32 ratio_mult = ratio[i] << tx_band_sel[j];
184
185			vco = bclk >> half_rate_mode;
186			vco *= ratio_mult;
187			vco_freq[vco_freq_index++] = vco;
188		}
189	}
190
191	for (i = 0; i < 60; i++) {
192		u64 vco_tmp = vco_freq[i];
193
194		if ((vco_tmp >= HDMI_VCO_MIN_FREQ) &&
195		    (vco_tmp <= vco_optimal)) {
196			vco_optimal = vco_tmp;
197			vco_optimal_index = i;
198		}
199	}
200
201	if (vco_optimal_index == -1) {
202		if (!half_rate_mode) {
203			half_rate_mode = 1;
204			goto retry;
205		}
206	} else {
207		pd->vco_freq = vco_optimal;
208		pd->tx_band_sel = tx_band_sel[vco_optimal_index % 4];
209		pd->vco_ratio = ratio[vco_optimal_index / 4];
210		pd->hsclk_divsel = hs_divsel[vco_optimal_index / 4];
211
212		return 0;
213	}
214
215	return -EINVAL;
216}
217
218static int pll_calculate(unsigned long pix_clk, unsigned long ref_clk,
219			 struct hdmi_8996_phy_pll_reg_cfg *cfg)
220{
221	struct hdmi_8996_post_divider pd;
222	u64 bclk;
223	u64 tmds_clk;
224	u64 dec_start;
225	u64 frac_start;
226	u64 fdata;
227	u32 pll_divisor;
228	u32 rem;
229	u32 cpctrl;
230	u32 rctrl;
231	u32 cctrl;
232	u32 integloop_gain;
233	u32 pll_cmp;
234	int i, ret;
235
236	/* bit clk = 10 * pix_clk */
237	bclk = ((u64)pix_clk) * 10;
238
239	if (bclk > HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD)
240		tmds_clk = pix_clk >> 2;
241	else
242		tmds_clk = pix_clk;
243
244	ret = pll_get_post_div(&pd, bclk);
245	if (ret)
246		return ret;
247
248	dec_start = pd.vco_freq;
249	pll_divisor = 4 * ref_clk;
250	do_div(dec_start, pll_divisor);
251
252	frac_start = pd.vco_freq * (1 << 20);
253
254	rem = do_div(frac_start, pll_divisor);
255	frac_start -= dec_start * (1 << 20);
256	if (rem > (pll_divisor >> 1))
257		frac_start++;
258
259	cpctrl = pll_get_cpctrl(frac_start, ref_clk, false);
260	rctrl = pll_get_rctrl(frac_start, false);
261	cctrl = pll_get_cctrl(frac_start, false);
262	integloop_gain = pll_get_integloop_gain(frac_start, bclk,
263						ref_clk, false);
264
265	fdata = pd.vco_freq;
266	do_div(fdata, pd.vco_ratio);
267
268	pll_cmp = pll_get_pll_cmp(fdata, ref_clk);
269
270	DBG("VCO freq: %llu", pd.vco_freq);
271	DBG("fdata: %llu", fdata);
272	DBG("pix_clk: %lu", pix_clk);
273	DBG("tmds clk: %llu", tmds_clk);
274	DBG("HSCLK_SEL: %d", pd.hsclk_divsel);
275	DBG("DEC_START: %llu", dec_start);
276	DBG("DIV_FRAC_START: %llu", frac_start);
277	DBG("PLL_CPCTRL: %u", cpctrl);
278	DBG("PLL_RCTRL: %u", rctrl);
279	DBG("PLL_CCTRL: %u", cctrl);
280	DBG("INTEGLOOP_GAIN: %u", integloop_gain);
281	DBG("TX_BAND: %d", pd.tx_band_sel);
282	DBG("PLL_CMP: %u", pll_cmp);
283
284	/* Convert these values to register specific values */
285	if (bclk > HDMI_DIG_FREQ_BIT_CLK_THRESHOLD)
286		cfg->com_svs_mode_clk_sel = 1;
287	else
288		cfg->com_svs_mode_clk_sel = 2;
289
290	cfg->com_hsclk_sel = (0x20 | pd.hsclk_divsel);
291	cfg->com_pll_cctrl_mode0 = cctrl;
292	cfg->com_pll_rctrl_mode0 = rctrl;
293	cfg->com_cp_ctrl_mode0 = cpctrl;
294	cfg->com_dec_start_mode0 = dec_start;
295	cfg->com_div_frac_start1_mode0 = (frac_start & 0xff);
296	cfg->com_div_frac_start2_mode0 = ((frac_start & 0xff00) >> 8);
297	cfg->com_div_frac_start3_mode0 = ((frac_start & 0xf0000) >> 16);
298	cfg->com_integloop_gain0_mode0 = (integloop_gain & 0xff);
299	cfg->com_integloop_gain1_mode0 = ((integloop_gain & 0xf00) >> 8);
300	cfg->com_lock_cmp1_mode0 = (pll_cmp & 0xff);
301	cfg->com_lock_cmp2_mode0 = ((pll_cmp & 0xff00) >> 8);
302	cfg->com_lock_cmp3_mode0 = ((pll_cmp & 0x30000) >> 16);
303	cfg->com_lock_cmp_en = 0x0;
304	cfg->com_core_clk_en = 0x2c;
305	cfg->com_coreclk_div = HDMI_CORECLK_DIV;
306	cfg->phy_mode = (bclk > HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD) ? 0x10 : 0x0;
307	cfg->com_vco_tune_ctrl = 0x0;
308
309	cfg->tx_lx_lane_mode[0] =
310		cfg->tx_lx_lane_mode[2] = 0x43;
311
312	cfg->tx_lx_hp_pd_enables[0] =
313		cfg->tx_lx_hp_pd_enables[1] =
314		cfg->tx_lx_hp_pd_enables[2] = 0x0c;
315	cfg->tx_lx_hp_pd_enables[3] = 0x3;
316
317	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++)
318		cfg->tx_lx_tx_band[i] = pd.tx_band_sel + 4;
319
320	if (bclk > HDMI_HIGH_FREQ_BIT_CLK_THRESHOLD) {
321		cfg->tx_lx_tx_drv_lvl[0] =
322			cfg->tx_lx_tx_drv_lvl[1] =
323			cfg->tx_lx_tx_drv_lvl[2] = 0x25;
324		cfg->tx_lx_tx_drv_lvl[3] = 0x22;
325
326		cfg->tx_lx_tx_emp_post1_lvl[0] =
327			cfg->tx_lx_tx_emp_post1_lvl[1] =
328			cfg->tx_lx_tx_emp_post1_lvl[2] = 0x23;
329		cfg->tx_lx_tx_emp_post1_lvl[3] = 0x27;
330
331		cfg->tx_lx_vmode_ctrl1[0] =
332			cfg->tx_lx_vmode_ctrl1[1] =
333			cfg->tx_lx_vmode_ctrl1[2] =
334			cfg->tx_lx_vmode_ctrl1[3] = 0x00;
335
336		cfg->tx_lx_vmode_ctrl2[0] =
337			cfg->tx_lx_vmode_ctrl2[1] =
338			cfg->tx_lx_vmode_ctrl2[2] = 0x0D;
339
340		cfg->tx_lx_vmode_ctrl2[3] = 0x00;
341	} else if (bclk > HDMI_MID_FREQ_BIT_CLK_THRESHOLD) {
342		for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
343			cfg->tx_lx_tx_drv_lvl[i] = 0x25;
344			cfg->tx_lx_tx_emp_post1_lvl[i] = 0x23;
345			cfg->tx_lx_vmode_ctrl1[i] = 0x00;
346		}
347
348		cfg->tx_lx_vmode_ctrl2[0] =
349			cfg->tx_lx_vmode_ctrl2[1] =
350			cfg->tx_lx_vmode_ctrl2[2] = 0x0D;
351		cfg->tx_lx_vmode_ctrl2[3] = 0x00;
352	} else {
353		for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
354			cfg->tx_lx_tx_drv_lvl[i] = 0x20;
355			cfg->tx_lx_tx_emp_post1_lvl[i] = 0x20;
356			cfg->tx_lx_vmode_ctrl1[i] = 0x00;
357			cfg->tx_lx_vmode_ctrl2[i] = 0x0E;
358		}
359	}
360
361	DBG("com_svs_mode_clk_sel = 0x%x", cfg->com_svs_mode_clk_sel);
362	DBG("com_hsclk_sel = 0x%x", cfg->com_hsclk_sel);
363	DBG("com_lock_cmp_en = 0x%x", cfg->com_lock_cmp_en);
364	DBG("com_pll_cctrl_mode0 = 0x%x", cfg->com_pll_cctrl_mode0);
365	DBG("com_pll_rctrl_mode0 = 0x%x", cfg->com_pll_rctrl_mode0);
366	DBG("com_cp_ctrl_mode0 = 0x%x", cfg->com_cp_ctrl_mode0);
367	DBG("com_dec_start_mode0 = 0x%x", cfg->com_dec_start_mode0);
368	DBG("com_div_frac_start1_mode0 = 0x%x", cfg->com_div_frac_start1_mode0);
369	DBG("com_div_frac_start2_mode0 = 0x%x", cfg->com_div_frac_start2_mode0);
370	DBG("com_div_frac_start3_mode0 = 0x%x", cfg->com_div_frac_start3_mode0);
371	DBG("com_integloop_gain0_mode0 = 0x%x", cfg->com_integloop_gain0_mode0);
372	DBG("com_integloop_gain1_mode0 = 0x%x", cfg->com_integloop_gain1_mode0);
373	DBG("com_lock_cmp1_mode0 = 0x%x", cfg->com_lock_cmp1_mode0);
374	DBG("com_lock_cmp2_mode0 = 0x%x", cfg->com_lock_cmp2_mode0);
375	DBG("com_lock_cmp3_mode0 = 0x%x", cfg->com_lock_cmp3_mode0);
376	DBG("com_core_clk_en = 0x%x", cfg->com_core_clk_en);
377	DBG("com_coreclk_div = 0x%x", cfg->com_coreclk_div);
378	DBG("phy_mode = 0x%x", cfg->phy_mode);
379
380	DBG("tx_l0_lane_mode = 0x%x", cfg->tx_lx_lane_mode[0]);
381	DBG("tx_l2_lane_mode = 0x%x", cfg->tx_lx_lane_mode[2]);
382
383	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
384		DBG("tx_l%d_tx_band = 0x%x", i, cfg->tx_lx_tx_band[i]);
385		DBG("tx_l%d_tx_drv_lvl = 0x%x", i, cfg->tx_lx_tx_drv_lvl[i]);
386		DBG("tx_l%d_tx_emp_post1_lvl = 0x%x", i,
387		    cfg->tx_lx_tx_emp_post1_lvl[i]);
388		DBG("tx_l%d_vmode_ctrl1 = 0x%x", i, cfg->tx_lx_vmode_ctrl1[i]);
389		DBG("tx_l%d_vmode_ctrl2 = 0x%x", i, cfg->tx_lx_vmode_ctrl2[i]);
390	}
391
392	return 0;
393}
394
395static int hdmi_8996_pll_set_clk_rate(struct clk_hw *hw, unsigned long rate,
396				      unsigned long parent_rate)
397{
398	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
399	struct hdmi_phy *phy = pll_get_phy(pll);
400	struct hdmi_8996_phy_pll_reg_cfg cfg;
401	int i, ret;
402
403	memset(&cfg, 0x00, sizeof(cfg));
404
405	ret = pll_calculate(rate, parent_rate, &cfg);
406	if (ret) {
407		DRM_ERROR("PLL calculation failed\n");
408		return ret;
409	}
410
411	/* Initially shut down PHY */
412	DBG("Disabling PHY");
413	hdmi_phy_write(phy, REG_HDMI_8996_PHY_PD_CTL, 0x0);
414	udelay(500);
415
416	/* Power up sequence */
417	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BG_CTRL, 0x04);
418
419	hdmi_phy_write(phy, REG_HDMI_8996_PHY_PD_CTL, 0x1);
420	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_RESETSM_CNTRL, 0x20);
421	hdmi_phy_write(phy, REG_HDMI_8996_PHY_TX0_TX1_LANE_CTL, 0x0F);
422	hdmi_phy_write(phy, REG_HDMI_8996_PHY_TX2_TX3_LANE_CTL, 0x0F);
423
424	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
425		hdmi_tx_chan_write(pll, i,
426				   REG_HDMI_PHY_QSERDES_TX_LX_CLKBUF_ENABLE,
427				   0x03);
428		hdmi_tx_chan_write(pll, i,
429				   REG_HDMI_PHY_QSERDES_TX_LX_TX_BAND,
430				   cfg.tx_lx_tx_band[i]);
431		hdmi_tx_chan_write(pll, i,
432				   REG_HDMI_PHY_QSERDES_TX_LX_RESET_TSYNC_EN,
433				   0x03);
434	}
435
436	hdmi_tx_chan_write(pll, 0, REG_HDMI_PHY_QSERDES_TX_LX_LANE_MODE,
437			   cfg.tx_lx_lane_mode[0]);
438	hdmi_tx_chan_write(pll, 2, REG_HDMI_PHY_QSERDES_TX_LX_LANE_MODE,
439			   cfg.tx_lx_lane_mode[2]);
440
441	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SYSCLK_BUF_ENABLE, 0x1E);
442	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BIAS_EN_CLKBUFLR_EN, 0x07);
443	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SYSCLK_EN_SEL, 0x37);
444	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SYS_CLK_CTRL, 0x02);
445	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CLK_ENABLE1, 0x0E);
446
447	/* Bypass VCO calibration */
448	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SVS_MODE_CLK_SEL,
449		       cfg.com_svs_mode_clk_sel);
450
451	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BG_TRIM, 0x0F);
452	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_PLL_IVCO, 0x0F);
453	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_VCO_TUNE_CTRL,
454		       cfg.com_vco_tune_ctrl);
455
456	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_BG_CTRL, 0x06);
457
458	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CLK_SELECT, 0x30);
459	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_HSCLK_SEL,
460		       cfg.com_hsclk_sel);
461	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP_EN,
462		       cfg.com_lock_cmp_en);
463
464	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_PLL_CCTRL_MODE0,
465		       cfg.com_pll_cctrl_mode0);
466	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_PLL_RCTRL_MODE0,
467		       cfg.com_pll_rctrl_mode0);
468	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CP_CTRL_MODE0,
469		       cfg.com_cp_ctrl_mode0);
470	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DEC_START_MODE0,
471		       cfg.com_dec_start_mode0);
472	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DIV_FRAC_START1_MODE0,
473		       cfg.com_div_frac_start1_mode0);
474	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DIV_FRAC_START2_MODE0,
475		       cfg.com_div_frac_start2_mode0);
476	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_DIV_FRAC_START3_MODE0,
477		       cfg.com_div_frac_start3_mode0);
478
479	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_INTEGLOOP_GAIN0_MODE0,
480		       cfg.com_integloop_gain0_mode0);
481	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_INTEGLOOP_GAIN1_MODE0,
482		       cfg.com_integloop_gain1_mode0);
483
484	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP1_MODE0,
485		       cfg.com_lock_cmp1_mode0);
486	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP2_MODE0,
487		       cfg.com_lock_cmp2_mode0);
488	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP3_MODE0,
489		       cfg.com_lock_cmp3_mode0);
490
491	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_VCO_TUNE_MAP, 0x00);
492	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CORE_CLK_EN,
493		       cfg.com_core_clk_en);
494	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CORECLK_DIV,
495		       cfg.com_coreclk_div);
496	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_CMN_CONFIG, 0x02);
497
498	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_RESCODE_DIV_NUM, 0x15);
499
500	/* TX lanes setup (TX 0/1/2/3) */
501	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
502		hdmi_tx_chan_write(pll, i,
503				   REG_HDMI_PHY_QSERDES_TX_LX_TX_DRV_LVL,
504				   cfg.tx_lx_tx_drv_lvl[i]);
505		hdmi_tx_chan_write(pll, i,
506				   REG_HDMI_PHY_QSERDES_TX_LX_TX_EMP_POST1_LVL,
507				   cfg.tx_lx_tx_emp_post1_lvl[i]);
508		hdmi_tx_chan_write(pll, i,
509				   REG_HDMI_PHY_QSERDES_TX_LX_VMODE_CTRL1,
510				   cfg.tx_lx_vmode_ctrl1[i]);
511		hdmi_tx_chan_write(pll, i,
512				   REG_HDMI_PHY_QSERDES_TX_LX_VMODE_CTRL2,
513				   cfg.tx_lx_vmode_ctrl2[i]);
514		hdmi_tx_chan_write(pll, i,
515				   REG_HDMI_PHY_QSERDES_TX_LX_TX_DRV_LVL_OFFSET,
516				   0x00);
517		hdmi_tx_chan_write(pll, i,
518			REG_HDMI_PHY_QSERDES_TX_LX_RES_CODE_LANE_OFFSET,
519			0x00);
520		hdmi_tx_chan_write(pll, i,
521			REG_HDMI_PHY_QSERDES_TX_LX_TRAN_DRVR_EMP_EN,
522			0x03);
523		hdmi_tx_chan_write(pll, i,
524			REG_HDMI_PHY_QSERDES_TX_LX_PARRATE_REC_DETECT_IDLE_EN,
525			0x40);
526		hdmi_tx_chan_write(pll, i,
527				   REG_HDMI_PHY_QSERDES_TX_LX_HP_PD_ENABLES,
528				   cfg.tx_lx_hp_pd_enables[i]);
529	}
530
531	hdmi_phy_write(phy, REG_HDMI_8996_PHY_MODE, cfg.phy_mode);
532	hdmi_phy_write(phy, REG_HDMI_8996_PHY_PD_CTL, 0x1F);
533
534	/*
535	 * Ensure that vco configuration gets flushed to hardware before
536	 * enabling the PLL
537	 */
538	wmb();
539
540	return 0;
541}
542
543static int hdmi_8996_phy_ready_status(struct hdmi_phy *phy)
544{
545	u32 nb_tries = HDMI_PLL_POLL_MAX_READS;
546	unsigned long timeout = HDMI_PLL_POLL_TIMEOUT_US;
547	u32 status;
548	int phy_ready = 0;
549
550	DBG("Waiting for PHY ready");
551
552	while (nb_tries--) {
553		status = hdmi_phy_read(phy, REG_HDMI_8996_PHY_STATUS);
554		phy_ready = status & BIT(0);
555
556		if (phy_ready)
557			break;
558
559		udelay(timeout);
560	}
561
562	DBG("PHY is %sready", phy_ready ? "" : "*not* ");
563
564	return phy_ready;
565}
566
567static int hdmi_8996_pll_lock_status(struct hdmi_pll_8996 *pll)
568{
569	u32 status;
570	int nb_tries = HDMI_PLL_POLL_MAX_READS;
571	unsigned long timeout = HDMI_PLL_POLL_TIMEOUT_US;
572	int pll_locked = 0;
573
574	DBG("Waiting for PLL lock");
575
576	while (nb_tries--) {
577		status = hdmi_pll_read(pll,
578				       REG_HDMI_PHY_QSERDES_COM_C_READY_STATUS);
579		pll_locked = status & BIT(0);
580
581		if (pll_locked)
582			break;
583
584		udelay(timeout);
585	}
586
587	DBG("HDMI PLL is %slocked", pll_locked ? "" : "*not* ");
588
589	return pll_locked;
590}
591
592static int hdmi_8996_pll_prepare(struct clk_hw *hw)
593{
594	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
595	struct hdmi_phy *phy = pll_get_phy(pll);
596	int i, ret = 0;
597
598	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x1);
599	udelay(100);
600
601	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x19);
602	udelay(100);
603
604	ret = hdmi_8996_pll_lock_status(pll);
605	if (!ret)
606		return ret;
607
608	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++)
609		hdmi_tx_chan_write(pll, i,
610			REG_HDMI_PHY_QSERDES_TX_LX_HIGHZ_TRANSCEIVEREN_BIAS_DRVR_EN,
611			0x6F);
612
613	/* Disable SSC */
614	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_PER1, 0x0);
615	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_PER2, 0x0);
616	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_STEP_SIZE1, 0x0);
617	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_STEP_SIZE2, 0x0);
618	hdmi_pll_write(pll, REG_HDMI_PHY_QSERDES_COM_SSC_EN_CENTER, 0x2);
619
620	ret = hdmi_8996_phy_ready_status(phy);
621	if (!ret)
622		return ret;
623
624	/* Restart the retiming buffer */
625	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x18);
626	udelay(1);
627	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x19);
628
629	return 0;
630}
631
632static long hdmi_8996_pll_round_rate(struct clk_hw *hw,
633				     unsigned long rate,
634				     unsigned long *parent_rate)
635{
636	if (rate < HDMI_PCLK_MIN_FREQ)
637		return HDMI_PCLK_MIN_FREQ;
638	else if (rate > HDMI_PCLK_MAX_FREQ)
639		return HDMI_PCLK_MAX_FREQ;
640	else
641		return rate;
642}
643
644static unsigned long hdmi_8996_pll_recalc_rate(struct clk_hw *hw,
645					       unsigned long parent_rate)
646{
647	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
648	u64 fdata;
649	u32 cmp1, cmp2, cmp3, pll_cmp;
650
651	cmp1 = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP1_MODE0);
652	cmp2 = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP2_MODE0);
653	cmp3 = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_LOCK_CMP3_MODE0);
654
655	pll_cmp = cmp1 | (cmp2 << 8) | (cmp3 << 16);
656
657	fdata = pll_cmp_to_fdata(pll_cmp + 1, parent_rate);
658
659	do_div(fdata, 10);
660
661	return fdata;
662}
663
664static void hdmi_8996_pll_unprepare(struct clk_hw *hw)
665{
666	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
667	struct hdmi_phy *phy = pll_get_phy(pll);
668
669	hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x6);
670	usleep_range(100, 150);
671}
672
673static int hdmi_8996_pll_is_enabled(struct clk_hw *hw)
674{
675	struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
676	u32 status;
677	int pll_locked;
678
679	status = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_C_READY_STATUS);
680	pll_locked = status & BIT(0);
681
682	return pll_locked;
683}
684
685static const struct clk_ops hdmi_8996_pll_ops = {
686	.set_rate = hdmi_8996_pll_set_clk_rate,
687	.round_rate = hdmi_8996_pll_round_rate,
688	.recalc_rate = hdmi_8996_pll_recalc_rate,
689	.prepare = hdmi_8996_pll_prepare,
690	.unprepare = hdmi_8996_pll_unprepare,
691	.is_enabled = hdmi_8996_pll_is_enabled,
692};
693
694static const struct clk_init_data pll_init = {
 
 
 
 
695	.name = "hdmipll",
696	.ops = &hdmi_8996_pll_ops,
697	.parent_data = (const struct clk_parent_data[]){
698		{ .fw_name = "xo", .name = "xo_board" },
699	},
700	.num_parents = 1,
701	.flags = CLK_IGNORE_UNUSED,
702};
703
704int msm_hdmi_pll_8996_init(struct platform_device *pdev)
705{
706	struct device *dev = &pdev->dev;
707	struct hdmi_pll_8996 *pll;
708	int i, ret;
 
709
710	pll = devm_kzalloc(dev, sizeof(*pll), GFP_KERNEL);
711	if (!pll)
712		return -ENOMEM;
713
714	pll->pdev = pdev;
715
716	pll->mmio_qserdes_com = msm_ioremap(pdev, "hdmi_pll");
717	if (IS_ERR(pll->mmio_qserdes_com)) {
718		DRM_DEV_ERROR(dev, "failed to map pll base\n");
719		return -ENOMEM;
720	}
721
722	for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
723		char name[32];
724
725		snprintf(name, sizeof(name), "hdmi_tx_l%d", i);
 
726
727		pll->mmio_qserdes_tx[i] = msm_ioremap(pdev, name);
728		if (IS_ERR(pll->mmio_qserdes_tx[i])) {
729			DRM_DEV_ERROR(dev, "failed to map pll base\n");
730			return -ENOMEM;
731		}
732	}
733	pll->clk_hw.init = &pll_init;
734
735	ret = devm_clk_hw_register(dev, &pll->clk_hw);
736	if (ret) {
737		DRM_DEV_ERROR(dev, "failed to register pll clock\n");
738		return ret;
739	}
740
741	ret = devm_of_clk_add_hw_provider(dev, of_clk_hw_simple_get, &pll->clk_hw);
742	if (ret) {
743		DRM_DEV_ERROR(dev, "%s: failed to register clk provider: %d\n", __func__, ret);
744		return ret;
745	}
746
747	return 0;
748}
749
750static const char * const hdmi_phy_8996_reg_names[] = {
751	"vddio",
752	"vcca",
753};
754
755static const char * const hdmi_phy_8996_clk_names[] = {
756	"iface", "ref",
 
 
757};
758
759const struct hdmi_phy_cfg msm_hdmi_phy_8996_cfg = {
760	.type = MSM_HDMI_PHY_8996,
761	.reg_names = hdmi_phy_8996_reg_names,
762	.num_regs = ARRAY_SIZE(hdmi_phy_8996_reg_names),
763	.clk_names = hdmi_phy_8996_clk_names,
764	.num_clks = ARRAY_SIZE(hdmi_phy_8996_clk_names),
765};