Merge tag 's390-5.10-1' of git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux
[linux-2.6-microblaze.git] / drivers / gpu / drm / bridge / parade-ps8640.c
1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3  * Copyright (c) 2016 MediaTek Inc.
4  */
5
6 #include <linux/delay.h>
7 #include <linux/err.h>
8 #include <linux/gpio/consumer.h>
9 #include <linux/i2c.h>
10 #include <linux/module.h>
11 #include <linux/of_graph.h>
12 #include <linux/regulator/consumer.h>
13
14 #include <drm/drm_bridge.h>
15 #include <drm/drm_mipi_dsi.h>
16 #include <drm/drm_of.h>
17 #include <drm/drm_panel.h>
18 #include <drm/drm_print.h>
19
20 #define PAGE2_GPIO_H            0xa7
21 #define PS_GPIO9                BIT(1)
22 #define PAGE2_I2C_BYPASS        0xea
23 #define I2C_BYPASS_EN           0xd0
24 #define PAGE2_MCS_EN            0xf3
25 #define MCS_EN                  BIT(0)
26 #define PAGE3_SET_ADD           0xfe
27 #define VDO_CTL_ADD             0x13
28 #define VDO_DIS                 0x18
29 #define VDO_EN                  0x1c
30 #define DP_NUM_LANES            4
31
32 /*
33  * PS8640 uses multiple addresses:
34  * page[0]: for DP control
35  * page[1]: for VIDEO Bridge
36  * page[2]: for control top
37  * page[3]: for DSI Link Control1
38  * page[4]: for MIPI Phy
39  * page[5]: for VPLL
40  * page[6]: for DSI Link Control2
41  * page[7]: for SPI ROM mapping
42  */
43 enum page_addr_offset {
44         PAGE0_DP_CNTL = 0,
45         PAGE1_VDO_BDG,
46         PAGE2_TOP_CNTL,
47         PAGE3_DSI_CNTL1,
48         PAGE4_MIPI_PHY,
49         PAGE5_VPLL,
50         PAGE6_DSI_CNTL2,
51         PAGE7_SPI_CNTL,
52         MAX_DEVS
53 };
54
55 enum ps8640_vdo_control {
56         DISABLE = VDO_DIS,
57         ENABLE = VDO_EN,
58 };
59
60 struct ps8640 {
61         struct drm_bridge bridge;
62         struct drm_bridge *panel_bridge;
63         struct mipi_dsi_device *dsi;
64         struct i2c_client *page[MAX_DEVS];
65         struct regulator_bulk_data supplies[2];
66         struct gpio_desc *gpio_reset;
67         struct gpio_desc *gpio_powerdown;
68         bool powered;
69 };
70
71 static inline struct ps8640 *bridge_to_ps8640(struct drm_bridge *e)
72 {
73         return container_of(e, struct ps8640, bridge);
74 }
75
76 static int ps8640_bridge_vdo_control(struct ps8640 *ps_bridge,
77                                      const enum ps8640_vdo_control ctrl)
78 {
79         struct i2c_client *client = ps_bridge->page[PAGE3_DSI_CNTL1];
80         u8 vdo_ctrl_buf[] = { VDO_CTL_ADD, ctrl };
81         int ret;
82
83         ret = i2c_smbus_write_i2c_block_data(client, PAGE3_SET_ADD,
84                                              sizeof(vdo_ctrl_buf),
85                                              vdo_ctrl_buf);
86         if (ret < 0) {
87                 DRM_ERROR("failed to %sable VDO: %d\n",
88                           ctrl == ENABLE ? "en" : "dis", ret);
89                 return ret;
90         }
91
92         return 0;
93 }
94
95 static void ps8640_bridge_poweron(struct ps8640 *ps_bridge)
96 {
97         struct i2c_client *client = ps_bridge->page[PAGE2_TOP_CNTL];
98         unsigned long timeout;
99         int ret, status;
100
101         if (ps_bridge->powered)
102                 return;
103
104         ret = regulator_bulk_enable(ARRAY_SIZE(ps_bridge->supplies),
105                                     ps_bridge->supplies);
106         if (ret < 0) {
107                 DRM_ERROR("cannot enable regulators %d\n", ret);
108                 return;
109         }
110
111         gpiod_set_value(ps_bridge->gpio_powerdown, 0);
112         gpiod_set_value(ps_bridge->gpio_reset, 1);
113         usleep_range(2000, 2500);
114         gpiod_set_value(ps_bridge->gpio_reset, 0);
115
116         /*
117          * Wait for the ps8640 embedded MCU to be ready
118          * First wait 200ms and then check the MCU ready flag every 20ms
119          */
120         msleep(200);
121
122         timeout = jiffies + msecs_to_jiffies(200) + 1;
123
124         while (time_is_after_jiffies(timeout)) {
125                 status = i2c_smbus_read_byte_data(client, PAGE2_GPIO_H);
126                 if (status < 0) {
127                         DRM_ERROR("failed read PAGE2_GPIO_H: %d\n", status);
128                         goto err_regulators_disable;
129                 }
130                 if ((status & PS_GPIO9) == PS_GPIO9)
131                         break;
132
133                 msleep(20);
134         }
135
136         msleep(50);
137
138         /*
139          * The Manufacturer Command Set (MCS) is a device dependent interface
140          * intended for factory programming of the display module default
141          * parameters. Once the display module is configured, the MCS shall be
142          * disabled by the manufacturer. Once disabled, all MCS commands are
143          * ignored by the display interface.
144          */
145         status = i2c_smbus_read_byte_data(client, PAGE2_MCS_EN);
146         if (status < 0) {
147                 DRM_ERROR("failed read PAGE2_MCS_EN: %d\n", status);
148                 goto err_regulators_disable;
149         }
150
151         ret = i2c_smbus_write_byte_data(client, PAGE2_MCS_EN,
152                                         status & ~MCS_EN);
153         if (ret < 0) {
154                 DRM_ERROR("failed write PAGE2_MCS_EN: %d\n", ret);
155                 goto err_regulators_disable;
156         }
157
158         /* Switch access edp panel's edid through i2c */
159         ret = i2c_smbus_write_byte_data(client, PAGE2_I2C_BYPASS,
160                                         I2C_BYPASS_EN);
161         if (ret < 0) {
162                 DRM_ERROR("failed write PAGE2_I2C_BYPASS: %d\n", ret);
163                 goto err_regulators_disable;
164         }
165
166         ps_bridge->powered = true;
167
168         return;
169
170 err_regulators_disable:
171         regulator_bulk_disable(ARRAY_SIZE(ps_bridge->supplies),
172                                ps_bridge->supplies);
173 }
174
175 static void ps8640_bridge_poweroff(struct ps8640 *ps_bridge)
176 {
177         int ret;
178
179         if (!ps_bridge->powered)
180                 return;
181
182         gpiod_set_value(ps_bridge->gpio_reset, 1);
183         gpiod_set_value(ps_bridge->gpio_powerdown, 1);
184         ret = regulator_bulk_disable(ARRAY_SIZE(ps_bridge->supplies),
185                                      ps_bridge->supplies);
186         if (ret < 0)
187                 DRM_ERROR("cannot disable regulators %d\n", ret);
188
189         ps_bridge->powered = false;
190 }
191
192 static void ps8640_pre_enable(struct drm_bridge *bridge)
193 {
194         struct ps8640 *ps_bridge = bridge_to_ps8640(bridge);
195         int ret;
196
197         ps8640_bridge_poweron(ps_bridge);
198
199         ret = ps8640_bridge_vdo_control(ps_bridge, ENABLE);
200         if (ret < 0)
201                 ps8640_bridge_poweroff(ps_bridge);
202 }
203
204 static void ps8640_post_disable(struct drm_bridge *bridge)
205 {
206         struct ps8640 *ps_bridge = bridge_to_ps8640(bridge);
207
208         ps8640_bridge_vdo_control(ps_bridge, DISABLE);
209         ps8640_bridge_poweroff(ps_bridge);
210 }
211
212 static int ps8640_bridge_attach(struct drm_bridge *bridge,
213                                 enum drm_bridge_attach_flags flags)
214 {
215         struct ps8640 *ps_bridge = bridge_to_ps8640(bridge);
216         struct device *dev = &ps_bridge->page[0]->dev;
217         struct device_node *in_ep, *dsi_node;
218         struct mipi_dsi_device *dsi;
219         struct mipi_dsi_host *host;
220         int ret;
221         const struct mipi_dsi_device_info info = { .type = "ps8640",
222                                                    .channel = 0,
223                                                    .node = NULL,
224                                                  };
225
226         if (!(flags & DRM_BRIDGE_ATTACH_NO_CONNECTOR))
227                 return -EINVAL;
228
229         /* port@0 is ps8640 dsi input port */
230         in_ep = of_graph_get_endpoint_by_regs(dev->of_node, 0, -1);
231         if (!in_ep)
232                 return -ENODEV;
233
234         dsi_node = of_graph_get_remote_port_parent(in_ep);
235         of_node_put(in_ep);
236         if (!dsi_node)
237                 return -ENODEV;
238
239         host = of_find_mipi_dsi_host_by_node(dsi_node);
240         of_node_put(dsi_node);
241         if (!host)
242                 return -ENODEV;
243
244         dsi = mipi_dsi_device_register_full(host, &info);
245         if (IS_ERR(dsi)) {
246                 dev_err(dev, "failed to create dsi device\n");
247                 ret = PTR_ERR(dsi);
248                 return ret;
249         }
250
251         ps_bridge->dsi = dsi;
252
253         dsi->host = host;
254         dsi->mode_flags = MIPI_DSI_MODE_VIDEO |
255                           MIPI_DSI_MODE_VIDEO_SYNC_PULSE;
256         dsi->format = MIPI_DSI_FMT_RGB888;
257         dsi->lanes = DP_NUM_LANES;
258         ret = mipi_dsi_attach(dsi);
259         if (ret)
260                 goto err_dsi_attach;
261
262         /* Attach the panel-bridge to the dsi bridge */
263         return drm_bridge_attach(bridge->encoder, ps_bridge->panel_bridge,
264                                  &ps_bridge->bridge, flags);
265
266 err_dsi_attach:
267         mipi_dsi_device_unregister(dsi);
268         return ret;
269 }
270
271 static struct edid *ps8640_bridge_get_edid(struct drm_bridge *bridge,
272                                            struct drm_connector *connector)
273 {
274         struct ps8640 *ps_bridge = bridge_to_ps8640(bridge);
275         bool poweroff = !ps_bridge->powered;
276         struct edid *edid;
277
278         /*
279          * When we end calling get_edid() triggered by an ioctl, i.e
280          *
281          *   drm_mode_getconnector (ioctl)
282          *     -> drm_helper_probe_single_connector_modes
283          *        -> drm_bridge_connector_get_modes
284          *           -> ps8640_bridge_get_edid
285          *
286          * We need to make sure that what we need is enabled before reading
287          * EDID, for this chip, we need to do a full poweron, otherwise it will
288          * fail.
289          */
290         drm_bridge_chain_pre_enable(bridge);
291
292         edid = drm_get_edid(connector,
293                             ps_bridge->page[PAGE0_DP_CNTL]->adapter);
294
295         /*
296          * If we call the get_edid() function without having enabled the chip
297          * before, return the chip to its original power state.
298          */
299         if (poweroff)
300                 drm_bridge_chain_post_disable(bridge);
301
302         return edid;
303 }
304
305 static const struct drm_bridge_funcs ps8640_bridge_funcs = {
306         .attach = ps8640_bridge_attach,
307         .get_edid = ps8640_bridge_get_edid,
308         .post_disable = ps8640_post_disable,
309         .pre_enable = ps8640_pre_enable,
310 };
311
312 static int ps8640_probe(struct i2c_client *client)
313 {
314         struct device *dev = &client->dev;
315         struct device_node *np = dev->of_node;
316         struct ps8640 *ps_bridge;
317         struct drm_panel *panel;
318         int ret;
319         u32 i;
320
321         ps_bridge = devm_kzalloc(dev, sizeof(*ps_bridge), GFP_KERNEL);
322         if (!ps_bridge)
323                 return -ENOMEM;
324
325         /* port@1 is ps8640 output port */
326         ret = drm_of_find_panel_or_bridge(np, 1, 0, &panel, NULL);
327         if (ret < 0)
328                 return ret;
329         if (!panel)
330                 return -ENODEV;
331
332         ps_bridge->panel_bridge = devm_drm_panel_bridge_add(dev, panel);
333         if (IS_ERR(ps_bridge->panel_bridge))
334                 return PTR_ERR(ps_bridge->panel_bridge);
335
336         ps_bridge->supplies[0].supply = "vdd33";
337         ps_bridge->supplies[1].supply = "vdd12";
338         ret = devm_regulator_bulk_get(dev, ARRAY_SIZE(ps_bridge->supplies),
339                                       ps_bridge->supplies);
340         if (ret)
341                 return ret;
342
343         ps_bridge->gpio_powerdown = devm_gpiod_get(&client->dev, "powerdown",
344                                                    GPIOD_OUT_HIGH);
345         if (IS_ERR(ps_bridge->gpio_powerdown))
346                 return PTR_ERR(ps_bridge->gpio_powerdown);
347
348         /*
349          * Assert the reset to avoid the bridge being initialized prematurely
350          */
351         ps_bridge->gpio_reset = devm_gpiod_get(&client->dev, "reset",
352                                                GPIOD_OUT_HIGH);
353         if (IS_ERR(ps_bridge->gpio_reset))
354                 return PTR_ERR(ps_bridge->gpio_reset);
355
356         ps_bridge->bridge.funcs = &ps8640_bridge_funcs;
357         ps_bridge->bridge.of_node = dev->of_node;
358         ps_bridge->bridge.ops = DRM_BRIDGE_OP_EDID;
359         ps_bridge->bridge.type = DRM_MODE_CONNECTOR_eDP;
360
361         ps_bridge->page[PAGE0_DP_CNTL] = client;
362
363         for (i = 1; i < ARRAY_SIZE(ps_bridge->page); i++) {
364                 ps_bridge->page[i] = devm_i2c_new_dummy_device(&client->dev,
365                                                              client->adapter,
366                                                              client->addr + i);
367                 if (IS_ERR(ps_bridge->page[i])) {
368                         dev_err(dev, "failed i2c dummy device, address %02x\n",
369                                 client->addr + i);
370                         return PTR_ERR(ps_bridge->page[i]);
371                 }
372         }
373
374         i2c_set_clientdata(client, ps_bridge);
375
376         drm_bridge_add(&ps_bridge->bridge);
377
378         return 0;
379 }
380
381 static int ps8640_remove(struct i2c_client *client)
382 {
383         struct ps8640 *ps_bridge = i2c_get_clientdata(client);
384
385         drm_bridge_remove(&ps_bridge->bridge);
386
387         return 0;
388 }
389
390 static const struct of_device_id ps8640_match[] = {
391         { .compatible = "parade,ps8640" },
392         { }
393 };
394 MODULE_DEVICE_TABLE(of, ps8640_match);
395
396 static struct i2c_driver ps8640_driver = {
397         .probe_new = ps8640_probe,
398         .remove = ps8640_remove,
399         .driver = {
400                 .name = "ps8640",
401                 .of_match_table = ps8640_match,
402         },
403 };
404 module_i2c_driver(ps8640_driver);
405
406 MODULE_AUTHOR("Jitao Shi <jitao.shi@mediatek.com>");
407 MODULE_AUTHOR("CK Hu <ck.hu@mediatek.com>");
408 MODULE_AUTHOR("Enric Balletbo i Serra <enric.balletbo@collabora.com>");
409 MODULE_DESCRIPTION("PARADE ps8640 DSI-eDP converter driver");
410 MODULE_LICENSE("GPL v2");