linux gpib 驱动
一:背景:
应项目需要gpib通信,因此需要添加gpib驱动,但从gpib linux 驱动以下链接说明中知道:GitHub - coolshou/linux-gpib: The Linux GPIB Package is a support package for GPIB (IEEE 488.2) hardware. The package contains a development environment consisting of a GPIB library written in C, kernel driver modules, and bindings for several other languages.
内核版本小于6.13,此gpib驱动只能将其单独编译成内科模块安装进文件系统中,大于等于6.13版本既可以在drivers/staging/下找到gpib驱动,需要内核配置和开启相关宏定义编译进内核即可。
从资料中知道,gpib驱动添加后,是需要在系统中开启服务并且在应用中需要使用到gpib-user包编译成静态库放进应用程序中调用的,链路如下:
内核模块配置(含 TNT4882)→ 设备树适配 → gpib.conf 配置(加载模块即生效,无需重启)→ 应用层链接静态库调用接口
“按内核版本选内核模块(≥6.13 用内核内置 staging 驱动,<6.13 用独立 kernel 包)+ 必装用户空间软件 + 配置 gpib.conf + 应用层链接库调用”
二:gpib drivers 编译:(博主采用低于6.13版本)
tar xzvf linux-gpib-kernel-4.3.7.tar.gz
cd linux-gpib-kernel-4.3.7# 2. 清理旧版本模块(官方强制要求,避免冲突)
sudo rm -rf /lib/modules/`uname -r`/gpib# 3. 编译安装
make -j$(nproc)
sudo make install 上述安装后,可以将生成的.ko模块,改为安装到buildroot模块目录
三:gpib -user 编译
# 1. 解压用户空间包
tar xzvf linux-gpib-user-4.3.7.tar.gz
cd linux-gpib-user-4.3.7# 2. 清理旧版本udev规则(官方重点提醒,避免冲突)
sudo rm -f /etc/udev/rules.d/98-gpib-generic.rules
sudo rm -f /etc/udev/rules.d/99-*gpib*.rules# 3. 配置编译(指定配置文件路径为/etc)
./configure --sysconfdir=/etc # 确保gpib.conf生成在/etc目录
make -j$(nproc)编译生成静态库和头文件
生成以下四个文件。libgpib.a,gpib_user.h,gpib_version.h,ib.h,分别放进应用程序的lib,include 目录即可。
四:系统gpib服务配置
此配置是为了支持gpib通信,并且描述了该gpib节点的相关通信信息:可以参考gpib-user里面的\util\templates\gpib.conf 并放进/etc/gpib.conf 。
/etc/gpib.conf
interface {minor = 0; # 对应/dev/gpib0board_type = "tnt4882"; # 板卡类型(必须与驱动匹配)base = 0x300; # I/O基地址(硬件实际地址,或动态分配)irq = 5; # 中断号(无需手动指定则留空)master = 1; # 作为GPIB主设备timeout = 10; # 超时10秒assert_ren = 1; # 配置为系统控制器时断言REN
}# 可选:预配置从设备(应用层也可动态设置)
device {minor = 0; # 绑定到上述接口pad = 1; # 从设备GPIB地址(0~30)sad = 31; # 次级地址(官方4.3.7支持31)timeout = 5;
}
可以尝试在系统起来后,手动加载
# 方法1:重新加载模块(自动读取gpib.conf)
sudo rmmod gpib_tnt4882 gpib_common
sudo modprobe gpib_common gpib_tnt4882# 方法2:用gpib_config工具手动加载配置(官方新增功能,无需改文件)
gpib_config -i 0 -b tnt4882 -m 1 # -i=minor号,-b=板卡类型,-m=主设备
五:应用程序调用
包含上述头文件。使用以下gpib api即可访问
int main() {int dev;char buf[1024] = {0};int ret;// 1. 打开GPIB设备(minor=0,从设备地址pad=1)dev = ibdev(0, 1, 31, 10, 1, 0); // ibdev(接口号, pad, sad, 超时, 自动状态, 初始化)if (dev < 0) {perror("ibdev failed");return -1;}ret = ibwrt(dev, "*IDN?", 5); // 发送5字节命令if (ret) {printf("ibwrt failed, error: %d\n", ret);ibonl(dev, 0);return -1;}// 3. 读取设备响应ret = ibrd(dev, buf, sizeof(buf)-1);if (ret) {printf("ibrd failed, error: %d\n", ret);ibonl(dev, 0);return -1;}printf("设备响应:%s\n", buf);// 5. 关闭设备ibonl(dev, 1); // 1=释放资源return 0;
}
六:使用》6.13版本,
需要格外添加两步。即设备树配置和内核宏定义配置,这里不展开,后续补充
