aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--ChangeLog30
-rw-r--r--Makefile.am3
-rw-r--r--NEWS1
-rw-r--r--acinclude.m49
-rw-r--r--netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java93
-rw-r--r--netx/net/sourceforge/jnlp/security/HttpsCertVerifier.java5
-rw-r--r--netx/net/sourceforge/jnlp/security/VariableX509TrustManager.java140
-rw-r--r--netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK6.java75
-rw-r--r--netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK7.java136
9 files changed, 416 insertions, 76 deletions
diff --git a/ChangeLog b/ChangeLog
index 80b4da8..6829b58 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,33 @@
+2012-09-17 Deepak Bhole <[email protected]>
+
+ PR1161: X509VariableTrustManager does not work correctly with OpenJDK7
+ * Makefile.am: If building with JDK 6, don't build
+ VariableX509TrustManagerJDK7.
+ * NEWS: Updated.
+ * acinclude.m4: In addition to setting VERSION_DEFS, also set HAVE_JAVA7
+ if building with JDK7.
+ * netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java (initialize): Use new
+ getSSLSocketTrustManager() method to get the trust manager.
+ (getSSLSocketTrustManager): New method. Depending on runtime JRE version,
+ returns the appropriate trust manager.
+ * netx/net/sourceforge/jnlp/security/HttpsCertVerifier.java: Removed
+ unused tm variable.
+ * netx/net/sourceforge/jnlp/security/VariableX509TrustManager.java: No
+ longer extends com.sun.net.ssl.internal.ssl.X509ExtendedTrustManager.
+ (checkClientTrusted): Renamed to checkTrustClient and removed overloaded
+ implementations.
+ (checkServerTrusted): Renamed to checkTrustServer. Also, modified to
+ accept socket and engine (may be null). Assume that CN is mismatched by
+ default, rather than matched. If explicitly trusted, bypass other checks,
+ including CN mismatch.
+ (checkAllManagers): Modified to accept socket and engine. Modified to work
+ for both JDK6 and JDK7.
+ (getAcceptedIssuers): Make protected (called by others in package).
+ * netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK6.java:
+ New class -- X509TrustManager for JDK6.
+ * netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK7.java:
+ New class -- X509TrustManager for JDK7.
+
2012-09-07 Saad Mohammad <[email protected]>
Added signed jnlp tests for applications with multiple jar resources.
diff --git a/Makefile.am b/Makefile.am
index cc71215..37324ac 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -348,6 +348,9 @@ netx-source-files.txt:
if !WITH_RHINO
sed -i '/RhinoBasedPacEvaluator/ d' $@
endif
+if !HAVE_JAVA7
+ sed -i '/VariableX509TrustManagerJDK7/ d' $@
+endif
stamps/netx.stamp: netx-source-files.txt stamps/bootstrap-directory.stamp
mkdir -p $(NETX_DIR)
diff --git a/NEWS b/NEWS
index 3e48bad..82172e1 100644
--- a/NEWS
+++ b/NEWS
@@ -17,6 +17,7 @@ New in release 1.4 (2012-XX-XX):
* Common
- PR1049: Extension jnlp's signed jar with the content of only META-INF/* is considered
- PR955: regression: SweetHome3D fails to run
+ - PR1161: X509VariableTrustManager does not work correctly with OpenJDK7
New in release 1.3 (2012-XX-XX):
* NetX
diff --git a/acinclude.m4 b/acinclude.m4
index 1ab4c9a..fc22891 100644
--- a/acinclude.m4
+++ b/acinclude.m4
@@ -715,9 +715,12 @@ AC_DEFUN_ONCE([IT_FIND_JAVA],
AC_MSG_RESULT(${JAVA})
AC_SUBST(JAVA)
JAVA_VERSION=`$JAVA -version 2>&1 | sed -n '1s/@<:@^"@:>@*"\(.*\)"$/\1/p'`
- case "${JAVA_VERSION}" in
- 1.7*) VERSION_DEFS='-DHAVE_JAVA7';;
- esac
+ HAVE_JAVA7=`echo $JAVA_VERSION | awk '{if ($(0) >= 1.7) print "yes"}'`
+ if ! test -z "$HAVE_JAVA7" ; then
+ VERSION_DEFS='-DHAVE_JAVA7'
+ fi
+
+ AM_CONDITIONAL([HAVE_JAVA7], test x"${HAVE_JAVA7}" = "xyes" )
AC_SUBST(VERSION_DEFS)
])
diff --git a/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java b/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java
index ec97300..113e51b 100644
--- a/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java
+++ b/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java
@@ -16,38 +16,59 @@
package net.sourceforge.jnlp.runtime;
-import java.io.*;
+import java.awt.EventQueue;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.PrintStream;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Method;
+import java.lang.reflect.InvocationTargetException;
import java.net.Authenticator;
import java.net.ProxySelector;
import java.nio.channels.FileChannel;
import java.nio.channels.FileLock;
-import java.awt.*;
-import java.text.*;
-import java.util.*;
+import java.security.AllPermission;
+import java.security.KeyStore;
+import java.security.Policy;
+import java.security.Security;
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+import java.text.MessageFormat;
import java.util.List;
-import java.security.*;
-import javax.jnlp.*;
+import java.util.ResourceBundle;
+
+import javax.jnlp.ServiceManager;
import javax.naming.ConfigurationException;
import javax.net.ssl.HttpsURLConnection;
import javax.net.ssl.KeyManagerFactory;
import javax.net.ssl.SSLContext;
+import javax.net.ssl.SSLEngine;
+import javax.net.ssl.SSLSocket;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManager;
import javax.swing.UIManager;
import javax.swing.text.html.parser.ParserDelegator;
-import sun.net.www.protocol.jar.URLJarFile;
-
-import net.sourceforge.jnlp.*;
+import net.sourceforge.jnlp.DefaultLaunchHandler;
+import net.sourceforge.jnlp.GuiLaunchHandler;
+import net.sourceforge.jnlp.LaunchHandler;
+import net.sourceforge.jnlp.Launcher;
import net.sourceforge.jnlp.browser.BrowserAwareProxySelector;
-import net.sourceforge.jnlp.cache.*;
+import net.sourceforge.jnlp.cache.CacheUtil;
+import net.sourceforge.jnlp.cache.DefaultDownloadIndicator;
+import net.sourceforge.jnlp.cache.DownloadIndicator;
+import net.sourceforge.jnlp.cache.UpdatePolicy;
import net.sourceforge.jnlp.config.DeploymentConfiguration;
import net.sourceforge.jnlp.security.JNLPAuthenticator;
import net.sourceforge.jnlp.security.KeyStores;
import net.sourceforge.jnlp.security.SecurityDialogMessageHandler;
import net.sourceforge.jnlp.security.VariableX509TrustManager;
-import net.sourceforge.jnlp.services.*;
-import net.sourceforge.jnlp.util.*;
+import net.sourceforge.jnlp.services.XServiceManagerStub;
+import net.sourceforge.jnlp.util.FileUtils;
+import net.sourceforge.jnlp.util.TeeOutputStream;
+import sun.net.www.protocol.jar.URLJarFile;
/**
* Configure and access the runtime environment. This class
@@ -223,7 +244,7 @@ public class JNLPRuntime {
KeyStore ks = KeyStores.getKeyStore(KeyStores.Level.USER, KeyStores.Type.CLIENT_CERTS);
KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
kmf.init(ks, KeyStores.getPassword());
- TrustManager[] trust = new TrustManager[] { VariableX509TrustManager.getInstance() };
+ TrustManager[] trust = new TrustManager[] { getSSLSocketTrustManager() };
context.init(kmf.getKeyManagers(), trust, null);
sslSocketFactory = context.getSocketFactory();
@@ -248,6 +269,52 @@ public class JNLPRuntime {
}
/**
+ * Returns a TrustManager ideal for the running VM.
+ *
+ * @return TrustManager the trust manager to use for verifying https certificates
+ */
+ private static TrustManager getSSLSocketTrustManager() throws
+ ClassNotFoundException, IllegalAccessException, InstantiationException, InvocationTargetException {
+
+ try {
+
+ Class<?> trustManagerClass;
+ Constructor<?> tmCtor = null;
+
+ if (System.getProperty("java.version").startsWith("1.6")) { // Java 6
+ try {
+ trustManagerClass = Class.forName("net.sourceforge.jnlp.security.VariableX509TrustManagerJDK6");
+ } catch (ClassNotFoundException cnfe) {
+ System.err.println("Unable to find class net.sourceforge.jnlp.security.VariableX509TrustManagerJDK6");
+ return null;
+ }
+ } else { // Java 7 or more (technically could be <= 1.5 but <= 1.5 is unsupported)
+ try {
+ trustManagerClass = Class.forName("net.sourceforge.jnlp.security.VariableX509TrustManagerJDK7");
+ } catch (ClassNotFoundException cnfe) {
+ System.err.println("Unable to find class net.sourceforge.jnlp.security.VariableX509TrustManagerJDK7");
+ return null;
+ }
+ }
+
+ Constructor<?>[] tmCtors = trustManagerClass.getDeclaredConstructors();
+ tmCtor = tmCtors[0];
+
+ for (Constructor<?> ctor : tmCtors) {
+ if (tmCtor.getGenericParameterTypes().length == 0) {
+ tmCtor = ctor;
+ break;
+ }
+ }
+
+ return (TrustManager) tmCtor.newInstance();
+ } catch (RuntimeException e) {
+ System.err.println("Unable to load JDK-specific TrustManager. Was this version of IcedTea-Web compiled with JDK6?");
+ throw e;
+ }
+ }
+
+ /**
* This must NOT be called form the application ThreadGroup. An application
* can inject events into its {@link EventQueue} and bypass the security
* dialogs.
diff --git a/netx/net/sourceforge/jnlp/security/HttpsCertVerifier.java b/netx/net/sourceforge/jnlp/security/HttpsCertVerifier.java
index a7787d2..8490cf8 100644
--- a/netx/net/sourceforge/jnlp/security/HttpsCertVerifier.java
+++ b/netx/net/sourceforge/jnlp/security/HttpsCertVerifier.java
@@ -59,7 +59,6 @@ import sun.security.x509.X500Name;
public class HttpsCertVerifier implements CertVerifier {
- private VariableX509TrustManager tm;
private X509Certificate[] chain;
private String authType;
private String hostName;
@@ -67,11 +66,9 @@ public class HttpsCertVerifier implements CertVerifier {
private boolean hostMatched;
private ArrayList<String> details = new ArrayList<String>();
- public HttpsCertVerifier(VariableX509TrustManager tm,
- X509Certificate[] chain, String authType,
+ public HttpsCertVerifier(X509Certificate[] chain, String authType,
boolean isTrusted, boolean hostMatched,
String hostName) {
- this.tm = tm;
this.chain = chain;
this.authType = authType;
this.hostName = hostName;
diff --git a/netx/net/sourceforge/jnlp/security/VariableX509TrustManager.java b/netx/net/sourceforge/jnlp/security/VariableX509TrustManager.java
index b90bb1b..4f508d8 100644
--- a/netx/net/sourceforge/jnlp/security/VariableX509TrustManager.java
+++ b/netx/net/sourceforge/jnlp/security/VariableX509TrustManager.java
@@ -37,6 +37,9 @@ exception statement from your version.
package net.sourceforge.jnlp.security;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.net.Socket;
import java.security.AccessController;
import java.security.KeyStore;
import java.security.PrivilegedAction;
@@ -47,17 +50,16 @@ import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
+import javax.net.ssl.SSLEngine;
+import javax.net.ssl.SSLSocket;
import javax.net.ssl.TrustManager;
import javax.net.ssl.TrustManagerFactory;
import javax.net.ssl.X509TrustManager;
-import sun.security.util.HostnameChecker;
-import sun.security.validator.ValidatorException;
-
-import com.sun.net.ssl.internal.ssl.X509ExtendedTrustManager;
import net.sourceforge.jnlp.runtime.JNLPRuntime;
-
import net.sourceforge.jnlp.security.SecurityDialogs.AccessType;
+import sun.security.util.HostnameChecker;
+import sun.security.validator.ValidatorException;
/**
* This class implements an X509 Trust Manager. The certificates it trusts are
@@ -65,7 +67,7 @@ import net.sourceforge.jnlp.security.SecurityDialogs.AccessType;
* different certificates that are not in the keystore.
*/
-final public class VariableX509TrustManager extends X509ExtendedTrustManager {
+final public class VariableX509TrustManager {
/** TrustManagers containing trusted CAs */
private X509TrustManager[] caTrustManagers = null;
@@ -164,8 +166,8 @@ final public class VariableX509TrustManager extends X509ExtendedTrustManager {
/**
* Check if client is trusted (no support for custom here, only system/user)
*/
- public void checkClientTrusted(X509Certificate[] chain, String authType,
- String hostName, String algorithm)
+ public void checkTrustClient(X509Certificate[] chain, String authType,
+ String hostName)
throws CertificateException {
boolean trusted = false;
@@ -186,99 +188,125 @@ final public class VariableX509TrustManager extends X509ExtendedTrustManager {
throw savedException;
}
- public void checkClientTrusted(X509Certificate[] chain, String authType)
- throws CertificateException {
- checkClientTrusted(chain, authType, null, null);
- }
-
- public void checkServerTrusted(X509Certificate[] chain, String authType,
- String hostName, String algorithm)
- throws CertificateException {
- checkServerTrusted(chain, authType, hostName, false);
- }
-
- public void checkServerTrusted(X509Certificate[] chain, String authType)
- throws CertificateException {
- checkServerTrusted(chain, authType, null, null);
- }
-
/**
- * Check if the server is trusted
+ * Check if the server is trusted.
+ *
+ * First, existing stores are checked to see if the certificate is trusted.
+ * Next, if the certificate is not explicitly trusted by the user, a host
+ * name check is performed. The user is them prompted as needed.
*
* @param chain The cert chain
* @param authType The auth type algorithm
- * @param checkOnly Whether to "check only" i.e. no user prompt, or to prompt for permission
+ * @param hostName The expected hostName that the server should have
+ * @param socket The SSLSocket in use (may be null)
+ * @param ending The SSLEngine in use (may be null)
*/
- public synchronized void checkServerTrusted(X509Certificate[] chain,
+ public synchronized void checkTrustServer(X509Certificate[] chain,
String authType, String hostName,
- boolean checkOnly) throws CertificateException {
+ SSLSocket socket, SSLEngine engine) throws CertificateException {
CertificateException ce = null;
boolean trusted = true;
- boolean CNMatched = true;
+ boolean CNMatched = false;
+ // Check trust stores
try {
- checkAllManagers(chain, authType);
+ checkAllManagers(chain, authType, socket, engine);
} catch (CertificateException e) {
trusted = false;
ce = e;
}
// If the certificate is not explicitly trusted, we
- // need to prompt the user
+ // check host match
if (!isExplicitlyTrusted(chain, authType)) {
-
- if (hostName == null) {
- CNMatched = false;
- } else {
+ if (hostName != null) {
try {
HostnameChecker checker = HostnameChecker
.getInstance(HostnameChecker.TYPE_TLS);
- checker.match(hostName, chain[0]); // only need to match @ 0 for
- // CN
+ checker.match(hostName, chain[0]); // only need to match @ 0 for CN
+ CNMatched = true;
} catch (CertificateException e) {
- CNMatched = false;
ce = e;
}
}
+ } else {
+ // If it is explicitly trusted, just return right away.
+ return;
}
+ // If it is (not explicitly trusted) AND
+ // ((it is not in store) OR (there is a host mismatch))
if (!trusted || !CNMatched) {
- if (checkOnly) {
- throw ce;
- } else {
- if (!isTemporarilyUntrusted(chain[0])) {
- boolean b = askUser(chain, authType, trusted, CNMatched, hostName);
-
- if (b) {
- temporarilyTrust(chain[0]);
- } else {
- temporarilyUntrust(chain[0]);
- }
+ if (!isTemporarilyUntrusted(chain[0])) {
+ boolean b = askUser(chain, authType, trusted, CNMatched, hostName);
+
+ if (b) {
+ temporarilyTrust(chain[0]);
+ return;
+ } else {
+ temporarilyUntrust(chain[0]);
}
-
- checkAllManagers(chain, authType);
}
+
+ throw ce;
}
}
/**
- * Check system, user and custom trust manager
+ * Check system, user and custom trust manager.
+ *
+ * This method is intended to work with both, JRE6 and JRE7. If socket
+ * and engine are null, it assumes that the call is for JRE6 (i.e. not
+ * javax.net.ssl.X509ExtendedTrustManager which is Java 7 specific). If
+ * either of those are not null, it will assume that the caTrustManagers
+ * are javax.net.ssl.X509ExtendedTrustManager instances and will
+ * invoke their check methods.
+ *
+ * @param chain The certificate chain
+ * @param authType The authentication type
+ * @param socket the SSLSocket being used for the connection
+ * @param engine the SSLEngine being used for the connection
*/
- private void checkAllManagers(X509Certificate[] chain, String authType) throws CertificateException {
+ private void checkAllManagers(X509Certificate[] chain, String authType, Socket socket, SSLEngine engine) throws CertificateException {
+
// first try CA TrustManagers
boolean trusted = false;
ValidatorException savedException = null;
for (int i = 0; i < caTrustManagers.length; i++) {
try {
- caTrustManagers[i].checkServerTrusted(chain, authType);
+ if (socket == null && engine == null) {
+ caTrustManagers[i].checkServerTrusted(chain, authType);
+ } else {
+
+ try {
+ Class<?> x509ETMClass = Class.forName("javax.net.ssl.X509ExtendedTrustManager");
+ if (engine == null) {
+ Method mcheckServerTrusted = x509ETMClass.getDeclaredMethod("checkServerTrusted", X509Certificate[].class, String.class, Socket.class);
+ mcheckServerTrusted.invoke(caTrustManagers[i], chain, authType, socket);
+ } else {
+ Method mcheckServerTrusted = x509ETMClass.getDeclaredMethod("checkServerTrusted", X509Certificate[].class, String.class, SSLEngine.class);
+ mcheckServerTrusted.invoke(caTrustManagers[i], chain, authType, engine);
+ }
+ } catch (NoSuchMethodException nsme) {
+ throw new ValidatorException(nsme.getMessage());
+ } catch (InvocationTargetException ite) {
+ throw new ValidatorException(ite.getMessage());
+ } catch (IllegalAccessException iae) {
+ throw new ValidatorException(iae.getMessage());
+ } catch (ClassNotFoundException cnfe) {
+ throw new ValidatorException(cnfe.getMessage());
+ }
+ }
+
trusted = true;
break;
} catch (ValidatorException caex) {
savedException = caex;
}
}
+
if (trusted) {
return;
}
@@ -332,7 +360,7 @@ final public class VariableX509TrustManager extends X509ExtendedTrustManager {
return explicitlyTrusted;
}
- public X509Certificate[] getAcceptedIssuers() {
+ protected X509Certificate[] getAcceptedIssuers() {
List<X509Certificate> issuers = new ArrayList<X509Certificate>();
for (int i = 0; i < caTrustManagers.length; i++) {
@@ -394,7 +422,7 @@ final public class VariableX509TrustManager extends X509ExtendedTrustManager {
public Boolean run() {
return SecurityDialogs.showCertWarningDialog(
AccessType.UNVERIFIED, null,
- new HttpsCertVerifier(trustManager, chain, authType,
+ new HttpsCertVerifier(chain, authType,
isTrusted, hostMatched,
hostName));
}
diff --git a/netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK6.java b/netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK6.java
new file mode 100644
index 0000000..517be80
--- /dev/null
+++ b/netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK6.java
@@ -0,0 +1,75 @@
+/* VariableX509TrustManagerJDK6.java
+ Copyright (C) 2012 Red Hat, Inc.
+
+This file is part of IcedTea.
+
+IcedTea is free software; you can redistribute it and/or
+modify it under the terms of the GNU General Public License as published by
+the Free Software Foundation, version 2.
+
+IcedTea is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with IcedTea; see the file COPYING. If not, write to
+the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version.
+*/
+
+package net.sourceforge.jnlp.security;
+
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+
+import com.sun.net.ssl.internal.ssl.X509ExtendedTrustManager;
+
+public class VariableX509TrustManagerJDK6 extends X509ExtendedTrustManager {
+
+ private VariableX509TrustManager vX509TM = VariableX509TrustManager.getInstance();
+
+ @Override
+ public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
+ checkClientTrusted(chain, authType, null, null);
+ }
+
+ @Override
+ public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
+ vX509TM.checkTrustServer(chain, authType, null /* hostname*/, null /* socket */, null /* engine */);
+ }
+
+ @Override
+ public X509Certificate[] getAcceptedIssuers() {
+ return vX509TM.getAcceptedIssuers();
+ }
+
+ @Override
+ public void checkClientTrusted(X509Certificate[] chain, String authType, String hostname, String algorithm) throws CertificateException {
+ vX509TM.checkTrustClient(chain, authType, hostname); // We don't need algorithm, we will always use this for TLS only
+ }
+
+ @Override
+ public void checkServerTrusted(X509Certificate[] chain, String authType, String hostname, String algorithm) throws CertificateException {
+ // We don't need to pass algorithm, we will always use this for TLS only
+ vX509TM.checkTrustServer(chain, authType, hostname, null /* socket */, null /* engine */);
+ }
+
+}
diff --git a/netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK7.java b/netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK7.java
new file mode 100644
index 0000000..6f91c0f
--- /dev/null
+++ b/netx/net/sourceforge/jnlp/security/VariableX509TrustManagerJDK7.java
@@ -0,0 +1,136 @@
+/* VariableX509TrustManagerJDK7.java
+ Copyright (C) 2012 Red Hat, Inc.
+
+This file is part of IcedTea.
+
+IcedTea is free software; you can redistribute it and/or
+modify it under the terms of the GNU General Public License as published by
+the Free Software Foundation, version 2.
+
+IcedTea is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with IcedTea; see the file COPYING. If not, write to
+the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version.
+*/
+
+package net.sourceforge.jnlp.security;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.net.Socket;
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+
+import javax.net.ssl.SSLEngine;
+import javax.net.ssl.SSLSession;
+import javax.net.ssl.SSLSocket;
+import javax.net.ssl.X509ExtendedTrustManager;
+
+public class VariableX509TrustManagerJDK7 extends X509ExtendedTrustManager {
+
+ private VariableX509TrustManager vX509TM = VariableX509TrustManager.getInstance();
+
+ @Override
+ public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
+ vX509TM.checkTrustClient(chain, authType, null /* hostname*/);
+ }
+
+ @Override
+ public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
+ vX509TM.checkTrustServer(chain, authType, null /* hostname*/, null /* socket */, null /* engine */);
+ }
+
+ @Override
+ public X509Certificate[] getAcceptedIssuers() {
+ return vX509TM.getAcceptedIssuers();
+ }
+
+ @Override
+ public void checkClientTrusted(X509Certificate[] chain, String authType, Socket socket) throws CertificateException {
+ checkTrustClient(chain, authType, socket, null);
+ }
+
+ @Override
+ public void checkServerTrusted(X509Certificate[] chain, String authType, Socket socket) throws CertificateException {
+ checkTrustServer(chain, authType, socket, null);
+
+ }
+
+ @Override
+ public void checkClientTrusted(X509Certificate[] chain, String authType, SSLEngine engine) throws CertificateException {
+ checkTrustClient(chain, authType, null, engine);
+ }
+
+ @Override
+ public void checkServerTrusted(X509Certificate[] chain, String authType, SSLEngine engine) throws CertificateException {
+ checkTrustServer(chain, authType, null, engine);
+ }
+
+ /**
+ * Check if the server is trusted
+ *
+ * @param chain The cert chain
+ * @param authType The auth type algorithm
+ * @param socket the SSLSocket, may be null
+ * @param engine the SSLEngine, may be null
+ */
+ private void checkTrustServer(X509Certificate[] chain,
+ String authType, Socket socket,
+ SSLEngine engine) throws CertificateException {
+
+ String hostName = null;
+
+ if (socket != null) {
+ hostName = ((SSLSocket) socket).getHandshakeSession().getPeerHost();
+ } else if (engine != null) {
+ hostName = engine.getHandshakeSession().getPeerHost();
+ }
+
+ vX509TM.checkTrustServer(chain, authType, hostName, (SSLSocket) socket, engine);
+ }
+
+ /**
+ * Check if the client is trusted
+ *
+ * @param chain The cert chain
+ * @param authType The auth type algorithm
+ * @param socket the SSLSocket, if provided
+ * @param engine the SSLEngine, if provided
+ */
+ private void checkTrustClient(X509Certificate[] chain,
+ String authType, Socket socket,
+ SSLEngine engine) throws CertificateException {
+
+ String hostName = null;
+
+ if (socket != null) {
+ hostName = ((SSLSocket) socket).getHandshakeSession().getPeerHost();
+ } else if (engine != null) {
+ hostName = engine.getHandshakeSession().getPeerHost();
+ }
+
+ vX509TM.checkTrustClient(chain, authType, hostName);
+ }
+}