def main(): c = 3082489874584540355861976440154957444349802968606358209180310319846045010290428219945114844043901302597650924982910286231671337430936664185809669066762817535499514756463968189674472801536320141026694560204079394058935377378137004712487812117718010360346278762378192809353855702825349327607244514852447790414426389507325928721778099789473656709278135098915643867190345991798884214391389207351837734104494534915592459046635480167584016281186038004020937047971991512996625468347184973943467542720967761335734799148698672931984386755418194996569343120441376243026639952906891084792796113007934063427372263145841708494015 e = 65537 n = 4835750187736017002199910402633824276307631898091000077771942652114774929553132338780864979244300002934950340799255707706719068807452407480611171357191437808195657961280485410190950021251938036710663784185407986885413060120305830667265752106891991907683349203859430029804970061705163529856022394765039070626284349963490115392327176993981111921903099443600754324722527818078282290124479202829123212555658572674854964849787146566576353289029751920324001899153487870430173605050309512383603908334958874100463419711909679461073160404554664143408055364570826428967757690953156967295496007885336849722190950712736684455537 factor_list = fermat_factorization(n) print(factor_list) [X1, Y1] = factor_list[0] [X2, Y2] = factor_list[1] assert X1 * Y1 == n assert X2 * Y2 == n #p1 = GCD(X1, X2) #p2 = X1 / p1 #q1 = GCD(Y1, Y2) #q2 = Y1 / q1 p1 = GCD(X1,X2) q1 = X1//p1 p2 = GCD(Y1,Y2) q2 = Y1//p2 phi = (p1 - 1) * (q1 - 1) * (p2 - 1) * (q2 - 1) d = inverse(e, phi) flag = l2b(pow(c, d, n)) print(flag)
def generate_keypair(self): # https://www.swarthmore.edu/NatSci/echeeve1/Ref/BinaryMath/BinaryMath.html p_size = self.security // 2 q_size = self.security - p_size p, q = int(getPrime(p_size)), int(getPrime(q_size)) if p == q: raise ValueError('p and q cannot be equal') # n = pq n = p * q # Totient of n phi = (p - 1) * (q - 1) # Choose an integer e such that e and phi(n) are coprime e = random.randrange(1, phi) if self.echo: print("Klucz publiczny: \n", e) # Use Euclid's Algorithm to verify that e and phi(n) are comprime g = GCD(e, phi) while g != 1: e = random.randrange(1, phi) g = GCD(e, phi) if self.echo: print("Test e*d == 1 OK") # Use Extended Euclid's Algorithm to generate the private key d = inverse(e, phi) if self.echo: print("Klucz prywatny: \n", d) # Return public and private keypair # Public key is (e, n) and private key is (d, n) self.public = namedtuple('public_key', ['e', 'n'])(e=e, n=n) self.private = namedtuple('private_key', ['d', 'n'])(d=d, n=n)
def main(): c = 5333020300559057627358629150444779517927607675346073210522985591749203153560945527905471617055390862832090724275674301850841328746015818539999254106959583022492771703624475944141387595460858005483478153896882057074736219148307775833908988111821196571444363406298895482129627722808797729608415039516568435053064741173178431954979628184113077609472474158501321140759120865933591449468716625271915315192237652960416609140093720936411488882176262245872088399590046010317722025560167003681009206835834580085250672176381127010208394234527481235534697123574687573506314887709574961111534684456158044614521548036760981001130 e = 65537 n = 7661893861079288704612324056824281971553256849386803241531603299789846141029329254547934930958439426559413588181586850979797598156981380154181904473913556755982046171992133300178070732688527462379925496142741944410278173915503007594075131197019636352126219973024134086516300904590025630353490746964989205729428932590318185431652353310237407006739807162337887502047657095011822728581616805184689818928930804574318013115689430260450572839060904176023480504876807310962105063058782417722431654669730509157358979892491644691833798706704808468441748166558510311296180338934849110001861689206816856832238128874896790516637 factor_list = fermat_factorization(n) print(factor_list) [X1, Y1] = factor_list[0] [X2, Y2] = factor_list[1] assert X1 * Y1 == n assert X2 * Y2 == n #p1 = GCD(X1, X2) #p2 = X1 / p1 #q1 = GCD(Y1, Y2) #q2 = Y1 / q1 p1 = GCD(X1, X2) q1 = X1 / p1 p2 = GCD(Y1, Y2) q2 = Y1 / p2 phi = (p1 - 1) * (q1 - 1) * (p2 - 1) * (q2 - 1) d = inverse(e, phi) flag = l2b(pow(c, d, n)) print(flag)
def genrsa(s): e = 65537 while True: r = randint(0, 4**s) p = next_prime(r) q = next_prime(r + randint(1, 2**s)) if GCD(p - 1, e) == GCD(q - 1, e) == 1: return p * q, 2 * e
def getCoprimes(e = 65537): bitSize = 512 p1, p2 = -1, -1 while p1 == p2: p1 = getStrongPrime(bitSize, e) p2 = getStrongPrime(bitSize, e) assert(GCD(e, p1 - 1) == 1) assert(GCD(e, p2 - 1) == 1) return p1, p2
def solve_key(): global RES, MOD, LST cnt = 0 while True: cnt += 1 print("cnt:", cnt) # myy^2 = myx^3 - 3 myx + b (in secp256r1) # myy^2 = myx^3 - 3 myx + ?? (in "secp224r1") # that curve must have small order u = rand.randint(0, 1 << 223) v = rand.randint(0, 1 << 223) b = (v * v - u * u * u + 3 * u) % p224 E = EllipticCurve(GF(p224), [-3, b]) ORD = E.order() for i in range(300, 1000): if isPrime(i) and MOD % i != 0 and ORD % i == 0: GG = None while True: G = E.random_point() GG = (ORD // i) * G if GG != GG + GG: break myx = int(crt(X256, int(GG.xy()[0]), p256, p224)) myy = int(crt(Y256, int(GG.xy()[1]), p256, p224)) params = [] print(i) for j in range(1, i // 2 + 1): CC = j * GG shared = int(CC.xy()[0]) params.append((myx, myy, shared, j)) ex = False pool = mp.Pool(12) for result in pool.imap_unordered(run_session_brute, params): if result != None: ex = True RES = int(crt(RES, result, MOD, i)) MOD = MOD * i // GCD(MOD, i) LST.append((result, i)) break if ex == False: RES = int(crt(RES, 0, MOD, i)) MOD = MOD * i // GCD(MOD, i) LST.append((0, i)) print(MOD) print(LST) print(RES) print(MOD) print(LST) if MOD >= (1 << 224): break
def gen_key(bits=2048): x = RSA.generate(bits) n = x.n n2 = pow(n, 2) while True: g = getRandomInteger((n.bit_length() * 2) - 1) lm = ((x.p - 1) * (x.q - 1)) // GCD(x.p - 1, x.q - 1) glm = pow(g, lm, n2) a = (glm - 1) // n if GCD(a, n) == 1: mu = inverse(a, n) public_key = (n, g) secret_key = (lm, mu) return public_key, secret_key
def extract_pq_from_edn(e, d, n): k = d * e - 1 t = 0 r = k while r % 2 != 1: r //= 2 t += 1 if t == 0: return None, None for i in range(100): FIN = 0 g = random.randint(0, n - 1) y = pow(g, r, n) if y == 1 or y == n - 1: continue for j in range(t): x = pow(y, 2, n) if x == 1: FIN = 2 break if x == n - 1: FIN = 1 break y = x if FIN == 1: continue if FIN == 2: break x = pow(y, 2, n) if x == 1: break p = GCD(y - 1, n) q = n // p return p, q
def _encrypt(self, data): p = int(self.key.p) while 1: k = random.randint(1, p - 1) if GCD(k, p - 1) == 1: break encrypted = [self.key.publickey().encrypt(i, k) for i in data] return encrypted
def check_secret(secret): assert secret.bits == 512 assert secret.p.bit_length() == secret.bits assert secret.q.bit_length() == secret.bits assert secret.e < secret.bits assert isPrime(secret.p) and isPrime(secret.q) assert GCD(secret.e, (secret.p - 1) * (secret.q - 1)) == 1
def sign(self, m): p, q, u = 1, 1, 1 while p * q != self.n: p = self._db.load('p') q = self._db.load('q') while u * p % q != 1: u = self._db.load('u') while True: dp = self._db.load('dp') dq = self._db.load('dq') s1 = pow(m, dp, p) s2 = pow(m, dq, q) h = s2 - s1 if h < 0: h = h + q h = h * u % q s = h * p + s1 # Avoid fault if GCD(pow(s, self.e, self.n) - m, self.n) not in [p, q]: return s
def main(args): pubkey1 = RSA.import_key(args.k1.read()) pubkey2 = RSA.import_key(args.k2.read()) c1 = b64decode(args.c1.read()) c1 = bytes_to_long(c1) c2 = b64decode(args.c2.read()) c2 = bytes_to_long(c2) # We first check that the modulus N of both public keys are equal if pubkey1.n != pubkey2.n: sys.stderr.write( "[ERROR] The modulus of both public keys must be the same\n") sys.exit(1) if GCD(pubkey1.e, pubkey2.e) != 1: sys.stderr.write( "[ERROR] The greatest common denominator between the exponent of each keys should be 1\n" ) sys.exit(2) deciphered_message = common_modulus(pubkey1.e, pubkey2.e, pubkey1.n, c1, c2) deciphered_bytes = long_to_bytes(deciphered_message) print("[+] Recovered message:") print(deciphered_message) print("[+] Recovered bytes:") print(deciphered_bytes) if args.o: args.o.write(deciphered_bytes)
def sign(self, m): """ *Step-1*: Calculate hash of the message to be signed """ e = sha256(m).digest() """ *Step-2*: Compute `z` as the `Ln` left most bits of `e`, `Ln` is the bit length of group order `n` """ Ln = len(bin(self.n)[2:]) z = bytes_to_long(slice_string(e, Ln)) """ *Step-3*: Generate a random number `k` from [1, n-1] """ k = gen_rand(1, self.n - 1) """ *Step-4*: Calculate r as the x-coordinate of result of scalar multiplication of `k` with generator point `G` """ r = (k * self.G).x() """ GCD of `k` and order of subgroup generated by `G` ie. n, should be 1 to be able to calculate inverse of `k` over mod `n` """ assert GCD(k, self.n) == 1 """ *Step-5*: Calculate signature s = (k^{-1}*(z + k*d)) % n """ s = (inverse(k, self.n) * (z + r * self.d)) % self.n return (r, s)
def pollard_brute(N): """ For one of N's prime p, 1. If (p-1) is a K-smooth number. (k is small) 2. When all (p-1)'s factor were iterated by b Then it can be factorization by pollard_pm1. """ a = 2 b = 1 factors = [] if isPrime(N) : return N try : while True: a = pow(a, b, N) p = GCD(a - 1, N) if 1 < p < N: factors.append(p) print(f"factor found: {p}") q = N // p if isPrime(q) : print(f"factor found: {q}") factors.append(q) return factors b += 1 except: return factors
def crt(list_a, list_m): """ Reference: https://crypto.stanford.edu/pbc/notes/numbertheory/crt.html Returns the output after computing Chinese Remainder Theorem on x = a_1 mod m_1 x = a_2 mod m_2 ... x = a_n mod m_n input parameter list_a = [a_1, a_2, ..., a_n] input parameter list_m = [m_1, m_2, ..., m_n] Returns -1 if the operation is unsuccessful due to some exceptions """ for i in range(len(list_m)): for j in range(len(list_m)): if GCD(list_m[i], list_m[j]) != 1 and i != j: raise Exception("Moduli should be pairwise co-prime") M = 1 for i in list_m: M *= i list_b = [M // i for i in list_m] assert len(list_b) == len(list_m) try: list_b_inv = [ inverse(list_b[i], list_m[i]) for i in range(len(list_m)) ] except: raise Exception( "Encountered an unusual error while calculating inverse") x = 0 for i in range(len(list_m)): x += list_a[i] * list_b[i] * list_b_inv[i] return x % M
def generate(bits, e): p, q = getPrime(bits), getPrime(bits) n = p * q phi = (p - 1) * (q - 1) assert GCD(e, phi) == 1 d = inverse(e, phi) return RSA((n, e, d))
def PollardProcess(a, N): for j in range(1, N): a = pow(a, j, N) d = GCD(a - 1, N) if 1 < d and d < N: return d return 1
def rsa_compatible(n, phi): phi = long(phi) while True: e = StrongRandom().randint(1, phi - 1) if GCD(e, phi) == 1: break return RSAKey(mpz(n), mpz(e), None, None, None, 1024)
def keygen(sz): phi = lambda p, q: (p - 1) * (q - 1) while (True): p, q = (getPrime(sz) for i in range(2)) if GCD(p * q, phi(p, q)) == 1: break return publickey(p * q), privatekey(p, q)
def generate(self, algorithm, mode): algorithm = algorithm.get() modes = mode.get() mode = get_mode(mode.get()) sim_key = self.HexToByte(get_data(self.sim_key_path, 'Secret key')) if (algorithm.split('-')[0].upper() == 'AES'): iv = Random.new().read(AES.block_size) cipher = AES.new(sim_key, mode, iv) else: iv = Random.new().read(DES3.block_size) cipher = DES3.new(sim_key, mode, iv) data = get_data(self.input_path, 'Data') if len(data) % cipher.block_size != 0: data += ' ' * (cipher.block_size - len(data) % cipher.block_size) encoded = cipher.encrypt(data) encoded = b64encode(encoded) modulus = int(int(get_data(self.public_key_path, 'Modulus'), 16)) public_exp = int( int(get_data(self.public_key_path, 'Public exponent').strip(), 16)) asimmetric_alg = get_data(self.public_key_path, 'Method') if asimmetric_alg != 'RSA': generator = int( int(get_data(self.public_key_path, 'Generator'), 16)) if (asimmetric_alg == 'RSA'): RSAEncryptor = RSA.construct((modulus, public_exp)) encrypted_key = RSAEncryptor.encrypt(sim_key, '') encrypted_key = encrypted_key[0] else: ElGamalEncryptor = ElGamal.construct( (modulus, generator, public_exp)) while 1: k = random.StrongRandom().randint(1, modulus - 1) if GCD(k, modulus - 1) == 1: break encrypted_key = ElGamalEncryptor.encrypt(sim_key, int(k)) k = encrypted_key[1] encrypted_key = encrypted_key[0] file = open(self.envelope_path, 'w') file.write('---BEGIN OS2 CRYPTO DATA---\n') file.write('Description:\n Envelope\n\n') file.write('File name:\n ') file.write(self.envelope_path) file.write('\n\nMethod:\n ' + algorithm.split('-')[0].upper() + '\n ' + asimmetric_alg + '\n\n') if asimmetric_alg != 'RSA': file.write('Secret number:\n ') write_to_file(file, self.ByteToHex(k)) file.write('\n\nCrypt Method:\n ' + modes + '\n\n') file.write('Initialization vector:\n ' + str(self.ByteToHex(iv))) file.write('\n\nKey length:\n ' + str(hex(len(sim_key) * 8)).replace('0x', '') + '\n ') file.write(get_data(self.public_key_path, 'Key length')) file.write('\n\nEnvelope data:\n ') write_to_file(file, encoded.decode()) file.write('\n\nEnvelope crypt key:\n ') write_to_file(file, self.ByteToHex(encrypted_key)) file.write('\n\n---END OS2 CRYPTO DATA---')
def gen_ed(self, bits): while True: d = getRandomNBitInteger(int(bits*0.4)) if GCD(d, self.lbd) == 1: e = inverse(d, self.lbd) self.e, self.d = e, d break
def sign_hash(pub_algorithm_type, secret_key, hash_, k=None): if pub_algorithm_type in (1, 3): # RSA sig_string = PKCS1_v1_5.new(secret_key).sign(hash_) return (bytes_to_long(sig_string), ) elif pub_algorithm_type == 20: # ELG # TODO: Should only be allowed for test purposes if k is None: while 1: # This can be pretty darn slow k = random.StrongRandom().randint(1, secret_key.p - 1) if GCD(k, secret_key.p - 1) == 1: break print(k) # TODO: Remove dependence on undocumented method sig_string = PKCS1_v1_5.EMSA_PKCS1_V1_5_ENCODE(hash_, secret_key.size()) return secret_key.sign(sig_string, k) elif pub_algorithm_type == 17: q = secret_key.q qbits = int(math.floor(float(math.log(q, 2)))) + 1 qbytes = int(math.ceil(qbits / 8.0)) if k is None: k = random.StrongRandom().randint(1, q - 1) digest = hash_.digest()[:qbytes] return secret_key.sign(bytes_to_long(digest), k) else: # TODO: complete raise ValueError
def elgamal(): #伪随机数生成器 random_generator = Random.new().read #生成elgamal Key elgKey = ElGamal.generate(256, random_generator) #生成私钥 while 1: alpha = random.StrongRandom().randint(1, elgKey.p - 1) if GCD(alpha, elgKey.p - 1) == 1: break h = mod(elgKey.g, alpha, elgKey.p) message = [33, 14, 22, 62, 00, 17, 4, 62, 24, 14, 20, 66] print('message: ', message) #加密过程 #1.随机选择整数y y = random.StrongRandom().randint(1, elgKey.p - 1) #2.计算c1 c1 = mod(elgKey.g, y, elgKey.p) #3.计算s s = mod(h, y, elgKey.p) #4.对message进行加密 ciphertext = [(m * s) % (elgKey.p) for m in message] print('ciphetext: ', ciphertext) #解密过程 #1.通过c1计算得到s de_s = mod(c1, alpha, elgKey.p) #2.获得明文 x, y, r = ex_gcd(elgKey.p, de_s) s_reverse = y % (elgKey.p) if s_reverse < 0: s_reverse += elgKey.p plaintext = [(m * s_reverse) % (elgKey.p) for m in ciphertext] print('plaintext: ', plaintext)
def verify(self, signature, m): try: """ *Step-2*: Verify that `r`, `s` are integers in [1, n-1] """ r, s = signature assert GCD(s, self.n) == 1 assert r >= 1 except: return False """ *Step-3*: Calculate hash of message to be signed """ e = sha256(m).digest() """ *Step-4*: Compute the `Ln` left most bits of `e` as `z` """ Ln = len(bin(self.n)[2:]) z = bytes_to_long(slice_string(e, Ln)) """ *Step-5*: Compute `u_1` and `u_2` as: `u_1` \equiv z*s^{-1} \mod n `u_2` \equiv r*s^{-1} \mod n """ s_inv = inverse(s, self.n) u_1 = (s_inv * z) % self.n u_2 = (s_inv * r) % self.n """ *Step-6*: Calculate T = u_1*G + u_2*P """ T = u_1 * self.G + u_2 * self.P """ *Step-7*: Final check for signature verification """ return r == T.x()
def sol_ex(A, M, L, R): if L == 0 or L > R: return True g = GCD(A, M) if (L - 1) // g == R // g: return False return True
def rsa_construct(n, e, d=None, p=None, q=None, u=None): """Construct an RSAKey object""" assert isinstance(n, int) assert isinstance(e, int) assert isinstance(d, (int, type(None))) assert isinstance(p, (int, type(None))) assert isinstance(q, (int, type(None))) assert isinstance(u, (int, type(None))) obj = _RSAKey() obj.n = n obj.e = e if d is None: return obj obj.d = d if p is not None and q is not None: obj.p = p obj.q = q else: # Compute factors p and q from the private exponent d. # We assume that n has no more than two factors. # See 8.2.2(i) in Handbook of Applied Cryptography. ktot = d * e - 1 # The quantity d*e-1 is a multiple of phi(n), even, # and can be represented as t*2^s. t = ktot while t % 2 == 0: t = divmod(t, 2)[0] # Cycle through all multiplicative inverses in Zn. # The algorithm is non-deterministic, but there is a 50% chance # any candidate a leads to successful factoring. # See "Digitalized Signatures and Public Key Functions as Intractable # as Factorization", M. Rabin, 1979 spotted = 0 a = 2 while not spotted and a < 100: k = t # Cycle through all values a^{t*2^i}=a^k while k < ktot: cand = pow(a, k, n) # Check if a^k is a non-trivial root of unity (mod n) if cand != 1 and cand != (n - 1) and pow(cand, 2, n) == 1: # We have found a number such that (cand-1)(cand+1)=0 (mod n). # Either of the terms divides n. obj.p = GCD(cand + 1, n) spotted = 1 break k = k * 2 # This value was not any good... let's try another! a = a + 2 if not spotted: raise ValueError( "Unable to compute factors p and q from exponent d.") # Found ! assert ((n % obj.p) == 0) obj.q = divmod(n, obj.p)[0] if u is not None: obj.u = u else: obj.u = inverse(obj.p, obj.q) return obj
def decrypt_multi_cipher(self, crypto_list, pub_keys): p = int(self.key.p) g = int(self.key.g) x = int(self.key.x) while 1: k = random.randint(1, p - 1) if GCD(k, p - 1) == 1: break decrypted_list = [] for cipher_pair in crypto_list: decrypted_pair = [] for c in cipher_pair: c1 = int(c[0]) c2 = int(c[1]) c1_ = (c1 * pow(g, k, p)) % p prod = 1 for y in pub_keys: y = int(y) prod *= pow(y, k, p) prod %= p c1_pow = pow(c1, x, p) c2_ = (((c2 * prod) % p) * inverse(c1_pow, p)) % p decrypted_pair.append((c1_, c2_)) decrypted_list.append(decrypted_pair) random.shuffle(decrypted_list) return decrypted_list
def gcd_all(X): p = productTree(X) R = p.pop() while p: X = p.pop() R = [R[long(floor(i/2))] % X[i]**2 for i in range(len(X))] return [GCD(r/n,n) for r,n in zip(R,X)]
def crt(list_a, list_m): try: assert len(list_a) == len(list_m) except: print "[+] Length of list_a should be equal to length of list_m" return -1 for i in range(len(list_m)): for j in range(len(list_m)): if GCD(list_m[i], list_m[j])!= 1 and i!=j: print "[+] Moduli should be pairwise co-prime" return -1 M = 1 for i in list_m: M *= i list_b = [M/i for i in list_m] assert len(list_b) == len(list_m) try: list_b_inv = [int(gmpy2.invert(list_b[i], list_m[i])) for i in range(len(list_m))] except: print "[+] Encountered an unusual error while calculating inverse using gmpy2.invert()" return -1 x = 0 for i in range(len(list_m)): x += list_a[i]*list_b[i]*list_b_inv[i] return x % M
def gen_key(): while True: p = getPrime(512) q = getPrime(512) # p = getPrime(64) # q = getPrime(512) if GCD(p - 1, q - 1) == 2: return p, q