4. 设备树绑定文档
设备树绑定文档,说白了就是硬件描述语言的“说明书”。
我刚开始接触设备树时,最头疼的就是看那些密密麻麻的文本。后来发现,只要掌握了套路,绑定文档其实比芯片手册好读多了。今天我就带你走一遍——怎么读、怎么理解、怎么写。
4.1 绑定文档到底长什么样?
绑定文档通常放在内核源码的 Documentation/devicetree/bindings/ 目录下。每个硬件IP都会有一个对应的YAML文件或纯文本描述。
我个人习惯先看文件头。它一般会告诉你:
- 这个设备是干什么的
- 它挂在哪个总线上
- 需要哪些必须的属性
举个例子,一个典型的I2C设备绑定文档开头是这样的:
# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
%YAML 1.2
---
$id: http://devicetree.org/schemas/i2c/foo,bar.yaml#
$schema: http://devicetree.org/meta-schemas/core.yaml#
title: Foo Bar I2C Sensor
maintainers:
- John Doe <john@example.com>
description: |
This binding describes the Foo Bar temperature and humidity sensor.
It communicates over I2C bus at addresses 0x48-0x4b.
嗯,这里要注意——maintainers字段很重要。如果你发现文档有问题,可以直接找维护者。我曾经就靠这个字段找到了一个文档错误的原作者,省了我两天排查时间。
4.2 常见绑定格式解析
现在的内核主流格式是YAML,但老一些的文档还是纯文本。我建议你两种都要会看。
4.2.1 YAML格式(新标准)
YAML格式的核心是 properties 部分。它定义了每个属性的类型、是否必须、取值范围。
properties:
compatible:
const: foo,bar-sensor
reg:
maxItems: 1
description: I2C slave address
interrupts:
maxItems: 1
vdd-supply:
description: Power supply regulator
required:
- compatible
- reg
- vdd-supply
你看,required 列表里列出的属性,一个都不能少。少了内核就会报错。我在项目中遇到过有人漏了 vdd-supply,结果设备驱动加载时一直报电源错误,查了两天才发现是绑定文档里写了必须,但设备树里没配。
4.2.2 纯文本格式(老标准)
老格式虽然不推荐了,但很多成熟IP还在用。它长这样:
Required properties:
- compatible: Should be "foo,bar-sensor"
- reg: I2C address of the device
- interrupts: Interrupt specifier
Optional properties:
- vdd-supply: Phandle to the regulator node
- wakeup-source: Mark the device as wakeup capable
说白了,老格式就是“人写的说明书”,新格式是“机器能校验的说明书”。我个人更推荐新格式,因为它能自动检查错误。
4.3 如何高效阅读绑定文档?
我总结了一个三步法:
- 先看compatible —— 找到设备树里对应的字符串
- 再看required —— 确保所有必须属性都配了
- 最后看examples —— 大部分文档末尾都有完整示例
举个例子,假设你要配一个温度传感器。先搜 compatible = "foo,bar-sensor",然后看required里要 reg 和 vdd-supply,最后抄一下example里的写法。十分钟就能搞定。
4.4 编写自己的绑定文档
当你需要为一个新硬件写绑定时,别慌。我一般按这个流程走:
4.4.1 确定compatible字符串
格式是 厂商,设备名。比如 ti,ads1115、nxp,pca9685。注意厂商名要小写,设备名用短横线连接。
4.4.2 列出所有属性
先列必须的,再列可选的。我建议你画个表格:
| 属性名 | 类型 | 必须/可选 | 说明 |
|---|---|---|---|
| compatible | string | 必须 | 设备标识 |
| reg | uint32 | 必须 | I2C地址或片选号 |
| interrupts | uint32 | 可选 | 中断号 |
| reset-gpios | gpio | 可选 | 复位引脚 |
4.4.3 编写YAML文件
这里我直接给个完整模板:
# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
%YAML 1.2
---
$id: http://devicetree.org/schemas/i2c/my,device.yaml#
$schema: http://devicetree.org/meta-schemas/core.yaml#
title: My Custom I2C Device
maintainers:
- Your Name <your@email.com>
properties:
compatible:
const: my,device
reg:
maxItems: 1
description: I2C slave address
interrupts:
maxItems: 1
my,threshold:
$ref: /schemas/types.yaml#/definitions/uint32
description: Threshold value for the device
default: 100
required:
- compatible
- reg
additionalProperties: false
examples:
- |
i2c {
#address-cells = <1>;
#size-cells = <0>;
sensor@48 {
compatible = "my,device";
reg = <0x48>;
interrupts = <13 2>;
my,threshold = <200>;
};
};
additionalProperties: false 这个字段很关键。它告诉校验工具:除了我列出的属性,其他的一律不认。我曾经没加这个,结果设备树里写了个拼写错误的属性名,内核默默忽略了,查了半天才发现。
4.5 知识体系总览
下面这张图帮你理清绑定文档的整个知识脉络:
4.6 避坑指南
最后分享几个我踩过的坑:
- compatible字符串别写错 —— 大小写、标点符号都要和驱动里完全一致。我曾经把
foo,bar写成了foo-bar,驱动死活不认。 - reg属性注意地址格式 —— I2C设备用7位地址,SPI设备用片选号。别搞混了。
- 别忘了加
additionalProperties: false—— 这个能帮你发现拼写错误。 - example一定要能通过校验 —— 我见过很多文档的example本身就是错的,抄了就会翻车。
总结一下: 绑定文档是设备树和驱动之间的桥梁。读懂了它,你就能理解硬件是怎么被软件描述的;写好了它,别人就能正确使用你的硬件。说白了,这就是嵌入式开发者的“契约精神”。
可可精品资料库