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