在 GStreamer 中解析视频流的 HDR(高动态范围)信息并将其传递给 DRM 显示模块,涉及以下几个步骤:
解析 HDR 元数据:从视频流中提取 HDR 元数据(如亮度、色彩空间等)。
配置 DRM 显示模块:将 HDR 元数据传递给 DRM 显示模块,以正确显示 HDR 内容。
以下是详细的实现步骤和示例代码:
- 解析 HDR 元数据
HDR 元数据通常嵌入在视频流的 SEI(Supplemental Enhancement Information)或容器格式(如 MP4、MKV)中。GStreamer 提供了插件和工具来解析这些元数据。
1.1 使用 gst-discoverer 检查 HDR 信息
gst-discoverer 是 GStreamer 提供的一个工具,用于分析媒体文件的元数据。
gst-discoverer-1.0 video_with_hdr.mp4
输出示例:
HDR Metadata:
Mastering Display Color Volume:
Red: (0.6800, 0.3200)
Green: (0.2650, 0.6900)
Blue: (0.1500, 0.0600)
White Point: (0.3127, 0.3290)
Max Luminance: 1000.0000 cd/m²
Min Luminance: 0.0010 cd/m²
1.2 使用 gst-plugins-bad 解析 HDR 元数据
gst-plugins-bad 提供了 h264parse、h265parse 等插件,可以解析 HDR 元数据。
示例 Pipeline
gst-launch-1.0 filesrc location=video_with_hdr.mp4 ! qtdemux ! h265parse ! avdec_h265 ! videoconvert ! autovideosink
qtdemux:解复用 MP4 容器。
h265parse:解析 H.265 视频流中的 HDR 元数据。
avdec_h265:解码 H.265 视频流。
videoconvert:转换视频格式。
autovideosink:自动选择视频输出。
- 配置 DRM 显示模块
DRM 显示模块需要接收 HDR 元数据,以正确配置显示器的 HDR 模式。
2.1 使用 libdrm 设置 HDR 元数据
DRM 提供了 drmModeCreatePropertyBlob 和 drmModeObjectSetProperty 等函数,用于设置 HDR 元数据。
#include <xf86drm.h>
#include <xf86drmMode.h>
void set_hdr_metadata(int fd, uint32_t connector_id, uint32_t blob_id) {
drmModeObjectSetProperty(fd, connector_id, DRM_MODE_OBJECT_CONNECTOR,
DRM_MODE_PROP_HDR_METADATA, blob_id);
}
int main()
{
int fd = drmOpen("card0", NULL);
if (fd < 0) {
fprintf(stderr, "Failed to open DRM device\n");
return -1;
}
// 创建 HDR 元数据 Blob
struct hdr_metadata hdr_meta = {
.max_cll = 1000,
.max_fall = 400,
.min_dml = 0.001,
.max_dml = 1000,
};
uint32_t blob_id;
drmModeCreatePropertyBlob(fd, &hdr_meta, sizeof(hdr_meta), &blob_id);
// 设置 HDR 元数据
set_hdr_metadata(fd, connector_id, blob_id);
drmClose(fd);
return 0;
}
drmModeCreatePropertyBlob
:创建 HDR 元数据的 Blob。
drmModeObjectSetProperty
:将 HDR 元数据设置到 DRM 连接器。
HDR_OUTPUT_METADATA:
userspace/app can get HDR cap info
from sink device EDID, and then send it to driver, driver will packet it in SDP of HDMI then send it to sink device.
drm driver will pack the sink-HDR-metadata + DRM hardware capability to sink device. Driver will pack sink-device-HDR + video/game HDR + hardware HDR info into HDMI/DP info packet
struct rk_hdr_metadata_infoframe {
/**
* @eotf: Electro-Optical Transfer Function (EOTF)
* used in the stream.
*/
unsigned char eotf; // 0: SDR-Gamma, 1: HDR-Gamma, 2: SMPTE2084, 3: HLG
/**
* @metadata_type: Static_Metadata_Descriptor_ID.
*/
unsigned char metadata_type;
/**
* @display_primaries: Color Primaries of the Data.
* These are coded as unsigned 16-bit values in units of
* 0.00002, where 0x0000 represents zero and 0xC350
* represents 1.0000.
* @display_primaries.x: X cordinate of color primary.
* @display_primaries.y: Y cordinate of color primary.
*/
struct {
unsigned short x, y;
} display_primaries[3];
/**
* @white_point: White Point of Colorspace Data.
* These are coded as unsigned 16-bit values in units of
* 0.00002, where 0x0000 represents zero and 0xC350
* represents 1.0000.
* @white_point.x: X cordinate of whitepoint of color primary.
* @white_point.y: Y cordinate of whitepoint of color primary.
*/
struct {
unsigned short x, y;
} white_point;
/**
* @max_display_mastering_luminance: Max Mastering Display Luminance.
* This value is coded as an unsigned 16-bit value in units of 1 cd/m2,
* where 0x0001 represents 1 cd/m2 and 0xFFFF represents 65535 cd/m2.
*/
unsigned short max_display_mastering_luminance;
/**
* @min_display_mastering_luminance: Min Mastering Display Luminance.
* This value is coded as an unsigned 16-bit value in units of
* 0.0001 cd/m2, where 0x0001 represents 0.0001 cd/m2 and 0xFFFF
* represents 6.5535 cd/m2.
*/
unsigned short min_display_mastering_luminance;
/**
* @max_cll: Max Content Light Level.
* This value is coded as an unsigned 16-bit value in units of 1 cd/m2,
* where 0x0001 represents 1 cd/m2 and 0xFFFF represents 65535 cd/m2.
*/
unsigned short max_cll;
/**
* @max_fall: Max Frame Average Light Level.
* This value is coded as an unsigned 16-bit value in units of 1 cd/m2,
* where 0x0001 represents 1 cd/m2 and 0xFFFF represents 65535 cd/m2.
*/
unsigned short max_fall;
};