1. HDMI协议基础:从诞生到信号传输
做显示驱动这些年,我接触过各种接口——VGA、DVI、DisplayPort,但HDMI绝对是最“麻烦”也最“有趣”的一个。为什么这么说?因为它既要兼容老设备,又要跑4K@60Hz甚至8K,中间还夹着HDCP版权保护。今天咱们就从根上把HDMI捋一遍。
1.1 HDMI发展史:一个接口的进化之路
HDMI的全称是High-Definition Multimedia Interface,高清晰度多媒体接口。2002年12月,日立、松下、飞利浦、索尼、汤姆逊等七家公司联合推出了HDMI 1.0。当时的目标很明确——用一个接口同时传输视频+音频,取代VGA和模拟音频线。
我刚开始做驱动时,主流还是HDMI 1.3。那时候最头疼的是Deep Color支持,很多电视声称支持但实际EDID里写的乱七八糟。嗯,EDID这东西后面会细讲。
| 版本 | 发布时间 | 最大带宽 | 关键特性 |
|---|---|---|---|
| HDMI 1.0 | 2002.12 | 4.95 Gbps | 1080p@60Hz, 8声道音频 |
| HDMI 1.3 | 2006.06 | 10.2 Gbps | Deep Color, Dolby TrueHD |
| HDMI 1.4 | 2009.05 | 10.2 Gbps | 4K@30Hz, 3D, ARC, 以太网通道 |
| HDMI 2.0 | 2013.09 | 18.0 Gbps | 4K@60Hz, BT.2020, 32声道 |
| HDMI 2.1 | 2017.11 | 48.0 Gbps | 8K@60Hz, 4K@120Hz, eARC, VRR, FRL |
个人经验:HDMI 2.1的FRL(Fixed Rate Link)模式跟之前完全不一样。以前是TMDS时钟+数据通道,2.1改成了4个高速通道跑16b/18b编码。我调试2.1驱动时,发现很多老线缆在48Gbps下直接罢工——线材质量真的会卡脖子。
1.2 TMDS编码原理:为什么是3个通道?
TMDS全称Transition Minimized Differential Signaling,最小化传输差分信号。说白了,就是把8位数据编码成10位,目的是减少信号跳变次数,降低电磁干扰。
你想想看,如果原始数据是连续的0xFF(11111111),直接传的话电平一直不变,接收端容易失锁。TMDS做了两件事:
- 编码阶段:8位数据→10位,尽量让0和1的数量平衡,同时减少连续相同位的长度。
- 差分传输:用一对差分线(正负信号)传输,抗共模干扰。
HDMI用了3个TMDS数据通道(Channel 0/1/2)加1个TMDS时钟通道。为什么是3个?因为RGB每个颜色分量各占一个通道。每个通道在像素时钟的驱动下,每个时钟周期传输10位数据。
避坑指南:我曾经遇到过一个问题——HDMI输出画面有随机噪点。查了半天,发现是PCB上TMDS差分线等长没做好。差分线长度差超过5mm,高速信号就开始出问题。记住:等长、阻抗匹配、屏蔽,这三点是TMDS布线的命门。
TMDS编码流程大致如下:
// TMDS编码简化流程(以8位R/G/B数据为例)
// 输入:8位像素数据 + 2位控制信号
// 输出:10位TMDS符号
步骤1: 计算输入数据中1的个数
步骤2: 如果1的个数 > 4,或者1的个数==4且最低位为0
则对数据进行取反,设置XNOR标志
步骤3: 根据当前DC平衡状态,决定是否再次取反
步骤4: 输出10位编码 + 更新DC平衡计数器
这个编码过程保证了:
- 连续相同位的长度不超过5个
- 长期来看,0和1的数量趋于平衡(DC平衡)
- 接收端可以用PLL从数据流中恢复时钟
1.3 HDMI引脚定义与信号分类
HDMI Type-A接口有19个引脚,分三排排列。我刚开始做硬件调试时,经常拿万用表量引脚,后来干脆背下来了。
| 引脚 | 信号 | 说明 |
|---|---|---|
| 1-3 | TMDS Data 2+/2-/2 Shield | 通道2差分信号及屏蔽 |
| 4-6 | TMDS Data 1+/1-/1 Shield | 通道1差分信号及屏蔽 |
| 7-9 | TMDS Data 0+/0-/0 Shield | 通道0差分信号及屏蔽 |
| 10-12 | TMDS Clock+/Clock-/Clock Shield | 时钟通道差分信号及屏蔽 |
| 13 | CEC | 消费电子控制总线 |
| 14 | HEC Data- (ARC) | 以太网/音频回传通道 |
| 15 | SCL | DDC I²C时钟线 |
| 16 | SDA | DDC I²C数据线 |
| 17 | DDC/CEC Ground | DDC和CEC共用地 |
| 18 | +5V Power | 源端提供5V电源(最大55mA) |
| 19 | Hot Plug Detect | 热插拔检测 |
信号可以分成几类:
- 视频数据通道:TMDS Data 0/1/2 + Clock,这是主干道
- 控制总线:DDC(I²C)用于读取EDID,CEC用于设备间控制
- 辅助通道:HEC(以太网)和ARC(音频回传),HDMI 1.4引入
- 电源与检测:+5V和HPD,这是握手的第一步
注意:HPD(热插拔检测)是HDMI驱动的“敲门砖”。源端检测到HPD拉高后,才会开始读取EDID。我遇到过一种情况——某些电视在待机时HPD会周期性拉低再拉高,导致驱动反复初始化。解决方案是在驱动里加一个HPD去抖定时器,至少等100ms再响应。
1.4 HDMI信号传输流程
下面这张图展示了HDMI从连接建立到画面显示的整体流程:
这个流程看起来简单,但每个环节都可能出问题。我调试过一台投影仪,HPD信号正常,EDID也能读出来,但就是不出画面。最后发现是TMDS时钟频率跟EDID里声明的像素时钟对不上——驱动里配的时钟源分频系数错了。
核心要点:HDMI驱动开发,本质上就是管理好这个流程。从HPD中断处理开始,到EDID解析、模式匹配、时钟配置、TMDS通道使能,最后到画面输出。每一步都要有状态机保护,不能跳步。
1.5 小结
这一章我们聊了HDMI从1.0到2.1的演进,TMDS编码为什么要把8位扩成10位,以及19个引脚各自干什么活。说白了,HDMI就是一套精心设计的“视频+音频+控制”三合一传输方案。TMDS负责把数据变成适合高速传输的格式,DDC负责源端和显示端之间的“谈判”,HPD负责告诉源端“有人插线了”。