FSMLabs 有很多如何为 RT-Linux 编写实时代码的例子,但是这个发行版在很多年前就被放弃了。目前,针对 vanilla 内核的 PREEMPT_RT 补丁正在积极开发中,但官方 Wiki 上的代码示例很少。首先介绍一下我的问题。
我正在编写一个包含 2 个程序的项目:
- 字节码虚拟机 - 它必须作为实时应用程序工作 - 它有 64 KB 的 I/O 内存和 64 KB 的字节码。
- 客户端程序——它将读取和写入 I/O 内存、启动/暂停机器、加载新程序、设置参数等。它不必是实时的。
如何在这些进程之间进行通信以保持进程(1)实时并避免页面错误或其他可能干扰实时应用程序的行为?
方法 1. 仅使用线程
有2个线程:
具有最高优先级的虚拟机线程
与用户和机器通信的具有正常优先级的客户端线程 两个线程都可以按名称访问所有全局变量。我可以在每个机器周期后为传入/传出数据创建额外的缓冲区。但是,如果客户端线程导致应用程序崩溃,机器线程也会终止。实现远程访问也更加困难。
方法 2. 共享内存
在旧的 FSMLabs 中,建议在进程之间使用共享全局内存。现代 PREEMPT_RT 的 Wiki 页面建议使用 mmap() 进行进程数据共享,但在同一篇文章中,由于页面错误,它不鼓励 mmap()。
方法 3. 命名管道
这是在进程之间进行通信的更灵活的方式。但是,我是 Linux 编程的新手。我们希望在机器和客户端之间共享内存,但它还应该提供一种加载新程序(文件路径或程序代码)、停止/启动机器等的方法。旧 FSMLabs RT-Linux 实现了自己的 FIFO 队列(命名管道)。现代 PREEMPT_RT 没有。使用名称管道会破坏实时行为吗?如何正确地做到这一点?我应该使用 O_NONBLOCK 标志读取数据还是创建另一个线程来从/向管道读取/写入数据?
您是否知道在一个进程必须是实时的进程之间进行通信的其他方式?也许我只需要线程。但是,考虑更多客户端连接到虚拟机进程的场景。