您的位置:首页 > 其它

local_irq_disable与local_irq_enable

2015-09-23 14:39 806 查看
这两个函数可用于禁止与激活当前处理器(仅仅是当前处理器)上的所有本地中断(所有本地中断线上的中断),禁止本地CPU中断是确保一组内核语句被当作一个临界区处理的主要机制。这个机制的意义是:即使当硬件设备产生了一个IRQ信号时,中断禁止也让内核控制路径继续执行,因此,这就提供了一种有效的方式,确保内核控制路径中的一些中断处理程序能访问的数据结构也受到保护。然而,禁止本地中断并不保护运行在另一个CPU上的中断处理程序对该数据结构的并发访问,因此,在多处理器系统上,禁止本地中断经常与自旋锁结合使用。

这两个函数通常是以两个汇编指令来实现(当然,这依赖于体系结构),在i386架构中,local_irq_disable()仅仅是cli指令,local_irq_enable()只是sti指令,cli与sti分别是对clear与set中断标志的汇编调用,即他将禁止和激活中断的传递。cli将IF置0,屏蔽掉“可屏蔽中断”,sti将IF置1,允许“可屏蔽中断”,两者之间的代码就不会被外部中断打断。所以可以尽量保护代码连续执行。但是对于一些不允许屏蔽的中断以及异常,代码的运行还是会被中断。

/*i386*/
/**
* 禁止本地中断
*/
#define local_irq_disable() 	__asm__ __volatile__("cli": : :"memory")
/**
* 打开被关闭的中断
*/
#define local_irq_enable()	__asm__ __volatile__("sti": : :"memory")


上述代码是在C中嵌入的,__asm__表示汇编代码的开始,后面可以跟__volatile__,其与C中的volatile意义是一样的,这里作用是避免asm指令被删除,移动或组合。

如果一个内联汇编语句的Clobber/Modify域存在"memory",那么GCC会保证在此内联汇编之前,如果某个内存的内容被装入了寄存器,那么在这个内联汇编之后,如果需要使用这个内存处的内容,就会直接到这个内存处重新读取,而不是使用被存放 在寄存器中的拷贝。因为这个时候寄存器中的拷贝已经很可能和内存处的内容不一致了。
http://blog.csdn.net/stone_kingnet/article/details/2910832 http://www.cnblogs.com/fengyv/archive/2012/07/25/2608451.html
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: