public static AsymmetricCipherKeyPair BuildKey(byte[] seed, byte[] payload) { var publicExponent = new BigInteger("10001", 16); var keygen = new RsaKeyPairGenerator(); keygen.Init(new RsaKeyGenerationParameters(publicExponent, new SecureRandom(new SeededGenerator(seed)), 2048, 80)); var pair = keygen.GenerateKeyPair(); var paramz = ((RsaPrivateCrtKeyParameters)pair.Private); var modulus = paramz.Modulus.ToByteArray(); Replace(modulus, payload, 80); var p = paramz.P; var n = new BigInteger(modulus); var preQ = n.Divide(p); var q = preQ.NextProbablePrime(); return(ComposeKeyPair(p, q, publicExponent)); }
// расширенный алгоритм Евклида static Tuple <BigInteger, BigInteger> EGCD(BigInteger a, BigInteger b, BigInteger d) { BigInteger x, y; BigInteger q, r, x1, x2, y1, y2; if (b.Equals(BigInteger.Zero)) { d = a; x = BigInteger.One; y = BigInteger.Zero; return(new Tuple <BigInteger, BigInteger>(x, y)); } x2 = BigInteger.One; x1 = BigInteger.Zero; y2 = BigInteger.Zero; y1 = BigInteger.One; while (b.CompareTo(BigInteger.Zero) == 1) { q = a.Divide(b); r = a.Subtract(q.Multiply(b)); x = x2.Subtract(q.Multiply(x1)); y = y2.Subtract(q.Multiply(y1)); a = b; b = r; x2 = x1; x1 = x; y2 = y1; y1 = y; } d = a; x = x2; y = y2; return(new Tuple <BigInteger, BigInteger>(x, y)); }
private static BigInteger Sqrt(BigInteger number) { // https://social.msdn.microsoft.com/Forums/ru-RU/f9aca8c2-af21-40e4-b5bb-c9613b9db4ca/-biginteger?forum=fordesktopru. var root = number; int bitLength = 1; while (root / 2 != 0) { root /= 2; bitLength++; } bitLength = (bitLength + 1) / 2; root = number >> bitLength; var lastRoot = BigInteger.Zero; do { lastRoot = root; root = (BigInteger.Divide(number, root) + root) >> 1; }while (!((root ^ lastRoot).ToString() == "0")); return(root); }
// факторизация N при близко расположенных p и q static Tuple <BigInteger, BigInteger> FermatFactoringMethod(BigInteger n) { #region optimized /* * BigInteger x = BigIntSqrt(n).Add(BigInteger.One); * BigInteger Bsq = x.Multiply(x).Subtract(n); * BigInteger y = BigIntSqrt(Bsq); * BigInteger XsubY = x.Subtract(y); * * // c is a chosen bound which controls when Fermat stops * BigInteger c = new BigInteger("30"); * BigInteger XsubY_prev = x.Subtract(y).Add(c); * BigInteger result = null; * * while (!BigIntSqrt(Bsq).Pow(2).Equals(Bsq) && XsubY_prev.Subtract(XsubY).CompareTo(c) > -1) * { * x = x.Add(BigInteger.One); * Bsq = x.Multiply(x).Subtract(n); * * y = BigIntSqrt(Bsq); * XsubY_prev = XsubY; * XsubY = x.Subtract(y); * } * * if (BigIntSqrt(Bsq).Pow(2).Equals(Bsq)) * { * result = XsubY; * } * * // Trial Division * else * { * bool solved = false; * BigInteger p = XsubY.Add(BigInteger.Two); * * if (p.Remainder(BigInteger.Two).IntValue == 0) * { * p = p.Add(BigInteger.One); * } * while (!solved) * { * p = p.Subtract(BigInteger.Two); * if (n.Remainder(p).Equals(BigInteger.Zero)) * { * solved = true; * } * } * * result = p; * }*/ #endregion BigInteger result = BigInteger.Zero; //BigInteger x = BigIntSqrt(n).Add(BigInteger.One); BigInteger x = BigIntSqrt(n); BigInteger k = BigInteger.One; BigInteger y = x.Add(k).Pow(2).Subtract(n); BigInteger ysq = BigIntSqrt(y); BigInteger temp = BigInteger.Zero; while (!ysq.Pow(2).Equals(y)) { k = k.Add(BigInteger.One); y = (x.Add(k)).Square().Subtract(n); ysq = BigIntSqrt(y); } if (ysq.Pow(2).Equals(y)) { temp = x.Add(k); result = temp.Subtract(ysq); } return(new Tuple <BigInteger, BigInteger>(result, n.Divide(result))); }