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

Commit a04b8a5e authored by ramindani's avatar ramindani
Browse files

[SF] Update DisplayMode::Fps with PeakFps

Update to incorporate display refresh rate on
DisplayMode

With the addition of VRR, vsync period
does not necessarily represent the
refresh rate of the display, having a
peakRefreshRate that represents the
display peak refresh rate helps with
separating the concern of vsync period
being different from the peak refresh rate
supported by the device.

Test: atest libsurfaceflinger_unittest
BUG: 286048920
BUG: 284845445
Change-Id: I9d90e4def4cf3efcd5a696a4ec43fbf7698abfe4
parent 70465c42
Loading
Loading
Loading
Loading
+16 −14
Original line number Diff line number Diff line
@@ -208,12 +208,12 @@ bool DisplayDevice::isPoweredOn() const {
    return mPowerMode && *mPowerMode != hal::PowerMode::OFF;
}

void DisplayDevice::setActiveMode(DisplayModeId modeId, Fps displayFps, Fps renderFps) {
    ATRACE_INT(mActiveModeFPSTrace.c_str(), displayFps.getIntValue());
void DisplayDevice::setActiveMode(DisplayModeId modeId, Fps vsyncRate, Fps renderFps) {
    ATRACE_INT(mActiveModeFPSTrace.c_str(), vsyncRate.getIntValue());
    ATRACE_INT(mRenderFrameRateFPSTrace.c_str(), renderFps.getIntValue());

    mRefreshRateSelector->setActiveMode(modeId, renderFps);
    updateRefreshRateOverlayRate(displayFps, renderFps);
    updateRefreshRateOverlayRate(vsyncRate, renderFps);
}

status_t DisplayDevice::initiateModeChange(const ActiveModeInfo& info,
@@ -230,14 +230,14 @@ status_t DisplayDevice::initiateModeChange(const ActiveModeInfo& info,
    mIsModeSetPending = true;

    const auto& pendingMode = *info.modeOpt->modePtr;
    ATRACE_INT(mActiveModeFPSHwcTrace.c_str(), pendingMode.getFps().getIntValue());
    ATRACE_INT(mActiveModeFPSHwcTrace.c_str(), pendingMode.getVsyncRate().getIntValue());

    return mHwComposer.setActiveModeWithConstraints(getPhysicalId(), pendingMode.getHwcId(),
                                                    constraints, outTimeline);
}

void DisplayDevice::finalizeModeChange(DisplayModeId modeId, Fps displayFps, Fps renderFps) {
    setActiveMode(modeId, displayFps, renderFps);
void DisplayDevice::finalizeModeChange(DisplayModeId modeId, Fps vsyncRate, Fps renderFps) {
    setActiveMode(modeId, vsyncRate, renderFps);
    mIsModeSetPending = false;
}

@@ -253,7 +253,7 @@ nsecs_t DisplayDevice::getVsyncPeriodFromHWC() const {
        return vsyncPeriod;
    }

    return refreshRateSelector().getActiveMode().modePtr->getVsyncPeriod();
    return refreshRateSelector().getActiveMode().modePtr->getVsyncRate().getPeriodNsecs();
}

ui::Dataspace DisplayDevice::getCompositionDataSpace() const {
@@ -466,17 +466,19 @@ void DisplayDevice::enableRefreshRateOverlay(bool enable, bool setByHwc, bool sh
        features |= RefreshRateOverlay::Features::SetByHwc;
    }

    // TODO(b/296636258) Update to use the render rate range in VRR mode.
    const auto fpsRange = mRefreshRateSelector->getSupportedRefreshRateRange();
    mRefreshRateOverlay = std::make_unique<RefreshRateOverlay>(fpsRange, features);
    mRefreshRateOverlay->setLayerStack(getLayerStack());
    mRefreshRateOverlay->setViewport(getSize());
    updateRefreshRateOverlayRate(getActiveMode().modePtr->getFps(), getActiveMode().fps, setByHwc);
    updateRefreshRateOverlayRate(getActiveMode().modePtr->getVsyncRate(), getActiveMode().fps,
                                 setByHwc);
}

void DisplayDevice::updateRefreshRateOverlayRate(Fps displayFps, Fps renderFps, bool setByHwc) {
void DisplayDevice::updateRefreshRateOverlayRate(Fps vsyncRate, Fps renderFps, bool setByHwc) {
    ATRACE_CALL();
    if (mRefreshRateOverlay && (!mRefreshRateOverlay->isSetByHwc() || setByHwc)) {
        mRefreshRateOverlay->changeRefreshRate(displayFps, renderFps);
        mRefreshRateOverlay->changeRefreshRate(vsyncRate, renderFps);
    }
}

@@ -486,7 +488,7 @@ bool DisplayDevice::onKernelTimerChanged(std::optional<DisplayModeId> desiredMod
        const auto newMode =
                mRefreshRateSelector->onKernelTimerChanged(desiredModeId, timerExpired);
        if (newMode) {
            updateRefreshRateOverlayRate(newMode->modePtr->getFps(), newMode->fps);
            updateRefreshRateOverlayRate(newMode->modePtr->getVsyncRate(), newMode->fps);
            return true;
        }
    }
@@ -541,14 +543,14 @@ auto DisplayDevice::setDesiredActiveMode(const ActiveModeInfo& info, bool force)
            return DesiredActiveModeAction::None;
        }

        setActiveMode(desiredMode.getId(), desiredMode.getFps(), info.modeOpt->fps);
        setActiveMode(desiredMode.getId(), desiredMode.getVsyncRate(), info.modeOpt->fps);
        return DesiredActiveModeAction::InitiateRenderRateSwitch;
    }

    // Set the render frame rate to the current physical refresh rate to schedule the next
    // frame as soon as possible.
    setActiveMode(currentMode.modePtr->getId(), currentMode.modePtr->getFps(),
                  currentMode.modePtr->getFps());
    setActiveMode(currentMode.modePtr->getId(), currentMode.modePtr->getVsyncRate(),
                  currentMode.modePtr->getVsyncRate());

    // Initiate a mode change.
    mDesiredActiveModeChanged = true;
+3 −3
Original line number Diff line number Diff line
@@ -224,14 +224,14 @@ public:
        return mRefreshRateSelector->getActiveMode();
    }

    void setActiveMode(DisplayModeId, Fps displayFps, Fps renderFps);
    void setActiveMode(DisplayModeId, Fps vsyncRate, Fps renderFps);

    status_t initiateModeChange(const ActiveModeInfo&,
                                const hal::VsyncPeriodChangeConstraints& constraints,
                                hal::VsyncPeriodChangeTimeline* outTimeline)
            REQUIRES(kMainThreadContext);

    void finalizeModeChange(DisplayModeId, Fps displayFps, Fps renderFps)
    void finalizeModeChange(DisplayModeId, Fps vsyncRate, Fps renderFps)
            REQUIRES(kMainThreadContext);

    scheduler::RefreshRateSelector& refreshRateSelector() const { return *mRefreshRateSelector; }
@@ -246,7 +246,7 @@ public:
    // Enables an overlay to be displayed with the current refresh rate
    void enableRefreshRateOverlay(bool enable, bool setByHwc, bool showSpinner, bool showRenderRate,
                                  bool showInMiddle) REQUIRES(kMainThreadContext);
    void updateRefreshRateOverlayRate(Fps displayFps, Fps renderFps, bool setByHwc = false);
    void updateRefreshRateOverlayRate(Fps vsyncRate, Fps renderFps, bool setByHwc = false);
    bool isRefreshRateOverlayEnabled() const { return mRefreshRateOverlay != nullptr; }
    bool onKernelTimerChanged(std::optional<DisplayModeId>, bool timerExpired);

+29 −10
Original line number Diff line number Diff line
@@ -32,6 +32,8 @@
#include "DisplayHardware/Hal.h"
#include "Scheduler/StrongTyping.h"

#include <com_android_graphics_surfaceflinger_flags.h>

namespace android {

namespace hal = android::hardware::graphics::composer::hal;
@@ -49,6 +51,7 @@ using DisplayModeId = StrongTyping<ui::DisplayModeId, struct DisplayModeIdTag, C

using DisplayModes = ftl::SmallMap<DisplayModeId, DisplayModePtr, 3>;
using DisplayModeIterator = DisplayModes::const_iterator;
using namespace com::android::graphics::surfaceflinger;

class DisplayMode {
public:
@@ -76,7 +79,12 @@ public:
        }

        Builder& setVsyncPeriod(nsecs_t vsyncPeriod) {
            mDisplayMode->mFps = Fps::fromPeriodNsecs(vsyncPeriod);
            mDisplayMode->mVsyncRate = Fps::fromPeriodNsecs(vsyncPeriod);
            return *this;
        }

        Builder& setVrrConfig(std::optional<hal::VrrConfig> vrrConfig) {
            mDisplayMode->mVrrConfig = std::move(vrrConfig);
            return *this;
        }

@@ -130,8 +138,17 @@ public:
    int32_t getWidth() const { return mResolution.getWidth(); }
    int32_t getHeight() const { return mResolution.getHeight(); }

    Fps getFps() const { return mFps; }
    nsecs_t getVsyncPeriod() const { return mFps.getPeriodNsecs(); }
    // Peak refresh rate represents the highest refresh rate that can be used
    // for the presentation.
    Fps getPeakFps() const {
        return flags::vrr_config() && mVrrConfig
                ? Fps::fromPeriodNsecs(mVrrConfig->minFrameIntervalNs)
                : mVsyncRate;
    }

    Fps getVsyncRate() const { return mVsyncRate; }

    std::optional<hal::VrrConfig> getVrrConfig() const { return mVrrConfig; }

    struct Dpi {
        float x = -1;
@@ -155,23 +172,25 @@ private:
    PhysicalDisplayId mPhysicalDisplayId;

    ui::Size mResolution;
    Fps mFps;
    Fps mVsyncRate;
    Dpi mDpi;
    int32_t mGroup = -1;
    std::optional<hal::VrrConfig> mVrrConfig;
};

inline bool equalsExceptDisplayModeId(const DisplayMode& lhs, const DisplayMode& rhs) {
    return lhs.getHwcId() == rhs.getHwcId() && lhs.getResolution() == rhs.getResolution() &&
            lhs.getVsyncPeriod() == rhs.getVsyncPeriod() && lhs.getDpi() == rhs.getDpi() &&
            lhs.getGroup() == rhs.getGroup();
            lhs.getVsyncRate().getPeriodNsecs() == rhs.getVsyncRate().getPeriodNsecs() &&
            lhs.getDpi() == rhs.getDpi() && lhs.getGroup() == rhs.getGroup();
}

inline std::string to_string(const DisplayMode& mode) {
    return base::StringPrintf("{id=%d, hwcId=%d, resolution=%dx%d, refreshRate=%s, "
                              "dpi=%.2fx%.2f, group=%d}",
    return base::StringPrintf("{id=%d, hwcId=%d, resolution=%dx%d, vsyncRate=%s, "
                              "dpi=%.2fx%.2f, group=%d, vrrConfig=%s}",
                              mode.getId().value(), mode.getHwcId(), mode.getWidth(),
                              mode.getHeight(), to_string(mode.getFps()).c_str(), mode.getDpi().x,
                              mode.getDpi().y, mode.getGroup());
                              mode.getHeight(), to_string(mode.getVsyncRate()).c_str(),
                              mode.getDpi().x, mode.getDpi().y, mode.getGroup(),
                              to_string(mode.getVrrConfig()).c_str());
}

template <typename... DisplayModePtrs>
+6 −7
Original line number Diff line number Diff line
@@ -285,13 +285,12 @@ std::vector<HWComposer::HWCDisplayMode> HWComposer::getModesFromDisplayConfigura
    std::vector<HWCDisplayMode> modes;
    modes.reserve(configs.size());
    for (auto config : configs) {
        auto hwcMode = HWCDisplayMode{
                .hwcId = static_cast<hal::HWConfigId>(config.configId),
        auto hwcMode = HWCDisplayMode{.hwcId = static_cast<hal::HWConfigId>(config.configId),
                                      .width = config.width,
                                      .height = config.height,
                                      .vsyncPeriod = config.vsyncPeriod,
                                      .configGroup = config.configGroup,
        };
                                      .vrrConfig = config.vrrConfig};

        if (config.dpi) {
            hwcMode.dpiX = config.dpi->x;
+3 −1
Original line number Diff line number Diff line
@@ -102,11 +102,13 @@ public:
        float dpiX = -1.f;
        float dpiY = -1.f;
        int32_t configGroup = -1;
        std::optional<hal::VrrConfig> vrrConfig;

        friend std::ostream& operator<<(std::ostream& os, const HWCDisplayMode& mode) {
            return os << "id=" << mode.hwcId << " res=" << mode.width << "x" << mode.height
                      << " vsyncPeriod=" << mode.vsyncPeriod << " dpi=" << mode.dpiX << "x"
                      << mode.dpiY << " group=" << mode.configGroup;
                      << mode.dpiY << " group=" << mode.configGroup
                      << " vrrConfig=" << to_string(mode.vrrConfig).c_str();
        }
    };

Loading