ARM: tegra: cardhu: Changes for DIDIM/Backlight
[linux-2.6.git] / arch / arm / mach-tegra / board-cardhu-panel.c
1 /*
2  * arch/arm/mach-tegra/board-cardhu-panel.c
3  *
4  * Copyright (c) 2010-2011, NVIDIA Corporation.
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
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
17  * with this program; if not, write to the Free Software Foundation, Inc.,
18  * 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
19  */
20
21 #include <linux/delay.h>
22 #include <linux/gpio.h>
23 #include <linux/regulator/consumer.h>
24 #include <linux/resource.h>
25 #include <asm/mach-types.h>
26 #include <linux/platform_device.h>
27 #include <linux/pwm_backlight.h>
28 #include <asm/atomic.h>
29 #include <mach/nvhost.h>
30 #include <mach/nvmap.h>
31 #include <mach/irqs.h>
32 #include <mach/iomap.h>
33 #include <mach/dc.h>
34 #include <mach/fb.h>
35
36 #include "board.h"
37 #include "board-cardhu.h"
38 #include "devices.h"
39 #include "gpio-names.h"
40
41 /* Select panel to be used. */
42 #define DSI_PANEL_219 0
43 #define DSI_PANEL_218 1
44 #define AVDD_LCD PMU_TCA6416_GPIO_PORT17
45 #define DSI_PANEL_RESET 0
46
47 #define pm269_lvds_shutdown     TEGRA_GPIO_PN6
48 #define cardhu_lvds_shutdown    TEGRA_GPIO_PL2
49 #define cardhu_bl_enb           TEGRA_GPIO_PH2
50 #define cardhu_bl_pwm           TEGRA_GPIO_PH0
51 #define cardhu_hdmi_hpd         TEGRA_GPIO_PN7
52
53 #if defined(DSI_PANEL_219) || defined(DSI_PANEL_218)
54 #define cardhu_dsia_bl_enb      TEGRA_GPIO_PW1
55 #define cardhu_dsib_bl_enb      TEGRA_GPIO_PW0
56 #define cardhu_dsi_panel_reset  TEGRA_GPIO_PD2
57 #endif
58
59 static struct regulator *cardhu_hdmi_reg = NULL;
60 static struct regulator *cardhu_hdmi_pll = NULL;
61 static struct regulator *cardhu_hdmi_vddio = NULL;
62
63 static atomic_t sd_brightness = ATOMIC_INIT(255);
64
65 #ifdef CONFIG_TEGRA_CARDHU_DSI
66 static struct regulator *cardhu_dsi_reg = NULL;
67 #else
68 static struct regulator *cardhu_lvds_reg = NULL;
69 static struct regulator *cardhu_lvds_vdd_bl = NULL;
70 static struct regulator *cardhu_lvds_vdd_panel = NULL;
71 #endif
72
73 static struct board_info board_info;
74
75 static tegra_dc_bl_output cardhu_bl_output_measured = {
76         0, 1, 2, 3, 4, 5, 6, 7,
77         8, 9, 10, 11, 12, 13, 14, 15,
78         16, 17, 18, 19, 20, 21, 22, 23,
79         24, 25, 26, 27, 28, 29, 30, 31,
80         32, 33, 34, 35, 36, 37, 38, 39,
81         40, 41, 42, 43, 44, 45, 46, 47,
82         48, 49, 49, 50, 51, 52, 53, 54,
83         55, 56, 57, 58, 59, 60, 61, 62,
84         63, 64, 65, 66, 67, 68, 69, 70,
85         70, 72, 73, 74, 75, 76, 77, 78,
86         79, 80, 81, 82, 83, 84, 85, 86,
87         87, 88, 89, 90, 91, 92, 93, 94,
88         95, 96, 97, 98, 99, 100, 101, 102,
89         103, 104, 105, 106, 107, 108, 110, 111,
90         112, 113, 114, 115, 116, 117, 118, 119,
91         120, 121, 122, 123, 124, 124, 125, 126,
92         127, 128, 129, 130, 131, 132, 133, 133,
93         134, 135, 137, 138, 139, 140, 141, 142,
94         143, 144, 145, 146, 147, 148, 148, 149,
95         150, 151, 152, 153, 154, 155, 156, 157,
96         158, 159, 160, 161, 162, 163, 164, 165,
97         166, 167, 168, 169, 170, 171, 172, 173,
98         174, 175, 176, 177, 179, 180, 181, 182,
99         184, 185, 186, 187, 188, 189, 190, 191,
100         192, 193, 194, 195, 196, 197, 198, 199,
101         200, 201, 202, 203, 204, 205, 206, 207,
102         208, 209, 211, 212, 213, 214, 215, 216,
103         217, 218, 219, 220, 221, 222, 223, 224,
104         225, 226, 227, 228, 229, 230, 231, 232,
105         233, 234, 235, 236, 237, 238, 239, 240,
106         241, 242, 243, 244, 245, 246, 247, 248,
107         249, 250, 251, 252, 253, 254, 255
108 };
109
110 static p_tegra_dc_bl_output bl_output = cardhu_bl_output_measured;
111
112 static int cardhu_backlight_init(struct device *dev) {
113         int ret;
114
115 #ifndef CONFIG_TEGRA_CARDHU_DSI
116         tegra_gpio_disable(cardhu_bl_pwm);
117
118         ret = gpio_request(cardhu_bl_enb, "backlight_enb");
119         if (ret < 0)
120                 return ret;
121
122         ret = gpio_direction_output(cardhu_bl_enb, 1);
123         if (ret < 0)
124                 gpio_free(cardhu_bl_enb);
125         else
126                 tegra_gpio_enable(cardhu_bl_enb);
127
128         return ret;
129 #endif
130
131 #if DSI_PANEL_219 || DSI_PANEL_218
132         /* Enable back light for DSIa panel */
133         printk("cardhu_dsi_backlight_init\n");
134         ret = gpio_request(cardhu_dsia_bl_enb, "dsia_bl_enable");
135         if (ret < 0)
136                 return ret;
137
138         ret = gpio_direction_output(cardhu_dsia_bl_enb, 1);
139         if (ret < 0)
140                 gpio_free(cardhu_dsia_bl_enb);
141         else
142                 tegra_gpio_enable(cardhu_dsia_bl_enb);
143
144         /* Enable back light for DSIb panel */
145         ret = gpio_request(cardhu_dsib_bl_enb, "dsib_bl_enable");
146         if (ret < 0)
147                 return ret;
148
149         ret = gpio_direction_output(cardhu_dsib_bl_enb, 1);
150         if (ret < 0)
151                 gpio_free(cardhu_dsib_bl_enb);
152         else
153                 tegra_gpio_enable(cardhu_dsib_bl_enb);
154 #endif
155
156         return ret;
157 };
158
159 static void cardhu_backlight_exit(struct device *dev) {
160 #ifndef CONFIG_TEGRA_CARDHU_DSI
161         /* int ret; */
162         /*ret = gpio_request(cardhu_bl_enb, "backlight_enb");*/
163         gpio_set_value(cardhu_bl_enb, 0);
164         gpio_free(cardhu_bl_enb);
165         tegra_gpio_disable(cardhu_bl_enb);
166         return;
167 #endif
168 #if DSI_PANEL_219 || DSI_PANEL_218
169         /* Disable back light for DSIa panel */
170         gpio_set_value(cardhu_dsia_bl_enb, 0);
171         gpio_free(cardhu_dsia_bl_enb);
172         tegra_gpio_disable(cardhu_dsia_bl_enb);
173
174         /* Disable back light for DSIb panel */
175         gpio_set_value(cardhu_dsib_bl_enb, 0);
176         gpio_free(cardhu_dsib_bl_enb);
177         tegra_gpio_disable(cardhu_dsib_bl_enb);
178
179         gpio_set_value(cardhu_lvds_shutdown, 1);
180         mdelay(20);
181 #endif
182 }
183
184 static int cardhu_backlight_notify(struct device *unused, int brightness)
185 {
186         int cur_sd_brightness = atomic_read(&sd_brightness);
187         int orig_brightness = brightness;
188
189 #ifndef CONFIG_TEGRA_CARDHU_DSI
190         /* Set the backlight GPIO pin mode to 'backlight_enable' */
191         gpio_request(cardhu_bl_enb, "backlight_enb");
192         gpio_set_value(cardhu_bl_enb, !!brightness);
193 #elif DSI_PANEL_219 || DSI_PANEL_218
194         /* DSIa */
195         gpio_set_value(cardhu_dsia_bl_enb, !!brightness);
196
197         /* DSIb */
198         gpio_set_value(cardhu_dsib_bl_enb, !!brightness);
199 #endif
200
201         /* SD brightness is a percentage, 8-bit value. */
202         brightness = (brightness * cur_sd_brightness) / 255;
203         if (cur_sd_brightness != 255) {
204                 printk("NVSD BL - in: %d, sd: %d, out: %d\n",
205                         orig_brightness, cur_sd_brightness, brightness);
206         }
207
208         /* Apply any backlight response curve */
209         if (brightness > 255) {
210                 pr_info("Error: Brightness > 255!\n");
211         } else {
212                 brightness = bl_output[brightness];
213         }
214
215         return brightness;
216 }
217
218 static struct platform_pwm_backlight_data cardhu_backlight_data = {
219         .pwm_id         = 0,
220         .max_brightness = 255,
221         .dft_brightness = 224,
222         .pwm_period_ns  = 5000000,
223         .init           = cardhu_backlight_init,
224         .exit           = cardhu_backlight_exit,
225         .notify         = cardhu_backlight_notify,
226 };
227
228 static struct platform_device cardhu_backlight_device = {
229         .name   = "pwm-backlight",
230         .id     = -1,
231         .dev    = {
232                 .platform_data = &cardhu_backlight_data,
233         },
234 };
235
236 #ifndef CONFIG_TEGRA_CARDHU_DSI
237 static int cardhu_panel_enable(void)
238 {
239         if (cardhu_lvds_reg == NULL) {
240                 cardhu_lvds_reg = regulator_get(NULL, "vdd_lvds");
241                 if (WARN_ON(IS_ERR(cardhu_lvds_reg)))
242                         pr_err("%s: couldn't get regulator vdd_lvds: %ld\n",
243                                __func__, PTR_ERR(cardhu_lvds_reg));
244                 else
245                         regulator_enable(cardhu_lvds_reg);
246         }
247
248         if (cardhu_lvds_vdd_bl == NULL) {
249                 cardhu_lvds_vdd_bl = regulator_get(NULL, "vdd_backlight");
250                 if (WARN_ON(IS_ERR(cardhu_lvds_vdd_bl)))
251                         pr_err("%s: couldn't get regulator vdd_backlight: %ld\n",
252                                __func__, PTR_ERR(cardhu_lvds_vdd_bl));
253                 else
254                         regulator_enable(cardhu_lvds_vdd_bl);
255         }
256
257         if (cardhu_lvds_vdd_panel == NULL) {
258                 cardhu_lvds_vdd_panel = regulator_get(NULL, "vdd_lcd_panel");
259                 if (WARN_ON(IS_ERR(cardhu_lvds_vdd_panel)))
260                         pr_err("%s: couldn't get regulator vdd_lcd_panel: %ld\n",
261                                __func__, PTR_ERR(cardhu_lvds_vdd_panel));
262                 else
263                         regulator_enable(cardhu_lvds_vdd_panel);
264         }
265         if (board_info.board_id == BOARD_PM269)
266                 gpio_set_value(pm269_lvds_shutdown, 1);
267         else
268                 gpio_set_value(cardhu_lvds_shutdown, 1);
269
270         return 0;
271 }
272
273 static int cardhu_panel_disable(void)
274 {
275         regulator_disable(cardhu_lvds_reg);
276         regulator_put(cardhu_lvds_reg);
277         cardhu_lvds_reg = NULL;
278
279         regulator_disable(cardhu_lvds_vdd_bl);
280         regulator_put(cardhu_lvds_vdd_bl);
281         cardhu_lvds_vdd_bl = NULL;
282
283         regulator_disable(cardhu_lvds_vdd_panel);
284         regulator_put(cardhu_lvds_vdd_panel);
285         cardhu_lvds_vdd_panel= NULL;
286         if (board_info.board_id == BOARD_PM269)
287                 gpio_set_value(pm269_lvds_shutdown, 0);
288         else
289                 gpio_set_value(cardhu_lvds_shutdown, 0);
290         return 0;
291 }
292 #endif
293
294 static int cardhu_hdmi_vddio_enable(void)
295 {
296         int ret;
297         if (!cardhu_hdmi_vddio) {
298                 cardhu_hdmi_vddio = regulator_get(NULL, "vdd_hdmi_con");
299                 if (IS_ERR_OR_NULL(cardhu_hdmi_vddio)) {
300                         ret = PTR_ERR(cardhu_hdmi_vddio);
301                         pr_err("hdmi: couldn't get regulator vdd_hdmi_con\n");
302                         cardhu_hdmi_vddio = NULL;
303                         return ret;
304                 }
305         }
306         ret = regulator_enable(cardhu_hdmi_vddio);
307         if (ret < 0) {
308                 pr_err("hdmi: couldn't enable regulator vdd_hdmi_con\n");
309                 regulator_put(cardhu_hdmi_vddio);
310                 cardhu_hdmi_vddio = NULL;
311                 return ret;
312         }
313         return ret;
314 }
315
316 static int cardhu_hdmi_vddio_disable(void)
317 {
318         if (cardhu_hdmi_vddio) {
319                 regulator_disable(cardhu_hdmi_vddio);
320                 regulator_put(cardhu_hdmi_vddio);
321                 cardhu_hdmi_vddio = NULL;
322         }
323         return 0;
324 }
325
326 static int cardhu_hdmi_enable(void)
327 {
328         int ret;
329         if (!cardhu_hdmi_reg) {
330                 cardhu_hdmi_reg = regulator_get(NULL, "avdd_hdmi");
331                 if (IS_ERR_OR_NULL(cardhu_hdmi_reg)) {
332                         pr_err("hdmi: couldn't get regulator avdd_hdmi\n");
333                         cardhu_hdmi_reg = NULL;
334                         return PTR_ERR(cardhu_hdmi_reg);
335                 }
336         }
337         ret = regulator_enable(cardhu_hdmi_reg);
338         if (ret < 0) {
339                 pr_err("hdmi: couldn't enable regulator avdd_hdmi\n");
340                 return ret;
341         }
342         if (!cardhu_hdmi_pll) {
343                 cardhu_hdmi_pll = regulator_get(NULL, "avdd_hdmi_pll");
344                 if (IS_ERR_OR_NULL(cardhu_hdmi_pll)) {
345                         pr_err("hdmi: couldn't get regulator avdd_hdmi_pll\n");
346                         cardhu_hdmi_pll = NULL;
347                         regulator_put(cardhu_hdmi_reg);
348                         cardhu_hdmi_reg = NULL;
349                         return PTR_ERR(cardhu_hdmi_pll);
350                 }
351         }
352         ret = regulator_enable(cardhu_hdmi_pll);
353         if (ret < 0) {
354                 pr_err("hdmi: couldn't enable regulator avdd_hdmi_pll\n");
355                 return ret;
356         }
357         return 0;
358 }
359
360 static int cardhu_hdmi_disable(void)
361 {
362         regulator_disable(cardhu_hdmi_reg);
363         regulator_put(cardhu_hdmi_reg);
364         cardhu_hdmi_reg = NULL;
365
366         regulator_disable(cardhu_hdmi_pll);
367         regulator_put(cardhu_hdmi_pll);
368         cardhu_hdmi_pll = NULL;
369         return 0;
370 }
371 static struct resource cardhu_disp1_resources[] = {
372         {
373                 .name   = "irq",
374                 .start  = INT_DISPLAY_GENERAL,
375                 .end    = INT_DISPLAY_GENERAL,
376                 .flags  = IORESOURCE_IRQ,
377         },
378         {
379                 .name   = "regs",
380                 .start  = TEGRA_DISPLAY_BASE,
381                 .end    = TEGRA_DISPLAY_BASE + TEGRA_DISPLAY_SIZE-1,
382                 .flags  = IORESOURCE_MEM,
383         },
384         {
385                 .name   = "fbmem",
386                 .start  = 0,    /* Filled in by cardhu_panel_init() */
387                 .end    = 0,    /* Filled in by cardhu_panel_init() */
388                 .flags  = IORESOURCE_MEM,
389         },
390 #ifdef CONFIG_TEGRA_DSI_INSTANCE_1
391         {
392                 .name   = "dsi_regs",
393                 .start  = TEGRA_DSIB_BASE,
394                 .end    = TEGRA_DSIB_BASE + TEGRA_DSIB_SIZE - 1,
395                 .flags  = IORESOURCE_MEM,
396         },
397 #else
398         {
399                 .name   = "dsi_regs",
400                 .start  = TEGRA_DSI_BASE,
401                 .end    = TEGRA_DSI_BASE + TEGRA_DSI_SIZE - 1,
402                 .flags  = IORESOURCE_MEM,
403         },
404 #endif
405 };
406
407 static struct resource cardhu_disp2_resources[] = {
408         {
409                 .name   = "irq",
410                 .start  = INT_DISPLAY_B_GENERAL,
411                 .end    = INT_DISPLAY_B_GENERAL,
412                 .flags  = IORESOURCE_IRQ,
413         },
414         {
415                 .name   = "regs",
416                 .start  = TEGRA_DISPLAY2_BASE,
417                 .end    = TEGRA_DISPLAY2_BASE + TEGRA_DISPLAY2_SIZE - 1,
418                 .flags  = IORESOURCE_MEM,
419         },
420         {
421                 .name   = "fbmem",
422                 .flags  = IORESOURCE_MEM,
423                 .start  = 0,
424                 .end    = 0,
425         },
426         {
427                 .name   = "hdmi_regs",
428                 .start  = TEGRA_HDMI_BASE,
429                 .end    = TEGRA_HDMI_BASE + TEGRA_HDMI_SIZE - 1,
430                 .flags  = IORESOURCE_MEM,
431         },
432 };
433
434 #ifndef CONFIG_TEGRA_CARDHU_DSI
435 static struct tegra_dc_mode cardhu_panel_modes[] = {
436         {
437                 /* 1366x768@59Hz */
438                 .pclk = 68000000,
439                 .h_ref_to_sync = 4,
440                 .v_ref_to_sync = 2,
441                 .h_sync_width = 30,
442                 .v_sync_width = 5,
443                 .h_back_porch = 18,
444                 .v_back_porch = 12,
445                 .h_active = 1366,
446                 .v_active = 768,
447                 .h_front_porch = 48,
448                 .v_front_porch = 3,
449         },
450 };
451 #endif
452
453 static struct tegra_dc_sd_settings cardhu_sd_settings = {
454         .enable = 0, /* Disabled by default. */
455         .use_auto_pwm = false,
456         .hw_update_delay = 0,
457         .bin_width = -1,
458         .aggressiveness = 3,
459         .use_vid_luma = true,
460         /* Default video coefficients */
461         .coeff = {5, 9, 2},
462         .fc = {0, 0},
463         /* Immediate backlight changes */
464         .blp = {1024, 255},
465         /* Gammas: R: 2.2 G: 2.2 B: 2.2 */
466         /* Default BL TF */
467         .bltf = {
468                         {
469                                 {57, 65, 74, 83},
470                                 {93, 103, 114, 126},
471                                 {138, 151, 165, 179},
472                                 {194, 209, 225, 242},
473                         },
474                         {
475                                 {58, 66, 75, 84},
476                                 {94, 105, 116, 127},
477                                 {140, 153, 166, 181},
478                                 {196, 211, 227, 244},
479                         },
480                         {
481                                 {60, 68, 77, 87},
482                                 {97, 107, 119, 130},
483                                 {143, 156, 170, 184},
484                                 {199, 215, 231, 248},
485                         },
486                         {
487                                 {64, 73, 82, 91},
488                                 {102, 113, 124, 137},
489                                 {149, 163, 177, 192},
490                                 {207, 223, 240, 255},
491                         },
492                 },
493         /* Default LUT */
494         .lut = {
495                         {
496                                 {250, 250, 250},
497                                 {194, 194, 194},
498                                 {149, 149, 149},
499                                 {113, 113, 113},
500                                 {82, 82, 82},
501                                 {56, 56, 56},
502                                 {34, 34, 34},
503                                 {15, 15, 15},
504                                 {0, 0, 0},
505                         },
506                         {
507                                 {246, 246, 246},
508                                 {191, 191, 191},
509                                 {147, 147, 147},
510                                 {111, 111, 111},
511                                 {80, 80, 80},
512                                 {55, 55, 55},
513                                 {33, 33, 33},
514                                 {14, 14, 14},
515                                 {0, 0, 0},
516                         },
517                         {
518                                 {239, 239, 239},
519                                 {185, 185, 185},
520                                 {142, 142, 142},
521                                 {107, 107, 107},
522                                 {77, 77, 77},
523                                 {52, 52, 52},
524                                 {30, 30, 30},
525                                 {12, 12, 12},
526                                 {0, 0, 0},
527                         },
528                         {
529                                 {224, 224, 224},
530                                 {173, 173, 173},
531                                 {133, 133, 133},
532                                 {99, 99, 99},
533                                 {70, 70, 70},
534                                 {46, 46, 46},
535                                 {25, 25, 25},
536                                 {7, 7, 7},
537                                 {0, 0, 0},
538                         },
539                 },
540         .sd_brightness = &sd_brightness,
541         .bl_device = &cardhu_backlight_device,
542 };
543
544 #ifndef CONFIG_TEGRA_CARDHU_DSI
545 static struct tegra_fb_data cardhu_fb_data = {
546         .win            = 0,
547         .xres           = 1366,
548         .yres           = 768,
549         .bits_per_pixel = 32,
550         .flags          = TEGRA_FB_FLIP_ON_PROBE,
551 };
552 #endif
553
554 static struct tegra_fb_data cardhu_hdmi_fb_data = {
555         .win            = 0,
556         .xres           = 1366,
557         .yres           = 768,
558         .bits_per_pixel = 32,
559         .flags          = TEGRA_FB_FLIP_ON_PROBE,
560 };
561
562 static struct tegra_dc_out cardhu_disp2_out = {
563         .type           = TEGRA_DC_OUT_HDMI,
564         .flags          = TEGRA_DC_OUT_HOTPLUG_HIGH,
565         .parent_clk     = "pll_d2_out0",
566
567         .dcc_bus        = 3,
568         .hotplug_gpio   = cardhu_hdmi_hpd,
569
570         .max_pixclock   = KHZ2PICOS(148500),
571
572         .align          = TEGRA_DC_ALIGN_MSB,
573         .order          = TEGRA_DC_ORDER_RED_BLUE,
574
575         .enable         = cardhu_hdmi_enable,
576         .disable        = cardhu_hdmi_disable,
577
578         .postsuspend    = cardhu_hdmi_vddio_disable,
579         .hotplug_init   = cardhu_hdmi_vddio_enable,
580 };
581
582 static struct tegra_dc_platform_data cardhu_disp2_pdata = {
583         .flags          = 0,
584         .default_out    = &cardhu_disp2_out,
585         .fb             = &cardhu_hdmi_fb_data,
586         .emc_clk_rate   = 300000000,
587 };
588
589 #ifdef CONFIG_TEGRA_CARDHU_DSI
590 static int cardhu_dsi_panel_enable(void)
591 {
592         int ret;
593
594         if (cardhu_dsi_reg == NULL) {
595                 cardhu_dsi_reg = regulator_get(NULL, "avdd_dsi_csi");
596                 if (IS_ERR_OR_NULL(cardhu_dsi_reg)) {
597                 pr_err("dsi: Could not get regulator avdd_dsi_csi\n");
598                         cardhu_dsi_reg = NULL;
599                         return PTR_ERR(cardhu_dsi_reg);
600                 }
601         }
602         regulator_enable(cardhu_dsi_reg);
603
604         ret = gpio_request(TEGRA_GPIO_PJ1, "DSI TE");
605         if (ret < 0)
606                 return ret;
607
608         ret = gpio_direction_input(TEGRA_GPIO_PJ1);
609         if (ret < 0) {
610                 gpio_free(TEGRA_GPIO_PJ1);
611                 return ret;
612         }
613         tegra_gpio_enable(TEGRA_GPIO_PJ1);
614
615 #if DSI_PANEL_219
616
617         ret = gpio_request(TEGRA_GPIO_PH0, "ph0");
618         if (ret < 0)
619                 return ret;
620         ret = gpio_direction_output(TEGRA_GPIO_PH0, 0);
621         if (ret < 0) {
622                 gpio_free(TEGRA_GPIO_PH0);
623                 return ret;
624         }
625         else
626                 tegra_gpio_enable(TEGRA_GPIO_PH0);
627
628         ret = gpio_request(TEGRA_GPIO_PH2, "ph2");
629         if (ret < 0)
630                 return ret;
631         ret = gpio_direction_output(TEGRA_GPIO_PH2, 0);
632         if (ret < 0) {
633                 gpio_free(TEGRA_GPIO_PH2);
634                 return ret;
635         }
636         else
637                 tegra_gpio_enable(TEGRA_GPIO_PH2);
638
639         ret = gpio_request(TEGRA_GPIO_PU2, "pu2");
640         if (ret < 0)
641                 return ret;
642         ret = gpio_direction_output(TEGRA_GPIO_PU2, 0);
643         if (ret < 0) {
644                 gpio_free(TEGRA_GPIO_PU2);
645                 return ret;
646         }
647         else
648                 tegra_gpio_enable(TEGRA_GPIO_PU2);
649
650         gpio_set_value(cardhu_lvds_shutdown, 1);
651         mdelay(20);
652         gpio_set_value(TEGRA_GPIO_PH0, 1);
653         mdelay(10);
654         gpio_set_value(TEGRA_GPIO_PH2, 1);
655         mdelay(15);
656         gpio_set_value(TEGRA_GPIO_PU2, 0);
657         gpio_set_value(TEGRA_GPIO_PU2, 1);
658         mdelay(10);
659         gpio_set_value(TEGRA_GPIO_PU2, 0);
660         mdelay(10);
661         gpio_set_value(TEGRA_GPIO_PU2, 1);
662         mdelay(15);
663 #endif
664
665 #if DSI_PANEL_218
666         printk("DSI_PANEL_218 is enabled\n");
667         ret = gpio_request(AVDD_LCD, "avdd_lcd");
668         if(ret < 0)
669                 gpio_free(AVDD_LCD);
670         ret = gpio_direction_output(AVDD_LCD, 1);
671         if(ret < 0)
672                 gpio_free(AVDD_LCD);
673         else
674                 tegra_gpio_enable(AVDD_LCD);
675
676 #if DSI_PANEL_RESET
677         ret = gpio_request(TEGRA_GPIO_PD2, "pd2");
678         if (ret < 0){
679                 return ret;
680         }
681         ret = gpio_direction_output(TEGRA_GPIO_PD2, 0);
682         if (ret < 0) {
683                 gpio_free(TEGRA_GPIO_PD2);
684                 return ret;
685         }
686         else
687                 tegra_gpio_enable(TEGRA_GPIO_PD2);
688
689         gpio_set_value(TEGRA_GPIO_PD2, 1);
690         gpio_set_value(TEGRA_GPIO_PD2, 0);
691         mdelay(2);
692         gpio_set_value(TEGRA_GPIO_PD2, 1);
693         mdelay(2);
694 #endif
695 #endif
696
697         return 0;
698 }
699
700 static int cardhu_dsi_panel_disable(void)
701 {
702         int err;
703
704         err = 0;
705         printk(KERN_INFO "DSI panel disable\n");
706
707 #if DSI_PANEL_219
708         tegra_gpio_disable(TEGRA_GPIO_PU2);
709         gpio_free(TEGRA_GPIO_PU2);
710         tegra_gpio_disable(TEGRA_GPIO_PH2);
711         gpio_free(TEGRA_GPIO_PH2);
712         tegra_gpio_disable(TEGRA_GPIO_PH0);
713         gpio_free(TEGRA_GPIO_PH0);
714         tegra_gpio_disable(TEGRA_GPIO_PL2);
715         gpio_free(TEGRA_GPIO_PL2);
716 #endif
717
718 #if DSI_PANEL_218
719         tegra_gpio_disable(TEGRA_GPIO_PD2);
720         gpio_free(TEGRA_GPIO_PD2);
721 #endif
722
723         return err;
724 }
725
726 static int cardhu_dsi_panel_postsuspend(void)
727 {
728         int err;
729
730         err = 0;
731         printk(KERN_INFO "DSI panel postsuspend\n");
732
733         if (cardhu_dsi_reg) {
734                 err = regulator_disable(cardhu_dsi_reg);
735                 if (err < 0)
736                         printk(KERN_ERR
737                         "DSI regulator avdd_dsi_csi disable failed\n");
738                 regulator_put(cardhu_dsi_reg);
739                 cardhu_dsi_reg = NULL;
740         }
741
742 #if DSI_PANEL_218
743         tegra_gpio_disable(AVDD_LCD);
744         gpio_free(AVDD_LCD);
745 #endif
746
747         return err;
748 }
749
750 static struct tegra_dsi_cmd dsi_init_cmd[]= {
751         DSI_CMD_SHORT(0x05, 0x11, 0x00),
752         DSI_DLY_MS(150),
753         DSI_CMD_SHORT(0x05, 0x29, 0x00),
754         DSI_DLY_MS(20),
755 };
756
757 static struct tegra_dsi_cmd dsi_suspend_cmd[] = {
758         DSI_CMD_SHORT(0x05, 0x28, 0x00),
759         DSI_DLY_MS(20),
760         DSI_CMD_SHORT(0x05, 0x10, 0x00),
761         DSI_DLY_MS(5),
762 };
763
764 struct tegra_dsi_out cardhu_dsi = {
765         .n_data_lanes = 2,
766         .pixel_format = TEGRA_DSI_PIXEL_FORMAT_24BIT_P,
767         .refresh_rate = 60,
768         .virtual_channel = TEGRA_DSI_VIRTUAL_CHANNEL_0,
769
770         .panel_has_frame_buffer = true,
771 #ifdef CONFIG_TEGRA_DSI_INSTANCE_1
772         .dsi_instance = 1,
773 #else
774         .dsi_instance = 0,
775 #endif
776         .panel_reset = DSI_PANEL_RESET,
777
778         .n_init_cmd = ARRAY_SIZE(dsi_init_cmd),
779         .dsi_init_cmd = dsi_init_cmd,
780
781         .n_suspend_cmd = ARRAY_SIZE(dsi_suspend_cmd),
782         .dsi_suspend_cmd = dsi_suspend_cmd,
783
784         .video_data_type = TEGRA_DSI_VIDEO_TYPE_COMMAND_MODE,
785         .lp_cmd_mode_freq_khz = 430000,
786 };
787
788 static struct tegra_dc_mode cardhu_dsi_modes[] = {
789 #if DSI_PANEL_219
790         {
791                 .pclk = 10000000,
792                 .h_ref_to_sync = 4,
793                 .v_ref_to_sync = 1,
794                 .h_sync_width = 16,
795                 .v_sync_width = 1,
796                 .h_back_porch = 32,
797                 .v_back_porch = 1,
798                 .h_active = 540,
799                 .v_active = 960,
800                 .h_front_porch = 32,
801                 .v_front_porch = 2,
802         },
803 #endif
804
805 #if DSI_PANEL_218
806         {
807                 .pclk = 323000000,
808                 .h_ref_to_sync = 11,
809                 .v_ref_to_sync = 1,
810                 .h_sync_width = 16,
811                 .v_sync_width = 4,
812                 .h_back_porch = 16,
813                 .v_back_porch = 4,
814                 .h_active = 864,
815                 .v_active = 480,
816                 .h_front_porch = 16,
817                 .v_front_porch = 4,
818         },
819 #endif
820
821 };
822
823
824 static struct tegra_fb_data cardhu_dsi_fb_data = {
825 #if DSI_PANEL_219
826         .win            = 0,
827         .xres           = 540,
828         .yres           = 960,
829         .bits_per_pixel = 32,
830 #endif
831
832 #if DSI_PANEL_218
833         .win            = 0,
834         .xres           = 864,
835         .yres           = 480,
836         .bits_per_pixel = 32,
837 #endif
838         .flags          = TEGRA_FB_FLIP_ON_PROBE,
839 };
840 #endif
841
842 static struct tegra_dc_out cardhu_disp1_out = {
843         .align          = TEGRA_DC_ALIGN_MSB,
844         .order          = TEGRA_DC_ORDER_RED_BLUE,
845         .sd_settings    = &cardhu_sd_settings,
846
847 #ifndef CONFIG_TEGRA_CARDHU_DSI
848         .type           = TEGRA_DC_OUT_RGB,
849         .parent_clk     = "pll_d_out0",
850
851         .modes          = cardhu_panel_modes,
852         .n_modes        = ARRAY_SIZE(cardhu_panel_modes),
853
854         .enable         = cardhu_panel_enable,
855         .disable        = cardhu_panel_disable,
856 #else
857         .type           = TEGRA_DC_OUT_DSI,
858
859         .modes          = cardhu_dsi_modes,
860         .n_modes        = ARRAY_SIZE(cardhu_dsi_modes),
861
862         .dsi            = &cardhu_dsi,
863
864         .enable         = cardhu_dsi_panel_enable,
865         .disable        = cardhu_dsi_panel_disable,
866         .postsuspend    = cardhu_dsi_panel_postsuspend,
867 #endif
868 };
869 static struct tegra_dc_platform_data cardhu_disp1_pdata = {
870         .flags          = TEGRA_DC_FLAG_ENABLED,
871         .default_out    = &cardhu_disp1_out,
872         .emc_clk_rate   = 300000000,
873 #ifndef CONFIG_TEGRA_CARDHU_DSI
874         .fb             = &cardhu_fb_data,
875 #else
876         .fb             = &cardhu_dsi_fb_data,
877 #endif
878 };
879 static struct nvhost_device cardhu_disp1_device = {
880         .name           = "tegradc",
881         .id             = 0,
882         .resource       = cardhu_disp1_resources,
883         .num_resources  = ARRAY_SIZE(cardhu_disp1_resources),
884         .dev = {
885                 .platform_data = &cardhu_disp1_pdata,
886         },
887 };
888
889 static struct nvhost_device cardhu_disp2_device = {
890         .name           = "tegradc",
891         .id             = 1,
892         .resource       = cardhu_disp2_resources,
893         .num_resources  = ARRAY_SIZE(cardhu_disp2_resources),
894         .dev = {
895                 .platform_data = &cardhu_disp2_pdata,
896         },
897 };
898
899 static struct nvmap_platform_carveout cardhu_carveouts[] = {
900         [0] = NVMAP_HEAP_CARVEOUT_IRAM_INIT,
901         [1] = {
902                 .name           = "generic-0",
903                 .usage_mask     = NVMAP_HEAP_CARVEOUT_GENERIC,
904                 .base           = 0,    /* Filled in by cardhu_panel_init() */
905                 .size           = 0,    /* Filled in by cardhu_panel_init() */
906                 .buddy_size     = SZ_32K,
907         },
908 };
909
910 static struct nvmap_platform_data cardhu_nvmap_data = {
911         .carveouts      = cardhu_carveouts,
912         .nr_carveouts   = ARRAY_SIZE(cardhu_carveouts),
913 };
914
915 static struct platform_device cardhu_nvmap_device = {
916         .name   = "tegra-nvmap",
917         .id     = -1,
918         .dev    = {
919                 .platform_data = &cardhu_nvmap_data,
920         },
921 };
922
923 static struct platform_device *cardhu_gfx_devices[] __initdata = {
924         &cardhu_nvmap_device,
925         &tegra_grhost_device,
926         &tegra_pwfm0_device,
927         &cardhu_backlight_device,
928 };
929
930
931 int __init cardhu_panel_init(void)
932 {
933         int err;
934         struct resource *res;
935
936         tegra_get_board_info(&board_info);
937
938         cardhu_carveouts[1].base = tegra_carveout_start;
939         cardhu_carveouts[1].size = tegra_carveout_size;
940
941         if (board_info.board_id == BOARD_PM269)
942                 gpio_request(pm269_lvds_shutdown, "lvds_shutdown");
943         else
944                 gpio_request(cardhu_lvds_shutdown, "lvds_shutdown");
945
946         tegra_gpio_enable(cardhu_hdmi_hpd);
947         gpio_request(cardhu_hdmi_hpd, "hdmi_hpd");
948         gpio_direction_input(cardhu_hdmi_hpd);
949         err = platform_add_devices(cardhu_gfx_devices,
950                                 ARRAY_SIZE(cardhu_gfx_devices));
951
952         res = nvhost_get_resource_byname(&cardhu_disp1_device,
953                                          IORESOURCE_MEM, "fbmem");
954         res->start = tegra_fb_start;
955         res->end = tegra_fb_start + tegra_fb_size - 1;
956
957         /* Copy the bootloader fb to the fb. */
958         tegra_move_framebuffer(tegra_fb_start, tegra_bootloader_fb_start,
959                                 min(tegra_fb_size, tegra_bootloader_fb_size));
960
961         if (!err)
962                 err = nvhost_device_register(&cardhu_disp1_device);
963
964         res = nvhost_get_resource_byname(&cardhu_disp2_device,
965                                          IORESOURCE_MEM, "fbmem");
966         res->start = tegra_fb2_start;
967         res->end = tegra_fb2_start + tegra_fb2_size - 1;
968         if (!err)
969                 err = nvhost_device_register(&cardhu_disp2_device);
970         return err;
971 }