TL; DRバージョン:「CPUとGPUの動作を並行して実行できるように、Python / PyCUDAを使用して複数のGPUへのカーネル呼び出しをラウンドロビンするための最良の方法は何ですか?」「私がこれを最初に尋ねた人にはなれなかった。私が読み上げるべきことは何か?」という側面を持っている。
完全版:
複数のGPUを搭載したシステムでCUDAを使用するアプリケーションでコンテキストなどを処理するための最良の方法を知りたいです。コンテキストの再利用とレクリエーションが適切な場合のガイドラインについて説明している文献を探していますが、これまでのところ、ベストプラクティスや経験則などの概要を説明するものは見つかりませんでした。
私たちがしなければならないことの一般的な概要は次のとおりです。
- リクエストは中央のプロセスに入ります。
- そのプロセスは、単一の要求を処理するために分岐します。
- データはDBからロードされます(比較的高価です)。
以下は、リクエストに基づいて任意の回数(数十回)繰り返されます。
- 後のカーネルに必要なデータを計算するためのいくつかの簡単なカーネル呼び出し。
- 1回の遅いカーネル呼び出し(10秒)。
ついに:
- カーネル呼び出しの結果は、CPUで収集および処理されてから、保存されます。
現時点では、各カーネル呼び出しはコンテキストを作成してから破棄しますが、これは無駄に思えます。セットアップには、コンテキストとカーネルの負荷ごとに約0.1秒かかります。これはそれほど大きなことではありませんが、他のより高速なタスクをGPUに移動することはできません。
機械を効率よく使うために、コンテキストなどを管理する最善の方法を模索しています。シングルGPUの場合、それは比較的単純だと思います。
- GPU作業を開始する前に、コンテキストを作成します。
- データの最初のセットのカーネルを起動します。
- シリーズの最後のカーネル呼び出し後のイベントを記録します。
- 最初のデータセットがGPUで計算している間に、CPUで2番目のデータセットを準備します。
- 2番目のセットを起動し、繰り返します。
- 結果を収集して保存する前に、各イベントが同期されていることを確認してください。
オーバーラップしたメモリコピーを適切に使用することを前提とすると、これでうまくいくようです。
ただし、数十のアイテムのそれぞれをラウンドロビンして複数のGPUで処理する場合は、どうすればよいかわかりません。
ホストプログラムはPython2.7で、PyCUDAを使用してGPUにアクセスします。現在、マルチスレッドではありません。私はそれをそのままにしておきたいのですが(「今、2つの問題があります」など)、答えがスレッドを意味する場合、それはスレッドを意味します。同様に、データをブロックするときにメインスレッドでevent.synchronize()を呼び出すことができれば便利ですが、私たちのニーズでは、ハードウェアを効率的に使用することがより重要です。一度に複数のリクエストを処理する可能性があるため、このプロセスがGPUを使用していないときに、他のプロセスにGPUを使用させることが重要です。
排他的計算モードを使用する明確な理由はないと思います(つまり、カードのメモリを1つの作業項目でいっぱいにしない)ので、長年のコンテキストを含むソリューションはないと思いますテーブルから外れています。
私の質問をカバーする他のコンテンツへのリンクの形での回答は、APIだけでなく、その理由について十分に詳細に説明されていれば、完全に受け入れられます(推奨されます) 。読んでくれてありがとう!