intel_fb: amend connectors report with display name

The EDID reported by connected displays contains data to identify
displays based on product strings and PNP IDs. Amended the connectors
report <connector> node by an optional display_name attribute containing
the EDID information if available.

Fixes 
This commit is contained in:
Christian Helmuth 2025-03-31 10:10:01 +02:00 committed by Norman Feske
parent af3e8725ca
commit 73213872f8
4 changed files with 38 additions and 3 deletions
repos/pc/src/driver/framebuffer/intel/pc

@ -36,7 +36,7 @@ The exported report has the following format:
! <mode width="1920" height="1080" hz="60" id="1" preferred="true" used="true" width_mm="288" height_mm="165"/>
! ...
! </connector>
! <connector name="DP-1" connected="true" width_mm="280" height_mm="160">
! <connector name="DP-1" connected="true" display_name="ACME 123" width_mm="280" height_mm="160">
! <mode width="1920" height="1200" hz="60" id="1" preferred="true" width_mm="280" height_mm="160"/>
! <mode width="1920" height="1080" hz="60" id="2" used="true" width_mm="278" height_mm="158"/>
! <mode width="1280" height="1024" hz="60" id="3"/>
@ -47,6 +47,7 @@ The exported report has the following format:
! </merge>
! </connectors>
If available, the EDID display name is reported via 'display_name'.
The physical dimension of the display is reported as 'width_mm' and 'height_mm'
in millimeter per connector and if available, also per mode. The values can
be used as input to DPI calculations. The currently used mode of the connector

@ -56,6 +56,7 @@ void lx_emul_i915_report_connector(void * lx_data, void * genode_xml,
char const *name, char connected,
char valid_fb,
unsigned brightness,
char const *display_name,
unsigned width_mm, unsigned height_mm);
void lx_emul_i915_iterate_modes(void *lx_data, void * genode_data);
void lx_emul_i915_report_modes(void * genode_xml, struct genode_mode *);

@ -15,6 +15,7 @@
#include <linux/sched/task.h>
#include <drm/drm_client.h>
#include <drm/drm_edid.h>
#include <drm_crtc_internal.h>
#include "i915_drv.h"
@ -855,6 +856,29 @@ void lx_user_init(void)
}
static void display_name_from_edid(struct drm_property_blob *edid_blob_ptr,
char *name, size_t capacity)
{
struct edid const *edid = edid_blob_ptr->data;
if (!edid)
return;
drm_edid_get_monitor_name(edid, name, capacity);
/* fall back to PNP ID */
if (name[0] == 0) {
u32 const panel_id = (u32)edid->mfg_id[0] << 24
| (u32)edid->mfg_id[1] << 16
| (u32)EDID_PRODUCT_ID(edid);
u16 prod;
char vend[4];
drm_edid_decode_panel_id(panel_id, vend, &prod);
snprintf(name, capacity, "%.3s%04X", vend, prod);
}
}
static void _report_connectors(void * genode_data, bool const discrete)
{
struct drm_connector_list_iter conn_iter;
@ -868,17 +892,23 @@ static void _report_connectors(void * genode_data, bool const discrete)
struct genode_mode conf_mode = {};
char display_name[16] = { 0 };
/* read configuration for connector */
lx_emul_i915_connector_config(connector->name, &conf_mode);
if ((discrete && conf_mode.mirror) || (!discrete && !conf_mode.mirror))
continue;
if (connector->edid_blob_ptr)
display_name_from_edid(connector->edid_blob_ptr, display_name, sizeof(display_name));
lx_emul_i915_report_connector(connector, genode_data,
connector->name,
connector->status != connector_status_disconnected,
valid_fb,
get_brightness(connector, INVALID_BRIGHTNESS),
*display_name ? display_name : 0,
connector->display_info.width_mm,
connector->display_info.height_mm);
}

@ -683,8 +683,9 @@ int lx_emul_i915_action_to_process(int const action_failed)
void lx_emul_i915_report_connector(void * lx_data, void * genode_xml,
char const *name, char const connected,
char const /* fb_available */,
unsigned brightness, unsigned width_mm,
unsigned height_mm)
unsigned brightness,
char const *display_name,
unsigned width_mm, unsigned height_mm)
{
auto &xml = *reinterpret_cast<Genode::Xml_generator *>(genode_xml);
@ -692,6 +693,8 @@ void lx_emul_i915_report_connector(void * lx_data, void * genode_xml,
{
xml.attribute("connected", !!connected);
xml.attribute("name", name);
if (display_name)
xml.attribute("display_name", display_name);
if (width_mm)
xml.attribute("width_mm" , width_mm);
if (height_mm)