0CTF Crypto200(oldcrypto) WriteUp

Reading time ~1 minute

0ctf都过去这么久了,想来网上writeup已然到处都是,不过在这里还是简单记录一下自己比赛当时的解题过程吧……

首先这题给出了加解密的程序:

def encrypt(plaintext, key):
    ciphertext = ""
    for i in xrange(len(plaintext)):
        p = ord(plaintext[i]) - ord('a')
        k = ord(key[i % len(key)]) - ord('a')
        c = (tr[k][p] + i**7) % 26
        ciphertext += chr(c + ord('a'))
    return ciphertext

def decrypt(ciphertext, key):
    plaintext = ""
    for i in xrange(len(ciphertext)):
        c = ord(ciphertext[i]) - ord('a')
        k = ord(key[i % len(key)]) - ord('a')
        p = tr[k][(c - i**7) % 26]
        plaintext += chr(p + ord('a'))
    return plaintext

初看程序会觉得有种好神奇的感觉的说,竟然用了同一个矩阵同时做加解密的置换,只能说矩阵是特殊设计好的了,本来还以为加解密的key值可能不同,观察一下矩阵却发现其实加解密的key应该是一样的,因为矩阵每一行逆过来都是自身。不过,这都是废话,下面开始正式解题:

首先,i**7很明显是多余的部分,于是上来就将i**7从密文中减掉,这样密文每个字母就和明文字母一一对应了,此时,整个程序其实就和维吉尼亚密码很相似了,唯一的区别就是维吉尼亚密码中采取的是偏移量不同的恺撒密码,而这里采取的是26种置换(也就是表中对应的26行)。

于是乎,果断祭出之前破维吉尼亚密码的程序,破维吉尼亚密码的时候,首先是对重合指数进行分析,确定密钥长度,这一步显然对于这题的加密算法也是适用的。然后确定密钥长度后,就是尝试用每一个密钥解密,统计解密出来的字母频率与标准频率的差值,显然我们这里也可以这样,只是需要把解密过程替换下,将凯撒加密替换成这里的置换表。

本来这样很轻松就解决了这题的,结果可曾想,竟然在改程序的时候犯了超二的错,结果一直过不掉,甚至开始怀疑他这里故意破坏了频率:

如上图所示,它这个程序本身是调用的Caesar的encipher来做的解密,由于凯撒加密和解密的区别只是密钥而已,所以他这里是可以的,也正是这样,他下面得到密钥的时候就要用26来减,也就是注释的那句,结果刚开始我忘记改这里了,于是乎就真的就是满满的都是泪……

这题不得不说挺水的,浪费这么多时间不得不说是个悲剧,最后给出比赛时改的代码

挂载网络文件夹后网络故障时文件操作命令卡死

挂载 NFS 或者 Samba 的时候,经常会由于网络故障导致挂载好的链接断掉。此时如果尝试进行 ls、cd、df 等各种命令,只要与此目录沾上边,就会卡住。如果使用了类似 oh-my-zsh 这种配置的,只要在网络目录中,弹出命令提示符前就会直接卡住。这个时候第一反应就是...… Continue reading

路由折腾记 第四弹

Published on September 02, 2017