1d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin/* 2d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * Copyright (C) 2013 The Android Open Source Project 3d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * 4d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * Licensed under the Apache License, Version 2.0 (the "License"); 5d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * you may not use this file except in compliance with the License. 6d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * You may obtain a copy of the License at 7d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * 8d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * http://www.apache.org/licenses/LICENSE-2.0 9d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * 10d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * Unless required by applicable law or agreed to in writing, software 11d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * distributed under the License is distributed on an "AS IS" BASIS, 12d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * See the License for the specific language governing permissions and 14d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * limitations under the License. 15d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin */ 16d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 17d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin//#define LOG_NDEBUG 0 18d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#define LOG_TAG "RingBufferConsumer" 19d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#define ATRACE_TAG ATRACE_TAG_GRAPHICS 20d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#include <utils/Log.h> 21d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 22d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#include <gui/RingBufferConsumer.h> 23d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 24d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#define BI_LOGV(x, ...) ALOGV("[%s] "x, mName.string(), ##__VA_ARGS__) 25d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#define BI_LOGD(x, ...) ALOGD("[%s] "x, mName.string(), ##__VA_ARGS__) 26d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#define BI_LOGI(x, ...) ALOGI("[%s] "x, mName.string(), ##__VA_ARGS__) 27d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#define BI_LOGW(x, ...) ALOGW("[%s] "x, mName.string(), ##__VA_ARGS__) 28d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin#define BI_LOGE(x, ...) ALOGE("[%s] "x, mName.string(), ##__VA_ARGS__) 29d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 308e2afd9817e53858e3f99f810c0b7abe4c4d5533Igor Murashkin#undef assert 318e2afd9817e53858e3f99f810c0b7abe4c4d5533Igor Murashkin#define assert(x) ALOG_ASSERT((x), #x) 328e2afd9817e53858e3f99f810c0b7abe4c4d5533Igor Murashkin 33d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkintypedef android::RingBufferConsumer::PinnedBufferItem PinnedBufferItem; 34d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 35d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinnamespace android { 36d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 37deeef54487a34034dc0cfaab20b20d557224c07cMathias AgopianRingBufferConsumer::RingBufferConsumer(const sp<IGraphicBufferConsumer>& consumer, 38deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian uint32_t consumerUsage, 39d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin int bufferCount) : 40deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian ConsumerBase(consumer), 41d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin mBufferCount(bufferCount) 42d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin{ 43deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian mConsumer->setConsumerUsageBits(consumerUsage); 44deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian mConsumer->setMaxAcquiredBufferCount(bufferCount); 45d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 46d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin assert(bufferCount > 0); 47d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 48d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 49d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor MurashkinRingBufferConsumer::~RingBufferConsumer() { 50d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 51d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 52d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinvoid RingBufferConsumer::setName(const String8& name) { 53d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 54d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin mName = name; 55deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian mConsumer->setConsumerName(name); 56d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 57d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 58d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinsp<PinnedBufferItem> RingBufferConsumer::pinSelectedBuffer( 59d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin const RingBufferComparator& filter, 60d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin bool waitForFence) { 61d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 62d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin sp<PinnedBufferItem> pinnedBuffer; 63d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 64d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin { 65d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin List<RingBufferItem>::iterator it, end, accIt; 66d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BufferInfo acc, cur; 67d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BufferInfo* accPtr = NULL; 68d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 69d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 70d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 71d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin for (it = mBufferItemList.begin(), end = mBufferItemList.end(); 72d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin it != end; 73d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin ++it) { 74d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 75d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin const RingBufferItem& item = *it; 76d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 77d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin cur.mCrop = item.mCrop; 78d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin cur.mTransform = item.mTransform; 79d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin cur.mScalingMode = item.mScalingMode; 80d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin cur.mTimestamp = item.mTimestamp; 81d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin cur.mFrameNumber = item.mFrameNumber; 82d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin cur.mPinned = item.mPinCount > 0; 83d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 84d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin int ret = filter.compare(accPtr, &cur); 85d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 86d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (ret == 0) { 87d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin accPtr = NULL; 88d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } else if (ret > 0) { 89d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin acc = cur; 90d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin accPtr = &acc; 91d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin accIt = it; 92d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } // else acc = acc 93d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 94d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 95d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (!accPtr) { 96d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return NULL; 97d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 98d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 99d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin pinnedBuffer = new PinnedBufferItem(this, *accIt); 100d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin pinBufferLocked(pinnedBuffer->getBufferItem()); 101d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 102d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } // end scope of mMutex autolock 103d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 104d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (waitForFence) { 105d76442421eadfa73f2f3a9e50f6caf65b0dd1ce9Mathias Agopian status_t err = pinnedBuffer->getBufferItem().mFence->waitForever( 106d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin "RingBufferConsumer::pinSelectedBuffer"); 107d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err != OK) { 108d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGE("Failed to wait for fence of acquired buffer: %s (%d)", 109d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin strerror(-err), err); 110d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 111d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 112d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 113d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return pinnedBuffer; 114d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 115d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 116d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinstatus_t RingBufferConsumer::clear() { 117d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 118d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin status_t err; 119d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 120d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 121d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGV("%s", __FUNCTION__); 122d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 123d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // Avoid annoying log warnings by returning early 124d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (mBufferItemList.size() == 0) { 125d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return OK; 126d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 127d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 128d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin do { 129d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin size_t pinnedFrames = 0; 130d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin err = releaseOldestBufferLocked(&pinnedFrames); 131d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 132d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err == NO_BUFFER_AVAILABLE) { 133d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin assert(pinnedFrames == mBufferItemList.size()); 134d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin break; 135d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 136d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 137d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err == NOT_ENOUGH_DATA) { 138d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // Fine. Empty buffer item list. 139d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin break; 140d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 141d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 142d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err != OK) { 143d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGE("Clear failed, could not release buffer"); 144d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return err; 145d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 146d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 147d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } while(true); 148d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 149d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return OK; 150d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 151d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 152d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinvoid RingBufferConsumer::pinBufferLocked(const BufferItem& item) { 153d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin List<RingBufferItem>::iterator it, end; 154d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 155d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin for (it = mBufferItemList.begin(), end = mBufferItemList.end(); 156d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin it != end; 157d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin ++it) { 158d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 159d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin RingBufferItem& find = *it; 160d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (item.mGraphicBuffer == find.mGraphicBuffer) { 161d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin find.mPinCount++; 162d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin break; 163d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 164d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 165d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 166d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (it == end) { 167d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGE("Failed to pin buffer (timestamp %lld, framenumber %lld)", 168d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mTimestamp, item.mFrameNumber); 169efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin } else { 170efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin BI_LOGV("Pinned buffer (frame %lld, timestamp %lld)", 171efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin item.mFrameNumber, item.mTimestamp); 172d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 173d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 174d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 175d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinstatus_t RingBufferConsumer::releaseOldestBufferLocked(size_t* pinnedFrames) { 176d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin status_t err = OK; 177d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 178d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin List<RingBufferItem>::iterator it, end, accIt; 179d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 180d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin it = mBufferItemList.begin(); 181d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin end = mBufferItemList.end(); 182efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin accIt = end; 183d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 184d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (it == end) { 185d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin /** 186d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * This is fine. We really care about being able to acquire a buffer 187d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * successfully after this function completes, not about it releasing 188d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * some buffer. 189d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin */ 190d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGV("%s: No buffers yet acquired, can't release anything", 191d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin __FUNCTION__); 192d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return NOT_ENOUGH_DATA; 193d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 194d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 195d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin for (; it != end; ++it) { 196d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin RingBufferItem& find = *it; 197efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin 198efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin if (find.mPinCount > 0) { 199efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin if (pinnedFrames != NULL) { 200efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin ++(*pinnedFrames); 201efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin } 202efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin // Filter out pinned frame when searching for buffer to release 203efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin continue; 204d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 205d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 206efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin if (find.mTimestamp < accIt->mTimestamp || accIt == end) { 207efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin accIt = it; 208d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 209d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 210d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 211d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (accIt != end) { 212d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin RingBufferItem& item = *accIt; 213d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 214d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // In case the object was never pinned, pass the acquire fence 215d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // back to the release fence. If the fence was already waited on, 216d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // it'll just be a no-op to wait on it again. 217d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar 218d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar // item.mGraphicBuffer was populated with the proper graphic-buffer 219d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar // at acquire even if it was previously acquired 220d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar err = addReleaseFenceLocked(item.mBuf, 221d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar item.mGraphicBuffer, item.mFence); 222d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 223d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err != OK) { 224d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGE("Failed to add release fence to buffer " 225d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin "(timestamp %lld, framenumber %lld", 226d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mTimestamp, item.mFrameNumber); 227d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return err; 228d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 229d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 230d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGV("Attempting to release buffer timestamp %lld, frame %lld", 231d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mTimestamp, item.mFrameNumber); 232d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 233d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar // item.mGraphicBuffer was populated with the proper graphic-buffer 234d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar // at acquire even if it was previously acquired 235d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar err = releaseBufferLocked(item.mBuf, item.mGraphicBuffer, 236d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin EGL_NO_DISPLAY, 237d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin EGL_NO_SYNC_KHR); 238d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err != OK) { 239d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGE("Failed to release buffer: %s (%d)", 240d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin strerror(-err), err); 241d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return err; 242d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 243d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 244d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGV("Buffer timestamp %lld, frame %lld evicted", 245d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mTimestamp, item.mFrameNumber); 246d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 247d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin size_t currentSize = mBufferItemList.size(); 248d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin mBufferItemList.erase(accIt); 249d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin assert(mBufferItemList.size() == currentSize - 1); 250d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } else { 251d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGW("All buffers pinned, could not find any to release"); 252d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return NO_BUFFER_AVAILABLE; 253d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 254d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 255d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 256d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return OK; 257d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 258d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 259d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinvoid RingBufferConsumer::onFrameAvailable() { 260d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin status_t err; 261d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 262d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin { 263d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 264d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 265d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin /** 266d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * Release oldest frame 267d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin */ 268d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (mBufferItemList.size() >= (size_t)mBufferCount) { 269d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin err = releaseOldestBufferLocked(/*pinnedFrames*/NULL); 270d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin assert(err != NOT_ENOUGH_DATA); 271d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 272d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // TODO: implement the case for NO_BUFFER_AVAILABLE 273d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin assert(err != NO_BUFFER_AVAILABLE); 274d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err != OK) { 275d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return; 276d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 277d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // TODO: in unpinBuffer rerun this routine if we had buffers 278d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin // we could've locked but didn't because there was no space 279d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 280d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 281d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin RingBufferItem& item = *mBufferItemList.insert(mBufferItemList.end(), 282d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin RingBufferItem()); 283d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 284d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin /** 285d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin * Acquire new frame 286d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin */ 287656e86250cd68f7f362c50a4bc92a865e9deacbeAndy McFadden err = acquireBufferLocked(&item, 0); 288d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err != OK) { 289d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (err != NO_BUFFER_AVAILABLE) { 290d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGE("Error acquiring buffer: %s (%d)", strerror(err), err); 291d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 292d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 293d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin mBufferItemList.erase(--mBufferItemList.end()); 294d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return; 295d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 296d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 297d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGV("New buffer acquired (timestamp %lld), " 298d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin "buffer items %u out of %d", 299d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mTimestamp, 300d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin mBufferItemList.size(), mBufferCount); 301d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 302d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mGraphicBuffer = mSlots[item.mBuf].mGraphicBuffer; 303d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } // end of mMutex lock 304d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 305d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin ConsumerBase::onFrameAvailable(); 306d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 307d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 308d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinvoid RingBufferConsumer::unpinBuffer(const BufferItem& item) { 309d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 310d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 311d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin List<RingBufferItem>::iterator it, end, accIt; 312d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 313d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin for (it = mBufferItemList.begin(), end = mBufferItemList.end(); 314d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin it != end; 315d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin ++it) { 316d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 317d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin RingBufferItem& find = *it; 318d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (item.mGraphicBuffer == find.mGraphicBuffer) { 319d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar status_t res = addReleaseFenceLocked(item.mBuf, 320d030447b617105b31bf3013e5e4b39d422b53b77Lajos Molnar item.mGraphicBuffer, item.mFence); 321d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 322d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (res != OK) { 323d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin BI_LOGE("Failed to add release fence to buffer " 324d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin "(timestamp %lld, framenumber %lld", 325d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mTimestamp, item.mFrameNumber); 326d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin return; 327d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 328d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 329d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin find.mPinCount--; 330d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin break; 331d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 332d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 333d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 334d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin if (it == end) { 335efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin // This should never happen. If it happens, we have a bug. 336efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin BI_LOGE("Failed to unpin buffer (timestamp %lld, framenumber %lld)", 337efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin item.mTimestamp, item.mFrameNumber); 338efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin } else { 339efb0fd232388b1f726c59f2ec20eea2d3ea8465dIgor Murashkin BI_LOGV("Unpinned buffer (timestamp %lld, framenumber %lld)", 340d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin item.mTimestamp, item.mFrameNumber); 341d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin } 342d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 343d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 344d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinstatus_t RingBufferConsumer::setDefaultBufferSize(uint32_t w, uint32_t h) { 345d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 346deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian return mConsumer->setDefaultBufferSize(w, h); 347d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 348d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 349d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinstatus_t RingBufferConsumer::setDefaultBufferFormat(uint32_t defaultFormat) { 350d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 351deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian return mConsumer->setDefaultBufferFormat(defaultFormat); 352d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 353d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 354d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkinstatus_t RingBufferConsumer::setConsumerUsage(uint32_t usage) { 355d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin Mutex::Autolock _l(mMutex); 356deeef54487a34034dc0cfaab20b20d557224c07cMathias Agopian return mConsumer->setConsumerUsageBits(usage); 357d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} 358d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin 359d4d5227521a53dec6f77bed33846b4ccd4a760e4Igor Murashkin} // namespace android 360