Python 3 で ROT13 (シーザ暗号) を実装する
1. はじめに
Python 3 には ROT13 が組み込まれているため,シーザー暗号をフルスクラッチで実装する必要はありません。しかし,鍵が 13 で固定されているため,汎用性に欠けています。そこで,本記事ではシーザー暗号の暗号化,復号化,及び,解析 (ブルートフォースアタック) を行うスクリプトを Python 3 で実装し,実行結果を確認します。また,本記事内で行っている作業は,以下の環境下で実行したものです。
- Python Ver.3.6.9
- Zorin OS 15.2 Core (Ubuntu 18.04 LTS)
2. 暗号化スクリプト
以下の平文を暗号化するスクリプトを任意のフォルダ内に encryption.py というファイル名で保存します。encryption.py を実行し,暗号化したい平文と鍵を入力すると,暗号文が出力されます。
1#!/usr/bin/env python32# -*- coding: utf-8 -*-3
4def encrypt(str, key):5 ciphertext = ""6
7 for ch in list(str):8 if 'A' <= ch <= 'Z':9 ciphertext += chr((ord(ch) - ord('A') - key) % 26 + ord('A'))10 elif 'a' <= ch <= 'z':11 ciphertext += chr((ord(ch) - ord('a') - key) % 26 + ord('a'))12 else:13 ciphertext += ch14
15 return ciphertext16
17if __name__ == '__main__':18 plaintext = input("PLEASE INPUT PLAINTEXT : ")19 key = input("PLEASE INPUT KEY : ")20 ciphertext = encrypt(plaintext, int(key))21
22 print("CIPHERTEXT : " + ciphertext)23
24 input("PLEASE PRESS ANY")
1$ python3 encryption.py2PLEASE INPUT PLAINTEXT : Apple3PLEASE INPUT KEY : 134CIPHERTEXT : Nccyr5PLEASE PRESS ANY
3. 復号化スクリプト
以下の暗号文を復号化するスクリプトを任意のフォルダ内に decryption.py というファイル名で保存します。decryption.py を実行し,暗号文と鍵を入力すると,復号された平文が出力されます。
1#!/usr/bin/env python32# -*- coding: utf-8 -*-3
4def deencrypt(str, key):5 plaintext = ""6
7 for ch in list(str):8 if 'A' <= ch <= 'Z':9 plaintext += chr((ord(ch) - ord('A') + key) % 26 + ord('A'))10 elif 'a' <= ch <= 'z':11 plaintext += chr((ord(ch) - ord('a') + key) % 26 + ord('a'))12 else:13 plaintext += ch14
15 return plaintext16
17if __name__ == '__main__':18 ciphertext = input("PLEASE INPUT CIPHERTEXT : ")19 key = input("PLEASE INPUT KEY : ")20 plaintext = deencrypt(ciphertext, int(key))21
22 print("PLAINTEXTtext : " + plaintext)23
24 input("PLEASE PRESS ANY")
1$ python3 decryption.py2PLEASE INPUT CIPHERTEXT : Nccyr3PLEASE INPUT KEY : 134PLAINTEXTtext : Apple5PLEASE PRESS ANY
4. 解析スクリプト
以下の暗号文をブルートフォースアタックによって解析するスクリプトを任意のフォルダ内に bfa.py というファイル名で保存します。bfa.py を実行し,暗号文を入力すると,総当りで解析された平文が出力されます。
1#!/usr/bin/env python32# -*- coding: utf-8 -*-3
4def deencrypt(str, key):5 plaintext = ""6
7 for ch in list(str):8 if 'A' <= ch <= 'Z':9 plaintext += chr((ord(ch) - ord('A') + key) % 26 + ord('A'))10 elif 'a' <= ch <= 'z':11 plaintext += chr((ord(ch) - ord('a') + key) % 26 + ord('a'))12 else:13 plaintext += ch14
15 return plaintext16
17if __name__ == '__main__':18 ciphertext = input("PLEASE INPUT CIPHERTEXT : ")19
20 for i in range(1, 26):21 print('{0:2d}'.format(i) + " : " + deencrypt(ciphertext, i))22
23 input(input("PLEASE PRESS ANY"))
1$ python3 bfa.py2PLEASE INPUT CIPHERTEXT : Nccyr3 1 : Oddzs4 2 : Peeat5 3 : Qffbu6 4 : Rggcv7 5 : Shhdw8 6 : Tiiex9 7 : Ujjfy10 8 : Vkkgz11 9 : Wllha1210 : Xmmib1311 : Ynnjc1412 : Zookd1513 : Apple1614 : Bqqmf1715 : Crrng1816 : Dssoh1917 : Ettpi2018 : Fuuqj2119 : Gvvrk2220 : Hwwsl2321 : Ixxtm2422 : Jyyun2523 : Kzzvo2624 : Laawp2725 : Mbbxq28PLEASE PRESS ANY
5. おわりに
本記事では,シーザー暗号の暗号化,復号化,及び,解析 (ブルートフォースアタック) を行うスクリプトを Python で実装し,その実行結果を確認することが出来た。世の中には,シーザー暗号の他にユニークな古典暗号が数多く存在しています。そこで,今後はそれらの暗号の実装にも取り組んでいきたいと考えています。