一文秒懂CPU使用率
CPU:Cores, and Hyper-Threading
超线程(Hyper-Threading )
超线程是Intel最早提出一项技术,最早出现在2002年的Pentium4上。单个采用超线程的CPU对于操作系统来说就像有两个逻辑CPU,为此P4处理器需要多加入一个Logical CPU Pointer(逻辑处理单元)。
虽然采用超线程技术能同时执行两个线程,但它并不像两个真正的CPU那样,每个CPU都具有独立的资源。当两个线程都同时需要某一个资源时,其中一个要暂时停止,并让出资源,直到这些资源闲置后才能继续。因此超线程的性能并不等于两颗CPU的性能。
多核(multi-cores)
最开始CPU只有一个核(core),为了提高性能,引入了双核CPU,四核CPU等,双核CPU能同时执行两个线程。和超线程不同的是,双核CPU是实打实的有两个central processing units在一个CPU chip。
上图显示主板上有1个插槽(socket),这个插槽插着一个CPU,这个CPU有4个核(core),每个核都使用超线程技术,所以这台机器总共有8个逻辑核。
CPU使用率计算
CPU使用率测试
一台拥有8个logic core CPU的机器,执行如下程序:
该程序开启9个线程每个线程都执行一个死循环。执行后用top查看cpu使用情况:
可以看到cputest的CPU使用情况为800%,也就是8个logic core都在执行cputest这个进程。
而在一个只有1个logic的CPU上跑的结果如下:
可以看到,纵使开启了9个线程,每个线程都执行死循环,CPU使用率只有97.7%。
如何计算CPU使用率
以上截取自man top中对于CPU使用率的定义,总结来说某个进程的CPU使用率就是这个进程在一段时间内占用的CPU时间占总的CPU时间的百分比。
比如某个开启多线程的进程1s内占用了CPU0 0.6s, CPU1 0.9s, 那么它的占用率是150%。这样就不难理解上例中cputest进程CPU占用率为800%这个结果了。
实现CPU使用率统计程序
某进程cpu使用率 = 该进程cpu时间 / 总cpu时间。
/proc/pid/stat中可以得出进程自启动以来占用的cpu时间。以bash进程为例:
第14项utime和第15项stime分别表示bash自启动起来,执行用户代码态占用的时间和执行内核态代码占用的时间,单位是clock tick,clock tick是时间单位。这两项的详细解释如下(摘自man proc):
每个clock tick占用多少时间呢?
可以通过sysconf(_SC_CLK_TCK)获取1秒内有多少个clock tick(通常是100)。也就是说1 clock tick为1 / 100秒。
有了上面的基础,
我们可以每隔period秒读取/proc/pid/stat,解析其中的utime和stime,将其和(utime+stime)减去上一次采样时这两项的和(lastutime + laststime),这就是period秒内该进程占用CPU的时间,单位为clock tick。
总的CPU时间为period * sysconf(_SC_CLK_TCK),单位也为clock tick。
所以公式如下:
某进程cpu使用率 = ((utime+stime) - (lastutime + laststime)) / period * sysconf(_SC_CLK_TCK)
以下是实现:
代码很简单,每隔两秒采一次样,计算这两秒内指定进程的CPU使用率。
为了测试,先将前文的cputest运行起来,该程序会占满8个logic core。
./cputest &,然后top看下CPU使用率,大约占用了800%的CPU。
接着用我们的自己的写的程序看下,pid是867,
./cpumon 867
可以看到每隔两秒都会计算一次,使用率略低于800%,也可以理解,因为现在cpumon也会占用一定的CPU时间。
参考资料:https://www.howtogeek.com/194756/cpu-basics-multiple-cpus-cores-and-hyper-threading-explained/
原文:https://www.cnblogs.com/gatsby123/p/11127158.html
2024-11-14 广告