VMPCEngine.cs 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137
  1. #if !BESTHTTP_DISABLE_ALTERNATE_SSL && (!UNITY_WEBGL || UNITY_EDITOR)
  2. #pragma warning disable
  3. using System;
  4. using BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto.Parameters;
  5. namespace BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto.Engines
  6. {
  7. public class VmpcEngine
  8. : IStreamCipher
  9. {
  10. /*
  11. * variables to hold the state of the VMPC engine during encryption and
  12. * decryption
  13. */
  14. protected byte n = 0;
  15. protected byte[] P = null;
  16. protected byte s = 0;
  17. protected byte[] workingIV;
  18. protected byte[] workingKey;
  19. public virtual string AlgorithmName
  20. {
  21. get { return "VMPC"; }
  22. }
  23. /**
  24. * initialise a VMPC cipher.
  25. *
  26. * @param forEncryption
  27. * whether or not we are for encryption.
  28. * @param params
  29. * the parameters required to set up the cipher.
  30. * @exception ArgumentException
  31. * if the params argument is inappropriate.
  32. */
  33. public virtual void Init(
  34. bool forEncryption,
  35. ICipherParameters parameters)
  36. {
  37. if (!(parameters is ParametersWithIV))
  38. throw new ArgumentException("VMPC Init parameters must include an IV");
  39. ParametersWithIV ivParams = (ParametersWithIV) parameters;
  40. if (!(ivParams.Parameters is KeyParameter))
  41. throw new ArgumentException("VMPC Init parameters must include a key");
  42. KeyParameter key = (KeyParameter)ivParams.Parameters;
  43. this.workingIV = ivParams.GetIV();
  44. if (workingIV == null || workingIV.Length < 1 || workingIV.Length > 768)
  45. throw new ArgumentException("VMPC requires 1 to 768 bytes of IV");
  46. this.workingKey = key.GetKey();
  47. InitKey(this.workingKey, this.workingIV);
  48. }
  49. protected virtual void InitKey(
  50. byte[] keyBytes,
  51. byte[] ivBytes)
  52. {
  53. s = 0;
  54. P = new byte[256];
  55. for (int i = 0; i < 256; i++)
  56. {
  57. P[i] = (byte) i;
  58. }
  59. for (int m = 0; m < 768; m++)
  60. {
  61. s = P[(s + P[m & 0xff] + keyBytes[m % keyBytes.Length]) & 0xff];
  62. byte temp = P[m & 0xff];
  63. P[m & 0xff] = P[s & 0xff];
  64. P[s & 0xff] = temp;
  65. }
  66. for (int m = 0; m < 768; m++)
  67. {
  68. s = P[(s + P[m & 0xff] + ivBytes[m % ivBytes.Length]) & 0xff];
  69. byte temp = P[m & 0xff];
  70. P[m & 0xff] = P[s & 0xff];
  71. P[s & 0xff] = temp;
  72. }
  73. n = 0;
  74. }
  75. public virtual void ProcessBytes(
  76. byte[] input,
  77. int inOff,
  78. int len,
  79. byte[] output,
  80. int outOff)
  81. {
  82. Check.DataLength(input, inOff, len, "input buffer too short");
  83. Check.OutputLength(output, outOff, len, "output buffer too short");
  84. for (int i = 0; i < len; i++)
  85. {
  86. s = P[(s + P[n & 0xff]) & 0xff];
  87. byte z = P[(P[(P[s & 0xff]) & 0xff] + 1) & 0xff];
  88. // encryption
  89. byte temp = P[n & 0xff];
  90. P[n & 0xff] = P[s & 0xff];
  91. P[s & 0xff] = temp;
  92. n = (byte) ((n + 1) & 0xff);
  93. // xor
  94. output[i + outOff] = (byte) (input[i + inOff] ^ z);
  95. }
  96. }
  97. public virtual void Reset()
  98. {
  99. InitKey(this.workingKey, this.workingIV);
  100. }
  101. public virtual byte ReturnByte(
  102. byte input)
  103. {
  104. s = P[(s + P[n & 0xff]) & 0xff];
  105. byte z = P[(P[(P[s & 0xff]) & 0xff] + 1) & 0xff];
  106. // encryption
  107. byte temp = P[n & 0xff];
  108. P[n & 0xff] = P[s & 0xff];
  109. P[s & 0xff] = temp;
  110. n = (byte) ((n + 1) & 0xff);
  111. // xor
  112. return (byte) (input ^ z);
  113. }
  114. }
  115. }
  116. #pragma warning restore
  117. #endif