using System;
using System.Diagnostics;
using System.Linq;
using Process.NET.Marshaling;
namespace Process.NET.Modules
{
///
/// Class representing an injected module in a remote process.
///
public class InjectedModule : RemoteModule, IDisposableState
{
///
/// Initializes a new instance of the class.
///
/// The reference of the object.
/// The native object corresponding to the injected module.
/// The module will be ejected when the finalizer collects the object.
public InjectedModule(IProcess processPlus, ProcessModule module, bool mustBeDisposed = true)
: base(processPlus, module)
{
// Save the parameter
MustBeDisposed = mustBeDisposed;
}
///
/// Gets a value indicating whether the element is disposed.
///
public bool IsDisposed { get; private set; }
///
/// Gets a value indicating whether the element must be disposed when the Garbage Collector collects the object.
///
public bool MustBeDisposed { get; set; }
///
/// Releases all resources used by the object.
///
public virtual void Dispose()
{
if (!IsDisposed)
{
// Set the flag to true
IsDisposed = true;
// Eject the module
Process.ModuleFactory.Eject(this);
// Avoid the finalizer
GC.SuppressFinalize(this);
}
}
///
/// Frees resources and perform other cleanup operations before it is reclaimed by garbage collection.
///
~InjectedModule()
{
if (MustBeDisposed)
Dispose();
}
///
/// Injects the specified module into the address space of the remote process.
///
/// The reference of the object.
///
/// The path of the module. This can be either a library module (a .dll file) or an executable module
/// (an .exe file).
///
/// A new instance of the class.
/// A new instance of the class.
internal static InjectedModule InternalInject(IProcess memorySharp, string path)
{
// Call LoadLibraryA remotely
var thread = memorySharp.ThreadFactory.CreateAndJoin(memorySharp["kernel32"]["LoadLibraryA"].BaseAddress, path);
// Get the inject module
if (thread.GetExitCode() != IntPtr.Zero)
return new InjectedModule(memorySharp, memorySharp.ModuleFactory.NativeModules.First(m => m.BaseAddress == thread.GetExitCode()));
return null;
}
}
}