/// <summary> /// Changes memory permissions to ensure memory can be written and writes a generic type to a specified memory address. /// </summary> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to write to.</param> /// <param name="data">The data to write to the specified address.</param> public static void SafeWriteRaw(this IMemory memory, IntPtr memoryAddress, byte[] data) { var oldProtection = memory.ChangePermission(memoryAddress, data.Length, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); memory.WriteRaw(memoryAddress, data); memory.ChangePermission(memoryAddress, data.Length, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be read and reads a generic type from a specified memory address. /// </summary> /// <typeparam name="T">An individual struct type of a class with an explicit StructLayout.LayoutKind attribute.</typeparam> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to read from.</param> /// <param name="value">Local variable to receive the read in struct.</param> public static void SafeRead <T>(this IMemory memory, IntPtr memoryAddress, out T value) where T : unmanaged { int structSize = Struct.GetSize <T>(); var oldProtection = memory.ChangePermission(memoryAddress, structSize, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); memory.Read(memoryAddress, out value); memory.ChangePermission(memoryAddress, structSize, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be written and writes a generic type array to a specified memory address. /// </summary> /// <typeparam name="T">An individual struct type of a class with an explicit StructLayout.LayoutKind attribute.</typeparam> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to write to.</param> /// <param name="items">The array of items to write to the address.</param> /// <param name="marshal">Set this to true to enable struct marshalling.</param> public static void SafeWrite <T>(this IMemory memory, IntPtr memoryAddress, T[] items, bool marshal = false) { int regionSize = StructArray.GetSize <T>(items.Length, marshal); var oldProtection = memory.ChangePermission(memoryAddress, regionSize, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); memory.Write(memoryAddress, items, marshal); memory.ChangePermission(memoryAddress, regionSize, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be written and writes a generic type to a specified memory address. /// </summary> /// <typeparam name="T">An individual struct type of a class with an explicit StructLayout.LayoutKind attribute.</typeparam> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to write to.</param> /// <param name="item">The items to write to the address.</param> public static void SafeWrite <T>(this IMemory memory, IntPtr memoryAddress, ref T item) where T : unmanaged { int memorySize = Struct.GetSize <T>(); var oldProtection = memory.ChangePermission(memoryAddress, memorySize, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); memory.Write(memoryAddress, ref item); memory.ChangePermission(memoryAddress, memorySize, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be read and reads a generic type array from a specified memory address. /// </summary> /// <typeparam name="T">An individual struct type of a class with an explicit StructLayout.LayoutKind attribute.</typeparam> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to read from.</param> /// <param name="value">Local variable to receive the read in struct array.</param> /// <param name="arrayLength">The amount of array items to read.</param> /// <param name="marshal">Set this to true to enable struct marshalling.</param> public static void SafeRead <T>(this IMemory memory, IntPtr memoryAddress, out T[] value, int arrayLength, bool marshal = false) { int regionSize = StructArray.GetSize <T>(arrayLength, marshal); var oldProtection = memory.ChangePermission(memoryAddress, regionSize, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); memory.Read(memoryAddress, out value, arrayLength, marshal); memory.ChangePermission(memoryAddress, regionSize, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be read and reads bytes from a specified memory address. /// </summary> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to read from.</param> /// <param name="value">Local variable to receive the read in bytes.</param> /// <param name="length">The amount of bytes to read from the executable.</param> public static void SafeReadRaw(this IMemory memory, IntPtr memoryAddress, out byte[] value, int length) { var oldProtection = memory.ChangePermission(memoryAddress, length, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); value = new byte[length]; memory.ReadRaw(memoryAddress, out value, length); memory.ChangePermission(memoryAddress, length, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be read and reads a generic type from a specified memory address. /// </summary> /// <typeparam name="T">An individual struct type of a class with an explicit StructLayout.LayoutKind attribute.</typeparam> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to read from.</param> /// <param name="value">Local variable to receive the read in struct.</param> /// <param name="marshal">Set this to true to enable struct marshalling.</param> public static void SafeRead <T>(this IMemory memory, IntPtr memoryAddress, out T value, bool marshal = false) { int structSize = Struct.GetSize <T>(marshal); var oldProtection = memory.ChangePermission(memoryAddress, structSize, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); memory.Read(memoryAddress, out value, marshal); memory.ChangePermission(memoryAddress, structSize, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be written and writes a generic type to a specified memory address. /// </summary> /// <typeparam name="T">An individual struct type of a class with an explicit StructLayout.LayoutKind attribute.</typeparam> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to write to.</param> /// <param name="item">The items to write to the address.</param> /// <param name="marshal">Set this to true to enable struct marshalling.</param> public static void SafeWrite <T>(this IMemory memory, IntPtr memoryAddress, ref T item, bool marshal = false) { int memorySize = Struct.GetSize <T>(marshal); var oldProtection = memory.ChangePermission(memoryAddress, memorySize, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); memory.Write(memoryAddress, ref item, marshal); memory.ChangePermission(memoryAddress, memorySize, oldProtection); }
/// <summary> /// Changes memory permissions to ensure memory can be read and reads bytes from a specified memory address. /// </summary> /// <param name="memory"></param> /// <param name="memoryAddress">The memory address to read from.</param> /// <param name="value">Local variable to receive the read in bytes.</param> /// <param name="length">The amount of bytes to read from the executable.</param> public static void SafeReadRaw(this IMemory memory, IntPtr memoryAddress, out byte[] value, int length) { var oldProtection = memory.ChangePermission(memoryAddress, length, Kernel32.Kernel32.MEM_PROTECTION.PAGE_EXECUTE_READWRITE); #if NET5_0_OR_GREATER value = GC.AllocateUninitializedArray <byte>(length, false); #else value = new byte[length]; #endif memory.ReadRaw(memoryAddress, out value, length); memory.ChangePermission(memoryAddress, length, oldProtection); }
[ExcludeFromCodeCoverage] // Wrapper that simply lets pass with base element calculated with functions tested elsewhere, no logic. public static Kernel32.Kernel32.MEM_PROTECTION ChangePermission <T>(this IMemory memory, IntPtr memoryAddress, ref T baseElement, Kernel32.Kernel32.MEM_PROTECTION newPermissions, bool marshalElement = false) => memory.ChangePermission(memoryAddress, Struct.GetSize <T>(marshalElement), newPermissions);