1/* 2 * Copyright 2016 The Android Open Source Project 3 * * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16#define LOG_TAG "Gralloc0Mapper" 17 18#include "Gralloc0Mapper.h" 19 20#include <log/log.h> 21 22namespace android { 23namespace hardware { 24namespace graphics { 25namespace mapper { 26namespace V2_0 { 27namespace implementation { 28 29Gralloc0Mapper::Gralloc0Mapper(const hw_module_t* module) 30 : mModule(reinterpret_cast<const gralloc_module_t*>(module)), 31 mMinor(module->module_api_version & 0xff) { 32 mCapabilities.highUsageBits = false; 33 mCapabilities.layeredBuffers = false; 34 mCapabilities.unregisterImplyDelete = false; 35} 36 37Error Gralloc0Mapper::registerBuffer(buffer_handle_t bufferHandle) { 38 int result = mModule->registerBuffer(mModule, bufferHandle); 39 return result ? Error::BAD_BUFFER : Error::NONE; 40} 41 42void Gralloc0Mapper::unregisterBuffer(buffer_handle_t bufferHandle) { 43 mModule->unregisterBuffer(mModule, bufferHandle); 44} 45 46Error Gralloc0Mapper::lockBuffer(buffer_handle_t bufferHandle, 47 uint64_t cpuUsage, 48 const IMapper::Rect& accessRegion, int fenceFd, 49 void** outData) { 50 int result; 51 void* data = nullptr; 52 if (mMinor >= 3 && mModule->lockAsync) { 53 // Dup fenceFd as it is going to be owned by gralloc. Note that it is 54 // gralloc's responsibility to close it, even on locking errors. 55 if (fenceFd >= 0) { 56 fenceFd = dup(fenceFd); 57 if (fenceFd < 0) { 58 return Error::NO_RESOURCES; 59 } 60 } 61 62 result = mModule->lockAsync(mModule, bufferHandle, cpuUsage, 63 accessRegion.left, accessRegion.top, 64 accessRegion.width, accessRegion.height, 65 &data, fenceFd); 66 } else { 67 waitFenceFd(fenceFd, "Gralloc0Mapper::lock"); 68 69 result = mModule->lock(mModule, bufferHandle, cpuUsage, 70 accessRegion.left, accessRegion.top, 71 accessRegion.width, accessRegion.height, &data); 72 } 73 74 if (result) { 75 return Error::BAD_VALUE; 76 } else { 77 *outData = data; 78 return Error::NONE; 79 } 80} 81 82Error Gralloc0Mapper::lockBuffer(buffer_handle_t bufferHandle, 83 uint64_t cpuUsage, 84 const IMapper::Rect& accessRegion, int fenceFd, 85 YCbCrLayout* outLayout) { 86 int result; 87 android_ycbcr ycbcr = {}; 88 if (mMinor >= 3 && mModule->lockAsync_ycbcr) { 89 // Dup fenceFd as it is going to be owned by gralloc. Note that it is 90 // gralloc's responsibility to close it, even on locking errors. 91 if (fenceFd >= 0) { 92 fenceFd = dup(fenceFd); 93 if (fenceFd < 0) { 94 return Error::NO_RESOURCES; 95 } 96 } 97 98 result = mModule->lockAsync_ycbcr(mModule, bufferHandle, cpuUsage, 99 accessRegion.left, accessRegion.top, 100 accessRegion.width, 101 accessRegion.height, &ycbcr, fenceFd); 102 } else { 103 waitFenceFd(fenceFd, "Gralloc0Mapper::lockYCbCr"); 104 105 if (mModule->lock_ycbcr) { 106 result = mModule->lock_ycbcr(mModule, bufferHandle, cpuUsage, 107 accessRegion.left, accessRegion.top, 108 accessRegion.width, 109 accessRegion.height, &ycbcr); 110 } else { 111 result = -EINVAL; 112 } 113 } 114 115 if (result) { 116 return Error::BAD_VALUE; 117 } else { 118 outLayout->y = ycbcr.y; 119 outLayout->cb = ycbcr.cb; 120 outLayout->cr = ycbcr.cr; 121 outLayout->yStride = ycbcr.ystride; 122 outLayout->cStride = ycbcr.cstride; 123 outLayout->chromaStep = ycbcr.chroma_step; 124 return Error::NONE; 125 } 126} 127 128Error Gralloc0Mapper::unlockBuffer(buffer_handle_t bufferHandle, 129 int* outFenceFd) { 130 int result; 131 int fenceFd = -1; 132 if (mMinor >= 3 && mModule->unlockAsync) { 133 result = mModule->unlockAsync(mModule, bufferHandle, &fenceFd); 134 } else { 135 result = mModule->unlock(mModule, bufferHandle); 136 } 137 138 if (result) { 139 // we always own the fenceFd even when unlock failed 140 if (fenceFd >= 0) { 141 close(fenceFd); 142 } 143 144 return Error::BAD_VALUE; 145 } else { 146 *outFenceFd = fenceFd; 147 return Error::NONE; 148 } 149} 150 151} // namespace implementation 152} // namespace V2_0 153} // namespace mapper 154} // namespace graphics 155} // namespace hardware 156} // namespace android 157