Loading camera/device/3.4/default/ExternalCameraDeviceSession.cpp +63 −62 Original line number Diff line number Diff line Loading @@ -526,15 +526,14 @@ Status ExternalCameraDeviceSession::processOneCaptureRequest(const CaptureReques return Status::INTERNAL_ERROR; } // TODO: reduce object copy in this path HalRequest halReq = { .frameNumber = request.frameNumber, .setting = mLatestReqSetting, .frameIn = frameIn, .shutterTs = shutterTs}; halReq.buffers.resize(numOutputBufs); std::shared_ptr<HalRequest> halReq = std::make_shared<HalRequest>(); halReq->frameNumber = request.frameNumber; halReq->setting = mLatestReqSetting; halReq->frameIn = frameIn; halReq->shutterTs = shutterTs; halReq->buffers.resize(numOutputBufs); for (size_t i = 0; i < numOutputBufs; i++) { HalStreamBuffer& halBuf = halReq.buffers[i]; HalStreamBuffer& halBuf = halReq->buffers[i]; int streamId = halBuf.streamId = request.outputBuffers[i].streamId; halBuf.bufferId = request.outputBuffers[i].bufferId; const Stream& stream = mStreamMap[streamId]; Loading @@ -546,7 +545,7 @@ Status ExternalCameraDeviceSession::processOneCaptureRequest(const CaptureReques halBuf.acquireFence = allFences[i]; halBuf.fenceTimeout = false; } mInflightFrames.insert(halReq.frameNumber); mInflightFrames.insert(halReq->frameNumber); // Send request to OutputThread for the rest of processing mOutputThread->submitRequest(halReq); mFirstRequest = false; Loading @@ -572,30 +571,31 @@ void ExternalCameraDeviceSession::notifyError( } //TODO: refactor with processCaptureResult Status ExternalCameraDeviceSession::processCaptureRequestError(const HalRequest& req) { Status ExternalCameraDeviceSession::processCaptureRequestError( const std::shared_ptr<HalRequest>& req) { // Return V4L2 buffer to V4L2 buffer queue enqueueV4l2Frame(req.frameIn); enqueueV4l2Frame(req->frameIn); // NotifyShutter notifyShutter(req.frameNumber, req.shutterTs); notifyShutter(req->frameNumber, req->shutterTs); notifyError(/*frameNum*/req.frameNumber, /*stream*/-1, ErrorCode::ERROR_REQUEST); notifyError(/*frameNum*/req->frameNumber, /*stream*/-1, ErrorCode::ERROR_REQUEST); // Fill output buffers hidl_vec<CaptureResult> results; results.resize(1); CaptureResult& result = results[0]; result.frameNumber = req.frameNumber; result.frameNumber = req->frameNumber; result.partialResult = 1; result.inputBuffer.streamId = -1; result.outputBuffers.resize(req.buffers.size()); for (size_t i = 0; i < req.buffers.size(); i++) { result.outputBuffers[i].streamId = req.buffers[i].streamId; result.outputBuffers[i].bufferId = req.buffers[i].bufferId; result.outputBuffers.resize(req->buffers.size()); for (size_t i = 0; i < req->buffers.size(); i++) { result.outputBuffers[i].streamId = req->buffers[i].streamId; result.outputBuffers[i].bufferId = req->buffers[i].bufferId; result.outputBuffers[i].status = BufferStatus::ERROR; if (req.buffers[i].acquireFence >= 0) { if (req->buffers[i].acquireFence >= 0) { native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); handle->data[0] = req.buffers[i].acquireFence; handle->data[0] = req->buffers[i].acquireFence; result.outputBuffers[i].releaseFence.setTo(handle, /*shouldOwn*/false); } } Loading @@ -603,7 +603,7 @@ Status ExternalCameraDeviceSession::processCaptureRequestError(const HalRequest& // update inflight records { Mutex::Autolock _l(mLock); mInflightFrames.erase(req.frameNumber); mInflightFrames.erase(req->frameNumber); } // Callback into framework Loading @@ -612,51 +612,51 @@ Status ExternalCameraDeviceSession::processCaptureRequestError(const HalRequest& return Status::OK; } Status ExternalCameraDeviceSession::processCaptureResult(HalRequest& req) { Status ExternalCameraDeviceSession::processCaptureResult(std::shared_ptr<HalRequest>& req) { // Return V4L2 buffer to V4L2 buffer queue enqueueV4l2Frame(req.frameIn); enqueueV4l2Frame(req->frameIn); // NotifyShutter notifyShutter(req.frameNumber, req.shutterTs); notifyShutter(req->frameNumber, req->shutterTs); // Fill output buffers hidl_vec<CaptureResult> results; results.resize(1); CaptureResult& result = results[0]; result.frameNumber = req.frameNumber; result.frameNumber = req->frameNumber; result.partialResult = 1; result.inputBuffer.streamId = -1; result.outputBuffers.resize(req.buffers.size()); for (size_t i = 0; i < req.buffers.size(); i++) { result.outputBuffers[i].streamId = req.buffers[i].streamId; result.outputBuffers[i].bufferId = req.buffers[i].bufferId; if (req.buffers[i].fenceTimeout) { result.outputBuffers.resize(req->buffers.size()); for (size_t i = 0; i < req->buffers.size(); i++) { result.outputBuffers[i].streamId = req->buffers[i].streamId; result.outputBuffers[i].bufferId = req->buffers[i].bufferId; if (req->buffers[i].fenceTimeout) { result.outputBuffers[i].status = BufferStatus::ERROR; native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); handle->data[0] = req.buffers[i].acquireFence; handle->data[0] = req->buffers[i].acquireFence; result.outputBuffers[i].releaseFence.setTo(handle, /*shouldOwn*/false); notifyError(req.frameNumber, req.buffers[i].streamId, ErrorCode::ERROR_BUFFER); notifyError(req->frameNumber, req->buffers[i].streamId, ErrorCode::ERROR_BUFFER); } else { result.outputBuffers[i].status = BufferStatus::OK; // TODO: refactor if (req.buffers[i].acquireFence > 0) { if (req->buffers[i].acquireFence > 0) { native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); handle->data[0] = req.buffers[i].acquireFence; handle->data[0] = req->buffers[i].acquireFence; result.outputBuffers[i].releaseFence.setTo(handle, /*shouldOwn*/false); } } } // Fill capture result metadata fillCaptureResult(req.setting, req.shutterTs); const camera_metadata_t *rawResult = req.setting.getAndLock(); fillCaptureResult(req->setting, req->shutterTs); const camera_metadata_t *rawResult = req->setting.getAndLock(); V3_2::implementation::convertToHidl(rawResult, &result.result); req.setting.unlock(rawResult); req->setting.unlock(rawResult); // update inflight records { Mutex::Autolock _l(mLock); mInflightFrames.erase(req.frameNumber); mInflightFrames.erase(req->frameNumber); } // Callback into framework Loading Loading @@ -1387,7 +1387,7 @@ ssize_t ExternalCameraDeviceSession::getJpegBufferSize( int ExternalCameraDeviceSession::OutputThread::createJpegLocked( HalStreamBuffer &halBuf, HalRequest &req) const std::shared_ptr<HalRequest>& req) { int ret; auto lfail = [&](auto... args) { Loading @@ -1414,17 +1414,17 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( int jpegQuality, thumbQuality; Size thumbSize; if (req.setting.exists(ANDROID_JPEG_QUALITY)) { if (req->setting.exists(ANDROID_JPEG_QUALITY)) { camera_metadata_entry entry = req.setting.find(ANDROID_JPEG_QUALITY); req->setting.find(ANDROID_JPEG_QUALITY); jpegQuality = entry.data.u8[0]; } else { return lfail("%s: ANDROID_JPEG_QUALITY not set",__FUNCTION__); } if (req.setting.exists(ANDROID_JPEG_THUMBNAIL_QUALITY)) { if (req->setting.exists(ANDROID_JPEG_THUMBNAIL_QUALITY)) { camera_metadata_entry entry = req.setting.find(ANDROID_JPEG_THUMBNAIL_QUALITY); req->setting.find(ANDROID_JPEG_THUMBNAIL_QUALITY); thumbQuality = entry.data.u8[0]; } else { return lfail( Loading @@ -1432,9 +1432,9 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( __FUNCTION__); } if (req.setting.exists(ANDROID_JPEG_THUMBNAIL_SIZE)) { if (req->setting.exists(ANDROID_JPEG_THUMBNAIL_SIZE)) { camera_metadata_entry entry = req.setting.find(ANDROID_JPEG_THUMBNAIL_SIZE); req->setting.find(ANDROID_JPEG_THUMBNAIL_SIZE); thumbSize = Size { static_cast<uint32_t>(entry.data.i32[0]), static_cast<uint32_t>(entry.data.i32[1]) }; Loading Loading @@ -1494,7 +1494,7 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( /* Combine camera characteristics with request settings to form EXIF * metadata */ common::V1_0::helper::CameraMetadata meta(parent->mCameraCharacteristics); meta.append(req.setting); meta.append(req->setting); /* Generate EXIF object */ std::unique_ptr<ExifUtils> utils(ExifUtils::create()); Loading Loading @@ -1558,7 +1558,7 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( } bool ExternalCameraDeviceSession::OutputThread::threadLoop() { HalRequest req; std::shared_ptr<HalRequest> req; auto parent = mParent.promote(); if (parent == nullptr) { ALOGE("%s: session has been disconnected!", __FUNCTION__); Loading @@ -1569,7 +1569,7 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { // regularly to prevent v4l buffer queue filled with stale buffers // when app doesn't program a preveiw request waitForNextRequest(&req); if (req.frameIn == nullptr) { if (req == nullptr) { // No new request, wait again return true; } Loading @@ -1577,17 +1577,17 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { auto onDeviceError = [&](auto... args) { ALOGE(args...); parent->notifyError( req.frameNumber, /*stream*/-1, ErrorCode::ERROR_DEVICE); req->frameNumber, /*stream*/-1, ErrorCode::ERROR_DEVICE); signalRequestDone(); return false; }; if (req.frameIn->mFourcc != V4L2_PIX_FMT_MJPEG) { if (req->frameIn->mFourcc != V4L2_PIX_FMT_MJPEG) { return onDeviceError("%s: do not support V4L2 format %c%c%c%c", __FUNCTION__, req.frameIn->mFourcc & 0xFF, (req.frameIn->mFourcc >> 8) & 0xFF, (req.frameIn->mFourcc >> 16) & 0xFF, (req.frameIn->mFourcc >> 24) & 0xFF); req->frameIn->mFourcc & 0xFF, (req->frameIn->mFourcc >> 8) & 0xFF, (req->frameIn->mFourcc >> 16) & 0xFF, (req->frameIn->mFourcc >> 24) & 0xFF); } std::unique_lock<std::mutex> lk(mBufferLock); Loading @@ -1595,7 +1595,7 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { // TODO: see if we can save some computation by converting to YV12 here uint8_t* inData; size_t inDataSize; req.frameIn->map(&inData, &inDataSize); req->frameIn->map(&inData, &inDataSize); // TODO: profile // TODO: in some special case maybe we can decode jpg directly to gralloc output? int res = libyuv::MJPGToI420( Loading Loading @@ -1623,7 +1623,7 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { ALOGV("%s processing new request", __FUNCTION__); const int kSyncWaitTimeoutMs = 500; for (auto& halBuf : req.buffers) { for (auto& halBuf : req->buffers) { if (halBuf.acquireFence != -1) { int ret = sync_wait(halBuf.acquireFence, kSyncWaitTimeoutMs); if (ret) { Loading Loading @@ -1780,9 +1780,9 @@ Status ExternalCameraDeviceSession::OutputThread::allocateIntermediateBuffers( return Status::OK; } Status ExternalCameraDeviceSession::OutputThread::submitRequest(const HalRequest& req) { Status ExternalCameraDeviceSession::OutputThread::submitRequest( const std::shared_ptr<HalRequest>& req) { std::unique_lock<std::mutex> lk(mRequestListLock); // TODO: reduce object copy in this path mRequestList.push_back(req); lk.unlock(); mRequestCond.notify_one(); Loading @@ -1797,7 +1797,7 @@ void ExternalCameraDeviceSession::OutputThread::flush() { } std::unique_lock<std::mutex> lk(mRequestListLock); std::list<HalRequest> reqs = mRequestList; std::list<std::shared_ptr<HalRequest>> reqs = std::move(mRequestList); mRequestList.clear(); if (mProcessingRequest) { std::chrono::seconds timeout = std::chrono::seconds(kFlushWaitTimeoutSec); Loading @@ -1813,7 +1813,8 @@ void ExternalCameraDeviceSession::OutputThread::flush() { } } void ExternalCameraDeviceSession::OutputThread::waitForNextRequest(HalRequest* out) { void ExternalCameraDeviceSession::OutputThread::waitForNextRequest( std::shared_ptr<HalRequest>* out) { if (out == nullptr) { ALOGE("%s: out is null", __FUNCTION__); return; Loading @@ -1838,7 +1839,7 @@ void ExternalCameraDeviceSession::OutputThread::waitForNextRequest(HalRequest* o *out = mRequestList.front(); mRequestList.pop_front(); mProcessingRequest = true; mProcessingFrameNumer = out->frameNumber; mProcessingFrameNumer = (*out)->frameNumber; } void ExternalCameraDeviceSession::OutputThread::signalRequestDone() { Loading @@ -1858,7 +1859,7 @@ void ExternalCameraDeviceSession::OutputThread::dump(int fd) { } dprintf(fd, "OutputThread request list contains frame: "); for (const auto& req : mRequestList) { dprintf(fd, "%d, ", req.frameNumber); dprintf(fd, "%d, ", req->frameNumber); } dprintf(fd, "\n"); } Loading camera/device/3.4/default/include/ext_device_v3_4_impl/ExternalCameraDeviceSession.h +8 −7 Original line number Diff line number Diff line Loading @@ -199,8 +199,8 @@ protected: Status processOneCaptureRequest(const CaptureRequest& request); Status processCaptureResult(HalRequest&); Status processCaptureRequestError(const HalRequest&); Status processCaptureResult(std::shared_ptr<HalRequest>&); Status processCaptureRequestError(const std::shared_ptr<HalRequest>&); void notifyShutter(uint32_t frameNumber, nsecs_t shutterTs); void notifyError(uint32_t frameNumber, int32_t streamId, ErrorCode ec); void invokeProcessCaptureResultCallback( Loading @@ -220,7 +220,7 @@ protected: Status allocateIntermediateBuffers( const Size& v4lSize, const Size& thumbSize, const hidl_vec<Stream>& streams); Status submitRequest(const HalRequest&); Status submitRequest(const std::shared_ptr<HalRequest>&); void flush(); void dump(int fd); virtual bool threadLoop() override; Loading @@ -238,7 +238,7 @@ protected: static const int kReqWaitTimeoutMs = 33; // 33ms static const int kReqWaitTimesMax = 90; // 33ms * 90 ~= 3 sec void waitForNextRequest(HalRequest* out); void waitForNextRequest(std::shared_ptr<HalRequest>* out); void signalRequestDone(); int cropAndScaleLocked( Loading @@ -258,15 +258,16 @@ protected: void *out, size_t maxOutSize, size_t &actualCodeSize); int createJpegLocked(HalStreamBuffer &halBuf, HalRequest &req); int createJpegLocked(HalStreamBuffer &halBuf, const std::shared_ptr<HalRequest>& req); const wp<ExternalCameraDeviceSession> mParent; const CroppingType mCroppingType; mutable std::mutex mRequestListLock; // Protect acccess to mRequestList mutable std::mutex mRequestListLock; // Protect acccess to mRequestList, // mProcessingRequest and mProcessingFrameNumer std::condition_variable mRequestCond; // signaled when a new request is submitted std::condition_variable mRequestDoneCond; // signaled when a request is done processing std::list<HalRequest> mRequestList; std::list<std::shared_ptr<HalRequest>> mRequestList; bool mProcessingRequest = false; uint32_t mProcessingFrameNumer = 0; Loading Loading
camera/device/3.4/default/ExternalCameraDeviceSession.cpp +63 −62 Original line number Diff line number Diff line Loading @@ -526,15 +526,14 @@ Status ExternalCameraDeviceSession::processOneCaptureRequest(const CaptureReques return Status::INTERNAL_ERROR; } // TODO: reduce object copy in this path HalRequest halReq = { .frameNumber = request.frameNumber, .setting = mLatestReqSetting, .frameIn = frameIn, .shutterTs = shutterTs}; halReq.buffers.resize(numOutputBufs); std::shared_ptr<HalRequest> halReq = std::make_shared<HalRequest>(); halReq->frameNumber = request.frameNumber; halReq->setting = mLatestReqSetting; halReq->frameIn = frameIn; halReq->shutterTs = shutterTs; halReq->buffers.resize(numOutputBufs); for (size_t i = 0; i < numOutputBufs; i++) { HalStreamBuffer& halBuf = halReq.buffers[i]; HalStreamBuffer& halBuf = halReq->buffers[i]; int streamId = halBuf.streamId = request.outputBuffers[i].streamId; halBuf.bufferId = request.outputBuffers[i].bufferId; const Stream& stream = mStreamMap[streamId]; Loading @@ -546,7 +545,7 @@ Status ExternalCameraDeviceSession::processOneCaptureRequest(const CaptureReques halBuf.acquireFence = allFences[i]; halBuf.fenceTimeout = false; } mInflightFrames.insert(halReq.frameNumber); mInflightFrames.insert(halReq->frameNumber); // Send request to OutputThread for the rest of processing mOutputThread->submitRequest(halReq); mFirstRequest = false; Loading @@ -572,30 +571,31 @@ void ExternalCameraDeviceSession::notifyError( } //TODO: refactor with processCaptureResult Status ExternalCameraDeviceSession::processCaptureRequestError(const HalRequest& req) { Status ExternalCameraDeviceSession::processCaptureRequestError( const std::shared_ptr<HalRequest>& req) { // Return V4L2 buffer to V4L2 buffer queue enqueueV4l2Frame(req.frameIn); enqueueV4l2Frame(req->frameIn); // NotifyShutter notifyShutter(req.frameNumber, req.shutterTs); notifyShutter(req->frameNumber, req->shutterTs); notifyError(/*frameNum*/req.frameNumber, /*stream*/-1, ErrorCode::ERROR_REQUEST); notifyError(/*frameNum*/req->frameNumber, /*stream*/-1, ErrorCode::ERROR_REQUEST); // Fill output buffers hidl_vec<CaptureResult> results; results.resize(1); CaptureResult& result = results[0]; result.frameNumber = req.frameNumber; result.frameNumber = req->frameNumber; result.partialResult = 1; result.inputBuffer.streamId = -1; result.outputBuffers.resize(req.buffers.size()); for (size_t i = 0; i < req.buffers.size(); i++) { result.outputBuffers[i].streamId = req.buffers[i].streamId; result.outputBuffers[i].bufferId = req.buffers[i].bufferId; result.outputBuffers.resize(req->buffers.size()); for (size_t i = 0; i < req->buffers.size(); i++) { result.outputBuffers[i].streamId = req->buffers[i].streamId; result.outputBuffers[i].bufferId = req->buffers[i].bufferId; result.outputBuffers[i].status = BufferStatus::ERROR; if (req.buffers[i].acquireFence >= 0) { if (req->buffers[i].acquireFence >= 0) { native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); handle->data[0] = req.buffers[i].acquireFence; handle->data[0] = req->buffers[i].acquireFence; result.outputBuffers[i].releaseFence.setTo(handle, /*shouldOwn*/false); } } Loading @@ -603,7 +603,7 @@ Status ExternalCameraDeviceSession::processCaptureRequestError(const HalRequest& // update inflight records { Mutex::Autolock _l(mLock); mInflightFrames.erase(req.frameNumber); mInflightFrames.erase(req->frameNumber); } // Callback into framework Loading @@ -612,51 +612,51 @@ Status ExternalCameraDeviceSession::processCaptureRequestError(const HalRequest& return Status::OK; } Status ExternalCameraDeviceSession::processCaptureResult(HalRequest& req) { Status ExternalCameraDeviceSession::processCaptureResult(std::shared_ptr<HalRequest>& req) { // Return V4L2 buffer to V4L2 buffer queue enqueueV4l2Frame(req.frameIn); enqueueV4l2Frame(req->frameIn); // NotifyShutter notifyShutter(req.frameNumber, req.shutterTs); notifyShutter(req->frameNumber, req->shutterTs); // Fill output buffers hidl_vec<CaptureResult> results; results.resize(1); CaptureResult& result = results[0]; result.frameNumber = req.frameNumber; result.frameNumber = req->frameNumber; result.partialResult = 1; result.inputBuffer.streamId = -1; result.outputBuffers.resize(req.buffers.size()); for (size_t i = 0; i < req.buffers.size(); i++) { result.outputBuffers[i].streamId = req.buffers[i].streamId; result.outputBuffers[i].bufferId = req.buffers[i].bufferId; if (req.buffers[i].fenceTimeout) { result.outputBuffers.resize(req->buffers.size()); for (size_t i = 0; i < req->buffers.size(); i++) { result.outputBuffers[i].streamId = req->buffers[i].streamId; result.outputBuffers[i].bufferId = req->buffers[i].bufferId; if (req->buffers[i].fenceTimeout) { result.outputBuffers[i].status = BufferStatus::ERROR; native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); handle->data[0] = req.buffers[i].acquireFence; handle->data[0] = req->buffers[i].acquireFence; result.outputBuffers[i].releaseFence.setTo(handle, /*shouldOwn*/false); notifyError(req.frameNumber, req.buffers[i].streamId, ErrorCode::ERROR_BUFFER); notifyError(req->frameNumber, req->buffers[i].streamId, ErrorCode::ERROR_BUFFER); } else { result.outputBuffers[i].status = BufferStatus::OK; // TODO: refactor if (req.buffers[i].acquireFence > 0) { if (req->buffers[i].acquireFence > 0) { native_handle_t* handle = native_handle_create(/*numFds*/1, /*numInts*/0); handle->data[0] = req.buffers[i].acquireFence; handle->data[0] = req->buffers[i].acquireFence; result.outputBuffers[i].releaseFence.setTo(handle, /*shouldOwn*/false); } } } // Fill capture result metadata fillCaptureResult(req.setting, req.shutterTs); const camera_metadata_t *rawResult = req.setting.getAndLock(); fillCaptureResult(req->setting, req->shutterTs); const camera_metadata_t *rawResult = req->setting.getAndLock(); V3_2::implementation::convertToHidl(rawResult, &result.result); req.setting.unlock(rawResult); req->setting.unlock(rawResult); // update inflight records { Mutex::Autolock _l(mLock); mInflightFrames.erase(req.frameNumber); mInflightFrames.erase(req->frameNumber); } // Callback into framework Loading Loading @@ -1387,7 +1387,7 @@ ssize_t ExternalCameraDeviceSession::getJpegBufferSize( int ExternalCameraDeviceSession::OutputThread::createJpegLocked( HalStreamBuffer &halBuf, HalRequest &req) const std::shared_ptr<HalRequest>& req) { int ret; auto lfail = [&](auto... args) { Loading @@ -1414,17 +1414,17 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( int jpegQuality, thumbQuality; Size thumbSize; if (req.setting.exists(ANDROID_JPEG_QUALITY)) { if (req->setting.exists(ANDROID_JPEG_QUALITY)) { camera_metadata_entry entry = req.setting.find(ANDROID_JPEG_QUALITY); req->setting.find(ANDROID_JPEG_QUALITY); jpegQuality = entry.data.u8[0]; } else { return lfail("%s: ANDROID_JPEG_QUALITY not set",__FUNCTION__); } if (req.setting.exists(ANDROID_JPEG_THUMBNAIL_QUALITY)) { if (req->setting.exists(ANDROID_JPEG_THUMBNAIL_QUALITY)) { camera_metadata_entry entry = req.setting.find(ANDROID_JPEG_THUMBNAIL_QUALITY); req->setting.find(ANDROID_JPEG_THUMBNAIL_QUALITY); thumbQuality = entry.data.u8[0]; } else { return lfail( Loading @@ -1432,9 +1432,9 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( __FUNCTION__); } if (req.setting.exists(ANDROID_JPEG_THUMBNAIL_SIZE)) { if (req->setting.exists(ANDROID_JPEG_THUMBNAIL_SIZE)) { camera_metadata_entry entry = req.setting.find(ANDROID_JPEG_THUMBNAIL_SIZE); req->setting.find(ANDROID_JPEG_THUMBNAIL_SIZE); thumbSize = Size { static_cast<uint32_t>(entry.data.i32[0]), static_cast<uint32_t>(entry.data.i32[1]) }; Loading Loading @@ -1494,7 +1494,7 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( /* Combine camera characteristics with request settings to form EXIF * metadata */ common::V1_0::helper::CameraMetadata meta(parent->mCameraCharacteristics); meta.append(req.setting); meta.append(req->setting); /* Generate EXIF object */ std::unique_ptr<ExifUtils> utils(ExifUtils::create()); Loading Loading @@ -1558,7 +1558,7 @@ int ExternalCameraDeviceSession::OutputThread::createJpegLocked( } bool ExternalCameraDeviceSession::OutputThread::threadLoop() { HalRequest req; std::shared_ptr<HalRequest> req; auto parent = mParent.promote(); if (parent == nullptr) { ALOGE("%s: session has been disconnected!", __FUNCTION__); Loading @@ -1569,7 +1569,7 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { // regularly to prevent v4l buffer queue filled with stale buffers // when app doesn't program a preveiw request waitForNextRequest(&req); if (req.frameIn == nullptr) { if (req == nullptr) { // No new request, wait again return true; } Loading @@ -1577,17 +1577,17 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { auto onDeviceError = [&](auto... args) { ALOGE(args...); parent->notifyError( req.frameNumber, /*stream*/-1, ErrorCode::ERROR_DEVICE); req->frameNumber, /*stream*/-1, ErrorCode::ERROR_DEVICE); signalRequestDone(); return false; }; if (req.frameIn->mFourcc != V4L2_PIX_FMT_MJPEG) { if (req->frameIn->mFourcc != V4L2_PIX_FMT_MJPEG) { return onDeviceError("%s: do not support V4L2 format %c%c%c%c", __FUNCTION__, req.frameIn->mFourcc & 0xFF, (req.frameIn->mFourcc >> 8) & 0xFF, (req.frameIn->mFourcc >> 16) & 0xFF, (req.frameIn->mFourcc >> 24) & 0xFF); req->frameIn->mFourcc & 0xFF, (req->frameIn->mFourcc >> 8) & 0xFF, (req->frameIn->mFourcc >> 16) & 0xFF, (req->frameIn->mFourcc >> 24) & 0xFF); } std::unique_lock<std::mutex> lk(mBufferLock); Loading @@ -1595,7 +1595,7 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { // TODO: see if we can save some computation by converting to YV12 here uint8_t* inData; size_t inDataSize; req.frameIn->map(&inData, &inDataSize); req->frameIn->map(&inData, &inDataSize); // TODO: profile // TODO: in some special case maybe we can decode jpg directly to gralloc output? int res = libyuv::MJPGToI420( Loading Loading @@ -1623,7 +1623,7 @@ bool ExternalCameraDeviceSession::OutputThread::threadLoop() { ALOGV("%s processing new request", __FUNCTION__); const int kSyncWaitTimeoutMs = 500; for (auto& halBuf : req.buffers) { for (auto& halBuf : req->buffers) { if (halBuf.acquireFence != -1) { int ret = sync_wait(halBuf.acquireFence, kSyncWaitTimeoutMs); if (ret) { Loading Loading @@ -1780,9 +1780,9 @@ Status ExternalCameraDeviceSession::OutputThread::allocateIntermediateBuffers( return Status::OK; } Status ExternalCameraDeviceSession::OutputThread::submitRequest(const HalRequest& req) { Status ExternalCameraDeviceSession::OutputThread::submitRequest( const std::shared_ptr<HalRequest>& req) { std::unique_lock<std::mutex> lk(mRequestListLock); // TODO: reduce object copy in this path mRequestList.push_back(req); lk.unlock(); mRequestCond.notify_one(); Loading @@ -1797,7 +1797,7 @@ void ExternalCameraDeviceSession::OutputThread::flush() { } std::unique_lock<std::mutex> lk(mRequestListLock); std::list<HalRequest> reqs = mRequestList; std::list<std::shared_ptr<HalRequest>> reqs = std::move(mRequestList); mRequestList.clear(); if (mProcessingRequest) { std::chrono::seconds timeout = std::chrono::seconds(kFlushWaitTimeoutSec); Loading @@ -1813,7 +1813,8 @@ void ExternalCameraDeviceSession::OutputThread::flush() { } } void ExternalCameraDeviceSession::OutputThread::waitForNextRequest(HalRequest* out) { void ExternalCameraDeviceSession::OutputThread::waitForNextRequest( std::shared_ptr<HalRequest>* out) { if (out == nullptr) { ALOGE("%s: out is null", __FUNCTION__); return; Loading @@ -1838,7 +1839,7 @@ void ExternalCameraDeviceSession::OutputThread::waitForNextRequest(HalRequest* o *out = mRequestList.front(); mRequestList.pop_front(); mProcessingRequest = true; mProcessingFrameNumer = out->frameNumber; mProcessingFrameNumer = (*out)->frameNumber; } void ExternalCameraDeviceSession::OutputThread::signalRequestDone() { Loading @@ -1858,7 +1859,7 @@ void ExternalCameraDeviceSession::OutputThread::dump(int fd) { } dprintf(fd, "OutputThread request list contains frame: "); for (const auto& req : mRequestList) { dprintf(fd, "%d, ", req.frameNumber); dprintf(fd, "%d, ", req->frameNumber); } dprintf(fd, "\n"); } Loading
camera/device/3.4/default/include/ext_device_v3_4_impl/ExternalCameraDeviceSession.h +8 −7 Original line number Diff line number Diff line Loading @@ -199,8 +199,8 @@ protected: Status processOneCaptureRequest(const CaptureRequest& request); Status processCaptureResult(HalRequest&); Status processCaptureRequestError(const HalRequest&); Status processCaptureResult(std::shared_ptr<HalRequest>&); Status processCaptureRequestError(const std::shared_ptr<HalRequest>&); void notifyShutter(uint32_t frameNumber, nsecs_t shutterTs); void notifyError(uint32_t frameNumber, int32_t streamId, ErrorCode ec); void invokeProcessCaptureResultCallback( Loading @@ -220,7 +220,7 @@ protected: Status allocateIntermediateBuffers( const Size& v4lSize, const Size& thumbSize, const hidl_vec<Stream>& streams); Status submitRequest(const HalRequest&); Status submitRequest(const std::shared_ptr<HalRequest>&); void flush(); void dump(int fd); virtual bool threadLoop() override; Loading @@ -238,7 +238,7 @@ protected: static const int kReqWaitTimeoutMs = 33; // 33ms static const int kReqWaitTimesMax = 90; // 33ms * 90 ~= 3 sec void waitForNextRequest(HalRequest* out); void waitForNextRequest(std::shared_ptr<HalRequest>* out); void signalRequestDone(); int cropAndScaleLocked( Loading @@ -258,15 +258,16 @@ protected: void *out, size_t maxOutSize, size_t &actualCodeSize); int createJpegLocked(HalStreamBuffer &halBuf, HalRequest &req); int createJpegLocked(HalStreamBuffer &halBuf, const std::shared_ptr<HalRequest>& req); const wp<ExternalCameraDeviceSession> mParent; const CroppingType mCroppingType; mutable std::mutex mRequestListLock; // Protect acccess to mRequestList mutable std::mutex mRequestListLock; // Protect acccess to mRequestList, // mProcessingRequest and mProcessingFrameNumer std::condition_variable mRequestCond; // signaled when a new request is submitted std::condition_variable mRequestDoneCond; // signaled when a request is done processing std::list<HalRequest> mRequestList; std::list<std::shared_ptr<HalRequest>> mRequestList; bool mProcessingRequest = false; uint32_t mProcessingFrameNumer = 0; Loading