【密码学】密码学实验报告

密码学实验报告

第一次实验

任务1:破解一个Many Time Pad加密

思路:可以看注释~

(运行结果也一并放到代码里了,Shell部分就是)

__reference = 'https://github.com/Morrandir/Crypto001_Week1'

from string import ascii_letters
TARGET = '32510ba9babebbbefd001547a810e67149caee11d945cd7fc81a05e9f85aac650e9052ba6a8cd8257bf14d13e6f0a803b54fde9e77472dbff89d71b57bddef121336cb85ccb8f3315f4b52e301d16e9f52f904'
#使用TARGET与每条之前的MSGS进行异或
#原理:c(a)^c(b) == m(a) ^ m(b) ^ k ^ k == m(a) ^ m(b)
#以及空格和ascii中大小写字母异或的结果为反转其大小写
potential_str = ' ' + ascii_letters  #有意义的字符
MSGS = (
    '315c4eeaa8b5f8aaf9174145bf43e1784b8fa00dc71d885a804e5ee9fa40b16349c146fb778cdf2d3aff021dfff5b403b510d0d0455468aeb98622b137dae857553ccd8883a7bc37520e06e515d22c954eba5025b8cc57ee59418ce7dc6bc41556bdb36bbca3e8774301fbcaa3b83b220809560987815f65286764703de0f3d524400a19b159610b11ef3e',
    '234c02ecbbfbafa3ed18510abd11fa724fcda2018a1a8342cf064bbde548b12b07df44ba7191d9606ef4081ffde5ad46a5069d9f7f543bedb9c861bf29c7e205132eda9382b0bc2c5c4b45f919cf3a9f1cb74151f6d551f4480c82b2cb24cc5b028aa76eb7b4ab24171ab3cdadb8356f',
    '32510ba9a7b2bba9b8005d43a304b5714cc0bb0c8a34884dd91304b8ad40b62b07df44ba6e9d8a2368e51d04e0e7b207b70b9b8261112bacb6c866a232dfe257527dc29398f5f3251a0d47e503c66e935de81230b59b7afb5f41afa8d661cb',
    '32510ba9aab2a8a4fd06414fb517b5605cc0aa0dc91a8908c2064ba8ad5ea06a029056f47a8ad3306ef5021eafe1ac01a81197847a5c68a1b78769a37bc8f4575432c198ccb4ef63590256e305cd3a9544ee4160ead45aef520489e7da7d835402bca670bda8eb775200b8dabbba246b130f040d8ec6447e2c767f3d30ed81ea2e4c1404e1315a1010e7229be6636aaa',
    '3f561ba9adb4b6ebec54424ba317b564418fac0dd35f8c08d31a1fe9e24fe56808c213f17c81d9607cee021dafe1e001b21ade877a5e68bea88d61b93ac5ee0d562e8e9582f5ef375f0a4ae20ed86e935de81230b59b73fb4302cd95d770c65b40aaa065f2a5e33a5a0bb5dcaba43722130f042f8ec85b7c2070',
    '32510bfbacfbb9befd54415da243e1695ecabd58c519cd4bd2061bbde24eb76a19d84aba34d8de287be84d07e7e9a30ee714979c7e1123a8bd9822a33ecaf512472e8e8f8db3f9635c1949e640c621854eba0d79eccf52ff111284b4cc61d11902aebc66f2b2e436434eacc0aba938220b084800c2ca4e693522643573b2c4ce35050b0cf774201f0fe52ac9f26d71b6cf61a711cc229f77ace7aa88a2f19983122b11be87a59c355d25f8e4',
    '32510bfbacfbb9befd54415da243e1695ecabd58c519cd4bd90f1fa6ea5ba47b01c909ba7696cf606ef40c04afe1ac0aa8148dd066592ded9f8774b529c7ea125d298e8883f5e9305f4b44f915cb2bd05af51373fd9b4af511039fa2d96f83414aaaf261bda2e97b170fb5cce2a53e675c154c0d9681596934777e2275b381ce2e40582afe67650b13e72287ff2270abcf73bb028932836fbdecfecee0a3b894473c1bbeb6b4913a536ce4f9b13f1efff71ea313c8661dd9a4ce',
    '315c4eeaa8b5f8bffd11155ea506b56041c6a00c8a08854dd21a4bbde54ce56801d943ba708b8a3574f40c00fff9e00fa1439fd0654327a3bfc860b92f89ee04132ecb9298f5fd2d5e4b45e40ecc3b9d59e9417df7c95bba410e9aa2ca24c5474da2f276baa3ac325918b2daada43d6712150441c2e04f6565517f317da9d3',
    '271946f9bbb2aeadec111841a81abc300ecaa01bd8069d5cc91005e9fe4aad6e04d513e96d99de2569bc5e50eeeca709b50a8a987f4264edb6896fb537d0a716132ddc938fb0f836480e06ed0fcd6e9759f40462f9cf57f4564186a2c1778f1543efa270bda5e933421cbe88a4a52222190f471e9bd15f652b653b7071aec59a2705081ffe72651d08f822c9ed6d76e48b63ab15d0208573a7eef027',
    '466d06ece998b7a2fb1d464fed2ced7641ddaa3cc31c9941cf110abbf409ed39598005b3399ccfafb61d0315fca0a314be138a9f32503bedac8067f03adbf3575c3b8edc9ba7f537530541ab0f9f3cd04ff50d66f1d559ba520e89a2cb2a83'
)

CRACK = 'The secret message is: When using a stream cipher, never use the key more than once'
#根据异或结果,我们可以推断出,结果大概为:
#The secuet message is Whtn usinw a stream cipher never use the key more than once
#因为密钥为一串有意义的字符,我们可以推断出,其真正含义大概为:
#The secret message is When using a stream cipher never use the key more than once


def strxor(a, b):     # xor two strings of different lengths,因为源代码给的是py2的,这里修改了下改成了py3的
    if len(a) > len(b):
        return "".join([chr(x ^ y) for (x, y) in zip(a[:len(b)], b)])
    else:
        return "".join([chr(ord(x) ^ y) for (x, y) in zip(a, b[:len(a)])])



for MSG in MSGS:
    result = strxor(bytes.fromhex(MSG), bytes.fromhex(TARGET))
    for j in range(0, len(bytes.fromhex(TARGET))):
        if result[j] in potential_str:
            print(result[j],end='')
        else:
            print('*',end='')
    print('')

key = strxor(CRACK, bytes.fromhex(TARGET))

for MSG in MSGS:
    result = strxor(key, bytes.fromhex(MSG))
    print(result)
keyint = ''
for i in range(0,len(key)):
    keyint+=str(ord(key[i]))
Eighth = strxor(key,bytes.fromhex(MSGS[7]))
print(f"key={
     keyint}\n8th message={
     Eighth}")
'''
shell:
**EC**C***T**S***EN**XE*HT******GQ*A****A*O********N**E*A*S*L**EF***O*O**ET***B**CT
***E*E****DM******L*S*N***NT***N*O*****E**E****E*IC****RAU**R*******N*O*******T*NNE
********E*H***S***U*SqE****QU**N*O****R***P******DE**V**NU**I**EAK**TM**EF*********
**********T***S***D***Dw**NAU******N******O*I*****I***E*O******EG******R*I****T***E
*******U*TW***S**EB***Aw******I**RAK***E**O*I*H**U****E*P***A***E*E*NM***A*********
***R*E***TT**S****SI*******T*****H***T**********R*I**V**E*S*E***T*E*A**R*R**A*O**C*
***R*E***TT**S****SI*******O*****Y*****E**A*I*****SN***Rg***R***N*E*OM********EO***
**EC**C*******S***N*SMH***NT**I**I****R***A***H***AN****GU**TT******TM********U***E
*HMP**********ZAG*N**CP**********EAS*****M*C*****ET***IRN***L*H*****C****ET********
t**ES*****S*E*****D**YT****R*SA*W*W*S*****N**P****T*E**RT**EA**EO*EYW****N*H*NRO***
We can factor the number 15 with quantum computers. We can also factor the number 1
Euler would probably enjoy that now his theorem becomes a corner stone of crypto -
The nice thing about Keeyloq is now we cryptographers can drive a lot of fancy cars
The ciphertext produced by a weak encryption algorithm looks as good as ciphertext
You don't want to buy a set of car keys from a guy who specializes in stealing cars
There are two types of cryptography - that which will keep secrets safe from your l
There are two types of cyptography: one that allows the Government to use brute for
We can see the point where the chip is unhappy if a wrong bit is sent and consumes
A (private-key)  encryption scheme states 3 algorithms, namely a procedure for gene
 The Concise OxfordDictionary (2006) deï¬nes crypto as the art of  writing o r sol
key=1025711013720121921620415211653422059914916461752061201701272374016012710720114141197111051765115425248170642615610911214312819210219999254240184972205216232220891169135119519317425223621315667581073813996191782406015497
8th message=We can see the point where the chip is unhappy if a wrong bit is sent and consumes
'''

任务2:破解维吉尼亚密码,和任务3思路很相似

思路:写在代码注释里~(还注释掉了一部分另一种思路的做法)

import string
import re
cipherlist = []
testkeys = []
for i in range(0x00,0xff):
    testkeys.append(i)
#加入所有可能密钥
potentialchars = test_chars = string.ascii_letters + string.digits + ',' + '.' + ' '
re__ = '[A-Za-z0-9,. ]'
def findindexkey(arr):
    global testchars
    global testkeys
    anskeys = list(testkeys)#不要使用anskeys =testkeys,python复习了属于是
    for i in testkeys:
        for s in arr:
            if chr(s ^ i) not in potentialchars:
                anskeys.remove(i)
                break
            #if re.search(re__,str(chr(s ^ i))):
            #    pass
            #else:
            #    anskeys.remove(i)
            #    break
            #使用正则表达式的实现方法
    return anskeys
#找出所有可能密钥,通过删除实现


text = 'F96DE8C227A259C87EE1DA2AED57C93FE5DA36ED4EC87EF2C63AAE5B9A7EFFD673BE4ACF7BE8923CAB1ECE7AF2DA3DA44FCF7AE29235A24C963FF0DF3CA3599A70E5DA36BF1ECE77F8DC34BE129A6CF4D126BF5B9A7CFEDF3EB850D37CF0C63AA2509A76FF9227A55B9A6FE3D720A850D97AB1DD35ED5FCE6BF0D138A84CC931B1F121B44ECE70F6C032BD56C33FF9D320ED5CDF7AFF9226BE5BDE3FF7DD21ED56CF71F5C036A94D963FF8D473A351CE3FE5DA3CB84DDB71F5C17FED51DC3FE8D732BF4D963FF3C727ED4AC87EF5DB27A451D47EFD9230BF47CA6BFEC12ABE4ADF72E29224A84CDF3FF5D720A459D47AF59232A35A9A7AE7D33FB85FCE7AF5923AA31EDB3FF7D33ABF52C33FF0D673A551D93FFCD33DA35BC831B1F43CBF1EDF67F0DF23A15B963FE5DA36ED68D378F4DC36BF5B9A7AFFD121B44ECE76FEDC73BE5DD27AFCD773BA5FC93FE5DA3CB859D26BB1C63CED5CDF3FE2D730B84CDF3FF7DD21ED5ADF7CF0D636BE1EDB79E5D721ED57CE3FE6D320ED57D469F4DC27A85A963FF3C727ED49DF3FFFDD24ED55D470E69E73AC50DE3FE5DA3ABE1EDF67F4C030A44DDF3FF5D73EA250C96BE3D327A84D963FE5DA32B91ED36BB1D132A31ED87AB1D021A255DF71B1C436BF479A7AF0C13AA14794'
for i in range(0,len(text),2):
    cipherlist.append(int(text[i:i+2],16))

for keylenth in range(1,12):
    for index in range(0,keylenth):
        modedlist = cipherlist[index::keylenth]
        anskeys = findindexkey(modedlist)
        #print(f"anskeys={anskeys},index is {index},and at this time the len is {keylenth}")
#此时发现只有7的时候有anskeys结果出现,结果为
'''
anskeys=[186],index is 0,and at this time the len is 7
anskeys=[31],index is 1,and at this time the len is 7
anskeys=[145],index is 2,and at this time the len is 7
anskeys=[178],index is 3,and at this time the len is 7
anskeys=[83],index is 4,and at this time the len is 7
anskeys=[205],index is 5,and at this time the len is 7
anskeys=[62],index is 6,and at this time the len is 7
'''
key = [186,31,145,178,83,205,62]
origin = ''
for i in range(0,len(cipherlist)):
    origin = origin + chr(cipherlist[i] ^ key[i%7])
print(origin)

运行结果:

在这里插入图片描述

任务3:给出一串用维吉尼亚密码加密后的密文,要求使用重合指数法获得明文。

http://www.cryptopals.com/sets/1

思路:先求密钥长度,看密钥可能的长度是多少,然后分片分成每个段的[0],[1]…的位置,依次进行试验,使得每个子段进行维吉尼亚解密后的结果处于正常英文的ASCII序号列表里,更好点的还可以通过进行字母出现频率判断来进一步缩小答案范围,最终范围只有一个。


import base64
import binascii

cipherbase64 = b'HUIfTQsPAh9PE048GmllH0kcDk4TAQsHThsBFkU2AB4BSWQgVB0\dQzNTTmVS\
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'
cipher = base64.b64decode(cipherbase64)
cipher64 = binascii.b2a_hex(base64.b64decode(cipherbase64))
cipherlist = []
for i in range(0,len(cipher64),2):
    cipherlist.append(int(cipher64[i:i+2],16))
#print(cipherlist)
#cipherlist是一个list,里面每项为字符ASCII的int值
dict1 = {
   }
def HammingDistance(list1,list2):
    string = ''
    for i in range(0,len(list1)):
        a = bin(list1[i]^list2[i])
        string+=a[2:]
    return string.count('1')

def hamdistenceaverage(mlist):
  count = 0
  for j in mlist:
      for k in mlist:
        if j != k:
          count += HammingDistance(j,k) / i
  return count
  

for i in range(2,41):
    firstm = cipherlist[0:i]
    secondm = cipherlist[i:2*i]
    thirdm = cipherlist[2*i:3*i]
    fouthm = cipherlist[3*i:4*i]
    mlist = [firstm,secondm,thirdm,fouthm]
    count = hamdistenceaverage(mlist)
    dict1[f'{
     i}'] = count
#此部分用于找KEYSIZE

print(dict1)
list1= sorted(dict1.items(),key=lambda x:x[1])
print(list1)

OptionalKEYSIZE = [29,5,2,24]
'''
[('29', 32.96551724137932), ('5', 34.8), ('2', 36.0), ('24', 36.25), ('7', 36.85714285714286), ('6', 37.0), ('19', 37.1578947368421), ('20', 37.2), 
('3', 37.333333333333336), ('8', 37.5), ('28', 37.85714285714286), ('30', 38.13333333333333), ('34', 38.1764705882353), ('9', 38.22222222222222), ('39', 38.35897435897436), ('10', 38.4), ('17', 38.47058823529411), ('16', 38.5), ('40', 38.6), ('18', 39.0), ('26', 39.0), ('37', 39.027027027027025), ('32', 39.125), ('23', 39.130434782608695), ('38', 39.21052631578947), ('15', 39.33333333333333), ('33', 39.45454545454546), ('21', 39.61904761904762), ('35', 39.65714285714286), ('31', 39.74193548387096), ('25', 39.76), ('13', 39.84615384615385), ('4', 40.0), ('14', 40.142857142857146), ('27', 40.148148148148145), ('22', 40.54545454545455), ('36', 40.611111111111114), ('11', 41.09090909090909), ('12', 41.5)]
'''

def singlekey_xor(cipher):
    '''get the most probable key byte
    cipher: encrypted by the same byte of key(bytes)
    return: the byte of key(bytes)'''
    result = -1
    for i in range(256):
        tempmsg = bytes(
  • 1
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值