0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

Linux中pinctrl操作GPIO只需要几步

麦辣鸡腿堡 来源:嵌入式Linux系统开发 作者:Jasonangel 2023-09-27 17:24 次阅读

pinctrl 子系统 API

pinctrl 子系统的 API 有很多,对于驱动工程师来说,pinctrl 操作一个 GPIO 只需要三步:

1、devm_pinctrl_get
2、pinctrl_lookup_state
3、pinctrl_select_state

Linux 中,加 devm_ 开头的函数,代表这个函数支持资源管理。一般情况下,我们写一个驱动程序,在程序开头都会申请资源,比如内存、中断号等,万一后面哪一步申请出错,我们要回滚到第一步,去释放已经申请的资源,这样很麻烦。后来 Linux 开发出了很多 devm_ 开头的函数,代表这个函数有支持资源管理的版本,不管哪一步出错,只要错误退出,就会自动释放所申请的资源。

1)devm_pinctrl_get:用于获取设备树中自己用 pinctrl 建立的节点的句柄;

2) pinctrl_lookup_state:用于选择其中一个 pinctrl 的状态,同一个 pinctrl 可以有很多状态。比如 GPIO50 , 一开始初始化的时候是 I2C ,设备待机时候,我希望切换到普通 GPIO 模式,并且配置为下拉输入,省电 。这时候如果 pinctrl 节点有描述,我们就可以在代码中切换 pin 的功能,从 I2C 功能切换成普通 GPIO 功能;

3) pinctrl_select_stat:用于真正设置,在上一步获取到某个状态以后,这一步真正设置为这个状态。

对于 pinctrl 子系统的设备树配置,是遵守 service 和 client 结构

client 端各个平台基本都是一样的,server 端每个平台都不一样,使用的字符串的配置也不一样。

设备树配置:

//client端,设置不同状态
&test {
 pinctrl-names = "default","test_low","test_high";
 pinctrl-0 = < &test_default >;
 pinctrl-1 = < &test_low >;
 pinctrl-2 = < &test_high >;
 gpio = < &gpio5 1 GPIO_ACTIVE_LOW >;
 status = "okay";
};

//server 即 pin controller 端,设置 GPIO 几种功能状态
&gpio5 {
 test_default:test_default{};
  
 test_low:test_low{
  fsl,pins = <
   MX6UL_PAD_GPIO5_IO01__GPIO5_IO01 0x17059
  >
 };
  
 test_high:test_low{
  fsl,pins = <
   MX6UL_PAD_GPIO5_IO01__GPIO5_IO01 0x1b0b1
  >
 };
};

pinctrl.c

#include < linux/init.h >
#include < linux/kernel.h >
#include < linux/module.h >
#include < linux/platform_device.h >
#include < linux/delay.h >
#include < linux/pinctrl/pinctrl.h >
#include < linux/pinctrl/consumer.h >

static int __init mypinctrl_init(void)
{
 int ret = 0;
 struct pinctrl *pctrl;
 struct platform_device *pdev;
 struct pinctrl_state *test_high;
 struct pinctrl_state *test_low;
  
 pctrl = devm_pinctrl_get(&pdev- >dev);
 if(IS_ERR(pctrl)){
  ret = PTR_ERR(pctrl);
  printk("devm_pinctrl_get errorn");
  return ret;
 }
  
 test_high = pinctrl_lookup_state(pctrl,"test_high");
 if(IS_ERR(pctrl)){
  ret = PTR_ERR(test_high);
  printk("pinctrl_lookup_state test_high errorn");
  return ret;
 }
  
 test_low = pinctrl_lookup_state(pctrl,"test_low");
 if(IS_ERR(pctrl)){
  ret = PTR_ERR(test_low);
  printk("pinctrl_lookup_state test_low errorn");
  return ret;
 }
  
 pinctrl_select_state(pctrl,test_low);
 udelay(200);
 pinctrl_select_state(pctrl,test_high);
  
 return 0;
}

static void __exit mypinctrl_exit(void)
{
 printk("%sn",__func__);
}

module_init(mypinctrl_init);
module_exit(mypinctrl_exit);

MUDULE_LICENSE("GPL");

Makefile 与上面相同,只是更改一下编译输出的名字。

这个驱动加载上去,可以切换GPIO口的功能状态,我这里只是控制GPIO输出高低,具体看你设备树怎么配,比如你可以配置某个GPIO一开始是I2C功能,待机时候是普通GPIO功能,达到省电的目的。

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • Linux
    +关注

    关注

    87

    文章

    11304

    浏览量

    209467
  • API
    API
    +关注

    关注

    2

    文章

    1500

    浏览量

    62005
  • 子系统
    +关注

    关注

    0

    文章

    109

    浏览量

    12398
  • GPIO
    +关注

    关注

    16

    文章

    1204

    浏览量

    52090
收藏 人收藏

    评论

    相关推荐

    一文搞懂Linux pinctrl/gpio子系统

    注: 所有文章基于linux-3.13以上,本系列主要介绍 GPIO的一些基本知识,驱动操作GPIO的接口,应用层通过sysfs操作
    发表于 06-09 09:52 2717次阅读

    高通平台中gpio简单操作和调试

    //获取gpio寄存器的值二、在kernel代码操作gpio在代码中有两种方式操作gpio,一
    发表于 09-26 17:04

    「正点原子Linux连载」第四十五章 pinctrlgpio子系统实验(一)

    。在这里大家只需要知道,当设备和驱动匹配成功以后platform_driver的probe成员变量所代表的函数就会执行,在353行设置probe成员变量为imx6ul_pinctrl_probe函数
    发表于 03-19 14:58

    「正点原子Linux连载」第四十五章 pinctrlgpio子系统实验(二)

    1)实验平台:正点原子Linux开发板2)摘自《正点原子I.MX6U嵌入式Linux驱动开发指南》关注官方微信号公众号,获取更多资料:正点原子大家将imx35_gpio_hwdata
    发表于 03-19 14:59

    如何在嵌入式linux应用层操作gpio

    嵌入式linux文件io方式操作gpio口示例在嵌入式linux应用层操作
    发表于 12-16 06:19

    有什么方法让Linux在一块新的ARM SoC上运行呢

    共存,实现引脚的GPIO和其他功能之间的复用,各SoC只需要实现统一的gpio_chip结构体的成员函数即可;当前GPIO、时钟、pinmux等都能良好地进行设备树的映射处理,因此可方
    发表于 05-09 09:50

    RK3399开发板的pinctrlgpio子系统相关资料介绍

    ,驱动工程师只做驱动,应用工程师专注做应用。  linux下的pintcrl和gpio子系统就类似于ST的“BSP库”,但是linuxpinctrl
    发表于 09-16 17:27

    AD9162通过SPI进行寄存器配置时,只需要配置sequence的寄存器吗?

    对AD9162通过SPI进行寄存器配置时,只需要配置sequence的寄存器吗?sequence外的其它寄存器就不用管了? sequence中有对寄存器的读,这些读操作可以不进行吗? 谢谢。
    发表于 12-11 06:36

    linuxgpio复用设置操作步骤

    要向大家介绍下如何写一个python程序实现控制Arduino才能控制的I/O接口。上篇文章也说过,如果想使用python程序,必须使用SD卡Linux系统。那么如何在Linux
    发表于 11-15 11:34 7600次阅读
    <b class='flag-5'>linux</b><b class='flag-5'>中</b><b class='flag-5'>gpio</b>复用设置<b class='flag-5'>操作</b>步骤

    从TrueSTUDIO迁移STM32CubeIDE只需要简单几步

    从TrueSTUDIO迁移到STM32CubeIDE只需要简单几步
    的头像 发表于 02-28 16:33 3531次阅读

    Linux内核GPIO操作函数的详解分析

    本文档的主要内容详细介绍的是Linux内核GPIO操作函数的详解分析免费下载。
    发表于 01-22 16:58 28次下载

    gpiopinctrl子系统的关系与区别

    gpiopinctrl 子系统在内核里的使用率非常高,和嵌入式产品的关联非常大。从这两个子系统开始学习驱动开发是个不错的入门选择。
    的头像 发表于 03-15 11:40 4960次阅读

    使用pinctrlgpio子系统实现LED灯驱动

    前边已经学了两种点灯,本质依然还是通过配置寄存器;在学习STM32的时候除了学习配置一下寄存器,基本都是使用库来开发,那么在i.MX6ULL还使用寄存器开发明显是不太适合,那么i.MX6ULL有更方便的开发呢,这篇就来学习一下使用 pinctrlgpio 子系统来完
    的头像 发表于 04-03 10:17 1365次阅读

    RK3568pinctrlgpio 子系统详解

    如果 pinctrl 子系统将 PIN 复用为 GPIO,那么接下来就要配置 gpio 子系统,且 gpio 子系统依赖于 pinctrl
    的头像 发表于 12-20 10:22 2790次阅读
    RK3568<b class='flag-5'>pinctrl</b> 和 <b class='flag-5'>gpio</b> 子系统详解

    Linux平台来研究GPIO软件框架

    方法,让它可以像单片机一样简单的操作 IO 口,这得益于各路 Linux 大神对系统底层的封装。 在 Linux 中有 pinctrlgpio
    的头像 发表于 09-28 16:05 634次阅读
    从<b class='flag-5'>Linux</b>平台来研究<b class='flag-5'>GPIO</b>软件框架