Driver is not returning any value

0

Today I started experimenting with some kernel driver. It is supposed to read/write virtual memory. I have done some basic implementation in C# but it does not return desired values:

[Flags]
public enum EIOControlCode : uint
{
    // FILE_DEVICE_UNKNOWN = 0x00000022
    // METHOD_BUFFERED = 0
    IO_READ_REQUEST = (0x00000022 << 16) | (0x0701 << 2) | 0 | (0 << 14),
    IO_WRITE_REQUEST = (0x00000022 << 16) | (0x0702 << 2) | 0 | (0 << 14),
    IO_GET_ID_REQUEST = (0x00000022 << 16) | (0x0703 << 2) | 0 | (0 << 14),
    IO_GET_MODULE_REQUEST = (0x00000022 << 16) | (0x0704 << 2) | 0 | (0 << 14)
}

[StructLayout(LayoutKind.Sequential)]
public struct KERNEL_READ_REQUEST
{
    public ulong ProcessId;

    public ulong Address;
    public ulong Response;
    public ulong Size;

    public KERNEL_READ_REQUEST(ulong _ProcessId, ulong _Address, ulong _Response, ulong _Size)
    {
        ProcessId = _ProcessId;
        Address = _Address;
        Response = _Response;
        Size = _Size;
    }
}

[DllImport("Kernel32.dll", SetLastError = true, EntryPoint = "DeviceIoControl")]
public static extern bool DeviceIoControlRead(
    SafeFileHandle hDevice,
    EIOControlCode IoControlCode,
    ref KERNEL_READ_REQUEST InBuffer,
    int nInBufferSize,
    out KERNEL_READ_REQUEST OutBuffer,
    int nOutBufferSize,
    out uint pBytesReturned,
    IntPtr Overlapped
);

KERNEL_READ_REQUEST ReadRequest = new KERNEL_READ_REQUEST();
ReadRequest.ProcessId = ProcessId;
ReadRequest.Address = ReadAddress;
ReadRequest.Size = Size;

if (DeviceIoControlRead(driverHandle, EIOControlCode.IO_READ_REQUEST, ref ReadRequest, 32, out ReadRequest, 32, out Bytes, IntPtr.Zero))
{
    // Returning 0
    return ReadRequest.Response;
}
else
{
    return 0;
}

Does anyone has a clue why it is not working? It is returning the same ReadRequest values as they were initialized.

Thank you.

EDIT: Actually I tried debugging the driver (which works normal through c++ interface) and it turns out that the ReadRequest.Adress value is passed to driver as 0. How it is possible?

EDIT2: I updated struct and some other code:

[StructLayout(LayoutKind.Explicit, CharSet = CharSet.Unicode)]
public struct KERNEL_READ_REQUEST
{
    [FieldOffset(0)] public UInt32 ProcessId;

    [FieldOffset(8)] public UInt32 Address;
    [FieldOffset(16)] public UInt32 Response;
    [FieldOffset(24)] public UInt32 Size;
}

Driver output:

screenshot

The return value is actually the address?

EDIT3: Actually it seems like to work with just LayoutKind.Sequential and UInt32. Yeeeeey.

c#
windows
driver
dllimport
asked on Stack Overflow May 1, 2019 by Samuel Tulach • edited May 2, 2019 by Samuel Tulach

0 Answers

Nobody has answered this question yet.


User contributions licensed under CC BY-SA 3.0