18 public const string Namespace =
"http://waher.se/Schema/EllipticCurves.xsd";
23 public static readonly BigInteger
Two =
new BigInteger(2);
33 protected static readonly RandomNumberGenerator
rnd = RandomNumberGenerator.Create();
43 protected readonly BigInteger
n;
70 private byte[] secret;
71 private byte[] privateKey;
72 private byte[] publicKey;
73 private byte[] publicKeyBigEndian;
74 private byte[] additionalInfo;
101 this.secret = Secret;
102 this.privateKey =
null;
103 this.publicKey =
null;
104 this.publicKeyBigEndian =
null;
105 this.additionalInfo =
null;
108 this.orderBytes = this.bigIntegerBytes = (this.orderBits + 7) >> 3;
109 this.msbOrderMask = 0xff;
114 this.bigIntegerBytes++;
115 this.msbOrderMask = 0;
118 this.msbOrderMask >>= MaskBits;
126 if (this.secret is
null)
139 if (this.privateKey is
null)
142 return this.privateKey;
153 if (this.publicKey is
null)
156 return this.publicKey;
167 if (this.publicKeyBigEndian is
null)
170 return this.publicKeyBigEndian;
181 if (this.additionalInfo is
null)
184 return this.additionalInfo;
195 if (this.publicKey is
null)
198 return this.publicKeyPoint;
203 this.publicKeyPoint = value;
268 this.publicKey = this.
Encode(P,
false);
269 this.publicKeyBigEndian = this.
Encode(P,
true);
270 this.publicKeyPoint = P;
271 this.privateKey = Info.Item1;
272 this.additionalInfo = Info.Item2;
273 this.secret = Secret;
283 return new Tuple<byte[], byte[]>(Secret,
null);
293 return this.
Encode(Point,
false);
304 byte[] X = Point.
X.ToByteArray();
305 byte[] Y = Point.
Y.ToByteArray();
306 byte[] Result =
new byte[this.orderBytes << 1];
308 if (X.Length !=
this.orderBytes)
309 Array.Resize(ref X, this.orderBytes);
311 if (Y.Length !=
this.orderBytes)
312 Array.Resize(ref Y, this.orderBytes);
320 Buffer.BlockCopy(X, 0, Result, 0, this.orderBytes);
321 Buffer.BlockCopy(Y, 0, Result, this.orderBytes, this.orderBytes);
333 return this.
Decode(Point,
false);
344 if (Point.Length !=
this.orderBytes << 1)
345 throw new ArgumentException(
"Invalid point.", nameof(Point));
350 Buffer.BlockCopy(Point, 0, X, 0, this.orderBytes);
351 Buffer.BlockCopy(Point, this.orderBytes, Y, 0, this.orderBytes);
389 for (i = 0; i < c; i++)
393 for (Bit = 1; Bit != 0; Bit <<= 1)
396 this.
AddTo(ref Result, P);
412 return new PointOnCurve(BigInteger.Zero, BigInteger.Zero);
475 public virtual byte[]
GetSharedKey(
byte[] RemotePublicKey,
bool BigEndian,
487 public byte[]
Sign(
byte[] Data)
489 return this.
Sign(Data,
false);
498 public abstract byte[]
Sign(
byte[] Data,
bool BigEndian);
505 public byte[]
Sign(Stream Data)
507 return this.
Sign(Data,
false);
516 public abstract byte[]
Sign(Stream Data,
bool BigEndian);
561 public abstract bool Verify(Stream Data,
byte[]
PublicKey,
bool BigEndian,
byte[] Signature);
567 public virtual void Export(XmlWriter Output)
569 if (this.secret is
null)
573 Output.WriteAttributeString(
"type", this.GetType().FullName);
574 Output.WriteAttributeString(
"d", Convert.ToBase64String(
this.secret));
575 Output.WriteEndElement();
583 XmlWriterSettings Settings =
new XmlWriterSettings()
586 OmitXmlDeclaration =
true
588 StringBuilder sb =
new StringBuilder();
589 using (XmlWriter w = XmlWriter.Create(sb, Settings))
595 return sb.ToString();
605 public static BigInteger
ToInt(
byte[] Binary,
bool BigEndian)
609 Binary = (
byte[])Binary.Clone();
610 Array.Reverse(Binary);
613 return ToInt(Binary);
622 public static BigInteger
ToInt(
byte[] Binary)
624 int c = Binary.Length;
625 if ((Binary[c - 1] & 0x80) != 0)
626 Array.Resize(ref Binary, c + 1);
628 return new BigInteger(Binary);
638 return this.
IsPoint(Point,
false);
647 public virtual bool IsPoint(
byte[] Point,
bool BigEndian)
Implements the Elliptic Curve Diffie-Hellman (ECDH) algorithm.
static PointOnCurve GetSharedPoint(byte[] LocalPrivateKey, byte[] RemotePublicKey, bool RemoteBigEndian, EllipticCurve Curve)
Gets a shared key using the Elliptic Curve Diffie-Hellman (ECDH) algorithm.
static byte[] GetSharedKey(byte[] LocalPrivateKey, byte[] RemotePublicKey, bool RemoteBigEndian, HashFunctionArray HashFunction, EllipticCurve Curve)
Gets a shared key using the Elliptic Curve Diffie-Hellman (ECDH) algorithm.
Abstract base class for elliptic curves.
virtual byte[] GetSharedKey(byte[] RemotePublicKey, bool BigEndian, HashFunctionArray HashFunction)
Gets a shared key using the Elliptic Curve Diffie-Hellman (ECDH) algorithm.
virtual PointOnCurve ScalarMultiplication(byte[] N, PointOnCurve P, bool Normalize)
Performs the scalar multiplication of N *P .
EllipticCurve(PointOnCurve BasePoint, BigInteger Order, int Cofactor)
Abstract base class for elliptic curves.
byte[] Sign(byte[] Data)
Creates a signature of Data using the ECDSA algorithm.
readonly PointOnCurve g
Base point
readonly int orderBits
Number of bits used for the order of the curve.
abstract string CurveName
Name of curve.
virtual Tuple< byte[], byte[]> CalculatePrivateKey(byte[] Secret)
Calculates a private key from a secret.
byte[] Encode(PointOnCurve Point)
Encodes a point on the curve.
abstract byte[] GenerateSecret()
Generates a new secret.
virtual byte[] PublicKeyBigEndian
Returns a big-endian representation of the public key.
BigInteger Order
Order of curve.
readonly int cofactor
cofactor
readonly int orderBytes
Number of bytes used for the order of the curve.
readonly BigInteger n
Order
virtual bool IsPoint(byte[] Point, bool BigEndian)
Checks if an encoded point is on the curve.
byte[] AdditionalInfo
Curve-specific additional information
abstract bool Verify(Stream Data, byte[] PublicKey, bool BigEndian, byte[] Signature)
Verifies a signature of Data made by the ECDSA algorithm.
int OrderBits
Number of bits required to represent the order of the curve.
abstract void Double(ref PointOnCurve P)
Doubles a point on the curve.
abstract byte[] Sign(Stream Data, bool BigEndian)
Creates a signature of Data using the ECDSA algorithm.
EllipticCurve(PointOnCurve BasePoint, BigInteger Order, int Cofactor, byte[] Secret)
Abstract base class for elliptic curves.
virtual bool IsPoint(byte[] Point)
Checks if an encoded point is on the curve.
virtual void Export(XmlWriter Output)
Exports the curve parameters to XML.
int Cofactor
Cofactor of curve.
byte MsbOrderMask
Mask for most significant byte of scalars (as byte arrays of size BigIntegerBytes).
bool Verify(Stream Data, byte[] PublicKey, byte[] Signature)
Verifies a signature of Data made by the ECDSA algorithm.
static BigInteger ToInt(byte[] Binary, bool BigEndian)
Converts a little-endian binary representation of a big integer to a BigInteger.
string Export()
Exports the curve parameters to an XML string.
int OrderBytes
Number of bytes required to represent the order of the curve.
virtual PointOnCurve Decode(byte[] Point, bool BigEndian)
Decodes an encoded point on the curve.
byte[] Sign(Stream Data)
Creates a signature of Data using the ECDSA algorithm.
readonly int bigIntegerBytes
Number of bytes used for big integers in the curve.
static BigInteger ToInt(byte[] Binary)
Converts a little-endian binary representation of a big integer to a BigInteger.
abstract bool IsPoint(PointOnCurve Point)
Checks if a point is on the curve.
int BigIntegerBytes
Number of bytes required to represent coordinates using BigInteger of the curve. This number may diff...
const string ElementName
"EllipticCurve"
abstract byte[] Sign(byte[] Data, bool BigEndian)
Creates a signature of Data using the ECDSA algorithm.
virtual byte[] PublicKey
Encoded public key
void GenerateKeys()
Generates a new Private Key.
static readonly BigInteger Two
2
bool Verify(byte[] Data, byte[] PublicKey, byte[] Signature)
Verifies a signature of Data made by the ECDSA algorithm.
virtual void Init()
Method initiazing the elliptic curve properties.
virtual PointOnCurve GetSharedPoint(byte[] RemotePublicKey, bool BigEndian)
Gets a shared key, as a point, using the Elliptic Curve Diffie-Hellman (ECDH) algorithm.
PointOnCurve GetSharedPoint(byte[] RemotePublicKey)
Gets a shared key, as a point, using the Elliptic Curve Diffie-Hellman (ECDH) algorithm.
virtual PointOnCurve Zero
Neutral point.
static readonly RandomNumberGenerator rnd
Random number generator
abstract bool Verify(byte[] Data, byte[] PublicKey, bool BigEndian, byte[] Signature)
Verifies a signature of Data made by the ECDSA algorithm.
virtual byte[] Encode(PointOnCurve Point, bool BigEndian)
Encodes a point on the curve.
PointOnCurve Decode(byte[] Point)
Decodes an encoded point on the curve.
const string Namespace
http://waher.se/Schema/EllipticCurves.xsd
PointOnCurve BasePoint
Base-point of curve.
virtual byte[] GetSharedKey(byte[] RemotePublicKey, HashFunctionArray HashFunction)
Gets a shared key using the Elliptic Curve Diffie-Hellman (ECDH) algorithm.
byte[] PrivateKey
Private key
virtual void SetPrivateKey(byte[] Secret)
Sets the private key (and therefore also the public key) of the curve.
virtual PointOnCurve PublicKeyPoint
Public key, as a point on the elliptic curve.
readonly byte msbOrderMask
Mask for most significant byte of scalars.
abstract void AddTo(ref PointOnCurve P, PointOnCurve Q)
Adds Q to P .
PointOnCurve ScalarMultiplication(BigInteger N, PointOnCurve P, bool Normalize)
Performs the scalar multiplication of N *P .
Integer arithmetic, modulus a prime.
static int CalcBits(BigInteger n)
Calculates the number of bits used.
Interface for digital signature algorithms.
delegate byte[] HashFunctionArray(byte[] Data)
Delegate to hash function.
HashFunction
Hash method enumeration.
Represents a point on a curve.