From 184dfe4ea5e2ba33951bed2b1366007aee0ce3da Mon Sep 17 00:00:00 2001 From: Eino-Ville Talvala Date: Thu, 7 Nov 2013 15:13:16 -0800 Subject: [PATCH] Camera API2: Add support for partial result quirk - Camera3Device: Include requestId in partial 3A results - FrameProcessorBase: Add support for partial result listeners - CameraDeviceClient: Listen and forward partial results to client Bug: 11115603 Change-Id: If1cc6bbc32932742ac142c058688761ebf6a8024 --- .../libcameraservice/api2/CameraDeviceClient.cpp | 3 ++- .../libcameraservice/common/FrameProcessorBase.cpp | 12 +++++++----- .../libcameraservice/common/FrameProcessorBase.h | 7 +++++-- .../camera/libcameraservice/device3/Camera3Device.cpp | 18 +++++++++++++----- .../camera/libcameraservice/device3/Camera3Device.h | 3 ++- 5 files changed, 29 insertions(+), 14 deletions(-) diff --git a/services/camera/libcameraservice/api2/CameraDeviceClient.cpp b/services/camera/libcameraservice/api2/CameraDeviceClient.cpp index 72126c16a3..1cdf8dcc1b 100644 --- a/services/camera/libcameraservice/api2/CameraDeviceClient.cpp +++ b/services/camera/libcameraservice/api2/CameraDeviceClient.cpp @@ -81,7 +81,8 @@ status_t CameraDeviceClient::initialize(camera_module_t *module) mFrameProcessor->registerListener(FRAME_PROCESSOR_LISTENER_MIN_ID, FRAME_PROCESSOR_LISTENER_MAX_ID, - /*listener*/this); + /*listener*/this, + /*quirkSendPartials*/true); return OK; } diff --git a/services/camera/libcameraservice/common/FrameProcessorBase.cpp b/services/camera/libcameraservice/common/FrameProcessorBase.cpp index b2c9b33065..f2064fbc0e 100644 --- a/services/camera/libcameraservice/common/FrameProcessorBase.cpp +++ b/services/camera/libcameraservice/common/FrameProcessorBase.cpp @@ -37,11 +37,11 @@ FrameProcessorBase::~FrameProcessorBase() { } status_t FrameProcessorBase::registerListener(int32_t minId, - int32_t maxId, wp listener) { + int32_t maxId, wp listener, bool quirkSendPartials) { Mutex::Autolock l(mInputMutex); ALOGV("%s: Registering listener for frame id range %d - %d", __FUNCTION__, minId, maxId); - RangeListener rListener = { minId, maxId, listener }; + RangeListener rListener = { minId, maxId, listener, quirkSendPartials }; mRangeListeners.push_back(rListener); return OK; } @@ -145,13 +145,14 @@ status_t FrameProcessorBase::processListeners(const CameraMetadata &frame, ATRACE_CALL(); camera_metadata_ro_entry_t entry; - // Quirks: Don't deliver partial results to listeners + // Quirks: Don't deliver partial results to listeners that don't want them + bool quirkIsPartial = false; entry = frame.find(ANDROID_QUIRKS_PARTIAL_RESULT); if (entry.count != 0 && entry.data.u8[0] == ANDROID_QUIRKS_PARTIAL_RESULT_PARTIAL) { ALOGV("%s: Camera %d: Not forwarding partial result to listeners", __FUNCTION__, device->getId()); - return OK; + quirkIsPartial = true; } entry = frame.find(ANDROID_REQUEST_ID); @@ -169,7 +170,8 @@ status_t FrameProcessorBase::processListeners(const CameraMetadata &frame, List::iterator item = mRangeListeners.begin(); while (item != mRangeListeners.end()) { if (requestId >= item->minId && - requestId < item->maxId) { + requestId < item->maxId && + (!quirkIsPartial || item->quirkSendPartials) ) { sp listener = item->listener.promote(); if (listener == 0) { item = mRangeListeners.erase(item); diff --git a/services/camera/libcameraservice/common/FrameProcessorBase.h b/services/camera/libcameraservice/common/FrameProcessorBase.h index 4d80ebffaf..89b608aae5 100644 --- a/services/camera/libcameraservice/common/FrameProcessorBase.h +++ b/services/camera/libcameraservice/common/FrameProcessorBase.h @@ -44,9 +44,11 @@ class FrameProcessorBase: public Thread { }; // Register a listener for a range of IDs [minId, maxId). Multiple listeners - // can be listening to the same range + // can be listening to the same range. + // QUIRK: sendPartials controls whether partial results will be sent. status_t registerListener(int32_t minId, int32_t maxId, - wp listener); + wp listener, + bool quirkSendPartials = true); status_t removeListener(int32_t minId, int32_t maxId, wp listener); @@ -64,6 +66,7 @@ class FrameProcessorBase: public Thread { int32_t minId; int32_t maxId; wp listener; + bool quirkSendPartials; }; List mRangeListeners; diff --git a/services/camera/libcameraservice/device3/Camera3Device.cpp b/services/camera/libcameraservice/device3/Camera3Device.cpp index cb72e0e86f..3dbc1b0fb8 100644 --- a/services/camera/libcameraservice/device3/Camera3Device.cpp +++ b/services/camera/libcameraservice/device3/Camera3Device.cpp @@ -1405,7 +1405,8 @@ status_t Camera3Device::registerInFlight(int32_t frameNumber, * Check if all 3A fields are ready, and send off a partial 3A-only result * to the output frame queue */ -bool Camera3Device::processPartial3AQuirk(int32_t frameNumber, +bool Camera3Device::processPartial3AQuirk( + int32_t frameNumber, int32_t requestId, const CameraMetadata& partial) { // Check if all 3A states are present @@ -1452,10 +1453,10 @@ bool Camera3Device::processPartial3AQuirk(int32_t frameNumber, if (!gotAllStates) return false; - ALOGVV("%s: Camera %d: Frame %d: AF mode %d, AWB mode %d, " + ALOGVV("%s: Camera %d: Frame %d, Request ID %d: AF mode %d, AWB mode %d, " "AF state %d, AE state %d, AWB state %d, " "AF trigger %d, AE precapture trigger %d", - __FUNCTION__, mId, frameNumber, + __FUNCTION__, mId, frameNumber, requestId, afMode, awbMode, afState, aeState, awbState, afTriggerId, aeTriggerId); @@ -1463,9 +1464,10 @@ bool Camera3Device::processPartial3AQuirk(int32_t frameNumber, // Got all states, so construct a minimal result to send // In addition to the above fields, this means adding in // android.request.frameCount + // android.request.requestId // android.quirks.partialResult - const size_t kMinimal3AResultEntries = 7; + const size_t kMinimal3AResultEntries = 10; Mutex::Autolock l(mOutputLock); @@ -1479,6 +1481,11 @@ bool Camera3Device::processPartial3AQuirk(int32_t frameNumber, return false; } + if (!insert3AResult(min3AResult, ANDROID_REQUEST_ID, + &requestId, frameNumber)) { + return false; + } + static const uint8_t partialResult = ANDROID_QUIRKS_PARTIAL_RESULT_PARTIAL; if (!insert3AResult(min3AResult, ANDROID_QUIRKS_PARTIAL_RESULT, &partialResult, frameNumber)) { @@ -1615,7 +1622,8 @@ void Camera3Device::processCaptureResult(const camera3_capture_result *result) { if (!request.partialResultQuirk.haveSent3A) { request.partialResultQuirk.haveSent3A = processPartial3AQuirk(frameNumber, - request.partialResultQuirk.collectedResult); + request.requestId, + request.partialResultQuirk.collectedResult); } } } diff --git a/services/camera/libcameraservice/device3/Camera3Device.h b/services/camera/libcameraservice/device3/Camera3Device.h index 4a24a88379..468f641bb7 100644 --- a/services/camera/libcameraservice/device3/Camera3Device.h +++ b/services/camera/libcameraservice/device3/Camera3Device.h @@ -491,7 +491,8 @@ class Camera3Device : * and if so, queue up 3A-only result to the client. Returns true if 3A * is sent. */ - bool processPartial3AQuirk(int32_t frameNumber, const CameraMetadata& partial); + bool processPartial3AQuirk(int32_t frameNumber, int32_t requestId, + const CameraMetadata& partial); // Helpers for reading and writing 3A metadata into to/from partial results template -- 2.11.0