我正在尝试实现一个从触觉传感器读取数据的程序,但我遇到了高 CPU 负载的问题。我需要帮助来减少 CPU 负载。
我的设置
我正在从多个(最多 16 个)tacilte 传感器读取数据。传感器通过 USB 连接到我的电脑。在 Linux 中,这些设备创建虚拟串行端口:/dev/ttyACM0、/dev/ttyACM1、/dev/ttyACM2 ...
这是 dmesg 告诉我的,当我插入传感器时(一个传感器的输出):
[ 321.998462] usb 2-2: USB disconnect, device number 3 [ 327.541414] usb 2-2: new full-speed USB device number 5 using ohci_hcd [ 327.998963] usb 2-2: New USB device found, idVendor=0471, idProduct=0889 [ 327.998983] usb 2-2: New USB device strings: Mfr=1, Product=2, SerialNumber=3 [ 327.998997] usb 2-2: Product: WTS [ 327.999011] usb 2-2: Manufacturer: Weiss Robotics [ 327.999024] usb 2-2: SerialNumber: 0001 [ 328.035356] cdc_acm 2-2:1.0: This device cannot do calls on its own. It is not a modem. [ 328.035424] cdc_acm 2-2:1.0: ttyACM0: USB ACM device
I use termios from termios.h to open the serial device. As the sensors have a binary protocol I set the device to non-canonical and use raw output. The sensors provide a periodic sampling feature which will send about 270 frames of data per second.
My program should read and process the frame from the serial device as soon as the complete frame is available.
The Problem: high cpu load
This is what my code basically does:
int fd = open("/dev/ttyACM0");
struct termios settings;
settings.xxx = ... // see full code for details
tcflush( fd, TCIFLUSH );
tcsetattr( fd, TCSANOW, &settings );
while(1)
{
Frame f = readCompleteFrame(fd);
processFrame(f);
}
当我将设备置于阻塞读取模式并执行我的循环时,CPU 负载达到大约 15%。每个传感器都有一个单独的线程。由于我有多个传感器,每个线程将占用一个 CPU 内核的 15%。
我使用 time 命令分析程序:几乎所有的 cpu 时间都花在了内核上。用户时间接近于零。
我试图解决的问题
- 我将设备置于非阻塞模式并使用来自 sys/poll.h 的轮询。 CPU 负载相同:每个传感器 15%。
- 我将设备置于非阻塞模式并使用 select from unistd.h。与投票结果相同。
- 我将设备置于非阻塞模式并不断调用 read(fd); sleep (1);直到我得到一些数据。这使用 50% 的 CPU,但与传感器的数量无关。
完整的测试代码
我用于测试的完整代码可以在这里找到:http://pastebin.com/7dv0U2nN
最佳答案
检查代码后,您可能无法在应用程序中修复此问题。
负载可能是由内核驱动程序中的问题或 USB 设备与 PC 通信的方式引起的。
关于c++ - 从/dev/ttyACM0 读取时 CPU 负载高,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24449124/