树莓派——libgpiod
这里写目录标题一、libgpiod 介绍(1)libgpiod(2)安装编译(3)命令行使用二、libgpiod – C API三、libgpiod – C API examples一、libgpiod 介绍(1)libgpiod 用于与 linux GPIO 字符设备交互的 C 库和工具 字符设备(gpiod 代表 GPIO 设备)从 linux 4.8 开始,不推荐使用 GPIO sysf
一、libgpiod – C library
(1)libgpiod
用于与 linux GPIO 字符设备交互的 C 库和工具
字符设备(gpiod 代表 GPIO 设备)
从 linux 4.8 开始,不推荐使用 GPIO sysfs 接口。用户空间应该使用
字符设备。这个库封装了 ioctl 调用和简单的 API 背后的数据结构。
其实还有另一个库Raspberry Pi,但是现在已经停止维护了,所以我们不再继续使用。
(2)安装编译
-
下载地址:
https://git.kernel.org/pub/scm/libs/libgpiod/libgpiod.git/about/ -
下载解压之后,我们首先确保安装依赖:
autoconf --version
- 配置编译安装
./autogen.sh
./configure
make
sudo make install
(3)命令行使用
目前有六个命令行工具可用:
-
gpiodetect - 列出系统上存在的所有 gpiochips,它们的名称,标和 GPIO 线数
-
gpioinfo - 列出指定 gpiochips 的所有行、它们的名称、消费者、方向、活动状态和附加标志
-
gpioget - 读取指定 GPIO 线的值
-
gpioset - 设置指定 GPIO 线的值,可能保留这些线导出并等待超时、用户输入或信号
-
gpiofind - 找到 gpiochip 名称和给定行名称的行偏移
-
gpiomon - 等待 GPIO 线上的事件,指定要观看的事件,退出前要处理多少事件或事件应该报告给控制台
例子:
# 获取帮助信息
$ gpio -h
# 获取BCM编号
$ gpio readall
# 读取单个 GPIO 线的值。
$ gpioget gpiochip1 23
0
# 同时读取两个值。设置线的活动状态
# 低。
$ gpioget --active-low gpiochip1 23 24
1 1
# 设置两行的值,然后守护进程并等待信号(SIGINT 或
# SIGTERM) 在释放它们之前。
$ gpioset --mode=signal --background gpiochip1 23=1 24=0
# 设置单行的值,然后立即退出。这很有用
# 用于浮动引脚。
$ gpioset gpiochip1 23=1
# 按名称查找 GPIO 行。
$ gpiofind "USR-LED-2"
GPIO芯片1 23
# 按名称切换 GPIO,然后等待用户按 ENTER。
$ gpioset --mode=wait `gpiofind "USR-LED-2"`=1
# 等待单个 GPIO 线上的三个上升沿事件,然后退出。
$ gpiomon --num-events=3 --rising-edge gpiochip2 3
事件:RISING EDGE 偏移量:3 时间戳:[1151.814356387]
事件:RISING EDGE 偏移量:3 时间戳:[1151.815449803]
事件:RISING EDGE 偏移量:3 时间戳:[1152.091556803]
# 等待单个下降沿事件。指定自定义输出格式。
$ gpiomon --format="%e %o %s %n" --falling-edge gpiochip1 4
0 4 1156 615459801
# 暂停执行,直到发生任何类型的单个事件。不打印
# 任何事物。按名称查找行。
$ gpiomon --num-events=1 --silent `gpiofind "USR-IN"`
# 监控多行,第一个事件后退出。
$ gpiomon --silent --num-events=1 gpiochip0 2 3 5
二、libgpiod – C API
用户API全部都在头文件(linux/gpio.h)中,逻辑上分为:
○ 芯片信息
○ 线路信息
○ 线路请求的值
○ 读取数值
○ 设置数值
○ 线路请求事件
○ 轮询事件
○ 读取事件
通过头文件查找相关API,请点击:
https://github.com/brgl/libgpiod/blob/master/include/gpiod.h
三、libgpiod – C API examples
- example 1(操作GPIO线路步骤)
struct gpiod_chip *chip; //定义chip结构体
struct gpiod_line *line; //定义line结构体
int rv, value;
chip = gpiod_chip_open("/dev/gpiochip0"); //访问芯片
if (!chip)
return -1;
line = gpiod_chip_get_line(chip, 3); //从芯片上申请GPIO线路
if (!line) {
gpiod_chip_close(chip);
return -1
}
rv = gpiod_line_request_input(line, “foobar”); //设置GPIO线路为输入或输出模式
if (rv) {
gpiod_chip_close(chip);
return -1; }
value = gpiod_line_get_value(line); //设置GPIO线路的值:高电平/低电平(1/0)
gpiod_chip_close(chip) //关闭芯片访问
- example 2 (事件轮询)
struct timespec ts = { 0, 1000000 };
struct gpiod_line_event event;
struct gpiod_chip *chip;
struct gpiod_line *line;
int rv, value;
chip = gpiod_chip_open("/dev/gpiochip0");
line = gpiod_chip_get_line(chip, 3);
gpiod_line_request_rising_edge_events(line, “foobar”);
do {
rv = gpiod_line_event_wait(line, &ts);
} while (rv <= 0);
rv = gpiod_line_event_read(line, &event);
if (!rv)
printf("event: %s timestamp: [%8ld.%09ld]\n",event.event_type,event.ts.tv_sec, event.ts.tv_nsec);
gpiod_chip_close(chip)
两个例程都是通过libgpiod提供的API操作GPIO线路,没有写成程序,为了更简洁的观察步骤
更多推荐
所有评论(0)