Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 25db3818 authored by Alec Mouri's avatar Alec Mouri Committed by Automerger Merge Worker
Browse files

Merge "Tweak wakeup time for OneShotTimer to reduce jank" into tm-dev am:...

Merge "Tweak wakeup time for OneShotTimer to reduce jank" into tm-dev am: 57a40d9d am: 0ca9e31d am: c5c5bd8d

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/native/+/18702545



Change-Id: I43771d5248b52b0da28a5d0c875b8bc13f5aad4d
Signed-off-by: default avatarAutomerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
parents c2a61501 c5c5bd8d
Loading
Loading
Loading
Loading
+12 −11
Original line number Diff line number Diff line
@@ -118,17 +118,18 @@ void OneShotTimer::loop() {
        auto triggerTime = mClock->now() + mInterval;
        state = TimerState::WAITING;
        while (true) {
            // Wait until triggerTime time to check if we need to reset or drop into the idle state.
            if (const auto triggerInterval = triggerTime - mClock->now(); triggerInterval > 0ns) {
                mWaiting = true;
            constexpr auto zero = std::chrono::steady_clock::duration::zero();
            // Wait for mInterval time to check if we need to reset or drop into the idle state.
                struct timespec ts;
            calculateTimeoutTime(std::chrono::nanoseconds(mInterval), &ts);
                calculateTimeoutTime(triggerInterval, &ts);
                int result = sem_clockwait(&mSemaphore, CLOCK_MONOTONIC, &ts);
                if (result && errno != ETIMEDOUT && errno != EINTR) {
                    std::stringstream ss;
                    ss << "sem_clockwait failed (" << errno << ")";
                    LOG_ALWAYS_FATAL("%s", ss.str().c_str());
                }
            }

            mWaiting = false;
            state = checkForResetAndStop(state);
@@ -136,7 +137,7 @@ void OneShotTimer::loop() {
                break;
            }

            if (state == TimerState::WAITING && (triggerTime - mClock->now()) <= zero) {
            if (state == TimerState::WAITING && (triggerTime - mClock->now()) <= 0ns) {
                triggerTimeout = true;
                state = TimerState::IDLE;
                break;
+34 −0
Original line number Diff line number Diff line
@@ -130,6 +130,40 @@ TEST_F(OneShotTimerTest, DISABLED_resetBackToBackTest) {
    EXPECT_FALSE(mResetTimerCallback.waitForUnexpectedCall().has_value());
}

// TODO(b/186417847) This test is new and passes locally, but may be flaky
TEST_F(OneShotTimerTest, DISABLED_resetBackToBackSlowAdvanceTest) {
    fake::FakeClock* clock = new fake::FakeClock();
    mIdleTimer = std::make_unique<scheduler::OneShotTimer>("TestTimer", 1ms,
                                                           mResetTimerCallback.getInvocable(),
                                                           mExpiredTimerCallback.getInvocable(),
                                                           std::unique_ptr<fake::FakeClock>(clock));
    mIdleTimer->start();
    EXPECT_TRUE(mResetTimerCallback.waitForCall().has_value());

    mIdleTimer->reset();
    EXPECT_FALSE(mResetTimerCallback.waitForUnexpectedCall().has_value());
    EXPECT_FALSE(mExpiredTimerCallback.waitForUnexpectedCall().has_value());

    clock->advanceTime(200us);
    mIdleTimer->reset();

    // Normally we would check that the timer callbacks weren't invoked here
    // after resetting the timer, but we need to precisely control the timing of
    // this test, and checking that callbacks weren't invoked requires non-zero
    // time.

    clock->advanceTime(1500us);
    EXPECT_TRUE(mExpiredTimerCallback.waitForCall(1100us).has_value());
    mIdleTimer->reset();
    EXPECT_TRUE(mResetTimerCallback.waitForCall().has_value());

    mIdleTimer->stop();
    clock->advanceTime(2ms);
    // Final quick check that no more callback were observed.
    EXPECT_FALSE(mExpiredTimerCallback.waitForUnexpectedCall().has_value());
    EXPECT_FALSE(mResetTimerCallback.waitForUnexpectedCall().has_value());
}

TEST_F(OneShotTimerTest, startNotCalledTest) {
    fake::FakeClock* clock = new fake::FakeClock();
    mIdleTimer = std::make_unique<scheduler::OneShotTimer>("TestTimer", 1ms,