Home | History | Annotate | Download | only in OMXCameraAdapter
      1 /*
      2  * Copyright (C) Texas Instruments - http://www.ti.com/
      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 * @file OMXCapture.cpp
     19 *
     20 * This file contains functionality for handling image capture.
     21 *
     22 */
     23 
     24 #undef LOG_TAG
     25 
     26 #define LOG_TAG "CameraHAL"
     27 
     28 #include "CameraHal.h"
     29 #include "OMXCameraAdapter.h"
     30 #include "ErrorUtils.h"
     31 
     32 
     33 namespace android {
     34 
     35 status_t OMXCameraAdapter::setParametersCapture(const CameraParameters &params,
     36                                                 BaseCameraAdapter::AdapterState state)
     37 {
     38     status_t ret = NO_ERROR;
     39     const char *str = NULL;
     40     int w, h;
     41     OMX_COLOR_FORMATTYPE pixFormat;
     42     const char *valstr = NULL;
     43 
     44     LOG_FUNCTION_NAME;
     45 
     46     OMXCameraPortParameters *cap;
     47     cap = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
     48 
     49     params.getPictureSize(&w, &h);
     50 
     51     if ( ( w != ( int ) cap->mWidth ) ||
     52           ( h != ( int ) cap->mHeight ) )
     53         {
     54         mPendingCaptureSettings |= SetFormat;
     55         }
     56 
     57     cap->mWidth = w;
     58     cap->mHeight = h;
     59     //TODO: Support more pixelformats
     60     cap->mStride = 2;
     61 
     62     CAMHAL_LOGVB("Image: cap.mWidth = %d", (int)cap->mWidth);
     63     CAMHAL_LOGVB("Image: cap.mHeight = %d", (int)cap->mHeight);
     64 
     65     if ( (valstr = params.getPictureFormat()) != NULL )
     66         {
     67         if (strcmp(valstr, (const char *) CameraParameters::PIXEL_FORMAT_YUV422I) == 0)
     68             {
     69             CAMHAL_LOGDA("CbYCrY format selected");
     70             pixFormat = OMX_COLOR_FormatCbYCrY;
     71             }
     72         else if(strcmp(valstr, (const char *) CameraParameters::PIXEL_FORMAT_YUV420SP) == 0)
     73             {
     74             CAMHAL_LOGDA("YUV420SP format selected");
     75             pixFormat = OMX_COLOR_FormatYUV420SemiPlanar;
     76             }
     77         else if(strcmp(valstr, (const char *) CameraParameters::PIXEL_FORMAT_RGB565) == 0)
     78             {
     79             CAMHAL_LOGDA("RGB565 format selected");
     80             pixFormat = OMX_COLOR_Format16bitRGB565;
     81             }
     82         else if(strcmp(valstr, (const char *) CameraParameters::PIXEL_FORMAT_JPEG) == 0)
     83             {
     84             CAMHAL_LOGDA("JPEG format selected");
     85             pixFormat = OMX_COLOR_FormatUnused;
     86             mCodingMode = CodingNone;
     87             }
     88         else if(strcmp(valstr, (const char *) TICameraParameters::PIXEL_FORMAT_JPS) == 0)
     89             {
     90             CAMHAL_LOGDA("JPS format selected");
     91             pixFormat = OMX_COLOR_FormatUnused;
     92             mCodingMode = CodingJPS;
     93             }
     94         else if(strcmp(valstr, (const char *) TICameraParameters::PIXEL_FORMAT_MPO) == 0)
     95             {
     96             CAMHAL_LOGDA("MPO format selected");
     97             pixFormat = OMX_COLOR_FormatUnused;
     98             mCodingMode = CodingMPO;
     99             }
    100         else if(strcmp(valstr, (const char *) TICameraParameters::PIXEL_FORMAT_RAW_JPEG) == 0)
    101             {
    102             CAMHAL_LOGDA("RAW + JPEG format selected");
    103             pixFormat = OMX_COLOR_FormatUnused;
    104             mCodingMode = CodingRAWJPEG;
    105             }
    106         else if(strcmp(valstr, (const char *) TICameraParameters::PIXEL_FORMAT_RAW_MPO) == 0)
    107             {
    108             CAMHAL_LOGDA("RAW + MPO format selected");
    109             pixFormat = OMX_COLOR_FormatUnused;
    110             mCodingMode = CodingRAWMPO;
    111             }
    112         else if(strcmp(valstr, (const char *) TICameraParameters::PIXEL_FORMAT_RAW) == 0)
    113             {
    114             CAMHAL_LOGDA("RAW Picture format selected");
    115             pixFormat = OMX_COLOR_FormatRawBayer10bit;
    116             }
    117         else
    118             {
    119             CAMHAL_LOGEA("Invalid format, JPEG format selected as default");
    120             pixFormat = OMX_COLOR_FormatUnused;
    121             }
    122         }
    123     else
    124         {
    125         CAMHAL_LOGEA("Picture format is NULL, defaulting to JPEG");
    126         pixFormat = OMX_COLOR_FormatUnused;
    127         }
    128 
    129     // JPEG capture is not supported in video mode by OMX Camera
    130     // Set capture format to yuv422i...jpeg encode will
    131     // be done on A9
    132     valstr = params.get(TICameraParameters::KEY_CAP_MODE);
    133     if ( (valstr && !strcmp(valstr, (const char *) TICameraParameters::VIDEO_MODE)) &&
    134          (pixFormat == OMX_COLOR_FormatUnused) ) {
    135         CAMHAL_LOGDA("Capturing in video mode...selecting yuv422i");
    136         pixFormat = OMX_COLOR_FormatCbYCrY;
    137     }
    138 
    139     if ( pixFormat != cap->mColorFormat )
    140         {
    141         mPendingCaptureSettings |= SetFormat;
    142         cap->mColorFormat = pixFormat;
    143         }
    144 
    145     str = params.get(TICameraParameters::KEY_EXP_BRACKETING_RANGE);
    146     if ( NULL != str ) {
    147         parseExpRange(str, mExposureBracketingValues, EXP_BRACKET_RANGE, mExposureBracketingValidEntries);
    148     } else {
    149         // if bracketing was previously set...we set again before capturing to clear
    150         if (mExposureBracketingValidEntries) mPendingCaptureSettings |= SetExpBracket;
    151         mExposureBracketingValidEntries = 0;
    152     }
    153 
    154     if ( params.getInt(CameraParameters::KEY_ROTATION) != -1 )
    155         {
    156         if (params.getInt(CameraParameters::KEY_ROTATION) != mPictureRotation) {
    157             mPendingCaptureSettings |= SetRotation;
    158         }
    159         mPictureRotation = params.getInt(CameraParameters::KEY_ROTATION);
    160         }
    161     else
    162         {
    163         if (mPictureRotation) mPendingCaptureSettings |= SetRotation;
    164         mPictureRotation = 0;
    165         }
    166 
    167     CAMHAL_LOGVB("Picture Rotation set %d", mPictureRotation);
    168 
    169     // Read Sensor Orientation and set it based on perating mode
    170 
    171      if (( params.getInt(TICameraParameters::KEY_SENSOR_ORIENTATION) != -1 ) && (mCapMode == OMXCameraAdapter::VIDEO_MODE))
    172         {
    173          mSensorOrientation = params.getInt(TICameraParameters::KEY_SENSOR_ORIENTATION);
    174          if (mSensorOrientation == 270 ||mSensorOrientation==90)
    175              {
    176              CAMHAL_LOGEA(" Orientation is 270/90. So setting counter rotation  to Ducati");
    177              mSensorOrientation +=180;
    178              mSensorOrientation%=360;
    179               }
    180          }
    181      else
    182         {
    183          mSensorOrientation = 0;
    184         }
    185 
    186      CAMHAL_LOGVB("Sensor Orientation  set : %d", mSensorOrientation);
    187 
    188     if ( params.getInt(TICameraParameters::KEY_BURST)  >= 1 )
    189         {
    190         if (params.getInt(TICameraParameters::KEY_BURST) != mBurstFrames) {
    191             mPendingCaptureSettings |= SetExpBracket;
    192         }
    193         mBurstFrames = params.getInt(TICameraParameters::KEY_BURST);
    194         }
    195     else
    196         {
    197         if (mBurstFrames != 1) mPendingCaptureSettings |= SetExpBracket;
    198         mBurstFrames = 1;
    199         }
    200 
    201     CAMHAL_LOGVB("Burst Frames set %d", mBurstFrames);
    202 
    203     if ( ( params.getInt(CameraParameters::KEY_JPEG_QUALITY)  >= MIN_JPEG_QUALITY ) &&
    204          ( params.getInt(CameraParameters::KEY_JPEG_QUALITY)  <= MAX_JPEG_QUALITY ) )
    205         {
    206         if (params.getInt(CameraParameters::KEY_JPEG_QUALITY) != mPictureQuality) {
    207             mPendingCaptureSettings |= SetQuality;
    208         }
    209         mPictureQuality = params.getInt(CameraParameters::KEY_JPEG_QUALITY);
    210         }
    211     else
    212         {
    213         if (mPictureQuality != MAX_JPEG_QUALITY) mPendingCaptureSettings |= SetQuality;
    214         mPictureQuality = MAX_JPEG_QUALITY;
    215         }
    216 
    217     CAMHAL_LOGVB("Picture Quality set %d", mPictureQuality);
    218 
    219     if ( params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH)  >= 0 )
    220         {
    221         if (params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH) != mThumbWidth) {
    222             mPendingCaptureSettings |= SetThumb;
    223         }
    224         mThumbWidth = params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH);
    225         }
    226     else
    227         {
    228         if (mThumbWidth != DEFAULT_THUMB_WIDTH) mPendingCaptureSettings |= SetThumb;
    229         mThumbWidth = DEFAULT_THUMB_WIDTH;
    230         }
    231 
    232 
    233     CAMHAL_LOGVB("Picture Thumb width set %d", mThumbWidth);
    234 
    235     if ( params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT)  >= 0 )
    236         {
    237         if (params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT) != mThumbHeight) {
    238             mPendingCaptureSettings |= SetThumb;
    239         }
    240         mThumbHeight = params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT);
    241         }
    242     else
    243         {
    244         if (mThumbHeight != DEFAULT_THUMB_HEIGHT) mPendingCaptureSettings |= SetThumb;
    245         mThumbHeight = DEFAULT_THUMB_HEIGHT;
    246         }
    247 
    248 
    249     CAMHAL_LOGVB("Picture Thumb height set %d", mThumbHeight);
    250 
    251     if ( ( params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY)  >= MIN_JPEG_QUALITY ) &&
    252          ( params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY)  <= MAX_JPEG_QUALITY ) )
    253         {
    254         if (params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY) != mThumbQuality) {
    255             mPendingCaptureSettings |= SetThumb;
    256         }
    257         mThumbQuality = params.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY);
    258         }
    259     else
    260         {
    261         if (mThumbQuality != MAX_JPEG_QUALITY) mPendingCaptureSettings |= SetThumb;
    262         mThumbQuality = MAX_JPEG_QUALITY;
    263         }
    264 
    265     CAMHAL_LOGDB("Thumbnail Quality set %d", mThumbQuality);
    266 
    267     if (mFirstTimeInit) {
    268         mPendingCaptureSettings = ECapturesettingsAll;
    269     }
    270 
    271     if (mPendingCaptureSettings) {
    272         disableImagePort();
    273         if ( NULL != mReleaseImageBuffersCallback ) {
    274             mReleaseImageBuffersCallback(mReleaseData);
    275         }
    276     }
    277 
    278     LOG_FUNCTION_NAME_EXIT;
    279 
    280     return ret;
    281 }
    282 
    283 status_t OMXCameraAdapter::getPictureBufferSize(size_t &length, size_t bufferCount)
    284 {
    285     status_t ret = NO_ERROR;
    286     OMXCameraPortParameters *imgCaptureData = NULL;
    287     OMX_ERRORTYPE eError = OMX_ErrorNone;
    288 
    289     LOG_FUNCTION_NAME;
    290 
    291     if ( NO_ERROR == ret )
    292         {
    293         imgCaptureData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
    294 
    295         imgCaptureData->mNumBufs = bufferCount;
    296 
    297         // check if image port is already configured...
    298         // if it already configured then we don't have to query again
    299         if (!mCaptureConfigured) {
    300             ret = setFormat(OMX_CAMERA_PORT_IMAGE_OUT_IMAGE, *imgCaptureData);
    301         }
    302 
    303         if ( ret == NO_ERROR )
    304             {
    305             length = imgCaptureData->mBufSize;
    306             }
    307         else
    308             {
    309             CAMHAL_LOGEB("setFormat() failed 0x%x", ret);
    310             length = 0;
    311             }
    312         }
    313 
    314     CAMHAL_LOGDB("getPictureBufferSize %d", length);
    315 
    316     LOG_FUNCTION_NAME_EXIT;
    317 
    318     return ret;
    319 }
    320 
    321 status_t OMXCameraAdapter::parseExpRange(const char *rangeStr,
    322                                          int * expRange,
    323                                          size_t count,
    324                                          size_t &validEntries)
    325 {
    326     status_t ret = NO_ERROR;
    327     char *ctx, *expVal;
    328     char *tmp = NULL;
    329     size_t i = 0;
    330 
    331     LOG_FUNCTION_NAME;
    332 
    333     if ( NULL == rangeStr )
    334         {
    335         return -EINVAL;
    336         }
    337 
    338     if ( NULL == expRange )
    339         {
    340         return -EINVAL;
    341         }
    342 
    343     if ( NO_ERROR == ret )
    344         {
    345         tmp = ( char * ) malloc( strlen(rangeStr) + 1 );
    346 
    347         if ( NULL == tmp )
    348             {
    349             CAMHAL_LOGEA("No resources for temporary buffer");
    350             return -1;
    351             }
    352         memset(tmp, '\0', strlen(rangeStr) + 1);
    353 
    354         }
    355 
    356     if ( NO_ERROR == ret )
    357         {
    358         strncpy(tmp, rangeStr, strlen(rangeStr) );
    359         expVal = strtok_r( (char *) tmp, CameraHal::PARAMS_DELIMITER, &ctx);
    360 
    361         i = 0;
    362         while ( ( NULL != expVal ) && ( i < count ) )
    363             {
    364             expRange[i] = atoi(expVal);
    365             expVal = strtok_r(NULL, CameraHal::PARAMS_DELIMITER, &ctx);
    366             i++;
    367             }
    368         validEntries = i;
    369         }
    370 
    371     if ( NULL != tmp )
    372         {
    373         free(tmp);
    374         }
    375 
    376     LOG_FUNCTION_NAME_EXIT;
    377 
    378     return ret;
    379 }
    380 
    381 status_t OMXCameraAdapter::setExposureBracketing(int *evValues,
    382                                                  size_t evCount,
    383                                                  size_t frameCount)
    384 {
    385     status_t ret = NO_ERROR;
    386     OMX_ERRORTYPE eError = OMX_ErrorNone;
    387     OMX_CONFIG_CAPTUREMODETYPE expCapMode;
    388     OMX_CONFIG_EXTCAPTUREMODETYPE extExpCapMode;
    389 
    390     LOG_FUNCTION_NAME;
    391 
    392     if ( OMX_StateInvalid == mComponentState )
    393         {
    394         CAMHAL_LOGEA("OMX component is in invalid state");
    395         ret = -EINVAL;
    396         }
    397 
    398     if ( NULL == evValues )
    399         {
    400         CAMHAL_LOGEA("Exposure compensation values pointer is invalid");
    401         ret = -EINVAL;
    402         }
    403 
    404     if ( NO_ERROR == ret )
    405         {
    406         OMX_INIT_STRUCT_PTR (&expCapMode, OMX_CONFIG_CAPTUREMODETYPE);
    407         expCapMode.nPortIndex = mCameraAdapterParameters.mImagePortIndex;
    408 
    409         /// If frameCount>0 but evCount<=0, then this is the case of HQ burst.
    410         //Otherwise, it is normal HQ capture
    411         ///If frameCount>0 and evCount>0 then this is the cause of HQ Exposure bracketing.
    412         if ( 0 == evCount && 0 == frameCount )
    413             {
    414             expCapMode.bFrameLimited = OMX_FALSE;
    415             }
    416         else
    417             {
    418             expCapMode.bFrameLimited = OMX_TRUE;
    419             expCapMode.nFrameLimit = frameCount;
    420             }
    421 
    422         eError =  OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
    423                                 OMX_IndexConfigCaptureMode,
    424                                 &expCapMode);
    425         if ( OMX_ErrorNone != eError )
    426             {
    427             CAMHAL_LOGEB("Error while configuring capture mode 0x%x", eError);
    428             }
    429         else
    430             {
    431             CAMHAL_LOGDA("Camera capture mode configured successfully");
    432             }
    433         }
    434 
    435     if ( NO_ERROR == ret )
    436         {
    437         OMX_INIT_STRUCT_PTR (&extExpCapMode, OMX_CONFIG_EXTCAPTUREMODETYPE);
    438         extExpCapMode.nPortIndex = mCameraAdapterParameters.mImagePortIndex;
    439 
    440         if ( 0 == evCount )
    441             {
    442             extExpCapMode.bEnableBracketing = OMX_FALSE;
    443             }
    444         else
    445             {
    446             extExpCapMode.bEnableBracketing = OMX_TRUE;
    447             extExpCapMode.tBracketConfigType.eBracketMode = OMX_BracketExposureRelativeInEV;
    448             extExpCapMode.tBracketConfigType.nNbrBracketingValues = evCount - 1;
    449             }
    450 
    451         for ( unsigned int i = 0 ; i < evCount ; i++ )
    452             {
    453             extExpCapMode.tBracketConfigType.nBracketValues[i]  =  ( evValues[i] * ( 1 << Q16_OFFSET ) )  / 10;
    454             }
    455 
    456         eError =  OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
    457                                 ( OMX_INDEXTYPE ) OMX_IndexConfigExtCaptureMode,
    458                                 &extExpCapMode);
    459         if ( OMX_ErrorNone != eError )
    460             {
    461             CAMHAL_LOGEB("Error while configuring extended capture mode 0x%x", eError);
    462             }
    463         else
    464             {
    465             CAMHAL_LOGDA("Extended camera capture mode configured successfully");
    466             }
    467         }
    468 
    469     LOG_FUNCTION_NAME_EXIT;
    470 
    471     return ret;
    472 }
    473 
    474 status_t OMXCameraAdapter::setShutterCallback(bool enabled)
    475 {
    476     status_t ret = NO_ERROR;
    477     OMX_ERRORTYPE eError = OMX_ErrorNone;
    478     OMX_CONFIG_CALLBACKREQUESTTYPE shutterRequstCallback;
    479 
    480     LOG_FUNCTION_NAME;
    481 
    482     if ( OMX_StateExecuting != mComponentState )
    483         {
    484         CAMHAL_LOGEA("OMX component not in executing state");
    485         ret = -1;
    486         }
    487 
    488     if ( NO_ERROR == ret )
    489         {
    490 
    491         OMX_INIT_STRUCT_PTR (&shutterRequstCallback, OMX_CONFIG_CALLBACKREQUESTTYPE);
    492         shutterRequstCallback.nPortIndex = OMX_ALL;
    493 
    494         if ( enabled )
    495             {
    496             shutterRequstCallback.bEnable = OMX_TRUE;
    497             shutterRequstCallback.nIndex = ( OMX_INDEXTYPE ) OMX_TI_IndexConfigShutterCallback;
    498             CAMHAL_LOGDA("Enabling shutter callback");
    499             }
    500         else
    501             {
    502             shutterRequstCallback.bEnable = OMX_FALSE;
    503             shutterRequstCallback.nIndex = ( OMX_INDEXTYPE ) OMX_TI_IndexConfigShutterCallback;
    504             CAMHAL_LOGDA("Disabling shutter callback");
    505             }
    506 
    507         eError =  OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
    508                                 ( OMX_INDEXTYPE ) OMX_IndexConfigCallbackRequest,
    509                                 &shutterRequstCallback);
    510         if ( OMX_ErrorNone != eError )
    511             {
    512             CAMHAL_LOGEB("Error registering shutter callback 0x%x", eError);
    513             ret = -1;
    514             }
    515         else
    516             {
    517             CAMHAL_LOGDB("Shutter callback for index 0x%x registered successfully",
    518                          OMX_TI_IndexConfigShutterCallback);
    519             }
    520         }
    521 
    522     LOG_FUNCTION_NAME_EXIT;
    523 
    524     return ret;
    525 }
    526 
    527 status_t OMXCameraAdapter::doBracketing(OMX_BUFFERHEADERTYPE *pBuffHeader,
    528                                         CameraFrame::FrameType typeOfFrame)
    529 {
    530     status_t ret = NO_ERROR;
    531     int currentBufferIdx, nextBufferIdx;
    532     OMXCameraPortParameters * imgCaptureData = NULL;
    533 
    534     LOG_FUNCTION_NAME;
    535 
    536     imgCaptureData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
    537 
    538     if ( OMX_StateExecuting != mComponentState )
    539         {
    540         CAMHAL_LOGEA("OMX component is not in executing state");
    541         ret = -EINVAL;
    542         }
    543 
    544     if ( NO_ERROR == ret )
    545         {
    546         currentBufferIdx = ( unsigned int ) pBuffHeader->pAppPrivate;
    547 
    548         if ( currentBufferIdx >= imgCaptureData->mNumBufs)
    549             {
    550             CAMHAL_LOGEB("Invalid bracketing buffer index 0x%x", currentBufferIdx);
    551             ret = -EINVAL;
    552             }
    553         }
    554 
    555     if ( NO_ERROR == ret )
    556         {
    557         mBracketingBuffersQueued[currentBufferIdx] = false;
    558         mBracketingBuffersQueuedCount--;
    559 
    560         if ( 0 >= mBracketingBuffersQueuedCount )
    561             {
    562             nextBufferIdx = ( currentBufferIdx + 1 ) % imgCaptureData->mNumBufs;
    563             mBracketingBuffersQueued[nextBufferIdx] = true;
    564             mBracketingBuffersQueuedCount++;
    565             mLastBracetingBufferIdx = nextBufferIdx;
    566             setFrameRefCount(imgCaptureData->mBufferHeader[nextBufferIdx]->pBuffer, typeOfFrame, 1);
    567             returnFrame(imgCaptureData->mBufferHeader[nextBufferIdx]->pBuffer, typeOfFrame);
    568             }
    569         }
    570 
    571     LOG_FUNCTION_NAME_EXIT;
    572 
    573     return ret;
    574 }
    575 
    576 status_t OMXCameraAdapter::sendBracketFrames()
    577 {
    578     status_t ret = NO_ERROR;
    579     int currentBufferIdx;
    580     OMXCameraPortParameters * imgCaptureData = NULL;
    581 
    582     LOG_FUNCTION_NAME;
    583 
    584     imgCaptureData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
    585 
    586     if ( OMX_StateExecuting != mComponentState )
    587         {
    588         CAMHAL_LOGEA("OMX component is not in executing state");
    589         ret = -EINVAL;
    590         }
    591 
    592     if ( NO_ERROR == ret )
    593         {
    594 
    595         currentBufferIdx = mLastBracetingBufferIdx;
    596         do
    597             {
    598             currentBufferIdx++;
    599             currentBufferIdx %= imgCaptureData->mNumBufs;
    600             if (!mBracketingBuffersQueued[currentBufferIdx] )
    601                 {
    602                 CameraFrame cameraFrame;
    603                 sendCallBacks(cameraFrame,
    604                               imgCaptureData->mBufferHeader[currentBufferIdx],
    605                               imgCaptureData->mImageType,
    606                               imgCaptureData);
    607                 }
    608             } while ( currentBufferIdx != mLastBracetingBufferIdx );
    609 
    610         }
    611 
    612     LOG_FUNCTION_NAME_EXIT;
    613 
    614     return ret;
    615 }
    616 
    617 status_t OMXCameraAdapter::startBracketing(int range)
    618 {
    619     status_t ret = NO_ERROR;
    620     OMXCameraPortParameters * imgCaptureData = NULL;
    621 
    622     LOG_FUNCTION_NAME;
    623 
    624     imgCaptureData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
    625 
    626     if ( OMX_StateExecuting != mComponentState )
    627         {
    628         CAMHAL_LOGEA("OMX component is not in executing state");
    629         ret = -EINVAL;
    630         }
    631 
    632         {
    633         Mutex::Autolock lock(mBracketingLock);
    634 
    635         if ( mBracketingEnabled )
    636             {
    637             return ret;
    638             }
    639         }
    640 
    641     if ( 0 == imgCaptureData->mNumBufs )
    642         {
    643         CAMHAL_LOGEB("Image capture buffers set to %d", imgCaptureData->mNumBufs);
    644         ret = -EINVAL;
    645         }
    646 
    647     if ( mPending3Asettings )
    648         apply3Asettings(mParameters3A);
    649 
    650     if ( NO_ERROR == ret )
    651         {
    652         Mutex::Autolock lock(mBracketingLock);
    653 
    654         mBracketingRange = range;
    655         mBracketingBuffersQueued = new bool[imgCaptureData->mNumBufs];
    656         if ( NULL == mBracketingBuffersQueued )
    657             {
    658             CAMHAL_LOGEA("Unable to allocate bracketing management structures");
    659             ret = -1;
    660             }
    661 
    662         if ( NO_ERROR == ret )
    663             {
    664             mBracketingBuffersQueuedCount = imgCaptureData->mNumBufs;
    665             mLastBracetingBufferIdx = mBracketingBuffersQueuedCount - 1;
    666 
    667             for ( int i = 0 ; i  < imgCaptureData->mNumBufs ; i++ )
    668                 {
    669                 mBracketingBuffersQueued[i] = true;
    670                 }
    671 
    672             }
    673         }
    674 
    675     if ( NO_ERROR == ret )
    676         {
    677 
    678         ret = startImageCapture();
    679             {
    680             Mutex::Autolock lock(mBracketingLock);
    681 
    682             if ( NO_ERROR == ret )
    683                 {
    684                 mBracketingEnabled = true;
    685                 }
    686             else
    687                 {
    688                 mBracketingEnabled = false;
    689                 }
    690             }
    691         }
    692 
    693     LOG_FUNCTION_NAME_EXIT;
    694 
    695     return ret;
    696 }
    697 
    698 status_t OMXCameraAdapter::stopBracketing()
    699 {
    700   status_t ret = NO_ERROR;
    701 
    702     LOG_FUNCTION_NAME;
    703 
    704     Mutex::Autolock lock(mBracketingLock);
    705 
    706     if ( NULL != mBracketingBuffersQueued )
    707     {
    708         delete [] mBracketingBuffersQueued;
    709     }
    710 
    711     ret = stopImageCapture();
    712 
    713     mBracketingBuffersQueued = NULL;
    714     mBracketingEnabled = false;
    715     mBracketingBuffersQueuedCount = 0;
    716     mLastBracetingBufferIdx = 0;
    717 
    718     LOG_FUNCTION_NAME_EXIT;
    719 
    720     return ret;
    721 }
    722 
    723 status_t OMXCameraAdapter::startImageCapture()
    724 {
    725     status_t ret = NO_ERROR;
    726     OMX_ERRORTYPE eError = OMX_ErrorNone;
    727     OMXCameraPortParameters * capData = NULL;
    728     OMX_CONFIG_BOOLEANTYPE bOMX;
    729 
    730     LOG_FUNCTION_NAME;
    731 
    732     if(!mCaptureConfigured)
    733         {
    734         ///Image capture was cancelled before we could start
    735         return NO_ERROR;
    736         }
    737 
    738     if ( 0 != mStartCaptureSem.Count() )
    739         {
    740         CAMHAL_LOGEB("Error mStartCaptureSem semaphore count %d", mStartCaptureSem.Count());
    741         return NO_INIT;
    742         }
    743 
    744     // Camera framework doesn't expect face callbacks once capture is triggered
    745     pauseFaceDetection(true);
    746 
    747     //During bracketing image capture is already active
    748     {
    749     Mutex::Autolock lock(mBracketingLock);
    750     if ( mBracketingEnabled )
    751         {
    752         //Stop bracketing, activate normal burst for the remaining images
    753         mBracketingEnabled = false;
    754         mCapturedFrames = mBracketingRange;
    755         ret = sendBracketFrames();
    756         if(ret != NO_ERROR)
    757             goto EXIT;
    758         else
    759             return ret;
    760         }
    761     }
    762 
    763     if ( NO_ERROR == ret ) {
    764         if (mPendingCaptureSettings & SetRotation) {
    765             mPendingCaptureSettings &= ~SetRotation;
    766             ret = setPictureRotation(mPictureRotation);
    767             if ( NO_ERROR != ret ) {
    768                 CAMHAL_LOGEB("Error configuring image rotation %x", ret);
    769             }
    770         }
    771     }
    772 
    773     //OMX shutter callback events are only available in hq mode
    774     if ( (HIGH_QUALITY == mCapMode) || (HIGH_QUALITY_ZSL== mCapMode))
    775         {
    776 
    777         if ( NO_ERROR == ret )
    778             {
    779             ret = RegisterForEvent(mCameraAdapterParameters.mHandleComp,
    780                                         (OMX_EVENTTYPE) OMX_EventIndexSettingChanged,
    781                                         OMX_ALL,
    782                                         OMX_TI_IndexConfigShutterCallback,
    783                                         mStartCaptureSem);
    784             }
    785 
    786         if ( NO_ERROR == ret )
    787             {
    788             ret = setShutterCallback(true);
    789             }
    790 
    791         }
    792 
    793     if ( NO_ERROR == ret ) {
    794         capData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
    795 
    796         ///Queue all the buffers on capture port
    797         for ( int index = 0 ; index < capData->mNumBufs ; index++ ) {
    798             CAMHAL_LOGDB("Queuing buffer on Capture port - 0x%x",
    799                          ( unsigned int ) capData->mBufferHeader[index]->pBuffer);
    800             eError = OMX_FillThisBuffer(mCameraAdapterParameters.mHandleComp,
    801                         (OMX_BUFFERHEADERTYPE*)capData->mBufferHeader[index]);
    802 
    803             GOTO_EXIT_IF((eError!=OMX_ErrorNone), eError);
    804         }
    805 
    806         mWaitingForSnapshot = true;
    807         mCaptureSignalled = false;
    808 
    809         // Capturing command is not needed when capturing in video mode
    810         // Only need to queue buffers on image ports
    811         if (mCapMode != VIDEO_MODE) {
    812             OMX_INIT_STRUCT_PTR (&bOMX, OMX_CONFIG_BOOLEANTYPE);
    813             bOMX.bEnabled = OMX_TRUE;
    814 
    815             /// sending Capturing Command to the component
    816             eError = OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
    817                                    OMX_IndexConfigCapturing,
    818                                    &bOMX);
    819 
    820             CAMHAL_LOGDB("Capture set - 0x%x", eError);
    821 
    822             GOTO_EXIT_IF((eError!=OMX_ErrorNone), eError);
    823         }
    824     }
    825 
    826     //OMX shutter callback events are only available in hq mode
    827     if ( (HIGH_QUALITY == mCapMode) || (HIGH_QUALITY_ZSL== mCapMode))
    828         {
    829 
    830         if ( NO_ERROR == ret )
    831             {
    832             ret = mStartCaptureSem.WaitTimeout(OMX_CAPTURE_TIMEOUT);
    833             }
    834 
    835         //If somethiing bad happened while we wait
    836         if (mComponentState == OMX_StateInvalid)
    837           {
    838             CAMHAL_LOGEA("Invalid State after Image Capture Exitting!!!");
    839             goto EXIT;
    840           }
    841 
    842         if ( NO_ERROR == ret )
    843             {
    844             CAMHAL_LOGDA("Shutter callback received");
    845             notifyShutterSubscribers();
    846             }
    847         else
    848             {
    849             ret |= RemoveEvent(mCameraAdapterParameters.mHandleComp,
    850                                (OMX_EVENTTYPE) OMX_EventIndexSettingChanged,
    851                                OMX_ALL,
    852                                OMX_TI_IndexConfigShutterCallback,
    853                                NULL);
    854             CAMHAL_LOGEA("Timeout expired on shutter callback");
    855             goto EXIT;
    856             }
    857 
    858         }
    859 
    860     return (ret | ErrorUtils::omxToAndroidError(eError));
    861 
    862 EXIT:
    863     CAMHAL_LOGEB("Exiting function %s because of ret %d eError=%x", __FUNCTION__, ret, eError);
    864     mWaitingForSnapshot = false;
    865     mCaptureSignalled = false;
    866     performCleanupAfterError();
    867     LOG_FUNCTION_NAME_EXIT;
    868     return (ret | ErrorUtils::omxToAndroidError(eError));
    869 }
    870 
    871 status_t OMXCameraAdapter::stopImageCapture()
    872 {
    873     status_t ret = NO_ERROR;
    874     OMX_ERRORTYPE eError = OMX_ErrorNone;
    875     OMX_CONFIG_BOOLEANTYPE bOMX;
    876     OMXCameraPortParameters *imgCaptureData = NULL;
    877 
    878     LOG_FUNCTION_NAME;
    879 
    880     if (!mCaptureConfigured) {
    881         //Capture is not ongoing, return from here
    882         return NO_ERROR;
    883     }
    884 
    885     if ( 0 != mStopCaptureSem.Count() ) {
    886         CAMHAL_LOGEB("Error mStopCaptureSem semaphore count %d", mStopCaptureSem.Count());
    887         goto EXIT;
    888     }
    889 
    890     //Disable the callback first
    891     mWaitingForSnapshot = false;
    892     mSnapshotCount = 0;
    893 
    894     // OMX shutter callback events are only available in hq mode
    895     if ((HIGH_QUALITY == mCapMode) || (HIGH_QUALITY_ZSL== mCapMode)) {
    896         //Disable the callback first
    897         ret = setShutterCallback(false);
    898 
    899         // if anybody is waiting on the shutter callback
    900         // signal them and then recreate the semaphore
    901         if ( 0 != mStartCaptureSem.Count() ) {
    902             for (int i = mStopCaptureSem.Count(); i > 0; i--) {
    903                 ret |= SignalEvent(mCameraAdapterParameters.mHandleComp,
    904                                    (OMX_EVENTTYPE) OMX_EventIndexSettingChanged,
    905                                    OMX_ALL,
    906                                    OMX_TI_IndexConfigShutterCallback,
    907                                    NULL );
    908             }
    909             mStartCaptureSem.Create(0);
    910         }
    911     }
    912 
    913     // After capture, face detection should be disabled
    914     // and application needs to restart face detection
    915     stopFaceDetection();
    916 
    917     //Wait here for the capture to be done, in worst case timeout and proceed with cleanup
    918     ret = mCaptureSem.WaitTimeout(OMX_CAPTURE_TIMEOUT);
    919 
    920     //If somethiing bad happened while we wait
    921     if (mComponentState == OMX_StateInvalid)
    922       {
    923         CAMHAL_LOGEA("Invalid State Image Capture Stop Exitting!!!");
    924         goto EXIT;
    925       }
    926 
    927     if ( NO_ERROR != ret ) {
    928         ret |= RemoveEvent(mCameraAdapterParameters.mHandleComp,
    929                            (OMX_EVENTTYPE) OMX_EventIndexSettingChanged,
    930                            OMX_ALL,
    931                            OMX_TI_IndexConfigShutterCallback,
    932                            NULL);
    933         CAMHAL_LOGEA("Timeout expired on capture sem");
    934         goto EXIT;
    935     }
    936 
    937     // Disable image capture
    938     // Capturing command is not needed when capturing in video mode
    939     if (mCapMode != VIDEO_MODE) {
    940         OMX_INIT_STRUCT_PTR (&bOMX, OMX_CONFIG_BOOLEANTYPE);
    941         bOMX.bEnabled = OMX_FALSE;
    942         imgCaptureData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
    943         eError = OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
    944                                OMX_IndexConfigCapturing,
    945                                &bOMX);
    946         if ( OMX_ErrorNone != eError ) {
    947             CAMHAL_LOGDB("Error during SetConfig- 0x%x", eError);
    948             ret = -1;
    949             goto EXIT;
    950         }
    951     }
    952     CAMHAL_LOGDB("Capture set - 0x%x", eError);
    953 
    954     mCaptureSignalled = true; //set this to true if we exited because of timeout
    955 
    956     {
    957         Mutex::Autolock lock(mFrameCountMutex);
    958         mFrameCount = 0;
    959         mFirstFrameCondition.broadcast();
    960     }
    961 
    962     return (ret | ErrorUtils::omxToAndroidError(eError));
    963 
    964 EXIT:
    965     CAMHAL_LOGEB("Exiting function %s because of ret %d eError=%x", __FUNCTION__, ret, eError);
    966     //Release image buffers
    967     if ( NULL != mReleaseImageBuffersCallback ) {
    968         mReleaseImageBuffersCallback(mReleaseData);
    969     }
    970 
    971     {
    972         Mutex::Autolock lock(mFrameCountMutex);
    973         mFrameCount = 0;
    974         mFirstFrameCondition.broadcast();
    975     }
    976 
    977     performCleanupAfterError();
    978     LOG_FUNCTION_NAME_EXIT;
    979     return (ret | ErrorUtils::omxToAndroidError(eError));
    980 }
    981 
    982 status_t OMXCameraAdapter::disableImagePort(){
    983     status_t ret = NO_ERROR;
    984     OMX_ERRORTYPE eError = OMX_ErrorNone;
    985     OMXCameraPortParameters *imgCaptureData = NULL;
    986 
    987     if (!mCaptureConfigured) {
    988         return NO_ERROR;
    989     }
    990 
    991     mCaptureConfigured = false;
    992     imgCaptureData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
    993 
    994     ///Register for Image port Disable event
    995     ret = RegisterForEvent(mCameraAdapterParameters.mHandleComp,
    996                                 OMX_EventCmdComplete,
    997                                 OMX_CommandPortDisable,
    998                                 mCameraAdapterParameters.mImagePortIndex,
    999                                 mStopCaptureSem);
   1000     ///Disable Capture Port
   1001     eError = OMX_SendCommand(mCameraAdapterParameters.mHandleComp,
   1002                                 OMX_CommandPortDisable,
   1003                                 mCameraAdapterParameters.mImagePortIndex,
   1004                                 NULL);
   1005 
   1006     ///Free all the buffers on capture port
   1007     if (imgCaptureData) {
   1008         CAMHAL_LOGDB("Freeing buffer on Capture port - %d", imgCaptureData->mNumBufs);
   1009         for ( int index = 0 ; index < imgCaptureData->mNumBufs ; index++) {
   1010             CAMHAL_LOGDB("Freeing buffer on Capture port - 0x%x",
   1011                          ( unsigned int ) imgCaptureData->mBufferHeader[index]->pBuffer);
   1012             eError = OMX_FreeBuffer(mCameraAdapterParameters.mHandleComp,
   1013                                     mCameraAdapterParameters.mImagePortIndex,
   1014                                     (OMX_BUFFERHEADERTYPE*)imgCaptureData->mBufferHeader[index]);
   1015 
   1016             GOTO_EXIT_IF((eError!=OMX_ErrorNone), eError);
   1017         }
   1018     }
   1019     CAMHAL_LOGDA("Waiting for port disable");
   1020     //Wait for the image port enable event
   1021     ret = mStopCaptureSem.WaitTimeout(OMX_CMD_TIMEOUT);
   1022 
   1023     //If somethiing bad happened while we wait
   1024     if (mComponentState == OMX_StateInvalid)
   1025       {
   1026         CAMHAL_LOGEA("Invalid State after Disable Image Port Exitting!!!");
   1027         goto EXIT;
   1028       }
   1029 
   1030     if ( NO_ERROR == ret ) {
   1031         CAMHAL_LOGDA("Port disabled");
   1032     } else {
   1033         ret |= RemoveEvent(mCameraAdapterParameters.mHandleComp,
   1034                            OMX_EventCmdComplete,
   1035                            OMX_CommandPortDisable,
   1036                            mCameraAdapterParameters.mImagePortIndex,
   1037                            NULL);
   1038         CAMHAL_LOGDA("Timeout expired on port disable");
   1039         goto EXIT;
   1040     }
   1041 
   1042  EXIT:
   1043     return (ret | ErrorUtils::omxToAndroidError(eError));
   1044 }
   1045 
   1046 
   1047 status_t OMXCameraAdapter::UseBuffersCapture(void* bufArr, int num)
   1048 {
   1049     LOG_FUNCTION_NAME;
   1050 
   1051     status_t ret = NO_ERROR;
   1052     OMX_ERRORTYPE eError = OMX_ErrorNone;
   1053     OMXCameraPortParameters * imgCaptureData = NULL;
   1054     uint32_t *buffers = (uint32_t*)bufArr;
   1055     OMXCameraPortParameters cap;
   1056 
   1057     imgCaptureData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex];
   1058 
   1059     if ( 0 != mUseCaptureSem.Count() )
   1060         {
   1061         CAMHAL_LOGEB("Error mUseCaptureSem semaphore count %d", mUseCaptureSem.Count());
   1062         return BAD_VALUE;
   1063         }
   1064 
   1065     // capture is already configured...we can skip this step
   1066     if (mCaptureConfigured) {
   1067 
   1068         if ( NO_ERROR == ret )
   1069             {
   1070             ret = setupEXIF();
   1071             if ( NO_ERROR != ret )
   1072                 {
   1073                 CAMHAL_LOGEB("Error configuring EXIF Buffer %x", ret);
   1074                 }
   1075             }
   1076 
   1077         mCapturedFrames = mBurstFrames;
   1078         return NO_ERROR;
   1079     }
   1080 
   1081     imgCaptureData->mNumBufs = num;
   1082 
   1083     //TODO: Support more pixelformats
   1084 
   1085     CAMHAL_LOGDB("Params Width = %d", (int)imgCaptureData->mWidth);
   1086     CAMHAL_LOGDB("Params Height = %d", (int)imgCaptureData->mWidth);
   1087 
   1088     if (mPendingCaptureSettings & SetFormat) {
   1089         mPendingCaptureSettings &= ~SetFormat;
   1090         ret = setFormat(OMX_CAMERA_PORT_IMAGE_OUT_IMAGE, *imgCaptureData);
   1091         if ( ret != NO_ERROR ) {
   1092             CAMHAL_LOGEB("setFormat() failed %d", ret);
   1093             LOG_FUNCTION_NAME_EXIT;
   1094             return ret;
   1095         }
   1096     }
   1097 
   1098     if (mPendingCaptureSettings & SetThumb) {
   1099         mPendingCaptureSettings &= ~SetThumb;
   1100         ret = setThumbnailParams(mThumbWidth, mThumbHeight, mThumbQuality);
   1101         if ( NO_ERROR != ret) {
   1102             CAMHAL_LOGEB("Error configuring thumbnail size %x", ret);
   1103             return ret;
   1104         }
   1105     }
   1106 
   1107     if (mPendingCaptureSettings & SetExpBracket) {
   1108         mPendingCaptureSettings &= ~SetExpBracket;
   1109         ret = setExposureBracketing( mExposureBracketingValues,
   1110                                      mExposureBracketingValidEntries, mBurstFrames);
   1111         if ( ret != NO_ERROR ) {
   1112             CAMHAL_LOGEB("setExposureBracketing() failed %d", ret);
   1113             goto EXIT;
   1114         }
   1115     }
   1116 
   1117     if (mPendingCaptureSettings & SetQuality) {
   1118         mPendingCaptureSettings &= ~SetQuality;
   1119         ret = setImageQuality(mPictureQuality);
   1120         if ( NO_ERROR != ret) {
   1121             CAMHAL_LOGEB("Error configuring image quality %x", ret);
   1122             goto EXIT;
   1123         }
   1124     }
   1125 
   1126     ///Register for Image port ENABLE event
   1127     ret = RegisterForEvent(mCameraAdapterParameters.mHandleComp,
   1128                            OMX_EventCmdComplete,
   1129                            OMX_CommandPortEnable,
   1130                            mCameraAdapterParameters.mImagePortIndex,
   1131                            mUseCaptureSem);
   1132 
   1133     ///Enable Capture Port
   1134     eError = OMX_SendCommand(mCameraAdapterParameters.mHandleComp,
   1135                              OMX_CommandPortEnable,
   1136                              mCameraAdapterParameters.mImagePortIndex,
   1137                              NULL);
   1138 
   1139     CAMHAL_LOGDB("OMX_UseBuffer = 0x%x", eError);
   1140     GOTO_EXIT_IF(( eError != OMX_ErrorNone ), eError);
   1141 
   1142     for ( int index = 0 ; index < imgCaptureData->mNumBufs ; index++ )
   1143     {
   1144         OMX_BUFFERHEADERTYPE *pBufferHdr;
   1145         CAMHAL_LOGDB("OMX_UseBuffer Capture address: 0x%x, size = %d",
   1146                      (unsigned int)buffers[index],
   1147                      (int)imgCaptureData->mBufSize);
   1148 
   1149         eError = OMX_UseBuffer(mCameraAdapterParameters.mHandleComp,
   1150                                &pBufferHdr,
   1151                                mCameraAdapterParameters.mImagePortIndex,
   1152                                0,
   1153                                mCaptureBuffersLength,
   1154                                (OMX_U8*)buffers[index]);
   1155 
   1156         CAMHAL_LOGDB("OMX_UseBuffer = 0x%x", eError);
   1157         GOTO_EXIT_IF(( eError != OMX_ErrorNone ), eError);
   1158 
   1159         pBufferHdr->pAppPrivate = (OMX_PTR) index;
   1160         pBufferHdr->nSize = sizeof(OMX_BUFFERHEADERTYPE);
   1161         pBufferHdr->nVersion.s.nVersionMajor = 1 ;
   1162         pBufferHdr->nVersion.s.nVersionMinor = 1 ;
   1163         pBufferHdr->nVersion.s.nRevision = 0;
   1164         pBufferHdr->nVersion.s.nStep =  0;
   1165         imgCaptureData->mBufferHeader[index] = pBufferHdr;
   1166     }
   1167 
   1168     //Wait for the image port enable event
   1169     CAMHAL_LOGDA("Waiting for port enable");
   1170     ret = mUseCaptureSem.WaitTimeout(OMX_CMD_TIMEOUT);
   1171 
   1172     //If somethiing bad happened while we wait
   1173     if (mComponentState == OMX_StateInvalid)
   1174       {
   1175         CAMHAL_LOGEA("Invalid State after Enable Image Port Exitting!!!");
   1176         goto EXIT;
   1177       }
   1178 
   1179     if ( ret == NO_ERROR )
   1180         {
   1181         CAMHAL_LOGDA("Port enabled");
   1182         }
   1183     else
   1184         {
   1185         ret |= RemoveEvent(mCameraAdapterParameters.mHandleComp,
   1186                            OMX_EventCmdComplete,
   1187                            OMX_CommandPortEnable,
   1188                            mCameraAdapterParameters.mImagePortIndex,
   1189                            NULL);
   1190         CAMHAL_LOGDA("Timeout expired on port enable");
   1191         goto EXIT;
   1192         }
   1193 
   1194     if ( NO_ERROR == ret )
   1195         {
   1196         ret = setupEXIF();
   1197         if ( NO_ERROR != ret )
   1198             {
   1199             CAMHAL_LOGEB("Error configuring EXIF Buffer %x", ret);
   1200             }
   1201         }
   1202 
   1203     mCapturedFrames = mBurstFrames;
   1204     mCaptureConfigured = true;
   1205 
   1206     return (ret | ErrorUtils::omxToAndroidError(eError));
   1207 
   1208 EXIT:
   1209     CAMHAL_LOGEB("Exiting function %s because of ret %d eError=%x", __FUNCTION__, ret, eError);
   1210     //Release image buffers
   1211     if ( NULL != mReleaseImageBuffersCallback ) {
   1212         mReleaseImageBuffersCallback(mReleaseData);
   1213     }
   1214     performCleanupAfterError();
   1215     LOG_FUNCTION_NAME_EXIT;
   1216     return (ret | ErrorUtils::omxToAndroidError(eError));
   1217 
   1218 }
   1219 
   1220 };
   1221