diff --git a/dlls/ntoskrnl.exe/ntoskrnl.c b/dlls/ntoskrnl.exe/ntoskrnl.c index 912d0840318..eac81f79276 100644 --- a/dlls/ntoskrnl.exe/ntoskrnl.c +++ b/dlls/ntoskrnl.exe/ntoskrnl.c @@ -744,31 +744,20 @@ PVOID WINAPI IoAllocateErrorLogEntry( PVOID IoObject, UCHAR EntrySize ) */ PMDL WINAPI IoAllocateMdl( PVOID va, ULONG length, BOOLEAN secondary, BOOLEAN charge_quota, IRP *irp ) { + SIZE_T mdl_size; PMDL mdl; - ULONG_PTR address = (ULONG_PTR)va; - ULONG_PTR page_address; - SIZE_T nb_pages, mdl_size; TRACE("(%p, %u, %i, %i, %p)\n", va, length, secondary, charge_quota, irp); if (charge_quota) FIXME("Charge quota is not yet supported\n"); - /* FIXME: We suppose that page size is 4096 */ - page_address = address & ~(4096 - 1); - nb_pages = (((address + length - 1) & ~(4096 - 1)) - page_address) / 4096 + 1; - - mdl_size = sizeof(MDL) + nb_pages * sizeof(PVOID); - - mdl = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, mdl_size); + mdl_size = sizeof(MDL) + sizeof(PFN_NUMBER) * ADDRESS_AND_SIZE_TO_SPAN_PAGES(va, length); + mdl = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, mdl_size ); if (!mdl) return NULL; - mdl->Size = mdl_size; - mdl->Process = NULL; /* FIXME: IoGetCurrentProcess */ - mdl->StartVa = (PVOID)page_address; - mdl->ByteCount = length; - mdl->ByteOffset = address - page_address; + MmInitializeMdl( mdl, va, length ); if (!irp) return mdl; diff --git a/include/ddk/wdm.h b/include/ddk/wdm.h index 3e934697961..3829e8b0554 100644 --- a/include/ddk/wdm.h +++ b/include/ddk/wdm.h @@ -28,6 +28,16 @@ #define POINTER_ALIGNMENT #endif +/* FIXME: We suppose that page size is 4096 */ +#undef PAGE_SIZE +#define PAGE_SIZE 0x1000 +#define PAGE_SHIFT 12 + +#define BYTE_OFFSET(va) ((ULONG)((ULONG_PTR)(va) & (PAGE_SIZE - 1))) +#define PAGE_ALIGN(va) ((PVOID)((ULONG_PTR)(va) & ~(PAGE_SIZE - 1))) +#define ADDRESS_AND_SIZE_TO_SPAN_PAGES(va, length) \ + ((BYTE_OFFSET(va) + ((SIZE_T)(length)) + (PAGE_SIZE - 1)) >> PAGE_SHIFT) + typedef LONG KPRIORITY; typedef ULONG_PTR KSPIN_LOCK, *PKSPIN_LOCK; @@ -1035,6 +1045,17 @@ typedef struct _MDL { } MDL, *PMDL; typedef MDL *PMDLX; +typedef ULONG PFN_NUMBER, *PPFN_NUMBER; + +static inline void MmInitializeMdl(MDL *mdl, void *va, SIZE_T length) +{ + mdl->Next = NULL; + mdl->Size = sizeof(MDL) + sizeof(PFN_NUMBER) * ADDRESS_AND_SIZE_TO_SPAN_PAGES(va, length); + mdl->MdlFlags = 0; + mdl->StartVa = (void *)PAGE_ALIGN(va); + mdl->ByteOffset = BYTE_OFFSET(va); + mdl->ByteCount = length; +} typedef struct _KTIMER { DISPATCHER_HEADER Header;