1 /*
2 * Copyright 2016, 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 #include <algorithm>
18
19 #include <media/omx/1.0/WOmxNode.h>
20 #include <media/omx/1.0/WOmxBufferSource.h>
21 #include <media/omx/1.0/Conversion.h>
22
23 namespace android {
24 namespace hardware {
25 namespace media {
26 namespace omx {
27 namespace V1_0 {
28 namespace utils {
29
30 using ::android::hardware::Void;
31
32 // LWOmxNode
freeNode()33 status_t LWOmxNode::freeNode() {
34 return toStatusT(mBase->freeNode());
35 }
36
sendCommand(OMX_COMMANDTYPE cmd,OMX_S32 param)37 status_t LWOmxNode::sendCommand(
38 OMX_COMMANDTYPE cmd, OMX_S32 param) {
39 return toStatusT(mBase->sendCommand(
40 toRawCommandType(cmd), param));
41 }
42
getParameter(OMX_INDEXTYPE index,void * params,size_t size)43 status_t LWOmxNode::getParameter(
44 OMX_INDEXTYPE index, void *params, size_t size) {
45 hidl_vec<uint8_t> tParams = inHidlBytes(params, size);
46 status_t fnStatus;
47 status_t transStatus = toStatusT(mBase->getParameter(
48 toRawIndexType(index),
49 tParams,
50 [&fnStatus, params](
51 Status status, hidl_vec<uint8_t> const& outParams) {
52 fnStatus = toStatusT(status);
53 std::copy(
54 outParams.data(),
55 outParams.data() + outParams.size(),
56 static_cast<uint8_t*>(params));
57 }));
58 return transStatus == NO_ERROR ? fnStatus : transStatus;
59 }
60
setParameter(OMX_INDEXTYPE index,const void * params,size_t size)61 status_t LWOmxNode::setParameter(
62 OMX_INDEXTYPE index, const void *params, size_t size) {
63 hidl_vec<uint8_t> tParams = inHidlBytes(params, size);
64 return toStatusT(mBase->setParameter(
65 toRawIndexType(index), tParams));
66 }
67
getConfig(OMX_INDEXTYPE index,void * params,size_t size)68 status_t LWOmxNode::getConfig(
69 OMX_INDEXTYPE index, void *params, size_t size) {
70 hidl_vec<uint8_t> tParams = inHidlBytes(params, size);
71 status_t fnStatus;
72 status_t transStatus = toStatusT(mBase->getConfig(
73 toRawIndexType(index),
74 tParams,
75 [&fnStatus, params, size](
76 Status status, hidl_vec<uint8_t> const& outParams) {
77 fnStatus = toStatusT(status);
78 std::copy(
79 outParams.data(),
80 outParams.data() + size,
81 static_cast<uint8_t*>(params));
82 }));
83 return transStatus == NO_ERROR ? fnStatus : transStatus;
84 }
85
setConfig(OMX_INDEXTYPE index,const void * params,size_t size)86 status_t LWOmxNode::setConfig(
87 OMX_INDEXTYPE index, const void *params, size_t size) {
88 hidl_vec<uint8_t> tParams = inHidlBytes(params, size);
89 return toStatusT(mBase->setConfig(toRawIndexType(index), tParams));
90 }
91
setPortMode(OMX_U32 port_index,IOMX::PortMode mode)92 status_t LWOmxNode::setPortMode(
93 OMX_U32 port_index, IOMX::PortMode mode) {
94 return toStatusT(mBase->setPortMode(port_index, toHardwarePortMode(mode)));
95 }
96
prepareForAdaptivePlayback(OMX_U32 portIndex,OMX_BOOL enable,OMX_U32 maxFrameWidth,OMX_U32 maxFrameHeight)97 status_t LWOmxNode::prepareForAdaptivePlayback(
98 OMX_U32 portIndex, OMX_BOOL enable,
99 OMX_U32 maxFrameWidth, OMX_U32 maxFrameHeight) {
100 return toStatusT(mBase->prepareForAdaptivePlayback(
101 portIndex, toRawBool(enable), maxFrameWidth, maxFrameHeight));
102 }
103
configureVideoTunnelMode(OMX_U32 portIndex,OMX_BOOL tunneled,OMX_U32 audioHwSync,native_handle_t ** sidebandHandle)104 status_t LWOmxNode::configureVideoTunnelMode(
105 OMX_U32 portIndex, OMX_BOOL tunneled,
106 OMX_U32 audioHwSync, native_handle_t **sidebandHandle) {
107 status_t fnStatus;
108 status_t transStatus = toStatusT(mBase->configureVideoTunnelMode(
109 portIndex,
110 toRawBool(tunneled),
111 audioHwSync,
112 [&fnStatus, sidebandHandle](
113 Status status, hidl_handle const& outSidebandHandle) {
114 fnStatus = toStatusT(status);
115 *sidebandHandle = outSidebandHandle == nullptr ?
116 nullptr : native_handle_clone(outSidebandHandle);
117 }));
118 return transStatus == NO_ERROR ? fnStatus : transStatus;
119 }
120
getGraphicBufferUsage(OMX_U32 portIndex,OMX_U32 * usage)121 status_t LWOmxNode::getGraphicBufferUsage(
122 OMX_U32 portIndex, OMX_U32* usage) {
123 status_t fnStatus;
124 status_t transStatus = toStatusT(mBase->getGraphicBufferUsage(
125 portIndex,
126 [&fnStatus, usage](
127 Status status, uint32_t outUsage) {
128 fnStatus = toStatusT(status);
129 *usage = outUsage;
130 }));
131 return transStatus == NO_ERROR ? fnStatus : transStatus;
132 }
133
setInputSurface(const sp<IOMXBufferSource> & bufferSource)134 status_t LWOmxNode::setInputSurface(
135 const sp<IOMXBufferSource> &bufferSource) {
136 return toStatusT(mBase->setInputSurface(
137 new TWOmxBufferSource(bufferSource)));
138 }
139
allocateSecureBuffer(OMX_U32 portIndex,size_t size,buffer_id * buffer,void ** buffer_data,sp<NativeHandle> * native_handle)140 status_t LWOmxNode::allocateSecureBuffer(
141 OMX_U32 portIndex, size_t size, buffer_id *buffer,
142 void **buffer_data, sp<NativeHandle> *native_handle) {
143 *buffer_data = nullptr;
144 status_t fnStatus;
145 status_t transStatus = toStatusT(mBase->allocateSecureBuffer(
146 portIndex,
147 static_cast<uint64_t>(size),
148 [&fnStatus, buffer, native_handle](
149 Status status,
150 uint32_t outBuffer,
151 hidl_handle const& outNativeHandle) {
152 fnStatus = toStatusT(status);
153 *buffer = outBuffer;
154 *native_handle = outNativeHandle.getNativeHandle() == nullptr ?
155 nullptr : NativeHandle::create(
156 native_handle_clone(outNativeHandle), true);
157 }));
158 return transStatus == NO_ERROR ? fnStatus : transStatus;
159 }
160
useBuffer(OMX_U32 portIndex,const OMXBuffer & omxBuffer,buffer_id * buffer)161 status_t LWOmxNode::useBuffer(
162 OMX_U32 portIndex, const OMXBuffer &omxBuffer, buffer_id *buffer) {
163 CodecBuffer codecBuffer;
164 if (!wrapAs(&codecBuffer, omxBuffer)) {
165 return BAD_VALUE;
166 }
167 status_t fnStatus;
168 status_t transStatus = toStatusT(mBase->useBuffer(
169 portIndex,
170 codecBuffer,
171 [&fnStatus, buffer](Status status, uint32_t outBuffer) {
172 fnStatus = toStatusT(status);
173 *buffer = outBuffer;
174 }));
175 return transStatus == NO_ERROR ? fnStatus : transStatus;
176 }
177
freeBuffer(OMX_U32 portIndex,buffer_id buffer)178 status_t LWOmxNode::freeBuffer(
179 OMX_U32 portIndex, buffer_id buffer) {
180 return toStatusT(mBase->freeBuffer(portIndex, buffer));
181 }
182
fillBuffer(buffer_id buffer,const OMXBuffer & omxBuffer,int fenceFd)183 status_t LWOmxNode::fillBuffer(
184 buffer_id buffer, const OMXBuffer &omxBuffer, int fenceFd) {
185 CodecBuffer codecBuffer;
186 if (!wrapAs(&codecBuffer, omxBuffer)) {
187 return BAD_VALUE;
188 }
189 native_handle_t* fenceNh = native_handle_create_from_fd(fenceFd);
190 if (!fenceNh) {
191 return NO_MEMORY;
192 }
193 status_t status = toStatusT(mBase->fillBuffer(
194 buffer, codecBuffer, fenceNh));
195 native_handle_close(fenceNh);
196 native_handle_delete(fenceNh);
197 return status;
198 }
199
emptyBuffer(buffer_id buffer,const OMXBuffer & omxBuffer,OMX_U32 flags,OMX_TICKS timestamp,int fenceFd)200 status_t LWOmxNode::emptyBuffer(
201 buffer_id buffer, const OMXBuffer &omxBuffer,
202 OMX_U32 flags, OMX_TICKS timestamp, int fenceFd) {
203 CodecBuffer codecBuffer;
204 if (!wrapAs(&codecBuffer, omxBuffer)) {
205 return BAD_VALUE;
206 }
207 native_handle_t* fenceNh = native_handle_create_from_fd(fenceFd);
208 if (!fenceNh) {
209 return NO_MEMORY;
210 }
211 status_t status = toStatusT(mBase->emptyBuffer(
212 buffer,
213 codecBuffer,
214 flags,
215 toRawTicks(timestamp),
216 fenceNh));
217 native_handle_close(fenceNh);
218 native_handle_delete(fenceNh);
219 return status;
220 }
getExtensionIndex(const char * parameter_name,OMX_INDEXTYPE * index)221 status_t LWOmxNode::getExtensionIndex(
222 const char *parameter_name,
223 OMX_INDEXTYPE *index) {
224 status_t fnStatus;
225 status_t transStatus = toStatusT(mBase->getExtensionIndex(
226 hidl_string(parameter_name),
227 [&fnStatus, index](Status status, uint32_t outIndex) {
228 fnStatus = toStatusT(status);
229 *index = toEnumIndexType(outIndex);
230 }));
231 return transStatus == NO_ERROR ? fnStatus : transStatus;
232 }
233
dispatchMessage(const omx_message & lMsg)234 status_t LWOmxNode::dispatchMessage(const omx_message &lMsg) {
235 Message tMsg;
236 native_handle_t* nh;
237 if (!wrapAs(&tMsg, &nh, lMsg)) {
238 return NO_MEMORY;
239 }
240 status_t status = toStatusT(mBase->dispatchMessage(tMsg));
241 native_handle_close(nh);
242 native_handle_delete(nh);
243 return status;
244 }
245
246 // TWOmxNode
TWOmxNode(sp<IOMXNode> const & base)247 TWOmxNode::TWOmxNode(sp<IOMXNode> const& base) : mBase(base) {
248 }
249
freeNode()250 Return<Status> TWOmxNode::freeNode() {
251 return toStatus(mBase->freeNode());
252 }
253
sendCommand(uint32_t cmd,int32_t param)254 Return<Status> TWOmxNode::sendCommand(uint32_t cmd, int32_t param) {
255 return toStatus(mBase->sendCommand(toEnumCommandType(cmd), param));
256 }
257
getParameter(uint32_t index,hidl_vec<uint8_t> const & inParams,getParameter_cb _hidl_cb)258 Return<void> TWOmxNode::getParameter(
259 uint32_t index, hidl_vec<uint8_t> const& inParams,
260 getParameter_cb _hidl_cb) {
261 hidl_vec<uint8_t> params(inParams);
262 Status status = toStatus(mBase->getParameter(
263 toEnumIndexType(index),
264 static_cast<void*>(params.data()),
265 params.size()));
266 _hidl_cb(status, params);
267 return Void();
268 }
269
setParameter(uint32_t index,hidl_vec<uint8_t> const & inParams)270 Return<Status> TWOmxNode::setParameter(
271 uint32_t index, hidl_vec<uint8_t> const& inParams) {
272 hidl_vec<uint8_t> params(inParams);
273 return toStatus(mBase->setParameter(
274 toEnumIndexType(index),
275 static_cast<void const*>(params.data()),
276 params.size()));
277 }
278
getConfig(uint32_t index,const hidl_vec<uint8_t> & inConfig,getConfig_cb _hidl_cb)279 Return<void> TWOmxNode::getConfig(
280 uint32_t index, const hidl_vec<uint8_t>& inConfig,
281 getConfig_cb _hidl_cb) {
282 hidl_vec<uint8_t> config(inConfig);
283 Status status = toStatus(mBase->getConfig(
284 toEnumIndexType(index),
285 static_cast<void*>(config.data()),
286 config.size()));
287 _hidl_cb(status, config);
288 return Void();
289 }
290
setConfig(uint32_t index,const hidl_vec<uint8_t> & inConfig)291 Return<Status> TWOmxNode::setConfig(
292 uint32_t index, const hidl_vec<uint8_t>& inConfig) {
293 hidl_vec<uint8_t> config(inConfig);
294 return toStatus(mBase->setConfig(
295 toEnumIndexType(index),
296 static_cast<void const*>(config.data()),
297 config.size()));
298 }
299
setPortMode(uint32_t portIndex,PortMode mode)300 Return<Status> TWOmxNode::setPortMode(uint32_t portIndex, PortMode mode) {
301 return toStatus(mBase->setPortMode(portIndex, toIOMXPortMode(mode)));
302 }
303
prepareForAdaptivePlayback(uint32_t portIndex,bool enable,uint32_t maxFrameWidth,uint32_t maxFrameHeight)304 Return<Status> TWOmxNode::prepareForAdaptivePlayback(
305 uint32_t portIndex, bool enable,
306 uint32_t maxFrameWidth, uint32_t maxFrameHeight) {
307 return toStatus(mBase->prepareForAdaptivePlayback(
308 portIndex,
309 toEnumBool(enable),
310 maxFrameWidth,
311 maxFrameHeight));
312 }
313
configureVideoTunnelMode(uint32_t portIndex,bool tunneled,uint32_t audioHwSync,configureVideoTunnelMode_cb _hidl_cb)314 Return<void> TWOmxNode::configureVideoTunnelMode(
315 uint32_t portIndex, bool tunneled, uint32_t audioHwSync,
316 configureVideoTunnelMode_cb _hidl_cb) {
317 native_handle_t* sidebandHandle = nullptr;
318 Status status = toStatus(mBase->configureVideoTunnelMode(
319 portIndex,
320 toEnumBool(tunneled),
321 audioHwSync,
322 &sidebandHandle));
323 _hidl_cb(status, hidl_handle(sidebandHandle));
324 return Void();
325 }
326
getGraphicBufferUsage(uint32_t portIndex,getGraphicBufferUsage_cb _hidl_cb)327 Return<void> TWOmxNode::getGraphicBufferUsage(
328 uint32_t portIndex, getGraphicBufferUsage_cb _hidl_cb) {
329 OMX_U32 usage;
330 Status status = toStatus(mBase->getGraphicBufferUsage(
331 portIndex, &usage));
332 _hidl_cb(status, usage);
333 return Void();
334 }
335
setInputSurface(const sp<IOmxBufferSource> & bufferSource)336 Return<Status> TWOmxNode::setInputSurface(
337 const sp<IOmxBufferSource>& bufferSource) {
338 return toStatus(mBase->setInputSurface(new LWOmxBufferSource(
339 bufferSource)));
340 }
341
allocateSecureBuffer(uint32_t portIndex,uint64_t size,allocateSecureBuffer_cb _hidl_cb)342 Return<void> TWOmxNode::allocateSecureBuffer(
343 uint32_t portIndex, uint64_t size,
344 allocateSecureBuffer_cb _hidl_cb) {
345 IOMX::buffer_id buffer;
346 void* bufferData;
347 sp<NativeHandle> nativeHandle;
348 Status status = toStatus(mBase->allocateSecureBuffer(
349 portIndex,
350 static_cast<size_t>(size),
351 &buffer,
352 &bufferData,
353 &nativeHandle));
354 _hidl_cb(status, buffer, nativeHandle == nullptr ?
355 nullptr : nativeHandle->handle());
356 return Void();
357 }
358
useBuffer(uint32_t portIndex,const CodecBuffer & codecBuffer,useBuffer_cb _hidl_cb)359 Return<void> TWOmxNode::useBuffer(
360 uint32_t portIndex, const CodecBuffer& codecBuffer,
361 useBuffer_cb _hidl_cb) {
362 IOMX::buffer_id buffer;
363 OMXBuffer omxBuffer;
364 if (!convertTo(&omxBuffer, codecBuffer)) {
365 _hidl_cb(Status::BAD_VALUE, 0);
366 return Void();
367 }
368 Status status = toStatus(mBase->useBuffer(
369 portIndex, omxBuffer, &buffer));
370 _hidl_cb(status, buffer);
371 return Void();
372 }
373
freeBuffer(uint32_t portIndex,uint32_t buffer)374 Return<Status> TWOmxNode::freeBuffer(uint32_t portIndex, uint32_t buffer) {
375 return toStatus(mBase->freeBuffer(portIndex, buffer));
376 }
377
fillBuffer(uint32_t buffer,const CodecBuffer & codecBuffer,const hidl_handle & fence)378 Return<Status> TWOmxNode::fillBuffer(
379 uint32_t buffer, const CodecBuffer& codecBuffer,
380 const hidl_handle& fence) {
381 OMXBuffer omxBuffer;
382 if (!convertTo(&omxBuffer, codecBuffer)) {
383 return Status::BAD_VALUE;
384 }
385 return toStatus(mBase->fillBuffer(
386 buffer,
387 omxBuffer,
388 dup(native_handle_read_fd(fence))));
389 }
390
emptyBuffer(uint32_t buffer,const CodecBuffer & codecBuffer,uint32_t flags,uint64_t timestampUs,const hidl_handle & fence)391 Return<Status> TWOmxNode::emptyBuffer(
392 uint32_t buffer, const CodecBuffer& codecBuffer, uint32_t flags,
393 uint64_t timestampUs, const hidl_handle& fence) {
394 OMXBuffer omxBuffer;
395 if (!convertTo(&omxBuffer, codecBuffer)) {
396 return Status::BAD_VALUE;
397 }
398 return toStatus(mBase->emptyBuffer(
399 buffer,
400 omxBuffer,
401 flags,
402 toOMXTicks(timestampUs),
403 dup(native_handle_read_fd(fence))));
404 }
405
getExtensionIndex(const hidl_string & parameterName,getExtensionIndex_cb _hidl_cb)406 Return<void> TWOmxNode::getExtensionIndex(
407 const hidl_string& parameterName,
408 getExtensionIndex_cb _hidl_cb) {
409 OMX_INDEXTYPE index;
410 Status status = toStatus(mBase->getExtensionIndex(
411 parameterName.c_str(), &index));
412 _hidl_cb(status, toRawIndexType(index));
413 return Void();
414 }
415
dispatchMessage(const Message & tMsg)416 Return<Status> TWOmxNode::dispatchMessage(const Message& tMsg) {
417 omx_message lMsg;
418 if (!convertTo(&lMsg, tMsg)) {
419 return Status::BAD_VALUE;
420 }
421 return toStatus(mBase->dispatchMessage(lMsg));
422 }
423
424 } // namespace utils
425 } // namespace V1_0
426 } // namespace omx
427 } // namespace media
428 } // namespace hardware
429 } // namespace android
430