Example #1
0
        internal Argon2Lane[] InitializeLanes(byte[] password)
        {
            byte[] blockHash = Initialize(password);

            Argon2Lane[] lanes = new Argon2Lane[1];

            // Adjust memory size if needed so that each segment has an even size
            int segmentLength = MemorySize / (lanes.Length * 4);

            MemorySize = segmentLength * 4 * lanes.Length;
            int blocksPerLane = MemorySize / lanes.Length;

            if (blocksPerLane < 4)
            {
                throw new InvalidOperationException($"Memory should be enough to provide at least 4 blocks");
            }

            Action[] init = new Action[lanes.Length * 2];
            for (int i = 0; i < lanes.Length; ++i)
            {
                lanes[i] = new Argon2Lane(blocksPerLane);

                int taskIndex = i * 2;
                int iClosure  = i;
                init[taskIndex] = () => {
                    LittleEndianActiveStream stream = new LittleEndianActiveStream();
                    stream.Expose(blockHash);
                    stream.Expose(0);
                    stream.Expose(iClosure);

                    ModifiedBlake2.Blake2Prime(lanes[iClosure][0], stream);
                };

                init[taskIndex + 1] = () => {
                    LittleEndianActiveStream stream = new LittleEndianActiveStream();
                    stream.Expose(blockHash);
                    stream.Expose(1);
                    stream.Expose(iClosure);

                    ModifiedBlake2.Blake2Prime(lanes[iClosure][1], stream);
                };
            }

            foreach (Action t in init)
            {
                t();
            }

            Array.Clear(blockHash, 0, blockHash.Length);
            return(lanes);
        }
Example #2
0
        private byte[] Finalize(Argon2Lane[] lanes)
        {
            XorLanes(lanes);

            LittleEndianActiveStream ds = new LittleEndianActiveStream();

            ds.Expose(lanes[0][lanes[0].BlockCount - 1]);

            ModifiedBlake2.Blake2Prime(lanes[0][1], ds, TagLine);
            byte[]       result = new byte[TagLine];
            Argon2Memory memory = lanes[0][1];

            memory.GetBuffer(result);

            return(result);
        }
Example #3
0
        internal static void Compress(Argon2Memory dest, Argon2Memory refb, Argon2Memory prev)
        {
            ulong[] tmpblock = new ulong[dest.Length];
            for (int n = 0; n < 128; ++n)
            {
                tmpblock[n] = refb[n] ^ prev[n];
                dest[n]    ^= tmpblock[n];
            }

            for (int i = 0; i < 8; ++i)
            {
                ModifiedBlake2.DoRoundColumns(tmpblock, i);
            }
            for (int i = 0; i < 8; ++i)
            {
                ModifiedBlake2.DoRoundRows(tmpblock, i);
            }

            for (int n = 0; n < 128; ++n)
            {
                dest[n] ^= tmpblock[n];
            }
        }