// Copyright (C) 2021 The Android Open Source Project // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. #include "ShaderCache.h" #include "aemu/base/MruCache.h" #include #include #include #include namespace { using BlobCacheType = std::vector; template class CacheObserver : android::base::MruCache::MruCacheObserver { public: int count = 0; CacheObserver(android::base::MruCache* cacheReference) { mCacheRef = cacheReference; cacheReference->setObserver(this); } void cacheChanged() override { // TODO: This will dictate when we flatten the cache. } private: android::base::MruCache* mCacheRef; }; template class CacheFlattener : public android::base::MruCache::CacheFlattener { using MruCache = std::map::template EntryWithSize, typename android::base::MruCache::template EntryWithSize>; public: void handleFlatten(MruCache &mCache, void* buf, size_t bufSize) { // TODO: This will handle the actual serialization. } }; CacheFlattener testFlattener; // 3200 is ~32MB of shaders, very rough estimate. android::base::MruCache mruCache(3200, &testFlattener); CacheObserver sss(&mruCache); } void SetBlob(const void* key, EGLsizeiANDROID keySize, const void* value, EGLsizeiANDROID valueSize) { std::vector keyVec(keySize); memcpy(keyVec.data(), key, keySize); std::vector valueVec(valueSize); memcpy(valueVec.data(), value, valueSize); mruCache.put(keyVec, keySize, std::move(valueVec), valueSize); } EGLsizeiANDROID GetBlob(const void* key, EGLsizeiANDROID keySize, void* value, EGLsizeiANDROID valueSize) { std::vector keyVec(keySize); memcpy(keyVec.data(), key, keySize); const std::vector *result; auto found = mruCache.get(keyVec, &result); if (!found) { return 0; } if (result->size() <= static_cast(valueSize)) { memcpy(value, result->data(), result->size()); } // If the size provided was too small, return the right size regardless. return result->size(); }