def repeating_key_loop(key): """generates the next byte of key information for repeating key XOR.""" loc = 0 while(True): h = crypt_utils.toHex(key[loc]) yield h loc = (loc + 1) % len(key)
def base64_to_hex(b64): if type(b64) != str and type(b64) != bytes: raise TypeError("Error: base64_to_hex requires input in str") if type(b64) is not bytes: b64 = bytes(b64, 'UTF8') h = base64.standard_b64decode(b64) return crypt_utils.toHex(h)
def crack_vigenere(cyphertext): if not crypt_utils.is_hex(cyphertext): cyphertext = crypt_utils.toHex(cyphertext) keysizes = generate_vigenere_key_sizes(cyphertext) options = {} for keysize in keysizes: blocks = vigenere_blocks(cyphertext, keysize) try: # Chunk the hex strings into 8 bit lengths (2 Hex digits) # Otherwise transpose would split bytes incorrectly blocks = [[s[i] + s[i+1] for i in range(0, len(s), 2)] for s in blocks] except IndexError: # blocks contain invalid Hex, so assume this is not the solution continue blocks = vigenere_transpose(blocks) decrypted_message = [] key = '' for block in blocks: key_byte, message_part = search_single_byte_xor_key(block) decrypted_message.append(message_part) key += key_byte decrypted_message = vigenere_transpose(decrypted_message) decrypted_message = ''.join(decrypted_message) score = score_char_freq(decrypted_message) try: key = binascii.unhexlify(key).decode('ascii') except: #if key cannot be converted to ascii, leave as is pass options[score] = (key, decrypted_message) return options[min(options)]