blob: a3164e529339a92832278cde02bb1215127427e2 [file] [log] [blame]
Alex Ray7ee0b7a2012-11-06 00:12:49 -08001/*
2 * Copyright (C) 2012 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 <cstdlib>
18#include <pthread.h>
Alex Ray69f1f912013-10-21 00:46:44 -070019#include <stdio.h>
Alex Raya0ed4be2013-02-25 15:02:16 -080020#include <hardware/camera3.h>
Alex Ray083315c2013-04-26 19:32:29 -070021#include <sync/sync.h>
Alex Raybfcbd952013-03-20 13:20:02 -070022#include <system/camera_metadata.h>
Alex Rayb0be1032013-05-28 15:52:47 -070023#include <system/graphics.h>
Alex Raya0ed4be2013-02-25 15:02:16 -080024#include "CameraHAL.h"
Alex Rayb0be1032013-05-28 15:52:47 -070025#include "Metadata.h"
Alex Raybcaf7882013-02-28 16:04:35 -080026#include "Stream.h"
Alex Ray7ee0b7a2012-11-06 00:12:49 -080027
Alex Rayed6b8a72012-12-27 10:42:22 -080028//#define LOG_NDEBUG 0
Alex Ray7ee0b7a2012-11-06 00:12:49 -080029#define LOG_TAG "Camera"
30#include <cutils/log.h>
31
Alex Rayed6b8a72012-12-27 10:42:22 -080032#define ATRACE_TAG (ATRACE_TAG_CAMERA | ATRACE_TAG_HAL)
Alex Rayea803822013-10-14 15:56:43 -070033#include <utils/Trace.h>
Alex Rayed6b8a72012-12-27 10:42:22 -080034
Alex Ray7ee0b7a2012-11-06 00:12:49 -080035#include "Camera.h"
36
Alex Ray083315c2013-04-26 19:32:29 -070037#define CAMERA_SYNC_TIMEOUT 5000 // in msecs
38
Alex Ray7ee0b7a2012-11-06 00:12:49 -080039namespace default_camera_hal {
40
41extern "C" {
42// Shim passed to the framework to close an opened device.
43static int close_device(hw_device_t* dev)
44{
Alex Raya0ed4be2013-02-25 15:02:16 -080045 camera3_device_t* cam_dev = reinterpret_cast<camera3_device_t*>(dev);
Alex Ray7ee0b7a2012-11-06 00:12:49 -080046 Camera* cam = static_cast<Camera*>(cam_dev->priv);
47 return cam->close();
48}
49} // extern "C"
50
Alex Raya0ed4be2013-02-25 15:02:16 -080051Camera::Camera(int id)
52 : mId(id),
Alex Rayb0be1032013-05-28 15:52:47 -070053 mStaticInfo(NULL),
Alex Raya0ed4be2013-02-25 15:02:16 -080054 mBusy(false),
Alex Raybcaf7882013-02-28 16:04:35 -080055 mCallbackOps(NULL),
56 mStreams(NULL),
Alex Raybfcbd952013-03-20 13:20:02 -070057 mNumStreams(0),
58 mSettings(NULL)
Alex Ray7ee0b7a2012-11-06 00:12:49 -080059{
Alex Ray0f82f5a2013-07-17 14:23:04 -070060 pthread_mutex_init(&mMutex, NULL);
61 pthread_mutex_init(&mStaticInfoMutex, NULL);
Alex Ray7ee0b7a2012-11-06 00:12:49 -080062
Alex Ray61f7a0c2013-07-03 17:54:19 -070063 memset(&mTemplates, 0, sizeof(mTemplates));
Alex Raya0ed4be2013-02-25 15:02:16 -080064 memset(&mDevice, 0, sizeof(mDevice));
Alex Ray7ee0b7a2012-11-06 00:12:49 -080065 mDevice.common.tag = HARDWARE_DEVICE_TAG;
Alex Rayb0be1032013-05-28 15:52:47 -070066 mDevice.common.version = CAMERA_DEVICE_API_VERSION_3_0;
Alex Ray7ee0b7a2012-11-06 00:12:49 -080067 mDevice.common.close = close_device;
Alex Raya0ed4be2013-02-25 15:02:16 -080068 mDevice.ops = const_cast<camera3_device_ops_t*>(&sOps);
Alex Ray7ee0b7a2012-11-06 00:12:49 -080069 mDevice.priv = this;
70}
71
72Camera::~Camera()
73{
Alex Ray0f82f5a2013-07-17 14:23:04 -070074 pthread_mutex_destroy(&mMutex);
75 pthread_mutex_destroy(&mStaticInfoMutex);
Alex Ray61f7a0c2013-07-03 17:54:19 -070076 if (mStaticInfo != NULL) {
77 free_camera_metadata(mStaticInfo);
78 }
Alex Ray7ee0b7a2012-11-06 00:12:49 -080079}
80
Alex Raya0ed4be2013-02-25 15:02:16 -080081int Camera::open(const hw_module_t *module, hw_device_t **device)
Alex Ray7ee0b7a2012-11-06 00:12:49 -080082{
Alex Raya0ed4be2013-02-25 15:02:16 -080083 ALOGI("%s:%d: Opening camera device", __func__, mId);
Alex Rayea803822013-10-14 15:56:43 -070084 ATRACE_CALL();
Alex Ray7ee0b7a2012-11-06 00:12:49 -080085 pthread_mutex_lock(&mMutex);
86 if (mBusy) {
87 pthread_mutex_unlock(&mMutex);
Alex Raya0ed4be2013-02-25 15:02:16 -080088 ALOGE("%s:%d: Error! Camera device already opened", __func__, mId);
Alex Ray7ee0b7a2012-11-06 00:12:49 -080089 return -EBUSY;
90 }
91
92 // TODO: open camera dev nodes, etc
93 mBusy = true;
Alex Raya0ed4be2013-02-25 15:02:16 -080094 mDevice.common.module = const_cast<hw_module_t*>(module);
95 *device = &mDevice.common;
Alex Ray7ee0b7a2012-11-06 00:12:49 -080096
97 pthread_mutex_unlock(&mMutex);
98 return 0;
99}
100
Alex Rayb0be1032013-05-28 15:52:47 -0700101int Camera::getInfo(struct camera_info *info)
102{
Alex Rayb0be1032013-05-28 15:52:47 -0700103 info->facing = CAMERA_FACING_FRONT;
104 info->orientation = 0;
105 info->device_version = mDevice.common.version;
106
Alex Ray0f82f5a2013-07-17 14:23:04 -0700107 pthread_mutex_lock(&mStaticInfoMutex);
Alex Rayb0be1032013-05-28 15:52:47 -0700108 if (mStaticInfo == NULL) {
Alex Ray0f82f5a2013-07-17 14:23:04 -0700109 mStaticInfo = initStaticInfo();
Alex Rayb0be1032013-05-28 15:52:47 -0700110 }
Alex Ray0f82f5a2013-07-17 14:23:04 -0700111 pthread_mutex_unlock(&mStaticInfoMutex);
Alex Rayb0be1032013-05-28 15:52:47 -0700112
113 info->static_camera_characteristics = mStaticInfo;
114
Alex Ray0f82f5a2013-07-17 14:23:04 -0700115 return 0;
Alex Rayb0be1032013-05-28 15:52:47 -0700116}
117
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800118int Camera::close()
119{
Alex Raya0ed4be2013-02-25 15:02:16 -0800120 ALOGI("%s:%d: Closing camera device", __func__, mId);
Alex Rayea803822013-10-14 15:56:43 -0700121 ATRACE_CALL();
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800122 pthread_mutex_lock(&mMutex);
123 if (!mBusy) {
124 pthread_mutex_unlock(&mMutex);
Alex Raya0ed4be2013-02-25 15:02:16 -0800125 ALOGE("%s:%d: Error! Camera device not open", __func__, mId);
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800126 return -EINVAL;
127 }
128
129 // TODO: close camera dev nodes, etc
130 mBusy = false;
131
132 pthread_mutex_unlock(&mMutex);
133 return 0;
134}
135
Alex Raya0ed4be2013-02-25 15:02:16 -0800136int Camera::initialize(const camera3_callback_ops_t *callback_ops)
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800137{
Alex Ray61f7a0c2013-07-03 17:54:19 -0700138 int res;
139
Alex Raya0ed4be2013-02-25 15:02:16 -0800140 ALOGV("%s:%d: callback_ops=%p", __func__, mId, callback_ops);
141 mCallbackOps = callback_ops;
Alex Ray61f7a0c2013-07-03 17:54:19 -0700142 // per-device specific initialization
143 res = initDevice();
144 if (res != 0) {
145 ALOGE("%s:%d: Failed to initialize device!", __func__, mId);
146 return res;
Alex Ray89a82662013-05-28 20:32:48 -0700147 }
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800148 return 0;
149}
150
Alex Raybcaf7882013-02-28 16:04:35 -0800151int Camera::configureStreams(camera3_stream_configuration_t *stream_config)
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800152{
Alex Raybcaf7882013-02-28 16:04:35 -0800153 camera3_stream_t *astream;
154 Stream **newStreams = NULL;
155
Alex Rayea803822013-10-14 15:56:43 -0700156 ATRACE_CALL();
Alex Raybcaf7882013-02-28 16:04:35 -0800157 ALOGV("%s:%d: stream_config=%p", __func__, mId, stream_config);
158
159 if (stream_config == NULL) {
160 ALOGE("%s:%d: NULL stream configuration array", __func__, mId);
161 return -EINVAL;
162 }
163 if (stream_config->num_streams == 0) {
164 ALOGE("%s:%d: Empty stream configuration array", __func__, mId);
165 return -EINVAL;
166 }
167
168 // Create new stream array
169 newStreams = new Stream*[stream_config->num_streams];
170 ALOGV("%s:%d: Number of Streams: %d", __func__, mId,
171 stream_config->num_streams);
172
173 pthread_mutex_lock(&mMutex);
174
175 // Mark all current streams unused for now
176 for (int i = 0; i < mNumStreams; i++)
177 mStreams[i]->mReuse = false;
178 // Fill new stream array with reused streams and new streams
Alex Rayc6bf2f22013-05-28 15:52:04 -0700179 for (unsigned int i = 0; i < stream_config->num_streams; i++) {
Alex Raybcaf7882013-02-28 16:04:35 -0800180 astream = stream_config->streams[i];
Alex Ray2b286da2013-05-29 15:08:29 -0700181 if (astream->max_buffers > 0) {
182 ALOGV("%s:%d: Reusing stream %d", __func__, mId, i);
Alex Raybcaf7882013-02-28 16:04:35 -0800183 newStreams[i] = reuseStream(astream);
Alex Ray2b286da2013-05-29 15:08:29 -0700184 } else {
185 ALOGV("%s:%d: Creating new stream %d", __func__, mId, i);
Alex Raybcaf7882013-02-28 16:04:35 -0800186 newStreams[i] = new Stream(mId, astream);
Alex Ray2b286da2013-05-29 15:08:29 -0700187 }
Alex Raybcaf7882013-02-28 16:04:35 -0800188
189 if (newStreams[i] == NULL) {
190 ALOGE("%s:%d: Error processing stream %d", __func__, mId, i);
191 goto err_out;
192 }
193 astream->priv = newStreams[i];
194 }
195
196 // Verify the set of streams in aggregate
197 if (!isValidStreamSet(newStreams, stream_config->num_streams)) {
198 ALOGE("%s:%d: Invalid stream set", __func__, mId);
199 goto err_out;
200 }
201
202 // Set up all streams (calculate usage/max_buffers for each)
203 setupStreams(newStreams, stream_config->num_streams);
204
205 // Destroy all old streams and replace stream array with new one
206 destroyStreams(mStreams, mNumStreams);
207 mStreams = newStreams;
208 mNumStreams = stream_config->num_streams;
209
Alex Raybfcbd952013-03-20 13:20:02 -0700210 // Clear out last seen settings metadata
211 setSettings(NULL);
212
Alex Raybcaf7882013-02-28 16:04:35 -0800213 pthread_mutex_unlock(&mMutex);
Alex Raya0ed4be2013-02-25 15:02:16 -0800214 return 0;
Alex Raybcaf7882013-02-28 16:04:35 -0800215
216err_out:
217 // Clean up temporary streams, preserve existing mStreams/mNumStreams
218 destroyStreams(newStreams, stream_config->num_streams);
219 pthread_mutex_unlock(&mMutex);
220 return -EINVAL;
221}
222
223void Camera::destroyStreams(Stream **streams, int count)
224{
225 if (streams == NULL)
226 return;
227 for (int i = 0; i < count; i++) {
228 // Only destroy streams that weren't reused
229 if (streams[i] != NULL && !streams[i]->mReuse)
230 delete streams[i];
231 }
232 delete [] streams;
233}
234
235Stream *Camera::reuseStream(camera3_stream_t *astream)
236{
237 Stream *priv = reinterpret_cast<Stream*>(astream->priv);
238 // Verify the re-used stream's parameters match
239 if (!priv->isValidReuseStream(mId, astream)) {
240 ALOGE("%s:%d: Mismatched parameter in reused stream", __func__, mId);
241 return NULL;
242 }
243 // Mark stream to be reused
244 priv->mReuse = true;
245 return priv;
246}
247
248bool Camera::isValidStreamSet(Stream **streams, int count)
249{
250 int inputs = 0;
251 int outputs = 0;
252
253 if (streams == NULL) {
254 ALOGE("%s:%d: NULL stream configuration streams", __func__, mId);
255 return false;
256 }
257 if (count == 0) {
258 ALOGE("%s:%d: Zero count stream configuration streams", __func__, mId);
259 return false;
260 }
261 // Validate there is at most one input stream and at least one output stream
262 for (int i = 0; i < count; i++) {
263 // A stream may be both input and output (bidirectional)
264 if (streams[i]->isInputType())
265 inputs++;
266 if (streams[i]->isOutputType())
267 outputs++;
268 }
Alex Ray768216e2013-07-02 16:56:14 -0700269 ALOGV("%s:%d: Configuring %d output streams and %d input streams",
270 __func__, mId, outputs, inputs);
Alex Raybcaf7882013-02-28 16:04:35 -0800271 if (outputs < 1) {
272 ALOGE("%s:%d: Stream config must have >= 1 output", __func__, mId);
273 return false;
274 }
275 if (inputs > 1) {
276 ALOGE("%s:%d: Stream config must have <= 1 input", __func__, mId);
277 return false;
278 }
279 // TODO: check for correct number of Bayer/YUV/JPEG/Encoder streams
280 return true;
281}
282
283void Camera::setupStreams(Stream **streams, int count)
284{
285 /*
286 * This is where the HAL has to decide internally how to handle all of the
287 * streams, and then produce usage and max_buffer values for each stream.
288 * Note, the stream array has been checked before this point for ALL invalid
289 * conditions, so it must find a successful configuration for this stream
290 * array. The HAL may not return an error from this point.
291 *
292 * In this demo HAL, we just set all streams to be the same dummy values;
293 * real implementations will want to avoid USAGE_SW_{READ|WRITE}_OFTEN.
294 */
295 for (int i = 0; i < count; i++) {
296 uint32_t usage = 0;
297
298 if (streams[i]->isOutputType())
299 usage |= GRALLOC_USAGE_SW_WRITE_OFTEN |
300 GRALLOC_USAGE_HW_CAMERA_WRITE;
301 if (streams[i]->isInputType())
302 usage |= GRALLOC_USAGE_SW_READ_OFTEN |
303 GRALLOC_USAGE_HW_CAMERA_READ;
304
305 streams[i]->setUsage(usage);
306 streams[i]->setMaxBuffers(1);
307 }
Alex Raya0ed4be2013-02-25 15:02:16 -0800308}
309
310int Camera::registerStreamBuffers(const camera3_stream_buffer_set_t *buf_set)
311{
312 ALOGV("%s:%d: buffer_set=%p", __func__, mId, buf_set);
Alex Ray8a8f86b2013-03-01 01:32:21 -0800313 if (buf_set == NULL) {
314 ALOGE("%s:%d: NULL buffer set", __func__, mId);
315 return -EINVAL;
316 }
317 if (buf_set->stream == NULL) {
318 ALOGE("%s:%d: NULL stream handle", __func__, mId);
319 return -EINVAL;
320 }
321 Stream *stream = reinterpret_cast<Stream*>(buf_set->stream->priv);
322 return stream->registerBuffers(buf_set);
Alex Raya0ed4be2013-02-25 15:02:16 -0800323}
324
Alex Ray61f7a0c2013-07-03 17:54:19 -0700325bool Camera::isValidTemplateType(int type)
326{
327 return type < 1 || type >= CAMERA3_TEMPLATE_COUNT;
328}
329
Alex Raya0ed4be2013-02-25 15:02:16 -0800330const camera_metadata_t* Camera::constructDefaultRequestSettings(int type)
331{
332 ALOGV("%s:%d: type=%d", __func__, mId, type);
Alex Ray89a82662013-05-28 20:32:48 -0700333
Alex Ray61f7a0c2013-07-03 17:54:19 -0700334 if (!isValidTemplateType(type)) {
Alex Ray89a82662013-05-28 20:32:48 -0700335 ALOGE("%s:%d: Invalid template request type: %d", __func__, mId, type);
336 return NULL;
337 }
Alex Ray61f7a0c2013-07-03 17:54:19 -0700338 return mTemplates[type];
Alex Raya0ed4be2013-02-25 15:02:16 -0800339}
340
341int Camera::processCaptureRequest(camera3_capture_request_t *request)
342{
Alex Ray083315c2013-04-26 19:32:29 -0700343 camera3_capture_result result;
344
Alex Raya0ed4be2013-02-25 15:02:16 -0800345 ALOGV("%s:%d: request=%p", __func__, mId, request);
Alex Rayea803822013-10-14 15:56:43 -0700346 ATRACE_CALL();
Alex Raya0ed4be2013-02-25 15:02:16 -0800347
348 if (request == NULL) {
349 ALOGE("%s:%d: NULL request recieved", __func__, mId);
Alex Raya0ed4be2013-02-25 15:02:16 -0800350 return -EINVAL;
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800351 }
352
Alex Raybfcbd952013-03-20 13:20:02 -0700353 ALOGV("%s:%d: Request Frame:%d Settings:%p", __func__, mId,
354 request->frame_number, request->settings);
355
356 // NULL indicates use last settings
357 if (request->settings == NULL) {
358 if (mSettings == NULL) {
359 ALOGE("%s:%d: NULL settings without previous set Frame:%d Req:%p",
360 __func__, mId, request->frame_number, request);
361 return -EINVAL;
362 }
363 } else {
364 setSettings(request->settings);
365 }
366
Alex Ray11bbeef2013-04-26 14:47:08 -0700367 if (request->input_buffer != NULL) {
368 ALOGV("%s:%d: Reprocessing input buffer %p", __func__, mId,
369 request->input_buffer);
370
371 if (!isValidReprocessSettings(request->settings)) {
372 ALOGE("%s:%d: Invalid settings for reprocess request: %p",
373 __func__, mId, request->settings);
374 return -EINVAL;
375 }
376 } else {
377 ALOGV("%s:%d: Capturing new frame.", __func__, mId);
378
379 if (!isValidCaptureSettings(request->settings)) {
380 ALOGE("%s:%d: Invalid settings for capture request: %p",
381 __func__, mId, request->settings);
382 return -EINVAL;
383 }
384 }
385
Alex Ray083315c2013-04-26 19:32:29 -0700386 if (request->num_output_buffers <= 0) {
387 ALOGE("%s:%d: Invalid number of output buffers: %d", __func__, mId,
388 request->num_output_buffers);
389 return -EINVAL;
390 }
391 result.num_output_buffers = request->num_output_buffers;
392 result.output_buffers = new camera3_stream_buffer_t[result.num_output_buffers];
393 for (unsigned int i = 0; i < request->num_output_buffers; i++) {
394 int res = processCaptureBuffer(&request->output_buffers[i],
395 const_cast<camera3_stream_buffer_t*>(&result.output_buffers[i]));
396 if (res)
397 goto err_out;
398 }
399
400 result.frame_number = request->frame_number;
401 // TODO: return actual captured/reprocessed settings
402 result.result = request->settings;
403 // TODO: asynchronously return results
Alex Ray764e4422013-06-04 12:38:07 -0700404 notifyShutter(request->frame_number, 0);
Alex Ray083315c2013-04-26 19:32:29 -0700405 mCallbackOps->process_capture_result(mCallbackOps, &result);
406
Alex Raya0ed4be2013-02-25 15:02:16 -0800407 return 0;
Alex Ray083315c2013-04-26 19:32:29 -0700408
409err_out:
410 delete [] result.output_buffers;
411 // TODO: this should probably be a total device failure; transient for now
412 return -EINVAL;
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800413}
414
Alex Raybfcbd952013-03-20 13:20:02 -0700415void Camera::setSettings(const camera_metadata_t *new_settings)
416{
417 if (mSettings != NULL) {
418 free_camera_metadata(mSettings);
419 mSettings = NULL;
420 }
421
422 if (new_settings != NULL)
423 mSettings = clone_camera_metadata(new_settings);
424}
425
Alex Rayc6bf2f22013-05-28 15:52:04 -0700426bool Camera::isValidReprocessSettings(const camera_metadata_t* /*settings*/)
Alex Ray11bbeef2013-04-26 14:47:08 -0700427{
428 // TODO: reject settings that cannot be reprocessed
429 // input buffers unimplemented, use this to reject reprocessing requests
430 ALOGE("%s:%d: Input buffer reprocessing not implemented", __func__, mId);
431 return false;
432}
433
Alex Ray083315c2013-04-26 19:32:29 -0700434int Camera::processCaptureBuffer(const camera3_stream_buffer_t *in,
435 camera3_stream_buffer_t *out)
436{
Alex Ray77ecfd72013-05-30 00:19:04 -0700437 if (in->acquire_fence != -1) {
438 int res = sync_wait(in->acquire_fence, CAMERA_SYNC_TIMEOUT);
439 if (res == -ETIME) {
440 ALOGE("%s:%d: Timeout waiting on buffer acquire fence",
441 __func__, mId);
442 return res;
443 } else if (res) {
444 ALOGE("%s:%d: Error waiting on buffer acquire fence: %s(%d)",
445 __func__, mId, strerror(-res), res);
446 return res;
447 }
Alex Ray083315c2013-04-26 19:32:29 -0700448 }
449
450 out->stream = in->stream;
451 out->buffer = in->buffer;
452 out->status = CAMERA3_BUFFER_STATUS_OK;
453 // TODO: use driver-backed release fences
454 out->acquire_fence = -1;
455 out->release_fence = -1;
456
457 // TODO: lock and software-paint buffer
458 return 0;
459}
460
Alex Ray764e4422013-06-04 12:38:07 -0700461void Camera::notifyShutter(uint32_t frame_number, uint64_t timestamp)
462{
463 int res;
464 struct timespec ts;
465
466 // If timestamp is 0, get timestamp from right now instead
467 if (timestamp == 0) {
468 ALOGW("%s:%d: No timestamp provided, using CLOCK_BOOTTIME",
469 __func__, mId);
470 res = clock_gettime(CLOCK_BOOTTIME, &ts);
471 if (res == 0) {
472 timestamp = ts.tv_sec * 1000000000ULL + ts.tv_nsec;
473 } else {
474 ALOGE("%s:%d: No timestamp and failed to get CLOCK_BOOTTIME %s(%d)",
475 __func__, mId, strerror(errno), errno);
476 }
477 }
478 camera3_notify_msg_t m;
479 memset(&m, 0, sizeof(m));
480 m.type = CAMERA3_MSG_SHUTTER;
481 m.message.shutter.frame_number = frame_number;
482 m.message.shutter.timestamp = timestamp;
483 mCallbackOps->notify(mCallbackOps, &m);
484}
485
Alex Raya0ed4be2013-02-25 15:02:16 -0800486void Camera::getMetadataVendorTagOps(vendor_tag_query_ops_t *ops)
487{
488 ALOGV("%s:%d: ops=%p", __func__, mId, ops);
489 // TODO: return vendor tag ops
490}
491
492void Camera::dump(int fd)
493{
Alex Rayaf3a4612013-04-29 14:16:10 -0700494 ALOGV("%s:%d: Dumping to fd %d", __func__, mId, fd);
Alex Ray69f1f912013-10-21 00:46:44 -0700495
496 pthread_mutex_lock(&mMutex);
497
498 fdprintf(fd, "Camera ID: %d (Busy: %d)\n", mId, mBusy);
499
500 // TODO: dump all settings
501 fdprintf(fd, "Most Recent Settings: (%p)\n", mSettings);
502
503 fdprintf(fd, "Number of streams: %d\n", mNumStreams);
504 for (int i = 0; i < mNumStreams; i++) {
505 fdprintf(fd, "Stream %d/%d:\n", i, mNumStreams);
506 mStreams[i]->dump(fd);
507 }
508
509 pthread_mutex_unlock(&mMutex);
Alex Raya0ed4be2013-02-25 15:02:16 -0800510}
511
Alex Ray62735082013-10-21 12:55:24 -0700512const char* Camera::templateToString(int type)
513{
514 switch (type) {
515 case CAMERA3_TEMPLATE_PREVIEW:
516 return "CAMERA3_TEMPLATE_PREVIEW";
517 case CAMERA3_TEMPLATE_STILL_CAPTURE:
518 return "CAMERA3_TEMPLATE_STILL_CAPTURE";
519 case CAMERA3_TEMPLATE_VIDEO_RECORD:
520 return "CAMERA3_TEMPLATE_VIDEO_RECORD";
521 case CAMERA3_TEMPLATE_VIDEO_SNAPSHOT:
522 return "CAMERA3_TEMPLATE_VIDEO_SNAPSHOT";
523 case CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG:
524 return "CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG";
525 }
526 // TODO: support vendor templates
527 return "Invalid template type!";
528}
529
530int Camera::setTemplate(int type, camera_metadata_t *settings)
Alex Ray61f7a0c2013-07-03 17:54:19 -0700531{
532 if (!isValidTemplateType(type)) {
533 ALOGE("%s:%d: Invalid template request type: %d", __func__, mId, type);
Alex Ray62735082013-10-21 12:55:24 -0700534 return -EINVAL;
Alex Ray61f7a0c2013-07-03 17:54:19 -0700535 }
536 pthread_mutex_lock(&mMutex);
537 if (mTemplates[type] != NULL) {
Alex Ray62735082013-10-21 12:55:24 -0700538 ALOGE("%s:%d: Setting already constructed template type %s(%d)",
539 __func__, mId, templateToString(type), type);
540 pthread_mutex_unlock(&mMutex);
541 return -EINVAL;
Alex Ray61f7a0c2013-07-03 17:54:19 -0700542 }
Alex Ray62735082013-10-21 12:55:24 -0700543 // Make a durable copy of the underlying metadata
Alex Ray61f7a0c2013-07-03 17:54:19 -0700544 mTemplates[type] = clone_camera_metadata(settings);
Alex Ray62735082013-10-21 12:55:24 -0700545 if (mTemplates[type] == NULL) {
546 ALOGE("%s:%d: Failed to clone metadata %p for template type %s(%d)",
547 __func__, mId, settings, templateToString(type), type);
548 pthread_mutex_unlock(&mMutex);
549 return -EINVAL;
550 }
Alex Ray61f7a0c2013-07-03 17:54:19 -0700551 pthread_mutex_unlock(&mMutex);
Alex Ray62735082013-10-21 12:55:24 -0700552 return 0;
Alex Ray61f7a0c2013-07-03 17:54:19 -0700553}
554
Alex Raya0ed4be2013-02-25 15:02:16 -0800555extern "C" {
556// Get handle to camera from device priv data
557static Camera *camdev_to_camera(const camera3_device_t *dev)
558{
559 return reinterpret_cast<Camera*>(dev->priv);
560}
561
562static int initialize(const camera3_device_t *dev,
563 const camera3_callback_ops_t *callback_ops)
564{
565 return camdev_to_camera(dev)->initialize(callback_ops);
566}
567
568static int configure_streams(const camera3_device_t *dev,
569 camera3_stream_configuration_t *stream_list)
570{
571 return camdev_to_camera(dev)->configureStreams(stream_list);
572}
573
574static int register_stream_buffers(const camera3_device_t *dev,
575 const camera3_stream_buffer_set_t *buffer_set)
576{
577 return camdev_to_camera(dev)->registerStreamBuffers(buffer_set);
578}
579
580static const camera_metadata_t *construct_default_request_settings(
581 const camera3_device_t *dev, int type)
582{
583 return camdev_to_camera(dev)->constructDefaultRequestSettings(type);
584}
585
586static int process_capture_request(const camera3_device_t *dev,
587 camera3_capture_request_t *request)
588{
589 return camdev_to_camera(dev)->processCaptureRequest(request);
590}
591
592static void get_metadata_vendor_tag_ops(const camera3_device_t *dev,
593 vendor_tag_query_ops_t *ops)
594{
595 camdev_to_camera(dev)->getMetadataVendorTagOps(ops);
596}
597
598static void dump(const camera3_device_t *dev, int fd)
599{
600 camdev_to_camera(dev)->dump(fd);
601}
602} // extern "C"
603
604const camera3_device_ops_t Camera::sOps = {
605 .initialize = default_camera_hal::initialize,
606 .configure_streams = default_camera_hal::configure_streams,
607 .register_stream_buffers = default_camera_hal::register_stream_buffers,
608 .construct_default_request_settings =
609 default_camera_hal::construct_default_request_settings,
610 .process_capture_request = default_camera_hal::process_capture_request,
611 .get_metadata_vendor_tag_ops =
612 default_camera_hal::get_metadata_vendor_tag_ops,
613 .dump = default_camera_hal::dump
614};
615
Alex Ray7ee0b7a2012-11-06 00:12:49 -0800616} // namespace default_camera_hal