add_tca9555_driver - TreeNewbeer/Coonix GitHub Wiki
TCA9555是一个I2C接口的16路IO扩展芯片。查阅 dirver/gpio 中的代码发现内核在 gpio-pca953x.c 文件中提供了pca9555的驱动,而没有tca9555的驱动。 经过对比pca9555和tca9555的数据手册发现寄存器定义完全一直。可能是ti出品的就叫tca9555,nxp出品的就叫pca9555吧。
首先进入linux-menuconfig,找到
- Device Drivers → (*)I2C support
- Device Drivers → I2C support → I2C Hardware Bus support → <*> NUC980 I2C Driver for Port 0
开启I2C支持,然后由于与TCA9555相连的是I2C0,所以也要开启NUC980的I2C0支持 至于 NUC980 I2C0 pin selection 这一部分可以不用管,引脚可以在设备树中设置。
首先进入linux-menuconfig,找到
- Device Drivers → GPIO Support
- Device Drivers → GPIO Support → [*]/sys/class/gpio/... (sysfs interface)
- Device Drivers → GPIO Support → I2C GPIO expanders → <*> PCA95[357]x, PCA9698, TCA64xx, and MAX7310 I/O ports
这个 /sys/class/gpio 是应用程序操作 GPIO的基础。
在设备树中只需要在 i2c0 这个节点下添加一个子节点就好了,就像这样
i2c0: i2c0@b0080000 {
status = "okay";
pinctrl-0 = <&pinctrl_i2c0_PA>;
tca9555: tca9555@20 {
compatible = "nxp,pca9555";
reg = <0x20>;
};
};
- 设置i2c0节点的 status = "okay" 启用 i2c0 节点。
- 设置pinctrl-0 = <&pinctrl_i2c0_PA> 设置 i2c0 的引脚为PA0, PA1。
- tca9555: tca9555@20 这一部分是 label: name@<address> 的结构。label和name都可以自己定义,address是指的总线地址。在这里 tca9555 挂在 i2c0 总线下,tca9555 的 i2c 设备地址为 0x20,所以这里的 address 是 20。
- compatible = "nxp,pca9555"说明这个节点的类型。在加载驱动的时候会自动根据 "nxp,pca9555" 这个字符串找到对应的驱动。
- reg = <0x20> 设置 tca9555 的 i2c 设备地址为0x20。
做完上述修改就可以编译内核然后烧写了。
首先进入 /sys/class/gpio 目录。输入 ls 命令后显示如下
export gpiochip0 gpiochip496 unexport
gpiochip0是nuc980自带的gpio,而gpiochip496则是tca9555扩展出来的gpio。可以进入gpiochip496这个文件夹中,发现这个文件夹中有
base device label ngpio subsystem uevent
这么几个文件。用cat可以查看这些文件的内容。
# cat label
pca9555
# cat base
496
# cat ngpio
16
所以在 label 文件内容是gpio芯片驱动的名称,base文件中放的是gpio的起始编号,ngpio文件中放的是gpio的数量。
# cat device/of_node/compatible
nxp,pca9555
# cat device/of_node/name
tca9555
这两个文件中的内容是设备树中该节点的 compatible 字段和节点的名称。
在操作gpio之前首先要导出 gpio ,导出gpio的方法是向 /sys/class/gpio/export 文件中写入 gpio 的编号。在上面通过base文件可以知道tca9555芯片的io-0的编号是496, io-1的编号是497.... 如果需要导出io-0,则需输入
echo 496 > /sys/class/gpio/export
然后会发现 /sys/class/gpio 目录下多了一个 gpio496 文件夹。然后通过向该文件夹中 direction 文件写入 in 或者 out 来控制gpio的方向,比如设置gpio的方向为输出:
echo out > gpio496/direction
通过向 value 文件中写入0或者1来控制io输出电平,也可以读取这个文件来获得io状态。
# echo 1 > gpio496/value
# cat gpio496/value
1
最后,如果gpio使用完毕可以向 /sys/class/gpio/unexport 文件中写入gpio编号取消导出对应的gpio。
# echo 496 > /sys/class/gpio/unexport
执行这条命令之后 gpio496 这个文件夹就消失了。