You've stumbled onto a significant vulnerability in a commonly used cryptographic library. It turns out that the random number generator it uses frequently produces the same primes when it is generating keys.
Exploit this knowledge to factor the (hexadecimal) keys below, and enter your answer as the last six digits of the largest factor you find (in decimal).
Key 1:
1c7bb1ae67670f7e6769b515c174414278e16c27e95b43a789099a1c7d55c717b2f0a0442a7d49503ee09552588ed9bb6eda4af738a02fb31576d78ff72b2499b347e49fef1028182f158182a0ba504902996ea161311fe62b86e6ccb02a9307d932f7fa94cde410619927677f94c571ea39c7f4105fae00415dd7d
Key 2:
2710e45014ed7d2550aac9887cc18b6858b978c2409e86f80bad4b59ebcbd90ed18790fc56f53ffabc0e4a021da2e906072404a8b3c5555f64f279a21ebb60655e4d61f4a18be9ad389d8ff05b994bb4c194d8803537ac6cd9f708e0dd12d1857554e41c9cbef98f61c5751b796e5b37d338f5d9b3ec3202b37a32f
This section requires Javascript.
You are seeing this because something didn't load right. We suggest you, (a) try
refreshing the page, (b) enabling javascript if it is disabled on your browser and,
finally, (c)
loading the
non-javascript version of this page
. We're sorry about the hassle.
Python code :
def gcd(a, b):
while b:
a, b = b, a%b
return a
x = int('1c7bb1ae67670f7e6769b515c174414278e16c27e95b43a789099a1c7d55c717b2f0a0442a7d49503ee09552588ed9bb6eda4af738a02fb31576d78ff72b2499b347e49fef1028182f158182a0ba504902996ea161311fe62b86e6ccb02a9307d932f7fa94cde410619927677f94c571ea39c7f4105fae00415dd7d', 16)
y = int('2710e45014ed7d2550aac9887cc18b6858b978c2409e86f80bad4b59ebcbd90ed18790fc56f53ffabc0e4a021da2e906072404a8b3c5555f64f279a21ebb60655e4d61f4a18be9ad389d8ff05b994bb4c194d8803537ac6cd9f708e0dd12d1857554e41c9cbef98f61c5751b796e5b37d338f5d9b3ec3202b37a32f', 16)
print (gcd(x, y))
which prints 8 4 7 1 2 4 5 5 3 2 9 4 5 8 4 7 2 2 1 0 4 7 5 0 9 2 5 7 2 6 7 8 5 0 9 5 2 6 2 7 2 7 0 8 9 9 3 4 0 4 5 7 4 2 3 1 9 3 3 2 6 2 9 6 3 2 7 4 9 6 2 3 6 4 4 4 3 7 8 9 5 1 0 7 4 2 3 2 8 4 9 6 3 3 3 7 8 2 1 5 6 3 9 8 3 1 6 8 3 2 4 4 7 1 6 0 7 4 0 3 2 6 1 9 3 1 6 5 8 2 1 3 4 1 0 7 0 2 6 5 8 5 8 6 1 6 4 6 7 . Thus, the answer is 6 1 6 4 6 7 .
Your solution is not quite complete: although the answer is right, you don't check the possibility that the largest factor (which is what you're asked to find) might not be the common one, but one of the others. This can be fixed by assigning gcd(x, y) to a variable, for example, g, and then printing max(g, x // g, y // g).
Yes and no. You're right that it says "largest factor" not "largest common factor". But if you don't assume that "largest common factor" was meant, then wouldn't Key 2 itself be the "largest factor"?
people, plz scroll towards right to see the full answer... and as the question says,
last 6 digits is the final answer.
The solution using a built-in library
from fractions import gcd
k1 = int("1c7bb1ae67670f7e6769b515c174414278e16c27e95b43a789099a1c7d55c717b2f0a0442a7d49503ee09552588ed9bb6eda4af738a02fb31576d78ff72b2499b347e49fef1028182f158182a0ba504902996ea161311fe62b86e6ccb02a9307d932f7fa94cde410619927677f94c571ea39c7f4105fae00415dd7d",16)
k2 = int("2710e45014ed7d2550aac9887cc18b6858b978c2409e86f80bad4b59ebcbd90ed18790fc56f53ffabc0e4a021da2e906072404a8b3c5555f64f279a21ebb60655e4d61f4a18be9ad389d8ff05b994bb4c194d8803537ac6cd9f708e0dd12d1857554e41c9cbef98f61c5751b796e5b37d338f5d9b3ec3202b37a32f",16)
g = gcd(k1,k2)
print str(max(g, k1//g, k2//g))[-6:]
Using the fact that key1 = a b and key2 = b c (one common prime factor) we need to find the last 6 digits of b. And b = gdc(key1, key2).
import java.math.BigInteger;
public class RSA {
public static void main(String[] args) {
BigInteger a = new BigInteger("1c7bb...", 16);
BigInteger b = new BigInteger("2710e...", 16);
System.out.println(a.gcd(b).mod(new BigInteger("1000000")));
}
}
Here's the solution in C++ , the hint was that one of the factors of both numbers is same.
#include <iostream>
#include <gmpxx.h>
int main()
{
mpz_class a,b,cf,f1,f2;
a = "0x1c7bb1ae67...7f94c571ea39c7f4105fae00415dd7d";
b = "0x2710e45014...796e5b37d338f5d9b3ec3202b37a32f";
mpz_gcd(cf.get_mpz_t(),a.get_mpz_t(),b.get_mpz_t());
f1 = a/cf; //actually calculating f1 and f2 is unnecessary,
f2 = b/cf; //as it comes out cf is the largest factor any way.
std::cout << std::max(cf,std::max(f1,f2))%1000000 << std::endl;
}
Problem Loading...
Note Loading...
Set Loading...
Let's call the given keys a and b . Let's assume each key is a product of two primes (like it is in RSA), so a = p q and b = r s . Since we know the generator is flawed, both keys probably share at least one prime factor, so let's say s = q , then a = p q and b = q r . If p and r are distinct primes, this means g c d ( a , b ) = q .
We can easily calculate the GCD of a and b using Euclid's algorithm ( a , b ← b , a m o d b until b = 0 , then a is the GCD), and the answer is 8 4 7 … 6 1 6 4 6 7 . So we've only got to choose the biggest number between q , p and r . q = 8 4 7 … 6 1 6 4 6 7 , r = q a = 3 4 3 … 7 3 4 1 2 7 , l = q b = 4 6 1 … 6 1 6 4 3 7 . q turns out to be the biggest number of them all, so 6 1 6 4 7 it is.