Exemple #1
0
        /// <summary>
        /// Pads input bitstrings to the sponge construction to a number of bits which is a multiple of the rate.
        /// </summary>
        /// <param name="r">The rate of the sponge construction.</param>
        /// <param name="m">The length of the bitstring whose length to pad to a multiple of <paramref name="r"/>.</param>
        /// <returns>A padding suffix for a bitstring of length <paramref name="m"/> being processed in a sponge
        /// construction with a rate <paramref name="r"/>.</returns>
        /// <remarks>Keccak-p permutations use a pad10*1 (multirate) padding rule.</remarks>
        protected override Bitstring GetPadding(int r, int m)
        {
            int       j   = Bin.Mod(-m - 2, r);
            Bitstring pad = new Bitstring(j + 2);

            pad[0] = true;
            pad[pad.Length - 1] = true;
            return(pad);
        }
Exemple #2
0
        /// <summary>
        /// Creates a new <see cref="SpongeState"/> specifying its size and rate.
        /// </summary>
        /// <param name="size">The size of the sponge state.</param>
        /// <param name="rate">The rate of the sponge state, i.e. the number of bits which are impacted while absorbing
        /// messages.</param>
        /// <exception cref="ArgumentException"><paramref name="rate"/> is lower than one, or <paramref name="rate"/> is
        /// greater than or equal to <paramref name="size"/>'s <see cref="SpongeSize.B"/>.</exception>
        /// <remarks>
        /// <para>The capacity of the state, i.e. the number of bits which are not impacted while absorbing messages, will
        /// be <paramref name="size"/>.B - <paramref name="rate"/>.</para>
        /// </remarks>
        public SpongeState(SpongeSize size, int rate)
        {
            int b = size.B;

            if ((rate < 1) || (rate >= b))
            {
                throw new ArgumentException($"Invalid rate {rate} for width {b}.", nameof(rate));
            }
            _size      = size;
            _rate      = rate;
            _bitstring = Bitstring.Zeroes(b);
        }
Exemple #3
0
        /// <summary>
        /// Squeezes internal state until at least specified number of bits is produced, and returns these bits.
        /// </summary>
        /// <param name="outputLength">The number of desired output bits.</param>
        /// <returns>The byte array holding resulting bits.</returns>
        protected virtual byte[] Squeeze(int outputLength)
        {
            int       rate = State.Rate;
            Bitstring q    = new Bitstring();

            while (true)
            {
                q.Append(State.Bitstring.Truncate(rate));
                if (q.Length >= outputLength)
                {
                    return((q.Length == outputLength) ? q.Bytes : q.Truncate(outputLength).Bytes);
                }
                Function();
            }
        }
Exemple #4
0
        /// <summary>
        /// Creates a new <see cref="SpongeState"/> from an existing bitstring and specified rate.
        /// </summary>
        /// <param name="bitstring">The bitstring which holds the bits of the sponge state.</param>
        /// <param name="rate">The number of bits which are impacted while aborbing messages.</param>
        /// <exception cref="ArgumentNullException"><paramref name="bitstring"/> is null.</exception>
        /// <exception cref="ArgumentException"><paramref name="bitstring"/> is empty, or <paramref name="rate"/> is lower
        /// than one, or <paramref name="rate"/> is greater than or equal to <paramref>
        ///         <name>size</name>
        ///     </paramref>
        ///     's
        /// <see cref="SpongeSize.B"/>.</exception>
        /// <remarks>
        /// <para>The capacity of the state, i.e. the number of bits which are not impacted while absorbing messages, will
        /// be <see cref="bitstring"/>.Length - <paramref name="rate"/>.</para>
        /// </remarks>
        public SpongeState(Bitstring bitstring, int rate)
        {
            _bitstring = bitstring ?? throw new ArgumentNullException(nameof(bitstring));
            int length = _bitstring.Length;

            if (length < 1)
            {
                throw new ArgumentException("Bitstring cannot be empty.", nameof(bitstring));
            }
            _size = new SpongeSize(length);
            if ((rate < 1) || (rate >= _size.B))
            {
                throw new ArgumentException($"Invalid rate {rate} for width {_size.B}.", nameof(rate));
            }
            _rate = rate;
        }
Exemple #5
0
        /// <summary>
        ///
        /// </summary>
        /// <param name="bytes"></param>
        /// <param name="length"></param>
        protected virtual void Absorb(byte[] bytes, int length)
        {
            State.Clear();
            Bitstring message = new Bitstring(bytes, length);
            int       rate    = State.Rate;

            message.Append(Suffix());
            message.Append(GetPadding(rate, message.Length));
            int       n      = message.Length / rate;
            Bitstring zeroes = new Bitstring(Capacity);
            Bitstring chunk;

            for (int i = 0; i < n; i++)
            {
                chunk = message.Substring(rate * i, rate);
                chunk.Append(zeroes);
                State.Bitstring.Xor(chunk);
                Function();
            }
        }
Exemple #6
0
        private static SpongeState Iota(SpongeState state, int round)
        {
            int       w  = state.Size.W;
            int       l  = state.Size.L;
            Bitstring rc = Bitstring.Zeroes(w);
            RoundT    roundT;
            int       t;
            int       rnd = 7 * round;

            for (int j = 0; j <= l; j++)
            {
                t      = j + rnd;
                roundT = new RoundT(round, t);
                if (!_roundTConstants.ContainsKey(roundT))
                {
                    _roundTConstants.Add(roundT, RoundConstant(t));
                }
                rc[(1 << j) - 1] = _roundTConstants[roundT];
            }
            state.XorLane(state.GetLane(0, 0), rc);
            return(state);
        }
Exemple #7
0
        private static bool RoundConstant(int t)
        {
            t = Bin.Mod(t, 255);
            if (_roundConstants.ContainsKey(t))
            {
                return(_roundConstants[t]);
            }
            Bitstring r = new Bitstring("10000000", 8);

            for (int i = 0; i < t; i++)
            {
                r.Prepend(Bitstring.Zero);
                r[0] ^= r[8];
                r[4] ^= r[8];
                r[5] ^= r[8];
                r[6] ^= r[8];
                r     = r.Truncate(8);
            }
            bool bit = r[0];

            _roundConstants.Add(t, bit);
            return(bit);
        }
Exemple #8
0
 /// <summary>
 /// Sets the bitstring holding the bits of this state to specified value.
 /// </summary>
 /// <param name="bitstring">The bitstring by which replacing this state's internal bitstring.</param>
 /// <remarks>Unchecked version of <see cref="Bitstring"/> setter. Internal use only.</remarks>
 internal void SetBitstring(Bitstring bitstring)
 {
     _bitstring = bitstring;
 }
Exemple #9
0
 /// <summary>
 /// Creates a new <see cref="SpongeState"/> from an existing one.
 /// </summary>
 /// <param name="state">The sponge state to copy.</param>
 public SpongeState(SpongeState state)
 {
     _size      = state._size;
     _rate      = state._rate;
     _bitstring = new Bitstring(state._bitstring);
 }
Exemple #10
0
 public override void Initialize()
 {
     _hash = new Bitstring();
 }
Exemple #11
0
 protected override byte[] HashFinal()
 {
     _hash = new Bitstring(_permutation.Process(_hash.Bytes, _permutation.Width));
     return(_hash?.Bytes ?? new byte[0]);
 }