SSL 握手失败并显示“sslv3 警报握手失败:SSL 警报编号 40”

Abh*_*ain 3 ssl openssl ssl-certificate handshake tls1.2

我有一个.pfx文件,在windows客户端上使用时可以完美连接远程服务器。我现在想使用 linux 客户端连接到服务器。

问题 1)我使用以下 openssl 命令从 pfx 文件中提取公共证书和私钥,

openssl pkcs12 -in Name.pfx -nocerts -out priv.pem -nodes
openssl pkcs12 -in Name.pfx -nokeys -out pub.pem
Run Code Online (Sandbox Code Playgroud)

但是当我运行以下两个命令来验证两个文件的 md5 时,我发现它们都不同。

openssl rsa -noout -text -in priv.pem | openssl md5
openssl x509 -noout -text -in pub.pem | openssl md5
Run Code Online (Sandbox Code Playgroud)

问题 2)我改为使用以下命令从具有证书和密钥的 pfx 中提取单个 pem 文件。

openssl pkcs12 -in Name.pfx -out bundle.pem
Run Code Online (Sandbox Code Playgroud)

使用这个 pem 文件,我尝试使用以下命令连接到远程服务器:

openssl s_client -servername 1.2.3.4 -connect 1.2.3.4:1234 -CAfile bundle.pem -state -tls1_2
Run Code Online (Sandbox Code Playgroud)

这在终端上给出以下输出

CONNECTED(00000003)
SSL_connect:before/connect initialization
SSL_connect:SSLv3 write client hello A
SSL_connect:SSLv3 read server hello A
depth=0 O = "My Name", CN = Name - Local
verify return:1
SSL_connect:SSLv3 read server certificate A
SSL_connect:SSLv3 read server key exchange A
SSL_connect:SSLv3 read server certificate request A
SSL_connect:SSLv3 read server done A
SSL_connect:SSLv3 write client certificate A
SSL_connect:SSLv3 write client key exchange A
SSL_connect:SSLv3 write change cipher spec A
SSL_connect:SSLv3 write finished A
SSL_connect:SSLv3 flush data
SSL3 alert read:fatal:handshake failure
SSL_connect:failed in SSLv3 read finished A
140250807310240:error:14094410:SSL routines:SSL3_READ_BYTES:sslv3 alert handshake failure:s3_pkt.c:1275:SSL alert number 40
140250807310240:error:1409E0E5:SSL routines:SSL3_WRITE_BYTES:ssl handshake failure:s3_pkt.c:598:
---
Certificate chain
 0 s:/O=My Name /CN=Name - Local
   i:/O=My Name /CN=Name - Local
---
Server certificate
-----BEGIN CERTIFICATE-----
<random string of certificate>
-----END CERTIFICATE-----
subject=/O=My Name /CN=Name - Local
issuer=/O=My Name /CN=Name - Local
---
No client certificate CA names sent
Server Temp Key: ECDH, secp521r1, 521 bits
---
SSL handshake has read 1332 bytes and written 206 bytes
---
New, TLSv1/SSLv3, Cipher is ECDHE-RSA-AES256-GCM-SHA384
Server public key is 2048 bit
Secure Renegotiation IS supported
Compression: NONE
Expansion: NONE
SSL-Session:
    Protocol  : TLSv1.2
    Cipher    : ECDHE-RSA-AES256-GCM-SHA384
    Session-ID: <some string>
    Session-ID-ctx: 
    Master-Key: <some string>
    Key-Arg   : None
    Krb5 Principal: None
    PSK identity: None
    PSK identity hint: None
    Start Time: 1495217834
    Timeout   : 7200 (sec)
    Verify return code: 0 (ok)
---
Run Code Online (Sandbox Code Playgroud)

我无法弄清楚为什么握手失败。卡住了3天,问题究竟出在哪里。

Ste*_*ich 5

但是当我运行以下两个命令来验证两个文件的 md5 时,我发现它们都不同。

openssl rsa -noout -text -in priv.pem | openssl md5
openssl x509 -noout -text -in pub.pem | openssl md5
Run Code Online (Sandbox Code Playgroud)

第一个命令显示有关私钥的文本信息。关于包含公钥的证书的第二个文本信息。当然,这些信息是不同的。

使用这个 pem 文件,我尝试使用以下命令连接到远程服务器:

openssl s_client -servername 1.2.3.4 -connect 1.2.3.4:1234 -CAfile bundle.pem -state -tls1_2
Run Code Online (Sandbox Code Playgroud)

这将使用证书作为受信任的 CA ( -CAfile)。这可能不是您想要的。相反,您希望将该证书用作客户端证书。这应该通过使用选项 和记录来完成,即在您的情况下。-cert-key-cert bundle.pem -key bundle.pem

除此之外-servername应该是主机名而不是IP地址。如果您没有主机名,请跳过此选项。

SSL_connect:SSLv3 read server certificate request A
...
SSL_connect:SSLv3 write client certificate A
...
SSL3 alert read:fatal:handshake failure
Run Code Online (Sandbox Code Playgroud)

由于您没有正确指定客户端证书,因此将发送一个空的客户端证书。但是服务器需要一个有效的客户端证书,因此在 SSL 警报中将失败的握手报告回客户端。