You are my friend
配布されたファイル
def rot13_char(c):
if 'a' <= c <= 'z':
return chr((ord(c) - ord('a') + 13) % 26 + ord('a'))
if 'A' <= c <= 'Z':
return chr((ord(c) - ord('A') + 13) % 26 + ord('A'))
return c
def rot13(text):
return ''.join(rot13_char(c) for c in text)
cts = [238, 55, 26, 13, 30, 30, 21, 56, 58, 43, 60, 40, 52, 45, 6, 47, 48, 33, 53, 51, 62, 24, 37, 61, 5, 56, 7, 23, 83, 123, 44, 56, 52, 24, 7, 23, 15]
ct = ['?'] * len(cts)
ct[0] = 'N'
for i in range(1, len(cts)):
ct[i] = chr(cts[i] ^ ord(ct[i - 1]))
ct = ''.join(ct)
flag = rot13(ct)
key = cts[0] ^ ord(ct[0])
print("ct =", ct)
print("key =", key)
print("flag =", flag)
writeup
ct[0]='N' となっており、与えられたプログラムに書いてある通り rot13('A') = 'N' に変換できます。
また cts は cts[i] ^ ord(ct[i-1]) となっていて XOR を行っているので、逆のことをしてあげれば復元できます。
solver
def rot13_char(c):
if 'a' <= c <= 'z':
return chr((ord(c) - ord('a') + 13) % 26 + ord('a'))
if 'A' <= c <= 'Z':
return chr((ord(c) - ord('A') + 13) % 26 + ord('A'))
return c
def rot13(text):
return ''.join(rot13_char(c) for c in text)
cts = [238, 55, 26, 13, 30, 30, 21, 56, 58, 43, 60, 40, 52, 45, 6, 47, 48, 33, 53, 51, 62, 24, 37, 61, 5, 56, 7, 23, 83, 123, 44, 56, 52, 24, 7, 23, 15]
ct = ['?'] * len(cts)
ct[0] = 'N'
for i in range(1, len(cts)):
ct[i] = chr(cts[i] ^ ord(ct[i - 1]))
ct = ''.join(ct)
flag = rot13(ct)
key = cts[0] ^ ord(ct[0])
print("ct =", ct)
print("key =", key)
print("flag =", flag)
ct = Nycnpn{CyRnFr_YvFgRa_Gb_Zber!ZvNzber}
key = 160
flag = Alpaca{PlEaSe_LiStEn_To_More!MiAmore}
FLAG : Alpaca{PlEaSe_LiStEn_To_More!MiAmore}