Мне нужно создать динамическую библиотеку DLL на C ++, чтобы заменить старую библиотеку DLL, написанную на Fortran, без изменения хост-приложения (поэтому функции и параметры должны оставаться неизменными).
У меня есть полная спецификация всех функций Fortran в этой библиотеке, но какие инструменты (компилятор) мне нужно использовать, и как можно кодировать DLL в этой ситуации (stdcall, cdecl, dllexport и т. Д.), Что подсказки не говорят много для меня, я никогда не создавал DLL раньше).
Это пример объявления функции Fortran в устаревшей DLL:
SUBROUTINE SetBoundaries(MaxFlow, MinFlow)
cDEC$ ATTRIBUTES DLLEXPORT :: SetBoundaries
cDEC$ ATTRIBUTES ALIAS: "SetBoundaries" :: SetBoundaries
REAL MaxFlow
REAL MinFlow
Я попытался скомпилировать VC2008 DLL, но получил ошибку:
Необработанная ошибка в «InitAllPublicVars» Ошибка времени выполнения 453: Не удается найти
DLL точка входа DLLVersion в SomeLib.DLL
Источник этой DLL (определение функции с именем DLLVersion не помогает):
void __stdcall SetBoundaries( float *min , float *max ) {
}
Является ли DLLVersion какой-то специальной процедурой DLL или просто отсутствует в моей документации, и я должен создать такую функцию?
Я не знаю подробностей об исходном процессе / компиляции исходного кода на языке Fortran DLL, но есть некоторая извлеченная информация:
Благодаря библиотеке времени исполнения библиотека Fortran DLL выглядит так, как будто она была построена с помощью компиляторов Compaq или Digital Fortran. По умолчанию эти компиляторы использовали соглашение о вызовах stdcall. Для вашего конкретного примера два аргумента (параметры на стороне C) эквивалентны float *
, подпрограммы эквивалентны пустым функциям. Вам нужно будет использовать компилятор C ++, который поддерживает stdcall. То, как вы указываете, что функция экспортируется в DLL, зависит от вашего компилятора C ++ или личных предпочтений, но типичное ключевое слово dllexport является типичным.
С точки зрения управления изменениями было бы гораздо проще написать заменяющую DLL на языке Fortran и использовать что-то вроде компилятора Intel Fortran, который, будучи потомком CVF-компилятора, имеет соответствующую устаревшую поддержку. Изменения в исходном коде DLL могут быть сделаны постепенно.
Я нашел решение. Функции DLL должны быть объявлены так:
extern "C" void __declspec(dllexport) SetBoundaries( int min , int max ) {
}
Обратите внимание, что параметры не являются указателями. Я зарегистрировал вызовы функций, и DLL получает действительные номера от хост-приложения, когда вместо оригинальной библиотеки Fortran DLL. Скомпилировано с Visual Studio 2008.