1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78
| import gmpy2 from Crypto.Util.number import *
import itertools def small_roots(f, bounds, m=1, d=None): if not d: d = f.degree()
R = f.base_ring() N = R.cardinality()
f /= f.coefficients().pop(0) f = f.change_ring(ZZ)
G = Sequence([], f.parent()) for i in range(m+1): base = N^(m-i) * f^i for shifts in itertools.product(range(d), repeat=f.nvariables()): g = base * prod(map(power, f.variables(), shifts)) G.append(g)
B, monomials = G.coefficient_matrix() monomials = vector(monomials)
factors = [monomial(*bounds) for monomial in monomials] for i, factor in enumerate(factors): B.rescale_col(i, factor)
B = B.dense_matrix().LLL()
B = B.change_ring(QQ) for i, factor in enumerate(factors): B.rescale_col(i, 1/factor)
H = Sequence([], f.parent().change_ring(QQ)) for h in filter(None, B*monomials): H.append(h) I = H.ideal() if I.dimension() == -1: H.pop() elif I.dimension() == 0: roots = [] for root in I.variety(ring=ZZ): root = tuple(R(root[var]) for var in f.variables()) roots.append(root) return roots return []
n = 10787879094547634536418400489544495490920545668797140045606047169206620885051312335135831508173231222095307914925085736895140618767731141232201839054986089 c = 6231259964139423317420399259419242000626426110518752018384660416595264962435087677191600419542766152613241809444876652160722765670645883113456355844854019
R.<x,y> = PolynomialRing(Zmod(n)) a = 2^127 + 2*x + 1 b = 2^127 + 2*y + 1 f = (a*2^128+b)*(b*2^128+a)
bound = (2^126,2^126) res = small_roots(f,bound,m=2,d=2) if res !=[]: for sol in res: a = 2^127 + 2*int(sol[0]) + 1 b = 2^127 + 2*int(sol[1]) + 1 p = int((bin(a)[2:].zfill(128) + bin(b)[2:].zfill(128)),2) q = int((bin(b)[2:].zfill(128) + bin(a)[2:].zfill(128)),2) if p > q: p, q = q, p n = p * q stream = [q] for i in range(114): num = (a * stream[-1] + b) % p stream.append(num) e = gmpy2.next_prime(stream[1] * stream[14] + stream[51] * stream[4]) d = gmpy2.invert(e,(p-1)*(q-1)) m = pow(c,d,n) flag = long_to_bytes(int(m)) if b'flag' in flag: print(flag)
|