OpenSSL:在0深度查找时出现错误20:无法获取本地发行者证书

问题描述

我使用Python创建了3个证书:rootca.crt,intermediateca.crt和server.crt。 我使用rootca.crt签署了中间体ca.crt,它可以按预期工作:

openssl verify -CAfile rootca.crt intermediateca.crt
intermediateca.crt: OK

然后我用中间的ca签署了server.crt,但是验证失败:

openssl verify -CAfile rootca.crt -untrusted intermediateca.crt server.crt
server.crt: C = DE,ST = mein Bundesland,L = meine Stadt,O = meine Firma,CN = server.example.com,emailAddress = info@meine-firma.de
error 20 at 0 depth lookup:unable to get local issuer certificate

当我解析证书时,server.crt授权密钥标识符与中间层主题密钥标识符匹配。谁能给我一个提示可能是什么问题?如果我使用openssl命令行工具生成相同的证书,则可以使用。除了授权密钥标识符还包含一个序列号和一个用于openssl生成的证书的cn之外,解析的内容是相同的。

解决方法

中间CA无法用于验证服务器证书,因为其主题名称与服务器证书中指定的颁发者名称不匹配。

让我们openssl转储主题名称和发行者名称。 -xx_hash显示openssl用于建立证书链的哈希:

$ openssl x509 -subject -subject_hash -noout -in rootca.crt 
subject=C = DE,ST = mein Bundesland,L = meine Stadt,O = meine Firma,OU = meine Abteilung,CN = serviceserver.example.com,emailAddress = info@meine-firma.de
347e2056

$ openssl x509 -issuer -issuer_hash -noout -in intermediateca.crt 
issuer=C = DE,emailAddress = info@meine-firma.de
347e2056

很好,中间节点的颁发者名称与根的使用者名称匹配。链中的那部分起作用。

$ openssl x509 -subject -subject_hash -noout -in intermediateca.crt 
subject=C = DE,emailAddress = info@meine-firma.de
c4dff14c

$ openssl x509 -issuer -issuer_hash -noout -in server.crt 
issuer=C = DE,emailAddress = info@meine-firma.de
347e2056

糟糕:哈希值不同,因此openssl无法将中间CA连接到服务器证书。区别在于中间节点的使用者名称包含一个OU字段,而服务器的发行者名称则没有。当openssl告诉您找不到发行人时,它是正确的。

我不确定您是如何在这种状态下获得它的,我想这可能是主题或发行者名称的某些错误配置。