Home | History | Annotate | Download | only in device3
      1 /*
      2  * Copyright (C) 2013 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #define LOG_TAG "Camera3-Device"
     18 #define ATRACE_TAG ATRACE_TAG_CAMERA
     19 //#define LOG_NDEBUG 0
     20 //#define LOG_NNDEBUG 0  // Per-frame verbose logging
     21 
     22 #ifdef LOG_NNDEBUG
     23 #define ALOGVV(...) ALOGV(__VA_ARGS__)
     24 #else
     25 #define ALOGVV(...) ((void)0)
     26 #endif
     27 
     28 // Convenience macro for transient errors
     29 #define CLOGE(fmt, ...) ALOGE("Camera %d: %s: " fmt, mId, __FUNCTION__, \
     30             ##__VA_ARGS__)
     31 
     32 // Convenience macros for transitioning to the error state
     33 #define SET_ERR(fmt, ...) setErrorState(   \
     34     "%s: " fmt, __FUNCTION__,              \
     35     ##__VA_ARGS__)
     36 #define SET_ERR_L(fmt, ...) setErrorStateLocked( \
     37     "%s: " fmt, __FUNCTION__,                    \
     38     ##__VA_ARGS__)
     39 
     40 #include <inttypes.h>
     41 
     42 #include <utils/Log.h>
     43 #include <utils/Trace.h>
     44 #include <utils/Timers.h>
     45 
     46 #include "utils/CameraTraces.h"
     47 #include "device3/Camera3Device.h"
     48 #include "device3/Camera3OutputStream.h"
     49 #include "device3/Camera3InputStream.h"
     50 #include "device3/Camera3ZslStream.h"
     51 #include "device3/Camera3DummyStream.h"
     52 #include "CameraService.h"
     53 
     54 using namespace android::camera3;
     55 
     56 namespace android {
     57 
     58 Camera3Device::Camera3Device(int id):
     59         mId(id),
     60         mHal3Device(NULL),
     61         mStatus(STATUS_UNINITIALIZED),
     62         mUsePartialResult(false),
     63         mNumPartialResults(1),
     64         mNextResultFrameNumber(0),
     65         mNextShutterFrameNumber(0),
     66         mListener(NULL)
     67 {
     68     ATRACE_CALL();
     69     camera3_callback_ops::notify = &sNotify;
     70     camera3_callback_ops::process_capture_result = &sProcessCaptureResult;
     71     ALOGV("%s: Created device for camera %d", __FUNCTION__, id);
     72 }
     73 
     74 Camera3Device::~Camera3Device()
     75 {
     76     ATRACE_CALL();
     77     ALOGV("%s: Tearing down for camera id %d", __FUNCTION__, mId);
     78     disconnect();
     79 }
     80 
     81 int Camera3Device::getId() const {
     82     return mId;
     83 }
     84 
     85 /**
     86  * CameraDeviceBase interface
     87  */
     88 
     89 status_t Camera3Device::initialize(camera_module_t *module)
     90 {
     91     ATRACE_CALL();
     92     Mutex::Autolock il(mInterfaceLock);
     93     Mutex::Autolock l(mLock);
     94 
     95     ALOGV("%s: Initializing device for camera %d", __FUNCTION__, mId);
     96     if (mStatus != STATUS_UNINITIALIZED) {
     97         CLOGE("Already initialized!");
     98         return INVALID_OPERATION;
     99     }
    100 
    101     /** Open HAL device */
    102 
    103     status_t res;
    104     String8 deviceName = String8::format("%d", mId);
    105 
    106     camera3_device_t *device;
    107 
    108     ATRACE_BEGIN("camera3->open");
    109     res = CameraService::filterOpenErrorCode(module->common.methods->open(
    110         &module->common, deviceName.string(),
    111         reinterpret_cast<hw_device_t**>(&device)));
    112     ATRACE_END();
    113 
    114     if (res != OK) {
    115         SET_ERR_L("Could not open camera: %s (%d)", strerror(-res), res);
    116         return res;
    117     }
    118 
    119     /** Cross-check device version */
    120     if (device->common.version < CAMERA_DEVICE_API_VERSION_3_0) {
    121         SET_ERR_L("Could not open camera: "
    122                 "Camera device should be at least %x, reports %x instead",
    123                 CAMERA_DEVICE_API_VERSION_3_0,
    124                 device->common.version);
    125         device->common.close(&device->common);
    126         return BAD_VALUE;
    127     }
    128 
    129     camera_info info;
    130     res = CameraService::filterGetInfoErrorCode(module->get_camera_info(
    131         mId, &info));
    132     if (res != OK) return res;
    133 
    134     if (info.device_version != device->common.version) {
    135         SET_ERR_L("HAL reporting mismatched camera_info version (%x)"
    136                 " and device version (%x).",
    137                 info.device_version, device->common.version);
    138         device->common.close(&device->common);
    139         return BAD_VALUE;
    140     }
    141 
    142     /** Initialize device with callback functions */
    143 
    144     ATRACE_BEGIN("camera3->initialize");
    145     res = device->ops->initialize(device, this);
    146     ATRACE_END();
    147 
    148     if (res != OK) {
    149         SET_ERR_L("Unable to initialize HAL device: %s (%d)",
    150                 strerror(-res), res);
    151         device->common.close(&device->common);
    152         return BAD_VALUE;
    153     }
    154 
    155     /** Start up status tracker thread */
    156     mStatusTracker = new StatusTracker(this);
    157     res = mStatusTracker->run(String8::format("C3Dev-%d-Status", mId).string());
    158     if (res != OK) {
    159         SET_ERR_L("Unable to start status tracking thread: %s (%d)",
    160                 strerror(-res), res);
    161         device->common.close(&device->common);
    162         mStatusTracker.clear();
    163         return res;
    164     }
    165 
    166     /** Start up request queue thread */
    167 
    168     mRequestThread = new RequestThread(this, mStatusTracker, device);
    169     res = mRequestThread->run(String8::format("C3Dev-%d-ReqQueue", mId).string());
    170     if (res != OK) {
    171         SET_ERR_L("Unable to start request queue thread: %s (%d)",
    172                 strerror(-res), res);
    173         device->common.close(&device->common);
    174         mRequestThread.clear();
    175         return res;
    176     }
    177 
    178     /** Everything is good to go */
    179 
    180     mDeviceVersion = device->common.version;
    181     mDeviceInfo = info.static_camera_characteristics;
    182     mHal3Device = device;
    183     mStatus = STATUS_UNCONFIGURED;
    184     mNextStreamId = 0;
    185     mDummyStreamId = NO_STREAM;
    186     mNeedConfig = true;
    187     mPauseStateNotify = false;
    188 
    189     // Will the HAL be sending in early partial result metadata?
    190     if (mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
    191         camera_metadata_entry partialResultsCount =
    192                 mDeviceInfo.find(ANDROID_REQUEST_PARTIAL_RESULT_COUNT);
    193         if (partialResultsCount.count > 0) {
    194             mNumPartialResults = partialResultsCount.data.i32[0];
    195             mUsePartialResult = (mNumPartialResults > 1);
    196         }
    197     } else {
    198         camera_metadata_entry partialResultsQuirk =
    199                 mDeviceInfo.find(ANDROID_QUIRKS_USE_PARTIAL_RESULT);
    200         if (partialResultsQuirk.count > 0 && partialResultsQuirk.data.u8[0] == 1) {
    201             mUsePartialResult = true;
    202         }
    203     }
    204 
    205     return OK;
    206 }
    207 
    208 status_t Camera3Device::disconnect() {
    209     ATRACE_CALL();
    210     Mutex::Autolock il(mInterfaceLock);
    211 
    212     ALOGV("%s: E", __FUNCTION__);
    213 
    214     status_t res = OK;
    215 
    216     {
    217         Mutex::Autolock l(mLock);
    218         if (mStatus == STATUS_UNINITIALIZED) return res;
    219 
    220         if (mStatus == STATUS_ACTIVE ||
    221                 (mStatus == STATUS_ERROR && mRequestThread != NULL)) {
    222             res = mRequestThread->clearRepeatingRequests();
    223             if (res != OK) {
    224                 SET_ERR_L("Can't stop streaming");
    225                 // Continue to close device even in case of error
    226             } else {
    227                 res = waitUntilStateThenRelock(/*active*/ false, kShutdownTimeout);
    228                 if (res != OK) {
    229                     SET_ERR_L("Timeout waiting for HAL to drain");
    230                     // Continue to close device even in case of error
    231                 }
    232             }
    233         }
    234 
    235         if (mStatus == STATUS_ERROR) {
    236             CLOGE("Shutting down in an error state");
    237         }
    238 
    239         if (mStatusTracker != NULL) {
    240             mStatusTracker->requestExit();
    241         }
    242 
    243         if (mRequestThread != NULL) {
    244             mRequestThread->requestExit();
    245         }
    246 
    247         mOutputStreams.clear();
    248         mInputStream.clear();
    249     }
    250 
    251     // Joining done without holding mLock, otherwise deadlocks may ensue
    252     // as the threads try to access parent state
    253     if (mRequestThread != NULL && mStatus != STATUS_ERROR) {
    254         // HAL may be in a bad state, so waiting for request thread
    255         // (which may be stuck in the HAL processCaptureRequest call)
    256         // could be dangerous.
    257         mRequestThread->join();
    258     }
    259 
    260     if (mStatusTracker != NULL) {
    261         mStatusTracker->join();
    262     }
    263 
    264     {
    265         Mutex::Autolock l(mLock);
    266 
    267         mRequestThread.clear();
    268         mStatusTracker.clear();
    269 
    270         if (mHal3Device != NULL) {
    271             ATRACE_BEGIN("camera3->close");
    272             mHal3Device->common.close(&mHal3Device->common);
    273             ATRACE_END();
    274             mHal3Device = NULL;
    275         }
    276 
    277         mStatus = STATUS_UNINITIALIZED;
    278     }
    279 
    280     ALOGV("%s: X", __FUNCTION__);
    281     return res;
    282 }
    283 
    284 // For dumping/debugging only -
    285 // try to acquire a lock a few times, eventually give up to proceed with
    286 // debug/dump operations
    287 bool Camera3Device::tryLockSpinRightRound(Mutex& lock) {
    288     bool gotLock = false;
    289     for (size_t i = 0; i < kDumpLockAttempts; ++i) {
    290         if (lock.tryLock() == NO_ERROR) {
    291             gotLock = true;
    292             break;
    293         } else {
    294             usleep(kDumpSleepDuration);
    295         }
    296     }
    297     return gotLock;
    298 }
    299 
    300 Camera3Device::Size Camera3Device::getMaxJpegResolution() const {
    301     int32_t maxJpegWidth = 0, maxJpegHeight = 0;
    302     if (mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
    303         const int STREAM_CONFIGURATION_SIZE = 4;
    304         const int STREAM_FORMAT_OFFSET = 0;
    305         const int STREAM_WIDTH_OFFSET = 1;
    306         const int STREAM_HEIGHT_OFFSET = 2;
    307         const int STREAM_IS_INPUT_OFFSET = 3;
    308         camera_metadata_ro_entry_t availableStreamConfigs =
    309                 mDeviceInfo.find(ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS);
    310         if (availableStreamConfigs.count == 0 ||
    311                 availableStreamConfigs.count % STREAM_CONFIGURATION_SIZE != 0) {
    312             return Size(0, 0);
    313         }
    314 
    315         // Get max jpeg size (area-wise).
    316         for (size_t i=0; i < availableStreamConfigs.count; i+= STREAM_CONFIGURATION_SIZE) {
    317             int32_t format = availableStreamConfigs.data.i32[i + STREAM_FORMAT_OFFSET];
    318             int32_t width = availableStreamConfigs.data.i32[i + STREAM_WIDTH_OFFSET];
    319             int32_t height = availableStreamConfigs.data.i32[i + STREAM_HEIGHT_OFFSET];
    320             int32_t isInput = availableStreamConfigs.data.i32[i + STREAM_IS_INPUT_OFFSET];
    321             if (isInput == ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT
    322                     && format == HAL_PIXEL_FORMAT_BLOB &&
    323                     (width * height > maxJpegWidth * maxJpegHeight)) {
    324                 maxJpegWidth = width;
    325                 maxJpegHeight = height;
    326             }
    327         }
    328     } else {
    329         camera_metadata_ro_entry availableJpegSizes =
    330                 mDeviceInfo.find(ANDROID_SCALER_AVAILABLE_JPEG_SIZES);
    331         if (availableJpegSizes.count == 0 || availableJpegSizes.count % 2 != 0) {
    332             return Size(0, 0);
    333         }
    334 
    335         // Get max jpeg size (area-wise).
    336         for (size_t i = 0; i < availableJpegSizes.count; i += 2) {
    337             if ((availableJpegSizes.data.i32[i] * availableJpegSizes.data.i32[i + 1])
    338                     > (maxJpegWidth * maxJpegHeight)) {
    339                 maxJpegWidth = availableJpegSizes.data.i32[i];
    340                 maxJpegHeight = availableJpegSizes.data.i32[i + 1];
    341             }
    342         }
    343     }
    344     return Size(maxJpegWidth, maxJpegHeight);
    345 }
    346 
    347 ssize_t Camera3Device::getJpegBufferSize(uint32_t width, uint32_t height) const {
    348     // Get max jpeg size (area-wise).
    349     Size maxJpegResolution = getMaxJpegResolution();
    350     if (maxJpegResolution.width == 0) {
    351         ALOGE("%s: Camera %d: Can't find find valid available jpeg sizes in static metadata!",
    352                 __FUNCTION__, mId);
    353         return BAD_VALUE;
    354     }
    355 
    356     // Get max jpeg buffer size
    357     ssize_t maxJpegBufferSize = 0;
    358     camera_metadata_ro_entry jpegBufMaxSize = mDeviceInfo.find(ANDROID_JPEG_MAX_SIZE);
    359     if (jpegBufMaxSize.count == 0) {
    360         ALOGE("%s: Camera %d: Can't find maximum JPEG size in static metadata!", __FUNCTION__, mId);
    361         return BAD_VALUE;
    362     }
    363     maxJpegBufferSize = jpegBufMaxSize.data.i32[0];
    364     assert(kMinJpegBufferSize < maxJpegBufferSize);
    365 
    366     // Calculate final jpeg buffer size for the given resolution.
    367     float scaleFactor = ((float) (width * height)) /
    368             (maxJpegResolution.width * maxJpegResolution.height);
    369     ssize_t jpegBufferSize = scaleFactor * (maxJpegBufferSize - kMinJpegBufferSize) +
    370             kMinJpegBufferSize;
    371     if (jpegBufferSize > maxJpegBufferSize) {
    372         jpegBufferSize = maxJpegBufferSize;
    373     }
    374 
    375     return jpegBufferSize;
    376 }
    377 
    378 status_t Camera3Device::dump(int fd, const Vector<String16> &args) {
    379     ATRACE_CALL();
    380     (void)args;
    381 
    382     // Try to lock, but continue in case of failure (to avoid blocking in
    383     // deadlocks)
    384     bool gotInterfaceLock = tryLockSpinRightRound(mInterfaceLock);
    385     bool gotLock = tryLockSpinRightRound(mLock);
    386 
    387     ALOGW_IF(!gotInterfaceLock,
    388             "Camera %d: %s: Unable to lock interface lock, proceeding anyway",
    389             mId, __FUNCTION__);
    390     ALOGW_IF(!gotLock,
    391             "Camera %d: %s: Unable to lock main lock, proceeding anyway",
    392             mId, __FUNCTION__);
    393 
    394     String8 lines;
    395 
    396     const char *status =
    397             mStatus == STATUS_ERROR         ? "ERROR" :
    398             mStatus == STATUS_UNINITIALIZED ? "UNINITIALIZED" :
    399             mStatus == STATUS_UNCONFIGURED  ? "UNCONFIGURED" :
    400             mStatus == STATUS_CONFIGURED    ? "CONFIGURED" :
    401             mStatus == STATUS_ACTIVE        ? "ACTIVE" :
    402             "Unknown";
    403 
    404     lines.appendFormat("    Device status: %s\n", status);
    405     if (mStatus == STATUS_ERROR) {
    406         lines.appendFormat("    Error cause: %s\n", mErrorCause.string());
    407     }
    408     lines.appendFormat("    Stream configuration:\n");
    409 
    410     if (mInputStream != NULL) {
    411         write(fd, lines.string(), lines.size());
    412         mInputStream->dump(fd, args);
    413     } else {
    414         lines.appendFormat("      No input stream.\n");
    415         write(fd, lines.string(), lines.size());
    416     }
    417     for (size_t i = 0; i < mOutputStreams.size(); i++) {
    418         mOutputStreams[i]->dump(fd,args);
    419     }
    420 
    421     lines = String8("    In-flight requests:\n");
    422     if (mInFlightMap.size() == 0) {
    423         lines.append("      None\n");
    424     } else {
    425         for (size_t i = 0; i < mInFlightMap.size(); i++) {
    426             InFlightRequest r = mInFlightMap.valueAt(i);
    427             lines.appendFormat("      Frame %d |  Timestamp: %" PRId64 ", metadata"
    428                     " arrived: %s, buffers left: %d\n", mInFlightMap.keyAt(i),
    429                     r.shutterTimestamp, r.haveResultMetadata ? "true" : "false",
    430                     r.numBuffersLeft);
    431         }
    432     }
    433     write(fd, lines.string(), lines.size());
    434 
    435     {
    436         lines = String8("    Last request sent:\n");
    437         write(fd, lines.string(), lines.size());
    438 
    439         CameraMetadata lastRequest = getLatestRequestLocked();
    440         lastRequest.dump(fd, /*verbosity*/2, /*indentation*/6);
    441     }
    442 
    443     if (mHal3Device != NULL) {
    444         lines = String8("    HAL device dump:\n");
    445         write(fd, lines.string(), lines.size());
    446         mHal3Device->ops->dump(mHal3Device, fd);
    447     }
    448 
    449     if (gotLock) mLock.unlock();
    450     if (gotInterfaceLock) mInterfaceLock.unlock();
    451 
    452     return OK;
    453 }
    454 
    455 const CameraMetadata& Camera3Device::info() const {
    456     ALOGVV("%s: E", __FUNCTION__);
    457     if (CC_UNLIKELY(mStatus == STATUS_UNINITIALIZED ||
    458                     mStatus == STATUS_ERROR)) {
    459         ALOGW("%s: Access to static info %s!", __FUNCTION__,
    460                 mStatus == STATUS_ERROR ?
    461                 "when in error state" : "before init");
    462     }
    463     return mDeviceInfo;
    464 }
    465 
    466 status_t Camera3Device::checkStatusOkToCaptureLocked() {
    467     switch (mStatus) {
    468         case STATUS_ERROR:
    469             CLOGE("Device has encountered a serious error");
    470             return INVALID_OPERATION;
    471         case STATUS_UNINITIALIZED:
    472             CLOGE("Device not initialized");
    473             return INVALID_OPERATION;
    474         case STATUS_UNCONFIGURED:
    475         case STATUS_CONFIGURED:
    476         case STATUS_ACTIVE:
    477             // OK
    478             break;
    479         default:
    480             SET_ERR_L("Unexpected status: %d", mStatus);
    481             return INVALID_OPERATION;
    482     }
    483     return OK;
    484 }
    485 
    486 status_t Camera3Device::convertMetadataListToRequestListLocked(
    487         const List<const CameraMetadata> &metadataList, RequestList *requestList) {
    488     if (requestList == NULL) {
    489         CLOGE("requestList cannot be NULL.");
    490         return BAD_VALUE;
    491     }
    492 
    493     int32_t burstId = 0;
    494     for (List<const CameraMetadata>::const_iterator it = metadataList.begin();
    495             it != metadataList.end(); ++it) {
    496         sp<CaptureRequest> newRequest = setUpRequestLocked(*it);
    497         if (newRequest == 0) {
    498             CLOGE("Can't create capture request");
    499             return BAD_VALUE;
    500         }
    501 
    502         // Setup burst Id and request Id
    503         newRequest->mResultExtras.burstId = burstId++;
    504         if (it->exists(ANDROID_REQUEST_ID)) {
    505             if (it->find(ANDROID_REQUEST_ID).count == 0) {
    506                 CLOGE("RequestID entry exists; but must not be empty in metadata");
    507                 return BAD_VALUE;
    508             }
    509             newRequest->mResultExtras.requestId = it->find(ANDROID_REQUEST_ID).data.i32[0];
    510         } else {
    511             CLOGE("RequestID does not exist in metadata");
    512             return BAD_VALUE;
    513         }
    514 
    515         requestList->push_back(newRequest);
    516 
    517         ALOGV("%s: requestId = %" PRId32, __FUNCTION__, newRequest->mResultExtras.requestId);
    518     }
    519     return OK;
    520 }
    521 
    522 status_t Camera3Device::capture(CameraMetadata &request, int64_t* /*lastFrameNumber*/) {
    523     ATRACE_CALL();
    524 
    525     List<const CameraMetadata> requests;
    526     requests.push_back(request);
    527     return captureList(requests, /*lastFrameNumber*/NULL);
    528 }
    529 
    530 status_t Camera3Device::submitRequestsHelper(
    531         const List<const CameraMetadata> &requests, bool repeating,
    532         /*out*/
    533         int64_t *lastFrameNumber) {
    534     ATRACE_CALL();
    535     Mutex::Autolock il(mInterfaceLock);
    536     Mutex::Autolock l(mLock);
    537 
    538     status_t res = checkStatusOkToCaptureLocked();
    539     if (res != OK) {
    540         // error logged by previous call
    541         return res;
    542     }
    543 
    544     RequestList requestList;
    545 
    546     res = convertMetadataListToRequestListLocked(requests, /*out*/&requestList);
    547     if (res != OK) {
    548         // error logged by previous call
    549         return res;
    550     }
    551 
    552     if (repeating) {
    553         res = mRequestThread->setRepeatingRequests(requestList, lastFrameNumber);
    554     } else {
    555         res = mRequestThread->queueRequestList(requestList, lastFrameNumber);
    556     }
    557 
    558     if (res == OK) {
    559         waitUntilStateThenRelock(/*active*/true, kActiveTimeout);
    560         if (res != OK) {
    561             SET_ERR_L("Can't transition to active in %f seconds!",
    562                     kActiveTimeout/1e9);
    563         }
    564         ALOGV("Camera %d: Capture request %" PRId32 " enqueued", mId,
    565               (*(requestList.begin()))->mResultExtras.requestId);
    566     } else {
    567         CLOGE("Cannot queue request. Impossible.");
    568         return BAD_VALUE;
    569     }
    570 
    571     return res;
    572 }
    573 
    574 status_t Camera3Device::captureList(const List<const CameraMetadata> &requests,
    575                                     int64_t *lastFrameNumber) {
    576     ATRACE_CALL();
    577 
    578     return submitRequestsHelper(requests, /*repeating*/false, lastFrameNumber);
    579 }
    580 
    581 status_t Camera3Device::setStreamingRequest(const CameraMetadata &request,
    582                                             int64_t* /*lastFrameNumber*/) {
    583     ATRACE_CALL();
    584 
    585     List<const CameraMetadata> requests;
    586     requests.push_back(request);
    587     return setStreamingRequestList(requests, /*lastFrameNumber*/NULL);
    588 }
    589 
    590 status_t Camera3Device::setStreamingRequestList(const List<const CameraMetadata> &requests,
    591                                                 int64_t *lastFrameNumber) {
    592     ATRACE_CALL();
    593 
    594     return submitRequestsHelper(requests, /*repeating*/true, lastFrameNumber);
    595 }
    596 
    597 sp<Camera3Device::CaptureRequest> Camera3Device::setUpRequestLocked(
    598         const CameraMetadata &request) {
    599     status_t res;
    600 
    601     if (mStatus == STATUS_UNCONFIGURED || mNeedConfig) {
    602         res = configureStreamsLocked();
    603         // Stream configuration failed due to unsupported configuration.
    604         // Device back to unconfigured state. Client might try other configuraitons
    605         if (res == BAD_VALUE && mStatus == STATUS_UNCONFIGURED) {
    606             CLOGE("No streams configured");
    607             return NULL;
    608         }
    609         // Stream configuration failed for other reason. Fatal.
    610         if (res != OK) {
    611             SET_ERR_L("Can't set up streams: %s (%d)", strerror(-res), res);
    612             return NULL;
    613         }
    614         // Stream configuration successfully configure to empty stream configuration.
    615         if (mStatus == STATUS_UNCONFIGURED) {
    616             CLOGE("No streams configured");
    617             return NULL;
    618         }
    619     }
    620 
    621     sp<CaptureRequest> newRequest = createCaptureRequest(request);
    622     return newRequest;
    623 }
    624 
    625 status_t Camera3Device::clearStreamingRequest(int64_t *lastFrameNumber) {
    626     ATRACE_CALL();
    627     Mutex::Autolock il(mInterfaceLock);
    628     Mutex::Autolock l(mLock);
    629 
    630     switch (mStatus) {
    631         case STATUS_ERROR:
    632             CLOGE("Device has encountered a serious error");
    633             return INVALID_OPERATION;
    634         case STATUS_UNINITIALIZED:
    635             CLOGE("Device not initialized");
    636             return INVALID_OPERATION;
    637         case STATUS_UNCONFIGURED:
    638         case STATUS_CONFIGURED:
    639         case STATUS_ACTIVE:
    640             // OK
    641             break;
    642         default:
    643             SET_ERR_L("Unexpected status: %d", mStatus);
    644             return INVALID_OPERATION;
    645     }
    646     ALOGV("Camera %d: Clearing repeating request", mId);
    647 
    648     return mRequestThread->clearRepeatingRequests(lastFrameNumber);
    649 }
    650 
    651 status_t Camera3Device::waitUntilRequestReceived(int32_t requestId, nsecs_t timeout) {
    652     ATRACE_CALL();
    653     Mutex::Autolock il(mInterfaceLock);
    654 
    655     return mRequestThread->waitUntilRequestProcessed(requestId, timeout);
    656 }
    657 
    658 status_t Camera3Device::createInputStream(
    659         uint32_t width, uint32_t height, int format, int *id) {
    660     ATRACE_CALL();
    661     Mutex::Autolock il(mInterfaceLock);
    662     Mutex::Autolock l(mLock);
    663     ALOGV("Camera %d: Creating new input stream %d: %d x %d, format %d",
    664             mId, mNextStreamId, width, height, format);
    665 
    666     status_t res;
    667     bool wasActive = false;
    668 
    669     switch (mStatus) {
    670         case STATUS_ERROR:
    671             ALOGE("%s: Device has encountered a serious error", __FUNCTION__);
    672             return INVALID_OPERATION;
    673         case STATUS_UNINITIALIZED:
    674             ALOGE("%s: Device not initialized", __FUNCTION__);
    675             return INVALID_OPERATION;
    676         case STATUS_UNCONFIGURED:
    677         case STATUS_CONFIGURED:
    678             // OK
    679             break;
    680         case STATUS_ACTIVE:
    681             ALOGV("%s: Stopping activity to reconfigure streams", __FUNCTION__);
    682             res = internalPauseAndWaitLocked();
    683             if (res != OK) {
    684                 SET_ERR_L("Can't pause captures to reconfigure streams!");
    685                 return res;
    686             }
    687             wasActive = true;
    688             break;
    689         default:
    690             SET_ERR_L("%s: Unexpected status: %d", mStatus);
    691             return INVALID_OPERATION;
    692     }
    693     assert(mStatus != STATUS_ACTIVE);
    694 
    695     if (mInputStream != 0) {
    696         ALOGE("%s: Cannot create more than 1 input stream", __FUNCTION__);
    697         return INVALID_OPERATION;
    698     }
    699 
    700     sp<Camera3InputStream> newStream = new Camera3InputStream(mNextStreamId,
    701                 width, height, format);
    702     newStream->setStatusTracker(mStatusTracker);
    703 
    704     mInputStream = newStream;
    705 
    706     *id = mNextStreamId++;
    707 
    708     // Continue captures if active at start
    709     if (wasActive) {
    710         ALOGV("%s: Restarting activity to reconfigure streams", __FUNCTION__);
    711         res = configureStreamsLocked();
    712         if (res != OK) {
    713             ALOGE("%s: Can't reconfigure device for new stream %d: %s (%d)",
    714                     __FUNCTION__, mNextStreamId, strerror(-res), res);
    715             return res;
    716         }
    717         internalResumeLocked();
    718     }
    719 
    720     ALOGV("Camera %d: Created input stream", mId);
    721     return OK;
    722 }
    723 
    724 
    725 status_t Camera3Device::createZslStream(
    726             uint32_t width, uint32_t height,
    727             int depth,
    728             /*out*/
    729             int *id,
    730             sp<Camera3ZslStream>* zslStream) {
    731     ATRACE_CALL();
    732     Mutex::Autolock il(mInterfaceLock);
    733     Mutex::Autolock l(mLock);
    734     ALOGV("Camera %d: Creating ZSL stream %d: %d x %d, depth %d",
    735             mId, mNextStreamId, width, height, depth);
    736 
    737     status_t res;
    738     bool wasActive = false;
    739 
    740     switch (mStatus) {
    741         case STATUS_ERROR:
    742             ALOGE("%s: Device has encountered a serious error", __FUNCTION__);
    743             return INVALID_OPERATION;
    744         case STATUS_UNINITIALIZED:
    745             ALOGE("%s: Device not initialized", __FUNCTION__);
    746             return INVALID_OPERATION;
    747         case STATUS_UNCONFIGURED:
    748         case STATUS_CONFIGURED:
    749             // OK
    750             break;
    751         case STATUS_ACTIVE:
    752             ALOGV("%s: Stopping activity to reconfigure streams", __FUNCTION__);
    753             res = internalPauseAndWaitLocked();
    754             if (res != OK) {
    755                 SET_ERR_L("Can't pause captures to reconfigure streams!");
    756                 return res;
    757             }
    758             wasActive = true;
    759             break;
    760         default:
    761             SET_ERR_L("Unexpected status: %d", mStatus);
    762             return INVALID_OPERATION;
    763     }
    764     assert(mStatus != STATUS_ACTIVE);
    765 
    766     if (mInputStream != 0) {
    767         ALOGE("%s: Cannot create more than 1 input stream", __FUNCTION__);
    768         return INVALID_OPERATION;
    769     }
    770 
    771     sp<Camera3ZslStream> newStream = new Camera3ZslStream(mNextStreamId,
    772                 width, height, depth);
    773     newStream->setStatusTracker(mStatusTracker);
    774 
    775     res = mOutputStreams.add(mNextStreamId, newStream);
    776     if (res < 0) {
    777         ALOGE("%s: Can't add new stream to set: %s (%d)",
    778                 __FUNCTION__, strerror(-res), res);
    779         return res;
    780     }
    781     mInputStream = newStream;
    782 
    783     mNeedConfig = true;
    784 
    785     *id = mNextStreamId++;
    786     *zslStream = newStream;
    787 
    788     // Continue captures if active at start
    789     if (wasActive) {
    790         ALOGV("%s: Restarting activity to reconfigure streams", __FUNCTION__);
    791         res = configureStreamsLocked();
    792         if (res != OK) {
    793             ALOGE("%s: Can't reconfigure device for new stream %d: %s (%d)",
    794                     __FUNCTION__, mNextStreamId, strerror(-res), res);
    795             return res;
    796         }
    797         internalResumeLocked();
    798     }
    799 
    800     ALOGV("Camera %d: Created ZSL stream", mId);
    801     return OK;
    802 }
    803 
    804 status_t Camera3Device::createStream(sp<ANativeWindow> consumer,
    805         uint32_t width, uint32_t height, int format, int *id) {
    806     ATRACE_CALL();
    807     Mutex::Autolock il(mInterfaceLock);
    808     Mutex::Autolock l(mLock);
    809     ALOGV("Camera %d: Creating new stream %d: %d x %d, format %d",
    810             mId, mNextStreamId, width, height, format);
    811 
    812     status_t res;
    813     bool wasActive = false;
    814 
    815     switch (mStatus) {
    816         case STATUS_ERROR:
    817             CLOGE("Device has encountered a serious error");
    818             return INVALID_OPERATION;
    819         case STATUS_UNINITIALIZED:
    820             CLOGE("Device not initialized");
    821             return INVALID_OPERATION;
    822         case STATUS_UNCONFIGURED:
    823         case STATUS_CONFIGURED:
    824             // OK
    825             break;
    826         case STATUS_ACTIVE:
    827             ALOGV("%s: Stopping activity to reconfigure streams", __FUNCTION__);
    828             res = internalPauseAndWaitLocked();
    829             if (res != OK) {
    830                 SET_ERR_L("Can't pause captures to reconfigure streams!");
    831                 return res;
    832             }
    833             wasActive = true;
    834             break;
    835         default:
    836             SET_ERR_L("Unexpected status: %d", mStatus);
    837             return INVALID_OPERATION;
    838     }
    839     assert(mStatus != STATUS_ACTIVE);
    840 
    841     sp<Camera3OutputStream> newStream;
    842     if (format == HAL_PIXEL_FORMAT_BLOB) {
    843         ssize_t jpegBufferSize = getJpegBufferSize(width, height);
    844         if (jpegBufferSize <= 0) {
    845             SET_ERR_L("Invalid jpeg buffer size %zd", jpegBufferSize);
    846             return BAD_VALUE;
    847         }
    848 
    849         newStream = new Camera3OutputStream(mNextStreamId, consumer,
    850                 width, height, jpegBufferSize, format);
    851     } else {
    852         newStream = new Camera3OutputStream(mNextStreamId, consumer,
    853                 width, height, format);
    854     }
    855     newStream->setStatusTracker(mStatusTracker);
    856 
    857     res = mOutputStreams.add(mNextStreamId, newStream);
    858     if (res < 0) {
    859         SET_ERR_L("Can't add new stream to set: %s (%d)", strerror(-res), res);
    860         return res;
    861     }
    862 
    863     *id = mNextStreamId++;
    864     mNeedConfig = true;
    865 
    866     // Continue captures if active at start
    867     if (wasActive) {
    868         ALOGV("%s: Restarting activity to reconfigure streams", __FUNCTION__);
    869         res = configureStreamsLocked();
    870         if (res != OK) {
    871             CLOGE("Can't reconfigure device for new stream %d: %s (%d)",
    872                     mNextStreamId, strerror(-res), res);
    873             return res;
    874         }
    875         internalResumeLocked();
    876     }
    877     ALOGV("Camera %d: Created new stream", mId);
    878     return OK;
    879 }
    880 
    881 status_t Camera3Device::createReprocessStreamFromStream(int outputId, int *id) {
    882     ATRACE_CALL();
    883     (void)outputId; (void)id;
    884 
    885     CLOGE("Unimplemented");
    886     return INVALID_OPERATION;
    887 }
    888 
    889 
    890 status_t Camera3Device::getStreamInfo(int id,
    891         uint32_t *width, uint32_t *height, uint32_t *format) {
    892     ATRACE_CALL();
    893     Mutex::Autolock il(mInterfaceLock);
    894     Mutex::Autolock l(mLock);
    895 
    896     switch (mStatus) {
    897         case STATUS_ERROR:
    898             CLOGE("Device has encountered a serious error");
    899             return INVALID_OPERATION;
    900         case STATUS_UNINITIALIZED:
    901             CLOGE("Device not initialized!");
    902             return INVALID_OPERATION;
    903         case STATUS_UNCONFIGURED:
    904         case STATUS_CONFIGURED:
    905         case STATUS_ACTIVE:
    906             // OK
    907             break;
    908         default:
    909             SET_ERR_L("Unexpected status: %d", mStatus);
    910             return INVALID_OPERATION;
    911     }
    912 
    913     ssize_t idx = mOutputStreams.indexOfKey(id);
    914     if (idx == NAME_NOT_FOUND) {
    915         CLOGE("Stream %d is unknown", id);
    916         return idx;
    917     }
    918 
    919     if (width) *width  = mOutputStreams[idx]->getWidth();
    920     if (height) *height = mOutputStreams[idx]->getHeight();
    921     if (format) *format = mOutputStreams[idx]->getFormat();
    922 
    923     return OK;
    924 }
    925 
    926 status_t Camera3Device::setStreamTransform(int id,
    927         int transform) {
    928     ATRACE_CALL();
    929     Mutex::Autolock il(mInterfaceLock);
    930     Mutex::Autolock l(mLock);
    931 
    932     switch (mStatus) {
    933         case STATUS_ERROR:
    934             CLOGE("Device has encountered a serious error");
    935             return INVALID_OPERATION;
    936         case STATUS_UNINITIALIZED:
    937             CLOGE("Device not initialized");
    938             return INVALID_OPERATION;
    939         case STATUS_UNCONFIGURED:
    940         case STATUS_CONFIGURED:
    941         case STATUS_ACTIVE:
    942             // OK
    943             break;
    944         default:
    945             SET_ERR_L("Unexpected status: %d", mStatus);
    946             return INVALID_OPERATION;
    947     }
    948 
    949     ssize_t idx = mOutputStreams.indexOfKey(id);
    950     if (idx == NAME_NOT_FOUND) {
    951         CLOGE("Stream %d does not exist",
    952                 id);
    953         return BAD_VALUE;
    954     }
    955 
    956     return mOutputStreams.editValueAt(idx)->setTransform(transform);
    957 }
    958 
    959 status_t Camera3Device::deleteStream(int id) {
    960     ATRACE_CALL();
    961     Mutex::Autolock il(mInterfaceLock);
    962     Mutex::Autolock l(mLock);
    963     status_t res;
    964 
    965     ALOGV("%s: Camera %d: Deleting stream %d", __FUNCTION__, mId, id);
    966 
    967     // CameraDevice semantics require device to already be idle before
    968     // deleteStream is called, unlike for createStream.
    969     if (mStatus == STATUS_ACTIVE) {
    970         ALOGV("%s: Camera %d: Device not idle", __FUNCTION__, mId);
    971         return -EBUSY;
    972     }
    973 
    974     sp<Camera3StreamInterface> deletedStream;
    975     ssize_t outputStreamIdx = mOutputStreams.indexOfKey(id);
    976     if (mInputStream != NULL && id == mInputStream->getId()) {
    977         deletedStream = mInputStream;
    978         mInputStream.clear();
    979     } else {
    980         if (outputStreamIdx == NAME_NOT_FOUND) {
    981             CLOGE("Stream %d does not exist", id);
    982             return BAD_VALUE;
    983         }
    984     }
    985 
    986     // Delete output stream or the output part of a bi-directional stream.
    987     if (outputStreamIdx != NAME_NOT_FOUND) {
    988         deletedStream = mOutputStreams.editValueAt(outputStreamIdx);
    989         mOutputStreams.removeItem(id);
    990     }
    991 
    992     // Free up the stream endpoint so that it can be used by some other stream
    993     res = deletedStream->disconnect();
    994     if (res != OK) {
    995         SET_ERR_L("Can't disconnect deleted stream %d", id);
    996         // fall through since we want to still list the stream as deleted.
    997     }
    998     mDeletedStreams.add(deletedStream);
    999     mNeedConfig = true;
   1000 
   1001     return res;
   1002 }
   1003 
   1004 status_t Camera3Device::deleteReprocessStream(int id) {
   1005     ATRACE_CALL();
   1006     (void)id;
   1007 
   1008     CLOGE("Unimplemented");
   1009     return INVALID_OPERATION;
   1010 }
   1011 
   1012 status_t Camera3Device::configureStreams() {
   1013     ATRACE_CALL();
   1014     ALOGV("%s: E", __FUNCTION__);
   1015 
   1016     Mutex::Autolock il(mInterfaceLock);
   1017     Mutex::Autolock l(mLock);
   1018 
   1019     return configureStreamsLocked();
   1020 }
   1021 
   1022 status_t Camera3Device::createDefaultRequest(int templateId,
   1023         CameraMetadata *request) {
   1024     ATRACE_CALL();
   1025     ALOGV("%s: for template %d", __FUNCTION__, templateId);
   1026     Mutex::Autolock il(mInterfaceLock);
   1027     Mutex::Autolock l(mLock);
   1028 
   1029     switch (mStatus) {
   1030         case STATUS_ERROR:
   1031             CLOGE("Device has encountered a serious error");
   1032             return INVALID_OPERATION;
   1033         case STATUS_UNINITIALIZED:
   1034             CLOGE("Device is not initialized!");
   1035             return INVALID_OPERATION;
   1036         case STATUS_UNCONFIGURED:
   1037         case STATUS_CONFIGURED:
   1038         case STATUS_ACTIVE:
   1039             // OK
   1040             break;
   1041         default:
   1042             SET_ERR_L("Unexpected status: %d", mStatus);
   1043             return INVALID_OPERATION;
   1044     }
   1045 
   1046     if (!mRequestTemplateCache[templateId].isEmpty()) {
   1047         *request = mRequestTemplateCache[templateId];
   1048         return OK;
   1049     }
   1050 
   1051     const camera_metadata_t *rawRequest;
   1052     ATRACE_BEGIN("camera3->construct_default_request_settings");
   1053     rawRequest = mHal3Device->ops->construct_default_request_settings(
   1054         mHal3Device, templateId);
   1055     ATRACE_END();
   1056     if (rawRequest == NULL) {
   1057         SET_ERR_L("HAL is unable to construct default settings for template %d",
   1058                 templateId);
   1059         return DEAD_OBJECT;
   1060     }
   1061     *request = rawRequest;
   1062     mRequestTemplateCache[templateId] = rawRequest;
   1063 
   1064     return OK;
   1065 }
   1066 
   1067 status_t Camera3Device::waitUntilDrained() {
   1068     ATRACE_CALL();
   1069     Mutex::Autolock il(mInterfaceLock);
   1070     Mutex::Autolock l(mLock);
   1071 
   1072     return waitUntilDrainedLocked();
   1073 }
   1074 
   1075 status_t Camera3Device::waitUntilDrainedLocked() {
   1076     switch (mStatus) {
   1077         case STATUS_UNINITIALIZED:
   1078         case STATUS_UNCONFIGURED:
   1079             ALOGV("%s: Already idle", __FUNCTION__);
   1080             return OK;
   1081         case STATUS_CONFIGURED:
   1082             // To avoid race conditions, check with tracker to be sure
   1083         case STATUS_ERROR:
   1084         case STATUS_ACTIVE:
   1085             // Need to verify shut down
   1086             break;
   1087         default:
   1088             SET_ERR_L("Unexpected status: %d",mStatus);
   1089             return INVALID_OPERATION;
   1090     }
   1091 
   1092     ALOGV("%s: Camera %d: Waiting until idle", __FUNCTION__, mId);
   1093     status_t res = waitUntilStateThenRelock(/*active*/ false, kShutdownTimeout);
   1094     if (res != OK) {
   1095         SET_ERR_L("Error waiting for HAL to drain: %s (%d)", strerror(-res),
   1096                 res);
   1097     }
   1098     return res;
   1099 }
   1100 
   1101 // Pause to reconfigure
   1102 status_t Camera3Device::internalPauseAndWaitLocked() {
   1103     mRequestThread->setPaused(true);
   1104     mPauseStateNotify = true;
   1105 
   1106     ALOGV("%s: Camera %d: Internal wait until idle", __FUNCTION__, mId);
   1107     status_t res = waitUntilStateThenRelock(/*active*/ false, kShutdownTimeout);
   1108     if (res != OK) {
   1109         SET_ERR_L("Can't idle device in %f seconds!",
   1110                 kShutdownTimeout/1e9);
   1111     }
   1112 
   1113     return res;
   1114 }
   1115 
   1116 // Resume after internalPauseAndWaitLocked
   1117 status_t Camera3Device::internalResumeLocked() {
   1118     status_t res;
   1119 
   1120     mRequestThread->setPaused(false);
   1121 
   1122     res = waitUntilStateThenRelock(/*active*/ true, kActiveTimeout);
   1123     if (res != OK) {
   1124         SET_ERR_L("Can't transition to active in %f seconds!",
   1125                 kActiveTimeout/1e9);
   1126     }
   1127     mPauseStateNotify = false;
   1128     return OK;
   1129 }
   1130 
   1131 status_t Camera3Device::waitUntilStateThenRelock(bool active,
   1132         nsecs_t timeout) {
   1133     status_t res = OK;
   1134     if (active == (mStatus == STATUS_ACTIVE)) {
   1135         // Desired state already reached
   1136         return res;
   1137     }
   1138 
   1139     bool stateSeen = false;
   1140     do {
   1141         mRecentStatusUpdates.clear();
   1142 
   1143         res = mStatusChanged.waitRelative(mLock, timeout);
   1144         if (res != OK) break;
   1145 
   1146         // Check state change history during wait
   1147         for (size_t i = 0; i < mRecentStatusUpdates.size(); i++) {
   1148             if (active == (mRecentStatusUpdates[i] == STATUS_ACTIVE) ) {
   1149                 stateSeen = true;
   1150                 break;
   1151             }
   1152         }
   1153     } while (!stateSeen);
   1154 
   1155     return res;
   1156 }
   1157 
   1158 
   1159 status_t Camera3Device::setNotifyCallback(NotificationListener *listener) {
   1160     ATRACE_CALL();
   1161     Mutex::Autolock l(mOutputLock);
   1162 
   1163     if (listener != NULL && mListener != NULL) {
   1164         ALOGW("%s: Replacing old callback listener", __FUNCTION__);
   1165     }
   1166     mListener = listener;
   1167     mRequestThread->setNotifyCallback(listener);
   1168 
   1169     return OK;
   1170 }
   1171 
   1172 bool Camera3Device::willNotify3A() {
   1173     return false;
   1174 }
   1175 
   1176 status_t Camera3Device::waitForNextFrame(nsecs_t timeout) {
   1177     status_t res;
   1178     Mutex::Autolock l(mOutputLock);
   1179 
   1180     while (mResultQueue.empty()) {
   1181         res = mResultSignal.waitRelative(mOutputLock, timeout);
   1182         if (res == TIMED_OUT) {
   1183             return res;
   1184         } else if (res != OK) {
   1185             ALOGW("%s: Camera %d: No frame in %" PRId64 " ns: %s (%d)",
   1186                     __FUNCTION__, mId, timeout, strerror(-res), res);
   1187             return res;
   1188         }
   1189     }
   1190     return OK;
   1191 }
   1192 
   1193 status_t Camera3Device::getNextResult(CaptureResult *frame) {
   1194     ATRACE_CALL();
   1195     Mutex::Autolock l(mOutputLock);
   1196 
   1197     if (mResultQueue.empty()) {
   1198         return NOT_ENOUGH_DATA;
   1199     }
   1200 
   1201     if (frame == NULL) {
   1202         ALOGE("%s: argument cannot be NULL", __FUNCTION__);
   1203         return BAD_VALUE;
   1204     }
   1205 
   1206     CaptureResult &result = *(mResultQueue.begin());
   1207     frame->mResultExtras = result.mResultExtras;
   1208     frame->mMetadata.acquire(result.mMetadata);
   1209     mResultQueue.erase(mResultQueue.begin());
   1210 
   1211     return OK;
   1212 }
   1213 
   1214 status_t Camera3Device::triggerAutofocus(uint32_t id) {
   1215     ATRACE_CALL();
   1216     Mutex::Autolock il(mInterfaceLock);
   1217 
   1218     ALOGV("%s: Triggering autofocus, id %d", __FUNCTION__, id);
   1219     // Mix-in this trigger into the next request and only the next request.
   1220     RequestTrigger trigger[] = {
   1221         {
   1222             ANDROID_CONTROL_AF_TRIGGER,
   1223             ANDROID_CONTROL_AF_TRIGGER_START
   1224         },
   1225         {
   1226             ANDROID_CONTROL_AF_TRIGGER_ID,
   1227             static_cast<int32_t>(id)
   1228         }
   1229     };
   1230 
   1231     return mRequestThread->queueTrigger(trigger,
   1232                                         sizeof(trigger)/sizeof(trigger[0]));
   1233 }
   1234 
   1235 status_t Camera3Device::triggerCancelAutofocus(uint32_t id) {
   1236     ATRACE_CALL();
   1237     Mutex::Autolock il(mInterfaceLock);
   1238 
   1239     ALOGV("%s: Triggering cancel autofocus, id %d", __FUNCTION__, id);
   1240     // Mix-in this trigger into the next request and only the next request.
   1241     RequestTrigger trigger[] = {
   1242         {
   1243             ANDROID_CONTROL_AF_TRIGGER,
   1244             ANDROID_CONTROL_AF_TRIGGER_CANCEL
   1245         },
   1246         {
   1247             ANDROID_CONTROL_AF_TRIGGER_ID,
   1248             static_cast<int32_t>(id)
   1249         }
   1250     };
   1251 
   1252     return mRequestThread->queueTrigger(trigger,
   1253                                         sizeof(trigger)/sizeof(trigger[0]));
   1254 }
   1255 
   1256 status_t Camera3Device::triggerPrecaptureMetering(uint32_t id) {
   1257     ATRACE_CALL();
   1258     Mutex::Autolock il(mInterfaceLock);
   1259 
   1260     ALOGV("%s: Triggering precapture metering, id %d", __FUNCTION__, id);
   1261     // Mix-in this trigger into the next request and only the next request.
   1262     RequestTrigger trigger[] = {
   1263         {
   1264             ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER,
   1265             ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_START
   1266         },
   1267         {
   1268             ANDROID_CONTROL_AE_PRECAPTURE_ID,
   1269             static_cast<int32_t>(id)
   1270         }
   1271     };
   1272 
   1273     return mRequestThread->queueTrigger(trigger,
   1274                                         sizeof(trigger)/sizeof(trigger[0]));
   1275 }
   1276 
   1277 status_t Camera3Device::pushReprocessBuffer(int reprocessStreamId,
   1278         buffer_handle_t *buffer, wp<BufferReleasedListener> listener) {
   1279     ATRACE_CALL();
   1280     (void)reprocessStreamId; (void)buffer; (void)listener;
   1281 
   1282     CLOGE("Unimplemented");
   1283     return INVALID_OPERATION;
   1284 }
   1285 
   1286 status_t Camera3Device::flush(int64_t *frameNumber) {
   1287     ATRACE_CALL();
   1288     ALOGV("%s: Camera %d: Flushing all requests", __FUNCTION__, mId);
   1289     Mutex::Autolock il(mInterfaceLock);
   1290 
   1291     NotificationListener* listener;
   1292     {
   1293         Mutex::Autolock l(mOutputLock);
   1294         listener = mListener;
   1295     }
   1296 
   1297     {
   1298         Mutex::Autolock l(mLock);
   1299         mRequestThread->clear(listener, /*out*/frameNumber);
   1300     }
   1301 
   1302     status_t res;
   1303     if (mHal3Device->common.version >= CAMERA_DEVICE_API_VERSION_3_1) {
   1304         res = mHal3Device->ops->flush(mHal3Device);
   1305     } else {
   1306         Mutex::Autolock l(mLock);
   1307         res = waitUntilDrainedLocked();
   1308     }
   1309 
   1310     return res;
   1311 }
   1312 
   1313 uint32_t Camera3Device::getDeviceVersion() {
   1314     ATRACE_CALL();
   1315     Mutex::Autolock il(mInterfaceLock);
   1316     return mDeviceVersion;
   1317 }
   1318 
   1319 /**
   1320  * Methods called by subclasses
   1321  */
   1322 
   1323 void Camera3Device::notifyStatus(bool idle) {
   1324     {
   1325         // Need mLock to safely update state and synchronize to current
   1326         // state of methods in flight.
   1327         Mutex::Autolock l(mLock);
   1328         // We can get various system-idle notices from the status tracker
   1329         // while starting up. Only care about them if we've actually sent
   1330         // in some requests recently.
   1331         if (mStatus != STATUS_ACTIVE && mStatus != STATUS_CONFIGURED) {
   1332             return;
   1333         }
   1334         ALOGV("%s: Camera %d: Now %s", __FUNCTION__, mId,
   1335                 idle ? "idle" : "active");
   1336         mStatus = idle ? STATUS_CONFIGURED : STATUS_ACTIVE;
   1337         mRecentStatusUpdates.add(mStatus);
   1338         mStatusChanged.signal();
   1339 
   1340         // Skip notifying listener if we're doing some user-transparent
   1341         // state changes
   1342         if (mPauseStateNotify) return;
   1343     }
   1344     NotificationListener *listener;
   1345     {
   1346         Mutex::Autolock l(mOutputLock);
   1347         listener = mListener;
   1348     }
   1349     if (idle && listener != NULL) {
   1350         listener->notifyIdle();
   1351     }
   1352 }
   1353 
   1354 /**
   1355  * Camera3Device private methods
   1356  */
   1357 
   1358 sp<Camera3Device::CaptureRequest> Camera3Device::createCaptureRequest(
   1359         const CameraMetadata &request) {
   1360     ATRACE_CALL();
   1361     status_t res;
   1362 
   1363     sp<CaptureRequest> newRequest = new CaptureRequest;
   1364     newRequest->mSettings = request;
   1365 
   1366     camera_metadata_entry_t inputStreams =
   1367             newRequest->mSettings.find(ANDROID_REQUEST_INPUT_STREAMS);
   1368     if (inputStreams.count > 0) {
   1369         if (mInputStream == NULL ||
   1370                 mInputStream->getId() != inputStreams.data.i32[0]) {
   1371             CLOGE("Request references unknown input stream %d",
   1372                     inputStreams.data.u8[0]);
   1373             return NULL;
   1374         }
   1375         // Lazy completion of stream configuration (allocation/registration)
   1376         // on first use
   1377         if (mInputStream->isConfiguring()) {
   1378             res = mInputStream->finishConfiguration(mHal3Device);
   1379             if (res != OK) {
   1380                 SET_ERR_L("Unable to finish configuring input stream %d:"
   1381                         " %s (%d)",
   1382                         mInputStream->getId(), strerror(-res), res);
   1383                 return NULL;
   1384             }
   1385         }
   1386 
   1387         newRequest->mInputStream = mInputStream;
   1388         newRequest->mSettings.erase(ANDROID_REQUEST_INPUT_STREAMS);
   1389     }
   1390 
   1391     camera_metadata_entry_t streams =
   1392             newRequest->mSettings.find(ANDROID_REQUEST_OUTPUT_STREAMS);
   1393     if (streams.count == 0) {
   1394         CLOGE("Zero output streams specified!");
   1395         return NULL;
   1396     }
   1397 
   1398     for (size_t i = 0; i < streams.count; i++) {
   1399         int idx = mOutputStreams.indexOfKey(streams.data.i32[i]);
   1400         if (idx == NAME_NOT_FOUND) {
   1401             CLOGE("Request references unknown stream %d",
   1402                     streams.data.u8[i]);
   1403             return NULL;
   1404         }
   1405         sp<Camera3OutputStreamInterface> stream =
   1406                 mOutputStreams.editValueAt(idx);
   1407 
   1408         // Lazy completion of stream configuration (allocation/registration)
   1409         // on first use
   1410         if (stream->isConfiguring()) {
   1411             res = stream->finishConfiguration(mHal3Device);
   1412             if (res != OK) {
   1413                 SET_ERR_L("Unable to finish configuring stream %d: %s (%d)",
   1414                         stream->getId(), strerror(-res), res);
   1415                 return NULL;
   1416             }
   1417         }
   1418 
   1419         newRequest->mOutputStreams.push(stream);
   1420     }
   1421     newRequest->mSettings.erase(ANDROID_REQUEST_OUTPUT_STREAMS);
   1422 
   1423     return newRequest;
   1424 }
   1425 
   1426 status_t Camera3Device::configureStreamsLocked() {
   1427     ATRACE_CALL();
   1428     status_t res;
   1429 
   1430     if (mStatus != STATUS_UNCONFIGURED && mStatus != STATUS_CONFIGURED) {
   1431         CLOGE("Not idle");
   1432         return INVALID_OPERATION;
   1433     }
   1434 
   1435     if (!mNeedConfig) {
   1436         ALOGV("%s: Skipping config, no stream changes", __FUNCTION__);
   1437         return OK;
   1438     }
   1439 
   1440     // Workaround for device HALv3.2 or older spec bug - zero streams requires
   1441     // adding a dummy stream instead.
   1442     // TODO: Bug: 17321404 for fixing the HAL spec and removing this workaround.
   1443     if (mOutputStreams.size() == 0) {
   1444         addDummyStreamLocked();
   1445     } else {
   1446         tryRemoveDummyStreamLocked();
   1447     }
   1448 
   1449     // Start configuring the streams
   1450     ALOGV("%s: Camera %d: Starting stream configuration", __FUNCTION__, mId);
   1451 
   1452     camera3_stream_configuration config;
   1453 
   1454     config.num_streams = (mInputStream != NULL) + mOutputStreams.size();
   1455 
   1456     Vector<camera3_stream_t*> streams;
   1457     streams.setCapacity(config.num_streams);
   1458 
   1459     if (mInputStream != NULL) {
   1460         camera3_stream_t *inputStream;
   1461         inputStream = mInputStream->startConfiguration();
   1462         if (inputStream == NULL) {
   1463             SET_ERR_L("Can't start input stream configuration");
   1464             return INVALID_OPERATION;
   1465         }
   1466         streams.add(inputStream);
   1467     }
   1468 
   1469     for (size_t i = 0; i < mOutputStreams.size(); i++) {
   1470 
   1471         // Don't configure bidi streams twice, nor add them twice to the list
   1472         if (mOutputStreams[i].get() ==
   1473             static_cast<Camera3StreamInterface*>(mInputStream.get())) {
   1474 
   1475             config.num_streams--;
   1476             continue;
   1477         }
   1478 
   1479         camera3_stream_t *outputStream;
   1480         outputStream = mOutputStreams.editValueAt(i)->startConfiguration();
   1481         if (outputStream == NULL) {
   1482             SET_ERR_L("Can't start output stream configuration");
   1483             return INVALID_OPERATION;
   1484         }
   1485         streams.add(outputStream);
   1486     }
   1487 
   1488     config.streams = streams.editArray();
   1489 
   1490     // Do the HAL configuration; will potentially touch stream
   1491     // max_buffers, usage, priv fields.
   1492     ATRACE_BEGIN("camera3->configure_streams");
   1493     res = mHal3Device->ops->configure_streams(mHal3Device, &config);
   1494     ATRACE_END();
   1495 
   1496     if (res == BAD_VALUE) {
   1497         // HAL rejected this set of streams as unsupported, clean up config
   1498         // attempt and return to unconfigured state
   1499         if (mInputStream != NULL && mInputStream->isConfiguring()) {
   1500             res = mInputStream->cancelConfiguration();
   1501             if (res != OK) {
   1502                 SET_ERR_L("Can't cancel configuring input stream %d: %s (%d)",
   1503                         mInputStream->getId(), strerror(-res), res);
   1504                 return res;
   1505             }
   1506         }
   1507 
   1508         for (size_t i = 0; i < mOutputStreams.size(); i++) {
   1509             sp<Camera3OutputStreamInterface> outputStream =
   1510                     mOutputStreams.editValueAt(i);
   1511             if (outputStream->isConfiguring()) {
   1512                 res = outputStream->cancelConfiguration();
   1513                 if (res != OK) {
   1514                     SET_ERR_L(
   1515                         "Can't cancel configuring output stream %d: %s (%d)",
   1516                         outputStream->getId(), strerror(-res), res);
   1517                     return res;
   1518                 }
   1519             }
   1520         }
   1521 
   1522         // Return state to that at start of call, so that future configures
   1523         // properly clean things up
   1524         mStatus = STATUS_UNCONFIGURED;
   1525         mNeedConfig = true;
   1526 
   1527         ALOGV("%s: Camera %d: Stream configuration failed", __FUNCTION__, mId);
   1528         return BAD_VALUE;
   1529     } else if (res != OK) {
   1530         // Some other kind of error from configure_streams - this is not
   1531         // expected
   1532         SET_ERR_L("Unable to configure streams with HAL: %s (%d)",
   1533                 strerror(-res), res);
   1534         return res;
   1535     }
   1536 
   1537     // Finish all stream configuration immediately.
   1538     // TODO: Try to relax this later back to lazy completion, which should be
   1539     // faster
   1540 
   1541     if (mInputStream != NULL && mInputStream->isConfiguring()) {
   1542         res = mInputStream->finishConfiguration(mHal3Device);
   1543         if (res != OK) {
   1544             SET_ERR_L("Can't finish configuring input stream %d: %s (%d)",
   1545                     mInputStream->getId(), strerror(-res), res);
   1546             return res;
   1547         }
   1548     }
   1549 
   1550     for (size_t i = 0; i < mOutputStreams.size(); i++) {
   1551         sp<Camera3OutputStreamInterface> outputStream =
   1552             mOutputStreams.editValueAt(i);
   1553         if (outputStream->isConfiguring()) {
   1554             res = outputStream->finishConfiguration(mHal3Device);
   1555             if (res != OK) {
   1556                 SET_ERR_L("Can't finish configuring output stream %d: %s (%d)",
   1557                         outputStream->getId(), strerror(-res), res);
   1558                 return res;
   1559             }
   1560         }
   1561     }
   1562 
   1563     // Request thread needs to know to avoid using repeat-last-settings protocol
   1564     // across configure_streams() calls
   1565     mRequestThread->configurationComplete();
   1566 
   1567     // Update device state
   1568 
   1569     mNeedConfig = false;
   1570 
   1571     if (mDummyStreamId == NO_STREAM) {
   1572         mStatus = STATUS_CONFIGURED;
   1573     } else {
   1574         mStatus = STATUS_UNCONFIGURED;
   1575     }
   1576 
   1577     ALOGV("%s: Camera %d: Stream configuration complete", __FUNCTION__, mId);
   1578 
   1579     // tear down the deleted streams after configure streams.
   1580     mDeletedStreams.clear();
   1581 
   1582     return OK;
   1583 }
   1584 
   1585 status_t Camera3Device::addDummyStreamLocked() {
   1586     ATRACE_CALL();
   1587     status_t res;
   1588 
   1589     if (mDummyStreamId != NO_STREAM) {
   1590         // Should never be adding a second dummy stream when one is already
   1591         // active
   1592         SET_ERR_L("%s: Camera %d: A dummy stream already exists!",
   1593                 __FUNCTION__, mId);
   1594         return INVALID_OPERATION;
   1595     }
   1596 
   1597     ALOGV("%s: Camera %d: Adding a dummy stream", __FUNCTION__, mId);
   1598 
   1599     sp<Camera3OutputStreamInterface> dummyStream =
   1600             new Camera3DummyStream(mNextStreamId);
   1601 
   1602     res = mOutputStreams.add(mNextStreamId, dummyStream);
   1603     if (res < 0) {
   1604         SET_ERR_L("Can't add dummy stream to set: %s (%d)", strerror(-res), res);
   1605         return res;
   1606     }
   1607 
   1608     mDummyStreamId = mNextStreamId;
   1609     mNextStreamId++;
   1610 
   1611     return OK;
   1612 }
   1613 
   1614 status_t Camera3Device::tryRemoveDummyStreamLocked() {
   1615     ATRACE_CALL();
   1616     status_t res;
   1617 
   1618     if (mDummyStreamId == NO_STREAM) return OK;
   1619     if (mOutputStreams.size() == 1) return OK;
   1620 
   1621     ALOGV("%s: Camera %d: Removing the dummy stream", __FUNCTION__, mId);
   1622 
   1623     // Ok, have a dummy stream and there's at least one other output stream,
   1624     // so remove the dummy
   1625 
   1626     sp<Camera3StreamInterface> deletedStream;
   1627     ssize_t outputStreamIdx = mOutputStreams.indexOfKey(mDummyStreamId);
   1628     if (outputStreamIdx == NAME_NOT_FOUND) {
   1629         SET_ERR_L("Dummy stream %d does not appear to exist", mDummyStreamId);
   1630         return INVALID_OPERATION;
   1631     }
   1632 
   1633     deletedStream = mOutputStreams.editValueAt(outputStreamIdx);
   1634     mOutputStreams.removeItemsAt(outputStreamIdx);
   1635 
   1636     // Free up the stream endpoint so that it can be used by some other stream
   1637     res = deletedStream->disconnect();
   1638     if (res != OK) {
   1639         SET_ERR_L("Can't disconnect deleted dummy stream %d", mDummyStreamId);
   1640         // fall through since we want to still list the stream as deleted.
   1641     }
   1642     mDeletedStreams.add(deletedStream);
   1643     mDummyStreamId = NO_STREAM;
   1644 
   1645     return res;
   1646 }
   1647 
   1648 void Camera3Device::setErrorState(const char *fmt, ...) {
   1649     Mutex::Autolock l(mLock);
   1650     va_list args;
   1651     va_start(args, fmt);
   1652 
   1653     setErrorStateLockedV(fmt, args);
   1654 
   1655     va_end(args);
   1656 }
   1657 
   1658 void Camera3Device::setErrorStateV(const char *fmt, va_list args) {
   1659     Mutex::Autolock l(mLock);
   1660     setErrorStateLockedV(fmt, args);
   1661 }
   1662 
   1663 void Camera3Device::setErrorStateLocked(const char *fmt, ...) {
   1664     va_list args;
   1665     va_start(args, fmt);
   1666 
   1667     setErrorStateLockedV(fmt, args);
   1668 
   1669     va_end(args);
   1670 }
   1671 
   1672 void Camera3Device::setErrorStateLockedV(const char *fmt, va_list args) {
   1673     // Print out all error messages to log
   1674     String8 errorCause = String8::formatV(fmt, args);
   1675     ALOGE("Camera %d: %s", mId, errorCause.string());
   1676 
   1677     // But only do error state transition steps for the first error
   1678     if (mStatus == STATUS_ERROR || mStatus == STATUS_UNINITIALIZED) return;
   1679 
   1680     mErrorCause = errorCause;
   1681 
   1682     mRequestThread->setPaused(true);
   1683     mStatus = STATUS_ERROR;
   1684 
   1685     // Notify upstream about a device error
   1686     if (mListener != NULL) {
   1687         mListener->notifyError(ICameraDeviceCallbacks::ERROR_CAMERA_DEVICE,
   1688                 CaptureResultExtras());
   1689     }
   1690 
   1691     // Save stack trace. View by dumping it later.
   1692     CameraTraces::saveTrace();
   1693     // TODO: consider adding errorCause and client pid/procname
   1694 }
   1695 
   1696 /**
   1697  * In-flight request management
   1698  */
   1699 
   1700 status_t Camera3Device::registerInFlight(uint32_t frameNumber,
   1701         int32_t numBuffers, CaptureResultExtras resultExtras, bool hasInput) {
   1702     ATRACE_CALL();
   1703     Mutex::Autolock l(mInFlightLock);
   1704 
   1705     ssize_t res;
   1706     res = mInFlightMap.add(frameNumber, InFlightRequest(numBuffers, resultExtras, hasInput));
   1707     if (res < 0) return res;
   1708 
   1709     return OK;
   1710 }
   1711 
   1712 /**
   1713  * Check if all 3A fields are ready, and send off a partial 3A-only result
   1714  * to the output frame queue
   1715  */
   1716 bool Camera3Device::processPartial3AResult(
   1717         uint32_t frameNumber,
   1718         const CameraMetadata& partial, const CaptureResultExtras& resultExtras) {
   1719 
   1720     // Check if all 3A states are present
   1721     // The full list of fields is
   1722     //   android.control.afMode
   1723     //   android.control.awbMode
   1724     //   android.control.aeState
   1725     //   android.control.awbState
   1726     //   android.control.afState
   1727     //   android.control.afTriggerID
   1728     //   android.control.aePrecaptureID
   1729     // TODO: Add android.control.aeMode
   1730 
   1731     bool gotAllStates = true;
   1732 
   1733     uint8_t afMode;
   1734     uint8_t awbMode;
   1735     uint8_t aeState;
   1736     uint8_t afState;
   1737     uint8_t awbState;
   1738 
   1739     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AF_MODE,
   1740         &afMode, frameNumber);
   1741 
   1742     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AWB_MODE,
   1743         &awbMode, frameNumber);
   1744 
   1745     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AE_STATE,
   1746         &aeState, frameNumber);
   1747 
   1748     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AF_STATE,
   1749         &afState, frameNumber);
   1750 
   1751     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AWB_STATE,
   1752         &awbState, frameNumber);
   1753 
   1754     if (!gotAllStates) return false;
   1755 
   1756     ALOGVV("%s: Camera %d: Frame %d, Request ID %d: AF mode %d, AWB mode %d, "
   1757         "AF state %d, AE state %d, AWB state %d, "
   1758         "AF trigger %d, AE precapture trigger %d",
   1759         __FUNCTION__, mId, frameNumber, resultExtras.requestId,
   1760         afMode, awbMode,
   1761         afState, aeState, awbState,
   1762         resultExtras.afTriggerId, resultExtras.precaptureTriggerId);
   1763 
   1764     // Got all states, so construct a minimal result to send
   1765     // In addition to the above fields, this means adding in
   1766     //   android.request.frameCount
   1767     //   android.request.requestId
   1768     //   android.quirks.partialResult (for HAL version below HAL3.2)
   1769 
   1770     const size_t kMinimal3AResultEntries = 10;
   1771 
   1772     Mutex::Autolock l(mOutputLock);
   1773 
   1774     CaptureResult captureResult;
   1775     captureResult.mResultExtras = resultExtras;
   1776     captureResult.mMetadata = CameraMetadata(kMinimal3AResultEntries, /*dataCapacity*/ 0);
   1777     // TODO: change this to sp<CaptureResult>. This will need other changes, including,
   1778     // but not limited to CameraDeviceBase::getNextResult
   1779     CaptureResult& min3AResult =
   1780             *mResultQueue.insert(mResultQueue.end(), captureResult);
   1781 
   1782     if (!insert3AResult(min3AResult.mMetadata, ANDROID_REQUEST_FRAME_COUNT,
   1783             // TODO: This is problematic casting. Need to fix CameraMetadata.
   1784             reinterpret_cast<int32_t*>(&frameNumber), frameNumber)) {
   1785         return false;
   1786     }
   1787 
   1788     int32_t requestId = resultExtras.requestId;
   1789     if (!insert3AResult(min3AResult.mMetadata, ANDROID_REQUEST_ID,
   1790             &requestId, frameNumber)) {
   1791         return false;
   1792     }
   1793 
   1794     if (mDeviceVersion < CAMERA_DEVICE_API_VERSION_3_2) {
   1795         static const uint8_t partialResult = ANDROID_QUIRKS_PARTIAL_RESULT_PARTIAL;
   1796         if (!insert3AResult(min3AResult.mMetadata, ANDROID_QUIRKS_PARTIAL_RESULT,
   1797                 &partialResult, frameNumber)) {
   1798             return false;
   1799         }
   1800     }
   1801 
   1802     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AF_MODE,
   1803             &afMode, frameNumber)) {
   1804         return false;
   1805     }
   1806 
   1807     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AWB_MODE,
   1808             &awbMode, frameNumber)) {
   1809         return false;
   1810     }
   1811 
   1812     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AE_STATE,
   1813             &aeState, frameNumber)) {
   1814         return false;
   1815     }
   1816 
   1817     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AF_STATE,
   1818             &afState, frameNumber)) {
   1819         return false;
   1820     }
   1821 
   1822     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AWB_STATE,
   1823             &awbState, frameNumber)) {
   1824         return false;
   1825     }
   1826 
   1827     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AF_TRIGGER_ID,
   1828             &resultExtras.afTriggerId, frameNumber)) {
   1829         return false;
   1830     }
   1831 
   1832     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AE_PRECAPTURE_ID,
   1833             &resultExtras.precaptureTriggerId, frameNumber)) {
   1834         return false;
   1835     }
   1836 
   1837     // We only send the aggregated partial when all 3A related metadata are available
   1838     // For both API1 and API2.
   1839     // TODO: we probably should pass through all partials to API2 unconditionally.
   1840     mResultSignal.signal();
   1841 
   1842     return true;
   1843 }
   1844 
   1845 template<typename T>
   1846 bool Camera3Device::get3AResult(const CameraMetadata& result, int32_t tag,
   1847         T* value, uint32_t frameNumber) {
   1848     (void) frameNumber;
   1849 
   1850     camera_metadata_ro_entry_t entry;
   1851 
   1852     entry = result.find(tag);
   1853     if (entry.count == 0) {
   1854         ALOGVV("%s: Camera %d: Frame %d: No %s provided by HAL!", __FUNCTION__,
   1855             mId, frameNumber, get_camera_metadata_tag_name(tag));
   1856         return false;
   1857     }
   1858 
   1859     if (sizeof(T) == sizeof(uint8_t)) {
   1860         *value = entry.data.u8[0];
   1861     } else if (sizeof(T) == sizeof(int32_t)) {
   1862         *value = entry.data.i32[0];
   1863     } else {
   1864         ALOGE("%s: Unexpected type", __FUNCTION__);
   1865         return false;
   1866     }
   1867     return true;
   1868 }
   1869 
   1870 template<typename T>
   1871 bool Camera3Device::insert3AResult(CameraMetadata& result, int32_t tag,
   1872         const T* value, uint32_t frameNumber) {
   1873     if (result.update(tag, value, 1) != NO_ERROR) {
   1874         mResultQueue.erase(--mResultQueue.end(), mResultQueue.end());
   1875         SET_ERR("Frame %d: Failed to set %s in partial metadata",
   1876                 frameNumber, get_camera_metadata_tag_name(tag));
   1877         return false;
   1878     }
   1879     return true;
   1880 }
   1881 
   1882 
   1883 void Camera3Device::returnOutputBuffers(
   1884         const camera3_stream_buffer_t *outputBuffers, size_t numBuffers,
   1885         nsecs_t timestamp) {
   1886     for (size_t i = 0; i < numBuffers; i++)
   1887     {
   1888         Camera3Stream *stream = Camera3Stream::cast(outputBuffers[i].stream);
   1889         status_t res = stream->returnBuffer(outputBuffers[i], timestamp);
   1890         // Note: stream may be deallocated at this point, if this buffer was
   1891         // the last reference to it.
   1892         if (res != OK) {
   1893             ALOGE("Can't return buffer to its stream: %s (%d)",
   1894                 strerror(-res), res);
   1895         }
   1896     }
   1897 }
   1898 
   1899 
   1900 void Camera3Device::removeInFlightRequestIfReadyLocked(int idx) {
   1901 
   1902     const InFlightRequest &request = mInFlightMap.valueAt(idx);
   1903     const uint32_t frameNumber = mInFlightMap.keyAt(idx);
   1904 
   1905     nsecs_t sensorTimestamp = request.sensorTimestamp;
   1906     nsecs_t shutterTimestamp = request.shutterTimestamp;
   1907 
   1908     // Check if it's okay to remove the request from InFlightMap:
   1909     // In the case of a successful request:
   1910     //      all input and output buffers, all result metadata, shutter callback
   1911     //      arrived.
   1912     // In the case of a unsuccessful request:
   1913     //      all input and output buffers arrived.
   1914     if (request.numBuffersLeft == 0 &&
   1915             (request.requestStatus != OK ||
   1916             (request.haveResultMetadata && shutterTimestamp != 0))) {
   1917         ATRACE_ASYNC_END("frame capture", frameNumber);
   1918 
   1919         // Sanity check - if sensor timestamp matches shutter timestamp
   1920         if (request.requestStatus == OK &&
   1921                 sensorTimestamp != shutterTimestamp) {
   1922             SET_ERR("sensor timestamp (%" PRId64
   1923                 ") for frame %d doesn't match shutter timestamp (%" PRId64 ")",
   1924                 sensorTimestamp, frameNumber, shutterTimestamp);
   1925         }
   1926 
   1927         // for an unsuccessful request, it may have pending output buffers to
   1928         // return.
   1929         assert(request.requestStatus != OK ||
   1930                request.pendingOutputBuffers.size() == 0);
   1931         returnOutputBuffers(request.pendingOutputBuffers.array(),
   1932             request.pendingOutputBuffers.size(), 0);
   1933 
   1934         mInFlightMap.removeItemsAt(idx, 1);
   1935 
   1936         ALOGVV("%s: removed frame %d from InFlightMap", __FUNCTION__, frameNumber);
   1937      }
   1938 
   1939     // Sanity check - if we have too many in-flight frames, something has
   1940     // likely gone wrong
   1941     if (mInFlightMap.size() > kInFlightWarnLimit) {
   1942         CLOGE("In-flight list too large: %zu", mInFlightMap.size());
   1943     }
   1944 }
   1945 
   1946 
   1947 void Camera3Device::sendCaptureResult(CameraMetadata &pendingMetadata,
   1948         CaptureResultExtras &resultExtras,
   1949         CameraMetadata &collectedPartialResult,
   1950         uint32_t frameNumber) {
   1951     if (pendingMetadata.isEmpty())
   1952         return;
   1953 
   1954     Mutex::Autolock l(mOutputLock);
   1955 
   1956     // TODO: need to track errors for tighter bounds on expected frame number
   1957     if (frameNumber < mNextResultFrameNumber) {
   1958         SET_ERR("Out-of-order capture result metadata submitted! "
   1959                 "(got frame number %d, expecting %d)",
   1960                 frameNumber, mNextResultFrameNumber);
   1961         return;
   1962     }
   1963     mNextResultFrameNumber = frameNumber + 1;
   1964 
   1965     CaptureResult captureResult;
   1966     captureResult.mResultExtras = resultExtras;
   1967     captureResult.mMetadata = pendingMetadata;
   1968 
   1969     if (captureResult.mMetadata.update(ANDROID_REQUEST_FRAME_COUNT,
   1970             (int32_t*)&frameNumber, 1) != OK) {
   1971         SET_ERR("Failed to set frame# in metadata (%d)",
   1972                 frameNumber);
   1973         return;
   1974     } else {
   1975         ALOGVV("%s: Camera %d: Set frame# in metadata (%d)",
   1976                 __FUNCTION__, mId, frameNumber);
   1977     }
   1978 
   1979     // Append any previous partials to form a complete result
   1980     if (mUsePartialResult && !collectedPartialResult.isEmpty()) {
   1981         captureResult.mMetadata.append(collectedPartialResult);
   1982     }
   1983 
   1984     captureResult.mMetadata.sort();
   1985 
   1986     // Check that there's a timestamp in the result metadata
   1987     camera_metadata_entry entry =
   1988             captureResult.mMetadata.find(ANDROID_SENSOR_TIMESTAMP);
   1989     if (entry.count == 0) {
   1990         SET_ERR("No timestamp provided by HAL for frame %d!",
   1991                 frameNumber);
   1992         return;
   1993     }
   1994 
   1995     // Valid result, insert into queue
   1996     List<CaptureResult>::iterator queuedResult =
   1997             mResultQueue.insert(mResultQueue.end(), CaptureResult(captureResult));
   1998     ALOGVV("%s: result requestId = %" PRId32 ", frameNumber = %" PRId64
   1999            ", burstId = %" PRId32, __FUNCTION__,
   2000            queuedResult->mResultExtras.requestId,
   2001            queuedResult->mResultExtras.frameNumber,
   2002            queuedResult->mResultExtras.burstId);
   2003 
   2004     mResultSignal.signal();
   2005 }
   2006 
   2007 /**
   2008  * Camera HAL device callback methods
   2009  */
   2010 
   2011 void Camera3Device::processCaptureResult(const camera3_capture_result *result) {
   2012     ATRACE_CALL();
   2013 
   2014     status_t res;
   2015 
   2016     uint32_t frameNumber = result->frame_number;
   2017     if (result->result == NULL && result->num_output_buffers == 0 &&
   2018             result->input_buffer == NULL) {
   2019         SET_ERR("No result data provided by HAL for frame %d",
   2020                 frameNumber);
   2021         return;
   2022     }
   2023 
   2024     // For HAL3.2 or above, If HAL doesn't support partial, it must always set
   2025     // partial_result to 1 when metadata is included in this result.
   2026     if (!mUsePartialResult &&
   2027             mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2 &&
   2028             result->result != NULL &&
   2029             result->partial_result != 1) {
   2030         SET_ERR("Result is malformed for frame %d: partial_result %u must be 1"
   2031                 " if partial result is not supported",
   2032                 frameNumber, result->partial_result);
   2033         return;
   2034     }
   2035 
   2036     bool isPartialResult = false;
   2037     CameraMetadata collectedPartialResult;
   2038     CaptureResultExtras resultExtras;
   2039     bool hasInputBufferInRequest = false;
   2040 
   2041     // Get shutter timestamp and resultExtras from list of in-flight requests,
   2042     // where it was added by the shutter notification for this frame. If the
   2043     // shutter timestamp isn't received yet, append the output buffers to the
   2044     // in-flight request and they will be returned when the shutter timestamp
   2045     // arrives. Update the in-flight status and remove the in-flight entry if
   2046     // all result data and shutter timestamp have been received.
   2047     nsecs_t shutterTimestamp = 0;
   2048 
   2049     {
   2050         Mutex::Autolock l(mInFlightLock);
   2051         ssize_t idx = mInFlightMap.indexOfKey(frameNumber);
   2052         if (idx == NAME_NOT_FOUND) {
   2053             SET_ERR("Unknown frame number for capture result: %d",
   2054                     frameNumber);
   2055             return;
   2056         }
   2057         InFlightRequest &request = mInFlightMap.editValueAt(idx);
   2058         ALOGVV("%s: got InFlightRequest requestId = %" PRId32
   2059                 ", frameNumber = %" PRId64 ", burstId = %" PRId32
   2060                 ", partialResultCount = %d",
   2061                 __FUNCTION__, request.resultExtras.requestId,
   2062                 request.resultExtras.frameNumber, request.resultExtras.burstId,
   2063                 result->partial_result);
   2064         // Always update the partial count to the latest one if it's not 0
   2065         // (buffers only). When framework aggregates adjacent partial results
   2066         // into one, the latest partial count will be used.
   2067         if (result->partial_result != 0)
   2068             request.resultExtras.partialResultCount = result->partial_result;
   2069 
   2070         // Check if this result carries only partial metadata
   2071         if (mUsePartialResult && result->result != NULL) {
   2072             if (mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
   2073                 if (result->partial_result > mNumPartialResults || result->partial_result < 1) {
   2074                     SET_ERR("Result is malformed for frame %d: partial_result %u must be  in"
   2075                             " the range of [1, %d] when metadata is included in the result",
   2076                             frameNumber, result->partial_result, mNumPartialResults);
   2077                     return;
   2078                 }
   2079                 isPartialResult = (result->partial_result < mNumPartialResults);
   2080                 if (isPartialResult) {
   2081                     request.partialResult.collectedResult.append(result->result);
   2082                 }
   2083             } else {
   2084                 camera_metadata_ro_entry_t partialResultEntry;
   2085                 res = find_camera_metadata_ro_entry(result->result,
   2086                         ANDROID_QUIRKS_PARTIAL_RESULT, &partialResultEntry);
   2087                 if (res != NAME_NOT_FOUND &&
   2088                         partialResultEntry.count > 0 &&
   2089                         partialResultEntry.data.u8[0] ==
   2090                         ANDROID_QUIRKS_PARTIAL_RESULT_PARTIAL) {
   2091                     // A partial result. Flag this as such, and collect this
   2092                     // set of metadata into the in-flight entry.
   2093                     isPartialResult = true;
   2094                     request.partialResult.collectedResult.append(
   2095                         result->result);
   2096                     request.partialResult.collectedResult.erase(
   2097                         ANDROID_QUIRKS_PARTIAL_RESULT);
   2098                 }
   2099             }
   2100 
   2101             if (isPartialResult) {
   2102                 // Fire off a 3A-only result if possible
   2103                 if (!request.partialResult.haveSent3A) {
   2104                     request.partialResult.haveSent3A =
   2105                             processPartial3AResult(frameNumber,
   2106                                     request.partialResult.collectedResult,
   2107                                     request.resultExtras);
   2108                 }
   2109             }
   2110         }
   2111 
   2112         shutterTimestamp = request.shutterTimestamp;
   2113         hasInputBufferInRequest = request.hasInputBuffer;
   2114 
   2115         // Did we get the (final) result metadata for this capture?
   2116         if (result->result != NULL && !isPartialResult) {
   2117             if (request.haveResultMetadata) {
   2118                 SET_ERR("Called multiple times with metadata for frame %d",
   2119                         frameNumber);
   2120                 return;
   2121             }
   2122             if (mUsePartialResult &&
   2123                     !request.partialResult.collectedResult.isEmpty()) {
   2124                 collectedPartialResult.acquire(
   2125                     request.partialResult.collectedResult);
   2126             }
   2127             request.haveResultMetadata = true;
   2128         }
   2129 
   2130         uint32_t numBuffersReturned = result->num_output_buffers;
   2131         if (result->input_buffer != NULL) {
   2132             if (hasInputBufferInRequest) {
   2133                 numBuffersReturned += 1;
   2134             } else {
   2135                 ALOGW("%s: Input buffer should be NULL if there is no input"
   2136                         " buffer sent in the request",
   2137                         __FUNCTION__);
   2138             }
   2139         }
   2140         request.numBuffersLeft -= numBuffersReturned;
   2141         if (request.numBuffersLeft < 0) {
   2142             SET_ERR("Too many buffers returned for frame %d",
   2143                     frameNumber);
   2144             return;
   2145         }
   2146 
   2147         camera_metadata_ro_entry_t entry;
   2148         res = find_camera_metadata_ro_entry(result->result,
   2149                 ANDROID_SENSOR_TIMESTAMP, &entry);
   2150         if (res == OK && entry.count == 1) {
   2151             request.sensorTimestamp = entry.data.i64[0];
   2152         }
   2153 
   2154         // If shutter event isn't received yet, append the output buffers to
   2155         // the in-flight request. Otherwise, return the output buffers to
   2156         // streams.
   2157         if (shutterTimestamp == 0) {
   2158             request.pendingOutputBuffers.appendArray(result->output_buffers,
   2159                 result->num_output_buffers);
   2160         } else {
   2161             returnOutputBuffers(result->output_buffers,
   2162                 result->num_output_buffers, shutterTimestamp);
   2163         }
   2164 
   2165         if (result->result != NULL && !isPartialResult) {
   2166             if (shutterTimestamp == 0) {
   2167                 request.pendingMetadata = result->result;
   2168                 request.partialResult.collectedResult = collectedPartialResult;
   2169             } else {
   2170                 CameraMetadata metadata;
   2171                 metadata = result->result;
   2172                 sendCaptureResult(metadata, request.resultExtras,
   2173                     collectedPartialResult, frameNumber);
   2174             }
   2175         }
   2176 
   2177         removeInFlightRequestIfReadyLocked(idx);
   2178     } // scope for mInFlightLock
   2179 
   2180     if (result->input_buffer != NULL) {
   2181         if (hasInputBufferInRequest) {
   2182             Camera3Stream *stream =
   2183                 Camera3Stream::cast(result->input_buffer->stream);
   2184             res = stream->returnInputBuffer(*(result->input_buffer));
   2185             // Note: stream may be deallocated at this point, if this buffer was the
   2186             // last reference to it.
   2187             if (res != OK) {
   2188                 ALOGE("%s: RequestThread: Can't return input buffer for frame %d to"
   2189                       "  its stream:%s (%d)",  __FUNCTION__,
   2190                       frameNumber, strerror(-res), res);
   2191             }
   2192         } else {
   2193             ALOGW("%s: Input buffer should be NULL if there is no input"
   2194                     " buffer sent in the request, skipping input buffer return.",
   2195                     __FUNCTION__);
   2196         }
   2197     }
   2198 }
   2199 
   2200 void Camera3Device::notify(const camera3_notify_msg *msg) {
   2201     ATRACE_CALL();
   2202     NotificationListener *listener;
   2203     {
   2204         Mutex::Autolock l(mOutputLock);
   2205         listener = mListener;
   2206     }
   2207 
   2208     if (msg == NULL) {
   2209         SET_ERR("HAL sent NULL notify message!");
   2210         return;
   2211     }
   2212 
   2213     switch (msg->type) {
   2214         case CAMERA3_MSG_ERROR: {
   2215             notifyError(msg->message.error, listener);
   2216             break;
   2217         }
   2218         case CAMERA3_MSG_SHUTTER: {
   2219             notifyShutter(msg->message.shutter, listener);
   2220             break;
   2221         }
   2222         default:
   2223             SET_ERR("Unknown notify message from HAL: %d",
   2224                     msg->type);
   2225     }
   2226 }
   2227 
   2228 void Camera3Device::notifyError(const camera3_error_msg_t &msg,
   2229         NotificationListener *listener) {
   2230 
   2231     // Map camera HAL error codes to ICameraDeviceCallback error codes
   2232     // Index into this with the HAL error code
   2233     static const ICameraDeviceCallbacks::CameraErrorCode
   2234             halErrorMap[CAMERA3_MSG_NUM_ERRORS] = {
   2235         // 0 = Unused error code
   2236         ICameraDeviceCallbacks::ERROR_CAMERA_INVALID_ERROR,
   2237         // 1 = CAMERA3_MSG_ERROR_DEVICE
   2238         ICameraDeviceCallbacks::ERROR_CAMERA_DEVICE,
   2239         // 2 = CAMERA3_MSG_ERROR_REQUEST
   2240         ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
   2241         // 3 = CAMERA3_MSG_ERROR_RESULT
   2242         ICameraDeviceCallbacks::ERROR_CAMERA_RESULT,
   2243         // 4 = CAMERA3_MSG_ERROR_BUFFER
   2244         ICameraDeviceCallbacks::ERROR_CAMERA_BUFFER
   2245     };
   2246 
   2247     ICameraDeviceCallbacks::CameraErrorCode errorCode =
   2248             ((msg.error_code >= 0) &&
   2249                     (msg.error_code < CAMERA3_MSG_NUM_ERRORS)) ?
   2250             halErrorMap[msg.error_code] :
   2251             ICameraDeviceCallbacks::ERROR_CAMERA_INVALID_ERROR;
   2252 
   2253     int streamId = 0;
   2254     if (msg.error_stream != NULL) {
   2255         Camera3Stream *stream =
   2256                 Camera3Stream::cast(msg.error_stream);
   2257         streamId = stream->getId();
   2258     }
   2259     ALOGV("Camera %d: %s: HAL error, frame %d, stream %d: %d",
   2260             mId, __FUNCTION__, msg.frame_number,
   2261             streamId, msg.error_code);
   2262 
   2263     CaptureResultExtras resultExtras;
   2264     switch (errorCode) {
   2265         case ICameraDeviceCallbacks::ERROR_CAMERA_DEVICE:
   2266             // SET_ERR calls notifyError
   2267             SET_ERR("Camera HAL reported serious device error");
   2268             break;
   2269         case ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST:
   2270         case ICameraDeviceCallbacks::ERROR_CAMERA_RESULT:
   2271         case ICameraDeviceCallbacks::ERROR_CAMERA_BUFFER:
   2272             {
   2273                 Mutex::Autolock l(mInFlightLock);
   2274                 ssize_t idx = mInFlightMap.indexOfKey(msg.frame_number);
   2275                 if (idx >= 0) {
   2276                     InFlightRequest &r = mInFlightMap.editValueAt(idx);
   2277                     r.requestStatus = msg.error_code;
   2278                     resultExtras = r.resultExtras;
   2279                 } else {
   2280                     resultExtras.frameNumber = msg.frame_number;
   2281                     ALOGE("Camera %d: %s: cannot find in-flight request on "
   2282                             "frame %" PRId64 " error", mId, __FUNCTION__,
   2283                             resultExtras.frameNumber);
   2284                 }
   2285             }
   2286             if (listener != NULL) {
   2287                 listener->notifyError(errorCode, resultExtras);
   2288             } else {
   2289                 ALOGE("Camera %d: %s: no listener available", mId, __FUNCTION__);
   2290             }
   2291             break;
   2292         default:
   2293             // SET_ERR calls notifyError
   2294             SET_ERR("Unknown error message from HAL: %d", msg.error_code);
   2295             break;
   2296     }
   2297 }
   2298 
   2299 void Camera3Device::notifyShutter(const camera3_shutter_msg_t &msg,
   2300         NotificationListener *listener) {
   2301     ssize_t idx;
   2302     // Verify ordering of shutter notifications
   2303     {
   2304         Mutex::Autolock l(mOutputLock);
   2305         // TODO: need to track errors for tighter bounds on expected frame number.
   2306         if (msg.frame_number < mNextShutterFrameNumber) {
   2307             SET_ERR("Shutter notification out-of-order. Expected "
   2308                     "notification for frame %d, got frame %d",
   2309                     mNextShutterFrameNumber, msg.frame_number);
   2310             return;
   2311         }
   2312         mNextShutterFrameNumber = msg.frame_number + 1;
   2313     }
   2314 
   2315     // Set timestamp for the request in the in-flight tracking
   2316     // and get the request ID to send upstream
   2317     {
   2318         Mutex::Autolock l(mInFlightLock);
   2319         idx = mInFlightMap.indexOfKey(msg.frame_number);
   2320         if (idx >= 0) {
   2321             InFlightRequest &r = mInFlightMap.editValueAt(idx);
   2322 
   2323             ALOGVV("Camera %d: %s: Shutter fired for frame %d (id %d) at %" PRId64,
   2324                     mId, __FUNCTION__,
   2325                     msg.frame_number, r.resultExtras.requestId, msg.timestamp);
   2326             // Call listener, if any
   2327             if (listener != NULL) {
   2328                 listener->notifyShutter(r.resultExtras, msg.timestamp);
   2329             }
   2330 
   2331             r.shutterTimestamp = msg.timestamp;
   2332 
   2333             // send pending result and buffers
   2334             sendCaptureResult(r.pendingMetadata, r.resultExtras,
   2335                 r.partialResult.collectedResult, msg.frame_number);
   2336             returnOutputBuffers(r.pendingOutputBuffers.array(),
   2337                 r.pendingOutputBuffers.size(), r.shutterTimestamp);
   2338             r.pendingOutputBuffers.clear();
   2339 
   2340             removeInFlightRequestIfReadyLocked(idx);
   2341         }
   2342     }
   2343     if (idx < 0) {
   2344         SET_ERR("Shutter notification for non-existent frame number %d",
   2345                 msg.frame_number);
   2346     }
   2347 }
   2348 
   2349 
   2350 CameraMetadata Camera3Device::getLatestRequestLocked() {
   2351     ALOGV("%s", __FUNCTION__);
   2352 
   2353     CameraMetadata retVal;
   2354 
   2355     if (mRequestThread != NULL) {
   2356         retVal = mRequestThread->getLatestRequest();
   2357     }
   2358 
   2359     return retVal;
   2360 }
   2361 
   2362 
   2363 /**
   2364  * RequestThread inner class methods
   2365  */
   2366 
   2367 Camera3Device::RequestThread::RequestThread(wp<Camera3Device> parent,
   2368         sp<StatusTracker> statusTracker,
   2369         camera3_device_t *hal3Device) :
   2370         Thread(false),
   2371         mParent(parent),
   2372         mStatusTracker(statusTracker),
   2373         mHal3Device(hal3Device),
   2374         mId(getId(parent)),
   2375         mReconfigured(false),
   2376         mDoPause(false),
   2377         mPaused(true),
   2378         mFrameNumber(0),
   2379         mLatestRequestId(NAME_NOT_FOUND),
   2380         mCurrentAfTriggerId(0),
   2381         mCurrentPreCaptureTriggerId(0),
   2382         mRepeatingLastFrameNumber(NO_IN_FLIGHT_REPEATING_FRAMES) {
   2383     mStatusId = statusTracker->addComponent();
   2384 }
   2385 
   2386 void Camera3Device::RequestThread::setNotifyCallback(
   2387         NotificationListener *listener) {
   2388     Mutex::Autolock l(mRequestLock);
   2389     mListener = listener;
   2390 }
   2391 
   2392 void Camera3Device::RequestThread::configurationComplete() {
   2393     Mutex::Autolock l(mRequestLock);
   2394     mReconfigured = true;
   2395 }
   2396 
   2397 status_t Camera3Device::RequestThread::queueRequestList(
   2398         List<sp<CaptureRequest> > &requests,
   2399         /*out*/
   2400         int64_t *lastFrameNumber) {
   2401     Mutex::Autolock l(mRequestLock);
   2402     for (List<sp<CaptureRequest> >::iterator it = requests.begin(); it != requests.end();
   2403             ++it) {
   2404         mRequestQueue.push_back(*it);
   2405     }
   2406 
   2407     if (lastFrameNumber != NULL) {
   2408         *lastFrameNumber = mFrameNumber + mRequestQueue.size() - 1;
   2409         ALOGV("%s: requestId %d, mFrameNumber %" PRId32 ", lastFrameNumber %" PRId64 ".",
   2410               __FUNCTION__, (*(requests.begin()))->mResultExtras.requestId, mFrameNumber,
   2411               *lastFrameNumber);
   2412     }
   2413 
   2414     unpauseForNewRequests();
   2415 
   2416     return OK;
   2417 }
   2418 
   2419 
   2420 status_t Camera3Device::RequestThread::queueTrigger(
   2421         RequestTrigger trigger[],
   2422         size_t count) {
   2423 
   2424     Mutex::Autolock l(mTriggerMutex);
   2425     status_t ret;
   2426 
   2427     for (size_t i = 0; i < count; ++i) {
   2428         ret = queueTriggerLocked(trigger[i]);
   2429 
   2430         if (ret != OK) {
   2431             return ret;
   2432         }
   2433     }
   2434 
   2435     return OK;
   2436 }
   2437 
   2438 int Camera3Device::RequestThread::getId(const wp<Camera3Device> &device) {
   2439     sp<Camera3Device> d = device.promote();
   2440     if (d != NULL) return d->mId;
   2441     return 0;
   2442 }
   2443 
   2444 status_t Camera3Device::RequestThread::queueTriggerLocked(
   2445         RequestTrigger trigger) {
   2446 
   2447     uint32_t tag = trigger.metadataTag;
   2448     ssize_t index = mTriggerMap.indexOfKey(tag);
   2449 
   2450     switch (trigger.getTagType()) {
   2451         case TYPE_BYTE:
   2452         // fall-through
   2453         case TYPE_INT32:
   2454             break;
   2455         default:
   2456             ALOGE("%s: Type not supported: 0x%x", __FUNCTION__,
   2457                     trigger.getTagType());
   2458             return INVALID_OPERATION;
   2459     }
   2460 
   2461     /**
   2462      * Collect only the latest trigger, since we only have 1 field
   2463      * in the request settings per trigger tag, and can't send more than 1
   2464      * trigger per request.
   2465      */
   2466     if (index != NAME_NOT_FOUND) {
   2467         mTriggerMap.editValueAt(index) = trigger;
   2468     } else {
   2469         mTriggerMap.add(tag, trigger);
   2470     }
   2471 
   2472     return OK;
   2473 }
   2474 
   2475 status_t Camera3Device::RequestThread::setRepeatingRequests(
   2476         const RequestList &requests,
   2477         /*out*/
   2478         int64_t *lastFrameNumber) {
   2479     Mutex::Autolock l(mRequestLock);
   2480     if (lastFrameNumber != NULL) {
   2481         *lastFrameNumber = mRepeatingLastFrameNumber;
   2482     }
   2483     mRepeatingRequests.clear();
   2484     mRepeatingRequests.insert(mRepeatingRequests.begin(),
   2485             requests.begin(), requests.end());
   2486 
   2487     unpauseForNewRequests();
   2488 
   2489     mRepeatingLastFrameNumber = NO_IN_FLIGHT_REPEATING_FRAMES;
   2490     return OK;
   2491 }
   2492 
   2493 bool Camera3Device::RequestThread::isRepeatingRequestLocked(const sp<CaptureRequest> requestIn) {
   2494     if (mRepeatingRequests.empty()) {
   2495         return false;
   2496     }
   2497     int32_t requestId = requestIn->mResultExtras.requestId;
   2498     const RequestList &repeatRequests = mRepeatingRequests;
   2499     // All repeating requests are guaranteed to have same id so only check first quest
   2500     const sp<CaptureRequest> firstRequest = *repeatRequests.begin();
   2501     return (firstRequest->mResultExtras.requestId == requestId);
   2502 }
   2503 
   2504 status_t Camera3Device::RequestThread::clearRepeatingRequests(/*out*/int64_t *lastFrameNumber) {
   2505     Mutex::Autolock l(mRequestLock);
   2506     mRepeatingRequests.clear();
   2507     if (lastFrameNumber != NULL) {
   2508         *lastFrameNumber = mRepeatingLastFrameNumber;
   2509     }
   2510     mRepeatingLastFrameNumber = NO_IN_FLIGHT_REPEATING_FRAMES;
   2511     return OK;
   2512 }
   2513 
   2514 status_t Camera3Device::RequestThread::clear(
   2515         NotificationListener *listener,
   2516         /*out*/int64_t *lastFrameNumber) {
   2517     Mutex::Autolock l(mRequestLock);
   2518     ALOGV("RequestThread::%s:", __FUNCTION__);
   2519 
   2520     mRepeatingRequests.clear();
   2521 
   2522     // Send errors for all requests pending in the request queue, including
   2523     // pending repeating requests
   2524     if (listener != NULL) {
   2525         for (RequestList::iterator it = mRequestQueue.begin();
   2526                  it != mRequestQueue.end(); ++it) {
   2527             // Set the frame number this request would have had, if it
   2528             // had been submitted; this frame number will not be reused.
   2529             // The requestId and burstId fields were set when the request was
   2530             // submitted originally (in convertMetadataListToRequestListLocked)
   2531             (*it)->mResultExtras.frameNumber = mFrameNumber++;
   2532             listener->notifyError(ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
   2533                     (*it)->mResultExtras);
   2534         }
   2535     }
   2536     mRequestQueue.clear();
   2537     mTriggerMap.clear();
   2538     if (lastFrameNumber != NULL) {
   2539         *lastFrameNumber = mRepeatingLastFrameNumber;
   2540     }
   2541     mRepeatingLastFrameNumber = NO_IN_FLIGHT_REPEATING_FRAMES;
   2542     return OK;
   2543 }
   2544 
   2545 void Camera3Device::RequestThread::setPaused(bool paused) {
   2546     Mutex::Autolock l(mPauseLock);
   2547     mDoPause = paused;
   2548     mDoPauseSignal.signal();
   2549 }
   2550 
   2551 status_t Camera3Device::RequestThread::waitUntilRequestProcessed(
   2552         int32_t requestId, nsecs_t timeout) {
   2553     Mutex::Autolock l(mLatestRequestMutex);
   2554     status_t res;
   2555     while (mLatestRequestId != requestId) {
   2556         nsecs_t startTime = systemTime();
   2557 
   2558         res = mLatestRequestSignal.waitRelative(mLatestRequestMutex, timeout);
   2559         if (res != OK) return res;
   2560 
   2561         timeout -= (systemTime() - startTime);
   2562     }
   2563 
   2564     return OK;
   2565 }
   2566 
   2567 void Camera3Device::RequestThread::requestExit() {
   2568     // Call parent to set up shutdown
   2569     Thread::requestExit();
   2570     // The exit from any possible waits
   2571     mDoPauseSignal.signal();
   2572     mRequestSignal.signal();
   2573 }
   2574 
   2575 bool Camera3Device::RequestThread::threadLoop() {
   2576 
   2577     status_t res;
   2578 
   2579     // Handle paused state.
   2580     if (waitIfPaused()) {
   2581         return true;
   2582     }
   2583 
   2584     // Get work to do
   2585 
   2586     sp<CaptureRequest> nextRequest = waitForNextRequest();
   2587     if (nextRequest == NULL) {
   2588         return true;
   2589     }
   2590 
   2591     // Create request to HAL
   2592     camera3_capture_request_t request = camera3_capture_request_t();
   2593     request.frame_number = nextRequest->mResultExtras.frameNumber;
   2594     Vector<camera3_stream_buffer_t> outputBuffers;
   2595 
   2596     // Get the request ID, if any
   2597     int requestId;
   2598     camera_metadata_entry_t requestIdEntry =
   2599             nextRequest->mSettings.find(ANDROID_REQUEST_ID);
   2600     if (requestIdEntry.count > 0) {
   2601         requestId = requestIdEntry.data.i32[0];
   2602     } else {
   2603         ALOGW("%s: Did not have android.request.id set in the request",
   2604                 __FUNCTION__);
   2605         requestId = NAME_NOT_FOUND;
   2606     }
   2607 
   2608     // Insert any queued triggers (before metadata is locked)
   2609     int32_t triggerCount;
   2610     res = insertTriggers(nextRequest);
   2611     if (res < 0) {
   2612         SET_ERR("RequestThread: Unable to insert triggers "
   2613                 "(capture request %d, HAL device: %s (%d)",
   2614                 request.frame_number, strerror(-res), res);
   2615         cleanUpFailedRequest(request, nextRequest, outputBuffers);
   2616         return false;
   2617     }
   2618     triggerCount = res;
   2619 
   2620     bool triggersMixedIn = (triggerCount > 0 || mPrevTriggers > 0);
   2621 
   2622     // If the request is the same as last, or we had triggers last time
   2623     if (mPrevRequest != nextRequest || triggersMixedIn) {
   2624         /**
   2625          * HAL workaround:
   2626          * Insert a dummy trigger ID if a trigger is set but no trigger ID is
   2627          */
   2628         res = addDummyTriggerIds(nextRequest);
   2629         if (res != OK) {
   2630             SET_ERR("RequestThread: Unable to insert dummy trigger IDs "
   2631                     "(capture request %d, HAL device: %s (%d)",
   2632                     request.frame_number, strerror(-res), res);
   2633             cleanUpFailedRequest(request, nextRequest, outputBuffers);
   2634             return false;
   2635         }
   2636 
   2637         /**
   2638          * The request should be presorted so accesses in HAL
   2639          *   are O(logn). Sidenote, sorting a sorted metadata is nop.
   2640          */
   2641         nextRequest->mSettings.sort();
   2642         request.settings = nextRequest->mSettings.getAndLock();
   2643         mPrevRequest = nextRequest;
   2644         ALOGVV("%s: Request settings are NEW", __FUNCTION__);
   2645 
   2646         IF_ALOGV() {
   2647             camera_metadata_ro_entry_t e = camera_metadata_ro_entry_t();
   2648             find_camera_metadata_ro_entry(
   2649                     request.settings,
   2650                     ANDROID_CONTROL_AF_TRIGGER,
   2651                     &e
   2652             );
   2653             if (e.count > 0) {
   2654                 ALOGV("%s: Request (frame num %d) had AF trigger 0x%x",
   2655                       __FUNCTION__,
   2656                       request.frame_number,
   2657                       e.data.u8[0]);
   2658             }
   2659         }
   2660     } else {
   2661         // leave request.settings NULL to indicate 'reuse latest given'
   2662         ALOGVV("%s: Request settings are REUSED",
   2663                __FUNCTION__);
   2664     }
   2665 
   2666     camera3_stream_buffer_t inputBuffer;
   2667     uint32_t totalNumBuffers = 0;
   2668 
   2669     // Fill in buffers
   2670 
   2671     if (nextRequest->mInputStream != NULL) {
   2672         request.input_buffer = &inputBuffer;
   2673         res = nextRequest->mInputStream->getInputBuffer(&inputBuffer);
   2674         if (res != OK) {
   2675             // Can't get input buffer from gralloc queue - this could be due to
   2676             // disconnected queue or other producer misbehavior, so not a fatal
   2677             // error
   2678             ALOGE("RequestThread: Can't get input buffer, skipping request:"
   2679                     " %s (%d)", strerror(-res), res);
   2680             Mutex::Autolock l(mRequestLock);
   2681             if (mListener != NULL) {
   2682                 mListener->notifyError(
   2683                         ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
   2684                         nextRequest->mResultExtras);
   2685             }
   2686             cleanUpFailedRequest(request, nextRequest, outputBuffers);
   2687             return true;
   2688         }
   2689         totalNumBuffers += 1;
   2690     } else {
   2691         request.input_buffer = NULL;
   2692     }
   2693 
   2694     outputBuffers.insertAt(camera3_stream_buffer_t(), 0,
   2695             nextRequest->mOutputStreams.size());
   2696     request.output_buffers = outputBuffers.array();
   2697     for (size_t i = 0; i < nextRequest->mOutputStreams.size(); i++) {
   2698         res = nextRequest->mOutputStreams.editItemAt(i)->
   2699                 getBuffer(&outputBuffers.editItemAt(i));
   2700         if (res != OK) {
   2701             // Can't get output buffer from gralloc queue - this could be due to
   2702             // abandoned queue or other consumer misbehavior, so not a fatal
   2703             // error
   2704             ALOGE("RequestThread: Can't get output buffer, skipping request:"
   2705                     " %s (%d)", strerror(-res), res);
   2706             Mutex::Autolock l(mRequestLock);
   2707             if (mListener != NULL) {
   2708                 mListener->notifyError(
   2709                         ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
   2710                         nextRequest->mResultExtras);
   2711             }
   2712             cleanUpFailedRequest(request, nextRequest, outputBuffers);
   2713             return true;
   2714         }
   2715         request.num_output_buffers++;
   2716     }
   2717     totalNumBuffers += request.num_output_buffers;
   2718 
   2719     // Log request in the in-flight queue
   2720     sp<Camera3Device> parent = mParent.promote();
   2721     if (parent == NULL) {
   2722         // Should not happen, and nowhere to send errors to, so just log it
   2723         CLOGE("RequestThread: Parent is gone");
   2724         cleanUpFailedRequest(request, nextRequest, outputBuffers);
   2725         return false;
   2726     }
   2727 
   2728     res = parent->registerInFlight(request.frame_number,
   2729             totalNumBuffers, nextRequest->mResultExtras,
   2730             /*hasInput*/request.input_buffer != NULL);
   2731     ALOGVV("%s: registered in flight requestId = %" PRId32 ", frameNumber = %" PRId64
   2732            ", burstId = %" PRId32 ".",
   2733             __FUNCTION__,
   2734             nextRequest->mResultExtras.requestId, nextRequest->mResultExtras.frameNumber,
   2735             nextRequest->mResultExtras.burstId);
   2736     if (res != OK) {
   2737         SET_ERR("RequestThread: Unable to register new in-flight request:"
   2738                 " %s (%d)", strerror(-res), res);
   2739         cleanUpFailedRequest(request, nextRequest, outputBuffers);
   2740         return false;
   2741     }
   2742 
   2743     // Inform waitUntilRequestProcessed thread of a new request ID
   2744     {
   2745         Mutex::Autolock al(mLatestRequestMutex);
   2746 
   2747         mLatestRequestId = requestId;
   2748         mLatestRequestSignal.signal();
   2749     }
   2750 
   2751     // Submit request and block until ready for next one
   2752     ATRACE_ASYNC_BEGIN("frame capture", request.frame_number);
   2753     ATRACE_BEGIN("camera3->process_capture_request");
   2754     res = mHal3Device->ops->process_capture_request(mHal3Device, &request);
   2755     ATRACE_END();
   2756 
   2757     if (res != OK) {
   2758         // Should only get a failure here for malformed requests or device-level
   2759         // errors, so consider all errors fatal.  Bad metadata failures should
   2760         // come through notify.
   2761         SET_ERR("RequestThread: Unable to submit capture request %d to HAL"
   2762                 " device: %s (%d)", request.frame_number, strerror(-res), res);
   2763         cleanUpFailedRequest(request, nextRequest, outputBuffers);
   2764         return false;
   2765     }
   2766 
   2767     // Update the latest request sent to HAL
   2768     if (request.settings != NULL) { // Don't update them if they were unchanged
   2769         Mutex::Autolock al(mLatestRequestMutex);
   2770 
   2771         camera_metadata_t* cloned = clone_camera_metadata(request.settings);
   2772         mLatestRequest.acquire(cloned);
   2773     }
   2774 
   2775     if (request.settings != NULL) {
   2776         nextRequest->mSettings.unlock(request.settings);
   2777     }
   2778 
   2779     // Remove any previously queued triggers (after unlock)
   2780     res = removeTriggers(mPrevRequest);
   2781     if (res != OK) {
   2782         SET_ERR("RequestThread: Unable to remove triggers "
   2783               "(capture request %d, HAL device: %s (%d)",
   2784               request.frame_number, strerror(-res), res);
   2785         return false;
   2786     }
   2787     mPrevTriggers = triggerCount;
   2788 
   2789     return true;
   2790 }
   2791 
   2792 CameraMetadata Camera3Device::RequestThread::getLatestRequest() const {
   2793     Mutex::Autolock al(mLatestRequestMutex);
   2794 
   2795     ALOGV("RequestThread::%s", __FUNCTION__);
   2796 
   2797     return mLatestRequest;
   2798 }
   2799 
   2800 
   2801 void Camera3Device::RequestThread::cleanUpFailedRequest(
   2802         camera3_capture_request_t &request,
   2803         sp<CaptureRequest> &nextRequest,
   2804         Vector<camera3_stream_buffer_t> &outputBuffers) {
   2805 
   2806     if (request.settings != NULL) {
   2807         nextRequest->mSettings.unlock(request.settings);
   2808     }
   2809     if (request.input_buffer != NULL) {
   2810         request.input_buffer->status = CAMERA3_BUFFER_STATUS_ERROR;
   2811         nextRequest->mInputStream->returnInputBuffer(*(request.input_buffer));
   2812     }
   2813     for (size_t i = 0; i < request.num_output_buffers; i++) {
   2814         outputBuffers.editItemAt(i).status = CAMERA3_BUFFER_STATUS_ERROR;
   2815         nextRequest->mOutputStreams.editItemAt(i)->returnBuffer(
   2816             outputBuffers[i], 0);
   2817     }
   2818 }
   2819 
   2820 sp<Camera3Device::CaptureRequest>
   2821         Camera3Device::RequestThread::waitForNextRequest() {
   2822     status_t res;
   2823     sp<CaptureRequest> nextRequest;
   2824 
   2825     // Optimized a bit for the simple steady-state case (single repeating
   2826     // request), to avoid putting that request in the queue temporarily.
   2827     Mutex::Autolock l(mRequestLock);
   2828 
   2829     while (mRequestQueue.empty()) {
   2830         if (!mRepeatingRequests.empty()) {
   2831             // Always atomically enqueue all requests in a repeating request
   2832             // list. Guarantees a complete in-sequence set of captures to
   2833             // application.
   2834             const RequestList &requests = mRepeatingRequests;
   2835             RequestList::const_iterator firstRequest =
   2836                     requests.begin();
   2837             nextRequest = *firstRequest;
   2838             mRequestQueue.insert(mRequestQueue.end(),
   2839                     ++firstRequest,
   2840                     requests.end());
   2841             // No need to wait any longer
   2842 
   2843             mRepeatingLastFrameNumber = mFrameNumber + requests.size() - 1;
   2844 
   2845             break;
   2846         }
   2847 
   2848         res = mRequestSignal.waitRelative(mRequestLock, kRequestTimeout);
   2849 
   2850         if ((mRequestQueue.empty() && mRepeatingRequests.empty()) ||
   2851                 exitPending()) {
   2852             Mutex::Autolock pl(mPauseLock);
   2853             if (mPaused == false) {
   2854                 ALOGV("%s: RequestThread: Going idle", __FUNCTION__);
   2855                 mPaused = true;
   2856                 // Let the tracker know
   2857                 sp<StatusTracker> statusTracker = mStatusTracker.promote();
   2858                 if (statusTracker != 0) {
   2859                     statusTracker->markComponentIdle(mStatusId, Fence::NO_FENCE);
   2860                 }
   2861             }
   2862             // Stop waiting for now and let thread management happen
   2863             return NULL;
   2864         }
   2865     }
   2866 
   2867     if (nextRequest == NULL) {
   2868         // Don't have a repeating request already in hand, so queue
   2869         // must have an entry now.
   2870         RequestList::iterator firstRequest =
   2871                 mRequestQueue.begin();
   2872         nextRequest = *firstRequest;
   2873         mRequestQueue.erase(firstRequest);
   2874     }
   2875 
   2876     // In case we've been unpaused by setPaused clearing mDoPause, need to
   2877     // update internal pause state (capture/setRepeatingRequest unpause
   2878     // directly).
   2879     Mutex::Autolock pl(mPauseLock);
   2880     if (mPaused) {
   2881         ALOGV("%s: RequestThread: Unpaused", __FUNCTION__);
   2882         sp<StatusTracker> statusTracker = mStatusTracker.promote();
   2883         if (statusTracker != 0) {
   2884             statusTracker->markComponentActive(mStatusId);
   2885         }
   2886     }
   2887     mPaused = false;
   2888 
   2889     // Check if we've reconfigured since last time, and reset the preview
   2890     // request if so. Can't use 'NULL request == repeat' across configure calls.
   2891     if (mReconfigured) {
   2892         mPrevRequest.clear();
   2893         mReconfigured = false;
   2894     }
   2895 
   2896     if (nextRequest != NULL) {
   2897         nextRequest->mResultExtras.frameNumber = mFrameNumber++;
   2898         nextRequest->mResultExtras.afTriggerId = mCurrentAfTriggerId;
   2899         nextRequest->mResultExtras.precaptureTriggerId = mCurrentPreCaptureTriggerId;
   2900     }
   2901     return nextRequest;
   2902 }
   2903 
   2904 bool Camera3Device::RequestThread::waitIfPaused() {
   2905     status_t res;
   2906     Mutex::Autolock l(mPauseLock);
   2907     while (mDoPause) {
   2908         if (mPaused == false) {
   2909             mPaused = true;
   2910             ALOGV("%s: RequestThread: Paused", __FUNCTION__);
   2911             // Let the tracker know
   2912             sp<StatusTracker> statusTracker = mStatusTracker.promote();
   2913             if (statusTracker != 0) {
   2914                 statusTracker->markComponentIdle(mStatusId, Fence::NO_FENCE);
   2915             }
   2916         }
   2917 
   2918         res = mDoPauseSignal.waitRelative(mPauseLock, kRequestTimeout);
   2919         if (res == TIMED_OUT || exitPending()) {
   2920             return true;
   2921         }
   2922     }
   2923     // We don't set mPaused to false here, because waitForNextRequest needs
   2924     // to further manage the paused state in case of starvation.
   2925     return false;
   2926 }
   2927 
   2928 void Camera3Device::RequestThread::unpauseForNewRequests() {
   2929     // With work to do, mark thread as unpaused.
   2930     // If paused by request (setPaused), don't resume, to avoid
   2931     // extra signaling/waiting overhead to waitUntilPaused
   2932     mRequestSignal.signal();
   2933     Mutex::Autolock p(mPauseLock);
   2934     if (!mDoPause) {
   2935         ALOGV("%s: RequestThread: Going active", __FUNCTION__);
   2936         if (mPaused) {
   2937             sp<StatusTracker> statusTracker = mStatusTracker.promote();
   2938             if (statusTracker != 0) {
   2939                 statusTracker->markComponentActive(mStatusId);
   2940             }
   2941         }
   2942         mPaused = false;
   2943     }
   2944 }
   2945 
   2946 void Camera3Device::RequestThread::setErrorState(const char *fmt, ...) {
   2947     sp<Camera3Device> parent = mParent.promote();
   2948     if (parent != NULL) {
   2949         va_list args;
   2950         va_start(args, fmt);
   2951 
   2952         parent->setErrorStateV(fmt, args);
   2953 
   2954         va_end(args);
   2955     }
   2956 }
   2957 
   2958 status_t Camera3Device::RequestThread::insertTriggers(
   2959         const sp<CaptureRequest> &request) {
   2960 
   2961     Mutex::Autolock al(mTriggerMutex);
   2962 
   2963     sp<Camera3Device> parent = mParent.promote();
   2964     if (parent == NULL) {
   2965         CLOGE("RequestThread: Parent is gone");
   2966         return DEAD_OBJECT;
   2967     }
   2968 
   2969     CameraMetadata &metadata = request->mSettings;
   2970     size_t count = mTriggerMap.size();
   2971 
   2972     for (size_t i = 0; i < count; ++i) {
   2973         RequestTrigger trigger = mTriggerMap.valueAt(i);
   2974         uint32_t tag = trigger.metadataTag;
   2975 
   2976         if (tag == ANDROID_CONTROL_AF_TRIGGER_ID || tag == ANDROID_CONTROL_AE_PRECAPTURE_ID) {
   2977             bool isAeTrigger = (trigger.metadataTag == ANDROID_CONTROL_AE_PRECAPTURE_ID);
   2978             uint32_t triggerId = static_cast<uint32_t>(trigger.entryValue);
   2979             if (isAeTrigger) {
   2980                 request->mResultExtras.precaptureTriggerId = triggerId;
   2981                 mCurrentPreCaptureTriggerId = triggerId;
   2982             } else {
   2983                 request->mResultExtras.afTriggerId = triggerId;
   2984                 mCurrentAfTriggerId = triggerId;
   2985             }
   2986             if (parent->mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
   2987                 continue; // Trigger ID tag is deprecated since device HAL 3.2
   2988             }
   2989         }
   2990 
   2991         camera_metadata_entry entry = metadata.find(tag);
   2992 
   2993         if (entry.count > 0) {
   2994             /**
   2995              * Already has an entry for this trigger in the request.
   2996              * Rewrite it with our requested trigger value.
   2997              */
   2998             RequestTrigger oldTrigger = trigger;
   2999 
   3000             oldTrigger.entryValue = entry.data.u8[0];
   3001 
   3002             mTriggerReplacedMap.add(tag, oldTrigger);
   3003         } else {
   3004             /**
   3005              * More typical, no trigger entry, so we just add it
   3006              */
   3007             mTriggerRemovedMap.add(tag, trigger);
   3008         }
   3009 
   3010         status_t res;
   3011 
   3012         switch (trigger.getTagType()) {
   3013             case TYPE_BYTE: {
   3014                 uint8_t entryValue = static_cast<uint8_t>(trigger.entryValue);
   3015                 res = metadata.update(tag,
   3016                                       &entryValue,
   3017                                       /*count*/1);
   3018                 break;
   3019             }
   3020             case TYPE_INT32:
   3021                 res = metadata.update(tag,
   3022                                       &trigger.entryValue,
   3023                                       /*count*/1);
   3024                 break;
   3025             default:
   3026                 ALOGE("%s: Type not supported: 0x%x",
   3027                       __FUNCTION__,
   3028                       trigger.getTagType());
   3029                 return INVALID_OPERATION;
   3030         }
   3031 
   3032         if (res != OK) {
   3033             ALOGE("%s: Failed to update request metadata with trigger tag %s"
   3034                   ", value %d", __FUNCTION__, trigger.getTagName(),
   3035                   trigger.entryValue);
   3036             return res;
   3037         }
   3038 
   3039         ALOGV("%s: Mixed in trigger %s, value %d", __FUNCTION__,
   3040               trigger.getTagName(),
   3041               trigger.entryValue);
   3042     }
   3043 
   3044     mTriggerMap.clear();
   3045 
   3046     return count;
   3047 }
   3048 
   3049 status_t Camera3Device::RequestThread::removeTriggers(
   3050         const sp<CaptureRequest> &request) {
   3051     Mutex::Autolock al(mTriggerMutex);
   3052 
   3053     CameraMetadata &metadata = request->mSettings;
   3054 
   3055     /**
   3056      * Replace all old entries with their old values.
   3057      */
   3058     for (size_t i = 0; i < mTriggerReplacedMap.size(); ++i) {
   3059         RequestTrigger trigger = mTriggerReplacedMap.valueAt(i);
   3060 
   3061         status_t res;
   3062 
   3063         uint32_t tag = trigger.metadataTag;
   3064         switch (trigger.getTagType()) {
   3065             case TYPE_BYTE: {
   3066                 uint8_t entryValue = static_cast<uint8_t>(trigger.entryValue);
   3067                 res = metadata.update(tag,
   3068                                       &entryValue,
   3069                                       /*count*/1);
   3070                 break;
   3071             }
   3072             case TYPE_INT32:
   3073                 res = metadata.update(tag,
   3074                                       &trigger.entryValue,
   3075                                       /*count*/1);
   3076                 break;
   3077             default:
   3078                 ALOGE("%s: Type not supported: 0x%x",
   3079                       __FUNCTION__,
   3080                       trigger.getTagType());
   3081                 return INVALID_OPERATION;
   3082         }
   3083 
   3084         if (res != OK) {
   3085             ALOGE("%s: Failed to restore request metadata with trigger tag %s"
   3086                   ", trigger value %d", __FUNCTION__,
   3087                   trigger.getTagName(), trigger.entryValue);
   3088             return res;
   3089         }
   3090     }
   3091     mTriggerReplacedMap.clear();
   3092 
   3093     /**
   3094      * Remove all new entries.
   3095      */
   3096     for (size_t i = 0; i < mTriggerRemovedMap.size(); ++i) {
   3097         RequestTrigger trigger = mTriggerRemovedMap.valueAt(i);
   3098         status_t res = metadata.erase(trigger.metadataTag);
   3099 
   3100         if (res != OK) {
   3101             ALOGE("%s: Failed to erase metadata with trigger tag %s"
   3102                   ", trigger value %d", __FUNCTION__,
   3103                   trigger.getTagName(), trigger.entryValue);
   3104             return res;
   3105         }
   3106     }
   3107     mTriggerRemovedMap.clear();
   3108 
   3109     return OK;
   3110 }
   3111 
   3112 status_t Camera3Device::RequestThread::addDummyTriggerIds(
   3113         const sp<CaptureRequest> &request) {
   3114     // Trigger ID 0 has special meaning in the HAL2 spec, so avoid it here
   3115     static const int32_t dummyTriggerId = 1;
   3116     status_t res;
   3117 
   3118     CameraMetadata &metadata = request->mSettings;
   3119 
   3120     // If AF trigger is active, insert a dummy AF trigger ID if none already
   3121     // exists
   3122     camera_metadata_entry afTrigger = metadata.find(ANDROID_CONTROL_AF_TRIGGER);
   3123     camera_metadata_entry afId = metadata.find(ANDROID_CONTROL_AF_TRIGGER_ID);
   3124     if (afTrigger.count > 0 &&
   3125             afTrigger.data.u8[0] != ANDROID_CONTROL_AF_TRIGGER_IDLE &&
   3126             afId.count == 0) {
   3127         res = metadata.update(ANDROID_CONTROL_AF_TRIGGER_ID, &dummyTriggerId, 1);
   3128         if (res != OK) return res;
   3129     }
   3130 
   3131     // If AE precapture trigger is active, insert a dummy precapture trigger ID
   3132     // if none already exists
   3133     camera_metadata_entry pcTrigger =
   3134             metadata.find(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER);
   3135     camera_metadata_entry pcId = metadata.find(ANDROID_CONTROL_AE_PRECAPTURE_ID);
   3136     if (pcTrigger.count > 0 &&
   3137             pcTrigger.data.u8[0] != ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_IDLE &&
   3138             pcId.count == 0) {
   3139         res = metadata.update(ANDROID_CONTROL_AE_PRECAPTURE_ID,
   3140                 &dummyTriggerId, 1);
   3141         if (res != OK) return res;
   3142     }
   3143 
   3144     return OK;
   3145 }
   3146 
   3147 
   3148 /**
   3149  * Static callback forwarding methods from HAL to instance
   3150  */
   3151 
   3152 void Camera3Device::sProcessCaptureResult(const camera3_callback_ops *cb,
   3153         const camera3_capture_result *result) {
   3154     Camera3Device *d =
   3155             const_cast<Camera3Device*>(static_cast<const Camera3Device*>(cb));
   3156     d->processCaptureResult(result);
   3157 }
   3158 
   3159 void Camera3Device::sNotify(const camera3_callback_ops *cb,
   3160         const camera3_notify_msg *msg) {
   3161     Camera3Device *d =
   3162             const_cast<Camera3Device*>(static_cast<const Camera3Device*>(cb));
   3163     d->notify(msg);
   3164 }
   3165 
   3166 }; // namespace android
   3167