summary refs log tree commit diff
path: root/crypto/src/asn1/x9
diff options
context:
space:
mode:
authorPeter Dettman <peter.dettman@bouncycastle.org>2015-10-14 17:03:48 +0700
committerPeter Dettman <peter.dettman@bouncycastle.org>2015-10-14 17:03:48 +0700
commit75a2a192d263c56e794be561ffbd6425ccd25b46 (patch)
treeadd458ad53d1aea198b54c35a4194cb6051d17cb /crypto/src/asn1/x9
parentFixed single line file handling (diff)
downloadBouncyCastle.NET-ed25519-75a2a192d263c56e794be561ffbd6425ccd25b46.tar.xz
Port latest X9 EC stuff from Java API
Diffstat (limited to 'crypto/src/asn1/x9')
-rw-r--r--crypto/src/asn1/x9/X962NamedCurves.cs46
-rw-r--r--crypto/src/asn1/x9/X9ECParameters.cs98
-rw-r--r--crypto/src/asn1/x9/X9ECPoint.cs54
-rw-r--r--crypto/src/asn1/x9/X9FieldID.cs16
4 files changed, 145 insertions, 69 deletions
diff --git a/crypto/src/asn1/x9/X962NamedCurves.cs b/crypto/src/asn1/x9/X962NamedCurves.cs
index a9ea0240c..6fa4e7c4b 100644
--- a/crypto/src/asn1/x9/X962NamedCurves.cs
+++ b/crypto/src/asn1/x9/X962NamedCurves.cs
@@ -38,7 +38,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     cFp192v1,
-                    cFp192v1.DecodePoint(
+                    new X9ECPoint(cFp192v1,
                         Hex.Decode("03188da80eb03090f67cbf20eb43a18800f4ff0afd82ff1012")),
                     n, h,
                     Hex.Decode("3045AE6FC8422f64ED579528D38120EAE12196D5"));
@@ -65,7 +65,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     cFp192v2,
-                    cFp192v2.DecodePoint(
+                    new X9ECPoint(cFp192v2,
                         Hex.Decode("03eea2bae7e1497842f2de7769cfe9c989c072ad696f48034a")),
                     n, h,
                     Hex.Decode("31a92ee2029fd10d901b113e990710f0d21ac6b6"));
@@ -92,7 +92,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     cFp192v3,
-                    cFp192v3.DecodePoint(
+                    new X9ECPoint(cFp192v3,
                         Hex.Decode("027d29778100c65a1da1783716588dce2b8b4aee8e228f1896")),
                     n, h,
                     Hex.Decode("c469684435deb378c4b65ca9591e2a5763059a2e"));
@@ -119,7 +119,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     cFp239v1,
-                    cFp239v1.DecodePoint(
+                    new X9ECPoint(cFp239v1,
                         Hex.Decode("020ffa963cdca8816ccc33b8642bedf905c3d358573d3f27fbbd3b3cb9aaaf")),
                     n, h,
                     Hex.Decode("e43bb460f0b80cc0c0b075798e948060f8321b7d"));
@@ -146,7 +146,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     cFp239v2,
-                    cFp239v2.DecodePoint(
+                    new X9ECPoint(cFp239v2,
                         Hex.Decode("0238af09d98727705120c921bb5e9e26296a3cdcf2f35757a0eafd87b830e7")),
                     n, h,
                     Hex.Decode("e8b4011604095303ca3b8099982be09fcb9ae616"));
@@ -173,7 +173,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     cFp239v3,
-                    cFp239v3.DecodePoint(
+                    new X9ECPoint(cFp239v3,
                         Hex.Decode("036768ae8e18bb92cfcf005c949aa2c6d94853d0e660bbf854b1c9505fe95a")),
                     n, h,
                     Hex.Decode("7d7374168ffe3471b60a857686a19475d3bfa2ff"));
@@ -200,7 +200,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     cFp256v1,
-                    cFp256v1.DecodePoint(
+                    new X9ECPoint(cFp256v1,
                         Hex.Decode("036b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c296")),
                     n, h,
                     Hex.Decode("c49d360886e704936a6678e1139d26b7819f7e90"));
@@ -231,7 +231,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m163v1,
-                    c2m163v1.DecodePoint(
+                    new X9ECPoint(c2m163v1,
                         Hex.Decode("0307AF69989546103D79329FCC3D74880F33BBE803CB")),
                     n, h,
                     Hex.Decode("D2C0FB15760860DEF1EEF4D696E6768756151754"));
@@ -259,7 +259,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m163v2,
-                    c2m163v2.DecodePoint(
+                    new X9ECPoint(c2m163v2,
                         Hex.Decode("030024266E4EB5106D0A964D92C4860E2671DB9B6CC5")),
                     n, h,
                     null);
@@ -287,7 +287,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m163v3,
-                    c2m163v3.DecodePoint(Hex.Decode("0202F9F87B7C574D0BDECF8A22E6524775F98CDEBDCB")),
+                    new X9ECPoint(c2m163v3, Hex.Decode("0202F9F87B7C574D0BDECF8A22E6524775F98CDEBDCB")),
                     n, h,
                     null);
             }
@@ -314,7 +314,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m176w1,
-                    c2m176w1.DecodePoint(
+                    new X9ECPoint(c2m176w1,
                         Hex.Decode("038D16C2866798B600F9F08BB4A8E860F3298CE04A5798")),
                     n, h,
                     null);
@@ -342,7 +342,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m191v1,
-                    c2m191v1.DecodePoint(
+                    new X9ECPoint(c2m191v1,
                         Hex.Decode("0236B3DAF8A23206F9C4F299D7B21A9C369137F2C84AE1AA0D")),
                     n, h,
                     Hex.Decode("4E13CA542744D696E67687561517552F279A8C84"));
@@ -370,7 +370,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m191v2,
-                    c2m191v2.DecodePoint(
+                    new X9ECPoint(c2m191v2,
                         Hex.Decode("023809B2B7CC1B28CC5A87926AAD83FD28789E81E2C9E3BF10")),
                     n, h,
                     null);
@@ -398,7 +398,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m191v3,
-                    c2m191v3.DecodePoint(
+                    new X9ECPoint(c2m191v3,
                         Hex.Decode("03375D4CE24FDE434489DE8746E71786015009E66E38A926DD")),
                     n, h,
                     null);
@@ -426,7 +426,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m208w1,
-                    c2m208w1.DecodePoint(
+                    new X9ECPoint(c2m208w1,
                         Hex.Decode("0289FDFBE4ABE193DF9559ECF07AC0CE78554E2784EB8C1ED1A57A")),
                     n, h,
                     null);
@@ -454,7 +454,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m239v1,
-                    c2m239v1.DecodePoint(
+                    new X9ECPoint(c2m239v1,
                         Hex.Decode("0257927098FA932E7C0A96D3FD5B706EF7E5F5C156E16B7E7C86038552E91D")),
                     n, h,
                     null);
@@ -482,7 +482,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m239v2,
-                    c2m239v2.DecodePoint(
+                    new X9ECPoint(c2m239v2,
                         Hex.Decode("0228F9D04E900069C8DC47A08534FE76D2B900B7D7EF31F5709F200C4CA205")),
                     n, h,
                     null);
@@ -510,7 +510,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m239v3,
-                    c2m239v3.DecodePoint(
+                    new X9ECPoint(c2m239v3,
                         Hex.Decode("0370F6E9D04D289C4E89913CE3530BFDE903977D42B146D539BF1BDE4E9C92")),
                     n, h,
                     null);
@@ -538,7 +538,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m272w1,
-                    c2m272w1.DecodePoint(
+                    new X9ECPoint(c2m272w1,
                         Hex.Decode("026108BABB2CEEBCF787058A056CBE0CFE622D7723A289E08A07AE13EF0D10D171DD8D")),
                     n, h,
                     null);
@@ -566,7 +566,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m304w1,
-                    c2m304w1.DecodePoint(
+                    new X9ECPoint(c2m304w1,
                         Hex.Decode("02197B07845E9BE2D96ADB0F5F3C7F2CFFBD7A3EB8B6FEC35C7FD67F26DDF6285A644F740A2614")),
                     n, h,
                     null);
@@ -594,7 +594,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m359v1,
-                    c2m359v1.DecodePoint(
+                    new X9ECPoint(c2m359v1,
                         Hex.Decode("033C258EF3047767E7EDE0F1FDAA79DAEE3841366A132E163ACED4ED2401DF9C6BDCDE98E8E707C07A2239B1B097")),
                     n, h,
                     null);
@@ -622,7 +622,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m368w1,
-                    c2m368w1.DecodePoint(
+                    new X9ECPoint(c2m368w1,
                         Hex.Decode("021085E2755381DCCCE3C1557AFA10C2F0C0C2825646C5B34A394CBCFA8BC16B22E7E789E927BE216F02E1FB136A5F")),
                     n, h,
                     null);
@@ -650,7 +650,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
                 return new X9ECParameters(
                     c2m431r1,
-                    c2m431r1.DecodePoint(
+                    new X9ECPoint(c2m431r1,
                         Hex.Decode("02120FC05D3C67A99DE161D2F4092622FECA701BE4F50F4758714E8A87BBF2A658EF8C21E7C5EFE965361F6C2999C0C247B0DBD70CE6B7")),
                     n, h,
                     null);
diff --git a/crypto/src/asn1/x9/X9ECParameters.cs b/crypto/src/asn1/x9/X9ECParameters.cs
index a192e4c52..2b6b14bcb 100644
--- a/crypto/src/asn1/x9/X9ECParameters.cs
+++ b/crypto/src/asn1/x9/X9ECParameters.cs
@@ -15,7 +15,7 @@ namespace Org.BouncyCastle.Asn1.X9
     {
         private X9FieldID	fieldID;
         private ECCurve		curve;
-        private ECPoint		g;
+        private X9ECPoint	g;
         private BigInteger	n;
         private BigInteger	h;
         private byte[]		seed;
@@ -29,36 +29,28 @@ namespace Org.BouncyCastle.Asn1.X9
                 throw new ArgumentException("bad version in X9ECParameters");
             }
 
-            X9Curve x9c = null;
-            if (seq[2] is X9Curve)
-            {
-                x9c = (X9Curve) seq[2];
-            }
-            else
-            {
-                x9c = new X9Curve(
-                    new X9FieldID(
-                        (Asn1Sequence) seq[1]),
-                        (Asn1Sequence) seq[2]);
-            }
+            X9Curve x9c = new X9Curve(
+                X9FieldID.GetInstance(seq[1]),
+                Asn1Sequence.GetInstance(seq[2]));
 
             this.curve = x9c.Curve;
+            object p = seq[3];
 
-            if (seq[3] is X9ECPoint)
+            if (p is X9ECPoint)
             {
-                this.g = ((X9ECPoint) seq[3]).Point;
+                this.g = ((X9ECPoint)p);
             }
             else
             {
-                this.g = new X9ECPoint(curve, (Asn1OctetString) seq[3]).Point;
+                this.g = new X9ECPoint(curve, (Asn1OctetString)p);
             }
 
-            this.n = ((DerInteger) seq[4]).Value;
+            this.n = ((DerInteger)seq[4]).Value;
             this.seed = x9c.GetSeed();
 
             if (seq.Count == 6)
             {
-                this.h = ((DerInteger) seq[5]).Value;
+                this.h = ((DerInteger)seq[5]).Value;
             }
         }
 
@@ -66,7 +58,16 @@ namespace Org.BouncyCastle.Asn1.X9
             ECCurve		curve,
             ECPoint		g,
             BigInteger	n)
-            : this(curve, g, n, BigInteger.One, null)
+            : this(curve, g, n, null, null)
+        {
+        }
+
+        public X9ECParameters(
+            ECCurve     curve,
+            X9ECPoint   g,
+            BigInteger  n,
+            BigInteger  h)
+            : this(curve, g, n, h, null)
         {
         }
 
@@ -85,9 +86,19 @@ namespace Org.BouncyCastle.Asn1.X9
             BigInteger	n,
             BigInteger	h,
             byte[]		seed)
+            : this(curve, new X9ECPoint(g), n, h, seed)
+        {
+        }
+
+        public X9ECParameters(
+            ECCurve     curve,
+            X9ECPoint   g,
+            BigInteger  n,
+            BigInteger  h,
+            byte[]      seed)
         {
             this.curve = curve;
-            this.g = g.Normalize();
+            this.g = g;
             this.n = n;
             this.h = h;
             this.seed = seed;
@@ -126,7 +137,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
         public ECPoint G
         {
-            get { return g; }
+            get { return g.Point; }
         }
 
         public BigInteger N
@@ -136,16 +147,7 @@ namespace Org.BouncyCastle.Asn1.X9
 
         public BigInteger H
         {
-            get
-            {
-                if (h == null)
-                {
-                    // TODO - this should be calculated, it will cause issues with custom curves.
-                    return BigInteger.One;
-                }
-
-                return h;
-            }
+            get { return h; }
         }
 
         public byte[] GetSeed()
@@ -154,6 +156,36 @@ namespace Org.BouncyCastle.Asn1.X9
         }
 
         /**
+         * Return the ASN.1 entry representing the Curve.
+         *
+         * @return the X9Curve for the curve in these parameters.
+         */
+        public X9Curve CurveEntry
+        {
+            get { return new X9Curve(curve, seed); }
+        }
+
+        /**
+         * Return the ASN.1 entry representing the FieldID.
+         *
+         * @return the X9FieldID for the FieldID in these parameters.
+         */
+        public X9FieldID FieldIDEntry
+        {
+            get { return fieldID; }
+        }
+
+        /**
+         * Return the ASN.1 entry representing the base point G.
+         *
+         * @return the X9ECPoint for the base point in these parameters.
+         */
+        public X9ECPoint BaseEntry
+        {
+            get { return g; }
+        }
+
+        /**
          * Produce an object suitable for an Asn1OutputStream.
          * <pre>
          *  ECParameters ::= Sequence {
@@ -169,10 +201,10 @@ namespace Org.BouncyCastle.Asn1.X9
         public override Asn1Object ToAsn1Object()
         {
             Asn1EncodableVector v = new Asn1EncodableVector(
-                new DerInteger(1),
+                new DerInteger(BigInteger.One),
                 fieldID,
                 new X9Curve(curve, seed),
-                new X9ECPoint(g),
+                g,
                 new DerInteger(n));
 
             if (h != null)
diff --git a/crypto/src/asn1/x9/X9ECPoint.cs b/crypto/src/asn1/x9/X9ECPoint.cs
index 75d58cd38..7ef4f13bc 100644
--- a/crypto/src/asn1/x9/X9ECPoint.cs
+++ b/crypto/src/asn1/x9/X9ECPoint.cs
@@ -1,5 +1,7 @@
 using Org.BouncyCastle.Math.EC;
 
+using Org.BouncyCastle.Utilities;
+
 namespace Org.BouncyCastle.Asn1.X9
 {
     /**
@@ -8,24 +10,58 @@ namespace Org.BouncyCastle.Asn1.X9
     public class X9ECPoint
         : Asn1Encodable
     {
-        private readonly ECPoint p;
+        private readonly Asn1OctetString encoding;
+
+        private ECCurve c;
+        private ECPoint p;
+
+        public X9ECPoint(ECPoint p)
+            : this(p, false)
+        {
+        }
 
-        public X9ECPoint(
-            ECPoint p)
+        public X9ECPoint(ECPoint p, bool compressed)
         {
             this.p = p.Normalize();
+            this.encoding = new DerOctetString(p.GetEncoded(compressed));
+        }
+
+        public X9ECPoint(ECCurve c, byte[] encoding)
+        {
+            this.c = c;
+            this.encoding = new DerOctetString(Arrays.Clone(encoding));
         }
 
-        public X9ECPoint(
-            ECCurve			c,
-            Asn1OctetString	s)
+        public X9ECPoint(ECCurve c, Asn1OctetString s)
+            : this(c, s.GetOctets())
         {
-            this.p = c.DecodePoint(s.GetOctets());
+        }
+
+        public byte[] GetPointEncoding()
+        {
+            return Arrays.Clone(encoding.GetOctets());
         }
 
         public ECPoint Point
         {
-            get { return p; }
+            get
+            {
+                if (p == null)
+                {
+                    p = c.DecodePoint(encoding.GetOctets()).Normalize();
+                }
+
+                return p;
+            }
+        }
+
+        public bool IsPointCompressed
+        {
+            get
+            {
+                byte[] octets = encoding.GetOctets();
+                return octets != null && octets.Length > 0 && (octets[0] == 2 || octets[0] == 3);
+            }
         }
 
         /**
@@ -38,7 +74,7 @@ namespace Org.BouncyCastle.Asn1.X9
          */
         public override Asn1Object ToAsn1Object()
         {
-            return new DerOctetString(p.GetEncoded());
+            return encoding;
         }
     }
 }
diff --git a/crypto/src/asn1/x9/X9FieldID.cs b/crypto/src/asn1/x9/X9FieldID.cs
index 58823a285..08d7d71b4 100644
--- a/crypto/src/asn1/x9/X9FieldID.cs
+++ b/crypto/src/asn1/x9/X9FieldID.cs
@@ -90,11 +90,19 @@ namespace Org.BouncyCastle.Asn1.X9
             this.parameters = new DerSequence(fieldIdParams);
         }
 
-        internal X9FieldID(
-            Asn1Sequence seq)
+        private X9FieldID(Asn1Sequence seq)
         {
-            this.id = (DerObjectIdentifier) seq[0];
-            this.parameters = (Asn1Object) seq[1];
+            this.id = DerObjectIdentifier.GetInstance(seq[0]);
+            this.parameters = seq[1].ToAsn1Object();
+        }
+
+        public static X9FieldID GetInstance(object obj)
+        {
+            if (obj is X9FieldID)
+                return (X9FieldID)obj;
+            if (obj == null)
+                return null;
+            return new X9FieldID(Asn1Sequence.GetInstance(obj));
         }
 
         public DerObjectIdentifier Identifier