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;
}
}