次の方法で共有


NdisMAllocateSharedMemory 関数 (ndis.h)

注意事項

ARM および ARM64 プロセッサの場合、NDIS ドライバー ライターは、NDIS 散布/収集 DMA の代わりに WDF DMA または WDM DMA を使用することを強くお勧めします。

WDF DMA の詳細については、「 KMDF ドライバーでの DMA 操作の処理」を参照してください。

WDM DMA の詳細については、「 ドライバーの入出力の管理」の DMA 関連の子トピックを参照してください。

NdisMAllocateSharedMemory は、ホスト システムと DMA NIC の両方からメモリ範囲に同時にアクセスできるように、ホスト メモリ範囲を割り当ててマップします。

構文

void NdisMAllocateSharedMemory(
  [in]  NDIS_HANDLE            MiniportAdapterHandle,
  [in]  ULONG                  Length,
  [in]  BOOLEAN                Cached,
  [out] PVOID                  *VirtualAddress,
  [out] PNDIS_PHYSICAL_ADDRESS PhysicalAddress
);

パラメーター

[in] MiniportAdapterHandle

MiniportInitializeEx へのハンドル入力を指定します。

[in] Length

割り当てるバイト数を指定します。

[in] Cached

このパラメーターは無視されます (キャッシュされたメモリは常に x86 および x64 システムで使用されます)。

[out] VirtualAddress

この関数がミニポート ドライバーで使用する割り当ての基本仮想アドレスを返す呼び出し元から提供された変数へのポインター。 NdisMAllocateSharedMemory が呼び出し元を満たすことができない場合は、メモリが割り当てられていないことを示す NULL を返します。

[out] PhysicalAddress

呼び出し元が指定した変数へのポインター。この関数は、 VirtualAddress で返された変数に対応する NIC で使用するのに適した物理アドレスを返すか、 NULL を返します。

戻り値

なし

解説

メモミニポート ドライバーは、NdisMAllocateSharedMemory を呼び出す前に、分散/収集 DMA チャネルを初期化するために、NdisMRegisterScatterGatherDma または NdisMRegisterDmaChannel を既に呼び出している必要があります。
 
Microsoft Windows Server 2003、Windows XP Service Pack 1 以降のバージョンの Windows では、バス マスター DMA NIC と下位 DMA NIC の両方で NdisMAllocateSharedMemory を呼び出すことができます。 以前のリリースでは、バス マスター DMA NIC のみが NdisMAllocateSharedMemory を呼び出すことができるようになります。 これらの以前のリリースでは、NdisMSetMiniportAttributes を呼び出したときに Nic がバス マスターであることを MiniportInitializeEx が指定しなかった場合、NdisMAllocateSharedMemory は割り当てを試みることなく単に制御を返します。

NdisMAllocateSharedMemory は、ドライバーが共有メモリ ブロックにアクセスするために使用するマップされた仮想アドレス範囲と、NIC が使用する NDIS_PHYSICAL_ADDRESS型の範囲の両方を提供します。 PhysicalAddress で返される値は、システムによって二重にマップできます。 つまり、 PhysicalAddressLength の値によって記述される "物理" アドレス範囲は、可能なすべてのプラットフォームでの割り当てに対してホストの物理アドレスと一致しないマップされた論理アドレスの範囲にすることができます。

NdisMAllocateSharedMemory、MiniportInitializeEx からのみ呼び出すことができます。 要求する割り当ての大きさは、NIC の機能と機能を把握しているドライバー ライターが、次のパフォーマンスとサイズのジレンマのトレードオフを決定する方法によって異なります。

  • ネットワーク トラフィックが多い期間、ミニポート ドライバーは、デバイスアクセス可能なデータ バッファーの共有メモリ領域が不足している場合、高い I/O スループットを維持できません。

    たとえば、ミニポート ドライバーは、受信のフラッディングが NIC に入ったときにバインドされたプロトコル ドライバーからこのようなバッファーが返されるよりも高速に共有メモリ内の受信バッファーを示している可能性があります。 未処理の受信バッファーによって共有メモリ領域がすべて消費される場合、ミニポート ドライバーは、受信バッファーに使用できる共有メモリ領域が存在するまで、NIC の受信割り込みを無効にする必要がある場合があります。

  • 一方、最大転送需要を予測するために選択された Length を指定して NdisMAllocateSharedMemory を呼び出すと、非常に高い I/O 需要のまれな期間を除き、ドライバーのイメージが大きくなり、そのリソース使用量は非常に不経済になります。 さらに、システム メモリが不足している場合、 NdisMAllocateSharedMemory はドライバーにこのような大きなブロックを与えない可能性があり、ドライバーの初期化に失敗する必要があります。
を提供するミニポート ドライバー MiniportSharedMemoryAllocateComplete 関数は、上記のパフォーマンスとサイズのジレンマを解決する柔軟性が大幅に向上しています。 MiniportInitializeEx は、ドライバーに MiniportSharedMemoryAllocateComplete 関数がある場合、NIC を介したネットワーク転送操作に対する中程度の需要のために、NdisMAllocateSharedMemory を使用して十分な共有メモリのみを割り当てる必要があります。 このようなミニポート ドライバーは、 を呼び出すことができます NdisMAllocateSharedMemoryAsyncEx を動的に使用して、NIC に対する転送要求の負荷が高い期間により多くの共有メモリを割り当てます。 転送の需要が高くなる場合、このようなドライバーは NdisMFreeSharedMemory を呼び出して、割り当てられた追加のメモリを解放します。 バス マスター DMA NIC のみが NdisMAllocateSharedMemoryAsyncEx を呼び出し、 ミニポートSharedMemoryAllocateComplete をエクスポートできることに注意してください。 この機能は、下位 DMA NIC ではサポートされていません。

NdisMAllocateSharedMemory および NdisMAllocateSharedMemoryAsyncEx は、仮想アドレスを使用するドライバーと、対応する論理アドレスを使用する NIC の間で共有されるホスト メモリを割り当てるために呼び出すことができる唯一の NdisXxx 関数です。

ミニポート ドライバーは、DMA 中にキャッシュラインのティアリングを防ぐために、ホストデータキャッシュライン境界の不可欠な共有キャッシュメモリから割り当てるバッファーを配置する必要があります。 キャッシュラインのティアリングにより、ドライバーのデータ整合性の問題が発生したり、データの整合性を維持するために過剰なデータ キャッシュフラッシュが必要になり、ドライバー (およびシステム) の I/O パフォーマンスが低下したりする可能性があります。 MiniportInitializeExNdisMGetDmaAlignment を呼び出して、ドライバーが割り当てられた共有メモリの範囲内で設定するデバイスアクセス可能なバッファーの現在のプラットフォームの配置境界を決定できます。

ミニポート ドライバーは、割り当てることができる共有メモリの量に制限を設定する必要があります。 この制限はドライバー固有であり、ドライバーがバッファーを使い果たさないように十分に高くする必要があります。 過剰に高い制限を設定しないでください。これにより、共有メモリが無駄に消費され、システム のパフォーマンスが低下する可能性があります。

また、ドライバー ライターがマルチプロセッサ マシンに大きな共有メモリ ブロックを割り当てることを決定した場合、SMP マシンがワークステーションよりも NIC のネットワーク転送要求が高いネットワーク サーバーである可能性が高いと判断した場合、MiniportInitializeExNdisMAllocateSharedMemory を呼び出す前に NdisSystemProcessorCount を呼び出す可能性もあります。

NdisMAllocateSharedMemory の呼び出しが失敗した場合、MiniportInitializeEx は小さい割り当てを要求して再度呼び出すことができます。 ただし、 MiniportInitializeEx が NIC に十分な共有メモリを割り当てることができない場合は、既に割り当てられているすべてのリソースを解放し、初期化に失敗する必要があります。

ミニポート ドライバーは、その後で を受信を示す場合 NdisMIndicateReceiveNetBufferLists では、共有メモリ ブロック内の NIC の受信バッファーをマップするバッファー プールからいくつかのバッファー記述子を割り当てる必要があります。

割り当てられたメモリがキャッシュされるため、転送時にフラッシュする必要がある場合、ミニポート ドライバーは NdisAllocateMdl を呼び出して、共有メモリ範囲のNDIS_BUFFER型記述子を割り当てる必要があります。 ミニポート ドライバーは、このようなフラッシュを実行するには、このバッファー記述子で KeFlushIoBuffers を呼び出す必要があります。

ミニポート ドライバーがを呼び出す場合 NdisMAllocateSharedMemoryAsyncEx または NdisMAllocateSharedMemory は、NIC が削除されたとき、つまり、MiniportHaltEx 関数が呼び出されたときに、NdisMFreeSharedMemory への 1 つ以上の呼び出しで未処理のすべての割り当てを解放する必要があります。

要件

要件
サポートされている最小のクライアント NDIS 6.0 以降でサポートされています。
対象プラットフォーム ユニバーサル
Header ndis.h (Ndis.h を含む)
Library Ndis.lib
IRQL PASSIVE_LEVEL

こちらもご覧ください

KeFlushIoBuffers

MiniportHaltEx

MiniportInitializeEx

MiniportSharedMemoryAllocateComplete

NdisAllocateMdl

NdisMAllocateNetBufferSGList

NdisMAllocateSharedMemoryAsyncEx

NdisMFreeSharedMemory

NdisMGetDmaAlignment

NdisMIndicateReceiveNetBufferLists

NdisMSetMiniportAttributes

NdisSystemProcessorCount