The following virtual memory can be understood as logical memory, because I think only in this way can we talk about everything below. The following "not paging" indicates that the page is not encoded.
The following is the MDL struct (I am very depressed. I did not find this struct on msdn)
Typedef struct _ MDL {
Struct _ MDL * Next; // The next MDL
Cshort size; // size
Cshort mdlflags; // flag, protection attribute, etc.
Struct _ eprocess * process ;//
Pvoid mappedsystemva;
Pvoid startva;
Ulong bytecount;
Ulong byteoffset;
} MDL, * pmdl;
How to Use MDL:
A continuous virtual memory address range may be composed of multiple distributions (spread over) on Non-adjacent physical pages. The system uses the MDL (memory Descriptor Table) struct to indicate the physical page layout of the virtual memory buffer. We should avoid direct access to MDL. We can use the macros provided by MS-windows. They provide the basic
.
· Mmgetmdlvirtualaddress: Obtain the virtual memory address of the buffer zone.
· Mmgetmdlbytecount obtain the buffer size (number of bytes)
· Mmgetmdlbyteoffset: obtains the size of the physical page starting with the buffer (in bytes)
· Mmgetmdlpfnarray gets an array pointer to the physical page number of the record.
We can use the ioallocatemdl function to allocate an MDL. If you want to cancel the allocation, use the iofreemdl function. Alternatively, you can use mminitializemdl to customize a previously defined buffer into an MDL. However, neither of the preceding methods can initialize the physical page number array.
For the buffer allocated in the non-Paging pool, you can use the mmbuidlmdlfornonpagedpool function to initialize the page number array. For paging memory, the relationship between virtual memory and physical memory is temporary, so the MDL page number array is only valid in a specific environment and time period, because it is very likely that other programs will re-allocate them, in order to make other programs unable to modify and re-allocate them (before we release them), we need to lock this memory, to prevent modification to other programs, we can use the matrix interface to implement it. This function also initializes the page number array for the current layout. When we use mmunlockpages to release the locked memory, the page number array will also be invalid.
If MDL is specified to map a kernel-level virtual address space, we need to use mmgetsystemaddressformdlsafe, so that we can prevent the ing target from the user-mode space, physical pages from the user mode space can only be used in the user mode Context Environment and may be cleared at any time. After being declared using the function, the above situation can be prevented.
The following function is used to create a new MDL: For details about the parameters, refer to the msdn
Pmdl ioallocatemdl (
In pvoid virtualaddress,
In ulong length,
In Boolean secondarybuffer,
In Boolean chargequota,
In out pirp optional
);
The last parameter refers to the IRP (input and output request packet), that is, to associate the newly created MDL buffer with the specified IRP. Why? For example, in a network driver, a temporary buffer should be created for each IP datagram sent to the local machine, and the end user-application needs to read the data in the buffer, the IRP request driver must be used to extract an IP datagram. To send the corresponding IRP to the driver, the driver traverses the created MDL chain to find the corresponding MDL, then extract and send the data. After the request is processed, the driver automatically clears the MDL. One IRP can be associated with multiple MDL, as in the example above, one IRP is associated with multiple IP datagram (that is, multiple MDL ). When an IRP of an application idiom requires a new request (which may be an IP datagram of a new IP address), the driver finds that there is no MDL associated with it, at this time, the IP address sends an IP datagram, and the driver establishes an MDL associated with it. If this is the first newly created MDL associated with this IRP, then, the driver assigns the MDL address to mdladdress. If it is not the first MDL, the newly created MDL is placed in the next unit of the last MDL to form the MDL chain. This is the meaning of the first Member in the MDL struct.
Summary: MDL refers to the structure of a virtual memory. A member records multiple page numbers, which are the page numbers of physical blocks with different physical addresses.
To write a system-protected area, you can modify its protection attributes as follows:
1. Create an MDL. Apparently, the physical page number array in the MDL does not initialize ioallocatemdl.
2. initialize the page number array to make it an effective MDL mmbuildmdlfornonpagedpool
3. Lock the database and assign a new value to the new protection attribute "readable matrix ".
4. Obtain the virtual address mmmaplockedpagesspecifycache of the mapped actual memory area.
A lot of code on the Internet is used for 2000 and earlier operating systems, and many functions have been modified in different ways. The following code is used to map an MDL in the kernel zone where the ssdt table is located, modify its read-only attribute to writable, and fix the memory to prevent it from being modified by other applications.
G_pmdlsystemcall = ioallocatemdl
(Keservicedescriptortable. servicetablebase, keservicedescriptortable. numberofservices * 4, false, false, null );
If (! G_pmdlsystemcall)
Return status_unsuccessful;
Mmbuildmdlfornonpagedpool (g_pmdlsystemcall); // initialize the MDL page number Array
// G_pmdlsystemcall-> mdlflags = g_pmdlsystemcall-> mdlflags | mdl_mapped_to_system_va; // change the flags of mdl to the readable state.
MMP robeandlockpages (g_pmdlsystemcall, kernelmode, iowriteaccess); // locked in memory and
The power to rewrite it
Mappedssdt = mmmaplockedpagesspecifycache (// ing locked memory, the so-called ing is to create a consortium of the original memory zone, you
// Modify the MDL, that is, modify the memory zone it describes.
G_pmdlsystemcall,
Kernelmode,
Menoncached, // whether to allow use as the CPU Buffer
False, // valid only when the second parameter is usermode
Null, // if an error occurs, null is returned directly.
); // Mappedssdt is the mapped ssdt address.
[Note] the last function is actually useless, but among the functions that can get the ing buffer address after 2000, this function is the most advanced supporter, and 2000 uses mmmaplockedpages;
References: msdn