Home | History | Annotate | Download | only in 3_0
      1 /*
      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 //#define LOG_NDEBUG 0
     17 #define LOG_TAG "Camera"
     18 
     19 #include <errno.h>
     20 #include <stdint.h>
     21 #include <stdio.h>
     22 #include <string.h>
     23 
     24 #include <cstdlib>
     25 
     26 #include <log/log.h>
     27 #include <utils/Mutex.h>
     28 
     29 #define ATRACE_TAG (ATRACE_TAG_CAMERA | ATRACE_TAG_HAL)
     30 #include <utils/Trace.h>
     31 
     32 #include <hardware/camera3.h>
     33 #include <sync/sync.h>
     34 #include <system/camera_metadata.h>
     35 #include <system/graphics.h>
     36 #include "CameraHAL.h"
     37 #include "Metadata.h"
     38 #include "Stream.h"
     39 
     40 #include "Camera.h"
     41 
     42 #define CAMERA_SYNC_TIMEOUT 5000 // in msecs
     43 
     44 namespace default_camera_hal {
     45 
     46 extern "C" {
     47 // Shim passed to the framework to close an opened device.
     48 static int close_device(hw_device_t* dev)
     49 {
     50     camera3_device_t* cam_dev = reinterpret_cast<camera3_device_t*>(dev);
     51     Camera* cam = static_cast<Camera*>(cam_dev->priv);
     52     return cam->close();
     53 }
     54 } // extern "C"
     55 
     56 Camera::Camera(int id)
     57   : mId(id),
     58     mStaticInfo(NULL),
     59     mBusy(false),
     60     mCallbackOps(NULL),
     61     mStreams(NULL),
     62     mNumStreams(0),
     63     mSettings(NULL)
     64 {
     65     memset(&mTemplates, 0, sizeof(mTemplates));
     66     memset(&mDevice, 0, sizeof(mDevice));
     67     mDevice.common.tag    = HARDWARE_DEVICE_TAG;
     68     mDevice.common.version = CAMERA_DEVICE_API_VERSION_3_0;
     69     mDevice.common.close  = close_device;
     70     mDevice.ops           = const_cast<camera3_device_ops_t*>(&sOps);
     71     mDevice.priv          = this;
     72 }
     73 
     74 Camera::~Camera()
     75 {
     76     if (mStaticInfo != NULL) {
     77         free_camera_metadata(mStaticInfo);
     78     }
     79 }
     80 
     81 int Camera::open(const hw_module_t *module, hw_device_t **device)
     82 {
     83     ALOGI("%s:%d: Opening camera device", __func__, mId);
     84     ATRACE_CALL();
     85     android::Mutex::Autolock al(mDeviceLock);
     86 
     87     if (mBusy) {
     88         ALOGE("%s:%d: Error! Camera device already opened", __func__, mId);
     89         return -EBUSY;
     90     }
     91 
     92     // TODO: open camera dev nodes, etc
     93     mBusy = true;
     94     mDevice.common.module = const_cast<hw_module_t*>(module);
     95     *device = &mDevice.common;
     96     return 0;
     97 }
     98 
     99 int Camera::getInfo(struct camera_info *info)
    100 {
    101     android::Mutex::Autolock al(mStaticInfoLock);
    102 
    103     info->facing = CAMERA_FACING_FRONT;
    104     info->orientation = 0;
    105     info->device_version = mDevice.common.version;
    106     if (mStaticInfo == NULL) {
    107         mStaticInfo = initStaticInfo();
    108     }
    109     info->static_camera_characteristics = mStaticInfo;
    110     return 0;
    111 }
    112 
    113 int Camera::close()
    114 {
    115     ALOGI("%s:%d: Closing camera device", __func__, mId);
    116     ATRACE_CALL();
    117     android::Mutex::Autolock al(mDeviceLock);
    118 
    119     if (!mBusy) {
    120         ALOGE("%s:%d: Error! Camera device not open", __func__, mId);
    121         return -EINVAL;
    122     }
    123 
    124     // TODO: close camera dev nodes, etc
    125     mBusy = false;
    126     return 0;
    127 }
    128 
    129 int Camera::initialize(const camera3_callback_ops_t *callback_ops)
    130 {
    131     int res;
    132 
    133     ALOGV("%s:%d: callback_ops=%p", __func__, mId, callback_ops);
    134     mCallbackOps = callback_ops;
    135     // per-device specific initialization
    136     res = initDevice();
    137     if (res != 0) {
    138         ALOGE("%s:%d: Failed to initialize device!", __func__, mId);
    139         return res;
    140     }
    141     return 0;
    142 }
    143 
    144 int Camera::configureStreams(camera3_stream_configuration_t *stream_config)
    145 {
    146     camera3_stream_t *astream;
    147     Stream **newStreams = NULL;
    148 
    149     ALOGV("%s:%d: stream_config=%p", __func__, mId, stream_config);
    150     ATRACE_CALL();
    151     android::Mutex::Autolock al(mDeviceLock);
    152 
    153     if (stream_config == NULL) {
    154         ALOGE("%s:%d: NULL stream configuration array", __func__, mId);
    155         return -EINVAL;
    156     }
    157     if (stream_config->num_streams == 0) {
    158         ALOGE("%s:%d: Empty stream configuration array", __func__, mId);
    159         return -EINVAL;
    160     }
    161 
    162     // Create new stream array
    163     newStreams = new Stream*[stream_config->num_streams];
    164     ALOGV("%s:%d: Number of Streams: %d", __func__, mId,
    165             stream_config->num_streams);
    166 
    167     // Mark all current streams unused for now
    168     for (int i = 0; i < mNumStreams; i++)
    169         mStreams[i]->mReuse = false;
    170     // Fill new stream array with reused streams and new streams
    171     for (unsigned int i = 0; i < stream_config->num_streams; i++) {
    172         astream = stream_config->streams[i];
    173         if (astream->max_buffers > 0) {
    174             ALOGV("%s:%d: Reusing stream %d", __func__, mId, i);
    175             newStreams[i] = reuseStream(astream);
    176         } else {
    177             ALOGV("%s:%d: Creating new stream %d", __func__, mId, i);
    178             newStreams[i] = new Stream(mId, astream);
    179         }
    180 
    181         if (newStreams[i] == NULL) {
    182             ALOGE("%s:%d: Error processing stream %d", __func__, mId, i);
    183             goto err_out;
    184         }
    185         astream->priv = newStreams[i];
    186     }
    187 
    188     // Verify the set of streams in aggregate
    189     if (!isValidStreamSet(newStreams, stream_config->num_streams)) {
    190         ALOGE("%s:%d: Invalid stream set", __func__, mId);
    191         goto err_out;
    192     }
    193 
    194     // Set up all streams (calculate usage/max_buffers for each)
    195     setupStreams(newStreams, stream_config->num_streams);
    196 
    197     // Destroy all old streams and replace stream array with new one
    198     destroyStreams(mStreams, mNumStreams);
    199     mStreams = newStreams;
    200     mNumStreams = stream_config->num_streams;
    201 
    202     // Clear out last seen settings metadata
    203     setSettings(NULL);
    204     return 0;
    205 
    206 err_out:
    207     // Clean up temporary streams, preserve existing mStreams/mNumStreams
    208     destroyStreams(newStreams, stream_config->num_streams);
    209     return -EINVAL;
    210 }
    211 
    212 void Camera::destroyStreams(Stream **streams, int count)
    213 {
    214     if (streams == NULL)
    215         return;
    216     for (int i = 0; i < count; i++) {
    217         // Only destroy streams that weren't reused
    218         if (streams[i] != NULL && !streams[i]->mReuse)
    219             delete streams[i];
    220     }
    221     delete [] streams;
    222 }
    223 
    224 Stream *Camera::reuseStream(camera3_stream_t *astream)
    225 {
    226     Stream *priv = reinterpret_cast<Stream*>(astream->priv);
    227     // Verify the re-used stream's parameters match
    228     if (!priv->isValidReuseStream(mId, astream)) {
    229         ALOGE("%s:%d: Mismatched parameter in reused stream", __func__, mId);
    230         return NULL;
    231     }
    232     // Mark stream to be reused
    233     priv->mReuse = true;
    234     return priv;
    235 }
    236 
    237 bool Camera::isValidStreamSet(Stream **streams, int count)
    238 {
    239     int inputs = 0;
    240     int outputs = 0;
    241 
    242     if (streams == NULL) {
    243         ALOGE("%s:%d: NULL stream configuration streams", __func__, mId);
    244         return false;
    245     }
    246     if (count == 0) {
    247         ALOGE("%s:%d: Zero count stream configuration streams", __func__, mId);
    248         return false;
    249     }
    250     // Validate there is at most one input stream and at least one output stream
    251     for (int i = 0; i < count; i++) {
    252         // A stream may be both input and output (bidirectional)
    253         if (streams[i]->isInputType())
    254             inputs++;
    255         if (streams[i]->isOutputType())
    256             outputs++;
    257     }
    258     ALOGV("%s:%d: Configuring %d output streams and %d input streams",
    259             __func__, mId, outputs, inputs);
    260     if (outputs < 1) {
    261         ALOGE("%s:%d: Stream config must have >= 1 output", __func__, mId);
    262         return false;
    263     }
    264     if (inputs > 1) {
    265         ALOGE("%s:%d: Stream config must have <= 1 input", __func__, mId);
    266         return false;
    267     }
    268     // TODO: check for correct number of Bayer/YUV/JPEG/Encoder streams
    269     return true;
    270 }
    271 
    272 void Camera::setupStreams(Stream **streams, int count)
    273 {
    274     /*
    275      * This is where the HAL has to decide internally how to handle all of the
    276      * streams, and then produce usage and max_buffer values for each stream.
    277      * Note, the stream array has been checked before this point for ALL invalid
    278      * conditions, so it must find a successful configuration for this stream
    279      * array.  The HAL may not return an error from this point.
    280      *
    281      * In this demo HAL, we just set all streams to be the same dummy values;
    282      * real implementations will want to avoid USAGE_SW_{READ|WRITE}_OFTEN.
    283      */
    284     for (int i = 0; i < count; i++) {
    285         uint32_t usage = 0;
    286 
    287         if (streams[i]->isOutputType())
    288             usage |= GRALLOC_USAGE_SW_WRITE_OFTEN |
    289                      GRALLOC_USAGE_HW_CAMERA_WRITE;
    290         if (streams[i]->isInputType())
    291             usage |= GRALLOC_USAGE_SW_READ_OFTEN |
    292                      GRALLOC_USAGE_HW_CAMERA_READ;
    293 
    294         streams[i]->setUsage(usage);
    295         streams[i]->setMaxBuffers(1);
    296     }
    297 }
    298 
    299 int Camera::registerStreamBuffers(const camera3_stream_buffer_set_t *buf_set)
    300 {
    301     ALOGV("%s:%d: buffer_set=%p", __func__, mId, buf_set);
    302     if (buf_set == NULL) {
    303         ALOGE("%s:%d: NULL buffer set", __func__, mId);
    304         return -EINVAL;
    305     }
    306     if (buf_set->stream == NULL) {
    307         ALOGE("%s:%d: NULL stream handle", __func__, mId);
    308         return -EINVAL;
    309     }
    310     Stream *stream = reinterpret_cast<Stream*>(buf_set->stream->priv);
    311     return stream->registerBuffers(buf_set);
    312 }
    313 
    314 bool Camera::isValidTemplateType(int type)
    315 {
    316     return type < 1 || type >= CAMERA3_TEMPLATE_COUNT;
    317 }
    318 
    319 const camera_metadata_t* Camera::constructDefaultRequestSettings(int type)
    320 {
    321     ALOGV("%s:%d: type=%d", __func__, mId, type);
    322 
    323     if (!isValidTemplateType(type)) {
    324         ALOGE("%s:%d: Invalid template request type: %d", __func__, mId, type);
    325         return NULL;
    326     }
    327     return mTemplates[type];
    328 }
    329 
    330 int Camera::processCaptureRequest(camera3_capture_request_t *request)
    331 {
    332     camera3_capture_result result;
    333 
    334     ALOGV("%s:%d: request=%p", __func__, mId, request);
    335     ATRACE_CALL();
    336 
    337     if (request == NULL) {
    338         ALOGE("%s:%d: NULL request recieved", __func__, mId);
    339         return -EINVAL;
    340     }
    341 
    342     ALOGV("%s:%d: Request Frame:%d Settings:%p", __func__, mId,
    343             request->frame_number, request->settings);
    344 
    345     // NULL indicates use last settings
    346     if (request->settings == NULL) {
    347         if (mSettings == NULL) {
    348             ALOGE("%s:%d: NULL settings without previous set Frame:%d Req:%p",
    349                     __func__, mId, request->frame_number, request);
    350             return -EINVAL;
    351         }
    352     } else {
    353         setSettings(request->settings);
    354     }
    355 
    356     if (request->input_buffer != NULL) {
    357         ALOGV("%s:%d: Reprocessing input buffer %p", __func__, mId,
    358                 request->input_buffer);
    359 
    360         if (!isValidReprocessSettings(request->settings)) {
    361             ALOGE("%s:%d: Invalid settings for reprocess request: %p",
    362                     __func__, mId, request->settings);
    363             return -EINVAL;
    364         }
    365     } else {
    366         ALOGV("%s:%d: Capturing new frame.", __func__, mId);
    367 
    368         if (!isValidCaptureSettings(request->settings)) {
    369             ALOGE("%s:%d: Invalid settings for capture request: %p",
    370                     __func__, mId, request->settings);
    371             return -EINVAL;
    372         }
    373     }
    374 
    375     if (request->num_output_buffers <= 0) {
    376         ALOGE("%s:%d: Invalid number of output buffers: %d", __func__, mId,
    377                 request->num_output_buffers);
    378         return -EINVAL;
    379     }
    380     result.num_output_buffers = request->num_output_buffers;
    381     result.output_buffers = new camera3_stream_buffer_t[result.num_output_buffers];
    382     for (unsigned int i = 0; i < request->num_output_buffers; i++) {
    383         int res = processCaptureBuffer(&request->output_buffers[i],
    384                 const_cast<camera3_stream_buffer_t*>(&result.output_buffers[i]));
    385         if (res)
    386             goto err_out;
    387     }
    388 
    389     result.frame_number = request->frame_number;
    390     // TODO: return actual captured/reprocessed settings
    391     result.result = request->settings;
    392     // TODO: asynchronously return results
    393     notifyShutter(request->frame_number, 0);
    394     mCallbackOps->process_capture_result(mCallbackOps, &result);
    395 
    396     return 0;
    397 
    398 err_out:
    399     delete [] result.output_buffers;
    400     // TODO: this should probably be a total device failure; transient for now
    401     return -EINVAL;
    402 }
    403 
    404 void Camera::setSettings(const camera_metadata_t *new_settings)
    405 {
    406     if (mSettings != NULL) {
    407         free_camera_metadata(mSettings);
    408         mSettings = NULL;
    409     }
    410 
    411     if (new_settings != NULL)
    412         mSettings = clone_camera_metadata(new_settings);
    413 }
    414 
    415 bool Camera::isValidReprocessSettings(const camera_metadata_t* /*settings*/)
    416 {
    417     // TODO: reject settings that cannot be reprocessed
    418     // input buffers unimplemented, use this to reject reprocessing requests
    419     ALOGE("%s:%d: Input buffer reprocessing not implemented", __func__, mId);
    420     return false;
    421 }
    422 
    423 int Camera::processCaptureBuffer(const camera3_stream_buffer_t *in,
    424         camera3_stream_buffer_t *out)
    425 {
    426     if (in->acquire_fence != -1) {
    427         int res = sync_wait(in->acquire_fence, CAMERA_SYNC_TIMEOUT);
    428         if (res == -ETIME) {
    429             ALOGE("%s:%d: Timeout waiting on buffer acquire fence",
    430                     __func__, mId);
    431             return res;
    432         } else if (res) {
    433             ALOGE("%s:%d: Error waiting on buffer acquire fence: %s(%d)",
    434                     __func__, mId, strerror(-res), res);
    435             return res;
    436         }
    437     }
    438 
    439     out->stream = in->stream;
    440     out->buffer = in->buffer;
    441     out->status = CAMERA3_BUFFER_STATUS_OK;
    442     // TODO: use driver-backed release fences
    443     out->acquire_fence = -1;
    444     out->release_fence = -1;
    445 
    446     // TODO: lock and software-paint buffer
    447     return 0;
    448 }
    449 
    450 void Camera::notifyShutter(uint32_t frame_number, uint64_t timestamp)
    451 {
    452     int res;
    453     struct timespec ts;
    454 
    455     // If timestamp is 0, get timestamp from right now instead
    456     if (timestamp == 0) {
    457         ALOGW("%s:%d: No timestamp provided, using CLOCK_BOOTTIME",
    458                 __func__, mId);
    459         res = clock_gettime(CLOCK_BOOTTIME, &ts);
    460         if (res == 0) {
    461             timestamp = ts.tv_sec * 1000000000ULL + ts.tv_nsec;
    462         } else {
    463             ALOGE("%s:%d: No timestamp and failed to get CLOCK_BOOTTIME %s(%d)",
    464                     __func__, mId, strerror(errno), errno);
    465         }
    466     }
    467     camera3_notify_msg_t m;
    468     memset(&m, 0, sizeof(m));
    469     m.type = CAMERA3_MSG_SHUTTER;
    470     m.message.shutter.frame_number = frame_number;
    471     m.message.shutter.timestamp = timestamp;
    472     mCallbackOps->notify(mCallbackOps, &m);
    473 }
    474 
    475 void Camera::dump(int fd)
    476 {
    477     ALOGV("%s:%d: Dumping to fd %d", __func__, mId, fd);
    478     ATRACE_CALL();
    479     android::Mutex::Autolock al(mDeviceLock);
    480 
    481     dprintf(fd, "Camera ID: %d (Busy: %d)\n", mId, mBusy);
    482 
    483     // TODO: dump all settings
    484     dprintf(fd, "Most Recent Settings: (%p)\n", mSettings);
    485 
    486     dprintf(fd, "Number of streams: %d\n", mNumStreams);
    487     for (int i = 0; i < mNumStreams; i++) {
    488         dprintf(fd, "Stream %d/%d:\n", i, mNumStreams);
    489         mStreams[i]->dump(fd);
    490     }
    491 }
    492 
    493 const char* Camera::templateToString(int type)
    494 {
    495     switch (type) {
    496     case CAMERA3_TEMPLATE_PREVIEW:
    497         return "CAMERA3_TEMPLATE_PREVIEW";
    498     case CAMERA3_TEMPLATE_STILL_CAPTURE:
    499         return "CAMERA3_TEMPLATE_STILL_CAPTURE";
    500     case CAMERA3_TEMPLATE_VIDEO_RECORD:
    501         return "CAMERA3_TEMPLATE_VIDEO_RECORD";
    502     case CAMERA3_TEMPLATE_VIDEO_SNAPSHOT:
    503         return "CAMERA3_TEMPLATE_VIDEO_SNAPSHOT";
    504     case CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG:
    505         return "CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG";
    506     }
    507     // TODO: support vendor templates
    508     return "Invalid template type!";
    509 }
    510 
    511 int Camera::setTemplate(int type, camera_metadata_t *settings)
    512 {
    513     android::Mutex::Autolock al(mDeviceLock);
    514 
    515     if (!isValidTemplateType(type)) {
    516         ALOGE("%s:%d: Invalid template request type: %d", __func__, mId, type);
    517         return -EINVAL;
    518     }
    519 
    520     if (mTemplates[type] != NULL) {
    521         ALOGE("%s:%d: Setting already constructed template type %s(%d)",
    522                 __func__, mId, templateToString(type), type);
    523         return -EINVAL;
    524     }
    525 
    526     // Make a durable copy of the underlying metadata
    527     mTemplates[type] = clone_camera_metadata(settings);
    528     if (mTemplates[type] == NULL) {
    529         ALOGE("%s:%d: Failed to clone metadata %p for template type %s(%d)",
    530                 __func__, mId, settings, templateToString(type), type);
    531         return -EINVAL;
    532     }
    533     return 0;
    534 }
    535 
    536 extern "C" {
    537 // Get handle to camera from device priv data
    538 static Camera *camdev_to_camera(const camera3_device_t *dev)
    539 {
    540     return reinterpret_cast<Camera*>(dev->priv);
    541 }
    542 
    543 static int initialize(const camera3_device_t *dev,
    544         const camera3_callback_ops_t *callback_ops)
    545 {
    546     return camdev_to_camera(dev)->initialize(callback_ops);
    547 }
    548 
    549 static int configure_streams(const camera3_device_t *dev,
    550         camera3_stream_configuration_t *stream_list)
    551 {
    552     return camdev_to_camera(dev)->configureStreams(stream_list);
    553 }
    554 
    555 static int register_stream_buffers(const camera3_device_t *dev,
    556         const camera3_stream_buffer_set_t *buffer_set)
    557 {
    558     return camdev_to_camera(dev)->registerStreamBuffers(buffer_set);
    559 }
    560 
    561 static const camera_metadata_t *construct_default_request_settings(
    562         const camera3_device_t *dev, int type)
    563 {
    564     return camdev_to_camera(dev)->constructDefaultRequestSettings(type);
    565 }
    566 
    567 static int process_capture_request(const camera3_device_t *dev,
    568         camera3_capture_request_t *request)
    569 {
    570     return camdev_to_camera(dev)->processCaptureRequest(request);
    571 }
    572 
    573 static void dump(const camera3_device_t *dev, int fd)
    574 {
    575     camdev_to_camera(dev)->dump(fd);
    576 }
    577 
    578 static int flush(const camera3_device_t*)
    579 {
    580     ALOGE("%s: unimplemented.", __func__);
    581     return -1;
    582 }
    583 
    584 } // extern "C"
    585 
    586 const camera3_device_ops_t Camera::sOps = {
    587     .initialize = default_camera_hal::initialize,
    588     .configure_streams = default_camera_hal::configure_streams,
    589     .register_stream_buffers = default_camera_hal::register_stream_buffers,
    590     .construct_default_request_settings
    591         = default_camera_hal::construct_default_request_settings,
    592     .process_capture_request = default_camera_hal::process_capture_request,
    593     .get_metadata_vendor_tag_ops = NULL,
    594     .dump = default_camera_hal::dump,
    595     .flush = default_camera_hal::flush,
    596     .reserved = {0},
    597 };
    598 
    599 } // namespace default_camera_hal
    600