Home | History | Annotate | Download | only in camera
      1 /*
      2  * Copyright (C) 2011 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 /*
     18  * Contains implementation of a class EmulatedCamera that encapsulates
     19  * functionality common to all emulated cameras ("fake", "webcam", "video file",
     20  * etc.). Instances of this class (for each emulated camera) are created during
     21  * the construction of the EmulatedCameraFactory instance. This class serves as
     22  * an entry point for all camera API calls that defined by camera_device_ops_t
     23  * API.
     24  */
     25 
     26 #include "guest/libs/platform_support/api_level_fixes.h"
     27 
     28 #define LOG_NDEBUG 0
     29 #define LOG_TAG "EmulatedCamera_Camera"
     30 #include <cutils/log.h>
     31 #include "EmulatedCamera.h"
     32 //#include "EmulatedFakeCameraDevice.h"
     33 #include "Converters.h"
     34 
     35 /* Defines whether we should trace parameter changes. */
     36 #define DEBUG_PARAM 1
     37 
     38 namespace android {
     39 namespace {
     40 const char* kSupportedFlashModes[] = {
     41     CameraParameters::FLASH_MODE_OFF,   CameraParameters::FLASH_MODE_AUTO,
     42     CameraParameters::FLASH_MODE_ON,    CameraParameters::FLASH_MODE_RED_EYE,
     43     CameraParameters::FLASH_MODE_TORCH, NULL};
     44 
     45 std::string BuildParameterValue(const char** value_array) {
     46   std::string result;
     47 
     48   for (int index = 0; value_array[index] != NULL; ++index) {
     49     if (index) result.append(",");
     50     result.append(value_array[index]);
     51   }
     52   return result;
     53 }
     54 
     55 bool CheckParameterValue(const char* value, const char** supported_values) {
     56   for (int index = 0; supported_values[index] != NULL; ++index) {
     57     if (!strcmp(value, supported_values[index])) return true;
     58   }
     59   return false;
     60 }
     61 
     62 }  // namespace
     63 
     64 #if DEBUG_PARAM
     65 /* Calculates and logs parameter changes.
     66  * Param:
     67  *  current - Current set of camera parameters.
     68  *  new_par - String representation of new parameters.
     69  */
     70 static void PrintParamDiff(const CameraParameters& current,
     71                            const char* new_par);
     72 #else
     73 #define PrintParamDiff(current, new_par) (void(0))
     74 #endif /* DEBUG_PARAM */
     75 
     76 EmulatedCamera::EmulatedCamera(int cameraId, struct hw_module_t* module)
     77     : EmulatedBaseCamera(cameraId, HARDWARE_DEVICE_API_VERSION(1, 0), &common,
     78                          module),
     79       mPreviewWindow(),
     80       mCallbackNotifier() {
     81   /* camera_device v1 fields. */
     82   common.close = EmulatedCamera::close;
     83   ops = &mDeviceOps;
     84   priv = this;
     85 }
     86 
     87 EmulatedCamera::~EmulatedCamera() {}
     88 
     89 /****************************************************************************
     90  * Public API
     91  ***************************************************************************/
     92 
     93 status_t EmulatedCamera::Initialize(const cvd::CameraDefinition&) {
     94   /* Preview formats supported by this HAL. */
     95   char preview_formats[1024];
     96   snprintf(preview_formats, sizeof(preview_formats), "%s,%s,%s",
     97            CameraParameters::PIXEL_FORMAT_YUV420SP,
     98            CameraParameters::PIXEL_FORMAT_YUV420P,
     99            CameraParameters::PIXEL_FORMAT_RGBA8888);
    100 
    101   /*
    102    * Fake required parameters.
    103    */
    104 
    105   mParameters.set(CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES,
    106                   "320x240,0x0");
    107 
    108   mParameters.set(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH, "512");
    109   mParameters.set(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT, "384");
    110   mParameters.set(CameraParameters::KEY_JPEG_QUALITY, "90");
    111   mParameters.set(CameraParameters::KEY_FOCAL_LENGTH, "4.31");
    112   mParameters.set(CameraParameters::KEY_HORIZONTAL_VIEW_ANGLE, "54.8");
    113   mParameters.set(CameraParameters::KEY_VERTICAL_VIEW_ANGLE, "42.5");
    114   mParameters.set(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY, "90");
    115 
    116   /* Preview format settings used here are related to panoramic view only. It's
    117    * not related to the preview window that works only with RGB frames, which
    118    * is explicitly stated when set_buffers_geometry is called on the preview
    119    * window object. */
    120   mParameters.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FORMATS,
    121                   preview_formats);
    122   mParameters.setPreviewFormat(CameraParameters::PIXEL_FORMAT_YUV420SP);
    123 
    124   /* We don't relay on the actual frame rates supported by the camera device,
    125    * since we will emulate them through timeouts in the emulated camera device
    126    * worker thread. */
    127   mParameters.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FRAME_RATES,
    128                   "30,24,20,15,10,5");
    129   mParameters.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FPS_RANGE,
    130                   "(5000,30000),(15000,15000),(30000,30000)");
    131   mParameters.set(CameraParameters::KEY_PREVIEW_FPS_RANGE, "5000,30000");
    132   mParameters.setPreviewFrameRate(30000);
    133 
    134   /* Only PIXEL_FORMAT_YUV420P is accepted by video framework in emulator! */
    135   mParameters.set(CameraParameters::KEY_VIDEO_FRAME_FORMAT,
    136                   CameraParameters::PIXEL_FORMAT_YUV420P);
    137   mParameters.set(CameraParameters::KEY_SUPPORTED_PICTURE_FORMATS,
    138                   CameraParameters::PIXEL_FORMAT_JPEG);
    139   mParameters.setPictureFormat(CameraParameters::PIXEL_FORMAT_JPEG);
    140 
    141   /* Set exposure compensation. */
    142   mParameters.set(CameraParameters::KEY_MAX_EXPOSURE_COMPENSATION, "6");
    143   mParameters.set(CameraParameters::KEY_MIN_EXPOSURE_COMPENSATION, "-6");
    144   mParameters.set(CameraParameters::KEY_EXPOSURE_COMPENSATION_STEP, "0.5");
    145   mParameters.set(CameraParameters::KEY_EXPOSURE_COMPENSATION, "0");
    146 
    147   /* Sets the white balance modes and the device-dependent scale factors. */
    148   char supported_white_balance[1024];
    149   snprintf(supported_white_balance, sizeof(supported_white_balance),
    150            "%s,%s,%s,%s", CameraParameters::WHITE_BALANCE_AUTO,
    151            CameraParameters::WHITE_BALANCE_INCANDESCENT,
    152            CameraParameters::WHITE_BALANCE_DAYLIGHT,
    153            CameraParameters::WHITE_BALANCE_TWILIGHT);
    154   mParameters.set(CameraParameters::KEY_SUPPORTED_WHITE_BALANCE,
    155                   supported_white_balance);
    156   mParameters.set(CameraParameters::KEY_WHITE_BALANCE,
    157                   CameraParameters::WHITE_BALANCE_AUTO);
    158   getCameraDevice()->initializeWhiteBalanceModes(
    159       CameraParameters::WHITE_BALANCE_AUTO, 1.0f, 1.0f);
    160   getCameraDevice()->initializeWhiteBalanceModes(
    161       CameraParameters::WHITE_BALANCE_INCANDESCENT, 1.38f, 0.60f);
    162   getCameraDevice()->initializeWhiteBalanceModes(
    163       CameraParameters::WHITE_BALANCE_DAYLIGHT, 1.09f, 0.92f);
    164   getCameraDevice()->initializeWhiteBalanceModes(
    165       CameraParameters::WHITE_BALANCE_TWILIGHT, 0.92f, 1.22f);
    166   getCameraDevice()->setWhiteBalanceMode(CameraParameters::WHITE_BALANCE_AUTO);
    167 
    168   /*
    169    * Not supported features
    170    */
    171   mParameters.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
    172                   CameraParameters::FOCUS_MODE_FIXED);
    173   mParameters.set(CameraParameters::KEY_FOCUS_MODE,
    174                   CameraParameters::FOCUS_MODE_FIXED);
    175   mParameters.set(CameraParameters::KEY_SUPPORTED_FLASH_MODES,
    176                   BuildParameterValue(kSupportedFlashModes).c_str());
    177   mParameters.set(CameraParameters::KEY_FLASH_MODE,
    178                   CameraParameters::FLASH_MODE_OFF);
    179   mParameters.set(CameraParameters::KEY_FOCUS_DISTANCES, "0.1,0.1,0.1");
    180   mParameters.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_HW, "0");
    181   mParameters.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_SW, "0");
    182   mParameters.set(CameraParameters::KEY_ZOOM_RATIOS, "100");
    183   mParameters.set(CameraParameters::KEY_ZOOM_SUPPORTED,
    184                   CameraParameters::FALSE);
    185   mParameters.set(CameraParameters::KEY_SMOOTH_ZOOM_SUPPORTED,
    186                   CameraParameters::FALSE);
    187   mParameters.set(CameraParameters::KEY_ZOOM, "0");
    188   mParameters.set(CameraParameters::KEY_MAX_ZOOM, "0");
    189 
    190   return NO_ERROR;
    191 }
    192 
    193 void EmulatedCamera::onNextFrameAvailable(const void* frame, nsecs_t timestamp,
    194                                           EmulatedCameraDevice* camera_dev) {
    195   /* Notify the preview window first. */
    196   mPreviewWindow.onNextFrameAvailable(frame, timestamp, camera_dev);
    197 
    198   /* Notify callback notifier next. */
    199   mCallbackNotifier.onNextFrameAvailable(frame, timestamp, camera_dev);
    200 }
    201 
    202 void EmulatedCamera::onCameraDeviceError(int err) {
    203   /* Errors are reported through the callback notifier */
    204   mCallbackNotifier.onCameraDeviceError(err);
    205 }
    206 
    207 void EmulatedCamera::onCameraFocusAcquired() {
    208   mCallbackNotifier.onCameraFocusAcquired();
    209 }
    210 
    211 /****************************************************************************
    212  * Camera API implementation.
    213  ***************************************************************************/
    214 
    215 status_t EmulatedCamera::connectCamera(hw_device_t** device) {
    216   ALOGV("%s", __FUNCTION__);
    217 
    218   status_t res = EINVAL;
    219   EmulatedCameraDevice* const camera_dev = getCameraDevice();
    220   ALOGE_IF(camera_dev == NULL, "%s: No camera device instance.", __FUNCTION__);
    221 
    222   if (camera_dev != NULL) {
    223     /* Connect to the camera device. */
    224     res = getCameraDevice()->connectDevice();
    225     if (res == NO_ERROR) {
    226       *device = &common;
    227     }
    228   }
    229 
    230   return -res;
    231 }
    232 
    233 status_t EmulatedCamera::closeCamera() {
    234   ALOGV("%s", __FUNCTION__);
    235 
    236   return cleanupCamera();
    237 }
    238 
    239 status_t EmulatedCamera::getCameraInfo(struct camera_info* info) {
    240   ALOGV("%s", __FUNCTION__);
    241 
    242   const char* valstr = NULL;
    243 
    244   valstr = mParameters.get(EmulatedCamera::FACING_KEY);
    245   if (valstr != NULL) {
    246     if (strcmp(valstr, EmulatedCamera::FACING_FRONT) == 0) {
    247       info->facing = CAMERA_FACING_FRONT;
    248     } else if (strcmp(valstr, EmulatedCamera::FACING_BACK) == 0) {
    249       info->facing = CAMERA_FACING_BACK;
    250     }
    251   } else {
    252     info->facing = CAMERA_FACING_BACK;
    253   }
    254 
    255   valstr = mParameters.get(EmulatedCamera::ORIENTATION_KEY);
    256   if (valstr != NULL) {
    257     info->orientation = atoi(valstr);
    258   } else {
    259     info->orientation = 0;
    260   }
    261 
    262 #if VSOC_PLATFORM_SDK_AFTER(L_MR1)
    263   info->resource_cost = 100;
    264   info->conflicting_devices = NULL;
    265   info->conflicting_devices_length = 0;
    266 #endif
    267 
    268   return EmulatedBaseCamera::getCameraInfo(info);
    269 }
    270 
    271 const CameraParameters* EmulatedCamera::getCameraParameters() {
    272   return &mParameters;
    273 }
    274 
    275 status_t EmulatedCamera::setPreviewWindow(struct preview_stream_ops* window) {
    276   /* Callback should return a negative errno. */
    277   return -mPreviewWindow.setPreviewWindow(window,
    278                                           mParameters.getPreviewFrameRate());
    279 }
    280 
    281 void EmulatedCamera::setCallbacks(
    282     camera_notify_callback notify_cb, camera_data_callback data_cb,
    283     camera_data_timestamp_callback data_cb_timestamp,
    284     camera_request_memory get_memory, void* user) {
    285   mCallbackNotifier.setCallbacks(notify_cb, data_cb, data_cb_timestamp,
    286                                  get_memory, user);
    287 }
    288 
    289 void EmulatedCamera::enableMsgType(int32_t msg_type) {
    290   mCallbackNotifier.enableMessage(msg_type);
    291 }
    292 
    293 void EmulatedCamera::disableMsgType(int32_t msg_type) {
    294   mCallbackNotifier.disableMessage(msg_type);
    295 }
    296 
    297 int EmulatedCamera::isMsgTypeEnabled(int32_t msg_type) {
    298   return mCallbackNotifier.isMessageEnabled(msg_type);
    299 }
    300 
    301 status_t EmulatedCamera::startPreview() {
    302   /* Callback should return a negative errno. */
    303   return -doStartPreview();
    304 }
    305 
    306 void EmulatedCamera::stopPreview() { doStopPreview(); }
    307 
    308 int EmulatedCamera::isPreviewEnabled() {
    309   return mPreviewWindow.isPreviewEnabled();
    310 }
    311 
    312 status_t EmulatedCamera::storeMetaDataInBuffers(int enable) {
    313   /* Callback should return a negative errno. */
    314   return -mCallbackNotifier.storeMetaDataInBuffers(enable);
    315 }
    316 
    317 status_t EmulatedCamera::startRecording() {
    318   /* Callback should return a negative errno. */
    319   return -mCallbackNotifier.enableVideoRecording(
    320       mParameters.getPreviewFrameRate());
    321 }
    322 
    323 void EmulatedCamera::stopRecording() {
    324   mCallbackNotifier.disableVideoRecording();
    325 }
    326 
    327 int EmulatedCamera::isRecordingEnabled() {
    328   return mCallbackNotifier.isVideoRecordingEnabled();
    329 }
    330 
    331 void EmulatedCamera::releaseRecordingFrame(const void* opaque) {
    332   mCallbackNotifier.releaseRecordingFrame(opaque);
    333 }
    334 
    335 status_t EmulatedCamera::setAutoFocus() {
    336   ALOGV("%s", __FUNCTION__);
    337 
    338   /* Trigger auto-focus. Focus response cannot be sent directly from here. */
    339   getCameraDevice()->startAutoFocus();
    340 
    341   /* TODO: Future enhancements. */
    342   return NO_ERROR;
    343 }
    344 
    345 status_t EmulatedCamera::cancelAutoFocus() {
    346   ALOGV("%s", __FUNCTION__);
    347 
    348   /* TODO: Future enhancements. */
    349   return NO_ERROR;
    350 }
    351 
    352 status_t EmulatedCamera::takePicture() {
    353   ALOGV("%s", __FUNCTION__);
    354 
    355   status_t res;
    356   int width, height;
    357   uint32_t org_fmt;
    358 
    359   /* Collect frame info for the picture. */
    360   mParameters.getPictureSize(&width, &height);
    361   const char* pix_fmt = mParameters.getPictureFormat();
    362   if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_YUV420P) == 0) {
    363     org_fmt = V4L2_PIX_FMT_YUV420;
    364   } else if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_RGBA8888) == 0) {
    365     org_fmt = V4L2_PIX_FMT_RGB32;
    366   } else if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_YUV420SP) == 0) {
    367     org_fmt = V4L2_PIX_FMT_NV21;
    368   } else if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_JPEG) == 0) {
    369     /* We only have JPEG converted for NV21 format. */
    370     org_fmt = V4L2_PIX_FMT_NV21;
    371   } else {
    372     ALOGE("%s: Unsupported pixel format %s", __FUNCTION__, pix_fmt);
    373     return EINVAL;
    374   }
    375   /* Get JPEG quality. */
    376   int jpeg_quality = mParameters.getInt(CameraParameters::KEY_JPEG_QUALITY);
    377   if (jpeg_quality <= 0) {
    378     jpeg_quality = 90; /* Fall back to default. */
    379   }
    380 
    381   /*
    382    * Make sure preview is not running, and device is stopped before taking
    383    * picture.
    384    */
    385 
    386   const bool preview_on = mPreviewWindow.isPreviewEnabled();
    387   if (preview_on) {
    388     doStopPreview();
    389   }
    390 
    391   /* Camera device should have been stopped when the shutter message has been
    392    * enabled. */
    393   EmulatedCameraDevice* const camera_dev = getCameraDevice();
    394   if (camera_dev->isStarted()) {
    395     ALOGW("%s: Camera device is started", __FUNCTION__);
    396     camera_dev->stopDeliveringFrames();
    397     camera_dev->stopDevice();
    398   }
    399 
    400   /* Compute target FPS rate.
    401    * Pretend to simulate generation of (max_fps_rate) */
    402   int min_fps_rate, max_fps_rate;
    403   mParameters.getPreviewFpsRange(&min_fps_rate, &max_fps_rate);
    404 
    405   /*
    406    * Take the picture now.
    407    */
    408 
    409   /* Start camera device for the picture frame. */
    410   ALOGD("Starting camera for picture: %.4s(%s)[%dx%d]",
    411         reinterpret_cast<const char*>(&org_fmt), pix_fmt, width, height);
    412   res = camera_dev->startDevice(width, height, org_fmt, max_fps_rate);
    413   if (res != NO_ERROR) {
    414     if (preview_on) {
    415       doStartPreview();
    416     }
    417     return res;
    418   }
    419 
    420   /* Deliver one frame only. */
    421   mCallbackNotifier.setJpegQuality(jpeg_quality);
    422   mCallbackNotifier.setTakingPicture(true);
    423   res = camera_dev->startDeliveringFrames(true);
    424   if (res != NO_ERROR) {
    425     mCallbackNotifier.setTakingPicture(false);
    426     if (preview_on) {
    427       doStartPreview();
    428     }
    429   }
    430   return res;
    431 }
    432 
    433 status_t EmulatedCamera::cancelPicture() {
    434   ALOGV("%s", __FUNCTION__);
    435 
    436   return NO_ERROR;
    437 }
    438 
    439 status_t EmulatedCamera::setParameters(const char* parms) {
    440   ALOGV("%s", __FUNCTION__);
    441   PrintParamDiff(mParameters, parms);
    442 
    443   CameraParameters new_param;
    444   String8 str8_param(parms);
    445   new_param.unflatten(str8_param);
    446 
    447   /*
    448    * Check if requested dimensions are valid.
    449    */
    450   if (!CheckParameterValue(new_param.get(CameraParameters::KEY_FLASH_MODE),
    451                            kSupportedFlashModes)) {
    452     ALOGE("%s: Unsupported flash mode: %s", __FUNCTION__,
    453           new_param.get(CameraParameters::KEY_FLASH_MODE));
    454     return -EINVAL;
    455   }
    456   if (strcmp(new_param.get(CameraParameters::KEY_FOCUS_MODE),
    457              CameraParameters::FOCUS_MODE_FIXED)) {
    458     ALOGE("%s: Unsupported flash mode: %s", __FUNCTION__,
    459           new_param.get(CameraParameters::KEY_FOCUS_MODE));
    460     return -EINVAL;
    461   }
    462 
    463   int preview_width, preview_height;
    464   new_param.getPreviewSize(&preview_width, &preview_height);
    465   if (preview_width <= 0 || preview_height <= 0) return -EINVAL;
    466 
    467   /*
    468    * Check for new exposure compensation parameter.
    469    */
    470   int new_exposure_compensation =
    471       new_param.getInt(CameraParameters::KEY_EXPOSURE_COMPENSATION);
    472   const int min_exposure_compensation =
    473       new_param.getInt(CameraParameters::KEY_MIN_EXPOSURE_COMPENSATION);
    474   const int max_exposure_compensation =
    475       new_param.getInt(CameraParameters::KEY_MAX_EXPOSURE_COMPENSATION);
    476 
    477   // Checks if the exposure compensation change is supported.
    478   if ((min_exposure_compensation != 0) || (max_exposure_compensation != 0)) {
    479     if (new_exposure_compensation > max_exposure_compensation) {
    480       new_exposure_compensation = max_exposure_compensation;
    481     }
    482     if (new_exposure_compensation < min_exposure_compensation) {
    483       new_exposure_compensation = min_exposure_compensation;
    484     }
    485 
    486     const int current_exposure_compensation =
    487         mParameters.getInt(CameraParameters::KEY_EXPOSURE_COMPENSATION);
    488     if (current_exposure_compensation != new_exposure_compensation) {
    489       const float exposure_value =
    490           new_exposure_compensation *
    491           new_param.getFloat(CameraParameters::KEY_EXPOSURE_COMPENSATION_STEP);
    492 
    493       getCameraDevice()->setExposureCompensation(exposure_value);
    494     }
    495   }
    496 
    497   const char* new_white_balance =
    498       new_param.get(CameraParameters::KEY_WHITE_BALANCE);
    499   const char* supported_white_balance =
    500       new_param.get(CameraParameters::KEY_SUPPORTED_WHITE_BALANCE);
    501 
    502   if ((supported_white_balance != NULL) && (new_white_balance != NULL) &&
    503       (strstr(supported_white_balance, new_white_balance) != NULL)) {
    504     const char* current_white_balance =
    505         mParameters.get(CameraParameters::KEY_WHITE_BALANCE);
    506     if ((current_white_balance == NULL) ||
    507         (strcmp(current_white_balance, new_white_balance) != 0)) {
    508       ALOGV("Setting white balance to %s", new_white_balance);
    509       getCameraDevice()->setWhiteBalanceMode(new_white_balance);
    510     }
    511   }
    512 
    513   mParameters = new_param;
    514 
    515   return NO_ERROR;
    516 }
    517 
    518 /* A dumb variable indicating "no params" / error on the exit from
    519  * EmulatedCamera::getParameters(). */
    520 static char lNoParam = '\0';
    521 char* EmulatedCamera::getParameters() {
    522   String8 params(mParameters.flatten());
    523   char* ret_str =
    524       reinterpret_cast<char*>(malloc(sizeof(char) * (params.length() + 1)));
    525   memset(ret_str, 0, params.length() + 1);
    526   if (ret_str != NULL) {
    527     strncpy(ret_str, params.string(), params.length() + 1);
    528     return ret_str;
    529   } else {
    530     ALOGE("%s: Unable to allocate string for %s", __FUNCTION__,
    531           params.string());
    532     /* Apparently, we can't return NULL fron this routine. */
    533     return &lNoParam;
    534   }
    535 }
    536 
    537 void EmulatedCamera::putParameters(char* params) {
    538   /* This method simply frees parameters allocated in getParameters(). */
    539   if (params != NULL && params != &lNoParam) {
    540     free(params);
    541   }
    542 }
    543 
    544 status_t EmulatedCamera::sendCommand(int32_t cmd, int32_t arg1, int32_t arg2) {
    545   ALOGV("%s: cmd = %d, arg1 = %d, arg2 = %d", __FUNCTION__, cmd, arg1, arg2);
    546 
    547   switch (cmd) {
    548     case CAMERA_CMD_START_FACE_DETECTION:
    549     case CAMERA_CMD_STOP_FACE_DETECTION:
    550       return -EINVAL;
    551   }
    552 
    553   /* TODO: Future enhancements. */
    554   return 0;
    555 }
    556 
    557 void EmulatedCamera::releaseCamera() {
    558   ALOGV("%s", __FUNCTION__);
    559 
    560   cleanupCamera();
    561 }
    562 
    563 status_t EmulatedCamera::dumpCamera(int /*fd*/) {
    564   ALOGV("%s", __FUNCTION__);
    565 
    566   /* TODO: Future enhancements. */
    567   return -EINVAL;
    568 }
    569 
    570 /****************************************************************************
    571  * Preview management.
    572  ***************************************************************************/
    573 
    574 status_t EmulatedCamera::doStartPreview() {
    575   ALOGV("%s", __FUNCTION__);
    576 
    577   EmulatedCameraDevice* camera_dev = getCameraDevice();
    578   if (camera_dev->isStarted()) {
    579     camera_dev->stopDeliveringFrames();
    580     camera_dev->stopDevice();
    581   }
    582 
    583   status_t res = mPreviewWindow.startPreview();
    584   if (res != NO_ERROR) {
    585     return res;
    586   }
    587 
    588   /* Make sure camera device is connected. */
    589   if (!camera_dev->isConnected()) {
    590     res = camera_dev->connectDevice();
    591     if (res != NO_ERROR) {
    592       mPreviewWindow.stopPreview();
    593       return res;
    594     }
    595   }
    596 
    597   int width, height;
    598   /* Lets see what should we use for frame width, and height. */
    599   if (mParameters.get(CameraParameters::KEY_VIDEO_SIZE) != NULL) {
    600     mParameters.getVideoSize(&width, &height);
    601   } else {
    602     mParameters.getPreviewSize(&width, &height);
    603   }
    604   /* Lets see what should we use for the frame pixel format. Note that there
    605    * are two parameters that define pixel formats for frames sent to the
    606    * application via notification callbacks:
    607    * - KEY_VIDEO_FRAME_FORMAT, that is used when recording video, and
    608    * - KEY_PREVIEW_FORMAT, that is used for preview frame notification.
    609    * We choose one or the other, depending on "recording-hint" property set by
    610    * the framework that indicating intention: video, or preview. */
    611   const char* pix_fmt = NULL;
    612   const char* is_video = mParameters.get(EmulatedCamera::RECORDING_HINT_KEY);
    613   if (is_video == NULL) {
    614     is_video = CameraParameters::FALSE;
    615   }
    616   if (strcmp(is_video, CameraParameters::TRUE) == 0) {
    617     /* Video recording is requested. Lets see if video frame format is set. */
    618     pix_fmt = mParameters.get(CameraParameters::KEY_VIDEO_FRAME_FORMAT);
    619   }
    620   /* If this was not video recording, or video frame format is not set, lets
    621    * use preview pixel format for the main framebuffer. */
    622   if (pix_fmt == NULL) {
    623     pix_fmt = mParameters.getPreviewFormat();
    624   }
    625   if (pix_fmt == NULL) {
    626     ALOGE("%s: Unable to obtain video format", __FUNCTION__);
    627     mPreviewWindow.stopPreview();
    628     return EINVAL;
    629   }
    630 
    631   /* Convert framework's pixel format to the FOURCC one. */
    632   uint32_t org_fmt;
    633   if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_YUV420P) == 0) {
    634     org_fmt = V4L2_PIX_FMT_YUV420;
    635   } else if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_RGBA8888) == 0) {
    636     org_fmt = V4L2_PIX_FMT_RGB32;
    637   } else if (strcmp(pix_fmt, CameraParameters::PIXEL_FORMAT_YUV420SP) == 0) {
    638     org_fmt = V4L2_PIX_FMT_NV21;
    639   } else {
    640     ALOGE("%s: Unsupported pixel format %s", __FUNCTION__, pix_fmt);
    641     mPreviewWindow.stopPreview();
    642     return EINVAL;
    643   }
    644 
    645   /* Fetch the desired frame rate. */
    646   int min_fps_rate, max_fps_rate;
    647   mParameters.getPreviewFpsRange(&min_fps_rate, &max_fps_rate);
    648 
    649   ALOGD("Starting camera: %dx%d -> %.4s(%s)", width, height,
    650         reinterpret_cast<const char*>(&org_fmt), pix_fmt);
    651   res = camera_dev->startDevice(width, height, org_fmt, max_fps_rate);
    652   if (res != NO_ERROR) {
    653     mPreviewWindow.stopPreview();
    654     return res;
    655   }
    656 
    657   res = camera_dev->startDeliveringFrames(false);
    658   if (res != NO_ERROR) {
    659     camera_dev->stopDevice();
    660     mPreviewWindow.stopPreview();
    661   }
    662 
    663   return res;
    664 }
    665 
    666 status_t EmulatedCamera::doStopPreview() {
    667   ALOGV("%s", __FUNCTION__);
    668 
    669   status_t res = NO_ERROR;
    670   if (mPreviewWindow.isPreviewEnabled()) {
    671     /* Stop the camera. */
    672     if (getCameraDevice()->isStarted()) {
    673       getCameraDevice()->stopDeliveringFrames();
    674       res = getCameraDevice()->stopDevice();
    675     }
    676 
    677     if (res == NO_ERROR) {
    678       /* Disable preview as well. */
    679       mPreviewWindow.stopPreview();
    680     }
    681   }
    682 
    683   return NO_ERROR;
    684 }
    685 
    686 /****************************************************************************
    687  * Private API.
    688  ***************************************************************************/
    689 
    690 status_t EmulatedCamera::cleanupCamera() {
    691   status_t res = NO_ERROR;
    692 
    693   /* If preview is running - stop it. */
    694   res = doStopPreview();
    695   if (res != NO_ERROR) {
    696     return -res;
    697   }
    698 
    699   /* Stop and disconnect the camera device. */
    700   EmulatedCameraDevice* const camera_dev = getCameraDevice();
    701   if (camera_dev != NULL) {
    702     if (camera_dev->isStarted()) {
    703       camera_dev->stopDeliveringFrames();
    704       res = camera_dev->stopDevice();
    705       if (res != NO_ERROR) {
    706         return -res;
    707       }
    708     }
    709     if (camera_dev->isConnected()) {
    710       res = camera_dev->disconnectDevice();
    711       if (res != NO_ERROR) {
    712         return -res;
    713       }
    714     }
    715   }
    716 
    717   mCallbackNotifier.cleanupCBNotifier();
    718 
    719   return NO_ERROR;
    720 }
    721 
    722 /****************************************************************************
    723  * Camera API callbacks as defined by camera_device_ops structure.
    724  *
    725  * Callbacks here simply dispatch the calls to an appropriate method inside
    726  * EmulatedCamera instance, defined by the 'dev' parameter.
    727  ***************************************************************************/
    728 
    729 int EmulatedCamera::set_preview_window(struct camera_device* dev,
    730                                        struct preview_stream_ops* window) {
    731   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    732   if (ec == NULL) {
    733     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    734     return -EINVAL;
    735   }
    736   return ec->setPreviewWindow(window);
    737 }
    738 
    739 void EmulatedCamera::set_callbacks(
    740     struct camera_device* dev, camera_notify_callback notify_cb,
    741     camera_data_callback data_cb,
    742     camera_data_timestamp_callback data_cb_timestamp,
    743     camera_request_memory get_memory, void* user) {
    744   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    745   if (ec == NULL) {
    746     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    747     return;
    748   }
    749   ec->setCallbacks(notify_cb, data_cb, data_cb_timestamp, get_memory, user);
    750 }
    751 
    752 void EmulatedCamera::enable_msg_type(struct camera_device* dev,
    753                                      int32_t msg_type) {
    754   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    755   if (ec == NULL) {
    756     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    757     return;
    758   }
    759   ec->enableMsgType(msg_type);
    760 }
    761 
    762 void EmulatedCamera::disable_msg_type(struct camera_device* dev,
    763                                       int32_t msg_type) {
    764   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    765   if (ec == NULL) {
    766     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    767     return;
    768   }
    769   ec->disableMsgType(msg_type);
    770 }
    771 
    772 int EmulatedCamera::msg_type_enabled(struct camera_device* dev,
    773                                      int32_t msg_type) {
    774   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    775   if (ec == NULL) {
    776     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    777     return -EINVAL;
    778   }
    779   return ec->isMsgTypeEnabled(msg_type);
    780 }
    781 
    782 int EmulatedCamera::start_preview(struct camera_device* dev) {
    783   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    784   if (ec == NULL) {
    785     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    786     return -EINVAL;
    787   }
    788   return ec->startPreview();
    789 }
    790 
    791 void EmulatedCamera::stop_preview(struct camera_device* dev) {
    792   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    793   if (ec == NULL) {
    794     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    795     return;
    796   }
    797   ec->stopPreview();
    798 }
    799 
    800 int EmulatedCamera::preview_enabled(struct camera_device* dev) {
    801   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    802   if (ec == NULL) {
    803     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    804     return -EINVAL;
    805   }
    806   return ec->isPreviewEnabled();
    807 }
    808 
    809 int EmulatedCamera::store_meta_data_in_buffers(struct camera_device* dev,
    810                                                int enable) {
    811   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    812   if (ec == NULL) {
    813     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    814     return -EINVAL;
    815   }
    816   return ec->storeMetaDataInBuffers(enable);
    817 }
    818 
    819 int EmulatedCamera::start_recording(struct camera_device* dev) {
    820   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    821   if (ec == NULL) {
    822     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    823     return -EINVAL;
    824   }
    825   return ec->startRecording();
    826 }
    827 
    828 void EmulatedCamera::stop_recording(struct camera_device* dev) {
    829   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    830   if (ec == NULL) {
    831     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    832     return;
    833   }
    834   ec->stopRecording();
    835 }
    836 
    837 int EmulatedCamera::recording_enabled(struct camera_device* dev) {
    838   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    839   if (ec == NULL) {
    840     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    841     return -EINVAL;
    842   }
    843   return ec->isRecordingEnabled();
    844 }
    845 
    846 void EmulatedCamera::release_recording_frame(struct camera_device* dev,
    847                                              const void* opaque) {
    848   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    849   if (ec == NULL) {
    850     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    851     return;
    852   }
    853   ec->releaseRecordingFrame(opaque);
    854 }
    855 
    856 int EmulatedCamera::auto_focus(struct camera_device* dev) {
    857   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    858   if (ec == NULL) {
    859     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    860     return -EINVAL;
    861   }
    862   return ec->setAutoFocus();
    863 }
    864 
    865 int EmulatedCamera::cancel_auto_focus(struct camera_device* dev) {
    866   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    867   if (ec == NULL) {
    868     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    869     return -EINVAL;
    870   }
    871   return ec->cancelAutoFocus();
    872 }
    873 
    874 int EmulatedCamera::take_picture(struct camera_device* dev) {
    875   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    876   if (ec == NULL) {
    877     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    878     return -EINVAL;
    879   }
    880   return ec->takePicture();
    881 }
    882 
    883 int EmulatedCamera::cancel_picture(struct camera_device* dev) {
    884   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    885   if (ec == NULL) {
    886     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    887     return -EINVAL;
    888   }
    889   return ec->cancelPicture();
    890 }
    891 
    892 int EmulatedCamera::set_parameters(struct camera_device* dev,
    893                                    const char* parms) {
    894   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    895   if (ec == NULL) {
    896     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    897     return -EINVAL;
    898   }
    899   return ec->setParameters(parms);
    900 }
    901 
    902 char* EmulatedCamera::get_parameters(struct camera_device* dev) {
    903   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    904   if (ec == NULL) {
    905     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    906     return NULL;
    907   }
    908   return ec->getParameters();
    909 }
    910 
    911 void EmulatedCamera::put_parameters(struct camera_device* dev, char* params) {
    912   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    913   if (ec == NULL) {
    914     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    915     return;
    916   }
    917   ec->putParameters(params);
    918 }
    919 
    920 int EmulatedCamera::send_command(struct camera_device* dev, int32_t cmd,
    921                                  int32_t arg1, int32_t arg2) {
    922   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    923   if (ec == NULL) {
    924     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    925     return -EINVAL;
    926   }
    927   return ec->sendCommand(cmd, arg1, arg2);
    928 }
    929 
    930 void EmulatedCamera::release(struct camera_device* dev) {
    931   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    932   if (ec == NULL) {
    933     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    934     return;
    935   }
    936   ec->releaseCamera();
    937 }
    938 
    939 int EmulatedCamera::dump(struct camera_device* dev, int fd) {
    940   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(dev->priv);
    941   if (ec == NULL) {
    942     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    943     return -EINVAL;
    944   }
    945   return ec->dumpCamera(fd);
    946 }
    947 
    948 int EmulatedCamera::close(struct hw_device_t* device) {
    949   EmulatedCamera* ec = reinterpret_cast<EmulatedCamera*>(
    950       reinterpret_cast<struct camera_device*>(device)->priv);
    951   if (ec == NULL) {
    952     ALOGE("%s: Unexpected NULL camera device", __FUNCTION__);
    953     return -EINVAL;
    954   }
    955   return ec->closeCamera();
    956 }
    957 
    958 /****************************************************************************
    959  * Static initializer for the camera callback API
    960  ****************************************************************************/
    961 
    962 camera_device_ops_t EmulatedCamera::mDeviceOps = {
    963     EmulatedCamera::set_preview_window,
    964     EmulatedCamera::set_callbacks,
    965     EmulatedCamera::enable_msg_type,
    966     EmulatedCamera::disable_msg_type,
    967     EmulatedCamera::msg_type_enabled,
    968     EmulatedCamera::start_preview,
    969     EmulatedCamera::stop_preview,
    970     EmulatedCamera::preview_enabled,
    971     EmulatedCamera::store_meta_data_in_buffers,
    972     EmulatedCamera::start_recording,
    973     EmulatedCamera::stop_recording,
    974     EmulatedCamera::recording_enabled,
    975     EmulatedCamera::release_recording_frame,
    976     EmulatedCamera::auto_focus,
    977     EmulatedCamera::cancel_auto_focus,
    978     EmulatedCamera::take_picture,
    979     EmulatedCamera::cancel_picture,
    980     EmulatedCamera::set_parameters,
    981     EmulatedCamera::get_parameters,
    982     EmulatedCamera::put_parameters,
    983     EmulatedCamera::send_command,
    984     EmulatedCamera::release,
    985     EmulatedCamera::dump};
    986 
    987 /****************************************************************************
    988  * Common keys
    989  ***************************************************************************/
    990 
    991 const char EmulatedCamera::FACING_KEY[] = "prop-facing";
    992 const char EmulatedCamera::ORIENTATION_KEY[] = "prop-orientation";
    993 const char EmulatedCamera::RECORDING_HINT_KEY[] = "recording-hint";
    994 
    995 /****************************************************************************
    996  * Common string values
    997  ***************************************************************************/
    998 
    999 const char EmulatedCamera::FACING_BACK[] = "back";
   1000 const char EmulatedCamera::FACING_FRONT[] = "front";
   1001 
   1002 /****************************************************************************
   1003  * Parameter debugging helpers
   1004  ***************************************************************************/
   1005 
   1006 #if DEBUG_PARAM
   1007 static void PrintParamDiff(const CameraParameters& current,
   1008                            const char* new_par) {
   1009   char tmp[2048];
   1010   const char* wrk = new_par;
   1011 
   1012   /* Divided with ';' */
   1013   const char* next = strchr(wrk, ';');
   1014   while (next != NULL) {
   1015     snprintf(tmp, sizeof(tmp), "%.*s", (int)(intptr_t)(next - wrk), wrk);
   1016     /* in the form key=value */
   1017     char* val = strchr(tmp, '=');
   1018     if (val != NULL) {
   1019       *val = '\0';
   1020       val++;
   1021       const char* in_current = current.get(tmp);
   1022       if (in_current != NULL) {
   1023         if (strcmp(in_current, val)) {
   1024           ALOGD("=== Value changed: %s: %s -> %s", tmp, in_current, val);
   1025         }
   1026       } else {
   1027         ALOGD("+++ New parameter: %s=%s", tmp, val);
   1028       }
   1029     } else {
   1030       ALOGW("No value separator in %s", tmp);
   1031     }
   1032     wrk = next + 1;
   1033     next = strchr(wrk, ';');
   1034   }
   1035 }
   1036 #endif /* DEBUG_PARAM */
   1037 
   1038 }; /* namespace android */
   1039