f2f644680ca8dfe2262fac39c42fcd50766982f0
[linux-3.10.git] / drivers / video / omap2 / displays / panel-taal.c
1 /*
2  * Taal DSI command mode panel
3  *
4  * Copyright (C) 2009 Nokia Corporation
5  * Author: Tomi Valkeinen <tomi.valkeinen@nokia.com>
6  *
7  * This program is free software; you can redistribute it and/or modify it
8  * under the terms of the GNU General Public License version 2 as published by
9  * the Free Software Foundation.
10  *
11  * This program is distributed in the hope that it will be useful, but WITHOUT
12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14  * more details.
15  *
16  * You should have received a copy of the GNU General Public License along with
17  * this program.  If not, see <http://www.gnu.org/licenses/>.
18  */
19
20 /*#define DEBUG*/
21
22 #include <linux/module.h>
23 #include <linux/delay.h>
24 #include <linux/err.h>
25 #include <linux/jiffies.h>
26 #include <linux/sched.h>
27 #include <linux/backlight.h>
28 #include <linux/fb.h>
29 #include <linux/interrupt.h>
30 #include <linux/gpio.h>
31 #include <linux/workqueue.h>
32 #include <linux/slab.h>
33 #include <linux/mutex.h>
34
35 #include <video/omapdss.h>
36 #include <video/omap-panel-nokia-dsi.h>
37 #include <video/mipi_display.h>
38
39 /* DSI Virtual channel. Hardcoded for now. */
40 #define TCH 0
41
42 #define DCS_READ_NUM_ERRORS     0x05
43 #define DCS_BRIGHTNESS          0x51
44 #define DCS_CTRL_DISPLAY        0x53
45 #define DCS_WRITE_CABC          0x55
46 #define DCS_READ_CABC           0x56
47 #define DCS_GET_ID1             0xda
48 #define DCS_GET_ID2             0xdb
49 #define DCS_GET_ID3             0xdc
50
51 static irqreturn_t taal_te_isr(int irq, void *data);
52 static void taal_te_timeout_work_callback(struct work_struct *work);
53 static int _taal_enable_te(struct omap_dss_device *dssdev, bool enable);
54
55 static int taal_panel_reset(struct omap_dss_device *dssdev);
56
57 /**
58  * struct panel_config - panel configuration
59  * @name: panel name
60  * @type: panel type
61  * @timings: panel resolution
62  * @sleep: various panel specific delays, passed to msleep() if non-zero
63  * @reset_sequence: reset sequence timings, passed to udelay() if non-zero
64  * @regulators: array of panel regulators
65  * @num_regulators: number of regulators in the array
66  */
67 struct panel_config {
68         const char *name;
69         int type;
70
71         struct omap_video_timings timings;
72
73         struct {
74                 unsigned int sleep_in;
75                 unsigned int sleep_out;
76                 unsigned int hw_reset;
77                 unsigned int enable_te;
78         } sleep;
79
80         struct {
81                 unsigned int high;
82                 unsigned int low;
83         } reset_sequence;
84
85 };
86
87 enum {
88         PANEL_TAAL,
89 };
90
91 static struct panel_config panel_configs[] = {
92         {
93                 .name           = "taal",
94                 .type           = PANEL_TAAL,
95                 .timings        = {
96                         .x_res          = 864,
97                         .y_res          = 480,
98                 },
99                 .sleep          = {
100                         .sleep_in       = 5,
101                         .sleep_out      = 5,
102                         .hw_reset       = 5,
103                         .enable_te      = 100, /* possible panel bug */
104                 },
105                 .reset_sequence = {
106                         .high           = 10,
107                         .low            = 10,
108                 },
109         },
110 };
111
112 struct taal_data {
113         struct mutex lock;
114
115         struct backlight_device *bldev;
116
117         unsigned long   hw_guard_end;   /* next value of jiffies when we can
118                                          * issue the next sleep in/out command
119                                          */
120         unsigned long   hw_guard_wait;  /* max guard time in jiffies */
121
122         struct omap_dss_device *dssdev;
123
124         /* panel specific HW info */
125         struct panel_config *panel_config;
126
127         /* panel HW configuration from DT or platform data */
128         int reset_gpio;
129         int ext_te_gpio;
130
131         bool use_dsi_backlight;
132
133         struct omap_dsi_pin_config pin_config;
134
135         /* runtime variables */
136         bool enabled;
137         u8 rotate;
138         bool mirror;
139
140         bool te_enabled;
141
142         atomic_t do_update;
143         int channel;
144
145         struct delayed_work te_timeout_work;
146
147         bool cabc_broken;
148         unsigned cabc_mode;
149
150         bool intro_printed;
151
152         struct workqueue_struct *workqueue;
153
154         struct delayed_work esd_work;
155         unsigned esd_interval;
156
157         bool ulps_enabled;
158         unsigned ulps_timeout;
159         struct delayed_work ulps_work;
160 };
161
162 static void taal_esd_work(struct work_struct *work);
163 static void taal_ulps_work(struct work_struct *work);
164
165 static void hw_guard_start(struct taal_data *td, int guard_msec)
166 {
167         td->hw_guard_wait = msecs_to_jiffies(guard_msec);
168         td->hw_guard_end = jiffies + td->hw_guard_wait;
169 }
170
171 static void hw_guard_wait(struct taal_data *td)
172 {
173         unsigned long wait = td->hw_guard_end - jiffies;
174
175         if ((long)wait > 0 && wait <= td->hw_guard_wait) {
176                 set_current_state(TASK_UNINTERRUPTIBLE);
177                 schedule_timeout(wait);
178         }
179 }
180
181 static int taal_dcs_read_1(struct taal_data *td, u8 dcs_cmd, u8 *data)
182 {
183         int r;
184         u8 buf[1];
185
186         r = dsi_vc_dcs_read(td->dssdev, td->channel, dcs_cmd, buf, 1);
187
188         if (r < 0)
189                 return r;
190
191         *data = buf[0];
192
193         return 0;
194 }
195
196 static int taal_dcs_write_0(struct taal_data *td, u8 dcs_cmd)
197 {
198         return dsi_vc_dcs_write(td->dssdev, td->channel, &dcs_cmd, 1);
199 }
200
201 static int taal_dcs_write_1(struct taal_data *td, u8 dcs_cmd, u8 param)
202 {
203         u8 buf[2];
204         buf[0] = dcs_cmd;
205         buf[1] = param;
206         return dsi_vc_dcs_write(td->dssdev, td->channel, buf, 2);
207 }
208
209 static int taal_sleep_in(struct taal_data *td)
210
211 {
212         u8 cmd;
213         int r;
214
215         hw_guard_wait(td);
216
217         cmd = MIPI_DCS_ENTER_SLEEP_MODE;
218         r = dsi_vc_dcs_write_nosync(td->dssdev, td->channel, &cmd, 1);
219         if (r)
220                 return r;
221
222         hw_guard_start(td, 120);
223
224         if (td->panel_config->sleep.sleep_in)
225                 msleep(td->panel_config->sleep.sleep_in);
226
227         return 0;
228 }
229
230 static int taal_sleep_out(struct taal_data *td)
231 {
232         int r;
233
234         hw_guard_wait(td);
235
236         r = taal_dcs_write_0(td, MIPI_DCS_EXIT_SLEEP_MODE);
237         if (r)
238                 return r;
239
240         hw_guard_start(td, 120);
241
242         if (td->panel_config->sleep.sleep_out)
243                 msleep(td->panel_config->sleep.sleep_out);
244
245         return 0;
246 }
247
248 static int taal_get_id(struct taal_data *td, u8 *id1, u8 *id2, u8 *id3)
249 {
250         int r;
251
252         r = taal_dcs_read_1(td, DCS_GET_ID1, id1);
253         if (r)
254                 return r;
255         r = taal_dcs_read_1(td, DCS_GET_ID2, id2);
256         if (r)
257                 return r;
258         r = taal_dcs_read_1(td, DCS_GET_ID3, id3);
259         if (r)
260                 return r;
261
262         return 0;
263 }
264
265 static int taal_set_addr_mode(struct taal_data *td, u8 rotate, bool mirror)
266 {
267         int r;
268         u8 mode;
269         int b5, b6, b7;
270
271         r = taal_dcs_read_1(td, MIPI_DCS_GET_ADDRESS_MODE, &mode);
272         if (r)
273                 return r;
274
275         switch (rotate) {
276         default:
277         case 0:
278                 b7 = 0;
279                 b6 = 0;
280                 b5 = 0;
281                 break;
282         case 1:
283                 b7 = 0;
284                 b6 = 1;
285                 b5 = 1;
286                 break;
287         case 2:
288                 b7 = 1;
289                 b6 = 1;
290                 b5 = 0;
291                 break;
292         case 3:
293                 b7 = 1;
294                 b6 = 0;
295                 b5 = 1;
296                 break;
297         }
298
299         if (mirror)
300                 b6 = !b6;
301
302         mode &= ~((1<<7) | (1<<6) | (1<<5));
303         mode |= (b7 << 7) | (b6 << 6) | (b5 << 5);
304
305         return taal_dcs_write_1(td, MIPI_DCS_SET_ADDRESS_MODE, mode);
306 }
307
308 static int taal_set_update_window(struct taal_data *td,
309                 u16 x, u16 y, u16 w, u16 h)
310 {
311         int r;
312         u16 x1 = x;
313         u16 x2 = x + w - 1;
314         u16 y1 = y;
315         u16 y2 = y + h - 1;
316
317         u8 buf[5];
318         buf[0] = MIPI_DCS_SET_COLUMN_ADDRESS;
319         buf[1] = (x1 >> 8) & 0xff;
320         buf[2] = (x1 >> 0) & 0xff;
321         buf[3] = (x2 >> 8) & 0xff;
322         buf[4] = (x2 >> 0) & 0xff;
323
324         r = dsi_vc_dcs_write_nosync(td->dssdev, td->channel, buf, sizeof(buf));
325         if (r)
326                 return r;
327
328         buf[0] = MIPI_DCS_SET_PAGE_ADDRESS;
329         buf[1] = (y1 >> 8) & 0xff;
330         buf[2] = (y1 >> 0) & 0xff;
331         buf[3] = (y2 >> 8) & 0xff;
332         buf[4] = (y2 >> 0) & 0xff;
333
334         r = dsi_vc_dcs_write_nosync(td->dssdev, td->channel, buf, sizeof(buf));
335         if (r)
336                 return r;
337
338         dsi_vc_send_bta_sync(td->dssdev, td->channel);
339
340         return r;
341 }
342
343 static void taal_queue_esd_work(struct omap_dss_device *dssdev)
344 {
345         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
346
347         if (td->esd_interval > 0)
348                 queue_delayed_work(td->workqueue, &td->esd_work,
349                                 msecs_to_jiffies(td->esd_interval));
350 }
351
352 static void taal_cancel_esd_work(struct omap_dss_device *dssdev)
353 {
354         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
355
356         cancel_delayed_work(&td->esd_work);
357 }
358
359 static void taal_queue_ulps_work(struct omap_dss_device *dssdev)
360 {
361         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
362
363         if (td->ulps_timeout > 0)
364                 queue_delayed_work(td->workqueue, &td->ulps_work,
365                                 msecs_to_jiffies(td->ulps_timeout));
366 }
367
368 static void taal_cancel_ulps_work(struct omap_dss_device *dssdev)
369 {
370         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
371
372         cancel_delayed_work(&td->ulps_work);
373 }
374
375 static int taal_enter_ulps(struct omap_dss_device *dssdev)
376 {
377         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
378         int r;
379
380         if (td->ulps_enabled)
381                 return 0;
382
383         taal_cancel_ulps_work(dssdev);
384
385         r = _taal_enable_te(dssdev, false);
386         if (r)
387                 goto err;
388
389         if (gpio_is_valid(td->ext_te_gpio))
390                 disable_irq(gpio_to_irq(td->ext_te_gpio));
391
392         omapdss_dsi_display_disable(dssdev, false, true);
393
394         td->ulps_enabled = true;
395
396         return 0;
397
398 err:
399         dev_err(&dssdev->dev, "enter ULPS failed");
400         taal_panel_reset(dssdev);
401
402         td->ulps_enabled = false;
403
404         taal_queue_ulps_work(dssdev);
405
406         return r;
407 }
408
409 static int taal_exit_ulps(struct omap_dss_device *dssdev)
410 {
411         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
412         int r;
413
414         if (!td->ulps_enabled)
415                 return 0;
416
417         r = omapdss_dsi_display_enable(dssdev);
418         if (r) {
419                 dev_err(&dssdev->dev, "failed to enable DSI\n");
420                 goto err1;
421         }
422
423         omapdss_dsi_vc_enable_hs(dssdev, td->channel, true);
424
425         r = _taal_enable_te(dssdev, true);
426         if (r) {
427                 dev_err(&dssdev->dev, "failed to re-enable TE");
428                 goto err2;
429         }
430
431         if (gpio_is_valid(td->ext_te_gpio))
432                 enable_irq(gpio_to_irq(td->ext_te_gpio));
433
434         taal_queue_ulps_work(dssdev);
435
436         td->ulps_enabled = false;
437
438         return 0;
439
440 err2:
441         dev_err(&dssdev->dev, "failed to exit ULPS");
442
443         r = taal_panel_reset(dssdev);
444         if (!r) {
445                 if (gpio_is_valid(td->ext_te_gpio))
446                         enable_irq(gpio_to_irq(td->ext_te_gpio));
447                 td->ulps_enabled = false;
448         }
449 err1:
450         taal_queue_ulps_work(dssdev);
451
452         return r;
453 }
454
455 static int taal_wake_up(struct omap_dss_device *dssdev)
456 {
457         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
458
459         if (td->ulps_enabled)
460                 return taal_exit_ulps(dssdev);
461
462         taal_cancel_ulps_work(dssdev);
463         taal_queue_ulps_work(dssdev);
464         return 0;
465 }
466
467 static int taal_bl_update_status(struct backlight_device *dev)
468 {
469         struct omap_dss_device *dssdev = dev_get_drvdata(&dev->dev);
470         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
471         int r;
472         int level;
473
474         if (dev->props.fb_blank == FB_BLANK_UNBLANK &&
475                         dev->props.power == FB_BLANK_UNBLANK)
476                 level = dev->props.brightness;
477         else
478                 level = 0;
479
480         dev_dbg(&dssdev->dev, "update brightness to %d\n", level);
481
482         mutex_lock(&td->lock);
483
484         if (td->enabled) {
485                 dsi_bus_lock(dssdev);
486
487                 r = taal_wake_up(dssdev);
488                 if (!r)
489                         r = taal_dcs_write_1(td, DCS_BRIGHTNESS, level);
490
491                 dsi_bus_unlock(dssdev);
492         } else {
493                 r = 0;
494         }
495
496         mutex_unlock(&td->lock);
497
498         return r;
499 }
500
501 static int taal_bl_get_intensity(struct backlight_device *dev)
502 {
503         if (dev->props.fb_blank == FB_BLANK_UNBLANK &&
504                         dev->props.power == FB_BLANK_UNBLANK)
505                 return dev->props.brightness;
506
507         return 0;
508 }
509
510 static const struct backlight_ops taal_bl_ops = {
511         .get_brightness = taal_bl_get_intensity,
512         .update_status  = taal_bl_update_status,
513 };
514
515 static void taal_get_resolution(struct omap_dss_device *dssdev,
516                 u16 *xres, u16 *yres)
517 {
518         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
519
520         if (td->rotate == 0 || td->rotate == 2) {
521                 *xres = dssdev->panel.timings.x_res;
522                 *yres = dssdev->panel.timings.y_res;
523         } else {
524                 *yres = dssdev->panel.timings.x_res;
525                 *xres = dssdev->panel.timings.y_res;
526         }
527 }
528
529 static ssize_t taal_num_errors_show(struct device *dev,
530                 struct device_attribute *attr, char *buf)
531 {
532         struct omap_dss_device *dssdev = to_dss_device(dev);
533         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
534         u8 errors = 0;
535         int r;
536
537         mutex_lock(&td->lock);
538
539         if (td->enabled) {
540                 dsi_bus_lock(dssdev);
541
542                 r = taal_wake_up(dssdev);
543                 if (!r)
544                         r = taal_dcs_read_1(td, DCS_READ_NUM_ERRORS, &errors);
545
546                 dsi_bus_unlock(dssdev);
547         } else {
548                 r = -ENODEV;
549         }
550
551         mutex_unlock(&td->lock);
552
553         if (r)
554                 return r;
555
556         return snprintf(buf, PAGE_SIZE, "%d\n", errors);
557 }
558
559 static ssize_t taal_hw_revision_show(struct device *dev,
560                 struct device_attribute *attr, char *buf)
561 {
562         struct omap_dss_device *dssdev = to_dss_device(dev);
563         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
564         u8 id1, id2, id3;
565         int r;
566
567         mutex_lock(&td->lock);
568
569         if (td->enabled) {
570                 dsi_bus_lock(dssdev);
571
572                 r = taal_wake_up(dssdev);
573                 if (!r)
574                         r = taal_get_id(td, &id1, &id2, &id3);
575
576                 dsi_bus_unlock(dssdev);
577         } else {
578                 r = -ENODEV;
579         }
580
581         mutex_unlock(&td->lock);
582
583         if (r)
584                 return r;
585
586         return snprintf(buf, PAGE_SIZE, "%02x.%02x.%02x\n", id1, id2, id3);
587 }
588
589 static const char *cabc_modes[] = {
590         "off",          /* used also always when CABC is not supported */
591         "ui",
592         "still-image",
593         "moving-image",
594 };
595
596 static ssize_t show_cabc_mode(struct device *dev,
597                 struct device_attribute *attr,
598                 char *buf)
599 {
600         struct omap_dss_device *dssdev = to_dss_device(dev);
601         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
602         const char *mode_str;
603         int mode;
604         int len;
605
606         mode = td->cabc_mode;
607
608         mode_str = "unknown";
609         if (mode >= 0 && mode < ARRAY_SIZE(cabc_modes))
610                 mode_str = cabc_modes[mode];
611         len = snprintf(buf, PAGE_SIZE, "%s\n", mode_str);
612
613         return len < PAGE_SIZE - 1 ? len : PAGE_SIZE - 1;
614 }
615
616 static ssize_t store_cabc_mode(struct device *dev,
617                 struct device_attribute *attr,
618                 const char *buf, size_t count)
619 {
620         struct omap_dss_device *dssdev = to_dss_device(dev);
621         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
622         int i;
623         int r;
624
625         for (i = 0; i < ARRAY_SIZE(cabc_modes); i++) {
626                 if (sysfs_streq(cabc_modes[i], buf))
627                         break;
628         }
629
630         if (i == ARRAY_SIZE(cabc_modes))
631                 return -EINVAL;
632
633         mutex_lock(&td->lock);
634
635         if (td->enabled) {
636                 dsi_bus_lock(dssdev);
637
638                 if (!td->cabc_broken) {
639                         r = taal_wake_up(dssdev);
640                         if (r)
641                                 goto err;
642
643                         r = taal_dcs_write_1(td, DCS_WRITE_CABC, i);
644                         if (r)
645                                 goto err;
646                 }
647
648                 dsi_bus_unlock(dssdev);
649         }
650
651         td->cabc_mode = i;
652
653         mutex_unlock(&td->lock);
654
655         return count;
656 err:
657         dsi_bus_unlock(dssdev);
658         mutex_unlock(&td->lock);
659         return r;
660 }
661
662 static ssize_t show_cabc_available_modes(struct device *dev,
663                 struct device_attribute *attr,
664                 char *buf)
665 {
666         int len;
667         int i;
668
669         for (i = 0, len = 0;
670              len < PAGE_SIZE && i < ARRAY_SIZE(cabc_modes); i++)
671                 len += snprintf(&buf[len], PAGE_SIZE - len, "%s%s%s",
672                         i ? " " : "", cabc_modes[i],
673                         i == ARRAY_SIZE(cabc_modes) - 1 ? "\n" : "");
674
675         return len < PAGE_SIZE ? len : PAGE_SIZE - 1;
676 }
677
678 static ssize_t taal_store_esd_interval(struct device *dev,
679                 struct device_attribute *attr,
680                 const char *buf, size_t count)
681 {
682         struct omap_dss_device *dssdev = to_dss_device(dev);
683         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
684
685         unsigned long t;
686         int r;
687
688         r = strict_strtoul(buf, 10, &t);
689         if (r)
690                 return r;
691
692         mutex_lock(&td->lock);
693         taal_cancel_esd_work(dssdev);
694         td->esd_interval = t;
695         if (td->enabled)
696                 taal_queue_esd_work(dssdev);
697         mutex_unlock(&td->lock);
698
699         return count;
700 }
701
702 static ssize_t taal_show_esd_interval(struct device *dev,
703                 struct device_attribute *attr,
704                 char *buf)
705 {
706         struct omap_dss_device *dssdev = to_dss_device(dev);
707         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
708         unsigned t;
709
710         mutex_lock(&td->lock);
711         t = td->esd_interval;
712         mutex_unlock(&td->lock);
713
714         return snprintf(buf, PAGE_SIZE, "%u\n", t);
715 }
716
717 static ssize_t taal_store_ulps(struct device *dev,
718                 struct device_attribute *attr,
719                 const char *buf, size_t count)
720 {
721         struct omap_dss_device *dssdev = to_dss_device(dev);
722         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
723         unsigned long t;
724         int r;
725
726         r = strict_strtoul(buf, 10, &t);
727         if (r)
728                 return r;
729
730         mutex_lock(&td->lock);
731
732         if (td->enabled) {
733                 dsi_bus_lock(dssdev);
734
735                 if (t)
736                         r = taal_enter_ulps(dssdev);
737                 else
738                         r = taal_wake_up(dssdev);
739
740                 dsi_bus_unlock(dssdev);
741         }
742
743         mutex_unlock(&td->lock);
744
745         if (r)
746                 return r;
747
748         return count;
749 }
750
751 static ssize_t taal_show_ulps(struct device *dev,
752                 struct device_attribute *attr,
753                 char *buf)
754 {
755         struct omap_dss_device *dssdev = to_dss_device(dev);
756         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
757         unsigned t;
758
759         mutex_lock(&td->lock);
760         t = td->ulps_enabled;
761         mutex_unlock(&td->lock);
762
763         return snprintf(buf, PAGE_SIZE, "%u\n", t);
764 }
765
766 static ssize_t taal_store_ulps_timeout(struct device *dev,
767                 struct device_attribute *attr,
768                 const char *buf, size_t count)
769 {
770         struct omap_dss_device *dssdev = to_dss_device(dev);
771         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
772         unsigned long t;
773         int r;
774
775         r = strict_strtoul(buf, 10, &t);
776         if (r)
777                 return r;
778
779         mutex_lock(&td->lock);
780         td->ulps_timeout = t;
781
782         if (td->enabled) {
783                 /* taal_wake_up will restart the timer */
784                 dsi_bus_lock(dssdev);
785                 r = taal_wake_up(dssdev);
786                 dsi_bus_unlock(dssdev);
787         }
788
789         mutex_unlock(&td->lock);
790
791         if (r)
792                 return r;
793
794         return count;
795 }
796
797 static ssize_t taal_show_ulps_timeout(struct device *dev,
798                 struct device_attribute *attr,
799                 char *buf)
800 {
801         struct omap_dss_device *dssdev = to_dss_device(dev);
802         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
803         unsigned t;
804
805         mutex_lock(&td->lock);
806         t = td->ulps_timeout;
807         mutex_unlock(&td->lock);
808
809         return snprintf(buf, PAGE_SIZE, "%u\n", t);
810 }
811
812 static DEVICE_ATTR(num_dsi_errors, S_IRUGO, taal_num_errors_show, NULL);
813 static DEVICE_ATTR(hw_revision, S_IRUGO, taal_hw_revision_show, NULL);
814 static DEVICE_ATTR(cabc_mode, S_IRUGO | S_IWUSR,
815                 show_cabc_mode, store_cabc_mode);
816 static DEVICE_ATTR(cabc_available_modes, S_IRUGO,
817                 show_cabc_available_modes, NULL);
818 static DEVICE_ATTR(esd_interval, S_IRUGO | S_IWUSR,
819                 taal_show_esd_interval, taal_store_esd_interval);
820 static DEVICE_ATTR(ulps, S_IRUGO | S_IWUSR,
821                 taal_show_ulps, taal_store_ulps);
822 static DEVICE_ATTR(ulps_timeout, S_IRUGO | S_IWUSR,
823                 taal_show_ulps_timeout, taal_store_ulps_timeout);
824
825 static struct attribute *taal_attrs[] = {
826         &dev_attr_num_dsi_errors.attr,
827         &dev_attr_hw_revision.attr,
828         &dev_attr_cabc_mode.attr,
829         &dev_attr_cabc_available_modes.attr,
830         &dev_attr_esd_interval.attr,
831         &dev_attr_ulps.attr,
832         &dev_attr_ulps_timeout.attr,
833         NULL,
834 };
835
836 static struct attribute_group taal_attr_group = {
837         .attrs = taal_attrs,
838 };
839
840 static void taal_hw_reset(struct omap_dss_device *dssdev)
841 {
842         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
843
844         if (!gpio_is_valid(td->reset_gpio))
845                 return;
846
847         gpio_set_value(td->reset_gpio, 1);
848         if (td->panel_config->reset_sequence.high)
849                 udelay(td->panel_config->reset_sequence.high);
850         /* reset the panel */
851         gpio_set_value(td->reset_gpio, 0);
852         /* assert reset */
853         if (td->panel_config->reset_sequence.low)
854                 udelay(td->panel_config->reset_sequence.low);
855         gpio_set_value(td->reset_gpio, 1);
856         /* wait after releasing reset */
857         if (td->panel_config->sleep.hw_reset)
858                 msleep(td->panel_config->sleep.hw_reset);
859 }
860
861 static void taal_probe_pdata(struct taal_data *td,
862                 const struct nokia_dsi_panel_data *pdata)
863 {
864         td->reset_gpio = pdata->reset_gpio;
865
866         if (pdata->use_ext_te)
867                 td->ext_te_gpio = pdata->ext_te_gpio;
868         else
869                 td->ext_te_gpio = -1;
870
871         td->esd_interval = pdata->esd_interval;
872         td->ulps_timeout = pdata->ulps_timeout;
873
874         td->use_dsi_backlight = pdata->use_dsi_backlight;
875
876         td->pin_config = pdata->pin_config;
877 }
878
879 static int taal_probe(struct omap_dss_device *dssdev)
880 {
881         struct backlight_properties props;
882         struct taal_data *td;
883         struct backlight_device *bldev = NULL;
884         int r, i;
885         const char *panel_name;
886
887         dev_dbg(&dssdev->dev, "probe\n");
888
889         td = devm_kzalloc(&dssdev->dev, sizeof(*td), GFP_KERNEL);
890         if (!td)
891                 return -ENOMEM;
892
893         dev_set_drvdata(&dssdev->dev, td);
894         td->dssdev = dssdev;
895
896         if (dssdev->data) {
897                 const struct nokia_dsi_panel_data *pdata = dssdev->data;
898
899                 taal_probe_pdata(td, pdata);
900
901                 panel_name = pdata->name;
902         } else {
903                 return -ENODEV;
904         }
905
906         if (panel_name == NULL)
907                 return -EINVAL;
908
909         for (i = 0; i < ARRAY_SIZE(panel_configs); i++) {
910                 if (strcmp(panel_name, panel_configs[i].name) == 0) {
911                         td->panel_config = &panel_configs[i];
912                         break;
913                 }
914         }
915
916         if (!td->panel_config)
917                 return -EINVAL;
918
919         dssdev->panel.timings = td->panel_config->timings;
920         dssdev->panel.dsi_pix_fmt = OMAP_DSS_DSI_FMT_RGB888;
921         dssdev->caps = OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE |
922                 OMAP_DSS_DISPLAY_CAP_TEAR_ELIM;
923
924         mutex_init(&td->lock);
925
926         atomic_set(&td->do_update, 0);
927
928         if (gpio_is_valid(td->reset_gpio)) {
929                 r = devm_gpio_request_one(&dssdev->dev, td->reset_gpio,
930                                 GPIOF_OUT_INIT_LOW, "taal rst");
931                 if (r) {
932                         dev_err(&dssdev->dev, "failed to request reset gpio\n");
933                         return r;
934                 }
935         }
936
937         if (gpio_is_valid(td->ext_te_gpio)) {
938                 r = devm_gpio_request_one(&dssdev->dev, td->ext_te_gpio,
939                                 GPIOF_IN, "taal irq");
940                 if (r) {
941                         dev_err(&dssdev->dev, "GPIO request failed\n");
942                         return r;
943                 }
944
945                 r = devm_request_irq(&dssdev->dev, gpio_to_irq(td->ext_te_gpio),
946                                 taal_te_isr,
947                                 IRQF_TRIGGER_RISING,
948                                 "taal vsync", dssdev);
949
950                 if (r) {
951                         dev_err(&dssdev->dev, "IRQ request failed\n");
952                         return r;
953                 }
954
955                 INIT_DEFERRABLE_WORK(&td->te_timeout_work,
956                                         taal_te_timeout_work_callback);
957
958                 dev_dbg(&dssdev->dev, "Using GPIO TE\n");
959         }
960
961         td->workqueue = create_singlethread_workqueue("taal_esd");
962         if (td->workqueue == NULL) {
963                 dev_err(&dssdev->dev, "can't create ESD workqueue\n");
964                 return -ENOMEM;
965         }
966         INIT_DEFERRABLE_WORK(&td->esd_work, taal_esd_work);
967         INIT_DELAYED_WORK(&td->ulps_work, taal_ulps_work);
968
969         taal_hw_reset(dssdev);
970
971         if (td->use_dsi_backlight) {
972                 memset(&props, 0, sizeof(struct backlight_properties));
973                 props.max_brightness = 255;
974
975                 props.type = BACKLIGHT_RAW;
976                 bldev = backlight_device_register(dev_name(&dssdev->dev),
977                                 &dssdev->dev, dssdev, &taal_bl_ops, &props);
978                 if (IS_ERR(bldev)) {
979                         r = PTR_ERR(bldev);
980                         goto err_bl;
981                 }
982
983                 td->bldev = bldev;
984
985                 bldev->props.fb_blank = FB_BLANK_UNBLANK;
986                 bldev->props.power = FB_BLANK_UNBLANK;
987                 bldev->props.brightness = 255;
988
989                 taal_bl_update_status(bldev);
990         }
991
992         r = omap_dsi_request_vc(dssdev, &td->channel);
993         if (r) {
994                 dev_err(&dssdev->dev, "failed to get virtual channel\n");
995                 goto err_req_vc;
996         }
997
998         r = omap_dsi_set_vc_id(dssdev, td->channel, TCH);
999         if (r) {
1000                 dev_err(&dssdev->dev, "failed to set VC_ID\n");
1001                 goto err_vc_id;
1002         }
1003
1004         r = sysfs_create_group(&dssdev->dev.kobj, &taal_attr_group);
1005         if (r) {
1006                 dev_err(&dssdev->dev, "failed to create sysfs files\n");
1007                 goto err_vc_id;
1008         }
1009
1010         return 0;
1011
1012 err_vc_id:
1013         omap_dsi_release_vc(dssdev, td->channel);
1014 err_req_vc:
1015         if (bldev != NULL)
1016                 backlight_device_unregister(bldev);
1017 err_bl:
1018         destroy_workqueue(td->workqueue);
1019         return r;
1020 }
1021
1022 static void __exit taal_remove(struct omap_dss_device *dssdev)
1023 {
1024         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1025         struct backlight_device *bldev;
1026
1027         dev_dbg(&dssdev->dev, "remove\n");
1028
1029         sysfs_remove_group(&dssdev->dev.kobj, &taal_attr_group);
1030         omap_dsi_release_vc(dssdev, td->channel);
1031
1032         bldev = td->bldev;
1033         if (bldev != NULL) {
1034                 bldev->props.power = FB_BLANK_POWERDOWN;
1035                 taal_bl_update_status(bldev);
1036                 backlight_device_unregister(bldev);
1037         }
1038
1039         taal_cancel_ulps_work(dssdev);
1040         taal_cancel_esd_work(dssdev);
1041         destroy_workqueue(td->workqueue);
1042
1043         /* reset, to be sure that the panel is in a valid state */
1044         taal_hw_reset(dssdev);
1045 }
1046
1047 static int taal_power_on(struct omap_dss_device *dssdev)
1048 {
1049         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1050         u8 id1, id2, id3;
1051         int r;
1052
1053         r = omapdss_dsi_configure_pins(dssdev, &td->pin_config);
1054         if (r) {
1055                 dev_err(&dssdev->dev, "failed to configure DSI pins\n");
1056                 goto err0;
1057         };
1058
1059         omapdss_dsi_set_size(dssdev, dssdev->panel.timings.x_res,
1060                 dssdev->panel.timings.y_res);
1061         omapdss_dsi_set_pixel_format(dssdev, OMAP_DSS_DSI_FMT_RGB888);
1062         omapdss_dsi_set_operation_mode(dssdev, OMAP_DSS_DSI_CMD_MODE);
1063
1064         r = omapdss_dsi_set_clocks(dssdev, 216000000, 10000000);
1065         if (r) {
1066                 dev_err(&dssdev->dev, "failed to set HS and LP clocks\n");
1067                 goto err0;
1068         }
1069
1070         r = omapdss_dsi_display_enable(dssdev);
1071         if (r) {
1072                 dev_err(&dssdev->dev, "failed to enable DSI\n");
1073                 goto err0;
1074         }
1075
1076         taal_hw_reset(dssdev);
1077
1078         omapdss_dsi_vc_enable_hs(dssdev, td->channel, false);
1079
1080         r = taal_sleep_out(td);
1081         if (r)
1082                 goto err;
1083
1084         r = taal_get_id(td, &id1, &id2, &id3);
1085         if (r)
1086                 goto err;
1087
1088         /* on early Taal revisions CABC is broken */
1089         if (td->panel_config->type == PANEL_TAAL &&
1090                 (id2 == 0x00 || id2 == 0xff || id2 == 0x81))
1091                 td->cabc_broken = true;
1092
1093         r = taal_dcs_write_1(td, DCS_BRIGHTNESS, 0xff);
1094         if (r)
1095                 goto err;
1096
1097         r = taal_dcs_write_1(td, DCS_CTRL_DISPLAY,
1098                         (1<<2) | (1<<5));       /* BL | BCTRL */
1099         if (r)
1100                 goto err;
1101
1102         r = taal_dcs_write_1(td, MIPI_DCS_SET_PIXEL_FORMAT,
1103                 MIPI_DCS_PIXEL_FMT_24BIT);
1104         if (r)
1105                 goto err;
1106
1107         r = taal_set_addr_mode(td, td->rotate, td->mirror);
1108         if (r)
1109                 goto err;
1110
1111         if (!td->cabc_broken) {
1112                 r = taal_dcs_write_1(td, DCS_WRITE_CABC, td->cabc_mode);
1113                 if (r)
1114                         goto err;
1115         }
1116
1117         r = taal_dcs_write_0(td, MIPI_DCS_SET_DISPLAY_ON);
1118         if (r)
1119                 goto err;
1120
1121         r = _taal_enable_te(dssdev, td->te_enabled);
1122         if (r)
1123                 goto err;
1124
1125         r = dsi_enable_video_output(dssdev, td->channel);
1126         if (r)
1127                 goto err;
1128
1129         td->enabled = 1;
1130
1131         if (!td->intro_printed) {
1132                 dev_info(&dssdev->dev, "%s panel revision %02x.%02x.%02x\n",
1133                         td->panel_config->name, id1, id2, id3);
1134                 if (td->cabc_broken)
1135                         dev_info(&dssdev->dev,
1136                                         "old Taal version, CABC disabled\n");
1137                 td->intro_printed = true;
1138         }
1139
1140         omapdss_dsi_vc_enable_hs(dssdev, td->channel, true);
1141
1142         return 0;
1143 err:
1144         dev_err(&dssdev->dev, "error while enabling panel, issuing HW reset\n");
1145
1146         taal_hw_reset(dssdev);
1147
1148         omapdss_dsi_display_disable(dssdev, true, false);
1149 err0:
1150         return r;
1151 }
1152
1153 static void taal_power_off(struct omap_dss_device *dssdev)
1154 {
1155         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1156         int r;
1157
1158         dsi_disable_video_output(dssdev, td->channel);
1159
1160         r = taal_dcs_write_0(td, MIPI_DCS_SET_DISPLAY_OFF);
1161         if (!r)
1162                 r = taal_sleep_in(td);
1163
1164         if (r) {
1165                 dev_err(&dssdev->dev,
1166                                 "error disabling panel, issuing HW reset\n");
1167                 taal_hw_reset(dssdev);
1168         }
1169
1170         omapdss_dsi_display_disable(dssdev, true, false);
1171
1172         td->enabled = 0;
1173 }
1174
1175 static int taal_panel_reset(struct omap_dss_device *dssdev)
1176 {
1177         dev_err(&dssdev->dev, "performing LCD reset\n");
1178
1179         taal_power_off(dssdev);
1180         taal_hw_reset(dssdev);
1181         return taal_power_on(dssdev);
1182 }
1183
1184 static int taal_enable(struct omap_dss_device *dssdev)
1185 {
1186         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1187         int r;
1188
1189         dev_dbg(&dssdev->dev, "enable\n");
1190
1191         mutex_lock(&td->lock);
1192
1193         if (dssdev->state != OMAP_DSS_DISPLAY_DISABLED) {
1194                 r = -EINVAL;
1195                 goto err;
1196         }
1197
1198         dsi_bus_lock(dssdev);
1199
1200         r = taal_power_on(dssdev);
1201
1202         dsi_bus_unlock(dssdev);
1203
1204         if (r)
1205                 goto err;
1206
1207         taal_queue_esd_work(dssdev);
1208
1209         dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
1210
1211         mutex_unlock(&td->lock);
1212
1213         return 0;
1214 err:
1215         dev_dbg(&dssdev->dev, "enable failed\n");
1216         mutex_unlock(&td->lock);
1217         return r;
1218 }
1219
1220 static void taal_disable(struct omap_dss_device *dssdev)
1221 {
1222         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1223
1224         dev_dbg(&dssdev->dev, "disable\n");
1225
1226         mutex_lock(&td->lock);
1227
1228         taal_cancel_ulps_work(dssdev);
1229         taal_cancel_esd_work(dssdev);
1230
1231         dsi_bus_lock(dssdev);
1232
1233         if (dssdev->state == OMAP_DSS_DISPLAY_ACTIVE) {
1234                 int r;
1235
1236                 r = taal_wake_up(dssdev);
1237                 if (!r)
1238                         taal_power_off(dssdev);
1239         }
1240
1241         dsi_bus_unlock(dssdev);
1242
1243         dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
1244
1245         mutex_unlock(&td->lock);
1246 }
1247
1248 static int taal_suspend(struct omap_dss_device *dssdev)
1249 {
1250         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1251         int r;
1252
1253         dev_dbg(&dssdev->dev, "suspend\n");
1254
1255         mutex_lock(&td->lock);
1256
1257         if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE) {
1258                 r = -EINVAL;
1259                 goto err;
1260         }
1261
1262         taal_cancel_ulps_work(dssdev);
1263         taal_cancel_esd_work(dssdev);
1264
1265         dsi_bus_lock(dssdev);
1266
1267         r = taal_wake_up(dssdev);
1268         if (!r)
1269                 taal_power_off(dssdev);
1270
1271         dsi_bus_unlock(dssdev);
1272
1273         dssdev->state = OMAP_DSS_DISPLAY_SUSPENDED;
1274
1275         mutex_unlock(&td->lock);
1276
1277         return 0;
1278 err:
1279         mutex_unlock(&td->lock);
1280         return r;
1281 }
1282
1283 static int taal_resume(struct omap_dss_device *dssdev)
1284 {
1285         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1286         int r;
1287
1288         dev_dbg(&dssdev->dev, "resume\n");
1289
1290         mutex_lock(&td->lock);
1291
1292         if (dssdev->state != OMAP_DSS_DISPLAY_SUSPENDED) {
1293                 r = -EINVAL;
1294                 goto err;
1295         }
1296
1297         dsi_bus_lock(dssdev);
1298
1299         r = taal_power_on(dssdev);
1300
1301         dsi_bus_unlock(dssdev);
1302
1303         if (r) {
1304                 dssdev->state = OMAP_DSS_DISPLAY_DISABLED;
1305         } else {
1306                 dssdev->state = OMAP_DSS_DISPLAY_ACTIVE;
1307                 taal_queue_esd_work(dssdev);
1308         }
1309
1310         mutex_unlock(&td->lock);
1311
1312         return r;
1313 err:
1314         mutex_unlock(&td->lock);
1315         return r;
1316 }
1317
1318 static void taal_framedone_cb(int err, void *data)
1319 {
1320         struct omap_dss_device *dssdev = data;
1321         dev_dbg(&dssdev->dev, "framedone, err %d\n", err);
1322         dsi_bus_unlock(dssdev);
1323 }
1324
1325 static irqreturn_t taal_te_isr(int irq, void *data)
1326 {
1327         struct omap_dss_device *dssdev = data;
1328         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1329         int old;
1330         int r;
1331
1332         old = atomic_cmpxchg(&td->do_update, 1, 0);
1333
1334         if (old) {
1335                 cancel_delayed_work(&td->te_timeout_work);
1336
1337                 r = omap_dsi_update(dssdev, td->channel, taal_framedone_cb,
1338                                 dssdev);
1339                 if (r)
1340                         goto err;
1341         }
1342
1343         return IRQ_HANDLED;
1344 err:
1345         dev_err(&dssdev->dev, "start update failed\n");
1346         dsi_bus_unlock(dssdev);
1347         return IRQ_HANDLED;
1348 }
1349
1350 static void taal_te_timeout_work_callback(struct work_struct *work)
1351 {
1352         struct taal_data *td = container_of(work, struct taal_data,
1353                                         te_timeout_work.work);
1354         struct omap_dss_device *dssdev = td->dssdev;
1355
1356         dev_err(&dssdev->dev, "TE not received for 250ms!\n");
1357
1358         atomic_set(&td->do_update, 0);
1359         dsi_bus_unlock(dssdev);
1360 }
1361
1362 static int taal_update(struct omap_dss_device *dssdev,
1363                                     u16 x, u16 y, u16 w, u16 h)
1364 {
1365         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1366         int r;
1367
1368         dev_dbg(&dssdev->dev, "update %d, %d, %d x %d\n", x, y, w, h);
1369
1370         mutex_lock(&td->lock);
1371         dsi_bus_lock(dssdev);
1372
1373         r = taal_wake_up(dssdev);
1374         if (r)
1375                 goto err;
1376
1377         if (!td->enabled) {
1378                 r = 0;
1379                 goto err;
1380         }
1381
1382         /* XXX no need to send this every frame, but dsi break if not done */
1383         r = taal_set_update_window(td, 0, 0,
1384                         td->panel_config->timings.x_res,
1385                         td->panel_config->timings.y_res);
1386         if (r)
1387                 goto err;
1388
1389         if (td->te_enabled && gpio_is_valid(td->ext_te_gpio)) {
1390                 schedule_delayed_work(&td->te_timeout_work,
1391                                 msecs_to_jiffies(250));
1392                 atomic_set(&td->do_update, 1);
1393         } else {
1394                 r = omap_dsi_update(dssdev, td->channel, taal_framedone_cb,
1395                                 dssdev);
1396                 if (r)
1397                         goto err;
1398         }
1399
1400         /* note: no bus_unlock here. unlock is in framedone_cb */
1401         mutex_unlock(&td->lock);
1402         return 0;
1403 err:
1404         dsi_bus_unlock(dssdev);
1405         mutex_unlock(&td->lock);
1406         return r;
1407 }
1408
1409 static int taal_sync(struct omap_dss_device *dssdev)
1410 {
1411         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1412
1413         dev_dbg(&dssdev->dev, "sync\n");
1414
1415         mutex_lock(&td->lock);
1416         dsi_bus_lock(dssdev);
1417         dsi_bus_unlock(dssdev);
1418         mutex_unlock(&td->lock);
1419
1420         dev_dbg(&dssdev->dev, "sync done\n");
1421
1422         return 0;
1423 }
1424
1425 static int _taal_enable_te(struct omap_dss_device *dssdev, bool enable)
1426 {
1427         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1428         int r;
1429
1430         if (enable)
1431                 r = taal_dcs_write_1(td, MIPI_DCS_SET_TEAR_ON, 0);
1432         else
1433                 r = taal_dcs_write_0(td, MIPI_DCS_SET_TEAR_OFF);
1434
1435         if (!gpio_is_valid(td->ext_te_gpio))
1436                 omapdss_dsi_enable_te(dssdev, enable);
1437
1438         if (td->panel_config->sleep.enable_te)
1439                 msleep(td->panel_config->sleep.enable_te);
1440
1441         return r;
1442 }
1443
1444 static int taal_enable_te(struct omap_dss_device *dssdev, bool enable)
1445 {
1446         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1447         int r;
1448
1449         mutex_lock(&td->lock);
1450
1451         if (td->te_enabled == enable)
1452                 goto end;
1453
1454         dsi_bus_lock(dssdev);
1455
1456         if (td->enabled) {
1457                 r = taal_wake_up(dssdev);
1458                 if (r)
1459                         goto err;
1460
1461                 r = _taal_enable_te(dssdev, enable);
1462                 if (r)
1463                         goto err;
1464         }
1465
1466         td->te_enabled = enable;
1467
1468         dsi_bus_unlock(dssdev);
1469 end:
1470         mutex_unlock(&td->lock);
1471
1472         return 0;
1473 err:
1474         dsi_bus_unlock(dssdev);
1475         mutex_unlock(&td->lock);
1476
1477         return r;
1478 }
1479
1480 static int taal_get_te(struct omap_dss_device *dssdev)
1481 {
1482         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1483         int r;
1484
1485         mutex_lock(&td->lock);
1486         r = td->te_enabled;
1487         mutex_unlock(&td->lock);
1488
1489         return r;
1490 }
1491
1492 static int taal_rotate(struct omap_dss_device *dssdev, u8 rotate)
1493 {
1494         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1495         u16 dw, dh;
1496         int r;
1497
1498         dev_dbg(&dssdev->dev, "rotate %d\n", rotate);
1499
1500         mutex_lock(&td->lock);
1501
1502         if (td->rotate == rotate)
1503                 goto end;
1504
1505         dsi_bus_lock(dssdev);
1506
1507         if (td->enabled) {
1508                 r = taal_wake_up(dssdev);
1509                 if (r)
1510                         goto err;
1511
1512                 r = taal_set_addr_mode(td, rotate, td->mirror);
1513                 if (r)
1514                         goto err;
1515         }
1516
1517         if (rotate == 0 || rotate == 2) {
1518                 dw = dssdev->panel.timings.x_res;
1519                 dh = dssdev->panel.timings.y_res;
1520         } else {
1521                 dw = dssdev->panel.timings.y_res;
1522                 dh = dssdev->panel.timings.x_res;
1523         }
1524
1525         omapdss_dsi_set_size(dssdev, dw, dh);
1526
1527         td->rotate = rotate;
1528
1529         dsi_bus_unlock(dssdev);
1530 end:
1531         mutex_unlock(&td->lock);
1532         return 0;
1533 err:
1534         dsi_bus_unlock(dssdev);
1535         mutex_unlock(&td->lock);
1536         return r;
1537 }
1538
1539 static u8 taal_get_rotate(struct omap_dss_device *dssdev)
1540 {
1541         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1542         int r;
1543
1544         mutex_lock(&td->lock);
1545         r = td->rotate;
1546         mutex_unlock(&td->lock);
1547
1548         return r;
1549 }
1550
1551 static int taal_mirror(struct omap_dss_device *dssdev, bool enable)
1552 {
1553         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1554         int r;
1555
1556         dev_dbg(&dssdev->dev, "mirror %d\n", enable);
1557
1558         mutex_lock(&td->lock);
1559
1560         if (td->mirror == enable)
1561                 goto end;
1562
1563         dsi_bus_lock(dssdev);
1564         if (td->enabled) {
1565                 r = taal_wake_up(dssdev);
1566                 if (r)
1567                         goto err;
1568
1569                 r = taal_set_addr_mode(td, td->rotate, enable);
1570                 if (r)
1571                         goto err;
1572         }
1573
1574         td->mirror = enable;
1575
1576         dsi_bus_unlock(dssdev);
1577 end:
1578         mutex_unlock(&td->lock);
1579         return 0;
1580 err:
1581         dsi_bus_unlock(dssdev);
1582         mutex_unlock(&td->lock);
1583         return r;
1584 }
1585
1586 static bool taal_get_mirror(struct omap_dss_device *dssdev)
1587 {
1588         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1589         int r;
1590
1591         mutex_lock(&td->lock);
1592         r = td->mirror;
1593         mutex_unlock(&td->lock);
1594
1595         return r;
1596 }
1597
1598 static int taal_run_test(struct omap_dss_device *dssdev, int test_num)
1599 {
1600         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1601         u8 id1, id2, id3;
1602         int r;
1603
1604         mutex_lock(&td->lock);
1605
1606         if (!td->enabled) {
1607                 r = -ENODEV;
1608                 goto err1;
1609         }
1610
1611         dsi_bus_lock(dssdev);
1612
1613         r = taal_wake_up(dssdev);
1614         if (r)
1615                 goto err2;
1616
1617         r = taal_dcs_read_1(td, DCS_GET_ID1, &id1);
1618         if (r)
1619                 goto err2;
1620         r = taal_dcs_read_1(td, DCS_GET_ID2, &id2);
1621         if (r)
1622                 goto err2;
1623         r = taal_dcs_read_1(td, DCS_GET_ID3, &id3);
1624         if (r)
1625                 goto err2;
1626
1627         dsi_bus_unlock(dssdev);
1628         mutex_unlock(&td->lock);
1629         return 0;
1630 err2:
1631         dsi_bus_unlock(dssdev);
1632 err1:
1633         mutex_unlock(&td->lock);
1634         return r;
1635 }
1636
1637 static int taal_memory_read(struct omap_dss_device *dssdev,
1638                 void *buf, size_t size,
1639                 u16 x, u16 y, u16 w, u16 h)
1640 {
1641         int r;
1642         int first = 1;
1643         int plen;
1644         unsigned buf_used = 0;
1645         struct taal_data *td = dev_get_drvdata(&dssdev->dev);
1646
1647         if (size < w * h * 3)
1648                 return -ENOMEM;
1649
1650         mutex_lock(&td->lock);
1651
1652         if (!td->enabled) {
1653                 r = -ENODEV;
1654                 goto err1;
1655         }
1656
1657         size = min(w * h * 3,
1658                         dssdev->panel.timings.x_res *
1659                         dssdev->panel.timings.y_res * 3);
1660
1661         dsi_bus_lock(dssdev);
1662
1663         r = taal_wake_up(dssdev);
1664         if (r)
1665                 goto err2;
1666
1667         /* plen 1 or 2 goes into short packet. until checksum error is fixed,
1668          * use short packets. plen 32 works, but bigger packets seem to cause
1669          * an error. */
1670         if (size % 2)
1671                 plen = 1;
1672         else
1673                 plen = 2;
1674
1675         taal_set_update_window(td, x, y, w, h);
1676
1677         r = dsi_vc_set_max_rx_packet_size(dssdev, td->channel, plen);
1678         if (r)
1679                 goto err2;
1680
1681         while (buf_used < size) {
1682                 u8 dcs_cmd = first ? 0x2e : 0x3e;
1683                 first = 0;
1684
1685                 r = dsi_vc_dcs_read(dssdev, td->channel, dcs_cmd,
1686                                 buf + buf_used, size - buf_used);
1687
1688                 if (r < 0) {
1689                         dev_err(&dssdev->dev, "read error\n");
1690                         goto err3;
1691                 }
1692
1693                 buf_used += r;
1694
1695                 if (r < plen) {
1696                         dev_err(&dssdev->dev, "short read\n");
1697                         break;
1698                 }
1699
1700                 if (signal_pending(current)) {
1701                         dev_err(&dssdev->dev, "signal pending, "
1702                                         "aborting memory read\n");
1703                         r = -ERESTARTSYS;
1704                         goto err3;
1705                 }
1706         }
1707
1708         r = buf_used;
1709
1710 err3:
1711         dsi_vc_set_max_rx_packet_size(dssdev, td->channel, 1);
1712 err2:
1713         dsi_bus_unlock(dssdev);
1714 err1:
1715         mutex_unlock(&td->lock);
1716         return r;
1717 }
1718
1719 static void taal_ulps_work(struct work_struct *work)
1720 {
1721         struct taal_data *td = container_of(work, struct taal_data,
1722                         ulps_work.work);
1723         struct omap_dss_device *dssdev = td->dssdev;
1724
1725         mutex_lock(&td->lock);
1726
1727         if (dssdev->state != OMAP_DSS_DISPLAY_ACTIVE || !td->enabled) {
1728                 mutex_unlock(&td->lock);
1729                 return;
1730         }
1731
1732         dsi_bus_lock(dssdev);
1733
1734         taal_enter_ulps(dssdev);
1735
1736         dsi_bus_unlock(dssdev);
1737         mutex_unlock(&td->lock);
1738 }
1739
1740 static void taal_esd_work(struct work_struct *work)
1741 {
1742         struct taal_data *td = container_of(work, struct taal_data,
1743                         esd_work.work);
1744         struct omap_dss_device *dssdev = td->dssdev;
1745         u8 state1, state2;
1746         int r;
1747
1748         mutex_lock(&td->lock);
1749
1750         if (!td->enabled) {
1751                 mutex_unlock(&td->lock);
1752                 return;
1753         }
1754
1755         dsi_bus_lock(dssdev);
1756
1757         r = taal_wake_up(dssdev);
1758         if (r) {
1759                 dev_err(&dssdev->dev, "failed to exit ULPS\n");
1760                 goto err;
1761         }
1762
1763         r = taal_dcs_read_1(td, MIPI_DCS_GET_DIAGNOSTIC_RESULT, &state1);
1764         if (r) {
1765                 dev_err(&dssdev->dev, "failed to read Taal status\n");
1766                 goto err;
1767         }
1768
1769         /* Run self diagnostics */
1770         r = taal_sleep_out(td);
1771         if (r) {
1772                 dev_err(&dssdev->dev, "failed to run Taal self-diagnostics\n");
1773                 goto err;
1774         }
1775
1776         r = taal_dcs_read_1(td, MIPI_DCS_GET_DIAGNOSTIC_RESULT, &state2);
1777         if (r) {
1778                 dev_err(&dssdev->dev, "failed to read Taal status\n");
1779                 goto err;
1780         }
1781
1782         /* Each sleep out command will trigger a self diagnostic and flip
1783          * Bit6 if the test passes.
1784          */
1785         if (!((state1 ^ state2) & (1 << 6))) {
1786                 dev_err(&dssdev->dev, "LCD self diagnostics failed\n");
1787                 goto err;
1788         }
1789         /* Self-diagnostics result is also shown on TE GPIO line. We need
1790          * to re-enable TE after self diagnostics */
1791         if (td->te_enabled && gpio_is_valid(td->ext_te_gpio)) {
1792                 r = taal_dcs_write_1(td, MIPI_DCS_SET_TEAR_ON, 0);
1793                 if (r)
1794                         goto err;
1795         }
1796
1797         dsi_bus_unlock(dssdev);
1798
1799         taal_queue_esd_work(dssdev);
1800
1801         mutex_unlock(&td->lock);
1802         return;
1803 err:
1804         dev_err(&dssdev->dev, "performing LCD reset\n");
1805
1806         taal_panel_reset(dssdev);
1807
1808         dsi_bus_unlock(dssdev);
1809
1810         taal_queue_esd_work(dssdev);
1811
1812         mutex_unlock(&td->lock);
1813 }
1814
1815 static struct omap_dss_driver taal_driver = {
1816         .probe          = taal_probe,
1817         .remove         = __exit_p(taal_remove),
1818
1819         .enable         = taal_enable,
1820         .disable        = taal_disable,
1821         .suspend        = taal_suspend,
1822         .resume         = taal_resume,
1823
1824         .update         = taal_update,
1825         .sync           = taal_sync,
1826
1827         .get_resolution = taal_get_resolution,
1828         .get_recommended_bpp = omapdss_default_get_recommended_bpp,
1829
1830         .enable_te      = taal_enable_te,
1831         .get_te         = taal_get_te,
1832
1833         .set_rotate     = taal_rotate,
1834         .get_rotate     = taal_get_rotate,
1835         .set_mirror     = taal_mirror,
1836         .get_mirror     = taal_get_mirror,
1837         .run_test       = taal_run_test,
1838         .memory_read    = taal_memory_read,
1839
1840         .driver         = {
1841                 .name   = "taal",
1842                 .owner  = THIS_MODULE,
1843         },
1844 };
1845
1846 static int __init taal_init(void)
1847 {
1848         omap_dss_register_driver(&taal_driver);
1849
1850         return 0;
1851 }
1852
1853 static void __exit taal_exit(void)
1854 {
1855         omap_dss_unregister_driver(&taal_driver);
1856 }
1857
1858 module_init(taal_init);
1859 module_exit(taal_exit);
1860
1861 MODULE_AUTHOR("Tomi Valkeinen <tomi.valkeinen@nokia.com>");
1862 MODULE_DESCRIPTION("Taal Driver");
1863 MODULE_LICENSE("GPL");