我可以为我的程序使用1个处理器内核吗?


12

我必须定时GPIO引脚上高->低和低->高信号沿之间的时间差。我写了一个简单的程序来做到这一点。运行了一段时间后,我对结果(0.01秒的变化)感到非常满意。但是,有时会出现0.5秒的错误。我当时认为这可能是由于当时正在运行其他系统进程所致。所以我的问题是:

我可以只为我的程序保留一个处理器内核,而为系统保留其他3个内核吗?

我正在使用Raspbian Jessie Lite,所以我认为3个内核足以运行它。


4
我假设您正在循环查询GPIO引脚的状态。这很容易受到操作系统决定执行程序的方式的影响,这将花费大部分时间使CPU处于繁忙状态,而实际上无用。您可能想研究一种在给定的GPIO引脚上设置中断的方法,您可以使用该方法使程序在GPIO引脚的信号沿之间休眠。
Florian Castellane

4
不确定您的项目是什么,但是有时微控制器更合适,尤其是当您需要更多更实时的系统时。Arduino提供了很多选项,您可以使用C / C ++编写程序。
SnakeDoc '17

@Florian RPi.GPIO中有一个类似于中断的功能。它将阻塞程序,直到检测到边缘为止(源:sourceforge.net/p/raspberry-gpio-python/wiki/Inputs)。
NonStandardModel '17

@SnakeDoc我知道微控制器更好。我希望避免这种情况,因为我不需要微秒的精度。1/100秒就足够了。另外,我只需要时间差,所以如果有延迟,我希望启动和停止都一样。如果这不起作用,我必须将微控制器连接到RPi来存储数据。
NonStandardModel '17

1
或在PI上运行实时操作系统。设置的问题在于它取决于操作系统的“尽力而为”。根据您的程序请求对GPIO进行特权访问的同时发生的其他事情,它可能会排在操作系统当时正在执行的其他任务之后。您的userland程序将获得比系统任务低的优先级。还有一个抢占,这意味着在程序运行时,操作系统可能会“暂停并搁置它以使另一个进程运行”,这意味着您的计时观察可能会有所偏差
SnakeDoc

Answers:


13

专注于核心可能是过大的。

我建议您尝试一下我的Pigpio库。默认情况下,它将使GPIO电平变化时间在10µs之内。

作为快速测试,我建议您看一下此Python示例,该示例将打印任何GPIO级别转换以及自该GPIO上一次转换以来的时间(以微秒为单位)。

在Jessie Lite中默认未安装Pigpio。从链接站点安装最新版本,或在存储库中安装旧版本。

sudo apt-get install pigpio python-pigpio python3-pigpio

pigpio - Library for Raspberry Pi GPIO control
python-pigpio - Python module which talks to the pigpio daemon (Python 2)
python3-pigpio - Python module which talks to the pigpio daemon (Python 3)

我将尝试您的Pigpio库。现在,我必须完成另一个项目,但是我将回到这一点。我将在几周后报告。谢谢!
NonStandardModel '17

4

您可以schedutils按照以下Cyber​​citi文章中的说明将程序锁定到一个内核:

sudo apt-get install schedutils
sudo taskset -c 3 -p 13545  # Lock PID 13545 to core 3

但是,其他进程仍可以安排在同一内核上。因此,第二件事是使用nice命令确保您的命令以最高优先级运行(这将告诉Linux内核,如有必要,其他进程应被抢占)。以这种方式启动程序:

nice -n -20 your-program

您的计时问题还有其他一些可能的原因。这些都不是一件容易的事:

  • 如果您使用Python进行编程,则有一个垃圾回收器有时会暂停您的程序以释放未使用的内存。
  • 中断使CPU处理了您不想要的其他事情。例如,网络数据包或其他输入/输出。
  • 如果您的程序睡眠很多,则可能还有其他进程占用了CPU缓存(L1 / L2缓存)。这迫使您等待RAM访问。
    • 更糟的是,如果您的RAM已满,那么您的进程将被换出到磁盘上,因为SD卡无法使用。

有多种方法可以使您的流程成为实时流程,这意味着它将在一定的时间保证下运行。这样做的问题是,其他所有事情可能都比较慢,这是一个复杂的话题。如果您想解决这个难题,建议您开始阅读Linux中的实时进程


2
最好给进程实时优先级,以确保它优先于非实时进程运行,而不是更好。
joan 2017年

好点,我将添加一个注释。
EmilVikström'17

1
“ gc.disable()”如果禁用垃圾收集器会发生什么?
Keine

@Keine您可能会遇到内存泄漏。假设您有一个对象A,该对象的变量指向B。Python将以数字跟踪此引用,它知道B有1个指向它的对象。当您不再需要A时,将其删除。B的引用计数将减少,如果达到0,Python也可以释放B。这称为参考计数。但现在说B具有参考给A.现在你有指向彼此对象的集群。它们都不会命中0并被释放。当主程序未指向群集时,GC可以找到此类群集并将其删除。
EmilVikström'17

1
我会将您提出的建议添加到我的项目中。但是我希望避免过于复杂的主题。在那种情况下,我认为最好进行微控制器中断检测并将其连接到RPi只是为了保存数据。谢谢!
NonStandardModel

2

由于您有计时要求,因此Raspberry Pi不再是适合此的平台。它不是一个实时平台,计时可能会因许多不同的干扰源而中断。

取而代之的是,您应该使用微控制器来测量该时间,最好使用中断,然后将信息传递给Pi。


1
但是,是否有可能在Raspberry Pi的GPIO引脚上获得中断?
Florian Castellane

当然,这取决于设计要求中是否有其他部分使linux计算机比MCU更合适。RPi能够很好地处理此任务,MCU的时钟频率为10 MHz。
肖恩·胡利哈内

1

根据您的要求,我认为您不需要使用单个核心处理器。您需要确保程序始终运行。为此,您可以将程序的优先级设置得很高,这样它就不会受到其他任何进程的干扰。

据我所知,我们使用的OS(通用OS)并非旨在用于实时系统,因此,如果要实时运行流程,以免其他进程干扰它,则需要执行用于实时操作系统(RTOS)。也许他们会提出核心选择。:)


1
有没有好的免费RTOS?
Keine

RTLinux和Vxworks是RTOS的示例,它们也很好。但是您需要在安装之前研究一下OS(创建它的重点),以便它可以满足您的需求。
Vishwajeet Vishu
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.