xref: /aosp_15_r20/external/coreboot/src/soc/qualcomm/common/usb/qmpv3_usb_phy.c (revision b9411a12aaaa7e1e6a6fb7c5e057f44ee179a49c)
1 /* SPDX-License-Identifier: GPL-2.0-only */
2 
3 #include <console/console.h>
4 #include <timer.h>
5 #include <soc/usb/qmp_usb_phy.h>
6 #include <soc/addressmap.h>
7 
8 /* Only for QMP V3 PHY - QSERDES COM registers */
9 struct usb3_phy_qserdes_com_reg_layout {
10 	u8 _reserved1[16];
11 	u32 com_ssc_en_center;
12 	u32 com_ssc_adj_per1;
13 	u32 com_ssc_adj_per2;
14 	u32 com_ssc_per1;
15 	u32 com_ssc_per2;
16 	u32 com_ssc_step_size1;
17 	u32 com_ssc_step_size2;
18 	u8 _reserved2[8];
19 	u32 com_bias_en_clkbuflr_en;
20 	u32 com_sys_clk_enable1;
21 	u32 com_sys_clk_ctrl;
22 	u32 com_sysclk_buf_enable;
23 	u32 com_pll_en;
24 	u32 com_pll_ivco;
25 	u8 _reserved3[20];
26 	u32 com_cp_ctrl_mode0;
27 	u8 _reserved4[4];
28 	u32 com_pll_rctrl_mode0;
29 	u8 _reserved5[4];
30 	u32 com_pll_cctrl_mode0;
31 	u8 _reserved6[12];
32 	u32 com_sysclk_en_sel;
33 	u8 _reserved7[8];
34 	u32 com_resetsm_ctrl2;
35 	u32 com_lock_cmp_en;
36 	u32 com_lock_cmp_cfg;
37 	u32 com_lock_cmp1_mode0;
38 	u32 com_lock_cmp2_mode0;
39 	u32 com_lock_cmp3_mode0;
40 	u8 _reserved8[12];
41 	u32 com_dec_start_mode0;
42 	u8 _reserved9[4];
43 	u32 com_div_frac_start1_mode0;
44 	u32 com_div_frac_start2_mode0;
45 	u32 com_div_frac_start3_mode0;
46 	u8 _reserved10[20];
47 	u32 com_integloop_gain0_mode0;
48 	u32 com_integloop_gain1_mode0;
49 	u8 _reserved11[16];
50 	u32 com_vco_tune_map;
51 	u32 com_vco_tune1_mode0;
52 	u32 com_vco_tune2_mode0;
53 	u8 _reserved12[60];
54 	u32 com_clk_select;
55 	u32 com_hsclk_sel;
56 	u8 _reserved13[8];
57 	u32 com_coreclk_div_mode0;
58 	u8 _reserved14[8];
59 	u32 com_core_clk_en;
60 	u32 com_c_ready_status;
61 	u32 com_cmn_config;
62 	u32 com_cmn_rate_override;
63 	u32 com_svs_mode_clk_sel;
64 };
65 check_member(usb3_phy_qserdes_com_reg_layout, com_ssc_en_center, 0x010);
66 check_member(usb3_phy_qserdes_com_reg_layout, com_ssc_adj_per1, 0x014);
67 check_member(usb3_phy_qserdes_com_reg_layout, com_ssc_adj_per2, 0x018);
68 check_member(usb3_phy_qserdes_com_reg_layout, com_ssc_per1, 0x01c);
69 check_member(usb3_phy_qserdes_com_reg_layout, com_ssc_per2, 0x020);
70 check_member(usb3_phy_qserdes_com_reg_layout, com_bias_en_clkbuflr_en, 0x034);
71 check_member(usb3_phy_qserdes_com_reg_layout, com_pll_ivco, 0x048);
72 check_member(usb3_phy_qserdes_com_reg_layout, com_cp_ctrl_mode0, 0x060);
73 check_member(usb3_phy_qserdes_com_reg_layout, com_sysclk_en_sel, 0x080);
74 check_member(usb3_phy_qserdes_com_reg_layout, com_resetsm_ctrl2, 0x08c);
75 check_member(usb3_phy_qserdes_com_reg_layout, com_dec_start_mode0, 0x0b0);
76 check_member(usb3_phy_qserdes_com_reg_layout, com_div_frac_start1_mode0, 0x0b8);
77 check_member(usb3_phy_qserdes_com_reg_layout, com_integloop_gain0_mode0, 0x0d8);
78 check_member(usb3_phy_qserdes_com_reg_layout, com_vco_tune_map, 0x0f0);
79 check_member(usb3_phy_qserdes_com_reg_layout, com_clk_select, 0x138);
80 check_member(usb3_phy_qserdes_com_reg_layout, com_coreclk_div_mode0, 0x148);
81 check_member(usb3_phy_qserdes_com_reg_layout, com_core_clk_en, 0x154);
82 check_member(usb3_phy_qserdes_com_reg_layout, com_svs_mode_clk_sel, 0x164);
83 
84 /* Only for QMP V3 PHY - TX registers */
85 struct usb3_phy_qserdes_tx_reg_layout {
86 	u8 _reserved1[68];
87 	u32 tx_res_code_lane_offset_tx;
88 	u32 tx_res_code_lane_offset_rx;
89 	u8 _reserved2[20];
90 	u32 tx_highz_drvr_en;
91 	u8 _reserved3[40];
92 	u32 tx_lane_mode_1;
93 	u8 _reserved4[20];
94 	u32 tx_rcv_detect_lvl_2;
95 };
96 check_member(usb3_phy_qserdes_tx_reg_layout, tx_res_code_lane_offset_tx, 0x044);
97 check_member(usb3_phy_qserdes_tx_reg_layout, tx_res_code_lane_offset_rx, 0x048);
98 check_member(usb3_phy_qserdes_tx_reg_layout, tx_highz_drvr_en, 0x060);
99 check_member(usb3_phy_qserdes_tx_reg_layout, tx_lane_mode_1, 0x08c);
100 check_member(usb3_phy_qserdes_tx_reg_layout, tx_rcv_detect_lvl_2, 0x0a4);
101 
102 /* Only for QMP V3 PHY - RX registers */
103 struct usb3_phy_qserdes_rx_reg_layout {
104 	u8 _reserved1[8];
105 	u32 rx_ucdr_fo_gain;
106 	u32 rx_ucdr_so_gain_half;
107 	u8 _reserved2[32];
108 	u32 rx_ucdr_fastlock_fo_gain;
109 	u32 rx_ucdr_so_saturtn_and_en;
110 	u8 _reserved3[12];
111 	u32 rx_ucdr_pi_cntrls;
112 	u8 _reserved4[120];
113 	u32 rx_vga_cal_ctrl2;
114 	u8 _reserved5[16];
115 	u32 rx_rx_equ_adap_ctrl2;
116 	u32 rx_rx_equ_adap_ctrl3;
117 	u32 rx_rx_equ_adap_ctrl4;
118 	u8 _reserved6[24];
119 	u32 rx_rx_eq_offset_adap_ctrl1;
120 	u32 rx_rx_offset_adap_ctrl2;
121 	u32 rx_sigdet_enables;
122 	u32 rx_sigdet_ctrl;
123 	u8 _reserved7[4];
124 	u32 rx_sigdet_deglitch_ctrl;
125 	u32 rx_rx_band;
126 	u8 _reserved8[80];
127 	u32 rx_rx_mode_00;
128 };
129 check_member(usb3_phy_qserdes_rx_reg_layout, rx_ucdr_fo_gain, 0x008);
130 check_member(usb3_phy_qserdes_rx_reg_layout, rx_ucdr_so_gain_half, 0x00c);
131 check_member(usb3_phy_qserdes_rx_reg_layout, rx_ucdr_fastlock_fo_gain, 0x030);
132 check_member(usb3_phy_qserdes_rx_reg_layout, rx_ucdr_so_saturtn_and_en, 0x034);
133 check_member(usb3_phy_qserdes_rx_reg_layout, rx_ucdr_pi_cntrls, 0x044);
134 check_member(usb3_phy_qserdes_rx_reg_layout, rx_vga_cal_ctrl2, 0x0c0);
135 check_member(usb3_phy_qserdes_rx_reg_layout, rx_rx_equ_adap_ctrl2, 0x0d4);
136 check_member(usb3_phy_qserdes_rx_reg_layout, rx_rx_equ_adap_ctrl3, 0x0d8);
137 check_member(usb3_phy_qserdes_rx_reg_layout, rx_rx_equ_adap_ctrl4, 0x0dc);
138 check_member(usb3_phy_qserdes_rx_reg_layout, rx_rx_eq_offset_adap_ctrl1, 0x0f8);
139 check_member(usb3_phy_qserdes_rx_reg_layout, rx_rx_offset_adap_ctrl2, 0x0fc);
140 check_member(usb3_phy_qserdes_rx_reg_layout, rx_sigdet_enables, 0x100);
141 check_member(usb3_phy_qserdes_rx_reg_layout, rx_sigdet_ctrl, 0x104);
142 check_member(usb3_phy_qserdes_rx_reg_layout, rx_sigdet_deglitch_ctrl, 0x10c);
143 check_member(usb3_phy_qserdes_rx_reg_layout, rx_rx_band, 0x110);
144 check_member(usb3_phy_qserdes_rx_reg_layout, rx_rx_mode_00, 0x164);
145 
146 /* Only for QMP V3 PHY - PCS registers */
147 struct usb3_phy_pcs_reg_layout {
148 	u32 pcs_sw_reset;
149 	u32 pcs_power_down_control;
150 	u32 pcs_start_control;
151 	u32 pcs_txmgn_v0;
152 	u32 pcs_txmgn_v1;
153 	u32 pcs_txmgn_v2;
154 	u32 pcs_txmgn_v3;
155 	u32 pcs_txmgn_v4;
156 	u32 pcs_txmgn_ls;
157 	u32 pcs_txdeemph_m6db_v0;
158 	u32 pcs_txdeemph_m3p5db_v0;
159 	u32 pcs_txdeemph_m6db_v1;
160 	u32 pcs_txdeemph_m3p5db_v1;
161 	u32 pcs_txdeemph_m6db_v2;
162 	u32 pcs_txdeemph_m3p5db_v2;
163 	u32 pcs_txdeemph_m6db_v3;
164 	u32 pcs_txdeemph_m3p5db_v3;
165 	u32 pcs_txdeemph_m6db_v4;
166 	u32 pcs_txdeemph_m3p5db_v4;
167 	u32 pcs_txdeemph_m6db_ls;
168 	u32 pcs_txdeemph_m3p5db_ls;
169 	u8 _reserved1[8];
170 	u32 pcs_rate_slew_cntrl;
171 	u8 _reserved2[4];
172 	u32 pcs_power_state_config2;
173 	u8 _reserved3[8];
174 	u32 pcs_rcvr_dtct_dly_p1u2_l;
175 	u32 pcs_rcvr_dtct_dly_p1u2_h;
176 	u32 pcs_rcvr_dtct_dly_u3_l;
177 	u32 pcs_rcvr_dtct_dly_u3_h;
178 	u32 pcs_lock_detect_config1;
179 	u32 pcs_lock_detect_config2;
180 	u32 pcs_lock_detect_config3;
181 	u32 pcs_tsync_rsync_time;
182 	u8 _reserved4[16];
183 	u32 pcs_pwrup_reset_dly_time_auxclk;
184 	u8 _reserved5[12];
185 	u32 pcs_lfps_ecstart_eqtlock;
186 	u8 _reserved6[4];
187 	u32 pcs_rxeqtraining_wait_time;
188 	u32 pcs_rxeqtraining_run_time;
189 	u8 _reserved7[4];
190 	u32 pcs_fll_ctrl1;
191 	u32 pcs_fll_ctrl2;
192 	u32 pcs_fll_cnt_val_l;
193 	u32 pcs_fll_cnt_val_h_tol;
194 	u32 pcs_fll_man_code;
195 	u32 pcs_autonomous_mode_ctrl;
196 	u8 _reserved8[152];
197 	u32 pcs_ready_status;
198 	u8 _reserved9[96];
199 	u32 pcs_rx_sigdet_lvl;
200 	u8 _reserved10[48];
201 	u32 pcs_refgen_req_config1;
202 	u32 pcs_refgen_req_config2;
203 };
204 check_member(usb3_phy_pcs_reg_layout, pcs_sw_reset, 0x000);
205 check_member(usb3_phy_pcs_reg_layout, pcs_txmgn_v0, 0x00c);
206 check_member(usb3_phy_pcs_reg_layout, pcs_txmgn_v1, 0x010);
207 check_member(usb3_phy_pcs_reg_layout, pcs_txmgn_v2, 0x014);
208 check_member(usb3_phy_pcs_reg_layout, pcs_txmgn_v3, 0x018);
209 check_member(usb3_phy_pcs_reg_layout, pcs_txmgn_v4, 0x01c);
210 check_member(usb3_phy_pcs_reg_layout, pcs_txmgn_ls, 0x020);
211 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m6db_v0, 0x024);
212 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m3p5db_v0, 0x028);
213 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m6db_v1, 0x02c);
214 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m3p5db_v1, 0x030);
215 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m6db_v2, 0x034);
216 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m3p5db_v2, 0x038);
217 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m6db_v3, 0x03c);
218 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m3p5db_v3, 0x040);
219 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m6db_v4, 0x044);
220 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m3p5db_v4, 0x048);
221 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m6db_ls, 0x04c);
222 check_member(usb3_phy_pcs_reg_layout, pcs_txdeemph_m3p5db_ls, 0x050);
223 check_member(usb3_phy_pcs_reg_layout, pcs_rate_slew_cntrl, 0x05c);
224 check_member(usb3_phy_pcs_reg_layout, pcs_power_state_config2, 0x064);
225 check_member(usb3_phy_pcs_reg_layout, pcs_rcvr_dtct_dly_p1u2_l, 0x070);
226 check_member(usb3_phy_pcs_reg_layout, pcs_rcvr_dtct_dly_p1u2_h, 0x074);
227 check_member(usb3_phy_pcs_reg_layout, pcs_rcvr_dtct_dly_u3_l, 0x078);
228 check_member(usb3_phy_pcs_reg_layout, pcs_rcvr_dtct_dly_u3_h, 0x07c);
229 check_member(usb3_phy_pcs_reg_layout, pcs_lock_detect_config1, 0x080);
230 check_member(usb3_phy_pcs_reg_layout, pcs_lock_detect_config2, 0x084);
231 check_member(usb3_phy_pcs_reg_layout, pcs_lock_detect_config3, 0x088);
232 check_member(usb3_phy_pcs_reg_layout, pcs_pwrup_reset_dly_time_auxclk, 0x0a0);
233 check_member(usb3_phy_pcs_reg_layout, pcs_rxeqtraining_wait_time, 0x0b8);
234 check_member(usb3_phy_pcs_reg_layout, pcs_fll_cnt_val_h_tol, 0x0d0);
235 check_member(usb3_phy_pcs_reg_layout, pcs_autonomous_mode_ctrl, 0x0d8);
236 check_member(usb3_phy_pcs_reg_layout, pcs_ready_status, 0x174);
237 check_member(usb3_phy_pcs_reg_layout, pcs_refgen_req_config2, 0x210);
238 
239 static struct usb3_phy_qserdes_com_reg_layout *const qserdes_com_reg_layout =
240 	(void *)QMP_PHY_QSERDES_COM_REG_BASE;
241 static struct usb3_phy_qserdes_tx_reg_layout *const qserdes_tx_reg_layout =
242 	(void *)QMP_PHY_QSERDES_TX_REG_BASE;
243 static struct usb3_phy_qserdes_rx_reg_layout *const qserdes_rx_reg_layout =
244 	(void *)QMP_PHY_QSERDES_RX_REG_BASE;
245 static struct usb3_phy_pcs_reg_layout *const pcs_reg_layout =
246 	(void *)QMP_PHY_PCS_REG_BASE;
247 
248 
249 static const struct qmp_phy_init_tbl qmp_v3_usb3_serdes_tbl[] = {
250 	{&qserdes_com_reg_layout->com_pll_ivco, 0x07},
251 	{&qserdes_com_reg_layout->com_sysclk_en_sel, 0x14},
252 	{&qserdes_com_reg_layout->com_bias_en_clkbuflr_en, 0x08},
253 	{&qserdes_com_reg_layout->com_clk_select, 0x30},
254 	{&qserdes_com_reg_layout->com_sys_clk_ctrl, 0x02},
255 	{&qserdes_com_reg_layout->com_resetsm_ctrl2, 0x08},
256 	{&qserdes_com_reg_layout->com_cmn_config, 0x16},
257 	{&qserdes_com_reg_layout->com_svs_mode_clk_sel, 0x01},
258 	{&qserdes_com_reg_layout->com_hsclk_sel, 0x80},
259 	{&qserdes_com_reg_layout->com_dec_start_mode0, 0x82},
260 	{&qserdes_com_reg_layout->com_div_frac_start1_mode0, 0xab},
261 	{&qserdes_com_reg_layout->com_div_frac_start2_mode0, 0xea},
262 	{&qserdes_com_reg_layout->com_div_frac_start3_mode0, 0x02},
263 	{&qserdes_com_reg_layout->com_cp_ctrl_mode0, 0x06},
264 	{&qserdes_com_reg_layout->com_pll_rctrl_mode0, 0x16},
265 	{&qserdes_com_reg_layout->com_pll_cctrl_mode0, 0x36},
266 	{&qserdes_com_reg_layout->com_integloop_gain1_mode0, 0x00},
267 	{&qserdes_com_reg_layout->com_integloop_gain0_mode0, 0x3f},
268 	{&qserdes_com_reg_layout->com_vco_tune2_mode0, 0x01},
269 	{&qserdes_com_reg_layout->com_vco_tune1_mode0, 0xc9},
270 	{&qserdes_com_reg_layout->com_coreclk_div_mode0, 0x0a},
271 	{&qserdes_com_reg_layout->com_lock_cmp3_mode0, 0x00},
272 	{&qserdes_com_reg_layout->com_lock_cmp2_mode0, 0x34},
273 	{&qserdes_com_reg_layout->com_lock_cmp1_mode0, 0x15},
274 	{&qserdes_com_reg_layout->com_lock_cmp_en, 0x04},
275 	{&qserdes_com_reg_layout->com_core_clk_en, 0x00},
276 	{&qserdes_com_reg_layout->com_lock_cmp_cfg, 0x00},
277 	{&qserdes_com_reg_layout->com_vco_tune_map, 0x00},
278 	{&qserdes_com_reg_layout->com_sysclk_buf_enable, 0x0a},
279 	{&qserdes_com_reg_layout->com_ssc_en_center, 0x01},
280 	{&qserdes_com_reg_layout->com_ssc_per1, 0x31},
281 	{&qserdes_com_reg_layout->com_ssc_per2, 0x01},
282 	{&qserdes_com_reg_layout->com_ssc_adj_per1, 0x00},
283 	{&qserdes_com_reg_layout->com_ssc_adj_per2, 0x00},
284 	{&qserdes_com_reg_layout->com_ssc_step_size1, 0x85},
285 	{&qserdes_com_reg_layout->com_ssc_step_size2, 0x07},
286 };
287 
288 static const struct qmp_phy_init_tbl qmp_v3_usb3_tx_tbl[] = {
289 	{&qserdes_tx_reg_layout->tx_highz_drvr_en, 0x10},
290 	{&qserdes_tx_reg_layout->tx_rcv_detect_lvl_2, 0x12},
291 	{&qserdes_tx_reg_layout->tx_lane_mode_1, 0x16},
292 	{&qserdes_tx_reg_layout->tx_res_code_lane_offset_rx, 0x09},
293 	{&qserdes_tx_reg_layout->tx_res_code_lane_offset_tx, 0x06},
294 };
295 
296 static const struct qmp_phy_init_tbl qmp_v3_usb3_rx_tbl[] = {
297 	{&qserdes_rx_reg_layout->rx_ucdr_fastlock_fo_gain, 0x0b},
298 	{&qserdes_rx_reg_layout->rx_rx_equ_adap_ctrl2, 0x0f},
299 	{&qserdes_rx_reg_layout->rx_rx_equ_adap_ctrl3, 0x4e},
300 	{&qserdes_rx_reg_layout->rx_rx_equ_adap_ctrl4, 0x18},
301 	{&qserdes_rx_reg_layout->rx_rx_eq_offset_adap_ctrl1, 0x77},
302 	{&qserdes_rx_reg_layout->rx_rx_offset_adap_ctrl2, 0x80},
303 	{&qserdes_rx_reg_layout->rx_sigdet_ctrl, 0x03},
304 	{&qserdes_rx_reg_layout->rx_sigdet_deglitch_ctrl, 0x16},
305 	{&qserdes_rx_reg_layout->rx_ucdr_so_saturtn_and_en, 0x75},
306 	{&qserdes_rx_reg_layout->rx_ucdr_pi_cntrls, 0x80},
307 	{&qserdes_rx_reg_layout->rx_ucdr_fo_gain, 0x0a},
308 	{&qserdes_rx_reg_layout->rx_ucdr_so_gain_half, 0x06},
309 	{&qserdes_rx_reg_layout->rx_sigdet_enables, 0x00},
310 };
311 
312 static const struct qmp_phy_init_tbl qmp_v3_usb3_pcs_tbl[] = {
313 	/* FLL settings */
314 	{&pcs_reg_layout->pcs_fll_ctrl2, 0x83},
315 	{&pcs_reg_layout->pcs_fll_cnt_val_l, 0x09},
316 	{&pcs_reg_layout->pcs_fll_cnt_val_h_tol, 0xa2},
317 	{&pcs_reg_layout->pcs_fll_man_code, 0x40},
318 	{&pcs_reg_layout->pcs_fll_ctrl1, 0x02},
319 
320 	/* Lock Det settings */
321 	{&pcs_reg_layout->pcs_lock_detect_config1, 0xd1},
322 	{&pcs_reg_layout->pcs_lock_detect_config2, 0x1f},
323 	{&pcs_reg_layout->pcs_lock_detect_config3, 0x47},
324 	{&pcs_reg_layout->pcs_power_state_config2, 0x1b},
325 
326 	{&pcs_reg_layout->pcs_rx_sigdet_lvl, 0xba},
327 	{&pcs_reg_layout->pcs_txmgn_v0, 0x9f},
328 	{&pcs_reg_layout->pcs_txmgn_v1, 0x9f},
329 	{&pcs_reg_layout->pcs_txmgn_v2, 0xb7},
330 	{&pcs_reg_layout->pcs_txmgn_v3, 0x4e},
331 	{&pcs_reg_layout->pcs_txmgn_v4, 0x65},
332 	{&pcs_reg_layout->pcs_txmgn_ls, 0x6b},
333 	{&pcs_reg_layout->pcs_txdeemph_m6db_v0, 0x15},
334 	{&pcs_reg_layout->pcs_txdeemph_m3p5db_v0, 0x0d},
335 	{&pcs_reg_layout->pcs_txdeemph_m6db_v1, 0x15},
336 	{&pcs_reg_layout->pcs_txdeemph_m3p5db_v1, 0x0d},
337 	{&pcs_reg_layout->pcs_txdeemph_m6db_v2, 0x15},
338 	{&pcs_reg_layout->pcs_txdeemph_m3p5db_v2, 0x0d},
339 	{&pcs_reg_layout->pcs_txdeemph_m6db_v3, 0x15},
340 	{&pcs_reg_layout->pcs_txdeemph_m3p5db_v3, 0x1d},
341 	{&pcs_reg_layout->pcs_txdeemph_m6db_v4, 0x15},
342 	{&pcs_reg_layout->pcs_txdeemph_m3p5db_v4, 0x0d},
343 	{&pcs_reg_layout->pcs_txdeemph_m6db_ls, 0x15},
344 	{&pcs_reg_layout->pcs_txdeemph_m3p5db_ls, 0x0d},
345 	{&pcs_reg_layout->pcs_rate_slew_cntrl, 0x02},
346 	{&pcs_reg_layout->pcs_pwrup_reset_dly_time_auxclk, 0x04},
347 	{&pcs_reg_layout->pcs_tsync_rsync_time, 0x44},
348 	{&pcs_reg_layout->pcs_rcvr_dtct_dly_p1u2_l, 0xe7},
349 	{&pcs_reg_layout->pcs_rcvr_dtct_dly_p1u2_h, 0x03},
350 	{&pcs_reg_layout->pcs_rcvr_dtct_dly_u3_l, 0x40},
351 	{&pcs_reg_layout->pcs_rcvr_dtct_dly_u3_h, 0x00},
352 	{&pcs_reg_layout->pcs_rxeqtraining_wait_time, 0x75},
353 	{&pcs_reg_layout->pcs_lfps_ecstart_eqtlock, 0x86},
354 	{&pcs_reg_layout->pcs_rxeqtraining_run_time, 0x13},
355 };
356 
357 struct ss_usb_phy_reg qmp_v3_usb_phy = {
358 	.serdes_tbl =		qmp_v3_usb3_serdes_tbl,
359 	.serdes_tbl_num	=	ARRAY_SIZE(qmp_v3_usb3_serdes_tbl),
360 	.tx_tbl =		qmp_v3_usb3_tx_tbl,
361 	.tx_tbl_num =		ARRAY_SIZE(qmp_v3_usb3_tx_tbl),
362 	.rx_tbl =		qmp_v3_usb3_rx_tbl,
363 	.rx_tbl_num =		ARRAY_SIZE(qmp_v3_usb3_rx_tbl),
364 	.pcs_tbl =		qmp_v3_usb3_pcs_tbl,
365 	.pcs_tbl_num =		ARRAY_SIZE(qmp_v3_usb3_pcs_tbl),
366 	.qmp_pcs_reg =		(void *)QMP_PHY_PCS_REG_BASE,
367 };
368 
qcom_qmp_phy_configure(const struct qmp_phy_init_tbl tbl[],int num)369 static void qcom_qmp_phy_configure(const struct qmp_phy_init_tbl tbl[],
370 				int num)
371 {
372 	int i;
373 	const struct qmp_phy_init_tbl *t = tbl;
374 
375 	if (!t)
376 		return;
377 
378 	for (i = 0; i < num; i++, t++)
379 		write32(t->address, t->val);
380 }
381 
ss_qmp_phy_init(void)382 void ss_qmp_phy_init(void)
383 {
384 	struct ss_usb_phy_reg *ss_phy_reg;
385 
386 	ss_phy_reg = &qmp_v3_usb_phy;
387 	/* power up USB3 PHY */
388 	write32(&ss_phy_reg->qmp_pcs_reg->pcs_power_down_control, 0x01);
389 
390 	 /* Serdes configuration */
391 	qcom_qmp_phy_configure(ss_phy_reg->serdes_tbl,
392 		ss_phy_reg->serdes_tbl_num);
393 	/* Tx, Rx, and PCS configurations */
394 	qcom_qmp_phy_configure(ss_phy_reg->tx_tbl, ss_phy_reg->tx_tbl_num);
395 	qcom_qmp_phy_configure(ss_phy_reg->rx_tbl, ss_phy_reg->rx_tbl_num);
396 	qcom_qmp_phy_configure(ss_phy_reg->pcs_tbl, ss_phy_reg->pcs_tbl_num);
397 
398 	/* perform software reset of PCS/Serdes */
399 	write32(&ss_phy_reg->qmp_pcs_reg->pcs_sw_reset, 0x00);
400 	/* start PCS/Serdes to operation mode */
401 	write32(&ss_phy_reg->qmp_pcs_reg->pcs_start_control, 0x03);
402 
403 	/*
404 	 * Wait for PHY initialization to be done
405 	 * PCS_STATUS: wait for 1ms for PHY STATUS;
406 	 * SW can continuously check for PHYSTATUS = 1.b0.
407 	 */
408 	long lock_us = wait_us(10000,
409 			!(read32(&ss_phy_reg->qmp_pcs_reg->pcs_ready_status) &
410 			USB3_PCS_PHYSTATUS));
411 	if (!lock_us)
412 		printk(BIOS_ERR, "QMP PHY PLL LOCK fails:\n");
413 	else
414 		printk(BIOS_DEBUG, "QMP PHY initialized and locked in %ldus\n",
415 				lock_us);
416 }
417