在Delphi中的整数读取原子吗? [英] Are integer reads atomic in Delphi?

查看:160
本文介绍了在Delphi中的整数读取原子吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

对于从XE2到XE8的Delphi编译器,对于非Windows目标平台,是一个整数数据成员的读取操作,注释为[Volatile],atomic?



我知道对于Windows平台的情况下,它是原子的,当且仅当数据成员对齐到4个字节,但是对于非Windows(Android等)?



请注意,我不是在询问线程安全。线程安全和原子性是两个不同的东西。

解决方案

LU RD的意见是正确的答案。 b
$ b

非windows的工作类似于windows,因为当且仅当数据成员是32位对齐时,读操作才是原子的。在一般情况下,你不能依赖它是原子的,因为你不知道对齐方式,但在特定情况下,你控制数据成员的声明,你可以使用{$ ALIGN 4}或{ $ ALIGN 8}指令在本地保证一致。



例如

  {$ IFDEF POSIX} 
{$ ALIGN 4}
type
TMyClass = class
[Volatile] FValue:integer;
end;
{$ ENDIF}

...在上面,FValue可以原子读。



在更一般的情况下,当FValue的对齐未知时,读取FValue可能不总是原子的,类似于以下代码。

  ReadOfValue:= TInterlocked.CompareExchange(FValue,0,0); 

上面有一个警告:TInterlocked类可能不适用于某些编译器。我不知道什么时候推出。可能是XE7。






更新



David Heffernan和Gabr,我声明以上代码将不会可靠地工作在非Windows平台上。保证正确对齐的唯一方法是使用指针算术。 OmniThreadLibrary 中的GpStuff单元有效地使用指针算术来提供可自动读取的整数值。



可能[Volatile]属性没有帮助,但你也可以说它没有害处,甚至可能有语义效益或代码阅读器。


For Delphi compilers from XE2 through to XE8, for non-windows target platforms, is the read operation of an integer data member, annotated with [Volatile], atomic?

I know for the case of windows platform, it is atomic if and only if the data member is aligned to 4 bytes, but what about non-windows (Android etc.)?

Please note, I am not asking about thread-safety. Thread-safety and atomicity are two different things.

解决方案

LU RD 's comment is the correct answer.

Non-windows works similar to windows, in that the read operation is atomic if and only if the data member is 32 bit aligned. In then general case, you can't rely on it being atomic because you don't know the alignment, but in the specific case, where you control the declaration of the data member, you can use the {$ALIGN 4} or {$ALIGN 8} directives locally to guarantee alignment.

Example,

{$IFDEF POSIX}
{$ALIGN 4}
type
TMyClass = class
  [Volatile] FValue: integer;
  end;
{$ENDIF}

... in the above, FValue can be read atomically. (Not making any claims about thread-safety).

In the more general case, where the alignment of FValue is unknown, reading FValue might not always be atomic, and something similiar to the following code would be required ...

ReadOfValue := TInterlocked.CompareExchange( FValue, 0, 0);

The above has one caveat: The TInterlocked class may be not available to some compilers. I am not sure when it was introduced. Probably XE7.


Update

Thanks to comments below from David Heffernan and Gabr, I declare above code will not reliably work on a non-windows platform. The only way to guarantee correct alignment is to use pointer arithmetic. The GpStuff unit in the OmniThreadLibrary effectively uses pointer arithmetic to provide an atomically readable integer value.

Possibly the [Volatile] attribute does not help, but you could also say it does no harm, and may even have a semantic benefit or code readers.

这篇关于在Delphi中的整数读取原子吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆