Merge "hwc: Source Split layers always if indicated by driver"
diff --git a/libhwcomposer/hwc_fbupdate.cpp b/libhwcomposer/hwc_fbupdate.cpp
index b1d7616..59f6245 100644
--- a/libhwcomposer/hwc_fbupdate.cpp
+++ b/libhwcomposer/hwc_fbupdate.cpp
@@ -474,9 +474,18 @@
 
     ovutils::eDest destR = ovutils::OV_INVALID;
 
-    //Request right pipe (2 pipes needed only if dim > 2048)
-    if((fbUpdatingRect.right - fbUpdatingRect.left) >
-            qdutils::MAX_DISPLAY_DIM) {
+    /*  Use 2 pipes IF
+        a) FB's width is > 2048 or
+        b) On primary, driver has indicated with caps to split always. This is
+           based on an empirically derived value of panel height.
+    */
+
+    bool primarySplitAlways = (mDpy == HWC_DISPLAY_PRIMARY) and
+            qdutils::MDPVersion::getInstance().isSrcSplitAlways();
+
+    if(((fbUpdatingRect.right - fbUpdatingRect.left) >
+            qdutils::MAX_DISPLAY_DIM) or
+            primarySplitAlways) {
         destR = ov.getPipe(pipeSpecs);
         if(destR == ovutils::OV_INVALID) {
             ALOGE("%s: No pipes available to configure fb for dpy %d's right"
diff --git a/libhwcomposer/hwc_mdpcomp.cpp b/libhwcomposer/hwc_mdpcomp.cpp
index 0331864..cf68a3a 100644
--- a/libhwcomposer/hwc_mdpcomp.cpp
+++ b/libhwcomposer/hwc_mdpcomp.cpp
@@ -2184,9 +2184,23 @@
         return false;
     }
 
-    //If layer's crop width or dest width > 2048, use 2 pipes
-    if((dst.right - dst.left) > qdutils::MAX_DISPLAY_DIM or
-            (crop.right - crop.left) > qdutils::MAX_DISPLAY_DIM) {
+    /* Use 2 pipes IF
+        a) Layer's crop width is > 2048 or
+        b) Layer's dest width > 2048 or
+        c) On primary, driver has indicated with caps to split always. This is
+           based on an empirically derived value of panel height. Applied only
+           if the layer's width is > mixer's width
+    */
+
+    bool primarySplitAlways = (mDpy == HWC_DISPLAY_PRIMARY) and
+            qdutils::MDPVersion::getInstance().isSrcSplitAlways();
+    int lSplit = getLeftSplit(ctx, mDpy);
+    int dstWidth = dst.right - dst.left;
+    int cropWidth = crop.right - crop.left;
+
+    if(dstWidth > qdutils::MAX_DISPLAY_DIM or
+            cropWidth > qdutils::MAX_DISPLAY_DIM or
+            (primarySplitAlways and (cropWidth > lSplit))) {
         pipe_info.rIndex = ctx->mOverlay->getPipe(pipeSpecs);
         if(pipe_info.rIndex == ovutils::OV_INVALID) {
             return false;
diff --git a/libqdutils/mdp_version.cpp b/libqdutils/mdp_version.cpp
index 96ed4d2..bc63ddf 100644
--- a/libqdutils/mdp_version.cpp
+++ b/libqdutils/mdp_version.cpp
@@ -88,6 +88,7 @@
     mLowBw = 0;
     mHighBw = 0;
     mSourceSplit = false;
+    mSourceSplitAlways = false;
     mRGBHasNoScalar = false;
 
     updatePanelInfo();
@@ -306,6 +307,30 @@
         free(line);
         fclose(sysfsFd);
     }
+
+    if(mSourceSplit) {
+        memset(sysfsPath, 0, sizeof(sysfsPath));
+        snprintf(sysfsPath , sizeof(sysfsPath),
+                "/sys/class/graphics/fb0/msm_fb_src_split_info");
+
+        sysfsFd = fopen(sysfsPath, "rb");
+        if (sysfsFd == NULL) {
+            ALOGE("%s: Opening file %s failed with error %s", __FUNCTION__,
+                    sysfsPath, strerror(errno));
+            return false;
+        } else {
+            line = (char *) malloc(len);
+            if((read = getline(&line, &len, sysfsFd)) != -1) {
+                if(!strncmp(line, "src_split_always",
+                        strlen("src_split_always"))) {
+                    mSourceSplitAlways = true;
+                }
+            }
+            free(line);
+            fclose(sysfsFd);
+        }
+    }
+
     ALOGD_IF(DEBUG, "%s: mMDPVersion: %d mMdpRev: %x mRGBPipes:%d,"
                     "mVGPipes:%d", __FUNCTION__, mMDPVersion, mMdpRev,
                     mRGBPipes, mVGPipes);
@@ -371,6 +396,10 @@
     return mSourceSplit;
 }
 
+bool MDPVersion::isSrcSplitAlways() const {
+    return mSourceSplitAlways;
+}
+
 bool MDPVersion::isRGBScalarSupported() const {
     return (!mRGBHasNoScalar);
 }
diff --git a/libqdutils/mdp_version.h b/libqdutils/mdp_version.h
index e862d2d..8bb9c39 100644
--- a/libqdutils/mdp_version.h
+++ b/libqdutils/mdp_version.h
@@ -140,6 +140,7 @@
     unsigned long getLowBw() { return mLowBw; }
     unsigned long getHighBw() { return mHighBw; }
     bool isSrcSplit() const;
+    bool isSrcSplitAlways() const;
     bool isRGBScalarSupported() const;
     bool is8x26();
     bool is8x74v2();
@@ -170,6 +171,8 @@
     unsigned long mLowBw; //kbps
     unsigned long mHighBw; //kbps
     bool mSourceSplit;
+    //Additional property on top of source split
+    bool mSourceSplitAlways;
     bool mRGBHasNoScalar;
 };
 }; //namespace qdutils