java - 存在多个匹配证书时如何选择SSL客户端证书?

标签 java apache ssl ssl-certificate

这不是设计应该发生的事情,但出于安全考虑,我想知道如何将“正确的”证书发送到服务器,假设有多个证书符合由某个人签名的要求加州?

我正在使用一个简单的 SSL JAVA 示例客户端,连接到 Apache HTTPD。

我尝试使用 4 个证书进行测试,每次都删除所选的证书并记录下一个被选中的人。除了证书的“sha256”的字典顺序之外,我找不到合理的逻辑(即日期、别名等)。这对我来说似乎不太可能......

示例客户端做类似的事情

System.setProperty("javax.net.ssl.keyStore","device.p12");  
System.setProperty("javax.net.ssl.keyStorePassword","password");  
System.setProperty("javax.net.ssl.keyStoreType", "PKCS12");  
System.setProperty("javax.net.ssl.trustStore","truststore.jks");  
System.setProperty("javax.net.ssl.trustStorePassword","password");  
SSLSocketFactory factory = (SSLSocketFactory) SSLSocketFactory.getDefault();  
SSLSocket sslSock = (SSLSocket) factory.createSocket("87.69.60.100",443);  
BufferedWriter wr = new BufferedWriter(new OutputStreamWriter(sslSock.getOutputStream(), "UTF8"));  
wr.write("GET /lather HTTP/1.1\r\nhost: 87.69.60.100\r\n\r\n");  
wr.flush();  

并且Apache配置为

SSLCACertificateFile rootCA.crt  
SSLVerifyClient require  

我找不到相关文档来回答这个问题。我也想知道——Apache 是否有可能以某种方式转发多个证书链? (比如说一个行为不端的客户发送了一些奇怪的东西)。

谢谢!

最佳答案

需要客户端身份验证的服务器将发送可接受的证书类型列表,可能连同可接受的 CA 列表。默认情况下,您的 Java 客户端会应用以下算法:

  1. 对于服务器接受的每种证书类型(RSA、DSA、EC),在 keystore 中找到使用指定算法生成的任何公钥/私钥对
  2. 如果服务器发送了可接受的 CA 列表,则删除其证书链中不包含列表中任何 CA 的任何 key 对
  3. 如果至少还剩下一对 key ,则选择第一对对应的私钥;否则返回步骤 1 以获取下一个 key 类型。

RFC 5246 中未指定客户端证书选择算法,但 Java 的简单默认实现似乎是合理的,如果将来会发生变化,如 EJP 所指出的那样。特别是,“第一个”几乎是随机的 - 凭据当前存储在 Map 中,因此它将取决于条目集的迭代顺序。此外,KeyManager 实现是可插入的,OpenJDK 提供了一个“NewSun”实现,它通过传递安全属性 ssl.KeyManagerFactory.algorithm=NewSunX509 来激活。第二个还将考虑您的客户端证书的 keyUsage 和 extendedKeyUsage 属性,以及到期日期。

如果您需要保证从一系列可能性中发送的证书,并且您发现默认行为不适合您,您最好的选择是手动创建一个单项 keystore 并使用它来初始化一个 SSLContext,或者编写您自己的 X509KeyManager 实现以在 chooseClientAlias 中执行您想要的操作,如 this question 的答案中那样或 this question .

关于java - 存在多个匹配证书时如何选择SSL客户端证书?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23527426/

相关文章:

ruby - SSL 证书、Ruby、Mac OS X Yosemite 故障排除

java - 如何创建并运行新线程

php - laravel redirect::back() 重定向到 favicon

apache - 如果请求来自特定主机,则特定 URL 重定向到 http

apache - 托管服务器上的内部 apache 重写问题

php - URL 中的随机字符串对 "Man in the Middle Attack"有帮助吗?

java - 字段 component.x 不可见

java - 如何在JSP中创建全局 session ?

java - 打开网络浏览器并以虚拟用户身份控制它

azure - 在 Azure Web 应用程序上找不到证书