From 4efd0d936e2a2bfd9a46432270d7960062265c7b Mon Sep 17 00:00:00 2001 From: Anton Ivanov Date: Fri, 14 Feb 2025 17:08:55 -0800 Subject: Delay initialization of a ConsumerBase instance to construction of a sp/wp. This is needed to ensure correcntess of wp view of `this` which is needed during initialization. Bug: 393217449 Test: presubmit Flag: EXEMPT_refactor Change-Id: I1c4ec5d4487e9bb7f16a2654e38b27d32d2b82f3 --- libs/gui/ConsumerBase.cpp | 32 ++++++++++++++++++-------------- 1 file changed, 18 insertions(+), 14 deletions(-) (limited to 'libs/gui/ConsumerBase.cpp') diff --git a/libs/gui/ConsumerBase.cpp b/libs/gui/ConsumerBase.cpp index 0266a3f2e0..117a362661 100644 --- a/libs/gui/ConsumerBase.cpp +++ b/libs/gui/ConsumerBase.cpp @@ -31,6 +31,7 @@ #include #include #include +#include #include #include #include @@ -68,8 +69,8 @@ ConsumerBase::ConsumerBase(const sp& bufferQueue, bool c #endif mAbandoned(false), mConsumer(bufferQueue), - mPrevFinalReleaseFence(Fence::NO_FENCE) { - initialize(controlledByApp); + mPrevFinalReleaseFence(Fence::NO_FENCE), + mIsControlledByApp(controlledByApp) { } #if COM_ANDROID_GRAPHICS_LIBGUI_FLAGS(WB_CONSUMER_BASE_OWNS_BQ) @@ -79,11 +80,11 @@ ConsumerBase::ConsumerBase(bool controlledByApp, bool consumerIsSurfaceFlinger) mSlots(BufferQueueDefs::NUM_BUFFER_SLOTS), #endif mAbandoned(false), - mPrevFinalReleaseFence(Fence::NO_FENCE) { + mPrevFinalReleaseFence(Fence::NO_FENCE), + mIsControlledByApp(controlledByApp) { sp producer; BufferQueue::createBufferQueue(&producer, &mConsumer, consumerIsSurfaceFlinger); mSurface = sp::make(producer, controlledByApp); - initialize(controlledByApp); } ConsumerBase::ConsumerBase(const sp& producer, @@ -95,24 +96,27 @@ ConsumerBase::ConsumerBase(const sp& producer, mAbandoned(false), mConsumer(consumer), mSurface(sp::make(producer, controlledByApp)), - mPrevFinalReleaseFence(Fence::NO_FENCE) { - initialize(controlledByApp); + mPrevFinalReleaseFence(Fence::NO_FENCE), + mIsControlledByApp(controlledByApp) { } #endif // COM_ANDROID_GRAPHICS_LIBGUI_FLAGS(WB_CONSUMER_BASE_OWNS_BQ) -void ConsumerBase::initialize(bool controlledByApp) { +void ConsumerBase::onFirstRef() { + ConsumerListener::onFirstRef(); + initialize(); +} + +void ConsumerBase::initialize() { // Choose a name using the PID and a process-unique ID. mName = String8::format("unnamed-%d-%d", getpid(), createProcessUniqueId()); - // Note that we can't create an sp<...>(this) in a ctor that will not keep a - // reference once the ctor ends, as that would cause the refcount of 'this' - // dropping to 0 at the end of the ctor. Since all we need is a wp<...> - // that's what we create. - wp listener = static_cast(this); - sp proxy = new BufferQueue::ProxyConsumerListener(listener); + // Here we depend on an sp/wp having been created for `this`. For this + // reason, initialize() cannot be called from a ctor. + wp listener = wp::fromExisting(this); + sp proxy = sp::make(listener); - status_t err = mConsumer->consumerConnect(proxy, controlledByApp); + status_t err = mConsumer->consumerConnect(proxy, mIsControlledByApp); if (err != NO_ERROR) { CB_LOGE("ConsumerBase: error connecting to BufferQueue: %s (%d)", strerror(-err), err); -- cgit v1.2.3-59-g8ed1b