116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giropackage org.bouncycastle.asn1.cms;
216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport java.util.Enumeration;
416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1EncodableVector;
616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1Integer;
716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1Object;
816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1ObjectIdentifier;
916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1Primitive;
1016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1Sequence;
1116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1Set;
1216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.ASN1TaggedObject;
1316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.BERSequence;
1416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.BERSet;
1516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.BERTaggedObject;
1616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giroimport org.bouncycastle.asn1.DERTaggedObject;
1716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
1816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro/**
1980261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * <a href="http://tools.ietf.org/html/rfc5652#section-5.1">RFC 5652</a>:
2080261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * <p>
2180261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * A signed data object containing multitude of {@link SignerInfo}s.
2280261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * <pre>
2380261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * SignedData ::= SEQUENCE {
2480261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *     version CMSVersion,
2580261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *     digestAlgorithms DigestAlgorithmIdentifiers,
2680261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *     encapContentInfo EncapsulatedContentInfo,
2780261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *     certificates [0] IMPLICIT CertificateSet OPTIONAL,
2880261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *     crls [1] IMPLICIT CertificateRevocationLists OPTIONAL,
2980261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *     signerInfos SignerInfos
3080261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *   }
3180261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *
3280261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * DigestAlgorithmIdentifiers ::= SET OF DigestAlgorithmIdentifier
3380261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *
3480261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * SignerInfos ::= SET OF SignerInfo
3580261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * </pre>
3680261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * <p>
37bdb7b3d37025690a0434040b4e0d0623d9fa74afSergio Giro * The version calculation uses following ruleset from RFC 5652 section 5.1:
3880261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * <pre>
3980261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * IF ((certificates is present) AND
4080261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *    (any certificates with a type of other are present)) OR
4180261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *    ((crls is present) AND
4280261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *    (any crls with a type of other are present))
4380261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * THEN version MUST be 5
4480261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * ELSE
4580261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *    IF (certificates is present) AND
4680261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *       (any version 2 attribute certificates are present)
4780261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *    THEN version MUST be 4
4880261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *    ELSE
4980261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *       IF ((certificates is present) AND
5080261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *          (any version 1 attribute certificates are present)) OR
5180261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *          (any SignerInfo structures are version 3) OR
5280261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *          (encapContentInfo eContentType is other than id-data)
5380261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *       THEN version MUST be 3
5480261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro *       ELSE version MUST be 1
5580261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * </pre>
5680261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro * <p>
5716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro */
5816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giropublic class SignedData
5916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    extends ASN1Object
6016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro{
6116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private static final ASN1Integer VERSION_1 = new ASN1Integer(1);
6216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private static final ASN1Integer VERSION_3 = new ASN1Integer(3);
6316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private static final ASN1Integer VERSION_4 = new ASN1Integer(4);
6416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private static final ASN1Integer VERSION_5 = new ASN1Integer(5);
6516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
6616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private ASN1Integer version;
6716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private ASN1Set     digestAlgorithms;
6816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private ContentInfo contentInfo;
6916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private ASN1Set     certificates;
7016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private ASN1Set     crls;
7116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private ASN1Set     signerInfos;
7216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private boolean certsBer;
7316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private boolean        crlsBer;
7416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
7580261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro    /**
7680261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * Return a SignedData object from the given object.
7780261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * <p>
7880261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * Accepted inputs:
7980261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * <ul>
8080261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * <li> null &rarr; null
8180261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * <li> {@link SignedData} object
8280261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * <li> {@link org.bouncycastle.asn1.ASN1Sequence#getInstance(java.lang.Object) ASN1Sequence} input formats with SignedData structure inside
8380261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * </ul>
8480261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     *
8580261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     * @param o the object we want converted.
86bdb7b3d37025690a0434040b4e0d0623d9fa74afSergio Giro     * @return a reference that can be assigned to SignedData (may be null)
87bdb7b3d37025690a0434040b4e0d0623d9fa74afSergio Giro     * @throws IllegalArgumentException if the object cannot be converted.
8880261dd2d1824bb3862e90e77a5412d56ad88b1fSergio Giro     */
8916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public static SignedData getInstance(
9016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        Object  o)
9116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
9216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (o instanceof SignedData)
9316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
9416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return (SignedData)o;
9516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
9616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        else if (o != null)
9716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
9816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return new SignedData(ASN1Sequence.getInstance(o));
9916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
10016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
10116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return null;
10216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
10316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
10416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public SignedData(
10516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Set     digestAlgorithms,
10616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ContentInfo contentInfo,
10716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Set     certificates,
10816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Set     crls,
10916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Set     signerInfos)
11016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
11116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.version = calculateVersion(contentInfo.getContentType(), certificates, crls, signerInfos);
11216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.digestAlgorithms = digestAlgorithms;
11316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.contentInfo = contentInfo;
11416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.certificates = certificates;
11516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.crls = crls;
11616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.signerInfos = signerInfos;
11716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.crlsBer = crls instanceof BERSet;
11816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        this.certsBer = certificates instanceof BERSet;
11916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
12016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
12116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
12216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private ASN1Integer calculateVersion(
12316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1ObjectIdentifier contentOid,
12416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Set certs,
12516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Set crls,
12616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Set signerInfs)
12716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
12816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        boolean otherCert = false;
12916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        boolean otherCrl = false;
13016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        boolean attrCertV1Found = false;
13116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        boolean attrCertV2Found = false;
13216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
13316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (certs != null)
13416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
13516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            for (Enumeration en = certs.getObjects(); en.hasMoreElements();)
13616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
13716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                Object obj = en.nextElement();
13816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                if (obj instanceof ASN1TaggedObject)
13916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                {
14016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    ASN1TaggedObject tagged = ASN1TaggedObject.getInstance(obj);
14116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
14216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    if (tagged.getTagNo() == 1)
14316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    {
14416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                        attrCertV1Found = true;
14516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    }
14616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    else if (tagged.getTagNo() == 2)
14716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    {
14816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                        attrCertV2Found = true;
14916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    }
15016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    else if (tagged.getTagNo() == 3)
15116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    {
15216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                        otherCert = true;
15316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    }
15416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                }
15516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
15616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
15716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
15816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (otherCert)
15916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
16016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return new ASN1Integer(5);
16116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
16216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
16316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (crls != null)         // no need to check if otherCert is true
16416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
16516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            for (Enumeration en = crls.getObjects(); en.hasMoreElements();)
16616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
16716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                Object obj = en.nextElement();
16816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                if (obj instanceof ASN1TaggedObject)
16916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                {
17016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    otherCrl = true;
17116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                }
17216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
17316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
17416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
17516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (otherCrl)
17616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
17716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return VERSION_5;
17816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
17916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
18016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (attrCertV2Found)
18116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
18216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return VERSION_4;
18316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
18416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
18516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (attrCertV1Found)
18616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
18716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return VERSION_3;
18816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
18916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
19016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (checkForVersion3(signerInfs))
19116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
19216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return VERSION_3;
19316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
19416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
19516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (!CMSObjectIdentifiers.data.equals(contentOid))
19616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
19716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            return VERSION_3;
19816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
19916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
20016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return VERSION_1;
20116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
20216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
20316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private boolean checkForVersion3(ASN1Set signerInfs)
20416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
20516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        for (Enumeration e = signerInfs.getObjects(); e.hasMoreElements();)
20616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
20716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            SignerInfo s = SignerInfo.getInstance(e.nextElement());
20816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
20916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            if (s.getVersion().getValue().intValue() == 3)
21016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
21116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                return true;
21216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
21316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
21416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
21516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return false;
21616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
21716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
21816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    private SignedData(
21916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1Sequence seq)
22016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
22116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        Enumeration     e = seq.getObjects();
22216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
22316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        version = ASN1Integer.getInstance(e.nextElement());
22416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        digestAlgorithms = ((ASN1Set)e.nextElement());
22516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        contentInfo = ContentInfo.getInstance(e.nextElement());
22616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
22716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        while (e.hasMoreElements())
22816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
22916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            ASN1Primitive o = (ASN1Primitive)e.nextElement();
23016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
23116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            //
23216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            // an interesting feature of SignedData is that there appear
23316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            // to be varying implementations...
23416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            // for the moment we ignore anything which doesn't fit.
23516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            //
23616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            if (o instanceof ASN1TaggedObject)
23716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
23816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                ASN1TaggedObject tagged = (ASN1TaggedObject)o;
23916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
24016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                switch (tagged.getTagNo())
24116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                {
24216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                case 0:
24316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    certsBer = tagged instanceof BERTaggedObject;
24416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    certificates = ASN1Set.getInstance(tagged, false);
24516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    break;
24616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                case 1:
24716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    crlsBer = tagged instanceof BERTaggedObject;
24816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    crls = ASN1Set.getInstance(tagged, false);
24916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    break;
25016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                default:
25116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                    throw new IllegalArgumentException("unknown tag value " + tagged.getTagNo());
25216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                }
25316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
25416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            else
25516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
25616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                signerInfos = (ASN1Set)o;
25716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
25816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
25916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
26016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
26116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public ASN1Integer getVersion()
26216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
26316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return version;
26416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
26516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
26616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public ASN1Set getDigestAlgorithms()
26716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
26816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return digestAlgorithms;
26916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
27016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
27116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public ContentInfo getEncapContentInfo()
27216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
27316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return contentInfo;
27416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
27516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
27616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public ASN1Set getCertificates()
27716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
27816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return certificates;
27916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
28016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
28116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public ASN1Set getCRLs()
28216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
28316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return crls;
28416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
28516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
28616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public ASN1Set getSignerInfos()
28716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
28816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return signerInfos;
28916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
29016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
29116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    /**
29216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro     * Produce an object suitable for an ASN1OutputStream.
29316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro     */
29416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    public ASN1Primitive toASN1Primitive()
29516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    {
29616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        ASN1EncodableVector  v = new ASN1EncodableVector();
29716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
29816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        v.add(version);
29916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        v.add(digestAlgorithms);
30016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        v.add(contentInfo);
30116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
30216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (certificates != null)
30316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
30416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            if (certsBer)
30516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
30616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                v.add(new BERTaggedObject(false, 0, certificates));
30716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
30816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            else
30916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
31016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                v.add(new DERTaggedObject(false, 0, certificates));
31116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
31216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
31316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
31416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        if (crls != null)
31516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        {
31616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            if (crlsBer)
31716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
31816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                v.add(new BERTaggedObject(false, 1, crls));
31916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
32016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            else
32116f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            {
32216f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro                v.add(new DERTaggedObject(false, 1, crls));
32316f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro            }
32416f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        }
32516f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
32616f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        v.add(signerInfos);
32716f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro
32816f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro        return new BERSequence(v);
32916f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro    }
33016f9ee464b68937f45d009d9c1b0eb9b544a8deeSergio Giro}
331