Tomcat 7 + SSL无法工作 - ERR_SSL_VERSION_OR_CIPHER_MISMATCH

15

Ubuntu 14、tomcat 7、java 7

我们从godaddy获取了our.crt、our.key和gd_bundle-g2-g1.crt。该捆绑包中有3个证书(通过vi命令查看文件可见)。

请注意,我们的密钥和证书已在node.js上使用,没有出现问题。

我们通过现有的crt文件创建了一个密钥库,步骤如下:

cd /etc/ssl
openssl pkcs12 -export -in our.crt -inkey our.key -out our.p12 -name tomcat -CAfile gd_bundle-g2-g1.crt -caname root -chain

服务器配置文件server.xml如下:

<Server port="8005" shutdown="SHUTDOWN">

<Listener className="org.apache.catalina.core.JasperListener" />
<Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener" />
<Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />
<Listener className="org.apache.catalina.core.ThreadLocalLeakPreventionListener" />



<GlobalNamingResources>
<Resource name="UserDatabase" auth="Container"
          type="org.apache.catalina.UserDatabase"
          description="User database that can be updated and saved"
          factory="org.apache.catalina.users.MemoryUserDatabaseFactory"
          pathname="conf/tomcat-users.xml" />
</GlobalNamingResources>


<Service name="Catalina">

<Connector port="80" protocol="HTTP/1.1"
           connectionTimeout="20000"
           URIEncoding="UTF-8"
           redirectPort="8443" />

<Connector port="8443" protocol="HTTP/1.1" SSLEnabled="true"
           maxThreads="200" scheme="https" secure="true"
           keystoreType="PKCS12"
           keystoreFile="/etc/ssl/our.p12" keystorePass=""
           clientAuth="false" sslProtocol="TLS" />
  • Tomcat启动没有错误。
  • Web应用在80端口上正常工作。
  • 服务器没有运行防火墙。

我们设置了从443到8443的本地重定向:

iptables -t nat -A PREROUTING -p tcp --dport 443 -j REDIRECT --to-port 8443

那么请尝试 https://www.ourserver.com/ourapp

Chrome 显示: ERR_SSL_VERSION_OR_CIPHER_MISMATCH

在本地机器上运行的 curl 示例:

curl -Iv https://www.ourserver.com:8443
* Rebuilt URL to: https://www.ourserver.com:8443/
* Hostname was NOT found in DNS cache
*   Trying 1xxxxxxxx...
* Connected to www.ourserver.com (1xxxx) port 8443 (#0)
* successfully set certificate verify locations:
*   CAfile: none
  CApath: /etc/ssl/certs
* SSLv3, TLS handshake, Client hello (1):
* SSLv3, TLS alert, Server hello (2):
* error:14077410:SSL routines:SSL23_GET_SERVER_HELLO:sslv3 alert handshake failure
* Closing connection 0
curl: (35) error:14077410:SSL routines:SSL23_GET_SERVER_HELLO:sslv3 alert handshake failure

有什么想法吗?

更新1

我尝试在新服务器上设置一个新的tomcat 7,并安装了一个全新的证书副本,但仍然出现相同的错误。


由于这个“握手失败”警报是由服务器发送的,因此在调试问题时应查看服务器端,即来自Tomcat的日志消息。 - Steffen Ullrich
遗憾的是,catalina.out 中没有错误。 - John Little
本地主机(localhost)*或其他Tomcat日志文件中有任何错误吗? - Norbert
当我访问SSL端口并在Chrome中收到ERR_SSL_VERSION_OR_CIPHER_MISMATCH消息时,localhost_access_log.yyyy-mm-dd没有条目。 - John Little
1
为什么不在Apache Web服务器后面运行它? - Michael-O
你确定你有keystorePass的值吗?如果这是一个自定义密码(不是'changeit'),也尝试为keyPass属性指定相同的密码。请参见https://tomcat.apache.org/tomcat-7.0-doc/config/http.html#SSL_Support_-_BIO_and_NIO。 - Anand Bhat
6个回答

19

尝试在连接器标签中添加ciphers属性,例如:

ciphers="TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256,TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,
   TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384,TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA,TLS_ECDHE_RSA_WITH_RC4_128_SHA,
   TLS_RSA_WITH_AES_128_CBC_SHA256,TLS_RSA_WITH_AES_128_CBC_SHA,TLS_RSA_WITH_AES_256_CBC_SHA256,
   TLS_RSA_WITH_AES_256_CBC_SHA,SSL_RSA_WITH_RC4_128_SHA"

如果这不起作用,尝试将您的协议属性从protocol="HTTP/1.1"更改为protocol="org.apache.coyote.http11.Http11Protocol"

有关更多参考,请参见


1
谢谢查看。我找到了一份类似的参考资料并尝试设置密码,但这没有帮助。我刚刚尝试了你找到的密码,重新启动了Tomcat,但不幸的是仍然出现相同的ERR_SSL_VERSION_OR_CIPHER_MISMATCH错误。 - John Little
刚刚按照您的建议尝试了org.apache.coyote.http11.Http11Protocol,但不幸的是这也没有帮助到我。 - John Little
2
为什么这个回答没有帮助到 OP,却获得了悬赏?我真的想知道,因为我也遇到了同样的问题。 - Be Kind To New Users
1
此答案解决了大多数“ERR_SSL_VERSION_OR_CIPHER_MISMATCH”错误。 - Matthew Peters
1
这个加密方式对我来说很有效,但对于从Windows转移到Linux的人来说很糟糕。当你复制粘贴server.xml时,会让你感到困惑并且不知道哪里出了问题。 - madhairsilence
显示剩余2条评论

3
最近我也遇到了同样的错误,当我尝试按照指南使用SSL保护Bitbucket Server with Tomcat时,我在这里找到了解决方案您需要将格式从pkcs12转换为java keystore
keytool -importkeystore \
        -deststorepass changeit -destkeypass changeit \
        -destkeystore /path/to/my/keystore.jks \
        -srckeystore our.p12 -srcstoretype PKCS12

在Tomcat中,只需设置:

<Connector ...
          keystoreFile="/path/to/my/keystore.jks" />

2
尝试将sslProtocol切换为"TLSv1,TLSv1.1,TLSv1.2"。 对于openssl / curl测试用例,您可能希望在其前面添加SSLv2Hello,因为一些较旧的库将希望在进行升级协商之前发送旧的hello。

嗨,谢谢您的想法 - 我尝试了这个但是出现了同样的错误。 - John Little

2
Ubuntu 14, Tomcat 7, Java 7.
请提供Tomcat和Java 7的确切版本号。
服务器的server.xml文件如下:
您没有提到使用哪种连接器实现,但是如果您从server.xml中删除了AprLifecycleListener,则意味着您正在使用“Http11Protocol”(也称为“BIO”)实现。很好。它应该在启动日志中可见。(如果您使用了“APR”实现,则配置将有所不同)。
curl -Iv https://www.ourserver.com/ourapp:8443
这是一个奇怪的URL。端口号应跟随服务器名称,https://www.ourserver.com:8443/ourapp。
尽管来自curl的消息“* Rebuilt URL to:https://www.ourserver.com:8443/”看起来知道如何处理这个问题。
error:14077410:SSL routines:SSL23_GET_SERVER_HELLO:sslv3 alert handshake failure。
由于发布的SSL漏洞(CVE-2014-3566 POODLE),Tomcat 7.0.57及以上默认禁用SSLv3协议。 SSL协议过滤禁用所有具有“SSL”名称的协议,包括SSLv2Hello。显然,此处curl尝试使用SSLv2Hello握手进行连接(其消息中的“SSL23”)。 您需要一个支持TLS协议(TLS 1.0、1.1或1.2)的客户端。
尝试将sslEnabledProtocols切换为“TLSv1、TLSv1.1、TLSv1.2”。 您可以在openssl / curl测试用例中将SSLv2Hello添加到头部,因为一些旧库将希望发送旧的hello,然后进行协商。这是一个很好的改进,但是需要更正:上面的值是sslEnabledProtocols属性(而不是sslProtocol)。
您可以尝试使用OpenSSL进行连接。
openssl s_client -connect hostname:8443

openssl s_client -connect hostname:8443 -tls1

OpenSSL文档:https://openssl.org/docs/apps/s_client.html

Tomcat 7配置参考:http://tomcat.apache.org/tomcat-7.0-doc/config/http.html#SSL_Support_-_BIO_and_NIO

这些链接提供了关于IT技术中的SSL支持和配置的相关信息。请查看链接以获取更多详细信息。

您IP地址为143.198.54.68,由于运营成本限制,当前对于免费用户的使用频率限制为每个IP每72小时10次对话,如需解除限制,请点击左下角设置图标按钮(手机用户先点击左上角菜单按钮)。 - John Little
很遗憾,我无法真正改变客户端 - 在Chrome、IE、curl和openssl中都会出现相同的错误。 - John Little

openssl s_client -connect 主机名:8443: 已连接(00000003) depth=3 C = US, O = "The Go Daddy Group, Inc.", OU = Go Daddy Class 2 Certification Authority verify error:num=19:self signed certificate in certificate chain verify return:0

证书链 0 s:/OU=Domain Control Validated/CN=*.respingaming.net i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
- John Little

openssl s_client -connect hostname:8443 在第二个服务器上设置相同的内容(至少应该是这样,但我尝试了很多变化)会出现以下情况:root@pansy:~# openssl s_client -connect localhost:8443 已连接(00000003) 139957150750368:error:14077410:SSL routines:SSL23_GET_SERVER_HELLO:sslv3 alert handshake failure:s23_clnt.c:770:

没有可用的对等证书

未发送客户端证书CA名称

SSL握手已读取7个字节并写入305个字节

新的,(无),密码是(无) 不支持安全重新协商 压缩:无 扩展:无

- John Little
尝试在openssl s_client命令中添加“-tls1”参数(我已更新上面的步骤)。7.0.52版本有些旧了。您需要查看我提到的FAQ条目以禁用SSLv3。 - Konstantin Kolinko

1

我曾遇到同样的问题,后来解决了。

请在您的密钥库中添加密码 - 这样就可以解决问题了!


1
需要创建.jks格式文件的证书。
密钥生成
1)在Java中输入密钥生成命令。
keytool -genkey -alias server -keyalg RSA -keysize 2048 -keystore your_domain_name.jks

2) 运行 CSR 命令

keytool -certreq -alias server -file csr.txt -keystore your_domain_name.jks

3)在Godaddy.com提交crs.txt文件

安装说明

1)转换您的证书文件。需要使用openssl(https://www.openssl.org/) 运行以下命令:xxx.pem来自证书文件(您的域名证书)

openssl crl2pkcs7 -nocrl -certfile xxx.pem -out your_file_name.p7b -certfile gd_bundle-g2-g1.crt

2)在Java中运行安装命令

keytool -import -trustcacerts -alias server -file your_file_name.p7b -keystore your_domain_name.jks

4) 打开 ..\Apache Software Foundation\Tomcat 7.0\conf 目录下的 server.xml 文件。 更新连接器设置。

<Connector 
       port="443"  
       scheme="https" 
       secure="true" 
       SSLEnabled="true" 
       clientAuth="false"
       sslProtocol="TLS" 
       keyAlias="server"  
       keystoreFile="/home/user_name/your_domain_name.jks"
       keystorePass="your_keystore_password"
 />

5) 欢迎。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接