Double the SSL input packet buffer size
[controller.git] / opendaylight / protocol_plugins / openflow / src / main / java / org / opendaylight / controller / protocol_plugin / openflow / core / internal / SecureMessageReadWriteService.java
index 43a64814d8498a1842ae9f4e2ce4ee75a08aca2f..d60bcab8b32fdf299d68505c348fe5b4fc5ec831 100644 (file)
@@ -19,13 +19,15 @@ import java.nio.channels.SocketChannel;
 import java.security.KeyStore;
 import java.security.SecureRandom;
 import java.util.List;
+
 import javax.net.ssl.KeyManagerFactory;
 import javax.net.ssl.SSLContext;
 import javax.net.ssl.SSLEngine;
 import javax.net.ssl.SSLEngineResult;
+import javax.net.ssl.SSLEngineResult.HandshakeStatus;
 import javax.net.ssl.SSLSession;
 import javax.net.ssl.TrustManagerFactory;
-import javax.net.ssl.SSLEngineResult.HandshakeStatus;
+
 import org.opendaylight.controller.protocol_plugin.openflow.core.IMessageReadWrite;
 import org.openflow.protocol.OFMessage;
 import org.openflow.protocol.factory.BasicFactory;
@@ -41,7 +43,6 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
             .getLogger(SecureMessageReadWriteService.class);
 
     private Selector selector;
-    private SelectionKey clientSelectionKey;
     private SocketChannel socket;
     private BasicFactory factory;
 
@@ -64,6 +65,7 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
             createSecureChannel(socket);
             createBuffers(sslEngine);
         } catch (Exception e) {
+            logger.warn("Failed to setup TLS connection {} {}", socket, e);
             stop();
             throw e;
         }
@@ -71,7 +73,7 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
 
     /**
      * Bring up secure channel using SSL Engine
-     * 
+     *
      * @param socket
      *            TCP socket channel
      * @throws Exception
@@ -88,35 +90,31 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
             keyStoreFile = keyStoreFile.trim();
         }
         if ((keyStoreFile == null) || keyStoreFile.isEmpty()) {
-            throw new FileNotFoundException(
-                    "controllerKeyStore not specified in ./configuration/config.ini");
+            throw new FileNotFoundException("TLS KeyStore file not found.");
         }
         if (keyStorePassword != null) {
             keyStorePassword = keyStorePassword.trim();
         }
         if ((keyStorePassword == null) || keyStorePassword.isEmpty()) {
-            throw new FileNotFoundException(
-                    "controllerKeyStorePassword not specified in ./configuration/config.ini");
+            throw new FileNotFoundException("TLS KeyStore Password not provided.");
         }
         if (trustStoreFile != null) {
             trustStoreFile = trustStoreFile.trim();
         }
         if ((trustStoreFile == null) || trustStoreFile.isEmpty()) {
-            throw new FileNotFoundException(
-                    "controllerTrustStore not specified in ./configuration/config.ini");
+            throw new FileNotFoundException("TLS TrustStore file not found");
         }
         if (trustStorePassword != null) {
             trustStorePassword = trustStorePassword.trim();
         }
         if ((trustStorePassword == null) || trustStorePassword.isEmpty()) {
-            throw new FileNotFoundException(
-                    "controllerTrustStorePassword not specified in ./configuration/config.ini");
+            throw new FileNotFoundException("TLS TrustStore Password not provided.");
         }
 
         KeyStore ks = KeyStore.getInstance("JKS");
         KeyStore ts = KeyStore.getInstance("JKS");
-        KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
-        TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509");
+        KeyManagerFactory kmf = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
+        TrustManagerFactory tmf = TrustManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
         kfd = new FileInputStream(keyStoreFile);
         tfd = new FileInputStream(trustStoreFile);
         ks.load(kfd, keyStorePassword.toCharArray());
@@ -132,18 +130,34 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
         sslEngine = sslContext.createSSLEngine();
         sslEngine.setUseClientMode(false);
         sslEngine.setNeedClientAuth(true);
+        sslEngine.setEnabledCipherSuites(new String[] {
+                "SSL_RSA_WITH_RC4_128_MD5",
+                "SSL_RSA_WITH_RC4_128_SHA",
+                "TLS_RSA_WITH_AES_128_CBC_SHA",
+                "TLS_DHE_RSA_WITH_AES_128_CBC_SHA",
+                "TLS_DHE_DSS_WITH_AES_128_CBC_SHA",
+                "SSL_RSA_WITH_3DES_EDE_CBC_SHA",
+                "SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA",
+                "SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA",
+                "SSL_RSA_WITH_DES_CBC_SHA",
+                "SSL_DHE_RSA_WITH_DES_CBC_SHA",
+                "SSL_DHE_DSS_WITH_DES_CBC_SHA",
+                "SSL_RSA_EXPORT_WITH_RC4_40_MD5",
+                "SSL_RSA_EXPORT_WITH_DES40_CBC_SHA",
+                "SSL_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA",
+                "SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA",
+                "TLS_EMPTY_RENEGOTIATION_INFO_SCSV"});
 
         // Do initial handshake
         doHandshake(socket, sslEngine);
 
-        this.clientSelectionKey = this.socket.register(this.selector,
-                SelectionKey.OP_READ);
+        this.socket.register(this.selector, SelectionKey.OP_READ);
     }
 
     /**
      * Sends the OF message out over the socket channel. The message is
      * encrypted by SSL Engine.
-     * 
+     *
      * @param msg
      *            OF message to be sent
      * @throws Exception
@@ -182,12 +196,10 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
 
             if (myAppData.hasRemaining()) {
                 myAppData.compact();
-                this.clientSelectionKey = this.socket.register(this.selector,
-                        SelectionKey.OP_WRITE, this);
+                this.socket.register(this.selector, SelectionKey.OP_WRITE, this);
             } else {
                 myAppData.clear();
-                this.clientSelectionKey = this.socket.register(this.selector,
-                        SelectionKey.OP_READ, this);
+                this.socket.register(this.selector, SelectionKey.OP_READ, this);
             }
 
             logger.trace("Message sent: {}", msg);
@@ -196,7 +208,7 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
 
     /**
      * Resumes sending the remaining messages in the outgoing buffer
-     * 
+     *
      * @throws Exception
      */
     @Override
@@ -221,12 +233,10 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
 
             if (myAppData.hasRemaining()) {
                 myAppData.compact();
-                this.clientSelectionKey = this.socket.register(this.selector,
-                        SelectionKey.OP_WRITE, this);
+                this.socket.register(this.selector, SelectionKey.OP_WRITE, this);
             } else {
                 myAppData.clear();
-                this.clientSelectionKey = this.socket.register(this.selector,
-                        SelectionKey.OP_READ, this);
+                this.socket.register(this.selector, SelectionKey.OP_READ, this);
             }
         }
     }
@@ -234,7 +244,7 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
     /**
      * Reads the incoming network data from the socket, decryptes them and then
      * retrieves the OF messages.
-     * 
+     *
      * @return list of OF messages
      * @throws Exception
      */
@@ -272,16 +282,20 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
                     peerNetData.position(), peerNetData.limit());
         }
 
-        peerAppData.flip();
-        msgs = factory.parseMessages(peerAppData);
-        if (peerAppData.hasRemaining()) {
-            peerAppData.compact();
-        } else {
+        try {
+            peerAppData.flip();
+            msgs = factory.parseMessages(peerAppData);
+            if (peerAppData.hasRemaining()) {
+                peerAppData.compact();
+            } else {
+                peerAppData.clear();
+            }
+        } catch (Exception e) {
             peerAppData.clear();
+            logger.debug("Caught exception: ", e);
         }
 
-        this.clientSelectionKey = this.socket.register(this.selector,
-                SelectionKey.OP_READ, this);
+        this.socket.register(this.selector, SelectionKey.OP_READ, this);
 
         return msgs;
     }
@@ -393,9 +407,9 @@ public class SecureMessageReadWriteService implements IMessageReadWrite {
         this.myAppData = ByteBuffer
                 .allocate(session.getApplicationBufferSize());
         this.peerAppData = ByteBuffer.allocate(session
-                .getApplicationBufferSize());
+                .getApplicationBufferSize() * 2);
         this.myNetData = ByteBuffer.allocate(session.getPacketBufferSize());
-        this.peerNetData = ByteBuffer.allocate(session.getPacketBufferSize());
+        this.peerNetData = ByteBuffer.allocate(session.getPacketBufferSize() * 2);
     }
 
     @Override