From steffen.mueller4 at kit.edu Tue May 5 10:53:32 2015 From: steffen.mueller4 at kit.edu (Mueller, Steffen (AIFB)) Date: Tue, 5 May 2015 12:53:32 +0200 Subject: SSLSocket renegotiation issue (JSSE) Message-ID: <0138BCE7F443E641ACB114A667C0AEA8A40E4F3B1C@KIT-MSX-05.kit.edu> Hi, I did not find anything regarding my issue in the archive or in the Web. I have a question regarding the renegotiation of SSLSockets (JSSE). Preconditions: - We installed the OpenJDK 8 update 40 (+ JCE unlimited strength policies) to run a distributed system that replicates its state over SSL-based socket connections - It is a peer-to-peer system. So, there is a set of socket connections between the various nodes of the distributed system - We only allow TLS 1.2 connections, so we get the SSLContext within the application by invoking: SSLContext ctx = SSLContext.getInstance("TLSv1.2"); KeyManager[] kms = KeyManagerFactory.getInstance("SunX509").getKeyManagers(); TrustManager[] tms = TrustManagerFactory.getInstance("SunX509").getTrustManagers(); ctx.init(kms, tms, null); - Furthermore, we enable a list of cipher suites for socket, i.e., we invoke socket.setEnabledCipherSuites(new String[]{"TLS_RSA_WITH_AES_128_CBC_SHA","TLS_RSA_WITH_AES_256_CBC_SHA","TLS_DHE_RSA_WITH_AES_128_CBC_SHA",...}); Goal: After the connection is established and used by the nodes to communicate their states within the cluster, we need to renegotiate the SSL connection after a while. Additionally, we would like to change the negotiated cipher suite. For example, if the negotiated cipher suite is "TLS_RSA_WITH_AES_256_CBC_SHA" we would like to change it to "TLS_RSA_WITH_AES_128_CBC_SHA". So, we invoke: socket.setEnabledCipherSuites(new String[]{"TLS_RSA_WITH_AES_128_CBC_SHA"}); if(!resume) socket.getSession().invalidate(); socket.startHandshake(); Problem: However, the cipher suite does not change. Even the renegotiation is not done anyway (neither resume = true nor resume = false). A previously registered HandshakeCompletedListener is not invoked anyway. The debug log does not give us any hint what could be wrong. We tested the renegotiation procedure on an adjusted JDK-Test case (RejectClientRenego)... It works. However, in the test case (RejectClientRenego) the application layer does not send application data to the SSLSocket while the renegotiation is being done... So, I have the questions: Are we doing something wrong? Is it possible/allowed to renegotiate the cipher suite for a connected socket which is used continuously by the application layer? Do you have any other hints what we can try to implement the desired behavior? ... Thanks Steffen Mueller From rob.mckenna at oracle.com Tue May 5 11:33:02 2015 From: rob.mckenna at oracle.com (Rob McKenna) Date: Tue, 05 May 2015 12:33:02 +0100 Subject: SSLSocket renegotiation issue (JSSE) In-Reply-To: <0138BCE7F443E641ACB114A667C0AEA8A40E4F3B1C@KIT-MSX-05.kit.edu> References: <0138BCE7F443E641ACB114A667C0AEA8A40E4F3B1C@KIT-MSX-05.kit.edu> Message-ID: <5548AA6E.3050104@oracle.com> security-dev at openjdk.java.net is probably a more appropriate alias. -Rob On 05/05/15 11:53, Mueller, Steffen (AIFB) wrote: > Hi, > > > > > > I did not find anything regarding my issue in the archive or in the Web. I have a question regarding the renegotiation of SSLSockets (JSSE). > > Preconditions: > > - We installed the OpenJDK 8 update 40 (+ JCE unlimited strength policies) to run a distributed system that replicates its state over SSL-based socket connections > > - It is a peer-to-peer system. So, there is a set of socket connections between the various nodes of the distributed system > > - We only allow TLS 1.2 connections, so we get the SSLContext within the application by invoking: > > SSLContext ctx = SSLContext.getInstance("TLSv1.2"); > KeyManager[] kms = KeyManagerFactory.getInstance("SunX509").getKeyManagers(); > TrustManager[] tms = TrustManagerFactory.getInstance("SunX509").getTrustManagers(); > ctx.init(kms, tms, null); > > > > - Furthermore, we enable a list of cipher suites for socket, i.e., we invoke socket.setEnabledCipherSuites(new String[]{"TLS_RSA_WITH_AES_128_CBC_SHA","TLS_RSA_WITH_AES_256_CBC_SHA","TLS_DHE_RSA_WITH_AES_128_CBC_SHA",...}); > > > > Goal: > > After the connection is established and used by the nodes to communicate their states within the cluster, we need to renegotiate the SSL connection after a while. Additionally, we would like to change the negotiated cipher suite. For example, if the negotiated cipher suite is "TLS_RSA_WITH_AES_256_CBC_SHA" we would like to change it to "TLS_RSA_WITH_AES_128_CBC_SHA". So, we invoke: > > > socket.setEnabledCipherSuites(new String[]{"TLS_RSA_WITH_AES_128_CBC_SHA"}); > > if(!resume) > > socket.getSession().invalidate(); > socket.startHandshake(); > > > > Problem: > > However, the cipher suite does not change. Even the renegotiation is not done anyway (neither resume = true nor resume = false). A previously registered HandshakeCompletedListener is not invoked anyway. The debug log does not give us any hint what could be wrong. > > We tested the renegotiation procedure on an adjusted JDK-Test case (RejectClientRenego)... It works. However, in the test case (RejectClientRenego) the application layer does not send application data to the SSLSocket while the renegotiation is being done... > > > > So, I have the questions: Are we doing something wrong? Is it possible/allowed to renegotiate the cipher suite for a connected socket which is used continuously by the application layer? Do you have any other hints what we can try to implement the desired behavior? ... > > > > > > Thanks > > Steffen Mueller >