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

Commit da9584dc authored by Mathias Agopian's avatar Mathias Agopian
Browse files

fix [3223749] media server crashes when switching mode from video capture to still image capture

there was an issue were in some situation SF would call prepare() on hwc
with a NULL handle and never call prepare again.
in this situation, we onw set the SKIP flag to make sure that hwc
won't process this layer and as soon as we receive our first buffer we
trigger a recompute of the visible regions which will end-up calling
prepare() again.

Change-Id: I6b400b2df79712408b9315a9859290c7fcb1609e
parent fb889810
Loading
Loading
Loading
Loading
+16 −3
Original line number Diff line number Diff line
@@ -246,9 +246,10 @@ void Layer::setGeometry(hwc_layer_t* hwcl)
void Layer::setPerFrameData(hwc_layer_t* hwcl) {
    sp<GraphicBuffer> buffer(mBufferManager.getActiveBuffer());
    if (buffer == NULL) {
        // this situation can happen if we ran out of memory for instance.
        // not much we can do. continue to use whatever texture was bound
        // to this context.
        // this can happen if the client never drew into this layer yet,
        // or if we ran out of memory. In that case, don't let
        // HWC handle it.
        hwcl->flags |= HWC_SKIP_LAYER;
        hwcl->handle = NULL;
        return;
    }
@@ -581,12 +582,20 @@ void Layer::lockPageFlip(bool& recomputeVisibleRegions)
    }

    // we retired a buffer, which becomes the new front buffer

    const bool noActiveBuffer = !mBufferManager.hasActiveBuffer();
    if (mBufferManager.setActiveBufferIndex(buf) < NO_ERROR) {
        LOGE("retireAndLock() buffer index (%d) out of range", int(buf));
        mPostedDirtyRegion.clear();
        return;
    }

    if (noActiveBuffer) {
        // we didn't have an active buffer, we need to recompute
        // our visible region
        recomputeVisibleRegions = true;
    }

    sp<GraphicBuffer> newFrontBuffer(getBuffer(buf));
    if (newFrontBuffer != NULL) {
        // get the dirty region
@@ -888,6 +897,10 @@ sp<GraphicBuffer> Layer::BufferManager::getActiveBuffer() const {
    return result;
}

bool Layer::BufferManager::hasActiveBuffer() const {
    return mActiveBuffer >= 0;
}

sp<GraphicBuffer> Layer::BufferManager::detachBuffer(size_t index)
{
    BufferData* const buffers = mBufferData;
+2 −0
Original line number Diff line number Diff line
@@ -188,6 +188,8 @@ private:
        size_t getActiveBufferIndex() const;
        // return the active buffer
        sp<GraphicBuffer> getActiveBuffer() const;
        // return wether we have an active buffer
        bool hasActiveBuffer() const;
        // return the active texture (or fail-over)
        Texture getActiveTexture() const;
        // frees resources associated with all buffers