I am trying to embed a bunch of DLLs in my C# executable using costura fody, but I am having some trouble with 2 DLLs. I am using the NAudio library and the NAudio.Lame library, and while both DLLs compile perfectly into the exe, the NAudio.Lame package adds the dlls "libmp3lame.64.dll" and "libmp3lame.32.dll", which I am not able to compile with the exe. I have tried adding the following in the FodyWeavers.xml file under the Costura node:
<Unmanaged32Assemblies>
libmp3lame.32
</Unmanaged32Assemblies>
<Unmanaged64Assemblies>
libmp3lame.64
</Unmanaged64Assemblies>
The XML does not change the filesize of the exe, so I assume it did nothing.
I have also tried to change the "Build Action" of the DLLs to "Embedded Resource", and while the executable file size increases significantly, I get a Runtime DLLNotFoundExeption if I launch the program without the DLLs in the same folder as the exe.
EDIT: I now noticed that I only need the 64 bit dll for the program to run on my computer, but I am not able to add only that dll either
EDIT2: I tried setting up an event for AssemblyResolve using the following code:
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);
}
}
It left a System.BadImageFormatException this time, as I think this code only works for managed DLLs.
I found a solution!
Apparently all I needed to do was to create the folders Costura32 and Costura64 in the root of my project, put the 32-bit and 64-bit DLLs in their respective folders, change their build action to "Embedded Resource" and compile with my original Costura settings.
This is how my project looks:

This is my 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>
Add the file to your project as "Embedded resource":

Save then to the main assembly directory:
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 cannot be loaded to the domain, you need to save it on application root only.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With