You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C++ Builder中Indy10设置SSL RootCertFile出现乱码路径报错怎么办

故障原因
  1. 编码转换Bug:C++ Builder 10.3自带的Indy 10构建版本存在属性传参缺陷。OpenSSL底层仅接受UTF-8编码的文件路径,该版本Indy在处理RootCertFile属性时,遗漏了Unicode到UTF-8的编码转换步骤,错误地按本地ANSI编码处理字符串,当路径包含中文、或内存读取偏移异常时,就会生成乱码文件名,与当前可执行文件工作目录拼接后成为无效路径,触发文件找不到异常。同版本Indy对CertFile、KeyFile属性的编码转换逻辑是正常的,因此仅设置这两个参数时不会报错。
  2. 配置项认知偏差:RootCertFile的作用是存储客户端用于校验服务端证书合法性的根CA证书链,并非提供给服务端校验客户端身份使用。客户端身份校验只需要配置正确的CertFile(客户端证书)和KeyFile(客户端私钥)即可完成,RootCertFile留空时仅代表客户端不主动校验服务端证书,不影响服务端对客户端的证书校验流程。
解决方案

按照改造成本从低到高可选以下方案:

  • 临时规避方案:将根证书文件放在纯英文、无空格和特殊字符的路径下,例如直接放在可执行文件同级目录,命名为rootca.crt这类纯英文文件名,给RootCertFile赋值时直接使用相对路径,避开会触发编码错误的非ASCII字符即可正常加载。
  • 稳定绕开Bug方案:不依赖Indy的RootCertFile属性传参,在调用Open()建立连接前,直接调用OpenSSL原生API加载根证书,完全绕开Indy的编码转换逻辑。示例代码如下:
// 需提前引入OpenSSL相关头文件
#include <openssl/ssl.h>
#include <IdSSLOpenSSL.hpp>

// 完成其他SSL参数初始化,RootCertFile属性保持留空
net->IdSSLIOHandlerSocketOpenSSL->SSLOptions->Mode        = sslmClient;
net->IdSSLIOHandlerSocketOpenSSL->Host = net->hostname;
net->IdSSLIOHandlerSocketOpenSSL->Port = net->port;
net->IdSSLIOHandlerSocketOpenSSL->SSLOptions->Method      = sslvTLSv1_2;
net->IdSSLIOHandlerSocketOpenSSL->SSLOptions->VerifyMode  = TIdSSLVerifyModeSet(sslvrfClientOnce);
net->IdSSLIOHandlerSocketOpenSSL->SSLOptions->VerifyDepth = 10;
net->IdSSLIOHandlerSocketOpenSSL->OnVerifyPeer            = MainForm->VerifyCertFile;
net->IdSSLIOHandlerSocketOpenSSL->ReadTimeout = 10000;
net->IdSSLIOHandlerSocketOpenSSL->SSLOptions->CertFile     = net->clientname;
net->IdSSLIOHandlerSocketOpenSSL->SSLOptions->KeyFile      = net->keyname;

// 手动获取底层SSL_CTX指针加载根证书
SSL_CTX* sslCtx = static_cast<SSL_CTX*>(net->IdSSLIOHandlerSocketOpenSSL->SSLContext->fContext);
UTF8String utf8RootCertPath = UnicodeToUtf8(net->certname);
if (SSL_CTX_load_verify_locations(sslCtx, utf8RootCertPath.c_str(), nullptr) != 1) {
    // 可通过ERR_get_error()获取具体OpenSSL错误码
    throw Exception("根证书加载失败");
}

// 加载完成后再建立连接
net->IdSSLIOHandlerSocketOpenSSL->Open();
  • 根治方案:升级Indy 10到官方最新修复版本。该编码转换Bug已经在后续Indy代码提交中修复,新版本统一了所有证书路径属性的UTF-8转换逻辑,直接给RootCertFile赋值含非ASCII字符的路径也不会出现乱码问题,项目依赖允许的话直接替换C++ Builder内置的Indy版本即可。

注意:如果开启了服务端证书校验,需要确保OnVerifyPeer回调事件的逻辑符合预期,避免回调返回false导致连接被主动断开。

内容的提问来源于stack exchange,提问作者Barry Andrews

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.29 11:06:20