跳转到内容

Ada 编程/编译指示/原子:3

来自维基教科书,自由的教科书

几乎总是错误地使用 原子易变 变量来进行 任务[1] 当一个对象是原子性的,它仅仅意味着它将被原子性地读入或写入内存。编译器不会在访问该对象时生成原子指令或内存屏障,它只会

  • 检查架构是否保证原子内存加载和存储,
  • 不允许一些编译器优化,比如重新排序或抑制对对象的冗余访问。

例如,下面的代码,其中A是一个原子对象,可能会被误解

A := A + 1;  -- Not an atomic increment!

编译器不会(并且根据标准也不允许)生成原子增量指令来直接增量并从内存中更新变量A[2] 这是编译器生成的代码

  A := A + 1;
804969f:	a1 04 95 05 08       	mov    0x8059504,%eax
80496a4:	40                   	inc    %eax
80496a5:	a3 04 95 05 08       	mov    %eax,0x8059504

如您所见,不会生成任何原子增量指令或测试并设置操作码。与其他编程语言一样,如果程序中需要这些特定指令,则必须使用机器代码插入显式地编写它们。[3]

上面的代码片段等效于以下代码(两个代码序列生成完全相同的目标代码),其中T是一个(非原子)临时变量

T := A;      -- A is copied atomically to local variable T
T := T + 1;  -- local variable T is incremented
A := T;      -- A is stored atomically

因此,从多个任务同时修改原子变量是不正确的。例如,两个任务并行地增量一个计数器。即使在单处理器中,也应该使用其他 Ada 任务功能,例如受保护的对象。在多处理器中,根据内存一致性模型,使用各种原子或易变变量进行任务通信会导致意想不到的后果。[2][4] 因此,在使用原子对象进行任务数据共享或同步时,尤其是在多处理器中,应格外小心。


参考文献

[编辑 | 编辑源代码]
  1. Arch Robison (2007-11-30). "Volatile: Almost Useless for Multi-Threaded Programming". Intel 软件网络. Retrieved 2008-05-30. There is a widespread notion that the keyword volatile is good for multi-threaded programming (...) volatile is almost useless for multi-threaded programming.
  2. a b Ian Lance Taylor (2008-03-05). "Volatile". Retrieved 2008-05-28. Using [the C/C++ qualifier] volatile does not mean that the variable is accessed atomically; no locks are used. Using volatile does not mean that other cores in a multi-core system will see the memory accesses; no cache flushes are used. (...) Using volatile does not imply any sort of memory barrier; the processor can and will rearrange volatile memory accesses. (...) You should not use more than one such variable to communicate between any pair of threads, as there is no guarantee that the different threads will see the accesses in the same order.
  3. Laurent Guerby (1995). "C.5 Shared Variable Control". Ada 95 Rationale. Intermetrics. A need to access specific machine instructions arises sometimes (...). Examples include instructions that perform compound operations atomically on shared memory, such as test-and-set and compare-and-swap (...) {{cite book}}: |access-date= requires |url= (help); External link in |chapter= (help); Unknown parameter |month= ignored (help)
  4. Sarita V. Adve, Kourosh Gharachorloo (1996). "Shared Memory Consistency Models: A Tutorial" (PDF). IEEE Computer. 29 (12): 66–76. Retrieved 2008-05-28. {{cite journal}}: Unknown parameter |month= ignored (help)
华夏公益教科书