如何在Java中启用客户端TLS会话重用 [英] How to enable client TLS session reuse in Java
问题描述
我有一个Java客户端,可以为同一台服务器创建多个会话。 TLS协议具有缓存会话密钥的功能,从而避免了对每个连接进行昂贵的PKI处理。但我无法让它真正起作用。
I have a Java client that may create many sessions to the same server. The TLS protocol has a facility to cache session keys and thus avoid the expensive PKI processing for each connection. But I cannot get it to actually work.
openssl s_client -reconnect -state -prexit -connect localhost:1234
报告服务器已重用,TLSv1 / SSLv3,Cipher是ECDHE-RSA-AES256-SHA384,和相同的主密钥。
openssl s_client -reconnect -state -prexit -connect localhost:1234 Reports that the server has "Reused, TLSv1/SSLv3, Cipher is ECDHE-RSA-AES256-SHA384", and same master keys.
数据流是二进制的,而不是HTTP封装的。
The data stream is binary, not HTTP encapsulated.
我使用的代码是(约),如下所示。它可以工作,但没有会话重用。
The code that I use is (approx.) as follows. It works, but no session reuse.
initSSLContext(keyStore, "password", trustStore, "PKIX", "TLSv1");
While (true) {
connect();
byte[] encode1 = { 0x42, 0, 0, 0, 0, 0, 0, 0, 0, };
outs.write(encode1);
byte[] ttlbuf = new byte[10000];
int len = ins.read(ttlbuf, 0, ttlbuf.length);
StringBuilder sb = new StringBuilder();
socket.close();
}
private void initSSLContext(KeyStore keyStore, String keyStorePwd, KeyStore trustStore,
String sslTrustManagerAlg, String sslProtocol) throws Exception {
KeyManager[] keyManagers = null;
if ( keyStore != null && keyStorePwd != null ) {
KeyManagerFactory kmf =
KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
kmf.init(keyStore, keyStorePwd.toCharArray());
keyManagers = kmf.getKeyManagers();
}
TrustManager[] trustManagers = null;
if ( trustStore != null ) {
TrustManagerFactory tmf = TrustManagerFactory.getInstance(sslTrustManagerAlg);
tmf.init(trustStore);
trustManagers = tmf.getTrustManagers();
}
ctx = SSLContext.getInstance(sslProtocol);
ctx.init(keyManagers, trustManagers, null);
factory = ctx.getSocketFactory();
}
private void connect() throws IOException {
socket = (SSLSocket) factory.createSocket(host, port);
socket.setSoTimeout(30000);
// ensure first ClientHello is TLSv1 rather than SSLv2
socket.setEnabledProtocols(new String[] { "TLSv1" });
socket.setEnabledCipherSuites(DEFAULT_SSL_CIPHER_SUITES);
localHost = socket.getLocalAddress().getHostAddress();
localPort = socket.getLocalPort();
ins = socket.getInputStream();
outs = socket.getOutputStream();
}
推荐答案
问题是任何致命的警报会导致会话恢复。因此,阅读一个流的结尾会导致后续的重复使用。这里还有更多
The problem is that any fatal alert kills the session resumption. So reading past the end of one stream kills subsequent resuse. There is more here
这篇关于如何在Java中启用客户端TLS会话重用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!