1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Copyright (c) 2017, The Linux Foundation. All rights reserved.
4  */
5 
6 #include <linux/clk.h>
7 #include <linux/clk-provider.h>
8 #include <linux/delay.h>
9 #include <linux/err.h>
10 #include <linux/io.h>
11 #include <linux/iopoll.h>
12 #include <linux/kernel.h>
13 #include <linux/module.h>
14 #include <linux/of.h>
15 #include <linux/of_device.h>
16 #include <linux/of_address.h>
17 #include <linux/phy/phy.h>
18 #include <linux/platform_device.h>
19 #include <linux/regulator/consumer.h>
20 #include <linux/reset.h>
21 #include <linux/slab.h>
22 
23 #include <dt-bindings/phy/phy.h>
24 
25 #include "phy-qcom-qmp.h"
26 
27 /* QPHY_SW_RESET bit */
28 #define SW_RESET				BIT(0)
29 /* QPHY_POWER_DOWN_CONTROL */
30 #define SW_PWRDN				BIT(0)
31 #define REFCLK_DRV_DSBL				BIT(1)
32 /* QPHY_START_CONTROL bits */
33 #define SERDES_START				BIT(0)
34 #define PCS_START				BIT(1)
35 #define PLL_READY_GATE_EN			BIT(3)
36 /* QPHY_PCS_STATUS bit */
37 #define PHYSTATUS				BIT(6)
38 #define PHYSTATUS_4_20				BIT(7)
39 /* QPHY_PCS_READY_STATUS & QPHY_COM_PCS_READY_STATUS bit */
40 #define PCS_READY				BIT(0)
41 
42 /* QPHY_V3_DP_COM_RESET_OVRD_CTRL register bits */
43 /* DP PHY soft reset */
44 #define SW_DPPHY_RESET				BIT(0)
45 /* mux to select DP PHY reset control, 0:HW control, 1: software reset */
46 #define SW_DPPHY_RESET_MUX			BIT(1)
47 /* USB3 PHY soft reset */
48 #define SW_USB3PHY_RESET			BIT(2)
49 /* mux to select USB3 PHY reset control, 0:HW control, 1: software reset */
50 #define SW_USB3PHY_RESET_MUX			BIT(3)
51 
52 /* QPHY_V3_DP_COM_PHY_MODE_CTRL register bits */
53 #define USB3_MODE				BIT(0) /* enables USB3 mode */
54 #define DP_MODE					BIT(1) /* enables DP mode */
55 
56 /* QPHY_PCS_AUTONOMOUS_MODE_CTRL register bits */
57 #define ARCVR_DTCT_EN				BIT(0)
58 #define ALFPS_DTCT_EN				BIT(1)
59 #define ARCVR_DTCT_EVENT_SEL			BIT(4)
60 
61 /* QPHY_PCS_LFPS_RXTERM_IRQ_CLEAR register bits */
62 #define IRQ_CLEAR				BIT(0)
63 
64 /* QPHY_PCS_LFPS_RXTERM_IRQ_STATUS register bits */
65 #define RCVR_DETECT				BIT(0)
66 
67 /* QPHY_V3_PCS_MISC_CLAMP_ENABLE register bits */
68 #define CLAMP_EN				BIT(0) /* enables i/o clamp_n */
69 
70 #define PHY_INIT_COMPLETE_TIMEOUT		10000
71 #define POWER_DOWN_DELAY_US_MIN			10
72 #define POWER_DOWN_DELAY_US_MAX			11
73 
74 #define MAX_PROP_NAME				32
75 
76 /* Define the assumed distance between lanes for underspecified device trees. */
77 #define QMP_PHY_LEGACY_LANE_STRIDE		0x400
78 
79 struct qmp_phy_init_tbl {
80 	unsigned int offset;
81 	unsigned int val;
82 	/*
83 	 * register part of layout ?
84 	 * if yes, then offset gives index in the reg-layout
85 	 */
86 	bool in_layout;
87 	/*
88 	 * mask of lanes for which this register is written
89 	 * for cases when second lane needs different values
90 	 */
91 	u8 lane_mask;
92 };
93 
94 #define QMP_PHY_INIT_CFG(o, v)		\
95 	{				\
96 		.offset = o,		\
97 		.val = v,		\
98 		.lane_mask = 0xff,	\
99 	}
100 
101 #define QMP_PHY_INIT_CFG_L(o, v)	\
102 	{				\
103 		.offset = o,		\
104 		.val = v,		\
105 		.in_layout = true,	\
106 		.lane_mask = 0xff,	\
107 	}
108 
109 #define QMP_PHY_INIT_CFG_LANE(o, v, l)	\
110 	{				\
111 		.offset = o,		\
112 		.val = v,		\
113 		.lane_mask = l,		\
114 	}
115 
116 /* set of registers with offsets different per-PHY */
117 enum qphy_reg_layout {
118 	/* Common block control registers */
119 	QPHY_COM_SW_RESET,
120 	QPHY_COM_POWER_DOWN_CONTROL,
121 	QPHY_COM_START_CONTROL,
122 	QPHY_COM_PCS_READY_STATUS,
123 	/* PCS registers */
124 	QPHY_SW_RESET,
125 	QPHY_START_CTRL,
126 	QPHY_PCS_READY_STATUS,
127 	QPHY_PCS_STATUS,
128 	QPHY_PCS_AUTONOMOUS_MODE_CTRL,
129 	QPHY_PCS_LFPS_RXTERM_IRQ_CLEAR,
130 	QPHY_PCS_LFPS_RXTERM_IRQ_STATUS,
131 	QPHY_PCS_POWER_DOWN_CONTROL,
132 	/* PCS_MISC registers */
133 	QPHY_PCS_MISC_TYPEC_CTRL,
134 	/* Keep last to ensure regs_layout arrays are properly initialized */
135 	QPHY_LAYOUT_SIZE
136 };
137 
138 static const unsigned int msm8996_ufsphy_regs_layout[QPHY_LAYOUT_SIZE] = {
139 	[QPHY_START_CTRL]		= 0x00,
140 	[QPHY_PCS_READY_STATUS]		= 0x168,
141 };
142 
143 static const unsigned int sdm845_ufsphy_regs_layout[QPHY_LAYOUT_SIZE] = {
144 	[QPHY_START_CTRL]		= 0x00,
145 	[QPHY_PCS_READY_STATUS]		= 0x160,
146 };
147 
148 static const unsigned int sm6115_ufsphy_regs_layout[QPHY_LAYOUT_SIZE] = {
149 	[QPHY_START_CTRL]		= 0x00,
150 	[QPHY_PCS_READY_STATUS]		= 0x168,
151 };
152 
153 static const unsigned int sm8150_ufsphy_regs_layout[QPHY_LAYOUT_SIZE] = {
154 	[QPHY_START_CTRL]		= QPHY_V4_PCS_UFS_PHY_START,
155 	[QPHY_PCS_READY_STATUS]		= QPHY_V4_PCS_UFS_READY_STATUS,
156 	[QPHY_SW_RESET]			= QPHY_V4_PCS_UFS_SW_RESET,
157 };
158 
159 static const struct qmp_phy_init_tbl msm8996_ufs_serdes_tbl[] = {
160 	QMP_PHY_INIT_CFG(QSERDES_COM_CMN_CONFIG, 0x0e),
161 	QMP_PHY_INIT_CFG(QSERDES_COM_SYSCLK_EN_SEL, 0xd7),
162 	QMP_PHY_INIT_CFG(QSERDES_COM_CLK_SELECT, 0x30),
163 	QMP_PHY_INIT_CFG(QSERDES_COM_SYS_CLK_CTRL, 0x06),
164 	QMP_PHY_INIT_CFG(QSERDES_COM_BIAS_EN_CLKBUFLR_EN, 0x08),
165 	QMP_PHY_INIT_CFG(QSERDES_COM_BG_TIMER, 0x0a),
166 	QMP_PHY_INIT_CFG(QSERDES_COM_HSCLK_SEL, 0x05),
167 	QMP_PHY_INIT_CFG(QSERDES_COM_CORECLK_DIV, 0x0a),
168 	QMP_PHY_INIT_CFG(QSERDES_COM_CORECLK_DIV_MODE1, 0x0a),
169 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP_EN, 0x01),
170 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_CTRL, 0x10),
171 	QMP_PHY_INIT_CFG(QSERDES_COM_RESETSM_CNTRL, 0x20),
172 	QMP_PHY_INIT_CFG(QSERDES_COM_CORE_CLK_EN, 0x00),
173 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP_CFG, 0x00),
174 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_TIMER1, 0xff),
175 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_TIMER2, 0x3f),
176 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_MAP, 0x54),
177 	QMP_PHY_INIT_CFG(QSERDES_COM_SVS_MODE_CLK_SEL, 0x05),
178 	QMP_PHY_INIT_CFG(QSERDES_COM_DEC_START_MODE0, 0x82),
179 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START1_MODE0, 0x00),
180 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START2_MODE0, 0x00),
181 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START3_MODE0, 0x00),
182 	QMP_PHY_INIT_CFG(QSERDES_COM_CP_CTRL_MODE0, 0x0b),
183 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_RCTRL_MODE0, 0x16),
184 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_CCTRL_MODE0, 0x28),
185 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN0_MODE0, 0x80),
186 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN1_MODE0, 0x00),
187 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE1_MODE0, 0x28),
188 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE2_MODE0, 0x02),
189 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP1_MODE0, 0xff),
190 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP2_MODE0, 0x0c),
191 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP3_MODE0, 0x00),
192 	QMP_PHY_INIT_CFG(QSERDES_COM_DEC_START_MODE1, 0x98),
193 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START1_MODE1, 0x00),
194 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START2_MODE1, 0x00),
195 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START3_MODE1, 0x00),
196 	QMP_PHY_INIT_CFG(QSERDES_COM_CP_CTRL_MODE1, 0x0b),
197 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_RCTRL_MODE1, 0x16),
198 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_CCTRL_MODE1, 0x28),
199 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN0_MODE1, 0x80),
200 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN1_MODE1, 0x00),
201 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE1_MODE1, 0xd6),
202 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE2_MODE1, 0x00),
203 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP1_MODE1, 0x32),
204 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP2_MODE1, 0x0f),
205 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP3_MODE1, 0x00),
206 };
207 
208 static const struct qmp_phy_init_tbl msm8996_ufs_tx_tbl[] = {
209 	QMP_PHY_INIT_CFG(QSERDES_TX_HIGHZ_TRANSCEIVEREN_BIAS_DRVR_EN, 0x45),
210 	QMP_PHY_INIT_CFG(QSERDES_TX_LANE_MODE, 0x02),
211 };
212 
213 static const struct qmp_phy_init_tbl msm8996_ufs_rx_tbl[] = {
214 	QMP_PHY_INIT_CFG(QSERDES_RX_SIGDET_LVL, 0x24),
215 	QMP_PHY_INIT_CFG(QSERDES_RX_SIGDET_CNTRL, 0x02),
216 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_INTERFACE_MODE, 0x00),
217 	QMP_PHY_INIT_CFG(QSERDES_RX_SIGDET_DEGLITCH_CNTRL, 0x18),
218 	QMP_PHY_INIT_CFG(QSERDES_RX_UCDR_FASTLOCK_FO_GAIN, 0x0B),
219 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_TERM_BW, 0x5b),
220 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN1_LSB, 0xff),
221 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN1_MSB, 0x3f),
222 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN2_LSB, 0xff),
223 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN2_MSB, 0x0f),
224 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQU_ADAPTOR_CNTRL2, 0x0E),
225 };
226 
227 static const struct qmp_phy_init_tbl sm6115_ufsphy_serdes_tbl[] = {
228 	QMP_PHY_INIT_CFG(QSERDES_COM_CMN_CONFIG, 0x0e),
229 	QMP_PHY_INIT_CFG(QSERDES_COM_SYSCLK_EN_SEL, 0x14),
230 	QMP_PHY_INIT_CFG(QSERDES_COM_CLK_SELECT, 0x30),
231 	QMP_PHY_INIT_CFG(QSERDES_COM_SYS_CLK_CTRL, 0x02),
232 	QMP_PHY_INIT_CFG(QSERDES_COM_BIAS_EN_CLKBUFLR_EN, 0x08),
233 	QMP_PHY_INIT_CFG(QSERDES_COM_BG_TIMER, 0x0a),
234 	QMP_PHY_INIT_CFG(QSERDES_COM_HSCLK_SEL, 0x00),
235 	QMP_PHY_INIT_CFG(QSERDES_COM_CORECLK_DIV, 0x0a),
236 	QMP_PHY_INIT_CFG(QSERDES_COM_CORECLK_DIV_MODE1, 0x0a),
237 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP_EN, 0x01),
238 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_CTRL, 0x00),
239 	QMP_PHY_INIT_CFG(QSERDES_COM_RESETSM_CNTRL, 0x20),
240 	QMP_PHY_INIT_CFG(QSERDES_COM_CORE_CLK_EN, 0x00),
241 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP_CFG, 0x00),
242 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_TIMER1, 0xff),
243 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_TIMER2, 0x3f),
244 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_MAP, 0x04),
245 	QMP_PHY_INIT_CFG(QSERDES_COM_SVS_MODE_CLK_SEL, 0x05),
246 	QMP_PHY_INIT_CFG(QSERDES_COM_DEC_START_MODE0, 0x82),
247 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START1_MODE0, 0x00),
248 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START2_MODE0, 0x00),
249 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START3_MODE0, 0x00),
250 	QMP_PHY_INIT_CFG(QSERDES_COM_CP_CTRL_MODE0, 0x0b),
251 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_RCTRL_MODE0, 0x16),
252 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_CCTRL_MODE0, 0x28),
253 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN0_MODE0, 0x80),
254 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN1_MODE0, 0x00),
255 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE1_MODE0, 0x28),
256 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE2_MODE0, 0x02),
257 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP1_MODE0, 0xff),
258 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP2_MODE0, 0x0c),
259 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP3_MODE0, 0x00),
260 	QMP_PHY_INIT_CFG(QSERDES_COM_DEC_START_MODE1, 0x98),
261 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START1_MODE1, 0x00),
262 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START2_MODE1, 0x00),
263 	QMP_PHY_INIT_CFG(QSERDES_COM_DIV_FRAC_START3_MODE1, 0x00),
264 	QMP_PHY_INIT_CFG(QSERDES_COM_CP_CTRL_MODE1, 0x0b),
265 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_RCTRL_MODE1, 0x16),
266 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_CCTRL_MODE1, 0x28),
267 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN0_MODE1, 0x80),
268 	QMP_PHY_INIT_CFG(QSERDES_COM_INTEGLOOP_GAIN1_MODE1, 0x00),
269 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE1_MODE1, 0xd6),
270 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE2_MODE1, 0x00),
271 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP1_MODE1, 0x32),
272 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP2_MODE1, 0x0f),
273 	QMP_PHY_INIT_CFG(QSERDES_COM_LOCK_CMP3_MODE1, 0x00),
274 	QMP_PHY_INIT_CFG(QSERDES_COM_PLL_IVCO, 0x0f),
275 	QMP_PHY_INIT_CFG(QSERDES_COM_BG_TRIM, 0x0f),
276 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_INITVAL1, 0xff),
277 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_INITVAL2, 0x00),
278 
279 	/* Rate B */
280 	QMP_PHY_INIT_CFG(QSERDES_COM_VCO_TUNE_MAP, 0x44),
281 };
282 
283 static const struct qmp_phy_init_tbl sm6115_ufsphy_tx_tbl[] = {
284 	QMP_PHY_INIT_CFG(QSERDES_TX_HIGHZ_TRANSCEIVEREN_BIAS_DRVR_EN, 0x45),
285 	QMP_PHY_INIT_CFG(QSERDES_TX_LANE_MODE, 0x06),
286 };
287 
288 static const struct qmp_phy_init_tbl sm6115_ufsphy_rx_tbl[] = {
289 	QMP_PHY_INIT_CFG(QSERDES_RX_SIGDET_LVL, 0x24),
290 	QMP_PHY_INIT_CFG(QSERDES_RX_SIGDET_CNTRL, 0x0F),
291 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_INTERFACE_MODE, 0x40),
292 	QMP_PHY_INIT_CFG(QSERDES_RX_SIGDET_DEGLITCH_CNTRL, 0x1E),
293 	QMP_PHY_INIT_CFG(QSERDES_RX_UCDR_FASTLOCK_FO_GAIN, 0x0B),
294 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_TERM_BW, 0x5B),
295 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN1_LSB, 0xFF),
296 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN1_MSB, 0x3F),
297 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN2_LSB, 0xFF),
298 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQ_GAIN2_MSB, 0x3F),
299 	QMP_PHY_INIT_CFG(QSERDES_RX_RX_EQU_ADAPTOR_CNTRL2, 0x0D),
300 	QMP_PHY_INIT_CFG(QSERDES_RX_UCDR_SVS_SO_GAIN_HALF, 0x04),
301 	QMP_PHY_INIT_CFG(QSERDES_RX_UCDR_SVS_SO_GAIN_QUARTER, 0x04),
302 	QMP_PHY_INIT_CFG(QSERDES_RX_UCDR_SVS_SO_GAIN, 0x04),
303 	QMP_PHY_INIT_CFG(QSERDES_RX_UCDR_SO_SATURATION_AND_ENABLE, 0x5B),
304 };
305 
306 static const struct qmp_phy_init_tbl sm6115_ufsphy_pcs_tbl[] = {
307 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_RX_PWM_GEAR_BAND, 0x15),
308 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_RX_SIGDET_CTRL2, 0x6d),
309 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_TX_LARGE_AMP_DRV_LVL, 0x0f),
310 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_TX_SMALL_AMP_DRV_LVL, 0x02),
311 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_RX_MIN_STALL_NOCONFIG_TIME_CAP, 0x28),
312 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_RX_SYM_RESYNC_CTRL, 0x03),
313 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_TX_LARGE_AMP_POST_EMP_LVL, 0x12),
314 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_TX_SMALL_AMP_POST_EMP_LVL, 0x0f),
315 	QMP_PHY_INIT_CFG(QPHY_V2_PCS_RX_MIN_HIBERN8_TIME, 0x9a), /* 8 us */
316 };
317 
318 static const struct qmp_phy_init_tbl sdm845_ufsphy_serdes_tbl[] = {
319 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_SYS_CLK_CTRL, 0x02),
320 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_BIAS_EN_CLKBUFLR_EN, 0x04),
321 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_BG_TIMER, 0x0a),
322 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_PLL_IVCO, 0x07),
323 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_CMN_CONFIG, 0x06),
324 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_SYSCLK_EN_SEL, 0xd5),
325 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_RESETSM_CNTRL, 0x20),
326 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_CLK_SELECT, 0x30),
327 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_HSCLK_SEL, 0x00),
328 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_LOCK_CMP_EN, 0x01),
329 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE_CTRL, 0x00),
330 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_CORE_CLK_EN, 0x00),
331 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE_MAP, 0x04),
332 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_SVS_MODE_CLK_SEL, 0x05),
333 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE_INITVAL1, 0xff),
334 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE_INITVAL2, 0x00),
335 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_DEC_START_MODE0, 0x82),
336 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_CP_CTRL_MODE0, 0x06),
337 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_PLL_RCTRL_MODE0, 0x16),
338 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_PLL_CCTRL_MODE0, 0x36),
339 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_INTEGLOOP_GAIN0_MODE0, 0x3f),
340 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_INTEGLOOP_GAIN1_MODE0, 0x00),
341 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE1_MODE0, 0xda),
342 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE2_MODE0, 0x01),
343 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_LOCK_CMP1_MODE0, 0xff),
344 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_LOCK_CMP2_MODE0, 0x0c),
345 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_DEC_START_MODE1, 0x98),
346 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_CP_CTRL_MODE1, 0x06),
347 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_PLL_RCTRL_MODE1, 0x16),
348 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_PLL_CCTRL_MODE1, 0x36),
349 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_INTEGLOOP_GAIN0_MODE1, 0x3f),
350 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_INTEGLOOP_GAIN1_MODE1, 0x00),
351 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE1_MODE1, 0xc1),
352 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE2_MODE1, 0x00),
353 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_LOCK_CMP1_MODE1, 0x32),
354 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_LOCK_CMP2_MODE1, 0x0f),
355 
356 	/* Rate B */
357 	QMP_PHY_INIT_CFG(QSERDES_V3_COM_VCO_TUNE_MAP, 0x44),
358 };
359 
360 static const struct qmp_phy_init_tbl sdm845_ufsphy_tx_tbl[] = {
361 	QMP_PHY_INIT_CFG(QSERDES_V3_TX_LANE_MODE_1, 0x06),
362 	QMP_PHY_INIT_CFG(QSERDES_V3_TX_RES_CODE_LANE_OFFSET_TX, 0x04),
363 	QMP_PHY_INIT_CFG(QSERDES_V3_TX_RES_CODE_LANE_OFFSET_RX, 0x07),
364 };
365 
366 static const struct qmp_phy_init_tbl sdm845_ufsphy_rx_tbl[] = {
367 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_SIGDET_LVL, 0x24),
368 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_SIGDET_CNTRL, 0x0f),
369 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_SIGDET_DEGLITCH_CNTRL, 0x1e),
370 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_RX_INTERFACE_MODE, 0x40),
371 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_UCDR_FASTLOCK_FO_GAIN, 0x0b),
372 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_RX_TERM_BW, 0x5b),
373 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_RX_EQU_ADAPTOR_CNTRL2, 0x06),
374 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_RX_EQU_ADAPTOR_CNTRL3, 0x04),
375 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_RX_EQU_ADAPTOR_CNTRL4, 0x1b),
376 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_UCDR_SVS_SO_GAIN_HALF, 0x04),
377 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_UCDR_SVS_SO_GAIN_QUARTER, 0x04),
378 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_UCDR_SVS_SO_GAIN, 0x04),
379 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_UCDR_SO_SATURATION_AND_ENABLE, 0x4b),
380 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_UCDR_PI_CONTROLS, 0x81),
381 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_UCDR_FASTLOCK_COUNT_LOW, 0x80),
382 	QMP_PHY_INIT_CFG(QSERDES_V3_RX_RX_MODE_00, 0x59),
383 };
384 
385 static const struct qmp_phy_init_tbl sdm845_ufsphy_pcs_tbl[] = {
386 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_RX_SIGDET_CTRL2, 0x6e),
387 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_TX_LARGE_AMP_DRV_LVL, 0x0a),
388 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_TX_SMALL_AMP_DRV_LVL, 0x02),
389 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_RX_SYM_RESYNC_CTRL, 0x03),
390 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_TX_MID_TERM_CTRL1, 0x43),
391 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_RX_SIGDET_CTRL1, 0x0f),
392 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_RX_MIN_HIBERN8_TIME, 0x9a),
393 	QMP_PHY_INIT_CFG(QPHY_V3_PCS_UFS_MULTI_LANE_CTRL1, 0x02),
394 };
395 
396 static const struct qmp_phy_init_tbl sm8150_ufsphy_serdes_tbl[] = {
397 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_SYSCLK_EN_SEL, 0xd9),
398 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_HSCLK_SEL, 0x11),
399 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_HSCLK_HS_SWITCH_SEL, 0x00),
400 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP_EN, 0x01),
401 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_VCO_TUNE_MAP, 0x02),
402 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_IVCO, 0x0f),
403 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_VCO_TUNE_INITVAL2, 0x00),
404 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_HSCLK_SEL, 0x11),
405 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_DEC_START_MODE0, 0x82),
406 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_CP_CTRL_MODE0, 0x06),
407 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_RCTRL_MODE0, 0x16),
408 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_CCTRL_MODE0, 0x36),
409 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP1_MODE0, 0xff),
410 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP2_MODE0, 0x0c),
411 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE1_MODE0, 0xac),
412 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE2_MODE0, 0x1e),
413 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_DEC_START_MODE1, 0x98),
414 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_CP_CTRL_MODE1, 0x06),
415 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_RCTRL_MODE1, 0x16),
416 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_CCTRL_MODE1, 0x36),
417 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP1_MODE1, 0x32),
418 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP2_MODE1, 0x0f),
419 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE1_MODE1, 0xdd),
420 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE2_MODE1, 0x23),
421 
422 	/* Rate B */
423 	QMP_PHY_INIT_CFG(QSERDES_V4_COM_VCO_TUNE_MAP, 0x06),
424 };
425 
426 static const struct qmp_phy_init_tbl sm8150_ufsphy_tx_tbl[] = {
427 	QMP_PHY_INIT_CFG(QSERDES_V4_TX_PWM_GEAR_1_DIVIDER_BAND0_1, 0x06),
428 	QMP_PHY_INIT_CFG(QSERDES_V4_TX_PWM_GEAR_2_DIVIDER_BAND0_1, 0x03),
429 	QMP_PHY_INIT_CFG(QSERDES_V4_TX_PWM_GEAR_3_DIVIDER_BAND0_1, 0x01),
430 	QMP_PHY_INIT_CFG(QSERDES_V4_TX_PWM_GEAR_4_DIVIDER_BAND0_1, 0x00),
431 	QMP_PHY_INIT_CFG(QSERDES_V4_TX_LANE_MODE_1, 0x05),
432 	QMP_PHY_INIT_CFG(QSERDES_V4_TX_TRAN_DRVR_EMP_EN, 0x0c),
433 };
434 
435 static const struct qmp_phy_init_tbl sm8150_ufsphy_rx_tbl[] = {
436 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_SIGDET_LVL, 0x24),
437 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_SIGDET_CNTRL, 0x0f),
438 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_SIGDET_DEGLITCH_CNTRL, 0x1e),
439 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_BAND, 0x18),
440 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_UCDR_FASTLOCK_FO_GAIN, 0x0a),
441 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_UCDR_SO_SATURATION_AND_ENABLE, 0x4b),
442 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_UCDR_PI_CONTROLS, 0xf1),
443 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_UCDR_FASTLOCK_COUNT_LOW, 0x80),
444 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_UCDR_PI_CTRL2, 0x80),
445 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_UCDR_FO_GAIN, 0x0c),
446 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_UCDR_SO_GAIN, 0x04),
447 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_TERM_BW, 0x1b),
448 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_EQU_ADAPTOR_CNTRL2, 0x06),
449 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_EQU_ADAPTOR_CNTRL3, 0x04),
450 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_EQU_ADAPTOR_CNTRL4, 0x1d),
451 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_OFFSET_ADAPTOR_CNTRL2, 0x00),
452 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_IDAC_MEASURE_TIME, 0x10),
453 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_IDAC_TSETTLE_LOW, 0xc0),
454 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_IDAC_TSETTLE_HIGH, 0x00),
455 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_00_LOW, 0x36),
456 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_00_HIGH, 0x36),
457 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_00_HIGH2, 0xf6),
458 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_00_HIGH3, 0x3b),
459 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_00_HIGH4, 0x3d),
460 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_01_LOW, 0xe0),
461 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_01_HIGH, 0xc8),
462 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_01_HIGH2, 0xc8),
463 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_01_HIGH3, 0x3b),
464 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_01_HIGH4, 0xb1),
465 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_10_LOW, 0xe0),
466 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_10_HIGH, 0xc8),
467 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_10_HIGH2, 0xc8),
468 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_10_HIGH3, 0x3b),
469 	QMP_PHY_INIT_CFG(QSERDES_V4_RX_RX_MODE_10_HIGH4, 0xb1),
470 
471 };
472 
473 static const struct qmp_phy_init_tbl sm8150_ufsphy_pcs_tbl[] = {
474 	QMP_PHY_INIT_CFG(QPHY_V4_PCS_UFS_RX_SIGDET_CTRL2, 0x6d),
475 	QMP_PHY_INIT_CFG(QPHY_V4_PCS_UFS_TX_LARGE_AMP_DRV_LVL, 0x0a),
476 	QMP_PHY_INIT_CFG(QPHY_V4_PCS_UFS_TX_SMALL_AMP_DRV_LVL, 0x02),
477 	QMP_PHY_INIT_CFG(QPHY_V4_PCS_UFS_TX_MID_TERM_CTRL1, 0x43),
478 	QMP_PHY_INIT_CFG(QPHY_V4_PCS_UFS_DEBUG_BUS_CLKSEL, 0x1f),
479 	QMP_PHY_INIT_CFG(QPHY_V4_PCS_UFS_RX_MIN_HIBERN8_TIME, 0xff),
480 	QMP_PHY_INIT_CFG(QPHY_V4_PCS_UFS_MULTI_LANE_CTRL1, 0x02),
481 };
482 
483 static const struct qmp_phy_init_tbl sm8350_ufsphy_serdes_tbl[] = {
484 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_SYSCLK_EN_SEL, 0xd9),
485 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_HSCLK_SEL, 0x11),
486 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_HSCLK_HS_SWITCH_SEL, 0x00),
487 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_LOCK_CMP_EN, 0x42),
488 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_VCO_TUNE_MAP, 0x02),
489 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_PLL_IVCO, 0x0f),
490 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_VCO_TUNE_INITVAL2, 0x00),
491 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_BIN_VCOCAL_HSCLK_SEL, 0x11),
492 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_DEC_START_MODE0, 0x82),
493 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_CP_CTRL_MODE0, 0x14),
494 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_PLL_RCTRL_MODE0, 0x18),
495 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_PLL_CCTRL_MODE0, 0x18),
496 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_LOCK_CMP1_MODE0, 0xff),
497 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_LOCK_CMP2_MODE0, 0x19),
498 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_BIN_VCOCAL_CMP_CODE1_MODE0, 0xac),
499 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_BIN_VCOCAL_CMP_CODE2_MODE0, 0x1e),
500 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_DEC_START_MODE1, 0x98),
501 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_CP_CTRL_MODE1, 0x14),
502 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_PLL_RCTRL_MODE1, 0x18),
503 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_PLL_CCTRL_MODE1, 0x18),
504 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_LOCK_CMP1_MODE1, 0x65),
505 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_LOCK_CMP2_MODE1, 0x1e),
506 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_BIN_VCOCAL_CMP_CODE1_MODE1, 0xdd),
507 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_BIN_VCOCAL_CMP_CODE2_MODE1, 0x23),
508 
509 	/* Rate B */
510 	QMP_PHY_INIT_CFG(QSERDES_V5_COM_VCO_TUNE_MAP, 0x06),
511 };
512 
513 static const struct qmp_phy_init_tbl sm8350_ufsphy_tx_tbl[] = {
514 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_PWM_GEAR_1_DIVIDER_BAND0_1, 0x06),
515 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_PWM_GEAR_2_DIVIDER_BAND0_1, 0x03),
516 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_PWM_GEAR_3_DIVIDER_BAND0_1, 0x01),
517 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_PWM_GEAR_4_DIVIDER_BAND0_1, 0x00),
518 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_LANE_MODE_1, 0xf5),
519 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_LANE_MODE_3, 0x3f),
520 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_RES_CODE_LANE_OFFSET_TX, 0x09),
521 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_RES_CODE_LANE_OFFSET_RX, 0x09),
522 	QMP_PHY_INIT_CFG(QSERDES_V5_TX_TRAN_DRVR_EMP_EN, 0x0c),
523 };
524 
525 static const struct qmp_phy_init_tbl sm8350_ufsphy_rx_tbl[] = {
526 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_SIGDET_LVL, 0x24),
527 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_SIGDET_CNTRL, 0x0f),
528 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_SIGDET_DEGLITCH_CNTRL, 0x1e),
529 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_BAND, 0x18),
530 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_UCDR_FASTLOCK_FO_GAIN, 0x0a),
531 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_UCDR_SO_SATURATION_AND_ENABLE, 0x5a),
532 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_UCDR_PI_CONTROLS, 0xf1),
533 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_UCDR_FASTLOCK_COUNT_LOW, 0x80),
534 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_UCDR_PI_CTRL2, 0x80),
535 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_UCDR_FO_GAIN, 0x0e),
536 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_UCDR_SO_GAIN, 0x04),
537 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_TERM_BW, 0x1b),
538 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_EQU_ADAPTOR_CNTRL1, 0x04),
539 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_EQU_ADAPTOR_CNTRL2, 0x06),
540 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_EQU_ADAPTOR_CNTRL3, 0x04),
541 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_EQU_ADAPTOR_CNTRL4, 0x1a),
542 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_EQ_OFFSET_ADAPTOR_CNTRL1, 0x17),
543 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_OFFSET_ADAPTOR_CNTRL2, 0x00),
544 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_IDAC_MEASURE_TIME, 0x10),
545 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_IDAC_TSETTLE_LOW, 0xc0),
546 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_IDAC_TSETTLE_HIGH, 0x00),
547 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_00_LOW, 0x6d),
548 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_00_HIGH, 0x6d),
549 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_00_HIGH2, 0xed),
550 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_00_HIGH3, 0x3b),
551 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_00_HIGH4, 0x3c),
552 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_01_LOW, 0xe0),
553 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_01_HIGH, 0xc8),
554 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_01_HIGH2, 0xc8),
555 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_01_HIGH3, 0x3b),
556 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_01_HIGH4, 0xb7),
557 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_10_LOW, 0xe0),
558 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_10_HIGH, 0xc8),
559 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_10_HIGH2, 0xc8),
560 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_10_HIGH3, 0x3b),
561 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_RX_MODE_10_HIGH4, 0xb7),
562 	QMP_PHY_INIT_CFG(QSERDES_V5_RX_DCC_CTRL1, 0x0c),
563 };
564 
565 static const struct qmp_phy_init_tbl sm8350_ufsphy_pcs_tbl[] = {
566 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_RX_SIGDET_CTRL2, 0x6d),
567 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TX_LARGE_AMP_DRV_LVL, 0x0a),
568 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TX_SMALL_AMP_DRV_LVL, 0x02),
569 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TX_MID_TERM_CTRL1, 0x43),
570 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_DEBUG_BUS_CLKSEL, 0x1f),
571 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_RX_MIN_HIBERN8_TIME, 0xff),
572 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_PLL_CNTL, 0x03),
573 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TIMER_20US_CORECLK_STEPS_MSB, 0x16),
574 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TIMER_20US_CORECLK_STEPS_LSB, 0xd8),
575 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TX_PWM_GEAR_BAND, 0xaa),
576 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TX_HS_GEAR_BAND, 0x06),
577 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_TX_HSGEAR_CAPABILITY, 0x03),
578 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_RX_HSGEAR_CAPABILITY, 0x03),
579 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_RX_SIGDET_CTRL1, 0x0e),
580 	QMP_PHY_INIT_CFG(QPHY_V5_PCS_UFS_MULTI_LANE_CTRL1, 0x02),
581 };
582 
583 struct qmp_phy;
584 
585 /* struct qmp_phy_cfg - per-PHY initialization config */
586 struct qmp_phy_cfg {
587 	/* phy-type - PCIE/UFS/USB */
588 	unsigned int type;
589 	/* number of lanes provided by phy */
590 	int nlanes;
591 
592 	/* Init sequence for PHY blocks - serdes, tx, rx, pcs */
593 	const struct qmp_phy_init_tbl *serdes_tbl;
594 	int serdes_tbl_num;
595 	const struct qmp_phy_init_tbl *tx_tbl;
596 	int tx_tbl_num;
597 	const struct qmp_phy_init_tbl *rx_tbl;
598 	int rx_tbl_num;
599 	const struct qmp_phy_init_tbl *pcs_tbl;
600 	int pcs_tbl_num;
601 
602 	/* clock ids to be requested */
603 	const char * const *clk_list;
604 	int num_clks;
605 	/* regulators to be requested */
606 	const char * const *vreg_list;
607 	int num_vregs;
608 
609 	/* array of registers with different offsets */
610 	const unsigned int *regs;
611 
612 	unsigned int start_ctrl;
613 	unsigned int pwrdn_ctrl;
614 	/* bit offset of PHYSTATUS in QPHY_PCS_STATUS register */
615 	unsigned int phy_status;
616 
617 	/* true, if PHY has secondary tx/rx lanes to be configured */
618 	bool is_dual_lane_phy;
619 
620 	/* true, if PCS block has no separate SW_RESET register */
621 	bool no_pcs_sw_reset;
622 };
623 
624 /**
625  * struct qmp_phy - per-lane phy descriptor
626  *
627  * @phy: generic phy
628  * @cfg: phy specific configuration
629  * @serdes: iomapped memory space for phy's serdes (i.e. PLL)
630  * @tx: iomapped memory space for lane's tx
631  * @rx: iomapped memory space for lane's rx
632  * @pcs: iomapped memory space for lane's pcs
633  * @tx2: iomapped memory space for second lane's tx (in dual lane PHYs)
634  * @rx2: iomapped memory space for second lane's rx (in dual lane PHYs)
635  * @pcs_misc: iomapped memory space for lane's pcs_misc
636  * @index: lane index
637  * @qmp: QMP phy to which this lane belongs
638  * @mode: current PHY mode
639  */
640 struct qmp_phy {
641 	struct phy *phy;
642 	const struct qmp_phy_cfg *cfg;
643 	void __iomem *serdes;
644 	void __iomem *tx;
645 	void __iomem *rx;
646 	void __iomem *pcs;
647 	void __iomem *tx2;
648 	void __iomem *rx2;
649 	void __iomem *pcs_misc;
650 	unsigned int index;
651 	struct qcom_qmp *qmp;
652 	enum phy_mode mode;
653 };
654 
655 /**
656  * struct qcom_qmp - structure holding QMP phy block attributes
657  *
658  * @dev: device
659  *
660  * @clks: array of clocks required by phy
661  * @resets: array of resets required by phy
662  * @vregs: regulator supplies bulk data
663  *
664  * @phys: array of per-lane phy descriptors
665  * @ufs_reset: optional UFS PHY reset handle
666  */
667 struct qcom_qmp {
668 	struct device *dev;
669 
670 	struct clk_bulk_data *clks;
671 	struct regulator_bulk_data *vregs;
672 
673 	struct qmp_phy **phys;
674 
675 	struct reset_control *ufs_reset;
676 };
677 
678 static inline void qphy_setbits(void __iomem *base, u32 offset, u32 val)
679 {
680 	u32 reg;
681 
682 	reg = readl(base + offset);
683 	reg |= val;
684 	writel(reg, base + offset);
685 
686 	/* ensure that above write is through */
687 	readl(base + offset);
688 }
689 
690 static inline void qphy_clrbits(void __iomem *base, u32 offset, u32 val)
691 {
692 	u32 reg;
693 
694 	reg = readl(base + offset);
695 	reg &= ~val;
696 	writel(reg, base + offset);
697 
698 	/* ensure that above write is through */
699 	readl(base + offset);
700 }
701 
702 /* list of clocks required by phy */
703 static const char * const msm8996_ufs_phy_clk_l[] = {
704 	"ref",
705 };
706 
707 /* the primary usb3 phy on sm8250 doesn't have a ref clock */
708 static const char * const sm8450_ufs_phy_clk_l[] = {
709 	"qref", "ref", "ref_aux",
710 };
711 
712 static const char * const sdm845_ufs_phy_clk_l[] = {
713 	"ref", "ref_aux",
714 };
715 
716 /* list of regulators */
717 static const char * const qmp_phy_vreg_l[] = {
718 	"vdda-phy", "vdda-pll",
719 };
720 
721 static const struct qmp_phy_cfg msm8996_ufs_cfg = {
722 	.type			= PHY_TYPE_UFS,
723 	.nlanes			= 1,
724 
725 	.serdes_tbl		= msm8996_ufs_serdes_tbl,
726 	.serdes_tbl_num		= ARRAY_SIZE(msm8996_ufs_serdes_tbl),
727 	.tx_tbl			= msm8996_ufs_tx_tbl,
728 	.tx_tbl_num		= ARRAY_SIZE(msm8996_ufs_tx_tbl),
729 	.rx_tbl			= msm8996_ufs_rx_tbl,
730 	.rx_tbl_num		= ARRAY_SIZE(msm8996_ufs_rx_tbl),
731 
732 	.clk_list		= msm8996_ufs_phy_clk_l,
733 	.num_clks		= ARRAY_SIZE(msm8996_ufs_phy_clk_l),
734 
735 	.vreg_list		= qmp_phy_vreg_l,
736 	.num_vregs		= ARRAY_SIZE(qmp_phy_vreg_l),
737 
738 	.regs			= msm8996_ufsphy_regs_layout,
739 
740 	.start_ctrl		= SERDES_START,
741 	.pwrdn_ctrl		= SW_PWRDN,
742 	.phy_status		= PHYSTATUS,
743 
744 	.no_pcs_sw_reset	= true,
745 };
746 
747 static const struct qmp_phy_cfg sdm845_ufsphy_cfg = {
748 	.type			= PHY_TYPE_UFS,
749 	.nlanes			= 2,
750 
751 	.serdes_tbl		= sdm845_ufsphy_serdes_tbl,
752 	.serdes_tbl_num		= ARRAY_SIZE(sdm845_ufsphy_serdes_tbl),
753 	.tx_tbl			= sdm845_ufsphy_tx_tbl,
754 	.tx_tbl_num		= ARRAY_SIZE(sdm845_ufsphy_tx_tbl),
755 	.rx_tbl			= sdm845_ufsphy_rx_tbl,
756 	.rx_tbl_num		= ARRAY_SIZE(sdm845_ufsphy_rx_tbl),
757 	.pcs_tbl		= sdm845_ufsphy_pcs_tbl,
758 	.pcs_tbl_num		= ARRAY_SIZE(sdm845_ufsphy_pcs_tbl),
759 	.clk_list		= sdm845_ufs_phy_clk_l,
760 	.num_clks		= ARRAY_SIZE(sdm845_ufs_phy_clk_l),
761 	.vreg_list		= qmp_phy_vreg_l,
762 	.num_vregs		= ARRAY_SIZE(qmp_phy_vreg_l),
763 	.regs			= sdm845_ufsphy_regs_layout,
764 
765 	.start_ctrl		= SERDES_START,
766 	.pwrdn_ctrl		= SW_PWRDN,
767 	.phy_status		= PHYSTATUS,
768 
769 	.is_dual_lane_phy	= true,
770 	.no_pcs_sw_reset	= true,
771 };
772 
773 static const struct qmp_phy_cfg sm6115_ufsphy_cfg = {
774 	.type			= PHY_TYPE_UFS,
775 	.nlanes			= 1,
776 
777 	.serdes_tbl		= sm6115_ufsphy_serdes_tbl,
778 	.serdes_tbl_num		= ARRAY_SIZE(sm6115_ufsphy_serdes_tbl),
779 	.tx_tbl			= sm6115_ufsphy_tx_tbl,
780 	.tx_tbl_num		= ARRAY_SIZE(sm6115_ufsphy_tx_tbl),
781 	.rx_tbl			= sm6115_ufsphy_rx_tbl,
782 	.rx_tbl_num		= ARRAY_SIZE(sm6115_ufsphy_rx_tbl),
783 	.pcs_tbl		= sm6115_ufsphy_pcs_tbl,
784 	.pcs_tbl_num		= ARRAY_SIZE(sm6115_ufsphy_pcs_tbl),
785 	.clk_list		= sdm845_ufs_phy_clk_l,
786 	.num_clks		= ARRAY_SIZE(sdm845_ufs_phy_clk_l),
787 	.vreg_list		= qmp_phy_vreg_l,
788 	.num_vregs		= ARRAY_SIZE(qmp_phy_vreg_l),
789 	.regs			= sm6115_ufsphy_regs_layout,
790 
791 	.start_ctrl		= SERDES_START,
792 	.pwrdn_ctrl		= SW_PWRDN,
793 
794 	.no_pcs_sw_reset	= true,
795 };
796 
797 static const struct qmp_phy_cfg sm8150_ufsphy_cfg = {
798 	.type			= PHY_TYPE_UFS,
799 	.nlanes			= 2,
800 
801 	.serdes_tbl		= sm8150_ufsphy_serdes_tbl,
802 	.serdes_tbl_num		= ARRAY_SIZE(sm8150_ufsphy_serdes_tbl),
803 	.tx_tbl			= sm8150_ufsphy_tx_tbl,
804 	.tx_tbl_num		= ARRAY_SIZE(sm8150_ufsphy_tx_tbl),
805 	.rx_tbl			= sm8150_ufsphy_rx_tbl,
806 	.rx_tbl_num		= ARRAY_SIZE(sm8150_ufsphy_rx_tbl),
807 	.pcs_tbl		= sm8150_ufsphy_pcs_tbl,
808 	.pcs_tbl_num		= ARRAY_SIZE(sm8150_ufsphy_pcs_tbl),
809 	.clk_list		= sdm845_ufs_phy_clk_l,
810 	.num_clks		= ARRAY_SIZE(sdm845_ufs_phy_clk_l),
811 	.vreg_list		= qmp_phy_vreg_l,
812 	.num_vregs		= ARRAY_SIZE(qmp_phy_vreg_l),
813 	.regs			= sm8150_ufsphy_regs_layout,
814 
815 	.start_ctrl		= SERDES_START,
816 	.pwrdn_ctrl		= SW_PWRDN,
817 	.phy_status		= PHYSTATUS,
818 
819 	.is_dual_lane_phy	= true,
820 };
821 
822 static const struct qmp_phy_cfg sm8350_ufsphy_cfg = {
823 	.type			= PHY_TYPE_UFS,
824 	.nlanes			= 2,
825 
826 	.serdes_tbl		= sm8350_ufsphy_serdes_tbl,
827 	.serdes_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_serdes_tbl),
828 	.tx_tbl			= sm8350_ufsphy_tx_tbl,
829 	.tx_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_tx_tbl),
830 	.rx_tbl			= sm8350_ufsphy_rx_tbl,
831 	.rx_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_rx_tbl),
832 	.pcs_tbl		= sm8350_ufsphy_pcs_tbl,
833 	.pcs_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_pcs_tbl),
834 	.clk_list		= sdm845_ufs_phy_clk_l,
835 	.num_clks		= ARRAY_SIZE(sdm845_ufs_phy_clk_l),
836 	.vreg_list		= qmp_phy_vreg_l,
837 	.num_vregs		= ARRAY_SIZE(qmp_phy_vreg_l),
838 	.regs			= sm8150_ufsphy_regs_layout,
839 
840 	.start_ctrl		= SERDES_START,
841 	.pwrdn_ctrl		= SW_PWRDN,
842 	.phy_status		= PHYSTATUS,
843 
844 	.is_dual_lane_phy	= true,
845 };
846 
847 static const struct qmp_phy_cfg sm8450_ufsphy_cfg = {
848 	.type			= PHY_TYPE_UFS,
849 	.nlanes			= 2,
850 
851 	.serdes_tbl		= sm8350_ufsphy_serdes_tbl,
852 	.serdes_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_serdes_tbl),
853 	.tx_tbl			= sm8350_ufsphy_tx_tbl,
854 	.tx_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_tx_tbl),
855 	.rx_tbl			= sm8350_ufsphy_rx_tbl,
856 	.rx_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_rx_tbl),
857 	.pcs_tbl		= sm8350_ufsphy_pcs_tbl,
858 	.pcs_tbl_num		= ARRAY_SIZE(sm8350_ufsphy_pcs_tbl),
859 	.clk_list		= sm8450_ufs_phy_clk_l,
860 	.num_clks		= ARRAY_SIZE(sm8450_ufs_phy_clk_l),
861 	.vreg_list		= qmp_phy_vreg_l,
862 	.num_vregs		= ARRAY_SIZE(qmp_phy_vreg_l),
863 	.regs			= sm8150_ufsphy_regs_layout,
864 
865 	.start_ctrl		= SERDES_START,
866 	.pwrdn_ctrl		= SW_PWRDN,
867 	.phy_status		= PHYSTATUS,
868 
869 	.is_dual_lane_phy	= true,
870 };
871 
872 static void qcom_qmp_phy_ufs_configure_lane(void __iomem *base,
873 					const unsigned int *regs,
874 					const struct qmp_phy_init_tbl tbl[],
875 					int num,
876 					u8 lane_mask)
877 {
878 	int i;
879 	const struct qmp_phy_init_tbl *t = tbl;
880 
881 	if (!t)
882 		return;
883 
884 	for (i = 0; i < num; i++, t++) {
885 		if (!(t->lane_mask & lane_mask))
886 			continue;
887 
888 		if (t->in_layout)
889 			writel(t->val, base + regs[t->offset]);
890 		else
891 			writel(t->val, base + t->offset);
892 	}
893 }
894 
895 static void qcom_qmp_phy_ufs_configure(void __iomem *base,
896 				   const unsigned int *regs,
897 				   const struct qmp_phy_init_tbl tbl[],
898 				   int num)
899 {
900 	qcom_qmp_phy_ufs_configure_lane(base, regs, tbl, num, 0xff);
901 }
902 
903 static int qcom_qmp_phy_ufs_serdes_init(struct qmp_phy *qphy)
904 {
905 	const struct qmp_phy_cfg *cfg = qphy->cfg;
906 	void __iomem *serdes = qphy->serdes;
907 	const struct qmp_phy_init_tbl *serdes_tbl = cfg->serdes_tbl;
908 	int serdes_tbl_num = cfg->serdes_tbl_num;
909 
910 	qcom_qmp_phy_ufs_configure(serdes, cfg->regs, serdes_tbl, serdes_tbl_num);
911 
912 	return 0;
913 }
914 
915 static int qcom_qmp_phy_ufs_com_init(struct qmp_phy *qphy)
916 {
917 	struct qcom_qmp *qmp = qphy->qmp;
918 	const struct qmp_phy_cfg *cfg = qphy->cfg;
919 	void __iomem *pcs = qphy->pcs;
920 	int ret;
921 
922 	/* turn on regulator supplies */
923 	ret = regulator_bulk_enable(cfg->num_vregs, qmp->vregs);
924 	if (ret) {
925 		dev_err(qmp->dev, "failed to enable regulators, err=%d\n", ret);
926 		return ret;
927 	}
928 
929 	ret = clk_bulk_prepare_enable(cfg->num_clks, qmp->clks);
930 	if (ret)
931 		goto err_disable_regulators;
932 
933 	if (cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL])
934 		qphy_setbits(pcs,
935 			     cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL],
936 			     cfg->pwrdn_ctrl);
937 	else
938 		qphy_setbits(pcs, QPHY_V2_PCS_POWER_DOWN_CONTROL,
939 			     cfg->pwrdn_ctrl);
940 
941 	return 0;
942 
943 err_disable_regulators:
944 	regulator_bulk_disable(cfg->num_vregs, qmp->vregs);
945 
946 	return ret;
947 }
948 
949 static int qcom_qmp_phy_ufs_com_exit(struct qmp_phy *qphy)
950 {
951 	struct qcom_qmp *qmp = qphy->qmp;
952 	const struct qmp_phy_cfg *cfg = qphy->cfg;
953 
954 	reset_control_assert(qmp->ufs_reset);
955 
956 	clk_bulk_disable_unprepare(cfg->num_clks, qmp->clks);
957 
958 	regulator_bulk_disable(cfg->num_vregs, qmp->vregs);
959 
960 	return 0;
961 }
962 
963 static int qcom_qmp_phy_ufs_init(struct phy *phy)
964 {
965 	struct qmp_phy *qphy = phy_get_drvdata(phy);
966 	struct qcom_qmp *qmp = qphy->qmp;
967 	const struct qmp_phy_cfg *cfg = qphy->cfg;
968 	int ret;
969 	dev_vdbg(qmp->dev, "Initializing QMP phy\n");
970 
971 	if (cfg->no_pcs_sw_reset) {
972 		/*
973 		 * Get UFS reset, which is delayed until now to avoid a
974 		 * circular dependency where UFS needs its PHY, but the PHY
975 		 * needs this UFS reset.
976 		 */
977 		if (!qmp->ufs_reset) {
978 			qmp->ufs_reset =
979 				devm_reset_control_get_exclusive(qmp->dev,
980 								 "ufsphy");
981 
982 			if (IS_ERR(qmp->ufs_reset)) {
983 				ret = PTR_ERR(qmp->ufs_reset);
984 				dev_err(qmp->dev,
985 					"failed to get UFS reset: %d\n",
986 					ret);
987 
988 				qmp->ufs_reset = NULL;
989 				return ret;
990 			}
991 		}
992 
993 		ret = reset_control_assert(qmp->ufs_reset);
994 		if (ret)
995 			return ret;
996 	}
997 
998 	ret = qcom_qmp_phy_ufs_com_init(qphy);
999 	if (ret)
1000 		return ret;
1001 
1002 	return 0;
1003 }
1004 
1005 static int qcom_qmp_phy_ufs_power_on(struct phy *phy)
1006 {
1007 	struct qmp_phy *qphy = phy_get_drvdata(phy);
1008 	struct qcom_qmp *qmp = qphy->qmp;
1009 	const struct qmp_phy_cfg *cfg = qphy->cfg;
1010 	void __iomem *tx = qphy->tx;
1011 	void __iomem *rx = qphy->rx;
1012 	void __iomem *pcs = qphy->pcs;
1013 	void __iomem *status;
1014 	unsigned int mask, val, ready;
1015 	int ret;
1016 
1017 	qcom_qmp_phy_ufs_serdes_init(qphy);
1018 
1019 	/* Tx, Rx, and PCS configurations */
1020 	qcom_qmp_phy_ufs_configure_lane(tx, cfg->regs,
1021 				    cfg->tx_tbl, cfg->tx_tbl_num, 1);
1022 
1023 	/* Configuration for other LANE for USB-DP combo PHY */
1024 	if (cfg->is_dual_lane_phy) {
1025 		qcom_qmp_phy_ufs_configure_lane(qphy->tx2, cfg->regs,
1026 					    cfg->tx_tbl, cfg->tx_tbl_num, 2);
1027 	}
1028 
1029 	qcom_qmp_phy_ufs_configure_lane(rx, cfg->regs,
1030 				    cfg->rx_tbl, cfg->rx_tbl_num, 1);
1031 
1032 	if (cfg->is_dual_lane_phy) {
1033 		qcom_qmp_phy_ufs_configure_lane(qphy->rx2, cfg->regs,
1034 					    cfg->rx_tbl, cfg->rx_tbl_num, 2);
1035 	}
1036 
1037 	qcom_qmp_phy_ufs_configure(pcs, cfg->regs, cfg->pcs_tbl, cfg->pcs_tbl_num);
1038 
1039 	ret = reset_control_deassert(qmp->ufs_reset);
1040 	if (ret)
1041 		return ret;
1042 
1043 	/* Pull PHY out of reset state */
1044 	if (!cfg->no_pcs_sw_reset)
1045 		qphy_clrbits(pcs, cfg->regs[QPHY_SW_RESET], SW_RESET);
1046 	/* start SerDes and Phy-Coding-Sublayer */
1047 	qphy_setbits(pcs, cfg->regs[QPHY_START_CTRL], cfg->start_ctrl);
1048 
1049 	status = pcs + cfg->regs[QPHY_PCS_READY_STATUS];
1050 	mask = PCS_READY;
1051 	ready = PCS_READY;
1052 
1053 	ret = readl_poll_timeout(status, val, (val & mask) == ready, 10,
1054 				 PHY_INIT_COMPLETE_TIMEOUT);
1055 	if (ret) {
1056 		dev_err(qmp->dev, "phy initialization timed-out\n");
1057 		return ret;
1058 	}
1059 
1060 	return 0;
1061 }
1062 
1063 static int qcom_qmp_phy_ufs_power_off(struct phy *phy)
1064 {
1065 	struct qmp_phy *qphy = phy_get_drvdata(phy);
1066 	const struct qmp_phy_cfg *cfg = qphy->cfg;
1067 
1068 	/* PHY reset */
1069 	if (!cfg->no_pcs_sw_reset)
1070 		qphy_setbits(qphy->pcs, cfg->regs[QPHY_SW_RESET], SW_RESET);
1071 
1072 	/* stop SerDes and Phy-Coding-Sublayer */
1073 	qphy_clrbits(qphy->pcs, cfg->regs[QPHY_START_CTRL], cfg->start_ctrl);
1074 
1075 	/* Put PHY into POWER DOWN state: active low */
1076 	if (cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL]) {
1077 		qphy_clrbits(qphy->pcs, cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL],
1078 			     cfg->pwrdn_ctrl);
1079 	} else {
1080 		qphy_clrbits(qphy->pcs, QPHY_V2_PCS_POWER_DOWN_CONTROL,
1081 				cfg->pwrdn_ctrl);
1082 	}
1083 
1084 	return 0;
1085 }
1086 
1087 static int qcom_qmp_phy_ufs_exit(struct phy *phy)
1088 {
1089 	struct qmp_phy *qphy = phy_get_drvdata(phy);
1090 
1091 	qcom_qmp_phy_ufs_com_exit(qphy);
1092 
1093 	return 0;
1094 }
1095 
1096 static int qcom_qmp_phy_ufs_enable(struct phy *phy)
1097 {
1098 	int ret;
1099 
1100 	ret = qcom_qmp_phy_ufs_init(phy);
1101 	if (ret)
1102 		return ret;
1103 
1104 	ret = qcom_qmp_phy_ufs_power_on(phy);
1105 	if (ret)
1106 		qcom_qmp_phy_ufs_exit(phy);
1107 
1108 	return ret;
1109 }
1110 
1111 static int qcom_qmp_phy_ufs_disable(struct phy *phy)
1112 {
1113 	int ret;
1114 
1115 	ret = qcom_qmp_phy_ufs_power_off(phy);
1116 	if (ret)
1117 		return ret;
1118 	return qcom_qmp_phy_ufs_exit(phy);
1119 }
1120 
1121 static int qcom_qmp_phy_ufs_set_mode(struct phy *phy,
1122 				 enum phy_mode mode, int submode)
1123 {
1124 	struct qmp_phy *qphy = phy_get_drvdata(phy);
1125 
1126 	qphy->mode = mode;
1127 
1128 	return 0;
1129 }
1130 
1131 static int qcom_qmp_phy_ufs_vreg_init(struct device *dev, const struct qmp_phy_cfg *cfg)
1132 {
1133 	struct qcom_qmp *qmp = dev_get_drvdata(dev);
1134 	int num = cfg->num_vregs;
1135 	int i;
1136 
1137 	qmp->vregs = devm_kcalloc(dev, num, sizeof(*qmp->vregs), GFP_KERNEL);
1138 	if (!qmp->vregs)
1139 		return -ENOMEM;
1140 
1141 	for (i = 0; i < num; i++)
1142 		qmp->vregs[i].supply = cfg->vreg_list[i];
1143 
1144 	return devm_regulator_bulk_get(dev, num, qmp->vregs);
1145 }
1146 
1147 static int qcom_qmp_phy_ufs_clk_init(struct device *dev, const struct qmp_phy_cfg *cfg)
1148 {
1149 	struct qcom_qmp *qmp = dev_get_drvdata(dev);
1150 	int num = cfg->num_clks;
1151 	int i;
1152 
1153 	qmp->clks = devm_kcalloc(dev, num, sizeof(*qmp->clks), GFP_KERNEL);
1154 	if (!qmp->clks)
1155 		return -ENOMEM;
1156 
1157 	for (i = 0; i < num; i++)
1158 		qmp->clks[i].id = cfg->clk_list[i];
1159 
1160 	return devm_clk_bulk_get(dev, num, qmp->clks);
1161 }
1162 
1163 static const struct phy_ops qcom_qmp_ufs_ops = {
1164 	.power_on	= qcom_qmp_phy_ufs_enable,
1165 	.power_off	= qcom_qmp_phy_ufs_disable,
1166 	.set_mode	= qcom_qmp_phy_ufs_set_mode,
1167 	.owner		= THIS_MODULE,
1168 };
1169 
1170 static
1171 int qcom_qmp_phy_ufs_create(struct device *dev, struct device_node *np, int id,
1172 			void __iomem *serdes, const struct qmp_phy_cfg *cfg)
1173 {
1174 	struct qcom_qmp *qmp = dev_get_drvdata(dev);
1175 	struct phy *generic_phy;
1176 	struct qmp_phy *qphy;
1177 	int ret;
1178 
1179 	qphy = devm_kzalloc(dev, sizeof(*qphy), GFP_KERNEL);
1180 	if (!qphy)
1181 		return -ENOMEM;
1182 
1183 	qphy->cfg = cfg;
1184 	qphy->serdes = serdes;
1185 	/*
1186 	 * Get memory resources for each phy lane:
1187 	 * Resources are indexed as: tx -> 0; rx -> 1; pcs -> 2.
1188 	 * For dual lane PHYs: tx2 -> 3, rx2 -> 4, pcs_misc (optional) -> 5
1189 	 * For single lane PHYs: pcs_misc (optional) -> 3.
1190 	 */
1191 	qphy->tx = of_iomap(np, 0);
1192 	if (!qphy->tx)
1193 		return -ENOMEM;
1194 
1195 	qphy->rx = of_iomap(np, 1);
1196 	if (!qphy->rx)
1197 		return -ENOMEM;
1198 
1199 	qphy->pcs = of_iomap(np, 2);
1200 	if (!qphy->pcs)
1201 		return -ENOMEM;
1202 
1203 	/*
1204 	 * If this is a dual-lane PHY, then there should be registers for the
1205 	 * second lane. Some old device trees did not specify this, so fall
1206 	 * back to old legacy behavior of assuming they can be reached at an
1207 	 * offset from the first lane.
1208 	 */
1209 	if (cfg->is_dual_lane_phy) {
1210 		qphy->tx2 = of_iomap(np, 3);
1211 		qphy->rx2 = of_iomap(np, 4);
1212 		if (!qphy->tx2 || !qphy->rx2) {
1213 			dev_warn(dev,
1214 				 "Underspecified device tree, falling back to legacy register regions\n");
1215 
1216 			/* In the old version, pcs_misc is at index 3. */
1217 			qphy->pcs_misc = qphy->tx2;
1218 			qphy->tx2 = qphy->tx + QMP_PHY_LEGACY_LANE_STRIDE;
1219 			qphy->rx2 = qphy->rx + QMP_PHY_LEGACY_LANE_STRIDE;
1220 
1221 		} else {
1222 			qphy->pcs_misc = of_iomap(np, 5);
1223 		}
1224 
1225 	} else {
1226 		qphy->pcs_misc = of_iomap(np, 3);
1227 	}
1228 
1229 	if (!qphy->pcs_misc)
1230 		dev_vdbg(dev, "PHY pcs_misc-reg not used\n");
1231 
1232 	generic_phy = devm_phy_create(dev, np, &qcom_qmp_ufs_ops);
1233 	if (IS_ERR(generic_phy)) {
1234 		ret = PTR_ERR(generic_phy);
1235 		dev_err(dev, "failed to create qphy %d\n", ret);
1236 		return ret;
1237 	}
1238 
1239 	qphy->phy = generic_phy;
1240 	qphy->index = id;
1241 	qphy->qmp = qmp;
1242 	qmp->phys[id] = qphy;
1243 	phy_set_drvdata(generic_phy, qphy);
1244 
1245 	return 0;
1246 }
1247 
1248 static const struct of_device_id qcom_qmp_phy_ufs_of_match_table[] = {
1249 	{
1250 		.compatible = "qcom,msm8996-qmp-ufs-phy",
1251 		.data = &msm8996_ufs_cfg,
1252 	}, {
1253 		.compatible = "qcom,msm8998-qmp-ufs-phy",
1254 		.data = &sdm845_ufsphy_cfg,
1255 	}, {
1256 		.compatible = "qcom,sc8180x-qmp-ufs-phy",
1257 		.data = &sm8150_ufsphy_cfg,
1258 	}, {
1259 		.compatible = "qcom,sc8280xp-qmp-ufs-phy",
1260 		.data = &sm8350_ufsphy_cfg,
1261 	}, {
1262 		.compatible = "qcom,sdm845-qmp-ufs-phy",
1263 		.data = &sdm845_ufsphy_cfg,
1264 	}, {
1265 		.compatible = "qcom,sm6115-qmp-ufs-phy",
1266 		.data = &sm6115_ufsphy_cfg,
1267 	}, {
1268 		.compatible = "qcom,sm6350-qmp-ufs-phy",
1269 		.data = &sdm845_ufsphy_cfg,
1270 	}, {
1271 		.compatible = "qcom,sm8150-qmp-ufs-phy",
1272 		.data = &sm8150_ufsphy_cfg,
1273 	}, {
1274 		.compatible = "qcom,sm8250-qmp-ufs-phy",
1275 		.data = &sm8150_ufsphy_cfg,
1276 	}, {
1277 		.compatible = "qcom,sm8350-qmp-ufs-phy",
1278 		.data = &sm8350_ufsphy_cfg,
1279 	}, {
1280 		.compatible = "qcom,sm8450-qmp-ufs-phy",
1281 		.data = &sm8450_ufsphy_cfg,
1282 	},
1283 	{ },
1284 };
1285 MODULE_DEVICE_TABLE(of, qcom_qmp_phy_ufs_of_match_table);
1286 
1287 static int qcom_qmp_phy_ufs_probe(struct platform_device *pdev)
1288 {
1289 	struct qcom_qmp *qmp;
1290 	struct device *dev = &pdev->dev;
1291 	struct device_node *child;
1292 	struct phy_provider *phy_provider;
1293 	void __iomem *serdes;
1294 	const struct qmp_phy_cfg *cfg = NULL;
1295 	int num, id;
1296 	int ret;
1297 
1298 	qmp = devm_kzalloc(dev, sizeof(*qmp), GFP_KERNEL);
1299 	if (!qmp)
1300 		return -ENOMEM;
1301 
1302 	qmp->dev = dev;
1303 	dev_set_drvdata(dev, qmp);
1304 
1305 	/* Get the specific init parameters of QMP phy */
1306 	cfg = of_device_get_match_data(dev);
1307 	if (!cfg)
1308 		return -EINVAL;
1309 
1310 	/* per PHY serdes; usually located at base address */
1311 	serdes = devm_platform_ioremap_resource(pdev, 0);
1312 	if (IS_ERR(serdes))
1313 		return PTR_ERR(serdes);
1314 
1315 	ret = qcom_qmp_phy_ufs_clk_init(dev, cfg);
1316 	if (ret)
1317 		return ret;
1318 
1319 	ret = qcom_qmp_phy_ufs_vreg_init(dev, cfg);
1320 	if (ret) {
1321 		if (ret != -EPROBE_DEFER)
1322 			dev_err(dev, "failed to get regulator supplies: %d\n",
1323 				ret);
1324 		return ret;
1325 	}
1326 
1327 	num = of_get_available_child_count(dev->of_node);
1328 	/* do we have a rogue child node ? */
1329 	if (num > 1)
1330 		return -EINVAL;
1331 
1332 	qmp->phys = devm_kcalloc(dev, num, sizeof(*qmp->phys), GFP_KERNEL);
1333 	if (!qmp->phys)
1334 		return -ENOMEM;
1335 
1336 	pm_runtime_set_active(dev);
1337 	pm_runtime_enable(dev);
1338 	/*
1339 	 * Prevent runtime pm from being ON by default. Users can enable
1340 	 * it using power/control in sysfs.
1341 	 */
1342 	pm_runtime_forbid(dev);
1343 
1344 	id = 0;
1345 	for_each_available_child_of_node(dev->of_node, child) {
1346 		/* Create per-lane phy */
1347 		ret = qcom_qmp_phy_ufs_create(dev, child, id, serdes, cfg);
1348 		if (ret) {
1349 			dev_err(dev, "failed to create lane%d phy, %d\n",
1350 				id, ret);
1351 			goto err_node_put;
1352 		}
1353 
1354 		id++;
1355 	}
1356 
1357 	phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate);
1358 	if (!IS_ERR(phy_provider))
1359 		dev_info(dev, "Registered Qcom-QMP phy\n");
1360 	else
1361 		pm_runtime_disable(dev);
1362 
1363 	return PTR_ERR_OR_ZERO(phy_provider);
1364 
1365 err_node_put:
1366 	pm_runtime_disable(dev);
1367 	of_node_put(child);
1368 	return ret;
1369 }
1370 
1371 static struct platform_driver qcom_qmp_phy_ufs_driver = {
1372 	.probe		= qcom_qmp_phy_ufs_probe,
1373 	.driver = {
1374 		.name	= "qcom-qmp-ufs-phy",
1375 		.of_match_table = qcom_qmp_phy_ufs_of_match_table,
1376 	},
1377 };
1378 
1379 module_platform_driver(qcom_qmp_phy_ufs_driver);
1380 
1381 MODULE_AUTHOR("Vivek Gautam <vivek.gautam@codeaurora.org>");
1382 MODULE_DESCRIPTION("Qualcomm QMP UFS PHY driver");
1383 MODULE_LICENSE("GPL v2");
1384