Why the “volatile” type class should not be used

Simulink模型变量如何精准“落户”?手把手教你用自定义Storage Class控制代码内存布局(以AUTOSAR为例) 本文详细介绍了如何在Simulink模型中通过自定义Storage Class精准控制变量内存布局,特别针对AUTOSAR标准进行优化。从工程价值到具体实现步骤,包括构建企业级Storage Class库、解决工程实践中的挑战,以及验证与调试方法论,帮助开发者高效管理嵌入式系统内存资源。 阅读详情

Why the “volatile” type class should not be used


C programmers have often taken volatile to mean that the variable could be changed outside of the current thread of execution; as a result, they are sometimes tempted to use it in kernel code when shared data structures are being used. In other words, they have been known to treat volatile types as a sort of easy atomic variable, which they are not. The use of volatile in kernel code is almost never correct; this document describes why.

The key point to understand with regard to volatile is that its purpose is to suppress optimization, which is almost never what one really wants to do. In the kernel, one must protect shared data structures against unwanted concurrent access, which is very much a different task. The process of protecting against unwanted concurrency will also avoid almost all optimization-related problems in a more efficient way.

Like volatile, the kernel primitives which make concurrent access to data safe (spinlocks, mutexes, memory barriers, etc.) are designed to prevent unwanted optimization. If they are being used properly, there will be no need to use volatile as well. If volatile is still necessary, there is almost certainly a bug in the code somewhere. In properly-written kernel code, volatile can only serve to slow things down.

Consider a typical block of kernel code:

spin_lock(&the_lock);
do_something_on(&shared_data);
do_something_else_with(&shared_data);
spin_unlock(&the_lock);

If all the code follows the locking rules, the value of shared_data cannot change unexpectedly while the_lock is held. Any other code which might want to play with that data will be waiting on the lock. The spinlock primitives act as memory barriers - they are explicitly written to do so - meaning that data accesses will not be optimized across them. So the compiler might think it knows what will be in shared_data, but the spin_lock() call, since it acts as a memory barrier, will force it to forget anything it knows. There will be no optimization problems with accesses to that data.

If shared_data were declared volatile, the locking would still be necessary. But the compiler would also be prevented from optimizing access to shared_data within the critical section, when we know that nobody else can be working with it. While the lock is held, shared_data is not volatile. When dealing with shared data, proper locking makes volatile unnecessary - and potentially harmful.

The volatile storage class was originally meant for memory-mapped I/O registers. Within the kernel, register accesses, too, should be protected by locks, but one also does not want the compiler “optimizing” register accesses within a critical section. But, within the kernel, I/O memory accesses are always done through accessor functions; accessing I/O memory directly through pointers is frowned upon and does not work on all architectures. Those accessors are written to prevent unwanted optimization, so, once again, volatile is unnecessary.

Another situation where one might be tempted to use volatile is when the processor is busy-waiting on the value of a variable. The right way to perform a busy wait is:

while (my_variable != what_i_want)
    cpu_relax();

The cpu_relax() call can lower CPU power consumption or yield to a hyperthreaded twin processor; it also happens to serve as a compiler barrier, so, once again, volatile is unnecessary. Of course, busy- waiting is generally an anti-social act to begin with.

There are still a few rare situations where volatile makes sense in the kernel:

The above-mentioned accessor functions might use volatile on architectures where direct I/O memory access does work. Essentially, each accessor call becomes a little critical section on its own and ensures that the access happens as expected by the programmer.
Inline assembly code which changes memory, but which has no other visible side effects, risks being deleted by GCC. Adding the volatile keyword to asm statements will prevent this removal.
The jiffies variable is special in that it can have a different value every time it is referenced, but it can be read without any special locking. So jiffies can be volatile, but the addition of other variables of this type is strongly frowned upon. Jiffies is considered to be a “stupid legacy” issue (Linus’s words) in this regard; fixing it would be more trouble than it is worth.

Pointers to data structures in coherent memory which might be modified by I/O devices can, sometimes, legitimately be volatile. A ring buffer used by a network adapter, where that adapter changes pointers to indicate which descriptors have been processed, is an example of this type of situation.

For most code, none of the above justifications for volatile apply. As a result, the use of volatile is likely to be seen as a bug and will bring additional scrutiny to the code. Developers who are tempted to use volatile should take a step back and think about what they are truly trying to accomplish.

深入解析volatile关键字:从内存模型到嵌入式实战应用 在计算机编程中,内存访问优化是编译器提升程序性能的核心手段之一,它通过分析代码的数据流和控制流,消除冗余计算和内存访问。然而,这种优化机制在面对特定场景时可能引发问题,例如硬件寄存器操作和异步信号处理。volatile关键字正是为了解决这类“内存访问不可预测性”问题而设计,它强制编译器不对指定变量的读写进行优化,确保每次访问都直接作用于内存。这一特性在嵌入式系统开发、设备驱动编程以及对实时性要求极高的领域具有重要技术价值,能够有效处理内存映射I/O、中断服务程序修改的全局变量等场景。通过理解volatile 阅读详情

相关推荐

ThinkPHP 8.1 + think-swoole 4.1 实战:5分钟搞定WebSocket聊天室(附完整代码)

本文详细介绍了如何使用ThinkPHP 8.1和think-swoole 4.1快速构建高并发WebSocket聊天室。通过5分钟实战教程,开发者可以轻松实现用户列表、消息广播等核心功能,支持2000+并发连接,适用于客服系统、在线协作等实时通信场景。

ol789012345的博客 126

线程安全(上)--彻底搞懂volatile关键字

对于volatile这个关键字,相信很多朋友都听说过,甚至使用过,这个关键字虽然字面上理解起来比较简单,但是要用好起来却不是一件容易的事。 这篇文章将从多个方面来讲解volatile,让你对它更加理解。 计算机中为什么会出现线程不安全的问题 volatile既然是与线程安全有关的问题,那我们先来了解一下计算机在处理数据的过程中为什么会出现线程不安全的问题。 大家都知道,计算机在执行程序时,每条指令...

weixin_34301132的博客 750

机器人抓取(一)—— ROS MoveIt! 程序控制真实UR5机器人运动(python)

接上篇:ubuntu18.04 ros-melodic 安装 ur_robot_driver,驱动真实的 ur5 机器人 上文在 ubuntu 系统中配置了ur 机器人ros功能包 universal_robot 和驱动 Universal_Robots_ROS_Driver,并实现了用 moveit_rviz 拖动机器人运动。本文旨在学习如何使用 moveit python 用户接口moveit_commander,实现真实的ur5 机器人轨迹规划与控制。 1. ur5 机器人控制 参考:MoveIt »

zxxRobot的博客 1万+

C++学习(一七零)类型安全type-safe 线程安全thread-safe

类型安全意味着编译器在编译的时候会验证类型,如果你尝试将一个错误的类型分配给一个变量时,会抛出一个错误。 一个函数被称为线程安全的(thread-safe),当且仅当被多个并发进程反复调用时,它会一直产生正确的结果。如果一个函数不是线程安全的,我们就说它是线程不安全的(thread-unsafe)。 ...

hankern的专栏 2311

开漏输出(漏极开路输出与集电极开路输出)和推挽输出怎么判断

判断一个引脚是还是。

weixin_56838517的博客 1055

QT+OSG/osgEarth编译之七十六:gltf+Qt编译(一套代码、一套框架,跨平台编译,版本:osgEarth-3.3插件库osgdb_gltf)

通过一套gltf代码和框架,实现osgdb_gltf跨平台编译。 在Qt环境下,集成头文件、库文件,构建跨平台编译的pro文件。 通过构建的一套配置工程,基于Qt Creator IDE,完成跨平台的编译实践。 在Windows、Linux、MacOS等操作系统上进行测试,成功编译,形成的成果(头文件、库文件等)可在不同系统下调用或使用,从而更好地构建跨平台解决方案。 采用的是osgEarth3.3版本。 读者可参考博客中的集成原理,构建不同版本的osgdb_gltf跨平台包。

LuckyHanMo的博客 1802

java高并发13——volatile关键字

The Java volatile keyword is used to mark a Java variable as “being stored in main memory”. More precisely that means, that every read of a volatile variable will be read from the computer’s main memo...

路人甲的路人乙的专栏 2090

20.Labview使用子vi进行VI间的数据传递详解(模块化)

子VI(模块化)题主在题注中也提到, 子VI的建立只是为了减少程序的负担,那么我们当使用子VI的时候首先就要明确什么是子VI?什么样的程序可以作为子VI?首先我们来看NI官方给的定义,具体说明如下图所示:题主已经将重点画出来了,在官方的解释中将子VI定义为了模块化,大家可以看到创建模块化子VI的特点在于减少代码重复工作优化了程序的框架结构。把一个代码打包,需要的时候就拎出来让他处理处理,不需要的时候就让它躺在我的列表里就行了也不占用运行空间。那么创建子VI需要需要注意以下几点:①任何一个程序。

关注我,更多技术问题欢迎私聊~ 3516

Thread Safety Using the Volatile Keyword

Thread Safety Using the Volatile Keyword As we all know, to write thread-safe code, we need to use locks. Besides this, we have another problem: what if the computer optimizes the code that accesses a

Robbie Mosaic's T-Log 1051

OCS2 入门教程(一)

OCS2 是专为切换系统优化控制(ptimalontrol forwitchedystems,OCS2)定制的 C++ 工具箱。该工具箱提供以下算法的高效实现:SLQ:连续时间域约束 DDPiLQR:离散时域约束 DDPSQP:基于 HPIPM 的多重打靶算法IPM: 基于非线性内点法的多重搜索算法SLP:基于 PIPG 的顺序线性规划算法OCS2 通过增强拉格朗日法(Augmented Lagrangian)或松弛障碍法(relaxed barrier methods)处理一般路径约束。

机器人控制与仿真应用 7837

嵌入式RTOS实战:uC/OS-III最新版移植指南(附项目源码)

本文提供uC/OS-III实时操作系统的完整移植指南,涵盖源码配置、工程搭建到任务调度的全流程。针对移植中的常见编译错误,给出关键修改方案(如中断重定义、配置使能等),附已验证的工程源码,通过LED任务实验验证稳定性,帮助开发者高效完成移植。适合嵌入式工程师及RTOS学习者参考。

Bit_Dong的博客 2472

彻底理解java语言的线程安全volatile用法

Java 语言中的 volatile 变量可以被看作是一种 “程度较轻的 synchronized”;与 synchronized 块相比,volatile 变量所需的编码较少,并且运行时开销也较少,但是它所能实现的功能也仅是 synchronized 的一部分。本文介绍了几种有效使用 volatile 变量的模式,并强调了几种不适合使用 volatile 变量的情形。锁提供了两种主要特性:互斥(

kwame211的博客 442

组基轨迹建模 GBTM的介绍与实现(Stata 或 R)

组基轨迹建模(Group-Based Trajectory Modeling,GBTM)(旧名称:Semiparametric mixture model)历史:由DANIELS.NAGIN提出,发表文献《Analyzing Developmental Trajectories:A Semiparametric,Group-Based Approach》GBTM能够将一群人的轨迹分类并生成数个具有代表性的运动轨迹模型,然后对每个轨迹模型进行分析,以了解人们的运动特征、生理水平和风险等级等。

三分钟热度 1万+

Why the "volatile" type class should not be used

------------------------------------------------ C programmers have often taken volatile to mean that the variable could be changed outside of the...

chuozhi7142的博客 308

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

计算机控制技术及应用

《计算机控制技术及应用》通过总结作者的科研成果和吸收国内外的先进理论、方法和技术,以计算机控制系统的网络化、开放化、智能化和集成化发展趋势为主线索,主要介绍计算机控制系统的基本概念和计算机控制系统的典型形式,计算机控制系统的数学描述与基本分析方法,以及数字PID控制器、最少拍控制系统、达林算法、状态变量设计法等设计方法及其各种改进算法。重点突出计算机控制系统输入输出通道接口的设计方法和典型控制系统的设计案例与实现方法等。

Java Volatile 变量的使用

<br />昨天有些闲暇时间,在网上看到了下面的文章。此文很简练,有助于对Volatile变量类型的理解。所以我翻译一下供那些对这种变量有兴趣的朋友们参考。另一方面,该文使用的例子得不到按该文说明的那样的结果,我看了一下,发现问题所在,本文最后会告诉你那个地方出了问题,而这一点也正是我们容易忽视的。<br /> <br />原文:<br /> Volatile keyword in Java<br />Author : Sutha<br />Date : Thu Feb 19th, 2009<br />To

hiroyuki的专栏 1462

visio安装包

Microsoft Office Visio 是一款专业的制图软件。利用经过更新的形状、协作工具和数据链接图表,创建专业级图表以简化复杂的信息。

结构体 volatile_「编译引擎」学习阅读Class文件结构(16进制版)-中

在《「编译引擎」学习阅读Class文件结构(16进制版)-上 》中,笔者讲解了如何以16进制的方式,解读Demo2.java对应字节码的常量池。我们继续解读Demo2.class字节码的属性表、方法表等重要的片段。1.对类的描述:访问标识JVM规范:The value of the access_flags item is a mask of flags used to denote access...

weixin_32349913的博客 281

霍尼韦尔SoftMaster使用说明

霍尼韦尔SoftMaster使用说明

【翻译十】volatile的含义

2019独角兽企业重金招聘Python工程师标准>>> ...

weixin_34099526的博客 189

C语言 static/volatile 关键字:嵌入式开发中 3 个易错场景与内存优化实战

本文深入探讨C语言中static和volatile关键字在嵌入式开发中的关键应用,通过3个典型场景分析易错陷阱与内存优化技巧。重点解析volatile在中断服务程序中的必要性,以及static在模块化编程中的内存管理优势,帮助开发者提升嵌入式系统稳定性和性能。

weixin_33720956的博客 419

JAVA多线程之volatile 与 synchronized 的比较

hapjin Technology is a powerful force in our society. Data, software,and communication can be used for bad: to entrench unfair power structures, to undermine human rights, and to protect vested i...

yizhizou123ABC的专栏 168

Kotlin 4. Kotlin 函数注解:Suppress,Volatile, Synchronized, Bindable, RequiresApi,SerializedName

这篇博客我们解释 Kotlin 函数注解:Suppress,Volatile, Synchronized, Bindable, RequiresApi,SerializedName 等。

破浪会有时的博客 1394

ClassFile之Fields

Each field is described by afield_infostructure. No two fields in oneclassfile may have the same name and descriptor (§4.3.2). The structure has the following format: field_info { u2 access_flags; u2 name_index; ...

kongkong的专栏 410

夯实Java基础系列9:深入理解Class类和Object类

目录 Java中Class类及用法 Class类原理 如何获得一个Class类对象 使用Class类的对象来生成目标类的实例 Object类 类构造器public Object(); registerNatives()方法; Clone()方法实现浅拷贝 getClass()方法 equals()方法 hashCode()方法; toString()方法 wait() notif...

weixin_30877181的博客 900

为什么你的Class II设备C代码总在Design Review阶段卡审?曝光FDA审查员内部核查清单TOP 6

揭秘Class II医疗设备C代码Design Review卡审根源,紧扣医疗设备C语言FDA认证编码规范,直击静态分析、可追溯性、MISRA合规等6大审查雷区。提供审查员内部核查清单与整改模板,助你一次过审。值得收藏

simcode的专栏 358

java线程相关知识点整理

1、创建新线程实例: Extends Thread类并重写run方法,创建这个类的实例即可; 或者创建一个类,实现Runnable接口,实现run方法,通过将这个类的实例传入Thread的构造器来创建一个Thread实例,这实例调用start方法时,这个实现类实现的run方法会在这个单独运行中的线程种被自动调用。 两种方法的比较:实现runnable接口更适合于if you are only...

AmyXia 403
上一篇: Bash常见的变量
下一篇: 内核第一阶段初始化
InvokerZhang
博客等级 码龄11年 9粉丝 24原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值