Merge "SurfaceFlinger: set refresh rate type when after an attempt to switch" into qt-r1-dev
diff --git a/libs/gui/BufferQueueProducer.cpp b/libs/gui/BufferQueueProducer.cpp
index c20c2f3..9c311a3 100644
--- a/libs/gui/BufferQueueProducer.cpp
+++ b/libs/gui/BufferQueueProducer.cpp
@@ -886,7 +886,7 @@
         item.mFence = acquireFence;
         item.mFenceTime = acquireFenceTime;
         item.mIsDroppable = mCore->mAsyncMode ||
-                (!mCore->mLegacyBufferDrop && mConsumerIsSurfaceFlinger) ||
+                (mConsumerIsSurfaceFlinger && mCore->mQueueBufferCanDrop) ||
                 (mCore->mLegacyBufferDrop && mCore->mQueueBufferCanDrop) ||
                 (mCore->mSharedBufferMode && mCore->mSharedBufferSlot == slot);
         item.mSurfaceDamage = surfaceDamage;
diff --git a/libs/gui/include/gui/BufferQueueCore.h b/libs/gui/include/gui/BufferQueueCore.h
index 9c0ee99..690a85f 100644
--- a/libs/gui/include/gui/BufferQueueCore.h
+++ b/libs/gui/include/gui/BufferQueueCore.h
@@ -233,7 +233,8 @@
 
     // mLegacyBufferDrop indicates whether mQueueBufferCanDrop is in effect.
     // If this flag is set mQueueBufferCanDrop is working as explained. If not
-    // queueBuffer will not drop buffers unless consumer is SurfaceFlinger.
+    // queueBuffer will not drop buffers unless consumer is SurfaceFlinger and
+    // mQueueBufferCanDrop is set.
     bool mLegacyBufferDrop;
 
     // mDefaultBufferFormat can be set so it will override the buffer format
diff --git a/services/surfaceflinger/Scheduler/DispSync.cpp b/services/surfaceflinger/Scheduler/DispSync.cpp
index f7a30af..95ff9d0 100644
--- a/services/surfaceflinger/Scheduler/DispSync.cpp
+++ b/services/surfaceflinger/Scheduler/DispSync.cpp
@@ -79,11 +79,7 @@
         Mutex::Autolock lock(mMutex);
 
         mPhase = phase;
-        if (mReferenceTime != referenceTime) {
-            for (auto& eventListener : mEventListeners) {
-                eventListener.mHasFired = false;
-            }
-        }
+        const bool referenceTimeChanged = mReferenceTime != referenceTime;
         mReferenceTime = referenceTime;
         if (mPeriod != 0 && mPeriod != period && mReferenceTime != 0) {
             // Inflate the reference time to be the most recent predicted
@@ -94,6 +90,13 @@
             mReferenceTime = mReferenceTime + (numOldPeriods)*mPeriod;
         }
         mPeriod = period;
+        if (!mModelLocked && referenceTimeChanged) {
+            for (auto& eventListener : mEventListeners) {
+                eventListener.mHasFired = false;
+                eventListener.mLastEventTime =
+                        mReferenceTime - mPeriod + mPhase + eventListener.mPhase;
+            }
+        }
         if (mTraceDetailedInfo) {
             ATRACE_INT64("DispSync:Period", mPeriod);
             ATRACE_INT64("DispSync:Phase", mPhase + mPeriod / 2);
@@ -120,6 +123,13 @@
 
     void unlockModel() {
         Mutex::Autolock lock(mMutex);
+        if (mModelLocked) {
+            for (auto& eventListener : mEventListeners) {
+                if (eventListener.mLastEventTime > mReferenceTime) {
+                    eventListener.mHasFired = true;
+                }
+            }
+        }
         mModelLocked = false;
         ATRACE_INT("DispSync:ModelLocked", mModelLocked);
     }
@@ -249,6 +259,10 @@
             listener.mLastCallbackTime = lastCallbackTime;
         }
 
+        if (!mModelLocked && listener.mLastEventTime > mReferenceTime) {
+            listener.mHasFired = true;
+        }
+
         mEventListeners.push_back(listener);
 
         mCond.signal();