hwc: Invoke commit ioctl even if there are no app layers
Android has scenarios where it calls HWC::prepare and HWC::set
without any application layers. In such cases, for power
optimization, user space avoids calling PLAY
(on FB - since there is no new content drawn) and COMMIT ioctls.
But we might have called UNSET on mdp pipes used for the previous
frame. As per the current MDP design, these freed pipes will not
be unstaged unless atleast a COMMIT ioctl is called on that mixer.
Change-Id: I7f7574b2e589e80c4926533066e35784bb29b4a5
CRs-Fixed: 437736
diff --git a/libhwcomposer/hwc.cpp b/libhwcomposer/hwc.cpp
index ba84580..84b1100 100644
--- a/libhwcomposer/hwc.cpp
+++ b/libhwcomposer/hwc.cpp
@@ -125,7 +125,6 @@
hwc_display_contents_1_t *list) {
hwc_context_t* ctx = (hwc_context_t*)(dev);
const int dpy = HWC_DISPLAY_PRIMARY;
-
if (LIKELY(list && list->numHwLayers > 1) &&
ctx->dpyAttr[dpy].isActive) {
@@ -306,14 +305,14 @@
int ret = 0;
const int dpy = HWC_DISPLAY_PRIMARY;
- if (LIKELY(list && list->numHwLayers > 1) &&
- ctx->dpyAttr[dpy].isActive) {
+ if (LIKELY(list) && ctx->dpyAttr[dpy].isActive) {
uint32_t last = list->numHwLayers - 1;
hwc_layer_1_t *fbLayer = &list->hwLayers[last];
int fd = -1; //FenceFD from the Copybit(valid in async mode)
if(ctx->mCopyBit[dpy])
ctx->mCopyBit[dpy]->draw(ctx, list, dpy, &fd);
- hwc_sync(ctx, list, dpy, fd);
+ if(list->numHwLayers > 1)
+ hwc_sync(ctx, list, dpy, fd);
if (!VideoOverlay::draw(ctx, list, dpy)) {
ALOGE("%s: VideoOverlay::draw fail!", __FUNCTION__);
ret = -1;
@@ -327,7 +326,8 @@
//always. Last layer is always FB
private_handle_t *hnd = (private_handle_t *)fbLayer->handle;
if(fbLayer->compositionType == HWC_FRAMEBUFFER_TARGET && hnd) {
- if(!(fbLayer->flags & HWC_SKIP_LAYER)) {
+ if(!(fbLayer->flags & HWC_SKIP_LAYER) &&
+ (list->numHwLayers > 1)) {
if (!ctx->mFBUpdate[dpy]->draw(ctx, fbLayer)) {
ALOGE("%s: FBUpdate::draw fail!", __FUNCTION__);
ret = -1;
@@ -349,8 +349,7 @@
Locker::Autolock _l(ctx->mExtSetLock);
- if (LIKELY(list && list->numHwLayers > 1) &&
- ctx->dpyAttr[dpy].isActive &&
+ if (LIKELY(list) && ctx->dpyAttr[dpy].isActive &&
ctx->dpyAttr[dpy].connected) {
uint32_t last = list->numHwLayers - 1;
hwc_layer_1_t *fbLayer = &list->hwLayers[last];
@@ -358,7 +357,8 @@
if(ctx->mCopyBit[dpy])
ctx->mCopyBit[dpy]->draw(ctx, list, dpy, &fd);
- hwc_sync(ctx, list, dpy, fd);
+ if(list->numHwLayers > 1)
+ hwc_sync(ctx, list, dpy, fd);
if (!VideoOverlay::draw(ctx, list, dpy)) {
ALOGE("%s: VideoOverlay::draw fail!", __FUNCTION__);
@@ -367,7 +367,8 @@
private_handle_t *hnd = (private_handle_t *)fbLayer->handle;
if(fbLayer->compositionType == HWC_FRAMEBUFFER_TARGET &&
- !(fbLayer->flags & HWC_SKIP_LAYER) && hnd) {
+ !(fbLayer->flags & HWC_SKIP_LAYER) && hnd &&
+ (list->numHwLayers > 1)) {
if (!ctx->mFBUpdate[dpy]->draw(ctx, fbLayer)) {
ALOGE("%s: FBUpdate::draw fail!", __FUNCTION__);
ret = -1;