我正在尝试找出我的服务器是受网络 IO 限制还是受 CPU 限制。我确实查看了一些典型工具的输出来检查系统的当前状态(下面的 iostat、sar 和 top 的输出),但我不太确定我对输出的解释是否正确。
这是我的设置:
- 应用服务器(实际上有 2 个):(Debian、JBoss)、四核、16 GB RAM
- 数据库服务器:(Suse、MySQL)、四核、64 GB RAM
- 应用服务器与数据库服务器之间的通信需要经过防火墙(可达 100 Mbit)
服务器正在做什么:
- 部署在 JBoss 中的应用程序读取大量文本文件,执行一些合理性检查(涉及与数据库对话),最后将文本文件中的数据存储在我们的数据库中
为了提高吞吐量,我们刚刚安装了 4 个额外的 JBoss 实例,因此现在我们的应用程序有 5 个实例在执行导入(无集群)。不幸的是,性能并没有像我希望的那样提高。
这些是我迄今为止在数据库服务器上收集的统计数据:
顶部:
top - 14:09:28 up 27 days, 9:45, 1 user, load average: 0.65, 0.69, 0.83
Tasks: 92 total, 1 running, 91 sleeping, 0 stopped, 0 zombie
Cpu(s): 10.8% us, 1.1% sy, 0.0% ni, 85.5% id, 1.7% wa, 0.1% hi, 0.8% si
Mem: 65884336k total, 61751244k used, 4133092k free, 524752k buffers
Swap: 8388600k total, 1097864k used, 7290736k free, 32520508k cached
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
9187 mysql 16 0 26.8g 26g 4168 S 49.3 41.7 12455:36 mysqld
1 root 16 0 656 88 56 S 0.0 0.0 0:06.30 init
2 root RT 0 0 0 0 S 0.0 0.0 0:00.62 migration/0
3 root 34 19 0 0 0 S 0.0 0.0 0:00.03 ksoftirqd/0
因此数据库服务器几乎处于空闲状态,我没有进一步调查它。
这些是我迄今为止在应用服务器上收集的统计数据:
顶部:
top - 14:31:11 up 43 days, 23:25, 1 user, load average: 7.31, 7.13, 6.90
Tasks: 87 total, 2 running, 85 sleeping, 0 stopped, 0 zombie
Cpu(s): 58.0%us, 3.9%sy, 0.0%ni, 35.7%id, 0.0%wa, 0.1%hi, 2.2%si, 0.0%st
Mem: 16440520k total, 15894640k used, 545880k free, 79580k buffers
Swap: 8192616k total, 56k used, 8192560k free, 2968948k cached
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
8318 lvs 18 0 2773m 2.2g 13m S 101 14.0 1233:34 java
8367 lvs 18 0 2752m 2.2g 13m S 65 13.9 1217:41 java
8118 lvs 18 0 4731m 2.2g 13m S 58 14.2 1201:01 java
8278 lvs 18 0 2755m 1.9g 13m S 21 12.3 1212:48 java
8411 lvs 20 0 2743m 2.1g 13m S 8 13.4 1206:58 java
1 root 18 0 6124 676 560 S 0 0.0 0:04.10 init
2 root RT 0 0 0 0 S 0 0.0 0:01.18 migration/0
3 root 34 19 0 0 0 S 0 0.0 0:00.12 ksoftirqd/0
这里的平均负载相当高,CPU 利用率也很高。令我困惑的是,CPU 利用率并不是一直很高。这是我使用 iostat 观察 CPU 使用率 20 秒后得到的结果:
lvs@ftpslavedev:~$ iostat -c | head -3 ; iostat -c 1 20 | grep "^ *[0-9]"
Linux 2.6.18-6-amd64 (ftpslavedev) 10/07/09
avg-cpu: %user %nice %system %iowait %steal %idle
2.40 0.00 0.34 0.16 0.00 97.10
58.00 0.00 4.00 0.00 0.00 38.00
50.62 0.00 3.23 0.00 0.00 46.15
35.16 0.00 3.49 0.50 0.00 60.85
75.43 0.00 5.46 0.00 0.00 19.11
72.07 0.00 2.49 0.25 0.00 25.19
50.12 0.00 4.24 0.00 0.00 45.64
50.25 0.00 1.00 0.00 0.00 48.75
32.18 0.00 3.71 0.00 0.00 64.11
51.74 0.00 1.99 0.00 0.00 46.27
53.12 0.00 2.99 1.00 0.00 42.89
47.64 0.00 2.73 0.00 0.00 49.63
13.18 0.00 2.74 0.00 0.00 84.08
0.00 0.00 2.24 0.00 0.00 97.76
0.25 0.00 3.23 0.00 0.00 96.52
0.00 0.00 2.74 0.50 0.00 96.77
0.00 0.00 2.99 0.00 0.00 97.01
17.41 0.00 2.74 0.00 0.00 79.85
23.19 0.00 2.99 0.75 0.00 73.07
23.33 0.00 3.23 0.00 0.00 73.45
因为 CPU 使用率并不是一直很高,所以我怀疑应用服务器和数据库之间的通信是否是瓶颈,因此使用了 sar:
lvs@ftpslavedev:~$ sar -n DEV | head -3 && sar -n DEV 1 20 | grep "eth0.*[1-9]"
Linux 2.6.18-6-amd64 (ftpslavedev) 10/07/09
00:00:01 IFACE rxpck/s txpck/s rxbyt/s txbyt/s rxcmp/s txcmp/s rxmcst/s
16:55:30 eth0 22562.00 21297.00 9632456.00 5156549.00 0.00 0.00 0.00
16:55:32 eth0 19690.10 18800.00 8496563.37 4558991.09 0.00 0.00 0.00
16:55:34 eth0 22716.00 21214.00 10610874.00 5378377.00 0.00 0.00 0.00
16:55:36 eth0 17737.62 16509.90 9027099.01 4784231.68 0.00 0.00 0.00
16:55:38 eth0 10749.69 9625.79 6233610.69 2357184.91 0.00 0.00 0.00
16:55:39 eth0 20929.70 21002.97 5359857.43 4705525.74 0.00 0.00 0.00
16:55:41 eth0 17462.38 17476.24 6281078.22 5062188.12 0.00 0.00 0.00
16:55:44 eth0 19410.19 19368.52 4770402.78 3916590.74 0.00 0.00 0.00
16:55:46 eth0 13388.12 13277.23 3501303.96 2883294.06 0.00 0.00 0.00
16:55:48 eth0 25988.12 24862.38 10358798.02 5966493.07 0.00 0.00 0.00
rxbyt/s 和 txbyt/s 中的值是每秒字节数。如果我将它们转换为每秒兆位,我会得到类似
rxbyt/s r Mbits/s txbyt/s t Mbits/s
9632456 73,49 5156549 39,34
8496563 64,82 4558991 34,78
10610874 80,95 5378377 41,03
9027099 68,87 4784231 36,50
6233610 47,56 2357184 17,98
5359857 40,89 4705525 35,90
6281078 47,92 5062188 38,62
4770402 36,40 3916590 29,88
3501303 26,71 2883294 22,00
10358798 79,03 5966493 45,52
3694266 28,19 2192922 16,73
因此,此处的值通常大于 60 Mbit。考虑到我们的第二台应用服务器也做了同样的事情,我认为我们的防火墙(如前所述,只能处理 100 Mbit)可能是服务器平均负载过高的真正原因,因此即使添加更多服务器也无济于事。
我不知道我对数据的解释是否合理,因此希望您能对此发表评论。
此致,
斯蒂芬
答案1
嗯,问题很复杂 :-/。一点:
我认为很可能我们的防火墙(如前所述,只能处理 100 Mbit)可能是服务器平均负载高的真正原因,因此即使添加更多服务器也无济于事。
如果防火墙限制了数据传输,您不会看到高 CPU 负载(%user 高于此值);相反,您会看到更高的 %iowait(因为其中包括网络 I/O)。因此这似乎不太可能(除非应用程序进行某种轮询)。
我认为您最好的做法是更仔细地检查应用服务器上的高 %user;进行某种分析以找出应用在加载 CPU 时究竟做了什么。这应该会给您一些线索。
防火墙可能也值得研究,因为您已经接近其容量了。
答案2
为什么你没有查看数据库服务器端的流量?如果你的防火墙支持 snmp,你应该能够看到它的负载,如果没有其他的话,至少可以看到输入和输出接口之间的差异。这应该能给你一些想法。此外,虽然你说它支持 100mbit,但仍然不清楚它每秒可以处理多少个数据包。这也是需要记住的事情。