Loading services/surfaceflinger/Scheduler/VSyncDispatch.h +10 −2 Original line number Diff line number Diff line Loading @@ -38,6 +38,14 @@ public: virtual ~VSyncDispatch(); /* * A callback that can be registered to be awoken at a given time relative to a vsync event. * \param [in] vsyncTime The timestamp of the vsync the callback is for. * \param [in] targetWakeupTime The timestamp of intended wakeup time of the cb. * */ using Callback = std::function<void(nsecs_t vsyncTime, nsecs_t targetWakeupTime)>; /* * Registers a callback that will be called at designated points on the vsync timeline. * The callback can be scheduled, rescheduled targeting vsync times, or cancelled. Loading @@ -51,7 +59,7 @@ public: * invocation of callbackFn. * */ virtual CallbackToken registerCallback(std::function<void(nsecs_t)> const& callbackFn, virtual CallbackToken registerCallback(Callback const& callbackFn, std::string callbackName) = 0; /* Loading Loading @@ -112,7 +120,7 @@ protected: */ class VSyncCallbackRegistration { public: VSyncCallbackRegistration(VSyncDispatch&, std::function<void(nsecs_t)> const& callbackFn, VSyncCallbackRegistration(VSyncDispatch&, VSyncDispatch::Callback const& callbackFn, std::string const& callbackName); VSyncCallbackRegistration(VSyncCallbackRegistration&&); VSyncCallbackRegistration& operator=(VSyncCallbackRegistration&&); Loading services/surfaceflinger/Scheduler/VSyncDispatchTimerQueue.cpp +9 −8 Original line number Diff line number Diff line Loading @@ -29,7 +29,7 @@ VSyncTracker::~VSyncTracker() = default; TimeKeeper::~TimeKeeper() = default; VSyncDispatchTimerQueueEntry::VSyncDispatchTimerQueueEntry(std::string const& name, std::function<void(nsecs_t)> const& cb, VSyncDispatch::Callback const& cb, nsecs_t minVsyncDistance) : mName(name), mCallback(cb), Loading Loading @@ -97,13 +97,13 @@ nsecs_t VSyncDispatchTimerQueueEntry::executing() { return *mLastDispatchTime; } void VSyncDispatchTimerQueueEntry::callback(nsecs_t t) { void VSyncDispatchTimerQueueEntry::callback(nsecs_t vsyncTimestamp, nsecs_t wakeupTimestamp) { { std::lock_guard<std::mutex> lk(mRunningMutex); mRunning = true; } mCallback(t); mCallback(vsyncTimestamp, wakeupTimestamp); std::lock_guard<std::mutex> lk(mRunningMutex); mRunning = false; Loading Loading @@ -171,7 +171,8 @@ void VSyncDispatchTimerQueue::rearmTimerSkippingUpdateFor( void VSyncDispatchTimerQueue::timerCallback() { struct Invocation { std::shared_ptr<VSyncDispatchTimerQueueEntry> callback; nsecs_t timestamp; nsecs_t vsyncTimestamp; nsecs_t wakeupTimestamp; }; std::vector<Invocation> invocations; { Loading @@ -186,7 +187,7 @@ void VSyncDispatchTimerQueue::timerCallback() { if (*wakeupTime < mIntendedWakeupTime + mTimerSlack) { callback->executing(); invocations.emplace_back( Invocation{callback, *callback->lastExecutedVsyncTarget()}); Invocation{callback, *callback->lastExecutedVsyncTarget(), *wakeupTime}); } } Loading @@ -195,12 +196,12 @@ void VSyncDispatchTimerQueue::timerCallback() { } for (auto const& invocation : invocations) { invocation.callback->callback(invocation.timestamp); invocation.callback->callback(invocation.vsyncTimestamp, invocation.wakeupTimestamp); } } VSyncDispatchTimerQueue::CallbackToken VSyncDispatchTimerQueue::registerCallback( std::function<void(nsecs_t)> const& callbackFn, std::string callbackName) { Callback const& callbackFn, std::string callbackName) { std::lock_guard<decltype(mMutex)> lk(mMutex); return CallbackToken{ mCallbacks Loading Loading @@ -271,7 +272,7 @@ CancelResult VSyncDispatchTimerQueue::cancel(CallbackToken token) { } VSyncCallbackRegistration::VSyncCallbackRegistration(VSyncDispatch& dispatch, std::function<void(nsecs_t)> const& callbackFn, VSyncDispatch::Callback const& callbackFn, std::string const& callbackName) : mDispatch(dispatch), mToken(dispatch.registerCallback(callbackFn, callbackName)), Loading services/surfaceflinger/Scheduler/VSyncDispatchTimerQueue.h +5 −6 Original line number Diff line number Diff line Loading @@ -36,7 +36,7 @@ public: // Valid transition: disarmed -> armed ( when scheduled ) // Valid transition: armed -> running -> disarmed ( when timer is called) // Valid transition: armed -> disarmed ( when cancelled ) VSyncDispatchTimerQueueEntry(std::string const& name, std::function<void(nsecs_t)> const& fn, VSyncDispatchTimerQueueEntry(std::string const& name, VSyncDispatch::Callback const& fn, nsecs_t minVsyncDistance); std::string_view name() const; Loading @@ -62,14 +62,14 @@ public: nsecs_t executing(); // End: functions that are not threadsafe. // Invoke the callback with the timestamp, moving the state from running->disarmed. void callback(nsecs_t timestamp); // Invoke the callback with the two given timestamps, moving the state from running->disarmed. void callback(nsecs_t vsyncTimestamp, nsecs_t wakeupTimestamp); // Block calling thread while the callback is executing. void ensureNotRunning(); private: std::string const mName; std::function<void(nsecs_t)> const mCallback; VSyncDispatch::Callback const mCallback; nsecs_t mWorkDuration; nsecs_t mEarliestVsync; Loading Loading @@ -104,8 +104,7 @@ public: nsecs_t timerSlack, nsecs_t minVsyncDistance); ~VSyncDispatchTimerQueue(); CallbackToken registerCallback(std::function<void(nsecs_t)> const& callbackFn, std::string callbackName) final; CallbackToken registerCallback(Callback const& callbackFn, std::string callbackName) final; void unregisterCallback(CallbackToken token) final; ScheduleResult schedule(CallbackToken token, nsecs_t workDuration, nsecs_t earliestVsync) final; CancelResult cancel(CallbackToken token) final; Loading services/surfaceflinger/Scheduler/VSyncReactor.cpp +4 −5 Original line number Diff line number Diff line Loading @@ -48,7 +48,8 @@ public: nsecs_t period, nsecs_t offset, nsecs_t notBefore) : mCallback(cb), mRegistration(dispatch, std::bind(&CallbackRepeater::callback, this, std::placeholders::_1), std::bind(&CallbackRepeater::callback, this, std::placeholders::_1, std::placeholders::_2), std::string(name)), mPeriod(period), mOffset(offset), Loading Loading @@ -85,15 +86,13 @@ public: } private: void callback(nsecs_t vsynctime) { nsecs_t period = 0; void callback(nsecs_t vsynctime, nsecs_t wakeupTime) { { std::lock_guard<std::mutex> lk(mMutex); period = mPeriod; mLastCallTime = vsynctime; } mCallback->onDispSyncEvent(vsynctime - period); mCallback->onDispSyncEvent(wakeupTime); { std::lock_guard<std::mutex> lk(mMutex); Loading services/surfaceflinger/tests/unittests/VSyncDispatchRealtimeTest.cpp +1 −1 Original line number Diff line number Diff line Loading @@ -101,7 +101,7 @@ public: RepeatingCallbackReceiver(VSyncDispatch& dispatch, nsecs_t wl) : mWorkload(wl), mCallback( dispatch, [&](auto time) { callback_called(time); }, "repeat0") {} dispatch, [&](auto time, auto) { callback_called(time); }, "repeat0") {} void repeatedly_schedule(size_t iterations, std::function<void(nsecs_t)> const& onEachFrame) { mCallbackTimes.reserve(iterations); Loading Loading
services/surfaceflinger/Scheduler/VSyncDispatch.h +10 −2 Original line number Diff line number Diff line Loading @@ -38,6 +38,14 @@ public: virtual ~VSyncDispatch(); /* * A callback that can be registered to be awoken at a given time relative to a vsync event. * \param [in] vsyncTime The timestamp of the vsync the callback is for. * \param [in] targetWakeupTime The timestamp of intended wakeup time of the cb. * */ using Callback = std::function<void(nsecs_t vsyncTime, nsecs_t targetWakeupTime)>; /* * Registers a callback that will be called at designated points on the vsync timeline. * The callback can be scheduled, rescheduled targeting vsync times, or cancelled. Loading @@ -51,7 +59,7 @@ public: * invocation of callbackFn. * */ virtual CallbackToken registerCallback(std::function<void(nsecs_t)> const& callbackFn, virtual CallbackToken registerCallback(Callback const& callbackFn, std::string callbackName) = 0; /* Loading Loading @@ -112,7 +120,7 @@ protected: */ class VSyncCallbackRegistration { public: VSyncCallbackRegistration(VSyncDispatch&, std::function<void(nsecs_t)> const& callbackFn, VSyncCallbackRegistration(VSyncDispatch&, VSyncDispatch::Callback const& callbackFn, std::string const& callbackName); VSyncCallbackRegistration(VSyncCallbackRegistration&&); VSyncCallbackRegistration& operator=(VSyncCallbackRegistration&&); Loading
services/surfaceflinger/Scheduler/VSyncDispatchTimerQueue.cpp +9 −8 Original line number Diff line number Diff line Loading @@ -29,7 +29,7 @@ VSyncTracker::~VSyncTracker() = default; TimeKeeper::~TimeKeeper() = default; VSyncDispatchTimerQueueEntry::VSyncDispatchTimerQueueEntry(std::string const& name, std::function<void(nsecs_t)> const& cb, VSyncDispatch::Callback const& cb, nsecs_t minVsyncDistance) : mName(name), mCallback(cb), Loading Loading @@ -97,13 +97,13 @@ nsecs_t VSyncDispatchTimerQueueEntry::executing() { return *mLastDispatchTime; } void VSyncDispatchTimerQueueEntry::callback(nsecs_t t) { void VSyncDispatchTimerQueueEntry::callback(nsecs_t vsyncTimestamp, nsecs_t wakeupTimestamp) { { std::lock_guard<std::mutex> lk(mRunningMutex); mRunning = true; } mCallback(t); mCallback(vsyncTimestamp, wakeupTimestamp); std::lock_guard<std::mutex> lk(mRunningMutex); mRunning = false; Loading Loading @@ -171,7 +171,8 @@ void VSyncDispatchTimerQueue::rearmTimerSkippingUpdateFor( void VSyncDispatchTimerQueue::timerCallback() { struct Invocation { std::shared_ptr<VSyncDispatchTimerQueueEntry> callback; nsecs_t timestamp; nsecs_t vsyncTimestamp; nsecs_t wakeupTimestamp; }; std::vector<Invocation> invocations; { Loading @@ -186,7 +187,7 @@ void VSyncDispatchTimerQueue::timerCallback() { if (*wakeupTime < mIntendedWakeupTime + mTimerSlack) { callback->executing(); invocations.emplace_back( Invocation{callback, *callback->lastExecutedVsyncTarget()}); Invocation{callback, *callback->lastExecutedVsyncTarget(), *wakeupTime}); } } Loading @@ -195,12 +196,12 @@ void VSyncDispatchTimerQueue::timerCallback() { } for (auto const& invocation : invocations) { invocation.callback->callback(invocation.timestamp); invocation.callback->callback(invocation.vsyncTimestamp, invocation.wakeupTimestamp); } } VSyncDispatchTimerQueue::CallbackToken VSyncDispatchTimerQueue::registerCallback( std::function<void(nsecs_t)> const& callbackFn, std::string callbackName) { Callback const& callbackFn, std::string callbackName) { std::lock_guard<decltype(mMutex)> lk(mMutex); return CallbackToken{ mCallbacks Loading Loading @@ -271,7 +272,7 @@ CancelResult VSyncDispatchTimerQueue::cancel(CallbackToken token) { } VSyncCallbackRegistration::VSyncCallbackRegistration(VSyncDispatch& dispatch, std::function<void(nsecs_t)> const& callbackFn, VSyncDispatch::Callback const& callbackFn, std::string const& callbackName) : mDispatch(dispatch), mToken(dispatch.registerCallback(callbackFn, callbackName)), Loading
services/surfaceflinger/Scheduler/VSyncDispatchTimerQueue.h +5 −6 Original line number Diff line number Diff line Loading @@ -36,7 +36,7 @@ public: // Valid transition: disarmed -> armed ( when scheduled ) // Valid transition: armed -> running -> disarmed ( when timer is called) // Valid transition: armed -> disarmed ( when cancelled ) VSyncDispatchTimerQueueEntry(std::string const& name, std::function<void(nsecs_t)> const& fn, VSyncDispatchTimerQueueEntry(std::string const& name, VSyncDispatch::Callback const& fn, nsecs_t minVsyncDistance); std::string_view name() const; Loading @@ -62,14 +62,14 @@ public: nsecs_t executing(); // End: functions that are not threadsafe. // Invoke the callback with the timestamp, moving the state from running->disarmed. void callback(nsecs_t timestamp); // Invoke the callback with the two given timestamps, moving the state from running->disarmed. void callback(nsecs_t vsyncTimestamp, nsecs_t wakeupTimestamp); // Block calling thread while the callback is executing. void ensureNotRunning(); private: std::string const mName; std::function<void(nsecs_t)> const mCallback; VSyncDispatch::Callback const mCallback; nsecs_t mWorkDuration; nsecs_t mEarliestVsync; Loading Loading @@ -104,8 +104,7 @@ public: nsecs_t timerSlack, nsecs_t minVsyncDistance); ~VSyncDispatchTimerQueue(); CallbackToken registerCallback(std::function<void(nsecs_t)> const& callbackFn, std::string callbackName) final; CallbackToken registerCallback(Callback const& callbackFn, std::string callbackName) final; void unregisterCallback(CallbackToken token) final; ScheduleResult schedule(CallbackToken token, nsecs_t workDuration, nsecs_t earliestVsync) final; CancelResult cancel(CallbackToken token) final; Loading
services/surfaceflinger/Scheduler/VSyncReactor.cpp +4 −5 Original line number Diff line number Diff line Loading @@ -48,7 +48,8 @@ public: nsecs_t period, nsecs_t offset, nsecs_t notBefore) : mCallback(cb), mRegistration(dispatch, std::bind(&CallbackRepeater::callback, this, std::placeholders::_1), std::bind(&CallbackRepeater::callback, this, std::placeholders::_1, std::placeholders::_2), std::string(name)), mPeriod(period), mOffset(offset), Loading Loading @@ -85,15 +86,13 @@ public: } private: void callback(nsecs_t vsynctime) { nsecs_t period = 0; void callback(nsecs_t vsynctime, nsecs_t wakeupTime) { { std::lock_guard<std::mutex> lk(mMutex); period = mPeriod; mLastCallTime = vsynctime; } mCallback->onDispSyncEvent(vsynctime - period); mCallback->onDispSyncEvent(wakeupTime); { std::lock_guard<std::mutex> lk(mMutex); Loading
services/surfaceflinger/tests/unittests/VSyncDispatchRealtimeTest.cpp +1 −1 Original line number Diff line number Diff line Loading @@ -101,7 +101,7 @@ public: RepeatingCallbackReceiver(VSyncDispatch& dispatch, nsecs_t wl) : mWorkload(wl), mCallback( dispatch, [&](auto time) { callback_called(time); }, "repeat0") {} dispatch, [&](auto time, auto) { callback_called(time); }, "repeat0") {} void repeatedly_schedule(size_t iterations, std::function<void(nsecs_t)> const& onEachFrame) { mCallbackTimes.reserve(iterations); Loading