Easyhook 32-битное приложение

Я использую EasyHook для перехвата вызовов реестра. Более подробно, я использую RegQueryValue, чтобы перехватить вызов, который читает ключ из реестра и изменить его значение на что-то другое. Соответствующий код выглядит так:

[UnmanagedFunctionPointer(CallingConvention.StdCall, CharSet = CharSet.Unicode, SetLastError = true)]
delegate int DRegQueryValueExW(
    IntPtr hKey,
    string lpValueName,
    int lpReserved,
    ref Microsoft.Win32.RegistryValueKind lpType,
    StringBuilder lpData,
    ref int lpcbData);

[DllImport("Advapi32.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.StdCall)]
static extern int RegQueryValueExW(
    IntPtr hKey,
    string lpValueName,
    int lpReserved,
    ref Microsoft.Win32.RegistryValueKind lpType,
    StringBuilder lpData,
    ref int lpcbData);

int RegQueryValueExW_Hooked(
    IntPtr hKey,
    string lpValueName,
    int lpReserved,
    ref Microsoft.Win32.RegistryValueKind lpType,
    StringBuilder lpData,
    ref int lpcbData)
{
    // todo: change value of lpData and return 0
    return RegQueryValueExW(hKey, lpValueName, lpReserved, ref lpType, lpData, ref lpcbData);                  
}

Если я собираю все с target x64, все это выполняется без проблем.

Однако, если я собираю его с целью x32, он вылетает в RegQueryValueExW_Hooked с ошибкой:

Необработанное исключение: System.Runtime.InteropServices.SEHException: внешний компонент выдал исключение. at DummyDCA.Program.Main(String[] args) Необработанное исключение: System.ArgumentOutOfRangeException: емкость превышает максимальную емкость. Имя параметра: емкость в AG.RU.Valuation.Controller.AFMToolbox.Inject.Main.RegQueryValueExW(IntPtrhKey, String lpValueName, Int32 lpReserved, RegistryValueKind& lpType, StringBuilder lpDataToLBT..Main.RegQueryValueExW_Hooked(IntPtr hKey, String lpValueName, Int32 lpReserved, RegistryValueKind& lpType, StringBuilder lpData, Int32& lpcbData)

Кажется, проблема в lpData типа StringBuilder (какое-то переполнение, StringBuilder недостаточно велик или что-то в этом роде). Если я заменю StringBuilder на IntPtr, он не вылетает; но тогда у меня есть указатель, а не StringBuilder, поэтому я не уверен, как я могу заменить значение lpData.

У кого-нибудь есть идея, почему это так и как это нужно делать?

Спасибо!

1 ответ

Решение

Казалось, что вместо StringBuilder мне пришлось использовать IntPtr; и реализация RegQueryValueExW_Hooked также была немного особенной.

Фактическое решение описано Luaan в этой теме: изменение строки, на которую указывает IntPtr

Другие вопросы по тегам