pthread继承了锁定的页面吗?

时间:2019-05-24 08:37:23

标签: c linux pthreads paging

我的实时系统上有一个分页问题,​​并且想知道linux在我的特定情况下应该如何表现。

在其他各种事情中,我的应用程序使用pthread_create()生成了2个线程,它们在一组共享缓冲区上运行。 我们将第一个线程称为A,从设备读取数据,对其进行一些计算,然后将结果写入其中一个缓冲区。 一旦该缓冲区已满,线程B将读取所有结果,并通过以太网将它们发送到PC,而线程A将写入下一个缓冲区。

我注意到,每次线程A开始向以前未使用的缓冲区中写入数据时,我都会错过一些中断并丢失数据(每个数据包的标头中都有一个id,如果递增一个以上,则表示我错过了)中断)。 因此,如果我使用n个缓冲区,则在数据采集开始时会恰好收到n次突发中断(因此,问题肯定是由分页引起的)。

要解决此问题,我在所有缓冲区上使用了mlock()和memset()来确保它们实际上已被分页。 这解决了我的问题,但是我想知道在我的代码中哪个位置是正确的位置。在我的主应用程序中,还是在一个/两个线程中? (当前我在两个线程中都这样做)

根据libc文档(第3.4.2节“锁定的内存详细信息”),使用fork()创建的子进程不会继承内存锁。 那pthreads呢?它们的行为是否相同,还是会从我的主进程继承这些锁?

关于我的系统的一些背景信息,即使我认为在特定情况下这并不重要:

  • 这是一个嵌入式系统,由具有双核Cortex-A9的SoC支持的SoC,该Cortex-A9运行带有PREEMPT_RT的Linux 4.1.22。
  • 中断频率为4kHz
  • 中断的线程优先级(如htop所示)为-99,线程A的线程优先级为-98(对于所有其他中断,线程优先级均高于-51的标准优先级),线程B的线程优先级为-2

编辑:

我做了一些附加的测试,从不同的线程(和主线程)中调用页面锁定功能。

如果我将页面锁定在main()中,然后尝试再次将它们锁定在一个线程中,则我希望看到main()出现大量页面错误,但线程本身没有页面错误(因为页面应该已经被锁定)。但是,htop讲述了一个不同的故事:我发现锁定这些页面的每个线程都有大量的页面错误(MINFLT列)。

对我来说,这表明pthread实际上具有与使用fork()产生的子进程相同的限制。如果是这种情况,将它们锁定在两个线程中(而不是在主线程中)将是正确的过程。

1 个答案:

答案 0 :(得分:1)

线程共享相同的内存管理上下文。如果页面驻留在一个线程中,则该页面驻留在同一进程中的所有线程中。

这意味着内存锁定是按进程而不是按线程的。

您可能在第一次写入时仍会看到一些小错误,因为使用了一个错误将页面标记为脏。您可以通过在锁定后也写入每个页面来避免这种情况。