RAM 使用量が制限されたユーザーを作成するにはどうすればよいですか?

RAM 使用量が制限されたユーザーを作成するにはどうすればよいですか?

つまり、4 GB の RAM + 4 GB のスワップがあります。RAM とスワップが制限されたユーザー (RAM 3 GB、スワップ 1 GB) を作成したいのですが、これは可能ですか? 別のユーザーを作成せずに (特別なアプリをインストールせず、デフォルトの Debian/CentOS サーバー構成のみを持ち、sudo を使用しない)、RAM とスワップが制限されたアプリケーションを起動することは可能ですか?

アップデート:

そこでターミナルを開いて入力しました制限コマンド:ulimit -v 1000000これは制限のようなものです976,6Mb。次に、ulimit -a制限が「​​オン」になっていることを確認しました。次に、コンパイルしてアプリを起動するbashスクリプトを開始しましたnohup長いもの nohup ./cloud-updater-linux.sh >& /dev/null &...しかし、しばらくして私は次のことに気づきました:

ここに画像の説明を入力してください

(制限が適用されていない場合は問題ありません。大きなライブラリがダウンロードされ、コンパイルが開始されます。)

しかし、シェルと、シェルで起動されるすべてのプロセスに制限を適用したと思いましたulimit -v 1000000。何が間違っているのでしょうか? ターミナルと、ターミナルが起動するすべてのサブプロセスの RAM 使用量を制限するにはどうすればよいですか?

答え1

ulimitulimitはこれを目的としています。ユーザーごとまたはグループごとにデフォルトを設定できます。

/etc/security/limits.conf

ulimit -v KBYTES最大仮想メモリ サイズを設定します。スワップの最大量を指定することはできないと思います。これは、ユーザーが使用できる仮想メモリの量を制限するだけです。

つまり、次の行ができます(メモリのlimits.conf最大値まで)4G

luser  hard  as   4000000

更新 - CGroups

ulimitおよびによって課される制限はlimits.confプロセスごとにあります。その点については確かによくわかりませんでした。

ユーザーが使用するメモリの総量を制限したい場合(これがあなたの質問です)。cグループ

/etc/cgconfig.conf

group memlimit {
    memory {
        memory.limit_in_bytes = 4294967296;
    }
}

これにより、cgroup最大メモリ制限が 4GiB の が作成されます。

/etc/cgrules.conf

luser   memory   memlimit/

これにより、 によって実行されるすべてのプロセスがで作成された cgroupluser内で実行されるようになります。memlimitcgconfig.conf

答え2

cgroups他の回答で指摘されているように、これが正しい方法です。残念ながら、この問題の完璧な解決策はありません。これについては後述します。cgroup のメモリ使用量制限を設定するには、さまざまな方法があります。ユーザーのログイン セッションを自動的に cgroup の一部にする方法は、システムによって異なります。 レッドハットいくつかのツールがあり、システム

memory.memsw.limit_in_bytesそれぞれ、スワップを含む制限とmemory.limit_in_bytesスワップを含まない制限を設定します。欠点はmemory.limit_in_bytes、cgroup 内のプロセスに代わってカーネルによってキャッシュされたファイルがグループのクォータに対してカウントされることです。キャッシュが少ないとディスク アクセスが増えるため、システムに使用可能なメモリがある場合は、パフォーマンスがいくらか低下する可能性があります。

一方、memory.soft_limit_in_bytescgroup がクォータを超過することを許可しますが、カーネル OOM キラーが呼び出されると、クォータを超過した cgroup が論理的に最初に強制終了されます。ただし、その欠点は、メモリがすぐに必要になり、OOM キラーが強制終了するプロセスを探す時間がない状況があり、その場合、クォータを超過したユーザーのプロセスが強制終了される前に何かが失敗する可能性があることです。

ulimitしかし、 は絶対にこの目的には適さないツールです。 ulimit は仮想メモリの使用に制限を設けますが、これはおそらく望ましくないことです。多くの実際のアプリケーションは、物理メモリよりもはるかに多くの仮想メモリを使用します。ほとんどのガベージコレクションランタイム (Java、Go) は、断片化を避けるためにこの方法で動作します。C の簡単な「hello world」プログラムは、アドレスサニタイザーを使用してコンパイルすると、20TB の仮想メモリを使用できます。 に依存しないアロケータsbrk、たとえばジェマロック(これはRustのデフォルトのアロケータです) またはtcmalloc、仮想メモリ使用量も物理使用量を大幅に上回ります。効率化のため、多くのツールはファイルを mmap しますが、これにより仮想使用量は増えますが、必ずしも物理使用量が増えるわけではありません。私の Chrome プロセスはすべて、それぞれ 2TB の仮想メモリを使用しています。私は 8GB の物理メモリを搭載したラップトップを使用しています。ここで仮想メモリ クォータを設定しようとすると、Chrome が壊れたり、大量の仮想メモリを割り当てる (使用しない) ことに依存する一部のセキュリティ機能を Chrome が強制的に無効にしたり、ユーザーがシステムを悪用するのをまったく防げなかったりします。

答え3

ユーザー レベルでメモリ使用量を制限することはできませんが、ulimit は単一のプロセスに対してのみそれを行うことができます。

でユーザーごとの制限を使用している場合でも/etc/security/limits.conf、ユーザーは複数のプロセスを実行してすべてのメモリを使用できます。

本当にリソースを制限したい場合は、次のようなリソース管理ツールを使用する必要があります。rcapdSolaris のプロジェクトとゾーンによって使用されます。

Linux 上で同様の機能を提供していると思われるものがあり、調べてみるとよいかもしれません。cグループ

答え4

systemd を搭載したシステム (私が使用している Ubuntu 22.04 など) では、CPU/メモリを制限する最も簡単な方法は、cgroups systemd 構成ファイルを使用することです。たとえば、4GB の RAM と 2 つのスレッドに制限する場合は次のようになります。

nano /etc/systemd/system/user-.slice.d/50-memory.conf

そしてそのファイルに次のように書き込みます:

[Slice]
MemoryMax=4G
CPUQuota=200%

systemctl daemon-reload適用するには実行してください)

これはすべてのユーザーに適用されますが、個々のユーザーを上書きすることもできます。/etc/systemd/system/user-[uid].slice.d/50-memory.conf

(conf ファイルの名前は重要ではないと思いますが、よくわかりません)

関連情報