OMAP3630: DSS2: Enable Pre-Multiplied Alpha Support
authorRajkumar N <rajkumar.nagarajan@ti.com>
Thu, 4 Nov 2010 11:28:42 +0000 (12:28 +0100)
committerTomi Valkeinen <tomi.valkeinen@nokia.com>
Mon, 10 Jan 2011 08:54:19 +0000 (10:54 +0200)
Enable dss to process color formats with pre-mulitplied alpha.
With this we can have alpha values defined for each pixel
and hence can have different blending values for each pixel.
sysfs entry has been created for this and pre-multiplied alpha
support is turned off by default.

Signed-off-by: Sudeep Basavaraj <sudeep.basavaraj@ti.com>
Signed-off-by: Rajkumar N <rajkumar.nagarajan@ti.com>
Signed-off-by: Samreen <samreen@ti.com>
Signed-off-by: Archit Taneja <archit@ti.com>
Signed-off-by: Tomi Valkeinen <tomi.valkeinen@nokia.com>
arch/arm/plat-omap/include/plat/display.h
drivers/video/omap2/dss/dispc.c
drivers/video/omap2/dss/dss.h
drivers/video/omap2/dss/manager.c
drivers/video/omap2/dss/overlay.c

index c915a661f1f5668a6aa7f0b9b50cbf664507f2d4..d433baf4e9777292e864d20d9172b12b9dc3f445 100644 (file)
@@ -268,6 +268,7 @@ struct omap_overlay_info {
        u16 out_width;  /* if 0, out_width == width */
        u16 out_height; /* if 0, out_height == height */
        u8 global_alpha;
+       u8 pre_mult_alpha;
 };
 
 struct omap_overlay {
index 4e04a73a8ff38ad07a5111668fc47377253fd010..54ba8d3ad317f4ce8cead8dd813aedd7d9ce9128 100644 (file)
@@ -773,13 +773,26 @@ static void _dispc_set_vid_size(enum omap_plane plane, int width, int height)
        dispc_write_reg(vsi_reg[plane-1], val);
 }
 
+static void _dispc_set_pre_mult_alpha(enum omap_plane plane, bool enable)
+{
+       if (!dss_has_feature(FEAT_PRE_MULT_ALPHA))
+               return;
+
+       if (!dss_has_feature(FEAT_GLOBAL_ALPHA_VID1) &&
+               plane == OMAP_DSS_VIDEO1)
+               return;
+
+       REG_FLD_MOD(dispc_reg_att[plane], enable ? 1 : 0, 28, 28);
+}
+
 static void _dispc_setup_global_alpha(enum omap_plane plane, u8 global_alpha)
 {
        if (!dss_has_feature(FEAT_GLOBAL_ALPHA))
                return;
 
-       BUG_ON(!dss_has_feature(FEAT_GLOBAL_ALPHA_VID1) &&
-                       plane == OMAP_DSS_VIDEO1);
+       if (!dss_has_feature(FEAT_GLOBAL_ALPHA_VID1) &&
+               plane == OMAP_DSS_VIDEO1)
+               return;
 
        if (plane == OMAP_DSS_GFX)
                REG_FLD_MOD(DISPC_GLOBAL_ALPHA, global_alpha, 7, 0);
@@ -1507,7 +1520,8 @@ static int _dispc_setup_plane(enum omap_plane plane,
                bool ilace,
                enum omap_dss_rotation_type rotation_type,
                u8 rotation, int mirror,
-               u8 global_alpha)
+               u8 global_alpha,
+               u8 pre_mult_alpha)
 {
        const int maxdownscale = cpu_is_omap34xx() ? 4 : 2;
        bool five_taps = 0;
@@ -1693,8 +1707,8 @@ static int _dispc_setup_plane(enum omap_plane plane,
 
        _dispc_set_rotation_attrs(plane, rotation, mirror, color_mode);
 
-       if (plane != OMAP_DSS_VIDEO1)
-               _dispc_setup_global_alpha(plane, global_alpha);
+       _dispc_set_pre_mult_alpha(plane, pre_mult_alpha);
+       _dispc_setup_global_alpha(plane, global_alpha);
 
        return 0;
 }
@@ -3138,7 +3152,8 @@ int dispc_setup_plane(enum omap_plane plane,
                       enum omap_color_mode color_mode,
                       bool ilace,
                       enum omap_dss_rotation_type rotation_type,
-                      u8 rotation, bool mirror, u8 global_alpha)
+                      u8 rotation, bool mirror, u8 global_alpha,
+                      u8 pre_mult_alpha)
 {
        int r = 0;
 
@@ -3160,7 +3175,8 @@ int dispc_setup_plane(enum omap_plane plane,
                           color_mode, ilace,
                           rotation_type,
                           rotation, mirror,
-                          global_alpha);
+                          global_alpha,
+                          pre_mult_alpha);
 
        enable_clocks(0);
 
index 5c7940d5f282f3137be4f8451c76a5692609b3a0..2bb515c61f4bd3e44252ffece049bd7a2f16ea97 100644 (file)
@@ -359,7 +359,8 @@ int dispc_setup_plane(enum omap_plane plane,
                      bool ilace,
                      enum omap_dss_rotation_type rotation_type,
                      u8 rotation, bool mirror,
-                     u8 global_alpha);
+                     u8 global_alpha,
+                     u8 pre_mult_alpha);
 
 bool dispc_go_busy(enum omap_channel channel);
 void dispc_go(enum omap_channel channel);
index 545e9b9a4d92fc19eac470e5d62cb508461f0e4c..873b33469060c8b6e3b609b2f26d5781d8476b58 100644 (file)
@@ -406,6 +406,7 @@ struct overlay_cache_data {
        u16 out_width;  /* if 0, out_width == width */
        u16 out_height; /* if 0, out_height == height */
        u8 global_alpha;
+       u8 pre_mult_alpha;
 
        enum omap_channel channel;
        bool replication;
@@ -842,7 +843,8 @@ static int configure_overlay(enum omap_plane plane)
                        c->rotation_type,
                        c->rotation,
                        c->mirror,
-                       c->global_alpha);
+                       c->global_alpha,
+                       c->pre_mult_alpha);
 
        if (r) {
                /* this shouldn't happen */
@@ -1265,6 +1267,7 @@ static int omap_dss_mgr_apply(struct omap_overlay_manager *mgr)
                oc->out_width = ovl->info.out_width;
                oc->out_height = ovl->info.out_height;
                oc->global_alpha = ovl->info.global_alpha;
+               oc->pre_mult_alpha = ovl->info.pre_mult_alpha;
 
                oc->replication =
                        dss_use_replication(dssdev, ovl->info.color_mode);
index 75642c22cac7f50724879ff3b8ef699b52aee14f..41a29024a8d0d8ac689ac95622eb149af7422793 100644 (file)
@@ -257,6 +257,43 @@ static ssize_t overlay_global_alpha_store(struct omap_overlay *ovl,
        return size;
 }
 
+static ssize_t overlay_pre_mult_alpha_show(struct omap_overlay *ovl,
+               char *buf)
+{
+       return snprintf(buf, PAGE_SIZE, "%d\n",
+                       ovl->info.pre_mult_alpha);
+}
+
+static ssize_t overlay_pre_mult_alpha_store(struct omap_overlay *ovl,
+               const char *buf, size_t size)
+{
+       int r;
+       struct omap_overlay_info info;
+
+       ovl->get_overlay_info(ovl, &info);
+
+       /* only GFX and Video2 plane support pre alpha multiplied
+        * set zero for Video1 plane
+        */
+       if (!dss_has_feature(FEAT_GLOBAL_ALPHA_VID1) &&
+               ovl->id == OMAP_DSS_VIDEO1)
+               info.pre_mult_alpha = 0;
+       else
+               info.pre_mult_alpha = simple_strtoul(buf, NULL, 10);
+
+       r = ovl->set_overlay_info(ovl, &info);
+       if (r)
+               return r;
+
+       if (ovl->manager) {
+               r = ovl->manager->apply(ovl->manager);
+               if (r)
+                       return r;
+       }
+
+       return size;
+}
+
 struct overlay_attribute {
        struct attribute attr;
        ssize_t (*show)(struct omap_overlay *, char *);
@@ -280,6 +317,9 @@ static OVERLAY_ATTR(enabled, S_IRUGO|S_IWUSR,
                overlay_enabled_show, overlay_enabled_store);
 static OVERLAY_ATTR(global_alpha, S_IRUGO|S_IWUSR,
                overlay_global_alpha_show, overlay_global_alpha_store);
+static OVERLAY_ATTR(pre_mult_alpha, S_IRUGO|S_IWUSR,
+               overlay_pre_mult_alpha_show,
+               overlay_pre_mult_alpha_store);
 
 static struct attribute *overlay_sysfs_attrs[] = {
        &overlay_attr_name.attr,
@@ -290,6 +330,7 @@ static struct attribute *overlay_sysfs_attrs[] = {
        &overlay_attr_output_size.attr,
        &overlay_attr_enabled.attr,
        &overlay_attr_global_alpha.attr,
+       &overlay_attr_pre_mult_alpha.attr,
        NULL
 };
 
This page took 0.031868 seconds and 5 git commands to generate.