diff options
author | Peter Dettman <peter.dettman@bouncycastle.org> | 2019-08-02 15:34:54 +0700 |
---|---|---|
committer | Peter Dettman <peter.dettman@bouncycastle.org> | 2019-08-02 15:34:54 +0700 |
commit | fe33e6090225fd173df691e307b034dd712f4e07 (patch) | |
tree | e6152f508adb3bb89cfabe6af826f76e6a6950e9 | |
parent | SHA-256 performance tweak (diff) | |
download | BouncyCastle.NET-ed25519-fe33e6090225fd173df691e307b034dd712f4e07.tar.xz |
Refactor Equals/GetHashCode in X509 objects
- cache public key in X509Certificate
-rw-r--r-- | crypto/src/x509/X509Certificate.cs | 61 | ||||
-rw-r--r-- | crypto/src/x509/X509Crl.cs | 47 | ||||
-rw-r--r-- | crypto/src/x509/X509CrlEntry.cs | 33 |
3 files changed, 107 insertions, 34 deletions
diff --git a/crypto/src/x509/X509Certificate.cs b/crypto/src/x509/X509Certificate.cs index 6f2f40411..2e627dbab 100644 --- a/crypto/src/x509/X509Certificate.cs +++ b/crypto/src/x509/X509Certificate.cs @@ -32,8 +32,11 @@ namespace Org.BouncyCastle.X509 private readonly BasicConstraints basicConstraints; private readonly bool[] keyUsage; - private bool hashValueSet; - private int hashValue; + private readonly object cacheLock = new object(); + private AsymmetricKeyParameter publicKeyValue; + + private volatile bool hashValueSet; + private volatile int hashValue; protected X509Certificate() { @@ -387,7 +390,24 @@ namespace Org.BouncyCastle.X509 /// <returns>The public key parameters.</returns> public virtual AsymmetricKeyParameter GetPublicKey() { - return PublicKeyFactory.CreateKey(c.SubjectPublicKeyInfo); + // Cache the public key to support repeated-use optimizations + lock (cacheLock) + { + if (null != publicKeyValue) + return publicKeyValue; + } + + AsymmetricKeyParameter temp = PublicKeyFactory.CreateKey(c.SubjectPublicKeyInfo); + + lock (cacheLock) + { + if (null == publicKeyValue) + { + publicKeyValue = temp; + } + + return publicKeyValue; + } } /// <summary> @@ -399,35 +419,40 @@ namespace Org.BouncyCastle.X509 return c.GetDerEncoded(); } - public override bool Equals( - object obj) + public override bool Equals(object other) { - if (obj == this) + if (this == other) return true; - X509Certificate other = obj as X509Certificate; - - if (other == null) + X509Certificate that = other as X509Certificate; + if (null == that) return false; - return c.Equals(other.c); + if (this.hashValueSet && that.hashValueSet) + { + if (this.hashValue != that.hashValue) + return false; + } + else if (!this.c.Signature.Equals(that.c.Signature)) + { + return false; + } + + return this.c.Equals(that.c); // NB: May prefer this implementation of Equals if more than one certificate implementation in play -// return Arrays.AreEqual(this.GetEncoded(), other.GetEncoded()); + //return Arrays.AreEqual(this.GetEncoded(), that.GetEncoded()); } public override int GetHashCode() { - lock (this) + if (!hashValueSet) { - if (!hashValueSet) - { - hashValue = c.GetHashCode(); - hashValueSet = true; - } + hashValue = this.c.GetHashCode(); + hashValueSet = true; } - return hashValue; + return hashValue; } // public void setBagAttribute( diff --git a/crypto/src/x509/X509Crl.cs b/crypto/src/x509/X509Crl.cs index ecfb14132..8903e69d0 100644 --- a/crypto/src/x509/X509Crl.cs +++ b/crypto/src/x509/X509Crl.cs @@ -6,6 +6,7 @@ using Org.BouncyCastle.Asn1; using Org.BouncyCastle.Asn1.Utilities; using Org.BouncyCastle.Asn1.X509; using Org.BouncyCastle.Crypto; +using Org.BouncyCastle.Crypto.Operators; using Org.BouncyCastle.Math; using Org.BouncyCastle.Security; using Org.BouncyCastle.Security.Certificates; @@ -14,7 +15,6 @@ using Org.BouncyCastle.Utilities.Collections; using Org.BouncyCastle.Utilities.Date; using Org.BouncyCastle.Utilities.Encoders; using Org.BouncyCastle.X509.Extension; -using Org.BouncyCastle.Crypto.Operators; namespace Org.BouncyCastle.X509 { @@ -36,6 +36,9 @@ namespace Org.BouncyCastle.X509 private readonly byte[] sigAlgParams; private readonly bool isIndirect; + private volatile bool hashValueSet; + private volatile int hashValue; + public X509Crl( CertificateList c) { @@ -229,27 +232,41 @@ namespace Org.BouncyCastle.X509 return Arrays.Clone(sigAlgParams); } - public override bool Equals( - object obj) + public override bool Equals(object other) { - if (obj == this) - return true; + if (this == other) + return true; - X509Crl other = obj as X509Crl; + X509Crl that = other as X509Crl; + if (null == that) + return false; - if (other == null) - return false; + if (this.hashValueSet && that.hashValueSet) + { + if (this.hashValue != that.hashValue) + return false; + } + else if (!this.c.Signature.Equals(that.c.Signature)) + { + return false; + } - return c.Equals(other.c); + return this.c.Equals(that.c); - // NB: May prefer this implementation of Equals if more than one certificate implementation in play - //return Arrays.AreEqual(this.GetEncoded(), other.GetEncoded()); + // NB: May prefer this implementation of Equals if more than one CRL implementation in play + //return Arrays.AreEqual(this.GetEncoded(), that.GetEncoded()); } - public override int GetHashCode() - { - return c.GetHashCode(); - } + public override int GetHashCode() + { + if (!hashValueSet) + { + hashValue = this.c.GetHashCode(); + hashValueSet = true; + } + + return hashValue; + } /** * Returns a string representation of this CRL. diff --git a/crypto/src/x509/X509CrlEntry.cs b/crypto/src/x509/X509CrlEntry.cs index caca29470..9e3608c18 100644 --- a/crypto/src/x509/X509CrlEntry.cs +++ b/crypto/src/x509/X509CrlEntry.cs @@ -1,6 +1,5 @@ using System; using System.Collections; -using System.IO; using System.Text; using Org.BouncyCastle.Asn1; @@ -27,6 +26,9 @@ namespace Org.BouncyCastle.X509 private X509Name previousCertificateIssuer; private X509Name certificateIssuer; + private volatile bool hashValueSet; + private volatile int hashValue; + public X509CrlEntry( CrlEntry c) { @@ -132,6 +134,35 @@ namespace Org.BouncyCastle.X509 get { return c.Extensions != null; } } + public override bool Equals(object other) + { + if (this == other) + return true; + + X509CrlEntry that = other as X509CrlEntry; + if (null == that) + return false; + + if (this.hashValueSet && that.hashValueSet) + { + if (this.hashValue != that.hashValue) + return false; + } + + return this.c.Equals(that.c); + } + + public override int GetHashCode() + { + if (!hashValueSet) + { + hashValue = this.c.GetHashCode(); + hashValueSet = true; + } + + return hashValue; + } + public override string ToString() { StringBuilder buf = new StringBuilder(); |