文章目录
- 前言
- [1. 头文件引入](#1. 头文件引入)
- [2. 导出GPIO引脚 export_gpio](#2. 导出GPIO引脚 export_gpio)
- [3. 设置GPIO方向 set_gpio_direction](#3. 设置GPIO方向 set_gpio_direction)
- [4. 设置GPIO值 set_gpio_value](#4. 设置GPIO值 set_gpio_value)
- [5. 初始化函数 gpio_init](#5. 初始化函数 gpio_init)
- 6.龙芯2K1000适配说明
-
- [6.1 GPIO编号映射](#6.1 GPIO编号映射)
- [6.2 性能优化建议](#6.2 性能优化建议)
- [6.3 权限问题](#6.3 权限问题)
- 6.4内存映射(高级优化)
- 6.5示例扩展:按键与LED控制
- 7.总结
前言
本文简单介绍了龙芯2k1000中的GPIO控制。
1. 头文件引入
c
#include <stdio.h> // 标准输入输出函数(如snprintf)
#include <stdlib.h> // 系统调用函数(如system)
#include <time.h> // 时间相关函数
#include <unistd.h> // POSIX操作系统API(如文件操作)
#include <fcntl.h> // 文件控制选项(如open的flags)
#include <sys/mman.h> // 内存映射相关函数
#include "GPIO.h" // 自定义GPIO相关声明(可能包含常量或宏)
作用
作用:引入必要的库和头文件 ,支持文件操作、字符串格式化等功能。
2. 导出GPIO引脚 export_gpio
c
void export_gpio(int gpio) {
char command[100];
snprintf(command, sizeof(command), "echo %d > /sys/class/gpio/export", gpio);
system(command);
}
功能
功能:通过写入/sys/class/gpio/export文件导出GPIO引脚。
示例
示例:echo 1 > /sys/class/gpio/export 导出GPIO1。
注意
若GPIO已导出,此操作会失败。
需添加错误检查(如检查文件是否存在)。
3. 设置GPIO方向 set_gpio_direction
c
void set_gpio_direction(int gpio, const char* direction) {
char command[100];
snprintf(command, sizeof(command), "echo \"%s\" > /sys/class/gpio/gpio%d/direction", direction, gpio);
system(command);
}
功能
功能:设置GPIO为输入("in")或输出("out")。
示例
示例:echo "out" > /sys/class/gpio/gpio1/direction 设置GPIO1为输出。
4. 设置GPIO值 set_gpio_value
c
void set_gpio_value(int gpio, int value) {
char command[100];
snprintf(command, sizeof(command), "echo \"%d\" > /sys/class/gpio/gpio%d/value", value, gpio);
system(command);
}
功能
功能:设置输出引脚的电平(0为低,1为高)。
示例
示例:echo 1 > /sys/class/gpio/gpio1/value 设置GPIO1为高电平。
5. 初始化函数 gpio_init
c
void gpio_init(int gpio, const char* direction, int value) {
export_gpio(gpio);
set_gpio_direction(gpio, direction);
set_gpio_value(gpio, value);
}
功能
功能:整合导出 、方向设置 和初始值设置的流程。
6.龙芯2K1000适配说明
6.1 GPIO编号映射
龙芯2K1000的GPIO可能按组(Bank)编号 ,需查阅手册确认物理引脚与逻辑编号的对应关系。
示例:GPIO1可能对应硬件引脚PZ.1,需参考《龙芯2K1000硬件手册》。
6.2 性能优化建议
c
直接文件操作代替system:
void export_gpio(int gpio) {
int fd = open("/sys/class/gpio/export", O_WRONLY);
if (fd < 0) { /* 错误处理 */ }
char buf[10];
snprintf(buf, sizeof(buf), "%d", gpio);
write(fd, buf, strlen(buf));
close(fd);
}
优点
优点:避免启动Shell进程,提升效率。
错误处理
错误处理:检查文件操作返回值 ,处理GPIO未导出或权限问题。
6.3 权限问题
操作/sys/class/gpio需要root权限。
解决方案
使用sudo 运行程序。
配置udev规则,允许普通用户访问GPIO设备。
6.4内存映射(高级优化)
对于高频操作(如PWM ),可通过内存映射直接操作GPIO寄存器:
c
volatile uint32_t *gpio_base;
int fd = open("/dev/mem", O_RDWR);
gpio_base = mmap(NULL, PAGE_SIZE, PROT_READ|PROT_WRITE, MAP_SHARED, fd, GPIO_BASE_ADDR);
// 直接读写寄存器:gpio_base[REG_OFFSET] |= (1 << PIN);
需查阅龙芯2K1000的GPIO寄存器基地址和偏移量。
6.5示例扩展:按键与LED控制
c
int main() {
// 初始化GPIO1(LED)为输出,初始关闭
gpio_init(1, "out", 0);
// 初始化GPIO2(按键)为输入
gpio_init(2, "in", 0);
while(1) {
// 读取按键状态(需实现read_gpio_value)
int key = read_gpio_value(2);
// 控制LED
set_gpio_value(1, key);
usleep(10000); // 10ms防抖
}
return 0;
}
7.总结
适用场景
适用场景:简单GPIO控制(如LED、继电器)。
优势
优势:代码简洁,依赖少,易于移植。
局限性
局限性:system调用效率低,缺少错误处理。
改进方向
改进方向:直接文件操作、内存映射寄存器、完善错误处理。