При помощи Pascal-сценариев можно вызывать функции из внешних библиотек DLL. Сюда относятся как стандартные функции Windows API из системных библиотек Windows, так и пользовательские функции из пользовательских библиотек DLL.
Пример использования внешних библиотек DLL показан в файле сценария "CodeDll.iss" из папки "Examples" по месту установки Inno Setup.
Папка "Examples" также содержит два примера проекта создания пользовательских DLL: один для Microsoft Visual C++ и один для Embarcadero Delphi.
Для вызова функции из библиотеки DLL сначала, как обычно, следует записать прототип функции, но вместо тела функции необходимо использовать ключевое слово 'external' и указать DLL. Если, к примеру, функция имеет прототип function A(B: Integer): Integer;, то для неё поддерживаются следующие три формы:
[Code] function A(B: Integer): Integer; external '<dllfunctionname>@<dllfilename>'; function A(B: Integer): Integer; external '<dllfunctionname>@<dllfilename> <callingconvention>'; function A(B: Integer): Integer; external '<dllfunctionname>@<dllfilename> <callingconvention> <options>';
Первая форма определяет вызов DLL-функции с использованием соглашения о вызовах по умолчанию.
Вторая форма определяет вызов DLL-функции с использованием специального соглашения о вызовах. Допустимыми соглашениями о вызовах являются: 'stdcall' (по умолчанию), 'cdecl', 'pascal' и 'register'. Все стандартные 32-разрядные функции Windows API используют 'stdcall', как и многие пользовательские 32-разрядные функции DLL. Для 64-разрядных функций Windows API и пользовательских файлов DLL соглашение об вызове все ещё может быть указано, но оно игнорируется, поскольку все 64-разрядные функции всегда используют одно и то же соглашение об вызовах.
Третья форма определяет один или несколько дополнительных параметров загрузки DLL, разделённых пробелами:
Определяет отложенную загрузку библиотеки DLL. Как правило, при запуске Pascal-сценарий проверяет доступность вызываемых DLL-функций и в случае отсутствия одной из них прекращает свою работу. Этого не произойдёт, если указать отложенную загрузку 'delayload': библиотека будет загружена не сразу, а только при первом обращении к функции. Используйте отложенную загрузку, когда не знаете, что при выполнении вызываемая DLL-функция будет фактически доступной. В случае невозможности её вызова Pascal-сценарий продолжит свою работу, но вызовет исключение, которое можно перехватить и корректно обработать отсутствие DLL-функции.
Определяет загрузку библиотеки DLL с флагом LOAD_WITH_ALTERED_SEARCH_PATH, который, по сути, заставляет загрузчик выполнять поиск зависимых DLL, начиная с каталога, в котором находится DLL.
Определяет загрузку библиотеки DLL только при выполнении сценария из программы установки.
Определяет загрузку библиотеки DLL только при выполнении сценария из программы удаления.
Например (вторая форма), если в библиотеке DLL функция называется 'A2', файл DLL имеет имя 'MyDll.dll' и DLL-функция использует соглашение о вызовах 'stdcall', то код записывается следующим образом:
[Code] function A(B: Integer): Integer; external 'A2@MyDll.dll stdcall';
Имя файла DLL может содержать константы.
При установке можно использовать специальную приставку 'files:', чтобы инструктировать программу установки автоматически извлекать один или более файлов DLL, указанных в секции [Files], до загрузки первой библиотеки DLL. Например:
[Files] Source: "MyDll.dll"; Flags: dontcopy noencryption Source: "A.dll"; Flags: dontcopy noencryption Source: "B.dll"; Flags: dontcopy noencryption [Code] procedure MyDllFunc(hWnd: HWND; lpText, lpCaption: AnsiString; uType: Cardinal); external 'MyDllFunc@files:MyDll.dll stdcall'; procedure ADllFunc(hWnd: HWND; lpText, lpCaption: AnsiString; uType: Cardinal); external 'ADllFunc@files:A.dll,B.dll stdcall loadwithalteredsearchpath'; //A.dll зависит от B.dll
Когда используется приставка 'files:' и включено непрерывное сжатие, постарайтесь разместить все файлы DLL в начале списка файлов секции [Files]. Чтобы извлечь произвольный файл в инсталляторе с непрерывным сжатием, программа установки должна будет сперва распаковать все предыдущие файлы, используя временный буфер в памяти. Это может привести к существенной задержке в работе инсталлятора, если перед необходимым файлом DLL перечислен ряд других файлов.
Используйте CreateCallback для выполнения вызова из DLL-функций напрямую в функции вашего сценария (подобно функциям API Windows).
Помимо THandle, для вызова функций Windows API доступны следующие
встроенные типы:
DWORD, UINT, BOOL, LONG, ULONG,
HANDLE, COLORREF, INT_PTR, LONG_PTR,
DWORD_PTR, UINT_PTR, ULONG_PTR, LRESULT,
HKEY, HINSTANCE, HMODULE, WPARAM,
LPARAM, SIZE_T, SSIZE_T, TFileTime,
HResult, TGUID, TCLSID, TIID,
HBITMAP, HDC, HFONT, and HWND.