Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

191 lines
4.2 KiB

  1. /*++
  2. Copyright (c) 2001 Microsoft Corporation. All Rights Reserved.
  3. Module Name:
  4. mapview.c
  5. Abstract:
  6. This code is used to map a read only copy of the glitch output buffer into
  7. a user mode process. It currently supports mapping the output buffer to
  8. only 1 user mode process at a time.
  9. Author:
  10. Joseph Ballantyne
  11. Environment:
  12. Kernel Mode
  13. Revision History:
  14. --*/
  15. #ifdef UNDER_NT
  16. #include "common.h"
  17. #include <ntddk.h>
  18. #include <rt.h>
  19. #include "glitch.h"
  20. #include "mapview.h"
  21. // Note that there are PAGEABLE_CODE and PAGEABLE_DATA pragmas in common.h
  22. // so all of this code is pageable. That is as it should be - as this code
  23. // is all called while handling IOCTLS.
  24. HANDLE SectionHandle=NULL;
  25. HANDLE Process=NULL;
  26. NTSTATUS
  27. MapContiguousBufferToUserModeProcess (
  28. PVOID Buffer,
  29. PVOID *MappedBuffer
  30. )
  31. {
  32. NTSTATUS Status;
  33. PHYSICAL_ADDRESS Physical;
  34. UNICODE_STRING SectionName;
  35. OBJECT_ATTRIBUTES ObjectAttributes;
  36. ULONG ViewSize;
  37. LARGE_INTEGER ViewBase;
  38. PVOID BaseAddress;
  39. // We only map our buffer into 1 process at a time.
  40. // Punt if we have already mapped or started to map it.
  41. if (InterlockedCompareExchangePointer(&SectionHandle, 1, NULL)!=NULL) {
  42. return STATUS_UNSUCCESSFUL;
  43. }
  44. // First get the physical address of the buffer we are going to
  45. // map into read only user mode memory of the process calling us.
  46. Physical=MmGetPhysicalAddress(Buffer);
  47. // Now map this buffer into user mode memory and return a pointer
  48. // to the mapped memory.
  49. //
  50. // Open a physical memory section to map in physical memory.
  51. //
  52. RtlInitUnicodeString(
  53. &SectionName,
  54. L"\\Device\\PhysicalMemory"
  55. );
  56. InitializeObjectAttributes(
  57. &ObjectAttributes,
  58. &SectionName,
  59. OBJ_CASE_INSENSITIVE,
  60. (HANDLE) NULL,
  61. (PSECURITY_DESCRIPTOR) NULL
  62. );
  63. Status = ZwOpenSection(
  64. &SectionHandle,
  65. SECTION_ALL_ACCESS,
  66. &ObjectAttributes
  67. );
  68. if (NT_SUCCESS(Status)) {
  69. BaseAddress = NULL;
  70. ViewSize = GlitchInfo->BufferSize+PROCPAGESIZE;
  71. ViewBase.QuadPart = Physical.QuadPart;
  72. Status =ZwMapViewOfSection(
  73. SectionHandle,
  74. NtCurrentProcess(),
  75. &BaseAddress,
  76. 0,
  77. ViewSize,
  78. &ViewBase,
  79. &ViewSize,
  80. ViewUnmap,
  81. 0,
  82. PAGE_READONLY
  83. );
  84. if (NT_SUCCESS(Status)) {
  85. // Keep track of which process opened and mapped this section.
  86. Process=IoGetCurrentProcess();
  87. *MappedBuffer=BaseAddress;
  88. }
  89. else {
  90. // If we fail to map the view. Then we clean up here.
  91. // Close down our SectionHandle and setup so we can run this routine
  92. // again later.
  93. ZwClose(SectionHandle);
  94. // Clear the SectionHandle so we can open it again.
  95. InterlockedExchangePointer(&SectionHandle, NULL);
  96. }
  97. }
  98. else {
  99. // Clear the SectionHandle so we don't lock out all future mapping attempts.
  100. InterlockedExchangePointer(&SectionHandle, NULL);
  101. }
  102. return Status;
  103. }
  104. NTSTATUS
  105. UnMapContiguousBufferFromUserModeProcess (
  106. PVOID MappedBuffer
  107. )
  108. {
  109. HANDLE CurrentProcess;
  110. NTSTATUS Status=STATUS_UNSUCCESSFUL;
  111. // Only let this call through, if we have an open section handle,
  112. // and the process calling us matches the process that opened the
  113. // section handle.
  114. CurrentProcess=IoGetCurrentProcess();
  115. if (InterlockedCompareExchangePointer(&Process, NULL, CurrentProcess)==CurrentProcess) {
  116. // I should NEVER be able to get here unless SectionHandle is valid
  117. // and was a handle opened by the current process. I should also
  118. // NEVER be able to get here unless MappedBuffer is valid as well.
  119. ASSERT( SectionHandle!=NULL );
  120. ASSERT( MappedBuffer!=NULL );
  121. Status = ZwUnmapViewOfSection(NtCurrentProcess(), MappedBuffer);
  122. ZwClose(SectionHandle);
  123. // Clear the SectionHandle so we can open it again.
  124. InterlockedExchangePointer(&SectionHandle, NULL);
  125. }
  126. return Status;
  127. }
  128. #endif