xref: /OK3568_Linux_fs/kernel/drivers/media/i2c/rk628/rk628_mipi_dphy.h (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 /* SPDX-License-Identifier: GPL-2.0 */
2 /*
3  * Copyright (c) 2020 Rockchip Electronics Co. Ltd.
4  *
5  * Author: Shunqing Chen <csq@rock-chips.com>
6  */
7 
8 #ifndef _RK628_MIPI_DPHY_H
9 #define _RK628_MIPI_DPHY_H
10 
11 #include <linux/module.h>
12 #include <linux/i2c.h>
13 #include <linux/regmap.h>
14 
15 #include "rk628_csi.h"
16 #include "rk628_dsi.h"
17 #include "rk628.h"
18 
19 /* Test Code: 0x44 (HS RX Control of Lane 0) */
20 #define HSFREQRANGE(x)			UPDATE(x, 6, 1)
21 
testif_testclk_assert(struct rk628 * rk628)22 static inline void testif_testclk_assert(struct rk628 *rk628)
23 {
24 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
25 			   PHY_TESTCLK, PHY_TESTCLK);
26 	udelay(1);
27 }
28 
testif_testclk_deassert(struct rk628 * rk628)29 static inline void testif_testclk_deassert(struct rk628 *rk628)
30 {
31 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
32 			   PHY_TESTCLK, 0);
33 	udelay(1);
34 }
35 
testif_testclr_assert(struct rk628 * rk628)36 static inline void testif_testclr_assert(struct rk628 *rk628)
37 {
38 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
39 			   PHY_TESTCLR, PHY_TESTCLR);
40 	udelay(1);
41 }
42 
testif_testclr_deassert(struct rk628 * rk628)43 static inline void testif_testclr_deassert(struct rk628 *rk628)
44 {
45 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
46 			   PHY_TESTCLR, 0);
47 	udelay(1);
48 }
49 
testif_testen_assert(struct rk628 * rk628)50 static inline void testif_testen_assert(struct rk628 *rk628)
51 {
52 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
53 			   PHY_TESTEN, PHY_TESTEN);
54 	udelay(1);
55 }
56 
testif_testen_deassert(struct rk628 * rk628)57 static inline void testif_testen_deassert(struct rk628 *rk628)
58 {
59 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
60 			   PHY_TESTEN, 0);
61 	udelay(1);
62 }
63 
testif_set_data(struct rk628 * rk628,u8 data)64 static inline void testif_set_data(struct rk628 *rk628, u8 data)
65 {
66 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
67 			   PHY_TESTDIN_MASK, PHY_TESTDIN(data));
68 	udelay(1);
69 }
70 
testif_get_data(struct rk628 * rk628)71 static inline u8 testif_get_data(struct rk628 *rk628)
72 {
73 	u32 data = 0;
74 
75 	rk628_i2c_read(rk628, GRF_DPHY0_STATUS, &data);
76 
77 	return data >> PHY_TESTDOUT_SHIFT;
78 }
79 
testif_test_code_write(struct rk628 * rk628,u8 test_code)80 static void testif_test_code_write(struct rk628 *rk628, u8 test_code)
81 {
82 	testif_testclk_assert(rk628);
83 	testif_set_data(rk628, test_code);
84 	testif_testen_assert(rk628);
85 	testif_testclk_deassert(rk628);
86 	testif_testen_deassert(rk628);
87 }
88 
testif_test_data_write(struct rk628 * rk628,u8 test_data)89 static void testif_test_data_write(struct rk628 *rk628, u8 test_data)
90 {
91 	testif_testclk_deassert(rk628);
92 	testif_set_data(rk628, test_data);
93 	testif_testclk_assert(rk628);
94 }
95 
testif_write(struct rk628 * rk628,u8 test_code,u8 test_data)96 static u8 testif_write(struct rk628 *rk628, u8 test_code, u8 test_data)
97 {
98 	u8 monitor_data;
99 
100 	testif_test_code_write(rk628, test_code);
101 	testif_test_data_write(rk628, test_data);
102 	monitor_data = testif_get_data(rk628);
103 
104 	dev_dbg(rk628->dev, "test_code=0x%02x, ", test_code);
105 	dev_dbg(rk628->dev, "test_data=0x%02x, ", test_data);
106 	dev_dbg(rk628->dev, "monitor_data=0x%02x\n", monitor_data);
107 
108 	return monitor_data;
109 }
110 
testif_read(struct rk628 * rk628,u8 test_code)111 static inline u8 testif_read(struct rk628 *rk628, u8 test_code)
112 {
113 	u8 test_data;
114 
115 	testif_test_code_write(rk628, test_code);
116 	test_data = testif_get_data(rk628);
117 	testif_test_data_write(rk628, test_data);
118 
119 	return test_data;
120 }
121 
mipi_dphy_enableclk_assert(struct rk628 * rk628)122 static inline void mipi_dphy_enableclk_assert(struct rk628 *rk628)
123 {
124 	rk628_i2c_update_bits(rk628, CSITX_DPHY_CTRL, DPHY_ENABLECLK,
125 			DPHY_ENABLECLK);
126 	udelay(1);
127 }
128 
mipi_dphy_enableclk_deassert(struct rk628 * rk628)129 static inline void mipi_dphy_enableclk_deassert(struct rk628 *rk628)
130 {
131 	rk628_i2c_update_bits(rk628, CSITX_DPHY_CTRL, DPHY_ENABLECLK, 0);
132 	udelay(1);
133 }
134 
mipi_dphy_shutdownz_assert(struct rk628 * rk628)135 static inline void mipi_dphy_shutdownz_assert(struct rk628 *rk628)
136 {
137 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON, CSI_PHYSHUTDOWNZ, 0);
138 	udelay(1);
139 }
140 
mipi_dphy_shutdownz_deassert(struct rk628 * rk628)141 static inline void mipi_dphy_shutdownz_deassert(struct rk628 *rk628)
142 {
143 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON, CSI_PHYSHUTDOWNZ,
144 			CSI_PHYSHUTDOWNZ);
145 	udelay(1);
146 }
147 
mipi_dphy_rstz_assert(struct rk628 * rk628)148 static inline void mipi_dphy_rstz_assert(struct rk628 *rk628)
149 {
150 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON, CSI_PHYRSTZ, 0);
151 	udelay(1);
152 }
153 
mipi_dphy_rstz_deassert(struct rk628 * rk628)154 static inline void mipi_dphy_rstz_deassert(struct rk628 *rk628)
155 {
156 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON, CSI_PHYRSTZ,
157 			CSI_PHYRSTZ);
158 	udelay(1);
159 }
160 
mipi_dphy_init_hsfreqrange(struct rk628 * rk628,int lane_mbps)161 static inline void mipi_dphy_init_hsfreqrange(struct rk628 *rk628, int lane_mbps)
162 {
163 	const struct {
164 		unsigned long max_lane_mbps;
165 		u8 hsfreqrange;
166 	} hsfreqrange_table[] = {
167 		{  90, 0x00}, { 100, 0x10}, { 110, 0x20}, { 130, 0x01},
168 		{ 140, 0x11}, { 150, 0x21}, { 170, 0x02}, { 180, 0x12},
169 		{ 200, 0x22}, { 220, 0x03}, { 240, 0x13}, { 250, 0x23},
170 		{ 270, 0x04}, { 300, 0x14}, { 330, 0x05}, { 360, 0x15},
171 		{ 400, 0x25}, { 450, 0x06}, { 500, 0x16}, { 550, 0x07},
172 		{ 600, 0x17}, { 650, 0x08}, { 700, 0x18}, { 750, 0x09},
173 		{ 800, 0x19}, { 850, 0x29}, { 900, 0x39}, { 950, 0x0a},
174 		{1000, 0x1a}, {1050, 0x2a}, {1100, 0x3a}, {1150, 0x0b},
175 		{1200, 0x1b}, {1250, 0x2b}, {1300, 0x3b}, {1350, 0x0c},
176 		{1400, 0x1c}, {1450, 0x2c}, {1500, 0x3c}
177 	};
178 	u8 hsfreqrange;
179 	unsigned int index;
180 
181 	for (index = 0; index < ARRAY_SIZE(hsfreqrange_table); index++)
182 		if (lane_mbps <= hsfreqrange_table[index].max_lane_mbps)
183 			break;
184 
185 	if (index == ARRAY_SIZE(hsfreqrange_table))
186 		--index;
187 
188 	hsfreqrange = hsfreqrange_table[index].hsfreqrange;
189 	testif_write(rk628, 0x44, HSFREQRANGE(hsfreqrange));
190 }
191 
mipi_dphy_reset(struct rk628 * rk628)192 static inline int mipi_dphy_reset(struct rk628 *rk628)
193 {
194 	u32 val, mask;
195 
196 	mipi_dphy_enableclk_deassert(rk628);
197 	mipi_dphy_shutdownz_assert(rk628);
198 	mipi_dphy_rstz_assert(rk628);
199 	testif_testclr_assert(rk628);
200 
201 	/* Set all REQUEST inputs to zero */
202 	rk628_i2c_update_bits(rk628, GRF_MIPI_TX0_CON,
203 		     FORCETXSTOPMODE_MASK | FORCERXMODE_MASK,
204 		     FORCETXSTOPMODE(0) | FORCERXMODE(0));
205 	udelay(1);
206 	testif_testclr_deassert(rk628);
207 	mipi_dphy_enableclk_assert(rk628);
208 	mipi_dphy_shutdownz_deassert(rk628);
209 	mipi_dphy_rstz_deassert(rk628);
210 	usleep_range(1500, 2000);
211 
212 	mask = STOPSTATE_CLK | STOPSTATE_LANE0;
213 	rk628_i2c_read(rk628, CSITX_CSITX_STATUS1, &val);
214 	if ((val & mask) != mask) {
215 		dev_err(rk628->dev, "lane module is not in stop state\n");
216 		return -1;
217 	}
218 
219 	return 0;
220 }
221 
222 #endif
223