Función MmAllocateMdlForIoSpace (wdm.h)
La rutina MmAllocateMdlForIoSpace asigna unMDL dee inicializa esta MDL para describir un conjunto de intervalos de direcciones físicos en el espacio de direcciones de E/S.
Sintaxis
NTSTATUS MmAllocateMdlForIoSpace(
[in] PMM_PHYSICAL_ADDRESS_LIST PhysicalAddressList,
[in] SIZE_T NumberOfEntries,
[out] PMDL *NewMdl
);
Parámetros
[in] PhysicalAddressList
Puntero a una matriz de MM_PHYSICAL_ADDRESS_LIST estructuras que describen los intervalos de direcciones físicos que se van a incluir en la MDL asignada.
[in] NumberOfEntries
Número de elementos de la matriz de MM_PHYSICAL_ADDRESS_LIST a los que apunta PhysicalAddressList.
[out] NewMdl
Puntero a una ubicación en la que la rutina escribe un puntero a la MDL recién asignada.
Valor devuelto
MmAllocateMdlForIoSpace devuelve STATUS_SUCCESS si se ejecuta correctamente. Entre los posibles valores devueltos de error se incluyen los siguientes códigos de estado.
Código devuelto | Descripción |
---|---|
STATUS_INVALID_PARAMETER_1 | Una dirección física no está alineada con un límite de página; o un intervalo de direcciones físicos no es un múltiplo del tamaño de página; o un intervalo de direcciones físicos lo usa el sistema operativo para RAM y no está disponible para su uso como espacio de E/S. |
STATUS_INSUFFICIENT_RESOURCES | Los recursos del sistema insuficientes están disponibles para realizar la operación solicitada. |
No suponga que la lista anterior de códigos de retorno de error es exhaustiva. La rutina puede devolver códigos de error que no aparecen en la lista.
Observaciones
Esta rutina acepta, como parámetro de entrada, una matriz de estructuras de MM_PHYSICAL_ADDRESS_LIST que describen un conjunto de intervalos de direcciones físicos en el espacio de direcciones de E/S y asigna una MDL que describe estos intervalos. No es necesario que los intervalos de direcciones físicos consecutivos de la matriz sean contiguos.
Los intervalos de direcciones físicos de la matriz de PhysicalAddressList deben cumplir las condiciones siguientes:
La dirección física base de cada intervalo debe alinearse con un límite de PAGE_SIZE en memoria.
El tamaño, en bytes, de cada intervalo debe ser un entero múltiplo de PAGE_SIZE.
Todos los intervalos de direcciones físicos deben estar en memoria que estén disponibles para su uso como espacio de direcciones de E/S. No pueden estar en el espacio de memoria que usa el sistema operativo para RAM.
El tamaño total de todos los intervalos debe ser inferior a 4 gigabytes. En concreto, el tamaño total no debe superar los 2^32 - 1 bytes.
El autor de la llamada es responsable de liberar el MDL asignado cuando ya no es necesario. Para liberar la MDL, llame a la rutina IoFreeMdl. Para obtener más información sobre las MDL, vea Using MDLs.
El MDL creado por MmAllocateMdlForIoSpace no está asignado a la memoria virtual, pero se puede proporcionar a una rutina como MapTransferEx para iniciar una transferencia DMA a o desde los intervalos de memoria físicos descritos por MDL. Para asignar esta MDL a un intervalo contiguo de direcciones virtuales para que el procesador pueda acceder a ella, llame a la rutina MmMapLockedPagesSpecifyCache.
Solo los intervalos del espacio de direcciones físicos que no están reservados por el sistema operativo para su uso como memoria están disponibles para los controladores para su uso como espacio de direcciones de E/S. Los controladores usan el espacio de direcciones de E/S para acceder a recursos de hardware asignados a memoria, como los registros de dispositivos. Cuando se inicia un controlador, puede recibir uno o varios intervalos de direcciones físicos como recursos de hardware traducidos. Para obtener más información, consulte Asignación de direcciones de Bus-Relative a direcciones virtuales.
En algunas arquitecturas de procesador, como x86, los dispositivos pueden asignarse a memoria o asignarse a direcciones de puerto en un espacio de direcciones de E/S especial dedicado a los dispositivos y es independiente del espacio de direcciones de memoria. Los controladores pueden usar MmAllocateMdlForIoSpace para asignar MDL solo para dispositivos asignados a memoria.
Ejemplos
En el ejemplo de código siguiente se muestra cómo construir una matriz de estructuras de MM_PHYSICAL_ADDRESS_LIST que describen los intervalos de direcciones físicos que se van a incluir en la MDL asignada.
extern ULONG64 BasePhysicalAddress;
extern SIZE_T ChunkSize;
extern SIZE_T Stride;
#define ARRAYSIZE(x) (sizeof(x)/sizeof((x)[0]))
NTSTATUS Status;
PMDL Mdl;
MM_PHYSICAL_ADDRESS_LIST AddressList[3];
AddressList[0].PhysicalAddress.QuadPart = BasePhysicalAddress;
AddressList[0].NumberOfBytes = ChunkSize;
BasePhysicalAddress += Stride;
AddressList[1].PhysicalAddress.QuadPart = BasePhysicalAddress;
AddressList[1].NumberOfBytes = ChunkSize;
BasePhysicalAddress += Stride;
AddressList[2].PhysicalAddress.QuadPart = BasePhysicalAddress;
AddressList[2].NumberOfBytes = ChunkSize;
Status = MmAllocateMdlForIoSpace (AddressList, ARRAYSIZE(AddressList), &Mdl);
En este ejemplo, la dirección física inicial se especifica mediante la variable BasePhysicalAddress
. La variable ChunkSize
especifica el número de bytes de cada intervalo de direcciones físicos. El desplazamiento de bytes desde el inicio de un intervalo físico hasta el inicio del siguiente se especifica mediante la variable Stride
.
BasePhysicalAddress
deben alinearse con un límite de página en la memoria y ChunkSize
y Stride
deben ser múltiplos del tamaño de página.
Requisitos
Requisito | Valor |
---|---|
cliente mínimo admitido | Disponible a partir de Windows 8. |
de la plataforma de destino de | Universal |
encabezado de | wdm.h (incluya Wdm.h) |
biblioteca de | NtosKrnl.lib |
DLL de | NtosKrnl.exe |
irQL | <= DISPATCH_LEVEL |