是否警告“SSL3_READ_BYTES:sslv3 alert bad certificate”表明 SSL 失敗
執行以下命令時 openssl s_client -host example.xyz -port 9093
我收到以下錯誤:
139810559764296:error:14094412:SSL routines:SSL3_READ_BYTES:sslv3 alert bad certificate:s3_pkt.c:1259:SSL alert number 42 39810559764296:error:140790E5:SSL routines:SSL23_WRITE:ssl handshake failure:s23_lib.c:184:
但最後我收到
"Verify return code: 0 (ok)"
消息。我的問題是上述警報意味著什麼,以及 SSL 是否真的成功。
SSL handshake has read 6648 bytes and written 354 bytes New, TLSv1/SSLv3, Cipher is AES128-SHA Server public key is 2048 bit Secure Renegotiation IS supported Compression: NONE Expansion: NONE SSL-Session: Protocol : TLSv1.2 Cipher : AES128-SHA Session-ID: xx Session-ID-ctx: Master-Key: xx Key-Arg : None Krb5 Principal: None PSK identity: None PSK identity hint: None Start Time: 1475096098 Timeout : 300 (sec) **Verify return code: 0 (ok)**
“握手失敗”表示握手失敗,並且沒有 SSL/TLS 連接。您應該看到
openssl
退出到 shell(或 CMD 等)並且不等待將輸入數據發送到伺服器。“驗證返回碼 0”表示在伺服器的證書中沒有發現任何問題,要麼是因為根本沒有檢查,要麼是因為它已經過檢查並且很好(就 OpenSSL 的檢查而言,它並沒有涵蓋所有內容);在這種情況下,通過了解協議,我們可以推斷出後一種情況適用。收到警報
bad certificate
(程式碼 42)意味著伺服器要求您使用證書進行身份驗證,而您沒有這樣做,導致握手失敗。在該行之前的幾行,SSL handshake has read ... and written ...
您應該會看到一行Acceptable client certificate CA names
通常後跟幾行標識 CA,可能後跟一行開頭Client Certificate Types
,可能還有一些Requested Signature Algorithms
取決於您的 OpenSSL 版本和協商的協議。在“可接受”列表中查找由 CA 頒發的證書,或者如果它是空的,請在伺服器上或關於伺服器的文件中查找說明它信任哪些 CA 或聯繫伺服器運營商或所有者並詢問他們,以及匹配的私鑰,兩者以 PEM 格式,並用;指定它們
-cert $file -key $file
如果您將兩者都放在一個文件中,就像 PEM 一樣,只需使用-cert $file
. 如果你有不同的格式,要麼指定它,要麼在這裡搜尋超級使用者和security.SX;已經有很多關於轉換各種證書和私鑰格式的問答。如果您的證書需要驗證“鏈”或“中間”證書(甚至多個),通常情況下來自公共 CA 的證書(相對於內部證書)取決於伺服器的配置方式,s_client
需要一個技巧:要麼將鏈證書添加到您的系統信任庫,要麼創建一個本地/臨時信任庫,其中包含您需要驗證伺服器的 CA 證書以及您需要發送的鏈證書。如果您沒有這樣的證書,您要麼需要獲得一個,這是一個需要更多詳細資訊才能回答的不同問題,要麼您需要找到一種不使用證書身份驗證連接到伺服器的方法;再次檢查文件和/或詢問運營商/所有者。
編輯:從評論看來,您可能擁有 Java 中的客戶端密鑰和證書鏈以及伺服器錨點。在檢查時,我沒有看到一個很好的現有答案完全涵蓋了這種情況,所以即使這可能不會很好地搜尋:
# Assume Java keystore is type JKS (the default but not only possibility) # named key.jks and the privatekey entry is named mykey (ditto) # and the verify certs are in trust.jks in entries named trust1 trust2 etc. # convert Java key entry to PKCS12 then PKCS12 to PEM files keytool -importkeystore -srckeystore key.jks -destkeystore key.p12 -deststoretype pkcs12 -srcalias mykey openssl pkcs12 -in key.p12 -nocerts -out key.pem openssl pkcs12 -in key.p12 -nokeys -clcerts -out cert.pem openssl pkcs12 -in key.p12 -nokeys -cacerts -out chain.pem # extract verify certs to individual PEM files # (or if you 'uploaded' PEM files and still have them just use those) keytool -keystore trust.jks -export -alias trust1 -rfc -file trust1.pem keytool -keystore trust.jks -export -alias trust2 -rfc -file trust2.pem ... more if needed ... # combine for s_client cat chain.pem trust*.pem >combined.pem openssl s_client -connect host:port -key key.pem -cert cert.pem -CAfile combined.pem