Crc32.cs 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. using System;
  2. using System.Collections.Generic;
  3. namespace SharpCompress.Compressors.Xz
  4. {
  5. internal static class Crc32
  6. {
  7. public const UInt32 DefaultPolynomial = 0xedb88320u;
  8. public const UInt32 DefaultSeed = 0xffffffffu;
  9. private static UInt32[] defaultTable;
  10. public static UInt32 Compute(byte[] buffer)
  11. {
  12. return Compute(DefaultSeed, buffer);
  13. }
  14. public static UInt32 Compute(UInt32 seed, byte[] buffer)
  15. {
  16. return Compute(DefaultPolynomial, seed, buffer);
  17. }
  18. public static UInt32 Compute(UInt32 polynomial, UInt32 seed, byte[] buffer)
  19. {
  20. return ~CalculateHash(InitializeTable(polynomial), seed, buffer, 0, buffer.Length);
  21. }
  22. private static UInt32[] InitializeTable(UInt32 polynomial)
  23. {
  24. if (polynomial == DefaultPolynomial && defaultTable != null)
  25. return defaultTable;
  26. var createTable = new UInt32[256];
  27. for (var i = 0; i < 256; i++)
  28. {
  29. var entry = (UInt32)i;
  30. for (var j = 0; j < 8; j++)
  31. if ((entry & 1) == 1)
  32. entry = (entry >> 1) ^ polynomial;
  33. else
  34. entry = entry >> 1;
  35. createTable[i] = entry;
  36. }
  37. if (polynomial == DefaultPolynomial)
  38. defaultTable = createTable;
  39. return createTable;
  40. }
  41. private static UInt32 CalculateHash(UInt32[] table, UInt32 seed, IList<byte> buffer, int start, int size)
  42. {
  43. var crc = seed;
  44. for (var i = start; i < size - start; i++)
  45. crc = (crc >> 8) ^ table[buffer[i] ^ crc & 0xff];
  46. return crc;
  47. }
  48. }
  49. }