def test_xor(self): s1 = 'abc' s2 = '9987' s1_xor_s2 = xor(s1, s2) self.assertEqual(3, len(s1_xor_s2)) self.assertEqual('X[[', s1_xor_s2) self.assertEqual('foobar', xor('foobarandsomejunk', '\x00' * 6))
def test2(testconf): """测试上传下载文件 异常情况:下载文件后,往文件后追加内容,这时两个文件的 md5 肯定会 不一样。 """ sgw_addr = testconf.sgw_addr sgw_port = testconf.sgw_port old_name = "test2.1" new_name = "test2.2" utils.removefile(old_name) utils.removefile(new_name) test1_stage0(old_name) test1_stage1(sgw_addr, sgw_port, old_name) test1_stage2(sgw_addr, sgw_port, old_name, new_name) rc = test1_stage3(old_name, new_name) if rc: utils.xor(new_name, 0) rc = test1_stage3(old_name, new_name) if rc: # new_name 的内容已更改,下载文件和源文件的 md5 不应该再相同 return False else: utils.xor(new_name, 0) rc = test1_stage3(old_name, new_name) return rc else: return False
def applyCBC(text, DESKey, initialVector, mode): # convert all parameters into binary # text = convertToBinary(text) # DESKey = convertToBinary(DESKey) # initialVector = convertToBinary(initialVector) feedback = initialVector # divide the text into blocks each of size 64 bits textIntoParts = splitIntoParts(text, 64) result = [] for i in range(len(textIntoParts)): if (mode == ENCRYPT): res = xor(feedback, textIntoParts[i], 64) feedback = applyDES(res, DESKey, ENCRYPT) result.append(feedback) else: desres = applyDES(textIntoParts[i], DESKey, DECRYPT) res = "" if (i == 0): res = xor(desres, initialVector, 64) else: res = xor(desres, textIntoParts[i - 1], 64) result.append(res) # convert the binary back to characters return ("".join(result))
def xor_scrambled(self, scrambled, pbar): for i in range(len(scrambled)): if not bool(i % 2): reverse = self.c_vector reverse.reverse() scrambled[i] = [utils.xor(scrambled[i][j], reverse[j], pbar) for j in range(len(self.c_vector))] else: scrambled[i] = [utils.xor(scrambled[i][j], self.c_vector[j], pbar) for j in range(len(self.c_vector))] pbar.update(1) for j in range(len(scrambled[0])): col = utils.get_column(scrambled, j) if not bool(j % 2): reverse = self.r_vector reverse.reverse() scrambled = utils.set_column(scrambled, j, [utils.xor(col[i], reverse[i], pbar) for i in range(len(self.r_vector))]) else: scrambled = utils.set_column(scrambled, j, [utils.xor(col[i], self.r_vector[i], pbar) for i in range(len(self.r_vector))]) pbar.update(1) return scrambled
def aes_cbc_decode(ciphertext: bytes, password: bytes, iv: bytes) -> bytes: blocks = split_into_groups(ciphertext, 16) res = [] # Sort out the first block on its own, as it requires iv res.append(xor(aes_ecb_decode(blocks[0], password), iv)) # Sort out all other blocks for i, block in enumerate(blocks[1:], 1): res.append(xor(aes_ecb_decode(block, password), blocks[i - 1])) return b''.join(res)
def resolve_q7(): cipher = r'6c73d5240a948c86981bc294814d'.decode('hex') plaintext = r'attack at dawn' key = xor(cipher, plaintext) # Encode the new secret message plaintext = r'attack at dusk' cipher = xor(key, plaintext.encode('hex')) print cipher.encode('hex')
def solve_q1(): enc_msg = "20814804c1767293b99f1d9cab3bc3e7ac1e37bfb15599e5f40eef805488281d".decode('hex') plaintext = "Pay Bob 100$...." block_size = AES.block_size iv = enc_msg[:block_size] ciphertext = enc_msg[block_size:] attacker_plaintext = "Pay Bob 500$...." ivp = xor(iv, xor(plaintext, attacker_plaintext)) print ivp.encode('hex')
def _hmac(self, message): key = self._key if (len(key) > self._block_size): key = self._hash_function(key).hexdigest().decode("hex") else: key = key.ljust(self._block_size, "\x00") outer_pad = utils.xor(key, "\x5c" * self._block_size) inner_pad = utils.xor(key, "\x36" * self._block_size) return self._hash_function(outer_pad + self._hash_function(inner_pad + message).hexdigest().decode("hex"))
def makeU_f(self, bitmap): #This was inspired by the rigetti code on their grove github (https://github.com/rigetti/grove/blob/master/grove/simona/Simon.py) n_bits = self.n_compQubs U_f = np.zeros(shape=(2 ** (2 * n_bits), 2 ** (2 * n_bits))) indexmap = defaultdict(dict) for b in range(2**n_bits): pad_str = np.binary_repr(b, n_bits) for k, v in bitmap.items(): indexmap[pad_str + k] = utils.xor(pad_str, v) + k i, j = int(pad_str+k, 2), int(utils.xor(pad_str, v) + k, 2) U_f[i, j] = 1 return U_f
def ctr_bitflip(): user_input = "AadminZtrueZ" desired = ";admin=true;" ciphertext = encrypt_params(user_input) ciphertext_user_input = ciphertext[32:32 + len(user_input)] delta = xor(string_to_bytearray(user_input), string_to_bytearray(desired)) new_ciphertext_flipped = xor(ciphertext_user_input, delta) new_ciphertext = ciphertext[:32] + new_ciphertext_flipped + ciphertext[ 32 + len(user_input):] return new_ciphertext
def hmac(key, message): if (len(key) > BLOCKSIZE): key = bytearray(sha1(key).decode( 'hex')) # keys longer than BLOCKSIZE are shortened if (len(key) < BLOCKSIZE): # keys shorter than BLOCKSIZE are zero-padded (where + is concatenation) key = key + bytearray([0x00] * (BLOCKSIZE - len(key))) # Where * is repetition. o_key_pad = xor(bytearray([0x5c] * BLOCKSIZE), key) i_key_pad = xor(bytearray([0x36] * BLOCKSIZE), key) h1 = sha1(i_key_pad + string_to_bytearray(message)) return sha1(o_key_pad + hexstr2bytearray(h1))
def encrypt_repeating_key(m, k): key_multiplier = len(m) // len(k) key_candidate = k * key_multiplier key_candidate += k[:len(m)-len(key_candidate)] xored = xor(m, key_candidate) return xored
def encrypt_and_sign(msg, k): (g, p, y, x) = keygen() (r, s) = sign(msg, g, p, x) content = json.dumps((msg, g, p, y, r, s)) encrypted = xor(content, str(k)).encode('ascii') return base64.b64encode(encrypted)
def setup0_response(self, response_data): setup_resp = proto.session_pb2.SessionData() setup_resp.ParseFromString(utils.bytearr_to_bytes(response_data)) self._print_verbose("Security version:\t" + str(setup_resp.sec_ver)) if setup_resp.sec_ver != session_pb2.SecScheme1: print("Incorrect sec scheme") exit(1) self._print_verbose( "Device Public Key:\t" + utils.bytes_to_hexstr(setup_resp.sec1.sr0.device_pubkey)) self._print_verbose( "Device Random:\t" + utils.bytes_to_hexstr(setup_resp.sec1.sr0.device_random)) sharedK = self.client_private_key.exchange( X25519PublicKey.from_public_bytes( setup_resp.sec1.sr0.device_pubkey)) self._print_verbose("Shared Key:\t" + utils.bytes_to_hexstr(sharedK)) if len(self.pop) > 0: h = hashes.Hash(hashes.SHA256(), backend=default_backend()) h.update(self.pop) digest = h.finalize() sharedK = utils.xor(sharedK, digest) self._print_verbose("New Shared Key XORed with PoP:\t" + utils.bytes_to_hexstr(sharedK)) self._print_verbose("IV " + hex( int(utils.bytes_to_hexstr(setup_resp.sec1.sr0.device_random), 16))) cipher = Cipher(algorithms.AES(sharedK), modes.CTR(setup_resp.sec1.sr0.device_random), backend=default_backend()) self.cipher = cipher.encryptor() self.client_verify = self.cipher.update( setup_resp.sec1.sr0.device_pubkey) self._print_verbose("Client Verify:\t" + utils.bytes_to_hexstr(self.client_verify))
def main(): #plaintext m1 m1 = "final grade: 20% (F-)" #one time pad encryption of plaintext m1 c1 = "09ea81c5f7b0a6653ac6519458e7e53f36ab0f232c" #plaintext m2 m2 = "final grade: 99% (A+)" m1_bin = utils.ascii2Bin(m1) c1_bin = utils.hex2Bin(c1) m2_bin = utils.ascii2Bin(m2) assert (len(m1_bin) == len(c1_bin) == len(m2_bin)) result = utils.xor(utils.xor(m1_bin, c1_bin), m2_bin) print(utils.bin2Hex(result))
def fiestalRound(text, key): # split the plaintext into two halves left = text[:32] right = text[32:] # use expansion on the right half exp = expansion(right) # xor the expansion result with the key xorRes = xor(exp, key, 48) # apply the sbox sboxRes = sBoxes(xorRes) # apply dbox dboxRes = dBox(sboxRes) # xor dbox result with left half xorRes = xor(left, dboxRes, 32) # return the swapped result return (right + xorRes)
def test_chat(db): conn = sqlite3.connect(db) sql = 'SELECT {seq} from {table}'.format(seq=','.join(PROJECT), table=table) # cursor = conn .execute('SELECT _id,msgData,time from mr_friend_C135CD0F840B8EBFB46A1F868D493D9C_New') cursor = conn.execute(sql) for row in cursor: tmp = row[PROJECT.index(Contents.frienduin)] # print(type(tmp),tmp) print(Contents.frienduin, '=', utils.xor(tmp)) tmp = row[PROJECT.index(Contents.msgData)] # print(type(tmp),tmp) print(Contents.msgData, '=', utils.xor(tmp))
def break_easy_way(): total_length = len(ciphertext) newtext = bytearray([0] * total_length) offset = 0 keystream = edit(offset, newtext) return xor(ciphertext, keystream)
def break_little_harder_way(): newtext = string_to_bytearray('FIXED VALUE') chunk_length = len(newtext) chunks = unequal_chunks(ciphertext, chunk_length) keystream = bytearray([]) for ix, chunk in enumerate(chunks): start = ix * chunk_length end = start + len(chunk) new_ciphertext = edit(start, newtext)[start:end] keystream_chunk = xor(new_ciphertext, newtext[:len(new_ciphertext)]) keystream.extend(keystream_chunk) return xor(ciphertext, keystream)
def encrypt(plain, key): prng = MT19937RNG.MT19937RNG() prng.seed_mt(KEY) keystream = b"".join( struct.pack('>I', prng.extract_number()) for _ in range(len(plain) // 4 + 1)) cipher = utils.xor(plain, keystream) return cipher
def guess_key_fully(): """ Once we have all the decrypted messages, we can get a stab at manually filling the remaining gaps, and improve our guess of the key: as it happens, MSG_8 can be fully guessed correctly, at which point the encryption key can be fully guessed. :return: the encryption key """ return xor(CIPHER_TEXTS[8], MSG_8)
def guess_key(): """ This is executed next: by XORing the guessed secret with its encrypted counterpart, we get an initial guess for the KEY - there will be incorrect guesses where GUESS has '*'s, but given that the nature of XOR encoding, the errors are localized, and can be corrected. :return: a guess for the encryption key """ return xor(SECRET, GUESS)
def get_messages(key): """ Helper method to decrypt all messages with the given ```key``` :param key: the encryption key :return: a list of decrypted messages """ messages = [xor(key, encrypted) for encrypted in CIPHER_TEXTS] return messages
def main(): guesses = get_messages(guess_key()) for i, msg in enumerate(guesses): print('{}: [{}]'.format(i, msg)) print '===' for i, secret in enumerate(CIPHER_TEXTS): junk = xor(CIPHER_TEXTS[8], secret) guess = [c for c in guesses[8]] for j, c in enumerate(junk): if c.isalpha() and 20 < j < 37: guess[j] = c.swapcase() print i, ''.join(guess) print '===' key = xor(CIPHER_TEXTS[8], MSG_8) decrypted_secret = xor(key, SECRET) print(decrypted_secret)
def cipher_decrypt(ciphertext, key): assert key < 2**16, '16-bit key please' assert key >= 0, '16-bit key please' prg = MT19937(key) key_stream = generate_bytes(prg, len(ciphertext)) return xor(ciphertext, key_stream)
def aes_cbc_encode(plaintext: bytes, password: bytes, iv: bytes) -> bytes: blocks = split_into_groups(plaintext, 16) res = [] prev_block = iv for block in blocks: prev_block = aes_ecb_encode(xor(prev_block, block), password) res.append(prev_block) return b''.join(res)
def is_valid_password(policy, password): i0 = policy['firstIndex'] i1 = policy['secondIndex'] # Silly non-zero based indexes :/ first_match = i0 <= len(password) and password[i0 - 1] == policy['letter'] second_match = i1 <= len(password) and password[i1 - 1] == policy['letter'] return xor(first_match, second_match)
def xor_with_keys(string): bin_string = hex_string_to_binary_string(string) binslen = len(bin_string) / 8 key_dict = {} for key in range(127): bin_key = bin(key)[2:].zfill(8) * 8 xored_string = xor(bin_string, bin_key) key_dict[dec_to_ascii(key)] = bin_to_ascii(xored_string) return key_dict
def decrypt(msg, k): encrypted = base64.b64decode(msg).decode('ascii') content = xor(encrypted, str(k)) (msg, g, p, y, r, s) = json.loads(content) isValid = check(msg, g, p, y, r, s) print('Signature is valid:', isValid) if isValid: print('Message:', msg)
def test_chat(db): conn = sqlite3.connect(db) sql = 'SELECT {seq} from {table}'.format(seq=','.join(PROJECT),table=table) # cursor = conn .execute('SELECT _id,msgData,time from mr_friend_C135CD0F840B8EBFB46A1F868D493D9C_New') cursor = conn .execute(sql) for row in cursor: tmp = row[PROJECT.index(Contents.frienduin)] # print(type(tmp),tmp) print(Contents.frienduin,'=',utils.xor(tmp)) tmp = row[PROJECT.index(Contents.msgData)] # print(type(tmp),tmp) print(Contents.msgData,'=',utils.xor(tmp))
def CBCDecryptRound(firstHalfFeedback, lastHalfFeedback, firstHalfCipher, lastHalfCipher, iv1, iv2, DESKey1, DESKey2): # xor the halves of cipher text and initial vector firstHalfCipher = xor(firstHalfCipher, iv1, 64) lastHalfCipher = xor(lastHalfCipher, iv2, 64) # apply des for the two halves of cipher text in decryption mode # firstHalfRes1 = applyDES(firstHalfCipher, DESKey1, DECRYPT) # lastHalfRes1 = applyDES(lastHalfCipher, DESKey2, DECRYPT) threads = [None] * 2 args = [[firstHalfCipher, DESKey1[::-1]], [lastHalfCipher, DESKey2[::-1]]] for i in range(2): threads[i] = Thread(target=callDES, args=(args[i][0], args[i][1], i)) threads[i].start() for i in range(2): threads[i].join() firstHalfRes1 = res[0] lastHalfRes1 = res[1] res.clear() threads.clear() args.clear() # apply des for the two halves of the feedback in encryption mode # firstHalfRes2 = applyDES(lastHalfFeedback, DESKey1, ENCRYPT) # lastHalfRes2 = applyDES(firstHalfFeedback, DESKey2, ENCRYPT) threads = [None] * 2 args = [[lastHalfFeedback, DESKey1], [firstHalfFeedback, DESKey2]] for i in range(2): threads[i] = Thread(target=callDES, args=(args[i][0], args[i][1], i)) threads[i].start() for i in range(2): threads[i].join() firstHalfRes2 = res[0] lastHalfRes2 = res[1] res.clear() threads.clear() args.clear() # cross xor the halves the two des results firstHalfText = xor(firstHalfRes2, lastHalfRes1, 64) lastHalfText = xor(firstHalfRes1, lastHalfRes2, 64) # return the plain text return [firstHalfText, lastHalfText]
def CBCEncryptRound(firstHalfFeedback, lastHalfFeedback, firstHalfText, lastHalfText, iv1, iv2, DESKey1, DESKey2): # apply des for the two halves of the feedback # firstHalfRes = applyDES(firstHalfFeedback, DESKey1, ENCRYPT) # lastHalfRes = applyDES(lastHalfFeedback, DESKey2, ENCRYPT) threads = [None] * 2 args = [[firstHalfFeedback, DESKey1], [lastHalfFeedback, DESKey2]] for i in range(2): threads[i] = Thread(target=callDES, args=(args[i][0], args[i][1], i)) threads[i].start() for i in range(2): threads[i].join() firstHalfRes = res[0] lastHalfRes = res[1] res.clear() threads.clear() args.clear() # xor the two des results with a half of the plain text firstHalfCipher = xor(firstHalfText, firstHalfRes, 64) lastHalfCipher = xor(lastHalfText, lastHalfRes, 64) # apply des for the xor'd results # lastCipher = applyDES(firstHalfCipher, DESKey2, ENCRYPT) # firstCipher = applyDES(lastHalfCipher, DESKey1, ENCRYPT) threads = [None] * 2 args = [[firstHalfCipher, DESKey2], [lastHalfCipher, DESKey1]] for i in range(2): threads[i] = Thread(target=callDES, args=(args[i][0], args[i][1], i)) threads[i].start() for i in range(2): threads[i].join() lastCipher = res[0] firstCipher = res[1] res.clear() threads.clear() args.clear() # xor the result of des with a half of the initial vector firstCipher = xor(firstCipher, iv1, 64) lastCipher = xor(lastCipher, iv2, 64) # return the cipher text return [firstCipher, lastCipher]
def main(): bt_a = hex_string_to_bytearray(hex_a) bt_b = hex_string_to_bytearray(hex_b) bt_expected = xor(bt_a, bt_b) bt_expected_hex = bytearray_to_hex_string(bt_expected) if bt_expected_hex == hex_expected: print("challenge 1.2 completed.") else: print("challenge 1.2 failed.")
def Enc(m: bytes): if len(m) != OAEP.expected_len_m: raise ValueError( f"`m` must by of length {OAEP.expected_len_m}, not {len(m)}") # message is padded with k1 zeros to be (n - k0) bits m_ = m + bytes(OAEP.k1 // 8) # r is a randomly generated k0-bit string randbits = random.getrandbits(OAEP.k0) r = randbits.to_bytes(OAEP.k0 // 8, byteorder='big') print(type(r), r[:10], '...') # G expands the k0 bits of `r` to (n - k0) bits X = utils.xor(m_, OAEP.G(r)) # H reduces the (n-k0) bits of X to k0 bits Y = utils.xor(r, OAEP.H(X)) return oaep(X=X, Y=Y, XY=X + Y, m=m, r=r, m_=m_)
def updateEntry(self, entry): for chunk_num in entry[0]: if self.chunks[chunk_num] is not None: entry[1] = xor(entry[1], self.chunks[chunk_num]) entry[0].remove(chunk_num) if len(entry[0]) == 1: self.chunks[entry[0][0]] = entry[1] self.entries.remove(entry) for d in self.entries: if entry[0][0] in d[0]: self.updateEntry(d)
def droplet(self): self.updateSeed() chunk_nums = randChunkNums(self.num_chunks) data = None for num in chunk_nums: if data is None: data = self.chunk(num) else: data = xor(data, self.chunk(num)) return Droplet(data, self.seed, self.num_chunks)
def aes_decrypt(c, k, mode, iv = None): aes = AES.new(k, AES.MODE_ECB) m = "" if mode == "CBC": if iv is None: raise ValueError("CBC mode requires and IV.") else: for i in range(0, len(c), BLOCK_SIZE()): block = aes.decrypt(c[i:i + BLOCK_SIZE()]) m = m + xor(block, iv) iv = c[i:i + BLOCK_SIZE()] return strip_padding(m) elif mode == "ECB": for i in range(0, len(c), BLOCK_SIZE()): m = m + aes.encrypt(c[i:i + BLOCK_SIZE()]) return strip_padding(m) else: raise ValueError("Incorrect mode used: " + mode)
def aes_encrypt(m, k, mode, iv = None): aes = AES.new(k, AES.MODE_ECB) c = "" # Add padding if len(m) % BLOCK_SIZE() != 0: m = m + pkcs7_pad(len(m), BLOCK_SIZE()) if mode == "CBC": if iv is None: raise ValueError("CBC mode requires an IV.") else: for i in range(0, len(m), BLOCK_SIZE()): block = xor(m[i:i + BLOCK_SIZE()], iv) iv = aes.encrypt(block) c = c + iv return c elif mode == "ECB": for i in range(0, len(m), BLOCK_SIZE()): c = c + aes.encrypt(m[i:i + BLOCK_SIZE()]) return c else: raise ValueError("Incorrect mode used: " + mode)
import sys sys.path.insert(1, "../common") # Want to locate modules in our 'common' directory import string import binascii import ltrfreq import utils scores = [] results = [] lineno = 0 with open("gistfile1.txt") as f: for line in f: lineno = lineno + 1; hexstring = string.rstrip(line) b = binascii.unhexlify(hexstring) for key in range(256): candidatebuf = utils.xor(key, b) scores.append(ltrfreq.totcscore(candidatebuf) + ltrfreq.norvigscore(candidatebuf)) spiffy = utils.SpiffyPrint(candidatebuf) results.append(spiffy) print "Highest score is", max(scores), " Sekrit message is", results[scores.index(max(scores))] print "Sekrit message came from line", scores.index(max(scores))/256 + 1 # Now that the party is jumping. // 7b5a4215415d544115415d5015455447414c155c46155f4058455c5b523f
accumulator = accumulator + utils.hamming(tbuf1,tbuf2) #Score for this keysize is (accumulator/bufpairs)/keysize print "Score for keylength", keysize, "is", (accumulator/bufpairs)/keysize # Keysize of 2 seems lowest. # Buffer 1: Odd bytes; Buffer 2: Even bytes buf1 = decoded[0::2] buf2 = decoded[1::2] scores = [] keys = [] for key in range(256): candidatebuf = utils.xor(key, buf1) scores.append(ltrfreq.totcscore(candidatebuf)) keys.append(key) print "Highest score from buf1 is", max(scores), "Corresponding key is", keys[scores.index(max(scores))] scores = [] keys = [] for key in range(256): candidatebuf = utils.xor(key, buf2) scores.append(ltrfreq.totcscore(candidatebuf)) keys.append(key) print "Highest score from buf2 is", max(scores), "Corresponding key is", keys[scores.index(max(scores))]
def main(): res1 = hex_to_base64( '49276d206b696c6c696e6720796f757220627261696e206c6' '96b65206120706f69736f6e6f7573206d757368726f6f6d') print('Task 1') print(res1) assert res1 == (b'SSdtIGtpbGxpbmcgeW91ciBicmFpbiBsaWtlIGEgcG9pc' b'29ub3VzIG11c2hyb29t') print('Task 2') x = hex_to_bytes('1c0111001f010100061a024b53535009181c') y = hex_to_bytes('686974207468652062756c6c277320657965') res2 = bytes_to_hex(xor(x, y)) print(res2) assert res2 == '746865206b696420646f6e277420706c6179' print('Task 3') ciphertext = hex_to_bytes('1b37373331363f78151b7f2b783431333d78397828372d' '363c78373e783a393b3736') res3 = decode_1_byte_xor(ciphertext) print(res3[1]) assert res3[1] == "Cooking MC's like a pound of bacon" print('Task 4') ciphertexts = get_file('4.txt').split('\n') res4 = find_and_decrypt_ciphertexts(ciphertexts) print('Key: {0}\nPlaintext: {1}'.format(*res4)) assert res4[1] == 'Now that the party is jumping\n' print('Task 5') plaintext5 = ("Burning 'em, if you ain't quick and nimble\n" "I go crazy when I hear a cymbal""") key = "ICE" correct_answer = ("0b3637272a2b2e63622c2e69692a23693a2a3c6324202d623d63343" "c2a26226324272765272a282b2f20430a652e2c652a3124333a653e" "2b2027630c692b20283165286326302e27282f") res5 = bytes_to_hex(repeating_key_xor(text_to_bytes(plaintext5), text_to_bytes(key))) print(res5) assert res5 == correct_answer print('Task 6') string1 = b'this is a test' string2 = b'wokka wokka!!!' print('Hamming Distance Check:', hamming_distance(string1, string2)) ciphertext6 = get_file('6.txt') ciphertext6 = base64_to_bytes(ciphertext6) res6 = decode_repeating_byte_xor(ciphertext6) assert res6[0] == 'Terminator X: Bring the noise' print('Key:', res6[0]) print('Plaintext:') print(res6[1]) print('Task 7') ciphertext7 = get_file('7.txt') ciphertext7 = base64_to_bytes(ciphertext7) password = b"YELLOW SUBMARINE" res7 = aes_ecb_decode(ciphertext7, password).decode('ascii') assert res7.startswith("I'm back and I'm ringin' the bell ") print(res7) print('Task 8') ciphertexts8 = get_file('8.txt').split('\n') ciphertexts8 = [bytes.fromhex(x) for x in ciphertexts8 if x] res8 = detect_aes_ecb_encrypted_texts(ciphertexts8) assert len(res8[1]) == 1 print('Most likely string:', bytes_to_hex(res8[1][0])) print('Max no. of repeats of a 16byte chunk found:', res8[0])