Динамически разрешать функции C stdlib из .NET - PullRequest
3 голосов
/ 29 марта 2012

Я хочу разрешить адреса функций, подобных тем, которые есть в C-stdlib, например, malloc во время выполнения, из кода .NET (поэтому я могу использовать машинный код JIT, который вызывает эти адреса для моей виртуальной машины).Я считаю, что я должен использовать LoadLibrary и GetProcAddress, поставляя kernel32.dll, но это не работает.Используя интерактивный F #, я получаю:

> [<DllImport("kernel32.dll", CharSet=CharSet.Ansi, SetLastError=true)>]
  extern IntPtr LoadLibrary(string fileName);;
val LoadLibrary : string -> IntPtr

> [<DllImport("kernel32.dll", CharSet=CharSet.Ansi, SetLastError=true)>]
  extern uint32 GetProcAddress(IntPtr hModule, string fn);;
val GetProcAddress : IntPtr * string -> uint32

> let kernel32 = LoadLibrary @"kernel32.dll";;
val kernel32 : IntPtr = 1993146368n

> let malloc = GetProcAddress(kernel32, "malloc");;
val malloc : uint32 = 0u

Таким образом, похоже, что получен дескриптор библиотеки DLL, но при попытке решить malloc возвращается указатель NULL.

Как мне это сделать

Ответы [ 3 ]

3 голосов
/ 29 марта 2012

Я не верю, malloc является частью kernel32.dll. Однако, если я правильно помню, все реализации malloc в конечном итоге переходят к HeapAlloc , который доступен в kernel32.dll.

3 голосов
/ 29 марта 2012

AFAIK malloc НЕ является частью kernel32.dll.Это часть библиотек времени выполнения MS C - поскольку вы не предоставляете никаких подробностей о том, как / где вы хотите использовать это, просто некоторые ссылки с соответствующей информацией:

В основном вам нужно загрузить соответствующую DLL, а затем разрешить нужную функцию, например:

let SomeMSCRT = LoadLibrary @"SomeMSCRT.dll";;
let malloc = GetProcAddress(SomeMSCRT, "malloc");;

Одна заметка:

В зависимости от того, что именно вы хотите сделать, вы можете столкнуться с серьезными и сложными проблемами отладки - например, использование malloc из F # - ИМХО плохая идея ... вы должны иметь в виду, что среда выполнения C требует правильной инициализации(в случае MS CRT вы должны назвать CRT_INIT как самое первое) и т. д. Среда выполнения C НЕ знает о каких-либо особенностях .NET и, таким образом, может привести к нестабильному поведению ... esp.поскольку CLR может использовать CRT (возможно, другую версию) для внутреннего использования ...

Другой момент:

Генерация машинного кода во время выполнения и выполнение его путем перехода в эту область памяти зависит отнесколько мер безопасности (в зависимости от версии Windows и т. д.).Возможно, вам потребуется пометить соответствующий сегмент памяти как «исполняемый», что НЕ возможно через среду выполнения C, это возможно только с помощью вызовов Windows API (например, VirtualAllocEx) с соответствующими разрешениями ... см. Здесь отправную точку и здесь .

2 голосов
/ 29 марта 2012

Я хочу разрешить адреса функций, подобных C stdlib

Есть ваша проблема.Вы говорите так, как будто есть одна библиотека времени выполнения Си.На самом деле их много.Каждый компилятор предоставляет свой собственный, в нескольких вариантах (отладка, выпуск, статическая ссылка, динамическая ссылка), и все они взаимно несовместимы.

Если вы знали, какой из них вы пытаетесь использовать, ответ навопрос станет очевидным.

Если вы хотите, чтобы предоставляемые ОС библиотеки использовались всеми приложениями Windows, тогда kernel32.dll - это правильное место для поиска, но функции соответствуют спецификации Win32 API, а не ANSI илиСтандарт ИСО С.

...