最新的kernel中的gpio的使用方法

4 篇文章 0 订阅
1 篇文章 0 订阅

最新的kernel中的gpio的使用方法

目录

1. 背景 1

2. 当前gpio在kernel的架构 2

3. 调试调用方法 3

4. 交叉编译方法 3

4.1 Linux下交叉编译 3

4.2 Android下面交叉编译 4

(1) 修改源码 4

(2) Android NDK下面进行交叉编译 4

(3) 放在Android源码中进行交叉编译 4

5. gpiotool 在android下面的使用 6

5.1 gpiodetect使用 6

5.2 gpioinfo使用 6

5.3 gpiofind使用 8

5.4 gpioget使用 8

5.5 gpioset使用 9

5.6 gpiomon使用 9

  1. 背景

最近在从4.x的内核移到5.4内核上的时候发现,原来的GPIO进行request所使用的GPIOF_EXPORT突然不能用了。上网上找发现,/sys/classs/gpio已经被最新的内核废弃了。

https://www.kernel.org/doc/Documentation/gpio/sysfs.txt

查阅相关的资料发现,这个改动是从2015年开始逐渐发从linux kernel 4.6到4.8 引入的。到了2020年,正式废弃。提交的代码记录如下:

kernel/git/torvalds/linux.git - Linux kernel source tree

但是虽然/sys/classs/gpio已经不能用了,但是还是可以通过打开CONFIG_GPIO_SYSFS,再加回来,

由于这个模块相对独立,当前使用还不会造成任何问题。但是不能确定主线内核到时候,会不会把这个也移除。

但是打开这个CONFIG_GPIO_SYSFS,也不能像以前一样看到GPIO的设备节点。

2. 当前gpiokernel的架构

当前的GPIO在内核中,会使能CONFIG_GPIOLIB, 会以一个chardev的方式出现. 这样对于所有注册的GPIO可以通过通用的通用的gpio访问的库libgpiod来对GPIO进行操作,操作的方法是通过IOCTL的接口来进行。而这个设备会在/dev下面,如:

/dev/gpiochip0
/dev/gpiochip1
/dev/gpiochip2

3. 调试调用方法

想要调用,可以通过libgpiod来进行。下载地址如下:

libgpiod/libgpiod.git - C library and tools for interacting with the linux GPIO character device

这个工具提供了调用库文件libgpiod,还提供了调试的工具,不过想要用到android上面,还需要进行交叉编译。

下载:

https://git.kernel.org/pub/scm/libs/libgpiod/libgpiod.git/snapshot/libgpiod-1.6.3.tar.gz

4. 交叉编译方法

编译前,ubuntu16.04下,需要安装libtool, autoconf

sudo apt install -y libtool autoconf

4.1  Linux下交叉编译

arm64的编译器可以使用linaro的,比如:gcc-linaro-7.3.1-2018.05-x86_64_aarch64-linux-gnu, 和在如下目录:

/opt/arm-gcc/gcc-linaro-7.3.1-2018.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-gcc

先配置环境变量:

export PATH=$PATH:/opt/arm-gcc/gcc-linaro-7.3.1-2018.05-x86_64_aarch64-linux-gnu/bin/

然后通过如下命令配置后,生成编译Makefile:

./autogen.sh --enable-tools=yes --host=armv8 CC=aarch64-linux-gnu-gcc --enable-static --prefix=/work/kernel/out

然后:

make
make install

4.2  Android下面交叉编译

(1). 修改源码

在Android下编译,有两个地方,需要修改size_t改成ssize_t, 第二个就是去掉program_invocation_name

这个是glibc提供的用法。android下面不改编译不过。

(2). Android NDK下面进行交叉编译

下载android 的最新的NDK

NDK 下载  |  Android NDK  |  Android Developers

在这里下载linux版本最新的NKD就可以。

https://dl.google.com/android/repository/android-ndk-r23c-linux.zip

解压后,打开终端,输入下面命令,加入到终端环境变量:

export PATH=$PATH:/work/Android/android-ndk-r23c/toolchains/llvm/prebuilt/linux-x86_64/bin

然后使用编译器:aarch64-linux-android24-clang 进行编译,进行配置如下:

./autogen.sh --enable-tools=yes --host=armv8 CC=aarch64-linux-android24-clang --with-sysroot=/work/Android/android-ndk-r23b/toolchains/llvm/prebuilt/linux-x86_64/sysroot --prefix=/work/kernel/out

然后输入:

make all install

编译完成后,会生成:

gpiodetect
gpiofind
gpioget
gpioinfo
gpiomon
gpioset

这个有一点类似于i2ctools.

(3). 放在Android源码中进行交叉编译

这个就需要书写Android.mk, 把tools, lib,及include下面的文件都入在一起。然后,lib的部分,可以编译成

一个静太库,或动态库。如果是动态库需要 push到android目录下面:

如果需要编成动态静态库,libgpiod的Android.mk如下:

LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES:= \
              core.c \
			  ctxless.c	\
			  misc.c	\
			  helpers.c	\
			  iter.c	

LOCAL_MODULE_TAGS := optional
LOCAL_MODULE := libgpiod
LOCAL_VENDOR_MODULE := true
include $(BUILD_SHARED_LIBRARY)

编译gpiod的工具的Android.mk如下:

LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES:= \
              gpiodetect.c \
			  tools-common.c	

LOCAL_MODULE_TAGS := optional
LOCAL_MODULE := gpiodetect
LOCAL_SHARED_LIBRARIES += libgpiod
LOCAL_MODULE_PATH := $(TARGET_OUT_VENDOR_EXECUTABLES)
include $(BUILD_EXECUTABLE)

如果需要编成静态库,libgpiod的Android.mk如下:

LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES:= \
              core.c \
			  ctxless.c	\
			  misc.c	\
			  helpers.c	\
			  iter.c	

LOCAL_MODULE_TAGS := optional
LOCAL_MODULE := libgpiod
LOCAL_VENDOR_MODULE := true
include $(BUILD_STATIC_LIBRARY)

编译gpiod的工具的Android.mk如下:

LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)
LOCAL_SRC_FILES:= \
              gpiodetect.c \
			  tools-common.c	

LOCAL_MODULE_TAGS := optional
LOCAL_MODULE := gpiodetect
LOCAL_STATIC_LIBRARIES += libgpiod
LOCAL_MODULE_PATH := $(TARGET_OUT_VENDOR_EXECUTABLES)
include $(BUILD_EXECUTABLE)

然后进入目前,使用mm编译就可以了。gpio tools有六个,除了gpiodetect,还有gpioget, gpiofind, gpioinfo, gpiomon, gpioset。也需要按gpiodetect一样增加mk的内容。编译成完会生成在/vendor/bin下面。

5. gpiotool android下面的使用

编译完成后,push进android系统的/vendor/bin下面。

5.1 gpiodetect使用

msmnile_au:/ # gpiodetect                                                                                                                     
gpiochip0 [3100000.pinctrl] (176 lines)
gpiochip1 [c440000.qcom,spmi:qcom,pm8150@0] (10 lines)
gpiochip2 [c440000.qcom,spmi:qcom,pm8150@4] (10 lines)

直接输入,就可以,可以列出当前的有几个gpio控制器,分别有几个GPIO.

5.2 gpioinfo使用

输入gpioinfo,可以看到所有的gpio的使用情况:

msmnile_au:/ # gpioinfo
gpiochip0 - 176 lines:
	line   0:      unnamed       unused   input  active-high 
	line   1:      unnamed       unused   input  active-high 
	line   2:      unnamed       unused   input  active-high 
	line   3:      unnamed       unused   input  active-high 
	line   4:      unnamed       unused   input  active-high 
	line   5:      unnamed       unused   input  active-high 
	line   6:      unnamed       unused   input  active-high 
	line   7:      unnamed       unused   input  active-high 
	line   8:      unnamed       unused   input  active-high 
	line   9:      unnamed       unused   input  active-high 
	line  10:      unnamed       unused   input  active-high 
	line  11:      unnamed "ssVreset-gpio" output active-high [used]
	line  12:      unnamed       unused   input  active-high 
	line  13:      unnamed  "interrupt"   input  active-high [used]
	line  14:      unnamed       unused   input  active-high 
	line  15:      unnamed       unused   input  active-high 
	line  16:      unnamed       unused   input  active-high 
	line  17:      unnamed "CCI_I2C_DATA0" input active-high [used]
	line  18:      unnamed "CCI_I2C_CLK0" input active-high [used]
	line  19:      unnamed "CCI_I2C_DATA1" input active-high [used]
	line  20:      unnamed "CCI_I2C_CLK1" input active-high [used]
	line  21:      unnamed "CAM_RESET0"  output  active-high [used]
	line  22:      unnamed       unused  output  active-high 
	line  23:      unnamed       unused  output  active-high 

第一列是gpio的编号,第二行,是一个叫line-name的东西,可以在dts里配置的时候通过gpio-line-names来进行指定,如:

&gpio1 {
       gpio-line-names = "red_led", "blue_led", "green_led";
};

这样通过gpioinfo查看的时候,会出现:

$ gpioinfo                                                                                                                                                                                                                            
gpiochip0 - 32 lines:                                                                                                                                                                                                                 
         line   0:    "red_led"       unused   input  active-high                                                                                                                                                                      
         line   1:   "blue_led"       unused   input  active-high                                                                                                                                                                      
         line   2:  "green_led"       unused   input  active-high                                                                                                                                                                      
         line   3:      unnamed  "interrupt"   input  active-high [used]                                                                                                                                                               
         line   4:      unnamed       unused  output  active-high                                                                                                                                                                      
         line   5:      unnamed     "status"  output  active-high [used]                                                                                                                                                               
         line   6:      unnamed       unused   input  active-high                                                                                                                                                                      
         line   7:      unnamed      "reset"   input  active-high [used]                                                                                                                                                               
         line   8:      unnamed       unused   input  active-high                                                                                                                                                                      
...   

不带命令是查看所有的,还可以指定控制器:

gpioinfo gpiochip0

或通过设备名:

gpioinfo 3100000.pinctrl

在高通平台上:

&tlmm {
    gpio-line-names = 
    "", 
    "", 
    "",
    "",
    "",
    "",
    "",
    "",
    "",
    "",
    "",
    "line12",
    "",
    "line14",
    "",
    "";
};

再通过gpioinfo查看,就可以看到:

5.3 gpiofind使用

这个工具是通过上面所说的gpio-line-names, 如果没有指定gpio-line-names的话,是无法查找的。如上面提到的例子:

gpiofind blue_led
gpiochip0 1
gpioset gpiochip0 1=1

如高通平台:

5.4 gpioget使用

用法如下:

msmnile_au:/ # gpioget gpiochip0 78                                                                                                           
0

5.5. gpioset使用
 

gpioset --mode=wait  gpiochip0 12=0

gpioset gpiochip0 1=1

5.6 . gpiomon使用

gpiomon --silent --num-events=1 gpiochip0 24 25 31

  • 1
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值