Loading services/surfaceflinger/Scheduler/EventThread.cpp +8 −0 Original line number Original line Diff line number Diff line Loading @@ -404,6 +404,9 @@ VsyncEventData EventThread::getLatestVsyncEventData( }(); }(); generateFrameTimeline(vsyncEventData, frameInterval.ns(), systemTime(SYSTEM_TIME_MONOTONIC), generateFrameTimeline(vsyncEventData, frameInterval.ns(), systemTime(SYSTEM_TIME_MONOTONIC), presentTime, deadline); presentTime, deadline); if (FlagManager::getInstance().vrr_config()) { mCallback.onExpectedPresentTimePosted(TimePoint::fromNs(presentTime)); } return vsyncEventData; return vsyncEventData; } } Loading Loading @@ -721,6 +724,11 @@ void EventThread::dispatchEvent(const DisplayEventReceiver::Event& event, removeDisplayEventConnectionLocked(consumer); removeDisplayEventConnectionLocked(consumer); } } } } if (event.header.type == DisplayEventReceiver::DISPLAY_EVENT_VSYNC && FlagManager::getInstance().vrr_config()) { mCallback.onExpectedPresentTimePosted( TimePoint::fromNs(event.vsync.vsyncData.preferredExpectedPresentationTime())); } } } void EventThread::dump(std::string& result) const { void EventThread::dump(std::string& result) const { Loading services/surfaceflinger/Scheduler/EventThread.h +1 −0 Original line number Original line Diff line number Diff line Loading @@ -142,6 +142,7 @@ struct IEventThreadCallback { virtual bool throttleVsync(TimePoint, uid_t) = 0; virtual bool throttleVsync(TimePoint, uid_t) = 0; virtual Period getVsyncPeriod(uid_t) = 0; virtual Period getVsyncPeriod(uid_t) = 0; virtual void resync() = 0; virtual void resync() = 0; virtual void onExpectedPresentTimePosted(TimePoint) = 0; }; }; namespace impl { namespace impl { Loading services/surfaceflinger/Scheduler/ISchedulerCallback.h +2 −0 Original line number Original line Diff line number Diff line Loading @@ -30,6 +30,8 @@ struct ISchedulerCallback { virtual void kernelTimerChanged(bool expired) = 0; virtual void kernelTimerChanged(bool expired) = 0; virtual void triggerOnFrameRateOverridesChanged() = 0; virtual void triggerOnFrameRateOverridesChanged() = 0; virtual void onChoreographerAttached() = 0; virtual void onChoreographerAttached() = 0; virtual void onExpectedPresentTimePosted(TimePoint, ftl::NonNull<DisplayModePtr>, Fps renderRate) = 0; protected: protected: ~ISchedulerCallback() = default; ~ISchedulerCallback() = default; Loading services/surfaceflinger/Scheduler/Scheduler.cpp +29 −9 Original line number Original line Diff line number Diff line Loading @@ -71,15 +71,13 @@ namespace android::scheduler { namespace android::scheduler { Scheduler::Scheduler(ICompositor& compositor, ISchedulerCallback& callback, FeatureFlags features, Scheduler::Scheduler(ICompositor& compositor, ISchedulerCallback& callback, FeatureFlags features, surfaceflinger::Factory& factory, Fps activeRefreshRate, TimeStats& timeStats, surfaceflinger::Factory& factory, Fps activeRefreshRate, TimeStats& timeStats) IVsyncTrackerCallback& vsyncTrackerCallback) : android::impl::MessageQueue(compositor), : android::impl::MessageQueue(compositor), mFeatures(features), mFeatures(features), mVsyncConfiguration(factory.createVsyncConfiguration(activeRefreshRate)), mVsyncConfiguration(factory.createVsyncConfiguration(activeRefreshRate)), mVsyncModulator(sp<VsyncModulator>::make(mVsyncConfiguration->getCurrentConfigs())), mVsyncModulator(sp<VsyncModulator>::make(mVsyncConfiguration->getCurrentConfigs())), mRefreshRateStats(std::make_unique<RefreshRateStats>(timeStats, activeRefreshRate)), mRefreshRateStats(std::make_unique<RefreshRateStats>(timeStats, activeRefreshRate)), mSchedulerCallback(callback), mSchedulerCallback(callback) {} mVsyncTrackerCallback(vsyncTrackerCallback) {} Scheduler::~Scheduler() { Scheduler::~Scheduler() { // MessageQueue depends on VsyncSchedule, so first destroy it. // MessageQueue depends on VsyncSchedule, so first destroy it. Loading Loading @@ -134,10 +132,11 @@ void Scheduler::setPacesetterDisplay(std::optional<PhysicalDisplayId> pacesetter } } void Scheduler::registerDisplay(PhysicalDisplayId displayId, RefreshRateSelectorPtr selectorPtr) { void Scheduler::registerDisplay(PhysicalDisplayId displayId, RefreshRateSelectorPtr selectorPtr) { auto schedulePtr = std::make_shared<VsyncSchedule>( auto schedulePtr = selectorPtr->getActiveMode().modePtr, mFeatures, std::make_shared<VsyncSchedule>(selectorPtr->getActiveMode().modePtr, mFeatures, [this](PhysicalDisplayId id, bool enable) { onHardwareVsyncRequest(id, enable); }, [this](PhysicalDisplayId id, bool enable) { mVsyncTrackerCallback); onHardwareVsyncRequest(id, enable); }); registerDisplayInternal(displayId, std::move(selectorPtr), std::move(schedulePtr)); registerDisplayInternal(displayId, std::move(selectorPtr), std::move(schedulePtr)); } } Loading Loading @@ -222,7 +221,12 @@ void Scheduler::onFrameSignal(ICompositor& compositor, VsyncId vsyncId, targets.try_emplace(id, &targeter.target()); targets.try_emplace(id, &targeter.target()); } } if (!compositor.commit(pacesetterPtr->displayId, targets)) return; if (!compositor.commit(pacesetterPtr->displayId, targets)) { if (FlagManager::getInstance().vrr_config()) { compositor.sendNotifyExpectedPresentHint(pacesetterPtr->displayId); } return; } } } // The pacesetter may have changed or been registered anew during commit. // The pacesetter may have changed or been registered anew during commit. Loading Loading @@ -263,6 +267,9 @@ void Scheduler::onFrameSignal(ICompositor& compositor, VsyncId vsyncId, } } const auto resultsPerDisplay = compositor.composite(pacesetterPtr->displayId, targeters); const auto resultsPerDisplay = compositor.composite(pacesetterPtr->displayId, targeters); if (FlagManager::getInstance().vrr_config()) { compositor.sendNotifyExpectedPresentHint(pacesetterPtr->displayId); } compositor.sample(); compositor.sample(); for (const auto& [id, targeter] : targeters) { for (const auto& [id, targeter] : targeters) { Loading Loading @@ -323,6 +330,19 @@ Period Scheduler::getVsyncPeriod(uid_t uid) { // behaviour. // behaviour. return Period::fromNs(currentPeriod.ns() * divisor); return Period::fromNs(currentPeriod.ns() * divisor); } } void Scheduler::onExpectedPresentTimePosted(TimePoint expectedPresentTime) { const auto frameRateMode = [this] { std::scoped_lock lock(mDisplayLock); const auto pacesetterOpt = pacesetterDisplayLocked(); const Display& pacesetter = *pacesetterOpt; return pacesetter.selectorPtr->getActiveMode(); }(); if (frameRateMode.modePtr->getVrrConfig()) { mSchedulerCallback.onExpectedPresentTimePosted(expectedPresentTime, frameRateMode.modePtr, frameRateMode.fps); } } ConnectionHandle Scheduler::createEventThread(Cycle cycle, ConnectionHandle Scheduler::createEventThread(Cycle cycle, frametimeline::TokenManager* tokenManager, frametimeline::TokenManager* tokenManager, Loading services/surfaceflinger/Scheduler/Scheduler.h +2 −3 Original line number Original line Diff line number Diff line Loading @@ -111,7 +111,7 @@ class Scheduler : public IEventThreadCallback, android::impl::MessageQueue { public: public: Scheduler(ICompositor&, ISchedulerCallback&, FeatureFlags, surfaceflinger::Factory&, Scheduler(ICompositor&, ISchedulerCallback&, FeatureFlags, surfaceflinger::Factory&, Fps activeRefreshRate, TimeStats&, IVsyncTrackerCallback&); Fps activeRefreshRate, TimeStats&); virtual ~Scheduler(); virtual ~Scheduler(); void startTimers(); void startTimers(); Loading Loading @@ -458,6 +458,7 @@ private: bool throttleVsync(TimePoint, uid_t) override; bool throttleVsync(TimePoint, uid_t) override; Period getVsyncPeriod(uid_t) override EXCLUDES(mDisplayLock); Period getVsyncPeriod(uid_t) override EXCLUDES(mDisplayLock); void resync() override EXCLUDES(mDisplayLock); void resync() override EXCLUDES(mDisplayLock); void onExpectedPresentTimePosted(TimePoint expectedPresentTime) override EXCLUDES(mDisplayLock); // Stores EventThread associated with a given VSyncSource, and an initial EventThreadConnection. // Stores EventThread associated with a given VSyncSource, and an initial EventThreadConnection. struct Connection { struct Connection { Loading Loading @@ -497,8 +498,6 @@ private: ISchedulerCallback& mSchedulerCallback; ISchedulerCallback& mSchedulerCallback; IVsyncTrackerCallback& mVsyncTrackerCallback; // mDisplayLock may be locked while under mPolicyLock. // mDisplayLock may be locked while under mPolicyLock. mutable std::mutex mPolicyLock; mutable std::mutex mPolicyLock; Loading Loading
services/surfaceflinger/Scheduler/EventThread.cpp +8 −0 Original line number Original line Diff line number Diff line Loading @@ -404,6 +404,9 @@ VsyncEventData EventThread::getLatestVsyncEventData( }(); }(); generateFrameTimeline(vsyncEventData, frameInterval.ns(), systemTime(SYSTEM_TIME_MONOTONIC), generateFrameTimeline(vsyncEventData, frameInterval.ns(), systemTime(SYSTEM_TIME_MONOTONIC), presentTime, deadline); presentTime, deadline); if (FlagManager::getInstance().vrr_config()) { mCallback.onExpectedPresentTimePosted(TimePoint::fromNs(presentTime)); } return vsyncEventData; return vsyncEventData; } } Loading Loading @@ -721,6 +724,11 @@ void EventThread::dispatchEvent(const DisplayEventReceiver::Event& event, removeDisplayEventConnectionLocked(consumer); removeDisplayEventConnectionLocked(consumer); } } } } if (event.header.type == DisplayEventReceiver::DISPLAY_EVENT_VSYNC && FlagManager::getInstance().vrr_config()) { mCallback.onExpectedPresentTimePosted( TimePoint::fromNs(event.vsync.vsyncData.preferredExpectedPresentationTime())); } } } void EventThread::dump(std::string& result) const { void EventThread::dump(std::string& result) const { Loading
services/surfaceflinger/Scheduler/EventThread.h +1 −0 Original line number Original line Diff line number Diff line Loading @@ -142,6 +142,7 @@ struct IEventThreadCallback { virtual bool throttleVsync(TimePoint, uid_t) = 0; virtual bool throttleVsync(TimePoint, uid_t) = 0; virtual Period getVsyncPeriod(uid_t) = 0; virtual Period getVsyncPeriod(uid_t) = 0; virtual void resync() = 0; virtual void resync() = 0; virtual void onExpectedPresentTimePosted(TimePoint) = 0; }; }; namespace impl { namespace impl { Loading
services/surfaceflinger/Scheduler/ISchedulerCallback.h +2 −0 Original line number Original line Diff line number Diff line Loading @@ -30,6 +30,8 @@ struct ISchedulerCallback { virtual void kernelTimerChanged(bool expired) = 0; virtual void kernelTimerChanged(bool expired) = 0; virtual void triggerOnFrameRateOverridesChanged() = 0; virtual void triggerOnFrameRateOverridesChanged() = 0; virtual void onChoreographerAttached() = 0; virtual void onChoreographerAttached() = 0; virtual void onExpectedPresentTimePosted(TimePoint, ftl::NonNull<DisplayModePtr>, Fps renderRate) = 0; protected: protected: ~ISchedulerCallback() = default; ~ISchedulerCallback() = default; Loading
services/surfaceflinger/Scheduler/Scheduler.cpp +29 −9 Original line number Original line Diff line number Diff line Loading @@ -71,15 +71,13 @@ namespace android::scheduler { namespace android::scheduler { Scheduler::Scheduler(ICompositor& compositor, ISchedulerCallback& callback, FeatureFlags features, Scheduler::Scheduler(ICompositor& compositor, ISchedulerCallback& callback, FeatureFlags features, surfaceflinger::Factory& factory, Fps activeRefreshRate, TimeStats& timeStats, surfaceflinger::Factory& factory, Fps activeRefreshRate, TimeStats& timeStats) IVsyncTrackerCallback& vsyncTrackerCallback) : android::impl::MessageQueue(compositor), : android::impl::MessageQueue(compositor), mFeatures(features), mFeatures(features), mVsyncConfiguration(factory.createVsyncConfiguration(activeRefreshRate)), mVsyncConfiguration(factory.createVsyncConfiguration(activeRefreshRate)), mVsyncModulator(sp<VsyncModulator>::make(mVsyncConfiguration->getCurrentConfigs())), mVsyncModulator(sp<VsyncModulator>::make(mVsyncConfiguration->getCurrentConfigs())), mRefreshRateStats(std::make_unique<RefreshRateStats>(timeStats, activeRefreshRate)), mRefreshRateStats(std::make_unique<RefreshRateStats>(timeStats, activeRefreshRate)), mSchedulerCallback(callback), mSchedulerCallback(callback) {} mVsyncTrackerCallback(vsyncTrackerCallback) {} Scheduler::~Scheduler() { Scheduler::~Scheduler() { // MessageQueue depends on VsyncSchedule, so first destroy it. // MessageQueue depends on VsyncSchedule, so first destroy it. Loading Loading @@ -134,10 +132,11 @@ void Scheduler::setPacesetterDisplay(std::optional<PhysicalDisplayId> pacesetter } } void Scheduler::registerDisplay(PhysicalDisplayId displayId, RefreshRateSelectorPtr selectorPtr) { void Scheduler::registerDisplay(PhysicalDisplayId displayId, RefreshRateSelectorPtr selectorPtr) { auto schedulePtr = std::make_shared<VsyncSchedule>( auto schedulePtr = selectorPtr->getActiveMode().modePtr, mFeatures, std::make_shared<VsyncSchedule>(selectorPtr->getActiveMode().modePtr, mFeatures, [this](PhysicalDisplayId id, bool enable) { onHardwareVsyncRequest(id, enable); }, [this](PhysicalDisplayId id, bool enable) { mVsyncTrackerCallback); onHardwareVsyncRequest(id, enable); }); registerDisplayInternal(displayId, std::move(selectorPtr), std::move(schedulePtr)); registerDisplayInternal(displayId, std::move(selectorPtr), std::move(schedulePtr)); } } Loading Loading @@ -222,7 +221,12 @@ void Scheduler::onFrameSignal(ICompositor& compositor, VsyncId vsyncId, targets.try_emplace(id, &targeter.target()); targets.try_emplace(id, &targeter.target()); } } if (!compositor.commit(pacesetterPtr->displayId, targets)) return; if (!compositor.commit(pacesetterPtr->displayId, targets)) { if (FlagManager::getInstance().vrr_config()) { compositor.sendNotifyExpectedPresentHint(pacesetterPtr->displayId); } return; } } } // The pacesetter may have changed or been registered anew during commit. // The pacesetter may have changed or been registered anew during commit. Loading Loading @@ -263,6 +267,9 @@ void Scheduler::onFrameSignal(ICompositor& compositor, VsyncId vsyncId, } } const auto resultsPerDisplay = compositor.composite(pacesetterPtr->displayId, targeters); const auto resultsPerDisplay = compositor.composite(pacesetterPtr->displayId, targeters); if (FlagManager::getInstance().vrr_config()) { compositor.sendNotifyExpectedPresentHint(pacesetterPtr->displayId); } compositor.sample(); compositor.sample(); for (const auto& [id, targeter] : targeters) { for (const auto& [id, targeter] : targeters) { Loading Loading @@ -323,6 +330,19 @@ Period Scheduler::getVsyncPeriod(uid_t uid) { // behaviour. // behaviour. return Period::fromNs(currentPeriod.ns() * divisor); return Period::fromNs(currentPeriod.ns() * divisor); } } void Scheduler::onExpectedPresentTimePosted(TimePoint expectedPresentTime) { const auto frameRateMode = [this] { std::scoped_lock lock(mDisplayLock); const auto pacesetterOpt = pacesetterDisplayLocked(); const Display& pacesetter = *pacesetterOpt; return pacesetter.selectorPtr->getActiveMode(); }(); if (frameRateMode.modePtr->getVrrConfig()) { mSchedulerCallback.onExpectedPresentTimePosted(expectedPresentTime, frameRateMode.modePtr, frameRateMode.fps); } } ConnectionHandle Scheduler::createEventThread(Cycle cycle, ConnectionHandle Scheduler::createEventThread(Cycle cycle, frametimeline::TokenManager* tokenManager, frametimeline::TokenManager* tokenManager, Loading
services/surfaceflinger/Scheduler/Scheduler.h +2 −3 Original line number Original line Diff line number Diff line Loading @@ -111,7 +111,7 @@ class Scheduler : public IEventThreadCallback, android::impl::MessageQueue { public: public: Scheduler(ICompositor&, ISchedulerCallback&, FeatureFlags, surfaceflinger::Factory&, Scheduler(ICompositor&, ISchedulerCallback&, FeatureFlags, surfaceflinger::Factory&, Fps activeRefreshRate, TimeStats&, IVsyncTrackerCallback&); Fps activeRefreshRate, TimeStats&); virtual ~Scheduler(); virtual ~Scheduler(); void startTimers(); void startTimers(); Loading Loading @@ -458,6 +458,7 @@ private: bool throttleVsync(TimePoint, uid_t) override; bool throttleVsync(TimePoint, uid_t) override; Period getVsyncPeriod(uid_t) override EXCLUDES(mDisplayLock); Period getVsyncPeriod(uid_t) override EXCLUDES(mDisplayLock); void resync() override EXCLUDES(mDisplayLock); void resync() override EXCLUDES(mDisplayLock); void onExpectedPresentTimePosted(TimePoint expectedPresentTime) override EXCLUDES(mDisplayLock); // Stores EventThread associated with a given VSyncSource, and an initial EventThreadConnection. // Stores EventThread associated with a given VSyncSource, and an initial EventThreadConnection. struct Connection { struct Connection { Loading Loading @@ -497,8 +498,6 @@ private: ISchedulerCallback& mSchedulerCallback; ISchedulerCallback& mSchedulerCallback; IVsyncTrackerCallback& mVsyncTrackerCallback; // mDisplayLock may be locked while under mPolicyLock. // mDisplayLock may be locked while under mPolicyLock. mutable std::mutex mPolicyLock; mutable std::mutex mPolicyLock; Loading