blob: e0395939e94609cdd905593fd9279539fb870314 [file] [log] [blame]
Pawin Vongmasae672cd02019-02-14 16:01:29 -08001/*
2 * Copyright 2019 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//#define LOG_NDEBUG 0
18#define LOG_TAG "H2BGraphicBufferProducer@2.0"
19
20#include <android-base/logging.h>
21
22#include <android/hardware/graphics/bufferqueue/2.0/types.h>
23#include <android/hardware/graphics/common/1.2/types.h>
24#include <gui/bufferqueue/2.0/H2BProducerListener.h>
25#include <gui/bufferqueue/2.0/B2HGraphicBufferProducer.h>
26#include <gui/bufferqueue/2.0/types.h>
27#include <ui/GraphicBuffer.h>
28#include <ui/Rect.h>
29#include <ui/Region.h>
30#include <vndk/hardware_buffer.h>
31
32namespace android {
33
34namespace hardware {
35namespace graphics {
36namespace bufferqueue {
37namespace V2_0 {
38namespace utils {
39
40// B2HGraphicBufferProducer
41// ========================
42
43B2HGraphicBufferProducer::B2HGraphicBufferProducer(
44 sp<BGraphicBufferProducer> const& base)
45 : mBase{base} {
46}
47
48Return<HStatus> B2HGraphicBufferProducer::setMaxDequeuedBufferCount(
49 int32_t maxDequeuedBuffers) {
50 HStatus hStatus{};
51 bool converted = b2h(
52 mBase->setMaxDequeuedBufferCount(
53 static_cast<int>(maxDequeuedBuffers)),
54 &hStatus);
55 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
56}
57
58Return<void> B2HGraphicBufferProducer::requestBuffer(
59 int32_t slot,
60 requestBuffer_cb _hidl_cb) {
61 sp<GraphicBuffer> bBuffer;
62 HStatus hStatus{};
63 HardwareBuffer hBuffer{};
64 uint32_t hGenerationNumber{};
65 bool converted =
66 b2h(mBase->requestBuffer(
67 static_cast<int>(slot), &bBuffer),
68 &hStatus) &&
69 b2h(bBuffer, &hBuffer, &hGenerationNumber);
70 _hidl_cb(converted ? hStatus : HStatus::UNKNOWN_ERROR,
71 hBuffer, hGenerationNumber);
72 return {};
73}
74
75Return<HStatus> B2HGraphicBufferProducer::setAsyncMode(bool async) {
76 HStatus hStatus{};
77 bool converted = b2h(mBase->setAsyncMode(async), &hStatus);
78 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
79}
80
81Return<void> B2HGraphicBufferProducer::dequeueBuffer(
82 DequeueBufferInput const& input,
83 dequeueBuffer_cb _hidl_cb) {
84 int bSlot{};
85 sp<BFence> bFence;
86 HStatus hStatus{};
87 DequeueBufferOutput hOutput{};
88 HFenceWrapper hFenceWrapper;
89 bool converted =
90 b2h(mBase->dequeueBuffer(
91 &bSlot,
92 &bFence,
93 input.width,
94 input.height,
95 static_cast<PixelFormat>(input.format),
96 input.usage,
97 &hOutput.bufferAge,
98 nullptr /* outTimestamps */),
99 &hStatus,
100 &hOutput.bufferNeedsReallocation,
101 &hOutput.releaseAllBuffers) &&
102 b2h(bFence, &hFenceWrapper);
103 hOutput.fence = hFenceWrapper.getHandle();
104 _hidl_cb(converted ? hStatus : HStatus::UNKNOWN_ERROR,
105 static_cast<int32_t>(bSlot),
106 hOutput);
107 return {};
108}
109
110Return<HStatus> B2HGraphicBufferProducer::detachBuffer(int32_t slot) {
111 HStatus hStatus{};
112 bool converted = b2h(
113 mBase->detachBuffer(static_cast<int>(slot)), &hStatus);
114 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
115}
116
117Return<void> B2HGraphicBufferProducer::detachNextBuffer(
118 detachNextBuffer_cb _hidl_cb) {
119 sp<GraphicBuffer> bBuffer;
120 sp<BFence> bFence;
121 HStatus hStatus{};
122 HardwareBuffer hBuffer{};
123 HFenceWrapper hFenceWrapper;
124 bool converted =
125 b2h(mBase->detachNextBuffer(&bBuffer, &bFence), &hStatus) &&
126 b2h(bBuffer, &hBuffer) &&
127 b2h(bFence, &hFenceWrapper);
128 _hidl_cb(converted ? hStatus : HStatus::UNKNOWN_ERROR,
129 hBuffer,
130 hFenceWrapper.getHandle());
131 return {};
132}
133
134Return<void> B2HGraphicBufferProducer::attachBuffer(
135 HardwareBuffer const& hBuffer,
136 uint32_t generationNumber,
137 attachBuffer_cb _hidl_cb) {
138 sp<GraphicBuffer> bBuffer;
139 if (!h2b(hBuffer, &bBuffer) || !bBuffer) {
140 _hidl_cb(HStatus::UNKNOWN_ERROR,
141 static_cast<int32_t>(SlotIndex::INVALID),
142 false);
143 return {};
144 }
145 bBuffer->setGenerationNumber(generationNumber);
146
147 int bSlot{};
148 HStatus hStatus{};
149 bool releaseAllBuffers{};
150 bool converted = b2h(
151 mBase->attachBuffer(&bSlot, bBuffer), &hStatus,
152 nullptr /* bufferNeedsReallocation */,
153 &releaseAllBuffers);
154 _hidl_cb(converted ? hStatus : HStatus::UNKNOWN_ERROR,
155 static_cast<int32_t>(bSlot),
156 releaseAllBuffers);
157 return {};
158}
159
160Return<void> B2HGraphicBufferProducer::queueBuffer(
161 int32_t slot,
162 QueueBufferInput const& hInput,
163 queueBuffer_cb _hidl_cb) {
164 using HOutput = QueueBufferOutput;
165 using BInput = BGraphicBufferProducer::QueueBufferInput;
166 using BOutput = BGraphicBufferProducer::QueueBufferOutput;
167
168 BInput bInput{
169 hInput.timestamp,
170 hInput.isAutoTimestamp,
171 static_cast<android_dataspace>(hInput.dataSpace),
172 {}, /* crop */
173 0 /* scalingMode = NATIVE_WINDOW_SCALING_MODE_FREEZE */,
174 static_cast<uint32_t>(hInput.transform),
175 {}, /* fence */
176 static_cast<uint32_t>(hInput.stickyTransform),
177 false /* getFrameTimestamps */};
178
179 // Convert crop.
180 if (!h2b(hInput.crop, &bInput.crop)) {
181 _hidl_cb(HStatus::UNKNOWN_ERROR, HOutput{});
182 return {};
183 }
184
185 // Convert surfaceDamage.
186 if (!h2b(hInput.surfaceDamage, &bInput.surfaceDamage)) {
187 _hidl_cb(HStatus::UNKNOWN_ERROR, HOutput{});
188 return {};
189 }
190
191 // Convert fence.
192 if (!h2b(hInput.fence, &bInput.fence)) {
193 _hidl_cb(HStatus::UNKNOWN_ERROR, HOutput{});
194 return {};
195 }
196
197 BOutput bOutput{};
198 HStatus hStatus{};
199 bool converted = b2h(
200 mBase->queueBuffer(static_cast<int>(slot), bInput, &bOutput),
201 &hStatus);
202
203 _hidl_cb(converted ? hStatus : HStatus::UNKNOWN_ERROR,
204 HOutput{bOutput.width,
205 bOutput.height,
206 static_cast<int32_t>(bOutput.transformHint),
207 bOutput.numPendingBuffers,
208 bOutput.nextFrameNumber,
209 bOutput.bufferReplaced});
210 return {};
211}
212
213Return<HStatus> B2HGraphicBufferProducer::cancelBuffer(
214 int32_t slot,
215 hidl_handle const& fence) {
216 sp<BFence> bFence;
217 if (!h2b(fence.getNativeHandle(), &bFence)) {
218 return {HStatus::UNKNOWN_ERROR};
219 }
220 HStatus hStatus{};
221 bool converted = b2h(
222 mBase->cancelBuffer(static_cast<int>(slot), bFence),
223 &hStatus);
224 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
225}
226
227Return<void> B2HGraphicBufferProducer::query(int32_t what, query_cb _hidl_cb) {
228 int value{};
229 int result = mBase->query(static_cast<int>(what), &value);
230 _hidl_cb(static_cast<int32_t>(result), static_cast<int32_t>(value));
231 return {};
232}
233
234Return<void> B2HGraphicBufferProducer::connect(
235 sp<HProducerListener> const& hListener,
236 HConnectionType hConnectionType,
237 bool producerControlledByApp,
238 connect_cb _hidl_cb) {
239 using BOutput = BGraphicBufferProducer::QueueBufferOutput;
240 using HOutput = HGraphicBufferProducer::QueueBufferOutput;
241 sp<BProducerListener> bListener = new H2BProducerListener(hListener);
242 if (!bListener) {
243 _hidl_cb(HStatus::UNKNOWN_ERROR, HOutput{});
244 return {};
245 }
246 int bConnectionType;
247 if (!h2b(hConnectionType, &bConnectionType)) {
248 _hidl_cb(HStatus::UNKNOWN_ERROR, HOutput{});
249 return {};
250 }
251 BOutput bOutput{};
252 HStatus hStatus{};
253 bool converted = b2h(
254 mBase->connect(bListener,
255 bConnectionType,
256 producerControlledByApp,
257 &bOutput),
258 &hStatus);
259 _hidl_cb(converted ? hStatus : HStatus::UNKNOWN_ERROR,
260 HOutput{bOutput.width,
261 bOutput.height,
262 static_cast<int32_t>(bOutput.transformHint),
263 bOutput.numPendingBuffers,
264 bOutput.nextFrameNumber,
265 bOutput.bufferReplaced});
266 return {};
267}
268
269Return<HStatus> B2HGraphicBufferProducer::disconnect(
270 HConnectionType hConnectionType) {
271 int bConnectionType;
272 if (!h2b(hConnectionType, &bConnectionType)) {
273 return {HStatus::UNKNOWN_ERROR};
274 }
275 HStatus hStatus{};
276 bool converted = b2h(mBase->disconnect(bConnectionType), &hStatus);
277 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
278}
279
280Return<HStatus> B2HGraphicBufferProducer::allocateBuffers(
281 uint32_t width, uint32_t height,
282 uint32_t format, uint64_t usage) {
283 mBase->allocateBuffers(
284 width, height, static_cast<PixelFormat>(format), usage);
285 return {HStatus::OK};
286}
287
288Return<HStatus> B2HGraphicBufferProducer::allowAllocation(bool allow) {
289 HStatus hStatus{};
290 bool converted = b2h(mBase->allowAllocation(allow), &hStatus);
291 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
292}
293
294Return<HStatus> B2HGraphicBufferProducer::setGenerationNumber(
295 uint32_t generationNumber) {
296 HStatus hStatus{};
297 bool converted = b2h(
298 mBase->setGenerationNumber(generationNumber),
299 &hStatus);
300 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
301}
302
303Return<HStatus> B2HGraphicBufferProducer::setDequeueTimeout(
304 int64_t timeoutNs) {
305 HStatus hStatus{};
306 bool converted = b2h(
307 mBase->setDequeueTimeout(static_cast<nsecs_t>(timeoutNs)),
308 &hStatus);
309 return {converted ? hStatus : HStatus::UNKNOWN_ERROR};
310}
311
312Return<uint64_t> B2HGraphicBufferProducer::getUniqueId() {
313 uint64_t outId{};
314 HStatus hStatus{};
315 bool converted = b2h(mBase->getUniqueId(&outId), &hStatus);
316 return {converted ? outId : 0};
317}
318
319Return<void> B2HGraphicBufferProducer::getConsumerName(
320 getConsumerName_cb _hidl_cb) {
321 _hidl_cb(hidl_string{mBase->getConsumerName().c_str()});
322 return {};
323}
324
325} // namespace utils
326} // namespace V2_0
327} // namespace bufferqueue
328} // namespace graphics
329} // namespace hardware
330} // namespace android
331