Amazon Linux2(systemd)のプロセス数やファイルディスクリプタ数を変更する
今回はAmazon Linux から Amazon Linux2 への移行をする機会があったので、 プロセス数やファイルディスクリプタ数といったリソース制限の変更に関して備忘録として残しておきます。
なお、以降の手順は公式の Amazon Linux2 のAMIをそのままブートした後に試しています。
ソフトリミットとハードリミット
まず、最初によく聞くソフトリミットとハードリミットの確認しましょう。 Linuxではユーザやプロセスごとに利用できるリソースを制限することできます。
これらには ソフトリミット と ハードリミット の2種類が存在します。
ソフトリミットはユーザの現在の設定値を指し、ハードリミットはユーザ側での変更可能なソフトリミットの上限値を意味します。
ログインユーザへの設定
limits.confを書き換える
Linuxへのログインユーザへの設定は /etc/security/limits.conf
ファイルにて設定がなされます。
なお、これはPAM認証が適用されたログインに限られます。
Ansibleの pam_limits を使うと、このファイルに追記がされます。
cat /etc/security/limits.conf
# /etc/security/limits.conf
#
#This file sets the resource limits for the users logged in via PAM.
#It does not affect resource limits of the system services.
#
#Also note that configuration files in /etc/security/limits.d directory,
#which are read in alphabetical order, override the settings in this
#file in case the domain is the same or more specific.
#That means for example that setting a limit for wildcard domain here
#can be overriden with a wildcard setting in a config file in the
#subdirectory, but a user specific setting here can be overriden only
#with a user specific setting in the subdirectory.
#
#Each line describes a limit for a user in the form:
#
#<domain> <type> <item> <value>
#
#Where:
#<domain> can be:
# - a user name
# - a group name, with @group syntax
# - the wildcard *, for default entry
# - the wildcard %, can be also used with %group syntax,
# for maxlogin limit
#
#<type> can have the two values:
# - "soft" for enforcing the soft limits
# - "hard" for enforcing hard limits
#
#<item> can be one of the following:
# - core - limits the core file size (KB)
# - data - max data size (KB)
# - fsize - maximum filesize (KB)
# - memlock - max locked-in-memory address space (KB)
# - nofile - max number of open file descriptors
# - rss - max resident set size (KB)
# - stack - max stack size (KB)
# - cpu - max CPU time (MIN)
# - nproc - max number of processes
# - as - address space limit (KB)
# - maxlogins - max number of logins for this user
# - maxsyslogins - max number of logins on the system
# - priority - the priority to run user process with
# - locks - max number of file locks the user can hold
# - sigpending - max number of pending signals
# - msgqueue - max memory used by POSIX message queues (bytes)
# - nice - max nice priority allowed to raise to values: [-20, 19]
# - rtprio - max realtime priority
#
#<domain> <type> <item> <value>
#
#* soft core 0
#* hard rss 10000
#@student hard nproc 20
#@faculty soft nproc 20
#@faculty hard nproc 50
#ftp hard nproc 0
#@student - maxlogins 4
# End of file
limits.confよりも優先されるファイル
/etc/security/limits.conf
のコメント内にも記載されていますが、 /etc/security/limits.d
ディレクトリ内のファイルを読み取り、
デフォルト値として設定することができます。
Amazon Linux2(CentOS系)の場合には /etc/security/limits.d/20-nproc.conf
がデフォルトで配備されており、
同ファイルにプロセスのソフトリミットがデフォルトで設定されていることがわかります。
アクシデンタルなフォーク爆弾を防ぐために、とも書かれていますね。
cat /etc/security/limits.d/20-nproc.conf
> # Default limit for number of user's processes to prevent
> # accidental fork bombs.
> # See rhbz #432903 for reasoning.
>
> * soft nproc 4096
> root soft nproc unlimited
設定値の確認方法
設定された項目は ulimit -a
コマンドにて一覧表示して確認可能です。
-H
オプションでハードリミット、 -S
オプションでソフトリミットを確認できます。
注意点として、ulimit
で表示されるのは、カレントユーザの設定値であることです。
別のユーザの設定値を確認したければ su
を使うなどする必要があります。
ulimit -a
> core file size (blocks, -c) 0
> data seg size (kbytes, -d) unlimited
> scheduling priority (-e) 0
> file size (blocks, -f) unlimited
> pending signals (-i) 3828
> max locked memory (kbytes, -l) 64
> max memory size (kbytes, -m) unlimited
> open files (-n) 1024
> pipe size (512 bytes, -p) 8
> POSIX message queues (bytes, -q) 819200
> real-time priority (-r) 0
> stack size (kbytes, -s) 8192
> cpu time (seconds, -t) unlimited
> max user processes (-u) 3828
> virtual memory (kbytes, -v) unlimited
> file locks (-x) unlimited
デーモンへの設定
次にサーバ上で動作させるデーモンプロセスのリソース制限をしましょう。
archlinuxのlimits.confのページ を見ると興味深いことが書いてあります。
ノート: systemd を使っている場合 /etc/security/limits.conf の値は反映されません。/etc/systemd/system.conf, /etc/systemd/user.conf,/etc/systemd/<systemd_unit>/override.conf などを使ってリソースを制御することが可能です。詳しくは systemd-system.conf の man ページを見てください。
デーモンに対する設定においては、systemd場合、 limits.conf
による設定はできないよ、ということです。
全体へのデフォルト設定をする
systemdにてコントロールされるプロセスのデフォルト値を変更するには /etc/systemd/system.conf
ファイルを編集します。
例えば、プロセス数やファイルディスクリプタ数を変更するには以下のように記述をします。
1[Manager]
2DefaultLimitNOFILE=65536
3DefaultLimitNPROC=65536
デーモンごとの設定をする
本来、サービスを運用するのであれば、サービスに対して適切なリソースを割り当てるのが好ましいでしょう。
その場合には /etc/systemd/system/(サービス名).service
ファイルを作成して、 [Service]
ブロックに追加することができます。
なお、 /etc/systemd/system/(サービス名).service
が既に存在し、割当リソースだけ変更したいケースでは /etc/systemd/system/(サービス名).service.d/override.conf
によって上書きするのがよいでしょう。
なお、設定値は (サービス名).service
の記述よりも override.conf
が優先されます。
以下ではファイルディスクリプタの数を定義しています。
1[Service]
2LimitNOFILE=40000
その後、デーモンを再起動して
systemctl daemon-reload
systemctl stop (サービス)
systemctl start (サービス)
設定が反映されているか確認しましょう。
cat /proc/${プロセス番号}/limits
Limit Soft Limit Hard Limit Units
Max cpu time unlimited unlimited seconds
Max file size unlimited unlimited bytes
Max data size unlimited unlimited bytes
Max stack size 8388608 unlimited bytes
Max core file size 0 unlimited bytes
Max resident set unlimited unlimited bytes
Max processes 65536 65536 processes
Max open files 40000 40000 files
Max locked memory 65536 65536 bytes
Max address space unlimited unlimited bytes
Max file locks unlimited unlimited locks
Max pending signals 29779 29779 signals
Max msgqueue size 819200 819200 bytes
Max nice priority 0 0
Max realtime priority 0 0
Max realtime timeout unlimited unlimited us
ファルディスクリプタ(Max open files)が40000になっていますね。
まとめ
systemdでのリソース変更を行いました。 PAM認証でのユーザログインと、systemd上のデーモンプロセスでは設定の仕方が異なるので注意が必要です。
くれぐれも ulimit
だけを変更して、 「Too many open files」 でアプリケーションが死亡しないように注意してくださいね!