返回> 网站首页 

linux驱动 - gpio中断

yoours2022-10-30 19:33:25 阅读 1396

简介一边听听音乐,一边写写文章。

一、设备树 - GPIO定义

#gpio-cells = <6>;

ant_paen-gpios = <&pio   1   1   1   1   1  0>;

       |                               |    |   |   |   |   |  |--------------表示有效电平

       |                               |    |   |   |   |   |-----------------上下拉, 0关闭功能, 1上拉, 2下拉, 3保留

       |                               |    |   |   |   |---------------------驱动力,电流等级(0 - 3),级别越高,输出电流越大

       |                               |    |   |   |-------------------------gpio功能类型,0输入, 1输出, 6和外部中断,7关闭功能(具体查手册)

       |                               |    |   |-----------------------------pin bank 内偏移(即组内第几个io口).

       |                               |    |---------------------------------哪组gpio, PA(0),PB(1),PC(2),PD(3),PE(4),PF(5),PG(6),PH(7),PI(8),PJ(9),PK(10),PL(11)

       |                               |--------------------------------------指向哪个gpio控制器,  pio / r_pio(PL组)

       |---------------------------------------------属性名字(随便命名),以-gpios结尾


二、初始化

static irqreturn_t irq_hander(int irq, void *dev_id)

{

printk(KERN_ERR"irq_hander!\n");

return IRQ_HANDLED;

}


static int xxx_probe(struct spi_device *spi)

{

        // 设置普通输入输出gpio

struct gpio_desc* ant_paen = devm_gpiod_get(&spi->dev, "ant_paen", GPIOF_OUT_INIT_LOW);

if(IS_ERR(ant_paen)) 

printk(KERN_ERR"Get ant_paen resource failed!\n"); 

return -1; 

}


//gpiod_set_value(ant_paen, 0);//set down level

        // 获取中断的gpio

struct gpio_desc* RxInterrupt = devm_gpiod_get(&spi->dev,"RxInterrupt",GPIOF_OUT_INIT_LOW);

if(IS_ERR(RxInterrupt)) 

printk(KERN_ERR"Get RxInterrupt resource failed!\n"); 

return -1; 

}

        // 设置中断

int ret = devm_request_irq(&spi->dev, gpiod_to_irq(RxInterrupt), irq_hander, 0, "irq_hander", NULL);

if(ret)

{

printk(KERN_ERR"RxInterruptInit faild\n");

return ret;

}

}


三、GPIO常用api

1. 申请GPIO资源

struct gpio_desc *__must_check gpiod_get(struct device *dev, const char *con_id, enum gpiod_flags flags);

static inline struct gpio_desc *__must_check gpiod_get_index( struct device *dev, const char *con_id, unsigned int idx, enum gpiod_flags flags)

struct gpio_desc *__must_check devm_gpiod_get( struct device *dev, const char *con_id, enum gpiod_flags flags)

struct gpio_desc *__must_check devm_gpiod_get_index( struct device *dev, const char *con_id, unsigned int idx, enum gpiod_flags flags)

2.设置 GPIO 方向

int gpiod_direction_input(struct gpio_desc *desc)

int gpiod_direction_output(struct gpio_desc *desc, int value)

3.获取 设置 GPIO 输出电平

int gpiod_get_value(const struct gpio_desc *desc)

void gpiod_set_value(struct gpio_desc *desc, int value)

4.释放 GPIO 资源

void gpiod_put(struct gpio_desc *desc)

void devm_gpiod_put(struct device *dev, struct gpio_desc *desc)

5.GPIO 与中断信号线

int gpiod_to_irq(const struct gpio_desc *desc)


四、常用中断API

1. 中断注册

request_irq(unsigned int irq, irq_handler_t handler, unsigned long flags,const char *name, void *dev)

request_threaded_irq(unsigned int irq, irq_handler_t handler,irq_handler_t thread_fn,unsigned long flags, const char *name, void *dev);

中断标志flag:

IRQF_TRIGGER_NONE:无触发中断,指采用默认触发或者之前设置的方式

IRQF_TRIGGER_RISING:上升沿触发

IRQF_TRIGGER_FALLING:下降沿触发

IRQF_TRIGGER_HIGH:高电平触发

IRQF_TRIGGER_LOW:低电平触发

IRQF_TRIGGER_MASK:所有电平都可触发

IRQF_TRIGGER_PROBE:触发式检测中断

IRQF_SHARED:共享中断


devm_request_irq(struct device *dev, unsigned int irq, irq_handler_t handler,unsigned long irqflags, const char *devname, void *dev_id)

devm_request_threaded_irq(struct device *dev, unsigned int irq,irq_handler_t handler, irq_handler_t thread_fn,unsigned long irqflags, const char *devname,void *dev_id);

2. 中断释放

const void *free_irq(unsigned int, void *);

void devm_free_irq(struct device *dev, unsigned int irq, void *dev_id);

3.关闭和打开指定中断

void disable_irq(unsigned int irq);

void disable_irq_nosync(unsigned int irq);

void enable_irq(unsigned int irq);


微信小程序扫码登陆

文章评论

1396人参与,0条评论