细粒度的 nanosleep 在 Linux 上的 c++ 程序中不节能

Posted

技术标签:

【中文标题】细粒度的 nanosleep 在 Linux 上的 c++ 程序中不节能【英文标题】:fine granularity nanosleep not power efficient in c++ program on linux 【发布时间】:2013-07-16 10:52:29 【问题描述】:

我正在尝试在我的 linux 机器上的 C++ 线程中定期调用采样函数。我想在很短的时间(理想情况下为 1 毫秒)后重新启动我的功能,但我发现 1 毫秒期间消耗的功率(以瓦特为单位)高得令人望而却步:系统运行时的功率水平是我的两倍周期为 5 毫秒。保持低功耗是我想要的功能的主要关注点。

具体来说,

void* loop_and_sample(void* arg) 
    while(1) 
      sample();
      nanosleep((struct timespec[])0,1000000, NULL);
    

需要 2 倍的力量:

void* loop_and_sample(void* arg) 
    while(1) 
      sample();
      nanosleep((struct timespec[])0,5000000, NULL);
    

我已经确定采样器在 2 个频率下的功耗差异可以忽略不计,并且额外的功耗来自睡眠调用。也就是说,即使我在上面的两个 sn-ps 中注释掉了 sample() 行,第二个仍然需要一半的功率。关于如何减少睡眠呼叫消耗的功率的任何想法?

仅供参考,我在 24 核 Intel Xeon 上运行 Ubuntu 3.2.0,搜索 /boot/config 的频率显示如下:

cat /boot/config-3.2.0-48-generic | egrep 'HZ'
CONFIG_RCU_FAST_NO_HZ=y
CONFIG_NO_HZ=y
# CONFIG_HZ_100 is not set
CONFIG_HZ_250=y
# CONFIG_HZ_300 is not set
# CONFIG_HZ_1000 is not set
CONFIG_HZ=250
CONFIG_MACHZ_WDT=m

但是,运行此脚本:http://www.advenage.com/topics/linux-timer-interrupt-frequency.php,我发现我的内核定时器中断至少为 4016 Hz(这是我想要采样的频率的 4 倍)。感谢您的帮助!

【问题讨论】:

请指定您的硬件以及您正在运行的内核版本。电源状态管理是深奥的巫术,并且高度依赖于硬件。 Mark B(下图)可能是正确的,所以这是一个很长的镜头,但是...您可以尝试使用 timerfd(请参阅linux.die.net/man/2/timerfd_create)以防这是内部实现的问题小间隔的 nanosleep。 Ubuntu 3.2.0(如前文所述)和Intel Xeon 24核机(现已加入主体) sample 是做什么的?可以改为基于事件吗? 示例实际上是在测量功率(通过读取英特尔的新 RAPL 计数器),我希望功率测量值为 1/ms,即计数器刷新率,所以我认为它不能基于事件 【参考方案1】:

几乎可以肯定,问题根本不是睡眠调用,而是您的 CPU 无法如此快速地上下电。 CPU 几乎肯定不会在您进入睡眠状态后立即消耗更少的电量,因此需要一些时间来这样做。当您进入睡眠时间较长时,CPU 能够更好地降低功耗。

我不确定您可以在此处做什么,尽管可能降低 CPU 频率可能有助于在更频繁地醒来时降低功耗。

【讨论】:

以上是关于细粒度的 nanosleep 在 Linux 上的 c++ 程序中不节能的主要内容,如果未能解决你的问题,请参考以下文章

细粒度图像相关汇总

细粒度图像分类

inotify 工具 是一种强大的细粒度的异步文件系统监控机制

细粒度与粗粒度域模型在内存数据网格中

还能这么玩?将Prompt Tuning用于细粒度的图像检索!

如何实时更改我的 VLC 播放速度细粒度?