注意事項

注意事項

Linuxは(まだ)POSIX.1標準に準拠していません。説明するプロセスのaは、renice「プロセスのすべてのシステム全体のスレッド」に影響します。pthreads(7) ドキュメント「スレッドは共通の良い価値を共有しません」。

しかし、時にはrenice特定のプロセスに関連する「すべてのもの」を持つのが便利かもしれません(例えば、Apacheサブプロセスとそのスレッドの両方)。だから、

  • reniceどうやって手に入れることができますか?特定のプロセスに属していますか?
  • reniceどうやって手に入れることができますか?サブプロセス特定のプロセスに属していますか?

私は非常に簡単な解決策を探しています。

わかりましたプロセスグループ時には役に立つかもしれませんが、私が望む仕事に常に合うわけではありません。より広い範囲または他のプロセスセットを含めることができます。

cgroup管理者を使用するsystemdことも役に立ちますが、それについて聞きたい場合でも主に「標準」ソリューションを探しています。

編集:また、man (7) pthreads「プロセス内のすべてのスレッドは同じスレッドグループに配置されます。スレッドグループのすべてのメンバーは同じPIDを共有します」と表示されます。それでは、renice独自のPIDなしで何かを持つことができますか?

答え1

/proc/$PID/task特定のプロセスのすべてのスレッドを見つけるために使用できるので、次のことができます。

$ ls /proc/$PID/task | xargs renice $PRIO

reniceすべて特定のプロセスに属します。

同じ方法を/proc/$PID/task/$PID/children使用してすべての項目を見つけることができます。サブプロセス(または/proc/$PID/task/*/childrenすべてが必要な場合サブプロセスみんな与えられたプロセス)。

$ cat /proc/$PID/task/$PID/children | xargs renice $PRIO
$ cat /proc/$PID/task/*/children | xargs renice $PRIO

答え2

すべてのPIDを探すrenice 再帰的

保留中のプロセスの子プロセス(子プロセスまたはスレッドグループのプロセス)であるすべてのプロセス(「一般」または「スレッド」)のPIDを取得する必要があります。これは再帰的でなければなりません(子供の子供を考慮)。

アントン・レオンティエフ答えはこれを行うためのヒントを提供します。フォルダ内のすべてのフォルダ名は、潜在的なサブプロセスを一覧表示するファイルを/proc/$PID/task/含むスレッドのPIDです。children

ただし、再帰機能が不足しているため、これを見つけるための迅速で汚れたシェルスクリプトは次のとおりです。

#!/bin/sh
[ "$#" -eq 1 -a -d "/proc/$1/task" ] || exit 1

PID_LIST=
findpids() {
        for pid in /proc/$1/task/* ; do
                pid="$(basename "$pid")"
                PID_LIST="$PID_LIST$pid "
                for cpid in $(cat /proc/$1/task/$pid/children) ; do
                        findpids $cpid
                done
        done
}

findpids $1
echo $PID_LIST

プロセスPID 1234が再帰的に処理したいプロセスである場合は、次のことができます。

renice -n 15 -p $(/path/to/findchildren.sh 1234)

注意事項

価値とCPUシェアのどちらが良いですか?

これで、自動ワークグループ化のため、特に次のものを使用するときに注意してください。システム。よりこの回答詳細については。

スレッドとプロセスの違い

メモ:この回答Linuxスレッドが正確に説明されました。

簡単に言えば、カーネルは「実行可能なエンティティ」だけを処理します。走るそして予定。カーネルの観点では、これらのエンティティをプロセスと呼びます。スレッドは(少なくとも)メモリ空間と信号ハンドラを他のプロセスと共有するプロセスです。これらの各プロセスには、システム全体の一意の識別子であるプロセスID(PID)があります。

その結果、あなたはできる renice各「スレッド」は独自の特性を持っているため、分離されています。私自身PID 1


1見るこの回答PID(ProcessID)とTID(ThreadID)の違いについて詳しく学んでください。

答え3

時々、TIDまたはpsコマンドLPWで作成されたプロセスPIDとスレッドIDを混同しないでください。このsコマンドにはスレッドを表示するオプションがあり、下topまたは下のhtopスレッドを切り替えてH文字ごとに進めることができます。 @Totorが以前に述べたように、NPTL(現在のカーネル> 2.6実装)を使用すると、すべてのスレッドのpidは同じですが、tidは異なります。以下を使用して、プロセス内のすべてのスレッドを表示できます。

$ ps -Ljf <pid>

これらのtidはデフォルトディレクトリの名前です/proc/<pid>/taskレニス(1)デフォルトの引数がpidであると仮定すると、pidに適用するとメインスレッドに対してのみ調整されます(これはLinux実装のバグです)。優先順位の設定(2))、スレッドのティッド、サイズ変更にも適用できます。これが@Antonの答えが有効な理由です。

しかし、ほとんどの場合、望ましい結果を得るためのより簡単な方法があります。これらのスレッドはすべて、グループリーダーのpidである同じpgidを共有します。 pgidから次のコマンドを実行して再起動できます。

$ renice -g <pgid>

同じリーダーセットに依存する他のプロセスを再度有効にしたくない場合は、@Antonのレシピを使用する必要があります。

$ renice <priority> $(ls -1 /proc/<pid>/task)

または:

$renice <priority> $(ps --no-header -Lo tid <pid>)

再利用したいプロセス、つまり同じpgidを共有するプロセスに加えて、同じグループに異なるプロセスがあるかどうかを知りたい場合があります。あなたはそれを使用することができます参考(1)psグループリーダーごとにプロセスを選択することはできませんが、grepでそれを行うことpsができます。 pgidを使用したプロセスは次1908のように提供されます。

$ ps --no-header axo pid,pgid |sed -n '/^ *[0-9][0-9]*  *1908/s/[0-9][0-9]* *$//p'

またはsedよりawkを好む場合:

$ ps --no-header axo pid,pgid|awk '{if ($2=="1908") print $1;}'

答え4

reniceを使用する場合は、-p(プロセスID)の代わりに-g(プロセスグループ)パラメータを使用することをお勧めします。 bash-fooがなくても同じことができます。

つまり

(sudo) renice -n <NEW_PRIORITY> -g <MAIN_PROCESS_ID>

関連情報