一、Pinctrl概述
许多soc内部都包含有pin控制器,通过pin控制器的寄存器,我们可以配置一个或者一组引脚的功能和特性。在软件方面,Linux内核提供了pinctrl子系统,目的是为了统一各soc厂商的pin脚管理。
Linux内核提供了pinctrl子系统,目的是为了统一各soc厂商的pin脚管理。
Linux Pinctrl子系统提供的功能:
➢(1) 管理系统中所有的可以控制的pin, 在系统初始化的时候,枚举所有可以控制的pin, 并标识这些pin。
➢(2) 管理这些pin的复用(Multiplexing) 。对于SOC而言,其引脚除了配置成普通的GPIO之外, 若干个引
脚还可以组成一-个pin group,行程特定的功能。pin control subsystem要管理所有的pin group。
➢(3)配置这些pin的特性。 例如使能或关闭引脚上的pul-up、 pull-down电阻, 配置引脚的driver strength。
在高通、MTK平台,上,pinmux管 脚复用控制器,是TLMM (Top-Level Mode Multiplexer)顶级模式多路复用控
制器。
二、Pinctrl的功能
关于pinctrl主要可以归结为两类设置,其中-类是功能选择,即一组gpio是用于iic还是uart还是就作为普通gpio来用,另一类是gpio的特性配置,即_ 上拉、下拉、 驱动能力和速率的配置。而pinctrl主要负责这两类配置的管理工作。总结起来pinctrl主要完成以下三种功能: .
1.引脚枚举与命名( Enumerating and naming )。
2.引脚复用(Multiplexing):比如用作GPIO、 I2C或其他功能。
3.引脚配置( Configuration): 比如上拉、下来、 open drain、 驱动强度等。
三、pinctrl的使用
1. 默认名称
Client device会通过pinctrl来将pin设置为相应的功能及配置。
2. 定制名称
3.默认名称解析
在pinctrl子系统的实现中,借助设备驱动模型中的driver_ probe_ device接口, 当device 与driver match
后,在driver probe_ device->really_ probe的接口中。在调用bus的probe接口之前, 通过调用
pinctrl bind pins接 口实现dev与pinctrl子系统的绑定,并完成pin相关的复用与配置操作。
int pinctrl_bind_pins(struct device *dev) { int ret; dev->pins = devm_kzalloc(dev, sizeof(*(dev->pins)), GFP_KERNEL); if (!dev->pins) return -ENOMEM; dev->pins->p = devm_pinctrl_get(dev); //获取pinctrl if (IS_ERR(dev->pins->p)) { dev_dbg(dev, "no pinctrl handle\n"); ret = PTR_ERR(dev->pins->p); goto cleanup_alloc; } dev->pins->default_state = pinctrl_lookup_state(dev->pins->p, //查找这个pin的default状态 PINCTRL_STATE_DEFAULT); if (IS_ERR(dev->pins->default_state)) { dev_dbg(dev, "no default pinctrl state\n"); ret = 0; goto cleanup_get; } ret = pinctrl_select_state(dev->pins->p, dev->pins->default_state); //设置pin的default状态 if (ret) { dev_dbg(dev, "failed to activate default pinctrl state\n"); goto cleanup_get; } return 0;