public void EqualityTests() { ulong[] data = new ulong[50124]; CryptographicRandomGenerator.FillBuffer(MemoryMarshal.AsBytes(data.AsSpan())); var arrMine = new HugeManagedArray <ulong>(data); // IEnumerable<T> Assert.Equal(data, arrMine); // simple indexing for (int i = 0; i < data.Length; i++) { Assert.Equal(data[i], arrMine[i]); } // pattern foreach int j = 0; foreach (ulong val in data) { Assert.Equal(val, arrMine[j++]); } Assert.Equal(j, arrMine.Length); }
public void Compress_MatchesArgon2ImplWithZeros() { var prev = new ulong[128]; var refblock = new ulong[128]; refblock[1] = 1; refblock[3] = 0x80; refblock[4] = 5; refblock[5] = 1; refblock[6] = 1; var nextblock = new ulong[128]; var expected = new ulong[] { 0x84fa1423752d03e4UL, 0xd4202fb5e9e8fc76UL, 0xfffa1f74eefd530cUL, 0xff7c0a624b2d77b2UL, 0xe8a455cbb2592761UL, 0xc49617628179fcb2UL, 0xe10eae8549a5e992UL, 0xb5813d8f4dac273cUL, 0x067f495a0552af87UL, 0x238c3ed4edd6d758UL, 0x636655eafceb80f7UL, 0x193bea5049153114UL, 0x4e5b213e432ef97aUL, 0x14c94f0dbc62bc8eUL, 0x09ea35f920abb321UL, 0x0b23e9ece9dda457UL, 0xec4e388afb66ea39UL, 0x19c17b355dc165b1UL, 0xd0bd510f54632199UL, 0xb40e566edc09c97eUL, 0x056fdcefacc848d2UL, 0xfd1cc09541f51f4cUL, 0x651ccdb58533ba76UL, 0xa1b455170480831eUL, 0x535917aaf9d3974aUL, 0x3d0f1bf73415dd8fUL, 0x6fc201d6dbd1712fUL, 0x1dada40b36deec2aUL, 0xf130f29f1d9766e9UL, 0xb6fefdc5028af788UL, 0xd1c246d907916c1fUL, 0x2244fc5e4feb60e0UL, 0x4c4f81a45537ab6bUL, 0x440598781ceb86c1UL, 0xab688aa9c4f6f0c2UL, 0x527ea4c76c916baaUL, 0xd02adede165f21b3UL, 0x8daeee454e611ddbUL, 0xc36f86b4caad1ffaUL, 0x43c6abc4f94980d2UL, 0x51fa85d61f9c2ef2UL, 0x172251c39600dfe4UL, 0x26ef4b10c5315223UL, 0x0b274be0b3cb37bdUL, 0x77800a8310362779UL, 0x13411c98fbecc5f2UL, 0x9e86f88b6652fec0UL, 0xd12fee1f085ee874UL, 0x8a914c5f194d28b2UL, 0xe9a22f089c9d57adUL, 0x951d3bff84abe634UL, 0x71b8260a2a731996UL, 0xa480b0f5d78daed0UL, 0x10ca5f44f6289690UL, 0x294496482369b61bUL, 0x01ab318471afa3c5UL, 0x616228e98ae1de52UL, 0x6229b313f3e99a70UL, 0xa25d758741aa72f3UL, 0x79f61170cdf8cafdUL, 0x5ede754c0ecc0ea5UL, 0xcf7ec86439e3ac88UL, 0xbcac84fb22740928UL, 0xfce402b15f174f4bUL, 0x189f2f0eb52841efUL, 0x6d65b61521eec372UL, 0xe861420a415aad52UL, 0x3892000405138cd1UL, 0x0d0af34dd7dc039aUL, 0x8b014f732fdbb82dUL, 0xe5c95577bde46b94UL, 0xaf6618de7b19ef01UL, 0x624dce2300275a72UL, 0x28664b6858bfb794UL, 0xd339096ebd2d1451UL, 0xb7db8307513e4f2aUL, 0x968f96ad0166b0adUL, 0xc46a0fa460318d1eUL, 0x2fb04781a81acbbaUL, 0x9d7179cfe284a10fUL, 0x3954c632392a611eUL, 0x6dfa09128217faefUL, 0x74426d7fee03fbc3UL, 0xc61f567ad86aa8c2UL, 0x9fa23e4891aad1d6UL, 0x6a58893e968b6a34UL, 0x60b69e60b5da9334UL, 0xe092eca5ed01ec4fUL, 0xa0f4feb8684bea61UL, 0xc939dc7fe3d71567UL, 0x78643c9bade945f2UL, 0x21c8abe075ff7160UL, 0xd186a649e5785126UL, 0x9b6f93f964cb318bUL, 0x47492fdca064413fUL, 0x56f4d760f417ba5cUL, 0x4ed8e92e9edb5fc0UL, 0x4531ddefa01746a7UL, 0xe6f97a66353993a1UL, 0xb58123f2f29d590bUL, 0xe46280eb5adfdd41UL, 0x8cc4de8d5820a4aeUL, 0x179b347d88b80fd8UL, 0x2f7aa24800d9d845UL, 0x5f9028aa992ea32fUL, 0x264eab2bf9bf7495UL, 0xd7053aeec01850e5UL, 0xdd7a30e85357db70UL, 0xbc274baae23b6556UL, 0xdd4003399a66c11fUL, 0x06c21646c45221d5UL, 0x33b7f3e18c8e2444UL, 0x705c2c573a431472UL, 0x87bfe2e032fdc855UL, 0x21c9934657e023eaUL, 0xe5d4f3356bfa775bUL, 0x1b3680f9f40d3445UL, 0xcade7f1d6394fc2cUL, 0xd227b3d54ea5ca08UL, 0xc488e6b380c7da2fUL, 0x920507cb9771205bUL, 0xb847e31a07b63321UL, 0x7a48fa6eac42ada5UL, 0xa51cff427629c751UL, 0xa69e24c9d96b2caaUL, 0xfa50d0f8d81bfa0cUL, 0x282732bba6f10ad1UL, 0x4de0ea71122db92aUL }; Argon2Core.Compress( nextblock.AsSpan(), refblock.AsSpan(), prev.AsSpan()); Assert.Equal(expected, nextblock); }
public void Run() { Span <ulong> bits = data.AsSpan(); bits.Fill(0); int q = (int)Math.Sqrt(SieveSize); // We can skip 2, 3, and 5, and start our checks with 7. // This will be index 1 in the steps list. // Cached bitmaps and index offsets for bit twiddling loop. ulong[] masks = new ulong[BitsPerWord]; int[] offsets = new int[BitsPerWord]; // Look for next prime for (int factor = 7, step = 1, inc = steps[step]; factor <= q; factor += inc, step = (step + 1) % 8, inc = steps[step]) { // A set bit means it's composite - keep searching. if (GetBit(ref bits, factor)) { continue; } // The following loop is the hotspot for this algorithm. // No need to start less than p^2 since all those // multiples have already been marked. // Performance optimization: since the bit mask we `or` // into the word (and the index offset added to the base) // RECUR every 64 iterations of this loop (for 64-bit words), we // can precalculate them and use them over and over until the end // of the sieve array. int baseVal = IndexOf(factor * factor); int cumOffset = 0; masks.AsSpan().Fill(0); int iUsed = 0; int offset = 0; for (int bitCount = 0, m = factor * factor; bitCount < BitsPerWord; bitCount++, m += factor * 2) { masks[iUsed] |= MaskOf(m); offset = IndexOf(m + factor * 2) - IndexOf(m); // Don't advance to a new word unless the next // bit is in the same word! if (offset != 0) { offsets[iUsed] = offset; iUsed++; cumOffset += offset; } } // In this case, the bits in the last word can just // be merged to the first. if (offset == 0) { masks[0] |= masks[iUsed]; } // In all cases, iUsed will be 1 BEYOND the last mask used. // Now just rip through the array or-ing in these masks in an // identical pattern. int iStop = IndexOf(SieveSize); int i = baseVal; for (; i <= iStop - cumOffset;) { for (int j = 0; j < iUsed; j++) { bits[i] |= masks[j]; i += offsets[j]; } } // Finish last few words being careful about array bounds. for (int j = 0; j < iUsed && i <= iStop; j++) { bits[i] |= masks[j]; i += offsets[j]; } ClearBit(ref bits, factor); } ArrayPool <ulong> .Shared.Return(data); }
public unsafe static void Main() { var start = DateTime.Now; var s = Console.ReadLine(); var t = Console.ReadLine(); int n = s.Length; int m = t.Length; ulong[][] sarrs = new ulong[64][]; for (int j = 0; j < 64; j++) { sarrs[j] = new ulong[(n >> 6) + 1]; for (int i = j; i < s.Length; i++) { if (s[i] == '0') { continue; } var ind = i - j; sarrs[j][ind >> 6] |= 1UL << (ind & 63); } } ulong[] tarr = new ulong[(m >> 6) + 1]; for (int i = 0; i < m; i++) { if (t[i] == '0') { continue; } tarr[i >> 6] |= 1UL << (i & 63); } var tspan = tarr.AsSpan(); Random rng = new Random(1337); var precnt = m >> 6; var mask = (1UL << (m & 63)) - 1; var res = ulong.MaxValue; foreach (var i in Enumerable.Range(0, n - m + 1).OrderBy(_ => rng.Next())) { var curres = 0UL; var sspan = sarrs[i & 63].AsSpan().Slice(i >> 6, precnt + 1); int j = 0; for (; j + 4 < precnt; j += 4) { var xored = Vector.Xor(new Vector <ulong>(sspan.Slice(j, 4)), new Vector <ulong>(tspan.Slice(j, 4))); curres += Popcnt.X64.PopCount(xored[0]); curres += Popcnt.X64.PopCount(xored[1]); curres += Popcnt.X64.PopCount(xored[2]); curres += Popcnt.X64.PopCount(xored[3]); if (res < curres) { goto end; } } for (; j < precnt; j++) { curres += Popcnt.X64.PopCount(sspan[j] ^ tspan[j]); } curres += Popcnt.X64.PopCount((sspan[precnt] ^ tspan[precnt]) & mask); res = Min(res, curres); end :; if (2800 <= (DateTime.Now - start).TotalMilliseconds) { break; } } Console.WriteLine(res); }