Как вы знаете, смешивание времени выполнения C является реальной проблемой. Таким образом, одним из аспектов распределения DLL всегда будет выбор времени выполнения. Иногда это не свободный выбор. DLL, которая будет загружена во время выполнения существующим приложением (думаю, плагином), должна (обычно) соответствовать выбору CRT, используемому хост-приложением.
Вы можете себе представить, что можете статически связать ЭЛТ с вашей DLL и избежать проблем. Проблема, которая возникает тогда, заключается в том, что вам приходится передавать выделенные указатели между DLL и ее хост-приложением, поскольку большая часть проблем со смешанными средами выполнения связана с наличием более одной реализации malloc()
и free()
в процессе. Однако с помощью тщательно разработанного и реализованного API для DLL это может быть решением.
В таких дистрибутивах, как Lua Binaries , описанных Ответ Марка Рушакова , используется большое количество средств автоматизации сборки, позволяющих сделать так много комбинаций платформы и компилятора. Поддержание процесса сборки - это значительный объем работы для его команды. Когда отдельная группа решила создать установщик Windows для Lua , чтобы предоставить пользователям Windows возможность простого первого использования, они решили (я считаю разумно) выбрать одну версию CRT для своего продукта и потребовать, чтобы все DLL-библиотеки расширений, которые поставляются с ним, скомпилированы для этой единственной версии.
Одной из практик, которой вы должны следовать как часть своей версии пакета, является использование Dependency Walker для проверки того, что используется ожидаемый CRT, и что все другие зависимости являются либо системной DLL, из приложения вашего хостинга установка, или также включена в ваш пакет. Обходчик зависимостей может быть запущен из пакетного файла, поэтому его можно использовать как часть набора регрессионных тестов для автоматической проверки. Например, при выпуске проектов, основанных на Lua, я запускаю свою окончательную сборку в Dependency Walker из Makefile как часть цели, которая создает установочный пакет, и использую сценарий perl для проверки журнала, чтобы убедиться, что единственные используемые DLL являются либо частями моей установки или из системы.
Как уже говорили другие, если ваша DLL используется конечными пользователями, которые не ожидают разработки с ней (например, плагином для более крупного приложения, распространяемого независимо), тогда все, что вам нужно для упаковки, - это сама DLL (и любые его зависимости, документация для конечного пользователя и т. д.). В этом случае вы просто должны убедиться, что DLL использует ту же среду выполнения, что и приложение.
Если DLL предназначена для сообщества разработчиков, то вы, скорее всего, в случае с множественными сборками Lua Binaries. Каждый дистрибутивный пакет будет содержать правильно построенную DLL, а также библиотеку импорта (.LIB) и всю документацию. Для библиотек DLL, созданных VS, которые, как ожидается, будут связаны с кодом из других компиляторов, может быть целесообразно включить файл .DEF, который документирует фактические экспортированные имена. Современному MinGW это на самом деле не нужно, но пользователи Borland C или, возможно, языков, отличных от C, могут использовать любую помощь, которую они могут получить.
Учитывая недавний рост популярности динамических языков, таких как Lua, Perl, TCL и Python, которые часто можно легко привязать к библиотекам, реализованным в C, эти пользовательские сообщества также могут получить высокую оценку, если вы можете предоставить привязки для эти языки вместе с двоичными файлами, скомпилированными по «локальному обычаю» для выбора CRT.