1
0
Fork 0

Move EdidWrapper from DrmConnector to HwcDisplay

The EdidWrapper lifecycle was previously managed by DrmConnector,
meaning the EDID parser was initialized when the connector was created.
This approach fails for physical connectors where a display is not
attached at boot, as no EDID blob is available to parse.

When a display was subsequently hot-plugged, the system would fall back
to a generic EdidWrapper. This provided incorrect or default display
properties to userspace, causing critical bugs such as:

  * Incorrect DPI calculations, leading to improperly scaled UI in
    Android.
  * Inability to detect HDR capabilities or supported color modes.

This change moves the ownership and lifecycle management of the
EdidWrapper to HwcDisplay. By creating the parser only when a display is
actually connected, we ensure that the correct EDID is always parsed,
making hot-plug functionality work as intended.

Change-Id: I5e056e423bbac2b23a411395b4ce13ccd03c4b64
Signed-off-by: Gil Dekel <gildekel@google.com>
This commit is contained in:
Gil Dekel 2025-10-03 23:03:40 -04:00
parent e54f0897ed
commit 9a76e062b6
4 changed files with 15 additions and 20 deletions

View file

@ -29,7 +29,6 @@
#include "DrmDevice.h"
#include "compositor/DisplayInfo.h"
#include "utils/log.h"
#ifndef DRM_MODE_CONNECTOR_SPI
// NOLINTNEXTLINE(cppcoreguidelines-macro-usage)
@ -88,14 +87,6 @@ auto DrmConnector::Init()-> bool {
return false;
}
UpdateEdidProperty();
#if HAS_LIBDISPLAY_INFO
auto edid = LibdisplayEdidWrapper::Create(GetEdidBlob());
edid_wrapper_ = edid ? std::move(edid) : std::make_unique<EdidWrapper>();
#else
edid_wrapper_ = std::make_unique<EdidWrapper>();
#endif
if (IsWriteback()) {
if (!GetConnectorProperty("WRITEBACK_PIXEL_FORMATS",
&writeback_pixel_formats_property_)) {

View file

@ -27,14 +27,11 @@
#include "DrmProperty.h"
#include "DrmUnique.h"
#include "compositor/DisplayInfo.h"
#include "utils/EdidWrapper.h"
namespace android::drm_hwcomposer {
class DrmDevice;
using EdidWrapperUnique = std::unique_ptr<EdidWrapper>;
class DrmConnector : public PipelineBindable<DrmConnector> {
friend class FakeDrmConnector;
@ -49,9 +46,6 @@ class DrmConnector : public PipelineBindable<DrmConnector> {
int UpdateEdidProperty();
auto GetEdidBlob() -> DrmModePropertyBlobUnique;
auto GetParsedEdid() -> EdidWrapperUnique & {
return edid_wrapper_;
}
auto GetDev() const -> DrmDevice & {
return *drm_;
@ -170,8 +164,6 @@ class DrmConnector : public PipelineBindable<DrmConnector> {
return GetConnectorProperty(prop_name, property, /*is_optional=*/true);
}
EdidWrapperUnique edid_wrapper_;
const uint32_t index_in_res_array_;
std::vector<DrmMode> modes_;

View file

@ -20,7 +20,6 @@
#include "HwcDisplay.h"
#include <cinttypes>
#include <sstream>
#include <ui/ColorSpace.h>
#include <utils/Trace.h>
@ -611,6 +610,15 @@ bool HwcDisplay::Init() {
.trigger = [this]() { hwc_->SendRefreshEventToClient(handle_); }};
flatcon_ = std::make_unique<FlatteningController>(flatcbk,
kFlatteningTimeout);
#if HAS_LIBDISPLAY_INFO
auto edid = LibdisplayEdidWrapper::Create(
pipeline_->connector->Get()->GetEdidBlob());
if (edid) {
edid_wrapper_ = std::move(edid);
}
ALOGW_IF(!edid, "Failed to create a LibdisplayInfo parser.");
#endif
}
HwcLayer::LayerProperties lp;

View file

@ -29,10 +29,12 @@
#include "drm/DrmAtomicStateManager.h"
#include "drm/VSyncWorker.h"
#include "stats/CompositionStats.h"
#include "utils/EdidWrapper.h"
namespace android::drm_hwcomposer {
using DisplayHandle = int64_t;
using EdidWrapperUnique = std::unique_ptr<EdidWrapper>;
class Backend;
class DrmHwc;
@ -272,6 +274,8 @@ class HwcDisplay {
DrmHwc *const hwc_;
EdidWrapperUnique edid_wrapper_ = std::make_unique<EdidWrapper>();
int64_t staged_mode_change_time_{};
std::optional<ConfigId> staged_mode_config_id_{};
@ -316,8 +320,8 @@ class HwcDisplay {
void SetHdrOutputMetadata(ui::Hdr hdrType);
void SetOutputType(OutputType hdr_output_type);
auto GetEdid() const -> EdidWrapperUnique & {
return GetPipe().connector->Get()->GetParsedEdid();
auto GetEdid() const -> const EdidWrapperUnique & {
return edid_wrapper_;
}
std::shared_ptr<FrontendDisplayBase> frontend_private_data_;