예제 #1
0
 /// <summary>
 /// Generates the random salt.
 /// </summary>
 /// <returns></returns>
 public byte[] GenerateRandomSalt() => CryptoRandom.NextBytesStatic(SaltLengthInBytes);
        /// <summary>
        /// Generates actual options from this
        /// </summary>
        /// <returns>ActualPasswordGeneratorOptions</returns>
        internal ActualPasswordGeneratorOptions GetActuals()
        {
            var options = new ActualPasswordGeneratorOptions
            {
                Length        = (int)Length,
                Lower         = ValidLowerCase,
                Upper         = ValidUpperCase,
                Symbols       = ValidSymbols,
                LowerLength   = (int)MinLowerCase,
                UpperLength   = (int)MinUpperCase,
                NumbersLength = (int)MinNumbers,
                SymbolsLength = (int)MinSymbols
            };

            int maxLower   = 2 * options.LowerLength;
            int maxUpper   = 2 * options.UpperLength;
            int maxNumbers = 2 * options.NumbersLength;
            int maxSymbols = 2 * options.SymbolsLength;

            using (var cr = new CryptoRandom())
            {
                while (maxLower + maxUpper + maxNumbers + maxSymbols < options.Length)
                {
                    switch (cr.NextInt(4))
                    {
                    case 0:
                        if (maxLower != 0)
                        {
                            maxLower++;
                        }
                        break;

                    case 1:
                        if (maxUpper != 0)
                        {
                            maxUpper++;
                        }
                        break;

                    case 2:
                        if (maxSymbols != 0)
                        {
                            maxSymbols++;
                        }
                        break;

                    case 3:
                        if (maxNumbers != 0)
                        {
                            maxNumbers++;
                        }
                        break;

                    default:
                        throw new IndexOutOfRangeException();
                    }
                }

                Func <bool> canAddLower  = () => maxLower > options.LowerLength;
                Func <bool> canAddUpper  = () => maxUpper > options.UpperLength;
                Func <bool> canAddNumber = () => maxNumbers > options.NumbersLength;
                Func <bool> canAddSymbol = () => maxSymbols > options.SymbolsLength;

                while (options.Length != options.UpperLength + options.LowerLength + options.NumbersLength + options.SymbolsLength)
                {
                    switch (cr.NextInt(4))
                    {
                    case 0:
                        if (canAddLower())
                        {
                            options.LowerLength++;
                        }
                        break;

                    case 1:
                        if (canAddUpper())
                        {
                            options.UpperLength++;
                        }
                        break;

                    case 2:
                        if (canAddSymbol())
                        {
                            options.SymbolsLength++;
                        }
                        break;

                    case 3:
                        if (canAddNumber())
                        {
                            options.NumbersLength++;
                        }
                        break;

                    default:
                        throw new IndexOutOfRangeException();
                    }
                }
            }

            return(options);
        }