def __mul__(self, k): """ point multiplication uses Jacobian coordinates internally for speedup """ if state.precompute: cost_results.CostSystem.costs["theoretical"]["setup"][ "accumulated"](EC_Mul=1) else: cost_results.CostSystem.costs["theoretical"]["online"][ "accumulated"](EC_Mul=1) if self.infinity: return ECPoint(0, 0, self.EC, True) if k == 1: return self if k == 2: # point doubling with affine coordinates if self.y == 0: #then we get the infinity point return ECPoint(0, 0, self.EC, True) s = gmpy.divm(3 * pow(self.x, 2, self.p) + self.EC.a, 2 * self.y, self.p) xn = (pow(s, 2, self.p) - (2 * self.x)) % self.p yn = (-self.y + s * (self.x - xn)) % self.p return ECPoint(xn, yn, self.EC) pc = (0, 0, 1) for bit in gmpy.digits(k, 2): pc = self._doubleP(pc) if bit == "1": pc = self._addP(pc) x = gmpy.divm(pc[0], pow(pc[2], 2, self.p), self.p) y = gmpy.divm(pc[1], pow(pc[2], 3, self.p), self.p) return ECPoint(x, y, self.EC)
def elemop(N=1000): r''' (Takes about 40ms on a first-generation Macbook Pro) ''' for i in range(N): assert a + b == 579 assert a - b == -333 assert b * a == a * b == 56088 assert b % a == 87 assert divmod(a, b) == (0, 123) assert divmod(b, a) == (3, 87) assert -a == -123 assert pow(a, 10) == 792594609605189126649 assert pow(a, 7, b) == 99 assert cmp(a, b) == -1 assert '7' in str(c) assert '0' not in str(c) assert a.sqrt() == 11 assert _g.lcm(a, b) == 18696 assert _g.fac(7) == 5040 assert _g.fib(17) == 1597 assert _g.divm(b, a, 20) == 12 assert _g.divm(4, 8, 20) == 3 assert _g.divm(4, 8, 20) == 3 assert _g.mpz(20) == 20 assert _g.mpz(8) == 8 assert _g.mpz(4) == 4 assert a.invert(100) == 87
def elemop(N=1000): r''' (Takes about 40ms on a first-generation Macbook Pro) ''' for i in range(N): assert a+b == 579 assert a-b == -333 assert b*a == a*b == 56088 assert b%a == 87 assert divmod(a, b) == (0, 123) assert divmod(b, a) == (3, 87) assert -a == -123 assert pow(a, 10) == 792594609605189126649 assert pow(a, 7, b) == 99 assert cmp(a, b) == -1 assert '7' in str(c) assert '0' not in str(c) assert a.sqrt() == 11 assert _g.lcm(a, b) == 18696 assert _g.fac(7) == 5040 assert _g.fib(17) == 1597 assert _g.divm(b, a, 20) == 12 assert _g.divm(4, 8, 20) == 3 assert _g.divm(4, 8, 20) == 3 assert _g.mpz(20) == 20 assert _g.mpz(8) == 8 assert _g.mpz(4) == 4 assert a.invert(100) == 87
def hack(self): print "[*] Initialized Elgamal ..." t = 0 t_ = 0 flag = 0 # First select two sigs which are valid and have the same r for i in range(len(self.sigs)): t = self.sigs[i] for j in range(i + 1, len(self.sigs)): t_ = self.sigs[j] if t["r"] != t_["r"]: continue if not self.verify(j) or not self.verify(i): continue flag = 1 break if flag == 1: break if flag == 0: print "[X] Signatures are secure" sys.exit(2) print "[*] Found sigs with common r! Trying to break." s1 = t["s"] s2 = t_["s"] m1 = int(hashlib.sha384(t["m"]).hexdigest(), 16) m2 = int(hashlib.sha384(t_["m"]).hexdigest(), 16) m1_m2 = m1 - m2 n = daedmath.euclid(s1 - s2, self.safeprime -1) k_ = gmpy.divm(m1_m2 / n, (s1 - s2) / n, (self.safeprime-1)/n) k = None for i in range(0, n): k = k_ + (i * (self.safeprime - 1) / n) if pow(self.generator, k, self.safeprime) == t["r"]: break if not k: print "[X] Failed to get a valid k!" sys.exit(2) print "[*] Found k: %d" % k n = daedmath.euclid(t["r"], self.safeprime - 1) side2 = m1 - k * t["s"] x_ = gmpy.divm(side2/n, t["r"]/n, (self.safeprime - 1) / n) x = None for i in range(0, n): x = x_ + (i * (self.safeprime - 1) / n) if pow(self.generator, x, self.safeprime) == self.pubkey: break if x: print "[*] Retrieved Private Key x: %d" % x else: print "[X] Unable to calculate x!"
def hack(self): print "[*] Initialized Elgamal ..." t = 0 t_ = 0 flag = 0 # First select two sigs which are valid and have the same r for i in range(len(self.sigs)): t = self.sigs[i] for j in range(i + 1, len(self.sigs)): t_ = self.sigs[j] if t["r"] != t_["r"]: continue if not self.verify(j) or not self.verify(i): continue flag = 1 break if flag == 1: break if flag == 0: print "[X] Signatures are secure" sys.exit(2) print "[*] Found sigs with common r! Trying to break." s1 = t["s"] s2 = t_["s"] m1 = int(hashlib.sha384(t["m"]).hexdigest(), 16) m2 = int(hashlib.sha384(t_["m"]).hexdigest(), 16) m1_m2 = m1 - m2 n = daedmath.euclid(s1 - s2, self.safeprime - 1) k_ = gmpy.divm(m1_m2 / n, (s1 - s2) / n, (self.safeprime - 1) / n) k = None for i in range(0, n): k = k_ + (i * (self.safeprime - 1) / n) if pow(self.generator, k, self.safeprime) == t["r"]: break if not k: print "[X] Failed to get a valid k!" sys.exit(2) print "[*] Found k: %d" % k n = daedmath.euclid(t["r"], self.safeprime - 1) side2 = m1 - k * t["s"] x_ = gmpy.divm(side2 / n, t["r"] / n, (self.safeprime - 1) / n) x = None for i in range(0, n): x = x_ + (i * (self.safeprime - 1) / n) if pow(self.generator, x, self.safeprime) == self.pubkey: break if x: print "[*] Retrieved Private Key x: %d" % x else: print "[X] Unable to calculate x!"
def generate_d(self, results): self.function_count[15] += 1 l_tot = results[0].value % self.e #print "l_tot = " + str(l_tot) try: zeta = gmpy.divm(1, l_tot, self.e) except: print "not invertable mod e" self.generate_p() #print "zeta (inv) = " + str(zeta) self.d = int(-(zeta * self.phi_i) / self.e) print "self.p = " + str(self.p) print "self.q = " + str(self.q) print "self.d = " + str(self.d) print "self.e = " + str(self.e) print "N (public) = " + str(self.n_revealed) print "Total bits in N = " + str(math.log(self.n_revealed, 2)) base = gmpy.mpz(self.m) power = gmpy.mpz(self.e) modulus = gmpy.mpz(self.n_revealed) self.c = int(pow(base, power, modulus)) print ">> self.cypher = " + str(self.c) if self.runtime.id == 1: self.c = gmpy.divm(1, self.c, self.n_revealed) base = gmpy.mpz(self.c) if self.runtime.id == 1: power = gmpy.mpz(-self.d) else: power = gmpy.mpz(self.d) modulus = gmpy.mpz(self.n_revealed) self.decrypt = int(pow(base, power, modulus)) print "self.decrypt (c^di mod N) = " + str(self.decrypt) c1, c2, c3 = self.runtime.shamir_share([1, 2, 3], self.Zp, self.decrypt) open_c1 = self.runtime.open(c1) open_c2 = self.runtime.open(c2) open_c3 = self.runtime.open(c3) results = gather_shares([open_c1, open_c2, open_c3]) results.addCallback(self.check_decrypt)
def decrypt_benchmark(self): self.decrypt_time1 = time.clock() base = gmpy.mpz(self.m) power = gmpy.mpz(self.e) modulus = gmpy.mpz(self.n_revealed) self.c = int(pow(base, power, modulus)) if self.runtime.id == 1: self.c = gmpy.divm(1, self.c, self.n_revealed) base = gmpy.mpz(self.c) if self.runtime.id == 1: power = gmpy.mpz(-self.d) else: power = gmpy.mpz(self.d) modulus = gmpy.mpz(self.n_revealed) self.decrypt = int(pow(base, power, modulus)) c1, c2, c3 = self.runtime.shamir_share([1, 2, 3], self.Zp, self.decrypt) c_tot = c1 * c2 * c3 open_c_tot = self.runtime.open(c_tot) results = gather_shares([open_c_tot]) results.addCallback(self.check_decrypt_benchmark)
def main(): tn = telnetlib.Telnet("54.64.40.172",5454) for i in range(10): ret = tn.read_until("\n") ret2 = tn.read_until("\n") ret3 = tn.read_until("\n") print ret[:-1] print ret2[:-1] print ret3[:-1] n = int(ret[:-1]) c1 = int(ret2) c2 = int(ret3) f = (c2 + 2*c1 -1) % n g = (c2 - c1 +2) % n m = gmpy.divm(f,g,n) print '\nsending: ',m tn.write(str(m)+"\n") feedback = tn.read_until("\n") print feedback print m print "" print hex(int(m)).rstrip("L").lstrip("0x").decode("hex")
def q4(N, p, q): c = gmpy.mpz( "22096451867410381776306561134883418017410069787892831071731839143676135600120538 \ 00428232965047350942434394621975151225646583996794288946076454204058156474898801 \ 37348641204523252293201764879166664029975091887299716905260832220677716000193292 \ 60870009579993724077458967773697817571267229951148662959627934791540" ) e = gmpy.mpz("65537") phi = (p - 1) * (q - 1) d = gmpy.divm(1, e, phi) assert (e * d) % phi == 1 m = power_mod(c, d, N) assert power_mod(m, e, N) == c #print "M = ", m hexstring = hex(m) #print len(hexstring), hexstring hexstring = hexstring.split('00')[1] #print len(hexstring) plaintext = hexstring.decode('hex') print "Answer to Question 4:" print plaintext # Answer: assert plaintext == "Factoring lets us break RSA."
def power_mod(b,e,n): """power_mod(b,e,n) computes the eth power of b mod n. (Actually, this is not needed, as pow(b,e,n) does the same thing for positive integers. This will be useful in future for non-integers or inverses.)""" if e<0: # Negative powers can be computed if gcd(b,n)=1 e = -e b = gmpy.divm(1,b,n) accum = 1; i = 0; bpow2 = b while ((e>>i)>0): if((e>>i) & 1): accum = (accum*bpow2) % n bpow2 = (bpow2*bpow2) % n i+=1 return accum
def __add__(self, X): if X == self: return X * 2 if self.infinity: return X if X.infinity: return self d = self.x - X.x if d == 0: #Then the point is infinity return ECPoint(0, 0, self.EC, True) s = gmpy.divm(self.y - X.y, d, self.p) xn = (pow(s, 2, self.p) - self.x - X.x) % self.p yn = (-self.y + s * (self.x - xn)) % self.p return ECPoint(xn, yn, self.EC)
def decrypt(self, c): """Decrypt ciphertext c. :returns: plaintext :rtype: int """ assert isinstance(c, ElgamalCiphertext) g = self.G[0] p = self.G[1] c1 = c.c1 c2 = c.c2 c1_prime = pow(c1, self.x, p) g_m = gmpy.divm(c2, c1_prime, p) m = dLog(p, g, g_m) return m
def check_g(self, results): self.function_count[10] += 1 #print "g = " + str(results[0].value) self.g = results[0].value jacobi = gmpy.jacobi(self.g, self.n_revealed) % self.n_revealed #print "jacobi = " + str(jacobi) if jacobi == 1: if self.runtime.id == 1: self.phi_i = self.n_revealed - self.p - self.q + 1 print "((N)): " + str(self.n_revealed) print "((p)): " + str(self.p) print "((q)): " + str(self.q) print "<<phi_i>>: " + str(self.phi_i) base = gmpy.mpz(self.g) power = gmpy.mpz(self.phi_i / 4) print "<<power>>: " + str(power) modulus = gmpy.mpz(self.n_revealed) self.v = int(pow(base, power, modulus)) #self.v = self.powermod(self.g, (self.n_revealed - self.p - self.q + 1) / 4, self.n_revealed) else: self.phi_i = -(self.p + self.q) self.inverse_v = int(gmpy.divm(1, self.g, self.n_revealed)) base = gmpy.mpz(self.inverse_v) power = gmpy.mpz(-self.phi_i / 4) modulus = gmpy.mpz(self.n_revealed) self.v = int(pow(base, power, modulus)) #print "self.phi_i = " + str(self.phi_i) else: self.generate_g() return #print "self.v = " + str(self.v) v1, v2, v3 = self.runtime.shamir_share([1, 2, 3], self.Zp, self.v) v_tot = v1 * v2 * v3 self.open_v = self.runtime.open(v_tot) results = gather_shares([self.open_v]) results.addCallback(self.check_v)
def main(): p = gmpy.mpz("134078079299425970995740249982058461274793658205923933 \ 77723561443721764030073546976801874298166903427690031 \ 858186486050853753882811946569946433649006084171") g = gmpy.mpz("11717829880366207009516117596335367088558084999998952205 \ 59997945906392949973658374667057217647146031292859482967 \ 5428279466566527115212748467589894601965568") h = gmpy.mpz("323947510405045044356526437872806578864909752095244 \ 952783479245297198197614329255807385693795855318053 \ 2878928001494706097394108577585732452307673444020333") ####### Find x such that h = g**x (mod p) # Also given, 1 <= x <= 2**40 B = gmpy.mpz(2**20) # Let x = B*x0 + x1, where x0, x1 < B # h / g**x1 == (g**B)**x0 in Zp x = None hash_table = dict() for x1 in range(0, B): #q, r = gmpy.fdivmod(g**x1,p) r = power_mod(g, x1, p) n = gmpy.divm(h, r, p) hash_table[n] = x1 g_pow_B = power_mod(g, B, p) for x0 in range(0, B): key = power_mod(g_pow_B, x0, p) if key in hash_table: x1 = hash_table[key] x = x0*B + x1 break assert x assert h == power_mod(g, x, p) print "x = Dlog of h to the base g in Zp = ", x
def signature(self, message): if self.runtime.id == 1: message = gmpy.divm(1, message, self.n_revealed) base = gmpy.mpz(message) if self.runtime.id == 1: power = gmpy.mpz(-self.d) else: power = gmpy.mpz(self.d) modulus = gmpy.mpz(self.n_revealed) c_i = int(pow(base, power, modulus)) c1, c2, c3 = self.runtime.shamir_share([1, 2, 3], self.Zp, c_i) c_tot = c1 * c2 * c3 open_c_tot = self.runtime.open(c_tot) results = gather_shares([open_c_tot]) results.addCallback(self.check_signature)
def decrypt(self, c): assert isinstance( c, El_Gamal_Ciphertext), "c does not seems to be a ciphertext" g = self.G[0] p = self.G[1] def dLog(g, g_m): a = 1 i = 0 while i < 2**20: if a == g_m: return i else: a = a * g % p i += 1 return None # no DLog < 2**20 found c1 = c.c1 c2 = c.c2 c1_prime = pow(c1, self.x, p) g_m = gmpy.divm(c2, c1_prime, p) m = dLog(g, g_m) return m
def decrypt(self, c): assert isinstance(c, El_Gamal_Ciphertext) g = self.G[0] p = self.G[1] def dLog(g, g_m): #TODO: optimize this a = 1 i = 0 while i < 2**20: if a == g_m: return i else: a = a * g % p i += 1 return None # no DLog < 2**32 found c1 = c.c1 c2 = c.c2 c1_prime = pow(c1, self.x, p) g_m = gmpy.divm(c2, c1_prime, p) m = dLog(g, g_m) return m
def deal_n(pos, deck_size, n): # new_pos = (n * pos) % deck_size x = int(gmpy.divm(pos, n, deck_size)) # while (n * x) % deck_size != pos: # x += 1 return x
def modinv(e, n): try: from gmpy import divm except: from gmpy2 import divm return int(divm(1, e, n))
b = [ 15914389274045831441, 12471333000718257439, 11189085043185963643, 14953553045254805869, 16969044464796096757, 12219369241978883401, 11051035063490494121, 12446419077417014895, 17033822019842116078, 9516363895804911673, 15079736889469193431, 10650632135951148921, 17812647846133398533, 11412472367550805013, 9778393688778074575, 16630642531754496501, 9364964556418467329, 14097382369878612419, 10512797518085747507, 15943449689777265613, 18324134584075223407, 11593718893451959913, 14797616246348898583, 10888050221402213645, 15964574501738046999, ] import gmpy for i in range(0, len(a)): print chr(gmpy.divm(f[i], a[i], b[i]) % 256),
(151, 7), (157, 4), (163, 8), (167, 2), (173, 2), (179, 8), (181, 3), (191, 13), (197, 5), (211, 13), (223, 13), (227, 4), (229, 4), (233, 4), (239, 7), (241, 4), (251, 8), (257, 2)] pairs = [] for p, k in factors: n = pow(p, k) phi = pow(p, k) - pow(p, k - 1) d = gmpy.divm(1, e, phi) m = pow(c, d, n) pairs.append((m, n)) m, _ = crt(pairs) print(bytes.fromhex(hex(m)[2:]))