简体   繁体   English

可以使用跨语言平台的 System V 共享内存在 4 字节 int 上实现无锁原子写/一致读操作吗?

[英]Can a lock-free atomic write / consistent read operation be achieved on a 4 byte int using System V shared memory across language platforms?

I want to implement a lock free counter , a 4-byte int , in System V shared memory.我想在 System V 共享内存中实现一个无锁counter ,一个 4 字节的int The writer is a C++ program, the reader is a Python program.作者是一个C++程序,读者是一个Python程序。 Working roughly like this:工作大致是这样的:

  • C++ code updates counter in an atomic operation C++ 代码在原子操作中更新counter
  • Python code reads counter and has a consistent view of memory (eventual consistency is perfectly acceptable) Python代码读取counter并具有一致的内存视图(最终一致性完全可以接受)
  • No locks are implemented to achieve this没有实施锁来实现这一点

Within the C++ language there are atomic get/update operations that allow for this and guarantee memory consistency, I believe the same is true in Python.在 C++ 语言中,有原子获取/更新操作可以实现这一点并保证内存一致性,我相信在 Python 中也是如此。

However, as I understand it, the assumptions in C++ regarding atomic operations do not necessarily apply to code written and compiled in another language and compiler.然而,据我所知,C++ 中关于原子操作的假设不一定适用于用另一种语言和编译器编写和编译的代码。

Is there a way to achieve a consistent view of shared memory across languages that doesn't involve implementing low level locks?有没有一种方法可以在不涉及实现低级锁的情况下实现跨语言的共享内存的一致视图?

Is there a way to achieve a consistent view of shared memory across languages that doesn't involve implementing low level locks?有没有一种方法可以在不涉及实现低级锁的情况下实现跨语言的共享内存的一致视图?

No, not in general.不,不是一般的。

First I would say this has nothing to do with languages but more with the actual platforms, architecture, implementation or operating system.首先,我想说这与语言无关,而更多地与实际平台、架构、实现或操作系统有关。

Because languages differ quite strongly, take Python for example: It has no language native way of accessing memory directly or lets say in an low level manner.因为语言差异很大,以 Python 为例:它没有直接访问内存的语言本机方式,或者以低级方式说。 However some of its implementations do offer its own API.然而,它的一些实现确实提供了自己的 API。 Languages intended for such low level use have abstractions for that, as C, C++ or Rust have.用于这种低级使用的语言对此具有抽象,就像 C、C++ 或 Rust 一样。 But that abstractions are then implemented often quite differently, as they often depend on where the code is run, interpreted or compiled for.但是这些抽象的实现方式通常完全不同,因为它们通常取决于代码的运行、解释或编译位置。 An integer for some architectures are big endian, on most, like x86 or arm, its little endian.某些架构的整数是大端,在大多数情况下,如 x86 或 arm,它的小端。 Operating systems also have a say, as for example memory is used and abstracted.操作系统也有发言权,例如内存被使用和抽象。

And while many languages have a common abstractions of linear memory, its gets even messier with atomics: The compiler for C++ could generate machine code ie assembly that check if the CPU run on does support new fancy atomic integer instructions and use them or fall back on often supported atomic flags plus the integer.虽然许多语言都有一个共同的线性内存抽象,但它在原子方面变得更加混乱:C++ 的编译器可以生成机器代码,即检查 CPU 运行的程序集是否支持新的花哨的原子整数指令并使用它们或回退通常支持原子标志加上整数。 It could just rely on operating system, a spin lock, or standardized APIs defined by POSIX, SystemV, Linux, Windows if the code has the luxury of running in an operating system managed environment .如果代码可以在操作系统管理的环境中运行,它可以只依赖于操作系统、自旋锁或由 POSIX、SystemV、Linux、Windows 定义的标准化 API。

For non imperative languages it gets even messier.对于非命令式语言,它变得更加混乱。

So in order to exchange data between languages, the implementations of those languages have to use some common exchange.因此,为了在语言之间交换数据,这些语言的实现必须使用一些公共交换。 They could try to do that directly via shared memory for instance.例如,他们可以尝试直接通过共享内存来做到这一点。 This is then called an Application Binary Interface (ABI), as a memory abstraction is at least common to them a priori.这被称为应用程序二进制接口 (ABI),因为内存抽象至少对它们先验是通用的。 Or the operating system or architecture might even standardized such things or even supports APIs.或者操作系统或架构甚至可能对这些东西进行标准化,甚至支持 API。

System V would be an API designed for such interchange but since AFAIK it does not have an abstraction for atomics or lock less abstractions, the answer stays no, even with the System V context out of the title. System V 将是为这种交换而设计的 API,但由于 AFAIK 它没有原子的抽象或锁定较少的抽象,因此即使 System V 上下文不在标题中,答案仍然是否定的。

I'm going to take issue with some of Superlokkus' assertions.我将对 Superlokkus 的一些断言提出异议。

The mmap primitive is available in both C++ and Python. mmap原语在 C++ 和 Python 中都可用。 That primitive gives you memory that is in a physical page shared by both processes.该原语为您提供位于两个进程共享的物理页面中的内存。 Different virtual addresses, same physical page of memory.不同的虚拟地址,相同的内存物理页。 Changes by one process are immediately viewable by the other process.另一个进程可以立即查看一个进程的更改。 That's how it has to work.这就是它必须工作的方式。 It operates at a hardware level.它在硬件级别运行。 Abstractions are irrelevant.抽象是无关紧要的。

Now, that DOESN'T mean you can get notification of those changes.现在,这并不意味着您可以获得这些更改的通知。 If you are polling in a loop (presumably a friendly loop with sleeping in between checks), then you will see the change the next time you check.如果您在循环中轮询(大概是在检查之间休眠的友好循环),那么您将在下次检查时看到更改。

Yes, using the atomics library, along with a suitable shared memory library (eg mmap or shared_memory ).是的,使用atomics库以及合适的共享内存库(例如mmapshared_memory )。
This example assumes your atomic int is in the first 4 bytes of the shared memory segment.此示例假设您的原子整数位于共享内存段的前 4 个字节中。

from atomics import atomicview, MemoryOrder, INT
from multiprocessing import shared_memory


# connect to existing shared memory segment
shmem = SharedMemory(name="test_shmem")

# get buf corresponding to "atomic" region
buf = shmem.buf[:4]

# atomically read from buffer
with atomicview(buffer=buf, atype=INT) as a:
    value = a.load(order=MemoryOrder.ACQUIRE)

# print our value
print(value)

# del our buf object (or shmem.close() will complain)
del buf

# close our shared memory handle
shmem.close()

We can use ACQUIRE memory order here rather than the default SEQ_CST .我们可以在这里使用ACQUIRE内存顺序而不是默认的SEQ_CST

The atomicview can only be created and used with a with statement, so you will need to manually keep your buf around (and manage its lifetime correctly). atomicview只能通过with语句创建和使用,因此您需要手动保留buf (并正确管理其生命周期)。

Note: I am the author of this library注意:我是这个库的作者

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM