web-dev-qa-db-ja.com

isolcpusの一連のコアでタスクセットが機能しない

序文として、AMD64チップセットのカーネル3.2でDebian Wheezyを使用しています。私のマシンには2つのXeon E5-2690コアがあります。 1つのCPU上のすべてのコアが1つのプロセス専用になるように、ブートパラメーターを設定しました。これを行うために、grubでisolcpus = 8,9,10,11,12,13,14,15を設定しました。

ここまでは順調ですね。ここで、特定のコマンドに分離されたCPUを使用したいとしましょう。簡単にするために、単純な無限ループを使用します。

$ taskset -c 8-15 bash -c 'while true; echo hello>/dev/null;完了 '&

これまでのところ、topは、コア8が最大100%の使用率まで回転することを示しています。次に、そのコマンドをもう一度起動するとします。

$ taskset -c 8-15 bash -c 'while true; echo hello>/dev/null;完了 '&

上部はコア9〜15がアイドルのままで、2つのプロセスがコア8を共有していることを示しています。代わりにこれを行うと、

$ taskset -c 8 bash -c 'while true; echo hello>/dev/null;完了 '&

$ taskset -c 9 bash -c 'while true; echo hello>/dev/null;完了 '&

コア8と9は、それぞれ100%の使用率になります。コア1〜7の同じタスクセットが関連するコアにプロセスを適切に分散するため、これはisolcpusにのみ適用されます。さらに、「taskset -p」は、8〜15プロセスのアフィニティマスクが正しく設定されていることを示しています。カーネルスケジューラは、isolcpusアフィニティマスクで指定された最低のコア以外の使用を拒否しているようです。

さて、これは通常、上記の例では大したことではなく、各プロセスに個別のコアを指定するだけです。ただし、専用のCPUで高度にマルチスレッド化されたアプリケーションを実行したい。コアセットを指定し、スレッドプールが自動的に使用するようにします。スポーンされる個々のスレッドごとにプロセッサアフィニティを個別にリセットする必要はありません。

スケジューラにisolcpuセットから複数のコアを提供する方法を知っている人はいますか?

13
user79126

1日の欲求不満の後、私は解決策を見つけました。この動作は、デフォルトのカーネルスケジューラアルゴリズム(このディストリビューション/カーネルではSCHED_OTHER)のアーティファクトのようです。プロセスを別のアルゴリズムに変更すると問題が解消され、isolcpusはプロセス/スレッド全体で適切に利用されます。

最終的にはSCHED_RRを使用しましたが、SCHED_FIFOとSCHED_IDLEもテストしました。どちらも機能しているようです。このプロセスは、chrtユーティリティを使用して、代替アルゴリズムで起動できます。

$ Sudo chrt -r 1 [コマンド]

(非ルートとして実行する場合は、setcapユーティリティを使用して、コマンドに関連するバイナリファイルでCAP_SYS_Niceを有効にできます)

10
user79126