rk3288 设备树语法学习

设备树背景

设备资源以前都是用.c文件,但是随着时间的推移。冗余代码越来越多,所以用设备树来替代资源文件的指定。
设备树在linux里的查看:

ls /sys/firmware/
devicetree fdt
#devicetree 目录下是以目录结构呈现的dtb文件,根节点对应base目录,每个节点对应一个目录,每个文件对应一个属性

官方文档:https://www.devicetree.org/specifications/

设备树文件

  • dtb:内核编译号的设备树镜像
  • dts:设备树的源码文件
  • dtsi:厂家出的,可以包含在dts里面的设备树代码文件,语法和dts文件时一样的。
    示例:
/dts-v1/;
#include <dt-bindings/input/input.h>
#include "imx6ull.dtsi"
/ {
	……
};

DTS文件格式

  1. dts文件布局:
/dts-v1/;								//表示版本
[memory reservations] 					//格式为: /meemreserve/ <address> <length>;
/{										//这里就是根节点,下面可以填写很多子节点
	[property definitions]				//根节点也有一些属性
	[child nodes]						//根节点的子节点
}
  1. 设备树中的基本单元,被称为"node",node节点的格式为:
[label:] node-name[@unit-address] {
	[properties definitions]
	[child nodes]
};
//label是标识,可以方便引用node
//node-name是节点的名字
//unit-address描述的是位于哪个地址
//其中用[]修饰的是可选项
  1. properties格式
    节点都会有properties属性,它的格式一般是"name = value",但是value有多种取值方式
  • array of cells:
    • cell是一个32位数据,用尖括号 显示,interrupts = <17 0xc>;
    • cell是一个64位数据,clock-frequency = <0x00000001 0x00000000>;
  • string:
    • 字符串属性用双引号包围,compatible = "simpile-bus";
  • bytestring:
    • 字节序列用中括号包围,local-mac-address = [00 00 12 34 56 78];
    • local-mac-address = [000012345678]
  • 也可以是各种值的组合,用逗号隔开
    • compatible = "ns16550", "ns8250";
    • example = <0xf00f0000 19>, "a strage property format";

常用属性

#address-cells、#size-cells

  • address-cells:表示address要用多少个32位数来表示。
  • size-cells:表示size要用多少个32位数来表示
/ {
#address-cells = <1>;				//reg中用1个树表示地址
#size-cells = <1>;					//reg中用1个数表示大小
	memory {
		reg = <0x80000000 0x20000000>;		//0x80000000为地址,0x20000000表示大小
	};
};

compatible

compatible的值,建议取这样的格式:“manufacturer,model”,即“厂家名,模块名”。

led {									
	compatible = “A”, “B”, “C”;			//compatible表示兼容,内核中可能有A、B、C三种驱动支持
};										//内核就会按顺序找驱动

model

model与compatible属性有些类似,modle用来准确地定义这个硬件是什么。

/ {
	compatible = "samsung,smdk2440", "samsung,mini2440";			//这个单板兼容内核中地smdk2440,mini2440
	model = "jz2440_v3";											//具体地板子用model来明确
};

status

在dtsi中有很多设备,但是在当前地板子上某些设备是没有地。这时候可以给设备节点添加status属性,设置为disabled。
status可以填写的值:

  • “okay”:设备正常运行。
  • “disabled”:设备不可操作,但是后面可以恢复工作。
  • “fail”:发生了严重错误,需修复。
  • “fail-sss”:发生了严重错误,需修复;sss表示错误信息。
&uart1 {
	status = "disabled";
};

reg

在设备树中描述一段空间。在ARM总,寄存器和内存是统一编址的,在访问上没有区别。

/dts-v1/;
/ {
	#address-cells = <1>;
	#size-cells = <1>;
	memory {
		reg = <0x80000000 0x20000000>;		//reg的地址和地址长度,有address和size决定
	};
};

name(过时了)

用来表示节点名字,在platform_driver匹配时使用,优先级最低。

ldevice_type(过时了)

字符串,用来表示节点类型。在platfrom_driver匹配时使用,优先级为中。

常用节点

根节点

dst中必须有一个根节点。

/dts-v1/;
/ {	
	model = "SMDK24440";				//这个板子是什么
	compatible = "samsung,smdk2440";	//板子兼容哪些平台,定义一系列的字符串, 用来指定内核中哪个 machine_desc 可以支持本设备
	#address-cells = <1>;			// 在它的子节点的 reg 属性中, 使用多少个 u32 整数来描述地址(address)
	#size-cells = <1>;				// 在它的子节点的 reg 属性中, 使用多少个 u32 整数来描述大小(size)
};

CPU节点

一般不需要我们设置,在 dtsi 文件中都定义好了

cpus {
	#address-cells = <1>;
	#size-cells = <0>;
	cpu0: cpu@0 {
		.......
	}
};

memory节点

芯片厂家不可能事先确定你的板子使用多大的内存,所以 memory 节点需要板厂设置。

memory {
	reg = <0x80000000 0x20000000>;
};

chosen节点

可以通过设备树文件给内核传入一些参数,这要在 chosen 节点中设置 bootargs 属性。

chosen {
	bootargs = "noinitrd root=/dev/mtdblock4 rw init=/linuxrc console=ttySAC0,115200";
};

编译、更换设备树

在内核中可以单独编译设备树

make dtbs V=1

手工编译,除非熟练掌握

./scripts/dtc/dtc -I dts -O dtb -o tmp.dtb arch/arm/boot/dts/xxx.dts // 编译 dts 为 dtb
./scripts/dtc/dtc -I dtb -O dts -o tmp.dts arch/arm/boot/dts/xxx.dtb // 反编译 dtb 为 dts

#/sys/firmware/fdt 文件,它就是 dtb 格式的设备树文件
./scripts/dtc/dtc -I dtb -O dts /从板子上/复制出来的/fdt -o tmp.dts

rk3288中源码编译在arch/arm/boot/dts/rk3288-firefly.dtb,更换设备树目录是/boot/rk3288-firefly.dtb

上一篇:Java并发包中原子操作类原理


下一篇:Python办公自动化之Excel转Word