blob: f0105b278276450e1add413eb20869d8290caabc [file] [log] [blame]
Chia-I Wuaaff73f2017-02-13 12:28:24 -08001/*
2 * Copyright (C) 2017 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
Lloyd Pique3b5a69e2020-01-16 17:51:01 -080017#include <compositionengine/impl/HwcBufferCache.h>
18
Chia-I Wuaaff73f2017-02-13 12:28:24 -080019#include <gui/BufferQueue.h>
Lloyd Pique76ed7032018-12-04 17:24:28 -080020#include <ui/GraphicBuffer.h>
Chia-I Wuaaff73f2017-02-13 12:28:24 -080021
Lloyd Pique76ed7032018-12-04 17:24:28 -080022namespace android::compositionengine::impl {
Chia-I Wuaaff73f2017-02-13 12:28:24 -080023
Lloyd Pique76ed7032018-12-04 17:24:28 -080024HwcBufferCache::HwcBufferCache() {
Brian Lindahl90553da2022-12-06 13:36:30 -070025 for (uint32_t i = kMaxLayerBufferCount; i-- > 0;) {
Brian Lindahl439afad2022-11-14 11:16:55 -070026 mFreeSlots.push(i);
27 }
Valerie Hau6f89c372019-03-02 00:13:33 +000028}
29
Brian Lindahl439afad2022-11-14 11:16:55 -070030HwcSlotAndBuffer HwcBufferCache::getHwcSlotAndBuffer(const sp<GraphicBuffer>& buffer) {
Brian Lindahl439afad2022-11-14 11:16:55 -070031 if (auto i = mCacheByBufferId.find(buffer->getId()); i != mCacheByBufferId.end()) {
32 Cache& cache = i->second;
33 // mark this cache slot as more recently used so it won't get evicted anytime soon
34 cache.lruCounter = mLeastRecentlyUsedCounter++;
35 return {cache.slot, nullptr};
Chia-I Wuaaff73f2017-02-13 12:28:24 -080036 }
Brian Lindahl439afad2022-11-14 11:16:55 -070037 return {cache(buffer), buffer};
38}
39
Brian Lindahlb158a5c2022-12-15 15:21:13 -070040HwcSlotAndBuffer HwcBufferCache::getOverrideHwcSlotAndBuffer(const sp<GraphicBuffer>& buffer) {
Brian Lindahl439afad2022-11-14 11:16:55 -070041 if (buffer == mLastOverrideBuffer) {
42 return {kOverrideBufferSlot, nullptr};
43 }
44 mLastOverrideBuffer = buffer;
45 return {kOverrideBufferSlot, buffer};
46}
47
48uint32_t HwcBufferCache::uncache(uint64_t bufferId) {
49 if (auto i = mCacheByBufferId.find(bufferId); i != mCacheByBufferId.end()) {
50 uint32_t slot = i->second.slot;
51 mCacheByBufferId.erase(i);
52 mFreeSlots.push(slot);
53 return slot;
54 }
55 if (mLastOverrideBuffer && bufferId == mLastOverrideBuffer->getId()) {
56 mLastOverrideBuffer = nullptr;
57 return kOverrideBufferSlot;
58 }
59 return UINT32_MAX;
60}
61
62uint32_t HwcBufferCache::cache(const sp<GraphicBuffer>& buffer) {
63 Cache cache;
64 cache.slot = getLeastRecentlyUsedSlot();
65 cache.lruCounter = mLeastRecentlyUsedCounter++;
66 cache.buffer = buffer;
67 mCacheByBufferId.emplace(buffer->getId(), cache);
68 return cache.slot;
69}
70
71uint32_t HwcBufferCache::getLeastRecentlyUsedSlot() {
72 if (mFreeSlots.empty()) {
73 assert(!mCacheByBufferId.empty());
74 // evict the least recently used cache entry
75 auto cacheToErase = mCacheByBufferId.begin();
76 for (auto i = cacheToErase; i != mCacheByBufferId.end(); ++i) {
77 if (i->second.lruCounter < cacheToErase->second.lruCounter) {
78 cacheToErase = i;
79 }
80 }
81 uint32_t slot = cacheToErase->second.slot;
82 mCacheByBufferId.erase(cacheToErase);
83 mFreeSlots.push(slot);
84 }
85 uint32_t slot = mFreeSlots.top();
86 mFreeSlots.pop();
87 return slot;
Chia-I Wuaaff73f2017-02-13 12:28:24 -080088}
89
Lloyd Pique76ed7032018-12-04 17:24:28 -080090} // namespace android::compositionengine::impl