Add the rt linux 4.1.3-rt3 as base
[kvmfornfv.git] / kernel / drivers / gpu / drm / gma500 / tc35876x-dsi-lvds.c
1 /*
2  * Copyright © 2011 Intel Corporation
3  *
4  * Permission is hereby granted, free of charge, to any person obtaining a
5  * copy of this software and associated documentation files (the "Software"),
6  * to deal in the Software without restriction, including without limitation
7  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8  * and/or sell copies of the Software, and to permit persons to whom the
9  * Software is furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice (including the next
12  * paragraph) shall be included in all copies or substantial portions of the
13  * Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21  * DEALINGS IN THE SOFTWARE.
22  *
23  */
24
25 #include "mdfld_dsi_dpi.h"
26 #include "mdfld_output.h"
27 #include "mdfld_dsi_pkg_sender.h"
28 #include "tc35876x-dsi-lvds.h"
29 #include <linux/i2c/tc35876x.h>
30 #include <linux/kernel.h>
31 #include <linux/module.h>
32 #include <asm/intel_scu_ipc.h>
33
34 static struct i2c_client *tc35876x_client;
35 static struct i2c_client *cmi_lcd_i2c_client;
36
37 #define FLD_MASK(start, end)    (((1 << ((start) - (end) + 1)) - 1) << (end))
38 #define FLD_VAL(val, start, end) (((val) << (end)) & FLD_MASK(start, end))
39
40 /* DSI D-PHY Layer Registers */
41 #define D0W_DPHYCONTTX          0x0004
42 #define CLW_DPHYCONTRX          0x0020
43 #define D0W_DPHYCONTRX          0x0024
44 #define D1W_DPHYCONTRX          0x0028
45 #define D2W_DPHYCONTRX          0x002C
46 #define D3W_DPHYCONTRX          0x0030
47 #define COM_DPHYCONTRX          0x0038
48 #define CLW_CNTRL               0x0040
49 #define D0W_CNTRL               0x0044
50 #define D1W_CNTRL               0x0048
51 #define D2W_CNTRL               0x004C
52 #define D3W_CNTRL               0x0050
53 #define DFTMODE_CNTRL           0x0054
54
55 /* DSI PPI Layer Registers */
56 #define PPI_STARTPPI            0x0104
57 #define PPI_BUSYPPI             0x0108
58 #define PPI_LINEINITCNT         0x0110
59 #define PPI_LPTXTIMECNT         0x0114
60 #define PPI_LANEENABLE          0x0134
61 #define PPI_TX_RX_TA            0x013C
62 #define PPI_CLS_ATMR            0x0140
63 #define PPI_D0S_ATMR            0x0144
64 #define PPI_D1S_ATMR            0x0148
65 #define PPI_D2S_ATMR            0x014C
66 #define PPI_D3S_ATMR            0x0150
67 #define PPI_D0S_CLRSIPOCOUNT    0x0164
68 #define PPI_D1S_CLRSIPOCOUNT    0x0168
69 #define PPI_D2S_CLRSIPOCOUNT    0x016C
70 #define PPI_D3S_CLRSIPOCOUNT    0x0170
71 #define CLS_PRE                 0x0180
72 #define D0S_PRE                 0x0184
73 #define D1S_PRE                 0x0188
74 #define D2S_PRE                 0x018C
75 #define D3S_PRE                 0x0190
76 #define CLS_PREP                0x01A0
77 #define D0S_PREP                0x01A4
78 #define D1S_PREP                0x01A8
79 #define D2S_PREP                0x01AC
80 #define D3S_PREP                0x01B0
81 #define CLS_ZERO                0x01C0
82 #define D0S_ZERO                0x01C4
83 #define D1S_ZERO                0x01C8
84 #define D2S_ZERO                0x01CC
85 #define D3S_ZERO                0x01D0
86 #define PPI_CLRFLG              0x01E0
87 #define PPI_CLRSIPO             0x01E4
88 #define HSTIMEOUT               0x01F0
89 #define HSTIMEOUTENABLE         0x01F4
90
91 /* DSI Protocol Layer Registers */
92 #define DSI_STARTDSI            0x0204
93 #define DSI_BUSYDSI             0x0208
94 #define DSI_LANEENABLE          0x0210
95 #define DSI_LANESTATUS0         0x0214
96 #define DSI_LANESTATUS1         0x0218
97 #define DSI_INTSTATUS           0x0220
98 #define DSI_INTMASK             0x0224
99 #define DSI_INTCLR              0x0228
100 #define DSI_LPTXTO              0x0230
101
102 /* DSI General Registers */
103 #define DSIERRCNT               0x0300
104
105 /* DSI Application Layer Registers */
106 #define APLCTRL                 0x0400
107 #define RDPKTLN                 0x0404
108
109 /* Video Path Registers */
110 #define VPCTRL                  0x0450
111 #define HTIM1                   0x0454
112 #define HTIM2                   0x0458
113 #define VTIM1                   0x045C
114 #define VTIM2                   0x0460
115 #define VFUEN                   0x0464
116
117 /* LVDS Registers */
118 #define LVMX0003                0x0480
119 #define LVMX0407                0x0484
120 #define LVMX0811                0x0488
121 #define LVMX1215                0x048C
122 #define LVMX1619                0x0490
123 #define LVMX2023                0x0494
124 #define LVMX2427                0x0498
125 #define LVCFG                   0x049C
126 #define LVPHY0                  0x04A0
127 #define LVPHY1                  0x04A4
128
129 /* System Registers */
130 #define SYSSTAT                 0x0500
131 #define SYSRST                  0x0504
132
133 /* GPIO Registers */
134 /*#define GPIOC                 0x0520*/
135 #define GPIOO                   0x0524
136 #define GPIOI                   0x0528
137
138 /* I2C Registers */
139 #define I2CTIMCTRL              0x0540
140 #define I2CMADDR                0x0544
141 #define WDATAQ                  0x0548
142 #define RDATAQ                  0x054C
143
144 /* Chip/Rev Registers */
145 #define IDREG                   0x0580
146
147 /* Debug Registers */
148 #define DEBUG00                 0x05A0
149 #define DEBUG01                 0x05A4
150
151 /* Panel CABC registers */
152 #define PANEL_PWM_CONTROL       0x90
153 #define PANEL_FREQ_DIVIDER_HI   0x91
154 #define PANEL_FREQ_DIVIDER_LO   0x92
155 #define PANEL_DUTY_CONTROL      0x93
156 #define PANEL_MODIFY_RGB        0x94
157 #define PANEL_FRAMERATE_CONTROL 0x96
158 #define PANEL_PWM_MIN           0x97
159 #define PANEL_PWM_REF           0x98
160 #define PANEL_PWM_MAX           0x99
161 #define PANEL_ALLOW_DISTORT     0x9A
162 #define PANEL_BYPASS_PWMI       0x9B
163
164 /* Panel color management registers */
165 #define PANEL_CM_ENABLE         0x700
166 #define PANEL_CM_HUE            0x701
167 #define PANEL_CM_SATURATION     0x702
168 #define PANEL_CM_INTENSITY      0x703
169 #define PANEL_CM_BRIGHTNESS     0x704
170 #define PANEL_CM_CE_ENABLE      0x705
171 #define PANEL_CM_PEAK_EN        0x710
172 #define PANEL_CM_GAIN           0x711
173 #define PANEL_CM_HUETABLE_START 0x730
174 #define PANEL_CM_HUETABLE_END   0x747 /* inclusive */
175
176 /* Input muxing for registers LVMX0003...LVMX2427 */
177 enum {
178         INPUT_R0,       /* 0 */
179         INPUT_R1,
180         INPUT_R2,
181         INPUT_R3,
182         INPUT_R4,
183         INPUT_R5,
184         INPUT_R6,
185         INPUT_R7,
186         INPUT_G0,       /* 8 */
187         INPUT_G1,
188         INPUT_G2,
189         INPUT_G3,
190         INPUT_G4,
191         INPUT_G5,
192         INPUT_G6,
193         INPUT_G7,
194         INPUT_B0,       /* 16 */
195         INPUT_B1,
196         INPUT_B2,
197         INPUT_B3,
198         INPUT_B4,
199         INPUT_B5,
200         INPUT_B6,
201         INPUT_B7,
202         INPUT_HSYNC,    /* 24 */
203         INPUT_VSYNC,
204         INPUT_DE,
205         LOGIC_0,
206         /* 28...31 undefined */
207 };
208
209 #define INPUT_MUX(lvmx03, lvmx02, lvmx01, lvmx00)               \
210         (FLD_VAL(lvmx03, 29, 24) | FLD_VAL(lvmx02, 20, 16) |    \
211         FLD_VAL(lvmx01, 12, 8) | FLD_VAL(lvmx00, 4, 0))
212
213 /**
214  * tc35876x_regw - Write DSI-LVDS bridge register using I2C
215  * @client: struct i2c_client to use
216  * @reg: register address
217  * @value: value to write
218  *
219  * Returns 0 on success, or a negative error value.
220  */
221 static int tc35876x_regw(struct i2c_client *client, u16 reg, u32 value)
222 {
223         int r;
224         u8 tx_data[] = {
225                 /* NOTE: Register address big-endian, data little-endian. */
226                 (reg >> 8) & 0xff,
227                 reg & 0xff,
228                 value & 0xff,
229                 (value >> 8) & 0xff,
230                 (value >> 16) & 0xff,
231                 (value >> 24) & 0xff,
232         };
233         struct i2c_msg msgs[] = {
234                 {
235                         .addr = client->addr,
236                         .flags = 0,
237                         .buf = tx_data,
238                         .len = ARRAY_SIZE(tx_data),
239                 },
240         };
241
242         r = i2c_transfer(client->adapter, msgs, ARRAY_SIZE(msgs));
243         if (r < 0) {
244                 dev_err(&client->dev, "%s: reg 0x%04x val 0x%08x error %d\n",
245                         __func__, reg, value, r);
246                 return r;
247         }
248
249         if (r < ARRAY_SIZE(msgs)) {
250                 dev_err(&client->dev, "%s: reg 0x%04x val 0x%08x msgs %d\n",
251                         __func__, reg, value, r);
252                 return -EAGAIN;
253         }
254
255         dev_dbg(&client->dev, "%s: reg 0x%04x val 0x%08x\n",
256                         __func__, reg, value);
257
258         return 0;
259 }
260
261 /**
262  * tc35876x_regr - Read DSI-LVDS bridge register using I2C
263  * @client: struct i2c_client to use
264  * @reg: register address
265  * @value: pointer for storing the value
266  *
267  * Returns 0 on success, or a negative error value.
268  */
269 static int tc35876x_regr(struct i2c_client *client, u16 reg, u32 *value)
270 {
271         int r;
272         u8 tx_data[] = {
273                 (reg >> 8) & 0xff,
274                 reg & 0xff,
275         };
276         u8 rx_data[4];
277         struct i2c_msg msgs[] = {
278                 {
279                         .addr = client->addr,
280                         .flags = 0,
281                         .buf = tx_data,
282                         .len = ARRAY_SIZE(tx_data),
283                 },
284                 {
285                         .addr = client->addr,
286                         .flags = I2C_M_RD,
287                         .buf = rx_data,
288                         .len = ARRAY_SIZE(rx_data),
289                  },
290         };
291
292         r = i2c_transfer(client->adapter, msgs, ARRAY_SIZE(msgs));
293         if (r < 0) {
294                 dev_err(&client->dev, "%s: reg 0x%04x error %d\n", __func__,
295                         reg, r);
296                 return r;
297         }
298
299         if (r < ARRAY_SIZE(msgs)) {
300                 dev_err(&client->dev, "%s: reg 0x%04x msgs %d\n", __func__,
301                         reg, r);
302                 return -EAGAIN;
303         }
304
305         *value = rx_data[0] << 24 | rx_data[1] << 16 |
306                 rx_data[2] << 8 | rx_data[3];
307
308         dev_dbg(&client->dev, "%s: reg 0x%04x value 0x%08x\n", __func__,
309                 reg, *value);
310
311         return 0;
312 }
313
314 void tc35876x_set_bridge_reset_state(struct drm_device *dev, int state)
315 {
316         struct tc35876x_platform_data *pdata;
317
318         if (WARN(!tc35876x_client, "%s called before probe", __func__))
319                 return;
320
321         dev_dbg(&tc35876x_client->dev, "%s: state %d\n", __func__, state);
322
323         pdata = dev_get_platdata(&tc35876x_client->dev);
324
325         if (pdata->gpio_bridge_reset == -1)
326                 return;
327
328         if (state) {
329                 gpio_set_value_cansleep(pdata->gpio_bridge_reset, 0);
330                 mdelay(10);
331         } else {
332                 /* Pull MIPI Bridge reset pin to Low */
333                 gpio_set_value_cansleep(pdata->gpio_bridge_reset, 0);
334                 mdelay(20);
335                 /* Pull MIPI Bridge reset pin to High */
336                 gpio_set_value_cansleep(pdata->gpio_bridge_reset, 1);
337                 mdelay(40);
338         }
339 }
340
341 void tc35876x_configure_lvds_bridge(struct drm_device *dev)
342 {
343         struct i2c_client *i2c = tc35876x_client;
344         u32 ppi_lptxtimecnt;
345         u32 txtagocnt;
346         u32 txtasurecnt;
347         u32 id;
348
349         if (WARN(!tc35876x_client, "%s called before probe", __func__))
350                 return;
351
352         dev_dbg(&tc35876x_client->dev, "%s\n", __func__);
353
354         if (!tc35876x_regr(i2c, IDREG, &id))
355                 dev_info(&tc35876x_client->dev, "tc35876x ID 0x%08x\n", id);
356         else
357                 dev_err(&tc35876x_client->dev, "Cannot read ID\n");
358
359         ppi_lptxtimecnt = 4;
360         txtagocnt = (5 * ppi_lptxtimecnt - 3) / 4;
361         txtasurecnt = 3 * ppi_lptxtimecnt / 2;
362         tc35876x_regw(i2c, PPI_TX_RX_TA, FLD_VAL(txtagocnt, 26, 16) |
363                 FLD_VAL(txtasurecnt, 10, 0));
364         tc35876x_regw(i2c, PPI_LPTXTIMECNT, FLD_VAL(ppi_lptxtimecnt, 10, 0));
365
366         tc35876x_regw(i2c, PPI_D0S_CLRSIPOCOUNT, FLD_VAL(1, 5, 0));
367         tc35876x_regw(i2c, PPI_D1S_CLRSIPOCOUNT, FLD_VAL(1, 5, 0));
368         tc35876x_regw(i2c, PPI_D2S_CLRSIPOCOUNT, FLD_VAL(1, 5, 0));
369         tc35876x_regw(i2c, PPI_D3S_CLRSIPOCOUNT, FLD_VAL(1, 5, 0));
370
371         /* Enabling MIPI & PPI lanes, Enable 4 lanes */
372         tc35876x_regw(i2c, PPI_LANEENABLE,
373                 BIT(4) | BIT(3) | BIT(2) | BIT(1) | BIT(0));
374         tc35876x_regw(i2c, DSI_LANEENABLE,
375                 BIT(4) | BIT(3) | BIT(2) | BIT(1) | BIT(0));
376         tc35876x_regw(i2c, PPI_STARTPPI, BIT(0));
377         tc35876x_regw(i2c, DSI_STARTDSI, BIT(0));
378
379         /* Setting LVDS output frequency */
380         tc35876x_regw(i2c, LVPHY0, FLD_VAL(1, 20, 16) |
381                 FLD_VAL(2, 15, 14) | FLD_VAL(6, 4, 0)); /* 0x00048006 */
382
383         /* Setting video panel control register,0x00000120 VTGen=ON ?!?!? */
384         tc35876x_regw(i2c, VPCTRL, BIT(8) | BIT(5));
385
386         /* Horizontal back porch and horizontal pulse width. 0x00280028 */
387         tc35876x_regw(i2c, HTIM1, FLD_VAL(40, 24, 16) | FLD_VAL(40, 8, 0));
388
389         /* Horizontal front porch and horizontal active video size. 0x00500500*/
390         tc35876x_regw(i2c, HTIM2, FLD_VAL(80, 24, 16) | FLD_VAL(1280, 10, 0));
391
392         /* Vertical back porch and vertical sync pulse width. 0x000e000a */
393         tc35876x_regw(i2c, VTIM1, FLD_VAL(14, 23, 16) | FLD_VAL(10, 7, 0));
394
395         /* Vertical front porch and vertical display size. 0x000e0320 */
396         tc35876x_regw(i2c, VTIM2, FLD_VAL(14, 23, 16) | FLD_VAL(800, 10, 0));
397
398         /* Set above HTIM1, HTIM2, VTIM1, and VTIM2 at next VSYNC. */
399         tc35876x_regw(i2c, VFUEN, BIT(0));
400
401         /* Soft reset LCD controller. */
402         tc35876x_regw(i2c, SYSRST, BIT(2));
403
404         /* LVDS-TX input muxing */
405         tc35876x_regw(i2c, LVMX0003,
406                 INPUT_MUX(INPUT_R5, INPUT_R4, INPUT_R3, INPUT_R2));
407         tc35876x_regw(i2c, LVMX0407,
408                 INPUT_MUX(INPUT_G2, INPUT_R7, INPUT_R1, INPUT_R6));
409         tc35876x_regw(i2c, LVMX0811,
410                 INPUT_MUX(INPUT_G1, INPUT_G0, INPUT_G4, INPUT_G3));
411         tc35876x_regw(i2c, LVMX1215,
412                 INPUT_MUX(INPUT_B2, INPUT_G7, INPUT_G6, INPUT_G5));
413         tc35876x_regw(i2c, LVMX1619,
414                 INPUT_MUX(INPUT_B4, INPUT_B3, INPUT_B1, INPUT_B0));
415         tc35876x_regw(i2c, LVMX2023,
416                 INPUT_MUX(LOGIC_0,  INPUT_B7, INPUT_B6, INPUT_B5));
417         tc35876x_regw(i2c, LVMX2427,
418                 INPUT_MUX(INPUT_R0, INPUT_DE, INPUT_VSYNC, INPUT_HSYNC));
419
420         /* Enable LVDS transmitter. */
421         tc35876x_regw(i2c, LVCFG, BIT(0));
422
423         /* Clear notifications. Don't write reserved bits. Was write 0xffffffff
424          * to 0x0288, must be in error?! */
425         tc35876x_regw(i2c, DSI_INTCLR, FLD_MASK(31, 30) | FLD_MASK(22, 0));
426 }
427
428 #define GPIOPWMCTRL     0x38F
429 #define PWM0CLKDIV0     0x62 /* low byte */
430 #define PWM0CLKDIV1     0x61 /* high byte */
431
432 #define SYSTEMCLK       19200000UL /* 19.2 MHz */
433 #define PWM_FREQUENCY   9600 /* Hz */
434
435 /* f = baseclk / (clkdiv + 1) => clkdiv = (baseclk - f) / f */
436 static inline u16 calc_clkdiv(unsigned long baseclk, unsigned int f)
437 {
438         return (baseclk - f) / f;
439 }
440
441 static void tc35876x_brightness_init(struct drm_device *dev)
442 {
443         int ret;
444         u8 pwmctrl;
445         u16 clkdiv;
446
447         /* Make sure the PWM reference is the 19.2 MHz system clock. Read first
448          * instead of setting directly to catch potential conflicts between PWM
449          * users. */
450         ret = intel_scu_ipc_ioread8(GPIOPWMCTRL, &pwmctrl);
451         if (ret || pwmctrl != 0x01) {
452                 if (ret)
453                         dev_err(&dev->pdev->dev, "GPIOPWMCTRL read failed\n");
454                 else
455                         dev_warn(&dev->pdev->dev, "GPIOPWMCTRL was not set to system clock (pwmctrl = 0x%02x)\n", pwmctrl);
456
457                 ret = intel_scu_ipc_iowrite8(GPIOPWMCTRL, 0x01);
458                 if (ret)
459                         dev_err(&dev->pdev->dev, "GPIOPWMCTRL set failed\n");
460         }
461
462         clkdiv = calc_clkdiv(SYSTEMCLK, PWM_FREQUENCY);
463
464         ret = intel_scu_ipc_iowrite8(PWM0CLKDIV1, (clkdiv >> 8) & 0xff);
465         if (!ret)
466                 ret = intel_scu_ipc_iowrite8(PWM0CLKDIV0, clkdiv & 0xff);
467
468         if (ret)
469                 dev_err(&dev->pdev->dev, "PWM0CLKDIV set failed\n");
470         else
471                 dev_dbg(&dev->pdev->dev, "PWM0CLKDIV set to 0x%04x (%d Hz)\n",
472                         clkdiv, PWM_FREQUENCY);
473 }
474
475 #define PWM0DUTYCYCLE                   0x67
476
477 void tc35876x_brightness_control(struct drm_device *dev, int level)
478 {
479         int ret;
480         u8 duty_val;
481         u8 panel_duty_val;
482
483         level = clamp(level, 0, MDFLD_DSI_BRIGHTNESS_MAX_LEVEL);
484
485         /* PWM duty cycle 0x00...0x63 corresponds to 0...99% */
486         duty_val = level * 0x63 / MDFLD_DSI_BRIGHTNESS_MAX_LEVEL;
487
488         /* I won't pretend to understand this formula. The panel spec is quite
489          * bad engrish.
490          */
491         panel_duty_val = (2 * level - 100) * 0xA9 /
492                          MDFLD_DSI_BRIGHTNESS_MAX_LEVEL + 0x56;
493
494         ret = intel_scu_ipc_iowrite8(PWM0DUTYCYCLE, duty_val);
495         if (ret)
496                 dev_err(&tc35876x_client->dev, "%s: ipc write fail\n",
497                         __func__);
498
499         if (cmi_lcd_i2c_client) {
500                 ret = i2c_smbus_write_byte_data(cmi_lcd_i2c_client,
501                                                 PANEL_PWM_MAX, panel_duty_val);
502                 if (ret < 0)
503                         dev_err(&cmi_lcd_i2c_client->dev, "%s: i2c write failed\n",
504                                 __func__);
505         }
506 }
507
508 void tc35876x_toshiba_bridge_panel_off(struct drm_device *dev)
509 {
510         struct tc35876x_platform_data *pdata;
511
512         if (WARN(!tc35876x_client, "%s called before probe", __func__))
513                 return;
514
515         dev_dbg(&tc35876x_client->dev, "%s\n", __func__);
516
517         pdata = dev_get_platdata(&tc35876x_client->dev);
518
519         if (pdata->gpio_panel_bl_en != -1)
520                 gpio_set_value_cansleep(pdata->gpio_panel_bl_en, 0);
521
522         if (pdata->gpio_panel_vadd != -1)
523                 gpio_set_value_cansleep(pdata->gpio_panel_vadd, 0);
524 }
525
526 void tc35876x_toshiba_bridge_panel_on(struct drm_device *dev)
527 {
528         struct tc35876x_platform_data *pdata;
529         struct drm_psb_private *dev_priv = dev->dev_private;
530
531         if (WARN(!tc35876x_client, "%s called before probe", __func__))
532                 return;
533
534         dev_dbg(&tc35876x_client->dev, "%s\n", __func__);
535
536         pdata = dev_get_platdata(&tc35876x_client->dev);
537
538         if (pdata->gpio_panel_vadd != -1) {
539                 gpio_set_value_cansleep(pdata->gpio_panel_vadd, 1);
540                 msleep(260);
541         }
542
543         if (cmi_lcd_i2c_client) {
544                 int ret;
545                 dev_dbg(&cmi_lcd_i2c_client->dev, "setting TCON\n");
546                 /* Bit 4 is average_saving. Setting it to 1, the brightness is
547                  * referenced to the average of the frame content. 0 means
548                  * reference to the maximum of frame contents. Bits 3:0 are
549                  * allow_distort. When set to a nonzero value, all color values
550                  * between 255-allow_distort*2 and 255 are mapped to the
551                  * 255-allow_distort*2 value.
552                  */
553                 ret = i2c_smbus_write_byte_data(cmi_lcd_i2c_client,
554                                                 PANEL_ALLOW_DISTORT, 0x10);
555                 if (ret < 0)
556                         dev_err(&cmi_lcd_i2c_client->dev,
557                                 "i2c write failed (%d)\n", ret);
558                 ret = i2c_smbus_write_byte_data(cmi_lcd_i2c_client,
559                                                 PANEL_BYPASS_PWMI, 0);
560                 if (ret < 0)
561                         dev_err(&cmi_lcd_i2c_client->dev,
562                                 "i2c write failed (%d)\n", ret);
563                 /* Set minimum brightness value - this is tunable */
564                 ret = i2c_smbus_write_byte_data(cmi_lcd_i2c_client,
565                                                 PANEL_PWM_MIN, 0x35);
566                 if (ret < 0)
567                         dev_err(&cmi_lcd_i2c_client->dev,
568                                 "i2c write failed (%d)\n", ret);
569         }
570
571         if (pdata->gpio_panel_bl_en != -1)
572                 gpio_set_value_cansleep(pdata->gpio_panel_bl_en, 1);
573
574         tc35876x_brightness_control(dev, dev_priv->brightness_adjusted);
575 }
576
577 static struct drm_display_mode *tc35876x_get_config_mode(struct drm_device *dev)
578 {
579         struct drm_display_mode *mode;
580
581         dev_dbg(&dev->pdev->dev, "%s\n", __func__);
582
583         mode = kzalloc(sizeof(*mode), GFP_KERNEL);
584         if (!mode)
585                 return NULL;
586
587         /* FIXME: do this properly. */
588         mode->hdisplay = 1280;
589         mode->vdisplay = 800;
590         mode->hsync_start = 1360;
591         mode->hsync_end = 1400;
592         mode->htotal = 1440;
593         mode->vsync_start = 814;
594         mode->vsync_end = 824;
595         mode->vtotal = 838;
596         mode->clock = 33324 << 1;
597
598         dev_info(&dev->pdev->dev, "hdisplay(w) = %d\n", mode->hdisplay);
599         dev_info(&dev->pdev->dev, "vdisplay(h) = %d\n", mode->vdisplay);
600         dev_info(&dev->pdev->dev, "HSS = %d\n", mode->hsync_start);
601         dev_info(&dev->pdev->dev, "HSE = %d\n", mode->hsync_end);
602         dev_info(&dev->pdev->dev, "htotal = %d\n", mode->htotal);
603         dev_info(&dev->pdev->dev, "VSS = %d\n", mode->vsync_start);
604         dev_info(&dev->pdev->dev, "VSE = %d\n", mode->vsync_end);
605         dev_info(&dev->pdev->dev, "vtotal = %d\n", mode->vtotal);
606         dev_info(&dev->pdev->dev, "clock = %d\n", mode->clock);
607
608         drm_mode_set_name(mode);
609         drm_mode_set_crtcinfo(mode, 0);
610
611         mode->type |= DRM_MODE_TYPE_PREFERRED;
612
613         return mode;
614 }
615
616 /* DV1 Active area 216.96 x 135.6 mm */
617 #define DV1_PANEL_WIDTH 217
618 #define DV1_PANEL_HEIGHT 136
619
620 static int tc35876x_get_panel_info(struct drm_device *dev, int pipe,
621                                 struct panel_info *pi)
622 {
623         if (!dev || !pi)
624                 return -EINVAL;
625
626         pi->width_mm = DV1_PANEL_WIDTH;
627         pi->height_mm = DV1_PANEL_HEIGHT;
628
629         return 0;
630 }
631
632 static int tc35876x_bridge_probe(struct i2c_client *client,
633                                 const struct i2c_device_id *id)
634 {
635         struct tc35876x_platform_data *pdata;
636
637         dev_info(&client->dev, "%s\n", __func__);
638
639         if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
640                 dev_err(&client->dev, "%s: i2c_check_functionality() failed\n",
641                         __func__);
642                 return -ENODEV;
643         }
644
645         pdata = dev_get_platdata(&client->dev);
646         if (!pdata) {
647                 dev_err(&client->dev, "%s: no platform data\n", __func__);
648                 return -ENODEV;
649         }
650
651         if (pdata->gpio_bridge_reset != -1) {
652                 gpio_request(pdata->gpio_bridge_reset, "tc35876x bridge reset");
653                 gpio_direction_output(pdata->gpio_bridge_reset, 0);
654         }
655
656         if (pdata->gpio_panel_bl_en != -1) {
657                 gpio_request(pdata->gpio_panel_bl_en, "tc35876x panel bl en");
658                 gpio_direction_output(pdata->gpio_panel_bl_en, 0);
659         }
660
661         if (pdata->gpio_panel_vadd != -1) {
662                 gpio_request(pdata->gpio_panel_vadd, "tc35876x panel vadd");
663                 gpio_direction_output(pdata->gpio_panel_vadd, 0);
664         }
665
666         tc35876x_client = client;
667
668         return 0;
669 }
670
671 static int tc35876x_bridge_remove(struct i2c_client *client)
672 {
673         struct tc35876x_platform_data *pdata = dev_get_platdata(&client->dev);
674
675         dev_dbg(&client->dev, "%s\n", __func__);
676
677         if (pdata->gpio_bridge_reset != -1)
678                 gpio_free(pdata->gpio_bridge_reset);
679
680         if (pdata->gpio_panel_bl_en != -1)
681                 gpio_free(pdata->gpio_panel_bl_en);
682
683         if (pdata->gpio_panel_vadd != -1)
684                 gpio_free(pdata->gpio_panel_vadd);
685
686         tc35876x_client = NULL;
687
688         return 0;
689 }
690
691 static const struct i2c_device_id tc35876x_bridge_id[] = {
692         { "i2c_disp_brig", 0 },
693         { }
694 };
695 MODULE_DEVICE_TABLE(i2c, tc35876x_bridge_id);
696
697 static struct i2c_driver tc35876x_bridge_i2c_driver = {
698         .driver = {
699                 .name = "i2c_disp_brig",
700         },
701         .id_table = tc35876x_bridge_id,
702         .probe = tc35876x_bridge_probe,
703         .remove = tc35876x_bridge_remove,
704 };
705
706 /* LCD panel I2C */
707 static int cmi_lcd_i2c_probe(struct i2c_client *client,
708                              const struct i2c_device_id *id)
709 {
710         dev_info(&client->dev, "%s\n", __func__);
711
712         if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
713                 dev_err(&client->dev, "%s: i2c_check_functionality() failed\n",
714                         __func__);
715                 return -ENODEV;
716         }
717
718         cmi_lcd_i2c_client = client;
719
720         return 0;
721 }
722
723 static int cmi_lcd_i2c_remove(struct i2c_client *client)
724 {
725         dev_dbg(&client->dev, "%s\n", __func__);
726
727         cmi_lcd_i2c_client = NULL;
728
729         return 0;
730 }
731
732 static const struct i2c_device_id cmi_lcd_i2c_id[] = {
733         { "cmi-lcd", 0 },
734         { }
735 };
736 MODULE_DEVICE_TABLE(i2c, cmi_lcd_i2c_id);
737
738 static struct i2c_driver cmi_lcd_i2c_driver = {
739         .driver = {
740                 .name = "cmi-lcd",
741         },
742         .id_table = cmi_lcd_i2c_id,
743         .probe = cmi_lcd_i2c_probe,
744         .remove = cmi_lcd_i2c_remove,
745 };
746
747 /* HACK to create I2C device while it's not created by platform code */
748 #define CMI_LCD_I2C_ADAPTER     2
749 #define CMI_LCD_I2C_ADDR        0x60
750
751 static int cmi_lcd_hack_create_device(void)
752 {
753         struct i2c_adapter *adapter;
754         struct i2c_client *client;
755         struct i2c_board_info info = {
756                 .type = "cmi-lcd",
757                 .addr = CMI_LCD_I2C_ADDR,
758         };
759
760         pr_debug("%s\n", __func__);
761
762         adapter = i2c_get_adapter(CMI_LCD_I2C_ADAPTER);
763         if (!adapter) {
764                 pr_err("%s: i2c_get_adapter(%d) failed\n", __func__,
765                         CMI_LCD_I2C_ADAPTER);
766                 return -EINVAL;
767         }
768
769         client = i2c_new_device(adapter, &info);
770         if (!client) {
771                 pr_err("%s: i2c_new_device() failed\n", __func__);
772                 i2c_put_adapter(adapter);
773                 return -EINVAL;
774         }
775
776         return 0;
777 }
778
779 static const struct drm_encoder_helper_funcs tc35876x_encoder_helper_funcs = {
780         .dpms = mdfld_dsi_dpi_dpms,
781         .mode_fixup = mdfld_dsi_dpi_mode_fixup,
782         .prepare = mdfld_dsi_dpi_prepare,
783         .mode_set = mdfld_dsi_dpi_mode_set,
784         .commit = mdfld_dsi_dpi_commit,
785 };
786
787 static const struct drm_encoder_funcs tc35876x_encoder_funcs = {
788         .destroy = drm_encoder_cleanup,
789 };
790
791 const struct panel_funcs mdfld_tc35876x_funcs = {
792         .encoder_funcs = &tc35876x_encoder_funcs,
793         .encoder_helper_funcs = &tc35876x_encoder_helper_funcs,
794         .get_config_mode = tc35876x_get_config_mode,
795         .get_panel_info = tc35876x_get_panel_info,
796 };
797
798 void tc35876x_init(struct drm_device *dev)
799 {
800         int r;
801
802         dev_dbg(&dev->pdev->dev, "%s\n", __func__);
803
804         cmi_lcd_hack_create_device();
805
806         r = i2c_add_driver(&cmi_lcd_i2c_driver);
807         if (r < 0)
808                 dev_err(&dev->pdev->dev,
809                         "%s: i2c_add_driver() for %s failed (%d)\n",
810                         __func__, cmi_lcd_i2c_driver.driver.name, r);
811
812         r = i2c_add_driver(&tc35876x_bridge_i2c_driver);
813         if (r < 0)
814                 dev_err(&dev->pdev->dev,
815                         "%s: i2c_add_driver() for %s failed (%d)\n",
816                         __func__, tc35876x_bridge_i2c_driver.driver.name, r);
817
818         tc35876x_brightness_init(dev);
819 }
820
821 void tc35876x_exit(void)
822 {
823         pr_debug("%s\n", __func__);
824
825         i2c_del_driver(&tc35876x_bridge_i2c_driver);
826
827         if (cmi_lcd_i2c_client)
828                 i2c_del_driver(&cmi_lcd_i2c_driver);
829 }