• 本文大部分来自于:http://witmax.cn/volatile.html

    我怕链接会失效,故转载此篇文章。。。

    volatile关键字是一种类型修饰符,用它声明的类型变量,编译器对访问该变量的代码就不再进行优化,从而可以提供对特殊地址的稳定访问。精确地说就是,优化器在用到这个变量时必须每次都小心地重新读取这个变量的值,而不是使用保存在寄存器里的备份。

    其中关键在于两个地方:     
     
    1. 编译器的优化

    在本次线程内, 当读取一个变量时,为提高存取速度,编译器优化时有时会先把变量读取到一个寄存器中;以后,再取变量值时,就直接从寄存器中取值;

    当变量值在本线程里改变时,会同时把变量的新值copy到该寄存器中,以便保持一致

    当变量在因别的线程等而改变了值,该寄存器的值不会相应改变,从而造成应用程序读取的值和实际的变量值不一致

    当该寄存器在因别的线程等而改变了值,原变量的值不会改变,从而造成应用程序读取的值和实际的变量值不一致

    2. 在什么情况下会用到

    • 并行设备的硬件寄存器(如:状态寄存器)
    • 一个中断服务子程序中会访问到的非自动变量(Non-automatic variables)
    • 多线程应用中被几个任务共享的变量

    再附一篇写得不错的介绍文章:

    用volatile关键字防止变量被编译器优化

    volatile 是在C、C++、Java等中语言中的一种修饰关键字。

    这个关键字在嵌入式系统中,是一个非常重要的一个使用。尽管在一般的Application中,可能很多人都不需要使用这个。但是在单片机中,如果不熟悉这个关键字,很有可能产生想像不到的意外。

    那么,我就来谈谈Volatile的意义--

    volatile在ANSI C(C89)以后的C标准规格和const一起被包含在内。在标准C中,这些关键字是必定存在的。

    关于volatile的意义,根据标准C的定义、volatile的目的是,避免进行默认的优化处理.比如说对于编译器优化的功能,如果从编译器看来,有些多余的代码的话,编译器就会启动优化程序,并删除一些代码,但是这在嵌入式系统中很有可能是关键性的处理,必须不能保证被编译器删掉,所以提供了Volitile来声明,告诉编译器无论如何都不要删掉我。

    volatile:易变的,不稳定的。。

    例子一:

    volatile a;(a是用volatile修饰后)
    a=1;
    a=2;
    a=3;
    a=4;
     volatile禁止编译器优化,编译后将产生4条代码。如果没用volatile修饰,编译器会优化上述代码,并认为只有最后1条是有效的,编译后将只产生1条代码,即最后一行。如果中间有其它代码,就不一定了。

    例子二:

    比如说下面条件的一段代码

    extern int event_flagvoid poll_event()
    {
    while (event_flag == 0) {/* 不操作event_flag */....
    }
    ....
    }

    我们不再循环中改变这里的event_flag的值,这样的话,event_flag 看起来就像是多余的,因此单片机编译器可能把此程序看为下段程序。

    void poll_event()
    {
    if (event_flag == 0) {while (1) {/* 不对event_flag操作 */....}
    }
    ....
    }
    • 对于一般的编译器,一般都会把程序优化成上述程序。这样的优化确实可以提高代码速度,比如while循环中不再需要对条件的判断,所以很快,但是这是正确的吗?

      对于单线程的程序,这是没有问题的,因为event_flag 就永远不会改变,但是对于多线程程序,RTOS的多任务处理的话,event_flag 的值可能被其他线程改变,这样问题就来了,因为被优化的代码并不具备对用event_flag 变化的能力。因此导致错误的意想不到的结果,如果此代码在ECU上执行的话,那我们的小命可就有可能没了。。。。

      为了避免这种情况,我们使用volatile关键字来防止程序被编译器优化。

volatile关键字的作用:防止变量被编译器优化相关推荐

  1. volatile关键字的作用、原理

    在只有双重检查锁,没有volatile的懒加载单例模式中,由于指令重排序的问题,我确实不会拿到两个不同的单例了,但我会拿到"半个"单例. 而发挥神奇作用的volatile,可以当之 ...

  2. [实验]-从汇编代码来看volatile关键字的作用

    ★★★ 个人博客导读首页-点击此处 ★★★ 环境aarch64的交叉编译器 我们将C语言翻译成汇编代码,来看volatile关键字的作用 我们先看一段C语言代码 void udelay(uint64_ ...

  3. 24.volatile关键字的作用、volatile原理、可见性、内存屏障、volatile性能、transient

    24.volatile关键字的作用 24.1.volatile原理 24.2.可见性 24.3.内存屏障 24.4.volatile性能 25.transient 24.volatile关键字的作用 ...

  4. 【说一千道一万】volatile关键字的作用和synchronized的关系

    [说一千道一万]volatile关键字的作用和synchronized的关系 volatile这个关键字在面试的时候通常会拿出来跟synchronized作比较,这也是比较基础的面试题目,这里自己总结 ...

  5. 一文搞懂Volatile关键字的作用

    前言 Volatile关键字的作用主要有如下两个: 1.线程的可见性:当一个线程修改一个共享变量时,另外一个线程能读到这个修改的值. 2. 顺序一致性:禁止指令重排序. 一.线程可见性 我们先通过一个 ...

  6. java volatile关键字的作用_java volatile关键字作用及使用场景详解

    1. volatile关键字的作用:保证了变量的可见性(visibility).被volatile关键字修饰的变量,如果值发生了变更,其他线程立马可见,避免出现脏读的现象.如以下代码片段,isShut ...

  7. 深入理解并发内存模型||JMM与内存屏障||多核并发缓存架构 ||JMM内存模型||volatile 关键字的作用 ||JMM 数据原子操作||JMM缓存不一致的问题

    深入理解并发内存模型||JMM与内存屏障 多核并发缓存架构 JMM内存模型 volatile 关键字的作用 JMM 数据原子操作 JMM缓存不一致的问题

  8. c语言中volatile关键字的作用

    读文章之前 可以先看一下<程序员的自我修养 >第28页 过度优化. volatile 提醒编译器它后面所定义的变量随时都有可能改变,因此编译后的程序每次需要存储或读取这个变量的时候,都会直 ...

  9. C语言volatile关键字的作用

    一.前言 1.编译器优化介绍: 由于内存访问速度远不及CPU处理速度,为提高机器整体性能,在硬件上引入硬件告诉缓存Cache,加速对内存的访问.另外在现代CPU中指令的执行并不一定严格按照顺序执行,没 ...

最新文章

  1. 《Apache Common CLI官方文档
  2. 数据库之存储引擎,数据类型-30
  3. Canvas动画基础之碰撞检测
  4. 点击按钮创建一个表格 点击按钮创建一个表格 权限选择 元素的value属性操作
  5. 《混合云计算》——2.2 结合服务创建混合云环境
  6. java 反向映射,如何使用lambdas實現反向映射Java?
  7. 通往大神之路,百度Java面试题前200页。
  8. python异常处理_Python入门 断言与异常处理
  9. SQL Cookbook—数字、日期
  10. C++_类和对象_对象特性_This指针的用途_用来解决名称冲突_*this实现链式编程---C++语言工作笔记049
  11. 自动化测试--实现一套完全解耦的简单测试框架(二)
  12. 微信朋友圈内容能删除吗?
  13. 和is哪个好_眼霜哪个牌子好用?这些品牌的眼霜睡前涂一涂,黑眼圈细纹没有了...
  14. idea 编译jar_Flink1.9.2源码编译和使用
  15. linux酷q运行不了,Linux上使用docker运行酷Q机器人
  16. PX4中四元数更新(毕卡求解法与一阶龙格库塔)
  17. ABO区块链在医疗行业中的重要作用
  18. 直播+迎来重磅炸弹,网易推出音乐+直播服务look直播,直播+是大趋势
  19. C# 利用正则表达式获取文本中的https网址并替换新的对应的值,微信小程序播放腾讯视频
  20. Python解二元一次方程,没想到如此简单

热门文章

  1. python etree库_python 标准库之xml.etree.ElementTree
  2. 8分钟答辩稿_8分钟的发言稿多少字
  3. 标准差,协方差与相关系数
  4. VMware Player 与 Device/Credential Guard 不兼容。在禁用 Device/Credential Guard 后,可以运行 VMware Player。
  5. 24届近3年合肥工业大学自动化考研院校分析
  6. 百家讲坛易中天的经典语录
  7. Kindle Clippings Export 2012-12
  8. 华为荣耀长按出现第三方信息及服务器,华为荣耀6手机常见问题要领.pdf
  9. idea验证失败_iphone x验证失败怎么办?苹果iphone x验证失败的解决方法
  10. Win8Codecs On Win8 X64