Linux 学习笔记:pinctrl 子系统

一、概述

在使用 pinctrlgpio 子系统之前,开发gpio驱动,需要在驱动代码中直接操作所涉及的 GPIO 寄存器(配置IO 复用,配置IO口为输出方,设置IO输出高低电平),驱动开发方式和裸机开发基本没区别。

Linux 内核提供了 pinctrl 和 gpio 子系统用于 GPIO 驱动,简化了GPIO 驱动开发。下面以 点亮一个LED 为例,介绍pinctrl 子系统的使用。

二、 主要工作内容

  • 获取设备树中 pin 信息。
  • 根据获取到的 pin 信息来设置 pin 的复用功能。
  • 根据获取到的 pin 信息来设置 pin 的电气特征,比如 上下拉,速度,驱动能力等。

对于我们使用者来说,只需要在设备树里面设置好某个pin 的相关属性即可,其他的初始化工作均由 pinctrl 子系统来完成。

pinctrl 子系统源码目录为 drivers/pinctrl

三、 设备树PIN的配置信息分析

1. 设备树中的pinctrl 子节点

pinctrl_led:ledgrp{
			fsl,pins = <
			MX6UL_PAD_GPIO1_IO03__GPIO1_IO03  0x10B0
			>
		};

MX6UL_PAD_GPIO1_IO03__GPIO1_IO03 的定义在 imx6ul-pinfunc.h ,定义如下:

#define MX6UL_PAD_GPIO1_IO03__GPIO1_IO03     0x0068 0x02F4 0x0000 0x5 0x0

2. pinctrl 配置数据与寄存器对应关系

Linux 学习笔记:pinctrl 子系统_第1张图片

各个寄存器和值的解析

  • mux_reg 寄存器偏移地址 : 值为 0x0068 。 从 iomuxc 节点的 reg 属性可以知道,iomuxc 外设寄存器的起始地址为 0x020E0000 。因此,0x020E0000 + 0x0068 = 0x020E0068, 刚好是寄存器 IOMUXC_SW_MUX_CTL_PAD_GPIO1_IO03 的地址。
  • conf_reg 寄存器偏移地址:值为 0x02F4。同理,0x020E0000 + 0x02F4 = 0x020E02F4, 刚好是寄存器 IOMUXC_SW_PAD_CTL_PAD_GPIO1_IO03 的地址。
  • input_reg 寄存器偏移地址:值为 0x0000 。有些外设没有 input_reg 寄存器,有 input_reg 寄存器的外设需要配置 input_reg 寄存器,没有的话,就不需要。当前IO 作为 GPIO1_IO03 时没有 input_reg 寄存器,因此这里 input_reg 是无效的。
  • mux_reg 寄存器的值 : 值为 0x05 。这里相当于设置 IOMUXC_SW_MUX_CTL_PAD_GPIO1_IO03 寄存器为 0x05 ,也就是设置 ALT5 — Select mux mode: ALT5 mux port: GPIO1_IO03 of instance: gpio1
  • input_reg 寄存器值: 值为0x00 。前面说到这里不需要 设置 input_reg 寄存器,所以这个值也是无效的。
  • conf_reg 寄存器的值: 值为0x10B0 。这里相当于给 IOMUXC_SW_PAD_CTL_PAD_GPIO1_IO03 寄存器赋值 0x10B0 。这里设置 一个 IO 的上/下 拉,驱动能力 和速度等。

四、如何在设备树配置 pin 信息

关于 I.MX 系列 SOC 的pinctrl 设备树绑定信息可以参考文档 fsl,imx-pinctrl.txt 。

1. 创建对应的节点

同一个外设的 PIN 都放到一个节点里面,打开 imx6ull-alientek-emmc.dts ,在 iomuxc 节点中的 “imx6ul-evk “ 子节点下添加 “pinctrl_led” 节点。

pinctrl_led:ledgrp{

		};

2. 添加 “fsl,pins” 属性

设备树是通过属性来保存信息的,因此我们需要添加一个属性,属性名字是一定要为 “fsl,pins” , 因为 对于 I.MX 系列 SOC 而已,pinctrl 驱动 程序 是通过读取 “ fsl,pins” 属性值来获取 PIN 的配置信息。

pinctrl_led:ledgrp{
			fsl,pins = <
			MX6UL_PAD_GPIO1_IO03__GPIO1_IO03  0x10B0
			>
		};

3. fsl,pins 属性值的确定

芯片厂家为 每个pin 的每一种复用都定义好了对应的宏,我们根据我们的复用要求,选择对应的宏就行。这个宏定义在 文件 imx6ul-pinfunc.h 文件中。

你可能感兴趣的:(Linux,读书笔记,linux,学习,驱动开发,pinctrl,子系统)