You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by ro...@apache.org on 2016/09/01 09:51:04 UTC

[2/3] qpid-proton git commit: PROTON-1224: Support newer BouncyCastle Implementations

PROTON-1224: Support newer BouncyCastle Implementations

Support new version of BouncyCastle library via existing reflection
mechanism.
Added Unit-tests


Project: http://git-wip-us.apache.org/repos/asf/qpid-proton/repo
Commit: http://git-wip-us.apache.org/repos/asf/qpid-proton/commit/e4be12a6
Tree: http://git-wip-us.apache.org/repos/asf/qpid-proton/tree/e4be12a6
Diff: http://git-wip-us.apache.org/repos/asf/qpid-proton/diff/e4be12a6

Branch: refs/heads/master
Commit: e4be12a69a753c133975bff0a57ed82af43aa51e
Parents: 3b66acf
Author: Jem Day <jd...@paypal.com>
Authored: Mon Aug 22 13:37:39 2016 -0700
Committer: Robert Gemmell <ro...@apache.org>
Committed: Thu Sep 1 10:22:49 2016 +0100

----------------------------------------------------------------------
 proton-j/pom.xml                                |   9 +
 .../engine/impl/ssl/SslEngineFacadeFactory.java | 326 +++++++++++--------
 .../impl/ssl/SslEngineFacadeFactoryTest.java    |  65 ++++
 .../qpid/proton/engine/impl/ssl/README.txt      |  38 +++
 .../qpid/proton/engine/impl/ssl/cert.pem.txt    |  27 ++
 .../qpid/proton/engine/impl/ssl/key.pem.txt     |  30 ++
 .../engine/impl/ssl/private-key-clear.pem.txt   |  27 ++
 tests/pom.xml                                   |   2 +-
 8 files changed, 385 insertions(+), 139 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/proton-j/pom.xml
----------------------------------------------------------------------
diff --git a/proton-j/pom.xml b/proton-j/pom.xml
index d09cdc5..d9e4760 100644
--- a/proton-j/pom.xml
+++ b/proton-j/pom.xml
@@ -31,6 +31,15 @@
     <url>http://svn.apache.org/viewvc/qpid/proton/</url>
   </scm>
 
+  <dependencies>
+    <dependency>
+      <groupId>org.bouncycastle</groupId>
+      <artifactId>bcpkix-jdk15on</artifactId>
+      <version>1.53</version>
+      <scope>test</scope>
+    </dependency>
+  </dependencies>
+
   <build>
     <plugins>
       <plugin>

http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/proton-j/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java
----------------------------------------------------------------------
diff --git a/proton-j/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java b/proton-j/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java
index 7d0cce8..4c991ba 100644
--- a/proton-j/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java
+++ b/proton-j/src/main/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactory.java
@@ -20,14 +20,16 @@
  */
 package org.apache.qpid.proton.engine.impl.ssl;
 
+import java.io.Closeable;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
 import java.io.FileReader;
 import java.io.IOException;
+import java.io.InputStream;
 import java.io.Reader;
 import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationHandler;
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
-import java.lang.reflect.Proxy;
 import java.security.KeyManagementException;
 import java.security.KeyPair;
 import java.security.KeyStore;
@@ -39,6 +41,7 @@ import java.security.Security;
 import java.security.UnrecoverableKeyException;
 import java.security.cert.Certificate;
 import java.security.cert.CertificateException;
+import java.security.cert.CertificateFactory;
 import java.security.cert.X509Certificate;
 import java.util.ArrayList;
 import java.util.Arrays;
@@ -53,9 +56,9 @@ import javax.net.ssl.TrustManager;
 import javax.net.ssl.TrustManagerFactory;
 import javax.net.ssl.X509TrustManager;
 
+import org.apache.qpid.proton.ProtonUnsupportedOperationException;
 import org.apache.qpid.proton.engine.SslDomain;
 import org.apache.qpid.proton.engine.SslPeerDetails;
-import org.apache.qpid.proton.ProtonUnsupportedOperationException;
 import org.apache.qpid.proton.engine.TransportException;
 
 public class SslEngineFacadeFactory
@@ -70,12 +73,28 @@ public class SslEngineFacadeFactory
      */
     private static final String TLS_PROTOCOL = "TLS";
 
-    private static final Class pemReaderClass = getClass("org.bouncycastle.openssl.PEMReader");
-    private static final Class passwordClass = getClass("org.bouncycastle.openssl.PasswordFinder");
-    private static final Class passwordProxy = makePasswordProxy();
-    private static final Constructor pemReaderCons = getConstructor(pemReaderClass, Reader.class, passwordClass);
-    private static final Method readObjectMeth = getMethod(pemReaderClass, "readObject");
+    // BouncyCastle Reflection Helpers
+    private static final Class<?>       PEMParserClass;
+    private static final Constructor<?> pemParserCons;
+    private static final Method         pemReadMethod;
+
+    private static final Class<?>       JcaPEMKeyConverterClass;
+    private static final Class<?>       PEMKeyPairClass;
+    private static final Method         getKeyPairMethod;
+    private static final Method         getPrivateKeyMethod;
+
+    private static final Class<?>       PEMDecrypterProvider;
 
+    private static final Class<?>       PEMEncryptedKeyPairClass;
+    private static final Method         decryptKeyPairMethod;
+
+    private static final Class<?>       JcePEMDecryptorProviderBuilderClass;
+    private static final Method         builderMethod;
+
+    private static final Class<?>       PrivateKeyInfoClass;
+    private static boolean              bouncyCastlePresent;
+
+    @SuppressWarnings("rawtypes")
     private static Class getClass(String klass) {
         try {
             return Class.forName(klass);
@@ -86,6 +105,7 @@ public class SslEngineFacadeFactory
         return null;
     }
 
+    @SuppressWarnings({ "rawtypes", "unchecked" })
     private static Constructor getConstructor(Class klass, Class<?> ... params) {
         if (klass == null) {
             return null;
@@ -98,6 +118,7 @@ public class SslEngineFacadeFactory
         }
     }
 
+    @SuppressWarnings({ "unchecked", "rawtypes" })
     private static Method getMethod(Class klass, String name, Class<?> ... params) {
         if (klass == null) {
             return null;
@@ -110,25 +131,56 @@ public class SslEngineFacadeFactory
         }
     }
 
-    private static Class makePasswordProxy() {
-        if (passwordClass != null) {
-            return Proxy.getProxyClass(passwordClass.getClassLoader(), new Class[] {passwordClass});
-        } else {
-            return null;
-        }
-    }
+  
 
     static
     {
-        try {
-            Class klass = Class.forName("org.bouncycastle.jce.provider.BouncyCastleProvider");
+        // Setup BouncyCastle Reflection artifacts
+        PEMParserClass = getClass("org.bouncycastle.openssl.PEMParser");
+        pemParserCons = getConstructor(PEMParserClass, Reader.class);
+        pemReadMethod = getMethod(PEMParserClass, "readObject");
+
+        JcaPEMKeyConverterClass = getClass("org.bouncycastle.openssl.jcajce.JcaPEMKeyConverter");
+        PEMKeyPairClass = getClass("org.bouncycastle.openssl.PEMKeyPair");
+        getKeyPairMethod = getMethod(JcaPEMKeyConverterClass, "getKeyPair", PEMKeyPairClass);
+
+        PEMDecrypterProvider = getClass("org.bouncycastle.openssl.PEMDecryptorProvider");
+
+        PEMEncryptedKeyPairClass = getClass("org.bouncycastle.openssl.PEMEncryptedKeyPair");
+        decryptKeyPairMethod = getMethod(PEMEncryptedKeyPairClass, "decryptKeyPair", PEMDecrypterProvider);
+
+        JcePEMDecryptorProviderBuilderClass = getClass(
+                "org.bouncycastle.openssl.jcajce.JcePEMDecryptorProviderBuilder");
+        builderMethod = getMethod(JcePEMDecryptorProviderBuilderClass, "build", char[].class);
+
+        PrivateKeyInfoClass = getClass("org.bouncycastle.asn1.pkcs.PrivateKeyInfo");
+        getPrivateKeyMethod = getMethod(JcaPEMKeyConverterClass, "getPrivateKey", PrivateKeyInfoClass);
+
+        try
+        {
+
+            bouncyCastlePresent = false; // Assume not present
+
+            // Try loading BC as a provider
+            Class<?> klass = Class.forName("org.bouncycastle.jce.provider.BouncyCastleProvider");
             Security.addProvider((Provider) klass.newInstance());
-        } catch (ClassNotFoundException e) {
-            _logger.warning("unable to load bouncycastle provider");
-        } catch (InstantiationException e) {
+
+            // Ensure we're running a newer version of BC
+            klass = Class.forName("org.bouncycastle.openssl.PEMParser");
+            bouncyCastlePresent = true;
+
+        } catch (ClassNotFoundException e)
+        {
+            _logger.warning("unable to load bouncycastle provider. " + e.getMessage());
+
+        } catch (InstantiationException e)
+        {
             _logger.warning("unable to instantiate bouncycastle provider");
-        } catch (IllegalAccessException e) {
+
+        } catch (IllegalAccessException e)
+        {
             _logger.warning("unable to access bouncycastle provider");
+
         }
     }
 
@@ -309,7 +361,7 @@ public class SslEngineFacadeFactory
                 {
                     _logger.log(Level.FINE, "_sslParams.getTrustedCaDb() : " + sslDomain.getTrustedCaDb());
                 }
-                Certificate trustedCaCert = (Certificate) readPemObject(sslDomain.getTrustedCaDb(), null, Certificate.class);
+                Certificate trustedCaCert = readCertificate(sslDomain.getTrustedCaDb());
                 keystore.setCertificateEntry(caCertAlias, trustedCaCert);
             }
 
@@ -317,25 +369,10 @@ public class SslEngineFacadeFactory
                     && sslDomain.getPrivateKeyFile() != null)
             {
                 String clientPrivateKeyAlias = "clientPrivateKey";
-                Certificate clientCertificate = (Certificate) readPemObject(sslDomain.getCertificateFile(), null, Certificate.class);
-                Object keyOrKeyPair = readPemObject(
-                        sslDomain.getPrivateKeyFile(),
-                        sslDomain.getPrivateKeyPassword(), PrivateKey.class, KeyPair.class);
-
-                final PrivateKey clientPrivateKey;
-                if (keyOrKeyPair instanceof PrivateKey)
-                {
-                    clientPrivateKey = (PrivateKey)keyOrKeyPair;
-                }
-                else if (keyOrKeyPair instanceof KeyPair)
-                {
-                    clientPrivateKey = ((KeyPair)keyOrKeyPair).getPrivate();
-                }
-                else
-                {
-                    // Should not happen - readPemObject will have already verified key type
-                    throw new TransportException("Unexpected key type " + keyOrKeyPair);
-                }
+                Certificate clientCertificate = (Certificate) readCertificate(sslDomain.getCertificateFile());
+             
+                PrivateKey clientPrivateKey = readPrivateKey(sslDomain.getPrivateKeyFile(), sslDomain.getPrivateKeyPassword());
+               
 
                 keystore.setKeyEntry(clientPrivateKeyAlias, clientPrivateKey,
                         dummyPassword, new Certificate[] { clientCertificate });
@@ -414,128 +451,141 @@ public class SslEngineFacadeFactory
             .append(" ]").toString();
     }
 
-    private Object readPemObject(String pemFile, String keyPassword, @SuppressWarnings("rawtypes") Class... expectedInterfaces)
-    {
-        final Object passwordFinder;
-        if (keyPassword != null)
-        {
-            passwordFinder = getPasswordFinderFor(keyPassword);
-        }
-        else
-        {
-            passwordFinder = null;
-        }
+   
+    Certificate readCertificate(String pemFile) {
 
-        Reader reader = null;
-        Reader pemReader = null;
-
-        if (pemReaderCons == null || readObjectMeth == null) {
-            throw new ProtonUnsupportedOperationException();
-        }
+        InputStream is = null;
 
         try
         {
-            reader = new FileReader(pemFile);
-            pemReader = (Reader) pemReaderCons.newInstance(new Object[] {reader, passwordFinder});
-            Object pemObject = readObjectMeth.invoke(pemReader);
-            if (!checkPemObjectIsOfAllowedTypes(pemObject, expectedInterfaces))
-            {
-                throw new TransportException
-                    ("File " + pemFile + " does not provide a object of the required type."
-                     + " Read an object of class " + pemObject.getClass().getName()
-                     + " whilst expecting an implementation of one of the following  : "
-                     + Arrays.asList(expectedInterfaces));
-            }
-            return pemObject;
-        }
-        catch(InstantiationException e)
+            CertificateFactory cFactory = CertificateFactory.getInstance("X.509");
+            is = new FileInputStream(pemFile);
+            return cFactory.generateCertificate(is);
+        } catch (CertificateException ce)
         {
-            _logger.log(Level.SEVERE, "Unable to read PEM object. Perhaps you need the unlimited strength libraries in <java-home>/jre/lib/security/ ?", e);
-            throw new TransportException("Unable to read PEM object from file " + pemFile, e);
-        }
-        catch(InvocationTargetException e)
+            String msg = "Failed to load certificate [" + pemFile + "]";
+            _logger.log(Level.SEVERE, msg);
+            throw new TransportException(msg, ce);
+
+        } catch (FileNotFoundException e)
         {
-            _logger.log(Level.SEVERE, "Unable to read PEM object. Perhaps you need the unlimited strength libraries in <java-home>/jre/lib/security/ ?", e);
-            throw new TransportException("Unable to read PEM object from file " + pemFile, e);
-        }
-        catch (IllegalAccessException e)
+            String msg = "Certificate file not found [" + pemFile + "]";
+            _logger.log(Level.SEVERE, msg);
+            throw new TransportException(msg, e);
+        } finally
         {
-            throw new TransportException(e);
+            closeSafely(is);
         }
-        catch (IOException e)
+
+    }
+
+    PrivateKey readPrivateKey(String pemFile, String password) {
+
+        // Sanity
+        if (!bouncyCastlePresent)
         {
-            throw new TransportException("Unable to read PEM object from file " + pemFile, e);
+            throw new ProtonUnsupportedOperationException("BouncyCastle Not Loaded");
         }
-        finally
+
+        PrivateKey privateKey = null;
+
+        final Object pemObject = readPemObject(pemFile);
+
+        try
         {
-            if(pemReader != null)
+            Object keyConverter = JcaPEMKeyConverterClass.newInstance();
+
+            // keyConverter.setProvider("BC");
+            setProvider(keyConverter, "BC");
+
+            // if (pemObject instanceof PEMEncryptedKeyPair)
+            if (PEMEncryptedKeyPairClass.isInstance(pemObject))
             {
-                try
-                {
-                    pemReader.close();
-                }
-                catch(IOException e)
-                {
-                    _logger.log(Level.SEVERE, "Couldn't close PEM reader", e);
-                }
-            }
-            if (reader != null)
+
+                Object decryptorBuilder = JcePEMDecryptorProviderBuilderClass.newInstance();
+
+                // Build a PEMDecryptProvider
+                Object decryptProvider = builderMethod.invoke(decryptorBuilder, password.toCharArray());
+
+                Object decryptedKeyPair = decryptKeyPairMethod.invoke(pemObject, decryptProvider);
+                KeyPair keyPair = (KeyPair) getKeyPairMethod.invoke(keyConverter, decryptedKeyPair);
+
+                privateKey = keyPair.getPrivate();
+
+            } else if (PEMKeyPairClass.isInstance(pemObject))
             {
-                try
-                {
-                    reader.close();
-                }
-                catch (IOException e)
-                {
-                    _logger.log(Level.SEVERE, "Couldn't close PEM file reader", e);
-                }
+                // It's a KeyPair but not encrypted.
+                KeyPair keyPair = (KeyPair) getKeyPairMethod.invoke(keyConverter, pemObject);
+                privateKey = keyPair.getPrivate();
+                
+            } else if (PrivateKeyInfoClass.isInstance(pemObject))
+            {
+                // It's an unencrypted private key
+                privateKey = (PrivateKey) getPrivateKeyMethod.invoke(pemObject);
+            } else
+            {
+                final String msg = "Unable to load PrivateKey, Unpexected Object [" + pemObject.getClass().getName()
+                        + "]";
+
+                _logger.log(Level.SEVERE, msg);
+                throw new TransportException(msg);
             }
-        }
-    }
 
-    @SuppressWarnings("rawtypes")
-    private boolean checkPemObjectIsOfAllowedTypes(Object pemObject,  Class... expectedInterfaces)
-    {
-        if (expectedInterfaces.length == 0)
+        } catch (InstantiationException | IllegalAccessException | IllegalArgumentException
+                | InvocationTargetException e)
         {
-            throw new IllegalArgumentException("Must be at least one expectedKeyTypes");
+            final String msg = "Failed to process key file [" + pemFile + "] - " + e.getMessage();
+            throw new TransportException(msg, e);
         }
 
-        for (Class keyInterface : expectedInterfaces)
-        {
-            if (keyInterface.isInstance(pemObject))
-            {
-                return true;
-            }
-        }
-        return false;
+        return privateKey;
     }
 
-    private Object getPasswordFinderFor(final String keyPassword)
-    {
-        if (passwordProxy == null) {
-            throw new ProtonUnsupportedOperationException();
-        }
+    private Object readPemObject(String pemFile) {
+
+        Reader reader = null;
+     
+        Object pemParser = null;
+        Object pemObject = null;
 
         try {
-            Constructor con = passwordProxy.getConstructor(new Class[] {InvocationHandler.class});
-            Object finder = con.newInstance(new InvocationHandler() {
-                public Object invoke(Object obj, Method meth, Object[] args) {
-                return keyPassword.toCharArray();
-                }
-            });
+            reader = new FileReader(pemFile);
+            pemParser = pemParserCons.newInstance(reader); // = new PEMParser(reader);
+            pemObject = pemReadMethod.invoke(pemParser); // = pemParser.readObject()       
+        }
+        catch (IOException | IllegalAccessException | IllegalArgumentException | InvocationTargetException | InstantiationException e) {
+            _logger.log(Level.SEVERE, "Unable to read PEM object. Perhaps you need the unlimited strength libraries in <java-home>/jre/lib/security/ ?", e);
+            throw new TransportException("Unable to read PEM object from file " + pemFile, e);
+        }
+        finally {
+          
+            closeSafely(reader);
+        }
 
-            return finder;
-        } catch (NoSuchMethodException e) {
-            throw new TransportException(e);
-        } catch (InstantiationException e) {
-            throw new TransportException(e);
-        } catch (IllegalAccessException e) {
-            throw new TransportException(e);
-        } catch (InvocationTargetException e) {
-            throw new TransportException(e);
+        return pemObject;
+    }
+
+    private void setProvider(Object obj, String provider) throws IllegalAccessException, IllegalArgumentException, InvocationTargetException {
+        
+        final Class<?> aClz = obj.getClass();
+        final Method setProvider = getMethod(aClz, "setProvider", String.class);
+        setProvider.invoke(obj, provider);
+        
+    }
+    
+    
+    private void closeSafely(Closeable c){
+        
+        if (c != null) {
+            try {
+                c.close();
+            }
+            catch (IOException e) {
+               // Swallow
+            }
         }
     }
+    
 
     private static final class AlwaysTrustingTrustManager implements X509TrustManager
     {

http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/proton-j/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactoryTest.java
----------------------------------------------------------------------
diff --git a/proton-j/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactoryTest.java b/proton-j/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactoryTest.java
new file mode 100644
index 0000000..e3e99cb
--- /dev/null
+++ b/proton-j/src/test/java/org/apache/qpid/proton/engine/impl/ssl/SslEngineFacadeFactoryTest.java
@@ -0,0 +1,65 @@
+package org.apache.qpid.proton.engine.impl.ssl;
+
+import static org.junit.Assert.assertNotNull;
+
+import java.net.URL;
+import java.security.PrivateKey;
+import java.security.cert.Certificate;
+
+import org.junit.Test;
+
+public class SslEngineFacadeFactoryTest {
+
+    
+    @Test
+    public void testCertifcateLoad() {
+        String ipFile = resolveFilename("cert.pem.txt");
+        
+        SslEngineFacadeFactory factory = new SslEngineFacadeFactory();
+        
+        Certificate cert = null;
+        
+       cert = factory.readCertificate(ipFile);
+       
+       assertNotNull("Certificate was NULL", cert);
+    }
+    
+    @Test
+    public void testLoadKey() {
+        String keyFile = resolveFilename("key.pem.txt");
+        SslEngineFacadeFactory factory = new SslEngineFacadeFactory();
+        
+        PrivateKey key = null;
+        
+        key = factory.readPrivateKey(keyFile, "unittest");
+        
+        assertNotNull("Key was NULL", key);
+        
+    }
+    
+    @Test
+    public void testLoadUnencryptedPrivateKey(){
+        
+        String keyFile = resolveFilename("private-key-clear.pem.txt");
+        SslEngineFacadeFactory factory = new SslEngineFacadeFactory();
+        
+        PrivateKey key = null;
+        
+        key = factory.readPrivateKey(keyFile, "unittest");
+        
+        assertNotNull("Key was NULL", key);
+    }
+    
+    private String resolveFilename(String testFilename) {
+        
+        URL resourceUri = this.getClass().getResource(testFilename);
+        
+        assertNotNull("Failed to load file: " + testFilename, resourceUri);
+        
+        String fName = resourceUri.getPath();
+        
+        return fName;
+        
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/README.txt
----------------------------------------------------------------------
diff --git a/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/README.txt b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/README.txt
new file mode 100644
index 0000000..163d472
--- /dev/null
+++ b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/README.txt
@@ -0,0 +1,38 @@
+# These resources are used during the unittesting of the SSL capabilities
+#
+#  cert.pem.txt              - A public certificate
+#  key.pem.txt               - A passphrase protected private key
+#  private-key-clear.pem.txt - An unprotected private key
+
+# Files have a .txt suffix to prevent undesired handling by other tooling (IDEs etc)
+# and can easilly be re-created using the following openssl commands or you can
+# execute this file directly with 
+#             sh README.txt
+
+## Clean Up
+
+echo
+echo Clean Up
+echo
+
+rm *.pem.txt
+
+# 1. Generate a certificate and protected private key
+
+echo
+echo when prompted use 'unittest' as the passphase, all other fields can be random values
+echo
+
+openssl req -x509 -newkey rsa:2048 -keyout key.pem.txt -out cert.pem.txt -days 10000
+ 
+# 2. The following command produces an unprotected private key
+
+echo
+echo when prompted, use 'unittest' as the passphrase
+echo
+
+openssl rsa -in key.pem.txt -out private-key-clear.pem.txt -outform PEM
+
+echo
+
+

http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/cert.pem.txt
----------------------------------------------------------------------
diff --git a/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/cert.pem.txt b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/cert.pem.txt
new file mode 100644
index 0000000..84ec75a
--- /dev/null
+++ b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/cert.pem.txt
@@ -0,0 +1,27 @@
+-----BEGIN CERTIFICATE-----
+MIIEmzCCA4OgAwIBAgIJAPjD77mpHLocMA0GCSqGSIb3DQEBBQUAMIGPMQswCQYD
+VQQGEwJVUzETMBEGA1UECBMKQ2FsaWZvcm5pYTERMA8GA1UEBxMIU2FuIEpvc2Ux
+EDAOBgNVBAoTB1Rlc3RpbmcxDzANBgNVBAsTBlRlc3RlcjETMBEGA1UEAxMKdGVz
+dGluZy5pdDEgMB4GCSqGSIb3DQEJARYRbm9ib2R5QHRlc3RpbmcuaXQwHhcNMTYw
+NjA5MTgxNjA0WhcNNDMxMDI2MTgxNjA0WjCBjzELMAkGA1UEBhMCVVMxEzARBgNV
+BAgTCkNhbGlmb3JuaWExETAPBgNVBAcTCFNhbiBKb3NlMRAwDgYDVQQKEwdUZXN0
+aW5nMQ8wDQYDVQQLEwZUZXN0ZXIxEzARBgNVBAMTCnRlc3RpbmcuaXQxIDAeBgkq
+hkiG9w0BCQEWEW5vYm9keUB0ZXN0aW5nLml0MIIBIjANBgkqhkiG9w0BAQEFAAOC
+AQ8AMIIBCgKCAQEAxbIpYVTdItTeWy1qaG3Lzs6IeMzAzHFsOw6rmeSM8GZ5S/vS
+PzsKfRCXKc52/2KblROsK2Eez/wt9CB9HgksHr/sjYtivwn/V/jumLb8z9R8jBnF
+jZ0KXyWxtiJFowh+Zd1BxJeQTmmbvJpYGVmKYu+4t66TQGhNUu8e+J5GIgJjDPnA
+TE5bGBMi7HtoXVy+Tp0sO/S7cXLXmWpeyCXS7HFUj+Jdzbed0yMs/JmbBXyLIYMU
+Rq1oSI8DOn5jtrTQz7/xI5qOebIwACcYk6LRI83zIIvcv6olpnzViDjAGT6PQtj5
+FuUe1WHKVjd4Bjyoo+zULwQoF1b6qSe5m6O7IQIDAQABo4H3MIH0MB0GA1UdDgQW
+BBQjS5wYZlVLz3eNVIxFGroXSPhl/zCBxAYDVR0jBIG8MIG5gBQjS5wYZlVLz3eN
+VIxFGroXSPhl/6GBlaSBkjCBjzELMAkGA1UEBhMCVVMxEzARBgNVBAgTCkNhbGlm
+b3JuaWExETAPBgNVBAcTCFNhbiBKb3NlMRAwDgYDVQQKEwdUZXN0aW5nMQ8wDQYD
+VQQLEwZUZXN0ZXIxEzARBgNVBAMTCnRlc3RpbmcuaXQxIDAeBgkqhkiG9w0BCQEW
+EW5vYm9keUB0ZXN0aW5nLml0ggkA+MPvuakcuhwwDAYDVR0TBAUwAwEB/zANBgkq
+hkiG9w0BAQUFAAOCAQEAM41jrwVEQZltTWiQ8kBMSl4K80gBlLLDu/XD9Dfe6snD
+8wQZD21LLBlsLaVwR8Fk1umFHnwYoTD1tghfW7LeTS3zTMRu269a5xbZ82rOoeYk
+MQwFK7rMXPfNKGSk06lXAzjrlZD+qd8qfm1UEoUmWlmJyBinCnX8x8G5Z6Za4UsK
+LmdZShnbXRvToPZ/xGMeWmB2NGG5uF3evLM6+cdOLhqxoei90dmufWUcRDBXBEED
+8cZpXARYS2Q5EflmrDWOwMN+1cfEZDNssb/GmKouNuVoobxgIo9lftTds+gR319N
+usu7JUbh5QbAOdXg4prQ3ASNq9a95J4Y8O9cW4XdSg==
+-----END CERTIFICATE-----

http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/key.pem.txt
----------------------------------------------------------------------
diff --git a/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/key.pem.txt b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/key.pem.txt
new file mode 100644
index 0000000..e1f72f5
--- /dev/null
+++ b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/key.pem.txt
@@ -0,0 +1,30 @@
+-----BEGIN RSA PRIVATE KEY-----
+Proc-Type: 4,ENCRYPTED
+DEK-Info: DES-EDE3-CBC,F0AAE930E2D9E692
+
+L9c43ZBCX8aRwhqrpbhKP2jNFi2c5MQO6qNV9/Ubk3fWC2pb0dqnHLBSzdOupIKa
+56wrzz9wtDUbPO3AsFBJmX5ov9rSLhAKeTdrYAUMk7qPhiMTUOvrDtGLHxhnBtYi
+2VV4I4ONhg+uYDa2GW8U/YI216E/t2nA4L6KuxI7ac8kWyMn5IJgk/GvnDlePxTc
+bDUGgRC/kiXhTTeBQoMih09MxCSJEgXbSKKB5FpNwzwwXGf2bHvdId8AY0e/7KDO
+pO5E9YpKu+HO+HbyhQJiIQr9CKkyfsdYST/ojGPGH+Yn8M4ZdBtPclisHkt7mIAz
+swqjpt9XHzVXJh4+Di0VPmvOnDcU8SV62VpyMnPbXL2eexEGrofIwfTHQQTHMfNZ
+OJOtXRJXBijGOd0mAT8ijTnuelBCsQtc0fMT8R0jSaQjONynaewNzBLnRD4E/9Gw
+gGPjEiLtXNSVjCFhIDgLFvuljrOqH+MIgkSFhpM/C9LnPXx3I7Mxe7198Fp/jDRZ
+GVpOQqAo4tbvw3cCOtRxdzwpUi9p6lnBGDRHjRRDMqzqncJhNej/cC8QonUw/7JO
+Rv3OMWIy682rCvS00q0dhm+If0f5Nox7rt1yxWYyX3zj/RdkeZezJTDuxDsyLpiw
+NzRSvLUVfdh1v6Ofcnh/6eDIi4uyCt+rDeZjvG3HGAssOD+27s6i18QDbbuolrkc
+yypQ7Bo/UeuUUCNE/G9ItHOCC1qxdJYIC30dAlmWPjYQrapQOuQWXzxs5u8+hxkb
+u32KA8nuCS1codbxPNXnVbrDyU/vWsxTjPr/ODChWfLeIu/9KwjxLLoOUwkRGJnm
+dQVZeawiSggIL2nwsS2c5hOV0yZZuNzB3RAqYV7ZfB5Xdk3LAEXjrYOELeFUY1vJ
+V3pcEdD8VfTLiEwQ/TMmg03ju+1dA5lMsLaQ0KrhUJbarkAeFEtAPgpaIhHoCAa5
+3ObLx/8dctrbHx4rRgkN6xWQz0qEMzAtpQaUYaFbnRrLKF4fqq+PC35BfwM5hVOa
+rXM1aQ065pV1cPVstqk0jN/36m+tMv5l7NperNS78UaFy+4KyX2/Lj3YvbLlTT75
+Hn6gf+nekTwW2V+P1Yn8MKr7jelCCai1MoLMugrUNfILKAohA/CGdupoUmxr5F3b
+F7XnY1RMAr0FROl5f5Fc6In12mey9mvHh1yT5HZa0SoK79/Bfv+3oiOXbqgKBJ8O
+2FkJtlBd/nx7EYx3teLXClvX+FfQL4gZkyvEE0m8HAFY0HfozNhKfi+PFDXz/R7X
+yCvBdIzE26nRtY9h4uhAcn3AefO8b0Slpmlq/+BDf8Pta9TF8zFWyzPRMIyuEE4l
+GTk1i6p9PDzu7lhC93tIfWZe5Xz1DB+c4bFQbzxAghoEOFz3NA17VEKEkl0t04sA
+lUqJmEftUPBZocgv7zO5v7z17G5yGqS+HyBGWaBqBRH9rGPhHxyEpPtwGNhP+biN
+7cvnlMbhD41KAkYDy3tQkztH/A0g/xNZTElhpXnnHq5AXnn46y/SVH5q6Tdy1xGz
+aEeKdL7JdPZ7XNmkHgbHLmxNFGtoJwx1hKw6slg+kh0j4xcNTpjJcQ==
+-----END RSA PRIVATE KEY-----

http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/private-key-clear.pem.txt
----------------------------------------------------------------------
diff --git a/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/private-key-clear.pem.txt b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/private-key-clear.pem.txt
new file mode 100644
index 0000000..e3de94c
--- /dev/null
+++ b/proton-j/src/test/resources/org/apache/qpid/proton/engine/impl/ssl/private-key-clear.pem.txt
@@ -0,0 +1,27 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIIEowIBAAKCAQEAxbIpYVTdItTeWy1qaG3Lzs6IeMzAzHFsOw6rmeSM8GZ5S/vS
+PzsKfRCXKc52/2KblROsK2Eez/wt9CB9HgksHr/sjYtivwn/V/jumLb8z9R8jBnF
+jZ0KXyWxtiJFowh+Zd1BxJeQTmmbvJpYGVmKYu+4t66TQGhNUu8e+J5GIgJjDPnA
+TE5bGBMi7HtoXVy+Tp0sO/S7cXLXmWpeyCXS7HFUj+Jdzbed0yMs/JmbBXyLIYMU
+Rq1oSI8DOn5jtrTQz7/xI5qOebIwACcYk6LRI83zIIvcv6olpnzViDjAGT6PQtj5
+FuUe1WHKVjd4Bjyoo+zULwQoF1b6qSe5m6O7IQIDAQABAoIBAC1RVNkB6hsk7r+5
+3m2H1bNXdsMyNHPpACVdjIqfcItfAikf1ac28oWOuwgTUwXh5cY7lzjub3C/3wza
+MbQj6CA4YJJlxEIEmarh3lfVgohlrhMziSyYNhtveZhFrO7dcJQLLxtQnvzKiq+m
+NdHBy844I4C/nPOjtS3wsInPRkZfHHnOgMFLP7Fr2ZmuOMkLLpQV09NL/eF7Z+uA
++jBv0z3I1xe3xeynczhUDvBv9lq90eSMsFzj/BOkqH8m329GQhk0rqf4uby5adPL
+59z/ScJ5/N5scTDPZ4sGHoH1rJYOQKKLL3m3esC9MY7YxueLVU9sFi5kq5irdveh
+0iIzYAECgYEA6lY5x0i6AecpNu8/tsdV8wkwrdW/Q6/9MdWx6zGBNyA87hzqrtsr
+jxf75SFR9AcFZhBLDUNycrsG3m7AB/urps/scCC8OKkevvLAUNxx2nT5tQd/0BG3
+OkVEAQFKZigsoLkvnRibmPOj5NtiyzK9L1Hya5Paab1W5e4qydd6/iECgYEA1/jM
+pCwv4KtBbLRR2wHO+cUv1Ll419J6aXoFncYVZ8eRekqz+GtBgeC0vyYfpQoVhpnb
+ZYJy9Hf2h6sWbk1imn44N0QCCkQxhGyCX+Olvx4kZTdFjQZG46LVdS8VgE319Nz+
+K3apjjGg9N3htyFVxzd5LhBNYCDuNi3pvGN/HQECgYAGogAqqt1Q9nkNLAJyqvu8
+0FLHaNhsEwwon/LURGdy5v+ygbEG1/9IopYnqyTFsnktpWJqcrFHnBGatCnNUAtQ
+wmvf1J1fQTI0l2xoHYU/eLYksJymiAnWpWVCXgX8FEEHH5bAbJTi5GqMLMWEGOCP
++VLSRrIU8h4GjhI5+lZp4QKBgB61wyupGNnCoFf7wBP7StobXvTJttRBmqR69Gd9
+7jdGmnogOz0cy0DTmgAARMmsCGmOYTMq/Hukv0qFWnguytGbFxVMt1mMXtosr9FA
+xqXJfHVkCaDG/reJxP6Xxl/rNgkuj3nQssWEaxXGozzuIYtlaPbS3J3JsPXFS5I9
+N6sBAoGBAICQAUuoMfmtGj/VvMKgSVSaIA3gK7qt4/Pm8K/z6j/G1G44+YDW25RO
++Y0PPdJRr9CO9SHccTkaa3PdqTA0XMV+jmOGc2dn+36eJBhxe6R0LINGp2LiNYfv
+OxuhpMneEbHWeRBw9YkiZOg3Mg/Dh2qNT9VASwfP5clnvprlX7WQ
+-----END RSA PRIVATE KEY-----

http://git-wip-us.apache.org/repos/asf/qpid-proton/blob/e4be12a6/tests/pom.xml
----------------------------------------------------------------------
diff --git a/tests/pom.xml b/tests/pom.xml
index 7b3243d..0634197 100644
--- a/tests/pom.xml
+++ b/tests/pom.xml
@@ -99,7 +99,7 @@ mvn test \
     <dependency>
       <groupId>org.bouncycastle</groupId>
       <artifactId>bcpkix-jdk15on</artifactId>
-      <version>1.47</version>
+      <version>1.53</version>
     </dependency>
     <dependency>
         <groupId>org.python</groupId>


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