diff options
author | 2024-05-23 15:16:54 +0900 | |
---|---|---|
committer | 2024-05-29 15:34:15 +0900 | |
commit | 39f510fb536d26247997141bdfdcc7d8af890514 (patch) | |
tree | b3b8eb1965d6b87795029d033194af975d4fdf6c | |
parent | fe0aa3b5a1750e0bc82103538c6208a6be35a4dd (diff) |
Pass dequeue timestamp along with buffer data
Avoids performance penalties associated with metadata.
Bug: 342174822
Test: atest libsurfaceflinger_unittest
Test: Manually verified dequeueTime sent without triggering
metadata change
Change-Id: Ifed747818ea252b2551780ffcefd3309eb41edbe
-rw-r--r-- | libs/gui/BLASTBufferQueue.cpp | 24 | ||||
-rw-r--r-- | libs/gui/LayerState.cpp | 2 | ||||
-rw-r--r-- | libs/gui/SurfaceComposerClient.cpp | 3 | ||||
-rw-r--r-- | libs/gui/include/gui/LayerState.h | 2 | ||||
-rw-r--r-- | libs/gui/include/gui/SurfaceComposerClient.h | 3 | ||||
-rw-r--r-- | services/surfaceflinger/Layer.cpp | 8 | ||||
-rw-r--r-- | services/surfaceflinger/Layer.h | 2 | ||||
-rw-r--r-- | services/surfaceflinger/SurfaceFlinger.cpp | 13 | ||||
-rw-r--r-- | services/surfaceflinger/Tracing/TransactionProtoParser.cpp | 1 | ||||
-rw-r--r-- | services/surfaceflinger/tests/unittests/TransactionFrameTracerTest.cpp | 2 | ||||
-rw-r--r-- | services/surfaceflinger/tests/unittests/TransactionSurfaceFrameTest.cpp | 24 |
11 files changed, 41 insertions, 43 deletions
diff --git a/libs/gui/BLASTBufferQueue.cpp b/libs/gui/BLASTBufferQueue.cpp index f317a2eea0..739c3c2a41 100644 --- a/libs/gui/BLASTBufferQueue.cpp +++ b/libs/gui/BLASTBufferQueue.cpp @@ -613,8 +613,19 @@ status_t BLASTBufferQueue::acquireNextBufferLocked( std::bind(releaseBufferCallbackThunk, wp<BLASTBufferQueue>(this) /* callbackContext */, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3); sp<Fence> fence = bufferItem.mFence ? new Fence(bufferItem.mFence->dup()) : Fence::NO_FENCE; + + nsecs_t dequeueTime = -1; + { + std::lock_guard _lock{mTimestampMutex}; + auto dequeueTimeIt = mDequeueTimestamps.find(buffer->getId()); + if (dequeueTimeIt != mDequeueTimestamps.end()) { + dequeueTime = dequeueTimeIt->second; + mDequeueTimestamps.erase(dequeueTimeIt); + } + } + t->setBuffer(mSurfaceControl, buffer, fence, bufferItem.mFrameNumber, mProducerId, - releaseBufferCallback); + releaseBufferCallback, dequeueTime); t->setDataspace(mSurfaceControl, static_cast<ui::Dataspace>(bufferItem.mDataSpace)); t->setHdrMetadata(mSurfaceControl, bufferItem.mHdrMetadata); t->setSurfaceDamageRegion(mSurfaceControl, bufferItem.mSurfaceDamage); @@ -658,17 +669,6 @@ status_t BLASTBufferQueue::acquireNextBufferLocked( mPendingFrameTimelines.pop(); } - { - std::lock_guard _lock{mTimestampMutex}; - auto dequeueTime = mDequeueTimestamps.find(buffer->getId()); - if (dequeueTime != mDequeueTimestamps.end()) { - Parcel p; - p.writeInt64(dequeueTime->second); - t->setMetadata(mSurfaceControl, gui::METADATA_DEQUEUE_TIME, p); - mDequeueTimestamps.erase(dequeueTime); - } - } - mergePendingTransactions(t, bufferItem.mFrameNumber); if (applyTransaction) { // All transactions on our apply token are one-way. See comment on mAppliedLastTransaction diff --git a/libs/gui/LayerState.cpp b/libs/gui/LayerState.cpp index c82bde9a83..3745805aa3 100644 --- a/libs/gui/LayerState.cpp +++ b/libs/gui/LayerState.cpp @@ -985,6 +985,7 @@ status_t BufferData::writeToParcel(Parcel* output) const { SAFE_PARCEL(output->writeBool, hasBarrier); SAFE_PARCEL(output->writeUint64, barrierFrameNumber); SAFE_PARCEL(output->writeUint32, producerId); + SAFE_PARCEL(output->writeInt64, dequeueTime); return NO_ERROR; } @@ -1024,6 +1025,7 @@ status_t BufferData::readFromParcel(const Parcel* input) { SAFE_PARCEL(input->readBool, &hasBarrier); SAFE_PARCEL(input->readUint64, &barrierFrameNumber); SAFE_PARCEL(input->readUint32, &producerId); + SAFE_PARCEL(input->readInt64, &dequeueTime); return NO_ERROR; } diff --git a/libs/gui/SurfaceComposerClient.cpp b/libs/gui/SurfaceComposerClient.cpp index b420aabb84..af91bb3ae2 100644 --- a/libs/gui/SurfaceComposerClient.cpp +++ b/libs/gui/SurfaceComposerClient.cpp @@ -1702,7 +1702,7 @@ SurfaceComposerClient::Transaction& SurfaceComposerClient::Transaction::setBuffe SurfaceComposerClient::Transaction& SurfaceComposerClient::Transaction::setBuffer( const sp<SurfaceControl>& sc, const sp<GraphicBuffer>& buffer, const std::optional<sp<Fence>>& fence, const std::optional<uint64_t>& optFrameNumber, - uint32_t producerId, ReleaseBufferCallback callback) { + uint32_t producerId, ReleaseBufferCallback callback, nsecs_t dequeueTime) { layer_state_t* s = getLayerState(sc); if (!s) { mStatus = BAD_INDEX; @@ -1718,6 +1718,7 @@ SurfaceComposerClient::Transaction& SurfaceComposerClient::Transaction::setBuffe bufferData->frameNumber = frameNumber; bufferData->producerId = producerId; bufferData->flags |= BufferData::BufferDataChange::frameNumberChanged; + bufferData->dequeueTime = dequeueTime; if (fence) { bufferData->acquireFence = *fence; bufferData->flags |= BufferData::BufferDataChange::fenceChanged; diff --git a/libs/gui/include/gui/LayerState.h b/libs/gui/include/gui/LayerState.h index 82889efe36..ba06101059 100644 --- a/libs/gui/include/gui/LayerState.h +++ b/libs/gui/include/gui/LayerState.h @@ -128,6 +128,8 @@ public: client_cache_t cachedBuffer; + nsecs_t dequeueTime; + // Generates the release callback id based on the buffer id and frame number. // This is used as an identifier when release callbacks are invoked. ReleaseCallbackId generateReleaseCallbackId() const; diff --git a/libs/gui/include/gui/SurfaceComposerClient.h b/libs/gui/include/gui/SurfaceComposerClient.h index 9712907396..0862e03c44 100644 --- a/libs/gui/include/gui/SurfaceComposerClient.h +++ b/libs/gui/include/gui/SurfaceComposerClient.h @@ -568,7 +568,8 @@ public: Transaction& setBuffer(const sp<SurfaceControl>& sc, const sp<GraphicBuffer>& buffer, const std::optional<sp<Fence>>& fence = std::nullopt, const std::optional<uint64_t>& frameNumber = std::nullopt, - uint32_t producerId = 0, ReleaseBufferCallback callback = nullptr); + uint32_t producerId = 0, ReleaseBufferCallback callback = nullptr, + nsecs_t dequeueTime = -1); Transaction& unsetBuffer(const sp<SurfaceControl>& sc); std::shared_ptr<BufferData> getAndClearBuffer(const sp<SurfaceControl>& sc); diff --git a/services/surfaceflinger/Layer.cpp b/services/surfaceflinger/Layer.cpp index 6b97e2f799..d27bfd29ef 100644 --- a/services/surfaceflinger/Layer.cpp +++ b/services/surfaceflinger/Layer.cpp @@ -3149,8 +3149,7 @@ void Layer::resetDrawingStateBufferInfo() { bool Layer::setBuffer(std::shared_ptr<renderengine::ExternalTexture>& buffer, const BufferData& bufferData, nsecs_t postTime, nsecs_t desiredPresentTime, - bool isAutoTimestamp, std::optional<nsecs_t> dequeueTime, - const FrameTimelineInfo& info) { + bool isAutoTimestamp, const FrameTimelineInfo& info) { ATRACE_FORMAT("setBuffer %s - hasBuffer=%s", getDebugName(), (buffer ? "true" : "false")); const bool frameNumberChanged = @@ -3224,10 +3223,11 @@ bool Layer::setBuffer(std::shared_ptr<renderengine::ExternalTexture>& buffer, setFrameTimelineVsyncForBufferTransaction(info, postTime); - if (dequeueTime && *dequeueTime != 0) { + if (bufferData.dequeueTime > 0) { const uint64_t bufferId = mDrawingState.buffer->getId(); mFlinger->mFrameTracer->traceNewLayer(layerId, getName().c_str()); - mFlinger->mFrameTracer->traceTimestamp(layerId, bufferId, frameNumber, *dequeueTime, + mFlinger->mFrameTracer->traceTimestamp(layerId, bufferId, frameNumber, + bufferData.dequeueTime, FrameTracer::FrameEvent::DEQUEUE); mFlinger->mFrameTracer->traceTimestamp(layerId, bufferId, frameNumber, postTime, FrameTracer::FrameEvent::QUEUE); diff --git a/services/surfaceflinger/Layer.h b/services/surfaceflinger/Layer.h index 9db7664aa2..b9fcd5c333 100644 --- a/services/surfaceflinger/Layer.h +++ b/services/surfaceflinger/Layer.h @@ -312,7 +312,7 @@ public: bool setBuffer(std::shared_ptr<renderengine::ExternalTexture>& /* buffer */, const BufferData& /* bufferData */, nsecs_t /* postTime */, nsecs_t /*desiredPresentTime*/, bool /*isAutoTimestamp*/, - std::optional<nsecs_t> /* dequeueTime */, const FrameTimelineInfo& /*info*/); + const FrameTimelineInfo& /*info*/); void setDesiredPresentTime(nsecs_t /*desiredPresentTime*/, bool /*isAutoTimestamp*/); bool setDataspace(ui::Dataspace /*dataspace*/); bool setExtendedRangeBrightness(float currentBufferRatio, float desiredRatio); diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp index 5f81cd45cc..c0faf16927 100644 --- a/services/surfaceflinger/SurfaceFlinger.cpp +++ b/services/surfaceflinger/SurfaceFlinger.cpp @@ -5618,10 +5618,7 @@ uint32_t SurfaceFlinger::setClientStateLocked(const FrameTimelineInfo& frameTime layer->setInputInfo(*s.windowInfoHandle->getInfo()); flags |= eTraversalNeeded; } - std::optional<nsecs_t> dequeueBufferTimestamp; if (what & layer_state_t::eMetadataChanged) { - dequeueBufferTimestamp = s.metadata.getInt64(gui::METADATA_DEQUEUE_TIME); - if (const int32_t gameMode = s.metadata.getInt32(gui::METADATA_GAME_MODE, -1); gameMode != -1) { // The transaction will be received on the Task layer and needs to be applied to all @@ -5763,8 +5760,7 @@ uint32_t SurfaceFlinger::setClientStateLocked(const FrameTimelineInfo& frameTime if (what & layer_state_t::eBufferChanged) { if (layer->setBuffer(composerState.externalTexture, *s.bufferData, postTime, - desiredPresentTime, isAutoTimestamp, dequeueBufferTimestamp, - frameTimelineInfo)) { + desiredPresentTime, isAutoTimestamp, frameTimelineInfo)) { flags |= eTraversalNeeded; } } else if (frameTimelineInfo.vsyncId != FrameTimelineInfo::INVALID_VSYNC_ID) { @@ -5850,10 +5846,6 @@ uint32_t SurfaceFlinger::updateLayerCallbacksAndStats(const FrameTimelineInfo& f if (what & layer_state_t::eProducerDisconnect) { layer->onDisconnect(); } - std::optional<nsecs_t> dequeueBufferTimestamp; - if (what & layer_state_t::eMetadataChanged) { - dequeueBufferTimestamp = s.metadata.getInt64(gui::METADATA_DEQUEUE_TIME); - } std::vector<sp<CallbackHandle>> callbackHandles; if ((what & layer_state_t::eHasListenerCallbacksChanged) && (!filteredListeners.empty())) { @@ -5900,8 +5892,7 @@ uint32_t SurfaceFlinger::updateLayerCallbacksAndStats(const FrameTimelineInfo& f } layer->setTransformHint(transformHint); if (layer->setBuffer(composerState.externalTexture, *s.bufferData, postTime, - desiredPresentTime, isAutoTimestamp, dequeueBufferTimestamp, - frameTimelineInfo)) { + desiredPresentTime, isAutoTimestamp, frameTimelineInfo)) { flags |= eTraversalNeeded; } mLayersWithQueuedFrames.emplace(layer); diff --git a/services/surfaceflinger/Tracing/TransactionProtoParser.cpp b/services/surfaceflinger/Tracing/TransactionProtoParser.cpp index fc496b2982..0bafb71f3f 100644 --- a/services/surfaceflinger/Tracing/TransactionProtoParser.cpp +++ b/services/surfaceflinger/Tracing/TransactionProtoParser.cpp @@ -436,6 +436,7 @@ void TransactionProtoParser::fromProto(const perfetto::protos::LayerState& proto layer.bufferData->flags = ftl::Flags<BufferData::BufferDataChange>(bufferProto.flags()); layer.bufferData->cachedBuffer.id = bufferProto.cached_buffer_id(); layer.bufferData->acquireFence = Fence::NO_FENCE; + layer.bufferData->dequeueTime = -1; } if (proto.what() & layer_state_t::eApiChanged) { diff --git a/services/surfaceflinger/tests/unittests/TransactionFrameTracerTest.cpp b/services/surfaceflinger/tests/unittests/TransactionFrameTracerTest.cpp index d4d5b32341..85b61f8fb9 100644 --- a/services/surfaceflinger/tests/unittests/TransactionFrameTracerTest.cpp +++ b/services/surfaceflinger/tests/unittests/TransactionFrameTracerTest.cpp @@ -94,7 +94,7 @@ public: HAL_PIXEL_FORMAT_RGBA_8888, 0ULL /*usage*/); layer->setBuffer(externalTexture, bufferData, postTime, /*desiredPresentTime*/ 30, false, - dequeueTime, FrameTimelineInfo{}); + FrameTimelineInfo{}); commitTransaction(layer.get()); nsecs_t latchTime = 25; diff --git a/services/surfaceflinger/tests/unittests/TransactionSurfaceFrameTest.cpp b/services/surfaceflinger/tests/unittests/TransactionSurfaceFrameTest.cpp index 5046a86304..46733b9a83 100644 --- a/services/surfaceflinger/tests/unittests/TransactionSurfaceFrameTest.cpp +++ b/services/surfaceflinger/tests/unittests/TransactionSurfaceFrameTest.cpp @@ -99,7 +99,7 @@ public: FrameTimelineInfo ftInfo; ftInfo.vsyncId = 1; ftInfo.inputEventId = 0; - layer->setBuffer(externalTexture, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture, bufferData, 10, 20, false, ftInfo); acquireFence->signalForTest(12); commitTransaction(layer.get()); @@ -134,7 +134,7 @@ public: FrameTimelineInfo ftInfo; ftInfo.vsyncId = 1; ftInfo.inputEventId = 0; - layer->setBuffer(externalTexture1, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture1, bufferData, 10, 20, false, ftInfo); EXPECT_EQ(0u, layer->mDrawingState.bufferlessSurfaceFramesTX.size()); ASSERT_NE(nullptr, layer->mDrawingState.bufferSurfaceFrameTX); const auto droppedSurfaceFrame = layer->mDrawingState.bufferSurfaceFrameTX; @@ -151,7 +151,7 @@ public: 2ULL /* bufferId */, HAL_PIXEL_FORMAT_RGBA_8888, 0ULL /*usage*/); - layer->setBuffer(externalTexture2, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture2, bufferData, 10, 20, false, ftInfo); nsecs_t end = systemTime(); acquireFence2->signalForTest(12); @@ -197,7 +197,7 @@ public: 1ULL /* bufferId */, HAL_PIXEL_FORMAT_RGBA_8888, 0ULL /*usage*/); - layer->setBuffer(externalTexture, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture, bufferData, 10, 20, false, ftInfo); acquireFence->signalForTest(12); EXPECT_EQ(0u, layer->mDrawingState.bufferlessSurfaceFramesTX.size()); @@ -232,7 +232,7 @@ public: FrameTimelineInfo ftInfo; ftInfo.vsyncId = 1; ftInfo.inputEventId = 0; - layer->setBuffer(externalTexture, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture, bufferData, 10, 20, false, ftInfo); EXPECT_EQ(0u, layer->mDrawingState.bufferlessSurfaceFramesTX.size()); ASSERT_NE(nullptr, layer->mDrawingState.bufferSurfaceFrameTX); @@ -275,7 +275,7 @@ public: FrameTimelineInfo ftInfo3; ftInfo3.vsyncId = 3; ftInfo3.inputEventId = 0; - layer->setBuffer(externalTexture, bufferData, 10, 20, false, std::nullopt, ftInfo3); + layer->setBuffer(externalTexture, bufferData, 10, 20, false, ftInfo3); EXPECT_EQ(2u, layer->mDrawingState.bufferlessSurfaceFramesTX.size()); ASSERT_NE(nullptr, layer->mDrawingState.bufferSurfaceFrameTX); const auto bufferSurfaceFrameTX = layer->mDrawingState.bufferSurfaceFrameTX; @@ -320,7 +320,7 @@ public: FrameTimelineInfo ftInfo; ftInfo.vsyncId = 1; ftInfo.inputEventId = 0; - layer->setBuffer(externalTexture1, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture1, bufferData, 10, 20, false, ftInfo); ASSERT_NE(nullptr, layer->mDrawingState.bufferSurfaceFrameTX); const auto droppedSurfaceFrame = layer->mDrawingState.bufferSurfaceFrameTX; @@ -335,7 +335,7 @@ public: 1ULL /* bufferId */, HAL_PIXEL_FORMAT_RGBA_8888, 0ULL /*usage*/); - layer->setBuffer(externalTexture2, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture2, bufferData, 10, 20, false, ftInfo); acquireFence2->signalForTest(12); ASSERT_NE(nullptr, layer->mDrawingState.bufferSurfaceFrameTX); @@ -372,7 +372,7 @@ public: FrameTimelineInfo ftInfo; ftInfo.vsyncId = 1; ftInfo.inputEventId = 0; - layer->setBuffer(externalTexture1, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture1, bufferData, 10, 20, false, ftInfo); EXPECT_EQ(0u, layer->mDrawingState.bufferlessSurfaceFramesTX.size()); ASSERT_NE(nullptr, layer->mDrawingState.bufferSurfaceFrameTX); const auto droppedSurfaceFrame1 = layer->mDrawingState.bufferSurfaceFrameTX; @@ -392,7 +392,7 @@ public: FrameTimelineInfo ftInfoInv; ftInfoInv.vsyncId = FrameTimelineInfo::INVALID_VSYNC_ID; ftInfoInv.inputEventId = 0; - layer->setBuffer(externalTexture2, bufferData, 10, 20, false, std::nullopt, ftInfoInv); + layer->setBuffer(externalTexture2, bufferData, 10, 20, false, ftInfoInv); auto dropEndTime1 = systemTime(); EXPECT_EQ(0u, layer->mDrawingState.bufferlessSurfaceFramesTX.size()); ASSERT_NE(nullptr, layer->mDrawingState.bufferSurfaceFrameTX); @@ -413,7 +413,7 @@ public: FrameTimelineInfo ftInfo2; ftInfo2.vsyncId = 2; ftInfo2.inputEventId = 0; - layer->setBuffer(externalTexture3, bufferData, 10, 20, false, std::nullopt, ftInfo2); + layer->setBuffer(externalTexture3, bufferData, 10, 20, false, ftInfo2); auto dropEndTime2 = systemTime(); acquireFence3->signalForTest(12); @@ -462,7 +462,7 @@ public: FrameTimelineInfo ftInfo; ftInfo.vsyncId = 1; ftInfo.inputEventId = 0; - layer->setBuffer(externalTexture, bufferData, 10, 20, false, std::nullopt, ftInfo); + layer->setBuffer(externalTexture, bufferData, 10, 20, false, ftInfo); FrameTimelineInfo ftInfo2; ftInfo2.vsyncId = 2; ftInfo2.inputEventId = 0; |