diff options
| author | 2023-10-02 15:11:09 -0700 | |
|---|---|---|
| committer | 2023-11-02 10:06:47 -0700 | |
| commit | d4354a9df28c38136f4bfdf75ea10067e3340d8b (patch) | |
| tree | e3e2da8a751f0a5161bf1218b7f66833588a8c60 | |
| parent | f8c0f1072bf50448ef8f02312f0b411783487fa3 (diff) | |
[SF] Adds callback from the VsyncPredictor
Hooks up the NotifyExpectedPresentIfRequired with
expectedPresentTime
BUG: 296636253
BUG: 284845445
Test: atest HWComposerTest
Change-Id: Idfd30929a0f4931b1a9f943340932c655ddd5903
25 files changed, 298 insertions, 78 deletions
diff --git a/services/surfaceflinger/Scheduler/Scheduler.cpp b/services/surfaceflinger/Scheduler/Scheduler.cpp index 1a8713d4a9..d3db5232c6 100644 --- a/services/surfaceflinger/Scheduler/Scheduler.cpp +++ b/services/surfaceflinger/Scheduler/Scheduler.cpp @@ -67,11 +67,12 @@ namespace android::scheduler { Scheduler::Scheduler(ICompositor& compositor, ISchedulerCallback& callback, FeatureFlags features, - sp<VsyncModulator> modulatorPtr) + sp<VsyncModulator> modulatorPtr, IVsyncTrackerCallback& vsyncTrackerCallback) : impl::MessageQueue(compositor), mFeatures(features), mVsyncModulator(std::move(modulatorPtr)), - mSchedulerCallback(callback) {} + mSchedulerCallback(callback), + mVsyncTrackerCallback(vsyncTrackerCallback) {} Scheduler::~Scheduler() { // MessageQueue depends on VsyncSchedule, so first destroy it. @@ -116,10 +117,10 @@ void Scheduler::setPacesetterDisplay(std::optional<PhysicalDisplayId> pacesetter } void Scheduler::registerDisplay(PhysicalDisplayId displayId, RefreshRateSelectorPtr selectorPtr) { - auto schedulePtr = std::make_shared<VsyncSchedule>(displayId, mFeatures, - [this](PhysicalDisplayId id, bool enable) { - onHardwareVsyncRequest(id, enable); - }); + auto schedulePtr = std::make_shared<VsyncSchedule>( + displayId, mFeatures, + [this](PhysicalDisplayId id, bool enable) { onHardwareVsyncRequest(id, enable); }, + mVsyncTrackerCallback); registerDisplayInternal(displayId, std::move(selectorPtr), std::move(schedulePtr)); } @@ -562,7 +563,19 @@ void Scheduler::setRenderRate(PhysicalDisplayId id, Fps renderFrameRate) { ALOGV("%s %s (%s)", __func__, to_string(mode.fps).c_str(), to_string(mode.modePtr->getVsyncRate()).c_str()); - display.schedulePtr->getTracker().setRenderRate(renderFrameRate); + display.schedulePtr->getTracker().setDisplayModeData( + {.renderRate = renderFrameRate, + .notifyExpectedPresentTimeoutOpt = getNotifyExpectedPresentTimeout(mode)}); +} + +std::optional<Period> Scheduler::getNotifyExpectedPresentTimeout(const FrameRateMode& mode) { + if (mode.modePtr->getVrrConfig() && mode.modePtr->getVrrConfig()->notifyExpectedPresentConfig) { + return Period::fromNs( + mode.modePtr->getVrrConfig() + ->notifyExpectedPresentConfig->notifyExpectedPresentTimeoutNs); + } else { + return std::nullopt; + } } void Scheduler::resync() { diff --git a/services/surfaceflinger/Scheduler/Scheduler.h b/services/surfaceflinger/Scheduler/Scheduler.h index b0520a61ff..a5a5e8d5a8 100644 --- a/services/surfaceflinger/Scheduler/Scheduler.h +++ b/services/surfaceflinger/Scheduler/Scheduler.h @@ -102,7 +102,8 @@ class Scheduler : public IEventThreadCallback, android::impl::MessageQueue { using Impl = android::impl::MessageQueue; public: - Scheduler(ICompositor&, ISchedulerCallback&, FeatureFlags, sp<VsyncModulator>); + Scheduler(ICompositor&, ISchedulerCallback&, FeatureFlags, sp<VsyncModulator>, + IVsyncTrackerCallback&); virtual ~Scheduler(); void startTimers(); @@ -429,6 +430,9 @@ private: Period getVsyncPeriod(uid_t) override EXCLUDES(mDisplayLock); void resync() override EXCLUDES(mDisplayLock); + std::optional<Period> getNotifyExpectedPresentTimeout(const FrameRateMode&) + REQUIRES(mDisplayLock); + // Stores EventThread associated with a given VSyncSource, and an initial EventThreadConnection. struct Connection { sp<EventThreadConnection> connection; @@ -462,6 +466,8 @@ private: ISchedulerCallback& mSchedulerCallback; + IVsyncTrackerCallback& mVsyncTrackerCallback; + // mDisplayLock may be locked while under mPolicyLock. mutable std::mutex mPolicyLock; diff --git a/services/surfaceflinger/Scheduler/VSyncPredictor.cpp b/services/surfaceflinger/Scheduler/VSyncPredictor.cpp index e969fdc679..799466bba2 100644 --- a/services/surfaceflinger/Scheduler/VSyncPredictor.cpp +++ b/services/surfaceflinger/Scheduler/VSyncPredictor.cpp @@ -35,6 +35,7 @@ #include <gui/TraceUtils.h> #include <utils/Log.h> +#include "FlagManager.h" #include "RefreshRateSelector.h" #include "VSyncPredictor.h" @@ -47,12 +48,14 @@ static auto constexpr kMaxPercent = 100u; VSyncPredictor::~VSyncPredictor() = default; VSyncPredictor::VSyncPredictor(PhysicalDisplayId id, nsecs_t idealPeriod, size_t historySize, - size_t minimumSamplesForPrediction, uint32_t outlierTolerancePercent) + size_t minimumSamplesForPrediction, uint32_t outlierTolerancePercent, + IVsyncTrackerCallback& callback) : mId(id), mTraceOn(property_get_bool("debug.sf.vsp_trace", false)), kHistorySize(historySize), kMinimumSamplesForPrediction(minimumSamplesForPrediction), kOutlierTolerancePercent(std::min(outlierTolerancePercent, kMaxPercent)), + mVsyncTrackerCallback(callback), mIdealPeriod(idealPeriod) { resetModel(); } @@ -275,11 +278,11 @@ nsecs_t VSyncPredictor::nextAnticipatedVSyncTimeFrom(nsecs_t timePoint) const { mLastVsyncSequence = getVsyncSequenceLocked(timePoint); const auto renderRatePhase = [&]() REQUIRES(mMutex) -> int { - if (!mRenderRate) return 0; + if (!mDisplayModeDataOpt) return 0; const auto divisor = RefreshRateSelector::getFrameRateDivisor(Fps::fromPeriodNsecs(mIdealPeriod), - *mRenderRate); + mDisplayModeDataOpt->renderRate); if (divisor <= 1) return 0; const int mod = mLastVsyncSequence->seq % divisor; @@ -289,12 +292,24 @@ nsecs_t VSyncPredictor::nextAnticipatedVSyncTimeFrom(nsecs_t timePoint) const { }(); if (renderRatePhase == 0) { - return mLastVsyncSequence->vsyncTime; + const auto vsyncTime = mLastVsyncSequence->vsyncTime; + if (FlagManager::getInstance().vrr_config() && mDisplayModeDataOpt) { + mVsyncTrackerCallback.onVsyncGenerated(mId, TimePoint::fromNs(vsyncTime), + *mDisplayModeDataOpt, + Period::fromNs(mIdealPeriod)); + } + return vsyncTime; } auto const [slope, intercept] = getVSyncPredictionModelLocked(); const auto approximateNextVsync = mLastVsyncSequence->vsyncTime + slope * renderRatePhase; - return nextAnticipatedVSyncTimeFromLocked(approximateNextVsync - slope / 2); + const auto nextAnticipatedVsyncTime = + nextAnticipatedVSyncTimeFromLocked(approximateNextVsync - slope / 2); + if (FlagManager::getInstance().vrr_config() && mDisplayModeDataOpt) { + mVsyncTrackerCallback.onVsyncGenerated(mId, TimePoint::fromNs(nextAnticipatedVsyncTime), + *mDisplayModeDataOpt, Period::fromNs(mIdealPeriod)); + } + return nextAnticipatedVsyncTime; } /* @@ -332,10 +347,14 @@ bool VSyncPredictor::isVSyncInPhaseLocked(nsecs_t timePoint, unsigned divisor) c return vsyncSequence.seq % divisor == 0; } -void VSyncPredictor::setRenderRate(Fps fps) { - ALOGV("%s %s: %s", __func__, to_string(mId).c_str(), to_string(fps).c_str()); +void VSyncPredictor::setDisplayModeData(const DisplayModeData& displayModeData) { + ALOGV("%s %s: RenderRate %s notifyExpectedPresentTimeout %s", __func__, to_string(mId).c_str(), + to_string(displayModeData.renderRate).c_str(), + displayModeData.notifyExpectedPresentTimeoutOpt + ? std::to_string(displayModeData.notifyExpectedPresentTimeoutOpt->ns()).c_str() + : "N/A"); std::lock_guard lock(mMutex); - mRenderRate = fps; + mDisplayModeDataOpt = displayModeData; } VSyncPredictor::Model VSyncPredictor::getVSyncPredictionModel() const { @@ -358,6 +377,7 @@ void VSyncPredictor::setPeriod(nsecs_t period) { mRateMap.erase(mRateMap.begin()); } + // TODO(b/308610306) mIdealPeriod to be updated with setDisplayModeData mIdealPeriod = period; if (mRateMap.find(period) == mRateMap.end()) { mRateMap[mIdealPeriod] = {period, 0}; diff --git a/services/surfaceflinger/Scheduler/VSyncPredictor.h b/services/surfaceflinger/Scheduler/VSyncPredictor.h index c01c44dc6b..c271eb738e 100644 --- a/services/surfaceflinger/Scheduler/VSyncPredictor.h +++ b/services/surfaceflinger/Scheduler/VSyncPredictor.h @@ -36,9 +36,11 @@ public: * \param [in] minimumSamplesForPrediction The minimum number of samples to collect before * predicting. \param [in] outlierTolerancePercent a number 0 to 100 that will be used to filter * samples that fall outlierTolerancePercent from an anticipated vsync event. + * \param [in] IVsyncTrackerCallback The callback for the VSyncTracker. */ VSyncPredictor(PhysicalDisplayId, nsecs_t idealPeriod, size_t historySize, - size_t minimumSamplesForPrediction, uint32_t outlierTolerancePercent); + size_t minimumSamplesForPrediction, uint32_t outlierTolerancePercent, + IVsyncTrackerCallback&); ~VSyncPredictor(); bool addVsyncTimestamp(nsecs_t timestamp) final EXCLUDES(mMutex); @@ -69,7 +71,7 @@ public: bool isVSyncInPhase(nsecs_t timePoint, Fps frameRate) const final EXCLUDES(mMutex); - void setRenderRate(Fps) final EXCLUDES(mMutex); + void setDisplayModeData(const DisplayModeData&) final EXCLUDES(mMutex); void dump(std::string& result) const final EXCLUDES(mMutex); @@ -99,6 +101,7 @@ private: size_t const kHistorySize; size_t const kMinimumSamplesForPrediction; size_t const kOutlierTolerancePercent; + IVsyncTrackerCallback& mVsyncTrackerCallback; std::mutex mutable mMutex; nsecs_t mIdealPeriod GUARDED_BY(mMutex); @@ -110,7 +113,7 @@ private: size_t mLastTimestampIndex GUARDED_BY(mMutex) = 0; std::vector<nsecs_t> mTimestamps GUARDED_BY(mMutex); - std::optional<Fps> mRenderRate GUARDED_BY(mMutex); + std::optional<DisplayModeData> mDisplayModeDataOpt GUARDED_BY(mMutex); mutable std::optional<VsyncSequence> mLastVsyncSequence GUARDED_BY(mMutex); }; diff --git a/services/surfaceflinger/Scheduler/VSyncTracker.h b/services/surfaceflinger/Scheduler/VSyncTracker.h index bc0e3bcbb2..7eedc312e2 100644 --- a/services/surfaceflinger/Scheduler/VSyncTracker.h +++ b/services/surfaceflinger/Scheduler/VSyncTracker.h @@ -16,6 +16,7 @@ #pragma once +#include <ui/DisplayId.h> #include <utils/Timers.h> #include <scheduler/Fps.h> @@ -23,6 +24,23 @@ #include "VSyncDispatch.h" namespace android::scheduler { + +struct DisplayModeData { + Fps renderRate; + std::optional<Period> notifyExpectedPresentTimeoutOpt; + + bool operator==(const DisplayModeData& other) const { + return isApproxEqual(renderRate, other.renderRate) && + notifyExpectedPresentTimeoutOpt == other.notifyExpectedPresentTimeoutOpt; + } +}; + +struct IVsyncTrackerCallback { + virtual ~IVsyncTrackerCallback() = default; + virtual void onVsyncGenerated(PhysicalDisplayId, TimePoint expectedPresentTime, + const DisplayModeData&, Period vsyncPeriod) = 0; +}; + /* * VSyncTracker is an interface for providing estimates on future Vsync signal times based on * historical vsync timing data. @@ -80,16 +98,20 @@ public: virtual bool isVSyncInPhase(nsecs_t timePoint, Fps frameRate) const = 0; /* - * Sets a render rate on the tracker. If the render rate is not a divisor - * of the period, the render rate is ignored until the period changes. + * Sets the metadata about the currently active display mode such as VRR + * timeout period, vsyncPeriod and framework property such as render rate. + * If the render rate is not a divisor of the period, the render rate is + * ignored until the period changes. * The tracker will continue to track the vsync timeline and expect it * to match the current period, however, nextAnticipatedVSyncTimeFrom will * return vsyncs according to the render rate set. Setting a render rate is useful * when a display is running at 120Hz but the render frame rate is 60Hz. + * When IVsyncTrackerCallback::onVsyncGenerated callback is made we will pass along + * the vsyncPeriod, render rate and timeoutNs. * - * \param [in] Fps The render rate the tracker should operate at. + * \param [in] DisplayModeData The DisplayModeData the tracker will use. */ - virtual void setRenderRate(Fps) = 0; + virtual void setDisplayModeData(const DisplayModeData&) = 0; virtual void dump(std::string& result) const = 0; diff --git a/services/surfaceflinger/Scheduler/VsyncSchedule.cpp b/services/surfaceflinger/Scheduler/VsyncSchedule.cpp index ff3f29dbbf..5fb53f9e20 100644 --- a/services/surfaceflinger/Scheduler/VsyncSchedule.cpp +++ b/services/surfaceflinger/Scheduler/VsyncSchedule.cpp @@ -54,10 +54,11 @@ private: }; VsyncSchedule::VsyncSchedule(PhysicalDisplayId id, FeatureFlags features, - RequestHardwareVsync requestHardwareVsync) + RequestHardwareVsync requestHardwareVsync, + IVsyncTrackerCallback& callback) : mId(id), mRequestHardwareVsync(std::move(requestHardwareVsync)), - mTracker(createTracker(id)), + mTracker(createTracker(id, callback)), mDispatch(createDispatch(mTracker)), mController(createController(id, *mTracker, features)), mTracer(features.test(Feature::kTracePredictedVsync) @@ -100,7 +101,8 @@ void VsyncSchedule::dump(std::string& out) const { mDispatch->dump(out); } -VsyncSchedule::TrackerPtr VsyncSchedule::createTracker(PhysicalDisplayId id) { +VsyncSchedule::TrackerPtr VsyncSchedule::createTracker(PhysicalDisplayId id, + IVsyncTrackerCallback& callback) { // TODO(b/144707443): Tune constants. constexpr nsecs_t kInitialPeriod = (60_Hz).getPeriodNsecs(); constexpr size_t kHistorySize = 20; @@ -108,7 +110,8 @@ VsyncSchedule::TrackerPtr VsyncSchedule::createTracker(PhysicalDisplayId id) { constexpr uint32_t kDiscardOutlierPercent = 20; return std::make_unique<VSyncPredictor>(id, kInitialPeriod, kHistorySize, - kMinSamplesForPrediction, kDiscardOutlierPercent); + kMinSamplesForPrediction, kDiscardOutlierPercent, + callback); } VsyncSchedule::DispatchPtr VsyncSchedule::createDispatch(TrackerPtr tracker) { diff --git a/services/surfaceflinger/Scheduler/VsyncSchedule.h b/services/surfaceflinger/Scheduler/VsyncSchedule.h index 47e92e107d..ca61f875c3 100644 --- a/services/surfaceflinger/Scheduler/VsyncSchedule.h +++ b/services/surfaceflinger/Scheduler/VsyncSchedule.h @@ -31,6 +31,7 @@ #include <scheduler/Time.h> #include "ThreadContext.h" +#include "VSyncTracker.h" namespace android { class EventThreadTest; @@ -56,7 +57,7 @@ class VsyncSchedule final : public IVsyncSource { public: using RequestHardwareVsync = std::function<void(PhysicalDisplayId, bool enabled)>; - VsyncSchedule(PhysicalDisplayId, FeatureFlags, RequestHardwareVsync); + VsyncSchedule(PhysicalDisplayId, FeatureFlags, RequestHardwareVsync, IVsyncTrackerCallback&); ~VsyncSchedule(); // IVsyncSource overrides: @@ -124,7 +125,7 @@ private: friend class android::VsyncScheduleTest; friend class android::fuzz::SchedulerFuzzer; - static TrackerPtr createTracker(PhysicalDisplayId); + static TrackerPtr createTracker(PhysicalDisplayId, IVsyncTrackerCallback&); static DispatchPtr createDispatch(TrackerPtr); static ControllerPtr createController(PhysicalDisplayId, VsyncTracker&, FeatureFlags); diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp index 62eb17d2e7..b1d8db5711 100644 --- a/services/surfaceflinger/SurfaceFlinger.cpp +++ b/services/surfaceflinger/SurfaceFlinger.cpp @@ -4036,6 +4036,21 @@ void SurfaceFlinger::onChoreographerAttached() { } } +void SurfaceFlinger::onVsyncGenerated(PhysicalDisplayId displayId, TimePoint expectedPresentTime, + const scheduler::DisplayModeData& displayModeData, + Period vsyncPeriod) { + const auto status = + getHwComposer() + .notifyExpectedPresentIfRequired(displayId, vsyncPeriod, expectedPresentTime, + displayModeData.renderRate, + displayModeData + .notifyExpectedPresentTimeoutOpt); + if (status != NO_ERROR) { + ALOGE("%s failed to notifyExpectedPresentHint for display %" PRId64, __func__, + displayId.value); + } +} + void SurfaceFlinger::initScheduler(const sp<const DisplayDevice>& display) { using namespace scheduler; @@ -4074,8 +4089,12 @@ void SurfaceFlinger::initScheduler(const sp<const DisplayDevice>& display) { mScheduler = std::make_unique<Scheduler>(static_cast<ICompositor&>(*this), static_cast<ISchedulerCallback&>(*this), features, - std::move(modulatorPtr)); + std::move(modulatorPtr), + static_cast<IVsyncTrackerCallback&>(*this)); mScheduler->registerDisplay(display->getPhysicalId(), display->holdRefreshRateSelector()); + if (FlagManager::getInstance().vrr_config()) { + mScheduler->setRenderRate(display->getPhysicalId(), activeMode.fps); + } mScheduler->startTimers(); const auto configs = mVsyncConfiguration->getCurrentConfigs(); diff --git a/services/surfaceflinger/SurfaceFlinger.h b/services/surfaceflinger/SurfaceFlinger.h index 520bd221b3..94eedc84c2 100644 --- a/services/surfaceflinger/SurfaceFlinger.h +++ b/services/surfaceflinger/SurfaceFlinger.h @@ -195,7 +195,8 @@ class SurfaceFlinger : public BnSurfaceComposer, private HWC2::ComposerCallback, private ICompositor, private scheduler::ISchedulerCallback, - private compositionengine::ICEPowerCallback { + private compositionengine::ICEPowerCallback, + private scheduler::IVsyncTrackerCallback { public: struct SkipInitializationTag {}; @@ -656,6 +657,10 @@ private: // ICEPowerCallback overrides: void notifyCpuLoadUp() override; + // IVsyncTrackerCallback overrides + void onVsyncGenerated(PhysicalDisplayId, TimePoint expectedPresentTime, + const scheduler::DisplayModeData&, Period vsyncPeriod) override; + // Toggles the kernel idle timer on or off depending the policy decisions around refresh rates. void toggleKernelIdleTimer() REQUIRES(mStateLock); diff --git a/services/surfaceflinger/fuzzer/surfaceflinger_fuzzers_utils.h b/services/surfaceflinger/fuzzer/surfaceflinger_fuzzers_utils.h index c4077dfbaa..70ce884eda 100644 --- a/services/surfaceflinger/fuzzer/surfaceflinger_fuzzers_utils.h +++ b/services/surfaceflinger/fuzzer/surfaceflinger_fuzzers_utils.h @@ -225,16 +225,19 @@ namespace scheduler { class TestableScheduler : public Scheduler, private ICompositor { public: TestableScheduler(const std::shared_ptr<scheduler::RefreshRateSelector>& selectorPtr, - sp<VsyncModulator> modulatorPtr, ISchedulerCallback& callback) + sp<VsyncModulator> modulatorPtr, ISchedulerCallback& callback, + IVsyncTrackerCallback& vsyncTrackerCallback) : TestableScheduler(std::make_unique<android::mock::VsyncController>(), std::make_shared<android::mock::VSyncTracker>(), selectorPtr, - std::move(modulatorPtr), callback) {} + std::move(modulatorPtr), callback, vsyncTrackerCallback) {} TestableScheduler(std::unique_ptr<VsyncController> controller, VsyncSchedule::TrackerPtr tracker, std::shared_ptr<RefreshRateSelector> selectorPtr, - sp<VsyncModulator> modulatorPtr, ISchedulerCallback& callback) - : Scheduler(*this, callback, Feature::kContentDetection, std::move(modulatorPtr)) { + sp<VsyncModulator> modulatorPtr, ISchedulerCallback& callback, + IVsyncTrackerCallback& vsyncTrackerCallback) + : Scheduler(*this, callback, Feature::kContentDetection, std::move(modulatorPtr), + vsyncTrackerCallback) { const auto displayId = selectorPtr->getActiveMode().modePtr->getPhysicalDisplayId(); registerDisplayInternal(displayId, std::move(selectorPtr), std::shared_ptr<VsyncSchedule>( @@ -400,7 +403,8 @@ public: } // namespace surfaceflinger::test // TODO(b/189053744) : Create a common test/mock library for surfaceflinger -class TestableSurfaceFlinger final : private scheduler::ISchedulerCallback { +class TestableSurfaceFlinger final : private scheduler::ISchedulerCallback, + private scheduler::IVsyncTrackerCallback { public: using HotplugEvent = SurfaceFlinger::HotplugEvent; @@ -656,6 +660,7 @@ public: std::unique_ptr<EventThread> appEventThread, std::unique_ptr<EventThread> sfEventThread, scheduler::ISchedulerCallback* callback = nullptr, + scheduler::IVsyncTrackerCallback* vsyncTrackerCallback = nullptr, bool hasMultipleModes = false) { constexpr DisplayModeId kModeId60{0}; DisplayModes modes = makeModes(mock::createDisplayMode(kModeId60, 60_Hz)); @@ -678,7 +683,8 @@ public: mScheduler = new scheduler::TestableScheduler(std::move(vsyncController), std::move(vsyncTracker), mRefreshRateSelector, - std::move(modulatorPtr), *(callback ?: this)); + std::move(modulatorPtr), *(callback ?: this), + *(vsyncTrackerCallback ?: this)); mFlinger->mAppConnectionHandle = mScheduler->createConnection(std::move(appEventThread)); mFlinger->mSfConnectionHandle = mScheduler->createConnection(std::move(sfEventThread)); @@ -799,6 +805,10 @@ private: void triggerOnFrameRateOverridesChanged() override {} void onChoreographerAttached() override {} + // IVsyncTrackerCallback overrides + void onVsyncGenerated(PhysicalDisplayId, TimePoint, const scheduler::DisplayModeData&, + Period) override {} + surfaceflinger::test::Factory mFactory; sp<SurfaceFlinger> mFlinger = sp<SurfaceFlinger>::make(mFactory, SurfaceFlinger::SkipInitialization); diff --git a/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.cpp b/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.cpp index a8727f966c..8fcfd8131a 100644 --- a/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.cpp +++ b/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.cpp @@ -178,14 +178,23 @@ void SchedulerFuzzer::fuzzVSyncDispatchTimerQueue() { dump<scheduler::VSyncDispatchTimerQueueEntry>(&entry, &mFdp); } +struct VsyncTrackerCallback : public scheduler::IVsyncTrackerCallback { + void onVsyncGenerated(PhysicalDisplayId, TimePoint, const scheduler::DisplayModeData&, + Period) override {} +}; + void SchedulerFuzzer::fuzzVSyncPredictor() { uint16_t now = mFdp.ConsumeIntegral<uint16_t>(); uint16_t historySize = mFdp.ConsumeIntegralInRange<uint16_t>(1, UINT16_MAX); uint16_t minimumSamplesForPrediction = mFdp.ConsumeIntegralInRange<uint16_t>(1, UINT16_MAX); nsecs_t idealPeriod = mFdp.ConsumeIntegralInRange<nsecs_t>(1, UINT32_MAX); - scheduler::VSyncPredictor tracker{kDisplayId, idealPeriod, historySize, + VsyncTrackerCallback callback; + scheduler::VSyncPredictor tracker{kDisplayId, + idealPeriod, + historySize, minimumSamplesForPrediction, - mFdp.ConsumeIntegral<uint32_t>() /*outlierTolerancePercent*/}; + mFdp.ConsumeIntegral<uint32_t>() /*outlierTolerancePercent*/, + callback}; uint16_t period = mFdp.ConsumeIntegral<uint16_t>(); tracker.setPeriod(period); for (uint16_t i = 0; i < minimumSamplesForPrediction; ++i) { diff --git a/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.h b/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.h index 8061a8f2dc..728708f05c 100644 --- a/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.h +++ b/services/surfaceflinger/fuzzer/surfaceflinger_scheduler_fuzzer.h @@ -100,7 +100,7 @@ public: return true; } - void setRenderRate(Fps) override {} + void setDisplayModeData(const scheduler::DisplayModeData&) override {} nsecs_t nextVSyncTime(nsecs_t timePoint) const { if (timePoint % mPeriod == 0) { diff --git a/services/surfaceflinger/tests/unittests/DisplayTransactionTest.cpp b/services/surfaceflinger/tests/unittests/DisplayTransactionTest.cpp index fa31643df1..13796650c8 100644 --- a/services/surfaceflinger/tests/unittests/DisplayTransactionTest.cpp +++ b/services/surfaceflinger/tests/unittests/DisplayTransactionTest.cpp @@ -80,7 +80,8 @@ void DisplayTransactionTest::injectMockScheduler(PhysicalDisplayId displayId) { std::unique_ptr<EventThread>(mEventThread), std::unique_ptr<EventThread>(mSFEventThread), TestableSurfaceFlinger::DefaultDisplayMode{displayId}, - TestableSurfaceFlinger::SchedulerCallbackImpl::kMock); + TestableSurfaceFlinger::SchedulerCallbackImpl::kMock, + TestableSurfaceFlinger::VsyncTrackerCallbackImpl::kMock); } void DisplayTransactionTest::injectMockComposer(int virtualDisplayCount) { diff --git a/services/surfaceflinger/tests/unittests/LayerHistoryIntegrationTest.cpp b/services/surfaceflinger/tests/unittests/LayerHistoryIntegrationTest.cpp index 2f6058f7a6..190c0e8c10 100644 --- a/services/surfaceflinger/tests/unittests/LayerHistoryIntegrationTest.cpp +++ b/services/surfaceflinger/tests/unittests/LayerHistoryIntegrationTest.cpp @@ -165,8 +165,10 @@ protected: DisplayModeId(0)); mock::SchedulerCallback mSchedulerCallback; + mock::VsyncTrackerCallback mVsyncTrackerCallback; - TestableScheduler* mScheduler = new TestableScheduler(mSelector, mSchedulerCallback); + TestableScheduler* mScheduler = + new TestableScheduler(mSelector, mSchedulerCallback, mVsyncTrackerCallback); TestableSurfaceFlinger mFlinger; }; diff --git a/services/surfaceflinger/tests/unittests/LayerHistoryTest.cpp b/services/surfaceflinger/tests/unittests/LayerHistoryTest.cpp index e8831ab51f..5328fa3a1f 100644 --- a/services/surfaceflinger/tests/unittests/LayerHistoryTest.cpp +++ b/services/surfaceflinger/tests/unittests/LayerHistoryTest.cpp @@ -144,7 +144,9 @@ protected: mock::SchedulerCallback mSchedulerCallback; - TestableScheduler* mScheduler = new TestableScheduler(mSelector, mSchedulerCallback); + mock::VsyncTrackerCallback mVsyncTrackerCallback; + TestableScheduler* mScheduler = + new TestableScheduler(mSelector, mSchedulerCallback, mVsyncTrackerCallback); TestableSurfaceFlinger mFlinger; }; diff --git a/services/surfaceflinger/tests/unittests/LayerInfoTest.cpp b/services/surfaceflinger/tests/unittests/LayerInfoTest.cpp index 11072bc4c9..830dcced6c 100644 --- a/services/surfaceflinger/tests/unittests/LayerInfoTest.cpp +++ b/services/surfaceflinger/tests/unittests/LayerInfoTest.cpp @@ -61,7 +61,9 @@ protected: HI_FPS)), DisplayModeId(0)); mock::SchedulerCallback mSchedulerCallback; - TestableScheduler* mScheduler = new TestableScheduler(mSelector, mSchedulerCallback); + mock::VsyncTrackerCallback mVsyncTrackerCallback; + TestableScheduler* mScheduler = + new TestableScheduler(mSelector, mSchedulerCallback, mVsyncTrackerCallback); TestableSurfaceFlinger mFlinger; }; diff --git a/services/surfaceflinger/tests/unittests/SchedulerTest.cpp b/services/surfaceflinger/tests/unittests/SchedulerTest.cpp index 87fae2c312..b5eb777a4d 100644 --- a/services/surfaceflinger/tests/unittests/SchedulerTest.cpp +++ b/services/surfaceflinger/tests/unittests/SchedulerTest.cpp @@ -89,7 +89,9 @@ protected: kDisplay1Mode60->getId()); mock::SchedulerCallback mSchedulerCallback; - TestableScheduler* mScheduler = new TestableScheduler{mSelector, mSchedulerCallback}; + mock::VsyncTrackerCallback mVsyncTrackerCallback; + TestableScheduler* mScheduler = + new TestableScheduler{mSelector, mSchedulerCallback, mVsyncTrackerCallback}; surfaceflinger::frontend::LayerHierarchyBuilder mLayerHierarchyBuilder{{}}; ConnectionHandle mConnectionHandle; diff --git a/services/surfaceflinger/tests/unittests/TestableScheduler.h b/services/surfaceflinger/tests/unittests/TestableScheduler.h index 3d1c900dcf..8b6f0f1b94 100644 --- a/services/surfaceflinger/tests/unittests/TestableScheduler.h +++ b/services/surfaceflinger/tests/unittests/TestableScheduler.h @@ -36,18 +36,21 @@ namespace android::scheduler { class TestableScheduler : public Scheduler, private ICompositor { public: - TestableScheduler(RefreshRateSelectorPtr selectorPtr, ISchedulerCallback& callback) + TestableScheduler(RefreshRateSelectorPtr selectorPtr, ISchedulerCallback& callback, + IVsyncTrackerCallback& vsyncTrackerCallback) : TestableScheduler(std::make_unique<mock::VsyncController>(), std::make_shared<mock::VSyncTracker>(), std::move(selectorPtr), - sp<VsyncModulator>::make(VsyncConfigSet{}), callback) {} + sp<VsyncModulator>::make(VsyncConfigSet{}), callback, + vsyncTrackerCallback) {} TestableScheduler(std::unique_ptr<VsyncController> controller, std::shared_ptr<VSyncTracker> tracker, RefreshRateSelectorPtr selectorPtr, - sp<VsyncModulator> modulatorPtr, ISchedulerCallback& callback) - : Scheduler(*this, callback, + sp<VsyncModulator> modulatorPtr, ISchedulerCallback& schedulerCallback, + IVsyncTrackerCallback& vsyncTrackerCallback) + : Scheduler(*this, schedulerCallback, (FeatureFlags)Feature::kContentDetection | Feature::kSmallDirtyContentDetection, - std::move(modulatorPtr)) { + std::move(modulatorPtr), vsyncTrackerCallback) { const auto displayId = selectorPtr->getActiveMode().modePtr->getPhysicalDisplayId(); registerDisplay(displayId, std::move(selectorPtr), std::move(controller), std::move(tracker)); diff --git a/services/surfaceflinger/tests/unittests/TestableSurfaceFlinger.h b/services/surfaceflinger/tests/unittests/TestableSurfaceFlinger.h index 03af56cc71..d0b2199c58 100644 --- a/services/surfaceflinger/tests/unittests/TestableSurfaceFlinger.h +++ b/services/surfaceflinger/tests/unittests/TestableSurfaceFlinger.h @@ -53,6 +53,7 @@ #include "mock/MockFrameTimeline.h" #include "mock/MockFrameTracer.h" #include "mock/MockSchedulerCallback.h" +#include "mock/MockVsyncTrackerCallback.h" #include "mock/system/window/MockNativeWindow.h" #include "Scheduler/VSyncTracker.h" @@ -204,6 +205,8 @@ public: enum class SchedulerCallbackImpl { kNoOp, kMock }; + enum class VsyncTrackerCallbackImpl { kNoOp, kMock }; + struct DefaultDisplayMode { // The ID of the injected RefreshRateSelector and its default display mode. PhysicalDisplayId displayId; @@ -213,13 +216,14 @@ public: using DisplayModesVariant = std::variant<DefaultDisplayMode, RefreshRateSelectorPtr>; - void setupScheduler(std::unique_ptr<scheduler::VsyncController> vsyncController, - std::shared_ptr<scheduler::VSyncTracker> vsyncTracker, - std::unique_ptr<EventThread> appEventThread, - std::unique_ptr<EventThread> sfEventThread, - DisplayModesVariant modesVariant, - SchedulerCallbackImpl callbackImpl = SchedulerCallbackImpl::kNoOp, - bool useNiceMock = false) { + void setupScheduler( + std::unique_ptr<scheduler::VsyncController> vsyncController, + std::shared_ptr<scheduler::VSyncTracker> vsyncTracker, + std::unique_ptr<EventThread> appEventThread, std::unique_ptr<EventThread> sfEventThread, + DisplayModesVariant modesVariant, + SchedulerCallbackImpl callbackImpl = SchedulerCallbackImpl::kNoOp, + VsyncTrackerCallbackImpl vsyncTrackerCallbackImpl = VsyncTrackerCallbackImpl::kNoOp, + bool useNiceMock = false) { RefreshRateSelectorPtr selectorPtr = ftl::match( modesVariant, [](DefaultDisplayMode arg) { @@ -239,10 +243,16 @@ public: mTokenManager = std::make_unique<frametimeline::impl::TokenManager>(); - using Callback = scheduler::ISchedulerCallback; - Callback& callback = callbackImpl == SchedulerCallbackImpl::kNoOp - ? static_cast<Callback&>(mNoOpSchedulerCallback) - : static_cast<Callback&>(mSchedulerCallback); + using ISchedulerCallback = scheduler::ISchedulerCallback; + ISchedulerCallback& schedulerCallback = callbackImpl == SchedulerCallbackImpl::kNoOp + ? static_cast<ISchedulerCallback&>(mNoOpSchedulerCallback) + : static_cast<ISchedulerCallback&>(mSchedulerCallback); + + using VsyncTrackerCallback = scheduler::IVsyncTrackerCallback; + VsyncTrackerCallback& vsyncTrackerCallback = + vsyncTrackerCallbackImpl == VsyncTrackerCallbackImpl::kNoOp + ? static_cast<VsyncTrackerCallback&>(mNoOpVsyncTrackerCallback) + : static_cast<VsyncTrackerCallback&>(mVsyncTrackerCallback); auto modulatorPtr = sp<scheduler::VsyncModulator>::make( mFlinger->mVsyncConfiguration->getCurrentConfigs()); @@ -253,12 +263,14 @@ public: std::move(vsyncTracker), std::move(selectorPtr), std::move(modulatorPtr), - callback); + schedulerCallback, + vsyncTrackerCallback); } else { mScheduler = new scheduler::TestableScheduler(std::move(vsyncController), std::move(vsyncTracker), std::move(selectorPtr), - std::move(modulatorPtr), callback); + std::move(modulatorPtr), + schedulerCallback, vsyncTrackerCallback); } mScheduler->initVsync(mScheduler->getVsyncSchedule()->getDispatch(), *mTokenManager, 0ms); @@ -297,7 +309,8 @@ public: EXPECT_CALL(*vsyncTracker, nextAnticipatedVSyncTimeFrom(_)).WillRepeatedly(Return(0)); setupScheduler(std::move(vsyncController), std::move(vsyncTracker), std::move(eventThread), std::move(sfEventThread), DefaultDisplayMode{options.displayId}, - SchedulerCallbackImpl::kNoOp, options.useNiceMock); + SchedulerCallbackImpl::kNoOp, VsyncTrackerCallbackImpl::kNoOp, + options.useNiceMock); } void resetScheduler(scheduler::Scheduler* scheduler) { mFlinger->mScheduler.reset(scheduler); } @@ -1071,6 +1084,8 @@ private: sp<SurfaceFlinger> mFlinger; scheduler::mock::SchedulerCallback mSchedulerCallback; scheduler::mock::NoOpSchedulerCallback mNoOpSchedulerCallback; + scheduler::mock::VsyncTrackerCallback mVsyncTrackerCallback; + scheduler::mock::NoOpVsyncTrackerCallback mNoOpVsyncTrackerCallback; std::unique_ptr<frametimeline::impl::TokenManager> mTokenManager; scheduler::TestableScheduler* mScheduler = nullptr; Hwc2::mock::PowerAdvisor mPowerAdvisor; diff --git a/services/surfaceflinger/tests/unittests/VSyncDispatchRealtimeTest.cpp b/services/surfaceflinger/tests/unittests/VSyncDispatchRealtimeTest.cpp index 41866a1c50..4be07a1ddb 100644 --- a/services/surfaceflinger/tests/unittests/VSyncDispatchRealtimeTest.cpp +++ b/services/surfaceflinger/tests/unittests/VSyncDispatchRealtimeTest.cpp @@ -54,7 +54,7 @@ public: void resetModel() final {} bool needsMoreSamples() const final { return false; } bool isVSyncInPhase(nsecs_t, Fps) const final { return false; } - void setRenderRate(Fps) final {} + void setDisplayModeData(const DisplayModeData&) final {} void dump(std::string&) const final {} private: @@ -92,7 +92,7 @@ public: void resetModel() final {} bool needsMoreSamples() const final { return false; } bool isVSyncInPhase(nsecs_t, Fps) const final { return false; } - void setRenderRate(Fps) final {} + void setDisplayModeData(const DisplayModeData&) final {} void dump(std::string&) const final {} private: diff --git a/services/surfaceflinger/tests/unittests/VSyncDispatchTimerQueueTest.cpp b/services/surfaceflinger/tests/unittests/VSyncDispatchTimerQueueTest.cpp index 1dc5498221..fbbb4a25af 100644 --- a/services/surfaceflinger/tests/unittests/VSyncDispatchTimerQueueTest.cpp +++ b/services/surfaceflinger/tests/unittests/VSyncDispatchTimerQueueTest.cpp @@ -59,7 +59,7 @@ public: MOCK_METHOD0(resetModel, void()); MOCK_CONST_METHOD0(needsMoreSamples, bool()); MOCK_CONST_METHOD2(isVSyncInPhase, bool(nsecs_t, Fps)); - MOCK_METHOD(void, setRenderRate, (Fps), (override)); + MOCK_METHOD(void, setDisplayModeData, (const DisplayModeData&), (override)); MOCK_CONST_METHOD1(dump, void(std::string&)); nsecs_t nextVSyncTime(nsecs_t timePoint) const { diff --git a/services/surfaceflinger/tests/unittests/VSyncPredictorTest.cpp b/services/surfaceflinger/tests/unittests/VSyncPredictorTest.cpp index 43d683d0fa..30a2855955 100644 --- a/services/surfaceflinger/tests/unittests/VSyncPredictorTest.cpp +++ b/services/surfaceflinger/tests/unittests/VSyncPredictorTest.cpp @@ -23,7 +23,9 @@ #define LOG_TAG "LibSurfaceFlingerUnittests" #define LOG_NDEBUG 0 +#include "FlagUtils.h" #include "Scheduler/VSyncPredictor.h" +#include "mock/MockVsyncTrackerCallback.h" #include <gmock/gmock.h> #include <gtest/gtest.h> @@ -31,8 +33,11 @@ #include <chrono> #include <utility> +#include <com_android_graphics_surfaceflinger_flags.h> + using namespace testing; using namespace std::literals; +using namespace com::android::graphics::surfaceflinger; namespace android::scheduler { @@ -52,13 +57,18 @@ constexpr PhysicalDisplayId DEFAULT_DISPLAY_ID = PhysicalDisplayId::fromPort(42u struct VSyncPredictorTest : testing::Test { nsecs_t mNow = 0; nsecs_t mPeriod = 1000; + scheduler::mock::VsyncTrackerCallback mVsyncTrackerCallback; static constexpr size_t kHistorySize = 10; static constexpr size_t kMinimumSamplesForPrediction = 6; static constexpr size_t kOutlierTolerancePercent = 25; static constexpr nsecs_t mMaxRoundingError = 100; - VSyncPredictor tracker{DEFAULT_DISPLAY_ID, mPeriod, kHistorySize, kMinimumSamplesForPrediction, - kOutlierTolerancePercent}; + VSyncPredictor tracker{DEFAULT_DISPLAY_ID, + mPeriod, + kHistorySize, + kMinimumSamplesForPrediction, + kOutlierTolerancePercent, + mVsyncTrackerCallback}; }; TEST_F(VSyncPredictorTest, reportsAnticipatedPeriod) { @@ -378,8 +388,12 @@ TEST_F(VSyncPredictorTest, doesNotPredictBeforeTimePointWithHigherIntercept) { // See b/151146131 TEST_F(VSyncPredictorTest, hasEnoughPrecision) { - VSyncPredictor tracker{DEFAULT_DISPLAY_ID, mPeriod, 20, kMinimumSamplesForPrediction, - kOutlierTolerancePercent}; + VSyncPredictor tracker{DEFAULT_DISPLAY_ID, + mPeriod, + 20, + kMinimumSamplesForPrediction, + kOutlierTolerancePercent, + mVsyncTrackerCallback}; std::vector<nsecs_t> const simulatedVsyncs{840873348817, 840890049444, 840906762675, 840923581635, 840940161584, 840956868096, 840973702473, 840990256277, 841007116851, @@ -566,7 +580,7 @@ TEST_F(VSyncPredictorTest, setRenderRateIsRespected) { tracker.addVsyncTimestamp(mNow); } - tracker.setRenderRate(Fps::fromPeriodNsecs(3 * mPeriod)); + tracker.setDisplayModeData({.renderRate = Fps::fromPeriodNsecs(3 * mPeriod)}); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow), Eq(mNow + mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 100), Eq(mNow + mPeriod)); @@ -588,12 +602,12 @@ TEST_F(VSyncPredictorTest, setRenderRateOfDivisorIsInPhase) { const auto refreshRate = Fps::fromPeriodNsecs(mPeriod); - tracker.setRenderRate(refreshRate / 4); + tracker.setDisplayModeData({.renderRate = refreshRate / 4}); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow), Eq(mNow + 3 * mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 3 * mPeriod), Eq(mNow + 7 * mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 7 * mPeriod), Eq(mNow + 11 * mPeriod)); - tracker.setRenderRate(refreshRate / 2); + tracker.setDisplayModeData({.renderRate = refreshRate / 2}); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow), Eq(mNow + 1 * mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 1 * mPeriod), Eq(mNow + 3 * mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 3 * mPeriod), Eq(mNow + 5 * mPeriod)); @@ -601,7 +615,7 @@ TEST_F(VSyncPredictorTest, setRenderRateOfDivisorIsInPhase) { EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 7 * mPeriod), Eq(mNow + 9 * mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 9 * mPeriod), Eq(mNow + 11 * mPeriod)); - tracker.setRenderRate(refreshRate / 6); + tracker.setDisplayModeData({.renderRate = refreshRate / 6}); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow), Eq(mNow + 1 * mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 1 * mPeriod), Eq(mNow + 7 * mPeriod)); } @@ -615,7 +629,7 @@ TEST_F(VSyncPredictorTest, setRenderRateIsIgnoredIfNotDivisor) { tracker.addVsyncTimestamp(mNow); } - tracker.setRenderRate(Fps::fromPeriodNsecs(3.5f * mPeriod)); + tracker.setDisplayModeData({.renderRate = Fps::fromPeriodNsecs(3.5f * mPeriod)}); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow), Eq(mNow + mPeriod)); EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 100), Eq(mNow + mPeriod)); @@ -626,6 +640,39 @@ TEST_F(VSyncPredictorTest, setRenderRateIsIgnoredIfNotDivisor) { EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 5100), Eq(mNow + 6 * mPeriod)); } +TEST_F(VSyncPredictorTest, vsyncTrackerCallback) { + SET_FLAG_FOR_TEST(flags::vrr_config, true); + const auto refreshRate = Fps::fromPeriodNsecs(mPeriod); + DisplayModeData displayModeData = + DisplayModeData{.renderRate = refreshRate, + .notifyExpectedPresentTimeoutOpt = Period::fromNs(30)}; + tracker.setDisplayModeData(displayModeData); + auto last = mNow; + for (auto i = 0u; i < kMinimumSamplesForPrediction; i++) { + EXPECT_CALL(mVsyncTrackerCallback, + onVsyncGenerated(DEFAULT_DISPLAY_ID, TimePoint::fromNs(last + mPeriod), + displayModeData, Period::fromNs(mPeriod))) + .Times(1); + EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow), Eq(last + mPeriod)); + mNow += mPeriod; + last = mNow; + tracker.addVsyncTimestamp(mNow); + } + + displayModeData = DisplayModeData{.renderRate = refreshRate / 2, + .notifyExpectedPresentTimeoutOpt = Period::fromNs(30)}; + tracker.setDisplayModeData(displayModeData); + { + // out of render rate phase + EXPECT_CALL(mVsyncTrackerCallback, + onVsyncGenerated(DEFAULT_DISPLAY_ID, TimePoint::fromNs(mNow + 3 * mPeriod), + displayModeData, Period::fromNs(mPeriod))) + .Times(1); + EXPECT_THAT(tracker.nextAnticipatedVSyncTimeFrom(mNow + 1 * mPeriod), + Eq(mNow + 3 * mPeriod)); + } +} + } // namespace android::scheduler // TODO(b/129481165): remove the #pragma below and fix conversion issues diff --git a/services/surfaceflinger/tests/unittests/VSyncReactorTest.cpp b/services/surfaceflinger/tests/unittests/VSyncReactorTest.cpp index 122192b036..aca3ccca6d 100644 --- a/services/surfaceflinger/tests/unittests/VSyncReactorTest.cpp +++ b/services/surfaceflinger/tests/unittests/VSyncReactorTest.cpp @@ -50,7 +50,7 @@ public: MOCK_METHOD0(resetModel, void()); MOCK_CONST_METHOD0(needsMoreSamples, bool()); MOCK_CONST_METHOD2(isVSyncInPhase, bool(nsecs_t, Fps)); - MOCK_METHOD(void, setRenderRate, (Fps), (override)); + MOCK_METHOD(void, setDisplayModeData, (const DisplayModeData&), (override)); MOCK_CONST_METHOD1(dump, void(std::string&)); }; diff --git a/services/surfaceflinger/tests/unittests/mock/MockVSyncTracker.h b/services/surfaceflinger/tests/unittests/mock/MockVSyncTracker.h index dcf25e18a8..31eb86e4c5 100644 --- a/services/surfaceflinger/tests/unittests/mock/MockVSyncTracker.h +++ b/services/surfaceflinger/tests/unittests/mock/MockVSyncTracker.h @@ -34,7 +34,7 @@ public: MOCK_METHOD0(resetModel, void()); MOCK_CONST_METHOD0(needsMoreSamples, bool()); MOCK_CONST_METHOD2(isVSyncInPhase, bool(nsecs_t, Fps)); - MOCK_METHOD(void, setRenderRate, (Fps), (override)); + MOCK_METHOD(void, setDisplayModeData, (const scheduler::DisplayModeData&), (override)); MOCK_CONST_METHOD1(dump, void(std::string&)); }; diff --git a/services/surfaceflinger/tests/unittests/mock/MockVsyncTrackerCallback.h b/services/surfaceflinger/tests/unittests/mock/MockVsyncTrackerCallback.h new file mode 100644 index 0000000000..b8e24e0593 --- /dev/null +++ b/services/surfaceflinger/tests/unittests/mock/MockVsyncTrackerCallback.h @@ -0,0 +1,35 @@ +/* + * Copyright 2023 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#pragma once + +#include <gmock/gmock.h> + +#include "Scheduler/VSyncTracker.h" + +namespace android::scheduler::mock { + +struct VsyncTrackerCallback final : IVsyncTrackerCallback { + MOCK_METHOD(void, onVsyncGenerated, + (PhysicalDisplayId, TimePoint, const scheduler::DisplayModeData&, Period), + (override)); +}; + +struct NoOpVsyncTrackerCallback final : IVsyncTrackerCallback { + void onVsyncGenerated(PhysicalDisplayId, TimePoint, const scheduler::DisplayModeData&, + Period) override{}; +}; +} // namespace android::scheduler::mock |