如何强制 java 服务器只接受 tls 1.2 并拒绝 tls 1.0 和 tls 1.1 连接

Posted

技术标签:

【中文标题】如何强制 java 服务器只接受 tls 1.2 并拒绝 tls 1.0 和 tls 1.1 连接【英文标题】:How to force java server to accept only tls 1.2 and reject tls 1.0 and tls 1.1 connections 【发布时间】:2015-12-04 15:31:24 【问题描述】:

我有一个在 Java 7 上运行的 HTTPS Web 服务。我需要进行更改,以便该服务只接受 TLS1.2 连接并拒绝 SSL3、TLS1.0 和 TLS1.1。

我添加了以下 Java 参数,以便 TLS1.2 为最高优先级。

-Dhttps.protocols=TLSv1.2

但它也接受来自 Java 客户端的 TLS1.0 连接。如果客户端也使用上述 Java 参数运行,则连接为 TLS1.2,但如果客户端在没有此参数的情况下运行,则连接为 TLS1.0。

我对@9​​87654324@ 文件夹中的java.security 文件进行了一些操作。

我目前有以下禁用的算法:

jdk.certpath.disabledAlgorithms= MD2, MD4, MD5, SHA224, DSA, EC keySize < 256, RSA keySize < 2048, SHA1 keysize < 224
jdk.tls.disabledAlgorithms=DSA, DHE, EC keySize < 256, RSA keySize < 2048, SHA1 keysize < 224

我正在使用 Java 7 update 79。我不倾向于拦截每个连接并检查 TLS 版本。

我的服务器证书是 2048 位使用 MD5 和 RSA 算法生成的。

如果禁用的算法列表使用 RSA 代替 RSA keySize SSLHandShakeError:

没有共同的密码套件。

我的测试程序正在从以下 URL 运行 HTTP 服务器: http://www.herongyang.com/JDK/HTTPS-HttpsEchoer-Better-HTTPS-Server.html

请帮助如何使 java 只接受 TLS1.2 连接。

【问题讨论】:

SSLContext.getInstance("TLSv1.2") 工作吗? @user5266804 不,它没有。 SSLContext.getInstance 方法基本上采用 SSLTLS 作为参数。我敢打赌,在幕后,Sun 提供商甚至不关心你传入的字符串:你总是得到 JSSE 提供的“TLS 引擎”。 sysprop htts.protocols 不起作用,因为它(和https.cipherSuites)只影响使用HttpsURLConnection传出 连接——不传入,也不直接使用@987654334 @ 或 SSLEngine。 @ChristopherSchultz:JCA 查找只接受(忽略大小写)由提供者预定义的字符串,对于 j7 JSSE 是 Default SSL SSLv3 TLS TLSv1 TLSv1.1 TLSv1.2 - 后两者在启用的协议方面有所不同最初但都使用相同的代码并且可以启用除disabledAlgorithms secprop 中的协议之外的任何已实现协议的子集 【参考方案1】:

我找到了解决方案。我设置了

jdk.tls.disabledAlgorithms= SSLv2Hello, SSLv3, TLSv1, TLSv1.1

在服务器上的文件jre/lib/security/java.security中。

设置后,服务器只接受TLS1.2连接,拒绝低安全协议版本。

【讨论】:

在哪里设置? 您需要在 /jre/lib/security 文件夹中找到的“java.security”文件中进行设置。 在 jdk/jre/lib/security 中更改此文件后是否需要重新编译我的应用程序? 此更改不需要重新编译,因为它不是代码更改。 我使用下面的属性 jdk.tls.disabledAlgorithms=EC, ECDHE, DHE, TLSv1.2, SSLv3, RSA keySize 【参考方案2】:

我也在“/java/jdk1.7.0_79/jre/lib/security”-java.security 文件中进行了相同的更改,但一些客户端仍然能够使用 SSL 协议调用我的服务。

----变化 jdk.tls.disabledAlgorithms=SSL,SSLv2,SSLv3, TLSv1, TLSv1.1,MD5, SSLv3, DSA, RSA keySize

【讨论】:

"但是一些客户端仍然可以使用 SSL 协议调用我的服务。"我喜欢这个。【参考方案3】:

只是一个小评论;

在您所说的问题中,您使用 MD5 生成了 2048 大小的证书。但是在证书路径 alg 中,您禁用了 MD5,因此这通常不起作用。其次,现代浏览器(如 Internet Explorer 10/Edge)禁止使用 MD5 哈希生成的服务器证书。

我想建议您至少使用 SHA256 或

【讨论】:

【参考方案4】:

2021 年 11 月更新

从 JDK 的 11.0.11 版开始,您无需执行任何操作,因为默认情况下禁用 TLS 1.0 和 TLS 1.1。

该修复程序也被向后移植到 JDK 7u301 和 8u291。

详情:JDK-8202343 : Disable TLS 1.0 and 1.1

您仍然可以通过更改 java.security 来显式启用 TLS 1.0/1.1,如接受的答案中所述。

【讨论】:

虽然在 j9 中 java.securityconf/security 而不是 jre/lib/security

以上是关于如何强制 java 服务器只接受 tls 1.2 并拒绝 tls 1.0 和 tls 1.1 连接的主要内容,如果未能解决你的问题,请参考以下文章

强制 HttpWebRequest 和 ClientWebSocket 使用 TLS 1.2

Apache:允许一台主机使用 TLS 1.0,同时强制所有其他主机使用 1.2?

更新 .NET Web 服务以使用 TLS 1.2

在握手期间检索公共服务器证书密钥

带有 TLS 1.3 的 Java 11 SSLHandshakeException:如何恢复到 TLS 1.2?

如何在 Java 7 中启用 TLS 1.2