1 /* 2 * Copyright (C) 2016 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 "CamDevSession (at) 3.2-impl" 18 #include <android/log.h> 19 20 #include <set> 21 #include <cutils/properties.h> 22 #include <utils/Trace.h> 23 #include <hardware/gralloc.h> 24 #include <hardware/gralloc1.h> 25 #include "CameraDeviceSession.h" 26 27 namespace android { 28 namespace hardware { 29 namespace camera { 30 namespace device { 31 namespace V3_2 { 32 namespace implementation { 33 34 // Size of request metadata fast message queue. Change to 0 to always use hwbinder buffer. 35 static constexpr int32_t CAMERA_REQUEST_METADATA_QUEUE_SIZE = 1 << 20 /* 1MB */; 36 // Size of result metadata fast message queue. Change to 0 to always use hwbinder buffer. 37 static constexpr int32_t CAMERA_RESULT_METADATA_QUEUE_SIZE = 1 << 20 /* 1MB */; 38 39 // Metadata sent by HAL will be replaced by a compact copy 40 // if their (total size >= compact size + METADATA_SHRINK_ABS_THRESHOLD && 41 // total_size >= compact size * METADATA_SHRINK_REL_THRESHOLD) 42 // Heuristically picked by size of one page 43 static constexpr int METADATA_SHRINK_ABS_THRESHOLD = 4096; 44 static constexpr int METADATA_SHRINK_REL_THRESHOLD = 2; 45 46 HandleImporter CameraDeviceSession::sHandleImporter; 47 buffer_handle_t CameraDeviceSession::sEmptyBuffer = nullptr; 48 49 const int CameraDeviceSession::ResultBatcher::NOT_BATCHED; 50 51 CameraDeviceSession::CameraDeviceSession( 52 camera3_device_t* device, 53 const camera_metadata_t* deviceInfo, 54 const sp<ICameraDeviceCallback>& callback) : 55 camera3_callback_ops({&sProcessCaptureResult, &sNotify, nullptr, nullptr}), 56 mDevice(device), 57 mDeviceVersion(device->common.version), 58 mFreeBufEarly(shouldFreeBufEarly()), 59 mIsAELockAvailable(false), 60 mDerivePostRawSensKey(false), 61 mNumPartialResults(1), 62 mResultBatcher(callback) { 63 mDeviceInfo = deviceInfo; 64 camera_metadata_entry partialResultsCount = 65 mDeviceInfo.find(ANDROID_REQUEST_PARTIAL_RESULT_COUNT); 66 if (partialResultsCount.count > 0) { 67 mNumPartialResults = partialResultsCount.data.i32[0]; 68 } 69 mResultBatcher.setNumPartialResults(mNumPartialResults); 70 71 camera_metadata_entry aeLockAvailableEntry = mDeviceInfo.find( 72 ANDROID_CONTROL_AE_LOCK_AVAILABLE); 73 if (aeLockAvailableEntry.count > 0) { 74 mIsAELockAvailable = (aeLockAvailableEntry.data.u8[0] == 75 ANDROID_CONTROL_AE_LOCK_AVAILABLE_TRUE); 76 } 77 78 // Determine whether we need to derive sensitivity boost values for older devices. 79 // If post-RAW sensitivity boost range is listed, so should post-raw sensitivity control 80 // be listed (as the default value 100) 81 if (mDeviceInfo.exists(ANDROID_CONTROL_POST_RAW_SENSITIVITY_BOOST_RANGE)) { 82 mDerivePostRawSensKey = true; 83 } 84 85 mInitFail = initialize(); 86 } 87 88 bool CameraDeviceSession::initialize() { 89 /** Initialize device with callback functions */ 90 ATRACE_BEGIN("camera3->initialize"); 91 status_t res = mDevice->ops->initialize(mDevice, this); 92 ATRACE_END(); 93 94 if (res != OK) { 95 ALOGE("%s: Unable to initialize HAL device: %s (%d)", 96 __FUNCTION__, strerror(-res), res); 97 mDevice->common.close(&mDevice->common); 98 mClosed = true; 99 return true; 100 } 101 102 // "ro.camera" properties are no longer supported on vendor side. 103 // Support a fall back for the fmq size override that uses "ro.vendor.camera" 104 // properties. 105 int32_t reqFMQSize = property_get_int32("ro.vendor.camera.req.fmq.size", /*default*/-1); 106 if (reqFMQSize < 0) { 107 reqFMQSize = property_get_int32("ro.camera.req.fmq.size", /*default*/-1); 108 if (reqFMQSize < 0) { 109 reqFMQSize = CAMERA_REQUEST_METADATA_QUEUE_SIZE; 110 } else { 111 ALOGV("%s: request FMQ size overridden to %d", __FUNCTION__, reqFMQSize); 112 } 113 } else { 114 ALOGV("%s: request FMQ size overridden to %d via fallback property", __FUNCTION__, 115 reqFMQSize); 116 } 117 118 mRequestMetadataQueue = std::make_unique<RequestMetadataQueue>( 119 static_cast<size_t>(reqFMQSize), 120 false /* non blocking */); 121 if (!mRequestMetadataQueue->isValid()) { 122 ALOGE("%s: invalid request fmq", __FUNCTION__); 123 return true; 124 } 125 126 // "ro.camera" properties are no longer supported on vendor side. 127 // Support a fall back for the fmq size override that uses "ro.vendor.camera" 128 // properties. 129 int32_t resFMQSize = property_get_int32("ro.vendor.camera.res.fmq.size", /*default*/-1); 130 if (resFMQSize < 0) { 131 resFMQSize = property_get_int32("ro.camera.res.fmq.size", /*default*/-1); 132 if (resFMQSize < 0) { 133 resFMQSize = CAMERA_RESULT_METADATA_QUEUE_SIZE; 134 } else { 135 ALOGV("%s: result FMQ size overridden to %d", __FUNCTION__, resFMQSize); 136 } 137 } else { 138 ALOGV("%s: result FMQ size overridden to %d via fallback property", __FUNCTION__, 139 resFMQSize); 140 } 141 142 mResultMetadataQueue = std::make_shared<RequestMetadataQueue>( 143 static_cast<size_t>(resFMQSize), 144 false /* non blocking */); 145 if (!mResultMetadataQueue->isValid()) { 146 ALOGE("%s: invalid result fmq", __FUNCTION__); 147 return true; 148 } 149 mResultBatcher.setResultMetadataQueue(mResultMetadataQueue); 150 151 return false; 152 } 153 154 bool CameraDeviceSession::shouldFreeBufEarly() { 155 return property_get_bool("ro.vendor.camera.free_buf_early", 0) == 1; 156 } 157 158 CameraDeviceSession::~CameraDeviceSession() { 159 if (!isClosed()) { 160 ALOGE("CameraDeviceSession deleted before close!"); 161 close(); 162 } 163 } 164 165 bool CameraDeviceSession::isClosed() { 166 Mutex::Autolock _l(mStateLock); 167 return mClosed; 168 } 169 170 Status CameraDeviceSession::initStatus() const { 171 Mutex::Autolock _l(mStateLock); 172 Status status = Status::OK; 173 if (mInitFail) { 174 status = Status::INTERNAL_ERROR; 175 } else if (mDisconnected) { 176 status = Status::CAMERA_DISCONNECTED; 177 } else if (mClosed) { 178 status = Status::INTERNAL_ERROR; 179 } 180 return status; 181 } 182 183 void CameraDeviceSession::disconnect() { 184 Mutex::Autolock _l(mStateLock); 185 mDisconnected = true; 186 ALOGW("%s: Camera device is disconnected. Closing.", __FUNCTION__); 187 if (!mClosed) { 188 mDevice->common.close(&mDevice->common); 189 mClosed = true; 190 } 191 } 192 193 void CameraDeviceSession::dumpState(const native_handle_t* fd) { 194 if (!isClosed()) { 195 mDevice->ops->dump(mDevice, fd->data[0]); 196 } 197 } 198 199 /** 200 * For devices <= CAMERA_DEVICE_API_VERSION_3_2, AE_PRECAPTURE_TRIGGER_CANCEL is not supported so 201 * we need to override AE_PRECAPTURE_TRIGGER_CANCEL to AE_PRECAPTURE_TRIGGER_IDLE and AE_LOCK_OFF 202 * to AE_LOCK_ON to start cancelling AE precapture. If AE lock is not available, it still overrides 203 * AE_PRECAPTURE_TRIGGER_CANCEL to AE_PRECAPTURE_TRIGGER_IDLE but doesn't add AE_LOCK_ON to the 204 * request. 205 */ 206 bool CameraDeviceSession::handleAePrecaptureCancelRequestLocked( 207 const camera3_capture_request_t &halRequest, 208 ::android::hardware::camera::common::V1_0::helper::CameraMetadata *settings /*out*/, 209 AETriggerCancelOverride *override /*out*/) { 210 if ((mDeviceVersion > CAMERA_DEVICE_API_VERSION_3_2) || 211 (nullptr == halRequest.settings) || (nullptr == settings) || 212 (0 == get_camera_metadata_entry_count(halRequest.settings))) { 213 return false; 214 } 215 216 settings->clear(); 217 settings->append(halRequest.settings); 218 camera_metadata_entry_t aePrecaptureTrigger = 219 settings->find(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER); 220 if (aePrecaptureTrigger.count > 0 && 221 aePrecaptureTrigger.data.u8[0] == 222 ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_CANCEL) { 223 // Always override CANCEL to IDLE 224 uint8_t aePrecaptureTrigger = 225 ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_IDLE; 226 settings->update(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER, 227 &aePrecaptureTrigger, 1); 228 *override = { false, ANDROID_CONTROL_AE_LOCK_OFF, 229 true, ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_CANCEL }; 230 231 if (mIsAELockAvailable == true) { 232 camera_metadata_entry_t aeLock = settings->find( 233 ANDROID_CONTROL_AE_LOCK); 234 if (aeLock.count == 0 || aeLock.data.u8[0] == 235 ANDROID_CONTROL_AE_LOCK_OFF) { 236 uint8_t aeLock = ANDROID_CONTROL_AE_LOCK_ON; 237 settings->update(ANDROID_CONTROL_AE_LOCK, &aeLock, 1); 238 override->applyAeLock = true; 239 override->aeLock = ANDROID_CONTROL_AE_LOCK_OFF; 240 } 241 } 242 243 return true; 244 } 245 246 return false; 247 } 248 249 /** 250 * Override result metadata for cancelling AE precapture trigger applied in 251 * handleAePrecaptureCancelRequestLocked(). 252 */ 253 void CameraDeviceSession::overrideResultForPrecaptureCancelLocked( 254 const AETriggerCancelOverride &aeTriggerCancelOverride, 255 ::android::hardware::camera::common::V1_0::helper::CameraMetadata *settings /*out*/) { 256 if (aeTriggerCancelOverride.applyAeLock) { 257 // Only devices <= v3.2 should have this override 258 assert(mDeviceVersion <= CAMERA_DEVICE_API_VERSION_3_2); 259 settings->update(ANDROID_CONTROL_AE_LOCK, &aeTriggerCancelOverride.aeLock, 1); 260 } 261 262 if (aeTriggerCancelOverride.applyAePrecaptureTrigger) { 263 // Only devices <= v3.2 should have this override 264 assert(mDeviceVersion <= CAMERA_DEVICE_API_VERSION_3_2); 265 settings->update(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER, 266 &aeTriggerCancelOverride.aePrecaptureTrigger, 1); 267 } 268 } 269 270 Status CameraDeviceSession::importBuffer(int32_t streamId, 271 uint64_t bufId, buffer_handle_t buf, 272 /*out*/buffer_handle_t** outBufPtr, 273 bool allowEmptyBuf) { 274 275 if (buf == nullptr && bufId == BUFFER_ID_NO_BUFFER) { 276 if (allowEmptyBuf) { 277 *outBufPtr = &sEmptyBuffer; 278 return Status::OK; 279 } else { 280 ALOGE("%s: bufferId %" PRIu64 " has null buffer handle!", __FUNCTION__, bufId); 281 return Status::ILLEGAL_ARGUMENT; 282 } 283 } 284 285 Mutex::Autolock _l(mInflightLock); 286 CirculatingBuffers& cbs = mCirculatingBuffers[streamId]; 287 if (cbs.count(bufId) == 0) { 288 // Register a newly seen buffer 289 buffer_handle_t importedBuf = buf; 290 sHandleImporter.importBuffer(importedBuf); 291 if (importedBuf == nullptr) { 292 ALOGE("%s: output buffer for stream %d is invalid!", __FUNCTION__, streamId); 293 return Status::INTERNAL_ERROR; 294 } else { 295 cbs[bufId] = importedBuf; 296 } 297 } 298 *outBufPtr = &cbs[bufId]; 299 return Status::OK; 300 } 301 302 Status CameraDeviceSession::importRequest( 303 const CaptureRequest& request, 304 hidl_vec<buffer_handle_t*>& allBufPtrs, 305 hidl_vec<int>& allFences) { 306 return importRequestImpl(request, allBufPtrs, allFences); 307 } 308 309 Status CameraDeviceSession::importRequestImpl( 310 const CaptureRequest& request, 311 hidl_vec<buffer_handle_t*>& allBufPtrs, 312 hidl_vec<int>& allFences, 313 bool allowEmptyBuf) { 314 bool hasInputBuf = (request.inputBuffer.streamId != -1 && 315 request.inputBuffer.bufferId != 0); 316 size_t numOutputBufs = request.outputBuffers.size(); 317 size_t numBufs = numOutputBufs + (hasInputBuf ? 1 : 0); 318 // Validate all I/O buffers 319 hidl_vec<buffer_handle_t> allBufs; 320 hidl_vec<uint64_t> allBufIds; 321 allBufs.resize(numBufs); 322 allBufIds.resize(numBufs); 323 allBufPtrs.resize(numBufs); 324 allFences.resize(numBufs); 325 std::vector<int32_t> streamIds(numBufs); 326 327 for (size_t i = 0; i < numOutputBufs; i++) { 328 allBufs[i] = request.outputBuffers[i].buffer.getNativeHandle(); 329 allBufIds[i] = request.outputBuffers[i].bufferId; 330 allBufPtrs[i] = &allBufs[i]; 331 streamIds[i] = request.outputBuffers[i].streamId; 332 } 333 if (hasInputBuf) { 334 allBufs[numOutputBufs] = request.inputBuffer.buffer.getNativeHandle(); 335 allBufIds[numOutputBufs] = request.inputBuffer.bufferId; 336 allBufPtrs[numOutputBufs] = &allBufs[numOutputBufs]; 337 streamIds[numOutputBufs] = request.inputBuffer.streamId; 338 } 339 340 for (size_t i = 0; i < numBufs; i++) { 341 Status st = importBuffer( 342 streamIds[i], allBufIds[i], allBufs[i], &allBufPtrs[i], 343 // Disallow empty buf for input stream, otherwise follow 344 // the allowEmptyBuf argument. 345 (hasInputBuf && i == numOutputBufs) ? false : allowEmptyBuf); 346 if (st != Status::OK) { 347 // Detailed error logs printed in importBuffer 348 return st; 349 } 350 } 351 352 // All buffers are imported. Now validate output buffer acquire fences 353 for (size_t i = 0; i < numOutputBufs; i++) { 354 if (!sHandleImporter.importFence( 355 request.outputBuffers[i].acquireFence, allFences[i])) { 356 ALOGE("%s: output buffer %zu acquire fence is invalid", __FUNCTION__, i); 357 cleanupInflightFences(allFences, i); 358 return Status::INTERNAL_ERROR; 359 } 360 } 361 362 // Validate input buffer acquire fences 363 if (hasInputBuf) { 364 if (!sHandleImporter.importFence( 365 request.inputBuffer.acquireFence, allFences[numOutputBufs])) { 366 ALOGE("%s: input buffer acquire fence is invalid", __FUNCTION__); 367 cleanupInflightFences(allFences, numOutputBufs); 368 return Status::INTERNAL_ERROR; 369 } 370 } 371 return Status::OK; 372 } 373 374 void CameraDeviceSession::cleanupInflightFences( 375 hidl_vec<int>& allFences, size_t numFences) { 376 for (size_t j = 0; j < numFences; j++) { 377 sHandleImporter.closeFence(allFences[j]); 378 } 379 } 380 381 CameraDeviceSession::ResultBatcher::ResultBatcher( 382 const sp<ICameraDeviceCallback>& callback) : mCallback(callback) {}; 383 384 bool CameraDeviceSession::ResultBatcher::InflightBatch::allDelivered() const { 385 if (!mShutterDelivered) return false; 386 387 if (mPartialResultProgress < mNumPartialResults) { 388 return false; 389 } 390 391 for (const auto& pair : mBatchBufs) { 392 if (!pair.second.mDelivered) { 393 return false; 394 } 395 } 396 return true; 397 } 398 399 void CameraDeviceSession::ResultBatcher::setNumPartialResults(uint32_t n) { 400 Mutex::Autolock _l(mLock); 401 mNumPartialResults = n; 402 } 403 404 void CameraDeviceSession::ResultBatcher::setBatchedStreams( 405 const std::vector<int>& streamsToBatch) { 406 Mutex::Autolock _l(mLock); 407 mStreamsToBatch = streamsToBatch; 408 } 409 410 void CameraDeviceSession::ResultBatcher::setResultMetadataQueue( 411 std::shared_ptr<ResultMetadataQueue> q) { 412 Mutex::Autolock _l(mLock); 413 mResultMetadataQueue = q; 414 } 415 416 void CameraDeviceSession::ResultBatcher::registerBatch(uint32_t frameNumber, uint32_t batchSize) { 417 auto batch = std::make_shared<InflightBatch>(); 418 batch->mFirstFrame = frameNumber; 419 batch->mBatchSize = batchSize; 420 batch->mLastFrame = batch->mFirstFrame + batch->mBatchSize - 1; 421 batch->mNumPartialResults = mNumPartialResults; 422 for (int id : mStreamsToBatch) { 423 batch->mBatchBufs.emplace(id, batch->mBatchSize); 424 } 425 Mutex::Autolock _l(mLock); 426 mInflightBatches.push_back(batch); 427 } 428 429 std::pair<int, std::shared_ptr<CameraDeviceSession::ResultBatcher::InflightBatch>> 430 CameraDeviceSession::ResultBatcher::getBatch( 431 uint32_t frameNumber) { 432 Mutex::Autolock _l(mLock); 433 int numBatches = mInflightBatches.size(); 434 if (numBatches == 0) { 435 return std::make_pair(NOT_BATCHED, nullptr); 436 } 437 uint32_t frameMin = mInflightBatches[0]->mFirstFrame; 438 uint32_t frameMax = mInflightBatches[numBatches - 1]->mLastFrame; 439 if (frameNumber < frameMin || frameNumber > frameMax) { 440 return std::make_pair(NOT_BATCHED, nullptr); 441 } 442 for (int i = 0; i < numBatches; i++) { 443 if (frameNumber >= mInflightBatches[i]->mFirstFrame && 444 frameNumber <= mInflightBatches[i]->mLastFrame) { 445 return std::make_pair(i, mInflightBatches[i]); 446 } 447 } 448 return std::make_pair(NOT_BATCHED, nullptr); 449 } 450 451 void CameraDeviceSession::ResultBatcher::checkAndRemoveFirstBatch() { 452 Mutex::Autolock _l(mLock); 453 if (mInflightBatches.size() > 0) { 454 std::shared_ptr<InflightBatch> batch = mInflightBatches[0]; 455 bool shouldRemove = false; 456 { 457 Mutex::Autolock _l(batch->mLock); 458 if (batch->allDelivered()) { 459 batch->mRemoved = true; 460 shouldRemove = true; 461 } 462 } 463 if (shouldRemove) { 464 mInflightBatches.pop_front(); 465 } 466 } 467 } 468 469 void CameraDeviceSession::ResultBatcher::sendBatchShutterCbsLocked( 470 std::shared_ptr<InflightBatch> batch) { 471 if (batch->mShutterDelivered) { 472 ALOGW("%s: batch shutter callback already sent!", __FUNCTION__); 473 return; 474 } 475 476 auto ret = mCallback->notify(batch->mShutterMsgs); 477 if (!ret.isOk()) { 478 ALOGE("%s: notify shutter transaction failed: %s", 479 __FUNCTION__, ret.description().c_str()); 480 } 481 batch->mShutterDelivered = true; 482 batch->mShutterMsgs.clear(); 483 } 484 485 void CameraDeviceSession::ResultBatcher::freeReleaseFences(hidl_vec<CaptureResult>& results) { 486 for (auto& result : results) { 487 if (result.inputBuffer.releaseFence.getNativeHandle() != nullptr) { 488 native_handle_t* handle = const_cast<native_handle_t*>( 489 result.inputBuffer.releaseFence.getNativeHandle()); 490 native_handle_close(handle); 491 native_handle_delete(handle); 492 } 493 for (auto& buf : result.outputBuffers) { 494 if (buf.releaseFence.getNativeHandle() != nullptr) { 495 native_handle_t* handle = const_cast<native_handle_t*>( 496 buf.releaseFence.getNativeHandle()); 497 native_handle_close(handle); 498 native_handle_delete(handle); 499 } 500 } 501 } 502 return; 503 } 504 505 void CameraDeviceSession::ResultBatcher::moveStreamBuffer(StreamBuffer&& src, StreamBuffer& dst) { 506 // Only dealing with releaseFence here. Assume buffer/acquireFence are null 507 const native_handle_t* handle = src.releaseFence.getNativeHandle(); 508 src.releaseFence = nullptr; 509 dst = src; 510 dst.releaseFence = handle; 511 if (handle != dst.releaseFence.getNativeHandle()) { 512 ALOGE("%s: native handle cloned!", __FUNCTION__); 513 } 514 } 515 516 void CameraDeviceSession::ResultBatcher::pushStreamBuffer( 517 StreamBuffer&& src, std::vector<StreamBuffer>& dst) { 518 // Only dealing with releaseFence here. Assume buffer/acquireFence are null 519 const native_handle_t* handle = src.releaseFence.getNativeHandle(); 520 src.releaseFence = nullptr; 521 dst.push_back(src); 522 dst.back().releaseFence = handle; 523 if (handle != dst.back().releaseFence.getNativeHandle()) { 524 ALOGE("%s: native handle cloned!", __FUNCTION__); 525 } 526 } 527 528 void CameraDeviceSession::ResultBatcher::sendBatchBuffersLocked( 529 std::shared_ptr<InflightBatch> batch) { 530 sendBatchBuffersLocked(batch, mStreamsToBatch); 531 } 532 533 void CameraDeviceSession::ResultBatcher::sendBatchBuffersLocked( 534 std::shared_ptr<InflightBatch> batch, const std::vector<int>& streams) { 535 size_t batchSize = 0; 536 for (int streamId : streams) { 537 auto it = batch->mBatchBufs.find(streamId); 538 if (it != batch->mBatchBufs.end()) { 539 InflightBatch::BufferBatch& bb = it->second; 540 if (bb.mDelivered) { 541 continue; 542 } 543 if (bb.mBuffers.size() > batchSize) { 544 batchSize = bb.mBuffers.size(); 545 } 546 } else { 547 ALOGE("%s: stream ID %d is not batched!", __FUNCTION__, streamId); 548 return; 549 } 550 } 551 552 if (batchSize == 0) { 553 ALOGW("%s: there is no buffer to be delivered for this batch.", __FUNCTION__); 554 for (int streamId : streams) { 555 auto it = batch->mBatchBufs.find(streamId); 556 if (it == batch->mBatchBufs.end()) { 557 ALOGE("%s: cannot find stream %d in batched buffers!", __FUNCTION__, streamId); 558 return; 559 } 560 InflightBatch::BufferBatch& bb = it->second; 561 bb.mDelivered = true; 562 } 563 return; 564 } 565 566 hidl_vec<CaptureResult> results; 567 results.resize(batchSize); 568 for (size_t i = 0; i < batchSize; i++) { 569 results[i].frameNumber = batch->mFirstFrame + i; 570 results[i].fmqResultSize = 0; 571 results[i].partialResult = 0; // 0 for buffer only results 572 results[i].inputBuffer.streamId = -1; 573 results[i].inputBuffer.bufferId = 0; 574 results[i].inputBuffer.buffer = nullptr; 575 std::vector<StreamBuffer> outBufs; 576 outBufs.reserve(streams.size()); 577 for (int streamId : streams) { 578 auto it = batch->mBatchBufs.find(streamId); 579 if (it == batch->mBatchBufs.end()) { 580 ALOGE("%s: cannot find stream %d in batched buffers!", __FUNCTION__, streamId); 581 return; 582 } 583 InflightBatch::BufferBatch& bb = it->second; 584 if (bb.mDelivered) { 585 continue; 586 } 587 if (i < bb.mBuffers.size()) { 588 pushStreamBuffer(std::move(bb.mBuffers[i]), outBufs); 589 } 590 } 591 results[i].outputBuffers.resize(outBufs.size()); 592 for (size_t j = 0; j < outBufs.size(); j++) { 593 moveStreamBuffer(std::move(outBufs[j]), results[i].outputBuffers[j]); 594 } 595 } 596 invokeProcessCaptureResultCallback(results, /* tryWriteFmq */false); 597 freeReleaseFences(results); 598 for (int streamId : streams) { 599 auto it = batch->mBatchBufs.find(streamId); 600 if (it == batch->mBatchBufs.end()) { 601 ALOGE("%s: cannot find stream %d in batched buffers!", __FUNCTION__, streamId); 602 return; 603 } 604 InflightBatch::BufferBatch& bb = it->second; 605 bb.mDelivered = true; 606 bb.mBuffers.clear(); 607 } 608 } 609 610 void CameraDeviceSession::ResultBatcher::sendBatchMetadataLocked( 611 std::shared_ptr<InflightBatch> batch, uint32_t lastPartialResultIdx) { 612 if (lastPartialResultIdx <= batch->mPartialResultProgress) { 613 // Result has been delivered. Return 614 ALOGW("%s: partial result %u has been delivered", __FUNCTION__, lastPartialResultIdx); 615 return; 616 } 617 618 std::vector<CaptureResult> results; 619 std::vector<uint32_t> toBeRemovedIdxes; 620 for (auto& pair : batch->mResultMds) { 621 uint32_t partialIdx = pair.first; 622 if (partialIdx > lastPartialResultIdx) { 623 continue; 624 } 625 toBeRemovedIdxes.push_back(partialIdx); 626 InflightBatch::MetadataBatch& mb = pair.second; 627 for (const auto& p : mb.mMds) { 628 CaptureResult result; 629 result.frameNumber = p.first; 630 result.result = std::move(p.second); 631 result.fmqResultSize = 0; 632 result.inputBuffer.streamId = -1; 633 result.inputBuffer.bufferId = 0; 634 result.inputBuffer.buffer = nullptr; 635 result.partialResult = partialIdx; 636 results.push_back(std::move(result)); 637 } 638 mb.mMds.clear(); 639 } 640 hidl_vec<CaptureResult> hResults; 641 hResults.setToExternal(results.data(), results.size()); 642 invokeProcessCaptureResultCallback(hResults, /* tryWriteFmq */true); 643 batch->mPartialResultProgress = lastPartialResultIdx; 644 for (uint32_t partialIdx : toBeRemovedIdxes) { 645 batch->mResultMds.erase(partialIdx); 646 } 647 } 648 649 void CameraDeviceSession::ResultBatcher::notifySingleMsg(NotifyMsg& msg) { 650 auto ret = mCallback->notify({msg}); 651 if (!ret.isOk()) { 652 ALOGE("%s: notify transaction failed: %s", 653 __FUNCTION__, ret.description().c_str()); 654 } 655 return; 656 } 657 658 void CameraDeviceSession::ResultBatcher::notify(NotifyMsg& msg) { 659 uint32_t frameNumber; 660 if (CC_LIKELY(msg.type == MsgType::SHUTTER)) { 661 frameNumber = msg.msg.shutter.frameNumber; 662 } else { 663 frameNumber = msg.msg.error.frameNumber; 664 } 665 666 auto pair = getBatch(frameNumber); 667 int batchIdx = pair.first; 668 if (batchIdx == NOT_BATCHED) { 669 notifySingleMsg(msg); 670 return; 671 } 672 673 // When error happened, stop batching for all batches earlier 674 if (CC_UNLIKELY(msg.type == MsgType::ERROR)) { 675 Mutex::Autolock _l(mLock); 676 for (int i = 0; i <= batchIdx; i++) { 677 // Send batched data up 678 std::shared_ptr<InflightBatch> batch = mInflightBatches[0]; 679 { 680 Mutex::Autolock _l(batch->mLock); 681 sendBatchShutterCbsLocked(batch); 682 sendBatchBuffersLocked(batch); 683 sendBatchMetadataLocked(batch, mNumPartialResults); 684 if (!batch->allDelivered()) { 685 ALOGE("%s: error: some batch data not sent back to framework!", 686 __FUNCTION__); 687 } 688 batch->mRemoved = true; 689 } 690 mInflightBatches.pop_front(); 691 } 692 // Send the error up 693 notifySingleMsg(msg); 694 return; 695 } 696 // Queue shutter callbacks for future delivery 697 std::shared_ptr<InflightBatch> batch = pair.second; 698 { 699 Mutex::Autolock _l(batch->mLock); 700 // Check if the batch is removed (mostly by notify error) before lock was acquired 701 if (batch->mRemoved) { 702 // Fall back to non-batch path 703 notifySingleMsg(msg); 704 return; 705 } 706 707 batch->mShutterMsgs.push_back(msg); 708 if (frameNumber == batch->mLastFrame) { 709 sendBatchShutterCbsLocked(batch); 710 } 711 } // end of batch lock scope 712 713 // see if the batch is complete 714 if (frameNumber == batch->mLastFrame) { 715 checkAndRemoveFirstBatch(); 716 } 717 } 718 719 void CameraDeviceSession::ResultBatcher::invokeProcessCaptureResultCallback( 720 hidl_vec<CaptureResult> &results, bool tryWriteFmq) { 721 if (mProcessCaptureResultLock.tryLock() != OK) { 722 ALOGV("%s: previous call is not finished! waiting 1s...", __FUNCTION__); 723 if (mProcessCaptureResultLock.timedLock(1000000000 /* 1s */) != OK) { 724 ALOGE("%s: cannot acquire lock in 1s, cannot proceed", 725 __FUNCTION__); 726 return; 727 } 728 } 729 if (tryWriteFmq && mResultMetadataQueue->availableToWrite() > 0) { 730 for (CaptureResult &result : results) { 731 if (result.result.size() > 0) { 732 if (mResultMetadataQueue->write(result.result.data(), result.result.size())) { 733 result.fmqResultSize = result.result.size(); 734 result.result.resize(0); 735 } else { 736 ALOGW("%s: couldn't utilize fmq, fall back to hwbinder, result size: %zu," 737 "shared message queue available size: %zu", 738 __FUNCTION__, result.result.size(), 739 mResultMetadataQueue->availableToWrite()); 740 result.fmqResultSize = 0; 741 } 742 } 743 } 744 } 745 auto ret = mCallback->processCaptureResult(results); 746 if (!ret.isOk()) { 747 ALOGE("%s: processCaptureResult transaction failed: %s", 748 __FUNCTION__, ret.description().c_str()); 749 } 750 mProcessCaptureResultLock.unlock(); 751 } 752 753 void CameraDeviceSession::ResultBatcher::processOneCaptureResult(CaptureResult& result) { 754 hidl_vec<CaptureResult> results; 755 results.resize(1); 756 results[0] = std::move(result); 757 invokeProcessCaptureResultCallback(results, /* tryWriteFmq */true); 758 freeReleaseFences(results); 759 return; 760 } 761 762 void CameraDeviceSession::ResultBatcher::processCaptureResult(CaptureResult& result) { 763 auto pair = getBatch(result.frameNumber); 764 int batchIdx = pair.first; 765 if (batchIdx == NOT_BATCHED) { 766 processOneCaptureResult(result); 767 return; 768 } 769 std::shared_ptr<InflightBatch> batch = pair.second; 770 { 771 Mutex::Autolock _l(batch->mLock); 772 // Check if the batch is removed (mostly by notify error) before lock was acquired 773 if (batch->mRemoved) { 774 // Fall back to non-batch path 775 processOneCaptureResult(result); 776 return; 777 } 778 779 // queue metadata 780 if (result.result.size() != 0) { 781 // Save a copy of metadata 782 batch->mResultMds[result.partialResult].mMds.push_back( 783 std::make_pair(result.frameNumber, result.result)); 784 } 785 786 // queue buffer 787 std::vector<int> filledStreams; 788 std::vector<StreamBuffer> nonBatchedBuffers; 789 for (auto& buffer : result.outputBuffers) { 790 auto it = batch->mBatchBufs.find(buffer.streamId); 791 if (it != batch->mBatchBufs.end()) { 792 InflightBatch::BufferBatch& bb = it->second; 793 pushStreamBuffer(std::move(buffer), bb.mBuffers); 794 filledStreams.push_back(buffer.streamId); 795 } else { 796 pushStreamBuffer(std::move(buffer), nonBatchedBuffers); 797 } 798 } 799 800 // send non-batched buffers up 801 if (nonBatchedBuffers.size() > 0 || result.inputBuffer.streamId != -1) { 802 CaptureResult nonBatchedResult; 803 nonBatchedResult.frameNumber = result.frameNumber; 804 nonBatchedResult.fmqResultSize = 0; 805 nonBatchedResult.outputBuffers.resize(nonBatchedBuffers.size()); 806 for (size_t i = 0; i < nonBatchedBuffers.size(); i++) { 807 moveStreamBuffer( 808 std::move(nonBatchedBuffers[i]), nonBatchedResult.outputBuffers[i]); 809 } 810 moveStreamBuffer(std::move(result.inputBuffer), nonBatchedResult.inputBuffer); 811 nonBatchedResult.partialResult = 0; // 0 for buffer only results 812 processOneCaptureResult(nonBatchedResult); 813 } 814 815 if (result.frameNumber == batch->mLastFrame) { 816 // Send data up 817 if (result.partialResult > 0) { 818 sendBatchMetadataLocked(batch, result.partialResult); 819 } 820 // send buffer up 821 if (filledStreams.size() > 0) { 822 sendBatchBuffersLocked(batch, filledStreams); 823 } 824 } 825 } // end of batch lock scope 826 827 // see if the batch is complete 828 if (result.frameNumber == batch->mLastFrame) { 829 checkAndRemoveFirstBatch(); 830 } 831 } 832 833 // Methods from ::android::hardware::camera::device::V3_2::ICameraDeviceSession follow. 834 Return<void> CameraDeviceSession::constructDefaultRequestSettings( 835 RequestTemplate type, ICameraDeviceSession::constructDefaultRequestSettings_cb _hidl_cb) { 836 CameraMetadata outMetadata; 837 Status status = constructDefaultRequestSettingsRaw( (int) type, &outMetadata); 838 _hidl_cb(status, outMetadata); 839 return Void(); 840 } 841 842 Status CameraDeviceSession::constructDefaultRequestSettingsRaw(int type, CameraMetadata *outMetadata) { 843 Status status = initStatus(); 844 const camera_metadata_t *rawRequest; 845 if (status == Status::OK) { 846 ATRACE_BEGIN("camera3->construct_default_request_settings"); 847 rawRequest = mDevice->ops->construct_default_request_settings(mDevice, (int) type); 848 ATRACE_END(); 849 if (rawRequest == nullptr) { 850 ALOGI("%s: template %d is not supported on this camera device", 851 __FUNCTION__, type); 852 status = Status::ILLEGAL_ARGUMENT; 853 } else { 854 mOverridenRequest.clear(); 855 mOverridenRequest.append(rawRequest); 856 // Derive some new keys for backward compatibility 857 if (mDerivePostRawSensKey && !mOverridenRequest.exists( 858 ANDROID_CONTROL_POST_RAW_SENSITIVITY_BOOST)) { 859 int32_t defaultBoost[1] = {100}; 860 mOverridenRequest.update( 861 ANDROID_CONTROL_POST_RAW_SENSITIVITY_BOOST, 862 defaultBoost, 1); 863 } 864 const camera_metadata_t *metaBuffer = 865 mOverridenRequest.getAndLock(); 866 convertToHidl(metaBuffer, outMetadata); 867 mOverridenRequest.unlock(metaBuffer); 868 } 869 } 870 return status; 871 } 872 873 /** 874 * Map Android N dataspace definitions back to Android M definitions, for 875 * use with HALv3.3 or older. 876 * 877 * Only map where correspondences exist, and otherwise preserve the value. 878 */ 879 android_dataspace CameraDeviceSession::mapToLegacyDataspace( 880 android_dataspace dataSpace) const { 881 if (mDeviceVersion <= CAMERA_DEVICE_API_VERSION_3_3) { 882 switch (dataSpace) { 883 case HAL_DATASPACE_V0_SRGB_LINEAR: 884 return HAL_DATASPACE_SRGB_LINEAR; 885 case HAL_DATASPACE_V0_SRGB: 886 return HAL_DATASPACE_SRGB; 887 case HAL_DATASPACE_V0_JFIF: 888 return HAL_DATASPACE_JFIF; 889 case HAL_DATASPACE_V0_BT601_625: 890 return HAL_DATASPACE_BT601_625; 891 case HAL_DATASPACE_V0_BT601_525: 892 return HAL_DATASPACE_BT601_525; 893 case HAL_DATASPACE_V0_BT709: 894 return HAL_DATASPACE_BT709; 895 default: 896 return dataSpace; 897 } 898 } 899 900 return dataSpace; 901 } 902 903 bool CameraDeviceSession::preProcessConfigurationLocked( 904 const StreamConfiguration& requestedConfiguration, 905 camera3_stream_configuration_t *stream_list /*out*/, 906 hidl_vec<camera3_stream_t*> *streams /*out*/) { 907 908 if ((stream_list == nullptr) || (streams == nullptr)) { 909 return false; 910 } 911 912 stream_list->operation_mode = (uint32_t) requestedConfiguration.operationMode; 913 stream_list->num_streams = requestedConfiguration.streams.size(); 914 streams->resize(stream_list->num_streams); 915 stream_list->streams = streams->data(); 916 917 for (uint32_t i = 0; i < stream_list->num_streams; i++) { 918 int id = requestedConfiguration.streams[i].id; 919 920 if (mStreamMap.count(id) == 0) { 921 Camera3Stream stream; 922 convertFromHidl(requestedConfiguration.streams[i], &stream); 923 mStreamMap[id] = stream; 924 mStreamMap[id].data_space = mapToLegacyDataspace( 925 mStreamMap[id].data_space); 926 mCirculatingBuffers.emplace(stream.mId, CirculatingBuffers{}); 927 } else { 928 // width/height/format must not change, but usage/rotation might need to change 929 if (mStreamMap[id].stream_type != 930 (int) requestedConfiguration.streams[i].streamType || 931 mStreamMap[id].width != requestedConfiguration.streams[i].width || 932 mStreamMap[id].height != requestedConfiguration.streams[i].height || 933 mStreamMap[id].format != (int) requestedConfiguration.streams[i].format || 934 mStreamMap[id].data_space != 935 mapToLegacyDataspace( static_cast<android_dataspace_t> ( 936 requestedConfiguration.streams[i].dataSpace))) { 937 ALOGE("%s: stream %d configuration changed!", __FUNCTION__, id); 938 return false; 939 } 940 mStreamMap[id].rotation = (int) requestedConfiguration.streams[i].rotation; 941 mStreamMap[id].usage = (uint32_t) requestedConfiguration.streams[i].usage; 942 } 943 (*streams)[i] = &mStreamMap[id]; 944 } 945 946 if (mFreeBufEarly) { 947 // Remove buffers of deleted streams 948 for(auto it = mStreamMap.begin(); it != mStreamMap.end(); it++) { 949 int id = it->first; 950 bool found = false; 951 for (const auto& stream : requestedConfiguration.streams) { 952 if (id == stream.id) { 953 found = true; 954 break; 955 } 956 } 957 if (!found) { 958 // Unmap all buffers of deleted stream 959 cleanupBuffersLocked(id); 960 } 961 } 962 } 963 964 return true; 965 } 966 967 void CameraDeviceSession::postProcessConfigurationLocked( 968 const StreamConfiguration& requestedConfiguration) { 969 // delete unused streams, note we do this after adding new streams to ensure new stream 970 // will not have the same address as deleted stream, and HAL has a chance to reference 971 // the to be deleted stream in configure_streams call 972 for(auto it = mStreamMap.begin(); it != mStreamMap.end();) { 973 int id = it->first; 974 bool found = false; 975 for (const auto& stream : requestedConfiguration.streams) { 976 if (id == stream.id) { 977 found = true; 978 break; 979 } 980 } 981 if (!found) { 982 // Unmap all buffers of deleted stream 983 // in case the configuration call succeeds and HAL 984 // is able to release the corresponding resources too. 985 if (!mFreeBufEarly) { 986 cleanupBuffersLocked(id); 987 } 988 it = mStreamMap.erase(it); 989 } else { 990 ++it; 991 } 992 } 993 994 // Track video streams 995 mVideoStreamIds.clear(); 996 for (const auto& stream : requestedConfiguration.streams) { 997 if (stream.streamType == StreamType::OUTPUT && 998 stream.usage & 999 graphics::common::V1_0::BufferUsage::VIDEO_ENCODER) { 1000 mVideoStreamIds.push_back(stream.id); 1001 } 1002 } 1003 mResultBatcher.setBatchedStreams(mVideoStreamIds); 1004 } 1005 1006 1007 void CameraDeviceSession::postProcessConfigurationFailureLocked( 1008 const StreamConfiguration& requestedConfiguration) { 1009 if (mFreeBufEarly) { 1010 // Re-build the buf cache entry for deleted streams 1011 for(auto it = mStreamMap.begin(); it != mStreamMap.end(); it++) { 1012 int id = it->first; 1013 bool found = false; 1014 for (const auto& stream : requestedConfiguration.streams) { 1015 if (id == stream.id) { 1016 found = true; 1017 break; 1018 } 1019 } 1020 if (!found) { 1021 mCirculatingBuffers.emplace(id, CirculatingBuffers{}); 1022 } 1023 } 1024 } 1025 } 1026 1027 Return<void> CameraDeviceSession::configureStreams( 1028 const StreamConfiguration& requestedConfiguration, 1029 ICameraDeviceSession::configureStreams_cb _hidl_cb) { 1030 Status status = initStatus(); 1031 HalStreamConfiguration outStreams; 1032 1033 // hold the inflight lock for entire configureStreams scope since there must not be any 1034 // inflight request/results during stream configuration. 1035 Mutex::Autolock _l(mInflightLock); 1036 if (!mInflightBuffers.empty()) { 1037 ALOGE("%s: trying to configureStreams while there are still %zu inflight buffers!", 1038 __FUNCTION__, mInflightBuffers.size()); 1039 _hidl_cb(Status::INTERNAL_ERROR, outStreams); 1040 return Void(); 1041 } 1042 1043 if (!mInflightAETriggerOverrides.empty()) { 1044 ALOGE("%s: trying to configureStreams while there are still %zu inflight" 1045 " trigger overrides!", __FUNCTION__, 1046 mInflightAETriggerOverrides.size()); 1047 _hidl_cb(Status::INTERNAL_ERROR, outStreams); 1048 return Void(); 1049 } 1050 1051 if (!mInflightRawBoostPresent.empty()) { 1052 ALOGE("%s: trying to configureStreams while there are still %zu inflight" 1053 " boost overrides!", __FUNCTION__, 1054 mInflightRawBoostPresent.size()); 1055 _hidl_cb(Status::INTERNAL_ERROR, outStreams); 1056 return Void(); 1057 } 1058 1059 if (status != Status::OK) { 1060 _hidl_cb(status, outStreams); 1061 return Void(); 1062 } 1063 1064 camera3_stream_configuration_t stream_list{}; 1065 hidl_vec<camera3_stream_t*> streams; 1066 if (!preProcessConfigurationLocked(requestedConfiguration, &stream_list, &streams)) { 1067 _hidl_cb(Status::INTERNAL_ERROR, outStreams); 1068 return Void(); 1069 } 1070 1071 ATRACE_BEGIN("camera3->configure_streams"); 1072 status_t ret = mDevice->ops->configure_streams(mDevice, &stream_list); 1073 ATRACE_END(); 1074 1075 // In case Hal returns error most likely it was not able to release 1076 // the corresponding resources of the deleted streams. 1077 if (ret == OK) { 1078 postProcessConfigurationLocked(requestedConfiguration); 1079 } else { 1080 postProcessConfigurationFailureLocked(requestedConfiguration); 1081 } 1082 1083 if (ret == -EINVAL) { 1084 status = Status::ILLEGAL_ARGUMENT; 1085 } else if (ret != OK) { 1086 status = Status::INTERNAL_ERROR; 1087 } else { 1088 convertToHidl(stream_list, &outStreams); 1089 mFirstRequest = true; 1090 } 1091 1092 _hidl_cb(status, outStreams); 1093 return Void(); 1094 } 1095 1096 // Needs to get called after acquiring 'mInflightLock' 1097 void CameraDeviceSession::cleanupBuffersLocked(int id) { 1098 for (auto& pair : mCirculatingBuffers.at(id)) { 1099 sHandleImporter.freeBuffer(pair.second); 1100 } 1101 mCirculatingBuffers[id].clear(); 1102 mCirculatingBuffers.erase(id); 1103 } 1104 1105 void CameraDeviceSession::updateBufferCaches(const hidl_vec<BufferCache>& cachesToRemove) { 1106 Mutex::Autolock _l(mInflightLock); 1107 for (auto& cache : cachesToRemove) { 1108 auto cbsIt = mCirculatingBuffers.find(cache.streamId); 1109 if (cbsIt == mCirculatingBuffers.end()) { 1110 // The stream could have been removed 1111 continue; 1112 } 1113 CirculatingBuffers& cbs = cbsIt->second; 1114 auto it = cbs.find(cache.bufferId); 1115 if (it != cbs.end()) { 1116 sHandleImporter.freeBuffer(it->second); 1117 cbs.erase(it); 1118 } else { 1119 ALOGE("%s: stream %d buffer %" PRIu64 " is not cached", 1120 __FUNCTION__, cache.streamId, cache.bufferId); 1121 } 1122 } 1123 } 1124 1125 Return<void> CameraDeviceSession::getCaptureRequestMetadataQueue( 1126 ICameraDeviceSession::getCaptureRequestMetadataQueue_cb _hidl_cb) { 1127 _hidl_cb(*mRequestMetadataQueue->getDesc()); 1128 return Void(); 1129 } 1130 1131 Return<void> CameraDeviceSession::getCaptureResultMetadataQueue( 1132 ICameraDeviceSession::getCaptureResultMetadataQueue_cb _hidl_cb) { 1133 _hidl_cb(*mResultMetadataQueue->getDesc()); 1134 return Void(); 1135 } 1136 1137 Return<void> CameraDeviceSession::processCaptureRequest( 1138 const hidl_vec<CaptureRequest>& requests, 1139 const hidl_vec<BufferCache>& cachesToRemove, 1140 ICameraDeviceSession::processCaptureRequest_cb _hidl_cb) { 1141 updateBufferCaches(cachesToRemove); 1142 1143 uint32_t numRequestProcessed = 0; 1144 Status s = Status::OK; 1145 for (size_t i = 0; i < requests.size(); i++, numRequestProcessed++) { 1146 s = processOneCaptureRequest(requests[i]); 1147 if (s != Status::OK) { 1148 break; 1149 } 1150 } 1151 1152 if (s == Status::OK && requests.size() > 1) { 1153 mResultBatcher.registerBatch(requests[0].frameNumber, requests.size()); 1154 } 1155 1156 _hidl_cb(s, numRequestProcessed); 1157 return Void(); 1158 } 1159 1160 Status CameraDeviceSession::processOneCaptureRequest(const CaptureRequest& request) { 1161 Status status = initStatus(); 1162 if (status != Status::OK) { 1163 ALOGE("%s: camera init failed or disconnected", __FUNCTION__); 1164 return status; 1165 } 1166 1167 camera3_capture_request_t halRequest; 1168 halRequest.frame_number = request.frameNumber; 1169 1170 bool converted = true; 1171 CameraMetadata settingsFmq; // settings from FMQ 1172 if (request.fmqSettingsSize > 0) { 1173 // non-blocking read; client must write metadata before calling 1174 // processOneCaptureRequest 1175 settingsFmq.resize(request.fmqSettingsSize); 1176 bool read = mRequestMetadataQueue->read(settingsFmq.data(), request.fmqSettingsSize); 1177 if (read) { 1178 converted = convertFromHidl(settingsFmq, &halRequest.settings); 1179 } else { 1180 ALOGE("%s: capture request settings metadata couldn't be read from fmq!", __FUNCTION__); 1181 converted = false; 1182 } 1183 } else { 1184 converted = convertFromHidl(request.settings, &halRequest.settings); 1185 } 1186 1187 if (!converted) { 1188 ALOGE("%s: capture request settings metadata is corrupt!", __FUNCTION__); 1189 return Status::ILLEGAL_ARGUMENT; 1190 } 1191 1192 if (mFirstRequest && halRequest.settings == nullptr) { 1193 ALOGE("%s: capture request settings must not be null for first request!", 1194 __FUNCTION__); 1195 return Status::ILLEGAL_ARGUMENT; 1196 } 1197 1198 hidl_vec<buffer_handle_t*> allBufPtrs; 1199 hidl_vec<int> allFences; 1200 bool hasInputBuf = (request.inputBuffer.streamId != -1 && 1201 request.inputBuffer.bufferId != 0); 1202 size_t numOutputBufs = request.outputBuffers.size(); 1203 size_t numBufs = numOutputBufs + (hasInputBuf ? 1 : 0); 1204 1205 if (numOutputBufs == 0) { 1206 ALOGE("%s: capture request must have at least one output buffer!", __FUNCTION__); 1207 return Status::ILLEGAL_ARGUMENT; 1208 } 1209 1210 status = importRequest(request, allBufPtrs, allFences); 1211 if (status != Status::OK) { 1212 return status; 1213 } 1214 1215 hidl_vec<camera3_stream_buffer_t> outHalBufs; 1216 outHalBufs.resize(numOutputBufs); 1217 bool aeCancelTriggerNeeded = false; 1218 ::android::hardware::camera::common::V1_0::helper::CameraMetadata settingsOverride; 1219 { 1220 Mutex::Autolock _l(mInflightLock); 1221 if (hasInputBuf) { 1222 auto key = std::make_pair(request.inputBuffer.streamId, request.frameNumber); 1223 auto& bufCache = mInflightBuffers[key] = camera3_stream_buffer_t{}; 1224 convertFromHidl( 1225 allBufPtrs[numOutputBufs], request.inputBuffer.status, 1226 &mStreamMap[request.inputBuffer.streamId], allFences[numOutputBufs], 1227 &bufCache); 1228 halRequest.input_buffer = &bufCache; 1229 } else { 1230 halRequest.input_buffer = nullptr; 1231 } 1232 1233 halRequest.num_output_buffers = numOutputBufs; 1234 for (size_t i = 0; i < numOutputBufs; i++) { 1235 auto key = std::make_pair(request.outputBuffers[i].streamId, request.frameNumber); 1236 auto& bufCache = mInflightBuffers[key] = camera3_stream_buffer_t{}; 1237 convertFromHidl( 1238 allBufPtrs[i], request.outputBuffers[i].status, 1239 &mStreamMap[request.outputBuffers[i].streamId], allFences[i], 1240 &bufCache); 1241 outHalBufs[i] = bufCache; 1242 } 1243 halRequest.output_buffers = outHalBufs.data(); 1244 1245 AETriggerCancelOverride triggerOverride; 1246 aeCancelTriggerNeeded = handleAePrecaptureCancelRequestLocked( 1247 halRequest, &settingsOverride /*out*/, &triggerOverride/*out*/); 1248 if (aeCancelTriggerNeeded) { 1249 mInflightAETriggerOverrides[halRequest.frame_number] = 1250 triggerOverride; 1251 halRequest.settings = settingsOverride.getAndLock(); 1252 } 1253 } 1254 halRequest.num_physcam_settings = 0; 1255 1256 ATRACE_ASYNC_BEGIN("frame capture", request.frameNumber); 1257 ATRACE_BEGIN("camera3->process_capture_request"); 1258 status_t ret = mDevice->ops->process_capture_request(mDevice, &halRequest); 1259 ATRACE_END(); 1260 if (aeCancelTriggerNeeded) { 1261 settingsOverride.unlock(halRequest.settings); 1262 } 1263 if (ret != OK) { 1264 Mutex::Autolock _l(mInflightLock); 1265 ALOGE("%s: HAL process_capture_request call failed!", __FUNCTION__); 1266 1267 cleanupInflightFences(allFences, numBufs); 1268 if (hasInputBuf) { 1269 auto key = std::make_pair(request.inputBuffer.streamId, request.frameNumber); 1270 mInflightBuffers.erase(key); 1271 } 1272 for (size_t i = 0; i < numOutputBufs; i++) { 1273 auto key = std::make_pair(request.outputBuffers[i].streamId, request.frameNumber); 1274 mInflightBuffers.erase(key); 1275 } 1276 if (aeCancelTriggerNeeded) { 1277 mInflightAETriggerOverrides.erase(request.frameNumber); 1278 } 1279 return Status::INTERNAL_ERROR; 1280 } 1281 1282 mFirstRequest = false; 1283 return Status::OK; 1284 } 1285 1286 Return<Status> CameraDeviceSession::flush() { 1287 Status status = initStatus(); 1288 if (status == Status::OK) { 1289 // Flush is always supported on device 3.1 or later 1290 status_t ret = mDevice->ops->flush(mDevice); 1291 if (ret != OK) { 1292 status = Status::INTERNAL_ERROR; 1293 } 1294 } 1295 return status; 1296 } 1297 1298 Return<void> CameraDeviceSession::close() { 1299 Mutex::Autolock _l(mStateLock); 1300 if (!mClosed) { 1301 { 1302 Mutex::Autolock _l(mInflightLock); 1303 if (!mInflightBuffers.empty()) { 1304 ALOGE("%s: trying to close while there are still %zu inflight buffers!", 1305 __FUNCTION__, mInflightBuffers.size()); 1306 } 1307 if (!mInflightAETriggerOverrides.empty()) { 1308 ALOGE("%s: trying to close while there are still %zu inflight " 1309 "trigger overrides!", __FUNCTION__, 1310 mInflightAETriggerOverrides.size()); 1311 } 1312 if (!mInflightRawBoostPresent.empty()) { 1313 ALOGE("%s: trying to close while there are still %zu inflight " 1314 " RAW boost overrides!", __FUNCTION__, 1315 mInflightRawBoostPresent.size()); 1316 } 1317 1318 } 1319 1320 ATRACE_BEGIN("camera3->close"); 1321 mDevice->common.close(&mDevice->common); 1322 ATRACE_END(); 1323 1324 // free all imported buffers 1325 Mutex::Autolock _l(mInflightLock); 1326 for(auto& pair : mCirculatingBuffers) { 1327 CirculatingBuffers& buffers = pair.second; 1328 for (auto& p2 : buffers) { 1329 sHandleImporter.freeBuffer(p2.second); 1330 } 1331 buffers.clear(); 1332 } 1333 mCirculatingBuffers.clear(); 1334 1335 mClosed = true; 1336 } 1337 return Void(); 1338 } 1339 1340 uint64_t CameraDeviceSession::getCapResultBufferId(const buffer_handle_t&, int) { 1341 // No need to fill in bufferId by default 1342 return BUFFER_ID_NO_BUFFER; 1343 } 1344 1345 status_t CameraDeviceSession::constructCaptureResult(CaptureResult& result, 1346 const camera3_capture_result *hal_result) { 1347 uint32_t frameNumber = hal_result->frame_number; 1348 bool hasInputBuf = (hal_result->input_buffer != nullptr); 1349 size_t numOutputBufs = hal_result->num_output_buffers; 1350 size_t numBufs = numOutputBufs + (hasInputBuf ? 1 : 0); 1351 if (numBufs > 0) { 1352 Mutex::Autolock _l(mInflightLock); 1353 if (hasInputBuf) { 1354 int streamId = static_cast<Camera3Stream*>(hal_result->input_buffer->stream)->mId; 1355 // validate if buffer is inflight 1356 auto key = std::make_pair(streamId, frameNumber); 1357 if (mInflightBuffers.count(key) != 1) { 1358 ALOGE("%s: input buffer for stream %d frame %d is not inflight!", 1359 __FUNCTION__, streamId, frameNumber); 1360 return -EINVAL; 1361 } 1362 } 1363 1364 for (size_t i = 0; i < numOutputBufs; i++) { 1365 int streamId = static_cast<Camera3Stream*>(hal_result->output_buffers[i].stream)->mId; 1366 // validate if buffer is inflight 1367 auto key = std::make_pair(streamId, frameNumber); 1368 if (mInflightBuffers.count(key) != 1) { 1369 ALOGE("%s: output buffer for stream %d frame %d is not inflight!", 1370 __FUNCTION__, streamId, frameNumber); 1371 return -EINVAL; 1372 } 1373 } 1374 } 1375 // We don't need to validate/import fences here since we will be passing them to camera service 1376 // within the scope of this function 1377 result.frameNumber = frameNumber; 1378 result.fmqResultSize = 0; 1379 result.partialResult = hal_result->partial_result; 1380 convertToHidl(hal_result->result, &result.result); 1381 if (nullptr != hal_result->result) { 1382 bool resultOverriden = false; 1383 Mutex::Autolock _l(mInflightLock); 1384 1385 // Derive some new keys for backward compatibility 1386 if (mDerivePostRawSensKey) { 1387 camera_metadata_ro_entry entry; 1388 if (find_camera_metadata_ro_entry(hal_result->result, 1389 ANDROID_CONTROL_POST_RAW_SENSITIVITY_BOOST, &entry) == 0) { 1390 mInflightRawBoostPresent[frameNumber] = true; 1391 } else { 1392 auto entry = mInflightRawBoostPresent.find(frameNumber); 1393 if (mInflightRawBoostPresent.end() == entry) { 1394 mInflightRawBoostPresent[frameNumber] = false; 1395 } 1396 } 1397 1398 if ((hal_result->partial_result == mNumPartialResults)) { 1399 if (!mInflightRawBoostPresent[frameNumber]) { 1400 if (!resultOverriden) { 1401 mOverridenResult.clear(); 1402 mOverridenResult.append(hal_result->result); 1403 resultOverriden = true; 1404 } 1405 int32_t defaultBoost[1] = {100}; 1406 mOverridenResult.update( 1407 ANDROID_CONTROL_POST_RAW_SENSITIVITY_BOOST, 1408 defaultBoost, 1); 1409 } 1410 1411 mInflightRawBoostPresent.erase(frameNumber); 1412 } 1413 } 1414 1415 auto entry = mInflightAETriggerOverrides.find(frameNumber); 1416 if (mInflightAETriggerOverrides.end() != entry) { 1417 if (!resultOverriden) { 1418 mOverridenResult.clear(); 1419 mOverridenResult.append(hal_result->result); 1420 resultOverriden = true; 1421 } 1422 overrideResultForPrecaptureCancelLocked(entry->second, 1423 &mOverridenResult); 1424 if (hal_result->partial_result == mNumPartialResults) { 1425 mInflightAETriggerOverrides.erase(frameNumber); 1426 } 1427 } 1428 1429 if (resultOverriden) { 1430 const camera_metadata_t *metaBuffer = 1431 mOverridenResult.getAndLock(); 1432 convertToHidl(metaBuffer, &result.result); 1433 mOverridenResult.unlock(metaBuffer); 1434 } 1435 } 1436 if (hasInputBuf) { 1437 result.inputBuffer.streamId = 1438 static_cast<Camera3Stream*>(hal_result->input_buffer->stream)->mId; 1439 result.inputBuffer.buffer = nullptr; 1440 result.inputBuffer.status = (BufferStatus) hal_result->input_buffer->status; 1441 // skip acquire fence since it's no use to camera service 1442 if (hal_result->input_buffer->release_fence != -1) { 1443 native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); 1444 handle->data[0] = hal_result->input_buffer->release_fence; 1445 result.inputBuffer.releaseFence = handle; 1446 } else { 1447 result.inputBuffer.releaseFence = nullptr; 1448 } 1449 } else { 1450 result.inputBuffer.streamId = -1; 1451 } 1452 1453 result.outputBuffers.resize(numOutputBufs); 1454 for (size_t i = 0; i < numOutputBufs; i++) { 1455 result.outputBuffers[i].streamId = 1456 static_cast<Camera3Stream*>(hal_result->output_buffers[i].stream)->mId; 1457 result.outputBuffers[i].buffer = nullptr; 1458 if (hal_result->output_buffers[i].buffer != nullptr) { 1459 result.outputBuffers[i].bufferId = getCapResultBufferId( 1460 *(hal_result->output_buffers[i].buffer), 1461 result.outputBuffers[i].streamId); 1462 } else { 1463 result.outputBuffers[i].bufferId = 0; 1464 } 1465 1466 result.outputBuffers[i].status = (BufferStatus) hal_result->output_buffers[i].status; 1467 // skip acquire fence since it's of no use to camera service 1468 if (hal_result->output_buffers[i].release_fence != -1) { 1469 native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); 1470 handle->data[0] = hal_result->output_buffers[i].release_fence; 1471 result.outputBuffers[i].releaseFence = handle; 1472 } else { 1473 result.outputBuffers[i].releaseFence = nullptr; 1474 } 1475 } 1476 1477 // Free inflight record/fences. 1478 // Do this before call back to camera service because camera service might jump to 1479 // configure_streams right after the processCaptureResult call so we need to finish 1480 // updating inflight queues first 1481 if (numBufs > 0) { 1482 Mutex::Autolock _l(mInflightLock); 1483 if (hasInputBuf) { 1484 int streamId = static_cast<Camera3Stream*>(hal_result->input_buffer->stream)->mId; 1485 auto key = std::make_pair(streamId, frameNumber); 1486 mInflightBuffers.erase(key); 1487 } 1488 1489 for (size_t i = 0; i < numOutputBufs; i++) { 1490 int streamId = static_cast<Camera3Stream*>(hal_result->output_buffers[i].stream)->mId; 1491 auto key = std::make_pair(streamId, frameNumber); 1492 mInflightBuffers.erase(key); 1493 } 1494 1495 if (mInflightBuffers.empty()) { 1496 ALOGV("%s: inflight buffer queue is now empty!", __FUNCTION__); 1497 } 1498 } 1499 return OK; 1500 } 1501 1502 // Static helper method to copy/shrink capture result metadata sent by HAL 1503 void CameraDeviceSession::sShrinkCaptureResult( 1504 camera3_capture_result* dst, const camera3_capture_result* src, 1505 std::vector<::android::hardware::camera::common::V1_0::helper::CameraMetadata>* mds, 1506 std::vector<const camera_metadata_t*>* physCamMdArray, 1507 bool handlePhysCam) { 1508 *dst = *src; 1509 // Reserve maximum number of entries to avoid metadata re-allocation. 1510 mds->reserve(1 + (handlePhysCam ? src->num_physcam_metadata : 0)); 1511 if (sShouldShrink(src->result)) { 1512 mds->emplace_back(sCreateCompactCopy(src->result)); 1513 dst->result = mds->back().getAndLock(); 1514 } 1515 1516 if (handlePhysCam) { 1517 // First determine if we need to create new camera_metadata_t* array 1518 bool needShrink = false; 1519 for (uint32_t i = 0; i < src->num_physcam_metadata; i++) { 1520 if (sShouldShrink(src->physcam_metadata[i])) { 1521 needShrink = true; 1522 } 1523 } 1524 1525 if (!needShrink) return; 1526 1527 physCamMdArray->reserve(src->num_physcam_metadata); 1528 dst->physcam_metadata = physCamMdArray->data(); 1529 for (uint32_t i = 0; i < src->num_physcam_metadata; i++) { 1530 if (sShouldShrink(src->physcam_metadata[i])) { 1531 mds->emplace_back(sCreateCompactCopy(src->physcam_metadata[i])); 1532 dst->physcam_metadata[i] = mds->back().getAndLock(); 1533 } else { 1534 dst->physcam_metadata[i] = src->physcam_metadata[i]; 1535 } 1536 } 1537 } 1538 } 1539 1540 bool CameraDeviceSession::sShouldShrink(const camera_metadata_t* md) { 1541 size_t compactSize = get_camera_metadata_compact_size(md); 1542 size_t totalSize = get_camera_metadata_size(md); 1543 if (totalSize >= compactSize + METADATA_SHRINK_ABS_THRESHOLD && 1544 totalSize >= compactSize * METADATA_SHRINK_REL_THRESHOLD) { 1545 ALOGV("Camera metadata should be shrunk from %zu to %zu", totalSize, compactSize); 1546 return true; 1547 } 1548 return false; 1549 } 1550 1551 camera_metadata_t* CameraDeviceSession::sCreateCompactCopy(const camera_metadata_t* src) { 1552 size_t compactSize = get_camera_metadata_compact_size(src); 1553 void* buffer = calloc(1, compactSize); 1554 if (buffer == nullptr) { 1555 ALOGE("%s: Allocating %zu bytes failed", __FUNCTION__, compactSize); 1556 } 1557 return copy_camera_metadata(buffer, compactSize, src); 1558 } 1559 1560 /** 1561 * Static callback forwarding methods from HAL to instance 1562 */ 1563 void CameraDeviceSession::sProcessCaptureResult( 1564 const camera3_callback_ops *cb, 1565 const camera3_capture_result *hal_result) { 1566 CameraDeviceSession *d = 1567 const_cast<CameraDeviceSession*>(static_cast<const CameraDeviceSession*>(cb)); 1568 1569 CaptureResult result = {}; 1570 camera3_capture_result shadowResult; 1571 bool handlePhysCam = (d->mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_5); 1572 std::vector<::android::hardware::camera::common::V1_0::helper::CameraMetadata> compactMds; 1573 std::vector<const camera_metadata_t*> physCamMdArray; 1574 sShrinkCaptureResult(&shadowResult, hal_result, &compactMds, &physCamMdArray, handlePhysCam); 1575 1576 status_t ret = d->constructCaptureResult(result, &shadowResult); 1577 if (ret == OK) { 1578 d->mResultBatcher.processCaptureResult(result); 1579 } 1580 } 1581 1582 void CameraDeviceSession::sNotify( 1583 const camera3_callback_ops *cb, 1584 const camera3_notify_msg *msg) { 1585 CameraDeviceSession *d = 1586 const_cast<CameraDeviceSession*>(static_cast<const CameraDeviceSession*>(cb)); 1587 NotifyMsg hidlMsg; 1588 convertToHidl(msg, &hidlMsg); 1589 1590 if (hidlMsg.type == (MsgType) CAMERA3_MSG_ERROR && 1591 hidlMsg.msg.error.errorStreamId != -1) { 1592 if (d->mStreamMap.count(hidlMsg.msg.error.errorStreamId) != 1) { 1593 ALOGE("%s: unknown stream ID %d reports an error!", 1594 __FUNCTION__, hidlMsg.msg.error.errorStreamId); 1595 return; 1596 } 1597 } 1598 1599 if (static_cast<camera3_msg_type_t>(hidlMsg.type) == CAMERA3_MSG_ERROR) { 1600 switch (hidlMsg.msg.error.errorCode) { 1601 case ErrorCode::ERROR_DEVICE: 1602 case ErrorCode::ERROR_REQUEST: 1603 case ErrorCode::ERROR_RESULT: { 1604 Mutex::Autolock _l(d->mInflightLock); 1605 auto entry = d->mInflightAETriggerOverrides.find( 1606 hidlMsg.msg.error.frameNumber); 1607 if (d->mInflightAETriggerOverrides.end() != entry) { 1608 d->mInflightAETriggerOverrides.erase( 1609 hidlMsg.msg.error.frameNumber); 1610 } 1611 1612 auto boostEntry = d->mInflightRawBoostPresent.find( 1613 hidlMsg.msg.error.frameNumber); 1614 if (d->mInflightRawBoostPresent.end() != boostEntry) { 1615 d->mInflightRawBoostPresent.erase( 1616 hidlMsg.msg.error.frameNumber); 1617 } 1618 1619 } 1620 break; 1621 case ErrorCode::ERROR_BUFFER: 1622 default: 1623 break; 1624 } 1625 1626 } 1627 1628 d->mResultBatcher.notify(hidlMsg); 1629 } 1630 1631 } // namespace implementation 1632 } // namespace V3_2 1633 } // namespace device 1634 } // namespace camera 1635 } // namespace hardware 1636 } // namespace android 1637