Partager via


NdisMAllocateSharedMemory, fonction (ndis.h)

Prudence

Pour les processeurs ARM et ARM64, nous recommandons vivement aux enregistreurs de pilotes NDIS d’utiliser WDF DMA ou WDM DMA au lieu de NDIS Scatter/Collect DMA.

Pour plus d’informations sur WDF DMA, consultez gestion des opérations DMA dans les pilotes KMDF.

Pour plus d’informations sur WDM DMA, consultez les rubriques enfants relatives à DMA de Gestion des entrées/sorties pour les pilotes.

NdisMAllocateSharedMemory alloue et mappe une plage de mémoire hôte afin que la plage de mémoire soit simultanément accessible à partir du système hôte et d’une carte réseau DMA.

Syntaxe

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

Paramètres

[in] MiniportAdapterHandle

Spécifie l’entrée de handle pour MiniportInitializeEx.

[in] Length

Spécifie le nombre d’octets à allouer.

[in] Cached

Ce paramètre est ignoré (la mémoire mise en cache est toujours utilisée sur les systèmes x86 et x64).

[out] VirtualAddress

Pointeur vers une variable fournie par l’appelant dans laquelle cette fonction retourne l’adresse virtuelle de base de l’allocation à utiliser par le pilote miniport. Si NdisMAllocateSharedMemory ne peut pas satisfaire son appelant, il retourne NULL pour indiquer qu’aucune mémoire n’a été allouée.

[out] PhysicalAddress

Pointeur vers une variable fournie par l’appelant dans laquelle cette fonction retourne une adresse physique, adaptée à l’utilisation par la carte réseau, qui correspond à celle retournée à VirtualAddress, ou retourne NULL.

Valeur de retour

Aucun

Remarques

Remarque Un pilote miniport doit déjà avoir appelé NdisMRegisterScatterGatherDma ou NdisMRegisterDmaChannel pour initialiser un canal DMA de nuages de points/collecter avant d’appeler NdisMAllocateSharedMemory.
 
Microsoft Windows Server 2003, Windows XP Service Pack 1 et versions ultérieures de Windows permettent aux cartes réseau DMA maître bus et aux cartes réseau DMA subordonnées d’appeler NdisMAllocateSharedMemory. Les versions antérieures autorisent uniquement les cartes réseau DMA de bus-master à appeler NdisMAllocateSharedMemory. Dans ces versions antérieures, si MiniportInitializeEx n’a pas spécifié que la carte réseau est une forme de base de bus lorsqu’elle a appelé NdisMSetMiniportAttributes, NdisMAllocateSharedMemory retourne simplement le contrôle sans tenter d’attribuer une allocation.

NdisMAllocateSharedMemory fournit à la fois la plage d’adresses virtuelle mappée utilisée par le pilote pour accéder au bloc de mémoire partagée et à la plage NDIS_PHYSICAL_ADDRESS-type utilisée par la carte réseau. Une valeur retournée à physicalAddress peut être doublement mappée par le système. Autrement dit, une plage d’adresses « physique » décrite par la valeur de PhysicalAddress et Length peut être une plage d’adresses logiques mappées qui ne correspondent pas aux adresses physiques de l’hôte pour l’allocation dans chaque plateforme possible.

NdisMAllocateSharedMemory ne peut être appelé qu’à partir de MiniportInitializeEx. La taille d’une allocation à demander dépend de la façon dont l’enregistreur de pilotes, sachant les fonctionnalités et les fonctionnalités de la carte réseau, décide de faire le compromis entre les performances suivantes et le dilemme de taille :

  • Dans les périodes de trafic réseau élevé, un pilote miniport ne peut pas conserver un débit d’E/S élevé s’il s’exécute faiblement sur l’espace mémoire partagé pour les mémoires tampons de données accessibles par l’appareil.

    Par exemple, le pilote miniport peut indiquer que les mémoires tampons de réception en mémoire partagée sont plus rapides que ces mémoires tampons sont retournées par des pilotes de protocole liés lorsqu’une inondation de réceptions arrive à une carte réseau. Si tous ses espaces de mémoire partagée sont consommés par des mémoires tampons de réception en attente, le pilote miniport peut devoir désactiver les interruptions de réception sur une carte réseau jusqu’à ce qu’il dispose d’un espace mémoire partagé disponible pour les mémoires tampons de réception.

  • En revanche, l’appel de NdisMAllocateSharedMemory avec une Longueur choisie pour anticiper une demande de transfert maximale rend l’image du pilote plus grande et son utilisation des ressources assez peu économique, à l’exception des rares périodes de demande d’E/S très élevées. De plus, NdisMAllocateSharedMemory risque de ne pas donner au pilote un bloc si la mémoire système insuffisante est disponible, forçant le pilote à échouer l’initialisation.
Un miniporteur qui fournit un miniportSharedMemoryAllocateComplete fonction a beaucoup plus de flexibilité pour résoudre les performances précédentes par rapport au dilemme de taille. MiniportInitializeEx ne doit allouer que suffisamment de mémoire partagée avec NdisMAllocateSharedMemory pour une demande modérée d’opérations de transfert réseau via la carte réseau si le pilote a une fonction MiniportSharedMemoryAllocateComplete. Un tel pilote miniport peut appeler NdisMAllocateSharedMemoryAsyncEx de manière dynamique pour allouer plus de mémoire partagée dans les périodes de demande de transfert plus importante sur une carte réseau. Lorsque la demande élevée de transferts diminue, un tel pilote appelle NdisMFreeSharedMemory pour libérer la mémoire supplémentaire allouée. Notez que seules les cartes réseau DMA maître de bus peuvent appeler NdisMAllocateSharedMemoryAsyncEx et exporter MiniportSharedMemoryAllocateComplete. Cette fonctionnalité n’est pas prise en charge pour les cartes réseau DMA subordonnées.

NdisMAllocateSharedMemory et NdisMAllocateSharedMemoryAsyncEx sont les seules fonctions NdisXxx qui peuvent être appelées pour allouer la mémoire hôte partagée entre le pilote, qui utilise des adresses virtuelles et une carte réseau, qui utilise les adresses logiques correspondantes.

Un pilote miniport doit aligner les mémoires tampons qu’il alloue à partir de la mémoire mise en cache partagée sur une partie intégrante de la limite de ligne de cache de données hôte pour empêcher la déchirure de ligne de cache pendant DMA. La déchirure de ligne de cache peut entraîner des problèmes d’intégrité des données dans le pilote ou dégrader les performances d’E/S du pilote (et du système) en nécessitant un vidage excessif du cache de données pour maintenir l’intégrité des données. MiniportInitializeEx pouvez appeler NdisMGetDmaAlignment pour déterminer la limite d’alignement dans la plateforme actuelle pour les mémoires tampons accessibles aux appareils que le pilote configurera dans une plage allouée de mémoire partagée.

Un pilote miniport doit définir une limite sur la quantité de mémoire partagée qu’il peut allouer. Cette limite est spécifique au pilote et doit être suffisamment élevée pour que le pilote ne manque pas de mémoires tampons. Ne définissez pas de limite excessivement élevée, car cela peut entraîner une consommation gaspilleuse de la mémoire partagée qui peut réduire les performances du système.

MiniportInitializeEx peut également appeler NdisSystemProcessorCount avant d’appeler NdisMAllocateSharedMemory si l’enregistreur de pilotes décide d’allouer un bloc de mémoire partagée plus volumineux dans les machines multiprocesseurs en supposant que n’importe quel ordinateur SMP est susceptible d’être un serveur réseau avec des demandes de transfert réseau plus élevées sur la carte réseau qu’une station de travail.

Si son appel à NdisMAllocateSharedMemory échoue, MiniportInitializeEx peut appeler à nouveau en demandant une allocation plus petite. Toutefois, si MiniportInitializeEx ne peut pas allouer suffisamment de mémoire partagée pour la carte réseau, elle doit libérer toutes les ressources qu’elle a déjà allouées et échouer l’initialisation.

Si le pilote miniport indique par la suite les réceptions avec NdisMIndicateReceiveNetBufferLists, il doit allouer un certain nombre de descripteurs de mémoire tampon du pool de mémoires tampons qui mappent les tampons de réception de la carte réseau dans le bloc de mémoire partagée.

Si la mémoire allouée est mise en cache et doit donc être vidée sur les transferts, le pilote miniport doit appeler NdisAllocateMdl pour allouer un descripteur de type NDIS_BUFFER pour la plage de mémoire partagée. Le pilote miniport doit appeler KeFlushIoBuffers avec ce descripteur de mémoire tampon pour effectuer une telle vidage.

Si un pilote miniport appelle NdisMAllocateSharedMemoryAsyncEx ou NdisMAllocateSharedMemory, il doit libérer toutes les allocations en attente avec un ou plusieurs appels à NdisMFreeSharedMemory lorsqu’une carte réseau est supprimée, autrement dit, quand sa fonction MiniportHaltEx est appelée.

Exigences

Exigence Valeur
client minimum pris en charge Prise en charge dans NDIS 6.0 et versions ultérieures.
plateforme cible Universel
d’en-tête ndis.h (include Ndis.h)
bibliothèque Ndis.lib
IRQL PASSIVE_LEVEL

Voir aussi

KeFlushIoBuffers

MiniportHaltEx

MiniportInitializeEx

MiniportSharedMemoryAllocateComplete

NdisAllocateMdl

NdisMAllocateNetBufferSGList

NdisMAllocateSharedMemoryAsyncEx

NdisMFreeSharedMemory

NdisMGetDmaAlignment

NdisMIndicateReceiveNetBufferLists

NdisMSetMiniportAttributes

NdisSystemProcessorCount