X448PrivateKeyParameters.cs 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. #if !BESTHTTP_DISABLE_ALTERNATE_SSL && (!UNITY_WEBGL || UNITY_EDITOR)
  2. #pragma warning disable
  3. using System;
  4. using System.IO;
  5. using Best.HTTP.SecureProtocol.Org.BouncyCastle.Math.EC.Rfc7748;
  6. using Best.HTTP.SecureProtocol.Org.BouncyCastle.Security;
  7. using Best.HTTP.SecureProtocol.Org.BouncyCastle.Utilities;
  8. using Best.HTTP.SecureProtocol.Org.BouncyCastle.Utilities.IO;
  9. namespace Best.HTTP.SecureProtocol.Org.BouncyCastle.Crypto.Parameters
  10. {
  11. public sealed class X448PrivateKeyParameters
  12. : AsymmetricKeyParameter
  13. {
  14. public static readonly int KeySize = X448.ScalarSize;
  15. public static readonly int SecretSize = X448.PointSize;
  16. private readonly byte[] data = new byte[KeySize];
  17. public X448PrivateKeyParameters(SecureRandom random)
  18. : base(true)
  19. {
  20. X448.GeneratePrivateKey(random, data);
  21. }
  22. public X448PrivateKeyParameters(byte[] buf)
  23. : this(Validate(buf), 0)
  24. {
  25. }
  26. public X448PrivateKeyParameters(byte[] buf, int off)
  27. : base(true)
  28. {
  29. Array.Copy(buf, off, data, 0, KeySize);
  30. }
  31. #if NETCOREAPP2_1_OR_GREATER || NETSTANDARD2_1_OR_GREATER || UNITY_2021_2_OR_NEWER
  32. public X448PrivateKeyParameters(ReadOnlySpan<byte> buf)
  33. : base(true)
  34. {
  35. if (buf.Length != KeySize)
  36. throw new ArgumentException("must have length " + KeySize, nameof(buf));
  37. buf.CopyTo(data);
  38. }
  39. #endif
  40. public X448PrivateKeyParameters(Stream input)
  41. : base(true)
  42. {
  43. if (KeySize != Streams.ReadFully(input, data))
  44. throw new EndOfStreamException("EOF encountered in middle of X448 private key");
  45. }
  46. public void Encode(byte[] buf, int off)
  47. {
  48. Array.Copy(data, 0, buf, off, KeySize);
  49. }
  50. #if NETCOREAPP2_1_OR_GREATER || NETSTANDARD2_1_OR_GREATER || UNITY_2021_2_OR_NEWER
  51. public void Encode(Span<byte> buf)
  52. {
  53. data.CopyTo(buf);
  54. }
  55. #endif
  56. public byte[] GetEncoded()
  57. {
  58. return Arrays.Clone(data);
  59. }
  60. public X448PublicKeyParameters GeneratePublicKey()
  61. {
  62. #if NETCOREAPP2_1_OR_GREATER || NETSTANDARD2_1_OR_GREATER || UNITY_2021_2_OR_NEWER
  63. Span<byte> publicKey = stackalloc byte[X448.PointSize];
  64. X448.GeneratePublicKey(data, publicKey);
  65. return new X448PublicKeyParameters(publicKey);
  66. #else
  67. byte[] publicKey = new byte[X448.PointSize];
  68. X448.GeneratePublicKey(data, 0, publicKey, 0);
  69. return new X448PublicKeyParameters(publicKey, 0);
  70. #endif
  71. }
  72. public void GenerateSecret(X448PublicKeyParameters publicKey, byte[] buf, int off)
  73. {
  74. #if NETCOREAPP2_1_OR_GREATER || NETSTANDARD2_1_OR_GREATER || UNITY_2021_2_OR_NEWER
  75. GenerateSecret(publicKey, buf.AsSpan(off));
  76. #else
  77. byte[] encoded = new byte[X448.PointSize];
  78. publicKey.Encode(encoded, 0);
  79. if (!X448.CalculateAgreement(data, 0, encoded, 0, buf, off))
  80. throw new InvalidOperationException("X448 agreement failed");
  81. #endif
  82. }
  83. #if NETCOREAPP2_1_OR_GREATER || NETSTANDARD2_1_OR_GREATER || UNITY_2021_2_OR_NEWER
  84. public void GenerateSecret(X448PublicKeyParameters publicKey, Span<byte> buf)
  85. {
  86. Span<byte> encoded = stackalloc byte[X448.PointSize];
  87. publicKey.Encode(encoded);
  88. if (!X448.CalculateAgreement(data, encoded, buf))
  89. throw new InvalidOperationException("X448 agreement failed");
  90. }
  91. #endif
  92. private static byte[] Validate(byte[] buf)
  93. {
  94. if (buf.Length != KeySize)
  95. throw new ArgumentException("must have length " + KeySize, nameof(buf));
  96. return buf;
  97. }
  98. }
  99. }
  100. #pragma warning restore
  101. #endif