From: Mans Rullgard Date: Fri, 29 Aug 2008 08:28:31 +0000 (+0100) Subject: OMAP: Add more video modes, and make the default configurable X-Git-Url: http://git.mansr.com/?p=linux-omap;a=commitdiff_plain;h=ef272670f19fac8fb0ceb82933927dab1fb496b7 OMAP: Add more video modes, and make the default configurable --- diff --git a/arch/arm/plat-omap/include/mach/omapfb.h b/arch/arm/plat-omap/include/mach/omapfb.h index 92e9ffd..a4a84f3 100644 --- a/arch/arm/plat-omap/include/mach/omapfb.h +++ b/arch/arm/plat-omap/include/mach/omapfb.h @@ -192,20 +192,6 @@ enum omapfb_update_mode { struct omapfb_device; -struct video_mode { - const char *name; - int x_res, y_res; - int pixel_clock; /* In kHz */ - int hsw; /* Horizontal synchronization - pulse width */ - int hfp; /* Horizontal front porch */ - int hbp; /* Horizontal back porch */ - int vsw; /* Vertical synchronization - pulse width */ - int vfp; /* Vertical front porch */ - int vbp; /* Vertical back porch */ -}; - struct lcd_panel { const char *name; int config; /* TFT/STN, signal inversion */ diff --git a/drivers/video/omap/Kconfig b/drivers/video/omap/Kconfig index bdeb8fb..9977e80 100644 --- a/drivers/video/omap/Kconfig +++ b/drivers/video/omap/Kconfig @@ -7,6 +7,14 @@ config FB_OMAP help Frame buffer driver for OMAP based boards. +config FB_OMAP_VIDEO_MODE + string "Default video mode" + depends on FB_OMAP + help + Enter video mode name to use if none is specified on the kernel + command line. If left blank, board-specific default timings + will be used. See omapfb_main.c for a list of valid mode names. + config FB_OMAP_LCDC_EXTERNAL bool "External LCD controller support" depends on FB_OMAP diff --git a/drivers/video/omap/omapfb_main.c b/drivers/video/omap/omapfb_main.c index f2229b1..2e53d8f 100644 --- a/drivers/video/omap/omapfb_main.c +++ b/drivers/video/omap/omapfb_main.c @@ -33,6 +33,20 @@ #define MODULE_NAME "omapfb" +struct video_mode { + const char *name; + int x_res, y_res; + int pixel_clock; /* In kHz */ + int hsw; /* Horizontal synchronization + pulse width */ + int hfp; /* Horizontal front porch */ + int hbp; /* Horizontal back porch */ + int vsw; /* Vertical synchronization + pulse width */ + int vfp; /* Vertical front porch */ + int vbp; /* Vertical back porch */ +}; + static unsigned int def_accel; static unsigned long def_vram[OMAPFB_PLANE_NUM]; static int def_vram_cnt; @@ -40,7 +54,7 @@ static unsigned long def_vxres; static unsigned long def_vyres; static unsigned int def_rotate; static unsigned int def_mirror; -static int def_mode = -1; +static char def_mode[16] = CONFIG_FB_OMAP_VIDEO_MODE; #ifdef CONFIG_FB_OMAP_MANUAL_UPDATE static int manual_update = 1; @@ -51,6 +65,7 @@ static int manual_update; static struct platform_device *fbdev_pdev; static struct lcd_panel *fbdev_panel; static struct omapfb_device *omapfb_dev; +static struct video_mode video_mode; struct caps_table_struct { unsigned long flag; @@ -81,9 +96,88 @@ static struct caps_table_struct color_caps[] = { { 1 << OMAPFB_COLOR_YUY422, "YUY422", }, }; -static const struct video_mode video_modes[] = { +static struct video_mode video_modes[] __initdata = { + { + /* 640 x 480 @ 60 Hz Reduced blanking VESA CVT 0.31M3-R */ + .name = "640x480@60", + .x_res = 640, + .y_res = 480, + .hfp = 48, + .hsw = 32, + .hbp = 80, + .vfp = 3, + .vsw = 4, + .vbp = 7, + .pixel_clock = 23500, + }, + { + /* 800 x 600 @ 60 Hz Reduced blanking VESA CVT 0.48M3-R */ + .name = "800x600@60", + .x_res = 800, + .y_res = 600, + .hfp = 48, + .hsw = 32, + .hbp = 80, + .vfp = 3, + .vsw = 4, + .vbp = 11, + .pixel_clock = 35500, + }, + { + /* 1024 x 768 @ 60 Hz Reduced blanking VESA CVT 0.79M3-R */ + .name = "1024x768@60", + .x_res = 1024, + .y_res = 768, + .hfp = 48, + .hsw = 32, + .hbp = 80, + .vfp = 3, + .vsw = 4, + .vbp = 15, + .pixel_clock = 56000, + }, + { + /* 1280 x 720 @ 60 Hz Reduced blanking VESA CVT 0.92M9-R */ + .name = "1280x720@60", + .x_res = 1280, + .y_res = 720, + .hfp = 48, + .hsw = 32, + .hbp = 80, + .vfp = 3, + .vsw = 5, + .vbp = 13, + .pixel_clock = 64000, + }, + { + /* 720 x 480 @ 60 Hz CEA-861 Format 3 */ + .name = "480p60", + .x_res = 720, + .y_res = 480, + .hfp = 16, + .hsw = 62, + .hbp = 60, + .vfp = 9, + .vsw = 6, + .vbp = 30, + .pixel_clock = 27027, + }, + { + /* 720 x 576 @ 60 Hz CEA-861 Format 18 */ + .name = "576p50", + .x_res = 720, + .y_res = 576, + .hfp = 12, + .hsw = 64, + .hbp = 68, + .vfp = 5, + .vsw = 5, + .vbp = 39, + .pixel_clock = 27000, + }, { - .name = "1280x720@50", + /* 1280 x 720 @ 50 Hz CEA-861B Format 19 */ + .name = "720p50", .x_res = 1280, .y_res = 720, .hfp = 440, @@ -95,7 +189,8 @@ static const struct video_mode video_modes[] = { .pixel_clock = 74250, }, { - .name = "1280x720@60", + /* 1280 x 720 @ 60 Hz CEA-861B Format 4 */ + .name = "720p60", .x_res = 1280, .y_res = 720, .hfp = 110, @@ -107,7 +202,8 @@ static const struct video_mode video_modes[] = { .pixel_clock = 74250, }, { - .name = "1920x1080@24", + /* 1920 x 1080 @ 24 Hz CEA-861B Format 32 */ + .name = "1080p24", .x_res = 1920, .y_res = 1080, .hfp = 148, @@ -116,10 +212,11 @@ static const struct video_mode video_modes[] = { .vfp = 36, .vsw = 5, .vbp = 4, - .pixel_clock = 74160, + .pixel_clock = 74250, }, { - .name = "1920x1080@25", + /* 1920 x 1080 @ 25 Hz CEA-861B Format 33 */ + .name = "1080p25", .x_res = 1920, .y_res = 1080, .hfp = 148, @@ -129,7 +226,20 @@ static const struct video_mode video_modes[] = { .vsw = 5, .vbp = 4, .pixel_clock = 74250, - } + }, + { + /* 1920 x 1080 @ 25 Hz CEA-861B Format 34 */ + .name = "1080p30", + .x_res = 1920, + .y_res = 1080, + .hfp = 148, + .hsw = 44, + .hbp = 88, + .vfp = 36, + .vsw = 5, + .vbp = 4, + .pixel_clock = 74250, + }, }; /* @@ -1763,16 +1873,18 @@ static int omapfb_do_probe(struct platform_device *pdev, goto cleanup; } - if (def_mode != -1) { - fbdev->panel->x_res = video_modes[def_mode].x_res; - fbdev->panel->y_res = video_modes[def_mode].y_res; - fbdev->panel->pixel_clock = video_modes[def_mode].pixel_clock; - fbdev->panel->hsw = video_modes[def_mode].hsw; - fbdev->panel->hfp = video_modes[def_mode].hfp; - fbdev->panel->hbp = video_modes[def_mode].hbp; - fbdev->panel->vsw = video_modes[def_mode].vsw; - fbdev->panel->vfp = video_modes[def_mode].vfp; - fbdev->panel->vbp = video_modes[def_mode].vbp; + if (video_mode.name) { + pr_info("omapfb: using mode %s\n", video_mode.name); + + fbdev->panel->x_res = video_mode.x_res; + fbdev->panel->y_res = video_mode.y_res; + fbdev->panel->pixel_clock = video_mode.pixel_clock; + fbdev->panel->hsw = video_mode.hsw; + fbdev->panel->hfp = video_mode.hfp; + fbdev->panel->hbp = video_mode.hbp; + fbdev->panel->vsw = video_mode.vsw; + fbdev->panel->vfp = video_mode.vfp; + fbdev->panel->vbp = video_mode.vbp; } r = fbdev->panel->init(fbdev->panel, fbdev); @@ -1931,14 +2043,15 @@ static struct platform_driver omapfb_driver = { }, }; -static int __init omapfb_find_mode(char *mode) +static void __init omapfb_find_mode(char *name, struct video_mode *vmode) { int i; for (i = 0; i < sizeof(video_modes)/sizeof(video_modes[0]); i++) - if (!strcmp(mode, video_modes[i].name)) - return i; - return -1; + if (!strcmp(name, video_modes[i].name)) { + *vmode = video_modes[i]; + break; + } } #ifndef MODULE @@ -1990,7 +2103,7 @@ static int __init omapfb_setup(char *options) else if (!strncmp(this_opt, "manual_update", 13)) manual_update = 1; else if (!strncmp(this_opt, "mode:", 5)) - def_mode = omapfb_find_mode(this_opt + 5); + strncpy(def_mode, this_opt + 5, sizeof(def_mode)); else { pr_debug("omapfb: invalid option\n"); r = -1; @@ -2012,6 +2125,9 @@ static int __init omapfb_init(void) return -ENODEV; omapfb_setup(option); #endif + + omapfb_find_mode(def_mode, &video_mode); + /* Register the driver with LDM */ if (platform_driver_register(&omapfb_driver)) { pr_debug("failed to register omapfb driver\n"); @@ -2033,6 +2149,7 @@ module_param_named(vyres, def_vyres, long, 0664); module_param_named(rotate, def_rotate, uint, 0664); module_param_named(mirror, def_mirror, uint, 0664); module_param_named(manual_update, manual_update, bool, 0664); +module_param_string(video_mode, def_mode, sizeof(def_mode), 0664); module_init(omapfb_init); module_exit(omapfb_cleanup);