2024年5月30日发(作者:)

qnx系统CPU负荷率C代码算法

CPU负载是用来体现当前CPU的工作任务loading情况,和

CPU繁忙程度的。其主要通过统计CPU rq上task处于runnable

的平均时间(runnable_load_avg = runnable_load_sum

/ LOAD_AVG_MAX)。并根据不同周期,统计出不同的k线,来体

现CPU负载的变化趋势。

我们知道单个task处于runnable的平均时间是由PELT算法机

制来完成统计的。所以,我们此次分析更偏向于如何利用统计出的单

个task数据,再进一步统计出不同周期的均线,来表示CPU负载。

代码路径如下:

scheduler_tick() -> cpu_load_update_active()

void cpu_load_update_active(struct rq *this_rq) { unsigned

long load = weighted_cpuload(this_rq);

//load = cfs_rq->le_load_avg if

(tick_nohz_tick_stopped()) cpu_load_update_nohz(this_rq,

READ_ONCE(jiffies), load);

//(1) else cpu_load_update_periodic(this_rq, load);

//(2) }

上面根据是否配置nohz而可能停止了tick走向不同的分支:

(1)cpu_load_update_nohz(this_rq, READ_ONCE(jiffies),

load) //更新cpu负载,基于no HZ场景

(2)cpu_load_update_periodic() //周期性更新cpu负载,基

于有HZ场景

NO_HZ的情况下,会走这个分支。pending_updates表示jiffies

数是否更新,即表示tick数。 经过的秒数 = jiffies / HZ(平台当前

HZ=250);一个tick为HZ倒数,即4ms。

/* * There is no sane way to deal with nohz on smp when

using jiffies because the * CPU doing the jiffies update might

drift wrt the CPU doing the jiffy reading * causing off-by-one

errors in observed deltas;

{0,2} instead of {1,1}. * * Therefore we need to avoid the

delta approach from the regular tick when * possible since

that would seriously skew the load calculation. This is why we *

use cpu_load_update_periodic() for CPUs out of nohz.

However we'll rely on * jiffies deltas for updates happening

while in nohz mode (idle ticks, idle * loop exit,

nohz_idle_balance, nohz ) * * This means we might

still be one tick off for nohz periods. */ static void

cpu_load_update_nohz(struct rq *this_rq, unsigned long

curr_jiffies, unsigned long load) { unsigned long

pending_updates;

pending_updates = curr_jiffies -

this_rq->last_load_update_tick;