diff options
Diffstat (limited to 'recipes/linux/linux-omap-2.6.29/dss2/0027-DSS2-VRFB-rotation-and-mirroring-implemented.patch')
-rw-r--r-- | recipes/linux/linux-omap-2.6.29/dss2/0027-DSS2-VRFB-rotation-and-mirroring-implemented.patch | 324 |
1 files changed, 324 insertions, 0 deletions
diff --git a/recipes/linux/linux-omap-2.6.29/dss2/0027-DSS2-VRFB-rotation-and-mirroring-implemented.patch b/recipes/linux/linux-omap-2.6.29/dss2/0027-DSS2-VRFB-rotation-and-mirroring-implemented.patch new file mode 100644 index 0000000000..b56e32a11c --- /dev/null +++ b/recipes/linux/linux-omap-2.6.29/dss2/0027-DSS2-VRFB-rotation-and-mirroring-implemented.patch @@ -0,0 +1,324 @@ +From 77e848eeba461e9b55b09d39fd0d640caea13e19 Mon Sep 17 00:00:00 2001 +From: Hardik Shah <hardik.shah@ti.com> +Date: Thu, 9 Apr 2009 12:09:44 +0530 +Subject: [PATCH] DSS2: VRFB rotation and mirroring implemented. + +DSS2 modified to accept the rotation_type input +to get the dma or VRFB rotation. + +DSS2: VRFB: Changed to pass DSS mode to vrfb_setup instead of Bpp. + +VRFB size registers requires the width to be halved when the +mode is YUV or UYVY. So modifed to pass the mode to omap_vrfb_setup +function. + +Code added by Tim Yamin for few bug fixes + +Signed-off-by: Tim Yamin <plasm@roo.me.uk> +Signed-off-by: Hardik Shah <hardik.shah@ti.com> +--- + arch/arm/plat-omap/include/mach/display.h | 6 ++ + arch/arm/plat-omap/include/mach/vrfb.h | 3 +- + arch/arm/plat-omap/vrfb.c | 36 +++++++++- + drivers/video/omap2/dss/dispc.c | 109 +++++++++++++++++++++++++++-- + drivers/video/omap2/dss/dss.h | 1 + + drivers/video/omap2/dss/manager.c | 1 + + 6 files changed, 144 insertions(+), 12 deletions(-) + +diff --git a/arch/arm/plat-omap/include/mach/display.h b/arch/arm/plat-omap/include/mach/display.h +index 6b702c7..b0a6272 100644 +--- a/arch/arm/plat-omap/include/mach/display.h ++++ b/arch/arm/plat-omap/include/mach/display.h +@@ -341,6 +341,11 @@ enum omap_dss_overlay_managers { + + struct omap_overlay_manager; + ++enum omap_dss_rotation_type { ++ OMAP_DSS_ROT_DMA = 0, ++ OMAP_DSS_ROT_VRFB = 1, ++}; ++ + struct omap_overlay_info { + bool enabled; + +@@ -351,6 +356,7 @@ struct omap_overlay_info { + u16 height; + enum omap_color_mode color_mode; + u8 rotation; ++ enum omap_dss_rotation_type rotation_type; + bool mirror; + + u16 pos_x; +diff --git a/arch/arm/plat-omap/include/mach/vrfb.h b/arch/arm/plat-omap/include/mach/vrfb.h +index 2047862..12c7fab 100644 +--- a/arch/arm/plat-omap/include/mach/vrfb.h ++++ b/arch/arm/plat-omap/include/mach/vrfb.h +@@ -24,6 +24,7 @@ + #ifndef __VRFB_H + #define __VRFB_H + ++#include <mach/display.h> + #define OMAP_VRFB_LINE_LEN 2048 + + struct vrfb +@@ -42,6 +43,6 @@ extern void omap_vrfb_adjust_size(u16 *width, u16 *height, + u8 bytespp); + extern void omap_vrfb_setup(struct vrfb *vrfb, unsigned long paddr, + u16 width, u16 height, +- u8 bytespp); ++ enum omap_color_mode color_mode); + + #endif /* __VRFB_H */ +diff --git a/arch/arm/plat-omap/vrfb.c b/arch/arm/plat-omap/vrfb.c +index d68065f..2f08f6d 100644 +--- a/arch/arm/plat-omap/vrfb.c ++++ b/arch/arm/plat-omap/vrfb.c +@@ -5,7 +5,6 @@ + + #include <mach/io.h> + #include <mach/vrfb.h> +- + /*#define DEBUG*/ + + #ifdef DEBUG +@@ -50,19 +49,48 @@ EXPORT_SYMBOL(omap_vrfb_adjust_size); + + void omap_vrfb_setup(struct vrfb *vrfb, unsigned long paddr, + u16 width, u16 height, +- u8 bytespp) ++ enum omap_color_mode color_mode) + { + unsigned pixel_size_exp; + u16 vrfb_width; + u16 vrfb_height; + u8 ctx = vrfb->context; ++ u8 bytespp; + + DBG("omapfb_set_vrfb(%d, %lx, %dx%d, %d)\n", ctx, paddr, + width, height, bytespp); + +- if (bytespp == 4) ++ switch (color_mode) { ++ case OMAP_DSS_COLOR_RGB16: ++ case OMAP_DSS_COLOR_ARGB16: ++ bytespp = 2; ++ break; ++ ++ case OMAP_DSS_COLOR_RGB24P: ++ bytespp = 3; ++ break; ++ ++ case OMAP_DSS_COLOR_RGB24U: ++ case OMAP_DSS_COLOR_ARGB32: ++ case OMAP_DSS_COLOR_RGBA32: ++ case OMAP_DSS_COLOR_RGBX32: ++ case OMAP_DSS_COLOR_YUV2: ++ case OMAP_DSS_COLOR_UYVY: ++ bytespp = 4; ++ break; ++ ++ default: ++ BUG(); ++ return; ++ } ++ ++ if (color_mode == OMAP_DSS_COLOR_YUV2 || ++ color_mode == OMAP_DSS_COLOR_UYVY) ++ width >>= 1; ++ ++ if (bytespp == 4) { + pixel_size_exp = 2; +- else if (bytespp == 2) ++ } else if (bytespp == 2) + pixel_size_exp = 1; + else + BUG(); +diff --git a/drivers/video/omap2/dss/dispc.c b/drivers/video/omap2/dss/dispc.c +index 16c68b8..23a8155 100644 +--- a/drivers/video/omap2/dss/dispc.c ++++ b/drivers/video/omap2/dss/dispc.c +@@ -1106,7 +1106,7 @@ static void _dispc_set_rotation_attrs(enum omap_plane plane, u8 rotation, + case 0: vidrot = 0; break; + case 1: vidrot = 1; break; + case 2: vidrot = 2; break; +- case 3: vidrot = 1; break; ++ case 3: vidrot = 3; break; + } + } + +@@ -1134,7 +1134,92 @@ static s32 pixinc(int pixels, u8 ps) + BUG(); + } + +-static void calc_rotation_offset(u8 rotation, bool mirror, ++static void calc_vrfb_rotation_offset(u8 rotation, bool mirror, ++ u16 screen_width, ++ u16 width, u16 height, ++ enum omap_color_mode color_mode, bool fieldmode, ++ unsigned *offset0, unsigned *offset1, ++ s32 *row_inc, s32 *pix_inc) ++{ ++ u8 ps; ++ ++ switch (color_mode) { ++ case OMAP_DSS_COLOR_RGB16: ++ case OMAP_DSS_COLOR_ARGB16: ++ ps = 2; ++ break; ++ ++ case OMAP_DSS_COLOR_RGB24P: ++ ps = 3; ++ break; ++ ++ case OMAP_DSS_COLOR_RGB24U: ++ case OMAP_DSS_COLOR_ARGB32: ++ case OMAP_DSS_COLOR_RGBA32: ++ case OMAP_DSS_COLOR_RGBX32: ++ case OMAP_DSS_COLOR_YUV2: ++ case OMAP_DSS_COLOR_UYVY: ++ ps = 4; ++ break; ++ ++ default: ++ BUG(); ++ return; ++ } ++ ++ DSSDBG("calc_rot(%d): scrw %d, %dx%d\n", rotation, screen_width, ++ width, height); ++ switch (rotation + mirror * 4) { ++ case 0: ++ case 2: ++ /* ++ * If the pixel format is YUV or UYVY divide the width ++ * of the image by 2 for 0 and 180 degree rotation. ++ */ ++ if (color_mode == OMAP_DSS_COLOR_YUV2 || ++ color_mode == OMAP_DSS_COLOR_UYVY) ++ width = width >> 1; ++ case 1: ++ case 3: ++ *offset0 = 0; ++ if (fieldmode) ++ *offset1 = screen_width * ps; ++ else ++ *offset1 = 0; ++ ++ *row_inc = pixinc(1 + (screen_width - width) + ++ (fieldmode ? screen_width : 0), ++ ps); ++ *pix_inc = pixinc(1, ps); ++ break; ++ ++ case 4: ++ case 6: ++ /* If the pixel format is YUV or UYVY divide the width ++ * of the image by 2 for 0 degree and 180 degree ++ */ ++ if (color_mode == OMAP_DSS_COLOR_YUV2 || ++ color_mode == OMAP_DSS_COLOR_UYVY) ++ width = width >> 1; ++ case 5: ++ case 7: ++ *offset0 = 0; ++ if (fieldmode) ++ *offset1 = screen_width * ps; ++ else ++ *offset1 = 0; ++ *row_inc = pixinc(1 - (screen_width + width) - ++ (fieldmode ? screen_width : 0), ++ ps); ++ *pix_inc = pixinc(1, ps); ++ break; ++ ++ default: ++ BUG(); ++ } ++} ++ ++static void calc_dma_rotation_offset(u8 rotation, bool mirror, + u16 screen_width, + u16 width, u16 height, + enum omap_color_mode color_mode, bool fieldmode, +@@ -1357,6 +1442,7 @@ static int _dispc_setup_plane(enum omap_plane plane, + u16 out_width, u16 out_height, + enum omap_color_mode color_mode, + bool ilace, ++ enum omap_dss_rotation_type rotation_type, + u8 rotation, int mirror) + { + const int maxdownscale = cpu_is_omap34xx() ? 4 : 2; +@@ -1463,10 +1549,16 @@ static int _dispc_setup_plane(enum omap_plane plane, + return -EINVAL; + } + +- calc_rotation_offset(rotation, mirror, +- screen_width, width, frame_height, color_mode, +- fieldmode, +- &offset0, &offset1, &row_inc, &pix_inc); ++ if (rotation_type == OMAP_DSS_ROT_DMA) ++ calc_dma_rotation_offset(rotation, mirror, ++ screen_width, width, frame_height, color_mode, ++ fieldmode, ++ &offset0, &offset1, &row_inc, &pix_inc); ++ else ++ calc_vrfb_rotation_offset(rotation, mirror, ++ screen_width, width, frame_height, color_mode, ++ fieldmode, ++ &offset0, &offset1, &row_inc, &pix_inc); + + DSSDBG("offset0 %u, offset1 %u, row_inc %d, pix_inc %d\n", + offset0, offset1, row_inc, pix_inc); +@@ -2889,6 +2981,7 @@ int dispc_setup_plane(enum omap_plane plane, enum omap_channel channel_out, + u16 out_width, u16 out_height, + enum omap_color_mode color_mode, + bool ilace, ++ enum omap_dss_rotation_type rotation_type, + u8 rotation, bool mirror) + { + int r = 0; +@@ -2909,6 +3002,7 @@ int dispc_setup_plane(enum omap_plane plane, enum omap_channel channel_out, + width, height, + out_width, out_height, + color_mode, ilace, ++ rotation_type, + rotation, mirror); + + enable_clocks(0); +@@ -3122,7 +3216,8 @@ void dispc_setup_partial_planes(struct omap_display *display, + pw, ph, + pow, poh, + pi->color_mode, 0, +- pi->rotation, // XXX rotation probably wrong ++ pi->rotation_type, ++ pi->rotation, + pi->mirror); + + dispc_enable_plane(ovl->id, 1); +diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h +index d0917a8..584dce6 100644 +--- a/drivers/video/omap2/dss/dss.h ++++ b/drivers/video/omap2/dss/dss.h +@@ -272,6 +272,7 @@ int dispc_setup_plane(enum omap_plane plane, enum omap_channel channel_out, + u16 out_width, u16 out_height, + enum omap_color_mode color_mode, + bool ilace, ++ enum omap_dss_rotation_type rotation_type, + u8 rotation, bool mirror); + + void dispc_go(enum omap_channel channel); +diff --git a/drivers/video/omap2/dss/manager.c b/drivers/video/omap2/dss/manager.c +index b0fee80..8ca0bbb 100644 +--- a/drivers/video/omap2/dss/manager.c ++++ b/drivers/video/omap2/dss/manager.c +@@ -395,6 +395,7 @@ static int omap_dss_mgr_apply(struct omap_overlay_manager *mgr) + outh, + ovl->info.color_mode, + ilace, ++ ovl->info.rotation_type, + ovl->info.rotation, + ovl->info.mirror); + +-- +1.5.6.5 + |