Exemplo n.º 1
0
        public void When_GenerateParameters_Should_ReturnCorrectValues()
        {
            for (int i = 0; i < 3; i++)
            {
                DsaSystemParameters parameters = _generator.GenerateParameters(1024, 160, 160);

                _primalityTester.CheckPrimality(parameters.Q).Should().BeTrue();
                _primalityTester.CheckPrimality(parameters.P).Should().BeTrue();

                //p - 1 is a multiple of q
                ((parameters.P - 1) % parameters.Q).Should().BeEquivalentTo(BigInteger.Zero);

                //g^q is congruent to mod 1
                BigInteger.ModPow(parameters.G, parameters.Q, parameters.P).Should().BeEquivalentTo(BigInteger.One);
            }
        }
Exemplo n.º 2
0
        public DsaSystemParameters GenerateParameters(int L, int N, int seedLen)
        {
            #region CONDITIONS

            //SHA-1 used
            //Bit length of the output block of choosen hash function, shall be equal to or greater than N
            int outlen = 160;

            // check combination support
            if (!CheckLengthCombinations(L, N))
            {
                throw new ArgumentException($"Combination of lengths: L={L} and N={N} is not supported");
            }

            if (outlen < N)
            {
                throw new ArgumentException("Outlen cannot be less than N");
            }

            // insisted by FIPS standard
            if (seedLen < N)
            {
                throw new ArgumentException("Seedlen cannot be less then N");
            }

            #endregion

            // calculate equation parameters L - 1 = n * 160(outlen) + b
            int n = (int)Math.Ceiling((double)L / outlen) - 1;
            int b = L - 1 - (n * outlen);

            // create container for seed
            int    remainingBits = seedLen % 8;
            byte[] seed          = new byte[(seedLen / 8) + (remainingBits == 0 ? 0 : 1)];

            BigInteger outlenPow = BigInteger.Pow(2, seedLen);
            BigInteger p, q;

            bool outerLoop = true;
            do
            {
                q = GenerateQ(outlenPow, remainingBits, seed);

                bool innerLoop = true;
                int  counter = 0, offset = 2;
                do
                {
                    p = GenerateP(L, outlen, outlenPow, n, b, seed, q, ref offset);

                    if (p < BigInteger.Pow(2, L - 1))
                    {
                        UpdateControlVariables(n, ref outerLoop, ref innerLoop, ref counter, ref offset);
                    }
                    else
                    {
                        if (_primalityTester.CheckPrimality(p))
                        {
                            outerLoop = false;
                            innerLoop = false;
                        }
                        else
                        {
                            UpdateControlVariables(n, ref outerLoop, ref innerLoop, ref counter, ref offset);
                        }
                    }
                } while (innerLoop);
            } while (outerLoop || (p - 1) % q != 0);

            BigInteger g = GenerateG(p, q);

            return(new DsaSystemParameters(p, q, g));
        }