我们有一个由VS构建的(纯本机C++).DLL.作为客户端,我们有一些本机C++应用程序和围绕这个用C++/CLI编写的DLL的.Net-Wrapper.最后,有一些用C#编写的.Net-Wrapper客户端应用程序.
我的问题是native.dll必须以与.Net世界不同的方式分发,并且VS不会跟踪该DLL.因此,要让我的所有C#应用程序正常工作,我必须将其复制到每个可执行文件目录中,或者将其放在%PATH%中(我会避免在开发人员计算机上,因为他们可能希望使用不同版本的DLL启动不同的应用程序).如果存在引用Wrapper-DLL的UserControl,则会出现更大的问题:您必须将DLL复制到VS的目录或再次复制到%PATH%.但最坏的情况发生在我们的翻译工具上.该工具跟踪.Net-Assemblies并将它们打包到可以发送给外部翻译器的Translator-packages中.据我所知,没有办法将原生.DLL放入该包中!
所以我打算将原生DLL静态链接到.Net-Wrapper,这将解决我的问题.但对于我们的Native应用程序,此本机DLL仍必须是DLL.
所以我有两个选择:
在我的应用程序中,我使用CodeDom.Compiler从source.cs文件编译另一个程序,我在编译时嵌入了一些资源(exe和dll文件),使用:
// .... rest of code
if (provider.Supports(GeneratorSupport.Resources))
{
cp.EmbeddedResources.Add("MyFile.exe");
}
if (provider.Supports(GeneratorSupport.Resources))
{
cp.EmbeddedResources.Add("New.dll");
}
// ....rest of code
Run Code Online (Sandbox Code Playgroud)
在编译文件中,我需要将嵌入资源作为字节数组读取.现在我通过使用下面的函数和使用将资源提取到磁盘来实现这一点
File.ReadAllBytes("extractedfile.exe");
File.ReadAllBytes("extracteddll.dll");
Run Code Online (Sandbox Code Playgroud)
我使用此函数将两个文件解压缩到磁盘后执行此操作:
public static void ExtractSaveResource(String filename, String location)
{
// Assembly assembly = Assembly.GetExecutingAssembly();
System.Reflection.Assembly a = System.Reflection.Assembly.GetExecutingAssembly();
// Stream stream = assembly.GetManifestResourceStream("Installer.Properties.mydll.dll"); // or whatever
// string my_namespace = a.GetName().Name.ToString();
Stream resFilestream = a.GetManifestResourceStream(filename);
if (resFilestream != null)
{
BinaryReader br = new BinaryReader(resFilestream);
FileStream fs = new FileStream(location, FileMode.Create); // say
BinaryWriter bw = new …Run Code Online (Sandbox Code Playgroud)