def factorize_n(pub_k, priv_k): n, d = priv_k _, e = pub_k tmp = e * d - 1 s = 0 t = None while True: if tmp % 2 == 0: tmp = tmp // 2 s += 1 else: t = tmp break a = random(2, n) if gcd(a, n) > 1: return a v = bin_pow(a, t, n) if v == 1: return None while v % n != 1: v0 = v % n v = bin_pow(v, 2, n) if v0 % n == -1: return None else: return gcd(v0 + 1, n)
def encrypt(pub_key, M): p, g, y = pub_key z = random(1, p - 1) c1 = bin_pow(g, z, p) c2 = M * bin_pow(y, z, p) C = [c1, c2] return C
def encrypt(public_key, M): ec, p, point, Q = public_key Pm = message_to_point(M, ec) y = random(0, p + 1 - (int(2 * sqrt(p)))) C1 = multiply_point(point, y, ec) C2 = sum_ec_points(Pm, multiply_point(Q, y, ec), ec) return [C1, C2]
def generate_keys(ec): A, B, p = ec point = rand_ec_point(ec) # Hasse's theorem x = random(0, p + 1 - (int(2 * sqrt(p)))) Q = multiply_point(point, x, ec) return {"pub": [ec, p, point, Q], "priv": [ec, p, point, Q, x]}
def is_prime(x): if x == 1: return False if x == 2 or x == 3: return True for _ in range(0, 32): # The a values 1 and n-1 are not used as the equality holds for # all n and all odd n respectively, hence testing them # adds no value. if x > 4: a = random(2, x - 2) else: a = random(2, x) if bin_pow(a, x - 1, x) != 1: return False return True
def generate_ec(p=None): if p is None: BIT_NUM = 300 while True: k = randkbits(BIT_NUM) p = 4 * k + 3 if is_prime(p): break while True: A = random(0, p) B = random(0, p) delta = ec_delta(A, B, p) if delta != 0: return (A, B, p)
def message_to_point(M, curve): global u A, B, p = curve u = random(30, 51) for j in range(1, u + 1): x = (M * u + j) % p f = (x * x * x + A * x + B) % p if legendre(f, p) == 1: y = sqrt(f, p) return (x, y)
def rand_ec_point(curve): A, B, p = curve if ec_delta(*curve) == 0: raise Exception("Invalid input") while True: x = random(0, p) f = calc_ec(curve, x) if legendre(f, p) != -1: break y = sqrt(f, p) return (x, y)
def generate_keys(): p = None q = None g = None while True: num = randkbits(1024) if is_prime(num) and is_prime(2 * num + 1): q = num p = 2 * num + 1 print(q, p) while True: g = random(1, p - 1) x = bin_pow(g, q, p) if x != 1: y = bin_pow(g, x, p) return {"public": (p, g, y), "private": (x, p)}
def generate_keys(): p = generate_prime() q = None e = None while True: q = generate_prime() if p != q: break n = p * q fi = (p - 1) * (q - 1) l = max(p - 1, q - 1) while True: e = random(l + 1, fi) if is_prime(e): break d = reverse(e, fi) return {"public": (n, e), "private": (n, d)}