hwc: Rotate RGB layer using MDP Rotator
1. Use MDP rotator to rotate RGB layers which are rendered by software
2. Restrict total number of rotator sessions to 4 for all displays
3. Disable RGB layer rotation for all MDP versions < MDP5
Change-Id: Ie93111082dff9a16b614e9768df5d8ce83ff9e25
diff --git a/libhwcomposer/hwc_utils.cpp b/libhwcomposer/hwc_utils.cpp
index 671388b..9adfe74 100644
--- a/libhwcomposer/hwc_utils.cpp
+++ b/libhwcomposer/hwc_utils.cpp
@@ -955,6 +955,32 @@
return false;
}
+bool isRotatorSupportedFormat(private_handle_t *hnd) {
+ // Following rotator src formats are supported by mdp driver
+ // TODO: Add more formats in future, if mdp driver adds support
+ switch(hnd->format) {
+ case HAL_PIXEL_FORMAT_RGBA_8888:
+ case HAL_PIXEL_FORMAT_RGB_565:
+ case HAL_PIXEL_FORMAT_RGB_888:
+ case HAL_PIXEL_FORMAT_BGRA_8888:
+ return true;
+ default:
+ return false;
+ }
+ return false;
+}
+
+bool isRotationDoable(hwc_context_t *ctx, private_handle_t *hnd) {
+ // Rotate layers, if it is YUV type or rendered by CPU and not
+ // for the MDP versions below MDP5
+ if((isCPURendered(hnd) && isRotatorSupportedFormat(hnd) &&
+ !ctx->mMDP.version < qdutils::MDSS_V5)
+ || isYuvBuffer(hnd)) {
+ return true;
+ }
+ return false;
+}
+
// returns true if Action safe dimensions are set and target supports Actionsafe
bool isActionSafePresent(hwc_context_t *ctx, int dpy) {
// if external supports underscan, do nothing
@@ -1422,7 +1448,7 @@
return ret;
}
-void setMdpFlags(hwc_layer_1_t *layer,
+void setMdpFlags(hwc_context_t *ctx, hwc_layer_1_t *layer,
ovutils::eMdpFlags &mdpFlags,
int rotDownscale, int transform) {
private_handle_t *hnd = (private_handle_t *)layer->handle;
@@ -1443,11 +1469,6 @@
ovutils::setMdpFlags(mdpFlags,
ovutils::OV_MDP_DEINTERLACE);
}
- //Pre-rotation will be used using rotator.
- if(transform & HWC_TRANSFORM_ROT_90) {
- ovutils::setMdpFlags(mdpFlags,
- ovutils::OV_MDP_SOURCE_ROTATED_90);
- }
}
if(isSecureDisplayBuffer(hnd)) {
@@ -1457,6 +1478,12 @@
ovutils::setMdpFlags(mdpFlags,
ovutils::OV_MDP_SECURE_DISPLAY_OVERLAY_SESSION);
}
+
+ //Pre-rotation will be used using rotator.
+ if(has90Transform(layer) && isRotationDoable(ctx, hnd)) {
+ ovutils::setMdpFlags(mdpFlags,
+ ovutils::OV_MDP_SOURCE_ROTATED_90);
+ }
//No 90 component and no rot-downscale then flips done by MDP
//If we use rot then it might as well do flips
if(!(transform & HWC_TRANSFORM_ROT_90) && !rotDownscale) {
@@ -1649,14 +1676,15 @@
}
}
- setMdpFlags(layer, mdpFlags, downscale, transform);
+ setMdpFlags(ctx, layer, mdpFlags, downscale, transform);
- if(isYuvBuffer(hnd) && //if 90 component or downscale, use rot
- ((transform & HWC_TRANSFORM_ROT_90) || downscale)) {
+ //if 90 component or downscale, use rot
+ if((has90Transform(layer) && isRotationDoable(ctx, hnd)) || downscale) {
*rot = ctx->mRotMgr->getNext();
if(*rot == NULL) return -1;
ctx->mLayerRotMap[dpy]->add(layer, *rot);
- if(!dpy)
+ // BWC is not tested for other formats So enable it only for YUV format
+ if(!dpy && isYuvBuffer(hnd))
BwcPM::setBwc(crop, dst, transform, mdpFlags);
//Configure rotator for pre-rotation
if(configRotator(*rot, whf, crop, mdpFlags, orient, downscale) < 0) {
@@ -1746,7 +1774,7 @@
ActionSafe, and extorientation features. */
calcExtDisplayPosition(ctx, hnd, dpy, crop, dst, transform, orient);
- setMdpFlags(layer, mdpFlagsL, 0, transform);
+ setMdpFlags(ctx, layer, mdpFlagsL, 0, transform);
if(lDest != OV_INVALID && rDest != OV_INVALID) {
//Enable overfetch
@@ -1760,7 +1788,7 @@
whf.format = wb->getOutputFormat();
}
- if(isYuvBuffer(hnd) && (transform & HWC_TRANSFORM_ROT_90)) {
+ if(has90Transform(layer) && isRotationDoable(ctx, hnd)) {
(*rot) = ctx->mRotMgr->getNext();
if((*rot) == NULL) return -1;
ctx->mLayerRotMap[dpy]->add(layer, *rot);
@@ -1888,14 +1916,15 @@
ActionSafe, and extorientation features. */
calcExtDisplayPosition(ctx, hnd, dpy, crop, dst, transform, orient);
- setMdpFlags(layer, mdpFlagsL, 0, transform);
+ setMdpFlags(ctx, layer, mdpFlagsL, 0, transform);
trimLayer(ctx, dpy, transform, crop, dst);
- if(isYuvBuffer(hnd) && (transform & HWC_TRANSFORM_ROT_90)) {
+ if(has90Transform(layer) && isRotationDoable(ctx, hnd)) {
(*rot) = ctx->mRotMgr->getNext();
if((*rot) == NULL) return -1;
ctx->mLayerRotMap[dpy]->add(layer, *rot);
- if(!dpy)
+ // BWC is not tested for other formats So enable it only for YUV format
+ if(!dpy && isYuvBuffer(hnd))
BwcPM::setBwc(crop, dst, transform, mdpFlagsL);
//Configure rotator for pre-rotation
if(configRotator(*rot, whf, crop, mdpFlagsL, orient, downscale) < 0) {