Home | History | Annotate | Download | only in gui
      1 /*
      2  * Copyright 2014 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #include <inttypes.h>
     18 
     19 #define LOG_TAG "BufferQueueProducer"
     20 #define ATRACE_TAG ATRACE_TAG_GRAPHICS
     21 //#define LOG_NDEBUG 0
     22 
     23 #if DEBUG_ONLY_CODE
     24 #define VALIDATE_CONSISTENCY() do { mCore->validateConsistencyLocked(); } while (0)
     25 #else
     26 #define VALIDATE_CONSISTENCY()
     27 #endif
     28 
     29 #define EGL_EGLEXT_PROTOTYPES
     30 
     31 #include <binder/IPCThreadState.h>
     32 #include <gui/BufferItem.h>
     33 #include <gui/BufferQueueCore.h>
     34 #include <gui/BufferQueueProducer.h>
     35 #include <gui/GLConsumer.h>
     36 #include <gui/IConsumerListener.h>
     37 #include <gui/IProducerListener.h>
     38 
     39 #include <utils/Log.h>
     40 #include <utils/Trace.h>
     41 
     42 namespace android {
     43 
     44 static constexpr uint32_t BQ_LAYER_COUNT = 1;
     45 
     46 BufferQueueProducer::BufferQueueProducer(const sp<BufferQueueCore>& core,
     47         bool consumerIsSurfaceFlinger) :
     48     mCore(core),
     49     mSlots(core->mSlots),
     50     mConsumerName(),
     51     mStickyTransform(0),
     52     mConsumerIsSurfaceFlinger(consumerIsSurfaceFlinger),
     53     mLastQueueBufferFence(Fence::NO_FENCE),
     54     mLastQueuedTransform(0),
     55     mCallbackMutex(),
     56     mNextCallbackTicket(0),
     57     mCurrentCallbackTicket(0),
     58     mCallbackCondition(),
     59     mDequeueTimeout(-1) {}
     60 
     61 BufferQueueProducer::~BufferQueueProducer() {}
     62 
     63 status_t BufferQueueProducer::requestBuffer(int slot, sp<GraphicBuffer>* buf) {
     64     ATRACE_CALL();
     65     BQ_LOGV("requestBuffer: slot %d", slot);
     66     Mutex::Autolock lock(mCore->mMutex);
     67 
     68     if (mCore->mIsAbandoned) {
     69         BQ_LOGE("requestBuffer: BufferQueue has been abandoned");
     70         return NO_INIT;
     71     }
     72 
     73     if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
     74         BQ_LOGE("requestBuffer: BufferQueue has no connected producer");
     75         return NO_INIT;
     76     }
     77 
     78     if (slot < 0 || slot >= BufferQueueDefs::NUM_BUFFER_SLOTS) {
     79         BQ_LOGE("requestBuffer: slot index %d out of range [0, %d)",
     80                 slot, BufferQueueDefs::NUM_BUFFER_SLOTS);
     81         return BAD_VALUE;
     82     } else if (!mSlots[slot].mBufferState.isDequeued()) {
     83         BQ_LOGE("requestBuffer: slot %d is not owned by the producer "
     84                 "(state = %s)", slot, mSlots[slot].mBufferState.string());
     85         return BAD_VALUE;
     86     }
     87 
     88     mSlots[slot].mRequestBufferCalled = true;
     89     *buf = mSlots[slot].mGraphicBuffer;
     90     return NO_ERROR;
     91 }
     92 
     93 status_t BufferQueueProducer::setMaxDequeuedBufferCount(
     94         int maxDequeuedBuffers) {
     95     ATRACE_CALL();
     96     BQ_LOGV("setMaxDequeuedBufferCount: maxDequeuedBuffers = %d",
     97             maxDequeuedBuffers);
     98 
     99     sp<IConsumerListener> listener;
    100     { // Autolock scope
    101         Mutex::Autolock lock(mCore->mMutex);
    102         mCore->waitWhileAllocatingLocked();
    103 
    104         if (mCore->mIsAbandoned) {
    105             BQ_LOGE("setMaxDequeuedBufferCount: BufferQueue has been "
    106                     "abandoned");
    107             return NO_INIT;
    108         }
    109 
    110         if (maxDequeuedBuffers == mCore->mMaxDequeuedBufferCount) {
    111             return NO_ERROR;
    112         }
    113 
    114         // The new maxDequeuedBuffer count should not be violated by the number
    115         // of currently dequeued buffers
    116         int dequeuedCount = 0;
    117         for (int s : mCore->mActiveBuffers) {
    118             if (mSlots[s].mBufferState.isDequeued()) {
    119                 dequeuedCount++;
    120             }
    121         }
    122         if (dequeuedCount > maxDequeuedBuffers) {
    123             BQ_LOGE("setMaxDequeuedBufferCount: the requested maxDequeuedBuffer"
    124                     "count (%d) exceeds the current dequeued buffer count (%d)",
    125                     maxDequeuedBuffers, dequeuedCount);
    126             return BAD_VALUE;
    127         }
    128 
    129         int bufferCount = mCore->getMinUndequeuedBufferCountLocked();
    130         bufferCount += maxDequeuedBuffers;
    131 
    132         if (bufferCount > BufferQueueDefs::NUM_BUFFER_SLOTS) {
    133             BQ_LOGE("setMaxDequeuedBufferCount: bufferCount %d too large "
    134                     "(max %d)", bufferCount, BufferQueueDefs::NUM_BUFFER_SLOTS);
    135             return BAD_VALUE;
    136         }
    137 
    138         const int minBufferSlots = mCore->getMinMaxBufferCountLocked();
    139         if (bufferCount < minBufferSlots) {
    140             BQ_LOGE("setMaxDequeuedBufferCount: requested buffer count %d is "
    141                     "less than minimum %d", bufferCount, minBufferSlots);
    142             return BAD_VALUE;
    143         }
    144 
    145         if (bufferCount > mCore->mMaxBufferCount) {
    146             BQ_LOGE("setMaxDequeuedBufferCount: %d dequeued buffers would "
    147                     "exceed the maxBufferCount (%d) (maxAcquired %d async %d "
    148                     "mDequeuedBufferCannotBlock %d)", maxDequeuedBuffers,
    149                     mCore->mMaxBufferCount, mCore->mMaxAcquiredBufferCount,
    150                     mCore->mAsyncMode, mCore->mDequeueBufferCannotBlock);
    151             return BAD_VALUE;
    152         }
    153 
    154         int delta = maxDequeuedBuffers - mCore->mMaxDequeuedBufferCount;
    155         if (!mCore->adjustAvailableSlotsLocked(delta)) {
    156             return BAD_VALUE;
    157         }
    158         mCore->mMaxDequeuedBufferCount = maxDequeuedBuffers;
    159         VALIDATE_CONSISTENCY();
    160         if (delta < 0) {
    161             listener = mCore->mConsumerListener;
    162         }
    163         mCore->mDequeueCondition.broadcast();
    164     } // Autolock scope
    165 
    166     // Call back without lock held
    167     if (listener != NULL) {
    168         listener->onBuffersReleased();
    169     }
    170 
    171     return NO_ERROR;
    172 }
    173 
    174 status_t BufferQueueProducer::setAsyncMode(bool async) {
    175     ATRACE_CALL();
    176     BQ_LOGV("setAsyncMode: async = %d", async);
    177 
    178     sp<IConsumerListener> listener;
    179     { // Autolock scope
    180         Mutex::Autolock lock(mCore->mMutex);
    181         mCore->waitWhileAllocatingLocked();
    182 
    183         if (mCore->mIsAbandoned) {
    184             BQ_LOGE("setAsyncMode: BufferQueue has been abandoned");
    185             return NO_INIT;
    186         }
    187 
    188         if (async == mCore->mAsyncMode) {
    189             return NO_ERROR;
    190         }
    191 
    192         if ((mCore->mMaxAcquiredBufferCount + mCore->mMaxDequeuedBufferCount +
    193                 (async || mCore->mDequeueBufferCannotBlock ? 1 : 0)) >
    194                 mCore->mMaxBufferCount) {
    195             BQ_LOGE("setAsyncMode(%d): this call would cause the "
    196                     "maxBufferCount (%d) to be exceeded (maxAcquired %d "
    197                     "maxDequeued %d mDequeueBufferCannotBlock %d)", async,
    198                     mCore->mMaxBufferCount, mCore->mMaxAcquiredBufferCount,
    199                     mCore->mMaxDequeuedBufferCount,
    200                     mCore->mDequeueBufferCannotBlock);
    201             return BAD_VALUE;
    202         }
    203 
    204         int delta = mCore->getMaxBufferCountLocked(async,
    205                 mCore->mDequeueBufferCannotBlock, mCore->mMaxBufferCount)
    206                 - mCore->getMaxBufferCountLocked();
    207 
    208         if (!mCore->adjustAvailableSlotsLocked(delta)) {
    209             BQ_LOGE("setAsyncMode: BufferQueue failed to adjust the number of "
    210                     "available slots. Delta = %d", delta);
    211             return BAD_VALUE;
    212         }
    213         mCore->mAsyncMode = async;
    214         VALIDATE_CONSISTENCY();
    215         mCore->mDequeueCondition.broadcast();
    216         if (delta < 0) {
    217             listener = mCore->mConsumerListener;
    218         }
    219     } // Autolock scope
    220 
    221     // Call back without lock held
    222     if (listener != NULL) {
    223         listener->onBuffersReleased();
    224     }
    225     return NO_ERROR;
    226 }
    227 
    228 int BufferQueueProducer::getFreeBufferLocked() const {
    229     if (mCore->mFreeBuffers.empty()) {
    230         return BufferQueueCore::INVALID_BUFFER_SLOT;
    231     }
    232     int slot = mCore->mFreeBuffers.front();
    233     mCore->mFreeBuffers.pop_front();
    234     return slot;
    235 }
    236 
    237 int BufferQueueProducer::getFreeSlotLocked() const {
    238     if (mCore->mFreeSlots.empty()) {
    239         return BufferQueueCore::INVALID_BUFFER_SLOT;
    240     }
    241     int slot = *(mCore->mFreeSlots.begin());
    242     mCore->mFreeSlots.erase(slot);
    243     return slot;
    244 }
    245 
    246 status_t BufferQueueProducer::waitForFreeSlotThenRelock(FreeSlotCaller caller,
    247         int* found) const {
    248     auto callerString = (caller == FreeSlotCaller::Dequeue) ?
    249             "dequeueBuffer" : "attachBuffer";
    250     bool tryAgain = true;
    251     while (tryAgain) {
    252         if (mCore->mIsAbandoned) {
    253             BQ_LOGE("%s: BufferQueue has been abandoned", callerString);
    254             return NO_INIT;
    255         }
    256 
    257         int dequeuedCount = 0;
    258         int acquiredCount = 0;
    259         for (int s : mCore->mActiveBuffers) {
    260             if (mSlots[s].mBufferState.isDequeued()) {
    261                 ++dequeuedCount;
    262             }
    263             if (mSlots[s].mBufferState.isAcquired()) {
    264                 ++acquiredCount;
    265             }
    266         }
    267 
    268         // Producers are not allowed to dequeue more than
    269         // mMaxDequeuedBufferCount buffers.
    270         // This check is only done if a buffer has already been queued
    271         if (mCore->mBufferHasBeenQueued &&
    272                 dequeuedCount >= mCore->mMaxDequeuedBufferCount) {
    273             BQ_LOGE("%s: attempting to exceed the max dequeued buffer count "
    274                     "(%d)", callerString, mCore->mMaxDequeuedBufferCount);
    275             return INVALID_OPERATION;
    276         }
    277 
    278         *found = BufferQueueCore::INVALID_BUFFER_SLOT;
    279 
    280         // If we disconnect and reconnect quickly, we can be in a state where
    281         // our slots are empty but we have many buffers in the queue. This can
    282         // cause us to run out of memory if we outrun the consumer. Wait here if
    283         // it looks like we have too many buffers queued up.
    284         const int maxBufferCount = mCore->getMaxBufferCountLocked();
    285         bool tooManyBuffers = mCore->mQueue.size()
    286                             > static_cast<size_t>(maxBufferCount);
    287         if (tooManyBuffers) {
    288             BQ_LOGV("%s: queue size is %zu, waiting", callerString,
    289                     mCore->mQueue.size());
    290         } else {
    291             // If in shared buffer mode and a shared buffer exists, always
    292             // return it.
    293             if (mCore->mSharedBufferMode && mCore->mSharedBufferSlot !=
    294                     BufferQueueCore::INVALID_BUFFER_SLOT) {
    295                 *found = mCore->mSharedBufferSlot;
    296             } else {
    297                 if (caller == FreeSlotCaller::Dequeue) {
    298                     // If we're calling this from dequeue, prefer free buffers
    299                     int slot = getFreeBufferLocked();
    300                     if (slot != BufferQueueCore::INVALID_BUFFER_SLOT) {
    301                         *found = slot;
    302                     } else if (mCore->mAllowAllocation) {
    303                         *found = getFreeSlotLocked();
    304                     }
    305                 } else {
    306                     // If we're calling this from attach, prefer free slots
    307                     int slot = getFreeSlotLocked();
    308                     if (slot != BufferQueueCore::INVALID_BUFFER_SLOT) {
    309                         *found = slot;
    310                     } else {
    311                         *found = getFreeBufferLocked();
    312                     }
    313                 }
    314             }
    315         }
    316 
    317         // If no buffer is found, or if the queue has too many buffers
    318         // outstanding, wait for a buffer to be acquired or released, or for the
    319         // max buffer count to change.
    320         tryAgain = (*found == BufferQueueCore::INVALID_BUFFER_SLOT) ||
    321                    tooManyBuffers;
    322         if (tryAgain) {
    323             // Return an error if we're in non-blocking mode (producer and
    324             // consumer are controlled by the application).
    325             // However, the consumer is allowed to briefly acquire an extra
    326             // buffer (which could cause us to have to wait here), which is
    327             // okay, since it is only used to implement an atomic acquire +
    328             // release (e.g., in GLConsumer::updateTexImage())
    329             if ((mCore->mDequeueBufferCannotBlock || mCore->mAsyncMode) &&
    330                     (acquiredCount <= mCore->mMaxAcquiredBufferCount)) {
    331                 return WOULD_BLOCK;
    332             }
    333             if (mDequeueTimeout >= 0) {
    334                 status_t result = mCore->mDequeueCondition.waitRelative(
    335                         mCore->mMutex, mDequeueTimeout);
    336                 if (result == TIMED_OUT) {
    337                     return result;
    338                 }
    339             } else {
    340                 mCore->mDequeueCondition.wait(mCore->mMutex);
    341             }
    342         }
    343     } // while (tryAgain)
    344 
    345     return NO_ERROR;
    346 }
    347 
    348 status_t BufferQueueProducer::dequeueBuffer(int *outSlot,
    349         sp<android::Fence> *outFence, uint32_t width, uint32_t height,
    350         PixelFormat format, uint32_t usage,
    351         FrameEventHistoryDelta* outTimestamps) {
    352     ATRACE_CALL();
    353     { // Autolock scope
    354         Mutex::Autolock lock(mCore->mMutex);
    355         mConsumerName = mCore->mConsumerName;
    356 
    357         if (mCore->mIsAbandoned) {
    358             BQ_LOGE("dequeueBuffer: BufferQueue has been abandoned");
    359             return NO_INIT;
    360         }
    361 
    362         if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
    363             BQ_LOGE("dequeueBuffer: BufferQueue has no connected producer");
    364             return NO_INIT;
    365         }
    366     } // Autolock scope
    367 
    368     BQ_LOGV("dequeueBuffer: w=%u h=%u format=%#x, usage=%#x", width, height,
    369             format, usage);
    370 
    371     if ((width && !height) || (!width && height)) {
    372         BQ_LOGE("dequeueBuffer: invalid size: w=%u h=%u", width, height);
    373         return BAD_VALUE;
    374     }
    375 
    376     status_t returnFlags = NO_ERROR;
    377     EGLDisplay eglDisplay = EGL_NO_DISPLAY;
    378     EGLSyncKHR eglFence = EGL_NO_SYNC_KHR;
    379     bool attachedByConsumer = false;
    380 
    381     { // Autolock scope
    382         Mutex::Autolock lock(mCore->mMutex);
    383         mCore->waitWhileAllocatingLocked();
    384 
    385         if (format == 0) {
    386             format = mCore->mDefaultBufferFormat;
    387         }
    388 
    389         // Enable the usage bits the consumer requested
    390         usage |= mCore->mConsumerUsageBits;
    391 
    392         const bool useDefaultSize = !width && !height;
    393         if (useDefaultSize) {
    394             width = mCore->mDefaultWidth;
    395             height = mCore->mDefaultHeight;
    396         }
    397 
    398         int found = BufferItem::INVALID_BUFFER_SLOT;
    399         while (found == BufferItem::INVALID_BUFFER_SLOT) {
    400             status_t status = waitForFreeSlotThenRelock(FreeSlotCaller::Dequeue,
    401                     &found);
    402             if (status != NO_ERROR) {
    403                 return status;
    404             }
    405 
    406             // This should not happen
    407             if (found == BufferQueueCore::INVALID_BUFFER_SLOT) {
    408                 BQ_LOGE("dequeueBuffer: no available buffer slots");
    409                 return -EBUSY;
    410             }
    411 
    412             const sp<GraphicBuffer>& buffer(mSlots[found].mGraphicBuffer);
    413 
    414             // If we are not allowed to allocate new buffers,
    415             // waitForFreeSlotThenRelock must have returned a slot containing a
    416             // buffer. If this buffer would require reallocation to meet the
    417             // requested attributes, we free it and attempt to get another one.
    418             if (!mCore->mAllowAllocation) {
    419                 if (buffer->needsReallocation(width, height, format,
    420                         BQ_LAYER_COUNT, usage)) {
    421                     if (mCore->mSharedBufferSlot == found) {
    422                         BQ_LOGE("dequeueBuffer: cannot re-allocate a shared"
    423                                 "buffer");
    424                         return BAD_VALUE;
    425                     }
    426                     mCore->mFreeSlots.insert(found);
    427                     mCore->clearBufferSlotLocked(found);
    428                     found = BufferItem::INVALID_BUFFER_SLOT;
    429                     continue;
    430                 }
    431             }
    432         }
    433 
    434         const sp<GraphicBuffer>& buffer(mSlots[found].mGraphicBuffer);
    435         if (mCore->mSharedBufferSlot == found &&
    436                 buffer->needsReallocation(width, height, format,
    437                         BQ_LAYER_COUNT, usage)) {
    438             BQ_LOGE("dequeueBuffer: cannot re-allocate a shared"
    439                     "buffer");
    440 
    441             return BAD_VALUE;
    442         }
    443 
    444         if (mCore->mSharedBufferSlot != found) {
    445             mCore->mActiveBuffers.insert(found);
    446         }
    447         *outSlot = found;
    448         ATRACE_BUFFER_INDEX(found);
    449 
    450         attachedByConsumer = mSlots[found].mNeedsReallocation;
    451         mSlots[found].mNeedsReallocation = false;
    452 
    453         mSlots[found].mBufferState.dequeue();
    454 
    455         if ((buffer == NULL) ||
    456                 buffer->needsReallocation(width, height, format, BQ_LAYER_COUNT, usage))
    457         {
    458             mSlots[found].mAcquireCalled = false;
    459             mSlots[found].mGraphicBuffer = NULL;
    460             mSlots[found].mRequestBufferCalled = false;
    461             mSlots[found].mEglDisplay = EGL_NO_DISPLAY;
    462             mSlots[found].mEglFence = EGL_NO_SYNC_KHR;
    463             mSlots[found].mFence = Fence::NO_FENCE;
    464             mCore->mBufferAge = 0;
    465             mCore->mIsAllocating = true;
    466 
    467             returnFlags |= BUFFER_NEEDS_REALLOCATION;
    468         } else {
    469             // We add 1 because that will be the frame number when this buffer
    470             // is queued
    471             mCore->mBufferAge =
    472                     mCore->mFrameCounter + 1 - mSlots[found].mFrameNumber;
    473         }
    474 
    475         BQ_LOGV("dequeueBuffer: setting buffer age to %" PRIu64,
    476                 mCore->mBufferAge);
    477 
    478         if (CC_UNLIKELY(mSlots[found].mFence == NULL)) {
    479             BQ_LOGE("dequeueBuffer: about to return a NULL fence - "
    480                     "slot=%d w=%d h=%d format=%u",
    481                     found, buffer->width, buffer->height, buffer->format);
    482         }
    483 
    484         eglDisplay = mSlots[found].mEglDisplay;
    485         eglFence = mSlots[found].mEglFence;
    486         // Don't return a fence in shared buffer mode, except for the first
    487         // frame.
    488         *outFence = (mCore->mSharedBufferMode &&
    489                 mCore->mSharedBufferSlot == found) ?
    490                 Fence::NO_FENCE : mSlots[found].mFence;
    491         mSlots[found].mEglFence = EGL_NO_SYNC_KHR;
    492         mSlots[found].mFence = Fence::NO_FENCE;
    493 
    494         // If shared buffer mode has just been enabled, cache the slot of the
    495         // first buffer that is dequeued and mark it as the shared buffer.
    496         if (mCore->mSharedBufferMode && mCore->mSharedBufferSlot ==
    497                 BufferQueueCore::INVALID_BUFFER_SLOT) {
    498             mCore->mSharedBufferSlot = found;
    499             mSlots[found].mBufferState.mShared = true;
    500         }
    501     } // Autolock scope
    502 
    503     if (returnFlags & BUFFER_NEEDS_REALLOCATION) {
    504         BQ_LOGV("dequeueBuffer: allocating a new buffer for slot %d", *outSlot);
    505         sp<GraphicBuffer> graphicBuffer = new GraphicBuffer(
    506                 width, height, format, BQ_LAYER_COUNT, usage,
    507                 {mConsumerName.string(), mConsumerName.size()});
    508 
    509         status_t error = graphicBuffer->initCheck();
    510 
    511         { // Autolock scope
    512             Mutex::Autolock lock(mCore->mMutex);
    513 
    514             if (error == NO_ERROR && !mCore->mIsAbandoned) {
    515                 graphicBuffer->setGenerationNumber(mCore->mGenerationNumber);
    516                 mSlots[*outSlot].mGraphicBuffer = graphicBuffer;
    517             }
    518 
    519             mCore->mIsAllocating = false;
    520             mCore->mIsAllocatingCondition.broadcast();
    521 
    522             if (error != NO_ERROR) {
    523                 mCore->mFreeSlots.insert(*outSlot);
    524                 mCore->clearBufferSlotLocked(*outSlot);
    525                 BQ_LOGE("dequeueBuffer: createGraphicBuffer failed");
    526                 return error;
    527             }
    528 
    529             if (mCore->mIsAbandoned) {
    530                 mCore->mFreeSlots.insert(*outSlot);
    531                 mCore->clearBufferSlotLocked(*outSlot);
    532                 BQ_LOGE("dequeueBuffer: BufferQueue has been abandoned");
    533                 return NO_INIT;
    534             }
    535 
    536             VALIDATE_CONSISTENCY();
    537         } // Autolock scope
    538     }
    539 
    540     if (attachedByConsumer) {
    541         returnFlags |= BUFFER_NEEDS_REALLOCATION;
    542     }
    543 
    544     if (eglFence != EGL_NO_SYNC_KHR) {
    545         EGLint result = eglClientWaitSyncKHR(eglDisplay, eglFence, 0,
    546                 1000000000);
    547         // If something goes wrong, log the error, but return the buffer without
    548         // synchronizing access to it. It's too late at this point to abort the
    549         // dequeue operation.
    550         if (result == EGL_FALSE) {
    551             BQ_LOGE("dequeueBuffer: error %#x waiting for fence",
    552                     eglGetError());
    553         } else if (result == EGL_TIMEOUT_EXPIRED_KHR) {
    554             BQ_LOGE("dequeueBuffer: timeout waiting for fence");
    555         }
    556         eglDestroySyncKHR(eglDisplay, eglFence);
    557     }
    558 
    559     BQ_LOGV("dequeueBuffer: returning slot=%d/%" PRIu64 " buf=%p flags=%#x",
    560             *outSlot,
    561             mSlots[*outSlot].mFrameNumber,
    562             mSlots[*outSlot].mGraphicBuffer->handle, returnFlags);
    563 
    564     addAndGetFrameTimestamps(nullptr, outTimestamps);
    565 
    566     return returnFlags;
    567 }
    568 
    569 status_t BufferQueueProducer::detachBuffer(int slot) {
    570     ATRACE_CALL();
    571     ATRACE_BUFFER_INDEX(slot);
    572     BQ_LOGV("detachBuffer: slot %d", slot);
    573 
    574     sp<IConsumerListener> listener;
    575     {
    576         Mutex::Autolock lock(mCore->mMutex);
    577 
    578         if (mCore->mIsAbandoned) {
    579             BQ_LOGE("detachBuffer: BufferQueue has been abandoned");
    580             return NO_INIT;
    581         }
    582 
    583         if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
    584             BQ_LOGE("detachBuffer: BufferQueue has no connected producer");
    585             return NO_INIT;
    586         }
    587 
    588         if (mCore->mSharedBufferMode || mCore->mSharedBufferSlot == slot) {
    589             BQ_LOGE("detachBuffer: cannot detach a buffer in shared buffer mode");
    590             return BAD_VALUE;
    591         }
    592 
    593         if (slot < 0 || slot >= BufferQueueDefs::NUM_BUFFER_SLOTS) {
    594             BQ_LOGE("detachBuffer: slot index %d out of range [0, %d)",
    595                     slot, BufferQueueDefs::NUM_BUFFER_SLOTS);
    596             return BAD_VALUE;
    597         } else if (!mSlots[slot].mBufferState.isDequeued()) {
    598             BQ_LOGE("detachBuffer: slot %d is not owned by the producer "
    599                     "(state = %s)", slot, mSlots[slot].mBufferState.string());
    600             return BAD_VALUE;
    601         } else if (!mSlots[slot].mRequestBufferCalled) {
    602             BQ_LOGE("detachBuffer: buffer in slot %d has not been requested",
    603                     slot);
    604             return BAD_VALUE;
    605         }
    606 
    607         mSlots[slot].mBufferState.detachProducer();
    608         mCore->mActiveBuffers.erase(slot);
    609         mCore->mFreeSlots.insert(slot);
    610         mCore->clearBufferSlotLocked(slot);
    611         mCore->mDequeueCondition.broadcast();
    612         VALIDATE_CONSISTENCY();
    613         listener = mCore->mConsumerListener;
    614     }
    615 
    616     if (listener != NULL) {
    617         listener->onBuffersReleased();
    618     }
    619 
    620     return NO_ERROR;
    621 }
    622 
    623 status_t BufferQueueProducer::detachNextBuffer(sp<GraphicBuffer>* outBuffer,
    624         sp<Fence>* outFence) {
    625     ATRACE_CALL();
    626 
    627     if (outBuffer == NULL) {
    628         BQ_LOGE("detachNextBuffer: outBuffer must not be NULL");
    629         return BAD_VALUE;
    630     } else if (outFence == NULL) {
    631         BQ_LOGE("detachNextBuffer: outFence must not be NULL");
    632         return BAD_VALUE;
    633     }
    634 
    635     sp<IConsumerListener> listener;
    636     {
    637         Mutex::Autolock lock(mCore->mMutex);
    638 
    639         if (mCore->mIsAbandoned) {
    640             BQ_LOGE("detachNextBuffer: BufferQueue has been abandoned");
    641             return NO_INIT;
    642         }
    643 
    644         if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
    645             BQ_LOGE("detachNextBuffer: BufferQueue has no connected producer");
    646             return NO_INIT;
    647         }
    648 
    649         if (mCore->mSharedBufferMode) {
    650             BQ_LOGE("detachNextBuffer: cannot detach a buffer in shared buffer "
    651                     "mode");
    652             return BAD_VALUE;
    653         }
    654 
    655         mCore->waitWhileAllocatingLocked();
    656 
    657         if (mCore->mFreeBuffers.empty()) {
    658             return NO_MEMORY;
    659         }
    660 
    661         int found = mCore->mFreeBuffers.front();
    662         mCore->mFreeBuffers.remove(found);
    663         mCore->mFreeSlots.insert(found);
    664 
    665         BQ_LOGV("detachNextBuffer detached slot %d", found);
    666 
    667         *outBuffer = mSlots[found].mGraphicBuffer;
    668         *outFence = mSlots[found].mFence;
    669         mCore->clearBufferSlotLocked(found);
    670         VALIDATE_CONSISTENCY();
    671         listener = mCore->mConsumerListener;
    672     }
    673 
    674     if (listener != NULL) {
    675         listener->onBuffersReleased();
    676     }
    677 
    678     return NO_ERROR;
    679 }
    680 
    681 status_t BufferQueueProducer::attachBuffer(int* outSlot,
    682         const sp<android::GraphicBuffer>& buffer) {
    683     ATRACE_CALL();
    684 
    685     if (outSlot == NULL) {
    686         BQ_LOGE("attachBuffer: outSlot must not be NULL");
    687         return BAD_VALUE;
    688     } else if (buffer == NULL) {
    689         BQ_LOGE("attachBuffer: cannot attach NULL buffer");
    690         return BAD_VALUE;
    691     }
    692 
    693     Mutex::Autolock lock(mCore->mMutex);
    694 
    695     if (mCore->mIsAbandoned) {
    696         BQ_LOGE("attachBuffer: BufferQueue has been abandoned");
    697         return NO_INIT;
    698     }
    699 
    700     if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
    701         BQ_LOGE("attachBuffer: BufferQueue has no connected producer");
    702         return NO_INIT;
    703     }
    704 
    705     if (mCore->mSharedBufferMode) {
    706         BQ_LOGE("attachBuffer: cannot attach a buffer in shared buffer mode");
    707         return BAD_VALUE;
    708     }
    709 
    710     if (buffer->getGenerationNumber() != mCore->mGenerationNumber) {
    711         BQ_LOGE("attachBuffer: generation number mismatch [buffer %u] "
    712                 "[queue %u]", buffer->getGenerationNumber(),
    713                 mCore->mGenerationNumber);
    714         return BAD_VALUE;
    715     }
    716 
    717     mCore->waitWhileAllocatingLocked();
    718 
    719     status_t returnFlags = NO_ERROR;
    720     int found;
    721     status_t status = waitForFreeSlotThenRelock(FreeSlotCaller::Attach, &found);
    722     if (status != NO_ERROR) {
    723         return status;
    724     }
    725 
    726     // This should not happen
    727     if (found == BufferQueueCore::INVALID_BUFFER_SLOT) {
    728         BQ_LOGE("attachBuffer: no available buffer slots");
    729         return -EBUSY;
    730     }
    731 
    732     *outSlot = found;
    733     ATRACE_BUFFER_INDEX(*outSlot);
    734     BQ_LOGV("attachBuffer: returning slot %d flags=%#x",
    735             *outSlot, returnFlags);
    736 
    737     mSlots[*outSlot].mGraphicBuffer = buffer;
    738     mSlots[*outSlot].mBufferState.attachProducer();
    739     mSlots[*outSlot].mEglFence = EGL_NO_SYNC_KHR;
    740     mSlots[*outSlot].mFence = Fence::NO_FENCE;
    741     mSlots[*outSlot].mRequestBufferCalled = true;
    742     mSlots[*outSlot].mAcquireCalled = false;
    743     mSlots[*outSlot].mNeedsReallocation = false;
    744     mCore->mActiveBuffers.insert(found);
    745     VALIDATE_CONSISTENCY();
    746 
    747     return returnFlags;
    748 }
    749 
    750 status_t BufferQueueProducer::queueBuffer(int slot,
    751         const QueueBufferInput &input, QueueBufferOutput *output) {
    752     ATRACE_CALL();
    753     ATRACE_BUFFER_INDEX(slot);
    754 
    755     int64_t requestedPresentTimestamp;
    756     bool isAutoTimestamp;
    757     android_dataspace dataSpace;
    758     Rect crop(Rect::EMPTY_RECT);
    759     int scalingMode;
    760     uint32_t transform;
    761     uint32_t stickyTransform;
    762     sp<Fence> acquireFence;
    763     bool getFrameTimestamps = false;
    764     input.deflate(&requestedPresentTimestamp, &isAutoTimestamp, &dataSpace,
    765             &crop, &scalingMode, &transform, &acquireFence, &stickyTransform,
    766             &getFrameTimestamps);
    767     Region surfaceDamage = input.getSurfaceDamage();
    768 
    769     if (acquireFence == NULL) {
    770         BQ_LOGE("queueBuffer: fence is NULL");
    771         return BAD_VALUE;
    772     }
    773 
    774     auto acquireFenceTime = std::make_shared<FenceTime>(acquireFence);
    775 
    776     switch (scalingMode) {
    777         case NATIVE_WINDOW_SCALING_MODE_FREEZE:
    778         case NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW:
    779         case NATIVE_WINDOW_SCALING_MODE_SCALE_CROP:
    780         case NATIVE_WINDOW_SCALING_MODE_NO_SCALE_CROP:
    781             break;
    782         default:
    783             BQ_LOGE("queueBuffer: unknown scaling mode %d", scalingMode);
    784             return BAD_VALUE;
    785     }
    786 
    787     sp<IConsumerListener> frameAvailableListener;
    788     sp<IConsumerListener> frameReplacedListener;
    789     int callbackTicket = 0;
    790     uint64_t currentFrameNumber = 0;
    791     BufferItem item;
    792     { // Autolock scope
    793         Mutex::Autolock lock(mCore->mMutex);
    794 
    795         if (mCore->mIsAbandoned) {
    796             BQ_LOGE("queueBuffer: BufferQueue has been abandoned");
    797             return NO_INIT;
    798         }
    799 
    800         if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
    801             BQ_LOGE("queueBuffer: BufferQueue has no connected producer");
    802             return NO_INIT;
    803         }
    804 
    805         if (slot < 0 || slot >= BufferQueueDefs::NUM_BUFFER_SLOTS) {
    806             BQ_LOGE("queueBuffer: slot index %d out of range [0, %d)",
    807                     slot, BufferQueueDefs::NUM_BUFFER_SLOTS);
    808             return BAD_VALUE;
    809         } else if (!mSlots[slot].mBufferState.isDequeued()) {
    810             BQ_LOGE("queueBuffer: slot %d is not owned by the producer "
    811                     "(state = %s)", slot, mSlots[slot].mBufferState.string());
    812             return BAD_VALUE;
    813         } else if (!mSlots[slot].mRequestBufferCalled) {
    814             BQ_LOGE("queueBuffer: slot %d was queued without requesting "
    815                     "a buffer", slot);
    816             return BAD_VALUE;
    817         }
    818 
    819         // If shared buffer mode has just been enabled, cache the slot of the
    820         // first buffer that is queued and mark it as the shared buffer.
    821         if (mCore->mSharedBufferMode && mCore->mSharedBufferSlot ==
    822                 BufferQueueCore::INVALID_BUFFER_SLOT) {
    823             mCore->mSharedBufferSlot = slot;
    824             mSlots[slot].mBufferState.mShared = true;
    825         }
    826 
    827         BQ_LOGV("queueBuffer: slot=%d/%" PRIu64 " time=%" PRIu64 " dataSpace=%d"
    828                 " crop=[%d,%d,%d,%d] transform=%#x scale=%s",
    829                 slot, mCore->mFrameCounter + 1, requestedPresentTimestamp,
    830                 dataSpace, crop.left, crop.top, crop.right, crop.bottom,
    831                 transform,
    832                 BufferItem::scalingModeName(static_cast<uint32_t>(scalingMode)));
    833 
    834         const sp<GraphicBuffer>& graphicBuffer(mSlots[slot].mGraphicBuffer);
    835         Rect bufferRect(graphicBuffer->getWidth(), graphicBuffer->getHeight());
    836         Rect croppedRect(Rect::EMPTY_RECT);
    837         crop.intersect(bufferRect, &croppedRect);
    838         if (croppedRect != crop) {
    839             BQ_LOGE("queueBuffer: crop rect is not contained within the "
    840                     "buffer in slot %d", slot);
    841             return BAD_VALUE;
    842         }
    843 
    844         // Override UNKNOWN dataspace with consumer default
    845         if (dataSpace == HAL_DATASPACE_UNKNOWN) {
    846             dataSpace = mCore->mDefaultBufferDataSpace;
    847         }
    848 
    849         mSlots[slot].mFence = acquireFence;
    850         mSlots[slot].mBufferState.queue();
    851 
    852         // Increment the frame counter and store a local version of it
    853         // for use outside the lock on mCore->mMutex.
    854         ++mCore->mFrameCounter;
    855         currentFrameNumber = mCore->mFrameCounter;
    856         mSlots[slot].mFrameNumber = currentFrameNumber;
    857 
    858         item.mAcquireCalled = mSlots[slot].mAcquireCalled;
    859         item.mGraphicBuffer = mSlots[slot].mGraphicBuffer;
    860         item.mCrop = crop;
    861         item.mTransform = transform &
    862                 ~static_cast<uint32_t>(NATIVE_WINDOW_TRANSFORM_INVERSE_DISPLAY);
    863         item.mTransformToDisplayInverse =
    864                 (transform & NATIVE_WINDOW_TRANSFORM_INVERSE_DISPLAY) != 0;
    865         item.mScalingMode = static_cast<uint32_t>(scalingMode);
    866         item.mTimestamp = requestedPresentTimestamp;
    867         item.mIsAutoTimestamp = isAutoTimestamp;
    868         item.mDataSpace = dataSpace;
    869         item.mFrameNumber = currentFrameNumber;
    870         item.mSlot = slot;
    871         item.mFence = acquireFence;
    872         item.mFenceTime = acquireFenceTime;
    873         item.mIsDroppable = mCore->mAsyncMode ||
    874                 mCore->mDequeueBufferCannotBlock ||
    875                 (mCore->mSharedBufferMode && mCore->mSharedBufferSlot == slot);
    876         item.mSurfaceDamage = surfaceDamage;
    877         item.mQueuedBuffer = true;
    878         item.mAutoRefresh = mCore->mSharedBufferMode && mCore->mAutoRefresh;
    879 
    880         mStickyTransform = stickyTransform;
    881 
    882         // Cache the shared buffer data so that the BufferItem can be recreated.
    883         if (mCore->mSharedBufferMode) {
    884             mCore->mSharedBufferCache.crop = crop;
    885             mCore->mSharedBufferCache.transform = transform;
    886             mCore->mSharedBufferCache.scalingMode = static_cast<uint32_t>(
    887                     scalingMode);
    888             mCore->mSharedBufferCache.dataspace = dataSpace;
    889         }
    890 
    891         output->bufferReplaced = false;
    892         if (mCore->mQueue.empty()) {
    893             // When the queue is empty, we can ignore mDequeueBufferCannotBlock
    894             // and simply queue this buffer
    895             mCore->mQueue.push_back(item);
    896             frameAvailableListener = mCore->mConsumerListener;
    897         } else {
    898             // When the queue is not empty, we need to look at the last buffer
    899             // in the queue to see if we need to replace it
    900             const BufferItem& last = mCore->mQueue.itemAt(
    901                     mCore->mQueue.size() - 1);
    902             if (last.mIsDroppable) {
    903 
    904                 if (!last.mIsStale) {
    905                     mSlots[last.mSlot].mBufferState.freeQueued();
    906 
    907                     // After leaving shared buffer mode, the shared buffer will
    908                     // still be around. Mark it as no longer shared if this
    909                     // operation causes it to be free.
    910                     if (!mCore->mSharedBufferMode &&
    911                             mSlots[last.mSlot].mBufferState.isFree()) {
    912                         mSlots[last.mSlot].mBufferState.mShared = false;
    913                     }
    914                     // Don't put the shared buffer on the free list.
    915                     if (!mSlots[last.mSlot].mBufferState.isShared()) {
    916                         mCore->mActiveBuffers.erase(last.mSlot);
    917                         mCore->mFreeBuffers.push_back(last.mSlot);
    918                         output->bufferReplaced = true;
    919                     }
    920                 }
    921 
    922                 // Overwrite the droppable buffer with the incoming one
    923                 mCore->mQueue.editItemAt(mCore->mQueue.size() - 1) = item;
    924                 frameReplacedListener = mCore->mConsumerListener;
    925             } else {
    926                 mCore->mQueue.push_back(item);
    927                 frameAvailableListener = mCore->mConsumerListener;
    928             }
    929         }
    930 
    931         mCore->mBufferHasBeenQueued = true;
    932         mCore->mDequeueCondition.broadcast();
    933         mCore->mLastQueuedSlot = slot;
    934 
    935         output->width = mCore->mDefaultWidth;
    936         output->height = mCore->mDefaultHeight;
    937         output->transformHint = mCore->mTransformHint;
    938         output->numPendingBuffers = static_cast<uint32_t>(mCore->mQueue.size());
    939         output->nextFrameNumber = mCore->mFrameCounter + 1;
    940 
    941         ATRACE_INT(mCore->mConsumerName.string(),
    942                 static_cast<int32_t>(mCore->mQueue.size()));
    943         mCore->mOccupancyTracker.registerOccupancyChange(mCore->mQueue.size());
    944 
    945         // Take a ticket for the callback functions
    946         callbackTicket = mNextCallbackTicket++;
    947 
    948         VALIDATE_CONSISTENCY();
    949     } // Autolock scope
    950 
    951     // It is okay not to clear the GraphicBuffer when the consumer is SurfaceFlinger because
    952     // it is guaranteed that the BufferQueue is inside SurfaceFlinger's process and
    953     // there will be no Binder call
    954     if (!mConsumerIsSurfaceFlinger) {
    955         item.mGraphicBuffer.clear();
    956     }
    957 
    958     // Don't send the slot number through the callback since the consumer shouldn't need it
    959     item.mSlot = BufferItem::INVALID_BUFFER_SLOT;
    960 
    961     // Call back without the main BufferQueue lock held, but with the callback
    962     // lock held so we can ensure that callbacks occur in order
    963 
    964     int connectedApi;
    965     sp<Fence> lastQueuedFence;
    966 
    967     { // scope for the lock
    968         Mutex::Autolock lock(mCallbackMutex);
    969         while (callbackTicket != mCurrentCallbackTicket) {
    970             mCallbackCondition.wait(mCallbackMutex);
    971         }
    972 
    973         if (frameAvailableListener != NULL) {
    974             frameAvailableListener->onFrameAvailable(item);
    975         } else if (frameReplacedListener != NULL) {
    976             frameReplacedListener->onFrameReplaced(item);
    977         }
    978 
    979         connectedApi = mCore->mConnectedApi;
    980         lastQueuedFence = std::move(mLastQueueBufferFence);
    981 
    982         mLastQueueBufferFence = std::move(acquireFence);
    983         mLastQueuedCrop = item.mCrop;
    984         mLastQueuedTransform = item.mTransform;
    985 
    986         ++mCurrentCallbackTicket;
    987         mCallbackCondition.broadcast();
    988     }
    989 
    990     // Wait without lock held
    991     if (connectedApi == NATIVE_WINDOW_API_EGL) {
    992         // Waiting here allows for two full buffers to be queued but not a
    993         // third. In the event that frames take varying time, this makes a
    994         // small trade-off in favor of latency rather than throughput.
    995         lastQueuedFence->waitForever("Throttling EGL Production");
    996     }
    997 
    998     // Update and get FrameEventHistory.
    999     nsecs_t postedTime = systemTime(SYSTEM_TIME_MONOTONIC);
   1000     NewFrameEventsEntry newFrameEventsEntry = {
   1001         currentFrameNumber,
   1002         postedTime,
   1003         requestedPresentTimestamp,
   1004         std::move(acquireFenceTime)
   1005     };
   1006     addAndGetFrameTimestamps(&newFrameEventsEntry,
   1007             getFrameTimestamps ? &output->frameTimestamps : nullptr);
   1008 
   1009     return NO_ERROR;
   1010 }
   1011 
   1012 status_t BufferQueueProducer::cancelBuffer(int slot, const sp<Fence>& fence) {
   1013     ATRACE_CALL();
   1014     BQ_LOGV("cancelBuffer: slot %d", slot);
   1015     Mutex::Autolock lock(mCore->mMutex);
   1016 
   1017     if (mCore->mIsAbandoned) {
   1018         BQ_LOGE("cancelBuffer: BufferQueue has been abandoned");
   1019         return NO_INIT;
   1020     }
   1021 
   1022     if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
   1023         BQ_LOGE("cancelBuffer: BufferQueue has no connected producer");
   1024         return NO_INIT;
   1025     }
   1026 
   1027     if (mCore->mSharedBufferMode) {
   1028         BQ_LOGE("cancelBuffer: cannot cancel a buffer in shared buffer mode");
   1029         return BAD_VALUE;
   1030     }
   1031 
   1032     if (slot < 0 || slot >= BufferQueueDefs::NUM_BUFFER_SLOTS) {
   1033         BQ_LOGE("cancelBuffer: slot index %d out of range [0, %d)",
   1034                 slot, BufferQueueDefs::NUM_BUFFER_SLOTS);
   1035         return BAD_VALUE;
   1036     } else if (!mSlots[slot].mBufferState.isDequeued()) {
   1037         BQ_LOGE("cancelBuffer: slot %d is not owned by the producer "
   1038                 "(state = %s)", slot, mSlots[slot].mBufferState.string());
   1039         return BAD_VALUE;
   1040     } else if (fence == NULL) {
   1041         BQ_LOGE("cancelBuffer: fence is NULL");
   1042         return BAD_VALUE;
   1043     }
   1044 
   1045     mSlots[slot].mBufferState.cancel();
   1046 
   1047     // After leaving shared buffer mode, the shared buffer will still be around.
   1048     // Mark it as no longer shared if this operation causes it to be free.
   1049     if (!mCore->mSharedBufferMode && mSlots[slot].mBufferState.isFree()) {
   1050         mSlots[slot].mBufferState.mShared = false;
   1051     }
   1052 
   1053     // Don't put the shared buffer on the free list.
   1054     if (!mSlots[slot].mBufferState.isShared()) {
   1055         mCore->mActiveBuffers.erase(slot);
   1056         mCore->mFreeBuffers.push_back(slot);
   1057     }
   1058 
   1059     mSlots[slot].mFence = fence;
   1060     mCore->mDequeueCondition.broadcast();
   1061     VALIDATE_CONSISTENCY();
   1062 
   1063     return NO_ERROR;
   1064 }
   1065 
   1066 int BufferQueueProducer::query(int what, int *outValue) {
   1067     ATRACE_CALL();
   1068     Mutex::Autolock lock(mCore->mMutex);
   1069 
   1070     if (outValue == NULL) {
   1071         BQ_LOGE("query: outValue was NULL");
   1072         return BAD_VALUE;
   1073     }
   1074 
   1075     if (mCore->mIsAbandoned) {
   1076         BQ_LOGE("query: BufferQueue has been abandoned");
   1077         return NO_INIT;
   1078     }
   1079 
   1080     int value;
   1081     switch (what) {
   1082         case NATIVE_WINDOW_WIDTH:
   1083             value = static_cast<int32_t>(mCore->mDefaultWidth);
   1084             break;
   1085         case NATIVE_WINDOW_HEIGHT:
   1086             value = static_cast<int32_t>(mCore->mDefaultHeight);
   1087             break;
   1088         case NATIVE_WINDOW_FORMAT:
   1089             value = static_cast<int32_t>(mCore->mDefaultBufferFormat);
   1090             break;
   1091         case NATIVE_WINDOW_LAYER_COUNT:
   1092             // All BufferQueue buffers have a single layer.
   1093             value = BQ_LAYER_COUNT;
   1094             break;
   1095         case NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS:
   1096             value = mCore->getMinUndequeuedBufferCountLocked();
   1097             break;
   1098         case NATIVE_WINDOW_STICKY_TRANSFORM:
   1099             value = static_cast<int32_t>(mStickyTransform);
   1100             break;
   1101         case NATIVE_WINDOW_CONSUMER_RUNNING_BEHIND:
   1102             value = (mCore->mQueue.size() > 1);
   1103             break;
   1104         case NATIVE_WINDOW_CONSUMER_USAGE_BITS:
   1105             value = static_cast<int32_t>(mCore->mConsumerUsageBits);
   1106             break;
   1107         case NATIVE_WINDOW_DEFAULT_DATASPACE:
   1108             value = static_cast<int32_t>(mCore->mDefaultBufferDataSpace);
   1109             break;
   1110         case NATIVE_WINDOW_BUFFER_AGE:
   1111             if (mCore->mBufferAge > INT32_MAX) {
   1112                 value = 0;
   1113             } else {
   1114                 value = static_cast<int32_t>(mCore->mBufferAge);
   1115             }
   1116             break;
   1117         case NATIVE_WINDOW_CONSUMER_IS_PROTECTED:
   1118             value = static_cast<int32_t>(mCore->mConsumerIsProtected);
   1119             break;
   1120         default:
   1121             return BAD_VALUE;
   1122     }
   1123 
   1124     BQ_LOGV("query: %d? %d", what, value);
   1125     *outValue = value;
   1126     return NO_ERROR;
   1127 }
   1128 
   1129 status_t BufferQueueProducer::connect(const sp<IProducerListener>& listener,
   1130         int api, bool producerControlledByApp, QueueBufferOutput *output) {
   1131     ATRACE_CALL();
   1132     Mutex::Autolock lock(mCore->mMutex);
   1133     mConsumerName = mCore->mConsumerName;
   1134     BQ_LOGV("connect: api=%d producerControlledByApp=%s", api,
   1135             producerControlledByApp ? "true" : "false");
   1136 
   1137     if (mCore->mIsAbandoned) {
   1138         BQ_LOGE("connect: BufferQueue has been abandoned");
   1139         return NO_INIT;
   1140     }
   1141 
   1142     if (mCore->mConsumerListener == NULL) {
   1143         BQ_LOGE("connect: BufferQueue has no consumer");
   1144         return NO_INIT;
   1145     }
   1146 
   1147     if (output == NULL) {
   1148         BQ_LOGE("connect: output was NULL");
   1149         return BAD_VALUE;
   1150     }
   1151 
   1152     if (mCore->mConnectedApi != BufferQueueCore::NO_CONNECTED_API) {
   1153         BQ_LOGE("connect: already connected (cur=%d req=%d)",
   1154                 mCore->mConnectedApi, api);
   1155         return BAD_VALUE;
   1156     }
   1157 
   1158     int delta = mCore->getMaxBufferCountLocked(mCore->mAsyncMode,
   1159             mDequeueTimeout < 0 ?
   1160             mCore->mConsumerControlledByApp && producerControlledByApp : false,
   1161             mCore->mMaxBufferCount) -
   1162             mCore->getMaxBufferCountLocked();
   1163     if (!mCore->adjustAvailableSlotsLocked(delta)) {
   1164         BQ_LOGE("connect: BufferQueue failed to adjust the number of available "
   1165                 "slots. Delta = %d", delta);
   1166         return BAD_VALUE;
   1167     }
   1168 
   1169     int status = NO_ERROR;
   1170     switch (api) {
   1171         case NATIVE_WINDOW_API_EGL:
   1172         case NATIVE_WINDOW_API_CPU:
   1173         case NATIVE_WINDOW_API_MEDIA:
   1174         case NATIVE_WINDOW_API_CAMERA:
   1175             mCore->mConnectedApi = api;
   1176 
   1177             output->width = mCore->mDefaultWidth;
   1178             output->height = mCore->mDefaultHeight;
   1179             output->transformHint = mCore->mTransformHint;
   1180             output->numPendingBuffers =
   1181                     static_cast<uint32_t>(mCore->mQueue.size());
   1182             output->nextFrameNumber = mCore->mFrameCounter + 1;
   1183             output->bufferReplaced = false;
   1184 
   1185             if (listener != NULL) {
   1186                 // Set up a death notification so that we can disconnect
   1187                 // automatically if the remote producer dies
   1188                 if (IInterface::asBinder(listener)->remoteBinder() != NULL) {
   1189                     status = IInterface::asBinder(listener)->linkToDeath(
   1190                             static_cast<IBinder::DeathRecipient*>(this));
   1191                     if (status != NO_ERROR) {
   1192                         BQ_LOGE("connect: linkToDeath failed: %s (%d)",
   1193                                 strerror(-status), status);
   1194                     }
   1195                     mCore->mLinkedToDeath = listener;
   1196                 }
   1197                 if (listener->needsReleaseNotify()) {
   1198                     mCore->mConnectedProducerListener = listener;
   1199                 }
   1200             }
   1201             break;
   1202         default:
   1203             BQ_LOGE("connect: unknown API %d", api);
   1204             status = BAD_VALUE;
   1205             break;
   1206     }
   1207     mCore->mConnectedPid = IPCThreadState::self()->getCallingPid();
   1208     mCore->mBufferHasBeenQueued = false;
   1209     mCore->mDequeueBufferCannotBlock = false;
   1210     if (mDequeueTimeout < 0) {
   1211         mCore->mDequeueBufferCannotBlock =
   1212                 mCore->mConsumerControlledByApp && producerControlledByApp;
   1213     }
   1214 
   1215     mCore->mAllowAllocation = true;
   1216     VALIDATE_CONSISTENCY();
   1217     return status;
   1218 }
   1219 
   1220 status_t BufferQueueProducer::disconnect(int api, DisconnectMode mode) {
   1221     ATRACE_CALL();
   1222     BQ_LOGV("disconnect: api %d", api);
   1223 
   1224     int status = NO_ERROR;
   1225     sp<IConsumerListener> listener;
   1226     { // Autolock scope
   1227         Mutex::Autolock lock(mCore->mMutex);
   1228 
   1229         if (mode == DisconnectMode::AllLocal) {
   1230             if (IPCThreadState::self()->getCallingPid() != mCore->mConnectedPid) {
   1231                 return NO_ERROR;
   1232             }
   1233             api = BufferQueueCore::CURRENTLY_CONNECTED_API;
   1234         }
   1235 
   1236         mCore->waitWhileAllocatingLocked();
   1237 
   1238         if (mCore->mIsAbandoned) {
   1239             // It's not really an error to disconnect after the surface has
   1240             // been abandoned; it should just be a no-op.
   1241             return NO_ERROR;
   1242         }
   1243 
   1244         if (api == BufferQueueCore::CURRENTLY_CONNECTED_API) {
   1245             if (mCore->mConnectedApi == NATIVE_WINDOW_API_MEDIA) {
   1246                 ALOGD("About to force-disconnect API_MEDIA, mode=%d", mode);
   1247             }
   1248             api = mCore->mConnectedApi;
   1249             // If we're asked to disconnect the currently connected api but
   1250             // nobody is connected, it's not really an error.
   1251             if (api == BufferQueueCore::NO_CONNECTED_API) {
   1252                 return NO_ERROR;
   1253             }
   1254         }
   1255 
   1256         switch (api) {
   1257             case NATIVE_WINDOW_API_EGL:
   1258             case NATIVE_WINDOW_API_CPU:
   1259             case NATIVE_WINDOW_API_MEDIA:
   1260             case NATIVE_WINDOW_API_CAMERA:
   1261                 if (mCore->mConnectedApi == api) {
   1262                     mCore->freeAllBuffersLocked();
   1263 
   1264                     // Remove our death notification callback if we have one
   1265                     if (mCore->mLinkedToDeath != NULL) {
   1266                         sp<IBinder> token =
   1267                                 IInterface::asBinder(mCore->mLinkedToDeath);
   1268                         // This can fail if we're here because of the death
   1269                         // notification, but we just ignore it
   1270                         token->unlinkToDeath(
   1271                                 static_cast<IBinder::DeathRecipient*>(this));
   1272                     }
   1273                     mCore->mSharedBufferSlot =
   1274                             BufferQueueCore::INVALID_BUFFER_SLOT;
   1275                     mCore->mLinkedToDeath = NULL;
   1276                     mCore->mConnectedProducerListener = NULL;
   1277                     mCore->mConnectedApi = BufferQueueCore::NO_CONNECTED_API;
   1278                     mCore->mConnectedPid = -1;
   1279                     mCore->mSidebandStream.clear();
   1280                     mCore->mDequeueCondition.broadcast();
   1281                     listener = mCore->mConsumerListener;
   1282                 } else if (mCore->mConnectedApi == BufferQueueCore::NO_CONNECTED_API) {
   1283                     BQ_LOGE("disconnect: not connected (req=%d)", api);
   1284                     status = NO_INIT;
   1285                 } else {
   1286                     BQ_LOGE("disconnect: still connected to another API "
   1287                             "(cur=%d req=%d)", mCore->mConnectedApi, api);
   1288                     status = BAD_VALUE;
   1289                 }
   1290                 break;
   1291             default:
   1292                 BQ_LOGE("disconnect: unknown API %d", api);
   1293                 status = BAD_VALUE;
   1294                 break;
   1295         }
   1296     } // Autolock scope
   1297 
   1298     // Call back without lock held
   1299     if (listener != NULL) {
   1300         listener->onBuffersReleased();
   1301         listener->onDisconnect();
   1302     }
   1303 
   1304     return status;
   1305 }
   1306 
   1307 status_t BufferQueueProducer::setSidebandStream(const sp<NativeHandle>& stream) {
   1308     sp<IConsumerListener> listener;
   1309     { // Autolock scope
   1310         Mutex::Autolock _l(mCore->mMutex);
   1311         mCore->mSidebandStream = stream;
   1312         listener = mCore->mConsumerListener;
   1313     } // Autolock scope
   1314 
   1315     if (listener != NULL) {
   1316         listener->onSidebandStreamChanged();
   1317     }
   1318     return NO_ERROR;
   1319 }
   1320 
   1321 void BufferQueueProducer::allocateBuffers(uint32_t width, uint32_t height,
   1322         PixelFormat format, uint32_t usage) {
   1323     ATRACE_CALL();
   1324     while (true) {
   1325         size_t newBufferCount = 0;
   1326         uint32_t allocWidth = 0;
   1327         uint32_t allocHeight = 0;
   1328         PixelFormat allocFormat = PIXEL_FORMAT_UNKNOWN;
   1329         uint32_t allocUsage = 0;
   1330         { // Autolock scope
   1331             Mutex::Autolock lock(mCore->mMutex);
   1332             mCore->waitWhileAllocatingLocked();
   1333 
   1334             if (!mCore->mAllowAllocation) {
   1335                 BQ_LOGE("allocateBuffers: allocation is not allowed for this "
   1336                         "BufferQueue");
   1337                 return;
   1338             }
   1339 
   1340             newBufferCount = mCore->mFreeSlots.size();
   1341             if (newBufferCount == 0) {
   1342                 return;
   1343             }
   1344 
   1345             allocWidth = width > 0 ? width : mCore->mDefaultWidth;
   1346             allocHeight = height > 0 ? height : mCore->mDefaultHeight;
   1347             allocFormat = format != 0 ? format : mCore->mDefaultBufferFormat;
   1348             allocUsage = usage | mCore->mConsumerUsageBits;
   1349 
   1350             mCore->mIsAllocating = true;
   1351         } // Autolock scope
   1352 
   1353         Vector<sp<GraphicBuffer>> buffers;
   1354         for (size_t i = 0; i <  newBufferCount; ++i) {
   1355             sp<GraphicBuffer> graphicBuffer = new GraphicBuffer(
   1356                     allocWidth, allocHeight, allocFormat, BQ_LAYER_COUNT,
   1357                     allocUsage, {mConsumerName.string(), mConsumerName.size()});
   1358 
   1359             status_t result = graphicBuffer->initCheck();
   1360 
   1361             if (result != NO_ERROR) {
   1362                 BQ_LOGE("allocateBuffers: failed to allocate buffer (%u x %u, format"
   1363                         " %u, usage %u)", width, height, format, usage);
   1364                 Mutex::Autolock lock(mCore->mMutex);
   1365                 mCore->mIsAllocating = false;
   1366                 mCore->mIsAllocatingCondition.broadcast();
   1367                 return;
   1368             }
   1369             buffers.push_back(graphicBuffer);
   1370         }
   1371 
   1372         { // Autolock scope
   1373             Mutex::Autolock lock(mCore->mMutex);
   1374             uint32_t checkWidth = width > 0 ? width : mCore->mDefaultWidth;
   1375             uint32_t checkHeight = height > 0 ? height : mCore->mDefaultHeight;
   1376             PixelFormat checkFormat = format != 0 ?
   1377                     format : mCore->mDefaultBufferFormat;
   1378             uint32_t checkUsage = usage | mCore->mConsumerUsageBits;
   1379             if (checkWidth != allocWidth || checkHeight != allocHeight ||
   1380                 checkFormat != allocFormat || checkUsage != allocUsage) {
   1381                 // Something changed while we released the lock. Retry.
   1382                 BQ_LOGV("allocateBuffers: size/format/usage changed while allocating. Retrying.");
   1383                 mCore->mIsAllocating = false;
   1384                 mCore->mIsAllocatingCondition.broadcast();
   1385                 continue;
   1386             }
   1387 
   1388             for (size_t i = 0; i < newBufferCount; ++i) {
   1389                 if (mCore->mFreeSlots.empty()) {
   1390                     BQ_LOGV("allocateBuffers: a slot was occupied while "
   1391                             "allocating. Dropping allocated buffer.");
   1392                     continue;
   1393                 }
   1394                 auto slot = mCore->mFreeSlots.begin();
   1395                 mCore->clearBufferSlotLocked(*slot); // Clean up the slot first
   1396                 mSlots[*slot].mGraphicBuffer = buffers[i];
   1397                 mSlots[*slot].mFence = Fence::NO_FENCE;
   1398 
   1399                 // freeBufferLocked puts this slot on the free slots list. Since
   1400                 // we then attached a buffer, move the slot to free buffer list.
   1401                 mCore->mFreeBuffers.push_front(*slot);
   1402 
   1403                 BQ_LOGV("allocateBuffers: allocated a new buffer in slot %d",
   1404                         *slot);
   1405 
   1406                 // Make sure the erase is done after all uses of the slot
   1407                 // iterator since it will be invalid after this point.
   1408                 mCore->mFreeSlots.erase(slot);
   1409             }
   1410 
   1411             mCore->mIsAllocating = false;
   1412             mCore->mIsAllocatingCondition.broadcast();
   1413             VALIDATE_CONSISTENCY();
   1414         } // Autolock scope
   1415     }
   1416 }
   1417 
   1418 status_t BufferQueueProducer::allowAllocation(bool allow) {
   1419     ATRACE_CALL();
   1420     BQ_LOGV("allowAllocation: %s", allow ? "true" : "false");
   1421 
   1422     Mutex::Autolock lock(mCore->mMutex);
   1423     mCore->mAllowAllocation = allow;
   1424     return NO_ERROR;
   1425 }
   1426 
   1427 status_t BufferQueueProducer::setGenerationNumber(uint32_t generationNumber) {
   1428     ATRACE_CALL();
   1429     BQ_LOGV("setGenerationNumber: %u", generationNumber);
   1430 
   1431     Mutex::Autolock lock(mCore->mMutex);
   1432     mCore->mGenerationNumber = generationNumber;
   1433     return NO_ERROR;
   1434 }
   1435 
   1436 String8 BufferQueueProducer::getConsumerName() const {
   1437     ATRACE_CALL();
   1438     Mutex::Autolock lock(mCore->mMutex);
   1439     BQ_LOGV("getConsumerName: %s", mConsumerName.string());
   1440     return mConsumerName;
   1441 }
   1442 
   1443 status_t BufferQueueProducer::setSharedBufferMode(bool sharedBufferMode) {
   1444     ATRACE_CALL();
   1445     BQ_LOGV("setSharedBufferMode: %d", sharedBufferMode);
   1446 
   1447     Mutex::Autolock lock(mCore->mMutex);
   1448     if (!sharedBufferMode) {
   1449         mCore->mSharedBufferSlot = BufferQueueCore::INVALID_BUFFER_SLOT;
   1450     }
   1451     mCore->mSharedBufferMode = sharedBufferMode;
   1452     return NO_ERROR;
   1453 }
   1454 
   1455 status_t BufferQueueProducer::setAutoRefresh(bool autoRefresh) {
   1456     ATRACE_CALL();
   1457     BQ_LOGV("setAutoRefresh: %d", autoRefresh);
   1458 
   1459     Mutex::Autolock lock(mCore->mMutex);
   1460 
   1461     mCore->mAutoRefresh = autoRefresh;
   1462     return NO_ERROR;
   1463 }
   1464 
   1465 status_t BufferQueueProducer::setDequeueTimeout(nsecs_t timeout) {
   1466     ATRACE_CALL();
   1467     BQ_LOGV("setDequeueTimeout: %" PRId64, timeout);
   1468 
   1469     Mutex::Autolock lock(mCore->mMutex);
   1470     int delta = mCore->getMaxBufferCountLocked(mCore->mAsyncMode, false,
   1471             mCore->mMaxBufferCount) - mCore->getMaxBufferCountLocked();
   1472     if (!mCore->adjustAvailableSlotsLocked(delta)) {
   1473         BQ_LOGE("setDequeueTimeout: BufferQueue failed to adjust the number of "
   1474                 "available slots. Delta = %d", delta);
   1475         return BAD_VALUE;
   1476     }
   1477 
   1478     mDequeueTimeout = timeout;
   1479     mCore->mDequeueBufferCannotBlock = false;
   1480 
   1481     VALIDATE_CONSISTENCY();
   1482     return NO_ERROR;
   1483 }
   1484 
   1485 status_t BufferQueueProducer::getLastQueuedBuffer(sp<GraphicBuffer>* outBuffer,
   1486         sp<Fence>* outFence, float outTransformMatrix[16]) {
   1487     ATRACE_CALL();
   1488     BQ_LOGV("getLastQueuedBuffer");
   1489 
   1490     Mutex::Autolock lock(mCore->mMutex);
   1491     if (mCore->mLastQueuedSlot == BufferItem::INVALID_BUFFER_SLOT) {
   1492         *outBuffer = nullptr;
   1493         *outFence = Fence::NO_FENCE;
   1494         return NO_ERROR;
   1495     }
   1496 
   1497     *outBuffer = mSlots[mCore->mLastQueuedSlot].mGraphicBuffer;
   1498     *outFence = mLastQueueBufferFence;
   1499 
   1500     // Currently only SurfaceFlinger internally ever changes
   1501     // GLConsumer's filtering mode, so we just use 'true' here as
   1502     // this is slightly specialized for the current client of this API,
   1503     // which does want filtering.
   1504     GLConsumer::computeTransformMatrix(outTransformMatrix,
   1505             mSlots[mCore->mLastQueuedSlot].mGraphicBuffer, mLastQueuedCrop,
   1506             mLastQueuedTransform, true /* filter */);
   1507 
   1508     return NO_ERROR;
   1509 }
   1510 
   1511 void BufferQueueProducer::getFrameTimestamps(FrameEventHistoryDelta* outDelta) {
   1512     addAndGetFrameTimestamps(nullptr, outDelta);
   1513 }
   1514 
   1515 void BufferQueueProducer::addAndGetFrameTimestamps(
   1516         const NewFrameEventsEntry* newTimestamps,
   1517         FrameEventHistoryDelta* outDelta) {
   1518     if (newTimestamps == nullptr && outDelta == nullptr) {
   1519         return;
   1520     }
   1521 
   1522     ATRACE_CALL();
   1523     BQ_LOGV("addAndGetFrameTimestamps");
   1524     sp<IConsumerListener> listener;
   1525     {
   1526         Mutex::Autolock lock(mCore->mMutex);
   1527         listener = mCore->mConsumerListener;
   1528     }
   1529     if (listener != NULL) {
   1530         listener->addAndGetFrameTimestamps(newTimestamps, outDelta);
   1531     }
   1532 }
   1533 
   1534 void BufferQueueProducer::binderDied(const wp<android::IBinder>& /* who */) {
   1535     // If we're here, it means that a producer we were connected to died.
   1536     // We're guaranteed that we are still connected to it because we remove
   1537     // this callback upon disconnect. It's therefore safe to read mConnectedApi
   1538     // without synchronization here.
   1539     int api = mCore->mConnectedApi;
   1540     disconnect(api);
   1541 }
   1542 
   1543 status_t BufferQueueProducer::getUniqueId(uint64_t* outId) const {
   1544     BQ_LOGV("getUniqueId");
   1545 
   1546     *outId = mCore->mUniqueId;
   1547     return NO_ERROR;
   1548 }
   1549 
   1550 } // namespace android
   1551