Ejemplo n.º 1
0
def do_padding(c1, known):
    if len(known)>0:
        padding = bytes([len(known)+1]*(len(known)))
        to_flip = xorstr(known, padding)
        flipped = xorstr(to_flip, c1[0-len(padding):])   
        return bytearray(c1[:-1*len(padding)]+flipped)
    else:
        return bytearray(c1)
Ejemplo n.º 2
0
def aes_ctr(key, nonce, data):
    crypt = AES.new(key, AES.MODE_ECB)
    blocks = to_blocks(data, 16)
    plaintext = b''
    for i in range(0, len(blocks)):
        f = struct.pack("<qq", nonce, i)
        k = crypt.encrypt(f)
        plaintext += xorstr(blocks[i], k)
    return plaintext
Ejemplo n.º 3
0
def cbc_decrypt(data, key, iv):
    crypt = AES.new(key, AES.MODE_ECB)
    blocks = [iv] + to_blocks(data, len(key))

    blocks = [
        xorstr(crypt.decrypt(blocks[i]), blocks[i - 1])
        for i in range(1, len(blocks))
    ]
    plaintext = b"".join(blocks)
    assert check_padding(plaintext)
    return plaintext
Ejemplo n.º 4
0
key = rndfile.read(16)

# Here is the challenge
plaintexts  = [b64decode(i) for i in open("c19_data.txt").readlines()]
ciphertexts = [aes_ctr(key, 1234, i) for i in plaintexts]
plaintexts = [b'' for i in ciphertexts]

max_len = max([len(i) for i in ciphertexts])
print(plaintexts)

# Let's try frequency analysis on the each byte of each of them
#
# (Okay, this turns out to be the same as transposing it and solving it
#  as a repeating xor key as in challenge 20)
#

key = b''
for n in range(max_len):
    n_bytes = bytes([i[n] for i in ciphertexts if n<len(i)])
    key += bytes([break_single_xor(n_bytes)])

for i in ciphertexts:
    print(xorstr(i, key))
            
# Drop to a console to play with it some more
# The approach above gets most of the keystream, up to
# about 30 bytes it looks correct.

code.InteractiveConsole(locals=globals()).interact()

Ejemplo n.º 5
0

def check_admin(token):
    global key
    crypt = AES.new(key, AES.MODE_CBC, token[0:16])
    plaintext = unpad(crypt.decrypt(
        token[16:]))  # oh no, padding oracles! (for later)
    pairs = [i.rsplit(b"=") for i in plaintext.rsplit(b";")]

    return ([b"admin", b"true"] in pairs)


##########################################################

# Generate a token, what is in it doesn't really matter the way we're
# doing it, since we know what lives in the last block - let's just make it
# "TOKEN," because that makes us land on an even padding :)
token = gen_token(b"TOKEN")

# The last two blocks are going to be filled with, like, a pound of bacon
# so we know what they are, and we know we can edit them at will without
# really breaking anything important.

blocks = to_blocks(token, 16)
bits_to_flip = xorstr(b";admin=true;A=A\x01", b"nd%20of%20bacon\x01")
blocks[-2] = xorstr(blocks[-2], bits_to_flip)

token = b"".join(blocks)

print(check_admin(token))
Ejemplo n.º 6
0
    return [i[0] for i in sorted(keysizes, key=lambda x: x[1])]
  
def to_blocks(data, blocksize):
    return [data[i:i+blocksize] for i in range(0, len(data), blocksize)]

def transpose(blocks, blocksize):
    return [bytes([x[i] for x in blocks if len(x)>i]) for i in range(blocksize)]


if __name__ == "__main__":
    data = b64decode(open("c06_data.txt").read())
    keysize = get_keysizes(data, 10)[0]

    print("Using keysize %d" % keysize)

    blocks = to_blocks(data, keysize)
    blocks = transpose(blocks, keysize)

    key = bytes([break_single_xor(i) for i in blocks])
    print("Using key '%s'\n=========================================" % key.decode("ascii"))

    print(xorstr(data, key).decode("ascii"))