c - 在非实时操作系统/内核上执行接近实时任务的最佳方法是什么?

标签 c linux real-time

在 GNU/Linux 机器上,如果想要执行“实时”(亚毫秒时间关键)任务,您几乎总是必须经历漫长、复杂且容易出现问题的过程,即修补内核以暴露足够的支持[1] [2] .

最大的问题是,许多实时任务最有用的系统甚至不具备让这些补丁工作的基本硬件要求,即高分辨率定时器外设。或者如果他们这样做,它是特定于硬件的,因此需要根据具体情况在补丁中具体实现。即使 CPU/指令时钟速率足够快,足以提供所需的时间粒度,也是如此。

那么,我的问题是,尽可能接近上述实时目标的最佳第二名方法/技巧是什么?人们可以在应用程序源代码中简单地做的事情,而不需要深入了解底层硬件或太多的“内核黑客”。

提升进程优先级,为“关键”任务启动一个额外的线程,以及(在 C 中)使用 nanosleep() 的变体是迄今为止我想到的最好看的答案/技巧。我希望找到更多。

最佳答案

sched_setscheduler(2)和 friend 允许你使用两个不同的软实时调度程序,SCHED_FIFO SCHED_RR。在这些调度程序下运行的进程的优先级高于常规进程。因此,只要您只有几个这些进程,并控制它们之间的优先级,您实际上可以获得相当低的实时响应。

根据评论中的要求,这是 SCHED_FIFO 和 SCHED_RR 之间的区别:

对于“实时”调度器,有多达 100 个不同的优先级(POSIX 只需要 32 个不同的级别,因此应该使用 sched_get_priority_min(2)sched_get_priority_max(2) 来获取实际数量。调度器都通过抢占来工作优先级较低的进程和线程,区别在于它们如何处理具有相同优先级的任务。

SCHED_FIFO,是一个先进先出的调度程序(因此得名)。这意味着首先进入运行队列的任务被允许运行直到完成,自愿放弃其在运行队列中的空间,或者被更高优先级的任务抢占。

SCHED_RR,是一个循环调度程序。这意味着具有相同优先级的任务只允许运行特定的时间片。如果在这个时间量程用完时任务仍在运行,则任务将被抢占,并且允许运行队列中的下一个任务(具有相同优先级)运行到其时间量程。与 SCHED_FIFO 一样,较高优先级的任务会抢占较低优先级的任务,但是,当允许被较高优先级任务抢占的任务再次运行时,它只能运行其量程中剩余的时间。请参阅 sched_rr_get_interval(2) 中的 Noes 部分了解如何设置任务的时间片。

关于c - 在非实时操作系统/内核上执行接近实时任务的最佳方法是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15505905/

相关文章:

C - 引号和撇号之间的区别( "vs ')

php - Ghostscript 无法转换某些 PDF

linux - 将文本放在行首的括号内

linux - 从文件中提取字符串模式

c - 一定时间后停止执行程序

c - fgets 中的段错误,试图在 c 程序中运行 shell 命令

web-services - Kafka-Web服务实时流

java - 参与者数量有限的 Firebase 房间

c - 使用 qsort() 对数组进行排序

sql-server - 实时系统数据库使用