linux内核--mb代码学习总结
来源:互联网 发布:软件测试工程师的前景 编辑:程序博客网 时间:2024/04/28 13:49
#define set_current_state(state_value) /
set_mb(current->state, (state_value))
#define set_mb(var, value) do { var = value; mb(); } while (0)
#define mb() __asm__ __volatile__ ("lock; addl $0,0(%%esp)" : : : "memory")
语句解释:
1.set_mb(),mb(),barrier()函数追踪到底,就是__asm__ __volatile__("lock; addl $0,0(%%esp)":::"memory"),而这行代码就是内存屏障。
2.__asm__:用于指示编译器在此插入汇编语句
3.volatile/__volatile__:基本可以做到两件事情:
(1).阻止编译器为了提高速度将一个变量缓存到寄存器内而不写回内存。
(2).阻止编译器调整操作volatile变量的指令顺序。
4.memory强制gcc编译器假设RAM所有内存单元均被汇编指令修改,这样cpu中的registers和cache中已缓存的内存单元中的数据将作废。cpu将不得不在需要的时候重新读取内存中的数据。这就阻止了cpu又将registers,cache中的数据用于去优化指令,而避免去访问内存。
5.lock前缀表示将后面这句汇编语句:"addl $0,0(%%esp)"作为cpu的一个内存屏障。
6.addl $0,0(%%esp)表示将数值0加到esp寄存器中,而该寄存器指向栈顶的内存单元。加上一个0,esp寄存器的数值依然不变。即这是一条无用的汇编指令。在此利用这条无价值的汇编指令来配合lock指令,在__asm__,__volatile__,memory的作用下,用作cpu的内存屏障。
个人思考:
volatile关键字来让编译器保证变量计算结果写回到内存之中,而没有用volatile关键字约束的变量的计算结果可能保存在寄存器之中,这种限制完全在我们的代码之中控制;语句中的memory强制gcc编译器假设RAM所有内存单元均被汇编指令修改,cpu将不得不在需要的时候重新读取内存中的数据。这两条关键字保证在多线程的环境下数据的一致性。
遗留问题:
void aaa()
{
int a = 1; //没有使用volatile,
a++; //a的计算结果保存在寄存器中的话
mb(); //寄存器失效
printf("%d/n", a); (问题:a等于几呢)
}
解决办法:
把汇编看看,然后编译,看看gcc编译处理的汇编代码。
- linux内核--mb代码学习总结
- Linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- 内核学习总结(Linux)
- Linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- Linux内核学习总结
- mysql 事务处理
- 工作感悟
- Oracle开发专题之:分析函数(OVER)1 【转】
- ORACLE常用数值函数、转换函数、字符串函数介绍
- CStringArray的排序问题
- linux内核--mb代码学习总结
- 遇到的js问题,已经解决但不大明白(清洁工大哥来给讲讲)
- oracle中实现mssql中的IDENTITY功能
- Agile Java读书笔记
- Google Maps API编程资源大全
- Qt-4.6动画Animation快速入门三字决
- TKIP和aes加密算法
- 如何成为编程高手
- Ext 可编辑表格批量提交