Add interface for controlling single buffer auto refresh

- Adds a boolean to BufferQueue that controls whether or not auto
  refresh is enabled in SurfaceFlinger when in single buffer mode.
- Adds plumbing up to ANativeWindow.
- When enabled, it will cache the shared buffer slot in Surface in
  order to prevent the Binder transaction with SurfaceFlinger.

Bug 24940410

Change-Id: I83142afdc00e203f198a32288f071d926f8fda95
diff --git a/include/gui/BufferItem.h b/include/gui/BufferItem.h
index a515f39..6f45181 100644
--- a/include/gui/BufferItem.h
+++ b/include/gui/BufferItem.h
@@ -119,8 +119,10 @@
     // previous frame
     Region mSurfaceDamage;
 
-    // Indicates that the BufferQueue is in single buffer mode
-    bool mSingleBufferMode;
+    // Indicates that the consumer should acquire the next frame as soon as it
+    // can and not wait for a frame to become available. This is only relevant
+    // in single buffer mode.
+    bool mAutoRefresh;
 
     // Indicates that this buffer was queued by the producer. When in single
     // buffer mode acquire() can return a BufferItem that wasn't in the queue.
diff --git a/include/gui/BufferQueueCore.h b/include/gui/BufferQueueCore.h
index e2e73a0..d10ba2f 100644
--- a/include/gui/BufferQueueCore.h
+++ b/include/gui/BufferQueueCore.h
@@ -292,6 +292,11 @@
     // consumer and producer to access the same buffer simultaneously.
     bool mSingleBufferMode;
 
+    // When single buffer mode is enabled, this indicates whether the consumer
+    // should acquire buffers even if BufferQueue doesn't indicate that they are
+    // available.
+    bool mAutoRefresh;
+
     // When single buffer mode is enabled, this tracks which slot contains the
     // shared buffer.
     int mSingleBufferSlot;
diff --git a/include/gui/BufferQueueProducer.h b/include/gui/BufferQueueProducer.h
index dc05e98..312f323 100644
--- a/include/gui/BufferQueueProducer.h
+++ b/include/gui/BufferQueueProducer.h
@@ -176,6 +176,9 @@
     // See IGraphicBufferProducer::setSingleBufferMode
     virtual status_t setSingleBufferMode(bool singleBufferMode) override;
 
+    // See IGraphicBufferProducer::setAutoRefresh
+    virtual status_t setAutoRefresh(bool autoRefresh) override;
+
     // See IGraphicBufferProducer::setDequeueTimeout
     virtual status_t setDequeueTimeout(nsecs_t timeout) override;
 
diff --git a/include/gui/IGraphicBufferProducer.h b/include/gui/IGraphicBufferProducer.h
index 265728f..f6b4230 100644
--- a/include/gui/IGraphicBufferProducer.h
+++ b/include/gui/IGraphicBufferProducer.h
@@ -531,6 +531,14 @@
     // the producer and consumer to simultaneously access the same buffer.
     virtual status_t setSingleBufferMode(bool singleBufferMode) = 0;
 
+    // Used to enable/disable auto-refresh.
+    //
+    // Auto refresh has no effect outside of single buffer mode. In single
+    // buffer mode, when enabled, it indicates to the consumer that it should
+    // attempt to acquire buffers even if it is not aware of any being
+    // available.
+    virtual status_t setAutoRefresh(bool autoRefresh) = 0;
+
     // Sets how long dequeueBuffer will wait for a buffer to become available
     // before returning an error (TIMED_OUT).
     //
diff --git a/include/gui/Surface.h b/include/gui/Surface.h
index f79210b..3afdaae 100644
--- a/include/gui/Surface.h
+++ b/include/gui/Surface.h
@@ -168,6 +168,7 @@
     int dispatchSetBuffersDataSpace(va_list args);
     int dispatchSetSurfaceDamage(va_list args);
     int dispatchSetSingleBufferMode(va_list args);
+    int dispatchSetAutoRefresh(va_list args);
 
 protected:
     virtual int dequeueBuffer(ANativeWindowBuffer** buffer, int* fenceFd);
@@ -197,6 +198,7 @@
     virtual int setMaxDequeuedBufferCount(int maxDequeuedBuffers);
     virtual int setAsyncMode(bool async);
     virtual int setSingleBufferMode(bool singleBufferMode);
+    virtual int setAutoRefresh(bool autoRefresh);
     virtual int lock(ANativeWindow_Buffer* outBuffer, ARect* inOutDirtyBounds);
     virtual int unlockAndPost();
 
@@ -331,6 +333,19 @@
     // Stores the current generation number. See setGenerationNumber and
     // IGraphicBufferProducer::setGenerationNumber for more information.
     uint32_t mGenerationNumber;
+
+    // Caches the values that have been passed to the producer.
+    bool mSingleBufferMode;
+    bool mAutoRefresh;
+
+    // If in single buffer mode and auto refresh is enabled, store the shared
+    // buffer slot and return it for all calls to queue/dequeue without going
+    // over Binder.
+    int mSharedBufferSlot;
+
+    // This is true if the shared buffer has already been queued/canceled. It's
+    // used to prevent a mismatch between the number of queue/dequeue calls.
+    bool mSharedBufferHasBeenQueued;
 };
 
 }; // namespace android