Компиляция неуправляемых DLL с помощью exe - PullRequest
0 голосов
/ 11 сентября 2018

Я пытаюсь встроить кучу библиотек DLL в мой исполняемый файл C #, используя costura fody, но у меня возникли некоторые проблемы с двумя библиотеками DLL.Я использую библиотеку NAudio и библиотеку NAudio.Lame, и хотя обе библиотеки DLL прекрасно компилируются в исполняемый файл, пакет NAudio.Lame добавляет библиотеки dll "libmp3lame.64.dll" и "libmp3lame.32.dll", которые яне в состоянии скомпилировать с exe.Я попытался добавить следующее в файл FodyWeavers.xml под узлом Costura:

<Unmanaged32Assemblies>
    libmp3lame.32
</Unmanaged32Assemblies>
<Unmanaged64Assemblies>
    libmp3lame.64
</Unmanaged64Assemblies>

XML не изменяет размер файла исполняемого файла, поэтому я предполагаю, что он ничего не сделал.

Я также попытался изменить «Build Action» библиотек DLL на «Embedded Resource», и, хотя размер исполняемого файла значительно увеличивается, я получаю DLLNotFoundExeption Runtime, если я запускаю программу без библиотек DLL в той же папке, что и exe.

РЕДАКТИРОВАТЬ: Теперь я заметил, что мне нужна только 64-битная DLL для запуска программы на моем компьютере, но я не могу добавить только эту DLL

EDIT2: Я попытался настроить событие для AssemblyResolve, используя следующий код:

    private static Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args) {
        using (var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream("Client.libmp3lame.64.dll")) {
            byte[] assemblyData = new byte[stream.Length];
            stream.Read(assemblyData, 0, assemblyData.Length);
            return Assembly.Load(assemblyData);
        }
    }

В этот раз он оставил исключение System.BadImageFormatExmat, так как я думаю этокод работает только для управляемых DLL.

Ответы [ 2 ]

0 голосов
/ 11 сентября 2018

Я нашел решение!

Очевидно, все, что мне нужно было сделать, это создать папки Costura32 и Costura64 в корне моего проекта, поместить 32-битные и 64-битные библиотеки DLL в соответствующие папки,измените их действие сборки на «Embedded Resource» и скомпилируйте с моими исходными настройками Costura.

Вот как выглядит мой проект:

Screenshot ofsolution explorer

Это мой FodyWeavers.xml:

<?xml version="1.0" encoding="utf-8"?>
<Weavers>
  <Costura>
    <IncludeAssemblies>
        NAudio
        NAudio.Lame
    </IncludeAssemblies>
    <Unmanaged32Assemblies>
      libmp3lame.32
    </Unmanaged32Assemblies>
    <Unmanaged64Assemblies>
      libmp3lame.64
    </Unmanaged64Assemblies>  
  </Costura>
</Weavers>
0 голосов
/ 11 сентября 2018

Добавьте файл в свой проект как «Встроенный ресурс»:

Embedded resource

Сохраните затем в основной каталог сборки:

Assembly assembly = this.GetType().Assembly;
string assemblyLocation = System.IO.Path.GetDirectoryName(assembly.Location);

if (!System.IO.File.Exists(System.IO.Path.Combine(assemblyLocation, "libmp3lame.64.dll")))
{
    using (FileStream fileStream = new FileStream(assemblyLocation + "libmp3lame.64.dll", FileMode.CreateNew, FileAccess.Write, FileShare.None))
        assembly.GetManifestResourceStream("Client.libmp3lame.64.dll").CopyTo(fileStream);
}

COM dll не может быть загружен в домен, его нужно сохранить только в корне приложения.

...