Java tutorial
/* ***** BEGIN LICENSE BLOCK ******************************************** * Version: EUPL 1.1/GPL 3.0 * * The contents of this file are subject to the EUPL, Version 1.1 or * - as soon they will be approved by the European Commission - * subsequent versions of the EUPL (the "Licence"); * you may not use this file except in compliance with * the License. You may obtain a copy of the License at * http://www.osor.eu/eupl/european-union-public-licence-eupl-v.1.1 * * Software distributed under the License is distributed on an "AS IS" basis, * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License * for the specific language governing rights and limitations under the * License. * * The Original Code is /oxsit-custom_it/src/com/yacme/ext/oxsit/cust_it/security/crl/RootsVerifier.java. * * The Initial Developers of the Original Code are * Giuseppe Castagno giuseppe.castagno@acca-esse.it * Roberto Resoli resoli@osor.eu * * Portions created by the Initial Developers are Copyright (C) 2009-2011 * the Initial Developers. All Rights Reserved. * * This code is partly derived from * it.infocamere.freesigner.crl.CertificationAuthorities class in freesigner * adapted to be used in OOo UNO environment * Copyright (c) 2005 Francesco Cendron - Infocamere * Contributor(s): * * Alternatively, the contents of this file may be used under the terms of * either the GNU General Public License Version 3 or later (the "GPL") * in which case the provisions of the GPL are applicable instead * of those above. If you wish to allow use of your version of this file only * under the terms of the GPL, and not to allow others to * use your version of this file under the terms of the EUPL, indicate your * decision by deleting the provisions above and replace them with the notice * and other provisions required by the GPL. If you do not delete * the provisions above, a recipient may use your version of this file under * the terms of any one of the EUPL, or the GPL. * * ***** END LICENSE BLOCK ******************************************** */ package com.yacme.ext.oxsit.cust_it.security.crl; import java.io.ByteArrayOutputStream; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.net.URISyntaxException; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; import java.security.NoSuchProviderException; import java.security.Provider; import java.security.Security; import java.security.cert.CertStore; import java.security.cert.CertStoreException; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; import java.util.Collection; import java.util.Iterator; import org.bouncycastle.asn1.cms.Attribute; import org.bouncycastle.asn1.cms.AttributeTable; import org.bouncycastle.asn1.cms.CMSAttributes; import org.bouncycastle.asn1.cms.SignerInfo; import org.bouncycastle.cms.CMSException; import org.bouncycastle.cms.CMSSignedData; import org.bouncycastle.cms.SignerInformation; import org.bouncycastle.cms.SignerInformationStore; import com.sun.star.frame.XFrame; import com.sun.star.lang.XMultiComponentFactory; import com.sun.star.script.BasicErrorException; import com.sun.star.uno.Exception; import com.sun.star.uno.XComponentContext; import com.yacme.ext.oxsit.Helpers; import com.yacme.ext.oxsit.cust_it.ConstantCustomIT; import com.yacme.ext.oxsit.logging.DynamicLoggerDialog; import com.yacme.ext.oxsit.ooo.registry.MessageConfigurationAccess; import com.yacme.ext.oxsit.ooo.ui.ControlDims; import com.yacme.ext.oxsit.ooo.ui.DialogRootVerify; public class RootsVerifier { private static RootsVerifier instance = null; private String CNIPADir = null; private String CAFilePath = null; private String CNIPACACertFilePath = null; private byte[] userApprovedFingerprint = null; private DynamicLoggerDialog m_aLogger; private XComponentContext m_xCC; private XFrame m_xFrame; private XMultiComponentFactory m_xMCF; private X509Certificate m_aRootSignatureCert; public RootsVerifier(XFrame _xFrame, XComponentContext _xContext) { // conf = Configuration.getInstance(); m_xCC = _xContext; m_xFrame = _xFrame; m_xMCF = m_xCC.getServiceManager(); m_aLogger = new DynamicLoggerDialog(this, _xContext); // m_aLogger.enableLogging(); init(); userApprovedFingerprint = getFingerprint(); } /* public static RootsVerifier getInstance(){ if(instance == null) { instance = new RootsVerifier(); } return instance; }*/ //beppec56: //FIXME needs some adjusting on the location where the //file will be, or automatic determination of the file present there. private void init() { //grab the extension internal path //the file is in a special directory // when checking for update, the file will be copied in a local user directory //we need to know what to do when the file doesn't exist or we need to update it from Internet //for the type being is absolute, will be given from configuration ? Or //do we devise a method to get it automatically? String _originPath; try { _originPath = Helpers.getExtensionInstallationSystemPath(m_xCC); this.CAFilePath = _originPath + System.getProperty("file.separator") + "ca-list-signed-p7m-it" + //fixed path, the directory containing the current root zip file System.getProperty("file.separator") + ConstantCustomIT.m_sCA_LIST_SIGNED_FILE; } catch (URISyntaxException e) { m_aLogger.severe(e); } catch (IOException e) { m_aLogger.severe(e); } } //FIXME, add certificate revocation check for CNIPA cert // private byte[] getFingerprint() { byte[] fingerprint = null; String sDispDate = ""; CertStore certs = null; CMSSignedData CNIPA_CMS = null; try { CNIPA_CMS = getCNIPA_CMS(); Provider p = new org.bouncycastle.jce.provider.BouncyCastleProvider(); if (Security.getProvider(p.getName()) == null) Security.addProvider(p); try { certs = CNIPA_CMS.getCertificatesAndCRLs("Collection", "BC"); } catch (CMSException ex2) { m_aLogger.severe("getFingerprint", "Errore nel CMS delle RootCA", ex2); } catch (NoSuchProviderException ex2) { m_aLogger.severe("getFingerprint", "Non esiste il provider del servizio", ex2); } catch (NoSuchAlgorithmException ex2) { m_aLogger.severe("getFingerprint", "Errore nell'algoritmo", ex2); } if (certs == null) m_aLogger.severe("getFingerprint", "No certs for CNIPA signature!"); else { SignerInformationStore signers = CNIPA_CMS.getSignerInfos(); Collection<SignerInformation> c = signers.getSigners(); if (c.size() != 1) { m_aLogger.severe("getFingerprint", "There is not exactly one signer!"); } else { Iterator<SignerInformation> it = c.iterator(); if (it.hasNext()) { SignerInformation signer = it.next(); //grab date AttributeTable att = signer.getSignedAttributes(); if (att.get(CMSAttributes.signingTime) == null) { //no date m_aLogger.info("getFingerprint()", "A date is NOT present on CA root archive signature !"); } else { Attribute atime = att.get(CMSAttributes.signingTime); //date present //@FIXME get date in a more clean way String sdate = atime.getAttrValues().toString(); sDispDate = "20" + sdate.substring(1, 3) + "-" + sdate.substring(3, 5) + "-" + sdate.substring(5, 7) + " " + sdate.substring(7, 9) + ":" + sdate.substring(9, 11) + ":" + sdate.substring(11, 13) + " UTC"; m_aLogger.debug("getFingerprint()", "A date is present: " + sDispDate); } Collection<?> certCollection = null; try { certCollection = certs.getCertificates(signer.getSID()); if (certCollection.size() == 1) { m_aRootSignatureCert = (X509Certificate) certCollection.toArray()[0]; fingerprint = getCertFingerprint(m_aRootSignatureCert); } else { //print an error? m_aLogger.severe("getFingerprint", "There is not exactly one certificate for this signer!"); } } catch (CertStoreException ex1) { //print an error? m_aLogger.severe("Errore nel CertStore", ex1); } } } } //grab the localized text to display String _format = "id_root_verify_message"; String _title = "id_root_verify_message_title"; String _no_fp = "id_root_verify_message_ko"; MessageConfigurationAccess m_aRegAcc = null; m_aRegAcc = new MessageConfigurationAccess(m_xCC, m_xMCF); try { _title = m_aRegAcc.getStringFromRegistry(_title); _format = m_aRegAcc.getStringFromRegistry(_format); _no_fp = m_aRegAcc.getStringFromRegistry(_no_fp); } catch (Exception e) { m_aLogger.severe(e); } m_aRegAcc.dispose(); String theFingerprint = ((fingerprint == null) ? _no_fp : formatAsGUString(fingerprint)); String _mex = String.format(_format, sDispDate, theFingerprint); DialogRootVerify aDialog1 = new DialogRootVerify(m_xFrame, m_xCC, m_xMCF, _mex); // DialogRootVerify aDialog1 = new DialogRootVerify( null, m_xCC, m_xMCF,_mex ); //PosX and PosY should be obtained from the parent window (in this case the frame) //the problem is that we get the pixel, but we need the logical pixel, so for now it doesn't work... int BiasX = ControlDims.RSC_SP_DLG_INNERBORDER_LEFT; int BiasY = ControlDims.RSC_SP_DLG_INNERBORDER_TOP; short ret; try { aDialog1.initialize(BiasX, BiasY); ret = aDialog1.executeDialog(); // ret = 0: NO // ret = 1: Yes if (ret == 1) { return fingerprint; } } catch (BasicErrorException e) { m_aLogger.severe(e); } catch (Exception e) { m_aLogger.severe(e); } } catch (FileNotFoundException ex) { m_aLogger.severe("getFingerprint", "Errore nella lettura del file delle RootCA: ", ex); } catch (CMSException e) { m_aLogger.severe("getFingerprint", "Errore nel CMS delle RootCA: ", e); } return null; } public String formatAsGUString(byte[] bytes) { int n, x; String w = new String(); String s = new String(); boolean separe = false; for (n = 0; n < bytes.length; n++) { x = (int) (0x000000FF & bytes[n]); w = Integer.toHexString(x).toUpperCase(); if (w.length() == 1) w = "0" + w; // Group 2 consecutive bytes separe = (((n + 1) % 2) == 0) && (n + 1 != bytes.length); s = s + w + (separe ? " " : ""); } // for return s; } private CMSSignedData getCNIPA_CMS() throws CMSException, FileNotFoundException { FileInputStream is = null; is = new FileInputStream(CAFilePath); return new CMSSignedData(is); } private byte[] getCertFingerprint(X509Certificate cert) { MessageDigest md; byte[] fingerprint = null; try { md = MessageDigest.getInstance("SHA1"); md.update(cert.getEncoded()); fingerprint = md.digest(); } catch (NoSuchAlgorithmException e) { m_aLogger.severe(e); } catch (CertificateException e) { m_aLogger.severe(e); } return fingerprint; } public byte[] getUserApprovedFingerprint() { return userApprovedFingerprint; } /** * @return the m_aRootSignatureCert */ public X509Certificate getRootSignatureCert() { return m_aRootSignatureCert; } }