package at.gv.egovernment.moa.id.iaik.pki.jsse; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.net.URL; import java.security.GeneralSecurityException; import java.security.cert.CertificateFactory; import java.security.cert.X509Certificate; import java.util.ArrayList; import java.util.List; import at.gv.egovernment.moa.id.util.MOAIDMessageProvider; import at.gv.egovernment.moa.logging.Logger; import at.gv.egovernment.moa.logging.LoggingContext; import at.gv.egovernment.moa.logging.LoggingContextManager; import iaik.pki.jsse.IAIKX509TrustManager; /** * TrustManager implementation featuring CRL checking (inherited from * IAIKX509TrustManager), plus server-end-SSL-certificate checking. * * @author Paul Ivancsics * @version $Id$ */ public class MOAIDTrustManager extends IAIKX509TrustManager { /** an x509Certificate array containing all accepted server certificates*/ private X509Certificate[] acceptedServerCertificates; /** * Constructor * @param acceptedServerCertificateStoreURL the url leading to the acceptedServer cert store * @throws GeneralSecurityException occurs on security errors * @throws IOException occurs on IO errors */ public MOAIDTrustManager(String acceptedServerCertificateStoreURL) throws IOException, GeneralSecurityException { if (acceptedServerCertificateStoreURL != null) buildAcceptedServerCertificates(acceptedServerCertificateStoreURL); else acceptedServerCertificates = null; } /** * Initializes the LoggingContextManager logging context. * Fixes a bug occuring in the case MOA-SP is called by API. * In this case, IAIKX509TrustManager uses the LogginConfig of MOA-SP. * This method must be called before a MOAIDTrustManager is constructed, * from every thread. */ public static void initializeLoggingContext() { if (LoggingContextManager.getInstance().getLoggingContext() == null) LoggingContextManager.getInstance().setLoggingContext( new LoggingContext(Thread.currentThread().getName())); } /** * Builds an Array of accepted server certificates from an URL, * and stores it in acceptedServerCertificates. * @param acceptedServerCertificateStoreURL file URL pointing to the directory * containing accepted server X509 certificates * @throws GeneralSecurityException on security errors * @throws IOException on any IO errors */ private void buildAcceptedServerCertificates(String acceptedServerCertificateStoreURL) throws IOException, GeneralSecurityException { List certList = new ArrayList(); URL storeURL = new URL(acceptedServerCertificateStoreURL); File storeDir = new File(storeURL.getFile()); // list certificate files in directory File[] certFiles = storeDir.listFiles(); for (int i = 0; i < certFiles.length; i++) { // for each: create an X509Certificate and store it in list File certFile = certFiles[i]; FileInputStream fis = new FileInputStream(certFile.getPath()); CertificateFactory certFact = CertificateFactory.getInstance("X.509"); X509Certificate cert = (X509Certificate)certFact.generateCertificate(fis); fis.close(); certList.add(cert); } // store acceptedServerCertificates acceptedServerCertificates = (X509Certificate[]) certList.toArray(new X509Certificate[0]); } /** * Does additional server-end-SSL-certificate checking. * @see com.sun.net.ssl.X509TrustManager#isServerTrusted(java.security.cert.X509Certificate[]) */ public boolean isServerTrusted(X509Certificate[] certChain) { boolean trusted = super.isServerTrusted(certChain); if (! trusted || acceptedServerCertificates == null) return trusted; else { // check server-end-SSL-certificate with acceptedServerCertificates X509Certificate serverCert = certChain[0]; for (int i = 0; i < acceptedServerCertificates.length; i++) { X509Certificate acceptedServerCert = acceptedServerCertificates[i]; if (serverCert.equals(acceptedServerCert)) return true; } Logger.warn(MOAIDMessageProvider.getInstance().getMessage("ssl.01", null)); return false; } } /** * In rare cases, this method is being called although it should not be. * @see com.sun.net.ssl.X509TrustManager#isClientTrusted(X509Certificate[]) */ public boolean isClientTrusted(java.security.cert.X509Certificate arg0[]) { return true; } }