centos7
負荷
stress
stress-ng

stress-ngコマンドの使い方

1 はじめに

負荷(CPU,ディスク,メモリ等)をかけるツールです。
stressにくらべ、負荷テストの種類が多いです。
stressコマンドの使い方は、「stressコマンドの使い方」を参照ください。

2 環境

VMware Workstation 12 Player上のゲストマシンを使っています。
ゲストマシンの仕様は以下のとおり。

OSはCentOS7.3です。
[root@server ~]# cat /etc/redhat-release
CentOS Linux release 7.3.1611 (Core)

搭載CPU数は4つです。
[root@server ~]# cat /proc/cpuinfo |grep processor
processor       : 0
processor       : 1
processor       : 2
processor       : 3

搭載メモリ量は1Gです。
[root@server ~]# free -m
              total        used        free      shared  buff/cache   available
Mem:            976         111         688           0         175         704
Swap:          1023           0        1023

3 インストール方法

stress-ngはepelリポジトリにあるので、まず、epelリポジトリをインストールする。
[root@server ~]# yum -y install epel-release

stress-ngパッケージをインストールする。
[root@server ~]# yum -y install stress-ng
[root@server ~]# stress-ng -V
stress-ng, version 0.07.29

4 共通オプションの使い方

共通オプションは、全ての負荷試験で使うことができます。
ここでは、CPU負荷(-c)を例に、共通オプションの使い方を説明します。

4.1 起動時のメッセージ出力を抑止する方法(-q)

CPU負荷をかけるプロセスをバックグラウンドで動かす。
[root@server ~]# stress-ng -c 1 -q &
[1] 1637

ジョブを確認する。stress-ngが動作していることがわかる。
[root@server ~]# jobs
[1]+  実行中               stress-ng -c 1 -q &

stressを終了する。
[root@server ~]# kill %1
[root@server ~]#
[1]+  終了                  stress-ng -c 1 -q

-qオプションを指定しないと、以下のようなメッセージが表示される。
[root@server ~]# stress-ng: info:  [2920] defaulting to a 86400 second run per stressor
stress-ng: info:  [2920] dispatching hogs: 1 cpu

4.2 実行時間の指定方法(-t <時間>)

-t <時間>は、stressの実行時間を指定します。
時間の後に指定するサフィックスは、s(秒),m(分),d(時),d(日)が使えます。
たとえば、5sは5秒、5mは5分を表します。

stressを5秒間実行する。14:17:35に開始して14:17:40に終了したことがわかる。
[root@server ~]# date;stress-ng -c 1 -t 5s;date
2017年 11月 23日 木曜日 14:17:35 JST
stress-ng: info:  [1357] dispatching hogs: 1 cpu
stress-ng: info:  [1357] successful run completed in 5.06s
2017年 11月 23日 木曜日 14:17:40 JST

4.3 指定したCPUでstressを実行する方法(--taskset)

負荷テストを指定したCPUで実行するときに使います。
たとえば、CU負荷テストをCPU=0で実行する、といったときに使います。

CPU=0で実行した場合
stressを実行する。stressをCPU=0で実行する。
[root@server ~]# stress-ng -c 1 --taskset 0 -q &
[1] 1248

プロセスの状態を確認する。プロセスがcpu=0(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,%cpu,psr
COMMAND            PID   PPID WCHAN  %CPU PSR
stress-ng         1248   1144 wait    0.4   0   <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-cpu     1249   1248 -      88.6 ★0   <=== 子プロセス。CPU=0でstressが動作していることがわかる。

ジョブを確認する。
[root@server ~]# jobs
[1]+  実行中               stress-ng -c 1 --taskset 0 -q &

stressを終了する。
[root@server ~]# kill %1
[root@server ~]#
[1]+  終了                  stress-ng -c 1 --taskset 0 -q
CPU=2で実行した場合
stressを実行する。stressをCPU=2で実行する。
[root@server ~]# stress-ng -c 1 --taskset 2 -q &
[1] 1267

プロセスの状態を確認する。プロセスがcpu=2(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,%cpu,psr
COMMAND            PID   PPID WCHAN  %CPU PSR
stress-ng         1267   1144 wait    0.3   2   <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-cpu     1268   1267 -      83.0 ★2   <=== 子プロセス。CPU=2でstressが動作していることがわかる。

stressを終了する。
[root@server ~]# kill %1
[root@server ~]#
[1]+  終了                  stress-ng -c 1 --taskset 2 -q

4.4 スケジューリングポリシーの使い方(--sched)

スケジューリングポリシーについてはここを参照ください。

サポートしているスケジューリングポリシーの確認
OSがサポートしているスケジューリングポリシーを確認する。other,batch,idle,fifo,rrをサポートしていることがわかる。
[root@server ~]# stress-ng --sched which
Available scheduler options are: other batch idle fifo rr
otherポリシーのプロセスを生成した場合
otherポリシーのプロセスを生成する。
[root@server ~]# stress-ng -c 1 --sched other -q &
[1] 1457

プロセスの状態を確認する。otherポリシー(★)で動作していることがわかる。
otherポリシーは、TS(タイムシェアリング)のことです。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,cls
COMMAND            PID   PPID WCHAN  CLS
stress-ng         1563   1139 wait  ★TS
stress-ng-cpu     1564   1563 -     ★TS
rrポリシーのプロセスを生成した場合
rr(round robin)ポリシーのプロセスを生成する。
[root@server ~]# stress-ng -c 1 --sched rr -q &
[1] 1435

プロセスの状態を確認する。rrポリシー(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,cls
COMMAND            PID   PPID WCHAN  CLS
stress-ng         1572   1139 wait  ★RR
stress-ng-cpu     1573   1572 -     ★RR
fifoポリシーのプロセスを生成した場合
fifoポリシーのプロセスを生成する。
[root@server ~]# stress-ng -c 1 --sched fifo -q &
[1] 1467

プロセスの状態を確認する。fifoポリシー(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,cls
COMMAND            PID   PPID WCHAN  CLS
stress-ng         1575   1139 wait  ★FF
stress-ng-cpu     1576   1575 -     ★FF

4.5 プライオリティの使い方(--sched-prio)

--sched-prioオプションは、rrやfifo(リアルタイムスケジューリングポリシー)の
プロセスに優先度を設定するときに使います。
リアルタイムの中で、1が最高優先度、99が最低優先度になります。
other等(通常のスケジューリングポリシー)のプロセスには設定できないようです。

rrポリシーのプロセスを起動する。起動するプロセスの優先度は1を設定する。
[root@server ~]# stress-ng -c 1 --sched rr --sched-prio 1 -q &
[1] 1654

プロセスの状態を確認する。プロセスの優先度が1(★)であることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,cls,rtprio
COMMAND            PID   PPID WCHAN  CLS RTPRIO
stress-ng         1654   1139 wait    RR    ★1
stress-ng-cpu     1655   1654 -       RR    ★1

fifoポリシーのプロセスを起動する。起動するプロセスの優先度は99を設定する。
[root@server ~]# stress-ng -c 1 --sched fifo --sched-prio 99 -q &
[1] 1657

プロセスの状態を確認する。プロセスの優先度が99(★)であることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,cls,rtprio
COMMAND            PID   PPID WCHAN  CLS RTPRIO
stress-ng         1657   1139 wait    FF   ★99
stress-ng-cpu     1658   1657 -       FF   ★99

4.6 負荷テストの種類を表示する方法(--stressors)

負荷テストの種類を表示します。
たとえば、以下の実行結果の中にcpu(★)という負荷テストがあります。
CPUの負荷テストは、CPU使用率を指定したり、CPU負荷を与える方法(--cpu-method)を選択することができます。
CPU負荷を与える方法には、rand()関数の呼び出しや単純な無限ループといった処理を選択することができます。

[root@server ~]# stress-ng --stressors
af-alg affinity aio aiol apparmor atomic bigheap bind-mount brk bsearch cache cap chdir chmod chown chroot clock clone context copy-file ★cpu cpu-online crypt daemon dccp dentry dir dirdeep dnotify dup epoll eventfd exec fallocate fanotify fault fcntl fiemap fifo filename flock fork fp-error fstat full futex get getdent getrandom handle hdd heapsort hsearch icache icmp-flood inotify io iomix ioprio itimer kcmp key kill klog lease link locka lockbus lockf lockofd longjmp lsearch madvise malloc matrix membarrier memcpy memfd mergesort mincore mknod mlock mmap mmapfork mmapmany mq mremap msg msync netlink-proc nice nop null numa oom-pipe opcode open personality pipe poll procfs pthread ptrace pty qsort quota rdrand readahead remap rename resources rlimit rmap rtc schedpolicy sctp seal seccomp seek sem sem-sysv sendfile shm shm-sysv sigfd sigfpe sigpending sigq sigsegv sigsuspend sleep sock sockfd sockpair spawn splice stack stackmmap str stream switch symlink sync-file sysfs sysinfo tee timer timerfd tlb-shootdown tmpfs tsc tsearch udp udp-flood unshare urandom userfaultfd utime vecmath vfork vforkmany vm vm-rw vm-splice wait wcs xattr yield zero zlib zombie

4.7 子プロセスの名前を親プロセスと同じ名前にする方法(-k)

stressコマンドを実行すると、親プロセスと子プロセスが生成されます。
このとき、親プロセスの名前はstress-ngですが、子プロセスの名前は負荷テストの種類毎の名前が付けられます。
たとえば、CPU負荷テストの場合、子プロセスの名前はstress-ng-cpuとなります。
-kオプションを指定すると、子プロセスの名前は親プロセスと同じstress-ngという名前になります。

stressコマンドを実行する。
[root@server ~]# stress-ng -c 1 -q &
[1] 2324

プロセスの状態を確認する。子プロセスの名前が親プロセスと違う名前であることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan
COMMAND            PID   PPID WCHAN
stress-ng         2324   1159 wait    <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-cpu★   2325   2324 -       <=== 子プロセス。親プロセスとは違う名前。

-kオプションを指定してstressコマンドを実行する。
[root@server ~]# stress-ng -c 1 -k -q &
[1] 2329

プロセスの状態を確認する。子プロセスの名前が親プロセスと同じ名前であることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan
COMMAND            PID   PPID WCHAN
stress-ng         2329   1159 wait    <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng★       2330   2329 -       <=== 子プロセス。親プロセスと同じ名前。

5 CPU負荷テスト(-c,--cpu)

5.1 負荷を掛けるプロセス数の指定方法

CPU負荷をかけるプロセス数を指定するオプションです。
CPU使用率を100%近くまで上げることができます。

CPU負荷をかけるプロセス数が1つの場合
CPU負荷をかけるプロセスを1つ生成する。
[root@server ~]# stress-ng -c 1 -q &
[1] 2171

プロセスの状態を確認する。プロセス(stress-ng-cpu)が1つ動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,%cpu
COMMAND            PID   PPID WCHAN  %CPU
stress-ng         2171   1139 wait    4.8    <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-cpu     2172   2171 -    ★95.0    <=== 子プロセス。

ジョブを確認する。
[root@server ~]# jobs
[1]+  実行中               stress-ng -c 1 -q &

ジョブを終了する。
[root@server ~]# kill %1
[root@server ~]#
[1]+  終了                  stress-ng -c 1 -q
CPU負荷をかけるプロセス数が2つの場合
CPU負荷をかけるプロセスを2つ生成する。
[root@server ~]# stress-ng -c 2 -q &
[1] 2166

プロセスの状態を確認する。プロセス(stress-ng-cpu)が2つ動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,%cpu
COMMAND            PID   PPID WCHAN  %CPU
stress-ng         2166   1139 wait    0.0    <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-cpu     2167   2166 -    ★96.3    <=== 子プロセス。
stress-ng-cpu     2168   2166 -    ★96.6    <=== 子プロセス。

ジョブを確認する。
[root@server ~]# jobs
[1]+  実行中               stress-ng -c 2 -q &

ジョブを終了する。
[root@server ~]# kill %1
[root@server ~]#
[1]+  終了                  stress-ng -c 2 -q

5.2 CPU使用率を指定する方法(-l)

指定したCPU使用率の負荷をCPUに与えるオプションです。

CPU使用率を50%に指定する。
[root@server ~]# stress-ng -c 1 -l 50 -q &
[1] 1624

ジョブを確認する。
[root@server ~]# jobs
[1]+  実行中               stress-ng -c 1 -l 50 -q &

プロセスの状態を確認する。CPU使用率が50%程度(★)であることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,%cpu
COMMAND            PID   PPID WCHAN  %CPU
stress-ng         1624   1137 wait    0.1     <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-cpu     1625   1624 -     ★53.0    <=== 子プロセス。CPU使用率が50%程度になっていることがわかる。

stressを終了する。
[root@server ~]# kill %1
[root@server ~]#
[1]+  終了                  stress-ng -c 1 -l 50 -q

CPU使用率を80%に指定する。
[root@server ~]# stress-ng -c 1 -l 80 -q &
[1] 1629

プロセスの状態を確認する。CPU使用率が80%程度(★)であることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-cpu -o comm,pid,ppid,wchan,%cpu
COMMAND            PID   PPID WCHAN   %CPU
stress-ng         1629   1137 wait     0.2     <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-cpu     1630   1629 poll_s ★81.5    <=== 子プロセス。CPU使用率が80%程度になっていることがわかる。

stressを終了する。
[root@server ~]# kill %1
[root@server ~]#
[1]+  終了                  stress-ng -c 1 -l 80 -q

6 CPUアフィニティ負荷テスト(--affinity)

動作するCPUを次々と切り替える、という負荷テストです。

stressコマンドを実行する。起動するプロセス(1個)は、動作するCPUを次々と変更します。
[root@server ~]# stress-ng --affinity 1 -q&
[1] 2038

プロセスの状態を確認する。CPU=0(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-affinity -o comm,pid,ppid,wchan,psr,%cpu
COMMAND            PID   PPID WCHAN  PSR %CPU
stress-ng         2038   1139 wait     0  0.6
stress-ng-affin   2039   2038 -      ★0 18.6

プロセスの状態を確認する。CPU=2(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-affinity -o comm,pid,ppid,wchan,psr,%cpu
COMMAND            PID   PPID WCHAN  PSR %CPU
stress-ng         2038   1139 wait     0  0.2
stress-ng-affin   2039   2038 -      ★2 18.6

プロセスの状態を確認する。CPU=1(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-affinity -o comm,pid,ppid,wchan,psr,%cpu
COMMAND            PID   PPID WCHAN  PSR %CPU
stress-ng         2038   1139 wait     0  0.0
stress-ng-affin   2039   2038 -      ★1 19.4

プロセスの状態を確認する。CPU=3(★)で動作していることがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-affinity -o comm,pid,ppid,wchan,psr,%cpu
COMMAND            PID   PPID WCHAN  PSR %CPU
stress-ng         2038   1139 wait     0  0.0
stress-ng-affin   2039   2038 -      ★3 19.2

stressがsched_setaffinityシステムコールを呼び出して、動作するCPUを次々と変更していることがわかる。
[root@server ~]# strace -ttT -p 2039
16:55:42.770771 sched_setaffinity(0, 128, {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 0 <0.000152>
16:55:42.771186 sched_getaffinity(0, 128, {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 128 <0.000036>
16:55:42.771423 sched_setaffinity(0, 128, {2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 0 <0.007440>
16:55:42.788335 sched_getaffinity(0, 128, {2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 128 <0.009544>
16:55:42.807988 sched_setaffinity(0, 128, {4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 0 <0.009893>
16:55:42.820123 sched_getaffinity(0, 128, {4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 128 <0.000050>
16:55:42.820441 sched_setaffinity(0, 128, {8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 0 <0.005591>
16:55:42.826284 sched_getaffinity(0, 128, {8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}) = 128 <0.000040>
-以下、略-

7 UDP負荷テスト(--udp)

7.1 UDPデータグラムの送受信ペアを生成する方法

UDPの送受信ペアを1組生成する。
[root@server ~]# stress-ng --udp 1 -q &
[1] 2500

プロセスの状態を確認する。UDPデータグラムの送受信ペアが1組生成されたことがわかる。
[root@server ~]# ps -C stress-ng,stress-ng-udp -o comm,pid,ppid,wchan
COMMAND            PID   PPID WCHAN
stress-ng         2500   1159 wait     <=== 親プロセス。wait()を実行して、子プロセスの終了待ち。
stress-ng-udp     2501   2500 -        <=== 子プロセス。UDP受信プロセス
stress-ng-udp     2502   2501 -        <=== 子プロセス。UDP送信プロセス

子プロセス(PID=2502)が実行しているシステムコールを確認する。5000番ポートにデータを送信していることがわかる。
[root@server ~]# strace -p 2502
sendto(4, "RRRRRRRRRRRRRRRRRRRRRRRRRRRRRRRR"..., 832, 0, {sa_family=AF_INET, sin_port=htons(5000), sin_addr=inet_addr("0.0.0.0")}, 16) = 832

子プロセス(PID=2501)が実行しているシステムコールを確認する。51722番ポートからデータを受信していることがわかる。
[root@server ~]# strace -p 2501
recvfrom(4, "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"..., 1024, 0, {sa_family=AF_INET, sin_port=htons(51722), sin_addr=inet_addr("127.0.0.1")}, [16]) = 336

X 参考情報

stressコマンドの使い方

How To Stress Test CPU and Memory (VM) On a Linux and Unix With Stress-ng