def attemptHackWithKeyLength(ciphertext, mostLikelyKeyLength):
    # menentukan huruf yang mirip pada setiap kata dalam kunci
    ciphertextUp = ciphertext.upper()

    allFreqScores = []
    for nth in range(1, mostLikelyKeyLength + 1):
        nthLetters = getNthSubkeysLetters(nth, mostLikelyKeyLength,
                                          ciphertextUp)

        freqScores = []
        for possibleKey in LETTERS:
            decryptedText = vigenereCipher.decryptMessage(
                possibleKey, nthLetters)
            keyAndFreqMatchTuple = (
                possibleKey, freqAnalysis.englishFreqMatchScore(decryptedText))
            freqScores.append(keyAndFreqMatchTuple)
        # mengurutkan score
        freqScores.sort(key=getItemAtIndexOne, reverse=True)

        allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTERS])

    if not SILENT_MODE:
        for i in range(len(allFreqScores)):
            # use i + 1 so the first letter is not called the "0th" letter
            print('Possible letters for letter %s of the key: ' % (i + 1),
                  end='')
            for freqScore in allFreqScores[i]:
                print('%s ' % freqScore[0], end='')
            print()  # print a newline

    #coba kombinasi yang mirip setiap formasi
    for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS),
                                     repeat=mostLikelyKeyLength):

        possibleKey = ''
        for i in range(mostLikelyKeyLength):
            possibleKey += allFreqScores[i][indexes[i]][0]

        if SILENT_MODE:
            print('Mencoba dengan Kata Kunci: %s' % (possibleKey))

        decryptedText = vigenereCipher.decryptMessage(possibleKey,
                                                      ciphertextUp)

        if detectEnglish.isEnglish(decryptedText):

            origCase = []
            for i in range(len(ciphertext)):
                if ciphertext[i].isupper():
                    origCase.append(decryptedText[i].upper())
                else:
                    origCase.append(decryptedText[i].lower())
            decryptedText = ''.join(origCase)

            return decryptedText

    # No English-looking decryption found, so return None.
    return None
예제 #2
0
def crack_xor_message_frequency(message):
    # Guess format of message
    # Is message a hex string like 'a41332ef', hex pairs represent bytes.
    if not is_hex_string(message):
        message = message.encode('hex')

    cracked_message = {'score': None, 'message': '', 'key': ''}
    best_score = 0

    bar = progressbar.ProgressBar(max_value=0xff, redirect_stdout=True)

    for key in range(0x00, 0xff):
        bar.update(key)

        # Xor params should be hex bytes. e.g. xor('\xaf', '\x0a')
        guessed_plaintext = xor(unhex(message),
                                unhex("{:02x}".format(key)),
                                cut='max')
        score = 0
        letter_frequency_order = freqAnalysis.getFrequencyOrder(
            guessed_plaintext, True)
        score = freqAnalysis.englishFreqMatchScore(guessed_plaintext)

        # Matches all non printable ascii characters
        # and lower score
        regex_non_ascii = r'[^ -~\x0D\x0A]'
        matches = re.findall(regex_non_ascii, guessed_plaintext)
        if matches:
            score -= len(matches)

        # Matches all non alpha ascii characters
        # and lower score.
        # Improved accuracy.
        regex_non_alpha_ascii = r'[^a-zA-Z]'
        matches = re.findall(regex_non_alpha_ascii, guessed_plaintext)
        if matches:
            score -= len(matches) / float(
                2)  # each find reduces score by 0.5 per find

        # Matches all non lowercase alpha ascii characters
        # and lower score


#        regex_non_lcalpha_ascii = r'[^a-z]'
#        matches = re.findall( regex_non_lcalpha_ascii, guessed_plaintext)
#        if matches:
#            score -= len(matches) / float(2) # each find reduces score by 0.5 per find

        if score > cracked_message['score']:
            cracked_message = {
                'score': score,
                'message': guessed_plaintext,
                'key': key
            }
    bar.finish()

    return cracked_message
예제 #3
0
def attemptHackWithKeyLength(ciphertext, mostLikelyKeyLength):
   # Determine the most likely letters for each letter in the key.
   ciphertextUp = ciphertext.upper()
   # allFreqScores is a list of mostLikelyKeyLength number of lists.
   # These inner lists are the freqScores lists.
   allFreqScores = []
   for nth in range(1, mostLikelyKeyLength + 1):
       nthLetters = getNthSubkeysLetters(nth, mostLikelyKeyLength, ciphertextUp)
       # freqScores is a list of tuples like:
       # [(<letter>, <Eng. Freq. match score>), ... ]
       # List is sorted by match score. Higher score means better match.
       # See the englishFreqMatchScore() comments in freqAnalysis.py.
       freqScores = []
       for possibleKey in LETTERS:
           decryptedText = vigenereCipher.decryptMessage(possibleKey, nthLetters)
           keyAndFreqMatchTuple = (possibleKey, freqAnalysis.englishFreqMatchScore(decryptedText))
           freqScores.append(keyAndFreqMatchTuple)
       # Sort by match score
       freqScores.sort(key=getItemAtIndexOne, reverse=True)
       allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTERS])
   if not SILENT_MODE:
       for i in range(len(allFreqScores)):
           # use i + 1 so the first letter is not called the "0th" letter
           print("Possible letters for letter %s of the key: ' % (i + 1), end='")
           for freqScore in allFreqScores[i]:
               print("%s ' % freqScore[0], end=")
           print() # print a newline
   # Try every combination of the most likely letters for each position
   # in the key.
   for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS), repeat=mostLikelyKeyLength):
       # Create a possible key from the letters in allFreqScores
       possibleKey = ''
       for i in range(mostLikelyKeyLength):
           possibleKey += allFreqScores[i][indexes[i]][0]
       if not SILENT_MODE:
           print('Attempting with key: %s' % (possibleKey))
       decryptedText = vigenereCipher.decryptMessage(possibleKey, ciphertextUp)
       if detectEnglish.isEnglish(decryptedText):
           # Set the hacked ciphertext to the original casing.
           origCase = []
           for i in range(len(ciphertext)):
               if ciphertext[i].isupper():
                   origCase.append(decryptedText[i].upper())
               else:
                   origCase.append(decryptedText[i].lower())
           decryptedText = ''.join(origCase)
           # Check with user to see if the key has been found.
           print('Possible encryption hack with key %s:' % (possibleKey))
           print(decryptedText[:200]) # only show first 200 characters
           print()
           print('Enter D for done, or just press Enter to continue hacking:')
           response = input('> ')
           if response.strip().upper().startswith('D'):
               return decryptedText
   # No English-looking decryption found, so return None.
   return None
예제 #4
0
def XORSingleCharBruteforce(input):

    messages = []

    for y in range(256):
        result = b''

        result = XORSingleChar(input, y)
        messages.append(
            [result, y,
             freqAnalysis.englishFreqMatchScore(str(result))])

    return sorted(messages, key=lambda x: x[2], reverse=True)[0]
def attemptHackWithKeyLength(ciphertext,mostLikelyKeyLength):
    ciphertextUp = ciphertext.upper()
    allFreqScores = []
    for nth in range(1, mostLikelyKeyLength + 1):
        nthLetters = getNthSubkeysLetters(nth, mostLikelyKeyLength, ciphertextUp)

        freqScores = []
        for possibleKey in vigenereCipher.LETTERS:
            decryptedText = vigenereCipher.decryptMessage(possibleKey, nthLetters)
            keyAndFreqMatchTuple = (possibleKey, freqAnalysis.englishFreqMatchScore(decryptedText))
            freqScores.append(keyAndFreqMatchTuple)

        freqScores.sort(key=getItemAtIndexOne, reverse=True)
        allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTERS])

    if not SILENT_MODE:
        for i in range(len(allFreqScores)):
            print('Possible letters for letter {0} of the key: '.format(i + 1))
            for freqScores in allFreqScores[i]:
                print('%s ' % freqScores[0], end = '')
            print()

    for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS), repeat=mostLikelyKeyLength):
        possibleKey = ''
        for i in range(mostLikelyKeyLength):
            possibleKey += allFreqScores[i][indexes[i]][0]
        if not SILENT_MODE:
            print('Attempting with key: %s' % (possibleKey))

        decryptedText = vigenereCipher.decryptMessage(possibleKey, ciphertextUp)

        if detectEnglish.isEnglish(decryptedText):
            origCase = []
            for i in range(len(ciphertext)):
                if ciphertext[i].isupper():
                    origCase.append(decryptedText[i].upper())
                else:
                    origCase.append(decryptedText[i].lower())
            decryptedText = ''.join(origCase)

            print('Possible encryption hack with key %s:' % (possibleKey))
            print(decryptedText[:200])
            print()
            print('Enter D fordone, or just press Enter tocontinue')
            response = input('> ')
            if response.strip().upper().startswith('D'):
                return decryptedText

    return None
예제 #6
0
def crack_vigenere_key(t, n):
    """Attempt to use frequncy to Crack the supplied cipher text and determine key. 
      This function is not working 100% of the time and I cannot figure out why.
      Basic Idea: 1. Get Nth letter chunk
                  2. Do freq analysis
                  3. Brute force keys 
   Args:
       t(str): Target text for encryption
       n(int): Length of key
   """
    # Determine the most likely letters for each letter in the key.
    answer = ""
    tUp = t.upper()
    # These inner lists are the scores lists.
    allScores = []
    # 1. Get Nth letter chunk
    for nth in range(1, n + 1):
        # returns every positional letter for each set of letters in key text
        # remove non-letters from the message
        tUp2 = re.compile('[^A-Z]').sub('', tUp.upper())
        i = nth - 1
        letters = []
        # while items remain to iterate
        while i < len(tUp2):
            letters.append(tUp2[i])
            i += n
        positionalLetters = ''.join(letters)
        # 2. Do freq analysis
        scores = []
        for key in alphabet:
            dt = compute_vigenere(positionalLetters, key, Method.DECRYPT)
            # using freqAnalysis library to assist
            match = (key, freqAnalysis.englishFreqMatchScore(dt))
            scores.append(match)
        # Sort by match score
        scores.sort(key=getIndexOne, reverse=True)
        allScores.append(scores[:4])
    # Try every combination of the most likely letters for each position
    # 3. Brute force keys
    for indexes in itertools.product(range(4), repeat=n):
        # Create a possible key from the letters in allFreqScores
        key = ""
        for i in range(n):
            key += allScores[i][indexes[i]][0]
        print("Most likey key is " + key)
        break
    return None
예제 #7
0
def attemptHackWithKeyLength(ciphertext,mostLikelyKeyLength):
	ciphertextUp = ciphertext.upper()
	allFreqScores = []
	for nth in range(1, mostLikelyKeyLength + 1):
		nthLetters = getNthSubkeyLetters(nth,mostLikelyKeyLength,ciphertextUp)
		freqScores = []
		for possibleKey in LETTERS:
			decryptedText = vigenereCipher.decryptMessage(possibleKey,nthLetters)
			keyAndFreqMatchTuple = (possibleKey,freqAnalysis.englishFreqMatchScore(decryptedText))
			freqScores.append(keyAndFreqMatchTuple)
		freqScores.sort(key=getItemAtIndexOne,reverse=True)
		allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTERS])
	if not SILENT_MODE:
		for i in range(len(allFreqScores)):
			print 'Possible letters for letter'
			for freqScore in allFreqScores[i]:
				print freqScore[0]
			print ''

	for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS),repeat=mostLikelyKeyLength):
		possibleKey = ''
		for i in range(mostLikelyKeyLength):
			possibleKey += allFreqScores[i][indexes[i]][0]

		if not SILENT_MODE:
			print 'Attempting with key: '+ possibleKey
		decryptedText = vigenereCipher.decryptMessage(possibleKey,ciphertextUp)

		if detectEnglish.isEnglish(decryptedText):
			origCase = []
			for i in range(len(ciphertext)):
				if ciphertext[i].isupper():
					origCase.append(decryptedText[i].upper())
				else:
					origCase.append(decryptedText[i].lower())
			decryptedText = ''.join(origCase)
			print 'Possible encryption hack with key '+possibleKey
			print decryptedText[:200]
			print ''
			print 'enter d for done ,or just press enter to continue'
			response = raw_input('>')
			if response.upper().startswith('D'):
				return decryptedText
	return None
def attemptHackWithKeyLength(ciphertext, mostLikelyKeyLength):
    # Determine the most likely letters for each letter in the key:
    ciphertextUp = ciphertext.upper()
    # allFreqScores is a list of mostLikelyKeyLength number of lists.
    # These inner lists are the freqScores lists.
    allFreqScores = []
    for nth in range(1, mostLikelyKeyLength + 1):
        nthLetters = getNthSubkeysLetters(nth, mostLikelyKeyLength,
                                          ciphertextUp)

        # freqScores is a list of tuples like:
        # [(<letter>, <Eng. Freq. match score>), ... ]
        # List is sorted by match score. Higher score means better match.
        # See the englishFreqMatchScore() comments in freqAnalysis.py.
        freqScores = []
        for possibleKey in LETTERS:
            decryptedText = vigenereCipher.decryptMessage(
                possibleKey, nthLetters)
            keyAndFreqMatchTuple = (
                possibleKey, freqAnalysis.englishFreqMatchScore(decryptedText))
            freqScores.append(keyAndFreqMatchTuple)
        # Sort by match score:
        freqScores.sort(key=getItemAtIndexOne, reverse=True)

        allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTERS])

    if not SILENT_MODE:
        for i in range(len(allFreqScores)):
            # Use i + 1 so the first letter is not called the "0th" letter:
            print('Possible letters for letter %s of the key: ' % (i + 1),
                  end='')
            for freqScore in allFreqScores[i]:
                print('%s ' % freqScore[0], end='')
            print()  # Print a newline.

    # Try every combination of the most likely letters for each position
    # in the key:
    for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS),
                                     repeat=mostLikelyKeyLength):
        # Create a possible key from the letters in allFreqScores:
        possibleKey = ''
        for i in range(mostLikelyKeyLength):
            possibleKey += allFreqScores[i][indexes[i]][0]

        if not SILENT_MODE:
            print('Attempting with key: %s' % (possibleKey))

        decryptedText = vigenereCipher.decryptMessage(possibleKey,
                                                      ciphertextUp)

        if detectEnglish.isEnglish(decryptedText):
            # Set the hacked ciphertext to the original casing:
            origCase = []
            for i in range(len(ciphertext)):
                if ciphertext[i].isupper():
                    origCase.append(decryptedText[i].upper())
                else:
                    origCase.append(decryptedText[i].lower())
            decryptedText = ''.join(origCase)

            # Check with user to see if the key has been found:
            print('Possible encryption hack with key %s:' % (possibleKey))
            print(decryptedText[:200])  # Only show first 200 characters.
            print()
            print('Enter D if done, anything else to continue hacking:')
            response = input('> ')

            if response.strip().upper().startswith('D'):
                return decryptedText

    # No English-looking decryption found, so return None:
    return None
for i in range(result_keyword_len):
    sub_string_list = []
    for sub_i in range(i, len(cipher_text), result_keyword_len):
        sub_string_list.append(cipher_text[sub_i])
    sub_string_list_big.append(''.join(sub_string_list))

# for each sub_string find the top possible letters
decode26_dict = defaultdict(list)
for index, sub_string in enumerate(sub_string_list_big):
    # decode 26 times
    for letter in LETTERS:
        decode26_dict[index].append(v_cipher(sub_string, letter, False))

letter_freq = defaultdict(list)
for key, value in decode26_dict.items():
    for sub_s in value:
        freq = freqAnalysis.englishFreqMatchScore(sub_s)
        letter_freq[key].append(freq)
# print(letter_freq)
final_result = defaultdict(list)
for key, value in letter_freq.items():
    # print(value)
    max_value = max(value)
    for sub_i, sub_l in enumerate(value):
        if sub_l == max_value:
            final_result[key].append(LETTERS[sub_i])

for words in list(itertools.product(*final_result.values())):
    print(''.join(words), end='   ')
    print(v_cipher(cipher_text[:20], ''.join(words), False))
예제 #10
0
    def attemptHackWithKeyLength(ciphertext, mostLikelyKeyLength):

        ciphertextUp = ciphertext.upper()

        allFreqScores = []
        for nth in range(1, mostLikelyKeyLength + 1):
            nthLetters = getNthSubkeysLetters(nth, mostLikelyKeyLength,
                                              ciphertextUp)

            freqScores = []
            for possibleKey in LETTERS:
                decryptedText = decryptMessage(possibleKey, nthLetters)
                keyAndFreqMatchTuple = (
                    possibleKey,
                    freqAnalysis.englishFreqMatchScore(decryptedText))
                freqScores.append(keyAndFreqMatchTuple)

            freqScores.sort(key=getItemAtIndexOne, reverse=True)

            allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTERS])

        if not SILENT_MODE:
            for i in range(len(allFreqScores)):
                # Use i + 1 so the first letter is not called the "0th" letter:
                print('Possible letters for letter %s of the key: ' % (i + 1),
                      end='')
                for freqScore in allFreqScores[i]:
                    print('%s ' % freqScore[0], end='')
                print()  # Print a newline.

        # Try every combination of the most likely letters for each position
        # in the key:
        for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS),
                                         repeat=mostLikelyKeyLength):
            # Create a possible key from the letters in allFreqScores:
            possibleKey = ''
            for i in range(mostLikelyKeyLength):
                possibleKey += allFreqScores[i][indexes[i]][0]

            if not SILENT_MODE:
                print('Attempting with key: %s' % (possibleKey))

            decryptedText = decryptMessage(possibleKey, ciphertextUp)

            if detectEnglish.isEnglish(decryptedText):
                # Set the hacked ciphertext to the original casing:
                origCase = []
                for i in range(len(ciphertext)):
                    if ciphertext[i].isupper():
                        origCase.append(decryptedText[i].upper())
                    else:
                        origCase.append(decryptedText[i].lower())
                decryptedText = ''.join(origCase)

                print('Possible encryption hack with key %s:' % (possibleKey))
                print(decryptedText[:200])
                print()
                print('Enter D if done, anything else to continue hacking:')
                response = input('> ')

                if response.strip().upper().startswith('D'):
                    return decryptedText

        return None
예제 #11
0
def attemptHackWithKeyLength(cipherText, mostLikelyKeyLength):
    # Determine the most likely letters for each letter in the key.
    cipherTextUp = cipherText.upper()
    # allFreqScores is a list of mostLikelyKeyLength number of lists.
    allFreqKey = []
    for nth in range(mostLikelyKeyLength):
        nthLetters = getNthSubkeysLetters(nth, mostLikelyKeyLength,
                                          cipherTextUp)

        # freqScores is a list of tuples like:
        # [(<letter>, <Eng. Freq. match score>), ... ]
        freqScores = []
        for possibleKey in LETTERS:
            decryptedText = vigenereCipher.decryptMessage(
                possibleKey, nthLetters)
            matchScore = freqAnalysis.englishFreqMatchScore(decryptedText)
            freqScores.append((possibleKey, matchScore))
        # Sort by match score
        freqScores.sort(key=lambda x: x[1], reverse=True)
        # Get top letter
        numFreq = MIN_NUM_MOST_FREQ_LETTERS
        while numFreq < len(
                LETTERS) and freqScores[0][1] == freqScores[numFreq][1]:
            numFreq += 1
        freqKey = [fs[0] for fs in freqScores[:numFreq]]
        allFreqKey.append(freqKey)

    if not SILENT_MODE:
        for i in range(mostLikelyKeyLength):
            print('Possible letters for letter %s of the key: ' % (i + 1) +
                  getStringPrint(allFreqKey[i]))

    # Try every combination of the most likely letters for each position
    # in the key.
    indexes = [0 for _ in range(mostLikelyKeyLength)]
    while indexes is not None:
        # Create a possible key
        possibleKey = ''
        for i in range(mostLikelyKeyLength):
            possibleKey += allFreqKey[i][indexes[i]]

        if not SILENT_MODE:
            print('Attempting with key: %s' % possibleKey)

        decryptedText = vigenereCipher.decryptMessage(possibleKey,
                                                      cipherTextUp)

        if detectEnglish.isEnglish(decryptedText):
            # Set the hacked ciphertext to the original casing.
            origCase = []
            for i in range(len(cipherText)):
                if cipherText[i].isupper():
                    origCase.append(decryptedText[i].upper())
                else:
                    origCase.append(decryptedText[i].lower())
            decryptedText = ''.join(origCase)

            # Check with user to see if the key has been found.
            print('Possible encryption hack with key %s:' % (possibleKey))
            print(decryptedText[:200])  # only show first 200 characters
            print()
            if STOP:
                print(
                    'Enter D for done, or just press Enter to continue hacking:'
                )
                response = input('> ')
                if response.strip().upper().startswith('D'):
                    return decryptedText

        indexes = getNextCombine(indexes, allFreqKey)
    # No English-looking decryption found, so return None.
    return None
예제 #12
0

input = ""

with open('6.txt', 'r') as f:
    for line in f:
        input += line.rstrip()

chiphertext = base64.b64decode(input)
keylen = findKeyLen(chiphertext)

key = b""
plaintexts = []

#Do the Transpose
for i in range(keylen):
    block = b''
    for j in range(i, len(chiphertext), keylen):
        block += bytes([chiphertext[j]])
    key += bytes([XORSingleCharBruteforce(block)[1]])
    result = XORRepeatingKey(chiphertext, key)
    plaintexts.append(
        [result, key,
         freqAnalysis.englishFreqMatchScore(str(result))])

maxscore = max(plaintexts, key=lambda x: x[2])[2]

for i in sorted(plaintexts, key=lambda x: x[2], reverse=True):
    if i[2] == maxscore:
        print(i)
예제 #13
0
def attempt_hack_with_key_length(ciphertext, most_likely_key_length):
    # Determine the most likely letters for each letter in the key:
    ciphertext_up = ciphertext.upper()
    # all_freq_scores is a list of mostLikelyKeyLength number of lists.
    # These inner lists are the freq_scores lists.
    all_freq_scores = []
    for nth in range(1, most_likely_key_length + 1):
        nth_letters = get_nth_subkeys_letters(nth, most_likely_key_length,
                                              ciphertext_up)

        # freq_scores is a list of tuples like:
        # [(<letter>, <Eng. Freq. match score>), ... ]
        # List is sorted by match score. Higher score means better match.
        # See the englishFreqMatchScore() comments in freqAnalysis.py.
        freq_scores = []
        for possible_key in LETTERS:
            crypt = vigenereCipher.Vigenere(possible_key)
            decrypted_text = crypt.decrypt(nth_letters)
            key_and_freq_match_tuple = (
                possible_key,
                freqAnalysis.englishFreqMatchScore(decrypted_text))
            freq_scores.append(key_and_freq_match_tuple)
        # Sort by match score:
        freq_scores.sort(key=get_item_at_index_one, reverse=True)

        all_freq_scores.append(freq_scores[:NUM_MOST_FREQ_LETTERS])

    if not SILENT_MODE:
        for i in range(len(all_freq_scores)):
            # Use i + 1 so the first letter is not called the "0th" letter:
            print('Possible letters for letter %s of the key: ' % (i + 1) +
                  ' ')
            for freqScore in all_freq_scores[i]:
                print('%s ' % freqScore[0] + ' ')
            print('')

    # Try every combination of the most likely letters for each position
    # in the key:
    for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS),
                                     repeat=most_likely_key_length):
        # Create a possible key from the letters in all_freq_scores:
        possible_key = ''
        for i in range(most_likely_key_length):
            possible_key += all_freq_scores[i][indexes[i]][0]

        if not SILENT_MODE:
            print(f'Attempting with key: {possible_key}')

        crypt = vigenereCipher.Vigenere(possible_key)
        decrypted_text = crypt.decrypt(ciphertext_up)

        if detectEnglish.isEnglish(decrypted_text):
            # Set the hacked ciphertext to the original casing:
            orig_case = []
            for i in range(len(ciphertext)):
                if ciphertext[i].isupper():
                    orig_case.append(decrypted_text[i].upper())
                else:
                    orig_case.append(decrypted_text[i].lower())
            decrypted_text = ''.join(orig_case)

            print("\nPossible decrypted message:")
            print(
                f"   Key {possible_key}({len(possible_key)}). part of decrypted message: {decrypted_text[:200]}"
            )
            response = input(
                "\nEnter D if done, or any other key to continue the attack: ")

            if response.strip().upper().startswith('D'):
                return decrypted_text

    # No English-looking decryption found, so return None:
    return None
예제 #14
0
def attemptHackWithKeyLength(ciphertext, mostLikelyKeyLength):
    # determine the most likely letter for each letter in the key.
    ciphertextUp = ciphertext.upper()
    # allFreqScores is a list of mostLikelyKeyLength number of lists.
    # these inner lists are the freqScores lists.
    allFreqScores = []
    for nth in range(1, mostLikelyKeyLength + 1):
        nthLetters = getNthSubKeysLetters(nth, mostLikelyKeyLength,
                                          ciphertextUp)

        freqScores = []
        for possibleKey in LETTERS:
            decryptedText = cipher.decryptMessage(possibleKey, nthLetters)

            keyAndFreqMatchTuple = (
                possibleKey, freqAnalysis.englishFreqMatchScore(decryptedText))
            freqScores.append(keyAndFreqMatchTuple)

            # sort by match score
        freqScores.sort(key=getItemAtIndexOne, reverse=True)

        allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTERS])

    if not SILENT_MODE:
        for i in range(len(allFreqScores)):
            print('possible letters for letter {0} of the key:'.format(i + 1))

            for freqScore in allFreqScores[i]:
                print('{}'.format(freqScore[0]), end='')
            print()

    for indexes in itertools.product(range(NUM_MOST_FREQ_LETTERS),
                                     repeat=mostLikelyKeyLength):
        # create a possible key from the letters in allFreqScores
        possibleKey = ''
        for i in range(mostLikelyKeyLength):
            possibleKey += allFreqScores[i][indexes[i]][0]

        if not SILENT_MODE:
            print('Attempting with key: {0}'.format(possibleKey))

        decryptedText = cipher.decryptMessage(possibleKey, ciphertextUp)

        if detectEnglish.isEnglish(decryptedText):
            # set the hacked ciphertext to original casing
            origCase = []
            for i in range(len(ciphertext)):
                if ciphertext[i].isupper():
                    origCase.append(decryptedText[i].upper())
                else:
                    origCase.append(decryptedText[i].lower())
            decryptedText = ''.join(origCase)

            # Check with user to see if the key has been found
            print('Possible encryption hack with key {0}:'.format(possibleKey))
            print(decryptedText[:200])
            print()
            print('Enter D for done , or just press Enter to continue hacking')
            response = input('> ')

            if response.strip().upper().startswith('D'):
                return decryptedText

    # No english-looking decrytion found, so return None.
    return None
예제 #15
0
def attemptHackWithKeyLength(ciphertext, mostLikelyKeyLength):
    #Determine the most likely letters for each letter in the key:
    ciphertextUp = ciphertext.upper()
    allFreqScores = []
    for nth in range(1, mostLikelyKeyLength + 1):
        nthLetters = getNthSubkeysLetters(nth, mostLikelyKeyLength,
                                          ciphertextUp)
        #FreqScore is a list of tuples like letter and English Freq match score
        #[<letter>, <Eng. Freq. match score>), ...]
        freqScores = []
        for possibleKey in LETTERS:
            decryptedText = vigenereCipher.decryptMessage(
                possibleKey, nthLetters)
            keyAndFreqMatchTuple = (
                possibleKey, freqAnalysis.englishFreqMatchScore(decryptedText))
            freqScores.append(keyAndFreqMatchTuple)
        freqScores.sort(key=getItemAtIndexOne, reverse=True)
        #Example of some of the allFreqScores =[[('A',9), ('E', 5), ('O', 4), ('P', 4)],
        #[('S', 10), ('D', 4), ('G', 4), ('H',4)]]
        allFreqScores.append(freqScores[:NUM_MOST_FREQ_LETTER])

    if not SILENT_MODE:
        for i in range(len(allFreqScores)):
            #Use i + 1 so the first letter is not called the "0th" letter:
            print('Possible letters for letter %s of the key: ' % (i + 1),
                  end='')
            for freqScore in allFreqScores[i]:
                print('%s ' % freqScore[0], end='')
            print()  # Print a newline

    #Try every combination of the most likely letters for each position in the key
    for indexes in itertools.product(range(NUM_MOST_FREQ_LETTER),
                                     repeat=mostLikelyKeyLength):
        #Create a possible key from the letters in allFreqScores:
        possibleKey = ''
        for i in range(mostLikelyKeyLength):
            possibleKey += allFreqScores[i][indexes[i]][0]
        if not SILENT_MODE:
            print('Attempting with key: %s' % (possibleKey))
        decryptedText = vigenereCipher.decryptMessage(possibleKey,
                                                      ciphertextUp)

        if detectEnglish.isEnglish(decryptedText):
            origCase = []
            for i in range(len(ciphertext)):
                if ciphertext[i].isupper():
                    origCase.append(decryptedText[i].upper())
                else:
                    origCase.append(decryptedText[i].lower())
            decryptedText = ''.join(origCase)

            #Check with user to see if the key has been found:
            print('Possible encryption hack with key %s:' % (possibleKey))
            print(decryptedText[:200])
            print()
            print('Enter D if done, anything else to continue hacking')
            response = input('> ')

            if response.strip().upper().startswith('D'):
                return decryptedText
    return None