xref: /rk3399_rockchip-uboot/drivers/video/drm/display-serdes/serdes-i2c.c (revision 77c57384925823ac7325dead6d2664651a86d016)
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * serdes-bridge.c  --  display bridge for different serdes chips
4  *
5  * Copyright (c) 2023 Rockchip Electronics Co. Ltd.
6  *
7  * Author: luowei <lw@rock-chips.com>
8  */
9 
10 #include "core.h"
11 
12 static struct serdes *g_serdes_ser_split[MAX_NUM_SERDES_SPLIT];
13 
serdes_i2c_init(struct serdes * serdes)14 static void serdes_i2c_init(struct serdes *serdes)
15 {
16 	if (serdes->vpower_supply)
17 		regulator_set_enable(serdes->vpower_supply, true);
18 
19 	if (dm_gpio_is_valid(&serdes->enable_gpio))
20 		dm_gpio_set_value(&serdes->enable_gpio, 1);
21 
22 	//mdelay(5);
23 
24 	//video_bridge_set_active(serdes->dev, true);
25 
26 	if (serdes->chip_data->bridge_ops->init)
27 		serdes->chip_data->bridge_ops->init(serdes);
28 
29 	serdes_i2c_set_sequence(serdes);
30 
31 	SERDES_DBG_MFD("%s: %s %s\n", __func__,
32 		       serdes->dev->name,
33 		       serdes->chip_data->name);
34 }
35 
serdes_set_i2c_address(struct serdes * serdes,u32 reg_hw,u32 reg_use,int link)36 static int serdes_set_i2c_address(struct serdes *serdes,
37 				  u32 reg_hw, u32 reg_use, int link)
38 {
39 	int ret = 0;
40 	struct dm_i2c_chip *chip_split;
41 	struct serdes *serdes_split = serdes->g_serdes_bridge_split;
42 
43 	if (!serdes_split) {
44 		pr_info("%s: serdes_split is null\n", __func__);
45 		return -1;
46 	}
47 
48 	chip_split = dev_get_parent_platdata(serdes->dev);
49 	SERDES_DBG_MFD("%s: %s addr=0x%x reg_hw=0x%x, reg_use=0x%x split=0x%p\n",
50 		       __func__, serdes_split->dev->name,
51 		       chip_split->chip_addr, serdes->reg_hw,
52 		       serdes->reg_use, serdes_split);
53 
54 	chip_split->chip_addr = serdes->reg_hw;
55 
56 	if (serdes_split && serdes_split->chip_data->split_ops &&
57 	    serdes_split->chip_data->split_ops->select)
58 		ret = serdes_split->chip_data->split_ops->select(serdes_split, link);
59 
60 	if (serdes->chip_data->split_ops &&
61 	    serdes->chip_data->split_ops->set_i2c_addr)
62 		serdes->chip_data->split_ops->set_i2c_addr(serdes,
63 							   reg_use, link);
64 
65 	if (serdes_split && serdes_split->chip_data->split_ops &&
66 	    serdes_split->chip_data->split_ops->select)
67 		ret = serdes_split->chip_data->split_ops->select(serdes_split,
68 								 SER_SPLITTER_MODE);
69 
70 	chip_split->chip_addr = serdes->reg_use;
71 
72 	serdes_i2c_set_sequence(serdes);
73 
74 	return ret;
75 }
76 
serdes_i2c_probe(struct udevice * dev)77 static int serdes_i2c_probe(struct udevice *dev)
78 {
79 	struct serdes *serdes = dev_get_priv(dev);
80 	struct serdes_bridge *serdes_bridge = NULL;
81 	struct serdes_bridge_split *serdes_bridge_split = NULL;
82 
83 	int ret;
84 
85 	ret = i2c_set_chip_offset_len(dev, 2);
86 	if (ret)
87 		return ret;
88 
89 	serdes->dev = dev;
90 	serdes->chip_data = (struct serdes_chip_data *)dev_get_driver_data(dev);
91 	serdes->type = serdes->chip_data->serdes_type;
92 
93 	SERDES_DBG_MFD("serdes %s %s probe start serdes=%p\n",
94 		       serdes->dev->name, serdes->chip_data->name, serdes);
95 
96 	ret = uclass_get_device_by_phandle(UCLASS_REGULATOR, dev,
97 					   "vpower-supply",
98 					   &serdes->vpower_supply);
99 	if (ret && ret != -ENOENT)
100 		SERDES_DBG_MFD("%s: Cannot get power supply: %d\n",
101 			       __func__, ret);
102 
103 	ret = gpio_request_by_name(dev, "enable-gpios", 0,
104 				   &serdes->enable_gpio, GPIOD_IS_OUT);
105 	if (ret)
106 		SERDES_DBG_MFD("%s: failed to get enable gpio: %d\n",
107 			       __func__, ret);
108 
109 	ret = gpio_request_by_name(dev, "lock-gpios", 0, &serdes->lock_gpio,
110 				   GPIOD_IS_IN);
111 	if (ret)
112 		SERDES_DBG_MFD("%s: failed to get lock gpio: %d\n",
113 			       __func__, ret);
114 
115 	ret = gpio_request_by_name(dev, "err-gpios", 0, &serdes->err_gpio,
116 				   GPIOD_IS_IN);
117 	if (ret)
118 		SERDES_DBG_MFD("%s: failed to err gpio: %d\n",
119 			       __func__, ret);
120 
121 	serdes->mcu_enable = dev_read_bool(dev, "mcu-enable");
122 
123 	if (serdes->chip_data->serdes_type == TYPE_OTHER) {
124 		SERDES_DBG_MFD("TYPE_OTHER just need only init i2c\n");
125 		serdes_i2c_init(serdes);
126 		return 0;
127 	}
128 
129 	ret = serdes_get_init_seq(serdes);
130 	if (ret)
131 		return ret;
132 
133 	if (serdes->chip_data->serdes_type == TYPE_SER)
134 		serdes_i2c_init(serdes);
135 
136 	if (serdes->chip_data->bridge_ops) {
137 		serdes_bridge = calloc(1, sizeof(*serdes_bridge));
138 		if (!serdes_bridge)
139 			return -ENOMEM;
140 		serdes->serdes_bridge = serdes_bridge;
141 
142 		serdes_bridge_split = calloc(1, sizeof(*serdes_bridge_split));
143 		if (!serdes_bridge_split)
144 			return -ENOMEM;
145 		serdes->serdes_bridge_split = serdes_bridge_split;
146 	}
147 
148 	ret = serdes_pinctrl_register(dev);
149 	if (ret)
150 		return ret;
151 
152 	serdes->id_serdes_bridge_split = dev_read_u32_default(dev, "id-serdes-bridge-split", 0);
153 	if ((serdes->id_serdes_bridge_split < MAX_NUM_SERDES_SPLIT) && (serdes->type == TYPE_SER)) {
154 		g_serdes_ser_split[serdes->id_serdes_bridge_split] = serdes;
155 		SERDES_DBG_MFD("%s: %s-%s g_serdes_split[%d]=0x%p\n", __func__,
156 			       serdes->dev->name, serdes->chip_data->name,
157 			       serdes->id_serdes_bridge_split, serdes);
158 	}
159 
160 	serdes->reg_hw = dev_read_u32_default(dev, "reg-hw", 0);
161 	serdes->reg_use = dev_read_u32_default(dev, "reg", 0);
162 	serdes->link_use = dev_read_u32_default(dev, "link", 0);
163 	serdes->id_serdes_panel_split = dev_read_u32_default(dev, "id-serdes-panel-split", 0);
164 
165 	if ((serdes->id_serdes_panel_split) && (serdes->type == TYPE_DES)) {
166 		serdes->g_serdes_bridge_split = g_serdes_ser_split[serdes->id_serdes_panel_split];
167 		SERDES_DBG_MFD("%s: id=%d p=0x%p\n", __func__,
168 			       serdes->id_serdes_panel_split,
169 			       serdes->g_serdes_bridge_split);
170 	}
171 
172 	if (serdes->reg_hw) {
173 		SERDES_DBG_MFD("%s: %s change i2c addr from 0x%x to 0x%x\n",
174 			       __func__, dev->name,
175 			       serdes->reg_hw, serdes->reg_use);
176 		serdes_set_i2c_address(serdes, serdes->reg_hw,
177 				       serdes->reg_use, serdes->link_use);
178 	}
179 
180 	printf("%s %s %s successful\n",
181 	       __func__,
182 	       serdes->dev->name,
183 	       serdes->chip_data->name);
184 
185 	return 0;
186 }
187 
188 static const struct udevice_id serdes_of_match[] = {
189 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_ROHM_BU18TL82)
190 	{ .compatible = "rohm,bu18tl82",
191 		.data = (ulong)&serdes_bu18tl82_data },
192 #endif
193 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_ROHM_BU18RL82)
194 	{ .compatible = "rohm,bu18rl82",
195 		.data = (ulong)&serdes_bu18rl82_data },
196 #endif
197 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_MAXIM_MAX96745)
198 	{ .compatible = "maxim,max96745",
199 		.data = (ulong)&serdes_max96745_data },
200 #endif
201 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_MAXIM_MAX96755)
202 	{ .compatible = "maxim,max96755",
203 		.data = (ulong)&serdes_max96755_data },
204 #endif
205 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_MAXIM_MAX96789)
206 	{ .compatible = "maxim,max96789",
207 		.data = (ulong)&serdes_max96789_data },
208 #endif
209 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_ROCKCHIP_RKX111)
210 	{ .compatible = "rockchip,rkx111",
211 		.data = (ulong)&serdes_rkx111_data },
212 #endif
213 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_MAXIM_MAX96752)
214 	{ .compatible = "maxim,max96752",
215 		.data = (ulong)&serdes_max96752_data },
216 #endif
217 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_MAXIM_MAX96772)
218 	{ .compatible = "maxim,max96772",
219 		.data = (ulong)&serdes_max96772_data },
220 #endif
221 #if IS_ENABLED(CONFIG_SERDES_DISPLAY_CHIP_ROCKCHIP_RKX121)
222 	{ .compatible = "rockchip,rkx121",
223 		.data = (ulong)&serdes_rkx121_data },
224 #endif
225 	{ }
226 };
227 
228 U_BOOT_DRIVER(serdes_i2c) = {
229 	.name = "serdes-i2c",
230 	.id = UCLASS_MISC,
231 	.of_match = serdes_of_match,
232 	.probe = serdes_i2c_probe,
233 	.bind = dm_scan_fdt_dev,
234 	.priv_auto_alloc_size = sizeof(struct serdes),
235 };
236