Reduce number of Fence syscalls made.
This patch saves 6 or more Fence syscalls per frame.
* Timelines are updated just before adding a new fence
since the newly added fence is unlikely to have signaled.
* Layer::latch uses a FenceTime now, so the signal time is
automatically shared with other owners of the FenceTime.
* DispSync uses FenceTime now, only using cached values of
the signal time that have been populated by a Timeline.
Test: SurfaceFlinger boots and dumps still work.
Change-Id: Ie0cfc1af2aca143dd8d5f08f08dbe1e597376f2f
diff --git a/services/surfaceflinger/Layer.cpp b/services/surfaceflinger/Layer.cpp
index 1b9a230..3e9b10d 100755
--- a/services/surfaceflinger/Layer.cpp
+++ b/services/surfaceflinger/Layer.cpp
@@ -1308,7 +1308,8 @@
// able to be latched. To avoid this, grab this buffer anyway.
return true;
}
- return mQueueItems[0].mFence->getSignalTime() != INT64_MAX;
+ return mQueueItems[0].mFenceTime->getSignalTime() !=
+ Fence::SIGNAL_TIME_PENDING;
#else
return true;
#endif
@@ -2011,9 +2012,6 @@
bool Layer::onPostComposition(const std::shared_ptr<FenceTime>& glDoneFence,
const std::shared_ptr<FenceTime>& presentFence,
const CompositorTiming& compositorTiming) {
- mAcquireTimeline.updateSignalTimes();
- mReleaseTimeline.updateSignalTimes();
-
// mFrameLatencyNeeded is true when a new frame was latched for the
// composition.
if (!mFrameLatencyNeeded)
@@ -2064,6 +2062,7 @@
auto releaseFenceTime = std::make_shared<FenceTime>(
mSurfaceFlingerConsumer->getPrevFinalReleaseFence());
+ mReleaseTimeline.updateSignalTimes();
mReleaseTimeline.push(releaseFenceTime);
Mutex::Autolock lock(mFrameEventHistoryMutex);
@@ -2254,6 +2253,7 @@
#ifndef USE_HWC2
auto releaseFenceTime = std::make_shared<FenceTime>(
mSurfaceFlingerConsumer->getPrevFinalReleaseFence());
+ mReleaseTimeline.updateSignalTimes();
mReleaseTimeline.push(releaseFenceTime);
if (mPreviousFrameNumber != 0) {
mFrameEventHistory.addRelease(mPreviousFrameNumber,
@@ -2509,6 +2509,12 @@
FrameEventHistoryDelta *outDelta) {
Mutex::Autolock lock(mFrameEventHistoryMutex);
if (newTimestamps) {
+ // If there are any unsignaled fences in the aquire timeline at this
+ // point, the previously queued frame hasn't been latched yet. Go ahead
+ // and try to get the signal time here so the syscall is taken out of
+ // the main thread's critical path.
+ mAcquireTimeline.updateSignalTimes();
+ // Push the new fence after updating since it's likely still pending.
mAcquireTimeline.push(newTimestamps->acquireFence);
mFrameEventHistory.addQueue(*newTimestamps);
}