From 63eb4b623a9b7da8ce7dd3596c872cb11379e3ff Mon Sep 17 00:00:00 2001 From: Pierre Schweitzer Date: Sat, 3 Jun 2017 10:29:39 +0000 Subject: [PATCH] [KMTESTS:MM] Test various sizes with MmMapLockedPagesSpecifyCache() to show that behavior is strictly identical. This was designed/tested under W2K3. CORE-8204 svn path=/trunk/; revision=74759 --- .../ntos_mm/MmMapLockedPagesSpecifyCache.h | 4 +- .../MmMapLockedPagesSpecifyCache_drv.c | 9 +- .../MmMapLockedPagesSpecifyCache_user.c | 171 +++++++++++++++++- 3 files changed, 172 insertions(+), 12 deletions(-) diff --git a/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache.h b/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache.h index 195703f7c75..6b4ecd668e4 100644 --- a/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache.h +++ b/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache.h @@ -20,10 +20,12 @@ typedef struct _READ_BUFFER { USHORT Length; PVOID Buffer; - USHORT Pattern; + ULONG Pattern; } READ_BUFFER, *PREAD_BUFFER; #define IOCTL_QUERY_BUFFER 1 #define IOCTL_READ_BUFFER 2 +#define WRITE_PATTERN 0xA4A5A6A7 + #endif /* !defined _KMTEST_MMMAPLOCKEDPAGESSPECIFYCACHE_H_ */ diff --git a/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_drv.c b/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_drv.c index 69c387db0ee..fac724db49e 100644 --- a/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_drv.c +++ b/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_drv.c @@ -122,7 +122,7 @@ TestMessageHandler( Length = QueryBuffer->Length; ok(Length > 0, "Null size!\n"); - CurrentBuffer = ExAllocatePoolWithTag(NonPagedPool, Length + 0x8, 'MLPC'); + CurrentBuffer = ExAllocatePoolWithTag(NonPagedPool, Length, 'MLPC'); ok(CurrentBuffer != NULL, "ExAllocatePool failed!\n"); CurrentUser = NULL; if (!skip(CurrentBuffer != NULL, "ExAllocatePool failed!\n")) @@ -195,14 +195,15 @@ TestMessageHandler( if (ReadBuffer->Buffer != NULL) { USHORT i; - PUSHORT KBuffer = MmGetSystemAddressForMdlSafe(CurrentMdl, NormalPagePriority); + PULONG KBuffer = MmGetSystemAddressForMdlSafe(CurrentMdl, NormalPagePriority); ok(KBuffer != NULL, "Failed to get kmode ptr\n"); + ok(ReadBuffer->Length % sizeof(ULONG) == 0, "Invalid size: %d\n", ReadBuffer->Length); if (!skip(Buffer != NULL, "Failed to get kmode ptr\n")) { - for (i = 0; i < ReadBuffer->Length / sizeof(USHORT); ++i) + for (i = 0; i < ReadBuffer->Length / sizeof(ULONG); ++i) { - ok_eq_ulong((ULONG)KBuffer[i], (ULONG)ReadBuffer->Pattern); + ok_eq_ulong(KBuffer[i], ReadBuffer->Pattern); } } } diff --git a/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_user.c b/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_user.c index d67e8e4be4c..e935ccb4e0b 100644 --- a/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_user.c +++ b/rostests/kmtests/ntos_mm/MmMapLockedPagesSpecifyCache_user.c @@ -9,44 +9,201 @@ #include "MmMapLockedPagesSpecifyCache.h" +#define SET_BUFFER_LENGTH(Var, Length) \ +{ \ + C_ASSERT(((Length) % sizeof(ULONG)) == 0); \ + Var = (Length); \ +} + START_TEST(MmMapLockedPagesSpecifyCache) { QUERY_BUFFER QueryBuffer; READ_BUFFER ReadBuffer; DWORD Length; USHORT i; - PUSHORT Buffer; + PULONG Buffer; + USHORT BufferLength; KmtLoadDriver(L"MmMapLockedPagesSpecifyCache", FALSE); KmtOpenDriver(); - QueryBuffer.Length = 0x100; + // Less than a page + SET_BUFFER_LENGTH(BufferLength, 2048); + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = FALSE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok_eq_pointer(QueryBuffer.Buffer, NULL); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = TRUE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok(QueryBuffer.Buffer != NULL, "Buffer is NULL\n"); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + if (!skip(QueryBuffer.Buffer != NULL, "Buffer is NULL\n")) + { + ReadBuffer.Pattern = WRITE_PATTERN; + ReadBuffer.Length = QueryBuffer.Length; + Buffer = QueryBuffer.Buffer; + for (i = 0; i < ReadBuffer.Length / sizeof(ULONG); ++i) + { + Buffer[i] = ReadBuffer.Pattern; + } + } + + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + // 1 page + SET_BUFFER_LENGTH(BufferLength, 4096); + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = FALSE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok_eq_pointer(QueryBuffer.Buffer, NULL); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = TRUE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok(QueryBuffer.Buffer != NULL, "Buffer is NULL\n"); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + if (!skip(QueryBuffer.Buffer != NULL, "Buffer is NULL\n")) + { + ReadBuffer.Pattern = WRITE_PATTERN; + ReadBuffer.Length = QueryBuffer.Length; + Buffer = QueryBuffer.Buffer; + for (i = 0; i < ReadBuffer.Length / sizeof(ULONG); ++i) + { + Buffer[i] = ReadBuffer.Pattern; + } + } + + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + // more than 1 page + SET_BUFFER_LENGTH(BufferLength, 4096 + 2048); + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = FALSE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok_eq_pointer(QueryBuffer.Buffer, NULL); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = TRUE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok(QueryBuffer.Buffer != NULL, "Buffer is NULL\n"); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + if (!skip(QueryBuffer.Buffer != NULL, "Buffer is NULL\n")) + { + ReadBuffer.Pattern = WRITE_PATTERN; + ReadBuffer.Length = QueryBuffer.Length; + Buffer = QueryBuffer.Buffer; + for (i = 0; i < ReadBuffer.Length / sizeof(ULONG); ++i) + { + Buffer[i] = ReadBuffer.Pattern; + } + } + + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + // 2 pages + SET_BUFFER_LENGTH(BufferLength, 2 * 4096); + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = FALSE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok_eq_pointer(QueryBuffer.Buffer, NULL); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + QueryBuffer.Length = BufferLength; + QueryBuffer.Buffer = NULL; + QueryBuffer.Cached = TRUE; + Length = sizeof(QUERY_BUFFER); + ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + ok_eq_int(QueryBuffer.Length, BufferLength); + ok(QueryBuffer.Buffer != NULL, "Buffer is NULL\n"); + + ReadBuffer.Buffer = QueryBuffer.Buffer; + if (!skip(QueryBuffer.Buffer != NULL, "Buffer is NULL\n")) + { + ReadBuffer.Pattern = WRITE_PATTERN; + ReadBuffer.Length = QueryBuffer.Length; + Buffer = QueryBuffer.Buffer; + for (i = 0; i < ReadBuffer.Length / sizeof(ULONG); ++i) + { + Buffer[i] = ReadBuffer.Pattern; + } + } + + Length = 0; + ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); + + // more than 2 pages + SET_BUFFER_LENGTH(BufferLength, 2 * 4096 + 2048); + QueryBuffer.Length = BufferLength; QueryBuffer.Buffer = NULL; QueryBuffer.Cached = FALSE; Length = sizeof(QUERY_BUFFER); ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); - ok_eq_int(QueryBuffer.Length, 0x100); + ok_eq_int(QueryBuffer.Length, BufferLength); ok_eq_pointer(QueryBuffer.Buffer, NULL); ReadBuffer.Buffer = QueryBuffer.Buffer; Length = 0; ok(KmtSendBufferToDriver(IOCTL_READ_BUFFER, &ReadBuffer, sizeof(READ_BUFFER), &Length) == ERROR_SUCCESS, "\n"); - QueryBuffer.Length = 0x100; + QueryBuffer.Length = BufferLength; QueryBuffer.Buffer = NULL; QueryBuffer.Cached = TRUE; Length = sizeof(QUERY_BUFFER); ok(KmtSendBufferToDriver(IOCTL_QUERY_BUFFER, &QueryBuffer, sizeof(QUERY_BUFFER), &Length) == ERROR_SUCCESS, "\n"); - ok_eq_int(QueryBuffer.Length, 0x100); + ok_eq_int(QueryBuffer.Length, BufferLength); ok(QueryBuffer.Buffer != NULL, "Buffer is NULL\n"); ReadBuffer.Buffer = QueryBuffer.Buffer; if (!skip(QueryBuffer.Buffer != NULL, "Buffer is NULL\n")) { - ReadBuffer.Pattern = 0xA7; + ReadBuffer.Pattern = WRITE_PATTERN; ReadBuffer.Length = QueryBuffer.Length; Buffer = QueryBuffer.Buffer; - for (i = 0; i < ReadBuffer.Length / sizeof(USHORT); ++i) + for (i = 0; i < ReadBuffer.Length / sizeof(ULONG); ++i) { Buffer[i] = ReadBuffer.Pattern; } -- 2.17.1