以下是一个典型的与GPIO关联的设备结构体 gpio_device
的设计示例,包含核心字段和操作抽象,适用于嵌入式系统开发:
#include <stdbool.h>
#include <stdint.h>
// GPIO方向枚举
typedef enum {
GPIO_DIR_IN, // 输入模式
GPIO_DIR_OUT // 输出模式
} gpio_direction;
// GPIO中断触发边沿枚举
typedef enum {
GPIO_EDGE_NONE, // 禁用中断
GPIO_EDGE_RISING, // 上升沿触发
GPIO_EDGE_FALLING, // 下降沿触发
GPIO_EDGE_BOTH // 双边沿触发
} gpio_edge;
// GPIO设备结构体
struct gpio_device {
unsigned int pin; // GPIO引脚编号(如0, 1, 2...)
gpio_direction direction; // 当前方向(输入/输出)
bool active_low; // 电平逻辑反相(true: 低电平有效)
gpio_edge edge; // 中断触发边沿配置
// 中断回调函数及参数
void (*irq_handler)(void *arg); // 中断触发时的回调函数
void *irq_arg; // 传递给回调函数的参数
// 硬件抽象层函数指针
int (*set_value)(struct gpio_device *dev, bool value); // 写GPIO电平
bool (*get_value)(struct gpio_device *dev); // 读GPIO电平
int (*set_direction)(struct gpio_device *dev, gpio_direction dir); // 设置方向
int (*enable_irq)(struct gpio_device *dev); // 启用中断
int (*disable_irq)(struct gpio_device *dev); // 禁用中断
// 平台私有数据(可选,用于存储寄存器地址等)
void *platform_data;
};
核心字段说明:
- 引脚配置
pin
: 物理引脚编号(如BCM编码的GPIO18)direction
: 输入/输出模式active_low
: 反转电平逻辑(如按钮按下时实际为低电平,但逻辑上视为高电平)
- 中断支持
edge
: 配置中断触发条件(上升沿、下降沿或双边沿)irq_handler
: 中断发生时调用的回调函数irq_arg
: 传递给回调函数的上下文参数
- 硬件抽象层(HAL)
set_value/get_value
: 读写GPIO电平的底层操作set_direction
: 切换GPIO方向enable_irq/disable_irq
: 中断使能控制
- 扩展性
platform_data
: 存储平台相关数据(如寄存器基地址),便于移植
使用示例:初始化一个LED设备
// 硬件相关函数实现(示例)
static int led_set_value(struct gpio_device *dev, bool value) {
// 实际硬件操作(如写入寄存器)
if (value) {
*(volatile uint32_t *)(dev->platform_data) |= (1 << dev->pin);
} else {
*(volatile uint32_t *)(dev->platform_data) &= ~(1 << dev->pin);
}
return 0;
}
// 初始化LED设备
void init_led(struct gpio_device *led) {
led->pin = 18; // GPIO18
led->direction = GPIO_DIR_OUT; // 输出模式
led->active_low = false; // 高电平点亮
led->set_value = led_set_value; // 绑定硬件操作函数
// 配置平台数据(假设寄存器基地址为0x40020000)
led->platform_data = (void *)0x40020000;
// 初始化为低电平(关闭LED)
led->set_value(led, false);
}
关键设计原则:
- 抽象与解耦
- 通过函数指针隔离硬件细节,使上层代码无需关心具体芯片型号。
- 可移植性
platform_data
字段允许存储芯片特定的寄存器地址或配置。
- 中断安全
- 回调函数
irq_handler
需设计为快速执行,避免阻塞中断。
- 回调函数
- 扩展性
- 可添加锁机制(如
spinlock
)或电源管理字段(如bool enabled
)。
- 可添加锁机制(如
此结构体可作为GPIO设备驱动的基础框架,适用于LED、按钮、传感器等多种外设。