max*_*zig 11 openssl certificates gnutls
我试图产生这样的证书验证错误openssl s_client
:
$ openssl s_client -crlf -verify 9 \
-CAfile /etc/ssl/certs/TURKTRUST_Certificate_Services_Provider_Root_1.pem \
-starttls smtp -host mx-ha03.web.de -port 25
Run Code Online (Sandbox Code Playgroud)
web.de服务器的证书是德国电信CA认证的,不是TURKTRUST,所以上面的命令应该会失败吧?
但它报告:
Verify return code: 0 (ok)
Run Code Online (Sandbox Code Playgroud)
为什么?
我的意思是模拟 gnutls-cli 命令按预期失败:
$ { echo -e 'ehlo example.org\nstarttls' ; sleep 1 } | \
gnutls-cli --starttls --crlf \
--x509cafile /etc/ssl/certs/TURKTRUST_Certificate_Services_Provider_Root_1.pem \
--port 25 mx-ha03.web.de
[..]
*** Verifying server certificate failed...
Run Code Online (Sandbox Code Playgroud)
进行交叉检查,即使用--x509cafile /etc/ssl/certs/ca-certificates.crt
gnutls-cli代替我得到:
[..]
- The hostname in the certificate matches 'mx-ha03.web.de'.
- Peer's certificate is trusted
Run Code Online (Sandbox Code Playgroud)
(这也是预期的)
Openssl s_client 打印 ca-certificates.crt:
Verify return code: 0 (ok)
Run Code Online (Sandbox Code Playgroud)
与 TURKTRUST 相同的结果......
首先,我使用默认设置疑似OpenSSL的-CApath
(即在/ etc / SSL /证书) -但是当我strace
的过程中,我只看到只是open
系统调用进行的争论CAfile
。
(所有测试均在 Ubuntu 10.04 服务器上完成)
更新:我已将 TURKTRUST 证书复制到 Fedora 20 系统并执行了第一个 openssl 语句 - 我得到了不同的结果:
Verify return code: 19 (self signed certificate in certificate chain)
Run Code Online (Sandbox Code Playgroud)
max*_*zig 11
事实证明,在openssl s_client
Ubuntu的10.04仍然会查询系统安装的证书默认位置,即使-CApath
与 -CAfile
被指定的:
8466 open("/usr/lib/ssl/certs/4e18c148.0", O_RDONLY) = 4
Run Code Online (Sandbox Code Playgroud)
(跟踪输出)
在哪里:
$ ls -l /usr/lib/ssl/certs/4e18c148.0
lrwxrwxrwx 1 root root 30 2014-04-11 21:50 /usr/lib/ssl/certs/4e18c148.0 ->
Deutsche_Telekom_Root_CA_2.pem
Run Code Online (Sandbox Code Playgroud)
该目录/usr/lib/ssl/certs
是/etc/ssl/certs
Ubuntu 10.04 上的符号链接,因此open
在 grepping '/etc/ssl' 时不会选择 strace 日志中的行...
查看openssl-0.9.8k,这个问题的根源在crypto/x509/by_dir.c
,dir_ctrl()
:
dir=(char *)Getenv(X509_get_default_cert_dir_env());
if (dir)
ret=add_cert_dir(ld,dir,X509_FILETYPE_PEM);
else
ret=add_cert_dir(ld,X509_get_default_cert_dir(),
X509_FILETYPE_PEM);
Run Code Online (Sandbox Code Playgroud)
哪里X509_get_default_cert_dir
返回/usr/lib/ssl/certs
和X509_get_default_cert_dir_env
返回SSL_CERT_DIR
。
因此,可以在 Ubuntu 10.04/openssl 0.9.8k 下使用以下解决方法来获得预期的行为:
$ SSL_CERT_DIR="" openssl s_client -crlf -verify 9 \
-CAfile /etc/ssl/certs/TURKTRUST_Certificate_Services_Provider_Root_1.crt \
-starttls smtp -host mx-ha03.web.de -port 25
Run Code Online (Sandbox Code Playgroud)
并且验证失败:
Verify return code: 19 (self signed certificate in certificate chain)
Run Code Online (Sandbox Code Playgroud)
这是一个 Ubuntu 问题。例如,对于 Fedora 20 的 openssl 1.0.1e 或 Fedora 29 的 openssl 1.1.1,此解决方法不是必需的,因为问题无法重现。这意味着当指定像-CAfile
或这样的选项时-CApath
,不会将默认证书系统目录添加到 Fedora 系统上的目录搜索列表中。
在带有 openssl 1.0.2g 的 Ubuntu 16 上,问题仍然存在。
它也出现在带有 openssl-1.0.2k-16 的 CentOS 7 上 - 不幸的是,上述解决方法在那里没有帮助,并且 gnutls-3.3.29-8 由于未知/意外的 TLS 数据包类型而失败。