c++中的volatile语义讲解
来源:互联网 发布:淘宝自动上下架 编辑:程序博客网 时间:2024/06/10 02:11
作者是从volatile的产生讲起的,当时是为了统一的使用相同的地址处理内存地址和IO port地址,所谓memory-mapped I/O (MMIO)。
个人觉得本质都是不同层次存储映射关系吧,类比寄存器和内存。下面都用寄存器和内存解释。
- 读的情况
unsigned int *p = GetMagicAddress();
unsigned int a, b;
a = *p
b = *p;
考虑上面的代码,假设GetMagicAddress()是获得内存的地址,那么a = *p, b = *p,会被编译器认为是相同的操作,假设a = *p 使得值缓存在寄存器中,那么为了速度优化,编译器可能会将最后一行的代码换成
b = a;
这样就不去内存读而是直接去寄存器读但这可能并不是我们想要的,因为如果这期间其他的线程改写了内存中*P的内容呢?
thread1 thread2
a = *p;
*p = 3
b = a //---------- 编译器优化的结果使得我们读到的并不是最新的p所指的内存的值
- 写的情况
*p = a;
*p = b;
向上面的代码,编译器可能会认为*p = a是冗余操作从而去掉它,而这也可能不是我们想要的。
volatile的作用 :
volatile exists for specifying special treatment for such locations, specifically:
(1) the content of a volatile variable is “unstable” (can change by means unknown to the compiler),
(2) all writes to volatile data are “observable” so they must be executed religiously, and
(3) all operations on volatile data are executed in the sequence in which they appear in the source code.
- 被声明为volatile的变量其内容是不稳定的(unstable),它的值有可能由编译器所不能知晓的情况所改变。
- 所有对声明为volatile的变量的写操作都是可见的,必须严格执行be executed religiously。
- 所有对声明为volatile的变量的操作(读写)都必须严格按照源代码的顺序执行。
但是即使是JAVA能够跨越线程保证,仍然是不够的因为volatile和非volatile操作之间的顺序仍然是未定义的,有可能产生问题,考虑下面的代码:
volatile int vi;
void bar(void) {
vi = 1;
foo();
vi = 0;
}
我们一般会认为vi会在调用foo之前设置为1,调用完后会被置为0。然而编译器不会对你保证这一点,它会很高兴的将你的foo()移位,比如跑到vi = 1前面,只要它知道在foo()里不会涉及到其它的volatile操作。所以安全的方法是用栅栏memory barrier例如“asm volatile (”" ::: “memory”)加到foo的前面和后面 来保证严格的执行顺序。
Meyers提到由于上面的原因我们通常会需要加大量的volatile变量,java1.5中的volatile给出了更严格简单的定义,所有对volatile的读操作,都将被确保发生在该语句后面的读写(any memory reference volatile or not)操作的前面。而写操作则保证会发生在该语句前面的读写操作的后面。.NET也定义了跨线程的volatile语意。
- c++中的volatile语义讲解
- volatile语义
- volatile语义
- C语言 volatile 关键字讲解:
- c语言中的volatile
- c语言中的volatile
- C中的Volatile用法
- C中的volatile用法
- C中的volatile用法
- C中的volatile用法
- C中的volatile用法
- c中的volatile
- C语言中的volatile
- C中的volatile用法
- C中的volatile用法
- C中的volatile用法
- C中的volatile用法
- C中的volatile用法
- GROUP BY的用法
- iOS中图片拉伸的方法
- httpclient发送过程中的乱码解决
- 任务并行编程模型
- 简单工厂模式
- c++中的volatile语义讲解
- 【phpcms v9】 后台添加栏目过多,会导致后台操作巨缓慢
- Linux Wireless基础知识
- TortoiseSvn介绍(配置与管理)
- 关于IIS 7读取web.config大小的问题
- grep、sed、awk
- 计算机编码的相关知识(二)
- u-boot 中start.S
- http://hi.baidu.com/romashell