blob: 0cc70a1d3049c30a4c27ddfb61f08421cfb0491b [file] [log] [blame]
Yin-Chia Yeh248ed702017-01-23 17:27:26 -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
17#define LOG_TAG "CamDev@1.0-impl"
18#include <utils/Log.h>
19#include <hardware/camera.h>
20#include <hardware/gralloc1.h>
21#include <utils/Trace.h>
22
Eino-Ville Talvala2d80c0d2017-03-23 15:39:12 -070023#include <grallocusage/GrallocUsageConversion.h>
24
Yin-Chia Yeh248ed702017-01-23 17:27:26 -080025#include "CameraDevice_1_0.h"
26
27namespace android {
28namespace hardware {
29namespace camera {
30namespace device {
31namespace V1_0 {
32namespace implementation {
33
Yin-Chia Yeh248ed702017-01-23 17:27:26 -080034using ::android::hardware::graphics::common::V1_0::PixelFormat;
35
36HandleImporter& CameraDevice::sHandleImporter = HandleImporter::getInstance();
37
38Status CameraDevice::getHidlStatus(const int& status) {
39 switch (status) {
40 case 0: return Status::OK;
41 case -ENOSYS: return Status::OPERATION_NOT_SUPPORTED;
42 case -EBUSY : return Status::CAMERA_IN_USE;
43 case -EUSERS: return Status::MAX_CAMERAS_IN_USE;
44 case -ENODEV: return Status::INTERNAL_ERROR;
45 case -EINVAL: return Status::ILLEGAL_ARGUMENT;
46 default:
47 ALOGE("%s: unknown HAL status code %d", __FUNCTION__, status);
48 return Status::INTERNAL_ERROR;
49 }
50}
51
52status_t CameraDevice::getStatusT(const Status& s) {
53 switch(s) {
54 case Status::OK:
55 return OK;
56 case Status::ILLEGAL_ARGUMENT:
57 return BAD_VALUE;
58 case Status::CAMERA_IN_USE:
59 return -EBUSY;
60 case Status::MAX_CAMERAS_IN_USE:
61 return -EUSERS;
62 case Status::METHOD_NOT_SUPPORTED:
63 return UNKNOWN_TRANSACTION;
64 case Status::OPERATION_NOT_SUPPORTED:
65 return INVALID_OPERATION;
66 case Status::CAMERA_DISCONNECTED:
67 return DEAD_OBJECT;
68 case Status::INTERNAL_ERROR:
69 return INVALID_OPERATION;
70 }
71 ALOGW("Unexpected HAL status code %d", s);
72 return INVALID_OPERATION;
73}
74
75Status CameraDevice::initStatus() const {
76 Mutex::Autolock _l(mLock);
77 Status status = Status::OK;
78 if (mInitFail) {
79 status = Status::INTERNAL_ERROR;
80 } else if (mDisconnected) {
81 status = Status::CAMERA_DISCONNECTED;
82 }
83 return status;
84}
85
86CameraDevice::CameraDevice(
87 sp<CameraModule> module, const std::string& cameraId,
88 const SortedVector<std::pair<std::string, std::string>>& cameraDeviceNames) :
89 mModule(module),
90 mCameraId(cameraId),
91 mDisconnected(false),
92 mCameraDeviceNames(cameraDeviceNames) {
93 mCameraIdInt = atoi(mCameraId.c_str());
94 // Should not reach here as provider also validate ID
95 if (mCameraIdInt < 0 || mCameraIdInt >= module->getNumberOfCameras()) {
96 ALOGE("%s: Invalid camera id: %s", __FUNCTION__, mCameraId.c_str());
97 mInitFail = true;
98 }
99
100 mDeviceVersion = mModule->getDeviceVersion(mCameraIdInt);
101 if (mDeviceVersion != CAMERA_DEVICE_API_VERSION_1_0 && !mModule->isOpenLegacyDefined()) {
102 ALOGI("%s: Camera id %s does not support HAL1.0",
103 __FUNCTION__, mCameraId.c_str());
104 mInitFail = true;
105 }
106}
107
108CameraDevice::~CameraDevice() {
109 Mutex::Autolock _l(mLock);
110 if (mDevice != nullptr) {
111 ALOGW("%s: camera %s is deleted while open", __FUNCTION__, mCameraId.c_str());
112 close();
113 }
114 mHalPreviewWindow.cleanUpCirculatingBuffers();
115}
116
117
118void CameraDevice::setConnectionStatus(bool connected) {
119 Mutex::Autolock _l(mLock);
120 mDisconnected = !connected;
121 if (mDevice == nullptr) {
122 return;
123 }
124 if (!connected) {
125 ALOGW("%s: camera %s is disconneted. Closing", __FUNCTION__, mCameraId.c_str());
126 close();
127 }
128 return;
129}
130
131void CameraDevice::CameraPreviewWindow::cleanUpCirculatingBuffers() {
132 Mutex::Autolock _l(mLock);
133 for (auto pair : mCirculatingBuffers) {
134 sHandleImporter.freeBuffer(pair.second);
135 }
136 mCirculatingBuffers.clear();
137 mBufferIdMap.clear();
138}
139
140int CameraDevice::sDequeueBuffer(struct preview_stream_ops* w,
141 buffer_handle_t** buffer, int *stride) {
142 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
143 if (object->mPreviewCallback == nullptr) {
144 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
145 return INVALID_OPERATION;
146 }
147
148 if (buffer == nullptr || stride == nullptr) {
149 ALOGE("%s: buffer (%p) and stride (%p) must not be null!", __FUNCTION__, buffer, stride);
150 return BAD_VALUE;
151 }
152
153 Status s;
154 object->mPreviewCallback->dequeueBuffer(
155 [&](auto status, uint64_t bufferId, const auto& buf, uint32_t strd) {
156 s = status;
157 if (s == Status::OK) {
158 Mutex::Autolock _l(object->mLock);
159 if (object->mCirculatingBuffers.count(bufferId) == 0) {
160 buffer_handle_t importedBuf = buf.getNativeHandle();
161 sHandleImporter.importBuffer(importedBuf);
162 if (importedBuf == nullptr) {
163 ALOGE("%s: preview buffer import failed!", __FUNCTION__);
164 s = Status::INTERNAL_ERROR;
165 return;
166 } else {
167 object->mCirculatingBuffers[bufferId] = importedBuf;
168 object->mBufferIdMap[&(object->mCirculatingBuffers[bufferId])] = bufferId;
169 }
170 }
171 *buffer = &(object->mCirculatingBuffers[bufferId]);
172 *stride = strd;
173 }
174 });
175 return getStatusT(s);
176}
177
178int CameraDevice::sLockBuffer(struct preview_stream_ops*, buffer_handle_t*) {
179 // TODO: make sure lock_buffer is indeed a no-op (and will always be)
180 return 0;
181}
182
183int CameraDevice::sEnqueueBuffer(struct preview_stream_ops* w, buffer_handle_t* buffer) {
184 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
185 if (object->mPreviewCallback == nullptr) {
186 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
187 return INVALID_OPERATION;
188 }
189 uint64_t bufferId = object->mBufferIdMap.at(buffer);
190 return getStatusT(object->mPreviewCallback->enqueueBuffer(bufferId));
191}
192
193int CameraDevice::sCancelBuffer(struct preview_stream_ops* w, buffer_handle_t* buffer) {
194 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
195 if (object->mPreviewCallback == nullptr) {
196 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
197 return INVALID_OPERATION;
198 }
199 uint64_t bufferId = object->mBufferIdMap.at(buffer);
200 return getStatusT(object->mPreviewCallback->cancelBuffer(bufferId));
201}
202
203int CameraDevice::sSetBufferCount(struct preview_stream_ops* w, int count) {
204 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
205 if (object->mPreviewCallback == nullptr) {
206 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
207 return INVALID_OPERATION;
208 }
209
210 object->cleanUpCirculatingBuffers();
211 return getStatusT(object->mPreviewCallback->setBufferCount(count));
212}
213
214int CameraDevice::sSetBuffersGeometry(struct preview_stream_ops* w,
215 int width, int height, int format) {
216 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
217 if (object->mPreviewCallback == nullptr) {
218 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
219 return INVALID_OPERATION;
220 }
221
222 object->cleanUpCirculatingBuffers();
223 return getStatusT(
224 object->mPreviewCallback->setBuffersGeometry(width, height, (PixelFormat) format));
225}
226
227int CameraDevice::sSetCrop(struct preview_stream_ops *w,
228 int left, int top, int right, int bottom) {
229 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
230 if (object->mPreviewCallback == nullptr) {
231 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
232 return INVALID_OPERATION;
233 }
234
235 return getStatusT(object->mPreviewCallback->setCrop(left, top, right, bottom));
236}
237
238int CameraDevice::sSetTimestamp(struct preview_stream_ops *w, int64_t timestamp) {
239 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
240 if (object->mPreviewCallback == nullptr) {
241 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
242 return INVALID_OPERATION;
243 }
244
245 return getStatusT(object->mPreviewCallback->setTimestamp(timestamp));
246}
247
248int CameraDevice::sSetUsage(struct preview_stream_ops* w, int usage) {
249 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
250 if (object->mPreviewCallback == nullptr) {
251 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
252 return INVALID_OPERATION;
253 }
254
255 object->cleanUpCirculatingBuffers();
Eino-Ville Talvala2d80c0d2017-03-23 15:39:12 -0700256 ProducerUsageFlags producerUsage;
257 uint64_t consumerUsage;
258 ::android_convertGralloc0To1Usage(usage, &producerUsage, &consumerUsage);
259 return getStatusT(object->mPreviewCallback->setUsage(producerUsage));
Yin-Chia Yeh248ed702017-01-23 17:27:26 -0800260}
261
262int CameraDevice::sSetSwapInterval(struct preview_stream_ops *w, int interval) {
263 CameraPreviewWindow* object = static_cast<CameraPreviewWindow*>(w);
264 if (object->mPreviewCallback == nullptr) {
265 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
266 return INVALID_OPERATION;
267 }
268
269 return getStatusT(object->mPreviewCallback->setSwapInterval(interval));
270}
271
272int CameraDevice::sGetMinUndequeuedBufferCount(
273 const struct preview_stream_ops *w,
274 int *count) {
275 const CameraPreviewWindow* object = static_cast<const CameraPreviewWindow*>(w);
276 if (object->mPreviewCallback == nullptr) {
277 ALOGE("%s: camera HAL calling preview ops while there is no preview window!", __FUNCTION__);
278 return INVALID_OPERATION;
279 }
280 if (count == nullptr) {
281 ALOGE("%s: count is null!", __FUNCTION__);
282 return BAD_VALUE;
283 }
284
285 Status s;
286 object->mPreviewCallback->getMinUndequeuedBufferCount(
287 [&](auto status, uint32_t cnt) {
288 s = status;
289 if (s == Status::OK) {
290 *count = cnt;
291 }
292 });
293 return getStatusT(s);
294}
295
296CameraDevice::CameraHeapMemory::CameraHeapMemory(int fd, size_t buf_size, uint_t num_buffers) :
297 mBufSize(buf_size),
298 mNumBufs(num_buffers) {
299 mHeap = new MemoryHeapBase(fd, buf_size * num_buffers);
300 commonInitialization();
301}
302
303CameraDevice::CameraHeapMemory::CameraHeapMemory(size_t buf_size, uint_t num_buffers) :
304 mBufSize(buf_size),
305 mNumBufs(num_buffers) {
306 mHeap = new MemoryHeapBase(buf_size * num_buffers);
307 commonInitialization();
308}
309
310void CameraDevice::CameraHeapMemory::commonInitialization() {
311 handle.data = mHeap->base();
312 handle.size = mBufSize * mNumBufs;
313 handle.handle = this;
314
315 mBuffers = new sp<MemoryBase>[mNumBufs];
316 for (uint_t i = 0; i < mNumBufs; i++) {
317 mBuffers[i] = new MemoryBase(mHeap, i * mBufSize, mBufSize);
318 }
319
320 handle.release = sPutMemory;
321}
322
323CameraDevice::CameraHeapMemory::~CameraHeapMemory() {
324 delete [] mBuffers;
325}
326
327// shared memory methods
328camera_memory_t* CameraDevice::sGetMemory(int fd, size_t buf_size, uint_t num_bufs, void *user) {
329 ALOGV("%s", __FUNCTION__);
330 CameraDevice* object = static_cast<CameraDevice*>(user);
331 if (object->mDeviceCallback == nullptr) {
332 ALOGE("%s: camera HAL request memory while camera is not opened!", __FUNCTION__);
333 return nullptr;
334 }
335
336 CameraHeapMemory* mem;
337 native_handle_t* handle = native_handle_create(1,0);
338
339 if (handle == nullptr) {
340 ALOGE("%s: native_handle_create failed!", __FUNCTION__);
341 return nullptr;
342 }
343
344 if (fd < 0) {
345 mem = new CameraHeapMemory(buf_size, num_bufs);
346 } else {
347 mem = new CameraHeapMemory(fd, buf_size, num_bufs);
348 }
349 handle->data[0] = mem->mHeap->getHeapID();
350 mem->incStrong(mem);
351
352 hidl_handle hidlHandle = handle;
353 MemoryId id = object->mDeviceCallback->registerMemory(hidlHandle, buf_size, num_bufs);
354 mem->handle.mId = id;
355 if (object->mMemoryMap.count(id) != 0) {
356 ALOGE("%s: duplicate MemoryId %d returned by client!", __FUNCTION__, id);
357 }
358 object->mMemoryMap[id] = mem;
359 mem->handle.mDevice = object;
360 native_handle_delete(handle);
361 return &mem->handle;
362}
363
364void CameraDevice::sPutMemory(camera_memory_t *data) {
365 if (!data)
366 return;
367
368 CameraHeapMemory* mem = static_cast<CameraHeapMemory *>(data->handle);
369 CameraDevice* device = mem->handle.mDevice;
370 if (device == nullptr) {
371 ALOGE("%s: camera HAL return memory for a null device!", __FUNCTION__);
372 }
373 if (device->mDeviceCallback == nullptr) {
374 ALOGE("%s: camera HAL return memory while camera is not opened!", __FUNCTION__);
375 }
376 device->mDeviceCallback->unregisterMemory(mem->handle.mId);
377 device->mMemoryMap.erase(mem->handle.mId);
378 mem->decStrong(mem);
379}
380
381// Callback forwarding methods
382void CameraDevice::sNotifyCb(int32_t msg_type, int32_t ext1, int32_t ext2, void *user) {
383 ALOGV("%s", __FUNCTION__);
384 CameraDevice* object = static_cast<CameraDevice*>(user);
385 if (object->mDeviceCallback != nullptr) {
386 object->mDeviceCallback->notifyCallback((NotifyCallbackMsg) msg_type, ext1, ext2);
387 }
388}
389
390void CameraDevice::sDataCb(int32_t msg_type, const camera_memory_t *data, unsigned int index,
391 camera_frame_metadata_t *metadata, void *user) {
392 ALOGV("%s", __FUNCTION__);
393 CameraDevice* object = static_cast<CameraDevice*>(user);
394 sp<CameraHeapMemory> mem(static_cast<CameraHeapMemory*>(data->handle));
395 if (index >= mem->mNumBufs) {
396 ALOGE("%s: invalid buffer index %d, max allowed is %d", __FUNCTION__,
397 index, mem->mNumBufs);
398 return;
399 }
400 if (object->mDeviceCallback != nullptr) {
401 CameraFrameMetadata hidlMetadata;
402 if (metadata) {
403 hidlMetadata.faces.resize(metadata->number_of_faces);
404 for (size_t i = 0; i < hidlMetadata.faces.size(); i++) {
405 hidlMetadata.faces[i].score = metadata->faces[i].score;
406 hidlMetadata.faces[i].id = metadata->faces[i].id;
407 for (int k = 0; k < 4; k++) {
408 hidlMetadata.faces[i].rect[k] = metadata->faces[i].rect[k];
409 }
410 for (int k = 0; k < 2; k++) {
411 hidlMetadata.faces[i].leftEye[k] = metadata->faces[i].left_eye[k];
412 }
413 for (int k = 0; k < 2; k++) {
414 hidlMetadata.faces[i].rightEye[k] = metadata->faces[i].right_eye[k];
415 }
416 for (int k = 0; k < 2; k++) {
417 hidlMetadata.faces[i].mouth[k] = metadata->faces[i].mouth[k];
418 }
419 }
420 }
421 CameraHeapMemory* mem = static_cast<CameraHeapMemory *>(data->handle);
422 object->mDeviceCallback->dataCallback(
423 (DataCallbackMsg) msg_type, mem->handle.mId, index, hidlMetadata);
424 }
425}
426
427void CameraDevice::sDataCbTimestamp(nsecs_t timestamp, int32_t msg_type,
428 const camera_memory_t *data, unsigned index, void *user) {
429 ALOGV("%s", __FUNCTION__);
430 CameraDevice* object = static_cast<CameraDevice*>(user);
431 // Start refcounting the heap object from here on. When the clients
432 // drop all references, it will be destroyed (as well as the enclosed
433 // MemoryHeapBase.
434 sp<CameraHeapMemory> mem(static_cast<CameraHeapMemory*>(data->handle));
435 if (index >= mem->mNumBufs) {
436 ALOGE("%s: invalid buffer index %d, max allowed is %d", __FUNCTION__,
437 index, mem->mNumBufs);
438 return;
439 }
440
441 native_handle_t* handle = nullptr;
442 if (object->mMetadataMode) {
443 if (mem->mBufSize == sizeof(VideoNativeHandleMetadata)) {
444 VideoNativeHandleMetadata* md = (VideoNativeHandleMetadata*)
445 mem->mBuffers[index]->pointer();
446 if (md->eType == VideoNativeHandleMetadata::kMetadataBufferTypeNativeHandleSource) {
447 handle = md->pHandle;
448 }
449 }
450 }
451
452 if (object->mDeviceCallback != nullptr) {
453 if (handle == nullptr) {
454 object->mDeviceCallback->dataCallbackTimestamp(
455 (DataCallbackMsg) msg_type, mem->handle.mId, index, timestamp);
456 } else {
457 object->mDeviceCallback->handleCallbackTimestamp(
458 (DataCallbackMsg) msg_type, handle, mem->handle.mId, index, timestamp);
459 }
460 }
461}
462
463void CameraDevice::initHalPreviewWindow()
464{
465 mHalPreviewWindow.cancel_buffer = sCancelBuffer;
466 mHalPreviewWindow.lock_buffer = sLockBuffer;
467 mHalPreviewWindow.dequeue_buffer = sDequeueBuffer;
468 mHalPreviewWindow.enqueue_buffer = sEnqueueBuffer;
469 mHalPreviewWindow.set_buffer_count = sSetBufferCount;
470 mHalPreviewWindow.set_buffers_geometry = sSetBuffersGeometry;
471 mHalPreviewWindow.set_crop = sSetCrop;
472 mHalPreviewWindow.set_timestamp = sSetTimestamp;
473 mHalPreviewWindow.set_usage = sSetUsage;
474 mHalPreviewWindow.set_swap_interval = sSetSwapInterval;
475
476 mHalPreviewWindow.get_min_undequeued_buffer_count =
477 sGetMinUndequeuedBufferCount;
478}
479
480// Methods from ::android::hardware::camera::device::V1_0::ICameraDevice follow.
481Return<void> CameraDevice::getResourceCost(getResourceCost_cb _hidl_cb) {
482 Status status = initStatus();
483 CameraResourceCost resCost;
484 if (status == Status::OK) {
485 int cost = 100;
486 std::vector<std::string> conflicting_devices;
487 struct camera_info info;
488
489 // If using post-2.4 module version, query the cost + conflicting devices from the HAL
490 if (mModule->getModuleApiVersion() >= CAMERA_MODULE_API_VERSION_2_4) {
491 int ret = mModule->getCameraInfo(mCameraIdInt, &info);
492 if (ret == OK) {
493 cost = info.resource_cost;
494 for (size_t i = 0; i < info.conflicting_devices_length; i++) {
495 std::string cameraId(info.conflicting_devices[i]);
496 for (const auto& pair : mCameraDeviceNames) {
497 if (cameraId == pair.first) {
498 conflicting_devices.push_back(pair.second);
499 }
500 }
501 }
502 } else {
503 status = Status::INTERNAL_ERROR;
504 }
505 }
506
507 if (status == Status::OK) {
508 resCost.resourceCost = cost;
509 resCost.conflictingDevices.resize(conflicting_devices.size());
510 for (size_t i = 0; i < conflicting_devices.size(); i++) {
511 resCost.conflictingDevices[i] = conflicting_devices[i];
512 ALOGV("CamDevice %s is conflicting with camDevice %s",
513 mCameraId.c_str(), resCost.conflictingDevices[i].c_str());
514 }
515 }
516 }
517 _hidl_cb(status, resCost);
518 return Void();
519}
520
521Return<void> CameraDevice::getCameraInfo(getCameraInfo_cb _hidl_cb) {
522 Status status = initStatus();
523 CameraInfo cameraInfo;
524 if (status == Status::OK) {
525 struct camera_info info;
526 int ret = mModule->getCameraInfo(mCameraIdInt, &info);
527 if (ret == OK) {
528 cameraInfo.facing = (CameraFacing) info.facing;
529 // Device 1.0 does not support external camera facing.
530 // The closest approximation would be front camera.
531 // TODO: figure out should we override here or let
532 // camera service handle it.
533 if (cameraInfo.facing == CameraFacing::EXTERNAL) {
534 cameraInfo.facing = CameraFacing::FRONT;
535 }
536 cameraInfo.orientation = info.orientation;
537 } else {
538 ALOGE("%s: get camera info failed!", __FUNCTION__);
539 status = Status::INTERNAL_ERROR;
540 }
541 }
542 _hidl_cb(status, cameraInfo);
543 return Void();
544}
545
546Return<Status> CameraDevice::setTorchMode(TorchMode mode) {
547 if (!mModule->isSetTorchModeSupported()) {
548 return Status::METHOD_NOT_SUPPORTED;
549 }
550
551 Status status = initStatus();
552 if (status == Status::OK) {
553 bool enable = (mode == TorchMode::ON) ? true : false;
554 status = getHidlStatus(mModule->setTorchMode(mCameraId.c_str(), enable));
555 }
556 return status;
557}
558
559Return<Status> CameraDevice::dumpState(const hidl_handle& handle) {
560 Mutex::Autolock _l(mLock);
561 if (handle.getNativeHandle() == nullptr) {
562 ALOGE("%s: handle must not be null", __FUNCTION__);
563 return Status::ILLEGAL_ARGUMENT;
564 }
565 if (handle->numFds != 1 || handle->numInts != 0) {
566 ALOGE("%s: handle must contain 1 FD and 0 integers! Got %d FDs and %d ints",
567 __FUNCTION__, handle->numFds, handle->numInts);
568 return Status::ILLEGAL_ARGUMENT;
569 }
570 int fd = handle->data[0];
571
572 if (mDevice != nullptr) {
573 if (mDevice->ops->dump) { // It's fine if the HAL doesn't implement dump()
574 return getHidlStatus(mDevice->ops->dump(mDevice, fd));
575 }
576 }
577 return Status::OK;
578}
579
580Return<Status> CameraDevice::open(const sp<ICameraDeviceCallback>& callback) {
581 ALOGI("Opening camera %s", mCameraId.c_str());
582 Mutex::Autolock _l(mLock);
583
584 camera_info info;
585 status_t res = mModule->getCameraInfo(mCameraIdInt, &info);
586 if (res != OK) {
587 ALOGE("Could not get camera info: %s: %d", mCameraId.c_str(), res);
588 return getHidlStatus(res);
589 }
590
591 int rc = OK;
592 if (mModule->getModuleApiVersion() >= CAMERA_MODULE_API_VERSION_2_3 &&
593 info.device_version > CAMERA_DEVICE_API_VERSION_1_0) {
594 // Open higher version camera device as HAL1.0 device.
595 rc = mModule->openLegacy(mCameraId.c_str(),
596 CAMERA_DEVICE_API_VERSION_1_0,
597 (hw_device_t **)&mDevice);
598 } else {
599 rc = mModule->open(mCameraId.c_str(), (hw_device_t **)&mDevice);
600 }
601 if (rc != OK) {
602 mDevice = nullptr;
603 ALOGE("Could not open camera %s: %d", mCameraId.c_str(), rc);
604 return getHidlStatus(rc);
605 }
606
607 initHalPreviewWindow();
608 mDeviceCallback = callback;
609
610 if (mDevice->ops->set_callbacks) {
611 mDevice->ops->set_callbacks(mDevice,
612 sNotifyCb, sDataCb, sDataCbTimestamp, sGetMemory, this);
613 }
614
615 return getHidlStatus(rc);
616}
617
618Return<Status> CameraDevice::setPreviewWindow(const sp<ICameraDevicePreviewCallback>& window) {
619 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
620 Mutex::Autolock _l(mLock);
621 if (!mDevice) {
622 ALOGE("%s called while camera is not opened", __FUNCTION__);
623 return Status::OPERATION_NOT_SUPPORTED;
624 }
625
626 mHalPreviewWindow.mPreviewCallback = window;
627 if (mDevice->ops->set_preview_window) {
628 return getHidlStatus(mDevice->ops->set_preview_window(mDevice,
629 (window == nullptr) ? nullptr : &mHalPreviewWindow));
630 }
631 return Status::INTERNAL_ERROR; // HAL should provide set_preview_window
632}
633
634Return<void> CameraDevice::enableMsgType(uint32_t msgType) {
635 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
636 Mutex::Autolock _l(mLock);
637 if (!mDevice) {
638 ALOGE("%s called while camera is not opened", __FUNCTION__);
639 return Void();
640 }
641 if (mDevice->ops->enable_msg_type) {
642 mDevice->ops->enable_msg_type(mDevice, msgType);
643 }
644 return Void();
645}
646
647Return<void> CameraDevice::disableMsgType(uint32_t msgType) {
648 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
649 Mutex::Autolock _l(mLock);
650 if (!mDevice) {
651 ALOGE("%s called while camera is not opened", __FUNCTION__);
652 return Void();
653 }
654 if (mDevice->ops->disable_msg_type) {
655 mDevice->ops->disable_msg_type(mDevice, msgType);
656 }
657 return Void();
658}
659
660Return<bool> CameraDevice::msgTypeEnabled(uint32_t msgType) {
661 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
662 Mutex::Autolock _l(mLock);
663 if (!mDevice) {
664 ALOGE("%s called while camera is not opened", __FUNCTION__);
665 return false;
666 }
667 if (mDevice->ops->msg_type_enabled) {
668 return mDevice->ops->msg_type_enabled(mDevice, msgType);
669 }
670 return false;
671}
672
673Return<Status> CameraDevice::startPreview() {
674 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
675 Mutex::Autolock _l(mLock);
676 if (!mDevice) {
677 ALOGE("%s called while camera is not opened", __FUNCTION__);
678 return Status::OPERATION_NOT_SUPPORTED;
679 }
680 if (mDevice->ops->start_preview) {
681 return getHidlStatus(mDevice->ops->start_preview(mDevice));
682 }
683 return Status::INTERNAL_ERROR; // HAL should provide start_preview
684}
685
686Return<void> CameraDevice::stopPreview() {
687 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
688 Mutex::Autolock _l(mLock);
689 if (!mDevice) {
690 ALOGE("%s called while camera is not opened", __FUNCTION__);
691 return Void();
692 }
693 if (mDevice->ops->stop_preview) {
694 mDevice->ops->stop_preview(mDevice);
695 }
696 return Void();
697}
698
699Return<bool> CameraDevice::previewEnabled() {
700 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
701 Mutex::Autolock _l(mLock);
702 if (!mDevice) {
703 ALOGE("%s called while camera is not opened", __FUNCTION__);
704 return false;
705 }
706 if (mDevice->ops->preview_enabled) {
707 return mDevice->ops->preview_enabled(mDevice);
708 }
709 return false;
710}
711
712Return<Status> CameraDevice::storeMetaDataInBuffers(bool enable) {
713 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
714 Mutex::Autolock _l(mLock);
715 if (!mDevice) {
716 ALOGE("%s called while camera is not opened", __FUNCTION__);
717 return Status::OPERATION_NOT_SUPPORTED;
718 }
719 if (mDevice->ops->store_meta_data_in_buffers) {
720 status_t s = mDevice->ops->store_meta_data_in_buffers(mDevice, enable);
721 if (s == OK && enable) {
722 mMetadataMode = true;
723 }
724 return getHidlStatus(s);
725 }
726 return enable ? Status::ILLEGAL_ARGUMENT : Status::OK;
727}
728
729Return<Status> CameraDevice::startRecording() {
730 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
731 Mutex::Autolock _l(mLock);
732 if (!mDevice) {
733 ALOGE("%s called while camera is not opened", __FUNCTION__);
734 return Status::OPERATION_NOT_SUPPORTED;
735 }
736 if (mDevice->ops->start_recording) {
737 return getHidlStatus(mDevice->ops->start_recording(mDevice));
738 }
739 return Status::ILLEGAL_ARGUMENT;
740}
741
742Return<void> CameraDevice::stopRecording() {
743 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
744 Mutex::Autolock _l(mLock);
745 if (!mDevice) {
746 ALOGE("%s called while camera is not opened", __FUNCTION__);
747 return Void();
748 }
749 if (mDevice->ops->stop_recording) {
750 mDevice->ops->stop_recording(mDevice);
751 }
752 return Void();
753}
754
755Return<bool> CameraDevice::recordingEnabled() {
756 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
757 Mutex::Autolock _l(mLock);
758 if (!mDevice) {
759 ALOGE("%s called while camera is not opened", __FUNCTION__);
760 return false;
761 }
762 if (mDevice->ops->recording_enabled) {
763 return mDevice->ops->recording_enabled(mDevice);
764 }
765 return false;
766}
767
768void CameraDevice::releaseRecordingFrameLocked(
769 uint32_t memId, uint32_t bufferIndex, const native_handle_t* handle) {
770 if (!mDevice) {
771 ALOGE("%s called while camera is not opened", __FUNCTION__);
772 return;
773 }
774 if (mDevice->ops->release_recording_frame) {
775 CameraHeapMemory* camMemory = mMemoryMap.at(memId);
776 sp<MemoryHeapBase> heap = camMemory->mHeap;
777 if (bufferIndex >= camMemory->mNumBufs) {
778 ALOGE("%s: bufferIndex %d exceeds number of buffers %d",
779 __FUNCTION__, bufferIndex, camMemory->mNumBufs);
780 return;
781 }
782 sp<IMemory> mem = camMemory->mBuffers[bufferIndex];
783 // TODO: simplify below logic once we verify offset is indeed idx * mBufSize
784 // and heap == heap2
785 ssize_t offset;
786 size_t size;
787 sp<IMemoryHeap> heap2 = mem->getMemory(&offset, &size);
788 if ((size_t)offset != bufferIndex * camMemory->mBufSize) {
789 ALOGI("%s: unexpected offset %zd (was expecting %zu)",
790 __FUNCTION__, offset, bufferIndex * camMemory->mBufSize);
791 }
792 if (heap != heap2) {
793 ALOGE("%s: heap mismatch!", __FUNCTION__);
794 return;
795 }
796 void *data = ((uint8_t *)heap->base()) + offset;
797 if (handle) {
798 VideoNativeHandleMetadata* md = (VideoNativeHandleMetadata*) data;
799 if (md->eType == VideoNativeHandleMetadata::kMetadataBufferTypeNativeHandleSource) {
800 // Input handle will be closed by HIDL transport later, so clone it
801 // HAL implementation is responsible to close/delete the clone
802 native_handle_t* clone = native_handle_clone(handle);
803 if (!clone) {
804 ALOGE("%s: failed to clone buffer %p", __FUNCTION__, handle);
805 return;
806 }
807 md->pHandle = clone;
808 } else {
809 ALOGE("%s:Malform VideoNativeHandleMetadata at memId %d, bufferId %d",
810 __FUNCTION__, memId, bufferIndex);
811 return;
812 }
813 }
814 mDevice->ops->release_recording_frame(mDevice, data);
815 }
816}
817
818Return<void> CameraDevice::releaseRecordingFrame(uint32_t memId, uint32_t bufferIndex) {
819 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
820 Mutex::Autolock _l(mLock);
821 releaseRecordingFrameLocked(memId, bufferIndex, nullptr);
822 return Void();
823}
824
825Return<void> CameraDevice::releaseRecordingFrameHandle(
826 uint32_t memId, uint32_t bufferIndex, const hidl_handle& frame) {
827 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
828 Mutex::Autolock _l(mLock);
829 releaseRecordingFrameLocked(
830 memId, bufferIndex, frame.getNativeHandle());
831 return Void();
832}
833
834Return<Status> CameraDevice::autoFocus() {
835 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
836 Mutex::Autolock _l(mLock);
837 if (!mDevice) {
838 ALOGE("%s called while camera is not opened", __FUNCTION__);
839 return Status::OPERATION_NOT_SUPPORTED;
840 }
841 if (mDevice->ops->auto_focus) {
842 return getHidlStatus(mDevice->ops->auto_focus(mDevice));
843 }
844 return Status::ILLEGAL_ARGUMENT;
845}
846
847Return<Status> CameraDevice::cancelAutoFocus() {
848 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
849 Mutex::Autolock _l(mLock);
850 if (!mDevice) {
851 ALOGE("%s called while camera is not opened", __FUNCTION__);
852 return Status::OPERATION_NOT_SUPPORTED;
853 }
854 if (mDevice->ops->cancel_auto_focus) {
855 return getHidlStatus(mDevice->ops->cancel_auto_focus(mDevice));
856 }
857 return Status::ILLEGAL_ARGUMENT;
858}
859
860Return<Status> CameraDevice::takePicture() {
861 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
862 Mutex::Autolock _l(mLock);
863 if (!mDevice) {
864 ALOGE("%s called while camera is not opened", __FUNCTION__);
865 return Status::OPERATION_NOT_SUPPORTED;
866 }
867 if (mDevice->ops->take_picture) {
868 return getHidlStatus(mDevice->ops->take_picture(mDevice));
869 }
870 return Status::ILLEGAL_ARGUMENT;
871}
872
873Return<Status> CameraDevice::cancelPicture() {
874 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
875 Mutex::Autolock _l(mLock);
876 if (!mDevice) {
877 ALOGE("%s called while camera is not opened", __FUNCTION__);
878 return Status::OPERATION_NOT_SUPPORTED;
879 }
880 if (mDevice->ops->cancel_picture) {
881 return getHidlStatus(mDevice->ops->cancel_picture(mDevice));
882 }
883 return Status::ILLEGAL_ARGUMENT;
884}
885
886Return<Status> CameraDevice::setParameters(const hidl_string& params) {
887 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
888 Mutex::Autolock _l(mLock);
889 if (!mDevice) {
890 ALOGE("%s called while camera is not opened", __FUNCTION__);
891 return Status::OPERATION_NOT_SUPPORTED;
892 }
893 if (mDevice->ops->set_parameters) {
894 return getHidlStatus(mDevice->ops->set_parameters(mDevice, params.c_str()));
895 }
896 return Status::ILLEGAL_ARGUMENT;
897}
898
899Return<void> CameraDevice::getParameters(getParameters_cb _hidl_cb) {
900 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
901 Mutex::Autolock _l(mLock);
902 hidl_string outStr;
903 if (!mDevice) {
904 ALOGE("%s called while camera is not opened", __FUNCTION__);
905 _hidl_cb(outStr);
906 return Void();
907 }
908 if (mDevice->ops->get_parameters) {
909 char *temp = mDevice->ops->get_parameters(mDevice);
910 outStr = temp;
911 if (mDevice->ops->put_parameters) {
912 mDevice->ops->put_parameters(mDevice, temp);
913 } else {
914 free(temp);
915 }
916 }
917 _hidl_cb(outStr);
918 return Void();
919}
920
921Return<Status> CameraDevice::sendCommand(CommandType cmd, int32_t arg1, int32_t arg2) {
922 ALOGV("%s(%s)", __FUNCTION__, mCameraId.c_str());
923 Mutex::Autolock _l(mLock);
924 if (!mDevice) {
925 ALOGE("%s called while camera is not opened", __FUNCTION__);
926 return Status::OPERATION_NOT_SUPPORTED;
927 }
928 if (mDevice->ops->send_command) {
929 return getHidlStatus(mDevice->ops->send_command(mDevice, (int32_t) cmd, arg1, arg2));
930 }
931 return Status::ILLEGAL_ARGUMENT;
932}
933
934Return<void> CameraDevice::close() {
935 ALOGI("Closing camera %s", mCameraId.c_str());
936 Mutex::Autolock _l(mLock);
937 if(mDevice) {
938 int rc = mDevice->common.close(&mDevice->common);
939 if (rc != OK) {
940 ALOGE("Could not close camera %s: %d", mCameraId.c_str(), rc);
941 }
942 mDevice = nullptr;
943 }
944 return Void();
945}
946
947} // namespace implementation
948} // namespace V1_0
949} // namespace device
950} // namespace camera
951} // namespace hardware
952} // namespace android