You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by kw...@apache.org on 2012/12/12 18:38:44 UTC

svn commit: r1420861 - in /qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src: main/java/org/apache/qpid/proton/engine/ main/java/org/apache/qpid/proton/engine/impl/ main/java/org/apache/qpid/proton/engine/impl/ssl/ test/java/org/apache/qpid/p...

Author: kwall
Date: Wed Dec 12 17:38:41 2012
New Revision: 1420861

URL: http://svn.apache.org/viewvc?rev=1420861&view=rev
Log:
PROTON-136: Java SSL session resumption. Added SslDomain and SslPeerDetails.

Applied patch from Philip Harvey<ph...@philharveyonline.com>.

Added:
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslDomain.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslPeerDetails.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslDomainImpl.java
Modified:
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Ssl.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Transport.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/TransportImpl.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapper.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslImpl.java
    qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapperTest.java

Modified: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Ssl.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Ssl.java?rev=1420861&r1=1420860&r2=1420861&view=diff
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Ssl.java (original)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Ssl.java Wed Dec 12 17:38:41 2012
@@ -20,6 +20,9 @@ package org.apache.qpid.proton.engine;
  *
  */
 
+/**
+ * PHTODO summarise use, also deprecate methods now on SslDomain
+ */
 public interface Ssl
 {
     public enum Mode
@@ -28,7 +31,6 @@ public interface Ssl
         SERVER     /** Local connection endpoint is an SSL server */
     }
 
-
     /** Initialize the pn_ssl_t object.
      *
      * An SSL object be either an SSL server or an SSL client.  It cannot be both. Those
@@ -53,10 +55,10 @@ public interface Ssl
      * sign the certificate
      * @param password the password used to sign the key, else NULL if key is not
      * protected.
+     *
+     * @deprecated in favour of {@link SslDomain#setCredentials(String, String, String)}
      */
-     void setCredentials( String certificate_file,
-                         String private_key_file,
-                         String password);
+     void setCredentials(String certificate_file, String private_key_file, String password);
 
      String getPrivateKeyFile(); // TODO
      String getPrivateKeyPassword();
@@ -70,8 +72,9 @@ public interface Ssl
      * trusted CAs that will be used to verify the signature of the remote's certificate.
      *
      * @param certificate_db database of trusted CAs, used to authenticate the peer.
+     *
+     * @deprecated in favour of {@link SslDomain#setTrustedCaDb(String)}
      */
-
     void setTrustedCaDb(String certificate_db);
 
     String getTrustedCaDb();
@@ -81,7 +84,6 @@ public interface Ssl
      * This configures the server to "sniff" the incoming client data stream, and dynamically
      * determine whether SSL/TLS is being used.  This option is disabled by default: only
      * clients using SSL/TLS are accepted.
-     *
      */
     void allowUnsecuredClient(boolean allowUnsecured);
 
@@ -140,9 +142,4 @@ public interface Ssl
      */
     String getProtocolName();
 
-
-
-
-
-
 }

Added: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslDomain.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslDomain.java?rev=1420861&view=auto
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslDomain.java (added)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslDomain.java Wed Dec 12 17:38:41 2012
@@ -0,0 +1,89 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.qpid.proton.engine;
+
+import org.apache.qpid.proton.engine.Ssl.Mode;
+import org.apache.qpid.proton.engine.Ssl.VerifyMode;
+import org.apache.qpid.proton.engine.impl.ssl.SslEngineFacade;
+
+/**
+ * PHTODO
+ */
+public interface SslDomain
+{
+    Mode getMode();
+
+    /**
+     * Set the certificate that identifies the local node to the remote.
+     *
+     * This certificate establishes the identity for the local node. It will be sent to the
+     * remote if the remote needs to verify the identity of this node. This may be used for
+     * both SSL servers and SSL clients (if client authentication is required by the server).
+     *
+     * @param certificate_file path to file/database containing the identifying
+     * certificate.
+     * @param private_key_file path to file/database containing the private key used to
+     * sign the certificate
+     * @param password the password used to sign the key, else NULL if key is not
+     * protected.
+     */
+    void setCredentials(String certificate_file, String private_key_file, String password);
+
+    String getPrivateKeyFile(); // TODO
+
+    String getPrivateKeyPassword();
+
+    String getCertificateFile();
+
+    /**
+     * Configure the set of trusted CA certificates used by this node to verify peers.
+     *
+     * If the local SSL client/server needs to verify the identity of the remote, it must
+     * validate the signature of the remote's certificate. This function sets the database of
+     * trusted CAs that will be used to verify the signature of the remote's certificate.
+     *
+     * @param certificate_db database of trusted CAs, used to authenticate the peer.
+     */
+    void setTrustedCaDb(String certificate_db);
+
+    String getTrustedCaDb();
+
+    /**
+     * Configure the level of verification used on the peer certificate.
+     *
+     * This method controls how the peer's certificate is validated, if at all. By default,
+     * neither servers nor clients attempt to verify their peers (PN_SSL_ANONYMOUS_PEER).
+     * Once certificates and trusted CAs are configured, peer verification can be enabled.
+     *
+     * In order to verify a peer, a trusted CA must be configured. See
+     * #setTrustedCaDb().
+     *
+     * @note Servers must provide their own certificate when verifying a peer. See
+     * #setCredentials().
+     *
+     * @param mode the level of validation to apply to the peer
+     *
+     * PHTODO rename to setDefaultPeerAuthentication?
+     */
+    void setPeerAuthentication(VerifyMode mode);
+
+    VerifyMode getPeerAuthentication();
+
+    SslEngineFacade getSslEngineFacade(SslPeerDetails sslPeerDetails);
+}

Added: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslPeerDetails.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslPeerDetails.java?rev=1420861&view=auto
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslPeerDetails.java (added)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/SslPeerDetails.java Wed Dec 12 17:38:41 2012
@@ -0,0 +1,61 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.qpid.proton.engine;
+
+/**
+ * The details of the remote peer involved in an SSL session.
+ *
+ * Used when creating an SSL session to hint that the underlying SSL implementation
+ * should attempt to resume a previous session if one exists for the same peer details,
+ * e.g. using session identifiers (http://tools.ietf.org/html/rfc5246) or session tickets
+ * (http://tools.ietf.org/html/rfc5077).
+ *
+ * PHTODO extract interface
+ */
+public class SslPeerDetails
+{
+    private String _hostname;
+    private int _port;
+
+    public SslPeerDetails(String hostname, int port)
+    {
+        _hostname = hostname;
+        _port = port;
+    }
+
+    public String getHostname()
+    {
+        return _hostname;
+    }
+
+    public void setHostname(String hostname)
+    {
+        _hostname = hostname;
+    }
+
+    public int getPort()
+    {
+        return _port;
+    }
+
+    public void setPort(int port)
+    {
+        _port = port;
+    }
+}

Modified: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Transport.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Transport.java?rev=1420861&r1=1420860&r2=1420861&view=diff
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Transport.java (original)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/Transport.java Wed Dec 12 17:38:41 2012
@@ -59,6 +59,12 @@ public interface Transport extends Endpo
 
     Sasl sasl();
 
+    /** PHTODO */
+    Ssl ssl(SslDomain sslDomain, SslPeerDetails sslPeerDetails);
     Ssl ssl();
 
+    /**
+     * As per {@link #ssl(SslDomain, SslPeerDetails)} but no attempt is made to resume a previous SSL session.
+     */
+    Ssl ssl(SslDomain sslDomain);
 }

Modified: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/TransportImpl.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/TransportImpl.java?rev=1420861&r1=1420860&r2=1420861&view=diff
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/TransportImpl.java (original)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/TransportImpl.java Wed Dec 12 17:38:41 2012
@@ -29,6 +29,8 @@ import org.apache.qpid.proton.engine.End
 import org.apache.qpid.proton.engine.EndpointState;
 import org.apache.qpid.proton.engine.Sasl;
 import org.apache.qpid.proton.engine.Ssl;
+import org.apache.qpid.proton.engine.SslDomain;
+import org.apache.qpid.proton.engine.SslPeerDetails;
 import org.apache.qpid.proton.engine.Transport;
 import org.apache.qpid.proton.engine.TransportException;
 import org.apache.qpid.proton.engine.impl.ssl.SslImpl;
@@ -233,12 +235,26 @@ public class TransportImpl extends Endpo
 
     }
 
+    /**
+     * PHTODO remove?
+     */
     @Override
     public Ssl ssl()
     {
+        return ssl(null, null);
+    }
+
+    /**
+     * PHTODO
+     * @param sslDomain may be null
+     * @param sslPeerDetails may be null
+     */
+    @Override
+    public Ssl ssl(SslDomain sslDomain, SslPeerDetails sslPeerDetails)
+    {
         if (_ssl == null)
         {
-            _ssl = new SslImpl();
+            _ssl = new SslImpl(sslDomain, sslPeerDetails);
             TransportWrapper transportWrapper = _ssl.wrap(_inputProcessor, _outputProcessor);
             _inputProcessor = transportWrapper;
             _outputProcessor = transportWrapper;
@@ -246,6 +262,12 @@ public class TransportImpl extends Endpo
         return _ssl;
     }
 
+    @Override
+    public Ssl ssl(SslDomain sslDomain)
+    {
+        return ssl(sslDomain, null);
+    }
+
     private void clearTransportWorkList()
     {
         DeliveryImpl delivery = _connectionEndpoint.getTransportWorkHead();

Modified: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapper.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapper.java?rev=1420861&r1=1420860&r2=1420861&view=diff
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapper.java (original)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapper.java Wed Dec 12 17:38:41 2012
@@ -55,7 +55,6 @@ public class SimpleSslTransportWrapper i
 
     private final TransportInput _underlyingInput;
     private final TransportOutput _underlyingOutput;
-    private final Ssl _sslParams;
 
     private SslEngineFacade _sslEngine;
 
@@ -77,22 +76,13 @@ public class SimpleSslTransportWrapper i
     /** could change during the lifetime of the ssl connection owing to renegotiation. */
     private String _protocolName;
 
-    private final SslEngineFacadeFactory _sslEngineFacadeFactory;
+    private Ssl.Mode _mode; // PHTODO
 
-    public SimpleSslTransportWrapper(Ssl sslConfiguration, TransportInput underlyingInput, TransportOutput underlyingOutput)
+    SimpleSslTransportWrapper(SslEngineFacade sslEngine, TransportInput underlyingInput, TransportOutput underlyingOutput)
     {
-        this(sslConfiguration, underlyingInput, underlyingOutput, new SslEngineFacadeFactory());
-    }
-
-    SimpleSslTransportWrapper(Ssl sslConfiguration,
-            TransportInput underlyingInput, TransportOutput underlyingOutput,
-            SslEngineFacadeFactory sslEngineFacadeFactory)
-    {
-        _sslParams = sslConfiguration;
         _underlyingInput = underlyingInput;
         _underlyingOutput = underlyingOutput;
-        _sslEngineFacadeFactory = sslEngineFacadeFactory;
-        _sslEngine = _sslEngineFacadeFactory.createSslEngineFacade(sslConfiguration);
+        _sslEngine = sslEngine;
         createByteHolders();
     }
 
@@ -136,7 +126,7 @@ public class SimpleSslTransportWrapper i
 
                 if(_logger.isLoggable(Level.FINEST))
                 {
-                    _logger.log(Level.FINEST, _sslParams.getMode() + " input " + resultToString(result));
+                    _logger.log(Level.FINEST, _mode + " input " + resultToString(result));
                 }
 
                 Status sslResultStatus = result.getStatus();
@@ -270,7 +260,7 @@ public class SimpleSslTransportWrapper i
         }
         catch(SSLException e)
         {
-            throw new TransportException("Mode " + _sslParams.getMode(), e);
+            throw new TransportException("Mode " + _mode, e);
         }
     }
 

Added: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslDomainImpl.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslDomainImpl.java?rev=1420861&view=auto
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslDomainImpl.java (added)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslDomainImpl.java Wed Dec 12 17:38:41 2012
@@ -0,0 +1,104 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.qpid.proton.engine.impl.ssl;
+
+import org.apache.qpid.proton.engine.Ssl.Mode;
+import org.apache.qpid.proton.engine.Ssl.VerifyMode;
+import org.apache.qpid.proton.engine.SslDomain;
+import org.apache.qpid.proton.engine.SslPeerDetails;
+
+public class SslDomainImpl implements SslDomain
+{
+    private Mode _mode;
+    private VerifyMode _verifyMode = VerifyMode.ANONYMOUS_PEER;
+    private String _certificateFile;
+    private String _privateKeyFile;
+    private String _privateKeyPassword;
+    private String _trustedCaDb;
+
+    private final SslEngineFacadeFactory _sslEngineFacadeFactory = new SslEngineFacadeFactory();
+
+    public void setMode(Mode mode)
+    {
+        _mode = mode;
+    }
+
+    @Override
+    public void setCredentials(String certificateFile, String privateKeyFile, String privateKeyPassword)
+    {
+        _certificateFile = certificateFile;
+        _privateKeyFile = privateKeyFile;
+        _privateKeyPassword = privateKeyPassword;
+    }
+
+    @Override
+    public void setTrustedCaDb(String certificateDb)
+    {
+        _trustedCaDb = certificateDb;
+    }
+
+    @Override
+    public String getTrustedCaDb()
+    {
+        return _trustedCaDb;
+    }
+
+    @Override
+    public void setPeerAuthentication(VerifyMode verifyMode)
+    {
+        _verifyMode = verifyMode;
+    }
+
+    @Override
+    public VerifyMode getPeerAuthentication()
+    {
+        return _verifyMode;
+    }
+
+    @Override
+    public Mode getMode()
+    {
+        return _mode;
+    }
+
+    @Override
+    public String getPrivateKeyFile()
+    {
+        return _privateKeyFile;
+    }
+
+    @Override
+    public String getPrivateKeyPassword()
+    {
+        return _privateKeyPassword;
+    }
+
+    @Override
+    public String getCertificateFile()
+    {
+        return _certificateFile;
+    }
+
+    @Override
+    public SslEngineFacade getSslEngineFacade(SslPeerDetails peerDetails)
+    {
+        return _sslEngineFacadeFactory.createSslEngineFacade(this, peerDetails);
+    }
+
+}

Modified: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java?rev=1420861&r1=1420860&r2=1420861&view=diff
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java (original)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java Wed Dec 12 17:38:41 2012
@@ -46,9 +46,10 @@ import javax.net.ssl.TrustManager;
 import javax.net.ssl.TrustManagerFactory;
 import javax.net.ssl.X509TrustManager;
 
-import org.apache.qpid.proton.engine.Ssl;
 import org.apache.qpid.proton.engine.Ssl.Mode;
 import org.apache.qpid.proton.engine.Ssl.VerifyMode;
+import org.apache.qpid.proton.engine.SslDomain;
+import org.apache.qpid.proton.engine.SslPeerDetails;
 import org.bouncycastle.jce.provider.BouncyCastleProvider;
 import org.bouncycastle.openssl.PEMException;
 import org.bouncycastle.openssl.PEMReader;
@@ -81,25 +82,28 @@ public class SslEngineFacadeFactory
             "SSL_DH_anon_WITH_DES_CBC_SHA",
             "SSL_DH_anon_EXPORT_WITH_DES40_CBC_SHA");
 
-    public SslEngineFacade createSslEngineFacade(Ssl sslConfiguration)
+    /** lazily initialized */
+    private SSLContext _sslContext;
+
+    public SslEngineFacade createSslEngineFacade(SslDomain domain, SslPeerDetails peerDetails)
     {
-        SSLEngine engine = createSslEngine(sslConfiguration);
+        SSLEngine engine = createAndInitialiseSslEngine(domain, peerDetails);
         return new DefaultSslEngineFacade(engine);
     }
 
-    private SSLEngine createSslEngine(Ssl sslConfiguration)
+    private SSLEngine createAndInitialiseSslEngine(SslDomain domain, SslPeerDetails peerDetails)
     {
-        SSLEngine sslEngine;
 
-        SSLContext sslContext = createSslContext(sslConfiguration);
-        sslEngine = sslContext.createSSLEngine();
-        if (sslConfiguration.getPeerAuthentication() == VerifyMode.ANONYMOUS_PEER)
+        SSLContext sslContext = getOrCreateSslContext(domain);
+        SSLEngine sslEngine = createSslEngine(sslContext, peerDetails);
+
+        if (domain.getPeerAuthentication() == VerifyMode.ANONYMOUS_PEER)
         {
             addAnonymousCipherSuites(sslEngine);
         }
         else
         {
-            if (sslConfiguration.getMode() == Mode.SERVER)
+            if (domain.getMode() == Mode.SERVER)
             {
                 sslEngine.setNeedClientAuth(true);
             }
@@ -107,87 +111,111 @@ public class SslEngineFacadeFactory
 
         if(_logger.isLoggable(Level.FINE))
         {
-            _logger.log(Level.FINE, sslConfiguration.getMode() + " Enabled cipher suites " + Arrays.asList(sslEngine.getEnabledCipherSuites()));
+            _logger.log(Level.FINE, domain.getMode() + " Enabled cipher suites " + Arrays.asList(sslEngine.getEnabledCipherSuites()));
         }
 
-        boolean useClientMode = sslConfiguration.getMode() == Mode.CLIENT ? true : false;
+        boolean useClientMode = domain.getMode() == Mode.CLIENT ? true : false;
         sslEngine.setUseClientMode(useClientMode);
 
         return sslEngine;
     }
 
-    private SSLContext createSslContext(Ssl sslConfiguration)
+    /**
+     * @param sslPeerDetails is allowed to be null. A non-null value is used to hint that SSL resumption
+     * should be attempted
+     */
+    private SSLEngine createSslEngine(SSLContext sslContext, SslPeerDetails sslPeerDetails)
     {
-        final char[] dummyPassword = "unused-passphrase".toCharArray(); // Dummy password required by KeyStore and KeyManagerFactory, but never referred to again
+        final SSLEngine sslEngine;
+        if(sslPeerDetails == null)
+        {
+            sslEngine = sslContext.createSSLEngine();
+        }
+        else
+        {
+            sslEngine = sslContext.createSSLEngine(sslPeerDetails.getHostname(), sslPeerDetails.getPort());
+        }
+        return sslEngine;
+    }
 
-        try
+    private SSLContext getOrCreateSslContext(SslDomain sslDomain)
+    {
+        if(_sslContext == null)
         {
-            SSLContext sslContext = SSLContext.getInstance(TLS_PROTOCOL);
-            KeyStore ksKeys = createKeyStoreFrom(sslConfiguration, dummyPassword);
+            // lazily initialize _sslContext
 
-            KeyManagerFactory kmf = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
-            kmf.init(ksKeys, dummyPassword);
+            final char[] dummyPassword = "unused-passphrase".toCharArray(); // Dummy password required by KeyStore and KeyManagerFactory, but never referred to again
+
+            try
+            {
+                SSLContext sslContext = SSLContext.getInstance(TLS_PROTOCOL);
+                KeyStore ksKeys = createKeyStoreFrom(sslDomain, dummyPassword);
+
+                KeyManagerFactory kmf = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
+                kmf.init(ksKeys, dummyPassword);
+
+                final TrustManager[] trustManagers;
+                if (sslDomain.getTrustedCaDb() == null && sslDomain.getPeerAuthentication() == VerifyMode.ANONYMOUS_PEER)
+                {
+                    trustManagers = new TrustManager[] { new AlwaysTrustingTrustManager() };
+                }
+                else
+                {
+                    TrustManagerFactory tmf = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
+                    tmf.init(ksKeys);
+                    trustManagers = tmf.getTrustManagers();
+                }
 
-            final TrustManager[] trustManagers;
-            if (sslConfiguration.getTrustedCaDb() == null && sslConfiguration.getPeerAuthentication() == VerifyMode.ANONYMOUS_PEER)
+                sslContext.init(kmf.getKeyManagers(), trustManagers, null);
+                _sslContext = sslContext;
+            }
+            catch (NoSuchAlgorithmException e)
             {
-                trustManagers = new TrustManager[] { new AlwaysTrustingTrustManager() };
+                throw new IllegalStateException("Unexpected exception creating SSLContext", e);
             }
-            else
+            catch (KeyStoreException e)
             {
-                TrustManagerFactory tmf = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
-                tmf.init(ksKeys);
-                trustManagers = tmf.getTrustManagers();
+                throw new IllegalStateException("Unexpected exception creating SSLContext", e);
+            }
+            catch (UnrecoverableKeyException e)
+            {
+                throw new IllegalStateException("Unexpected exception creating SSLContext", e);
+            }
+            catch (KeyManagementException e)
+            {
+                throw new IllegalStateException("Unexpected exception creating SSLContext", e);
             }
-
-            sslContext.init(kmf.getKeyManagers(), trustManagers, null);
-            return sslContext;
-        }
-        catch (NoSuchAlgorithmException e)
-        {
-            throw new IllegalStateException("Unexpected exception creating SSLContext", e);
-        }
-        catch (KeyStoreException e)
-        {
-            throw new IllegalStateException("Unexpected exception creating SSLContext", e);
-        }
-        catch (UnrecoverableKeyException e)
-        {
-            throw new IllegalStateException("Unexpected exception creating SSLContext", e);
-        }
-        catch (KeyManagementException e)
-        {
-            throw new IllegalStateException("Unexpected exception creating SSLContext", e);
         }
+        return _sslContext;
     }
 
-    private KeyStore createKeyStoreFrom(Ssl sslConfiguration, char[] dummyPassword)
+    private KeyStore createKeyStoreFrom(SslDomain sslDomain, char[] dummyPassword)
     {
         try
         {
             KeyStore keystore = KeyStore.getInstance(KeyStore.getDefaultType());
             keystore.load(null, null);
 
-            if (sslConfiguration.getTrustedCaDb() != null)
+            if (sslDomain.getTrustedCaDb() != null)
             {
                 String caCertAlias = "cacert";
 
                 if(_logger.isLoggable(Level.FINE))
                 {
-                    _logger.log(Level.FINE, "_sslParams.getTrustedCaDb() : " + sslConfiguration.getTrustedCaDb());
+                    _logger.log(Level.FINE, "_sslParams.getTrustedCaDb() : " + sslDomain.getTrustedCaDb());
                 }
-                Certificate trustedCaCert = (Certificate) readPemObject(sslConfiguration.getTrustedCaDb());
+                Certificate trustedCaCert = (Certificate) readPemObject(sslDomain.getTrustedCaDb());
                 keystore.setCertificateEntry(caCertAlias, trustedCaCert);
             }
 
-            if (sslConfiguration.getCertificateFile() != null
-                    && sslConfiguration.getPrivateKeyFile() != null)
+            if (sslDomain.getCertificateFile() != null
+                    && sslDomain.getPrivateKeyFile() != null)
             {
                 String clientPrivateKeyAlias = "clientPrivateKey";
-                Certificate clientCertificate = (Certificate) readPemObject(sslConfiguration.getCertificateFile());
+                Certificate clientCertificate = (Certificate) readPemObject(sslDomain.getCertificateFile());
                 Key clientPrivateKey = (Key) readPemObject(
-                        sslConfiguration.getPrivateKeyFile(),
-                        sslConfiguration.getPrivateKeyPassword());
+                        sslDomain.getPrivateKeyFile(),
+                        sslDomain.getPrivateKeyPassword());
 
                 keystore.setKeyEntry(clientPrivateKeyAlias, clientPrivateKey,
                         dummyPassword, new Certificate[] { clientCertificate });
@@ -314,4 +342,5 @@ public class SslEngineFacadeFactory
             // Do not check certificate
         }
     }
+
 }

Modified: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslImpl.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslImpl.java?rev=1420861&r1=1420860&r2=1420861&view=diff
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslImpl.java (original)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslImpl.java Wed Dec 12 17:38:41 2012
@@ -21,6 +21,8 @@
 package org.apache.qpid.proton.engine.impl.ssl;
 
 import org.apache.qpid.proton.engine.Ssl;
+import org.apache.qpid.proton.engine.SslDomain;
+import org.apache.qpid.proton.engine.SslPeerDetails;
 import org.apache.qpid.proton.engine.impl.TransportInput;
 import org.apache.qpid.proton.engine.impl.TransportOutput;
 import org.apache.qpid.proton.engine.impl.TransportWrapper;
@@ -43,6 +45,16 @@ public class SslImpl implements Ssl
 
     private SslTransportWrapper _unsecureClientAwareTransportWrapper;
 
+    private final SslDomain _domain;
+
+    private final SslPeerDetails _peerDetails;
+
+    public SslImpl(SslDomain domain, SslPeerDetails peerDetails)
+    {
+        _domain = domain;
+        _peerDetails = peerDetails;
+    }
+
     @Override
     public void init(Mode mode)
     {
@@ -206,7 +218,7 @@ public class SslImpl implements Ssl
         {
             if (_transportWrapper == null)
             {
-                SslTransportWrapper sslTransportWrapper = new SimpleSslTransportWrapper(SslImpl.this, _inputProcessor, _outputProcessor);
+                SslTransportWrapper sslTransportWrapper = new SimpleSslTransportWrapper(_domain.getSslEngineFacade(_peerDetails), _inputProcessor, _outputProcessor);
                 if (_allowUnsecuredClient)
                 {
                     TransportWrapper plainTransportWrapper = new PlainTransportWrapper(_outputProcessor, _inputProcessor);

Modified: qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapperTest.java
URL: http://svn.apache.org/viewvc/qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapperTest.java?rev=1420861&r1=1420860&r2=1420861&view=diff
==============================================================================
--- qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapperTest.java (original)
+++ qpid/proton/branches/kgiusti-proton-136/proton-j/proton/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SimpleSslTransportWrapperTest.java Wed Dec 12 17:38:41 2012
@@ -24,12 +24,7 @@ import static org.apache.qpid.proton.eng
 import static org.apache.qpid.proton.engine.impl.ssl.ByteTestHelper.createFilledBuffer;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertTrue;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
 
-import org.apache.qpid.proton.engine.Ssl;
-import org.apache.qpid.proton.engine.impl.ssl.SimpleSslTransportWrapper;
-import org.apache.qpid.proton.engine.impl.ssl.SslEngineFacadeFactory;
 import org.junit.Before;
 import org.junit.Test;
 
@@ -39,9 +34,6 @@ import org.junit.Test;
  */
 public class SimpleSslTransportWrapperTest
 {
-    private Ssl _sslConfiguration = mock(Ssl.class);
-    private SslEngineFacadeFactory _dummySslEngineFacadeFactory = mock(SslEngineFacadeFactory.class);
-
     private RememberingTransportInput _underlyingInput = new RememberingTransportInput();
     private CannedTransportOutput _underlyingOutput = new CannedTransportOutput();
 
@@ -52,8 +44,7 @@ public class SimpleSslTransportWrapperTe
     @Before
     public void setUp()
     {
-        when(_dummySslEngineFacadeFactory.createSslEngineFacade(_sslConfiguration)).thenReturn(_dummySslEngine);
-        _transportWrapper = new SimpleSslTransportWrapper(_sslConfiguration, _underlyingInput, _underlyingOutput, _dummySslEngineFacadeFactory);
+        _transportWrapper = new SimpleSslTransportWrapper(_dummySslEngine, _underlyingInput, _underlyingOutput);
     }
 
     @Test



---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@qpid.apache.org
For additional commands, e-mail: commits-help@qpid.apache.org