from random import randint import os from flag import flag import sys N=64 key=randint(0,2**N) # print key key=bin(key)[2:].rjust(N,'0') count=0 while True: zeros=[0] # indices of 0 in key for j in range(len(key)): if key[j]=='0': zeros.append(j) p=zeros[randint(0,len(zeros))-1] # pos of 0 q=zeros[randint(0,len(zeros))-1] # pos of 0 if p>q: tmp=q q=p p=tmp # assert p < q try: sys.stdout.write("mask:") sys.stdout.flush() mask=int(raw_input()) except: exit(0) mask=bin(mask)[2:] cnt = 0 new_key='' for j in range(0,N): if j in range(p,q+1): new_key += str(int(mask[cnt])^int(key[j])) else: new_key += key[j] cnt = (cnt + 1) % len(mask) key=new_key try: sys.stdout.write("guess:") sys.stdout.flush() guess=int(raw_input()) except: exit(0) if guess==int(key,2): count+=1 print 'Nice.' else: count=0 print 'Oops.' if count>2: print flag
64bitの乱数列が生成されて、値が0であるような2箇所が選ばれ、その間をmask
で bit flip できる。 mask
を1にして何度もbit flipを繰り返せば全部が1になるのでGuess は簡単
from ptrlib import Socket sock = Socket("52.163.228.53", 8082) # sock = Socket("localhost", 9999) print("[+] iterating...", end="") for i in range(200): print("{},".format(i+1), end="", flush=True) sock.sendlineafter("mask:", "1") sock.sendlineafter("guess:", "0") print("\n[+] done") sock.sendlineafter("mask:", "1") sock.sendlineafter("guess:", str(int("1" * 64, 2))) line = sock.recvline() count = 0 if b"Nice" in line: count += 1 print(line) sock.sendlineafter("mask:", "0" if count else "1") sock.sendlineafter("guess:", str(int("1" * 64, 2))) print(sock.recvline()) count += 1 sock.sendlineafter("mask:", "0") sock.sendlineafter("guess:", str(int("1" * 64, 2))) print(sock.recvline()) count += 1 if count > 2: print(sock.recvline()) quit() sock.sendlineafter("mask:", "0") sock.sendlineafter("guess:", str(int("1" * 64, 2))) print(sock.recvline()) print(sock.recvline())