GeneralDigest.cs 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. #if !BESTHTTP_DISABLE_ALTERNATE_SSL && (!UNITY_WEBGL || UNITY_EDITOR)
  2. #pragma warning disable
  3. using System;
  4. using BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities;
  5. namespace BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto.Digests
  6. {
  7. /**
  8. * base implementation of MD4 family style digest as outlined in
  9. * "Handbook of Applied Cryptography", pages 344 - 347.
  10. */
  11. [BestHTTP.PlatformSupport.IL2CPP.Il2CppSetOption(BestHTTP.PlatformSupport.IL2CPP.Option.NullChecks, false)]
  12. [BestHTTP.PlatformSupport.IL2CPP.Il2CppSetOption(BestHTTP.PlatformSupport.IL2CPP.Option.ArrayBoundsChecks, false)]
  13. [BestHTTP.PlatformSupport.IL2CPP.Il2CppSetOption(BestHTTP.PlatformSupport.IL2CPP.Option.DivideByZeroChecks, false)]
  14. [BestHTTP.PlatformSupport.IL2CPP.Il2CppEagerStaticClassConstructionAttribute]
  15. public abstract class GeneralDigest
  16. : IDigest, IMemoable
  17. {
  18. private const int BYTE_LENGTH = 64;
  19. private byte[] xBuf;
  20. private int xBufOff;
  21. private long byteCount;
  22. internal GeneralDigest()
  23. {
  24. xBuf = new byte[4];
  25. }
  26. internal GeneralDigest(GeneralDigest t)
  27. {
  28. xBuf = new byte[t.xBuf.Length];
  29. CopyIn(t);
  30. }
  31. protected void CopyIn(GeneralDigest t)
  32. {
  33. Array.Copy(t.xBuf, 0, xBuf, 0, t.xBuf.Length);
  34. xBufOff = t.xBufOff;
  35. byteCount = t.byteCount;
  36. }
  37. public void Update(byte input)
  38. {
  39. xBuf[xBufOff++] = input;
  40. if (xBufOff == xBuf.Length)
  41. {
  42. ProcessWord(xBuf, 0);
  43. xBufOff = 0;
  44. }
  45. byteCount++;
  46. }
  47. public unsafe void BlockUpdate(
  48. byte[] input,
  49. int inOff,
  50. int length)
  51. {
  52. length = System.Math.Max(0, length);
  53. //
  54. // fill the current word
  55. //
  56. int i = 0;
  57. if (xBufOff != 0)
  58. {
  59. fixed (byte* pxBuf = xBuf, pinput = input)
  60. while (i < length)
  61. {
  62. pxBuf[xBufOff++] = pinput[inOff + i++];
  63. if (xBufOff == 4)
  64. {
  65. ProcessWord(xBuf, 0);
  66. xBufOff = 0;
  67. break;
  68. }
  69. }
  70. }
  71. //
  72. // process whole words.
  73. //
  74. int limit = ((length - i) & ~3) + i;
  75. for (; i < limit; i += 4)
  76. {
  77. ProcessWord(input, inOff + i);
  78. }
  79. //
  80. // load in the remainder.
  81. //
  82. //while (i < length)
  83. //{
  84. // xBuf[xBufOff++] = input[inOff + i++];
  85. //}
  86. fixed (byte* pxBuf = xBuf, pinput = input)
  87. {
  88. while (i < length)
  89. pxBuf[xBufOff++] = pinput[inOff + i++];
  90. }
  91. byteCount += length;
  92. }
  93. public void Finish()
  94. {
  95. long bitLength = (byteCount << 3);
  96. //
  97. // add the pad bytes.
  98. //
  99. Update((byte)128);
  100. while (xBufOff != 0) Update((byte)0);
  101. ProcessLength(bitLength);
  102. ProcessBlock();
  103. }
  104. public virtual void Reset()
  105. {
  106. byteCount = 0;
  107. xBufOff = 0;
  108. Array.Clear(xBuf, 0, xBuf.Length);
  109. }
  110. public int GetByteLength()
  111. {
  112. return BYTE_LENGTH;
  113. }
  114. internal abstract void ProcessWord(byte[] input, int inOff);
  115. internal abstract void ProcessLength(long bitLength);
  116. internal abstract void ProcessBlock();
  117. public abstract string AlgorithmName { get; }
  118. public abstract int GetDigestSize();
  119. public abstract int DoFinal(byte[] output, int outOff);
  120. public abstract IMemoable Copy();
  121. public abstract void Reset(IMemoable t);
  122. }
  123. }
  124. #pragma warning restore
  125. #endif