負荷がかかったときに Linux の速度が低下するのを防ぐにはどうすればよいですか?

負荷がかかったときに Linux の速度が低下するのを防ぐにはどうすればよいですか?

大量のメモリを消費するプロセスがある場合や、CPU にバインドされたプロセスが多数実行されている場合、システムにログインすることさえ困難になることがよくあります。これを防ぎ、常にシステムの応答性を維持したいと考えています。これを実現する方法はありますか?

編集を明確にする:

私が同じ症状を経験する 2 つの異なる状況についてお話します。

  1. メモリ負荷が非常に高い。単一のプロセスが、使用可能な 64 GB の RAM に近いか、それ以上を消費します。システムの使用率が 100% に近づくと、プログラムは応答しなくなります。

  2. CPU 負荷が非常に高く、スケジュールに問題があります。実行可能なプロセスが 10,000 個あると、同じ問題が発生します。これは 100% CPU 負荷の問題ではないことに注意してください。これらのプロセスのうち 200 個を除くすべてを kill -STOP すると、32 個の CPU すべてが 100% 負荷のままになりますが、システムははるかに使いやすくなります。

そして、私が「システム」と考えるものの問題です。シェル プロセスと他のユーザー プロセスの間に概念的な違いはないことは理解していますが、それは単にそれらを異なるものにするだけの問題です。niceness などのオプションはまさにそれを行います。しかし、前述のように、niceness では、少なくともケース (2.) では問題は解決されませんでした。

私はこれらのシステムを完全に制御しており、すべてのケースで kill -STOP または Cc のみを使用してジョブを停止できました。私が修正したいのは、入力の処理が非常に遅いため、GUI を使用するとこれが非常に困難になり、場合によっては不可能になることです。 特定のジョブに変更を加えるのではなく、全体的にこれを修正したいと思います。

私が試したこと:

  1. 現在実行中の多くのプロセスについては、実行中のすべてのプロセスの niceness を +5 に再設定しましたが、効果はなかったようです。 niceness を 19 に設定しても効果はありませんでした。

  2. 回答の1つで示唆されているように、スケジューラポリシーをIDLEに変更してみましたsudo schedtool -D $(pgrep -u myuser progname -d " ")sudo sh -c 'for pid in $(pgrep -u myuser progname); do chrt -i -p 0 $pid; done;' これにより状況はいくらか改善されるようです。

答え1

問題は、メモリが飽和状態になり、その結果、オペレーティング システムがディスク キャッシュを解放し、プログラムとそのデータをスワップ メモリにスワップする必要に迫られることです。

スワップは、物理メモリの制限に達したときにシステムの動作を継続させる方法です。負荷の軽いシステムでは、システムが動作を継続し、不足が発生したときにページアウトされ、必要なときにわずかな影響でページインされることを意味します。

ほとんどのオペレーティング システムでは、プログラムとコードは「最も最近使われていない」という基準でスワップにフラッシュされます。メモリの負荷は変化し、「優先順位」は何がより重要であるかという主観的な判断の滑りやすい坂道であるため、メモリの「優先順位」について何らかの仮定を立てることは困難です。あるシステムにとってより重要なことは、別のシステムにとってはそれほど重要ではありません。コマンド ライン プログラムは他のプログラムと同じであり、ユーザーが実行する他のプログラムと区別することは不可能です。

大量のメモリを使用する多数のプロセスがある高負荷のシステムでは、競合の問題が発生します。オペレーティング システムがメモリを解放するために何かをディスクにページ アウトしようとした瞬間、別のプロセスが既に他のページを要求しており、そのページを戻す必要があります。何かを戻す要求ごとに、他の何かが押し出されます。

10,000 のプロセスの中で、他のプログラム要求と同じように見える「システム」コマンド ライン プログラム要求よりも優先すべきものをシステムがどうやって決定できるでしょうか?

もう 1 つの問題は、ハード ドライブのシーク時間です。旧式の HDD の場合、ドライブ ヘッドを移動して読み取りまたは書き込みを開始する時間は、約 9.5 ミリ秒です。さまざまな領域に対して一度に多数の要求が発生すると、シーク時間が他のすべての時間よりも優先され、実際の有効時間と帯域幅が驚くほど小さな数値に減少します。SSD は役立ちますが、メモリが限られている場合は、それほど役に立ちません。

同様のボトルネックはシステム全体で発生し、さまざまな症状を呈します。オペレーティング システムは多数の同時プログラムを管理できますが、それ自体は「単なる」プログラムであり、他のすべてのものの中で時間を必要とします。スワップ ファイルの使用は、最も極端なボトルネックの 1 つにすぎません。

このようにシステムを氾濫させて、システムがそれを「処理する」ことを期待するのは良い考えではありません。

常に、持っているメモリよりも多くのメモリを使用している場合は、メモリを追加購入する必要があります。データの読み取りまたは書き込みのためにハード ドライブの時間を争うプロセスが何千もある場合は、負荷をより多くのマシンまたはドライブに分散する必要があります。


他の状況では、10,000 個のアクティブなプロセスがある場合、競合と非現実的な期待の両方の問題が発生します。

1 つの問題は、「niceness」が必ずしも常に低い優先度であるとは限らないことです。これはオペレーティング システムのスケジューラに依存しており、プロセスを追加し続けると、特定のプロセスに割り当てられる時間の量を削減することになるため、公平で有用なシステムを実現するのに逆効果になる可能性があります。

Unix姉妹サイトのこの質問を参照してくださいナイスワークはどうですか?これは完全に公平なスケジューラについて説明しています。

CFS には、スケジューリング期間のターゲット レイテンシがあります。ターゲット レイテンシが小さいほど対話性は向上しますが、ターゲット レイテンシが小さくなると、スイッチング オーバーヘッドが増加し、全体的なスループットが低下します。

...

ここで、niceness が 0 (デフォルト) のプロセスと、niceness が 5 のプロセスの 2 つを考えてみましょう。対応する重みの比例差はおよそ 1/3 です。つまり、優先度の高いプロセスは約 15 ミリ秒のタイムスライスを受け取り、優先度の低いプロセスは 5 ミリ秒のタイムスライスを受け取ります。

このスケジューラでは、nicenessは10,000のプロセスがすべき時間は短くなりますが、その数が多すぎるため、「公平な」スケジュールのタイム スライス値の下限に達し、十分なサイズのタイム スライスを誰も得られない可能性があります。CPU へのタスクのプルまたは CPU からのプルが時間の大半を占めるという制限に達する可能性もあります。

これは事実上、ハード ドライブの競合と同じです。特定のプロセスで作業する有効な時間よりも、プロセス間の切り替えに多くの時間を費やすようにシステムを強制することになります。

スケジューラの詳細については、詳しくは、man7.org/linux/man-pages/man7/sched.7.html を参照してください。

より適切な数のプロセス (100 ~ 200) を使用すると、OS タスクとプロセスの間で適切な時間が分割されます。

一度に 10,000 個のタスクを開始するのではなく、古いタスクが終了するたびに新しいタスクを開始する必要があります。

関連情報