Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 57184d51 authored by Jayant Chowdhary's avatar Jayant Chowdhary
Browse files

Fix map key in PreparerThread pending streams.



mPendingStreams in PrepareThread was a map
[max stream buffers -> Camera3Streaminterface].

This would cause two streams with the same max buffers to be added
to the map only once which is unintended.

Changed mPendingStreams from
std::unordered_map<int, Camera3StreamInterface>  to
std::list<std::tuple<int,Camera3StreamInterface>>

Bug: 259735869

Test: NativeCameraDeviceTest.java#testCameraDevicePrepareSurface

Change-Id: I501b9d2fab4705bf24a2ec8b628803392a36f44b
Signed-off-by: default avatarJayant Chowdhary <jchowdhary@google.com>
parent 09b368b3
Loading
Loading
Loading
Loading
+3 −2
Original line number Diff line number Diff line
@@ -1481,7 +1481,7 @@ binder::Status CameraDeviceClient::flush(

binder::Status CameraDeviceClient::prepare(int streamId) {
    ATRACE_CALL();
    ALOGV("%s", __FUNCTION__);
    ALOGV("%s stream id %d", __FUNCTION__, streamId);

    binder::Status res;
    if (!(res = checkPidStatus(__FUNCTION__)).isOk()) return res;
@@ -1521,7 +1521,7 @@ binder::Status CameraDeviceClient::prepare(int streamId) {

binder::Status CameraDeviceClient::prepare2(int maxCount, int streamId) {
    ATRACE_CALL();
    ALOGV("%s", __FUNCTION__);
    ALOGV("%s stream id %d", __FUNCTION__, streamId);

    binder::Status res;
    if (!(res = checkPidStatus(__FUNCTION__)).isOk()) return res;
@@ -2046,6 +2046,7 @@ void CameraDeviceClient::notifyPrepared(int streamId) {
    // Thread safe. Don't bother locking.
    sp<hardware::camera2::ICameraDeviceCallbacks> remoteCb = getRemoteCallback();
    if (remoteCb != 0) {
        ALOGV("%s: stream id %d", __FUNCTION__, streamId);
        remoteCb->onPrepared(streamId);
    }
}
+13 −11
Original line number Diff line number Diff line
@@ -4893,7 +4893,8 @@ status_t Camera3Device::PreparerThread::prepare(int maxCount, sp<Camera3StreamIn
    }

    // queue up the work
    mPendingStreams.emplace(maxCount, stream);
    mPendingStreams.push_back(
            std::tuple<int, sp<camera3::Camera3StreamInterface>>(maxCount, stream));
    ALOGV("%s: Stream %d queued for preparing", __FUNCTION__, stream->getId());

    return OK;
@@ -4904,8 +4905,8 @@ void Camera3Device::PreparerThread::pause() {

    Mutex::Autolock l(mLock);

    std::unordered_map<int, sp<camera3::Camera3StreamInterface> > pendingStreams;
    pendingStreams.insert(mPendingStreams.begin(), mPendingStreams.end());
    std::list<std::tuple<int, sp<camera3::Camera3StreamInterface>>> pendingStreams;
    pendingStreams.insert(pendingStreams.begin(), mPendingStreams.begin(), mPendingStreams.end());
    sp<camera3::Camera3StreamInterface> currentStream = mCurrentStream;
    int currentMaxCount = mCurrentMaxCount;
    mPendingStreams.clear();
@@ -4926,18 +4927,19 @@ void Camera3Device::PreparerThread::pause() {
    //of the streams in the pending list.
    if (currentStream != nullptr) {
        if (!mCurrentPrepareComplete) {
            pendingStreams.emplace(currentMaxCount, currentStream);
            pendingStreams.push_back(std::tuple(currentMaxCount, currentStream));
        }
    }

    mPendingStreams.insert(pendingStreams.begin(), pendingStreams.end());
    mPendingStreams.insert(mPendingStreams.begin(), pendingStreams.begin(), pendingStreams.end());
    for (const auto& it : mPendingStreams) {
        it.second->cancelPrepare();
        std::get<1>(it)->cancelPrepare();
    }
}

status_t Camera3Device::PreparerThread::resume() {
    ATRACE_CALL();
    ALOGV("%s: PreparerThread", __FUNCTION__);
    status_t res;

    Mutex::Autolock l(mLock);
@@ -4950,10 +4952,10 @@ status_t Camera3Device::PreparerThread::resume() {

    auto it = mPendingStreams.begin();
    for (; it != mPendingStreams.end();) {
        res = it->second->startPrepare(it->first, true /*blockRequest*/);
        res = std::get<1>(*it)->startPrepare(std::get<0>(*it), true /*blockRequest*/);
        if (res == OK) {
            if (listener != NULL) {
                listener->notifyPrepared(it->second->getId());
                listener->notifyPrepared(std::get<1>(*it)->getId());
            }
            it = mPendingStreams.erase(it);
        } else if (res != NOT_ENOUGH_DATA) {
@@ -4987,7 +4989,7 @@ status_t Camera3Device::PreparerThread::clear() {
    Mutex::Autolock l(mLock);

    for (const auto& it : mPendingStreams) {
        it.second->cancelPrepare();
        std::get<1>(it)->cancelPrepare();
    }
    mPendingStreams.clear();
    mCancelNow = true;
@@ -5018,8 +5020,8 @@ bool Camera3Device::PreparerThread::threadLoop() {

            // Get next stream to prepare
            auto it = mPendingStreams.begin();
            mCurrentStream = it->second;
            mCurrentMaxCount = it->first;
            mCurrentMaxCount = std::get<0>(*it);
            mCurrentStream = std::get<1>(*it);
            mCurrentPrepareComplete = false;
            mPendingStreams.erase(it);
            ATRACE_ASYNC_BEGIN("stream prepare", mCurrentStream->getId());
+2 −1
Original line number Diff line number Diff line
@@ -20,6 +20,7 @@
#include <utility>
#include <unordered_map>
#include <set>
#include <tuple>

#include <utils/Condition.h>
#include <utils/Errors.h>
@@ -1221,7 +1222,7 @@ class Camera3Device :
        // Guarded by mLock

        wp<NotificationListener> mListener;
        std::unordered_map<int, sp<camera3::Camera3StreamInterface> > mPendingStreams;
        std::list<std::tuple<int, sp<camera3::Camera3StreamInterface>>> mPendingStreams;
        bool mActive;
        bool mCancelNow;