Initial Commit

This commit is contained in:
2023-06-21 12:46:23 -04:00
commit c70248a520
1352 changed files with 336780 additions and 0 deletions

View File

@@ -0,0 +1,88 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The AccessDescription object.
* <pre>
* AccessDescription ::= SEQUENCE {
* accessMethod OBJECT IDENTIFIER,
* accessLocation GeneralName }
* </pre>
*/
public class AccessDescription
: Asn1Encodable
{
public readonly static DerObjectIdentifier IdADCAIssuers = new DerObjectIdentifier("1.3.6.1.5.5.7.48.2");
public readonly static DerObjectIdentifier IdADOcsp = new DerObjectIdentifier("1.3.6.1.5.5.7.48.1");
internal DerObjectIdentifier accessMethod;
internal GeneralName accessLocation;
public static AccessDescription GetInstance(
object obj)
{
if (obj is AccessDescription)
{
return (AccessDescription) obj;
}
if (obj is Asn1Sequence)
{
return new AccessDescription((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
private AccessDescription(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("wrong number of elements in inner sequence");
accessMethod = DerObjectIdentifier.GetInstance(seq[0]);
accessLocation = GeneralName.GetInstance(seq[1]);
}
/**
* create an AccessDescription with the oid and location provided.
*/
public AccessDescription(
DerObjectIdentifier oid,
GeneralName location)
{
accessMethod = oid;
accessLocation = location;
}
/**
*
* @return the access method.
*/
public DerObjectIdentifier AccessMethod
{
get { return accessMethod; }
}
/**
*
* @return the access location
*/
public GeneralName AccessLocation
{
get { return accessLocation; }
}
public override Asn1Object ToAsn1Object()
{
return new DerSequence(accessMethod, accessLocation);
}
public override string ToString()
{
return ("AccessDescription: Oid(" + this.accessMethod.Id + ")");
}
}
}

View File

@@ -0,0 +1,110 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
public class AlgorithmIdentifier
: Asn1Encodable
{
private readonly DerObjectIdentifier objectID;
private readonly Asn1Encodable parameters;
public static AlgorithmIdentifier GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static AlgorithmIdentifier GetInstance(
object obj)
{
if (obj == null || obj is AlgorithmIdentifier)
{
return (AlgorithmIdentifier) obj;
}
if (obj is DerObjectIdentifier)
{
return new AlgorithmIdentifier((DerObjectIdentifier) obj);
}
if (obj is string)
{
return new AlgorithmIdentifier((string) obj);
}
if (obj is Asn1Sequence)
{
return new AlgorithmIdentifier((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public AlgorithmIdentifier(
DerObjectIdentifier objectID)
{
this.objectID = objectID;
}
public AlgorithmIdentifier(
string objectID)
{
this.objectID = new DerObjectIdentifier(objectID);
}
public AlgorithmIdentifier(
DerObjectIdentifier objectID,
Asn1Encodable parameters)
{
this.objectID = objectID;
this.parameters = parameters;
}
internal AlgorithmIdentifier(
Asn1Sequence seq)
{
if (seq.Count < 1 || seq.Count > 2)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
objectID = DerObjectIdentifier.GetInstance(seq[0]);
if (seq.Count == 2)
{
parameters = seq[1];
}
}
public virtual DerObjectIdentifier ObjectID
{
get { return objectID; }
}
public Asn1Encodable Parameters
{
get { return parameters; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* AlgorithmIdentifier ::= Sequence {
* algorithm OBJECT IDENTIFIER,
* parameters ANY DEFINED BY algorithm OPTIONAL }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector(objectID);
if (parameters != null)
{
v.Add(parameters);
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,86 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
public class AttCertIssuer
: Asn1Encodable
{
internal readonly Asn1Encodable obj;
internal readonly Asn1Object choiceObj;
public static AttCertIssuer GetInstance(
object obj)
{
if (obj is AttCertIssuer)
{
return (AttCertIssuer)obj;
}
else if (obj is V2Form)
{
return new AttCertIssuer(V2Form.GetInstance(obj));
}
else if (obj is GeneralNames)
{
return new AttCertIssuer((GeneralNames)obj);
}
else if (obj is Asn1TaggedObject)
{
return new AttCertIssuer(V2Form.GetInstance((Asn1TaggedObject)obj, false));
}
else if (obj is Asn1Sequence)
{
return new AttCertIssuer(GeneralNames.GetInstance(obj));
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public static AttCertIssuer GetInstance(
Asn1TaggedObject obj,
bool isExplicit)
{
return GetInstance(obj.GetObject()); // must be explictly tagged
}
/// <summary>
/// Don't use this one if you are trying to be RFC 3281 compliant.
/// Use it for v1 attribute certificates only.
/// </summary>
/// <param name="names">Our GeneralNames structure</param>
public AttCertIssuer(
GeneralNames names)
{
obj = names;
choiceObj = obj.ToAsn1Object();
}
public AttCertIssuer(
V2Form v2Form)
{
obj = v2Form;
choiceObj = new DerTaggedObject(false, 0, obj);
}
public Asn1Encodable Issuer
{
get { return obj; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* AttCertIssuer ::= CHOICE {
* v1Form GeneralNames, -- MUST NOT be used in this
* -- profile
* v2Form [0] V2Form -- v2 only
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return choiceObj;
}
}
}

View File

@@ -0,0 +1,78 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
public class AttCertValidityPeriod
: Asn1Encodable
{
private readonly DerGeneralizedTime notBeforeTime;
private readonly DerGeneralizedTime notAfterTime;
public static AttCertValidityPeriod GetInstance(
object obj)
{
if (obj is AttCertValidityPeriod || obj == null)
{
return (AttCertValidityPeriod) obj;
}
if (obj is Asn1Sequence)
{
return new AttCertValidityPeriod((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public static AttCertValidityPeriod GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
private AttCertValidityPeriod(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Bad sequence size: " + seq.Count);
notBeforeTime = DerGeneralizedTime.GetInstance(seq[0]);
notAfterTime = DerGeneralizedTime.GetInstance(seq[1]);
}
public AttCertValidityPeriod(
DerGeneralizedTime notBeforeTime,
DerGeneralizedTime notAfterTime)
{
this.notBeforeTime = notBeforeTime;
this.notAfterTime = notAfterTime;
}
public DerGeneralizedTime NotBeforeTime
{
get { return notBeforeTime; }
}
public DerGeneralizedTime NotAfterTime
{
get { return notAfterTime; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* AttCertValidityPeriod ::= Sequence {
* notBeforeTime GeneralizedTime,
* notAfterTime GeneralizedTime
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return new DerSequence(notBeforeTime, notAfterTime);
}
}
}

View File

@@ -0,0 +1,77 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
public class AttributeX509
: Asn1Encodable
{
private readonly DerObjectIdentifier attrType;
private readonly Asn1Set attrValues;
/**
* return an Attr object from the given object.
*
* @param o the object we want converted.
* @exception ArgumentException if the object cannot be converted.
*/
public static AttributeX509 GetInstance(
object obj)
{
if (obj == null || obj is AttributeX509)
{
return (AttributeX509) obj;
}
if (obj is Asn1Sequence)
{
return new AttributeX509((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
private AttributeX509(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Bad sequence size: " + seq.Count);
attrType = DerObjectIdentifier.GetInstance(seq[0]);
attrValues = Asn1Set.GetInstance(seq[1]);
}
public AttributeX509(
DerObjectIdentifier attrType,
Asn1Set attrValues)
{
this.attrType = attrType;
this.attrValues = attrValues;
}
public DerObjectIdentifier AttrType
{
get { return attrType; }
}
public Asn1Set AttrValues
{
get { return attrValues; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* Attr ::= Sequence {
* attrType OBJECT IDENTIFIER,
* attrValues Set OF AttributeValue
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return new DerSequence(attrType, attrValues);
}
}
}

View File

@@ -0,0 +1,85 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
public class AttributeCertificate
: Asn1Encodable
{
private readonly AttributeCertificateInfo acinfo;
private readonly AlgorithmIdentifier signatureAlgorithm;
private readonly DerBitString signatureValue;
/**
* @param obj
* @return
*/
public static AttributeCertificate GetInstance(
object obj)
{
if (obj is AttributeCertificate)
{
return (AttributeCertificate) obj;
}
if (obj is Asn1Sequence)
{
return new AttributeCertificate((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public AttributeCertificate(
AttributeCertificateInfo acinfo,
AlgorithmIdentifier signatureAlgorithm,
DerBitString signatureValue)
{
this.acinfo = acinfo;
this.signatureAlgorithm = signatureAlgorithm;
this.signatureValue = signatureValue;
}
private AttributeCertificate(
Asn1Sequence seq)
{
if (seq.Count != 3)
throw new ArgumentException("Bad sequence size: " + seq.Count);
this.acinfo = AttributeCertificateInfo.GetInstance(seq[0]);
this.signatureAlgorithm = AlgorithmIdentifier.GetInstance(seq[1]);
this.signatureValue = DerBitString.GetInstance(seq[2]);
}
public AttributeCertificateInfo ACInfo
{
get { return acinfo; }
}
public AlgorithmIdentifier SignatureAlgorithm
{
get { return signatureAlgorithm; }
}
public DerBitString SignatureValue
{
get { return signatureValue; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* AttributeCertificate ::= Sequence {
* acinfo AttributeCertificateInfo,
* signatureAlgorithm AlgorithmIdentifier,
* signatureValue BIT STRING
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return new DerSequence(acinfo, signatureAlgorithm, signatureValue);
}
}
}

View File

@@ -0,0 +1,156 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
public class AttributeCertificateInfo
: Asn1Encodable
{
internal readonly DerInteger version;
internal readonly Holder holder;
internal readonly AttCertIssuer issuer;
internal readonly AlgorithmIdentifier signature;
internal readonly DerInteger serialNumber;
internal readonly AttCertValidityPeriod attrCertValidityPeriod;
internal readonly Asn1Sequence attributes;
internal readonly DerBitString issuerUniqueID;
internal readonly X509Extensions extensions;
public static AttributeCertificateInfo GetInstance(
Asn1TaggedObject obj,
bool isExplicit)
{
return GetInstance(Asn1Sequence.GetInstance(obj, isExplicit));
}
public static AttributeCertificateInfo GetInstance(
object obj)
{
if (obj is AttributeCertificateInfo)
{
return (AttributeCertificateInfo) obj;
}
if (obj is Asn1Sequence)
{
return new AttributeCertificateInfo((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
private AttributeCertificateInfo(
Asn1Sequence seq)
{
if (seq.Count < 7 || seq.Count > 9)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
this.version = DerInteger.GetInstance(seq[0]);
this.holder = Holder.GetInstance(seq[1]);
this.issuer = AttCertIssuer.GetInstance(seq[2]);
this.signature = AlgorithmIdentifier.GetInstance(seq[3]);
this.serialNumber = DerInteger.GetInstance(seq[4]);
this.attrCertValidityPeriod = AttCertValidityPeriod.GetInstance(seq[5]);
this.attributes = Asn1Sequence.GetInstance(seq[6]);
for (int i = 7; i < seq.Count; i++)
{
Asn1Encodable obj = (Asn1Encodable) seq[i];
if (obj is DerBitString)
{
this.issuerUniqueID = DerBitString.GetInstance(seq[i]);
}
else if (obj is Asn1Sequence || obj is X509Extensions)
{
this.extensions = X509Extensions.GetInstance(seq[i]);
}
}
}
public DerInteger Version
{
get { return version; }
}
public Holder Holder
{
get { return holder; }
}
public AttCertIssuer Issuer
{
get { return issuer; }
}
public AlgorithmIdentifier Signature
{
get { return signature; }
}
public DerInteger SerialNumber
{
get { return serialNumber; }
}
public AttCertValidityPeriod AttrCertValidityPeriod
{
get { return attrCertValidityPeriod; }
}
public Asn1Sequence Attributes
{
get { return attributes; }
}
public DerBitString IssuerUniqueID
{
get { return issuerUniqueID; }
}
public X509Extensions Extensions
{
get { return extensions; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* AttributeCertificateInfo ::= Sequence {
* version AttCertVersion -- version is v2,
* holder Holder,
* issuer AttCertIssuer,
* signature AlgorithmIdentifier,
* serialNumber CertificateSerialNumber,
* attrCertValidityPeriod AttCertValidityPeriod,
* attributes Sequence OF Attr,
* issuerUniqueID UniqueIdentifier OPTIONAL,
* extensions Extensions OPTIONAL
* }
*
* AttCertVersion ::= Integer { v2(1) }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector(
version, holder, issuer, signature, serialNumber,
attrCertValidityPeriod, attributes);
if (issuerUniqueID != null)
{
v.Add(issuerUniqueID);
}
if (extensions != null)
{
v.Add(extensions);
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,54 @@
using System.Collections;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
public class AttributeTable
{
private readonly Hashtable attributes;
public AttributeTable(
Hashtable attrs)
{
this.attributes = new Hashtable(attrs);
}
public AttributeTable(
Asn1EncodableVector v)
{
this.attributes = new Hashtable(v.Count);
for (int i = 0; i != v.Count; i++)
{
AttributeX509 a = AttributeX509.GetInstance(v[i]);
attributes.Add(a.AttrType, a);
}
}
public AttributeTable(
Asn1Set s)
{
this.attributes = new Hashtable(s.Count);
for (int i = 0; i != s.Count; i++)
{
AttributeX509 a = AttributeX509.GetInstance(s[i]);
attributes.Add(a.AttrType, a);
}
}
public AttributeX509 Get(
DerObjectIdentifier oid)
{
return (AttributeX509) attributes[oid];
}
public Hashtable ToHashtable()
{
return new Hashtable(attributes);
}
}
}

View File

@@ -0,0 +1,87 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The AuthorityInformationAccess object.
* <pre>
* id-pe-authorityInfoAccess OBJECT IDENTIFIER ::= { id-pe 1 }
*
* AuthorityInfoAccessSyntax ::=
* Sequence SIZE (1..MAX) OF AccessDescription
* AccessDescription ::= Sequence {
* accessMethod OBJECT IDENTIFIER,
* accessLocation GeneralName }
*
* id-ad OBJECT IDENTIFIER ::= { id-pkix 48 }
* id-ad-caIssuers OBJECT IDENTIFIER ::= { id-ad 2 }
* id-ad-ocsp OBJECT IDENTIFIER ::= { id-ad 1 }
* </pre>
*/
public class AuthorityInformationAccess
: Asn1Encodable
{
internal readonly DerObjectIdentifier accessMethod;
internal readonly GeneralName accessLocation;
public static AuthorityInformationAccess GetInstance(
object obj)
{
if (obj is AuthorityInformationAccess)
{
return (AuthorityInformationAccess) obj;
}
if (obj is Asn1Sequence)
{
return new AuthorityInformationAccess((Asn1Sequence) obj);
}
if (obj is X509Extension)
{
return GetInstance(X509Extension.ConvertValueToObject((X509Extension) obj));
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
private AuthorityInformationAccess(
Asn1Sequence seq)
{
foreach (DerSequence vec in seq)
{
if (vec.Count != 2)
{
throw new ArgumentException("wrong number of elements in inner sequence");
}
accessMethod = (DerObjectIdentifier) vec[0];
accessLocation = (GeneralName) vec[1];
}
}
/**
* create an AuthorityInformationAccess with the oid and location provided.
*/
public AuthorityInformationAccess(
DerObjectIdentifier oid,
GeneralName location)
{
accessMethod = oid;
accessLocation = location;
}
public override Asn1Object ToAsn1Object()
{
return new DerSequence(new DerSequence(accessMethod, accessLocation));
}
public override string ToString()
{
return ("AuthorityInformationAccess: Oid(" + this.accessMethod.Id + ")");
}
}
}

View File

@@ -0,0 +1,211 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
using Org.BouncyCastle.Crypto;
using Org.BouncyCastle.Crypto.Digests;
using Org.BouncyCastle.Math;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The AuthorityKeyIdentifier object.
* <pre>
* id-ce-authorityKeyIdentifier OBJECT IDENTIFIER ::= { id-ce 35 }
*
* AuthorityKeyIdentifier ::= Sequence {
* keyIdentifier [0] IMPLICIT KeyIdentifier OPTIONAL,
* authorityCertIssuer [1] IMPLICIT GeneralNames OPTIONAL,
* authorityCertSerialNumber [2] IMPLICIT CertificateSerialNumber OPTIONAL }
*
* KeyIdentifier ::= OCTET STRING
* </pre>
*
*/
public class AuthorityKeyIdentifier
: Asn1Encodable
{
internal readonly Asn1OctetString keyidentifier;
internal readonly GeneralNames certissuer;
internal readonly DerInteger certserno;
public static AuthorityKeyIdentifier GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static AuthorityKeyIdentifier GetInstance(
object obj)
{
if (obj is AuthorityKeyIdentifier)
{
return (AuthorityKeyIdentifier) obj;
}
if (obj is Asn1Sequence)
{
return new AuthorityKeyIdentifier((Asn1Sequence) obj);
}
if (obj is X509Extension)
{
return GetInstance(X509Extension.ConvertValueToObject((X509Extension) obj));
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
protected internal AuthorityKeyIdentifier(
Asn1Sequence seq)
{
foreach (Asn1TaggedObject o in seq)
{
switch (o.TagNo)
{
case 0:
this.keyidentifier = Asn1OctetString.GetInstance(o, false);
break;
case 1:
this.certissuer = GeneralNames.GetInstance(o, false);
break;
case 2:
this.certserno = DerInteger.GetInstance(o, false);
break;
default:
throw new ArgumentException("illegal tag");
}
}
}
/**
*
* Calulates the keyidentifier using a SHA1 hash over the BIT STRING
* from SubjectPublicKeyInfo as defined in RFC2459.
*
* Example of making a AuthorityKeyIdentifier:
* <pre>
* SubjectPublicKeyInfo apki = new SubjectPublicKeyInfo((ASN1Sequence)new ASN1InputStream(
* publicKey.getEncoded()).readObject());
* AuthorityKeyIdentifier aki = new AuthorityKeyIdentifier(apki);
* </pre>
*
**/
public AuthorityKeyIdentifier(
SubjectPublicKeyInfo spki)
{
IDigest digest = new Sha1Digest();
byte[] resBuf = new byte[digest.GetDigestSize()];
byte[] bytes = spki.PublicKeyData.GetBytes();
digest.BlockUpdate(bytes, 0, bytes.Length);
digest.DoFinal(resBuf, 0);
this.keyidentifier = new DerOctetString(resBuf);
}
/**
* create an AuthorityKeyIdentifier with the GeneralNames tag and
* the serial number provided as well.
*/
public AuthorityKeyIdentifier(
SubjectPublicKeyInfo spki,
GeneralNames name,
BigInteger serialNumber)
{
IDigest digest = new Sha1Digest();
byte[] resBuf = new byte[digest.GetDigestSize()];
byte[] bytes = spki.PublicKeyData.GetBytes();
digest.BlockUpdate(bytes, 0, bytes.Length);
digest.DoFinal(resBuf, 0);
this.keyidentifier = new DerOctetString(resBuf);
this.certissuer = name;
this.certserno = new DerInteger(serialNumber);
}
/**
* create an AuthorityKeyIdentifier with the GeneralNames tag and
* the serial number provided.
*/
public AuthorityKeyIdentifier(
GeneralNames name,
BigInteger serialNumber)
{
this.keyidentifier = null;
this.certissuer = GeneralNames.GetInstance(name.ToAsn1Object());
this.certserno = new DerInteger(serialNumber);
}
/**
* create an AuthorityKeyIdentifier with a precomputed key identifier
*/
public AuthorityKeyIdentifier(
byte[] keyIdentifier)
{
this.keyidentifier = new DerOctetString(keyIdentifier);
this.certissuer = null;
this.certserno = null;
}
/**
* create an AuthorityKeyIdentifier with a precomupted key identifier
* and the GeneralNames tag and the serial number provided as well.
*/
public AuthorityKeyIdentifier(
byte[] keyIdentifier,
GeneralNames name,
BigInteger serialNumber)
{
this.keyidentifier = new DerOctetString(keyIdentifier);
this.certissuer = GeneralNames.GetInstance(name.ToAsn1Object());
this.certserno = new DerInteger(serialNumber);
}
public byte[] GetKeyIdentifier()
{
return keyidentifier == null ? null : keyidentifier.GetOctets();
}
public GeneralNames AuthorityCertIssuer
{
get { return certissuer; }
}
public BigInteger AuthorityCertSerialNumber
{
get { return certserno == null ? null : certserno.Value; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (keyidentifier != null)
{
v.Add(new DerTaggedObject(false, 0, keyidentifier));
}
if (certissuer != null)
{
v.Add(new DerTaggedObject(false, 1, certissuer));
}
if (certserno != null)
{
v.Add(new DerTaggedObject(false, 2, certserno));
}
return new DerSequence(v);
}
public override string ToString()
{
return ("AuthorityKeyIdentifier: KeyID(" + this.keyidentifier.GetOctets() + ")");
}
}
}

View File

@@ -0,0 +1,133 @@
using System;
using Org.BouncyCastle.Asn1;
using Org.BouncyCastle.Math;
namespace Org.BouncyCastle.Asn1.X509
{
public class BasicConstraints
: Asn1Encodable
{
private readonly DerBoolean cA;
private readonly DerInteger pathLenConstraint;
public static BasicConstraints GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static BasicConstraints GetInstance(
object obj)
{
if (obj == null || obj is BasicConstraints)
{
return (BasicConstraints) obj;
}
if (obj is Asn1Sequence)
{
return new BasicConstraints((Asn1Sequence) obj);
}
if (obj is X509Extension)
{
return GetInstance(X509Extension.ConvertValueToObject((X509Extension) obj));
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
private BasicConstraints(
Asn1Sequence seq)
{
if (seq.Count > 0)
{
if (seq[0] is DerBoolean)
{
this.cA = DerBoolean.GetInstance(seq[0]);
}
else
{
this.pathLenConstraint = DerInteger.GetInstance(seq[0]);
}
if (seq.Count > 1)
{
if (this.cA == null)
throw new ArgumentException("wrong sequence in constructor", "seq");
this.pathLenConstraint = DerInteger.GetInstance(seq[1]);
}
}
}
public BasicConstraints(
bool cA)
{
if (cA)
{
this.cA = DerBoolean.True;
}
}
/**
* create a cA=true object for the given path length constraint.
*
* @param pathLenConstraint
*/
public BasicConstraints(
int pathLenConstraint)
{
this.cA = DerBoolean.True;
this.pathLenConstraint = new DerInteger(pathLenConstraint);
}
public bool IsCA()
{
return cA != null && cA.IsTrue;
}
public BigInteger PathLenConstraint
{
get { return pathLenConstraint == null ? null : pathLenConstraint.Value; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* BasicConstraints := Sequence {
* cA Boolean DEFAULT FALSE,
* pathLenConstraint Integer (0..MAX) OPTIONAL
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (cA != null)
{
v.Add(cA);
}
if (pathLenConstraint != null) // yes some people actually do this when cA is false...
{
v.Add(pathLenConstraint);
}
return new DerSequence(v);
}
public override string ToString()
{
if (pathLenConstraint == null)
{
return "BasicConstraints: isCa(" + this.IsCA() + ")";
}
return "BasicConstraints: isCa(" + this.IsCA() + "), pathLenConstraint = " + pathLenConstraint.Value;
}
}
}

View File

@@ -0,0 +1,93 @@
using System;
using System.Text;
using Org.BouncyCastle.Utilities;
namespace Org.BouncyCastle.Asn1.X509
{
public class CrlDistPoint
: Asn1Encodable
{
internal readonly Asn1Sequence seq;
public static CrlDistPoint GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static CrlDistPoint GetInstance(
object obj)
{
if (obj is CrlDistPoint || obj == null)
{
return (CrlDistPoint) obj;
}
if (obj is Asn1Sequence)
{
return new CrlDistPoint((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
private CrlDistPoint(
Asn1Sequence seq)
{
this.seq = seq;
}
public CrlDistPoint(
DistributionPoint[] points)
{
seq = new DerSequence(points);
}
/**
* Return the distribution points making up the sequence.
*
* @return DistributionPoint[]
*/
public DistributionPoint[] GetDistributionPoints()
{
DistributionPoint[] dp = new DistributionPoint[seq.Count];
for (int i = 0; i != seq.Count; ++i)
{
dp[i] = DistributionPoint.GetInstance(seq[i]);
}
return dp;
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* CrlDistPoint ::= Sequence SIZE {1..MAX} OF DistributionPoint
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return seq;
}
public override string ToString()
{
StringBuilder buf = new StringBuilder();
string sep = Platform.NewLine;
buf.Append("CRLDistPoint:");
buf.Append(sep);
DistributionPoint[] dp = GetDistributionPoints();
for (int i = 0; i != dp.Length; i++)
{
buf.Append(" ");
buf.Append(dp[i]);
buf.Append(sep);
}
return buf.ToString();
}
}
}

View File

@@ -0,0 +1,30 @@
using Org.BouncyCastle.Math;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The CRLNumber object.
* <pre>
* CRLNumber::= Integer(0..MAX)
* </pre>
*/
public class CrlNumber
: DerInteger
{
public CrlNumber(
BigInteger number)
: base(number)
{
}
public BigInteger Number
{
get { return PositiveValue; }
}
public override string ToString()
{
return "CRLNumber: " + Number;
}
}
}

View File

@@ -0,0 +1,61 @@
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The CRLReason enumeration.
* <pre>
* CRLReason ::= Enumerated {
* unspecified (0),
* keyCompromise (1),
* cACompromise (2),
* affiliationChanged (3),
* superseded (4),
* cessationOfOperation (5),
* certificateHold (6),
* removeFromCRL (8),
* privilegeWithdrawn (9),
* aACompromise (10)
* }
* </pre>
*/
public class CrlReason
: DerEnumerated
{
public const int Unspecified = 0;
public const int KeyCompromise = 1;
public const int CACompromise = 2;
public const int AffiliationChanged = 3;
public const int Superseded = 4;
public const int CessationOfOperation = 5;
public const int CertificateHold = 6;
// 7 -> Unknown
public const int RemoveFromCrl = 8;
public const int PrivilegeWithdrawn = 9;
public const int AACompromise = 10;
private static readonly string[] ReasonString = new string[]
{
"Unspecified", "KeyCompromise", "CACompromise", "AffiliationChanged",
"Superseded", "CessationOfOperation", "CertificateHold", "Unknown",
"RemoveFromCrl", "PrivilegeWithdrawn", "AACompromise"
};
public CrlReason(
int reason)
: base(reason)
{
}
public CrlReason(
DerEnumerated reason)
: base(reason.Value.IntValue)
{
}
public override string ToString()
{
int reason = Value.IntValue;
string str = (reason < 0 || reason > 10) ? "Invalid" : ReasonString[reason];
return "CrlReason: " + str;
}
}
}

View File

@@ -0,0 +1,20 @@
namespace Org.BouncyCastle.Asn1.X509
{
/**
* CertPolicyId, used in the CertificatePolicies and PolicyMappings
* X509V3 Extensions.
*
* <pre>
* CertPolicyId ::= OBJECT IDENTIFIER
* </pre>
*/
public class CertPolicyID
: DerObjectIdentifier
{
public CertPolicyID(
string id)
: base(id)
{
}
}
}

View File

@@ -0,0 +1,112 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* PKIX RFC-2459
*
* The X.509 v2 CRL syntax is as follows. For signature calculation,
* the data that is to be signed is ASN.1 Der encoded.
*
* <pre>
* CertificateList ::= Sequence {
* tbsCertList TbsCertList,
* signatureAlgorithm AlgorithmIdentifier,
* signatureValue BIT STRING }
* </pre>
*/
public class CertificateList
: Asn1Encodable
{
private readonly TbsCertificateList tbsCertList;
private readonly AlgorithmIdentifier sigAlgID;
private readonly DerBitString sig;
public static CertificateList GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static CertificateList GetInstance(
object obj)
{
if (obj is CertificateList)
{
return (CertificateList) obj;
}
if (obj is Asn1Sequence)
{
return new CertificateList((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
private CertificateList(
Asn1Sequence seq)
{
if (seq.Count != 3)
throw new ArgumentException("sequence wrong size for CertificateList", "seq");
tbsCertList = TbsCertificateList.GetInstance(seq[0]);
sigAlgID = AlgorithmIdentifier.GetInstance(seq[1]);
sig = DerBitString.GetInstance(seq[2]);
}
public TbsCertificateList TbsCertList
{
get { return tbsCertList; }
}
public CrlEntry[] GetRevokedCertificates()
{
return tbsCertList.GetRevokedCertificates();
}
public IEnumerable GetRevokedCertificateEnumeration()
{
return tbsCertList.GetRevokedCertificateEnumeration();
}
public AlgorithmIdentifier SignatureAlgorithm
{
get { return sigAlgID; }
}
public DerBitString Signature
{
get { return sig; }
}
public int Version
{
get { return tbsCertList.Version; }
}
public X509Name Issuer
{
get { return tbsCertList.Issuer; }
}
public Time ThisUpdate
{
get { return tbsCertList.ThisUpdate; }
}
public Time NextUpdate
{
get { return tbsCertList.NextUpdate; }
}
public override Asn1Object ToAsn1Object()
{
return new DerSequence(tbsCertList, sigAlgID, sig);
}
}
}

View File

@@ -0,0 +1,160 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* This class helps to support crossCerfificatePairs in a LDAP directory
* according RFC 2587
*
* <pre>
* crossCertificatePairATTRIBUTE::={
* WITH SYNTAX CertificatePair
* EQUALITY MATCHING RULE certificatePairExactMatch
* ID joint-iso-ccitt(2) ds(5) attributeType(4) crossCertificatePair(40)}
* </pre>
*
* <blockquote> The forward elements of the crossCertificatePair attribute of a
* CA's directory entry shall be used to store all, except self-issued
* certificates issued to this CA. Optionally, the reverse elements of the
* crossCertificatePair attribute, of a CA's directory entry may contain a
* subset of certificates issued by this CA to other CAs. When both the forward
* and the reverse elements are present in a single attribute value, issuer name
* in one certificate shall match the subject name in the other and vice versa,
* and the subject public key in one certificate shall be capable of verifying
* the digital signature on the other certificate and vice versa.
*
* When a reverse element is present, the forward element value and the reverse
* element value need not be stored in the same attribute value; in other words,
* they can be stored in either a single attribute value or two attribute
* values. </blockquote>
*
* <pre>
* CertificatePair ::= SEQUENCE {
* forward [0] Certificate OPTIONAL,
* reverse [1] Certificate OPTIONAL,
* -- at least one of the pair shall be present -- }
* </pre>
*/
public class CertificatePair
: Asn1Encodable
{
private X509CertificateStructure forward, reverse;
public static CertificatePair GetInstance(
object obj)
{
if (obj == null || obj is CertificatePair)
{
return (CertificatePair) obj;
}
if (obj is Asn1Sequence)
{
return new CertificatePair((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from Asn1Sequence.
* <p/>
* The sequence is of type CertificatePair:
* <p/>
* <pre>
* CertificatePair ::= SEQUENCE {
* forward [0] Certificate OPTIONAL,
* reverse [1] Certificate OPTIONAL,
* -- at least one of the pair shall be present -- }
* </pre>
*
* @param seq The ASN.1 sequence.
*/
private CertificatePair(
Asn1Sequence seq)
{
if (seq.Count != 1 && seq.Count != 2)
{
throw new ArgumentException("Bad sequence size: " + seq.Count, "seq");
}
foreach (object obj in seq)
{
Asn1TaggedObject o = Asn1TaggedObject.GetInstance(obj);
if (o.TagNo == 0)
{
forward = X509CertificateStructure.GetInstance(o, true);
}
else if (o.TagNo == 1)
{
reverse = X509CertificateStructure.GetInstance(o, true);
}
else
{
throw new ArgumentException("Bad tag number: " + o.TagNo);
}
}
}
/**
* Constructor from a given details.
*
* @param forward Certificates issued to this CA.
* @param reverse Certificates issued by this CA to other CAs.
*/
public CertificatePair(
X509CertificateStructure forward,
X509CertificateStructure reverse)
{
this.forward = forward;
this.reverse = reverse;
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <p/>
* Returns:
* <p/>
* <pre>
* CertificatePair ::= SEQUENCE {
* forward [0] Certificate OPTIONAL,
* reverse [1] Certificate OPTIONAL,
* -- at least one of the pair shall be present -- }
* </pre>
*
* @return a DERObject
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector vec = new Asn1EncodableVector();
if (forward != null)
{
vec.Add(new DerTaggedObject(0, forward));
}
if (reverse != null)
{
vec.Add(new DerTaggedObject(1, reverse));
}
return new DerSequence(vec);
}
/**
* @return Returns the forward.
*/
public X509CertificateStructure Forward
{
get { return forward; }
}
/**
* @return Returns the reverse.
*/
public X509CertificateStructure Reverse
{
get { return reverse; }
}
}
}

View File

@@ -0,0 +1,77 @@
using System;
using System.Collections;
using Org.BouncyCastle.Math;
namespace Org.BouncyCastle.Asn1.X509
{
public class DsaParameter
: Asn1Encodable
{
internal readonly DerInteger p, q, g;
public static DsaParameter GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static DsaParameter GetInstance(
object obj)
{
if(obj == null || obj is DsaParameter)
{
return (DsaParameter) obj;
}
if(obj is Asn1Sequence)
{
return new DsaParameter((Asn1Sequence) obj);
}
throw new ArgumentException("Invalid DsaParameter: " + obj.GetType().Name);
}
public DsaParameter(
BigInteger p,
BigInteger q,
BigInteger g)
{
this.p = new DerInteger(p);
this.q = new DerInteger(q);
this.g = new DerInteger(g);
}
private DsaParameter(
Asn1Sequence seq)
{
if (seq.Count != 3)
throw new ArgumentException("Bad sequence size: " + seq.Count, "seq");
this.p = DerInteger.GetInstance(seq[0]);
this.q = DerInteger.GetInstance(seq[1]);
this.g = DerInteger.GetInstance(seq[2]);
}
public BigInteger P
{
get { return p.PositiveValue; }
}
public BigInteger Q
{
get { return q.PositiveValue; }
}
public BigInteger G
{
get { return g.PositiveValue; }
}
public override Asn1Object ToAsn1Object()
{
return new DerSequence(p, q, g);
}
}
}

View File

@@ -0,0 +1,76 @@
using System;
using System.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The DigestInfo object.
* <pre>
* DigestInfo::=Sequence{
* digestAlgorithm AlgorithmIdentifier,
* digest OCTET STRING }
* </pre>
*/
public class DigestInfo
: Asn1Encodable
{
private readonly byte[] digest;
private readonly AlgorithmIdentifier algID;
public static DigestInfo GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static DigestInfo GetInstance(
object obj)
{
if (obj is DigestInfo)
{
return (DigestInfo) obj;
}
if (obj is Asn1Sequence)
{
return new DigestInfo((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public DigestInfo(
AlgorithmIdentifier algID,
byte[] digest)
{
this.digest = digest;
this.algID = algID;
}
private DigestInfo(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Wrong number of elements in sequence", "seq");
algID = AlgorithmIdentifier.GetInstance(seq[0]);
digest = Asn1OctetString.GetInstance(seq[1]).GetOctets();
}
public AlgorithmIdentifier AlgorithmID
{
get { return algID; }
}
public byte[] GetDigest()
{
return digest;
}
public override Asn1Object ToAsn1Object()
{
return new DerSequence(algID, new DerOctetString(digest));
}
}
}

View File

@@ -0,0 +1,172 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* <code>DisplayText</code> class, used in
* <code>CertificatePolicies</code> X509 V3 extensions (in policy qualifiers).
*
* <p>It stores a string in a chosen encoding.
* <pre>
* DisplayText ::= CHOICE {
* ia5String IA5String (SIZE (1..200)),
* visibleString VisibleString (SIZE (1..200)),
* bmpString BMPString (SIZE (1..200)),
* utf8String UTF8String (SIZE (1..200)) }
* </pre></p>
* @see PolicyQualifierInfo
* @see PolicyInformation
*/
public class DisplayText
: Asn1Encodable
{
/**
* Constant corresponding to ia5String encoding.
*
*/
public const int ContentTypeIA5String = 0;
/**
* Constant corresponding to bmpString encoding.
*
*/
public const int ContentTypeBmpString = 1;
/**
* Constant corresponding to utf8String encoding.
*
*/
public const int ContentTypeUtf8String = 2;
/**
* Constant corresponding to visibleString encoding.
*
*/
public const int ContentTypeVisibleString = 3;
/**
* Describe constant <code>DisplayTextMaximumSize</code> here.
*
*/
public const int DisplayTextMaximumSize = 200;
internal readonly int contentType;
internal readonly IAsn1String contents;
/**
* Creates a new <code>DisplayText</code> instance.
*
* @param type the desired encoding type for the text.
* @param text the text to store. Strings longer than 200
* characters are truncated.
*/
public DisplayText(
int type,
string text)
{
if (text.Length > DisplayTextMaximumSize)
{
// RFC3280 limits these strings to 200 chars
// truncate the string
text = text.Substring(0, DisplayTextMaximumSize);
}
contentType = type;
switch (type)
{
case ContentTypeIA5String:
contents = (IAsn1String)new DerIA5String (text);
break;
case ContentTypeUtf8String:
contents = (IAsn1String)new DerUtf8String(text);
break;
case ContentTypeVisibleString:
contents = (IAsn1String)new DerVisibleString(text);
break;
case ContentTypeBmpString:
contents = (IAsn1String)new DerBmpString(text);
break;
default:
contents = (IAsn1String)new DerUtf8String(text);
break;
}
}
// /**
// * return true if the passed in string can be represented without
// * loss as a PrintableString, false otherwise.
// */
// private bool CanBePrintable(
// string str)
// {
// for (int i = str.Length - 1; i >= 0; i--)
// {
// if (str[i] > 0x007f)
// {
// return false;
// }
// }
//
// return true;
// }
/**
* Creates a new <code>DisplayText</code> instance.
*
* @param text the text to encapsulate. Strings longer than 200
* characters are truncated.
*/
public DisplayText(
string text)
{
// by default use UTF8String
if (text.Length > DisplayTextMaximumSize)
{
text = text.Substring(0, DisplayTextMaximumSize);
}
contentType = ContentTypeUtf8String;
contents = new DerUtf8String(text);
}
/**
* Creates a new <code>DisplayText</code> instance.
* <p>Useful when reading back a <code>DisplayText</code> class
* from it's Asn1Encodable form.</p>
*
* @param contents an <code>Asn1Encodable</code> instance.
*/
public DisplayText(
IAsn1String contents)
{
this.contents = contents;
}
public static DisplayText GetInstance(
object obj)
{
if (obj is IAsn1String)
{
return new DisplayText((IAsn1String) obj);
}
if (obj is DisplayText)
{
return (DisplayText) obj;
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public override Asn1Object ToAsn1Object()
{
return (Asn1Object) contents;
}
/**
* Returns the stored <code>string</code> object.
*
* @return the stored text as a <code>string</code>.
*/
public string GetString()
{
return contents.GetString();
}
}
}

View File

@@ -0,0 +1,161 @@
using System;
using System.Text;
using Org.BouncyCastle.Utilities;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The DistributionPoint object.
* <pre>
* DistributionPoint ::= Sequence {
* distributionPoint [0] DistributionPointName OPTIONAL,
* reasons [1] ReasonFlags OPTIONAL,
* cRLIssuer [2] GeneralNames OPTIONAL
* }
* </pre>
*/
public class DistributionPoint
: Asn1Encodable
{
internal readonly DistributionPointName distributionPoint;
internal readonly ReasonFlags reasons;
internal readonly GeneralNames cRLIssuer;
public static DistributionPoint GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static DistributionPoint GetInstance(
object obj)
{
if(obj == null || obj is DistributionPoint)
{
return (DistributionPoint) obj;
}
if(obj is Asn1Sequence)
{
return new DistributionPoint((Asn1Sequence) obj);
}
throw new ArgumentException("Invalid DistributionPoint: " + obj.GetType().Name);
}
private DistributionPoint(
Asn1Sequence seq)
{
for (int i = 0; i != seq.Count; i++)
{
Asn1TaggedObject t = Asn1TaggedObject.GetInstance(seq[i]);
switch (t.TagNo)
{
case 0:
distributionPoint = DistributionPointName.GetInstance(t, true);
break;
case 1:
reasons = new ReasonFlags(DerBitString.GetInstance(t, false));
break;
case 2:
cRLIssuer = GeneralNames.GetInstance(t, false);
break;
}
}
}
public DistributionPoint(
DistributionPointName distributionPointName,
ReasonFlags reasons,
GeneralNames crlIssuer)
{
this.distributionPoint = distributionPointName;
this.reasons = reasons;
this.cRLIssuer = crlIssuer;
}
public DistributionPointName DistributionPointName
{
get { return distributionPoint; }
}
public ReasonFlags Reasons
{
get { return reasons; }
}
public GeneralNames CrlIssuer
{
get { return cRLIssuer; }
}
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (distributionPoint != null)
{
//
// as this is a CHOICE it must be explicitly tagged
//
v.Add(new DerTaggedObject(0, distributionPoint));
}
if (reasons != null)
{
v.Add(new DerTaggedObject(false, 1, reasons));
}
if (cRLIssuer != null)
{
v.Add(new DerTaggedObject(false, 2, cRLIssuer));
}
return new DerSequence(v);
}
public override string ToString()
{
string sep = Platform.NewLine;
StringBuilder buf = new StringBuilder();
buf.Append("DistributionPoint: [");
buf.Append(sep);
if (distributionPoint != null)
{
appendObject(buf, sep, "distributionPoint", distributionPoint.ToString());
}
if (reasons != null)
{
appendObject(buf, sep, "reasons", reasons.ToString());
}
if (cRLIssuer != null)
{
appendObject(buf, sep, "cRLIssuer", cRLIssuer.ToString());
}
buf.Append("]");
buf.Append(sep);
return buf.ToString();
}
private void appendObject(
StringBuilder buf,
string sep,
string name,
string val)
{
string indent = " ";
buf.Append(indent);
buf.Append(name);
buf.Append(":");
buf.Append(sep);
buf.Append(indent);
buf.Append(indent);
buf.Append(val);
buf.Append(sep);
}
}
}

View File

@@ -0,0 +1,130 @@
using System;
using System.Text;
using Org.BouncyCastle.Utilities;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The DistributionPointName object.
* <pre>
* DistributionPointName ::= CHOICE {
* fullName [0] GeneralNames,
* nameRelativeToCRLIssuer [1] RelativeDistinguishedName
* }
* </pre>
*/
public class DistributionPointName
: Asn1Encodable
{
internal readonly Asn1Encodable name;
internal readonly int type;
public const int FullName = 0;
public const int NameRelativeToCrlIssuer = 1;
public static DistributionPointName GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1TaggedObject.GetInstance(obj, explicitly));
}
public static DistributionPointName GetInstance(
object obj)
{
if (obj == null || obj is DistributionPointName)
{
return (DistributionPointName) obj;
}
if (obj is Asn1TaggedObject)
{
return new DistributionPointName((Asn1TaggedObject) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public DistributionPointName(
int type,
Asn1Encodable name)
{
this.type = type;
this.name = name;
}
public DistributionPointName(
GeneralNames name)
: this(FullName, name)
{
}
public int PointType
{
get { return type; }
}
public Asn1Encodable Name
{
get { return name; }
}
public DistributionPointName(
Asn1TaggedObject obj)
{
this.type = obj.TagNo;
if (type == FullName)
{
this.name = GeneralNames.GetInstance(obj, false);
}
else
{
this.name = Asn1Set.GetInstance(obj, false);
}
}
public override Asn1Object ToAsn1Object()
{
return new DerTaggedObject(false, type, name);
}
public override string ToString()
{
string sep = Platform.NewLine;
StringBuilder buf = new StringBuilder();
buf.Append("DistributionPointName: [");
buf.Append(sep);
if (type == FullName)
{
appendObject(buf, sep, "fullName", name.ToString());
}
else
{
appendObject(buf, sep, "nameRelativeToCRLIssuer", name.ToString());
}
buf.Append("]");
buf.Append(sep);
return buf.ToString();
}
private void appendObject(
StringBuilder buf,
string sep,
string name,
string val)
{
string indent = " ";
buf.Append(indent);
buf.Append(name);
buf.Append(":");
buf.Append(sep);
buf.Append(indent);
buf.Append(indent);
buf.Append(val);
buf.Append(sep);
}
}
}

View File

@@ -0,0 +1,107 @@
using System;
using System.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The extendedKeyUsage object.
* <pre>
* extendedKeyUsage ::= Sequence SIZE (1..MAX) OF KeyPurposeId
* </pre>
*/
public class ExtendedKeyUsage
: Asn1Encodable
{
internal readonly Hashtable usageTable = new Hashtable();
internal readonly Asn1Sequence seq;
public static ExtendedKeyUsage GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static ExtendedKeyUsage GetInstance(
object obj)
{
if (obj is ExtendedKeyUsage)
{
return (ExtendedKeyUsage) obj;
}
if (obj is Asn1Sequence)
{
return new ExtendedKeyUsage((Asn1Sequence) obj);
}
if (obj is X509Extension)
{
return GetInstance(X509Extension.ConvertValueToObject((X509Extension) obj));
}
throw new ArgumentException("Invalid ExtendedKeyUsage: " + obj.GetType().Name);
}
private ExtendedKeyUsage(
Asn1Sequence seq)
{
this.seq = seq;
foreach (object o in seq)
{
if (!(o is DerObjectIdentifier))
throw new ArgumentException("Only DerObjectIdentifier instances allowed in ExtendedKeyUsage.");
this.usageTable.Add(o, o);
}
}
public ExtendedKeyUsage(
ArrayList usages)
{
Asn1EncodableVector v = new Asn1EncodableVector();
foreach (Asn1Object o in usages)
{
v.Add(o);
this.usageTable.Add(o, o);
}
this.seq = new DerSequence(v);
}
public bool HasKeyPurposeId(
KeyPurposeID keyPurposeId)
{
return usageTable[keyPurposeId] != null;
}
/**
* Returns all extended key usages.
* The returned ArrayList contains DerObjectIdentifier instances.
* @return An ArrayList with all key purposes.
*/
public ArrayList GetUsages()
{
return new ArrayList(usageTable.Values);
}
[Obsolete("Use 'Count' property instead")]
public int Size
{
get { return usageTable.Count; }
}
public int Count
{
get { return usageTable.Count; }
}
public override Asn1Object ToAsn1Object()
{
return seq;
}
}
}

View File

@@ -0,0 +1,240 @@
using System;
using System.Text;
using Org.BouncyCastle.Utilities.Net;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The GeneralName object.
* <pre>
* GeneralName ::= CHOICE {
* otherName [0] OtherName,
* rfc822Name [1] IA5String,
* dNSName [2] IA5String,
* x400Address [3] ORAddress,
* directoryName [4] Name,
* ediPartyName [5] EDIPartyName,
* uniformResourceIdentifier [6] IA5String,
* iPAddress [7] OCTET STRING,
* registeredID [8] OBJECT IDENTIFIER}
*
* OtherName ::= Sequence {
* type-id OBJECT IDENTIFIER,
* value [0] EXPLICIT ANY DEFINED BY type-id }
*
* EDIPartyName ::= Sequence {
* nameAssigner [0] DirectoryString OPTIONAL,
* partyName [1] DirectoryString }
* </pre>
*/
public class GeneralName
: Asn1Encodable
{
public const int OtherName = 0;
public const int Rfc822Name = 1;
public const int DnsName = 2;
public const int X400Address = 3;
public const int DirectoryName = 4;
public const int EdiPartyName = 5;
public const int UniformResourceIdentifier = 6;
public const int IPAddress = 7;
public const int RegisteredID = 8;
internal readonly Asn1Encodable obj;
internal readonly int tag;
public GeneralName(
X509Name directoryName)
{
this.obj = directoryName;
this.tag = 4;
}
/**
* When the subjectAltName extension contains an Internet mail address,
* the address MUST be included as an rfc822Name. The format of an
* rfc822Name is an "addr-spec" as defined in RFC 822 [RFC 822].
*
* When the subjectAltName extension contains a domain name service
* label, the domain name MUST be stored in the dNSName (an IA5String).
* The name MUST be in the "preferred name syntax," as specified by RFC
* 1034 [RFC 1034].
*
* When the subjectAltName extension contains a URI, the name MUST be
* stored in the uniformResourceIdentifier (an IA5String). The name MUST
* be a non-relative URL, and MUST follow the URL syntax and encoding
* rules specified in [RFC 1738]. The name must include both a scheme
* (e.g., "http" or "ftp") and a scheme-specific-part. The scheme-
* specific-part must include a fully qualified domain name or IP
* address as the host.
*
* When the subjectAltName extension contains a iPAddress, the address
* MUST be stored in the octet string in "network byte order," as
* specified in RFC 791 [RFC 791]. The least significant bit (LSB) of
* each octet is the LSB of the corresponding byte in the network
* address. For IP Version 4, as specified in RFC 791, the octet string
* MUST contain exactly four octets. For IP Version 6, as specified in
* RFC 1883, the octet string MUST contain exactly sixteen octets [RFC
* 1883].
*/
public GeneralName(
Asn1Object name,
int tag)
{
this.obj = name;
this.tag = tag;
}
public GeneralName(
int tag,
Asn1Encodable name)
{
this.obj = name;
this.tag = tag;
}
/**
* Create a GeneralName for the given tag from the passed in String.
* <p>
* This constructor can handle:
* <ul>
* <li>rfc822Name</li>
* <li>iPAddress</li>
* <li>directoryName</li>
* <li>dNSName</li>
* <li>uniformResourceIdentifier</li>
* <li>registeredID</li>
* </ul>
* For x400Address, otherName and ediPartyName there is no common string
* format defined.
* </p><p>
* Note: A directory name can be encoded in different ways into a byte
* representation. Be aware of this if the byte representation is used for
* comparing results.
* </p>
*
* @param tag tag number
* @param name string representation of name
* @throws ArgumentException if the string encoding is not correct or
* not supported.
*/
public GeneralName(
int tag,
string name)
{
this.tag = tag;
if (tag == Rfc822Name || tag == DnsName || tag == UniformResourceIdentifier)
{
this.obj = new DerIA5String(name);
}
else if (tag == RegisteredID)
{
this.obj = new DerObjectIdentifier(name);
}
else if (tag == DirectoryName)
{
this.obj = new X509Name(name);
}
else if (tag == IPAddress)
{
if (!Org.BouncyCastle.Utilities.Net.IPAddress.IsValid(name))
throw new ArgumentException("IP Address is invalid", "name");
this.obj = new DerOctetString(Encoding.UTF8.GetBytes(name));
}
else
{
throw new ArgumentException("can't process string for tag: " + tag, "tag");
}
}
public static GeneralName GetInstance(
object obj)
{
if (obj == null || obj is GeneralName)
{
return (GeneralName) obj;
}
if (obj is Asn1TaggedObject)
{
Asn1TaggedObject tagObj = (Asn1TaggedObject) obj;
int tag = tagObj.TagNo;
switch (tag)
{
case OtherName:
return new GeneralName(tag, Asn1Sequence.GetInstance(tagObj, false));
case Rfc822Name:
return new GeneralName(tag, DerIA5String.GetInstance(tagObj, false));
case DnsName:
return new GeneralName(tag, DerIA5String.GetInstance(tagObj, false));
case X400Address:
throw new ArgumentException("unknown tag: " + tag);
case DirectoryName:
return new GeneralName(tag, Asn1Sequence.GetInstance(tagObj, true));
case EdiPartyName:
return new GeneralName(tag, Asn1Sequence.GetInstance(tagObj, false));
case UniformResourceIdentifier:
return new GeneralName(tag, DerIA5String.GetInstance(tagObj, false));
case IPAddress:
return new GeneralName(tag, Asn1OctetString.GetInstance(tagObj, false));
case RegisteredID:
return new GeneralName(tag, DerObjectIdentifier.GetInstance(tagObj, false));
}
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
public static GeneralName GetInstance(
Asn1TaggedObject tagObj,
bool explicitly)
{
return GetInstance(Asn1TaggedObject.GetInstance(tagObj, explicitly));
}
public int TagNo
{
get { return tag; }
}
public Asn1Encodable Name
{
get { return obj; }
}
public override string ToString()
{
StringBuilder buf = new StringBuilder();
buf.Append(tag);
buf.Append(": ");
switch (tag)
{
case Rfc822Name:
case DnsName:
case UniformResourceIdentifier:
buf.Append(DerIA5String.GetInstance(obj).GetString());
break;
case DirectoryName:
buf.Append(X509Name.GetInstance(obj).ToString());
break;
default:
buf.Append(obj.ToString());
break;
}
return buf.ToString();
}
public override Asn1Object ToAsn1Object()
{
// Explicitly tagged if DirectoryName
return new DerTaggedObject(tag == 4, tag, obj);
}
}
}

View File

@@ -0,0 +1,91 @@
using System;
using System.Text;
using Org.BouncyCastle.Utilities;
namespace Org.BouncyCastle.Asn1.X509
{
public class GeneralNames
: Asn1Encodable
{
private readonly Asn1Sequence seq;
public static GeneralNames GetInstance(
object obj)
{
if (obj == null || obj is GeneralNames)
{
return (GeneralNames) obj;
}
if (obj is Asn1Sequence)
{
return new GeneralNames((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public static GeneralNames GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
/// <summary>Construct a GeneralNames object containing one GeneralName.</summary>
/// <param name="name">The name to be contained.</param>
public GeneralNames(
GeneralName name)
{
this.seq = new DerSequence(name);
}
private GeneralNames(
Asn1Sequence seq)
{
this.seq = seq;
}
public GeneralName[] GetNames()
{
GeneralName[] names = new GeneralName[seq.Count];
for (int i = 0; i != seq.Count; i++)
{
names[i] = GeneralName.GetInstance(seq[i]);
}
return names;
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* GeneralNames ::= Sequence SIZE {1..MAX} OF GeneralName
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return seq;
}
public override string ToString()
{
StringBuilder buf = new StringBuilder();
string sep = Platform.NewLine;
GeneralName[] names = GetNames();
buf.Append("GeneralNames:");
buf.Append(sep);
for (int i = 0; i != names.Length; i++)
{
buf.Append(" ");
buf.Append(names[i]);
buf.Append(sep);
}
return buf.ToString();
}
}
}

View File

@@ -0,0 +1,177 @@
using System;
using Org.BouncyCastle.Math;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Class for containing a restriction object subtrees in NameConstraints. See
* RFC 3280.
*
* <pre>
*
* GeneralSubtree ::= SEQUENCE
* {
* baseName GeneralName,
* minimum [0] BaseDistance DEFAULT 0,
* maximum [1] BaseDistance OPTIONAL
* }
* </pre>
*
* @see org.bouncycastle.asn1.x509.NameConstraints
*
*/
public class GeneralSubtree
: Asn1Encodable
{
private readonly GeneralName baseName;
private readonly DerInteger minimum;
private readonly DerInteger maximum;
private GeneralSubtree(
Asn1Sequence seq)
{
baseName = GeneralName.GetInstance(seq[0]);
switch (seq.Count)
{
case 1:
break;
case 2:
{
Asn1TaggedObject o = Asn1TaggedObject.GetInstance(seq[1]);
switch (o.TagNo)
{
case 0:
minimum = DerInteger.GetInstance(o, false);
break;
case 1:
maximum = DerInteger.GetInstance(o, false);
break;
default:
throw new ArgumentException("Bad tag number: " + o.TagNo);
}
break;
}
case 3:
{
minimum = DerInteger.GetInstance(Asn1TaggedObject.GetInstance(seq[1]));
maximum = DerInteger.GetInstance(Asn1TaggedObject.GetInstance(seq[2]));
break;
}
default:
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
}
/**
* Constructor from a given details.
*
* According RFC 3280, the minimum and maximum fields are not used with any
* name forms, thus minimum MUST be zero, and maximum MUST be absent.
* <p>
* If minimum is <code>null</code>, zero is assumed, if
* maximum is <code>null</code>, maximum is absent.</p>
*
* @param baseName
* A restriction.
* @param minimum
* Minimum
*
* @param maximum
* Maximum
*/
public GeneralSubtree(
GeneralName baseName,
BigInteger minimum,
BigInteger maximum)
{
this.baseName = baseName;
if (minimum != null)
{
this.minimum = new DerInteger(minimum);
}
if (maximum != null)
{
this.maximum = new DerInteger(maximum);
}
}
public GeneralSubtree(
GeneralName baseName)
: this(baseName, null, null)
{
}
public static GeneralSubtree GetInstance(
Asn1TaggedObject o,
bool isExplicit)
{
return new GeneralSubtree(Asn1Sequence.GetInstance(o, isExplicit));
}
public static GeneralSubtree GetInstance(
object obj)
{
if (obj == null)
{
return null;
}
if (obj is GeneralSubtree)
{
return (GeneralSubtree) obj;
}
return new GeneralSubtree(Asn1Sequence.GetInstance(obj));
}
public GeneralName Base
{
get { return baseName; }
}
public BigInteger Minimum
{
get { return minimum == null ? BigInteger.Zero : minimum.Value; }
}
public BigInteger Maximum
{
get { return maximum == null ? null : maximum.Value; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
*
* Returns:
*
* <pre>
* GeneralSubtree ::= SEQUENCE
* {
* baseName GeneralName,
* minimum [0] BaseDistance DEFAULT 0,
* maximum [1] BaseDistance OPTIONAL
* }
* </pre>
*
* @return a DERObject
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector(baseName);
if (minimum != null && minimum.Value.SignValue != 0)
{
v.Add(new DerTaggedObject(false, 0, minimum));
}
if (maximum != null)
{
v.Add(new DerTaggedObject(false, 1, maximum));
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,257 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The Holder object.
* <p>
* For an v2 attribute certificate this is:
*
* <pre>
* Holder ::= SEQUENCE {
* baseCertificateID [0] IssuerSerial OPTIONAL,
* -- the issuer and serial number of
* -- the holder's Public Key Certificate
* entityName [1] GeneralNames OPTIONAL,
* -- the name of the claimant or role
* objectDigestInfo [2] ObjectDigestInfo OPTIONAL
* -- used to directly authenticate the holder,
* -- for example, an executable
* }
* </pre>
* </p>
* <p>
* For an v1 attribute certificate this is:
*
* <pre>
* subject CHOICE {
* baseCertificateID [0] IssuerSerial,
* -- associated with a Public Key Certificate
* subjectName [1] GeneralNames },
* -- associated with a name
* </pre>
* </p>
*/
public class Holder
: Asn1Encodable
{
internal readonly IssuerSerial baseCertificateID;
internal readonly GeneralNames entityName;
internal readonly ObjectDigestInfo objectDigestInfo;
private readonly int version;
public static Holder GetInstance(
object obj)
{
if (obj is Holder)
{
return (Holder) obj;
}
if (obj is Asn1Sequence)
{
return new Holder((Asn1Sequence) obj);
}
if (obj is Asn1TaggedObject)
{
return new Holder((Asn1TaggedObject) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor for a holder for an v1 attribute certificate.
*
* @param tagObj The ASN.1 tagged holder object.
*/
public Holder(
Asn1TaggedObject tagObj)
{
switch (tagObj.TagNo)
{
case 0:
baseCertificateID = IssuerSerial.GetInstance(tagObj, false);
break;
case 1:
entityName = GeneralNames.GetInstance(tagObj, false);
break;
default:
throw new ArgumentException("unknown tag in Holder");
}
this.version = 0;
}
/**
* Constructor for a holder for an v2 attribute certificate. *
*
* @param seq The ASN.1 sequence.
*/
private Holder(
Asn1Sequence seq)
{
if (seq.Count > 3)
throw new ArgumentException("Bad sequence size: " + seq.Count);
for (int i = 0; i != seq.Count; i++)
{
Asn1TaggedObject tObj = Asn1TaggedObject.GetInstance(seq[i]);
switch (tObj.TagNo)
{
case 0:
baseCertificateID = IssuerSerial.GetInstance(tObj, false);
break;
case 1:
entityName = GeneralNames.GetInstance(tObj, false);
break;
case 2:
objectDigestInfo = ObjectDigestInfo.GetInstance(tObj, false);
break;
default:
throw new ArgumentException("unknown tag in Holder");
}
}
this.version = 1;
}
public Holder(
IssuerSerial baseCertificateID)
: this(baseCertificateID, 1)
{
}
/**
* Constructs a holder from a IssuerSerial.
* @param baseCertificateID The IssuerSerial.
* @param version The version of the attribute certificate.
*/
public Holder(
IssuerSerial baseCertificateID,
int version)
{
this.baseCertificateID = baseCertificateID;
this.version = version;
}
/**
* Returns 1 for v2 attribute certificates or 0 for v1 attribute
* certificates.
* @return The version of the attribute certificate.
*/
public int Version
{
get { return version; }
}
/**
* Constructs a holder with an entityName for v2 attribute certificates or
* with a subjectName for v1 attribute certificates.
*
* @param entityName The entity or subject name.
*/
public Holder(
GeneralNames entityName)
: this(entityName, 1)
{
}
/**
* Constructs a holder with an entityName for v2 attribute certificates or
* with a subjectName for v1 attribute certificates.
*
* @param entityName The entity or subject name.
* @param version The version of the attribute certificate.
*/
public Holder(
GeneralNames entityName,
int version)
{
this.entityName = entityName;
this.version = version;
}
/**
* Constructs a holder from an object digest info.
*
* @param objectDigestInfo The object digest info object.
*/
public Holder(
ObjectDigestInfo objectDigestInfo)
{
this.objectDigestInfo = objectDigestInfo;
this.version = 1;
}
public IssuerSerial BaseCertificateID
{
get { return baseCertificateID; }
}
/**
* Returns the entityName for an v2 attribute certificate or the subjectName
* for an v1 attribute certificate.
*
* @return The entityname or subjectname.
*/
public GeneralNames EntityName
{
get { return entityName; }
}
public ObjectDigestInfo ObjectDigestInfo
{
get { return objectDigestInfo; }
}
/**
* The Holder object.
* <pre>
* Holder ::= Sequence {
* baseCertificateID [0] IssuerSerial OPTIONAL,
* -- the issuer and serial number of
* -- the holder's Public Key Certificate
* entityName [1] GeneralNames OPTIONAL,
* -- the name of the claimant or role
* objectDigestInfo [2] ObjectDigestInfo OPTIONAL
* -- used to directly authenticate the holder,
* -- for example, an executable
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
if (version == 1)
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (baseCertificateID != null)
{
v.Add(new DerTaggedObject(false, 0, baseCertificateID));
}
if (entityName != null)
{
v.Add(new DerTaggedObject(false, 1, entityName));
}
if (objectDigestInfo != null)
{
v.Add(new DerTaggedObject(false, 2, objectDigestInfo));
}
return new DerSequence(v);
}
if (entityName != null)
{
return new DerTaggedObject(false, 1, entityName);
}
return new DerTaggedObject(false, 0, baseCertificateID);
}
}
}

View File

@@ -0,0 +1,161 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Implementation of <code>IetfAttrSyntax</code> as specified by RFC3281.
*/
public class IetfAttrSyntax
: Asn1Encodable
{
public const int ValueOctets = 1;
public const int ValueOid = 2;
public const int ValueUtf8 = 3;
internal readonly GeneralNames policyAuthority;
internal readonly Asn1EncodableVector values = new Asn1EncodableVector();
internal int valueChoice = -1;
/**
*
*/
public IetfAttrSyntax(
Asn1Sequence seq)
{
int i = 0;
if (seq[0] is Asn1TaggedObject)
{
policyAuthority = GeneralNames.GetInstance(((Asn1TaggedObject)seq[0]), false);
i++;
}
else if (seq.Count == 2)
{ // VOMS fix
policyAuthority = GeneralNames.GetInstance(seq[0]);
i++;
}
if (!(seq[i] is Asn1Sequence))
{
throw new ArgumentException("Non-IetfAttrSyntax encoding");
}
seq = (Asn1Sequence) seq[i];
foreach (Asn1Object obj in seq)
{
int type;
if (obj is DerObjectIdentifier)
{
type = ValueOid;
}
else if (obj is DerUtf8String)
{
type = ValueUtf8;
}
else if (obj is DerOctetString)
{
type = ValueOctets;
}
else
{
throw new ArgumentException("Bad value type encoding IetfAttrSyntax");
}
if (valueChoice < 0)
{
valueChoice = type;
}
if (type != valueChoice)
{
throw new ArgumentException("Mix of value types in IetfAttrSyntax");
}
values.Add(obj);
}
}
public GeneralNames PolicyAuthority
{
get { return policyAuthority; }
}
public int ValueType
{
get { return valueChoice; }
}
public object[] GetValues()
{
if (this.ValueType == ValueOctets)
{
Asn1OctetString[] tmp = new Asn1OctetString[values.Count];
for (int i = 0; i != tmp.Length; i++)
{
tmp[i] = (Asn1OctetString) values[i];
}
return tmp;
}
if (this.ValueType == ValueOid)
{
DerObjectIdentifier[] tmp = new DerObjectIdentifier[values.Count];
for (int i = 0; i != tmp.Length; i++)
{
tmp[i] = (DerObjectIdentifier) values[i];
}
return tmp;
}
{
DerUtf8String[] tmp = new DerUtf8String[values.Count];
for (int i = 0; i != tmp.Length; i++)
{
tmp[i] = (DerUtf8String) values[i];
}
return tmp;
}
}
/**
*
* <pre>
*
* IetfAttrSyntax ::= Sequence {
* policyAuthority [0] GeneralNames OPTIONAL,
* values Sequence OF CHOICE {
* octets OCTET STRING,
* oid OBJECT IDENTIFIER,
* string UTF8String
* }
* }
*
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (policyAuthority != null)
{
v.Add(new DerTaggedObject(0, policyAuthority));
}
v.Add(new DerSequence(values));
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,98 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
public class IssuerSerial
: Asn1Encodable
{
internal readonly GeneralNames issuer;
internal readonly DerInteger serial;
internal readonly DerBitString issuerUid;
public static IssuerSerial GetInstance(
object obj)
{
if (obj == null || obj is IssuerSerial)
{
return (IssuerSerial) obj;
}
if (obj is Asn1Sequence)
{
return new IssuerSerial((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public static IssuerSerial GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
private IssuerSerial(
Asn1Sequence seq)
{
if (seq.Count != 2 && seq.Count != 3)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
issuer = GeneralNames.GetInstance(seq[0]);
serial = DerInteger.GetInstance(seq[1]);
if (seq.Count == 3)
{
issuerUid = DerBitString.GetInstance(seq[2]);
}
}
public IssuerSerial(
GeneralNames issuer,
DerInteger serial)
{
this.issuer = issuer;
this.serial = serial;
}
public GeneralNames Issuer
{
get { return issuer; }
}
public DerInteger Serial
{
get { return serial; }
}
public DerBitString IssuerUid
{
get { return issuerUid; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* IssuerSerial ::= Sequence {
* issuer GeneralNames,
* serial CertificateSerialNumber,
* issuerUid UniqueIdentifier OPTIONAL
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector(
issuer, serial);
if (issuerUid != null)
{
v.Add(issuerUid);
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,247 @@
using System;
using System.Text;
using Org.BouncyCastle.Utilities;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* <pre>
* IssuingDistributionPoint ::= SEQUENCE {
* distributionPoint [0] DistributionPointName OPTIONAL,
* onlyContainsUserCerts [1] BOOLEAN DEFAULT FALSE,
* onlyContainsCACerts [2] BOOLEAN DEFAULT FALSE,
* onlySomeReasons [3] ReasonFlags OPTIONAL,
* indirectCRL [4] BOOLEAN DEFAULT FALSE,
* onlyContainsAttributeCerts [5] BOOLEAN DEFAULT FALSE }
* </pre>
*/
public class IssuingDistributionPoint
: Asn1Encodable
{
private readonly DistributionPointName _distributionPoint;
private readonly bool _onlyContainsUserCerts;
private readonly bool _onlyContainsCACerts;
private readonly ReasonFlags _onlySomeReasons;
private readonly bool _indirectCRL;
private readonly bool _onlyContainsAttributeCerts;
private readonly Asn1Sequence seq;
public static IssuingDistributionPoint GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static IssuingDistributionPoint GetInstance(
object obj)
{
if (obj == null || obj is IssuingDistributionPoint)
{
return (IssuingDistributionPoint) obj;
}
if (obj is Asn1Sequence)
{
return new IssuingDistributionPoint((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from given details.
*
* @param distributionPoint
* May contain an URI as pointer to most current CRL.
* @param onlyContainsUserCerts Covers revocation information for end certificates.
* @param onlyContainsCACerts Covers revocation information for CA certificates.
*
* @param onlySomeReasons
* Which revocation reasons does this point cover.
* @param indirectCRL
* If <code>true</code> then the CRL contains revocation
* information about certificates ssued by other CAs.
* @param onlyContainsAttributeCerts Covers revocation information for attribute certificates.
*/
public IssuingDistributionPoint(
DistributionPointName distributionPoint,
bool onlyContainsUserCerts,
bool onlyContainsCACerts,
ReasonFlags onlySomeReasons,
bool indirectCRL,
bool onlyContainsAttributeCerts)
{
this._distributionPoint = distributionPoint;
this._indirectCRL = indirectCRL;
this._onlyContainsAttributeCerts = onlyContainsAttributeCerts;
this._onlyContainsCACerts = onlyContainsCACerts;
this._onlyContainsUserCerts = onlyContainsUserCerts;
this._onlySomeReasons = onlySomeReasons;
Asn1EncodableVector vec = new Asn1EncodableVector();
if (distributionPoint != null)
{ // CHOICE item so explicitly tagged
vec.Add(new DerTaggedObject(true, 0, distributionPoint));
}
if (onlyContainsUserCerts)
{
vec.Add(new DerTaggedObject(false, 1, DerBoolean.True));
}
if (onlyContainsCACerts)
{
vec.Add(new DerTaggedObject(false, 2, DerBoolean.True));
}
if (onlySomeReasons != null)
{
vec.Add(new DerTaggedObject(false, 3, onlySomeReasons));
}
if (indirectCRL)
{
vec.Add(new DerTaggedObject(false, 4, DerBoolean.True));
}
if (onlyContainsAttributeCerts)
{
vec.Add(new DerTaggedObject(false, 5, DerBoolean.True));
}
seq = new DerSequence(vec);
}
/**
* Constructor from Asn1Sequence
*/
private IssuingDistributionPoint(
Asn1Sequence seq)
{
this.seq = seq;
for (int i = 0; i != seq.Count; i++)
{
Asn1TaggedObject o = Asn1TaggedObject.GetInstance(seq[i]);
switch (o.TagNo)
{
case 0:
// CHOICE so explicit
_distributionPoint = DistributionPointName.GetInstance(o, true);
break;
case 1:
_onlyContainsUserCerts = DerBoolean.GetInstance(o, false).IsTrue;
break;
case 2:
_onlyContainsCACerts = DerBoolean.GetInstance(o, false).IsTrue;
break;
case 3:
_onlySomeReasons = new ReasonFlags(ReasonFlags.GetInstance(o, false));
break;
case 4:
_indirectCRL = DerBoolean.GetInstance(o, false).IsTrue;
break;
case 5:
_onlyContainsAttributeCerts = DerBoolean.GetInstance(o, false).IsTrue;
break;
default:
throw new ArgumentException("unknown tag in IssuingDistributionPoint");
}
}
}
public bool OnlyContainsUserCerts
{
get { return _onlyContainsUserCerts; }
}
public bool OnlyContainsCACerts
{
get { return _onlyContainsCACerts; }
}
public bool IsIndirectCrl
{
get { return _indirectCRL; }
}
public bool OnlyContainsAttributeCerts
{
get { return _onlyContainsAttributeCerts; }
}
/**
* @return Returns the distributionPoint.
*/
public DistributionPointName DistributionPoint
{
get { return _distributionPoint; }
}
/**
* @return Returns the onlySomeReasons.
*/
public ReasonFlags OnlySomeReasons
{
get { return _onlySomeReasons; }
}
public override Asn1Object ToAsn1Object()
{
return seq;
}
public override string ToString()
{
string sep = Platform.NewLine;
StringBuilder buf = new StringBuilder();
buf.Append("IssuingDistributionPoint: [");
buf.Append(sep);
if (_distributionPoint != null)
{
appendObject(buf, sep, "distributionPoint", _distributionPoint.ToString());
}
if (_onlyContainsUserCerts)
{
appendObject(buf, sep, "onlyContainsUserCerts", _onlyContainsUserCerts.ToString());
}
if (_onlyContainsCACerts)
{
appendObject(buf, sep, "onlyContainsCACerts", _onlyContainsCACerts.ToString());
}
if (_onlySomeReasons != null)
{
appendObject(buf, sep, "onlySomeReasons", _onlySomeReasons.ToString());
}
if (_onlyContainsAttributeCerts)
{
appendObject(buf, sep, "onlyContainsAttributeCerts", _onlyContainsAttributeCerts.ToString());
}
if (_indirectCRL)
{
appendObject(buf, sep, "indirectCRL", _indirectCRL.ToString());
}
buf.Append("]");
buf.Append(sep);
return buf.ToString();
}
private void appendObject(
StringBuilder buf,
string sep,
string name,
string val)
{
string indent = " ";
buf.Append(indent);
buf.Append(name);
buf.Append(":");
buf.Append(sep);
buf.Append(indent);
buf.Append(indent);
buf.Append(val);
buf.Append(sep);
}
}
}

View File

@@ -0,0 +1,36 @@
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The KeyPurposeID object.
* <pre>
* KeyPurposeID ::= OBJECT IDENTIFIER
* </pre>
*/
public sealed class KeyPurposeID
: DerObjectIdentifier
{
private const string IdKP = "1.3.6.1.5.5.7.3";
private KeyPurposeID(
string id)
: base(id)
{
}
public static readonly KeyPurposeID AnyExtendedKeyUsage = new KeyPurposeID(X509Extensions.ExtendedKeyUsage.Id + ".0");
public static readonly KeyPurposeID IdKPServerAuth = new KeyPurposeID(IdKP + ".1");
public static readonly KeyPurposeID IdKPClientAuth = new KeyPurposeID(IdKP + ".2");
public static readonly KeyPurposeID IdKPCodeSigning = new KeyPurposeID(IdKP + ".3");
public static readonly KeyPurposeID IdKPEmailProtection = new KeyPurposeID(IdKP + ".4");
public static readonly KeyPurposeID IdKPIpsecEndSystem = new KeyPurposeID(IdKP + ".5");
public static readonly KeyPurposeID IdKPIpsecTunnel = new KeyPurposeID(IdKP + ".6");
public static readonly KeyPurposeID IdKPIpsecUser = new KeyPurposeID(IdKP + ".7");
public static readonly KeyPurposeID IdKPTimeStamping = new KeyPurposeID(IdKP + ".8");
public static readonly KeyPurposeID IdKPOcspSigning = new KeyPurposeID(IdKP + ".9");
//
// microsoft key purpose ids
//
public static readonly KeyPurposeID IdKPSmartCardLogon = new KeyPurposeID("1.3.6.1.4.1.311.20.2.2");
}
}

View File

@@ -0,0 +1,79 @@
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The KeyUsage object.
* <pre>
* id-ce-keyUsage OBJECT IDENTIFIER ::= { id-ce 15 }
*
* KeyUsage ::= BIT STRING {
* digitalSignature (0),
* nonRepudiation (1),
* keyEncipherment (2),
* dataEncipherment (3),
* keyAgreement (4),
* keyCertSign (5),
* cRLSign (6),
* encipherOnly (7),
* decipherOnly (8) }
* </pre>
*/
public class KeyUsage
: DerBitString
{
public const int DigitalSignature = (1 << 7);
public const int NonRepudiation = (1 << 6);
public const int KeyEncipherment = (1 << 5);
public const int DataEncipherment = (1 << 4);
public const int KeyAgreement = (1 << 3);
public const int KeyCertSign = (1 << 2);
public const int CrlSign = (1 << 1);
public const int EncipherOnly = (1 << 0);
public const int DecipherOnly = (1 << 15);
public static new KeyUsage GetInstance(
object obj)
{
if (obj is KeyUsage)
{
return (KeyUsage)obj;
}
if (obj is X509Extension)
{
return GetInstance(X509Extension.ConvertValueToObject((X509Extension) obj));
}
return new KeyUsage(DerBitString.GetInstance(obj));
}
/**
* Basic constructor.
*
* @param usage - the bitwise OR of the Key Usage flags giving the
* allowed uses for the key.
* e.g. (KeyUsage.keyEncipherment | KeyUsage.dataEncipherment)
*/
public KeyUsage(
int usage)
: base(GetBytes(usage), GetPadBits(usage))
{
}
private KeyUsage(
DerBitString usage)
: base(usage.GetBytes(), usage.PadBits)
{
}
public override string ToString()
{
byte[] data = GetBytes();
if (data.Length == 1)
{
return "KeyUsage: 0x" + (data[0] & 0xff).ToString("X");
}
return "KeyUsage: 0x" + ((data[1] & 0xff) << 8 | (data[0] & 0xff)).ToString("X");
}
}
}

View File

@@ -0,0 +1,90 @@
using System;
using System.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
public class NameConstraints
: Asn1Encodable
{
private Asn1Sequence permitted, excluded;
public NameConstraints(
Asn1Sequence seq)
{
foreach (Asn1TaggedObject o in seq)
{
switch (o.TagNo)
{
case 0:
permitted = Asn1Sequence.GetInstance(o, false);
break;
case 1:
excluded = Asn1Sequence.GetInstance(o, false);
break;
}
}
}
/**
* Constructor from a given details.
*
* <p>permitted and excluded are Vectors of GeneralSubtree objects.</p>
*
* @param permitted Permitted subtrees
* @param excluded Excluded subtrees
*/
public NameConstraints(
ArrayList permitted,
ArrayList excluded)
{
if (permitted != null)
{
this.permitted = createSequence(permitted);
}
if (excluded != null)
{
this.excluded = createSequence(excluded);
}
}
private DerSequence createSequence(
ArrayList subtree)
{
GeneralSubtree[] gsts = (GeneralSubtree[]) subtree.ToArray(typeof(GeneralSubtree));
return new DerSequence(gsts);
}
public Asn1Sequence PermittedSubtrees
{
get { return permitted; }
}
public Asn1Sequence ExcludedSubtrees
{
get { return excluded; }
}
/*
* NameConstraints ::= SEQUENCE { permittedSubtrees [0] GeneralSubtrees
* OPTIONAL, excludedSubtrees [1] GeneralSubtrees OPTIONAL }
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (permitted != null)
{
v.Add(new DerTaggedObject(false, 0, permitted));
}
if (excluded != null)
{
v.Add(new DerTaggedObject(false, 1, excluded));
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,128 @@
using System;
using System.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* <code>NoticeReference</code> class, used in
* <code>CertificatePolicies</code> X509 V3 extensions
* (in policy qualifiers).
*
* <pre>
* NoticeReference ::= Sequence {
* organization DisplayText,
* noticeNumbers Sequence OF Integer }
*
* </pre>
*
* @see PolicyQualifierInfo
* @see PolicyInformation
*/
public class NoticeReference
: Asn1Encodable
{
internal readonly DisplayText organization;
internal readonly Asn1Sequence noticeNumbers;
/**
* Creates a new <code>NoticeReference</code> instance.
*
* @param orgName a <code>string</code> value
* @param numbers a <code>ArrayList</code> value
*/
public NoticeReference(
string orgName,
ArrayList numbers)
{
organization = new DisplayText(orgName);
object o = numbers[0];
Asn1EncodableVector av = new Asn1EncodableVector();
if (o is int)
{
foreach (int nm in numbers)
{
av.Add(new DerInteger(nm));
}
}
noticeNumbers = new DerSequence(av);
}
/**
* Creates a new <code>NoticeReference</code> instance.
*
* @param orgName a <code>string</code> value
* @param numbers an <code>Asn1Sequence</code> value
*/
public NoticeReference(
string orgName,
Asn1Sequence numbers)
{
organization = new DisplayText(orgName);
noticeNumbers = numbers;
}
/**
* Creates a new <code>NoticeReference</code> instance.
*
* @param displayTextType an <code>int</code> value
* @param orgName a <code>string</code> value
* @param numbers an <code>Asn1Sequence</code> value
*/
public NoticeReference(
int displayTextType,
string orgName,
Asn1Sequence numbers)
{
organization = new DisplayText(displayTextType, orgName);
noticeNumbers = numbers;
}
/**
* Creates a new <code>NoticeReference</code> instance.
* <p>Useful for reconstructing a <code>NoticeReference</code>
* instance from its encodable/encoded form.</p>
*
* @param as an <code>Asn1Sequence</code> value obtained from either
* calling @{link ToAsn1Object()} for a <code>NoticeReference</code>
* instance or from parsing it from a Der-encoded stream.
*/
private NoticeReference(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Bad sequence size: " + seq.Count, "seq");
organization = DisplayText.GetInstance(seq[0]);
noticeNumbers = Asn1Sequence.GetInstance(seq[1]);
}
public static NoticeReference GetInstance(
object obj)
{
if (obj is NoticeReference)
{
return (NoticeReference) obj;
}
if (obj is Asn1Sequence)
{
return new NoticeReference((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
/**
* Describe <code>ToAsn1Object</code> method here.
*
* @return a <code>Asn1Object</code> value
*/
public override Asn1Object ToAsn1Object()
{
return new DerSequence(organization, noticeNumbers);
}
}
}

View File

@@ -0,0 +1,177 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* ObjectDigestInfo ASN.1 structure used in v2 attribute certificates.
*
* <pre>
*
* ObjectDigestInfo ::= SEQUENCE {
* digestedObjectType ENUMERATED {
* publicKey (0),
* publicKeyCert (1),
* otherObjectTypes (2) },
* -- otherObjectTypes MUST NOT
* -- be used in this profile
* otherObjectTypeID OBJECT IDENTIFIER OPTIONAL,
* digestAlgorithm AlgorithmIdentifier,
* objectDigest BIT STRING
* }
*
* </pre>
*
*/
public class ObjectDigestInfo
: Asn1Encodable
{
/**
* The public key is hashed.
*/
public const int PublicKey = 0;
/**
* The public key certificate is hashed.
*/
public const int PublicKeyCert = 1;
/**
* An other object is hashed.
*/
public const int OtherObjectDigest = 2;
internal readonly DerEnumerated digestedObjectType;
internal readonly DerObjectIdentifier otherObjectTypeID;
internal readonly AlgorithmIdentifier digestAlgorithm;
internal readonly DerBitString objectDigest;
public static ObjectDigestInfo GetInstance(
object obj)
{
if (obj == null || obj is ObjectDigestInfo)
{
return (ObjectDigestInfo) obj;
}
if (obj is Asn1Sequence)
{
return new ObjectDigestInfo((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public static ObjectDigestInfo GetInstance(
Asn1TaggedObject obj,
bool isExplicit)
{
return GetInstance(Asn1Sequence.GetInstance(obj, isExplicit));
}
/**
* Constructor from given details.
* <p>
* If <code>digestedObjectType</code> is not {@link #publicKeyCert} or
* {@link #publicKey} <code>otherObjectTypeID</code> must be given,
* otherwise it is ignored.</p>
*
* @param digestedObjectType The digest object type.
* @param otherObjectTypeID The object type ID for
* <code>otherObjectDigest</code>.
* @param digestAlgorithm The algorithm identifier for the hash.
* @param objectDigest The hash value.
*/
public ObjectDigestInfo(
int digestedObjectType,
string otherObjectTypeID,
AlgorithmIdentifier digestAlgorithm,
byte[] objectDigest)
{
this.digestedObjectType = new DerEnumerated(digestedObjectType);
if (digestedObjectType == OtherObjectDigest)
{
this.otherObjectTypeID = new DerObjectIdentifier(otherObjectTypeID);
}
this.digestAlgorithm = digestAlgorithm;
this.objectDigest = new DerBitString(objectDigest);
}
private ObjectDigestInfo(
Asn1Sequence seq)
{
if (seq.Count > 4 || seq.Count < 3)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
digestedObjectType = DerEnumerated.GetInstance(seq[0]);
int offset = 0;
if (seq.Count == 4)
{
otherObjectTypeID = DerObjectIdentifier.GetInstance(seq[1]);
offset++;
}
digestAlgorithm = AlgorithmIdentifier.GetInstance(seq[1 + offset]);
objectDigest = DerBitString.GetInstance(seq[2 + offset]);
}
public DerEnumerated DigestedObjectType
{
get { return digestedObjectType; }
}
public DerObjectIdentifier OtherObjectTypeID
{
get { return otherObjectTypeID; }
}
public AlgorithmIdentifier DigestAlgorithm
{
get { return digestAlgorithm; }
}
public DerBitString ObjectDigest
{
get { return objectDigest; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
*
* <pre>
*
* ObjectDigestInfo ::= SEQUENCE {
* digestedObjectType ENUMERATED {
* publicKey (0),
* publicKeyCert (1),
* otherObjectTypes (2) },
* -- otherObjectTypes MUST NOT
* -- be used in this profile
* otherObjectTypeID OBJECT IDENTIFIER OPTIONAL,
* digestAlgorithm AlgorithmIdentifier,
* objectDigest BIT STRING
* }
*
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector(digestedObjectType);
if (otherObjectTypeID != null)
{
v.Add(otherObjectTypeID);
}
v.Add(digestAlgorithm, objectDigest);
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,80 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
public class PolicyInformation
: Asn1Encodable
{
private readonly DerObjectIdentifier policyIdentifier;
private readonly Asn1Sequence policyQualifiers;
private PolicyInformation(
Asn1Sequence seq)
{
if (seq.Count < 1 || seq.Count > 2)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
policyIdentifier = DerObjectIdentifier.GetInstance(seq[0]);
if (seq.Count > 1)
{
policyQualifiers = Asn1Sequence.GetInstance(seq[1]);
}
}
public PolicyInformation(
DerObjectIdentifier policyIdentifier)
{
this.policyIdentifier = policyIdentifier;
}
public PolicyInformation(
DerObjectIdentifier policyIdentifier,
Asn1Sequence policyQualifiers)
{
this.policyIdentifier = policyIdentifier;
this.policyQualifiers = policyQualifiers;
}
public static PolicyInformation GetInstance(
object obj)
{
if (obj == null || obj is PolicyInformation)
{
return (PolicyInformation) obj;
}
return new PolicyInformation(Asn1Sequence.GetInstance(obj));
}
public DerObjectIdentifier PolicyIdentifier
{
get { return policyIdentifier; }
}
public Asn1Sequence PolicyQualifiers
{
get { return policyQualifiers; }
}
/*
* PolicyInformation ::= Sequence {
* policyIdentifier CertPolicyId,
* policyQualifiers Sequence SIZE (1..MAX) OF
* PolicyQualifierInfo OPTIONAL }
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector(policyIdentifier);
if (policyQualifiers != null)
{
v.Add(policyQualifiers);
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,62 @@
using System.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* PolicyMappings V3 extension, described in RFC3280.
* <pre>
* PolicyMappings ::= Sequence SIZE (1..MAX) OF Sequence {
* issuerDomainPolicy CertPolicyId,
* subjectDomainPolicy CertPolicyId }
* </pre>
*
* @see <a href="http://www.faqs.org/rfc/rfc3280.txt">RFC 3280, section 4.2.1.6</a>
*/
public class PolicyMappings
: Asn1Encodable
{
private readonly Asn1Sequence seq;
/**
* Creates a new <code>PolicyMappings</code> instance.
*
* @param seq an <code>Asn1Sequence</code> constructed as specified
* in RFC 3280
*/
public PolicyMappings(
Asn1Sequence seq)
{
this.seq = seq;
}
/**
* Creates a new <code>PolicyMappings</code> instance.
*
* @param mappings a <code>HashMap</code> value that maps
* <code>string</code> oids
* to other <code>string</code> oids.
*/
public PolicyMappings(
Hashtable mappings)
{
Asn1EncodableVector v = new Asn1EncodableVector();
foreach (string idp in mappings.Keys)
{
string sdp = (string) mappings[idp];
v.Add(
new DerSequence(
new DerObjectIdentifier(idp),
new DerObjectIdentifier(sdp)));
}
seq = new DerSequence(v);
}
public override Asn1Object ToAsn1Object()
{
return seq;
}
}
}

View File

@@ -0,0 +1,28 @@
namespace Org.BouncyCastle.Asn1.X509
{
/**
* PolicyQualifierId, used in the CertificatePolicies
* X509V3 extension.
*
* <pre>
* id-qt OBJECT IDENTIFIER ::= { id-pkix 2 }
* id-qt-cps OBJECT IDENTIFIER ::= { id-qt 1 }
* id-qt-unotice OBJECT IDENTIFIER ::= { id-qt 2 }
* PolicyQualifierId ::=
* OBJECT IDENTIFIER ( id-qt-cps | id-qt-unotice )
* </pre>
*/
public sealed class PolicyQualifierID : DerObjectIdentifier
{
private const string IdQt = "1.3.6.1.5.5.7.2";
private PolicyQualifierID(
string id)
: base(id)
{
}
public static readonly PolicyQualifierID IdQtCps = new PolicyQualifierID(IdQt + ".1");
public static readonly PolicyQualifierID IdQtUnotice = new PolicyQualifierID(IdQt + ".2");
}
}

View File

@@ -0,0 +1,91 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Policy qualifiers, used in the X509V3 CertificatePolicies
* extension.
*
* <pre>
* PolicyQualifierInfo ::= Sequence {
* policyQualifierId PolicyQualifierId,
* qualifier ANY DEFINED BY policyQualifierId }
* </pre>
*/
public class PolicyQualifierInfo
: Asn1Encodable
{
internal readonly DerObjectIdentifier policyQualifierId;
internal readonly Asn1Encodable qualifier;
/**
* Creates a new <code>PolicyQualifierInfo</code> instance.
*
* @param policyQualifierId a <code>PolicyQualifierId</code> value
* @param qualifier the qualifier, defined by the above field.
*/
public PolicyQualifierInfo(
DerObjectIdentifier policyQualifierId,
Asn1Encodable qualifier)
{
this.policyQualifierId = policyQualifierId;
this.qualifier = qualifier;
}
/**
* Creates a new <code>PolicyQualifierInfo</code> containing a
* cPSuri qualifier.
*
* @param cps the CPS (certification practice statement) uri as a
* <code>string</code>.
*/
public PolicyQualifierInfo(
string cps)
{
policyQualifierId = PolicyQualifierID.IdQtCps;
qualifier = new DerIA5String(cps);
}
/**
* Creates a new <code>PolicyQualifierInfo</code> instance.
*
* @param as <code>PolicyQualifierInfo</code> X509 structure
* encoded as an Asn1Sequence.
*/
private PolicyQualifierInfo(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Bad sequence size: " + seq.Count, "seq");
policyQualifierId = DerObjectIdentifier.GetInstance(seq[0]);
qualifier = seq[1];
}
public static PolicyQualifierInfo GetInstance(
object obj)
{
if (obj is PolicyQualifierInfo)
{
return (PolicyQualifierInfo) obj;
}
if (obj is Asn1Sequence)
{
return new PolicyQualifierInfo((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
/**
* Returns a Der-encodable representation of this instance.
*
* @return a <code>Asn1Object</code> value
*/
public override Asn1Object ToAsn1Object()
{
return new DerSequence(policyQualifierId, qualifier);
}
}
}

View File

@@ -0,0 +1,82 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/// <remarks>
/// <pre>
/// PrivateKeyUsagePeriod ::= SEQUENCE
/// {
/// notBefore [0] GeneralizedTime OPTIONAL,
/// notAfter [1] GeneralizedTime OPTIONAL }
/// </pre>
/// </remarks>
public class PrivateKeyUsagePeriod
: Asn1Encodable
{
public static PrivateKeyUsagePeriod GetInstance(
object obj)
{
if (obj is PrivateKeyUsagePeriod)
{
return (PrivateKeyUsagePeriod) obj;
}
if (obj is Asn1Sequence)
{
return new PrivateKeyUsagePeriod((Asn1Sequence) obj);
}
if (obj is X509Extension)
{
return GetInstance(X509Extension.ConvertValueToObject((X509Extension) obj));
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
private DerGeneralizedTime _notBefore, _notAfter;
private PrivateKeyUsagePeriod(
Asn1Sequence seq)
{
foreach (Asn1TaggedObject tObj in seq)
{
if (tObj.TagNo == 0)
{
_notBefore = DerGeneralizedTime.GetInstance(tObj, false);
}
else if (tObj.TagNo == 1)
{
_notAfter = DerGeneralizedTime.GetInstance(tObj, false);
}
}
}
public DerGeneralizedTime NotBefore
{
get { return _notBefore; }
}
public DerGeneralizedTime NotAfter
{
get { return _notAfter; }
}
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (_notBefore != null)
{
v.Add(new DerTaggedObject(false, 0, _notBefore));
}
if (_notAfter != null)
{
v.Add(new DerTaggedObject(false, 1, _notAfter));
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,82 @@
using Org.BouncyCastle.Asn1;
using Org.BouncyCastle.Math;
using System;
using System.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
public class RsaPublicKeyStructure
: Asn1Encodable
{
private BigInteger modulus;
private BigInteger publicExponent;
public static RsaPublicKeyStructure GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static RsaPublicKeyStructure GetInstance(
object obj)
{
if (obj == null || obj is RsaPublicKeyStructure)
{
return (RsaPublicKeyStructure) obj;
}
if (obj is Asn1Sequence)
{
return new RsaPublicKeyStructure((Asn1Sequence) obj);
}
throw new ArgumentException("Invalid RsaPublicKeyStructure: " + obj.GetType().Name);
}
public RsaPublicKeyStructure(
BigInteger modulus,
BigInteger publicExponent)
{
this.modulus = modulus;
this.publicExponent = publicExponent;
}
private RsaPublicKeyStructure(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Bad sequence size: " + seq.Count);
modulus = DerInteger.GetInstance(seq[0]).PositiveValue;
publicExponent = DerInteger.GetInstance(seq[1]).PositiveValue;
}
public BigInteger Modulus
{
get { return modulus; }
}
public BigInteger PublicExponent
{
get { return publicExponent; }
}
/**
* This outputs the key in Pkcs1v2 format.
* <pre>
* RSAPublicKey ::= Sequence {
* modulus Integer, -- n
* publicExponent Integer, -- e
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return new DerSequence(
new DerInteger(Modulus),
new DerInteger(PublicExponent));
}
}
}

View File

@@ -0,0 +1,46 @@
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The ReasonFlags object.
* <pre>
* ReasonFlags ::= BIT STRING {
* unused(0),
* keyCompromise(1),
* cACompromise(2),
* affiliationChanged(3),
* superseded(4),
* cessationOfOperation(5),
* certficateHold(6)
* }
* </pre>
*/
public class ReasonFlags
: DerBitString
{
public const int Unused = (1 << 7);
public const int KeyCompromise = (1 << 6);
public const int CACompromise = (1 << 5);
public const int AffiliationChanged = (1 << 4);
public const int Superseded = (1 << 3);
public const int CessationOfOperation = (1 << 2);
public const int CertificateHold = (1 << 1);
public const int PrivilegeWithdrawn = (1 << 0);
public const int AACompromise = (1 << 15);
/**
* @param reasons - the bitwise OR of the Key Reason flags giving the
* allowed uses for the key.
*/
public ReasonFlags(
int reasons)
: base(GetBytes(reasons), GetPadBits(reasons))
{
}
public ReasonFlags(
DerBitString reasons)
: base(reasons.GetBytes(), reasons.PadBits)
{
}
}
}

View File

@@ -0,0 +1,234 @@
using System;
using System.Text;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Implementation of the RoleSyntax object as specified by the RFC3281.
*
* <pre>
* RoleSyntax ::= SEQUENCE {
* roleAuthority [0] GeneralNames OPTIONAL,
* roleName [1] GeneralName
* }
* </pre>
*/
public class RoleSyntax
: Asn1Encodable
{
private readonly GeneralNames roleAuthority;
private readonly GeneralName roleName;
/**
* RoleSyntax factory method.
* @param obj the object used to construct an instance of <code>
* RoleSyntax</code>. It must be an instance of <code>RoleSyntax
* </code> or <code>Asn1Sequence</code>.
* @return the instance of <code>RoleSyntax</code> built from the
* supplied object.
* @throws java.lang.ArgumentException if the object passed
* to the factory is not an instance of <code>RoleSyntax</code> or
* <code>Asn1Sequence</code>.
*/
public static RoleSyntax GetInstance(
object obj)
{
if (obj == null || obj is RoleSyntax)
{
return (RoleSyntax) obj;
}
if (obj is Asn1Sequence)
{
return new RoleSyntax((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in 'RoleSyntax' factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor.
* @param roleAuthority the role authority of this RoleSyntax.
* @param roleName the role name of this RoleSyntax.
*/
public RoleSyntax(
GeneralNames roleAuthority,
GeneralName roleName)
{
if (roleName == null
|| roleName.TagNo != GeneralName.UniformResourceIdentifier
|| ((IAsn1String) roleName.Name).GetString().Equals(""))
{
throw new ArgumentException("the role name MUST be non empty and MUST " +
"use the URI option of GeneralName");
}
this.roleAuthority = roleAuthority;
this.roleName = roleName;
}
/**
* Constructor. Invoking this constructor is the same as invoking
* <code>new RoleSyntax(null, roleName)</code>.
* @param roleName the role name of this RoleSyntax.
*/
public RoleSyntax(
GeneralName roleName)
: this(null, roleName)
{
}
/**
* Utility constructor. Takes a <code>string</code> argument representing
* the role name, builds a <code>GeneralName</code> to hold the role name
* and calls the constructor that takes a <code>GeneralName</code>.
* @param roleName
*/
public RoleSyntax(
string roleName)
: this(new GeneralName(GeneralName.UniformResourceIdentifier,
(roleName == null)? "": roleName))
{
}
/**
* Constructor that builds an instance of <code>RoleSyntax</code> by
* extracting the encoded elements from the <code>Asn1Sequence</code>
* object supplied.
* @param seq an instance of <code>Asn1Sequence</code> that holds
* the encoded elements used to build this <code>RoleSyntax</code>.
*/
private RoleSyntax(
Asn1Sequence seq)
{
if (seq.Count < 1 || seq.Count > 2)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
for (int i = 0; i != seq.Count; i++)
{
Asn1TaggedObject taggedObject = Asn1TaggedObject.GetInstance(seq[i]);
switch (taggedObject.TagNo)
{
case 0:
roleAuthority = GeneralNames.GetInstance(taggedObject, false);
break;
case 1:
roleName = GeneralName.GetInstance(taggedObject, false);
break;
default:
throw new ArgumentException("Unknown tag in RoleSyntax");
}
}
}
/**
* Gets the role authority of this RoleSyntax.
* @return an instance of <code>GeneralNames</code> holding the
* role authority of this RoleSyntax.
*/
public GeneralNames RoleAuthority
{
get { return this.roleAuthority; }
}
/**
* Gets the role name of this RoleSyntax.
* @return an instance of <code>GeneralName</code> holding the
* role name of this RoleSyntax.
*/
public GeneralName RoleName
{
get { return this.roleName; }
}
/**
* Gets the role name as a <code>java.lang.string</code> object.
* @return the role name of this RoleSyntax represented as a
* <code>string</code> object.
*/
public string GetRoleNameAsString()
{
return ((IAsn1String) this.roleName.Name).GetString();
}
/**
* Gets the role authority as a <code>string[]</code> object.
* @return the role authority of this RoleSyntax represented as a
* <code>string[]</code> array.
*/
public string[] GetRoleAuthorityAsString()
{
if (roleAuthority == null)
{
return new string[0];
}
GeneralName[] names = roleAuthority.GetNames();
string[] namesString = new string[names.Length];
for(int i = 0; i < names.Length; i++)
{
Asn1Encodable asn1Value = names[i].Name;
if (asn1Value is IAsn1String)
{
namesString[i] = ((IAsn1String) asn1Value).GetString();
}
else
{
namesString[i] = asn1Value.ToString();
}
}
return namesString;
}
/**
* Implementation of the method <code>ToAsn1Object</code> as
* required by the superclass <code>ASN1Encodable</code>.
*
* <pre>
* RoleSyntax ::= SEQUENCE {
* roleAuthority [0] GeneralNames OPTIONAL,
* roleName [1] GeneralName
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (this.roleAuthority != null)
{
v.Add(new DerTaggedObject(false, 0, roleAuthority));
}
v.Add(new DerTaggedObject(false, 1, roleName));
return new DerSequence(v);
}
public override string ToString()
{
StringBuilder buff = new StringBuilder("Name: " + this.GetRoleNameAsString() +
" - Auth: ");
if (this.roleAuthority == null || roleAuthority.GetNames().Length == 0)
{
buff.Append("N/A");
}
else
{
string[] names = this.GetRoleAuthorityAsString();
buff.Append('[').Append(names[0]);
for(int i = 1; i < names.Length; i++)
{
buff.Append(", ").Append(names[i]);
}
buff.Append(']');
}
return buff.ToString();
}
}
}

View File

@@ -0,0 +1,128 @@
using System;
using System.Collections;
using Org.BouncyCastle.Utilities.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* This extension may contain further X.500 attributes of the subject. See also
* RFC 3039.
*
* <pre>
* SubjectDirectoryAttributes ::= Attributes
* Attributes ::= SEQUENCE SIZE (1..MAX) OF Attribute
* Attribute ::= SEQUENCE
* {
* type AttributeType
* values SET OF AttributeValue
* }
*
* AttributeType ::= OBJECT IDENTIFIER
* AttributeValue ::= ANY DEFINED BY AttributeType
* </pre>
*
* @see org.bouncycastle.asn1.x509.X509Name for AttributeType ObjectIdentifiers.
*/
public class SubjectDirectoryAttributes
: Asn1Encodable
{
private readonly ArrayList attributes = new ArrayList();
public static SubjectDirectoryAttributes GetInstance(
object obj)
{
if (obj == null || obj is SubjectDirectoryAttributes)
{
return (SubjectDirectoryAttributes) obj;
}
if (obj is Asn1Sequence)
{
return new SubjectDirectoryAttributes((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from Asn1Sequence.
*
* The sequence is of type SubjectDirectoryAttributes:
*
* <pre>
* SubjectDirectoryAttributes ::= Attributes
* Attributes ::= SEQUENCE SIZE (1..MAX) OF Attribute
* Attribute ::= SEQUENCE
* {
* type AttributeType
* values SET OF AttributeValue
* }
*
* AttributeType ::= OBJECT IDENTIFIER
* AttributeValue ::= ANY DEFINED BY AttributeType
* </pre>
*
* @param seq
* The ASN.1 sequence.
*/
private SubjectDirectoryAttributes(
Asn1Sequence seq)
{
foreach (object o in seq)
{
Asn1Sequence s = Asn1Sequence.GetInstance(o);
attributes.Add(AttributeX509.GetInstance(s));
}
}
/**
* Constructor from an ArrayList of attributes.
*
* The ArrayList consists of attributes of type {@link Attribute Attribute}
*
* @param attributes The attributes.
*
*/
public SubjectDirectoryAttributes(
ArrayList attributes)
{
this.attributes.AddRange(attributes);
}
/**
* Produce an object suitable for an Asn1OutputStream.
*
* Returns:
*
* <pre>
* SubjectDirectoryAttributes ::= Attributes
* Attributes ::= SEQUENCE SIZE (1..MAX) OF Attribute
* Attribute ::= SEQUENCE
* {
* type AttributeType
* values SET OF AttributeValue
* }
*
* AttributeType ::= OBJECT IDENTIFIER
* AttributeValue ::= ANY DEFINED BY AttributeType
* </pre>
*
* @return a DERObject
*/
public override Asn1Object ToAsn1Object()
{
AttributeX509[] v = (AttributeX509[]) attributes.ToArray(typeof(AttributeX509));
return new DerSequence(v);
}
/**
* @return Returns the attributes.
*/
public IEnumerable Attributes
{
get { return new EnumerableProxy(attributes); }
}
}
}

View File

@@ -0,0 +1,95 @@
using System;
using Org.BouncyCastle.Crypto;
using Org.BouncyCastle.Crypto.Digests;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The SubjectKeyIdentifier object.
* <pre>
* SubjectKeyIdentifier::= OCTET STRING
* </pre>
*/
public class SubjectKeyIdentifier
: Asn1Encodable
{
private readonly byte[] keyIdentifier;
public static SubjectKeyIdentifier GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1OctetString.GetInstance(obj, explicitly));
}
public static SubjectKeyIdentifier GetInstance(
object obj)
{
if (obj is SubjectKeyIdentifier)
{
return (SubjectKeyIdentifier) obj;
}
if (obj is SubjectPublicKeyInfo)
{
return new SubjectKeyIdentifier((SubjectPublicKeyInfo) obj);
}
if (obj is Asn1OctetString)
{
return new SubjectKeyIdentifier((Asn1OctetString) obj);
}
if (obj is X509Extension)
{
return GetInstance(X509Extension.ConvertValueToObject((X509Extension) obj));
}
throw new ArgumentException("Invalid SubjectKeyIdentifier: " + obj.GetType().Name);
}
public SubjectKeyIdentifier(
byte[] keyID)
{
if (keyID == null)
throw new ArgumentNullException("keyID");
this.keyIdentifier = keyID;
}
public SubjectKeyIdentifier(
Asn1OctetString keyID)
{
this.keyIdentifier = keyID.GetOctets();
}
/**
*
* Calulates the keyIdentifier using a SHA1 hash over the BIT STRING
* from SubjectPublicKeyInfo as defined in RFC2459.
*
**/
public SubjectKeyIdentifier(
SubjectPublicKeyInfo spki)
{
IDigest digest = new Sha1Digest();
byte[] resBuf = new byte[digest.GetDigestSize()];
byte[] bytes = spki.PublicKeyData.GetBytes();
digest.BlockUpdate(bytes, 0, bytes.Length);
digest.DoFinal(resBuf, 0);
this.keyIdentifier = resBuf;
}
public byte[] GetKeyIdentifier()
{
return keyIdentifier;
}
public override Asn1Object ToAsn1Object()
{
return new DerOctetString(keyIdentifier);
}
}
}

View File

@@ -0,0 +1,106 @@
using System;
using System.Collections;
using System.IO;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The object that contains the public key stored in a certficate.
* <p>
* The GetEncoded() method in the public keys in the JCE produces a DER
* encoded one of these.</p>
*/
public class SubjectPublicKeyInfo
: Asn1Encodable
{
private readonly AlgorithmIdentifier algID;
private readonly DerBitString keyData;
public static SubjectPublicKeyInfo GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static SubjectPublicKeyInfo GetInstance(
object obj)
{
if (obj is SubjectPublicKeyInfo)
{
return (SubjectPublicKeyInfo) obj;
}
if (obj is Asn1Sequence)
{
return new SubjectPublicKeyInfo((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public SubjectPublicKeyInfo(
AlgorithmIdentifier algID,
Asn1Encodable publicKey)
{
this.keyData = new DerBitString(publicKey);
this.algID = algID;
}
public SubjectPublicKeyInfo(
AlgorithmIdentifier algID,
byte[] publicKey)
{
this.keyData = new DerBitString(publicKey);
this.algID = algID;
}
private SubjectPublicKeyInfo(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Bad sequence size: " + seq.Count, "seq");
this.algID = AlgorithmIdentifier.GetInstance(seq[0]);
this.keyData = DerBitString.GetInstance(seq[1]);
}
public AlgorithmIdentifier AlgorithmID
{
get { return algID; }
}
/**
* for when the public key is an encoded object - if the bitstring
* can't be decoded this routine raises an IOException.
*
* @exception IOException - if the bit string doesn't represent a Der
* encoded object.
*/
public Asn1Object GetPublicKey()
{
return Asn1Object.FromByteArray(keyData.GetBytes());
}
/**
* for when the public key is raw bits...
*/
public DerBitString PublicKeyData
{
get { return keyData; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* SubjectPublicKeyInfo ::= Sequence {
* algorithm AlgorithmIdentifier,
* publicKey BIT STRING }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return new DerSequence(algID, keyData);
}
}
}

View File

@@ -0,0 +1,274 @@
using System;
using System.Collections;
using Org.BouncyCastle.Utilities.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
public class CrlEntry
: Asn1Encodable
{
internal Asn1Sequence seq;
internal DerInteger userCertificate;
internal Time revocationDate;
internal X509Extensions crlEntryExtensions;
public CrlEntry(
Asn1Sequence seq)
{
if (seq.Count < 2 || seq.Count > 3)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
this.seq = seq;
userCertificate = DerInteger.GetInstance(seq[0]);
revocationDate = Time.GetInstance(seq[1]);
}
public DerInteger UserCertificate
{
get { return userCertificate; }
}
public Time RevocationDate
{
get { return revocationDate; }
}
public X509Extensions Extensions
{
get
{
if (crlEntryExtensions == null && seq.Count == 3)
{
crlEntryExtensions = X509Extensions.GetInstance(seq[2]);
}
return crlEntryExtensions;
}
}
public override Asn1Object ToAsn1Object()
{
return seq;
}
}
/**
* PKIX RFC-2459 - TbsCertList object.
* <pre>
* TbsCertList ::= Sequence {
* version Version OPTIONAL,
* -- if present, shall be v2
* signature AlgorithmIdentifier,
* issuer Name,
* thisUpdate Time,
* nextUpdate Time OPTIONAL,
* revokedCertificates Sequence OF Sequence {
* userCertificate CertificateSerialNumber,
* revocationDate Time,
* crlEntryExtensions Extensions OPTIONAL
* -- if present, shall be v2
* } OPTIONAL,
* crlExtensions [0] EXPLICIT Extensions OPTIONAL
* -- if present, shall be v2
* }
* </pre>
*/
public class TbsCertificateList
: Asn1Encodable
{
private class RevokedCertificatesEnumeration
: IEnumerable
{
private readonly IEnumerable en;
internal RevokedCertificatesEnumeration(
IEnumerable en)
{
this.en = en;
}
public IEnumerator GetEnumerator()
{
return new RevokedCertificatesEnumerator(en.GetEnumerator());
}
private class RevokedCertificatesEnumerator
: IEnumerator
{
private readonly IEnumerator e;
internal RevokedCertificatesEnumerator(
IEnumerator e)
{
this.e = e;
}
public bool MoveNext()
{
return e.MoveNext();
}
public void Reset()
{
e.Reset();
}
public object Current
{
get { return new CrlEntry(Asn1Sequence.GetInstance(e.Current)); }
}
}
}
internal Asn1Sequence seq;
internal DerInteger version;
internal AlgorithmIdentifier signature;
internal X509Name issuer;
internal Time thisUpdate;
internal Time nextUpdate;
internal Asn1Sequence revokedCertificates;
internal X509Extensions crlExtensions;
public static TbsCertificateList GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static TbsCertificateList GetInstance(
object obj)
{
TbsCertificateList list = obj as TbsCertificateList;
if (obj == null || list != null)
{
return list;
}
if (obj is Asn1Sequence)
{
return new TbsCertificateList((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
internal TbsCertificateList(
Asn1Sequence seq)
{
if (seq.Count < 3 || seq.Count > 7)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
int seqPos = 0;
this.seq = seq;
if (seq[seqPos] is DerInteger)
{
version = DerInteger.GetInstance(seq[seqPos++]);
}
else
{
version = new DerInteger(0);
}
signature = AlgorithmIdentifier.GetInstance(seq[seqPos++]);
issuer = X509Name.GetInstance(seq[seqPos++]);
thisUpdate = Time.GetInstance(seq[seqPos++]);
if (seqPos < seq.Count
&& (seq[seqPos] is DerUtcTime
|| seq[seqPos] is DerGeneralizedTime
|| seq[seqPos] is Time))
{
nextUpdate = Time.GetInstance(seq[seqPos++]);
}
if (seqPos < seq.Count
&& !(seq[seqPos] is DerTaggedObject))
{
revokedCertificates = Asn1Sequence.GetInstance(seq[seqPos++]);
}
if (seqPos < seq.Count
&& seq[seqPos] is DerTaggedObject)
{
crlExtensions = X509Extensions.GetInstance(seq[seqPos]);
}
}
public int Version
{
get { return version.Value.IntValue + 1; }
}
public DerInteger VersionNumber
{
get { return version; }
}
public AlgorithmIdentifier Signature
{
get { return signature; }
}
public X509Name Issuer
{
get { return issuer; }
}
public Time ThisUpdate
{
get { return thisUpdate; }
}
public Time NextUpdate
{
get { return nextUpdate; }
}
public CrlEntry[] GetRevokedCertificates()
{
if (revokedCertificates == null)
{
return new CrlEntry[0];
}
CrlEntry[] entries = new CrlEntry[revokedCertificates.Count];
for (int i = 0; i < entries.Length; i++)
{
entries[i] = new CrlEntry(Asn1Sequence.GetInstance(revokedCertificates[i]));
}
return entries;
}
public IEnumerable GetRevokedCertificateEnumeration()
{
if (revokedCertificates == null)
{
return EmptyEnumerable.Instance;
}
return new RevokedCertificatesEnumeration(revokedCertificates);
}
public X509Extensions Extensions
{
get { return crlExtensions; }
}
public override Asn1Object ToAsn1Object()
{
return seq;
}
}
}

View File

@@ -0,0 +1,189 @@
using System;
using Org.BouncyCastle.Asn1.Pkcs;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The TbsCertificate object.
* <pre>
* TbsCertificate ::= Sequence {
* version [ 0 ] Version DEFAULT v1(0),
* serialNumber CertificateSerialNumber,
* signature AlgorithmIdentifier,
* issuer Name,
* validity Validity,
* subject Name,
* subjectPublicKeyInfo SubjectPublicKeyInfo,
* issuerUniqueID [ 1 ] IMPLICIT UniqueIdentifier OPTIONAL,
* subjectUniqueID [ 2 ] IMPLICIT UniqueIdentifier OPTIONAL,
* extensions [ 3 ] Extensions OPTIONAL
* }
* </pre>
* <p>
* Note: issuerUniqueID and subjectUniqueID are both deprecated by the IETF. This class
* will parse them, but you really shouldn't be creating new ones.</p>
*/
public class TbsCertificateStructure
: Asn1Encodable
{
internal Asn1Sequence seq;
internal DerInteger version;
internal DerInteger serialNumber;
internal AlgorithmIdentifier signature;
internal X509Name issuer;
internal Time startDate, endDate;
internal X509Name subject;
internal SubjectPublicKeyInfo subjectPublicKeyInfo;
internal DerBitString issuerUniqueID;
internal DerBitString subjectUniqueID;
internal X509Extensions extensions;
public static TbsCertificateStructure GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static TbsCertificateStructure GetInstance(
object obj)
{
if (obj is TbsCertificateStructure)
{
return (TbsCertificateStructure) obj;
}
if (obj is Asn1Sequence)
{
return new TbsCertificateStructure((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
internal TbsCertificateStructure(
Asn1Sequence seq)
{
int seqStart = 0;
this.seq = seq;
//
// some certficates don't include a version number - we assume v1
//
if (seq[0] is DerTaggedObject)
{
version = DerInteger.GetInstance(seq[0]);
}
else
{
seqStart = -1; // field 0 is missing!
version = new DerInteger(0);
}
serialNumber = DerInteger.GetInstance(seq[seqStart + 1]);
signature = AlgorithmIdentifier.GetInstance(seq[seqStart + 2]);
issuer = X509Name.GetInstance(seq[seqStart + 3]);
//
// before and after dates
//
Asn1Sequence dates = (Asn1Sequence)seq[seqStart + 4];
startDate = Time.GetInstance(dates[0]);
endDate = Time.GetInstance(dates[1]);
subject = X509Name.GetInstance(seq[seqStart + 5]);
//
// public key info.
//
subjectPublicKeyInfo = SubjectPublicKeyInfo.GetInstance(seq[seqStart + 6]);
for (int extras = seq.Count - (seqStart + 6) - 1; extras > 0; extras--)
{
DerTaggedObject extra = (DerTaggedObject) seq[seqStart + 6 + extras];
switch (extra.TagNo)
{
case 1:
issuerUniqueID = DerBitString.GetInstance(extra, false);
break;
case 2:
subjectUniqueID = DerBitString.GetInstance(extra, false);
break;
case 3:
extensions = X509Extensions.GetInstance(extra);
break;
}
}
}
public int Version
{
get { return version.Value.IntValue + 1; }
}
public DerInteger VersionNumber
{
get { return version; }
}
public DerInteger SerialNumber
{
get { return serialNumber; }
}
public AlgorithmIdentifier Signature
{
get { return signature; }
}
public X509Name Issuer
{
get { return issuer; }
}
public Time StartDate
{
get { return startDate; }
}
public Time EndDate
{
get { return endDate; }
}
public X509Name Subject
{
get { return subject; }
}
public SubjectPublicKeyInfo SubjectPublicKeyInfo
{
get { return subjectPublicKeyInfo; }
}
public DerBitString IssuerUniqueID
{
get { return issuerUniqueID; }
}
public DerBitString SubjectUniqueID
{
get { return subjectUniqueID; }
}
public X509Extensions Extensions
{
get { return extensions; }
}
public override Asn1Object ToAsn1Object()
{
return seq;
}
}
}

View File

@@ -0,0 +1,140 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Target structure used in target information extension for attribute
* certificates from RFC 3281.
*
* <pre>
* Target ::= CHOICE {
* targetName [0] GeneralName,
* targetGroup [1] GeneralName,
* targetCert [2] TargetCert
* }
* </pre>
*
* <p>
* The targetCert field is currently not supported and must not be used
* according to RFC 3281.</p>
*/
public class Target
: Asn1Encodable
//, ASN1Choice
{
public enum Choice
{
Name = 0,
Group = 1
};
private readonly GeneralName targetName;
private readonly GeneralName targetGroup;
/**
* Creates an instance of a Target from the given object.
* <p>
* <code>obj</code> can be a Target or a {@link Asn1TaggedObject}</p>
*
* @param obj The object.
* @return A Target instance.
* @throws ArgumentException if the given object cannot be
* interpreted as Target.
*/
public static Target GetInstance(
object obj)
{
if (obj is Target)
{
return (Target) obj;
}
if (obj is Asn1TaggedObject)
{
return new Target((Asn1TaggedObject) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from Asn1TaggedObject.
*
* @param tagObj The tagged object.
* @throws ArgumentException if the encoding is wrong.
*/
private Target(
Asn1TaggedObject tagObj)
{
switch ((Choice) tagObj.TagNo)
{
case Choice.Name: // GeneralName is already a choice so explicit
targetName = GeneralName.GetInstance(tagObj, true);
break;
case Choice.Group:
targetGroup = GeneralName.GetInstance(tagObj, true);
break;
default:
throw new ArgumentException("unknown tag: " + tagObj.TagNo);
}
}
/**
* Constructor from given details.
* <p>
* Exactly one of the parameters must be not <code>null</code>.</p>
*
* @param type the choice type to apply to the name.
* @param name the general name.
* @throws ArgumentException if type is invalid.
*/
public Target(
Choice type,
GeneralName name)
: this(new DerTaggedObject((int) type, name))
{
}
/**
* @return Returns the targetGroup.
*/
public virtual GeneralName TargetGroup
{
get { return targetGroup; }
}
/**
* @return Returns the targetName.
*/
public virtual GeneralName TargetName
{
get { return targetName; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
*
* Returns:
*
* <pre>
* Target ::= CHOICE {
* targetName [0] GeneralName,
* targetGroup [1] GeneralName,
* targetCert [2] TargetCert
* }
* </pre>
*
* @return an Asn1Object
*/
public override Asn1Object ToAsn1Object()
{
// GeneralName is a choice already so most be explicitly tagged
if (targetName != null)
{
return new DerTaggedObject(true, 0, targetName);
}
return new DerTaggedObject(true, 1, targetGroup);
}
}
}

View File

@@ -0,0 +1,123 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Target information extension for attributes certificates according to RFC
* 3281.
*
* <pre>
* SEQUENCE OF Targets
* </pre>
*
*/
public class TargetInformation
: Asn1Encodable
{
private readonly Asn1Sequence targets;
/**
* Creates an instance of a TargetInformation from the given object.
* <p>
* <code>obj</code> can be a TargetInformation or a {@link Asn1Sequence}</p>
*
* @param obj The object.
* @return A TargetInformation instance.
* @throws ArgumentException if the given object cannot be interpreted as TargetInformation.
*/
public static TargetInformation GetInstance(
object obj)
{
if (obj is TargetInformation)
{
return (TargetInformation) obj;
}
if (obj is Asn1Sequence)
{
return new TargetInformation((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from a Asn1Sequence.
*
* @param seq The Asn1Sequence.
* @throws ArgumentException if the sequence does not contain
* correctly encoded Targets elements.
*/
private TargetInformation(
Asn1Sequence targets)
{
this.targets = targets;
}
/**
* Returns the targets in this target information extension.
* <p>
* The ArrayList is cloned before it is returned.</p>
*
* @return Returns the targets.
*/
public virtual Targets[] GetTargetsObjects()
{
Targets[] result = new Targets[targets.Count];
for (int i = 0; i < targets.Count; ++i)
{
result[i] = Targets.GetInstance(targets[i]);
}
return result;
}
/**
* Constructs a target information from a single targets element.
* According to RFC 3281 only one targets element must be produced.
*
* @param targets A Targets instance.
*/
public TargetInformation(
Targets targets)
{
this.targets = new DerSequence(targets);
}
/**
* According to RFC 3281 only one targets element must be produced. If
* multiple targets are given they must be merged in
* into one targets element.
*
* @param targets An array with {@link Targets}.
*/
public TargetInformation(
Target[] targets)
: this(new Targets(targets))
{
}
/**
* Produce an object suitable for an Asn1OutputStream.
*
* Returns:
*
* <pre>
* SEQUENCE OF Targets
* </pre>
*
* <p>
* According to RFC 3281 only one targets element must be produced. If
* multiple targets are given in the constructor they are merged into one
* targets element. If this was produced from a
* {@link Org.BouncyCastle.Asn1.Asn1Sequence} the encoding is kept.</p>
*
* @return an Asn1Object
*/
public override Asn1Object ToAsn1Object()
{
return targets;
}
}
}

View File

@@ -0,0 +1,121 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Targets structure used in target information extension for attribute
* certificates from RFC 3281.
*
* <pre>
* Targets ::= SEQUENCE OF Target
*
* Target ::= CHOICE {
* targetName [0] GeneralName,
* targetGroup [1] GeneralName,
* targetCert [2] TargetCert
* }
*
* TargetCert ::= SEQUENCE {
* targetCertificate IssuerSerial,
* targetName GeneralName OPTIONAL,
* certDigestInfo ObjectDigestInfo OPTIONAL
* }
* </pre>
*
* @see org.bouncycastle.asn1.x509.Target
* @see org.bouncycastle.asn1.x509.TargetInformation
*/
public class Targets
: Asn1Encodable
{
private readonly Asn1Sequence targets;
/**
* Creates an instance of a Targets from the given object.
* <p>
* <code>obj</code> can be a Targets or a {@link Asn1Sequence}</p>
*
* @param obj The object.
* @return A Targets instance.
* @throws ArgumentException if the given object cannot be interpreted as Target.
*/
public static Targets GetInstance(
object obj)
{
if (obj is Targets)
{
return (Targets) obj;
}
if (obj is Asn1Sequence)
{
return new Targets((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from Asn1Sequence.
*
* @param targets The ASN.1 SEQUENCE.
* @throws ArgumentException if the contents of the sequence are
* invalid.
*/
private Targets(
Asn1Sequence targets)
{
this.targets = targets;
}
/**
* Constructor from given targets.
* <p>
* The ArrayList is copied.</p>
*
* @param targets An <code>ArrayList</code> of {@link Target}s.
* @see Target
* @throws ArgumentException if the ArrayList contains not only Targets.
*/
public Targets(
Target[] targets)
{
this.targets = new DerSequence(targets);
}
/**
* Returns the targets in an <code>ArrayList</code>.
* <p>
* The ArrayList is cloned before it is returned.</p>
*
* @return Returns the targets.
*/
public virtual Target[] GetTargets()
{
Target[] result = new Target[targets.Count];
for (int i = 0; i < targets.Count; ++i)
{
result[i] = Target.GetInstance(targets[i]);
}
return result;
}
/**
* Produce an object suitable for an Asn1OutputStream.
*
* Returns:
*
* <pre>
* Targets ::= SEQUENCE OF Target
* </pre>
*
* @return an Asn1Object
*/
public override Asn1Object ToAsn1Object()
{
return targets;
}
}
}

View File

@@ -0,0 +1,126 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
public class Time
: Asn1Encodable
{
internal Asn1Object time;
public static Time GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(obj.GetObject());
}
public Time(
Asn1Object time)
{
if (time == null)
throw new ArgumentNullException("time");
if (!(time is DerUtcTime) && !(time is DerGeneralizedTime))
{
throw new ArgumentException("unknown object passed to Time");
}
this.time = time;
}
/**
* creates a time object from a given date - if the date is between 1950
* and 2049 a UTCTime object is Generated, otherwise a GeneralizedTime
* is used.
*/
public Time(
DateTime date)
{
string d = date.ToString("yyyyMMddHHmmss") + "Z";
int year = Int32.Parse(d.Substring(0, 4));
if (year < 1950 || year > 2049)
{
time = new DerGeneralizedTime(d);
}
else
{
time = new DerUtcTime(d.Substring(2));
}
}
public static Time GetInstance(
object obj)
{
if (obj is Time)
{
return (Time) obj;
}
if (obj is DerUtcTime)
{
return new Time((DerUtcTime) obj);
}
if (obj is DerGeneralizedTime)
{
return new Time((DerGeneralizedTime) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public string GetTime()
{
if (time is DerUtcTime)
{
return ((DerUtcTime) time).AdjustedTimeString;
}
return ((DerGeneralizedTime) time).GetTime();
}
/// <summary>
/// Return our time as DateTime.
/// </summary>
/// <returns>A date time.</returns>
public DateTime ToDateTime()
{
try
{
if (time is DerUtcTime)
{
return ((DerUtcTime)time).ToAdjustedDateTime();
}
else
{
return ((DerGeneralizedTime)time).ToDateTime();
}
}
catch (FormatException e)
{
// this should never happen
throw new InvalidOperationException("invalid date string: " + e.Message);
}
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* Time ::= CHOICE {
* utcTime UTCTime,
* generalTime GeneralizedTime }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
return time;
}
public override string ToString()
{
return GetTime();
}
}
}

View File

@@ -0,0 +1,104 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* <code>UserNotice</code> class, used in
* <code>CertificatePolicies</code> X509 extensions (in policy
* qualifiers).
* <pre>
* UserNotice ::= Sequence {
* noticeRef NoticeReference OPTIONAL,
* explicitText DisplayText OPTIONAL}
*
* </pre>
*
* @see PolicyQualifierId
* @see PolicyInformation
*/
public class UserNotice
: Asn1Encodable
{
internal NoticeReference noticeRef;
internal DisplayText explicitText;
/**
* Creates a new <code>UserNotice</code> instance.
*
* @param noticeRef a <code>NoticeReference</code> value
* @param explicitText a <code>DisplayText</code> value
*/
public UserNotice(
NoticeReference noticeRef,
DisplayText explicitText)
{
this.noticeRef = noticeRef;
this.explicitText = explicitText;
}
/**
* Creates a new <code>UserNotice</code> instance.
*
* @param noticeRef a <code>NoticeReference</code> value
* @param str the explicitText field as a string.
*/
public UserNotice(
NoticeReference noticeRef,
string str)
{
this.noticeRef = noticeRef;
this.explicitText = new DisplayText(str);
}
/**
* Creates a new <code>UserNotice</code> instance.
* <p>Useful from reconstructing a <code>UserNotice</code> instance
* from its encodable/encoded form.
*
* @param as an <code>ASN1Sequence</code> value obtained from either
* calling @{link toASN1Object()} for a <code>UserNotice</code>
* instance or from parsing it from a DER-encoded stream.</p>
*/
public UserNotice(
Asn1Sequence seq)
{
if (seq.Count == 2)
{
noticeRef = NoticeReference.GetInstance(seq[0]);
explicitText = DisplayText.GetInstance(seq[1]);
}
else if (seq.Count == 1)
{
if (seq[0].ToAsn1Object() is Asn1Sequence)
{
noticeRef = NoticeReference.GetInstance(seq[0]);
}
else
{
explicitText = DisplayText.GetInstance(seq[0]);
}
}
else
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
}
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector av = new Asn1EncodableVector();
if (noticeRef != null)
{
av.Add(noticeRef);
}
if (explicitText != null)
{
av.Add(explicitText);
}
return new DerSequence(av);
}
}
}

View File

@@ -0,0 +1,108 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Generator for Version 1 TbsCertificateStructures.
* <pre>
* TbsCertificate ::= Sequence {
* version [ 0 ] Version DEFAULT v1(0),
* serialNumber CertificateSerialNumber,
* signature AlgorithmIdentifier,
* issuer Name,
* validity Validity,
* subject Name,
* subjectPublicKeyInfo SubjectPublicKeyInfo,
* }
* </pre>
*
*/
public class V1TbsCertificateGenerator
{
internal DerTaggedObject version = new DerTaggedObject(0, new DerInteger(0));
internal DerInteger serialNumber;
internal AlgorithmIdentifier signature;
internal X509Name issuer;
internal Time startDate, endDate;
internal X509Name subject;
internal SubjectPublicKeyInfo subjectPublicKeyInfo;
public V1TbsCertificateGenerator()
{
}
public void SetSerialNumber(
DerInteger serialNumber)
{
this.serialNumber = serialNumber;
}
public void SetSignature(
AlgorithmIdentifier signature)
{
this.signature = signature;
}
public void SetIssuer(
X509Name issuer)
{
this.issuer = issuer;
}
public void SetStartDate(
Time startDate)
{
this.startDate = startDate;
}
public void SetStartDate(
DerUtcTime startDate)
{
this.startDate = new Time(startDate);
}
public void SetEndDate(
Time endDate)
{
this.endDate = endDate;
}
public void SetEndDate(
DerUtcTime endDate)
{
this.endDate = new Time(endDate);
}
public void SetSubject(
X509Name subject)
{
this.subject = subject;
}
public void SetSubjectPublicKeyInfo(
SubjectPublicKeyInfo pubKeyInfo)
{
this.subjectPublicKeyInfo = pubKeyInfo;
}
public TbsCertificateStructure GenerateTbsCertificate()
{
if ((serialNumber == null) || (signature == null)
|| (issuer == null) || (startDate == null) || (endDate == null)
|| (subject == null) || (subjectPublicKeyInfo == null))
{
throw new InvalidOperationException("not all mandatory fields set in V1 TBScertificate generator");
}
return new TbsCertificateStructure(
new DerSequence(
//version, - not required as default value
serialNumber,
signature,
issuer,
new DerSequence(startDate, endDate), // before and after dates
subject,
subjectPublicKeyInfo));
}
}
}

View File

@@ -0,0 +1,137 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Generator for Version 2 AttributeCertificateInfo
* <pre>
* AttributeCertificateInfo ::= Sequence {
* version AttCertVersion -- version is v2,
* holder Holder,
* issuer AttCertIssuer,
* signature AlgorithmIdentifier,
* serialNumber CertificateSerialNumber,
* attrCertValidityPeriod AttCertValidityPeriod,
* attributes Sequence OF Attr,
* issuerUniqueID UniqueIdentifier OPTIONAL,
* extensions Extensions OPTIONAL
* }
* </pre>
*
*/
public class V2AttributeCertificateInfoGenerator
{
internal DerInteger version;
internal Holder holder;
internal AttCertIssuer issuer;
internal AlgorithmIdentifier signature;
internal DerInteger serialNumber;
// internal AttCertValidityPeriod attrCertValidityPeriod;
internal Asn1EncodableVector attributes;
internal DerBitString issuerUniqueID;
internal X509Extensions extensions;
internal DerGeneralizedTime startDate, endDate;
public V2AttributeCertificateInfoGenerator()
{
this.version = new DerInteger(1);
attributes = new Asn1EncodableVector();
}
public void SetHolder(
Holder holder)
{
this.holder = holder;
}
public void AddAttribute(
string oid,
Asn1Encodable value)
{
attributes.Add(new AttributeX509(new DerObjectIdentifier(oid), new DerSet(value)));
}
/**
* @param attribute
*/
public void AddAttribute(AttributeX509 attribute)
{
attributes.Add(attribute);
}
public void SetSerialNumber(
DerInteger serialNumber)
{
this.serialNumber = serialNumber;
}
public void SetSignature(
AlgorithmIdentifier signature)
{
this.signature = signature;
}
public void SetIssuer(
AttCertIssuer issuer)
{
this.issuer = issuer;
}
public void SetStartDate(
DerGeneralizedTime startDate)
{
this.startDate = startDate;
}
public void SetEndDate(
DerGeneralizedTime endDate)
{
this.endDate = endDate;
}
public void SetIssuerUniqueID(
DerBitString issuerUniqueID)
{
this.issuerUniqueID = issuerUniqueID;
}
public void SetExtensions(
X509Extensions extensions)
{
this.extensions = extensions;
}
public AttributeCertificateInfo GenerateAttributeCertificateInfo()
{
if ((serialNumber == null) || (signature == null)
|| (issuer == null) || (startDate == null) || (endDate == null)
|| (holder == null) || (attributes == null))
{
throw new InvalidOperationException("not all mandatory fields set in V2 AttributeCertificateInfo generator");
}
Asn1EncodableVector v = new Asn1EncodableVector(
version, holder, issuer, signature, serialNumber);
//
// before and after dates => AttCertValidityPeriod
//
v.Add(new AttCertValidityPeriod(startDate, endDate));
// Attributes
v.Add(new DerSequence(attributes));
if (issuerUniqueID != null)
{
v.Add(issuerUniqueID);
}
if (extensions != null)
{
v.Add(extensions);
}
return AttributeCertificateInfo.GetInstance(new DerSequence(v));
}
}
}

View File

@@ -0,0 +1,125 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
public class V2Form
: Asn1Encodable
{
internal GeneralNames issuerName;
internal IssuerSerial baseCertificateID;
internal ObjectDigestInfo objectDigestInfo;
public static V2Form GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static V2Form GetInstance(
object obj)
{
if (obj is V2Form)
{
return (V2Form) obj;
}
if (obj is Asn1Sequence)
{
return new V2Form((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public V2Form(
GeneralNames issuerName)
{
this.issuerName = issuerName;
}
private V2Form(
Asn1Sequence seq)
{
if (seq.Count > 3)
{
throw new ArgumentException("Bad sequence size: " + seq.Count);
}
int index = 0;
if (!(seq[0] is Asn1TaggedObject))
{
index++;
this.issuerName = GeneralNames.GetInstance(seq[0]);
}
for (int i = index; i != seq.Count; i++)
{
Asn1TaggedObject o = Asn1TaggedObject.GetInstance(seq[i]);
if (o.TagNo == 0)
{
baseCertificateID = IssuerSerial.GetInstance(o, false);
}
else if (o.TagNo == 1)
{
objectDigestInfo = ObjectDigestInfo.GetInstance(o, false);
}
else
{
throw new ArgumentException("Bad tag number: " + o.TagNo);
}
}
}
public GeneralNames IssuerName
{
get { return issuerName; }
}
public IssuerSerial BaseCertificateID
{
get { return baseCertificateID; }
}
public ObjectDigestInfo ObjectDigestInfo
{
get { return objectDigestInfo; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <pre>
* V2Form ::= Sequence {
* issuerName GeneralNames OPTIONAL,
* baseCertificateID [0] IssuerSerial OPTIONAL,
* objectDigestInfo [1] ObjectDigestInfo OPTIONAL
* -- issuerName MUST be present in this profile
* -- baseCertificateID and objectDigestInfo MUST NOT
* -- be present in this profile
* }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector v = new Asn1EncodableVector();
if (issuerName != null)
{
v.Add(issuerName);
}
if (baseCertificateID != null)
{
v.Add(new DerTaggedObject(false, 0, baseCertificateID));
}
if (objectDigestInfo != null)
{
v.Add(new DerTaggedObject(false, 1, objectDigestInfo));
}
return new DerSequence(v);
}
}
}

View File

@@ -0,0 +1,196 @@
using System;
using System.Collections;
using System.IO;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Generator for Version 2 TbsCertList structures.
* <pre>
* TbsCertList ::= Sequence {
* version Version OPTIONAL,
* -- if present, shall be v2
* signature AlgorithmIdentifier,
* issuer Name,
* thisUpdate Time,
* nextUpdate Time OPTIONAL,
* revokedCertificates Sequence OF Sequence {
* userCertificate CertificateSerialNumber,
* revocationDate Time,
* crlEntryExtensions Extensions OPTIONAL
* -- if present, shall be v2
* } OPTIONAL,
* crlExtensions [0] EXPLICIT Extensions OPTIONAL
* -- if present, shall be v2
* }
* </pre>
*
* <b>Note: This class may be subject to change</b>
*/
public class V2TbsCertListGenerator
{
private DerInteger version = new DerInteger(1);
private AlgorithmIdentifier signature;
private X509Name issuer;
private Time thisUpdate, nextUpdate;
private X509Extensions extensions;
private ArrayList crlEntries;
public V2TbsCertListGenerator()
{
}
public void SetSignature(
AlgorithmIdentifier signature)
{
this.signature = signature;
}
public void SetIssuer(
X509Name issuer)
{
this.issuer = issuer;
}
public void SetThisUpdate(
DerUtcTime thisUpdate)
{
this.thisUpdate = new Time(thisUpdate);
}
public void SetNextUpdate(
DerUtcTime nextUpdate)
{
this.nextUpdate = (nextUpdate != null)
? new Time(nextUpdate)
: null;
}
public void SetThisUpdate(
Time thisUpdate)
{
this.thisUpdate = thisUpdate;
}
public void SetNextUpdate(
Time nextUpdate)
{
this.nextUpdate = nextUpdate;
}
public void AddCrlEntry(
Asn1Sequence crlEntry)
{
if (crlEntries == null)
{
crlEntries = new ArrayList();
}
crlEntries.Add(crlEntry);
}
public void AddCrlEntry(DerInteger userCertificate, DerUtcTime revocationDate, int reason)
{
AddCrlEntry(userCertificate, new Time(revocationDate), reason);
}
public void AddCrlEntry(DerInteger userCertificate, Time revocationDate, int reason)
{
AddCrlEntry(userCertificate, revocationDate, reason, null);
}
public void AddCrlEntry(DerInteger userCertificate, Time revocationDate, int reason,
DerGeneralizedTime invalidityDate)
{
ArrayList extOids = new ArrayList();
ArrayList extValues = new ArrayList();
if (reason != 0)
{
CrlReason crlReason = new CrlReason(reason);
try
{
extOids.Add(X509Extensions.ReasonCode);
extValues.Add(new X509Extension(false, new DerOctetString(crlReason.GetEncoded())));
}
catch (IOException e)
{
throw new ArgumentException("error encoding reason: " + e);
}
}
if (invalidityDate != null)
{
try
{
extOids.Add(X509Extensions.InvalidityDate);
extValues.Add(new X509Extension(false, new DerOctetString(invalidityDate.GetEncoded())));
}
catch (IOException e)
{
throw new ArgumentException("error encoding invalidityDate: " + e);
}
}
if (extOids.Count != 0)
{
AddCrlEntry(userCertificate, revocationDate, new X509Extensions(extOids, extValues));
}
else
{
AddCrlEntry(userCertificate, revocationDate, null);
}
}
public void AddCrlEntry(DerInteger userCertificate, Time revocationDate, X509Extensions extensions)
{
Asn1EncodableVector v = new Asn1EncodableVector(
userCertificate, revocationDate);
if (extensions != null)
{
v.Add(extensions);
}
AddCrlEntry(new DerSequence(v));
}
public void SetExtensions(
X509Extensions extensions)
{
this.extensions = extensions;
}
public TbsCertificateList GenerateTbsCertList()
{
if ((signature == null) || (issuer == null) || (thisUpdate == null))
{
throw new InvalidOperationException("Not all mandatory fields set in V2 TbsCertList generator.");
}
Asn1EncodableVector v = new Asn1EncodableVector(
version, signature, issuer, thisUpdate);
if (nextUpdate != null)
{
v.Add(nextUpdate);
}
// Add CRLEntries if they exist
if (crlEntries != null)
{
Asn1Sequence[] certs = (Asn1Sequence[]) crlEntries.ToArray(typeof(Asn1Sequence));
v.Add(new DerSequence(certs));
}
if (extensions != null)
{
v.Add(new DerTaggedObject(0, extensions));
}
return new TbsCertificateList(new DerSequence(v));
}
}
}

View File

@@ -0,0 +1,144 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* Generator for Version 3 TbsCertificateStructures.
* <pre>
* TbsCertificate ::= Sequence {
* version [ 0 ] Version DEFAULT v1(0),
* serialNumber CertificateSerialNumber,
* signature AlgorithmIdentifier,
* issuer Name,
* validity Validity,
* subject Name,
* subjectPublicKeyInfo SubjectPublicKeyInfo,
* issuerUniqueID [ 1 ] IMPLICIT UniqueIdentifier OPTIONAL,
* subjectUniqueID [ 2 ] IMPLICIT UniqueIdentifier OPTIONAL,
* extensions [ 3 ] Extensions OPTIONAL
* }
* </pre>
*
*/
public class V3TbsCertificateGenerator
{
internal DerTaggedObject version = new DerTaggedObject(0, new DerInteger(2));
internal DerInteger serialNumber;
internal AlgorithmIdentifier signature;
internal X509Name issuer;
internal Time startDate, endDate;
internal X509Name subject;
internal SubjectPublicKeyInfo subjectPublicKeyInfo;
internal X509Extensions extensions;
private bool altNamePresentAndCritical;
public V3TbsCertificateGenerator()
{
}
public void SetSerialNumber(
DerInteger serialNumber)
{
this.serialNumber = serialNumber;
}
public void SetSignature(
AlgorithmIdentifier signature)
{
this.signature = signature;
}
public void SetIssuer(
X509Name issuer)
{
this.issuer = issuer;
}
public void SetStartDate(
DerUtcTime startDate)
{
this.startDate = new Time(startDate);
}
public void SetStartDate(
Time startDate)
{
this.startDate = startDate;
}
public void SetEndDate(
DerUtcTime endDate)
{
this.endDate = new Time(endDate);
}
public void SetEndDate(
Time endDate)
{
this.endDate = endDate;
}
public void SetSubject(
X509Name subject)
{
this.subject = subject;
}
public void SetSubjectPublicKeyInfo(
SubjectPublicKeyInfo pubKeyInfo)
{
this.subjectPublicKeyInfo = pubKeyInfo;
}
public void SetExtensions(
X509Extensions extensions)
{
this.extensions = extensions;
if (extensions != null)
{
X509Extension altName = extensions.GetExtension(X509Extensions.SubjectAlternativeName);
if (altName != null && altName.IsCritical)
{
altNamePresentAndCritical = true;
}
}
}
public TbsCertificateStructure GenerateTbsCertificate()
{
if ((serialNumber == null) || (signature == null)
|| (issuer == null) || (startDate == null) || (endDate == null)
|| (subject == null && !altNamePresentAndCritical)
|| (subjectPublicKeyInfo == null))
{
throw new InvalidOperationException("not all mandatory fields set in V3 TBScertificate generator");
}
DerSequence validity = new DerSequence(startDate, endDate); // before and after dates
Asn1EncodableVector v = new Asn1EncodableVector(
version, serialNumber, signature, issuer, validity);
if (subject != null)
{
v.Add(subject);
}
else
{
v.Add(DerSequence.Empty);
}
v.Add(subjectPublicKeyInfo);
if (extensions != null)
{
v.Add(new DerTaggedObject(3, extensions));
}
return new TbsCertificateStructure(new DerSequence(v));
}
}
}

View File

@@ -0,0 +1,9 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
public class X509Attributes
{
public static readonly DerObjectIdentifier RoleSyntax = new DerObjectIdentifier("2.5.4.72");
}
}

View File

@@ -0,0 +1,133 @@
using System;
using Org.BouncyCastle.Asn1.Pkcs;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* an X509Certificate structure.
* <pre>
* Certificate ::= Sequence {
* tbsCertificate TbsCertificate,
* signatureAlgorithm AlgorithmIdentifier,
* signature BIT STRING
* }
* </pre>
*/
public class X509CertificateStructure
: Asn1Encodable
{
private readonly TbsCertificateStructure tbsCert;
private readonly AlgorithmIdentifier sigAlgID;
private readonly DerBitString sig;
public static X509CertificateStructure GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static X509CertificateStructure GetInstance(
object obj)
{
if (obj is X509CertificateStructure)
{
return (X509CertificateStructure) obj;
}
if (obj is Asn1Sequence)
{
return new X509CertificateStructure((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
public X509CertificateStructure(
TbsCertificateStructure tbsCert,
AlgorithmIdentifier sigAlgID,
DerBitString sig)
{
if (tbsCert == null)
throw new ArgumentNullException("tbsCert");
if (sigAlgID == null)
throw new ArgumentNullException("sigAlgID");
if (sig == null)
throw new ArgumentNullException("sig");
this.tbsCert = tbsCert;
this.sigAlgID = sigAlgID;
this.sig = sig;
}
private X509CertificateStructure(
Asn1Sequence seq)
{
if (seq.Count != 3)
throw new ArgumentException("sequence wrong size for a certificate", "seq");
//
// correct x509 certficate
//
tbsCert = TbsCertificateStructure.GetInstance(seq[0]);
sigAlgID = AlgorithmIdentifier.GetInstance(seq[1]);
sig = DerBitString.GetInstance(seq[2]);
}
public TbsCertificateStructure TbsCertificate
{
get { return tbsCert; }
}
public int Version
{
get { return tbsCert.Version; }
}
public DerInteger SerialNumber
{
get { return tbsCert.SerialNumber; }
}
public X509Name Issuer
{
get { return tbsCert.Issuer; }
}
public Time StartDate
{
get { return tbsCert.StartDate; }
}
public Time EndDate
{
get { return tbsCert.EndDate; }
}
public X509Name Subject
{
get { return tbsCert.Subject; }
}
public SubjectPublicKeyInfo SubjectPublicKeyInfo
{
get { return tbsCert.SubjectPublicKeyInfo; }
}
public AlgorithmIdentifier SignatureAlgorithm
{
get { return sigAlgID; }
}
public DerBitString Signature
{
get { return sig; }
}
public override Asn1Object ToAsn1Object()
{
return new DerSequence(tbsCert, sigAlgID, sig);
}
}
}

View File

@@ -0,0 +1,62 @@
using System;
using System.IO;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* The default converter for X509 DN entries when going from their
* string value to ASN.1 strings.
*/
public class X509DefaultEntryConverter
: X509NameEntryConverter
{
/**
* Apply default conversion for the given value depending on the oid
* and the character range of the value.
*
* @param oid the object identifier for the DN entry
* @param value the value associated with it
* @return the ASN.1 equivalent for the string value.
*/
public override Asn1Object GetConvertedValue(
DerObjectIdentifier oid,
string value)
{
if (value.Length != 0 && value[0] == '#')
{
try
{
return ConvertHexEncoded(value, 1);
}
catch (IOException)
{
throw new Exception("can't recode value for oid " + oid.Id);
}
}
if (value.Length != 0 && value[0] == '\\')
{
value = value.Substring(1);
}
if (oid.Equals(X509Name.EmailAddress) || oid.Equals(X509Name.DC))
{
return new DerIA5String(value);
}
if (oid.Equals(X509Name.DateOfBirth)) // accept time string as well as # (for compatibility)
{
return new DerGeneralizedTime(value);
}
if (oid.Equals(X509Name.C)
|| oid.Equals(X509Name.SerialNumber)
|| oid.Equals(X509Name.DnQualifier))
{
return new DerPrintableString(value);
}
return new DerUtf8String(value);
}
}
}

View File

@@ -0,0 +1,74 @@
using System;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* an object for the elements in the X.509 V3 extension block.
*/
public class X509Extension
{
internal bool critical;
internal Asn1OctetString value;
public X509Extension(
DerBoolean critical,
Asn1OctetString value)
{
if (critical == null)
{
throw new ArgumentNullException("critical");
}
this.critical = critical.IsTrue;
this.value = value;
}
public X509Extension(
bool critical,
Asn1OctetString value)
{
this.critical = critical;
this.value = value;
}
public bool IsCritical { get { return critical; } }
public Asn1OctetString Value { get { return value; } }
public override int GetHashCode()
{
int vh = this.Value.GetHashCode();
return IsCritical ? vh : ~vh;
}
public override bool Equals(
object obj)
{
X509Extension other = obj as X509Extension;
if (other == null)
{
return false;
}
return Value.Equals(other.Value) && IsCritical == other.IsCritical;
}
/// <sumary>Convert the value of the passed in extension to an object.</sumary>
/// <param name="ext">The extension to parse.</param>
/// <returns>The object the value string contains.</returns>
/// <exception cref="ArgumentException">If conversion is not possible.</exception>
public static Asn1Object ConvertValueToObject(
X509Extension ext)
{
try
{
return Asn1Object.FromByteArray(ext.Value.GetOctets());
}
catch (Exception e)
{
throw new ArgumentException("can't convert extension", e);
}
}
}
}

View File

@@ -0,0 +1,348 @@
using System;
using System.Collections;
using Org.BouncyCastle.Utilities.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
public class X509Extensions
: Asn1Encodable
{
/**
* Subject Directory Attributes
*/
public static readonly DerObjectIdentifier SubjectDirectoryAttributes = new DerObjectIdentifier("2.5.29.9");
/**
* Subject Key Identifier
*/
public static readonly DerObjectIdentifier SubjectKeyIdentifier = new DerObjectIdentifier("2.5.29.14");
/**
* Key Usage
*/
public static readonly DerObjectIdentifier KeyUsage = new DerObjectIdentifier("2.5.29.15");
/**
* Private Key Usage Period
*/
public static readonly DerObjectIdentifier PrivateKeyUsagePeriod = new DerObjectIdentifier("2.5.29.16");
/**
* Subject Alternative Name
*/
public static readonly DerObjectIdentifier SubjectAlternativeName = new DerObjectIdentifier("2.5.29.17");
/**
* Issuer Alternative Name
*/
public static readonly DerObjectIdentifier IssuerAlternativeName = new DerObjectIdentifier("2.5.29.18");
/**
* Basic Constraints
*/
public static readonly DerObjectIdentifier BasicConstraints = new DerObjectIdentifier("2.5.29.19");
/**
* CRL Number
*/
public static readonly DerObjectIdentifier CrlNumber = new DerObjectIdentifier("2.5.29.20");
/**
* Reason code
*/
public static readonly DerObjectIdentifier ReasonCode = new DerObjectIdentifier("2.5.29.21");
/**
* Hold Instruction Code
*/
public static readonly DerObjectIdentifier InstructionCode = new DerObjectIdentifier("2.5.29.23");
/**
* Invalidity Date
*/
public static readonly DerObjectIdentifier InvalidityDate = new DerObjectIdentifier("2.5.29.24");
/**
* Delta CRL indicator
*/
public static readonly DerObjectIdentifier DeltaCrlIndicator = new DerObjectIdentifier("2.5.29.27");
/**
* Issuing Distribution Point
*/
public static readonly DerObjectIdentifier IssuingDistributionPoint = new DerObjectIdentifier("2.5.29.28");
/**
* Certificate Issuer
*/
public static readonly DerObjectIdentifier CertificateIssuer = new DerObjectIdentifier("2.5.29.29");
/**
* Name Constraints
*/
public static readonly DerObjectIdentifier NameConstraints = new DerObjectIdentifier("2.5.29.30");
/**
* CRL Distribution Points
*/
public static readonly DerObjectIdentifier CrlDistributionPoints = new DerObjectIdentifier("2.5.29.31");
/**
* Certificate Policies
*/
public static readonly DerObjectIdentifier CertificatePolicies = new DerObjectIdentifier("2.5.29.32");
/**
* Policy Mappings
*/
public static readonly DerObjectIdentifier PolicyMappings = new DerObjectIdentifier("2.5.29.33");
/**
* Authority Key Identifier
*/
public static readonly DerObjectIdentifier AuthorityKeyIdentifier = new DerObjectIdentifier("2.5.29.35");
/**
* Policy Constraints
*/
public static readonly DerObjectIdentifier PolicyConstraints = new DerObjectIdentifier("2.5.29.36");
/**
* Extended Key Usage
*/
public static readonly DerObjectIdentifier ExtendedKeyUsage = new DerObjectIdentifier("2.5.29.37");
/**
* Freshest CRL
*/
public static readonly DerObjectIdentifier FreshestCrl = new DerObjectIdentifier("2.5.29.46");
/**
* Inhibit Any Policy
*/
public static readonly DerObjectIdentifier InhibitAnyPolicy = new DerObjectIdentifier("2.5.29.54");
/**
* Authority Info Access
*/
public static readonly DerObjectIdentifier AuthorityInfoAccess = new DerObjectIdentifier("1.3.6.1.5.5.7.1.1");
/**
* Subject Info Access
*/
public static readonly DerObjectIdentifier SubjectInfoAccess = new DerObjectIdentifier("1.3.6.1.5.5.7.1.11");
/**
* Logo Type
*/
public static readonly DerObjectIdentifier LogoType = new DerObjectIdentifier("1.3.6.1.5.5.7.1.12");
/**
* BiometricInfo
*/
public static readonly DerObjectIdentifier BiometricInfo = new DerObjectIdentifier("1.3.6.1.5.5.7.1.2");
/**
* QCStatements
*/
public static readonly DerObjectIdentifier QCStatements = new DerObjectIdentifier("1.3.6.1.5.5.7.1.3");
/**
* Audit identity extension in attribute certificates.
*/
public static readonly DerObjectIdentifier AuditIdentity = new DerObjectIdentifier("1.3.6.1.5.5.7.1.4");
/**
* NoRevAvail extension in attribute certificates.
*/
public static readonly DerObjectIdentifier NoRevAvail = new DerObjectIdentifier("2.5.29.56");
/**
* TargetInformation extension in attribute certificates.
*/
public static readonly DerObjectIdentifier TargetInformation = new DerObjectIdentifier("2.5.29.55");
private readonly Hashtable extensions = new Hashtable();
private readonly ArrayList ordering = new ArrayList();
public static X509Extensions GetInstance(
Asn1TaggedObject obj,
bool explicitly)
{
return GetInstance(Asn1Sequence.GetInstance(obj, explicitly));
}
public static X509Extensions GetInstance(
object obj)
{
if (obj == null || obj is X509Extensions)
{
return (X509Extensions) obj;
}
if (obj is Asn1Sequence)
{
return new X509Extensions((Asn1Sequence) obj);
}
if (obj is Asn1TaggedObject)
{
return GetInstance(((Asn1TaggedObject) obj).GetObject());
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from Asn1Sequence.
*
* the extensions are a list of constructed sequences, either with (Oid, OctetString) or (Oid, Boolean, OctetString)
*/
private X509Extensions(
Asn1Sequence seq)
{
foreach (Asn1Encodable ae in seq)
{
Asn1Sequence s = Asn1Sequence.GetInstance(ae.ToAsn1Object());
if (s.Count < 2 || s.Count > 3)
throw new ArgumentException("Bad sequence size: " + s.Count);
DerObjectIdentifier oid = DerObjectIdentifier.GetInstance(s[0].ToAsn1Object());
bool isCritical = s.Count == 3
&& DerBoolean.GetInstance(s[1].ToAsn1Object()).IsTrue;
Asn1OctetString octets = Asn1OctetString.GetInstance(s[s.Count - 1].ToAsn1Object());
extensions.Add(oid, new X509Extension(isCritical, octets));
ordering.Add(oid);
}
}
/**
* constructor from a table of extensions.
* <p>
* it's is assumed the table contains Oid/string pairs.</p>
*/
public X509Extensions(
Hashtable extensions)
: this(null, extensions)
{
}
/**
* Constructor from a table of extensions with ordering.
* <p>
* It's is assumed the table contains Oid/string pairs.</p>
*/
public X509Extensions(
ArrayList ordering,
Hashtable extensions)
{
ICollection c = ordering == null
? extensions.Keys
: ordering;
this.ordering.AddRange(c);
foreach (DerObjectIdentifier oid in this.ordering)
{
this.extensions.Add(oid, (X509Extension) extensions[oid]);
}
}
/**
* Constructor from two vectors
*
* @param objectIDs an ArrayList of the object identifiers.
* @param values an ArrayList of the extension values.
*/
public X509Extensions(
ArrayList oids,
ArrayList values)
{
this.ordering.AddRange(oids);
int count = 0;
foreach (DerObjectIdentifier oid in this.ordering)
{
this.extensions.Add(oid, (X509Extension) values[count++]);
}
}
[Obsolete("Use ExtensionOids IEnumerable property")]
public IEnumerator Oids()
{
return ExtensionOids.GetEnumerator();
}
/**
* return an Enumeration of the extension field's object ids.
*/
public IEnumerable ExtensionOids
{
get { return new EnumerableProxy(ordering); }
}
/**
* return the extension represented by the object identifier
* passed in.
*
* @return the extension if it's present, null otherwise.
*/
public X509Extension GetExtension(
DerObjectIdentifier oid)
{
return (X509Extension) extensions[oid];
}
/**
* <pre>
* Extensions ::= SEQUENCE SIZE (1..MAX) OF Extension
*
* Extension ::= SEQUENCE {
* extnId EXTENSION.&amp;id ({ExtensionSet}),
* critical BOOLEAN DEFAULT FALSE,
* extnValue OCTET STRING }
* </pre>
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector vec = new Asn1EncodableVector();
foreach (DerObjectIdentifier oid in ordering)
{
X509Extension ext = (X509Extension) extensions[oid];
Asn1EncodableVector v = new Asn1EncodableVector(oid);
if (ext.IsCritical)
{
v.Add(DerBoolean.True);
}
v.Add(ext.Value);
vec.Add(new DerSequence(v));
}
return new DerSequence(vec);
}
public bool Equivalent(
X509Extensions other)
{
if (extensions.Count != other.extensions.Count)
return false;
foreach (DerObjectIdentifier oid in extensions.Keys)
{
if (!extensions[oid].Equals(other.extensions[oid]))
return false;
}
return true;
}
}
}

View File

@@ -0,0 +1,79 @@
using System;
using System.Collections;
namespace Org.BouncyCastle.Asn1.X509
{
/// <remarks>Generator for X.509 extensions</remarks>
public class X509ExtensionsGenerator
{
private Hashtable extensions = new Hashtable();
private ArrayList extOrdering = new ArrayList();
/// <summary>Reset the generator</summary>
public void Reset()
{
extensions = new Hashtable();
extOrdering = new ArrayList();
}
/// <summary>
/// Add an extension with the given oid and the passed in value to be included
/// in the OCTET STRING associated with the extension.
/// </summary>
/// <param name="oid">OID for the extension.</param>
/// <param name="critical">True if critical, false otherwise.</param>
/// <param name="extValue">The ASN.1 object to be included in the extension.</param>
public void AddExtension(
DerObjectIdentifier oid,
bool critical,
Asn1Encodable extValue)
{
byte[] encoded;
try
{
encoded = extValue.GetDerEncoded();
}
catch (Exception e)
{
throw new ArgumentException("error encoding value: " + e);
}
this.AddExtension(oid, critical, encoded);
}
/// <summary>
/// Add an extension with the given oid and the passed in byte array to be wrapped
/// in the OCTET STRING associated with the extension.
/// </summary>
/// <param name="oid">OID for the extension.</param>
/// <param name="critical">True if critical, false otherwise.</param>
/// <param name="extValue">The byte array to be wrapped.</param>
public void AddExtension(
DerObjectIdentifier oid,
bool critical,
byte[] extValue)
{
if (extensions.ContainsKey(oid))
{
throw new ArgumentException("extension " + oid + " already added");
}
extOrdering.Add(oid);
extensions.Add(oid, new X509Extension(critical, new DerOctetString(extValue)));
}
/// <summary>Return true if there are no extension present in this generator.</summary>
/// <returns>True if empty, false otherwise</returns>
public bool IsEmpty
{
get { return extOrdering.Count < 1; }
}
/// <summary>Generate an X509Extensions object based on the current state of the generator.</summary>
/// <returns>An <c>X509Extensions</c> object</returns>
public X509Extensions Generate()
{
return new X509Extensions(extOrdering, extensions);
}
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,89 @@
using System;
using System.Globalization;
using System.IO;
using System.Text;
using Org.BouncyCastle.Utilities.Encoders;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* It turns out that the number of standard ways the fields in a DN should be
* encoded into their ASN.1 counterparts is rapidly approaching the
* number of machines on the internet. By default the X509Name class
* will produce UTF8Strings in line with the current recommendations (RFC 3280).
* <p>
* An example of an encoder look like below:
* <pre>
* public class X509DirEntryConverter
* : X509NameEntryConverter
* {
* public Asn1Object GetConvertedValue(
* DerObjectIdentifier oid,
* string value)
* {
* if (str.Length() != 0 &amp;&amp; str.charAt(0) == '#')
* {
* return ConvertHexEncoded(str, 1);
* }
* if (oid.Equals(EmailAddress))
* {
* return new DerIA5String(str);
* }
* else if (CanBePrintable(str))
* {
* return new DerPrintableString(str);
* }
* else if (CanBeUTF8(str))
* {
* return new DerUtf8String(str);
* }
* else
* {
* return new DerBmpString(str);
* }
* }
* }
* </pre>
* </p>
*/
public abstract class X509NameEntryConverter
{
/**
* Convert an inline encoded hex string rendition of an ASN.1
* object back into its corresponding ASN.1 object.
*
* @param str the hex encoded object
* @param off the index at which the encoding starts
* @return the decoded object
*/
protected Asn1Object ConvertHexEncoded(
string hexString,
int offset)
{
string str = hexString.Substring(offset);
return Asn1Object.FromByteArray(Hex.Decode(str));
}
/**
* return true if the passed in string can be represented without
* loss as a PrintableString, false otherwise.
*/
protected bool CanBePrintable(
string str)
{
return DerPrintableString.IsPrintableString(str);
}
/**
* Convert the passed in string value into the appropriate ASN.1
* encoded object.
*
* @param oid the oid associated with the value in the DN.
* @param value the value of the particular DN component.
* @return the ASN.1 equivalent for the value.
*/
public abstract Asn1Object GetConvertedValue(DerObjectIdentifier oid, string value);
}
}

View File

@@ -0,0 +1,101 @@
using System.Text;
namespace Org.BouncyCastle.Asn1.X509
{
/**
* class for breaking up an X500 Name into it's component tokens, ala
* java.util.StringTokenizer. We need this class as some of the
* lightweight Java environment don't support classes like
* StringTokenizer.
*/
public class X509NameTokenizer
{
private string value;
private int index;
private char separator;
private StringBuilder buffer = new StringBuilder();
public X509NameTokenizer(
string oid)
: this(oid, ',')
{
}
public X509NameTokenizer(
string oid,
char separator)
{
this.value = oid;
this.index = -1;
this.separator = separator;
}
public bool HasMoreTokens()
{
return index != value.Length;
}
public string NextToken()
{
if (index == value.Length)
{
return null;
}
int end = index + 1;
bool quoted = false;
bool escaped = false;
buffer.Remove(0, buffer.Length);
while (end != value.Length)
{
char c = value[end];
if (c == '"')
{
if (!escaped)
{
quoted = !quoted;
}
else
{
buffer.Append(c);
}
escaped = false;
}
else
{
if (escaped || quoted)
{
if (c == '#' && buffer[buffer.Length - 1] == '=')
{
buffer.Append('\\');
}
buffer.Append(c);
escaped = false;
}
else if (c == '\\')
{
escaped = true;
}
else if (c == separator)
{
break;
}
else
{
buffer.Append(c);
}
}
end++;
}
index = end;
return buffer.ToString().Trim();
}
}
}

View File

@@ -0,0 +1,56 @@
namespace Org.BouncyCastle.Asn1.X509
{
public abstract class X509ObjectIdentifiers
{
//
// base id
//
internal const string ID = "2.5.4";
public static readonly DerObjectIdentifier CommonName = new DerObjectIdentifier(ID + ".3");
public static readonly DerObjectIdentifier CountryName = new DerObjectIdentifier(ID + ".6");
public static readonly DerObjectIdentifier LocalityName = new DerObjectIdentifier(ID + ".7");
public static readonly DerObjectIdentifier StateOrProvinceName = new DerObjectIdentifier(ID + ".8");
public static readonly DerObjectIdentifier Organization = new DerObjectIdentifier(ID + ".10");
public static readonly DerObjectIdentifier OrganizationalUnitName = new DerObjectIdentifier(ID + ".11");
// id-SHA1 OBJECT IDENTIFIER ::=
// {iso(1) identified-organization(3) oiw(14) secsig(3) algorithms(2) 26 } //
public static readonly DerObjectIdentifier IdSha1 = new DerObjectIdentifier("1.3.14.3.2.26");
//
// ripemd160 OBJECT IDENTIFIER ::=
// {iso(1) identified-organization(3) TeleTrust(36) algorithm(3) hashAlgorithm(2) RipeMD-160(1)}
//
public static readonly DerObjectIdentifier RipeMD160 = new DerObjectIdentifier("1.3.36.3.2.1");
//
// ripemd160WithRSAEncryption OBJECT IDENTIFIER ::=
// {iso(1) identified-organization(3) TeleTrust(36) algorithm(3) signatureAlgorithm(3) rsaSignature(1) rsaSignatureWithripemd160(2) }
//
public static readonly DerObjectIdentifier RipeMD160WithRsaEncryption = new DerObjectIdentifier("1.3.36.3.3.1.2");
public static readonly DerObjectIdentifier IdEARsa = new DerObjectIdentifier("2.5.8.1.1");
// id-pkix
public static readonly DerObjectIdentifier IdPkix = new DerObjectIdentifier("1.3.6.1.5.5.7");
//
// private internet extensions
//
public static readonly DerObjectIdentifier IdPE = new DerObjectIdentifier(IdPkix + ".1");
//
// authority information access
//
public static readonly DerObjectIdentifier IdAD = new DerObjectIdentifier(IdPkix + ".48");
public static readonly DerObjectIdentifier IdADCAIssuers = new DerObjectIdentifier(IdAD + ".2");
public static readonly DerObjectIdentifier IdADOcsp = new DerObjectIdentifier(IdAD + ".1");
//
// OID for ocsp and crl uri in AuthorityInformationAccess extension
//
public static readonly DerObjectIdentifier OcspAccessMethod = IdADOcsp;
public static readonly DerObjectIdentifier CrlAccessMethod = IdADCAIssuers;
}
}

View File

@@ -0,0 +1,112 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
using Org.BouncyCastle.Asn1.X509;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
/**
* The BiometricData object.
* <pre>
* BiometricData ::= SEQUENCE {
* typeOfBiometricData TypeOfBiometricData,
* hashAlgorithm AlgorithmIdentifier,
* biometricDataHash OCTET STRING,
* sourceDataUri IA5String OPTIONAL }
* </pre>
*/
public class BiometricData
: Asn1Encodable
{
private readonly TypeOfBiometricData typeOfBiometricData;
private readonly AlgorithmIdentifier hashAlgorithm;
private readonly Asn1OctetString biometricDataHash;
private readonly DerIA5String sourceDataUri;
public static BiometricData GetInstance(
object obj)
{
if (obj == null || obj is BiometricData)
{
return (BiometricData)obj;
}
if (obj is Asn1Sequence)
{
return new BiometricData(Asn1Sequence.GetInstance(obj));
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
private BiometricData(
Asn1Sequence seq)
{
typeOfBiometricData = TypeOfBiometricData.GetInstance(seq[0]);
hashAlgorithm = AlgorithmIdentifier.GetInstance(seq[1]);
biometricDataHash = Asn1OctetString.GetInstance(seq[2]);
if (seq.Count > 3)
{
sourceDataUri = DerIA5String.GetInstance(seq[3]);
}
}
public BiometricData(
TypeOfBiometricData typeOfBiometricData,
AlgorithmIdentifier hashAlgorithm,
Asn1OctetString biometricDataHash,
DerIA5String sourceDataUri)
{
this.typeOfBiometricData = typeOfBiometricData;
this.hashAlgorithm = hashAlgorithm;
this.biometricDataHash = biometricDataHash;
this.sourceDataUri = sourceDataUri;
}
public BiometricData(
TypeOfBiometricData typeOfBiometricData,
AlgorithmIdentifier hashAlgorithm,
Asn1OctetString biometricDataHash)
{
this.typeOfBiometricData = typeOfBiometricData;
this.hashAlgorithm = hashAlgorithm;
this.biometricDataHash = biometricDataHash;
this.sourceDataUri = null;
}
public TypeOfBiometricData TypeOfBiometricData
{
get { return typeOfBiometricData; }
}
public AlgorithmIdentifier HashAlgorithm
{
get { return hashAlgorithm; }
}
public Asn1OctetString BiometricDataHash
{
get { return biometricDataHash; }
}
public DerIA5String SourceDataUri
{
get { return sourceDataUri; }
}
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector seq = new Asn1EncodableVector(
typeOfBiometricData, hashAlgorithm, biometricDataHash);
if (sourceDataUri != null)
{
seq.Add(sourceDataUri);
}
return new DerSequence(seq);
}
}
}

View File

@@ -0,0 +1,19 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
public abstract class EtsiQCObjectIdentifiers
{
//
// base id
//
public static readonly DerObjectIdentifier IdEtsiQcs = new DerObjectIdentifier("0.4.0.1862.1");
public static readonly DerObjectIdentifier IdEtsiQcsQcCompliance = new DerObjectIdentifier(IdEtsiQcs+".1");
public static readonly DerObjectIdentifier IdEtsiQcsLimitValue = new DerObjectIdentifier(IdEtsiQcs+".2");
public static readonly DerObjectIdentifier IdEtsiQcsRetentionPeriod = new DerObjectIdentifier(IdEtsiQcs+".3");
public static readonly DerObjectIdentifier IdEtsiQcsQcSscd = new DerObjectIdentifier(IdEtsiQcs+".4");
}
}

View File

@@ -0,0 +1,84 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
/**
* The Iso4217CurrencyCode object.
* <pre>
* Iso4217CurrencyCode ::= CHOICE {
* alphabetic PrintableString (SIZE 3), --Recommended
* numeric INTEGER (1..999) }
* -- Alphabetic or numeric currency code as defined in ISO 4217
* -- It is recommended that the Alphabetic form is used
* </pre>
*/
public class Iso4217CurrencyCode
: Asn1Encodable
{
internal const int AlphabeticMaxSize = 3;
internal const int NumericMinSize = 1;
internal const int NumericMaxSize = 999;
internal Asn1Encodable obj;
// internal int numeric;
public static Iso4217CurrencyCode GetInstance(
object obj)
{
if (obj == null || obj is Iso4217CurrencyCode)
{
return (Iso4217CurrencyCode) obj;
}
if (obj is DerInteger)
{
DerInteger numericobj = DerInteger.GetInstance(obj);
int numeric = numericobj.Value.IntValue;
return new Iso4217CurrencyCode(numeric);
}
if (obj is DerPrintableString)
{
DerPrintableString alphabetic = DerPrintableString.GetInstance(obj);
return new Iso4217CurrencyCode(alphabetic.GetString());
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
public Iso4217CurrencyCode(
int numeric)
{
if (numeric > NumericMaxSize || numeric < NumericMinSize)
{
throw new ArgumentException("wrong size in numeric code : not in (" +NumericMinSize +".."+ NumericMaxSize +")");
}
obj = new DerInteger(numeric);
}
public Iso4217CurrencyCode(
string alphabetic)
{
if (alphabetic.Length > AlphabeticMaxSize)
{
throw new ArgumentException("wrong size in alphabetic code : max size is " + AlphabeticMaxSize);
}
obj = new DerPrintableString(alphabetic);
}
public bool IsAlphabetic { get { return obj is DerPrintableString; } }
public string Alphabetic { get { return ((DerPrintableString) obj).GetString(); } }
public int Numeric { get { return ((DerInteger)obj).Value.IntValue; } }
public override Asn1Object ToAsn1Object()
{
return obj.ToAsn1Object();
}
}
}

View File

@@ -0,0 +1,83 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
using Org.BouncyCastle.Math;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
/**
* The MonetaryValue object.
* <pre>
* MonetaryValue ::= SEQUENCE {
* currency Iso4217CurrencyCode,
* amount INTEGER,
* exponent INTEGER }
* -- value = amount * 10^exponent
* </pre>
*/
public class MonetaryValue
: Asn1Encodable
{
internal Iso4217CurrencyCode currency;
internal DerInteger amount;
internal DerInteger exponent;
public static MonetaryValue GetInstance(
object obj)
{
if (obj == null || obj is MonetaryValue)
{
return (MonetaryValue) obj;
}
if (obj is Asn1Sequence)
{
return new MonetaryValue(Asn1Sequence.GetInstance(obj));
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
private MonetaryValue(
Asn1Sequence seq)
{
if (seq.Count != 3)
throw new ArgumentException("Bad sequence size: " + seq.Count, "seq");
currency = Iso4217CurrencyCode.GetInstance(seq[0]);
amount = DerInteger.GetInstance(seq[1]);
exponent = DerInteger.GetInstance(seq[2]);
}
public MonetaryValue(
Iso4217CurrencyCode currency,
int amount,
int exponent)
{
this.currency = currency;
this.amount = new DerInteger(amount);
this.exponent = new DerInteger(exponent);
}
public Iso4217CurrencyCode Currency
{
get { return currency; }
}
public BigInteger Amount
{
get { return amount.Value; }
}
public BigInteger Exponent
{
get { return exponent.Value; }
}
public override Asn1Object ToAsn1Object()
{
return new DerSequence(currency, amount, exponent);
}
}
}

View File

@@ -0,0 +1,85 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
/**
* The QCStatement object.
* <pre>
* QCStatement ::= SEQUENCE {
* statementId OBJECT IDENTIFIER,
* statementInfo ANY DEFINED BY statementId OPTIONAL}
* </pre>
*/
public class QCStatement
: Asn1Encodable
{
private readonly DerObjectIdentifier qcStatementId;
private readonly Asn1Encodable qcStatementInfo;
public static QCStatement GetInstance(
object obj)
{
if (obj == null || obj is QCStatement)
{
return (QCStatement) obj;
}
if (obj is Asn1Sequence)
{
return new QCStatement(Asn1Sequence.GetInstance(obj));
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
private QCStatement(
Asn1Sequence seq)
{
qcStatementId = DerObjectIdentifier.GetInstance(seq[0]);
if (seq.Count > 1)
{
qcStatementInfo = seq[1];
}
}
public QCStatement(
DerObjectIdentifier qcStatementId)
{
this.qcStatementId = qcStatementId;
}
public QCStatement(
DerObjectIdentifier qcStatementId,
Asn1Encodable qcStatementInfo)
{
this.qcStatementId = qcStatementId;
this.qcStatementInfo = qcStatementInfo;
}
public DerObjectIdentifier StatementId
{
get { return qcStatementId; }
}
public Asn1Encodable StatementInfo
{
get { return qcStatementInfo; }
}
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector seq = new Asn1EncodableVector(qcStatementId);
if (qcStatementInfo != null)
{
seq.Add(qcStatementInfo);
}
return new DerSequence(seq);
}
}
}

View File

@@ -0,0 +1,21 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
public sealed class Rfc3739QCObjectIdentifiers
{
private Rfc3739QCObjectIdentifiers()
{
}
//
// base id
//
public static readonly DerObjectIdentifier IdQcs = new DerObjectIdentifier("1.3.6.1.5.5.7.11");
public static readonly DerObjectIdentifier IdQcsPkixQCSyntaxV1 = new DerObjectIdentifier(IdQcs+".1");
public static readonly DerObjectIdentifier IdQcsPkixQCSyntaxV2 = new DerObjectIdentifier(IdQcs+".2");
}
}

View File

@@ -0,0 +1,124 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1;
using Org.BouncyCastle.Asn1.X509;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
/**
* The SemanticsInformation object.
* <pre>
* SemanticsInformation ::= SEQUENCE {
* semanticsIdentifier OBJECT IDENTIFIER OPTIONAL,
* nameRegistrationAuthorities NameRegistrationAuthorities
* OPTIONAL }
* (WITH COMPONENTS {..., semanticsIdentifier PRESENT}|
* WITH COMPONENTS {..., nameRegistrationAuthorities PRESENT})
*
* NameRegistrationAuthorities ::= SEQUENCE SIZE (1..MAX) OF
* GeneralName
* </pre>
*/
public class SemanticsInformation
: Asn1Encodable
{
private readonly DerObjectIdentifier semanticsIdentifier;
private readonly GeneralName[] nameRegistrationAuthorities;
public static SemanticsInformation GetInstance(
object obj)
{
if (obj == null || obj is SemanticsInformation)
{
return (SemanticsInformation) obj;
}
if (obj is Asn1Sequence)
{
return new SemanticsInformation(Asn1Sequence.GetInstance(obj));
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
public SemanticsInformation(
Asn1Sequence seq)
{
if (seq.Count < 1)
{
throw new ArgumentException("no objects in SemanticsInformation");
}
IEnumerator e = seq.GetEnumerator();
e.MoveNext();
object obj = e.Current;
if (obj is DerObjectIdentifier)
{
semanticsIdentifier = DerObjectIdentifier.GetInstance(obj);
if (e.MoveNext())
{
obj = e.Current;
}
else
{
obj = null;
}
}
if (obj != null)
{
Asn1Sequence generalNameSeq = Asn1Sequence.GetInstance(obj );
nameRegistrationAuthorities = new GeneralName[generalNameSeq.Count];
for (int i= 0; i < generalNameSeq.Count; i++)
{
nameRegistrationAuthorities[i] = GeneralName.GetInstance(generalNameSeq[i]);
}
}
}
public SemanticsInformation(
DerObjectIdentifier semanticsIdentifier,
GeneralName[] generalNames)
{
this.semanticsIdentifier = semanticsIdentifier;
this.nameRegistrationAuthorities = generalNames;
}
public SemanticsInformation(
DerObjectIdentifier semanticsIdentifier)
{
this.semanticsIdentifier = semanticsIdentifier;
}
public SemanticsInformation(
GeneralName[] generalNames)
{
this.nameRegistrationAuthorities = generalNames;
}
public DerObjectIdentifier SemanticsIdentifier { get { return semanticsIdentifier; } }
public GeneralName[] GetNameRegistrationAuthorities()
{
return nameRegistrationAuthorities;
}
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector seq = new Asn1EncodableVector();
if (this.semanticsIdentifier != null)
{
seq.Add(semanticsIdentifier);
}
if (this.nameRegistrationAuthorities != null)
{
seq.Add(new DerSequence(nameRegistrationAuthorities));
}
return new DerSequence(seq);
}
}
}

View File

@@ -0,0 +1,91 @@
using System;
using Org.BouncyCastle.Asn1;
namespace Org.BouncyCastle.Asn1.X509.Qualified
{
/**
* The TypeOfBiometricData object.
* <pre>
* TypeOfBiometricData ::= CHOICE {
* predefinedBiometricType PredefinedBiometricType,
* biometricDataOid OBJECT IDENTIFIER }
*
* PredefinedBiometricType ::= INTEGER {
* picture(0),handwritten-signature(1)}
* (picture|handwritten-signature)
* </pre>
*/
public class TypeOfBiometricData
: Asn1Encodable
{
public const int Picture = 0;
public const int HandwrittenSignature = 1;
internal Asn1Encodable obj;
public static TypeOfBiometricData GetInstance(
object obj)
{
if (obj == null || obj is TypeOfBiometricData)
{
return (TypeOfBiometricData) obj;
}
if (obj is DerInteger)
{
DerInteger predefinedBiometricTypeObj = DerInteger.GetInstance(obj);
int predefinedBiometricType = predefinedBiometricTypeObj.Value.IntValue;
return new TypeOfBiometricData(predefinedBiometricType);
}
if (obj is DerObjectIdentifier)
{
DerObjectIdentifier BiometricDataOid = DerObjectIdentifier.GetInstance(obj);
return new TypeOfBiometricData(BiometricDataOid);
}
throw new ArgumentException("unknown object in GetInstance: " + obj.GetType().FullName, "obj");
}
public TypeOfBiometricData(
int predefinedBiometricType)
{
if (predefinedBiometricType == Picture || predefinedBiometricType == HandwrittenSignature)
{
obj = new DerInteger(predefinedBiometricType);
}
else
{
throw new ArgumentException("unknow PredefinedBiometricType : " + predefinedBiometricType);
}
}
public TypeOfBiometricData(
DerObjectIdentifier biometricDataOid)
{
obj = biometricDataOid;
}
public bool IsPredefined
{
get { return obj is DerInteger; }
}
public int PredefinedBiometricType
{
get { return ((DerInteger) obj).Value.IntValue; }
}
public DerObjectIdentifier BiometricDataOid
{
get { return (DerObjectIdentifier) obj; }
}
public override Asn1Object ToAsn1Object()
{
return obj.ToAsn1Object();
}
}
}

View File

@@ -0,0 +1,178 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1.X500;
namespace Org.BouncyCastle.Asn1.X509.SigI
{
/**
* Structure for a name or pseudonym.
*
* <pre>
* NameOrPseudonym ::= CHOICE {
* surAndGivenName SEQUENCE {
* surName DirectoryString,
* givenName SEQUENCE OF DirectoryString
* },
* pseudonym DirectoryString
* }
* </pre>
*
* @see org.bouncycastle.asn1.x509.sigi.PersonalData
*
*/
public class NameOrPseudonym
: Asn1Encodable
//, Asn1Choice
{
private readonly DirectoryString pseudonym;
private readonly DirectoryString surname;
private readonly Asn1Sequence givenName;
public static NameOrPseudonym GetInstance(
object obj)
{
if (obj == null || obj is NameOrPseudonym)
{
return (NameOrPseudonym)obj;
}
if (obj is IAsn1String)
{
return new NameOrPseudonym(DirectoryString.GetInstance(obj));
}
if (obj is Asn1Sequence)
{
return new NameOrPseudonym((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from DERString.
* <p/>
* The sequence is of type NameOrPseudonym:
* <p/>
* <pre>
* NameOrPseudonym ::= CHOICE {
* surAndGivenName SEQUENCE {
* surName DirectoryString,
* givenName SEQUENCE OF DirectoryString
* },
* pseudonym DirectoryString
* }
* </pre>
* @param pseudonym pseudonym value to use.
*/
public NameOrPseudonym(
DirectoryString pseudonym)
{
this.pseudonym = pseudonym;
}
/**
* Constructor from Asn1Sequence.
* <p/>
* The sequence is of type NameOrPseudonym:
* <p/>
* <pre>
* NameOrPseudonym ::= CHOICE {
* surAndGivenName SEQUENCE {
* surName DirectoryString,
* givenName SEQUENCE OF DirectoryString
* },
* pseudonym DirectoryString
* }
* </pre>
*
* @param seq The ASN.1 sequence.
*/
private NameOrPseudonym(
Asn1Sequence seq)
{
if (seq.Count != 2)
throw new ArgumentException("Bad sequence size: " + seq.Count);
if (!(seq[0] is IAsn1String))
throw new ArgumentException("Bad object encountered: " + seq[0].GetType().Name);
surname = DirectoryString.GetInstance(seq[0]);
givenName = Asn1Sequence.GetInstance(seq[1]);
}
/**
* Constructor from a given details.
*
* @param pseudonym The pseudonym.
*/
public NameOrPseudonym(
string pseudonym)
: this(new DirectoryString(pseudonym))
{
}
/**
* Constructor from a given details.
*
* @param surname The surname.
* @param givenName A sequence of directory strings making up the givenName
*/
public NameOrPseudonym(
DirectoryString surname,
Asn1Sequence givenName)
{
this.surname = surname;
this.givenName = givenName;
}
public DirectoryString Pseudonym
{
get { return pseudonym; }
}
public DirectoryString Surname
{
get { return surname; }
}
public DirectoryString[] GetGivenName()
{
DirectoryString[] items = new DirectoryString[givenName.Count];
int count = 0;
foreach (object o in givenName)
{
items[count++] = DirectoryString.GetInstance(o);
}
return items;
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <p/>
* Returns:
* <p/>
* <pre>
* NameOrPseudonym ::= CHOICE {
* surAndGivenName SEQUENCE {
* surName DirectoryString,
* givenName SEQUENCE OF DirectoryString
* },
* pseudonym DirectoryString
* }
* </pre>
*
* @return an Asn1Object
*/
public override Asn1Object ToAsn1Object()
{
if (pseudonym != null)
{
return pseudonym.ToAsn1Object();
}
return new DerSequence(surname, givenName);
}
}
}

View File

@@ -0,0 +1,210 @@
using System;
using System.Collections;
using Org.BouncyCastle.Asn1.X500;
using Org.BouncyCastle.Math;
namespace Org.BouncyCastle.Asn1.X509.SigI
{
/**
* Contains personal data for the otherName field in the subjectAltNames
* extension.
* <p/>
* <pre>
* PersonalData ::= SEQUENCE {
* nameOrPseudonym NameOrPseudonym,
* nameDistinguisher [0] INTEGER OPTIONAL,
* dateOfBirth [1] GeneralizedTime OPTIONAL,
* placeOfBirth [2] DirectoryString OPTIONAL,
* gender [3] PrintableString OPTIONAL,
* postalAddress [4] DirectoryString OPTIONAL
* }
* </pre>
*
* @see org.bouncycastle.asn1.x509.sigi.NameOrPseudonym
* @see org.bouncycastle.asn1.x509.sigi.SigIObjectIdentifiers
*/
public class PersonalData
: Asn1Encodable
{
private readonly NameOrPseudonym nameOrPseudonym;
private readonly BigInteger nameDistinguisher;
private readonly DerGeneralizedTime dateOfBirth;
private readonly DirectoryString placeOfBirth;
private readonly string gender;
private readonly DirectoryString postalAddress;
public static PersonalData GetInstance(
object obj)
{
if (obj == null || obj is PersonalData)
{
return (PersonalData) obj;
}
if (obj is Asn1Sequence)
{
return new PersonalData((Asn1Sequence) obj);
}
throw new ArgumentException("unknown object in factory: " + obj.GetType().Name, "obj");
}
/**
* Constructor from Asn1Sequence.
* <p/>
* The sequence is of type NameOrPseudonym:
* <p/>
* <pre>
* PersonalData ::= SEQUENCE {
* nameOrPseudonym NameOrPseudonym,
* nameDistinguisher [0] INTEGER OPTIONAL,
* dateOfBirth [1] GeneralizedTime OPTIONAL,
* placeOfBirth [2] DirectoryString OPTIONAL,
* gender [3] PrintableString OPTIONAL,
* postalAddress [4] DirectoryString OPTIONAL
* }
* </pre>
*
* @param seq The ASN.1 sequence.
*/
private PersonalData(
Asn1Sequence seq)
{
if (seq.Count < 1)
throw new ArgumentException("Bad sequence size: " + seq.Count);
IEnumerator e = seq.GetEnumerator();
e.MoveNext();
nameOrPseudonym = NameOrPseudonym.GetInstance(e.Current);
while (e.MoveNext())
{
Asn1TaggedObject o = Asn1TaggedObject.GetInstance(e.Current);
int tag = o.TagNo;
switch (tag)
{
case 0:
nameDistinguisher = DerInteger.GetInstance(o, false).Value;
break;
case 1:
dateOfBirth = DerGeneralizedTime.GetInstance(o, false);
break;
case 2:
placeOfBirth = DirectoryString.GetInstance(o, true);
break;
case 3:
gender = DerPrintableString.GetInstance(o, false).GetString();
break;
case 4:
postalAddress = DirectoryString.GetInstance(o, true);
break;
default:
throw new ArgumentException("Bad tag number: " + o.TagNo);
}
}
}
/**
* Constructor from a given details.
*
* @param nameOrPseudonym Name or pseudonym.
* @param nameDistinguisher Name distinguisher.
* @param dateOfBirth Date of birth.
* @param placeOfBirth Place of birth.
* @param gender Gender.
* @param postalAddress Postal Address.
*/
public PersonalData(
NameOrPseudonym nameOrPseudonym,
BigInteger nameDistinguisher,
DerGeneralizedTime dateOfBirth,
DirectoryString placeOfBirth,
string gender,
DirectoryString postalAddress)
{
this.nameOrPseudonym = nameOrPseudonym;
this.dateOfBirth = dateOfBirth;
this.gender = gender;
this.nameDistinguisher = nameDistinguisher;
this.postalAddress = postalAddress;
this.placeOfBirth = placeOfBirth;
}
public NameOrPseudonym NameOrPseudonym
{
get { return nameOrPseudonym; }
}
public BigInteger NameDistinguisher
{
get { return nameDistinguisher; }
}
public DerGeneralizedTime DateOfBirth
{
get { return dateOfBirth; }
}
public DirectoryString PlaceOfBirth
{
get { return placeOfBirth; }
}
public string Gender
{
get { return gender; }
}
public DirectoryString PostalAddress
{
get { return postalAddress; }
}
/**
* Produce an object suitable for an Asn1OutputStream.
* <p/>
* Returns:
* <p/>
* <pre>
* PersonalData ::= SEQUENCE {
* nameOrPseudonym NameOrPseudonym,
* nameDistinguisher [0] INTEGER OPTIONAL,
* dateOfBirth [1] GeneralizedTime OPTIONAL,
* placeOfBirth [2] DirectoryString OPTIONAL,
* gender [3] PrintableString OPTIONAL,
* postalAddress [4] DirectoryString OPTIONAL
* }
* </pre>
*
* @return an Asn1Object
*/
public override Asn1Object ToAsn1Object()
{
Asn1EncodableVector vec = new Asn1EncodableVector();
vec.Add(nameOrPseudonym);
if (nameDistinguisher != null)
{
vec.Add(new DerTaggedObject(false, 0, new DerInteger(nameDistinguisher)));
}
if (dateOfBirth != null)
{
vec.Add(new DerTaggedObject(false, 1, dateOfBirth));
}
if (placeOfBirth != null)
{
vec.Add(new DerTaggedObject(true, 2, placeOfBirth));
}
if (gender != null)
{
vec.Add(new DerTaggedObject(false, 3, new DerPrintableString(gender, true)));
}
if (postalAddress != null)
{
vec.Add(new DerTaggedObject(true, 4, postalAddress));
}
return new DerSequence(vec);
}
}
}

View File

@@ -0,0 +1,49 @@
using System;
namespace Org.BouncyCastle.Asn1.X509.SigI
{
/**
* Object Identifiers of SigI specifciation (German Signature Law
* Interoperability specification).
*/
public sealed class SigIObjectIdentifiers
{
private SigIObjectIdentifiers()
{
}
public readonly static DerObjectIdentifier IdSigI = new DerObjectIdentifier("1.3.36.8");
/**
* Key purpose IDs for German SigI (Signature Interoperability
* Specification)
*/
public readonly static DerObjectIdentifier IdSigIKP = new DerObjectIdentifier(IdSigI + ".2");
/**
* Certificate policy IDs for German SigI (Signature Interoperability
* Specification)
*/
public readonly static DerObjectIdentifier IdSigICP = new DerObjectIdentifier(IdSigI + ".1");
/**
* Other Name IDs for German SigI (Signature Interoperability Specification)
*/
public readonly static DerObjectIdentifier IdSigION = new DerObjectIdentifier(IdSigI + ".4");
/**
* To be used for for the generation of directory service certificates.
*/
public static readonly DerObjectIdentifier IdSigIKPDirectoryService = new DerObjectIdentifier(IdSigIKP + ".1");
/**
* ID for PersonalData
*/
public static readonly DerObjectIdentifier IdSigIONPersonalData = new DerObjectIdentifier(IdSigION + ".1");
/**
* Certificate is conform to german signature law.
*/
public static readonly DerObjectIdentifier IdSigICPSigConform = new DerObjectIdentifier(IdSigICP + ".1");
}
}