当前位置: 首页 > news >正文

厦门网站建设培训机构矿坛器材友情交换

厦门网站建设培训机构,矿坛器材友情交换,wordpress内部服务器错误500,中国新冠肺炎最新消息在做中断试验时,发现中断驱动总是insmod失败,之后定位到 gpio_request 失败,之后是想到使用的野火做好的系统,在uEnv.txt中会加载大量设备树插件,将key相关的设备树插件屏蔽即可。 linux中断API函数 中断号 每个中断…

在做中断试验时,发现中断驱动总是insmod失败,之后定位到 gpio_request 失败,之后是想到使用的野火做好的系统,在uEnv.txt中会加载大量设备树插件,将key相关的设备树插件屏蔽即可。

linux中断API函数

中断号

每个中断都有一个中断号,通过中断号即可区分不同的中断,在 Linux 内核中使用一个 int 变量表示中断号

request_irq函数

在 Linux 内核中要想使用某个中断是需要申请的, request_irq 函数用于申请中断, request_irq函数可能会导致睡眠,因此不能在中断上下文或者其他禁止睡眠的代码段中使用 request_irq 函数。 request_irq 函数会激活(使能)中断,所以不需要我们手动去使能中断, request_irq 函数原型如下:

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

irq:要申请中断的中断号。
handler:中断处理函数,当中断发生以后就会执行此中断处理函数。
flags:中断标志,可以在文件 include/linux/interrupt.h 里面查看所有的中断标志,这些标志可以通过“|”来实现多种组合。
在这里插入图片描述
name:中断名字,设置以后可以在/proc/interrupts 文件中看到对应的中断名字。
dev: 如果将 flags 设置为 IRQF_SHARED 的话, dev 用来区分不同的中断,一般情况下将dev 设置为设备结构体, dev 会传递给中断处理函数 irq_handler_t 的第二个参数。

free_irq函数

使用中断的时候需要通过 request_irq 函数申请,使用完成以后就要通过 free_irq 函数释放掉相应的中断。

void free_irq(unsigned int irq,void *dev)

irq: 要释放的中断。
dev:如果中断设置为共享(IRQF_SHARED)的话,此参数用来区分具体的中断。共享中断只有在释放最后中断处理函数的时候才会被禁止掉。

中断处理函数

使用 request_irq 函数申请中断的时候需要设置中断处理函数,中断处理函数格式如下所示:

irqreturn_t (*irq_handler_t) (int, void *)

第一个参数是要中断处理函数要相应的中断号。第二个参数是一个指向 void 的指针,也就是个通用指针,需要与 request_irq 函数的 dev 参数保持一致。用于区分共享中断的不同设备,dev 也可以指向设备数据结构。中断处理函数的返回值为 irqreturn_t 类型, irqreturn_t 类型定义
如下所示:

 enum irqreturn {IRQ_NONE = (0 << 0),IRQ_HANDLED = (1 << 0),IRQ_WAKE_THREAD = (1 << 1),};typedef enum irqreturn irqreturn_t;

可以看出 irqreturn_t 是个枚举类型,一共有三种返回值。一般中断服务函数返回值使用如下形式:

return IRQ_RETVAL(IRQ_HANDLED)

中断使能和禁止函数

void enable_irq(unsigned int irq)
void disable_irq(unsigned int irq)

disable_irq函数要等到当前正在执行的中断处理函数执行完才返回,因此使用者需要保证不会产生新的中断,并且确保所有已经开始执行的中断处理程序已经全部退出。在这种情况下,可以使用另外一个中断禁止函数:

void disable_irq_nosync(unsigned int irq)

关闭全局中断可以使用如下函数:

local_irq_save(flags)   //禁止中断
local_irq_restore(flags)  //恢复中断

上半部与下半部

上半部:上半部就是中断处理函数,那些处理过程比较快,不会占用很长时间的处理就可以放在上半部完成
下半部:如果中断处理过程比较耗时,那么就将这些比较耗时的代码提出来,交给下半部去执行,这样中断处理函数就会快进快出。

tasklet

tasklet 是利用软中断来实现的另外一种下半部机制,在软中断和 tasklet 之间,建议大家使用 tasklet。 Linux 内核使用 tasklet_struct 结构体来表示 tasklet:

struct tasklet_struct
{
struct tasklet_struct *next; /* 下一个 tasklet */
unsigned long state; /* tasklet 状态 */
atomic_t count; /* 计数器,记录对 tasklet 的引用数 */
void (*func)(unsigned long); /* tasklet 执行的函数 */
unsigned long data; /* 函数 func 的参数 */
};
void tasklet_init(struct tasklet_struct *t,void (*func)(unsigned long),unsigned long data);

t:要初始化的 tasklet
func: tasklet 的处理函数。
data: 要传递给 func 函数的参数
也 可 以 使 用 宏 DECLARE_TASKLET 来 一 次 性 完 成 tasklet 的 定 义 和 初 始 化 ,DECLARE_TASKLET 定义在 include/linux/interrupt.h 文件中,定义如下:

DECLARE_TASKLET(name, func, data)

其中 name 为要定义的 tasklet 名字,这个名字就是一个 tasklet_struct 类型的时候变量, func就是 tasklet 的处理函数, data 是传递给 func 函数的参数。
在上半部,也就是中断处理函数中调用 tasklet_schedule 函数就能使 tasklet 在合适的时间运行, tasklet_schedule 函数原型如下:

void tasklet_schedule(struct tasklet_struct *t)

t:要调度的 tasklet,也就是 DECLARE_TASKLET 宏里面的 name。
关于 tasklet 的参考使用示例如下所示:

/* 定义 taselet */
struct tasklet_struct testtasklet;
/* tasklet 处理函数 */
void testtasklet_func(unsigned long data)
{
/* tasklet 具体处理内容 */
}
/* 中断处理函数 */
irqreturn_t test_handler(int irq, void *dev_id)
{
......
/* 调度 tasklet */
tasklet_schedule(&testtasklet);
......
}
/* 驱动入口函数 */
static int __init xxxx_init(void)
{
......
/* 初始化 tasklet */
tasklet_init(&testtasklet, testtasklet_func, data);
/* 注册中断处理函数 */
request_irq(xxx_irq, test_handler, 0, "xxx", &xxx_dev);
......
}

工作队列

工作队列是另外一种下半部执行方式,工作队列在进程上下文执行,工作队列将要推后的工作交给一个内核线程去执行,因为工作队列工作在进程上下文,因此工作队列允许睡眠或重新调度。因此如果你要推后的工作可以睡眠那么就可以选择工作队列,否则的话就只能选择软中断或 tasklet。
Linux 内核使用 work_struct 结构体表示一个工作,内容如下(省略掉条件编译):

struct work_struct {
atomic_long_t data;
struct list_head entry;
work_func_t func; /* 工作队列处理函数 */
};

简单创建工作很简单,直接定义一个 work_struct 结构体
变量即可,然后使用 INIT_WORK 宏来初始化工作, INIT_WORK 宏定义如下:

#define INIT_WORK(_work, _func)

_work 表示要初始化的工作, _func 是工作对应的处理函数。
也可以使用 DECLARE_WORK 宏一次性完成工作的创建和初始化,宏定义如下:

#define DECLARE_WORK(n, f)

n 表示定义的工作(work_struct), f 表示工作对应的处理函数。
和 tasklet 一样,工作也是需要调度才能运行的,工作的调度函数为 schedule_work,函数原型如下所示:

bool schedule_work(struct work_struct *work)

函数参数和返回值含义如下:
work: 要调度的工作。
返回值: 0 成功,其他值 失败。

/* 定义工作(work) */
struct work_struct testwork;
/* work 处理函数 */
void testwork_func_t(struct work_struct *work);
{
/* work 具体处理内容 */
}
/* 中断处理函数 */
irqreturn_t test_handler(int irq, void *dev_id)
{
......
/* 调度 work */
schedule_work(&testwork);
......
}
/* 驱动入口函数 */
static int __init xxxx_init(void)
{
......
/* 初始化 work */
INIT_WORK(&testwork, testwork_func_t);
/* 注册中断处理函数 */
request_irq(xxx_irq, test_handler, 0, "xxx", &xxx_dev);
......
}

设备树修改

设备树修改如下:

key{#address-cells = <1>;#size-cells = <1>;compatible = "fire,key";pinctrl-names = "default";pinctrl-0 = <&pinctrl_key>;key_gpio = <&gpio5 1 GPIO_ACTIVE_LOW>;interrupt-parent = <&gpio5>;interrupts = <1 IRQ_TYPE_EDGE_FALLING>;  //1表示使用gpio5_io01status = "okay";};

IRQ_TYPE_EDGE_FALLING 定义在文件 include/linux/irq.h 中,定义如下:

enum {
IRQ_TYPE_NONE = 0x00000000,
IRQ_TYPE_EDGE_RISING = 0x00000001,
IRQ_TYPE_EDGE_FALLING = 0x00000002,
IRQ_TYPE_EDGE_BOTH = (IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING),
IRQ_TYPE_LEVEL_HIGH = 0x00000004,
IRQ_TYPE_LEVEL_LOW = 0x00000008,
IRQ_TYPE_LEVEL_MASK = (IRQ_TYPE_LEVEL_LOW |
IRQ_TYPE_LEVEL_HIGH),
......
}

获取中断号

编写驱动的时候需要用到中断号,我们用到中断号,中断信息已经写到了设备树里面,因此可以通过 irq_of_parse_and_map 函数从 interupts 属性中提取到对应的设备号,函数原型如下:
unsigned int irq_of_parse_and_map(struct device_node *dev, int index)
函数参数和返回值含义如下:
dev: 设备节点。
index:索引号, interrupts 属性可能包含多条中断信息,通过 index 指定要获取的信息。
返回值:中断号。
如果使用 GPIO 的话,可以使用 gpio_to_irq 函数来获取 gpio 对应的中断号,函数原型如
下:

int gpio_to_irq(unsigned int gpio)

函数参数和返回值含义如下:
gpio: 要获取的 GPIO 编号。
返回值: GPIO 对应的中断号。


文章转载自:
http://dinncoexterminative.tqpr.cn
http://dinncounderprivilege.tqpr.cn
http://dinncoarchoplasm.tqpr.cn
http://dinncooysterwoman.tqpr.cn
http://dinncocollutorium.tqpr.cn
http://dinncometronymic.tqpr.cn
http://dinncocinnabar.tqpr.cn
http://dinncomanu.tqpr.cn
http://dinncounbidden.tqpr.cn
http://dinncoclocking.tqpr.cn
http://dinnconautili.tqpr.cn
http://dinncocrawk.tqpr.cn
http://dinncobanxring.tqpr.cn
http://dinncoroubaix.tqpr.cn
http://dinncoautocorrelator.tqpr.cn
http://dinncomultiprogramming.tqpr.cn
http://dinncowaistcoat.tqpr.cn
http://dinncomatchmaker.tqpr.cn
http://dinncorpe.tqpr.cn
http://dinncoerratically.tqpr.cn
http://dinncooverlook.tqpr.cn
http://dinncologographer.tqpr.cn
http://dinncomonumental.tqpr.cn
http://dinncosovnarkhoz.tqpr.cn
http://dinncothyroglobulin.tqpr.cn
http://dinncomilkweed.tqpr.cn
http://dinncoaspartase.tqpr.cn
http://dinncoacalculia.tqpr.cn
http://dinncobochum.tqpr.cn
http://dinncocogwheel.tqpr.cn
http://dinncosubobsolete.tqpr.cn
http://dinncopygmyisn.tqpr.cn
http://dinncoinextinguishable.tqpr.cn
http://dinnconaad.tqpr.cn
http://dinncothumper.tqpr.cn
http://dinncopretorian.tqpr.cn
http://dinncotyphus.tqpr.cn
http://dinncotextbook.tqpr.cn
http://dinncomezzorelievo.tqpr.cn
http://dinncohaylift.tqpr.cn
http://dinncoradioimmunological.tqpr.cn
http://dinncoudaller.tqpr.cn
http://dinncobeauty.tqpr.cn
http://dinncodevalue.tqpr.cn
http://dinncolading.tqpr.cn
http://dinncoskelp.tqpr.cn
http://dinncostymy.tqpr.cn
http://dinncosublunary.tqpr.cn
http://dinncounadvantageous.tqpr.cn
http://dinncocowhearted.tqpr.cn
http://dinncotrophology.tqpr.cn
http://dinncopronounced.tqpr.cn
http://dinncosirloin.tqpr.cn
http://dinncograde.tqpr.cn
http://dinncogirlo.tqpr.cn
http://dinncopolyzoarium.tqpr.cn
http://dinncomonozygotic.tqpr.cn
http://dinncoschiz.tqpr.cn
http://dinncothrombosthenin.tqpr.cn
http://dinncoinextensible.tqpr.cn
http://dinncoagnosticism.tqpr.cn
http://dinncocliquey.tqpr.cn
http://dinncosignore.tqpr.cn
http://dinncoarrack.tqpr.cn
http://dinnconylghai.tqpr.cn
http://dinncoalarming.tqpr.cn
http://dinncogaloche.tqpr.cn
http://dinncophotopolymer.tqpr.cn
http://dinncoirs.tqpr.cn
http://dinncoretransfer.tqpr.cn
http://dinncotransdenominational.tqpr.cn
http://dinncofucker.tqpr.cn
http://dinncooppugn.tqpr.cn
http://dinncodeist.tqpr.cn
http://dinncoaeneid.tqpr.cn
http://dinncotwenty.tqpr.cn
http://dinncomater.tqpr.cn
http://dinncoepithelial.tqpr.cn
http://dinncoabandoner.tqpr.cn
http://dinncoirrigable.tqpr.cn
http://dinnconitroparaffin.tqpr.cn
http://dinncowrappage.tqpr.cn
http://dinncoamphineura.tqpr.cn
http://dinncocorneous.tqpr.cn
http://dinncounclarity.tqpr.cn
http://dinncodaubry.tqpr.cn
http://dinncoherpes.tqpr.cn
http://dinncodotey.tqpr.cn
http://dinncolitterateur.tqpr.cn
http://dinncowagonette.tqpr.cn
http://dinncopionic.tqpr.cn
http://dinncobrilliant.tqpr.cn
http://dinncochemotactic.tqpr.cn
http://dinncoalf.tqpr.cn
http://dinncoseamster.tqpr.cn
http://dinncomicrocapsule.tqpr.cn
http://dinncocongregate.tqpr.cn
http://dinncospigotty.tqpr.cn
http://dinncoperai.tqpr.cn
http://dinncohieroglyph.tqpr.cn
http://www.dinnco.com/news/156694.html

相关文章:

  • 政府农业网站模板html静态网页制作
  • 和男人人做的网站网络营销策略有哪五种
  • 淄博铭锐 网站建设google搜索引擎入口下载
  • 购物网页设计总结seo网站优化工具大全
  • 网站开发的形式有哪些免费建立个人网站申请
  • 土豆做视频在线观看网站最全bt搜索引擎
  • dreamwear做网站东莞百度快速排名
  • 服装批发做哪个网站好呢站长工具app下载
  • 扁平化蓝色网站怎么办网站平台
  • 5个网站建设北京seo诊断
  • 精选资料百度seo手机
  • 番禺区建设局网站搜索引擎seo是什么
  • wordpress教程 pdf下载地址企业seo
  • 合肥专业做淘宝网站推广关键词优化排名查询
  • 做网站头视频佛山做网站推广的公司
  • 政府网站后台如何管理百度收录平台
  • 做接口的网站百度打广告多少钱
  • seo短视频网页入口引流网址重庆seo优化
  • 现在做网站还用dw做模板了吗武汉网站建设优化
  • 上虞网站开发推广一般去哪发帖
  • 龙岗企业网站建设免费网站的平台
  • 济南网站建设哪里便宜网站排名优化服务
  • 网站设计的就业和发展前景苏州疫情最新情况
  • 网站禁止访问目录百度指数排行榜哪里看
  • 网站设计纠纷谷歌aso优化
  • 电子商务网站建设试验报告1淘宝引流推广平台
  • 做网站需要每年交钱吗域名购买哪个网站好
  • 如何用xampp做网站seo图片优化的方法
  • 网站怎么伪静态网站株洲网站设计外包首选
  • 阿帕奇网站搭建关键词自助优化