1.内联汇编
# 内联汇编的语法
asm asm-qualifiers (AssemblerTemplate
:OutputOperands
[:InputOperands
[:Clobbers]])
int add(int a,int b)
{
int sum;
__asm__ volatile(
"add %0, %1, %2"
:"=r"(sum)
:"r"(a),"r"(b)
:"cc"
);
return sum;
}
ATPCS 的具体语法(https://baike.baidu.com/item/ATPCS/10695243?fr=aladdin)
- asm : 也可以写作 “asm”, 表示这是一段内联汇编
- asm-qualifiers 有 3 个取值:volatile、inline、goto。
volatile 的意思是易变的、不稳定的,用来告诉编译器不要随便优化这段代码,否则可能出问题。比
如汇编指令“mov r0, r0”,它把 r0 的值复制到 r0,并没有实际做什么事情,你的本意可能是用这条指令
来延时。编译器看到这指令后,可能就把它去掉了。加上 volatile 的话,编译器就不会擅自优化。- AssemblerTemplate
汇编指令,用双引号包含起来,每条指令用“\n”分开- OutputOperands
输出操作数,内联汇编执行时,输出的结果保存在哪里。
格式如下,当有多个变量时,用逗号隔开:
[ [asmSymbolicName] ] constraint (cvariablename)- InputOperands
输入操作数,内联汇编执行前,输入的数据保存在哪里。
格式如下,当有多个变量时,用逗号隔开:
[ [asmSymbolicName] ] constraint (cexpression)- Clobbers
在汇编代码中,对于“OutputOperands”所涉及的寄存器、内存,肯定是做了修改。但是汇编代码中,
也许要修改的寄存器、内存会更多。比如在计算过程中可能要用到 r3 保存临时结果,我们必须在“Clobbers”
中声明 r3 会被修改
Clobbers | 描述 |
---|---|
cc | 表示汇编代码会修改“flags register” |
memory | 表示汇编代码中,除了“InputOperands”和“OutputOperands”中指定的之外,还会会读、写更多的内存 |
2. atomic 实现
ATOMIC_OP 在 UP 系统中的实现,代码路径(arch\arm\include\asm\atomic.h)
对于 ARMv6 以下的 CPU 系统,不支持 SMP。原子变量的操作简单粗暴:关中断
ARMv6 及以上的 CPU,有一些特殊的汇编指令来实现原子操作,不再需要关中断
在 ARMv6 及以上的架构中,原子操作的执行过程是可以被打断的,但是它的效果符合“原子”的定义:
一个完整的“读、修改、写入”原子的,不会被别的程序打断。它的思路很简单:如果被别的程序打断了,
那就重来,最后总会成功的
3.原子变量对外的 API
类型定义 include\linux\types.h
函数名 | 作用 |
---|---|
atomic_read(v) | 读出原子变量的值,即 v->counter |
atomic_set(v,i) | 设置原子变量的值,即 v->counter = i |
atomic_inc(v) | v->counter++ |
atomic_dec(v) | v->counter-- |
atomic_add(i,v) | v->counter += i |
atomic_sub(i,v) | v->counter -= i |
atomic_inc_and_test(v) | 先加 1,再判断新值是否等于 0;等于 0 的话,返回值为 1 |
atomic_dec_and_test(v) | 先减 1,再判断新值是否等于 0;等于 0 的话,返回值为 1 |
使用方法
static atomic_t valid = ATOMIC_INIT(1);
static ssize_t gpio_key_drv_open (struct inode *node, struct file *file)
{
if (atomic_dec_and_test(&valid))
{
return 0;
}
atomic_inc(&valid);
return -EBUSY;
}
static int gpio_key_drv_close (struct inode *node, struct file *file)
{
atomic_inc(&valid);
return 0;
}
关于原子位操作
基本实现是和原子操作是一样的,只是操作的是一位,所有速度会快。