You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@poi.apache.org by ki...@apache.org on 2014/08/10 20:25:12 UTC

svn commit: r1617141 [3/5] - in /poi/branches/xml_signature: ./ src/java/org/apache/poi/poifs/crypt/ src/ooxml/java/org/apache/poi/openxml4j/opc/ src/ooxml/java/org/apache/poi/openxml4j/opc/internal/ src/ooxml/java/org/apache/poi/poifs/crypt/dsig/ src/...

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RelationshipTransformService.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RelationshipTransformService.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RelationshipTransformService.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RelationshipTransformService.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,249 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.security.InvalidAlgorithmParameterException;
+import java.security.Provider;
+import java.security.Security;
+import java.security.spec.AlgorithmParameterSpec;
+import java.util.Comparator;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+
+import javax.xml.crypto.Data;
+import javax.xml.crypto.MarshalException;
+import javax.xml.crypto.OctetStreamData;
+import javax.xml.crypto.XMLCryptoContext;
+import javax.xml.crypto.XMLStructure;
+import javax.xml.crypto.dom.DOMStructure;
+import javax.xml.crypto.dsig.TransformException;
+import javax.xml.crypto.dsig.TransformService;
+import javax.xml.crypto.dsig.spec.TransformParameterSpec;
+
+import org.apache.poi.util.POILogFactory;
+import org.apache.poi.util.POILogger;
+import org.apache.poi.util.XmlSort;
+import org.apache.xmlbeans.XmlCursor;
+import org.apache.xmlbeans.XmlException;
+import org.apache.xmlbeans.XmlObject;
+import org.apache.xmlbeans.XmlOptions;
+import org.openxmlformats.schemas.xpackage.x2006.digitalSignature.RelationshipReferenceDocument;
+import org.openxmlformats.schemas.xpackage.x2006.relationships.CTRelationship;
+import org.openxmlformats.schemas.xpackage.x2006.relationships.CTRelationships;
+import org.openxmlformats.schemas.xpackage.x2006.relationships.RelationshipsDocument;
+import org.openxmlformats.schemas.xpackage.x2006.relationships.STTargetMode;
+import org.w3.x2000.x09.xmldsig.TransformDocument;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.Node;
+
+/**
+ * JSR105 implementation of the RelationshipTransform transformation.
+ * 
+ * <p>
+ * Specs: http://openiso.org/Ecma/376/Part2/12.2.4#26
+ * </p>
+ */
+public class RelationshipTransformService extends TransformService {
+
+    public static final String TRANSFORM_URI = "http://schemas.openxmlformats.org/package/2006/RelationshipTransform";
+
+    private final List<String> sourceIds;
+
+    private static final POILogger LOG = POILogFactory.getLogger(RelationshipTransformService.class);
+    
+    /**
+     * Relationship Transform parameter specification class.
+     */
+    public static class RelationshipTransformParameterSpec implements TransformParameterSpec {
+        List<String> sourceIds = new LinkedList<String>();
+        public void addRelationshipReference(String relationshipId) {
+            sourceIds.add(relationshipId);
+        }
+        public boolean hasSourceIds() {
+            return !sourceIds.isEmpty();
+        }
+    }
+    
+    
+    public RelationshipTransformService() {
+        super();
+        LOG.log(POILogger.DEBUG, "constructor");
+        this.sourceIds = new LinkedList<String>();
+    }
+
+    /**
+     * Register the provider for this TransformService
+     * 
+     * @see javax.xml.crypto.dsig.TransformService
+     */
+    public static synchronized void registerDsigProvider() {
+        // the xml signature classes will try to find a special TransformerService,
+        // which is ofcourse unknown to JCE before ...
+        final String dsigProvider = "POIXmlDsigProvider";
+        if (Security.getProperty(dsigProvider) == null) {
+            Provider p = new Provider(dsigProvider, 1.0, dsigProvider){
+                static final long serialVersionUID = 1L;
+            };
+            p.put("TransformService." + TRANSFORM_URI, RelationshipTransformService.class.getName());
+            p.put("TransformService." + TRANSFORM_URI + " MechanismType", "DOM");
+            Security.addProvider(p);
+        }
+    }
+    
+    
+    @Override
+    public void init(TransformParameterSpec params) throws InvalidAlgorithmParameterException {
+        LOG.log(POILogger.DEBUG, "init(params)");
+        if (!(params instanceof RelationshipTransformParameterSpec)) {
+            throw new InvalidAlgorithmParameterException();
+        }
+        RelationshipTransformParameterSpec relParams = (RelationshipTransformParameterSpec) params;
+        for (String sourceId : relParams.sourceIds) {
+            this.sourceIds.add(sourceId);
+        }
+    }
+
+    @Override
+    public void init(XMLStructure parent, XMLCryptoContext context) throws InvalidAlgorithmParameterException {
+        LOG.log(POILogger.DEBUG, "init(parent,context)");
+        LOG.log(POILogger.DEBUG, "parent java type: " + parent.getClass().getName());
+        DOMStructure domParent = (DOMStructure) parent;
+        Node parentNode = domParent.getNode();
+        
+        try {
+            TransformDocument transDoc = TransformDocument.Factory.parse(parentNode);
+            XmlObject xoList[] = transDoc.getTransform().selectChildren(RelationshipReferenceDocument.type.getDocumentElementName());
+            if (xoList.length == 0) {
+                LOG.log(POILogger.WARN, "no RelationshipReference/@SourceId parameters present");
+            }
+            for (XmlObject xo : xoList) {
+                RelationshipReferenceDocument refDoc =
+                    RelationshipReferenceDocument.Factory.parse(xo.getDomNode());
+                String sourceId = refDoc.getRelationshipReference().getSourceId();
+                LOG.log(POILogger.DEBUG, "sourceId: ", sourceId);
+                this.sourceIds.add(sourceId);
+            }
+        } catch (XmlException e) {
+            throw new InvalidAlgorithmParameterException(e);
+        }
+    }
+
+    @Override
+    public void marshalParams(XMLStructure parent, XMLCryptoContext context) throws MarshalException {
+        LOG.log(POILogger.DEBUG, "marshallParams(parent,context)");
+        DOMStructure domParent = (DOMStructure) parent;
+        Element parentNode = (Element)domParent.getNode();
+        // parentNode.setAttributeNS(Constants.NamespaceSpecNS, "xmlns:mdssi", DIGITAL_SIGNATURE);
+        Document doc = parentNode.getOwnerDocument();
+        
+        for (String sourceId : this.sourceIds) {
+            RelationshipReferenceDocument relRef = RelationshipReferenceDocument.Factory.newInstance();
+            relRef.addNewRelationshipReference().setSourceId(sourceId);
+            Node n = relRef.getRelationshipReference().getDomNode();
+            // TODO: is there a more elegant way to do this?
+            n.setPrefix("mdssi");
+            n = doc.importNode(n, true);
+            parentNode.appendChild(n);
+        }
+    }
+    
+    public AlgorithmParameterSpec getParameterSpec() {
+        LOG.log(POILogger.DEBUG, "getParameterSpec");
+        return null;
+    }
+
+    public Data transform(Data data, XMLCryptoContext context) throws TransformException {
+        LOG.log(POILogger.DEBUG, "transform(data,context)");
+        LOG.log(POILogger.DEBUG, "data java type: " + data.getClass().getName());
+        OctetStreamData octetStreamData = (OctetStreamData) data;
+        LOG.log(POILogger.DEBUG, "URI: " + octetStreamData.getURI());
+        InputStream octetStream = octetStreamData.getOctetStream();
+        
+        RelationshipsDocument relDoc;
+        try {
+            relDoc = RelationshipsDocument.Factory.parse(octetStream);
+        } catch (Exception e) {
+            throw new TransformException(e.getMessage(), e);
+        }
+        LOG.log(POILogger.DEBUG, "relationships document", relDoc);
+        
+        CTRelationships rels = relDoc.getRelationships();
+        List<CTRelationship> relList = rels.getRelationshipList();
+        Iterator<CTRelationship> relIter = rels.getRelationshipList().iterator();
+        while (relIter.hasNext()) {
+            CTRelationship rel = relIter.next();
+            /*
+             * See: ISO/IEC 29500-2:2008(E) - 13.2.4.24 Relationships Transform
+             * Algorithm.
+             */
+            if (!this.sourceIds.contains(rel.getId())) {
+                LOG.log(POILogger.DEBUG, "removing element: " + rel.getId());
+                relIter.remove();
+            } else {
+                if (!rel.isSetTargetMode()) {
+                    rel.setTargetMode(STTargetMode.INTERNAL);
+                }
+            }
+        }
+        
+        // TODO: remove non element nodes ???
+        LOG.log(POILogger.DEBUG, "# Relationship elements", relList.size());
+        
+        XmlSort.sort(rels, new Comparator<XmlCursor>(){
+            public int compare(XmlCursor c1, XmlCursor c2) {
+                String id1 = ((CTRelationship)c1.getObject()).getId();
+                String id2 = ((CTRelationship)c2.getObject()).getId();
+                return id1.compareTo(id2);
+            }
+        });
+
+        try {
+            ByteArrayOutputStream bos = new ByteArrayOutputStream();
+            XmlOptions xo = new XmlOptions();
+            xo.setSaveNoXmlDecl();
+            relDoc.save(bos, xo);
+            return new OctetStreamData(new ByteArrayInputStream(bos.toByteArray()));
+        } catch (IOException e) {
+            throw new TransformException(e.getMessage(), e);
+        }
+    }
+
+    public Data transform(Data data, XMLCryptoContext context, OutputStream os) throws TransformException {
+        LOG.log(POILogger.DEBUG, "transform(data,context,os)");
+        return null;
+    }
+
+    public boolean isFeatureSupported(String feature) {
+        LOG.log(POILogger.DEBUG, "isFeatureSupported(feature)");
+        return false;
+    }
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationData.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationData.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationData.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationData.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,131 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+import java.security.cert.CRLException;
+import java.security.cert.X509CRL;
+import java.util.LinkedList;
+import java.util.List;
+
+/**
+ * Container class for PKI revocation data.
+ * 
+ * @author Frank Cornelis
+ * 
+ */
+public class RevocationData {
+
+    private final List<byte[]> crls;
+
+    private final List<byte[]> ocsps;
+
+    /**
+     * Default constructor.
+     */
+    public RevocationData() {
+        this.crls = new LinkedList<byte[]>();
+        this.ocsps = new LinkedList<byte[]>();
+    }
+
+    /**
+     * Adds a CRL to this revocation data set.
+     * 
+     * @param encodedCrl
+     */
+    public void addCRL(byte[] encodedCrl) {
+        this.crls.add(encodedCrl);
+    }
+
+    /**
+     * Adds a CRL to this revocation data set.
+     * 
+     * @param crl
+     */
+    public void addCRL(X509CRL crl) {
+        byte[] encodedCrl;
+        try {
+            encodedCrl = crl.getEncoded();
+        } catch (CRLException e) {
+            throw new IllegalArgumentException("CRL coding error: "
+                    + e.getMessage(), e);
+        }
+        addCRL(encodedCrl);
+    }
+
+    /**
+     * Adds an OCSP response to this revocation data set.
+     * 
+     * @param encodedOcsp
+     */
+    public void addOCSP(byte[] encodedOcsp) {
+        this.ocsps.add(encodedOcsp);
+    }
+
+    /**
+     * Gives back a list of all CRLs.
+     * 
+     * @return
+     */
+    public List<byte[]> getCRLs() {
+        return this.crls;
+    }
+
+    /**
+     * Gives back a list of all OCSP responses.
+     * 
+     * @return
+     */
+    public List<byte[]> getOCSPs() {
+        return this.ocsps;
+    }
+
+    /**
+     * Returns <code>true</code> if this revocation data set holds OCSP
+     * responses.
+     * 
+     * @return
+     */
+    public boolean hasOCSPs() {
+        return false == this.ocsps.isEmpty();
+    }
+
+    /**
+     * Returns <code>true</code> if this revocation data set holds CRLs.
+     * 
+     * @return
+     */
+    public boolean hasCRLs() {
+        return false == this.crls.isEmpty();
+    }
+
+    /**
+     * Returns <code>true</code> if this revocation data is not empty.
+     * 
+     * @return
+     */
+    public boolean hasRevocationDataEntries() {
+        return hasOCSPs() || hasCRLs();
+    }
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationDataService.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationDataService.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationDataService.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/RevocationDataService.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,47 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+import java.security.cert.X509Certificate;
+import java.util.List;
+
+/**
+ * Interface for a service that retrieves revocation data about some given
+ * certificate chain.
+ * 
+ * @author Frank Cornelis
+ * 
+ */
+public interface RevocationDataService {
+
+    /**
+     * Gives back the revocation data corresponding with the given certificate
+     * chain.
+     * 
+     * @param certificateChain
+     * @return
+     */
+    RevocationData getRevocationData(List<X509Certificate> certificateChain);
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/SignatureService.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/SignatureService.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/SignatureService.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/SignatureService.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,101 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+import java.io.IOException;
+import java.security.NoSuchAlgorithmException;
+import java.security.cert.X509Certificate;
+import java.util.List;
+
+import org.apache.poi.poifs.crypt.dsig.CertificateSecurityException;
+import org.apache.poi.poifs.crypt.dsig.ExpiredCertificateSecurityException;
+import org.apache.poi.poifs.crypt.dsig.RevokedCertificateSecurityException;
+import org.apache.poi.poifs.crypt.dsig.TrustCertificateSecurityException;
+import org.apache.poi.poifs.crypt.dsig.spi.AddressDTO;
+import org.apache.poi.poifs.crypt.dsig.spi.DigestInfo;
+import org.apache.poi.poifs.crypt.dsig.spi.IdentityDTO;
+
+/**
+ * Interface for signature service component.
+ * 
+ * @author Frank Cornelis
+ * 
+ */
+public interface SignatureService {
+
+    /**
+     * Gives back the digest algorithm to be used for construction of the digest
+     * infos of the preSign method. Return a digest algorithm here if you want
+     * to let the client sign some locally stored files. Return
+     * <code>null</code> if no pre-sign digest infos are required.
+     * 
+     * @return the digest algorithm to be used when digesting local files.
+     * @see #preSign(List, List)
+     */
+    String getFilesDigestAlgorithm();
+
+    /**
+     * Pre-sign callback method. Depending on the configuration some parameters
+     * are passed. The returned value will be signed by the eID Applet.
+     * 
+     * <p>
+     * TODO: service must be able to throw some exception on failure.
+     * </p>
+     * 
+     * @param digestInfos
+     *            the optional list of digest infos.
+     * @param signingCertificateChain
+     *            the optional list of certificates.
+     * @param identity
+     *            the optional identity.
+     * @param address
+     *            the optional identity address.
+     * @param photo
+     *            the optional identity photo.
+     * @param timestamp
+     *            the optional timestamp, defaults to now
+     * @return the digest to be signed.
+     * @throws NoSuchAlgorithmException
+     */
+    DigestInfo preSign(List<DigestInfo> digestInfos,
+            List<X509Certificate> signingCertificateChain,
+            IdentityDTO identity, AddressDTO address, byte[] photo)
+            throws NoSuchAlgorithmException;
+
+    /**
+     * Post-sign callback method. Received the signature value. Depending on the
+     * configuration the signing certificate chain is also obtained.
+     * 
+     * @param signatureValue
+     * @param signingCertificateChain
+     *            the optional chain of signing certificates.
+     */
+    void postSign(byte[] signatureValue,
+            List<X509Certificate> signingCertificateChain)
+            throws ExpiredCertificateSecurityException,
+            RevokedCertificateSecurityException,
+            TrustCertificateSecurityException, CertificateSecurityException,
+            SecurityException, IOException;
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TSPTimeStampService.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TSPTimeStampService.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TSPTimeStampService.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TSPTimeStampService.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,392 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.OutputStream;
+import java.math.BigInteger;
+import java.net.HttpURLConnection;
+import java.net.InetSocketAddress;
+import java.net.Proxy;
+import java.net.URL;
+import java.nio.charset.Charset;
+import java.security.MessageDigest;
+import java.security.SecureRandom;
+import java.security.cert.Certificate;
+import java.security.cert.X509Certificate;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+
+import javax.security.auth.x500.X500Principal;
+import javax.xml.bind.DatatypeConverter;
+
+import org.apache.commons.codec.binary.Hex;
+import org.apache.poi.poifs.crypt.CryptoFunctions;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.ASN1InputStreamIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.ASN1OctetStringIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.AuthorityKeyIdentifierIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.BcDigestCalculatorProviderIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.BcRSASignerInfoVerifierBuilderIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.DEROctetStringIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.DefaultDigestAlgorithmIdentifierFinderIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.PKIFailureInfoIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.SignerIdIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.SignerInformationVerifierIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.SubjectKeyIdentifierIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.TimeStampRequestGeneratorIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.TimeStampRequestIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.TimeStampResponseIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.TimeStampTokenIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.X509CertificateHolderIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxy;
+import org.apache.poi.util.IOUtils;
+import org.apache.poi.util.POILogFactory;
+import org.apache.poi.util.POILogger;
+
+/**
+ * A TSP time-stamp service implementation.
+ * 
+ * @author Frank Cornelis
+ * 
+ */
+public class TSPTimeStampService implements TimeStampService {
+
+    private static final POILogger LOG = POILogFactory.getLogger(TSPTimeStampService.class);
+
+    static {
+        CryptoFunctions.registerBouncyCastle();
+    }
+
+    public static final String DEFAULT_USER_AGENT = "eID Applet Service TSP Client";
+
+    private final String tspServiceUrl;
+
+    private String requestPolicy;
+
+    private final String userAgent;
+
+    private final TimeStampServiceValidator validator;
+
+    private String username;
+
+    private String password;
+
+    private String proxyHost;
+
+    private int proxyPort;
+
+    private String digestAlgo;
+
+    private String digestAlgoOid;
+
+    public TSPTimeStampService(String tspServiceUrl,
+            TimeStampServiceValidator validator) {
+        this(tspServiceUrl, validator, null, null);
+    }
+
+    /**
+     * Main constructor.
+     * 
+     * @param tspServiceUrl
+     *            the URL of the TSP service.
+     * @param validator
+     *            the trust validator used to validate incoming TSP response
+     *            signatures.
+     * @param requestPolicy
+     *            the optional TSP request policy.
+     * @param userAgent
+     *            the optional User-Agent TSP request header value.
+     */
+    public TSPTimeStampService(String tspServiceUrl,
+            TimeStampServiceValidator validator, String requestPolicy,
+            String userAgent) {
+        if (null == tspServiceUrl) {
+            throw new IllegalArgumentException("TSP service URL required");
+        }
+        this.tspServiceUrl = tspServiceUrl;
+
+        if (null == validator) {
+            throw new IllegalArgumentException("TSP validator required");
+        }
+        this.validator = validator;
+
+        this.requestPolicy = requestPolicy;
+
+        if (null != userAgent) {
+            this.userAgent = userAgent;
+        } else {
+            this.userAgent = DEFAULT_USER_AGENT;
+        }
+
+        this.digestAlgo = "SHA-1";
+        this.digestAlgoOid = "1.3.14.3.2.26";
+    }
+
+    /**
+     * Sets the request policy OID.
+     * 
+     * @param policyOid
+     */
+    public void setRequestPolicy(String policyOid) {
+        this.requestPolicy = policyOid;
+    }
+
+    /**
+     * Sets the credentials used in case the TSP service requires
+     * authentication.
+     * 
+     * @param username
+     * @param password
+     */
+    public void setAuthenticationCredentials(String username, String password) {
+        this.username = username;
+        this.password = password;
+    }
+
+    /**
+     * Resets the authentication credentials.
+     */
+    public void resetAuthenticationCredentials() {
+        this.username = null;
+        this.password = null;
+    }
+
+    /**
+     * Sets the digest algorithm used for time-stamping data. Example value:
+     * "SHA-1".
+     * 
+     * @param digestAlgo
+     */
+    public void setDigestAlgo(String digestAlgo) {
+        if ("SHA-1".equals(digestAlgo)) {
+            this.digestAlgoOid = "1.3.14.3.2.26";
+        } else if ("SHA-256".equals(digestAlgo)) {
+            this.digestAlgoOid = "2.16.840.1.101.3.4.2.1";
+        } else if ("SHA-384".equals(digestAlgo)) {
+            this.digestAlgoOid = "2.16.840.1.101.3.4.2.2";
+        } else if ("SHA-512".equals(digestAlgo)) {
+            this.digestAlgoOid = "2.16.840.1.101.3.4.2.3";
+        } else {
+            throw new IllegalArgumentException("unsupported digest algo: " + digestAlgo);
+        }
+
+        this.digestAlgo = digestAlgo;
+    }
+
+    /**
+     * Configures the HTTP proxy settings to be used to connect to the TSP
+     * service.
+     * 
+     * @param proxyHost
+     * @param proxyPort
+     */
+    public void setProxy(String proxyHost, int proxyPort) {
+        this.proxyHost = proxyHost;
+        this.proxyPort = proxyPort;
+    }
+
+    /**
+     * Resets the HTTP proxy settings.
+     */
+    public void resetProxy() {
+        this.proxyHost = null;
+        this.proxyPort = 0;
+    }
+
+    public byte[] timeStamp(byte[] data, RevocationData revocationData)
+            throws Exception {
+        // digest the message
+        MessageDigest messageDigest = MessageDigest
+                .getInstance(this.digestAlgo);
+        byte[] digest = messageDigest.digest(data);
+
+        // generate the TSP request
+        BigInteger nonce = new BigInteger(128, new SecureRandom());
+        TimeStampRequestGeneratorIf requestGenerator = HorribleProxy.newProxy(TimeStampRequestGeneratorIf.class);
+        requestGenerator.setCertReq(true);
+        if (null != this.requestPolicy) {
+            requestGenerator.setReqPolicy(this.requestPolicy);
+        }
+        TimeStampRequestIf request = requestGenerator.generate(this.digestAlgoOid, digest, nonce);
+        byte[] encodedRequest = request.getEncoded();
+
+        // create the HTTP POST request
+        Proxy proxy = (this.proxyHost != null)
+            ? new Proxy(Proxy.Type.HTTP, new InetSocketAddress(this.proxyHost, this.proxyPort))
+            : Proxy.NO_PROXY;
+        HttpURLConnection huc = (HttpURLConnection)new URL(this.tspServiceUrl).openConnection(proxy);
+        
+        if (null != this.username) {
+            String userPassword = this.username + ":" + this.password;
+            String encoding = DatatypeConverter.printBase64Binary(userPassword.getBytes(Charset.forName("iso-8859-1")));
+            huc.setRequestProperty("Authorization", "Basic " + encoding);
+        }
+
+        huc.setDoOutput(true); // also sets method to POST.
+        huc.setRequestProperty("User-Agent", this.userAgent);
+        huc.setRequestProperty("Content-Type", "application/timestamp-query;charset=ISO-8859-1");
+        
+        OutputStream hucOut = huc.getOutputStream();
+        hucOut.write(encodedRequest);
+        
+        // invoke TSP service
+        huc.connect();
+        
+        int statusCode = huc.getResponseCode();
+        if (statusCode != 200) {
+            LOG.log(POILogger.ERROR, "Error contacting TSP server ", this.tspServiceUrl);
+            throw new Exception("Error contacting TSP server " + this.tspServiceUrl);
+        }
+
+        // HTTP input validation
+        String contentType = huc.getHeaderField("Content-Type");
+        if (null == contentType) {
+            throw new RuntimeException("missing Content-Type header");
+        }
+        
+        ByteArrayOutputStream bos = new ByteArrayOutputStream();
+        IOUtils.copy(huc.getInputStream(), bos);
+        LOG.log(POILogger.DEBUG, "response content: ", bos.toString());
+        
+        if (!contentType.startsWith("application/timestamp-reply")) {
+            throw new RuntimeException("invalid Content-Type: " + contentType);
+        }
+        
+        if (bos.size() == 0) {
+            throw new RuntimeException("Content-Length is zero");
+        }
+
+        // TSP response parsing and validation
+        TimeStampResponseIf timeStampResponse = HorribleProxy.newProxy(TimeStampResponseIf.class, bos.toByteArray());
+        timeStampResponse.validate(request);
+
+        if (0 != timeStampResponse.getStatus()) {
+            LOG.log(POILogger.DEBUG, "status: " + timeStampResponse.getStatus());
+            LOG.log(POILogger.DEBUG, "status string: " + timeStampResponse.getStatusString());
+            PKIFailureInfoIf failInfo = timeStampResponse.getFailInfo();
+            if (null != failInfo) {
+                LOG.log(POILogger.DEBUG, "fail info int value: " + failInfo.intValue());
+                if (/*PKIFailureInfo.unacceptedPolicy*/(1 << 8) == failInfo.intValue()) {
+                    LOG.log(POILogger.DEBUG, "unaccepted policy");
+                }
+            }
+            throw new RuntimeException("timestamp response status != 0: "
+                    + timeStampResponse.getStatus());
+        }
+        TimeStampTokenIf timeStampToken = timeStampResponse.getTimeStampToken();
+        SignerIdIf signerId = timeStampToken.getSID();
+        BigInteger signerCertSerialNumber = signerId.getSerialNumber();
+        X500Principal signerCertIssuer = signerId.getIssuer();
+        LOG.log(POILogger.DEBUG, "signer cert serial number: " + signerCertSerialNumber);
+        LOG.log(POILogger.DEBUG, "signer cert issuer: " + signerCertIssuer);
+
+        // TSP signer certificates retrieval
+        Collection<Certificate> certificates = timeStampToken.getCertificates().getMatches(null);
+        
+        X509Certificate signerCert = null;
+        Map<String, X509Certificate> certificateMap = new HashMap<String, X509Certificate>();
+        for (Certificate certificate : certificates) {
+            X509Certificate x509Certificate = (X509Certificate) certificate;
+            if (signerCertIssuer.equals(x509Certificate
+                    .getIssuerX500Principal())
+                    && signerCertSerialNumber.equals(x509Certificate
+                            .getSerialNumber())) {
+                signerCert = x509Certificate;
+            }
+            String ski = Hex.encodeHexString(getSubjectKeyId(x509Certificate));
+            certificateMap.put(ski, x509Certificate);
+            LOG.log(POILogger.DEBUG, "embedded certificate: "
+                    + x509Certificate.getSubjectX500Principal() + "; SKI="
+                    + ski);
+        }
+
+        // TSP signer cert path building
+        if (null == signerCert) {
+            throw new RuntimeException(
+                    "TSP response token has no signer certificate");
+        }
+        List<X509Certificate> tspCertificateChain = new LinkedList<X509Certificate>();
+        X509Certificate certificate = signerCert;
+        do {
+            LOG.log(POILogger.DEBUG, "adding to certificate chain: "
+                    + certificate.getSubjectX500Principal());
+            tspCertificateChain.add(certificate);
+            if (certificate.getSubjectX500Principal().equals(
+                    certificate.getIssuerX500Principal())) {
+                break;
+            }
+            String aki = Hex.encodeHexString(getAuthorityKeyId(certificate));
+            certificate = certificateMap.get(aki);
+        } while (null != certificate);
+
+        // verify TSP signer signature
+        X509CertificateHolderIf holder = HorribleProxy.newProxy(X509CertificateHolderIf.class, tspCertificateChain.get(0).getEncoded());
+        DefaultDigestAlgorithmIdentifierFinderIf finder = HorribleProxy.newProxy(DefaultDigestAlgorithmIdentifierFinderIf.class);
+        BcDigestCalculatorProviderIf calculator = HorribleProxy.newProxy(BcDigestCalculatorProviderIf.class);
+        BcRSASignerInfoVerifierBuilderIf verifierBuilder = HorribleProxy.newProxy(BcRSASignerInfoVerifierBuilderIf.class, finder, calculator);
+        SignerInformationVerifierIf verifier = verifierBuilder.build(holder);
+        
+        timeStampToken.validate(verifier);
+
+        // verify TSP signer certificate
+        this.validator.validate(tspCertificateChain, revocationData);
+
+        LOG.log(POILogger.DEBUG, "time-stamp token time: "
+                + timeStampToken.getTimeStampInfo().getGenTime());
+
+        byte[] timestamp = timeStampToken.getEncoded();
+        return timestamp;
+    }
+
+    private byte[] getSubjectKeyId(X509Certificate cert) throws Exception {
+        // X509Extensions.SubjectKeyIdentifier.getId()
+        byte[] extvalue = cert.getExtensionValue("2.5.29.14");
+        if (extvalue == null) return null;
+
+        ASN1InputStreamIf keyCntStream = HorribleProxy.newProxy(ASN1InputStreamIf.class, new ByteArrayInputStream(extvalue));
+        ASN1OctetStringIf cntStr = HorribleProxy.createProxy(ASN1OctetStringIf.class, "getInstance", keyCntStream.readObject$Object());
+        ASN1InputStreamIf keyIdStream = HorribleProxy.newProxy(ASN1InputStreamIf.class, new ByteArrayInputStream(cntStr.getOctets()));
+        SubjectKeyIdentifierIf keyId = HorribleProxy.createProxy(SubjectKeyIdentifierIf.class, "getInstance", keyIdStream.readObject$Object());
+
+        return keyId.getKeyIdentifier();
+    }
+
+    private byte[] getAuthorityKeyId(X509Certificate cert) throws Exception {
+        // X509Extensions.AuthorityKeyIdentifier.getId()
+        byte[] extvalue = cert.getExtensionValue("2.5.29.35");
+        if (extvalue == null) return null;
+
+        ASN1InputStreamIf keyCntStream = HorribleProxy.newProxy(ASN1InputStreamIf.class, new ByteArrayInputStream(extvalue));
+        DEROctetStringIf cntStr = keyCntStream.readObject$DERString();
+        ASN1InputStreamIf keyIdStream = HorribleProxy.newProxy(ASN1InputStreamIf.class, new ByteArrayInputStream(cntStr.getOctets()));
+        AuthorityKeyIdentifierIf keyId = HorribleProxy.newProxy(AuthorityKeyIdentifierIf.class, keyIdStream.readObject$Sequence());
+        
+        return keyId.getKeyIdentifier();
+    }
+}
\ No newline at end of file

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampService.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampService.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampService.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampService.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,52 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+
+/**
+ * Interface for a time-stamp service.
+ * 
+ * @author Frank Cornelis
+ * 
+ */
+public interface TimeStampService {
+
+    /**
+     * Gives back the encoded time-stamp token for the given array of data
+     * bytes. We assume that the time-stamp token itself contains its full
+     * certificate chain required for proper validation.
+     * 
+     * @param data
+     *            the data to be time-stamped.
+     * @param revocationData
+     *            the optional container that needs to be filled up with the
+     *            revocation data used to validate the TSA certificate chain.
+     * @return the DER encoded time-stamp token.
+     * @throws Exception
+     *             in case something went wrong.
+     */
+    byte[] timeStamp(byte[] data, RevocationData revocationData)
+            throws Exception;
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampServiceValidator.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampServiceValidator.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampServiceValidator.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/TimeStampServiceValidator.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,51 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+import java.security.cert.X509Certificate;
+import java.util.List;
+
+/**
+ * Interface for trust validator of a TSP.
+ * 
+ * @author Frank Cornelis
+ * 
+ */
+public interface TimeStampServiceValidator {
+
+    /**
+     * Validates the given certificate chain.
+     * 
+     * @param certificateChain
+     * @param revocationData
+     *            the optional data container that should be filled with
+     *            revocation data that was used to validate the given
+     *            certificate chain.
+     * @throws Exception
+     *             in case the certificate chain is invalid.
+     */
+    void validate(List<X509Certificate> certificateChain,
+            RevocationData revocationData) throws Exception;
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/XmlSignatureService.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/XmlSignatureService.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/XmlSignatureService.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/services/XmlSignatureService.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,610 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.services;
+
+import java.io.ByteArrayOutputStream;
+import java.io.File;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.net.MalformedURLException;
+import java.security.InvalidAlgorithmParameterException;
+import java.security.Key;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.security.NoSuchProviderException;
+import java.security.cert.X509Certificate;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.UUID;
+
+import javax.xml.crypto.MarshalException;
+import javax.xml.crypto.URIDereferencer;
+import javax.xml.crypto.XMLStructure;
+import javax.xml.crypto.dom.DOMCryptoContext;
+import javax.xml.crypto.dsig.CanonicalizationMethod;
+import javax.xml.crypto.dsig.DigestMethod;
+import javax.xml.crypto.dsig.Manifest;
+import javax.xml.crypto.dsig.Reference;
+import javax.xml.crypto.dsig.SignatureMethod;
+import javax.xml.crypto.dsig.SignedInfo;
+import javax.xml.crypto.dsig.XMLObject;
+import javax.xml.crypto.dsig.XMLSignContext;
+import javax.xml.crypto.dsig.XMLSignatureFactory;
+import javax.xml.crypto.dsig.dom.DOMSignContext;
+import javax.xml.crypto.dsig.spec.C14NMethodParameterSpec;
+import javax.xml.parsers.DocumentBuilderFactory;
+import javax.xml.parsers.ParserConfigurationException;
+import javax.xml.transform.TransformerException;
+import javax.xml.transform.TransformerFactoryConfigurationError;
+
+import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
+import org.apache.poi.openxml4j.opc.OPCPackage;
+import org.apache.poi.openxml4j.opc.PackageNamespaces;
+import org.apache.poi.openxml4j.opc.PackagePart;
+import org.apache.poi.openxml4j.opc.PackagePartName;
+import org.apache.poi.openxml4j.opc.PackageRelationship;
+import org.apache.poi.openxml4j.opc.PackageRelationshipCollection;
+import org.apache.poi.openxml4j.opc.PackageRelationshipTypes;
+import org.apache.poi.openxml4j.opc.PackagingURIHelper;
+import org.apache.poi.openxml4j.opc.TargetMode;
+import org.apache.poi.poifs.crypt.CryptoFunctions;
+import org.apache.poi.poifs.crypt.HashAlgorithm;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.DOMReferenceIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.DOMSignedInfoIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.DOMXMLSignatureIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxies.XMLSignatureIf;
+import org.apache.poi.poifs.crypt.dsig.HorribleProxy;
+import org.apache.poi.poifs.crypt.dsig.OOXMLURIDereferencer;
+import org.apache.poi.poifs.crypt.dsig.SignatureInfo;
+import org.apache.poi.poifs.crypt.dsig.facets.KeyInfoSignatureFacet;
+import org.apache.poi.poifs.crypt.dsig.facets.OOXMLSignatureFacet;
+import org.apache.poi.poifs.crypt.dsig.facets.Office2010SignatureFacet;
+import org.apache.poi.poifs.crypt.dsig.facets.SignatureFacet;
+import org.apache.poi.poifs.crypt.dsig.facets.XAdESSignatureFacet;
+import org.apache.poi.poifs.crypt.dsig.spi.AddressDTO;
+import org.apache.poi.poifs.crypt.dsig.spi.Constants;
+import org.apache.poi.poifs.crypt.dsig.spi.DigestInfo;
+import org.apache.poi.poifs.crypt.dsig.spi.IdentityDTO;
+import org.apache.poi.util.POILogFactory;
+import org.apache.poi.util.POILogger;
+import org.apache.xmlbeans.XmlException;
+import org.apache.xmlbeans.XmlOptions;
+import org.w3.x2000.x09.xmldsig.SignatureDocument;
+import org.w3.x2000.x09.xmldsig.SignatureType;
+import org.w3.x2000.x09.xmldsig.SignatureValueType;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.NodeList;
+import org.xml.sax.SAXException;
+
+
+/**
+ * Abstract base class for an XML Signature Service implementation.
+ */
+public class XmlSignatureService implements SignatureService {
+    private static final POILogger LOG = POILogFactory.getLogger(XmlSignatureService.class);
+
+    protected final List<SignatureFacet> signatureFacets;
+
+    private String signatureNamespacePrefix;
+    private String signatureId;
+    private final HashAlgorithm hashAlgo;
+    private final OPCPackage opcPackage;
+    private SignatureDocument sigDoc;
+    private XAdESSignatureFacet xadesSignatureFacet;
+    
+    /**
+     * Main constructor.
+     */
+    public XmlSignatureService(HashAlgorithm digestAlgo, OPCPackage opcPackage) {
+        this.signatureFacets = new LinkedList<SignatureFacet>();
+        this.signatureNamespacePrefix = null;
+        this.signatureId = null;
+        this.hashAlgo = digestAlgo;
+        this.opcPackage = opcPackage;
+        this.sigDoc = null;
+    }
+
+    public void initFacets(Date clock) {
+        if (clock == null) clock = new Date();
+        addSignatureFacet(new OOXMLSignatureFacet(this, clock, hashAlgo));
+        addSignatureFacet(new KeyInfoSignatureFacet(true, false, false));
+
+        this.xadesSignatureFacet = new XAdESSignatureFacet(clock, hashAlgo, null);
+        this.xadesSignatureFacet.setIdSignedProperties("idSignedProperties");
+        this.xadesSignatureFacet.setSignaturePolicyImplied(true);
+        /*
+         * Work-around for Office 2010.
+         */
+        this.xadesSignatureFacet.setIssuerNameNoReverseOrder(true);
+        setSignatureId("idPackageSignature");
+        addSignatureFacet(this.xadesSignatureFacet);
+        addSignatureFacet(new Office2010SignatureFacet());
+    }
+    
+    
+    /**
+     * Sets the signature Id attribute value used to create the XML signature. A
+     * <code>null</code> value will trigger an automatically generated signature
+     * Id.
+     * 
+     * @param signatureId
+     */
+    protected void setSignatureId(String signatureId) {
+            this.signatureId = signatureId;
+    }
+
+    /**
+     * Sets the XML Signature namespace prefix to be used for signature
+     * creation. A <code>null</code> value will omit the prefixing.
+     * 
+     * @param signatureNamespacePrefix
+     */
+    protected void setSignatureNamespacePrefix(String signatureNamespacePrefix) {
+        this.signatureNamespacePrefix = signatureNamespacePrefix;
+    }
+
+    /**
+     * Adds a signature facet to this XML signature service.
+     * 
+     * @param signatureFacet
+     */
+    protected void addSignatureFacet(SignatureFacet signatureFacet) {
+        this.signatureFacets.add(signatureFacet);
+    }
+
+    /**
+     * Gives back the signature digest algorithm. Allowed values are SHA-1,
+     * SHA-256, SHA-384, SHA-512, RIPEND160. The default algorithm is SHA-1.
+     * Override this method to select another signature digest algorithm.
+     * 
+     * @return
+     */
+    protected HashAlgorithm getSignatureDigestAlgorithm() {
+        return null != this.hashAlgo ? this.hashAlgo : HashAlgorithm.sha1;
+    }
+
+    /**
+     * Override this method to change the URI dereferener used by the signing
+     * engine.
+     * 
+     * @return
+     */
+    protected URIDereferencer getURIDereferencer() {
+        OPCPackage ooxmlDocument = getOfficeOpenXMLDocument();
+        return new OOXMLURIDereferencer(ooxmlDocument);
+    }
+
+    /**
+     * Gives back the human-readable description of what the citizen will be
+     * signing. The default value is "XML Document". Override this method to
+     * provide the citizen with another description.
+     * 
+     * @return
+     */
+    protected String getSignatureDescription() {
+        return "Office OpenXML Document";
+    }
+
+    /**
+     * Gives back the URL of the OOXML to be signed.
+     * 
+     * @return
+     */
+    public OPCPackage getOfficeOpenXMLDocument() {
+        return opcPackage;
+    }
+    
+
+    
+    /**
+     * Gives back the output stream to which to write the signed XML document.
+     * 
+     * @return
+     */
+    // protected abstract OutputStream getSignedDocumentOutputStream();
+
+    public DigestInfo preSign(List<DigestInfo> digestInfos,
+        List<X509Certificate> signingCertificateChain,
+        IdentityDTO identity, AddressDTO address, byte[] photo)
+    throws NoSuchAlgorithmException {
+        SignatureInfo.initXmlProvider();
+    
+        LOG.log(POILogger.DEBUG, "preSign");
+        HashAlgorithm hashAlgo = getSignatureDigestAlgorithm();
+
+        byte[] digestValue;
+        try {
+            digestValue = getXmlSignatureDigestValue(hashAlgo, digestInfos, signingCertificateChain);
+        } catch (Exception e) {
+            throw new RuntimeException("XML signature error: " + e.getMessage(), e);
+        }
+
+        String description = getSignatureDescription();
+        return new DigestInfo(digestValue, hashAlgo, description);
+    }
+
+    public void postSign(byte[] signatureValue, List<X509Certificate> signingCertificateChain)
+    throws IOException {
+        LOG.log(POILogger.DEBUG, "postSign");
+        SignatureInfo.initXmlProvider();
+
+        /*
+         * Retrieve the intermediate XML signature document from the temporary  
+         * data storage.
+         */
+        SignatureType sigType = sigDoc.getSignature();
+
+        /*
+         * Check ds:Signature node.
+         */
+        if (!signatureId.equals(sigType.getId())) {
+            throw new RuntimeException("ds:Signature not found for @Id: " + signatureId);
+        }
+
+        /*
+         * Insert signature value into the ds:SignatureValue element
+         */
+        SignatureValueType sigVal = sigType.getSignatureValue();
+        sigVal.setByteArrayValue(signatureValue);
+
+        /*
+         * Allow signature facets to inject their own stuff.
+         */
+        for (SignatureFacet signatureFacet : this.signatureFacets) {
+            signatureFacet.postSign(sigType, signingCertificateChain);
+        }
+
+        writeDocument();
+    }
+
+    @SuppressWarnings("unchecked")
+    private byte[] getXmlSignatureDigestValue(HashAlgorithm hashAlgo,
+        List<DigestInfo> digestInfos,
+        List<X509Certificate> signingCertificateChain)
+        throws ParserConfigurationException, NoSuchAlgorithmException,
+        InvalidAlgorithmParameterException, MarshalException,
+        javax.xml.crypto.dsig.XMLSignatureException,
+        TransformerFactoryConfigurationError, TransformerException,
+        IOException, SAXException, NoSuchProviderException, XmlException {
+        /*
+         * DOM Document construction.
+         */
+        DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
+        dbf.setNamespaceAware(true);
+        Document doc = dbf.newDocumentBuilder().newDocument();
+
+        /*
+         * Signature context construction.
+         */
+        Key key = new Key() {
+            private static final long serialVersionUID = 1L;
+
+            public String getAlgorithm() {
+                return null;
+            }
+
+            public byte[] getEncoded() {
+                return null;
+            }
+
+            public String getFormat() {
+                return null;
+            }
+        };
+        
+        // As of JDK 7, can't use sigDoc here directly, because the
+        // setAttributeID will be called and it's not implemented in xmlbeans
+        XMLSignContext xmlSignContext = new DOMSignContext(key, doc);
+        URIDereferencer uriDereferencer = getURIDereferencer();
+        if (null != uriDereferencer) {
+            xmlSignContext.setURIDereferencer(uriDereferencer);
+        }
+
+        xmlSignContext.putNamespacePrefix(
+                "http://schemas.openxmlformats.org/package/2006/digital-signature",
+                "mdssi");
+        
+        if (this.signatureNamespacePrefix != null) {
+            /*
+             * OOo doesn't like ds namespaces so per default prefixing is off.
+             */
+            xmlSignContext.putNamespacePrefix(
+                javax.xml.crypto.dsig.XMLSignature.XMLNS,
+                this.signatureNamespacePrefix);
+        }
+
+        XMLSignatureFactory signatureFactory = XMLSignatureFactory.getInstance("DOM", "XMLDSig");
+
+        /*
+         * Add ds:References that come from signing client local files.
+         */
+        List<Reference> references = new LinkedList<Reference>();
+        addDigestInfosAsReferences(digestInfos, signatureFactory, references);
+
+        /*
+         * Invoke the signature facets.
+         */
+        String localSignatureId;
+        if (null == this.signatureId) {
+            localSignatureId = "xmldsig-" + UUID.randomUUID().toString();
+        } else {
+            localSignatureId = this.signatureId;
+        }
+        List<XMLObject> objects = new LinkedList<XMLObject>();
+        for (SignatureFacet signatureFacet : this.signatureFacets) {
+            LOG.log(POILogger.DEBUG, "invoking signature facet: "
+                + signatureFacet.getClass().getSimpleName());
+            signatureFacet.preSign(signatureFactory, localSignatureId, signingCertificateChain, references, objects);
+        }
+
+        /*
+         * ds:SignedInfo
+         */
+        SignatureMethod signatureMethod = signatureFactory.newSignatureMethod(
+            getSignatureMethod(hashAlgo), null);
+        CanonicalizationMethod canonicalizationMethod = signatureFactory
+            .newCanonicalizationMethod(getCanonicalizationMethod(),
+            (C14NMethodParameterSpec) null);
+        SignedInfo signedInfo = signatureFactory.newSignedInfo(
+            canonicalizationMethod, signatureMethod, references);
+
+        /*
+         * JSR105 ds:Signature creation
+         */
+        String signatureValueId = localSignatureId + "-signature-value";
+        javax.xml.crypto.dsig.XMLSignature xmlSignature = signatureFactory
+            .newXMLSignature(signedInfo, null, objects, localSignatureId,
+            signatureValueId);
+
+        /*
+         * ds:Signature Marshalling.
+         */
+        DOMXMLSignatureIf domXmlSignature;
+        try {
+            domXmlSignature = HorribleProxy.newProxy(DOMXMLSignatureIf.class, xmlSignature);
+        } catch (Exception e) {
+            throw new RuntimeException("DomXmlSignature instance error: " + e.getMessage(), e);
+        }
+        
+        domXmlSignature.marshal(doc, this.signatureNamespacePrefix, (DOMCryptoContext) xmlSignContext);
+
+        registerIds(doc);
+        Element el = doc.getElementById("idPackageObject");
+        assert (el != null);
+        el.setAttributeNS(Constants.NamespaceSpecNS, "xmlns:mdssi", PackageNamespaces.DIGITAL_SIGNATURE);
+
+        
+        /*
+         * Completion of undigested ds:References in the ds:Manifests.
+         */
+        for (XMLObject object : objects) {
+            LOG.log(POILogger.DEBUG, "object java type: " + object.getClass().getName());
+            List<XMLStructure> objectContentList = object.getContent();
+            for (XMLStructure objectContent : objectContentList) {
+                LOG.log(POILogger.DEBUG, "object content java type: " + objectContent.getClass().getName());
+                if (!(objectContent instanceof Manifest)) continue;
+                Manifest manifest = (Manifest) objectContent;
+                List<Reference> manifestReferences = manifest.getReferences();
+                for (Reference manifestReference : manifestReferences) {
+                    if (manifestReference.getDigestValue() != null) continue;
+
+                    DOMReferenceIf manifestDOMReference;
+                    try {
+                        manifestDOMReference = HorribleProxy.newProxy(DOMReferenceIf.class, manifestReference);
+                    } catch (Exception e) {
+                        throw new RuntimeException("DOMReference instance error: " + e.getMessage(), e);
+                    }
+                    manifestDOMReference.digest(xmlSignContext);
+                }
+            }
+        }
+
+        /*
+         * Completion of undigested ds:References.
+         */
+        List<Reference> signedInfoReferences = signedInfo.getReferences();
+        for (Reference signedInfoReference : signedInfoReferences) {
+            DOMReferenceIf domReference;
+            try {
+                domReference = HorribleProxy.newProxy(DOMReferenceIf.class, signedInfoReference);
+            } catch (Exception e) {
+                throw new RuntimeException("DOMReference instance error: " + e.getMessage(), e);
+            }
+
+            // ds:Reference with external digest value
+            if (domReference.getDigestValue() != null) continue;
+            
+            domReference.digest(xmlSignContext);
+        }
+
+        /*
+         * Calculation of XML signature digest value.
+         */
+        DOMSignedInfoIf domSignedInfo;
+        try {
+            domSignedInfo = HorribleProxy.newProxy(DOMSignedInfoIf.class, signedInfo); 
+        } catch (Exception e) {
+            throw new RuntimeException("DOMSignedInfo instance error: " + e.getMessage(), e);
+        }
+        
+        ByteArrayOutputStream dataStream = new ByteArrayOutputStream();
+        domSignedInfo.canonicalize(xmlSignContext, dataStream);
+        byte[] octets = dataStream.toByteArray();
+
+        sigDoc = SignatureDocument.Factory.parse(doc.getDocumentElement());
+        
+        
+        /*
+         * TODO: we could be using DigestOutputStream here to optimize memory
+         * usage.
+         */
+
+        MessageDigest jcaMessageDigest = CryptoFunctions.getMessageDigest(hashAlgo);
+        byte[] digestValue = jcaMessageDigest.digest(octets);
+        return digestValue;
+    }
+
+    /**
+     * the resulting document needs to be tweaked before it can be digested -
+     * this applies to the verification and signing step
+     *
+     * @param doc
+     */
+    public void registerIds(Document doc) {
+        NodeList nl = doc.getElementsByTagNameNS("http://www.w3.org/2000/09/xmldsig#", "Object");
+        registerIdAttribute(nl);
+        nl = doc.getElementsByTagNameNS("http://uri.etsi.org/01903/v1.3.2#", "SignedProperties");
+        registerIdAttribute(nl);
+    }
+    
+    protected void registerIdAttribute(NodeList nl) {
+        for (int i=0; i<nl.getLength(); i++) {
+            Element el = (Element)nl.item(i);
+            if (el.hasAttribute("Id")) {
+                el.setIdAttribute("Id", true);
+            }
+        }
+    }
+    
+    private void addDigestInfosAsReferences(List<DigestInfo> digestInfos,
+        XMLSignatureFactory signatureFactory, List<Reference> references)
+        throws NoSuchAlgorithmException,
+        InvalidAlgorithmParameterException, MalformedURLException {
+        if (digestInfos == null) return;
+        for (DigestInfo digestInfo : digestInfos) {
+            byte[] documentDigestValue = digestInfo.digestValue;
+
+            DigestMethod digestMethod = signatureFactory.newDigestMethod(
+                            digestInfo.hashAlgo.xmlSignUri, null);
+
+            String uri = new File(digestInfo.description).getName();
+
+            Reference reference = signatureFactory.newReference(uri,
+                            digestMethod, null, null, null, documentDigestValue);
+            references.add(reference);
+        }
+    }
+
+    private String getSignatureMethod(HashAlgorithm hashAlgo) {
+        if (null == hashAlgo) {
+            throw new RuntimeException("digest algo is null");
+        }
+
+        XMLSignatureIf XmlSignature;
+        try {
+            XmlSignature = HorribleProxy.newProxy(XMLSignatureIf.class);
+        } catch (Exception e) {
+            throw new RuntimeException("JDK doesn't support XmlSignature", e);
+        }
+            
+        switch (hashAlgo) {
+        case sha1:   return XmlSignature.ALGO_ID_SIGNATURE_RSA_SHA1();
+        case sha256: return XmlSignature.ALGO_ID_SIGNATURE_RSA_SHA256();
+        case sha384: return XmlSignature.ALGO_ID_SIGNATURE_RSA_SHA384();
+        case sha512: return XmlSignature.ALGO_ID_SIGNATURE_RSA_SHA512();
+        case ripemd160: return XmlSignature.ALGO_ID_MAC_HMAC_RIPEMD160();
+        default: break;
+        }
+
+        throw new RuntimeException("unsupported sign algo: " + hashAlgo);
+    }
+
+    /**
+     * Gives back the used XAdES signature facet.
+     * 
+     * @return
+     */
+    protected XAdESSignatureFacet getXAdESSignatureFacet() {
+        return this.xadesSignatureFacet;
+    }
+
+    public String getFilesDigestAlgorithm() {
+        return null;
+    }
+
+    protected String getCanonicalizationMethod() {
+        return CanonicalizationMethod.INCLUSIVE;
+    }
+
+    protected void writeDocument() throws IOException {
+        XmlOptions xo = new XmlOptions();
+        Map<String,String> namespaceMap = new HashMap<String,String>();
+        for (SignatureFacet sf : this.signatureFacets) {
+            Map<String,String> sfm = sf.getNamespacePrefixMapping();
+            if (sfm != null) {
+                namespaceMap.putAll(sfm);
+            }
+        }
+        xo.setSaveSuggestedPrefixes(namespaceMap);
+        xo.setUseDefaultNamespace();
+
+        LOG.log(POILogger.DEBUG, "output signed Office OpenXML document");
+
+        /*
+         * Copy the original OOXML content to the signed OOXML package. During
+         * copying some files need to changed.
+         */
+        OPCPackage pkg = this.getOfficeOpenXMLDocument();
+
+        PackagePartName sigPartName, sigsPartName;
+        try {
+            // <Override PartName="/_xmlsignatures/sig1.xml" ContentType="application/vnd.openxmlformats-package.digital-signature-xmlsignature+xml"/>
+            sigPartName = PackagingURIHelper.createPartName("/_xmlsignatures/sig1.xml");
+            // <Default Extension="sigs" ContentType="application/vnd.openxmlformats-package.digital-signature-origin"/>
+            sigsPartName = PackagingURIHelper.createPartName("/_xmlsignatures/origin.sigs");
+        } catch (InvalidFormatException e) {
+            throw new IOException(e);
+        }
+        
+        String sigContentType = "application/vnd.openxmlformats-package.digital-signature-xmlsignature+xml";
+        PackagePart sigPart = pkg.getPart(sigPartName);
+        if (sigPart == null) {
+            sigPart = pkg.createPart(sigPartName, sigContentType);
+        }
+        
+        OutputStream os = sigPart.getOutputStream();
+        sigDoc.save(os, xo);
+        os.close();
+        
+        String sigsContentType = "application/vnd.openxmlformats-package.digital-signature-origin";
+        PackagePart sigsPart = pkg.getPart(sigsPartName);
+        if (sigsPart == null) {
+            // touch empty marker file
+            sigsPart = pkg.createPart(sigsPartName, sigsContentType);
+        }
+        
+        PackageRelationshipCollection relCol = pkg.getRelationshipsByType(PackageRelationshipTypes.DIGITAL_SIGNATURE_ORIGIN);
+        for (PackageRelationship pr : relCol) {
+            pkg.removeRelationship(pr.getId());
+        }
+        pkg.addRelationship(sigsPartName, TargetMode.INTERNAL, PackageRelationshipTypes.DIGITAL_SIGNATURE_ORIGIN);
+        
+        sigsPart.addRelationship(sigPartName, TargetMode.INTERNAL, PackageRelationshipTypes.DIGITAL_SIGNATURE);
+    }
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/AddressDTO.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/AddressDTO.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/AddressDTO.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/AddressDTO.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,51 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.spi;
+
+import java.io.Serializable;
+import java.security.Identity;
+
+/**
+ * Address Data Transfer Object.
+ * 
+ * @author Frank Cornelis
+ * @see Identity
+ * 
+ */
+public class AddressDTO implements Serializable {
+
+    /*
+     * We implement serializable to allow this class to be used in distributed
+     * containers as defined in the Servlet v2.4 specification.
+     */
+
+    private static final long serialVersionUID = 1L;
+
+    public String streetAndNumber;
+
+    public String zip;
+
+    public String city;
+}
\ No newline at end of file

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/Constants.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/Constants.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/Constants.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/Constants.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,30 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.spi;
+
+public interface Constants {
+    String NamespaceSpecNS = "http://www.w3.org/2000/xmlns/";
+    String SignatureSpecNS = "http://www.w3.org/2000/09/xmldsig#";
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/DigestInfo.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/DigestInfo.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/DigestInfo.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/DigestInfo.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,56 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.spi;
+
+import java.io.Serializable;
+
+import org.apache.poi.poifs.crypt.HashAlgorithm;
+
+/**
+ * Digest Information data transfer class.
+ */
+public class DigestInfo implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * Main constructor.
+     * 
+     * @param digestValue
+     * @param hashAlgo
+     * @param description
+     */
+    public DigestInfo(byte[] digestValue, HashAlgorithm hashAlgo, String description) {
+        this.digestValue = digestValue;
+        this.hashAlgo = hashAlgo;
+        this.description = description;
+    }
+
+    public final byte[] digestValue;
+
+    public final String description;
+
+    public final HashAlgorithm hashAlgo;
+}

Added: poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/IdentityDTO.java
URL: http://svn.apache.org/viewvc/poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/IdentityDTO.java?rev=1617141&view=auto
==============================================================================
--- poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/IdentityDTO.java (added)
+++ poi/branches/xml_signature/src/ooxml/java/org/apache/poi/poifs/crypt/dsig/spi/IdentityDTO.java Sun Aug 10 18:25:10 2014
@@ -0,0 +1,75 @@
+/* ====================================================================
+   Licensed to the Apache Software Foundation (ASF) under one or more
+   contributor license agreements.  See the NOTICE file distributed with
+   this work for additional information regarding copyright ownership.
+   The ASF licenses this file to You under the Apache License, Version 2.0
+   (the "License"); you may not use this file except in compliance with
+   the License.  You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+==================================================================== */
+
+/* ====================================================================
+   This product contains an ASLv2 licensed version of the OOXML signer
+   package from the eID Applet project
+   http://code.google.com/p/eid-applet/source/browse/trunk/README.txt  
+   Copyright (C) 2008-2014 FedICT.
+   ================================================================= */ 
+
+package org.apache.poi.poifs.crypt.dsig.spi;
+
+import java.io.Serializable;
+import java.util.GregorianCalendar;
+
+/**
+ * Identity Data Transfer Object.
+ * 
+ * @author Frank Cornelis
+ * 
+ */
+public class IdentityDTO implements Serializable {
+
+    /*
+     * We implement serializable to allow this class to be used in distributed
+     * containers as defined in the Servlet v2.4 specification.
+     */
+    private static final long serialVersionUID = 1L;
+
+    public String cardNumber;
+
+    public String chipNumber;
+
+    public GregorianCalendar cardValidityDateBegin;
+
+    public GregorianCalendar cardValidityDateEnd;
+
+    public String cardDeliveryMunicipality;
+
+    public String nationalNumber;
+
+    public String name;
+
+    public String firstName;
+
+    public String middleName;
+
+    public String nationality;
+
+    public String placeOfBirth;
+
+    public GregorianCalendar dateOfBirth;
+
+    public boolean male;
+
+    public boolean female;
+
+    public String nobleCondition;
+
+    public String duplicate;
+}
\ No newline at end of file



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