我正在使用多个多线程进程编写一个复杂的软件。因为在其中一个中我需要实时功能(基本上是为了健壮性)我修补了Xenomai的目标内核并使用Xenomai的原生皮肤对其进行了编程。
现在我需要传达两个流程:一个运行实时任务,另一个运行 pthreads (后者在没有Xenomai的实时库/皮肤的情况下编译) 。
我的问题是:我能以某种方式与他们沟通吗?例如,我是否可以创建共享内存对象(shm_open
)并共享互斥锁,即使其中一个在RT环境中也是如此?
答案 0 :(得分:2)
我建议您使用Xenomai原生API创建命名管道,例如rt_pipe_create()
等。
还有一件事你可以使用:消息队列。但是我总是在消息队列中选择命名管道。
共享内存和消息队列都可用于在进程之间交换信息。不同之处在于它们的使用方式。
共享内存正是您的想法:它是一个可以由多个进程读取和写入的存储区域。它没有提供固有的同步;换句话说,由程序员来确保一个进程不会破坏另一个进程的数据。但它在吞吐量方面效率很高:读写操作相对较快。
消息队列是单向管道:一个进程写入队列,另一个进程按照写入的顺序读取数据,直到发生数据结束。创建队列时,将设置消息大小(每个消息的字节数,通常相当小)和队列长度(最大未决消息数)。访问速度比共享内存慢,因为每次读/写操作通常都是单个消息。但是队列保证每个操作都将成功处理整个消息,或者在不更改队列的情况下失败。所以作者在写完部分信息之后永远不会失败,读者将要么找回一条完整的信息,要么根本不回复。
基本上,管道 - 无论是命名还是匿名 - 都像消息传递一样使用。有人向收件人发送一条信息,收件人可以收到。共享内存更像是发布数据 - 有人将数据放入共享内存,而读者(可能很多)必须使用同步,例如通过信号量来了解有新数据的事实,并且必须知道如何读取内存区域以查找信息。
使用管道,同步很简单并且内置于管道机制本身 - 当有趣的事情发生时,您的读取和写入将冻结并解冻应用程序。使用共享内存,可以更容易地异步工作并且偶尔检查一次新数据 - 但代价是更复杂的代码。此外,您可以获得多对多的通信,但它需要更多的工作。此外,由于上述原因,调试基于管道的通信比调试共享内存更容易。
一个微小的区别是,在文件系统中可以直接看到fifos,而共享内存区域需要像ipcs这样的特殊工具来管理它们,例如创建一个共享内存段但你的应用程序死了并且不会自行清理(信号量和许多其他同步机制也可以与共享内存一起使用)。
共享内存还使您可以更好地控制缓冲和资源使用 - 在操作系统允许的限制范围内,您决定分配多少内存以及如何使用它。使用管道,操作系统会自动控制事物,因此您再次失去了一些灵活性,但却放松了很多工作。
最重要的要点摘要:管道进行一对一通信,减少编码并让操作系统处理事物,共享内存以实现多对多,更多的手动控制,但代价是更多的工作和更难调试