Beispiel #1
0
        public static ulong ComputeHash(byte[] input)
        {
            uint len        = (uint)input.Length;
            uint num_chunks = len / 128;

            // copy tail, pad with zeroes
            byte[] tail      = new byte[128];
            uint   tail_size = len % 128;

            Array.Copy(input, len - tail_size, tail, 0, tail_size);

            UInt128 hash;

            if (num_chunks != 0)
            {
                hash = HashChunk(input, 128, 0);
            }
            else
            {
                hash = HashChunk(tail, tail_size, 0);
            }

            hash += ROUND_MAGIC;

            int offset = 0;

            if (num_chunks != 0)
            {
                while (--num_chunks > 0)
                {
                    offset += 128;
                    hash    = HashMulAdd(hash, ROUND_MAGIC, HashChunk(input, 128, offset));
                }

                if (tail_size > 0)
                {
                    hash = HashMulAdd(hash, ROUND_MAGIC, HashChunk(tail, tail_size, 0));
                }
            }

            hash += new UInt128(tail_size * 8, 0);

            if (hash > new UInt128(0x7fffffffffffffff, 0xffffffffffffffff))
            {
                hash++;
            }

            hash = hash << 1 >> 1;

            ulong X = hash.hi + (hash.lo >> 32);

            X = ((X + (X >> 32) + 1) >> 32) + hash.hi;
            ulong Y = (X << 32) + hash.lo;

            ulong A = X + FINAL_MAGIC0;

            if (A < X)
            {
                A += 0x101;
            }

            ulong B = Y + FINAL_MAGIC1;

            if (B < Y)
            {
                B += 0x101;
            }

            UInt128 H   = new UInt128(A) * B;
            UInt128 mul = new UInt128(0x101);

            H = (mul * H.hi) + H.lo;
            H = (mul * H.hi) + H.lo;

            if (H.hi > 0)
            {
                H += mul;
            }
            if (H.lo > 0xFFFFFFFFFFFFFEFE)
            {
                H += mul;
            }
            return(H.lo);
        }
Beispiel #2
0
 public bool Equals(UInt128 other)
 {
     return(hi == other.hi && lo == other.lo);
 }