【发布时间】:2018-12-25 05:20:09
【问题描述】:
我将 openssl 库 (openssl.lib) 包含到一个 dll 中。当我构建这个 dll 时,我发现很少有链接器错误。我调试并发现链接器错误是由于dll的调用约定造成的。我的 dll 使用 _stdcall 调用约定,而 openssl 使用 _cdecl 调用约定。我无法更改我的 dll 的调用约定,因为它是现有解决方案的一部分。所以我尝试将openssl的调用约定改为_stdcall。但我做不到,结果出现了以下构建错误。
\crypto\ui\ui_openssl.c(591) : 错误 C2440: 'function' : 无法从 'void (__stdcall *)(int)' 转换为 'void (__cdecl *)(int)' .\crypto\ui\ui_openssl.c(591):警告 C4024:“信号”:不同 形参和实参的类型 2 .\crypto\ui\ui_openssl.c(591) : 错误 C2440: '=' : 无法从 'void (__cdecl *)(int)' 转换为 'void (__stdcall *)(int)' .\crypto\ui\ui_openssl.c(592):错误 C2440: 'function' : 无法从 'void (__stdcall *)(int)' 转换为 'void (__cdecl *)(int)'
导致构建错误的代码行是:
static void pushsig(void)
{
#ifndef OPENSSL_SYS_WIN32
int i;
#endif
#ifdef SIGACTION
struct sigaction sa;
memset(&sa,0,sizeof sa);
sa.sa_handler=recsig;
#endif
#ifdef OPENSSL_SYS_WIN32
savsig[SIGABRT]=signal(SIGABRT,recsig); // **line 591**
savsig[SIGFPE]=signal(SIGFPE,recsig); // **line 592**
savsig[SIGILL]=signal(SIGILL,recsig);
如何使用 _stdcall(/Gz) 调用约定构建 openssl 库?或者有其他解决方案吗?
注意:signal是一个windows API(调用约定是_cdecl)。请参考此链接https://msdn.microsoft.com/en-us/library/xdkz3x12.aspx
谢谢, 萨蒂什。
【问题讨论】:
-
混合使用不同调用约定的代码没有问题,在您尝试更改调用约定之前最初的链接器错误是什么?
-
以下是在将 openssl.lib(_cdecl 调用约定)链接到 dll(_stdcall 调用约定)时观察到的链接器错误。错误 LNK2001:无法解析的外部符号 _HMAC_CTX_cleanup@4 错误 LNK2001:无法解析的外部符号 _HMAC_Final@12 错误 LNK2001:无法解析的外部符号 _HMAC_Update@12 错误 LNK2001:无法解析的外部符号 _HMAC_Init_ex@20
标签: c++ windows dll openssl calling-convention