Latch and relase buffers for offscreen layers on main thread.

The current code was calling fakeVsync, which was latching and releasing
buffers on a binder thread when a new frame arrived. This was causing a
race with the latchBuffer on the main thread. This change calls
latchAndReleaseBuffer on the main thread for offscreen layers to ensure
we don't block dequeueBuffer but also don't race the other latchBuffer
call.

Fixes: 139118508
Test: Race was only reproducible in monkey tests
Change-Id: Ie7d87aa775c215de3fb2322b73849402596cc3fc
diff --git a/services/surfaceflinger/BufferLayer.cpp b/services/surfaceflinger/BufferLayer.cpp
index 13c748f..e9af9e2 100644
--- a/services/surfaceflinger/BufferLayer.cpp
+++ b/services/surfaceflinger/BufferLayer.cpp
@@ -668,6 +668,15 @@
     return FloatRect(0, 0, bufWidth, bufHeight);
 }
 
+void BufferLayer::latchAndReleaseBuffer() {
+    mRefreshPending = false;
+    if (hasReadyFrame()) {
+        bool ignored = false;
+        latchBuffer(ignored, systemTime(), 0 /* expectedPresentTime */);
+    }
+    releasePendingBuffer(systemTime());
+}
+
 } // namespace android
 
 #if defined(__gl_h_)
diff --git a/services/surfaceflinger/BufferLayer.h b/services/surfaceflinger/BufferLayer.h
index 7a0f82b..fb8d7d0 100644
--- a/services/surfaceflinger/BufferLayer.h
+++ b/services/surfaceflinger/BufferLayer.h
@@ -103,6 +103,13 @@
     // Returns the current scaling mode, unless mOverrideScalingMode
     // is set, in which case, it returns mOverrideScalingMode
     uint32_t getEffectiveScalingMode() const override;
+
+    // Calls latchBuffer if the buffer has a frame queued and then releases the buffer.
+    // This is used if the buffer is just latched and releases to free up the buffer
+    // and will not be shown on screen.
+    // Should only be called on the main thread.
+    void latchAndReleaseBuffer() override;
+
     // -----------------------------------------------------------------------
 
     // -----------------------------------------------------------------------
diff --git a/services/surfaceflinger/BufferQueueLayer.cpp b/services/surfaceflinger/BufferQueueLayer.cpp
index 12be00f..5f494ff 100644
--- a/services/surfaceflinger/BufferQueueLayer.cpp
+++ b/services/surfaceflinger/BufferQueueLayer.cpp
@@ -412,14 +412,6 @@
 // Interface implementation for BufferLayerConsumer::ContentsChangedListener
 // -----------------------------------------------------------------------
 
-void BufferQueueLayer::fakeVsync() {
-    mRefreshPending = false;
-    bool ignored = false;
-    latchBuffer(ignored, systemTime(), 0 /* expectedPresentTime */);
-    usleep(16000);
-    releasePendingBuffer(systemTime());
-}
-
 void BufferQueueLayer::onFrameAvailable(const BufferItem& item) {
     ATRACE_CALL();
     // Add this buffer from our internal queue tracker
@@ -456,13 +448,7 @@
     mFlinger->mInterceptor->saveBufferUpdate(this, item.mGraphicBuffer->getWidth(),
                                              item.mGraphicBuffer->getHeight(), item.mFrameNumber);
 
-    // If this layer is orphaned, then we run a fake vsync pulse so that
-    // dequeueBuffer doesn't block indefinitely.
-    if (isRemovedFromCurrentState()) {
-        fakeVsync();
-    } else {
-        mFlinger->signalLayerUpdate();
-    }
+    mFlinger->signalLayerUpdate();
     mConsumer->onBufferAvailable(item);
 }
 
diff --git a/services/surfaceflinger/BufferQueueLayer.h b/services/surfaceflinger/BufferQueueLayer.h
index 231a531..392b706 100644
--- a/services/surfaceflinger/BufferQueueLayer.h
+++ b/services/surfaceflinger/BufferQueueLayer.h
@@ -138,8 +138,6 @@
     // thread-safe
     std::atomic<int32_t> mQueuedFrames{0};
     std::atomic<bool> mSidebandStreamChanged{false};
-
-    void fakeVsync();
 };
 
 } // namespace android
diff --git a/services/surfaceflinger/Layer.h b/services/surfaceflinger/Layer.h
index 87a5896..2a1564a 100644
--- a/services/surfaceflinger/Layer.h
+++ b/services/surfaceflinger/Layer.h
@@ -544,6 +544,8 @@
 
     virtual bool isBufferLatched() const { return false; }
 
+    virtual void latchAndReleaseBuffer() {}
+
     /*
      * Remove relative z for the layer if its relative parent is not part of the
      * provided layer tree.
diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp
index 04e7bf5..3375649 100644
--- a/services/surfaceflinger/SurfaceFlinger.cpp
+++ b/services/surfaceflinger/SurfaceFlinger.cpp
@@ -2887,14 +2887,6 @@
     }
 }
 
-void SurfaceFlinger::latchAndReleaseBuffer(const sp<Layer>& layer) {
-    if (layer->hasReadyFrame()) {
-        bool ignored = false;
-        layer->latchBuffer(ignored, systemTime(), 0 /* expectedPresentTime */);
-    }
-    layer->releasePendingBuffer(systemTime());
-}
-
 void SurfaceFlinger::commitTransaction()
 {
     if (!mLayersPendingRemoval.isEmpty()) {
@@ -2905,7 +2897,7 @@
 
             // Ensure any buffers set to display on any children are released.
             if (l->isRemovedFromCurrentState()) {
-                latchAndReleaseBuffer(l);
+                l->latchAndReleaseBuffer();
             }
 
             // If the layer has been removed and has no parent, then it will not be reachable
@@ -3163,6 +3155,14 @@
         }
     });
 
+    // The client can continue submitting buffers for offscreen layers, but they will not
+    // be shown on screen. Therefore, we need to latch and release buffers of offscreen
+    // layers to ensure dequeueBuffer doesn't block indefinitely.
+    for (Layer* offscreenLayer : mOffscreenLayers) {
+        offscreenLayer->traverseInZOrder(LayerVector::StateSet::Drawing,
+                                         [&](Layer* l) { l->latchAndReleaseBuffer(); });
+    }
+
     if (!mLayersWithQueuedFrames.empty()) {
         // mStateLock is needed for latchBuffer as LayerRejecter::reject()
         // writes to Layer current state. See also b/119481871
diff --git a/services/surfaceflinger/SurfaceFlinger.h b/services/surfaceflinger/SurfaceFlinger.h
index e199ad5..27a0f6b 100644
--- a/services/surfaceflinger/SurfaceFlinger.h
+++ b/services/surfaceflinger/SurfaceFlinger.h
@@ -576,7 +576,6 @@
     // Can only be called from the main thread or with mStateLock held
     uint32_t setTransactionFlags(uint32_t flags);
     uint32_t setTransactionFlags(uint32_t flags, Scheduler::TransactionStart transactionStart);
-    void latchAndReleaseBuffer(const sp<Layer>& layer);
     void commitTransaction() REQUIRES(mStateLock);
     void commitOffscreenLayers();
     bool transactionIsReadyToBeApplied(int64_t desiredPresentTime,