c# - 启动dll时C#环境堆栈溢出
问题描述
我有一个加载 dll 函数的 C# 程序:
[DllImport("/Users/frk/Workspaces/MySharedLibrary.dll", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Auto, EntryPoint = "MyCFunction")]
public static extern int MyFunction( [In][MarshalAs(UnmanagedType.I4)]MyFormat format, [In][MarshalAs(UnmanagedType.LPArray)] byte[] myString, [In][MarshalAs(UnmanagedType.I4)] int myStringLength, [MarshalAs(UnmanagedType.LPArray)] byte[] output, ref UIntPtr outputLength);
并称它为
int result = MyFunction(format, inPut, inputLength, outPut, ref outputLength);
在 C++ 方面,我有:
当从 C 测试可执行文件调用时,MyCPPFunction 可以完美运行。MyCPPFunction 在其依赖关系的深处包含一个在匿名命名空间中声明和初始化的全局 const 变量:
namespace
{
constexpr unsigned RandTileSize = 256;
std::array<unsigned, RandTileSize * RandTileSize> GenerateSamples()
{
std::array<unsigned, RandTileSize * RandTileSize> samples;
std::mt19937 rd(0);
std::uniform_int_distribution<unsigned> distribution(0, 255);
for (unsigned i = 0; i < RandTileSize * RandTileSize; ++i)
{
samples[i] = distribution(rd);
}
return samples;
};
const auto samples = GenerateSamples();<-- Option#1 this causes a stack overflow when loading the dll in C# environment
unsigned Sample(unsigned index)
{
static const auto samples = GenerateSamples();<-- Option#2 this works and dll loads correctly
return samples[index];
}
}
我在这里很困惑,因为 afaik,选项 1 应该在 dll 的代码部分分配内存,C# 环境应该处理对吗?
我们如何才能在加载 dll 时选择 #1 不导致内存分配问题?
解决方案
DLL 中函数中静态变量的生命周期是从第一次遇到语句到 DLL 卸载的时间。
类或文件范围变量的生命周期是从 DLL 加载到 DLL 卸载。
这样做的结果是,在失败的情况下,您的初始化代码正在运行,而 DLL 正在加载.
在类构造函数中运行重要的代码通常不是一个好主意,因为在加载器锁内可以安全地完成的事情是有限制的。
特别是如果您执行任何需要动态加载另一个 DLL 的操作(例如LoadLibrary
或调用延迟加载链接函数),这可能会导致难以诊断的问题。
如果不准确诊断您的情况出了什么问题,答案很简单:使用选项 2 或选项 3。
选项 3:
void MyDLLInitialize(){
// Initialize the dll here
}
void MyDLLUninitialize(){
// Uninitialize the dll here
}
然后分别在使用任何其他 DLL 函数之前和完成之后从 C# 调用这些函数。
推荐阅读
- azure-storage - 使用安全连接批量上传到 Azure 存储
- python - 我正在处理一个不平衡的数据集。应用 SMOTE 算法对少数类进行上采样会产生相同的准确性和 roc_auc_score 吗?
- java - 如何为 Collectors.toMap() 编写合并函数
- mqtt - 为什么高通 9205 iot 调制解调器在进入 PSM 模式之前会断开数据网络连接?
- c++ - c++ 一致性是否使用 decltype 来帮助进行模板推导?
- android - Flutter - 响应较大的 http 请求
- algorithm - 连接字符串的时间复杂度
- xaml - 显示图像的问题
- javascript - jQuery 数据表 fnDraw(false) 不工作
- svg - 找不到 SVG 元素