gpt4 book ai didi

c++ - 可以重新排序对 volatiles 的访问吗?

转载 作者:可可西里 更新时间:2023-11-01 16:16:09 24 4
gpt4 key购买 nike

考虑以下对 volatile 内存的写入序列,我从 David Chisnall's article at InformIT 中获取,“理解 C11 和 C++11 原子”:

volatile int a = 1;
volatile int b = 2;
a = 3;

我对 C++98 的理解是,根据 C++98 1.9,这些操作不能重新排序:

conforming implementations are required to emulate (only) the observable behavior of the abstract machine as explained below ... The observable behavior of the abstract machine is its sequence of reads and writes to volatile data and calls to library I/O functions

Chisnall 表示对顺序保留的约束仅适用于单个变量,并写道符合规范的实现可以生成执行此操作的代码:

a = 1;
a = 3;
b = 2;

或者这个:

b = 2;
a = 1;
a = 3;

C++11 重复了 C++98 的措辞

conforming implementations are required to emulate (only) the observable behavior of the abstract machine as explained below.

但是关于 volatile (1.9/8) 的说法是这样的:

Access to volatile objects are evaluated strictly according to the rules of the abstract machine.

1.9/12 表示访问 volatile 泛左值(包括变量 abc 以上)是一种副作用,1.9/14 规定一个完整表达式(例如,一条语句)中的副作用必须先于同一线程中后面的完整表达式的副作用。这使我得出结论,Chisnall 显示的两个重新排序是无效的,因为它们不符合抽象机规定的排序。

是我忽略了什么,还是 Chisnall 弄错了?

(请注意,这不是线程问题。问题是是否允许编译器在单个线程中重新排序对不同 volatile 变量的访问。)

最佳答案

IMO Chisnalls 的解释(由您提出)显然是错误的。更简单的情况是 C++98。 volatile 数据的读写顺序 需要保留,这适用于任何 volatile 数据的有序读写顺序,而不是单个变量。

如果您考虑使用 volatile 的最初动机:内存映射 I/O,这一点就变得显而易见了。在 mmio 中,您通常在不同的内存位置有几个相关的寄存器,并且 I/O 设备的协议(protocol)需要对其寄存器组进行特定的读取和写入序列 - 寄存器之间的顺序很重要。

C++11 的措辞避免谈论绝对的读取和写入序列,因为在多线程环境中,跨线程的此类事件没有一个明确定义的序列 - 而且如果这些访问转到独立的内存位置,这不是问题。但我相信其意图是,对于具有明确定义顺序的任何 volatile 数据访问序列,规则与 C++98 相同——必须保留顺序,无论在该序列中访问了多少不同的位置。

实现需要什么是一个完全独立的问题。如何(甚至如果)从程序外部观察到 volatile 数据访问,以及程序的访问顺序如何映射到外部可观察的事件是未指定的。一个实现可能应该给你一个合理的解释和合理的保证,但什么是合理的取决于上下文。

C++11 标准为非同步 volatile 访问之间的数据竞争留出了空间,因此不需要用完整的内存栅栏或类似结构来包围它们。如果内存的某些部分真正用作外部接口(interface) - 用于内存映射 I/O 或 DMA - 那么实现可以合理地为您保证对这些部分的 volatile 访问如何暴露给消费设备。

一个保证可能可以从标准中推断出来(参见 [into.execution]):volatile std::sigatomic_t 类型的值必须具有与写入它们的顺序兼容的值,即使在信号处理程序 - 至少在单线程程序中。

关于c++ - 可以重新排序对 volatiles 的访问吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14785639/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com