See More

using System; using ProcessNET.Native.Types; using ProcessNET.Utilities; namespace ProcessNET.Memory { ///

/// Class providing tools for manipulating memory protection. /// public class MemoryProtection : IDisposable { protected readonly SafeMemoryHandle Handle; private bool isDisposed = false; /// /// Initializes a new instance of the class. /// /// The reference of the object. /// The base address of the memory to change the protection. /// The size of the memory to change. /// The new protection to apply. /// The resource will be automatically disposed when the finalizer collects the object. public MemoryProtection(SafeMemoryHandle handle, IntPtr baseAddress, int size, MemoryProtectionFlags protection = MemoryProtectionFlags.ExecuteReadWrite, bool mustBeDisposed = true) { // Save the parameters Handle = handle; BaseAddress = baseAddress; NewProtection = protection; Size = size; MustBeDisposed = mustBeDisposed; // Change the memory protection OldProtection = MemoryHelper.ChangeProtection(Handle, baseAddress, size, protection); } /// /// The base address of the altered memory. /// public IntPtr BaseAddress { get; } /// /// States if the object nust be disposed when it is collected. /// public bool MustBeDisposed { get; set; } /// /// Defines the new protection applied to the memory. /// public MemoryProtectionFlags NewProtection { get; } /// /// References the inital protection of the memory. /// public MemoryProtectionFlags OldProtection { get; } /// /// The size of the altered memory. /// public int Size { get; } /// /// Restores the initial protection of the memory. /// public virtual void Dispose() { if (isDisposed) return; isDisposed = true; // Restore the memory protection MemoryHelper.ChangeProtection(Handle, BaseAddress, Size, OldProtection); // Avoid the finalizer GC.SuppressFinalize(this); } /// /// Frees resources and perform other cleanup operations before it is reclaimed by garbage collection. /// ~MemoryProtection() { if (MustBeDisposed) Dispose(); } /// /// Returns a string that represents the current object. /// public override string ToString() { return $"BaseAddress = 0x{BaseAddress.ToInt64():X} NewProtection = {NewProtection} OldProtection = {OldProtection}"; } } }