1
2
3
4
5
6
7#include <common.h>
8#include <dm.h>
9#include <errno.h>
10#include <i2c.h>
11#include <edid.h>
12#include <video_bridge.h>
13#include "../anx98xx-edp.h"
14
15#define DP_MAX_LINK_RATE 0x001
16#define DP_MAX_LANE_COUNT 0x002
17#define DP_MAX_LANE_COUNT_MASK 0x1f
18
19DECLARE_GLOBAL_DATA_PTR;
20
21struct anx6345_priv {
22 u8 edid[EDID_SIZE];
23};
24
25static int anx6345_write(struct udevice *dev, unsigned int addr_off,
26 unsigned char reg_addr, unsigned char value)
27{
28 uint8_t buf[2];
29 struct i2c_msg msg;
30 int ret;
31
32 msg.addr = addr_off;
33 msg.flags = 0;
34 buf[0] = reg_addr;
35 buf[1] = value;
36 msg.buf = buf;
37 msg.len = 2;
38 ret = dm_i2c_xfer(dev, &msg, 1);
39 if (ret) {
40 debug("%s: write failed, reg=%#x, value=%#x, ret=%d\n",
41 __func__, reg_addr, value, ret);
42 return ret;
43 }
44
45 return 0;
46}
47
48static int anx6345_read(struct udevice *dev, unsigned int addr_off,
49 unsigned char reg_addr, unsigned char *value)
50{
51 uint8_t addr, val;
52 struct i2c_msg msg[2];
53 int ret;
54
55 msg[0].addr = addr_off;
56 msg[0].flags = 0;
57 addr = reg_addr;
58 msg[0].buf = &addr;
59 msg[0].len = 1;
60 msg[1].addr = addr_off;
61 msg[1].flags = I2C_M_RD;
62 msg[1].buf = &val;
63 msg[1].len = 1;
64 ret = dm_i2c_xfer(dev, msg, 2);
65 if (ret) {
66 debug("%s: read failed, reg=%.2x, value=%p, ret=%d\n",
67 __func__, (int)reg_addr, value, ret);
68 return ret;
69 }
70 *value = val;
71
72 return 0;
73}
74
75static int anx6345_write_r0(struct udevice *dev, unsigned char reg_addr,
76 unsigned char value)
77{
78 struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
79
80 return anx6345_write(dev, chip->chip_addr, reg_addr, value);
81}
82
83static int anx6345_read_r0(struct udevice *dev, unsigned char reg_addr,
84 unsigned char *value)
85{
86 struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
87
88 return anx6345_read(dev, chip->chip_addr, reg_addr, value);
89}
90
91static int anx6345_write_r1(struct udevice *dev, unsigned char reg_addr,
92 unsigned char value)
93{
94 struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
95
96 return anx6345_write(dev, chip->chip_addr + 1, reg_addr, value);
97}
98
99static int anx6345_read_r1(struct udevice *dev, unsigned char reg_addr,
100 unsigned char *value)
101{
102 struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
103
104 return anx6345_read(dev, chip->chip_addr + 1, reg_addr, value);
105}
106
107static int anx6345_set_backlight(struct udevice *dev, int percent)
108{
109 return -ENOSYS;
110}
111
112static int anx6345_aux_wait(struct udevice *dev)
113{
114 int ret = -ETIMEDOUT;
115 u8 v;
116 int retries = 1000;
117
118 do {
119 anx6345_read_r0(dev, ANX9804_DP_AUX_CH_CTL_2, &v);
120 if (!(v & ANX9804_AUX_EN)) {
121 ret = 0;
122 break;
123 }
124 udelay(100);
125 } while (retries--);
126
127 if (ret) {
128 debug("%s: timed out waiting for AUX_EN to clear\n", __func__);
129 return ret;
130 }
131
132 ret = -ETIMEDOUT;
133 retries = 1000;
134 do {
135 anx6345_read_r1(dev, ANX9804_DP_INT_STA, &v);
136 if (v & ANX9804_RPLY_RECEIV) {
137 ret = 0;
138 break;
139 }
140 udelay(100);
141 } while (retries--);
142
143 if (ret) {
144 debug("%s: timed out waiting to receive reply\n", __func__);
145 return ret;
146 }
147
148
149 anx6345_write_r1(dev, ANX9804_DP_INT_STA, v);
150
151 anx6345_read_r0(dev, ANX9804_AUX_CH_STA, &v);
152 if ((v & ANX9804_AUX_STATUS_MASK) != 0) {
153 debug("AUX status: %d\n", v & ANX9804_AUX_STATUS_MASK);
154 ret = -EIO;
155 }
156
157 return ret;
158}
159
160static void anx6345_aux_addr(struct udevice *dev, u32 addr)
161{
162 u8 val;
163
164 val = addr & 0xff;
165 anx6345_write_r0(dev, ANX9804_DP_AUX_ADDR_7_0, val);
166 val = (addr >> 8) & 0xff;
167 anx6345_write_r0(dev, ANX9804_DP_AUX_ADDR_15_8, val);
168 val = (addr >> 16) & 0x0f;
169 anx6345_write_r0(dev, ANX9804_DP_AUX_ADDR_19_16, val);
170}
171
172static int anx6345_aux_transfer(struct udevice *dev, u8 req,
173 u32 addr, u8 *buf, size_t len)
174{
175 int i, ret;
176 u8 ctrl1 = req;
177 u8 ctrl2 = ANX9804_AUX_EN;
178
179 if (len > 16)
180 return -E2BIG;
181
182 if (len)
183 ctrl1 |= ANX9804_AUX_LENGTH(len);
184 else
185 ctrl2 |= ANX9804_ADDR_ONLY;
186
187 if (len && !(req & ANX9804_AUX_TX_COMM_READ)) {
188 for (i = 0; i < len; i++)
189 anx6345_write_r0(dev, ANX9804_BUF_DATA_0 + i, buf[i]);
190 }
191
192 anx6345_aux_addr(dev, addr);
193 anx6345_write_r0(dev, ANX9804_DP_AUX_CH_CTL_1, ctrl1);
194 anx6345_write_r0(dev, ANX9804_DP_AUX_CH_CTL_2, ctrl2);
195 ret = anx6345_aux_wait(dev);
196 if (ret) {
197 debug("AUX transaction timed out\n");
198 return ret;
199 }
200
201 if (len && (req & ANX9804_AUX_TX_COMM_READ)) {
202 for (i = 0; i < len; i++)
203 anx6345_read_r0(dev, ANX9804_BUF_DATA_0 + i, &buf[i]);
204 }
205
206 return 0;
207}
208
209static int anx6345_read_aux_i2c(struct udevice *dev, u8 chip_addr,
210 u8 offset, size_t count, u8 *buf)
211{
212 int i, ret;
213 size_t cur_cnt;
214 u8 cur_offset;
215
216 for (i = 0; i < count; i += 16) {
217 cur_cnt = (count - i) > 16 ? 16 : count - i;
218 cur_offset = offset + i;
219 ret = anx6345_aux_transfer(dev, ANX9804_AUX_TX_COMM_MOT,
220 chip_addr, &cur_offset, 1);
221 if (ret) {
222 debug("%s: failed to set i2c offset: %d\n",
223 __func__, ret);
224 return ret;
225 }
226 ret = anx6345_aux_transfer(dev, ANX9804_AUX_TX_COMM_READ,
227 chip_addr, buf + i, cur_cnt);
228 if (ret) {
229 debug("%s: failed to read from i2c device: %d\n",
230 __func__, ret);
231 return ret;
232 }
233 }
234
235 return 0;
236}
237
238static int anx6345_read_dpcd(struct udevice *dev, u32 reg, u8 *val)
239{
240 int ret;
241
242 ret = anx6345_aux_transfer(dev,
243 ANX9804_AUX_TX_COMM_READ |
244 ANX9804_AUX_TX_COMM_DP_TRANSACTION,
245 reg, val, 1);
246 if (ret) {
247 debug("Failed to read DPCD\n");
248 return ret;
249 }
250
251 return 0;
252}
253
254static int anx6345_read_edid(struct udevice *dev, u8 *buf, int size)
255{
256 struct anx6345_priv *priv = dev_get_priv(dev);
257
258 if (size > EDID_SIZE)
259 size = EDID_SIZE;
260 memcpy(buf, priv->edid, size);
261
262 return size;
263}
264
265static int anx6345_attach(struct udevice *dev)
266{
267
268 return 0;
269}
270
271static int anx6345_enable(struct udevice *dev)
272{
273 u8 chipid, colordepth, lanes, data_rate, c;
274 int ret, i, bpp;
275 struct display_timing timing;
276 struct anx6345_priv *priv = dev_get_priv(dev);
277
278
279 ret = video_bridge_set_active(dev, true);
280 if (ret)
281 return ret;
282
283
284 anx6345_write_r1(dev, ANX9804_RST_CTRL_REG, 1);
285 mdelay(100);
286 anx6345_write_r1(dev, ANX9804_RST_CTRL_REG, 0);
287
288
289 anx6345_write_r1(dev, ANX9804_POWERD_CTRL_REG, 0);
290
291 ret = anx6345_read_r1(dev, ANX9804_DEV_IDH_REG, &chipid);
292 if (ret)
293 debug("%s: read id failed: %d\n", __func__, ret);
294
295 switch (chipid) {
296 case 0x63:
297 debug("ANX63xx detected.\n");
298 break;
299 default:
300 debug("Error anx6345 chipid mismatch: %.2x\n", (int)chipid);
301 return -ENODEV;
302 }
303
304 for (i = 0; i < 100; i++) {
305 anx6345_read_r0(dev, ANX9804_SYS_CTRL2_REG, &c);
306 anx6345_write_r0(dev, ANX9804_SYS_CTRL2_REG, c);
307 anx6345_read_r0(dev, ANX9804_SYS_CTRL2_REG, &c);
308 if ((c & ANX9804_SYS_CTRL2_CHA_STA) == 0)
309 break;
310
311 mdelay(5);
312 }
313 if (i == 100)
314 debug("Error anx6345 clock is not stable\n");
315
316
317 anx6345_write_r0(dev, ANX9804_PLL_CTRL_REG, 0x00);
318 anx6345_write_r1(dev, ANX9804_ANALOG_DEBUG_REG1, 0x70);
319 anx6345_write_r0(dev, ANX9804_LINK_DEBUG_REG, 0x30);
320
321
322 anx6345_write_r0(dev, ANX9804_SYS_CTRL3_REG,
323 ANX9804_SYS_CTRL3_F_HPD | ANX9804_SYS_CTRL3_HPD_CTRL);
324
325
326 anx6345_write_r0(dev, ANX9804_ANALOG_POWER_DOWN_REG, 0x00);
327 anx6345_write_r0(dev, ANX9804_TRAINING_LANE0_SET_REG, 0x00);
328 anx6345_write_r0(dev, ANX9804_TRAINING_LANE1_SET_REG, 0x00);
329 anx6345_write_r0(dev, ANX9804_TRAINING_LANE2_SET_REG, 0x00);
330 anx6345_write_r0(dev, ANX9804_TRAINING_LANE3_SET_REG, 0x00);
331
332
333 anx6345_write_r1(dev, ANX9804_RST_CTRL2_REG,
334 ANX9804_RST_CTRL2_AUX);
335 anx6345_write_r1(dev, ANX9804_RST_CTRL2_REG, 0);
336
337
338 anx6345_write_r1(dev, ANX9804_POWERD_CTRL_REG, ANX9804_POWERD_AUDIO);
339 anx6345_write_r0(dev, ANX9804_HDCP_CONTROL_0_REG, 0x00);
340 anx6345_write_r0(dev, 0xa7, 0x00);
341
342 anx6345_read_aux_i2c(dev, 0x50, 0x0, EDID_SIZE, priv->edid);
343 if (edid_get_timing(priv->edid, EDID_SIZE, &timing, &bpp) != 0) {
344 debug("Failed to parse EDID\n");
345 return -EIO;
346 }
347 debug("%s: panel found: %dx%d, bpp %d\n", __func__,
348 timing.hactive.typ, timing.vactive.typ, bpp);
349 if (bpp == 6)
350 colordepth = 0x00;
351 else
352 colordepth = 0x10;
353 anx6345_write_r1(dev, ANX9804_VID_CTRL2_REG, colordepth);
354
355 if (anx6345_read_dpcd(dev, DP_MAX_LINK_RATE, &data_rate)) {
356 debug("%s: Failed to DP_MAX_LINK_RATE\n", __func__);
357 return -EIO;
358 }
359 debug("%s: data_rate: %d\n", __func__, (int)data_rate);
360 if (anx6345_read_dpcd(dev, DP_MAX_LANE_COUNT, &lanes)) {
361 debug("%s: Failed to read DP_MAX_LANE_COUNT\n", __func__);
362 return -EIO;
363 }
364 lanes &= DP_MAX_LANE_COUNT_MASK;
365 debug("%s: lanes: %d\n", __func__, (int)lanes);
366
367
368 anx6345_write_r0(dev, ANX9804_LINK_BW_SET_REG, data_rate);
369 anx6345_write_r0(dev, ANX9804_LANE_COUNT_SET_REG, lanes);
370
371
372 anx6345_write_r0(dev, ANX9804_LINK_TRAINING_CTRL_REG,
373 ANX9804_LINK_TRAINING_CTRL_EN);
374 mdelay(5);
375 for (i = 0; i < 100; i++) {
376 anx6345_read_r0(dev, ANX9804_LINK_TRAINING_CTRL_REG, &c);
377 if ((chipid == 0x63) && (c & 0x80) == 0)
378 break;
379
380 mdelay(5);
381 }
382 if (i == 100) {
383 debug("Error anx6345 link training timeout\n");
384 return -ENODEV;
385 }
386
387
388 anx6345_write_r1(dev, ANX9804_VID_CTRL1_REG,
389 ANX9804_VID_CTRL1_VID_EN | ANX9804_VID_CTRL1_EDGE);
390
391 anx6345_write_r0(dev, ANX9804_SYS_CTRL3_REG,
392 ANX9804_SYS_CTRL3_F_HPD |
393 ANX9804_SYS_CTRL3_HPD_CTRL |
394 ANX9804_SYS_CTRL3_F_VALID |
395 ANX9804_SYS_CTRL3_VALID_CTRL);
396
397 return 0;
398}
399
400static int anx6345_probe(struct udevice *dev)
401{
402 if (device_get_uclass_id(dev->parent) != UCLASS_I2C)
403 return -EPROTONOSUPPORT;
404
405 return anx6345_enable(dev);
406}
407
408struct video_bridge_ops anx6345_ops = {
409 .attach = anx6345_attach,
410 .set_backlight = anx6345_set_backlight,
411 .read_edid = anx6345_read_edid,
412};
413
414static const struct udevice_id anx6345_ids[] = {
415 { .compatible = "analogix,anx6345", },
416 { }
417};
418
419U_BOOT_DRIVER(analogix_anx6345) = {
420 .name = "analogix_anx6345",
421 .id = UCLASS_VIDEO_BRIDGE,
422 .of_match = anx6345_ids,
423 .probe = anx6345_probe,
424 .ops = &anx6345_ops,
425 .priv_auto_alloc_size = sizeof(struct anx6345_priv),
426};
427