为什么我的C++ DLL在Delphi应用中调用后Edit控件无响应?
问题根因及修复方案
你遇到的问题由以下几个常见错误导致,按优先级修复即可:
- DLL加载判断逻辑错误
Windows APILoadLibrary调用成功返回非0的有效模块句柄,失败返回0(NULL)。你代码中if(dll >= 32)的判断逻辑完全错误,绝大多数场景下DLL加载成功后句柄值也会小于32,导致后续逻辑直接跳过,控件自然没有更新。
修复:将判断逻辑改为if dll <> 0 then,同时建议后续增加加载失败的提示逻辑,用完DLL后调用FreeLibrary释放资源。 - 调用约定不统一
C端导出函数没有显式指定调用约定,不同编译器默认调用约定可能存在差异,和Delphi端声明的cdecl不匹配时会出现栈平衡错误、参数/返回值读取异常。
修复:修改C头文件的函数声明,显式指定调用约定:wchar_t* DLL_EXPORT __cdecl Fonksiyon(wchar_t* wchtAlinanMesaj); - 缺少有效性校验
你没有对GetProcAddress的返回值做非空判断,即使DLL加载成功,也可能因为导出函数名不对、编译符号修饰等问题找不到函数入口,导致调用无响应。
修复:获取函数地址后增加判断if Assigned(fonksiyonum) then,确认地址有效再执行调用。 - 返回字符串指针有效性问题
你使用的S2WC转换函数如果返回的是栈上临时内存的指针,函数返回后内存会被系统回收,Delphi端拿到的就是野指针,无法读取到正确内容。同时如果指针是堆分配,还需要注意内存释放规则,避免内存泄漏。
修复:建议使用Windows统一的COM内存分配器分配返回字符串的内存,两边遵循相同的释放规则:
Delphi端读取完返回字符串后,调用// C++端替换S2WC逻辑示例 wchar_t* S2WC(const string& s) { int len = MultiByteToWideChar(CP_ACP, 0, s.c_str(), -1, NULL, 0); wchar_t* res = (wchar_t*)CoTaskMemAlloc(len * sizeof(wchar_t)); MultiByteToWideChar(CP_ACP, 0, s.c_str(), -1, res, len); return res; }CoTaskMemFree(pwchAlinanMesaj)释放内存即可。
内容的提问来源于stack exchange,提问作者Ignacio Ponseti
相关产品推荐
相关产品推荐

