Metal の最適化: Apple のグラフィックス フレームワーク用に作成されたコードを改善する方法

Metal グラフィックス コードを最適化して最高のパフォーマンスを得る方法は数多くあります。ここでは、コードを Metal フレームワークに合わせてより適切な形に整える方法を説明します。

Apple GPU アーキテクチャ

AppleのGPUは、タイルベースの遅延レンダラー- これは、タイリングとレンダリングという 2 つの主要なパスを使用することを意味します。全体的なレンダリング パイプラインを以下に示します。

これら 2 つのフェーズは、ジオメトリが計算および作成されるときと、すべてのピクセル レンダリングが処理されるときの 2 つのフェーズとして考えることができます。

最新の Apple GPU ソフトウェアでは、ジオメトリが計算されてメッシュとポリゴンに分割され、フレームごとに 1 つの画像としてピクセルベースの画像にレンダリングされます。

最新の Apple GPU には、シェーダ、テクスチャ、ピクセル バックエンド、専用タイル メモリを処理する特定のサブセクションが各コアにあります。各コアはレンダリング中にこれらの 4 つの領域を使用します。

各フレームのレンダリング中に複数のパスが使用され、複数の GPU コアで実行され、各コアが複数のタスクを処理します。一般に、コアの数が多いほど、パフォーマンスが向上します。

最新の Apple GPU レンダリング パイプライン。

GPUカウンター

このパフォーマンスを測定するには、GPUカウンターが使用されています。

GPU カウンターは各 GPU の負荷を追跡し、それぞれが十分な作業を行っているかどうかを測定します。また、パフォーマンスのボトルネックも見つかります。

最後に、GPU カウンターは、パフォーマンスを高速化するために最も時間がかかるコマンドを最適化します。

Apple GPU パフォーマンス カウンターには 150 種類以上あり、それらすべてをカバーすることはこの記事の範囲を超えています。

すべてのパフォーマンス カウンター データを理解するという問題があります。これを行うには、組み込みの Metal System Trace と Metal Debugger を使用します。Xcodeそして楽器。

Metal System Trace とデバッガについては、「前のメタル記事

Metal GPU カウンターは 4 つあり、アプリやゲームで Metal を最適化する重要な方法が含まれています。彼らです:

  1. パフォーマンスリミッター
  2. メモリ帯域幅
  3. 占有率
  4. 隠れた表面の除去

パフォーマンスリミッター、 またはリミッターカウンター実行中の作業を検出し、並列実行をブロックまたは速度低下させる可能性のあるストールを検出することで、複数の GPU サブシステムのアクティビティを測定します。

最新の GPU は、演算、メモリ、ラスタライズ作業を並行して (同時に) 実行します。パフォーマンス リミッターは、コードの速度を低下させるパフォーマンスのボトルネックを特定するのに役立ちます。

Apple の Instruments アプリを使用すると、パフォーマンス リミッターを使用してコードを最適化できます。 Instruments には 6 種類の異なるパフォーマンス リミッターがあります。

Appleの楽器アプリ。

メモリ帯域幅カウンター

メモリ帯域幅 GPU カウンターは、GPU とシステム メモリ間の転送を測定します。 GPU は、バッファまたはテクスチャがアクセスされるたびにシステム メモリにアクセスします。

ただし、システム レベル キャッシュもトリガーされる可能性があることに注意してください。つまり、実際の DRAM 転送速度よりも高いメモリ スループットが小規模にバーストする場合があることを意味します。これは正常です。

メモリ帯域幅カウンターの値が高い場合は、転送によってレンダリングが遅くなっている可能性があります。これらのボトルネックを軽減するには、いくつかの方法があります。

メモリ帯域幅の低下を軽減する 1 つの方法は、作業データ セットのサイズを減らすことです。これにより、システム メモリから転送されるデータが少なくなるため、速度が向上します。

もう 1 つの方法は、現在のレンダー パスで必要なデータのみをロードし、将来のレンダー パスで必要なデータのみを保存することです。これにより、全体のデータ サイズも削減されます。

ブロック テクスチャ圧縮 (ASTC) を使用してテクスチャ アセット サイズを削減したり、実行時に生成されるテクスチャの可逆圧縮を使用したりすることもできます。

占有率合計スレッド プールのうち現在実行されているスレッドの数を測定します。 100% の占有率は、特定の GPU が処理できるスレッド数と全体的な作業の点で現在最大値に達していることを意味します。

占有GPUカウンターGPU によって使用される合計スレッド容量の割合を測定します。この合計は、コンピューティング、頂点、およびフラグメントの占有率の合計です。

隠れた表面の除去通常、フラグメント処理の前、つまりタイル頂点バッファがラスタライズされるために GPU に送信された直後の各レンダー パスの中間のどこかで発生します。

深度バッファと隠蔽サーフェスの削除は、現在のシーンのビューのカメラに表示されないサーフェスを削除するために使用されます。これらのサーフェスを描画する必要がないため、パフォーマンスが向上します。

たとえば、不透明な 3D オブジェクトの裏側のサーフェスは、カメラ (およびビューア) には決して表示されないため、描画する必要はありません。したがって、それらを描画しても意味がありません。

カメラに対して前にある他の 3D オブジェクトによって隠されているサーフェスも削除されます。

隠面の削除中に GPU カウンターを使用して、ラスター化されたピクセルの合計数、フラグメント シェーダーの数 (実際にはフラグメント シェーダーの呼び出し数)、および保存されたピクセルの数を確認できます。

GPU カウンターを使用してブレンディングを最小限に抑えることもできますが、これによってもパフォーマンス コストが発生します。

隠面除去による描画を最適化するには、可視性の状態の順序に従ってオブジェクトを描画する必要があります。つまり、オブジェクトが不透明かどうかをテストし、半透明によってテストし、不透明なメッシュと不透明でないメッシュのインターリーブを避けるようにします。

リソース

Apple の Metal 開発者ページ (developer.apple.com/metal/tools/) など、さまざまな Metal リソースが利用可能です。WWDCビデオ、および優れたサードパーティの書籍Metal プログラミング ガイド: Swift によるチュートリアルとリファレンスジャニー・クレイトン著。

Metal の最適化を始めるには、必ず WWDC ビデオをチェックしてください。GPU カウンターを使用して Metal アプリとゲームを最適化するWWDC20より、金属を使用した GPU の利用こちらもWWDC20から、最適化された Metal アプリとゲームを提供WWDC19より。

次に読んでくださいXcode での Metal ワークロードのキャプチャそしてメタルデバッグの種類Apple の開発者向けドキュメント Web サイトの Metal Debugger ページにあります。

もありますMetal ワークロードの分析Metal Debugger のドキュメントを参照してください。

Xcode の Metal Debugger と Trace のドキュメントに多くの時間を費やして、さまざまな GPU カウンターとパフォーマンス グラフがどのように機能するかを詳しく学ぶことをお勧めします。これらがなければ、Metal コードで実際に何が起こっているかを詳細レベルで把握することはできません。

圧縮テクスチャについては、こちらも読む価値があります。適応型のスケーラブルなテクスチャ圧縮(ASTC) とそれが最新のレンダリング パイプラインでどのように機能するかについて説明します。

ARM の開発者 Web サイトには ASTC の概要が詳しく記載されていますコミュニティ.arm.com。また、チェックしてください高性能グラフィックス.org

金属の性能の最適化は広大かつ複雑なテーマです。私たちはまだ始まったばかりであり、今後の記事でこのトピックをさらに詳しく検討していきます。