summary refs log tree commit diff
path: root/crypto/src/x509/store/X509AttrCertStoreSelector.cs
diff options
context:
space:
mode:
Diffstat (limited to 'crypto/src/x509/store/X509AttrCertStoreSelector.cs')
-rw-r--r--crypto/src/x509/store/X509AttrCertStoreSelector.cs376
1 files changed, 376 insertions, 0 deletions
diff --git a/crypto/src/x509/store/X509AttrCertStoreSelector.cs b/crypto/src/x509/store/X509AttrCertStoreSelector.cs
new file mode 100644
index 000000000..9f1dc20d1
--- /dev/null
+++ b/crypto/src/x509/store/X509AttrCertStoreSelector.cs
@@ -0,0 +1,376 @@
+using System;
+using System.Collections;
+using System.IO;
+
+using Org.BouncyCastle.Asn1;
+using Org.BouncyCastle.Asn1.X509;
+using Org.BouncyCastle.Math;
+using Org.BouncyCastle.Utilities.Collections;
+using Org.BouncyCastle.Utilities.Date;
+using Org.BouncyCastle.X509.Extension;
+
+namespace Org.BouncyCastle.X509.Store
+{
+	/**
+	* This class is an <code>Selector</code> like implementation to select
+	* attribute certificates from a given set of criteria.
+	*
+	* @see org.bouncycastle.x509.X509AttributeCertificate
+	* @see org.bouncycastle.x509.X509Store
+	*/
+	public class X509AttrCertStoreSelector
+		: IX509Selector
+	{
+		// TODO: name constraints???
+
+		private IX509AttributeCertificate attributeCert;
+		private DateTimeObject attributeCertificateValid;
+		private AttributeCertificateHolder holder;
+		private AttributeCertificateIssuer issuer;
+		private BigInteger serialNumber;
+		private ISet targetNames = new HashSet();
+		private ISet targetGroups = new HashSet();
+
+		public X509AttrCertStoreSelector()
+		{
+		}
+
+		private X509AttrCertStoreSelector(
+			X509AttrCertStoreSelector o)
+		{
+			this.attributeCert = o.attributeCert;
+			this.attributeCertificateValid = o.attributeCertificateValid;
+			this.holder = o.holder;
+			this.issuer = o.issuer;
+			this.serialNumber = o.serialNumber;
+			this.targetGroups = new HashSet(o.targetGroups);
+			this.targetNames = new HashSet(o.targetNames);
+		}
+
+		/// <summary>
+		/// Decides if the given attribute certificate should be selected.
+		/// </summary>
+		/// <param name="obj">The attribute certificate to be checked.</param>
+		/// <returns><code>true</code> if the object matches this selector.</returns>
+		public bool Match(
+			object obj)
+		{
+			if (obj == null)
+				throw new ArgumentNullException("obj");
+
+			IX509AttributeCertificate attrCert = obj as IX509AttributeCertificate;
+
+			if (attrCert == null)
+				return false;
+
+			if (this.attributeCert != null && !this.attributeCert.Equals(attrCert))
+				return false;
+
+			if (serialNumber != null && !attrCert.SerialNumber.Equals(serialNumber))
+				return false;
+
+			if (holder != null && !attrCert.Holder.Equals(holder))
+				return false;
+
+			if (issuer != null && !attrCert.Issuer.Equals(issuer))
+				return false;
+
+			if (attributeCertificateValid != null && !attrCert.IsValid(attributeCertificateValid.Value))
+				return false;
+
+			if (targetNames.Count > 0 || targetGroups.Count > 0)
+			{
+				Asn1OctetString targetInfoExt = attrCert.GetExtensionValue(
+					X509Extensions.TargetInformation);
+
+				if (targetInfoExt != null)
+				{
+					TargetInformation targetinfo;
+					try
+					{
+						targetinfo = TargetInformation.GetInstance(
+							X509ExtensionUtilities.FromExtensionValue(targetInfoExt));
+					}
+					catch (Exception)
+					{
+						return false;
+					}
+
+					Targets[] targetss = targetinfo.GetTargetsObjects();
+
+					if (targetNames.Count > 0)
+					{
+						bool found = false;
+
+						for (int i = 0; i < targetss.Length && !found; i++)
+						{
+							Target[] targets = targetss[i].GetTargets();
+
+							for (int j = 0; j < targets.Length; j++)
+							{
+								GeneralName targetName = targets[j].TargetName;
+
+								if (targetName != null && targetNames.Contains(targetName))
+								{
+									found = true;
+									break;
+								}
+							}
+						}
+						if (!found)
+						{
+							return false;
+						}
+					}
+
+					if (targetGroups.Count > 0)
+					{
+						bool found = false;
+
+						for (int i = 0; i < targetss.Length && !found; i++)
+						{
+							Target[] targets = targetss[i].GetTargets();
+
+							for (int j = 0; j < targets.Length; j++)
+							{
+								GeneralName targetGroup = targets[j].TargetGroup;
+
+								if (targetGroup != null && targetGroups.Contains(targetGroup))
+								{
+									found = true;
+									break;
+								}
+							}
+						}
+
+						if (!found)
+						{
+							return false;
+						}
+					}
+				}
+			}
+
+			return true;
+		}
+
+		public object Clone()
+		{
+			return new X509AttrCertStoreSelector(this);
+		}
+
+		/// <summary>The attribute certificate which must be matched.</summary>
+		/// <remarks>If <c>null</c> is given, any will do.</remarks>
+		public IX509AttributeCertificate AttributeCert
+		{
+			get { return attributeCert; }
+			set { this.attributeCert = value; }
+		}
+
+		[Obsolete("Use AttributeCertificateValid instead")]
+		public DateTimeObject AttribueCertificateValid
+		{
+			get { return attributeCertificateValid; }
+			set { this.attributeCertificateValid = value; }
+		}
+
+		/// <summary>The criteria for validity</summary>
+		/// <remarks>If <c>null</c> is given any will do.</remarks>
+		public DateTimeObject AttributeCertificateValid
+		{
+			get { return attributeCertificateValid; }
+			set { this.attributeCertificateValid = value; }
+		}
+
+		/// <summary>The holder.</summary>
+		/// <remarks>If <c>null</c> is given any will do.</remarks>
+		public AttributeCertificateHolder Holder
+		{
+			get { return holder; }
+			set { this.holder = value; }
+		}
+
+		/// <summary>The issuer.</summary>
+		/// <remarks>If <c>null</c> is given any will do.</remarks>
+		public AttributeCertificateIssuer Issuer
+		{
+			get { return issuer; }
+			set { this.issuer = value; }
+		}
+
+		/// <summary>The serial number.</summary>
+		/// <remarks>If <c>null</c> is given any will do.</remarks>
+		public BigInteger SerialNumber
+		{
+			get { return serialNumber; }
+			set { this.serialNumber = value; }
+		}
+
+		/**
+		* Adds a target name criterion for the attribute certificate to the target
+		* information extension criteria. The <code>X509AttributeCertificate</code>
+		* must contain at least one of the specified target names.
+		* <p>
+		* Each attribute certificate may contain a target information extension
+		* limiting the servers where this attribute certificate can be used. If
+		* this extension is not present, the attribute certificate is not targeted
+		* and may be accepted by any server.
+		* </p>
+		*
+		* @param name The name as a GeneralName (not <code>null</code>)
+		*/
+		public void AddTargetName(
+			GeneralName name)
+		{
+			targetNames.Add(name);
+		}
+
+		/**
+		* Adds a target name criterion for the attribute certificate to the target
+		* information extension criteria. The <code>X509AttributeCertificate</code>
+		* must contain at least one of the specified target names.
+		* <p>
+		* Each attribute certificate may contain a target information extension
+		* limiting the servers where this attribute certificate can be used. If
+		* this extension is not present, the attribute certificate is not targeted
+		* and may be accepted by any server.
+		* </p>
+		*
+		* @param name a byte array containing the name in ASN.1 DER encoded form of a GeneralName
+		* @throws IOException if a parsing error occurs.
+		*/
+		public void AddTargetName(
+			byte[] name)
+		{
+			AddTargetName(GeneralName.GetInstance(Asn1Object.FromByteArray(name)));
+		}
+
+		/**
+		* Adds a collection with target names criteria. If <code>null</code> is
+		* given any will do.
+		* <p>
+		* The collection consists of either GeneralName objects or byte[] arrays representing
+		* DER encoded GeneralName structures.
+		* </p>
+		* 
+		* @param names A collection of target names.
+		* @throws IOException if a parsing error occurs.
+		* @see #AddTargetName(byte[])
+		* @see #AddTargetName(GeneralName)
+		*/
+		public void SetTargetNames(
+			IEnumerable names)
+		{
+			targetNames = ExtractGeneralNames(names);
+		}
+
+		/**
+		* Gets the target names. The collection consists of <code>List</code>s
+		* made up of an <code>Integer</code> in the first entry and a DER encoded
+		* byte array or a <code>String</code> in the second entry.
+		* <p>The returned collection is immutable.</p>
+		* 
+		* @return The collection of target names
+		* @see #setTargetNames(Collection)
+		*/
+		public IEnumerable GetTargetNames()
+		{
+			return new EnumerableProxy(targetNames);
+		}
+
+		/**
+		* Adds a target group criterion for the attribute certificate to the target
+		* information extension criteria. The <code>X509AttributeCertificate</code>
+		* must contain at least one of the specified target groups.
+		* <p>
+		* Each attribute certificate may contain a target information extension
+		* limiting the servers where this attribute certificate can be used. If
+		* this extension is not present, the attribute certificate is not targeted
+		* and may be accepted by any server.
+		* </p>
+		*
+		* @param group The group as GeneralName form (not <code>null</code>)
+		*/
+		public void AddTargetGroup(
+			GeneralName group)
+		{
+			targetGroups.Add(group);
+		}
+
+		/**
+		* Adds a target group criterion for the attribute certificate to the target
+		* information extension criteria. The <code>X509AttributeCertificate</code>
+		* must contain at least one of the specified target groups.
+		* <p>
+		* Each attribute certificate may contain a target information extension
+		* limiting the servers where this attribute certificate can be used. If
+		* this extension is not present, the attribute certificate is not targeted
+		* and may be accepted by any server.
+		* </p>
+		*
+		* @param name a byte array containing the group in ASN.1 DER encoded form of a GeneralName
+		* @throws IOException if a parsing error occurs.
+		*/
+		public void AddTargetGroup(
+			byte[] name)
+		{
+			AddTargetGroup(GeneralName.GetInstance(Asn1Object.FromByteArray(name)));
+		}
+
+		/**
+		* Adds a collection with target groups criteria. If <code>null</code> is
+		* given any will do.
+		* <p>
+		* The collection consists of <code>GeneralName</code> objects or <code>byte[]</code>
+		* representing DER encoded GeneralNames.
+		* </p>
+		*
+		* @param names A collection of target groups.
+		* @throws IOException if a parsing error occurs.
+		* @see #AddTargetGroup(byte[])
+		* @see #AddTargetGroup(GeneralName)
+		*/
+		public void SetTargetGroups(
+			IEnumerable names)
+		{
+			targetGroups = ExtractGeneralNames(names);
+		}
+
+		/**
+		* Gets the target groups. The collection consists of <code>List</code>s
+		* made up of an <code>Integer</code> in the first entry and a DER encoded
+		* byte array or a <code>String</code> in the second entry.
+		* <p>The returned collection is immutable.</p>
+		*
+		* @return The collection of target groups.
+		* @see #setTargetGroups(Collection)
+		*/
+		public IEnumerable GetTargetGroups()
+		{
+			return new EnumerableProxy(targetGroups);
+		}
+
+		private ISet ExtractGeneralNames(
+			IEnumerable names)
+		{
+			ISet result = new HashSet();
+
+			if (names != null)
+			{
+				foreach (object o in names)
+				{
+					if (o is GeneralName)
+					{
+						result.Add(o);
+					}
+					else
+					{
+						result.Add(GeneralName.GetInstance(Asn1Object.FromByteArray((byte[]) o)));
+					}
+				}
+			}
+
+			return result;
+		}
+	}
+}