GNU Linux-libre 4.14.290-gnu1
[releases.git] / drivers / gpu / drm / msm / hdmi / hdmi_phy_8996.c
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
36 struct 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
48 struct 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
80 struct 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
88 static inline struct hdmi_phy *pll_get_phy(struct hdmi_pll_8996 *pll)
89 {
90         return platform_get_drvdata(pll->pdev);
91 }
92
93 static 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
99 static inline u32 hdmi_pll_read(struct hdmi_pll_8996 *pll, int offset)
100 {
101         return msm_readl(pll->mmio_qserdes_com + offset);
102 }
103
104 static 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
110 static 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
119 static 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
127 static 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
135 static 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
151 static 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
164 static 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
173 static 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
184 retry:
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
225 static 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
402 static 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
550 static 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
574 static 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
599 static 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
639 static 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
651 static 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
671 static void hdmi_8996_pll_unprepare(struct clk_hw *hw)
672 {
673         struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
674         struct hdmi_phy *phy = pll_get_phy(pll);
675
676         hdmi_phy_write(phy, REG_HDMI_8996_PHY_CFG, 0x6);
677         usleep_range(100, 150);
678 }
679
680 static int hdmi_8996_pll_is_enabled(struct clk_hw *hw)
681 {
682         struct hdmi_pll_8996 *pll = hw_clk_to_pll(hw);
683         u32 status;
684         int pll_locked;
685
686         status = hdmi_pll_read(pll, REG_HDMI_PHY_QSERDES_COM_C_READY_STATUS);
687         pll_locked = status & BIT(0);
688
689         return pll_locked;
690 }
691
692 static struct clk_ops hdmi_8996_pll_ops = {
693         .set_rate = hdmi_8996_pll_set_clk_rate,
694         .round_rate = hdmi_8996_pll_round_rate,
695         .recalc_rate = hdmi_8996_pll_recalc_rate,
696         .prepare = hdmi_8996_pll_prepare,
697         .unprepare = hdmi_8996_pll_unprepare,
698         .is_enabled = hdmi_8996_pll_is_enabled,
699 };
700
701 static const char * const hdmi_pll_parents[] = {
702         "xo",
703 };
704
705 static struct clk_init_data pll_init = {
706         .name = "hdmipll",
707         .ops = &hdmi_8996_pll_ops,
708         .parent_names = hdmi_pll_parents,
709         .num_parents = ARRAY_SIZE(hdmi_pll_parents),
710         .flags = CLK_IGNORE_UNUSED,
711 };
712
713 int msm_hdmi_pll_8996_init(struct platform_device *pdev)
714 {
715         struct device *dev = &pdev->dev;
716         struct hdmi_pll_8996 *pll;
717         struct clk *clk;
718         int i;
719
720         pll = devm_kzalloc(dev, sizeof(*pll), GFP_KERNEL);
721         if (!pll)
722                 return -ENOMEM;
723
724         pll->pdev = pdev;
725
726         pll->mmio_qserdes_com = msm_ioremap(pdev, "hdmi_pll", "HDMI_PLL");
727         if (IS_ERR(pll->mmio_qserdes_com)) {
728                 dev_err(dev, "failed to map pll base\n");
729                 return -ENOMEM;
730         }
731
732         for (i = 0; i < HDMI_NUM_TX_CHANNEL; i++) {
733                 char name[32], label[32];
734
735                 snprintf(name, sizeof(name), "hdmi_tx_l%d", i);
736                 snprintf(label, sizeof(label), "HDMI_TX_L%d", i);
737
738                 pll->mmio_qserdes_tx[i] = msm_ioremap(pdev, name, label);
739                 if (IS_ERR(pll->mmio_qserdes_tx[i])) {
740                         dev_err(dev, "failed to map pll base\n");
741                         return -ENOMEM;
742                 }
743         }
744         pll->clk_hw.init = &pll_init;
745
746         clk = devm_clk_register(dev, &pll->clk_hw);
747         if (IS_ERR(clk)) {
748                 dev_err(dev, "failed to register pll clock\n");
749                 return -EINVAL;
750         }
751
752         return 0;
753 }
754
755 static const char * const hdmi_phy_8996_reg_names[] = {
756         "vddio",
757         "vcca",
758 };
759
760 static const char * const hdmi_phy_8996_clk_names[] = {
761         "mmagic_iface_clk",
762         "iface_clk",
763         "ref_clk",
764 };
765
766 const struct hdmi_phy_cfg msm_hdmi_phy_8996_cfg = {
767         .type = MSM_HDMI_PHY_8996,
768         .reg_names = hdmi_phy_8996_reg_names,
769         .num_regs = ARRAY_SIZE(hdmi_phy_8996_reg_names),
770         .clk_names = hdmi_phy_8996_clk_names,
771         .num_clks = ARRAY_SIZE(hdmi_phy_8996_clk_names),
772 };