103 lines
3.9 KiB
C#
103 lines
3.9 KiB
C#
// File: Services/Scanners/ModuleScanner.cs
|
|
|
|
using System.Diagnostics;
|
|
using WebmrAPI.Exceptions;
|
|
using WebmrAPI.Models;
|
|
using WebmrAPI.Utils;
|
|
|
|
namespace WebmrAPI.Services.Scanners
|
|
{
|
|
public class ModuleScanner : AbstractScanner<ProcessModuleInfo>
|
|
{
|
|
override public ScanTarget Target { get => ScanTarget.Modules; }
|
|
internal int PID { get; private set; }
|
|
|
|
override async internal Task<bool> ScanAsync(Dictionary<long, ProcessModuleInfo> data)
|
|
{
|
|
var success = await Task.Run<bool?>(() =>
|
|
{
|
|
try
|
|
{
|
|
using (var process = Process.GetProcessById(PID))
|
|
{
|
|
foreach (ProcessModule module in process.Modules)
|
|
{
|
|
long addr = module.BaseAddress.ToInt64();
|
|
data.Add(addr, new ProcessModuleInfo
|
|
{
|
|
MemoryAddress = addr,
|
|
ModuleName = module.ModuleName,
|
|
FileName = module.FileName,
|
|
MemorySize = (ulong)module.ModuleMemorySize,
|
|
EntrypointRawAddress = module.EntryPointAddress.ToInt64()
|
|
});
|
|
}
|
|
|
|
return true;
|
|
}
|
|
}
|
|
catch (System.ComponentModel.Win32Exception ex) when (ex.NativeErrorCode == 5)
|
|
{
|
|
Provider.Logger.LogWarning($"Access denied to Process.Modules for PID {PID}. Attempting P/Invoke. Error: {ex.Message}");
|
|
if (Provider.ProcessReadAccess) return null;
|
|
}
|
|
catch (InvalidOperationException ex)
|
|
{
|
|
Provider.Logger.LogWarning($"Process with PID {PID} might have exited before module scanning. Error: {ex.Message}");
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
Provider.Logger.LogError(ex, $"An unexpected error occurred while getting modules for PID {PID} using managed API.");
|
|
}
|
|
return false;
|
|
});
|
|
|
|
if (success != null) return success == true ? true : false;
|
|
|
|
return await Task.Run(() =>
|
|
{
|
|
try
|
|
{
|
|
using (var process = new WindowsProcess(PID, true))
|
|
{
|
|
process.ForeachLoadedModule(info =>
|
|
{
|
|
long addr = info.BaseAddress.ToInt64();
|
|
data.Add(addr, new ProcessModuleInfo
|
|
{
|
|
ModuleName = info.Name.ToString(),
|
|
MemoryAddress = addr,
|
|
FileName = info.FileName.ToString(),
|
|
MemorySize = info.MemorySize,
|
|
EntrypointRawAddress = info.EntryPointAddress.ToInt64()
|
|
});
|
|
});
|
|
|
|
return true;
|
|
}
|
|
}
|
|
catch (GettingModuleInfoException ex)
|
|
{
|
|
Provider.Logger.LogDebug(ex.Message);
|
|
}
|
|
catch (ProcessMonitorException ex)
|
|
{
|
|
Provider.Logger.LogError(ex.Message);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
Provider.Logger.LogError(ex, $"An error occurred while getting modules for PID {PID} using P/Invoke.");
|
|
}
|
|
|
|
return false;
|
|
});
|
|
}
|
|
|
|
public ModuleScanner(IScanProvider scanner, LazyConcurrentContainer<ProcessModuleInfo> container, int pid)
|
|
: base(scanner, container)
|
|
{
|
|
PID = pid;
|
|
}
|
|
}
|
|
}
|