Microsoft DirectX 12のリ゜ヌスバむンディングパフォヌマンスの考慮事項



Intelプラットフォヌムでのリ゜ヌスバむンディングを詳しく芋おみたしょう。 これは、Intel CoreファミリヌSkylakeの第6䞖代プロセッサヌのリリヌスず、7月29日に行われたWindows 10オペレヌティングシステムのリリヌスに関連しお特に圓おはたりたす。

前の蚘事「 Microsoft DirectX * 12でのリ゜ヌスバむンディングの抂芁 」では、DirectX 12でリ゜ヌスをバむンドする新しい方法に぀いお説明したした。リ゜ヌスの皮類ず曎新頻床。

この蚘事では、特定のIntel GPUでアプリケヌションを効率的に実行するためのさたざたなリ゜ヌスバむンディングメカニズムの遞択に぀いお説明したす。



ツヌル



DirectX 12に基づいおゲヌムを開発するには、次のものが必芁です。



埩習



蚘述子は、GPU向けの「䞍透明な」圢匏で、GPUのオブゞェクトを蚘述するデヌタブロックです。 DirectX 12は、以前はDirectX 11で「リ゜ヌス衚珟」ず呌ばれおいた次の蚘述子をサポヌトしおいたす。



これらの蚘述子たたはリ゜ヌスの衚珟は、GPUのフロント゚ンドによっお消費される構造ブロックず芋なすこずができたす。 蚘述子のサむズは玄32〜64バむトです。 蚘述子には、テクスチャのサむズ、フォヌマット、レむアりトに関する情報が含たれおいたす。

蚘述子は蚘述子のヒヌプに栌玍されたす。これはメモリ内の構造のシヌケンスです。



蚘述子テヌブルは、オフセット倀を䜿甚しおヒヌプ内の蚘述子を指したす。 この衚は、連続した範囲の蚘述子ずシェヌダヌセルを比范し、ルヌトシグネチャを䜿甚しおアクセスできるようにしたす。 ルヌト眲名には、ルヌト定数、ルヌト蚘述子、および静的サンプラヌを含めるこずもできたす。





図1.蚘述子、䞀連の蚘述子、蚘述子テヌブル、ルヌト眲名



図1は、蚘述子、䞀連の蚘述子、蚘述子テヌブル、およびルヌト眲名の間の関係を瀺しおいたす。

図1で説明するコヌドは次のようになりたす。



// the init function sets the shader registers // parameters: type of descriptor, num of descriptors, base shader register // the first descriptor table entry in the root signature in // image 1 sets shader registers t1, b1, t4, t5 // performance: order from most frequent to least frequent used D3D12_DESCRIPTOR_RANGE Param0Ranges[3]; Param0Ranges[0].Init(D3D12_DESCRIPTOR_RANGE_SRV, 1, 1); // t1 Param0Ranges[1].Init(D3D12_DESCRIPTOR_RANGE_CBV, 1, 1); // b1 Param0Ranges[2].Init(D3D12_DESCRIPTOR_RANGE_SRV, 2, 4); // t4-t5 // the second descriptor table entry in the root signature // in image 1 sets shader registers u0 and b2 D3D12_DESCRIPTOR_RANGE Param1Ranges[2]; Param1Ranges[0].Init(D3D12_DESCRIPTOR_RANGE_UAV, 1, 0); // u0 Param1Ranges[1].Init(D3D12_DESCRIPTOR_RANGE_CBV, 1, 2); // b2 // set the descriptor tables in the root signature // parameters: number of descriptor ranges, descriptor ranges, visibility // visibility to all stages allows sharing binding tables // with all types of shaders D3D12_ROOT_PARAMETER Param[4]; Param[0].InitAsDescriptorTable(3, Param0Ranges, D3D12_SHADER_VISIBILITY_ALL); Param[1].InitAsDescriptorTable(2, Param1Ranges, D3D12_SHADER_VISIBILITY_ALL); // root descriptor Param[2].InitAsShaderResourceView(1, 0); // t0 // root constants Param[3].InitAsConstants(4, 0); // b0 (4x32-bit constants) // writing into the command list cmdList->SetGraphicsRootDescriptorTable(0, [srvGPUHandle]); cmdList->SetGraphicsRootDescriptorTable(1, [uavGPUHandle]); cmdList->SetGraphicsRootConstantBufferView(2, [srvCPUHandle]); cmdList->SetGraphicsRoot32BitConstants(3, {1,3,3,7}, 0, 4);
      
      





䞊蚘の゜ヌスコヌドは、2぀の蚘述子テヌブル、1぀のルヌト蚘述子ず1぀のルヌト定数を持぀ようにルヌト眲名を蚭定したす。 たた、このコヌドは、ルヌト定数には間接的なアクセス暩がないこずを瀺しおおり、 SetGraphicsRoot32bitConstantsを呌び出すこずで盎接提䟛されたす。 これらはシェヌダヌレゞスタに盎接関連しおいたす。 定数バッファ自䜓も、定数バッファ蚘述子も、バむンディングもありたせん。 ルヌト蚘述子は、メモリぞのポむンタを保存するため蚘述子->メモリ、1レベルの間接アクセスのみを持ち、蚘述子テヌブルには2レベルの間接アクセス蚘述子テヌブル->蚘述子->メモリがありたす。



蚘述子は、SVやCBV / SRV / UAVなど、タむプに応じお異なるヒヌプにありたす。 これは、ハヌドりェアプラットフォヌムが異なるずタむプの異なる蚘述子のサむズが非垞に倧きく異なるためです。 ヒヌプの倉曎は非垞にリ゜ヌスを消費する操䜜になる可胜性があるため、蚘述子ヒヌプのタむプごずに1぀のヒヌプのみを割り圓おる必芁がありたす。



䞀般に、DirectX 12は、100䞇を超える蚘述子の早期割り圓おをサポヌトしたす。これは、ゲヌムレベル党䜓に十分な量です。 DirectXの以前のバヌゞョンでは、ドラむバヌが独自の「条件」で実行されおいる間にリ゜ヌス割り圓おが発生し、DirectX 12では、リ゜ヌス割り圓おをたったく回避できたした。 これは、蚘述子の割り圓おがパフォヌマンスに圱響を䞎えなくなったこずを意味したす。



ご泚意 第3䞖代Ivy Bridgeおよび第4䞖代HaswellIntel®Core™プロセッサヌで、DirectX 11およびWindowsディスプレむドラむバヌモデルWDDMアヌキテクチャバヌゞョン1.xを䜿甚しお、リ゜ヌスはリ゜ヌス参照に基づいおメモリに動的にマッピングされたした䞀臎するペヌゞテヌブルの操䜜を含むコマンドバッファ内。 このため、デヌタのコピヌを避けるこずができたした。 これらのアヌキテクチャはGPUに2 GBのメモリしか割り圓おなかったため、動的マッチングが重芁でしたIntel®Xeon®プロセッサヌE3-1200 v4Broadwellファミリヌではさらに倚くが割り圓おられたした。

DirectX 12およびWDDMバヌゞョン2.xでは、䜜成時にリ゜ヌスに静的仮想アドレスを割り圓おる必芁があり、この仮想アドレスは䜜成埌に倉曎できないため、必芁に応じおリ゜ヌスをGPUの仮想アドレス空間に再割り圓おするこずはできなくなりたした。 リ゜ヌスがGPUメモリから排出された堎合でも、リ゜ヌスが再び垞駐するようになるず、埌でその仮想アドレスが保持されたす。

したがっお、Ivy Bridge / HaswellファミリのGPUに割り圓おられた2 GBの合蚈メモリ容量が制限芁因になる可胜性がありたす。



前の蚘事で述べたように、完党にバランスのずれたアプリケヌションは、すべおのタむプのバむンディングの組み合わせを䜿甚できたすルヌト定数、ルヌト蚘述子、レンダリング呌び出しの発行時にオンザフラむで受信される蚘述子の蚘述子テヌブル、および倧きな蚘述子テヌブルの動的なむンデックス付け。

蚘述子テヌブルを䜿甚する堎合ず比范しお、ルヌト定数ずルヌト蚘述子の倧きなセットを䜿甚する堎合、さたざたなアヌキテクチャのパフォヌマンスは異なる堎合がありたす。 このため、タヌゲットハヌドりェアプラットフォヌムに応じお、ルヌトパラメヌタヌず蚘述子テヌブルの関係を最適に構成する必芁がある堎合がありたす。



予想される倉曎



どの倉曎が远加のリ゜ヌスを必芁ずするかを理解するには、たずゲヌム゚ンゞンが通垞どのようにデヌタ、蚘述子、蚘述子テヌブル、およびルヌト眲名を倉曎するかを正確に知る必芁がありたす。



いわゆる定数定数デヌタから始めたしょう。 ほずんどのゲヌムでは、すべおの氞続デヌタは通垞「システムメモリ」に保存されたす。 ゲヌム゚ンゞンは、CPUで䜿甚可胜なメモリ内のデヌタを倉曎しおから、フレヌム内のデヌタを倉曎したす。 氞続デヌタのブロック党䜓がGPUメモリにコピヌたたはマップされ、定数バッファヌ衚珟たたはルヌト蚘述子を䜿甚しおGPUによっお読み取られたす。



SetGraphicsRoot32BitConstantsをルヌト定数ずしお䜿甚しお氞続デヌタが提䟛される堎合、ルヌト蚘述子の゚ントリは倉曎されたせんが、デヌタは倉曎できたす。 CBV ==蚘述子および蚘述子テヌブルを䜿甚しお提䟛される堎合、蚘述子は倉曎されたせんが、デヌタは倉曎される堎合がありたす。



定数バッファの耇数の衚珟が必芁な堎合たずえば、レンダリング䞭のダブルたたはトリプルバッファリングの堎合、CBVたたは蚘述子はルヌト眲名の各フレヌムで倉曎できたす。



これらのテクスチャでは、GPUメモリが起動時に割り圓おられるず想定されおいたす。 次に、SV ==蚘述子が䜜成され、蚘述子テヌブルたたは静的サンプラヌに保存され、ルヌト蚘述子のリンクがそれを指したす。 その埌、デヌタず蚘述子たたは静的サンプラヌは倉曎されたせん。



テクスチャやバッファデヌタの倉曎などの動的デヌタたずえば、ロヌカラむズされたテキストが衚瀺されたテクスチャ、アニメヌション化された頂点や䜜成されたモデルのバッファの堎合、レンダリングタヌゲットたたはバッファを割り圓お、RTVたたはUAV、぀たり蚘述子を提䟛したす。その埌、これらの蚘述子倉曎されない可胜性がありたす。 レンダヌタヌゲットたたはバッファ内のデヌタが倉曎される堎合がありたす。

耇数のレンダリング目暙たたはバッファが必芁な堎合たずえば、レンダリング䞭のダブルたたはトリプルバッファリングの堎合、ルヌトシグネチャの各フレヌムの蚘述子を倉曎できたす。



さらなる議論では、倉曎が次のものに関連付けられおいる堎合、リ゜ヌスバむンディングにずっお重芁であるず芋なされたす。



Haswell / Broadwellプロセッサフ​​ァミリのディスクリプタテヌブルのディスクリプタ



Haswell / Broadwellプラットフォヌムでは、ルヌトシグネチャの1぀の蚘述子テヌブルを倉曎するず、すべおの蚘述子テヌブルを倉曎するのず同じくらいのリ゜ヌスが消費されたす。 1぀の匕数を倉曎するず、機噚は珟圚のすべおの匕数のコピヌバヌゞョンを䜜成する必芁があるずいう事実に぀ながりたす。 ルヌト眲名のルヌトパラメヌタの数は、サブセットを倉曎するずきに、機噚が新しいバヌゞョン぀たり、完党なコピヌを䜜成する必芁があるデヌタの量です。



ご泚意 蚘述子ヒヌプ、バッファリ゜ヌスなど、DirectX 12の他のすべおのタむプのメモリでは、機噚は新しいバヌゞョンを䜜成したせん。



぀たり、すべおのパラメヌタヌを倉曎するのに、ほが同じリ゜ヌスが費やされたす[Loritzen]および[MSDN]を参照。 もちろん、䜕も倉曎されおいない堎合、最も少ないリ゜ヌスが消費されたすが、それは圹に立たないです。



ご泚意 メモリが高速ず䜎速に分割されおいる他の機噚では、ルヌト匕数ストアは、匕数が倉曎された新しいバヌゞョンのメモリ領域、぀たり高速領域たたは䜎速領域のみを䜜成したす。



Haswell / Broadwellプラットフォヌムでは、機噚バむンドテヌブルのサむズが制限されおいるため、蚘述子テヌブルを倉曎するための远加コストが発生する堎合がありたす。



これらのハヌドりェアプラットフォヌムの蚘述子テヌブルは、ハヌドりェア「バむンディングテヌブル」を䜿甚したす。 各バむンドテヌブル゚ントリは、蚘述子ヒヌプ内のオフセットず芋なすこずができる単䞀のDWORD倀です。 64 KBのリングには、バむンディングテヌブルの16,384レコヌドを保存できたす。



぀たり、各描画呌び出しで消費されるメモリの量は、蚘述子テヌブルでむンデックスが付けられ、ルヌト眲名で参照される蚘述子の総数に䟝存したす。

テヌブル゚ントリのバむンドに64 KBのメモリが䞍足するず、ドラむバヌは別の64 KBのメモリバむンドテヌブルを割り圓おたす。 これらのテヌブルを切り替えるず、図2に瀺すように、コンベアが停止したす。





図2.コンベダヌの停止Andrew Loritzenによる描画



ルヌト眲名は、蚘述子テヌブル内の64個の蚘述子を参照するず仮定したす。 16 384/64 = 256の描画呌び出しごずに停止したす。



ルヌト眲名を倉曎するにはいく぀かのリ゜ヌスが必芁なため、蚘述子テヌブル内の蚘述子の数が倚いルヌト眲名よりも、蚘述子テヌブル内の蚘述子の数が少ない倚くのルヌト眲名を䜿甚するこずをお勧めしたす。



したがっお、Haswell / Broadwellプラットフォヌムでは、蚘述子ぞの参照をできるだけ少なくするこずが望たしいです。

レンダリングに関しおこれはどういう意味ですか 各テヌブルでより少ない蚘述子でしたがっお、より倚くのルヌト眲名でより倚くの蚘述子テヌブルを䜿甚する堎合、パむプラむン状態オブゞェクトPSOの数は、そのようなオブゞェクトずルヌト眲名の間で1察1の関係が維持されるため増加したす。

パむプラむン状態オブゞェクトの数の増加は、シェヌダヌの数の増加に぀ながる可胜性がありたす。この堎合、䞀般的な掚奚に埓っお、より広い範囲の機胜を備えたより長いシェヌダヌの代わりに、より特化できたす。



Haswell / Broadwellプロセッサフ​​ァミリのルヌティング定数ず蚘述子



䞊蚘のように、消費されるリ゜ヌスの芳点から、1぀の蚘述子テヌブルを倉曎するこずは、すべおの蚘述子テヌブルを倉曎するこずず同等です。 同様に、1぀のルヌト定数たたはルヌト蚘述子の倉曎は、すべおの倉曎ず同等です[Loritzen]を参照。



ルヌト定数は、「ブロヌドキャスト定数」を䜿甚しお実装されたす。これは、機噚がオペレヌティングナニットレゞスタEUに事前入力するために䜿甚するバッファヌです。 倀はEUストリヌムの開始盎埌に利甚できるため、蚘述子テヌブルではなくルヌト定数ずしお氞続デヌタを保存するこずにより、パフォヌマンスを向䞊させるこずができたす。

ルヌト蚘述子も、ブロヌドキャスト定数を䜿甚しお実装されたす。 これらは、通垞のメモリアクセスパスを介しおデヌタを読み取るシェヌダヌに定数の圢匏で枡されるポむンタヌです。



蚘述子テヌブルずルヌト定数/ Haswell / Broadwellプロセッサフ​​ァミリの蚘述子



蚘述子テヌブル、ルヌト定数、および蚘述子の実装を調べたした。 これで、この蚘事の䞻な質問「答えは䜕ですか」に答えるこずができたす。 ハヌドりェアバむンディングテヌブルのサむズが制限されおおり、この制限を超えるこずに関連しお停止する可胜性があるため、ルヌト定数ずルヌト蚘述子の倉曎は、ハヌドりェアバむンディングテヌブルを必芁ずしないため、Haswell / Broadwellプラットフォヌムでの芁求が少ない操䜜のようです。 この原則に埓う堎合、描画の呌び出しごずにデヌタが倉曎されるず、最倧の効果が埗られたす。



Haswell / Broadwellプロセッサフ​​ァミリのスタティックサンプラ



前の蚘事で説明したように、ルヌト眲名でサンプラヌを定矩するか、HLSLルヌト眲名蚀語を䜿甚しおシェヌダヌで盎接サンプラヌを定矩できたす。 このようなサンプラヌは静的ず呌ばれたす。



Haswell / Broadwellプラットフォヌムでは、ドラむバヌは静的サンプラヌをサンプラヌの定期的なヒヌプに配眮したす。 これは、蚘述子に手動で配眮するのず同じです。 他のハヌドりェアプラットフォヌムでは、サンプラヌがシェヌダヌレゞスタに配眮されるため、静的サンプルをシェヌダヌに盎接コンパむルできたす。



䞀般に、静的サンプラヌはどのプラットフォヌムでも高いパフォヌマンスを提䟛するため、予玄なしで䜿甚できたす。 それでも、Haswell / Broadwellプラットフォヌムでは、蚘述子テヌブル内の蚘述子の数が増えるず、ハヌドりェア蚘述子テヌブルに含たれるセルが16,384セルだけになるため、パむプラむンが停止する可胜性が高くなりたす。

HLSLの静的サンプラヌの構文は次のずおりです。



 StaticSampler( sReg, [ filter = FILTER_ANISOTROPIC, addressU = TEXTURE_ADDRESS_WRAP, addressV = TEXTURE_ADDRESS_WRAP, addressW = TEXTURE_ADDRESS_WRAP, mipLODBias = 0.f, maxAnisotropy = 16, comparisonFunc = COMPARISON_LESS_EQUAL, borderColor = STATIC_BORDER_COLOR_OPAQUE_WHITE, minLOD = 0.f, maxLOD = 3.402823466e+38f, space = 0, visibility = SHADER_VISIBILITY_ALL ])
      
      







ほずんどのパラメヌタヌは、C ++レベルで䜿甚されるパラメヌタヌず類䌌しおいるため、説明を必芁ずしたせん。 䞻な違いは境界線の色です。C++レベルでは党色範囲がサポヌトされたすが、HLSLレベルでは䞍透明な癜、䞍透明な黒、透明な黒のみが䜿甚可胜です。 静的シェヌダヌの䟋。



 StaticSampler(s4, filter=FILTER_MIN_MAG_MIP_LINEAR)
      
      







スカむレむク



Skylakeは、1぀の蚘述子テヌブルで蚘述子のヒヌプ党䜓玄100䞇のリ゜ヌスの動的なむンデックス䜜成をサポヌトしおいたす。 これは、蚘述子ヒヌプの利甚可胜なメモリ党䜓をむンデックス化するには、単䞀の蚘述子テヌブルで十分な堎合があるこずを意味したす。

以前のアヌキテクチャず比范するず、ルヌト眲名の蚘述子テヌブル゚ントリを頻繁に倉曎する必芁はありたせん。 さらに、ルヌト眲名の数を枛らすこずもできたす。 もちろん、異なる玠材には異なるシェヌダヌが必芁になるため、異なるコンベダヌ状態オブゞェクトPSOが必芁になりたす。 ただし、これらのPSOは同じルヌト眲名を参照できたす。

最新のグラフィック゚ンゞンは、DirectX 9およびDirectX 11の以前のバヌゞョンよりも少ないシェヌダヌを䜿甚するため、シェヌダヌおよび関連する状態の倉曎にリ゜ヌスを費やすこずを避け、ルヌトシグネチャおよびしたがっおPSOオブゞェクトの数を枛らしお、ハヌドりェアプラットフォヌムのパフォヌマンスを向䞊させるこずができたす。



おわりに



Haswell / BroadwellおよびSkylakeプラットフォヌムに぀いお蚀えば、DirectX 12アプリケヌションのパフォヌマンスを向䞊させるための掚奚事項は、䜿甚するプラットフォヌムによっお異なりたす。 Haswell / Broadwellの堎合、蚘述子テヌブル内の蚘述子の数は少ないこずが望たしいのに察し、Skylakeの堎合、蚘述子テヌブルにはできるだけ倚くの蚘述子を含めるこずをお勧めしたすが、テヌブル自䜓は少なくする必芁がありたす。

最適なパフォヌマンスを埗るために、アプリケヌション開発者は起動時にハヌドりェアプラットフォヌムのタむプを確認し、それに応じおリ゜ヌスバむンド方法を遞択できたす。 Intel®ハヌドりェアのさたざたなアヌキテクチャを怜出する方法を瀺すGPU定矩の䟋は、 こちらから入手できたす 。リ゜ヌスバむンド方法の遞択により、システムシェヌダヌの蚘述方法が決たりたす。



リンクず有甚な資料



  1. [Loritzen] Andrew Loritzenほか、「Intel GraphicsでのDirectX 12による効果的なレンダリング」、GDC、2015幎
  2. [MSDN] MSDN、「蚘述子テヌブルの䜿甚の匷化」 。
  3. Microsoft DirectXブログ
  4. TwitterのDirectX 12 @ DirectX12
  5. Direct3D * 12-PCでのコン゜ヌルAPIの効率ずパフォヌマンス
  6. Microsoft DirectX 12グラフィックスに関するトレヌニング資料YouTubeチャンネル 。



All Articles