开春大礼《华为云技术精选集》大厂100+前沿技术实战分享!>>>
UNIX® 的平均负载 第一部分 :如何工作
作者:Dr. Neil Gunther,
Performance Dynamics Company
为了正确查看数学符号,请检查这里 ,然后再继续。
你曾经想知道这三个在UNIX®平均负荷(LA)报告中出现的数字是如何计算出来的?
这个TeamQuest在线栏说明如何做以及如何重组平均负载(LA)可以得到更好的容量规划。 但首先,请测试您的知识,在平均负载三胞胎"LA Triplets"测验。
在这两个系列部分我要探索平均数在性能分析与容量规划中的作用。 平均数有许多表现形式,例如,算术平均(通常使用的) ,移动平均线(通常在财务规划中采用) ,几何平均数(用于规格CPU的性能衡量 ) ,调和平均数(没有足够应用) ,等等。
更重要的是,我们将看到随时间推移的平均数或者依赖时间的平均数。 一个依赖时间的平均数的具体例子是在某些Unix命令中出现的平均负荷指标(load average metric)。 在第1部分我们将看看平均负荷是如何被计算出来的。 第2部分中我将它与其他均适用于容量规划和性能分析的技术进行比较。 本文假设你不熟悉Unix命令,因此我将首先回顾一些命令,它们都能显示平均负荷指标。直到第4部分 ,我们会投入到UNIX的内核代码中去,并且完成所有的工作。
1 Unix命令
其实,平均负载不是一个传统意义中的UNIX命令。相反,它是一个嵌入式的指标,显示在其他Unix命令如uptime和procinfo的输出中。这些命令通常是被UNIX的系统管理员用来观察系统资源消耗的。 让我们来仔细看看其中一些命令。
1.1经典输出
普通的ASCII文本格式出现在各种UNIX的命令中。 以下是一些常见的例子。
uptime
这个uptime外壳命令产生下列输出:
[pax:~]% uptime |
它显示自从上次系统重启以来,活动的用户进程数量和所谓的平均负荷指标(load average)。
procinfo
在Linux系统上,procinfo命令产生以下输出:
[pax:~]% procinfo |
平均负载指标出现在这个输出的左下角。
w
w(ho)命令产生下列输出:
[pax:~]% w 9:40am up 9 days, 10:35, 4 users, load average: 0.02, 0.01, 0.00 |
请注意,第一行的输出与uptime命令的输出相同。
top
top命令是最近加入到UNIX命令集中的,它通过计算进程消耗CPU的时间来给进程排名。它产生下列输出:
4:09am up 12:48, 1 user, load average: 0.02, 0.27, 0.17 58 processes: 57 sleeping, 1 running, 0 zombie, 0 stopped |
所有这些命令,请注意,输出中都有三个数字报告平均负载。相当普遍的是,这些数字显示出从左至右的降序。但是有时,又是升序排列,正如上面的输出。
1.2 图形输出
平均负荷也可以显示为一个时间序列一样,在这里显示的是工具ORCA的输出。
图1 :ORCA3日平均负载图。
虽然这种直观辅助工具帮助我们看到,绿色的曲线更spikey和比红色曲线变化更大,它使我们能够看到一天的完整的数据,目前尚不清楚这对能力规划或性能分析有多大作用。 我们需要了解的是平均负载指标的定义和计算方法。
2 它是什么?
那么,这些不同的命令确切地说明了什么是平均负载么? 让我们来看看官方的UNIX文档。
2.1 UNIX操作手册
[pax:~]% man "load average" |
哎呀!没有手册说明!平均负载是其他命令的内嵌输出,所以没有单独的手册文档。好吧,让我们看看uptime命令的文档,能否从中获得写帮助。
... uptime产生一条信息,包括当前时间,系统连续运行时间,当前登录用户 |
所以那三个数字指标,表示了“过去1、5、15分钟内的系统平均负载。”
|
但是,文档中仍然回避了什么是负载(load)的问题。
2.2 什么是大师不得不说的
让我们转向一些UNIX热点问题来看一看。
Tim O'Reilly and Crew
《UNIX超级工具》(UNIX Power Tools [])这本书,在726页告诉我们,CPU是:
|
这是令人鼓舞的!无论如何,它帮助我们解释了衡量的内容:活动进程数量。在720页 39.07 检查系统的负载:uptime 中这样说:
|
嗯... 这个数字“ 3 ”是怎么来的? 和这三个平均数( 1 , 5 , 15分钟) ,他们指的是什么?
Adrian Cockcroft 在 Solaris
在Sun性能和调优(Sun Performance and Tuning)[]中的97页中的一段:搞懂和使用平均负载,Adrian Cockcroft叙述到:
|
所以,即便是Sun的“大男孩们”做错了什么。然而,这样的想法,将平均负载与CPU运行队列联系在一起是重要的观点。
O'Reilly 等. 还注意到一些使用平均负载的潜在陷阱。
|
CPU被挂钩2100秒后进程被杀死 CPU在余下的1500秒后保持静默
3.2 采样过程
正如作者[]关于Linux内核的解释,因为我们的测试进程是CPU绑定的,他们将处在TASK_RUNNING状态。 这意味着它们是:
- 正在运行 ,即目前正在CPU中执行
- 可以运行 ,即在CPU的run_queue中等待被运行
Linux内核还检查是否有任何任务处在短期睡眠状态,称为TASK_UNINTERRUPTIBLE状态。 如果有,它们也包括在平均负载的采样中。它们都没有在我们的负载测试中。
下面的源代码片段显示如何做到这一点的更详细资料。
600 * Nr of active tasks - counted in fixed-point numbers |
所以,uptime每5秒钟的采样是Linux内核的内在时基更新平均负载的计算。
3.3 测试结果
实验结果的图示在图2。图中的颜色并不与图1中的具有相同的意思。
图 2: Linux 平均负载测试结果。
相比之下,这是如何一个单独繁忙循环运行在一个单CPU的Solaris系统中的图示。
Figure 3: Solaris 平均负载测试结果。
你应该原谅这个跳出来的“负载”就是CPU利用率的结论。 随着Linux的测试结果表明,当两个繁忙的进程在运行,在单个CPU的最高负载是2(而不是1 )。因此,负载不等于CPU利用率。
从另一个角度来看,图2类似于电容器的充电和放电过程
图 4: 电容的充电(charge)及放电(discharge)过程.
4 内核魔术
现在让我们进入Linux内核 ,看看这些平均负载的数字是如何产生的。
unsigned long avenrun[3]; |
倒计时是在5赫兹的LOAD_FREQ中进行的,这是多长时间呢?
1 HZ = 100 ticks |
所以,5赫兹指CALC_LOAD每5秒钟被调用一次。
4.1 魔术数字
函数CALC_LOAD其实是一个定义在sched.h文件中的宏。
58 extern unsigned long avenrun[]; /* Load averages */ |
一个值得注意并令人好奇的是这些数字: 1884, 2014, 2037。 代表什么? 如果我们看一下这段代码的开头,我们会知道:
/*
这是用来假冒定点平均负载计数的常量。
11位小数通过乘法扩大到22位:这样有了一个精度为10位整数和11为小数的平均负载数。
如果你想更频繁地记录平均负载,你就需要更大的精度,否则会四舍五入。使用2秒的计数
周期,如果仍然使用11位小数,EXP_n的数值将是1981,2034和2043。
|
这些魔术数字是使用定点(而不是浮点)的结果。
使用1分钟取样作为一个例子,转换的exp(5/60)到11位精度的二进制是这样的:
|
(1) |
但是EXP_M表示了逆运算exp(-5/60)。因此,我们能从下面的公式中直接计算出那些魔术数字。
|
(2) |
M=1代表分钟采样周期。表1整理了部分结果。
T | EXP_T | Rounded |
5/60 | 1884.25 | 1884 |
5/300 | 2014.15 | 2014 |
5/900 | 2036.65 | 2037 |
2/60 | 1980.86 | 1981 |
2/300 | 2034.39 | 2034 |
2/900 | 2043.45 | 2043 |
表 1: 平均负载的魔术数字
这些数字在上述的内核注释中得到了充分的认同。使用定点运算大概是出于性能考虑,因为计算能在内核空间中进行,而不是用户空间。
仍然有一个问题,像exp(5/60)这样的比值是如何来的?
4.2 魔法揭示
用1分钟平均数举例,CALC_LOAD等同于数学公式:
|
(3) |
如果我们认为n=0,公式(3) 简化为:
|
(4) |
如果我们迭代公式(4),在t = t0 和 t = T 之间,我们得到:
|
(5) |
这就是指数衰变,就像我们在图2中看到的从时间t0 = 2100到tT = 3600的一样。
Conversely, when n = 2 as it was in our experiments, the load average is dominated by the second term such that:
相反,就像在我们的实验中一样,当n=2时,平均负载被第二种因素主宰了:
|
(6) |
这是一个单调增函数,就像我们在图2中的t0 = 0到tT= 2100中看到的一样。
5 综述
因此,我们学到了什么? 那三个平均负载三胞胎(LA Triplets)中无伤大雅的数字背后有着令人惊奇的奥秘。
这三个数字为您提供某种形式的有关系统在最近的过去(1分钟),过去( 5分钟)和遥远的过去( 15分钟)所做事情的一些信息。
你如果试过了(LA Triplets)问答就会发现这样的问题:
- 负载不是利用率,而是任务队列长度。
- 他们指出了3种不同的样本时间序列。
- 他们是成倍阻尼的移动平均线。
- 他们使用了错误的顺序来代表趋势信息。
如果你试图使用它们进行容量规划,这些继承的限制是非常重要的。我会有更详细的解释在平均负载第二部分:不是你的平均的平均数。
参考文献
[BC01]D. P. Bovet and M. Cesati. Understanding the Linux Kernel. O'Reilly & Assoc. Inc., Sebastopol, California, 2001.
[Coc95]A. Cockcroft. Sun Performance and Tuning. SunSoft Press, Mountain View, California, 1st edition, 1995.
[Gun01]N. J. Gunther. Performance and scalability models for a hypergrowth e-Commerce Web site. In R. Dumke, C. Rautenstrauch, A. Schmietendorf, and A. Scholz, editors,Performance Engineering: State of the Art and Current Trends, volume # 2047, pages 267-282. Springer-Verlag, Heidelberg, 2001.
[POL97]J. Peek, T. O'Reilly, and M. Loukides. UNIX Power Tools. O'Reilly & Assoc. Inc., Sebastopol, California, 2nd edition, 1997.
译文地址:http://www.yeeyan.com/articles/view/79184/37314
原文:http://www.teamquest.com/resources/gunther/display/5/index.htm
学习了,好东西。
谢谢。