Flush decoder output intead of ISV output to framework

BUG: 23150939

ISV output buffer is very limited, it is 10 buffers (time stamp is 60fps after FRC).
The buffers to be displayed is in short if we flush ISV output buffers out during
framework/decoer reset in adaptive playback.

Decoder output buffer are around 20 (time stamp is 24/30 before FRC), we flush it out
to dispaly during framework/decoder reset in the adaptive playback.

Speed up the whole OMX decoder (deocder + ISV) start up process by output as quickly as
we can to avoid video jiter on resolution change of adaptive playback.

Note: temporarily don't make the flushing mechanism work for low resolution videos.

Change-Id: I308b1745f98a9df0c68e415496b2369a8a0f6914
Signed-off-by: Xigui Wang <xigui.wang@intel.com>
Signed-off-by: Haitao Ding <haitao.ding@intel.com>
Signed-off-by: Lily Ouyang <lily.ouyang@intel.com>
Signed-off-by: Austin Hu <austin.hu@intel.com>
diff --git a/ISV/include/isv_omxcomponent.h b/ISV/include/isv_omxcomponent.h
index 1e8d13e..bba2a32 100644
--- a/ISV/include/isv_omxcomponent.h
+++ b/ISV/include/isv_omxcomponent.h
@@ -274,6 +274,11 @@
     int32_t mNumISVBuffers;
     int32_t mNumDecoderBuffers;
     int32_t mNumDecoderBuffersBak;
+    /* To speed up the start up output decoder buffer directly
+     * for certain frames. ISV worker pipeline set up is hide by (in parallel with)
+     * display these output frames.
+     */
+    int32_t mOutputDecoderBufferNum;
     uint32_t mWidth;
     uint32_t mHeight;
     uint32_t mUseAndroidNativeBufferIndex;
@@ -297,6 +302,7 @@
     // protect create mProcThread instance
     bool mOwnProcessor;
     static pthread_mutex_t ProcThreadInstanceLock;
+    Mutex mDecoderBufLock;
 };
 
 #endif  // #define ISV_OMXCOMPONENT_H_
diff --git a/ISV/omx/isv_omxcomponent.cpp b/ISV/omx/isv_omxcomponent.cpp
index 6d84b52..1f87deb 100644
--- a/ISV/omx/isv_omxcomponent.cpp
+++ b/ISV/omx/isv_omxcomponent.cpp
@@ -30,6 +30,9 @@
 #undef LOG_TAG
 #define LOG_TAG "isv-omxil"
 
+#define OUTPUT_STARTUP_DEC_BUF_NUM (38)
+#define FLUSH_WIDTH  352
+#define FLUSH_HEIGHT 288
 
 using namespace android;
 
@@ -66,6 +69,7 @@
         mNumISVBuffers(MIN_ISV_BUFFER_NUM),
         mNumDecoderBuffers(0),
         mNumDecoderBuffersBak(0),
+        mOutputDecoderBufferNum(0),
         mWidth(0),
         mHeight(0),
         mUseAndroidNativeBufferIndex(0),
@@ -343,6 +347,7 @@
             if (def->nPortIndex == kPortIndexOutput) {
                 //set the buffer count we should fill to decoder before feed buffer to VPP
                 mNumDecoderBuffersBak = mNumDecoderBuffers = def->nBufferCountActual - MIN_OUTPUT_NUM - UNDEQUEUED_NUM;
+                mOutputDecoderBufferNum = 0;
                 OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def->format.video;
 
                 //FIXME: init itself here
@@ -663,6 +668,7 @@
     }
 
     if (mNumDecoderBuffers > 0) {
+        Mutex::Autolock autoLock(mDecoderBufLock);
         mNumDecoderBuffers--;
         ALOGD_IF(ISV_COMPONENT_DEBUG, "%s: fill pBuffer %p to the decoder, decoder still need extra %d buffers", __func__,
                 pBuffer, mNumDecoderBuffers);
@@ -716,6 +722,17 @@
         mOutputCropChanged = false;
     }
 
+    if ((mWidth > FLUSH_WIDTH) && (mHeight > FLUSH_HEIGHT) &&
+        (pBuffer->nFilledLen != 0) && (mOutputDecoderBufferNum < OUTPUT_STARTUP_DEC_BUF_NUM)) {
+        Mutex::Autolock autoLock(mDecoderBufLock);
+        // take one buffer from decoder loop here. Fill one buffer to the loop by mNumDecoderBuffers++
+        mNumDecoderBuffers++;
+        mOutputDecoderBufferNum++;
+        ALOGD_IF(ISV_COMPONENT_DEBUG, "%s: return %d decoder output Buffer, mNumDecoderBuffers get %d input buffer",
+                __func__, mOutputDecoderBufferNum, mNumDecoderBuffers);
+        return mpCallBacks->FillBufferDone(&mBaseComponent, pAppData, pBuffer);
+    }
+
     mProcThread->addInput(pBuffer);
 
     return OMX_ErrorNone;
@@ -766,6 +783,7 @@
                 mProcThread->waitFlushFinished();
                 mVPPFlushing = false;
                 mNumDecoderBuffers = mNumDecoderBuffersBak;
+                mOutputDecoderBufferNum = 0;
             }
             break;
         }
@@ -784,6 +802,9 @@
                 ALOGD_IF(ISV_COMPONENT_DEBUG, "%s: output crop changed", __func__);
                 mOutputCropChanged = true;
                 return OMX_ErrorNone;
+            } else if (nData1 == kPortIndexOutput && nData2 == OMX_IndexParamPortDefinition) {
+                ALOGI("%s: output format changed. ISV flush buffers", __func__);
+                mProcThread->notifyFlush();
             }
             break;
         }