解答密码学题目时我们要用到很多网站(有大佬手撸也可以),可参考ctf-wiki,GitHub,Max HackBar脚本以及很多在线网站。
001 base64
一看题目就知道这题和base64
解密有关。
不清楚的可以看刘志军师傅的知乎文章:https://zhuanlan.zhihu.com/p/339477329
打开附件,可以看到是一个txt文件,它的内容是这样的:
Y3liZXJwZWFjZXtXZWxjb21lX3RvX25ld19Xb3JsZCF9
根据题目提示,直接用base64进行解码:
都可以得到正确的答案。下面的题目就以一种方法进行解答了,毕竟每一种方法都很多。
002 Caesar
题目标注了这是个凯撒密码。
在早期,凯撒密码(Caeser Cipher)是指将密文平移三位,后来经过推广,平移个数扩展为任意位,即移位密码(Shift Cipher)
凯撒密码(Caesar)加密时会将明文中的 每个字母 都按照其在字母表中的顺序向后(或向前)移动固定数目(循环移动)作为密文。例如,当偏移量是左移 3 的时候(解密时的密钥就是 3):
明文字母表:ABCDEFGHIJKLMNOPQRSTUVWXYZ 密文字母表:DEFGHIJKLMNOPQRSTUVWXYZABC
使用时,加密者查找明文字母表中需要加密的消息中的每一个字母所在位置,并且写下密文字母表中对应的字母。需要解密的人则根据事先已知的密钥反过来操作,得到原来的明文。例如:
明文:THE QUICK BROWN FOX JUMPS OVER THE LAZY DOG 密文:WKH TXLFN EURZQ IRA MXPSV RYHU WKH ODCB GRJ
转自labster师傅的文章古典密码-凯撒密码Caeser
打开附件,可以看到:
oknqdbqmoq{kag_tmhq_xqmdzqp_omqemd_qzodkbfuaz}
下面进行解答。
当然,如果自己提前已经写好了脚本,直接运行也可以。
003 Morse
很显然就是摩尔斯密码了:打开附件。
11 111 010 000 0 1010 111 100 0 00 000 000 111 00 10 1 0 010 0 000 1 00 10 110
这就是最简单的摩尔斯密码了,直接使用工具,先将1
替换成.
,0
替换成-
,进行解码:
11 111 010 000 0 1010 111 100 0 00 000 000 111 00 10 1 0 010 0 000 1 00 10 110
——>.. ... -.- --- - .-.- ... .-- - -- --- --- ... -- .- . - -.- - --- . -- .- ..-
——>ISKOTSWTMOOSMAETKTOEMAU
感觉不不对,反过来试试
11 111 010 000 0 1010 111 100 0 00 000 000 111 00 10 1 0 010 0 000 1 00 10 110
——>-- --- .-. ... . -.-. --- -.. . .. ... ... --- .. -. - . .-. . ... - .. -. --.
——>MORSECODEISSOINTERESTING
啊这,行吧,答案就是这个,把格式改一下,加上cyberspace{}
,提交,成功!
wp里
ZER0_Nu1L
师傅对于这个问题的思考也很值得我们学习:Morse 编码能用两个符号就能表示26个字母和十个数字,并且不会产生歧义,一定有它的方法。稍微想一下,其实就能想到这个方法,就是用哈夫曼编码。 用
.
表示左分支,用-
表示右分支。 根结点没有数据,第二层左孩子和右孩子分别是.
和-
. 有:$2^5-2<26+10<2^6-2$ . 所以对应的树的深度是 5,亲测正确(手画)。
004 幂数加密
二进制幂数加密通过二进制的几次方表示字母的序号来对信息加密。由二进制转换成十进制的时候,还可以表示成2的N次方的形式。
例如:$15=2^0+2^1+2^2+2^3$
因此我们称这种加密方法为“二进制”的幂数加密。
详细内容可以参考这位师傅的文章:https://zhuanlan.zhihu.com/p/401814787
打开附件可以看到:
8842101220480224404014224202480122
其实幂数加密又名01248密码或云影密码。上网很容易就能搜到。
作者在他的github里是这么描述的:
【云影密码】 此密码运用了1248代码,因为本人才疏学浅,尚未发现有过使用的先例,因此暂归为原创密码,若有密码界前辈认为不妥, 请指出此密码或类似密码的普遍使用历史并附寄一份到我站内邮箱,我将以最快速度核查并改正。由于这个密码,我和片风云影初识,为了纪念,将其命名为“云影密码”,原文请见谜题大全精华区。 原理很简单,有了1,2,4,8这四个简单的数字,你可以以加法表示出0-9任何一个数字,例如0=28,7=124,9=18。 这样,再用1-26来表示A-Z,就可以用作密码了。 为了不至于混乱,我个人引入了第五个数字0,来用作间隔,以避免翻译错误,所以还可以称“01248密码”。
很奇妙的一种想法,我们解题知道这个密码的原理就行,然后继续使用工具(狗头保命!)
格式加上cyberspace{}
,提交,成功!
005 Railfence
打开附件可以看到:
ccehgyaefnpeoobe{lcirg}epriec_ora_g
这道题考的是==栅栏密码==,==crypto-wiki==是这么描述的
所谓栅栏密码,就是将要加密的明文分为N个一组,再从每组的选出一个字母连起来,形成一段无规律的密文。
栅栏密码并非一种强的加密法,其加密原理限制了密钥的最高数量不可能超过明文字母数,而实际加密时密钥数目更少,因此有些密码分析员甚至能用手直接解出明文。
这道题考察的不是简单的栅栏密码,而是它的变种www型栅栏密码。
一开始使用len=35
进行试探,惨遭失败。
WWW型的加密密钥就不只能是字符串长度的因子,小于其长度的任何一个数都可能是其key值,所以第一步也是确定密钥,可以一次次试探。
我们还是使用工具吧!我们编写完程序以后用工具的形式展现结果。
006 不仅仅是Morse
打开附件可以看到:
--/.-/-.--/..--.-/-..././..--.-/..../.-/...-/./..--.-/.-/-./---/-/...././.-./..--.-/-.././-.-./---/-.././..../..../..../..../.-/.-/.-/.-/.-/-.../.-/.-/-.../-.../-.../.-/.-/-.../-.../.-/.-/.-/.-/.-/.-/.-/.-/-.../.-/.-/-.../.-/-.../.-/.-/.-/.-/.-/.-/.-/-.../-.../.-/-.../.-/.-/.-/-.../-.../.-/.-/.-/-.../-.../.-/.-/-.../.-/.-/.-/.-/-.../.-/-.../.-/.-/-.../.-/.-/.-/-.../-.../.-/-.../.-/.-/.-/-.../.-/.-/.-/-.../.-/.-/-.../.-/-.../-.../.-/.-/-.../-.../-.../.-/-.../.-/.-/.-/-.../.-/-.../.-/-.../-.../.-/.-/.-/-.../-.../.-/-.../.-/.-/.-/-.../.-/.-/-.../.-/.-/-.../.-/.-/.-/.-/-.../-.../.-/-.../-.../.-/.-/-.../-.../.-/.-/-.../.-/.-/-.../.-/.-/.-/-.../.-/.-/-.../.-/.-/-.../.-/.-/-.../.-/-.../.-/.-/-.../-.../.-/-.../.-/.-/.-/.-/-.../-.../.-/-.../.-/.-/-.../-.../.-
他说不止Morse,肯定包含morse,先摩尔斯解码,得到:
MAY_BE_HAVE_ANOTHER_DECODEHHHH
AAAAABAABBBAABBAAAAAAAABAABABAAAAAAABBABAAABBAAABBAABAAAABABAABAAABBABAAABAAABAABABBAABBBABAAABABABBAAABBABAAABAABAABAAAABBABBAABBAABAABAAABAABAABAABABAABBABAAAABBABAABBA
他说了还有其他的解码方式,那么针对下面的一堆AB,可以很容易想到培根解密
。
==百度百科==里可以查到:
加密时,明文中的每个字母都会转换成一组五个英文字母。其转换依靠下表:
A/a aaaaa H/h aabbb O/o abbba V/v babab B/b aaaab I/i abaaa P/p abbbb W/w babba C/c aaaba J/j abaab Q/q baaaa X/x babbb D/d aaabb K/k ababa R/r baaab Y/y bbaaa E/e aabaa L/l ababb S/s baaba Z/z bbaab F/f aabab M/m abbaa T/t baabb G/g aabba N/n abbab U/u babaa 加密者需使用两种不同字体,分别代表A和B。准备好一篇包含相同AB字数的假信息后,按照密文格式化假信息,即依密文中每个字母是A还是B分别套用两种字体。
解密时,将上述方法倒转。所有字体一转回A,字体二转回B,以后再按上表拼回字母。
法兰西斯·培根另外准备了一种方法,其将大小写分别看作A与B,可用于无法使用不同字体的场合(例如只能处理纯文本时)。但这样比起字体不同更容易被看出来,而且和语言对大小写的要求也不太兼容。
培根密码本质上是将二进制信息通过样式的区别,加在了正常书写之上。培根密码所包含的信息可以和用于承载其的文章完全无关。
知道它是培根密码直接丢到工具里去就行了。
007 混合编码
打开附件:
JiM3NjsmIzEyMjsmIzY5OyYjMTIwOyYjNzk7JiM4MzsmIzU2OyYjMTIwOyYjNzc7JiM2ODsmIzY5OyYjMTE4OyYjNzc7JiM4NDsmIzY1OyYjNTI7JiM3NjsmIzEyMjsmIzEwNzsmIzUzOyYjNzY7JiMxMjI7JiM2OTsmIzEyMDsmIzc3OyYjODM7JiM1NjsmIzEyMDsmIzc3OyYjNjg7JiMxMDc7JiMxMTg7JiM3NzsmIzg0OyYjNjU7JiMxMjA7JiM3NjsmIzEyMjsmIzY5OyYjMTIwOyYjNzg7JiMxMDU7JiM1NjsmIzEyMDsmIzc3OyYjODQ7JiM2OTsmIzExODsmIzc5OyYjODQ7JiM5OTsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzUwOyYjNzY7JiMxMjI7JiM2OTsmIzEyMDsmIzc4OyYjMTA1OyYjNTY7JiM1MzsmIzc4OyYjMTIxOyYjNTY7JiM1MzsmIzc5OyYjODM7JiM1NjsmIzEyMDsmIzc3OyYjNjg7JiM5OTsmIzExODsmIzc5OyYjODQ7JiM5OTsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzExOTsmIzc2OyYjMTIyOyYjNjk7JiMxMTk7JiM3NzsmIzY3OyYjNTY7JiMxMjA7JiM3NzsmIzY4OyYjNjU7JiMxMTg7JiM3NzsmIzg0OyYjNjU7JiMxMjA7JiM3NjsmIzEyMjsmIzY5OyYjMTE5OyYjNzc7JiMxMDU7JiM1NjsmIzEyMDsmIzc3OyYjNjg7JiM2OTsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzExOTsmIzc2OyYjMTIyOyYjMTA3OyYjNTM7JiM3NjsmIzEyMjsmIzY5OyYjMTE5OyYjNzc7JiM4MzsmIzU2OyYjMTIwOyYjNzc7JiM4NDsmIzEwNzsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzEyMDsmIzc2OyYjMTIyOyYjNjk7JiMxMjA7JiM3ODsmIzY3OyYjNTY7JiMxMjA7JiM3NzsmIzY4OyYjMTAzOyYjMTE4OyYjNzc7JiM4NDsmIzY1OyYjMTE5Ow==
看上去是base64
,解码一下:
┌──(kali㉿kali)-[~]
└─$ echo JiM3NjsmIzEyMjsmIzY5OyYjMTIwOyYjNzk7JiM4MzsmIzU2OyYjMTIwOyYjNzc7JiM2ODsmIzY5OyYjMTE4OyYjNzc7JiM4NDsmIzY1OyYjNTI7JiM3NjsmIzEyMjsmIzEwNzsmIzUzOyYjNzY7JiMxMjI7JiM2OTsmIzEyMDsmIzc3OyYjODM7JiM1NjsmIzEyMDsmIzc3OyYjNjg7JiMxMDc7JiMxMTg7JiM3NzsmIzg0OyYjNjU7JiMxMjA7JiM3NjsmIzEyMjsmIzY5OyYjMTIwOyYjNzg7JiMxMDU7JiM1NjsmIzEyMDsmIzc3OyYjODQ7JiM2OTsmIzExODsmIzc5OyYjODQ7JiM5OTsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzUwOyYjNzY7JiMxMjI7JiM2OTsmIzEyMDsmIzc4OyYjMTA1OyYjNTY7JiM1MzsmIzc4OyYjMTIxOyYjNTY7JiM1MzsmIzc5OyYjODM7JiM1NjsmIzEyMDsmIzc3OyYjNjg7JiM5OTsmIzExODsmIzc5OyYjODQ7JiM5OTsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzExOTsmIzc2OyYjMTIyOyYjNjk7JiMxMTk7JiM3NzsmIzY3OyYjNTY7JiMxMjA7JiM3NzsmIzY4OyYjNjU7JiMxMTg7JiM3NzsmIzg0OyYjNjU7JiMxMjA7JiM3NjsmIzEyMjsmIzY5OyYjMTE5OyYjNzc7JiMxMDU7JiM1NjsmIzEyMDsmIzc3OyYjNjg7JiM2OTsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzExOTsmIzc2OyYjMTIyOyYjMTA3OyYjNTM7JiM3NjsmIzEyMjsmIzY5OyYjMTE5OyYjNzc7JiM4MzsmIzU2OyYjMTIwOyYjNzc7JiM4NDsmIzEwNzsmIzExODsmIzc3OyYjODQ7JiM2OTsmIzEyMDsmIzc2OyYjMTIyOyYjNjk7JiMxMjA7JiM3ODsmIzY3OyYjNTY7JiMxMjA7JiM3NzsmIzY4OyYjMTAzOyYjMTE4OyYjNzc7JiM4NDsmIzY1OyYjMTE5Ow==|base64 -d
LzExOS8xMDEvMTA4Lzk5LzExMS8xMDkvMTAxLzExNi8xMTEvOTcvMTE2LzExNi85Ny85OS8xMDcvOTcvMTEwLzEwMC8xMDAvMTAxLzEwMi8xMDEvMTEwLzk5LzEwMS8xMTkvMTExLzExNC8xMDgvMTAw
我们看到&#+数字
,这是Html实体编码(&#数字型),解码:
得到:
LzExOS8xMDEvMTA4Lzk5LzExMS8xMDkvMTAxLzExNi8xMTEvOTcvMTE2LzExNi85Ny85OS8xMDcvOTcvMTEwLzEwMC8xMDAvMTAxLzEwMi8xMDEvMTEwLzk5LzEwMS8xMTkvMTExLzExNC8xMDgvMTAw
看上去还是很长,继续用base64
解密一下,得到:
/119/101/108/99/111/109/101/116/111/97/116/116/97/99/107/97/110/100/100/101/102/101/110/99/101/119/111/114/108/100
可以看到这是纯数字,中间以/
隔开,且都没有超过127,很明显是ASCII编码,将/
替换为空格,解码一下:
然后和上面一样加上cyberspace{}
提交即可。
008 easy_RSA
打开附件:
在一次RSA密钥对生成中,假设p=473398607161,q=4511491,e=17,求解出d。
我们先了解一下RSA算法原理:
RSA公钥加密算法是1977年由Ron Rivest、Adi Shamirh和LenAdleman在(美国麻省理工学院)开发的。RSA取名来自开发他们三者的名字。RSA是目前最有影响力的公钥加密算法,它能够抵抗到目前为止已知的所有密码攻击,已被ISO推荐为公钥数据加密标准。RSA算法基于一个十分简单的数论事实:将两个大素数相乘十分容易,但那时想要对其乘积进行因式分解却极其困难,因此可以将乘积公开作为加密密钥。
┌──(kali㉿kali)-[~]
└─$ python3
Python 3.9.8 (main, Nov 7 2021, 15:47:09)
[GCC 11.2.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> q=4511491
>>> p=473398607161
>>> e=17
>>> pni=(p-1)*(q-1)
>>> import libnum
>>> d=libnum.invmod(e,pni)
>>> d
125631357777427553
那么flag就是cyberspace{125631357777427553}
009 easychallenge
下载附件可以看到是一个pyc
文件,网上查找一下相关内容:
pyc是一种二进制文件,是由Python文件经过编译后所生成的文件,它是一种byte code,Python文件变成pyc文件后,加载的速度有所提高,而且pyc还是一种跨平台的字节码,由python的虚拟机来执行的,就类似于JAVA或者.NET的虚拟机的概念。pyc的内容与python的版本是相关的,不同版本编译后的pyc文件是不同的,例如2.5版本编译的是pyc文件,而2.4版本编译的python是无法执行的
py文件是可以直接看到源码的,但是一般情况下开发出来的商业软件都不可能直接把源码泄漏出去,这样我们就需要把它编译成pyc文件来保护源码。另外pyc文件也是可以反编译的
可以看到pyc文件是隐蔽的,看不到源码的,而它运行的结果是这样的。
不管输入啥都会瞬间消失。我们可以试着反编译一下查看一下源码,搜一下相关工具,找到了一个只能运行在 python2.7
下的库uncompyle
。
我直接用最新版的python进行了,结果
┌──(kali㉿kali)-[~]
└─$ uncompyle6 1.pyc
I don't know about Python version '3.9.8' yet.
Python versions 3.9 and greater are not supported.
I don't know about Python version '3.9.8' yet.
Python versions 3.9 and greater are not supported.
I don't know about Python version '3.9.8' yet.
Python versions 3.9 and greater are not supported.
I don't know about Python version '3.9.8' yet.
Python versions 3.9 and greater are not supported.
I don't know about Python version '3.9.8' yet.
Python versions 3.9 and greater are not supported.
I don't know about Python version '3.9.8' yet.
Python versions 3.9 and greater are not supported.
Traceback (most recent call last):
File "/usr/local/bin/uncompyle6", line 33, in <module>
sys.exit(load_entry_point('uncompyle6==3.9.0a1', 'console_scripts', 'uncompyle6')())
File "/usr/local/bin/uncompyle6", line 25, in importlib_load_entry_point
return next(matches).load()
File "/usr/lib/python3.9/importlib/metadata.py", line 77, in load
module = import_module(match.group('module'))
File "/usr/lib/python3.9/importlib/__init__.py", line 127, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
File "<frozen importlib._bootstrap>", line 1030, in _gcd_import
File "<frozen importlib._bootstrap>", line 1007, in _find_and_load
File "<frozen importlib._bootstrap>", line 986, in _find_and_load_unlocked
File "<frozen importlib._bootstrap>", line 664, in _load_unlocked
File "<frozen importlib._bootstrap>", line 627, in _load_backward_compatible
File "<frozen zipimport>", line 259, in load_module
File "/usr/local/lib/python3.9/dist-packages/uncompyle6-3.9.0a1-py3.9.egg/uncompyle6/bin/uncompile.py", line 65, in <module>
File "<frozen importlib._bootstrap>", line 1007, in _find_and_load
File "<frozen importlib._bootstrap>", line 986, in _find_and_load_unlocked
File "<frozen importlib._bootstrap>", line 664, in _load_unlocked
File "<frozen importlib._bootstrap>", line 627, in _load_backward_compatible
File "<frozen zipimport>", line 259, in load_module
File "/usr/local/lib/python3.9/dist-packages/uncompyle6-3.9.0a1-py3.9.egg/uncompyle6/verify.py", line 24, in <module>
File "/usr/local/lib/python3.9/dist-packages/xdis-6.0.3-py3.9.egg/xdis/std.py", line 236, in <module>
_std_api = make_std_api()
File "/usr/local/lib/python3.9/dist-packages/xdis-6.0.3-py3.9.egg/xdis/std.py", line 233, in make_std_api
return _StdApi(python_version, variant)
File "/usr/local/lib/python3.9/dist-packages/xdis-6.0.3-py3.9.egg/xdis/std.py", line 78, in __init__
self.opc = opc = get_opcode_module(python_version, variant)
File "/usr/local/lib/python3.9/dist-packages/xdis-6.0.3-py3.9.egg/xdis/op_imports.py", line 180, in get_opcode_module
return op_imports[canonic_python_version[vers_str]]
KeyError: '3.9.8'
我一开始是想管理python库,将 python3.9 的版本转化为 python2.7 。最后再运行库,结果,还是返回相同的报错,总之搞了很长时间都没有解决,所以我换了个python版本是3.8
的虚拟机重新安装第三方库,然后就顺利得到了反编译代码:
# uncompyle6 version 3.8.0
# Python bytecode 2.7 (62211)
# Decompiled from: Python 3.8.10 (default, Nov 26 2021, 20:14:08)
# [GCC 9.3.0]
# Embedded file name: ans.py
# Compiled at: 2018-08-09 11:29:44
import base64
def encode1(ans):
s = ''
for i in ans:
x = ord(i) ^ 36
x = x + 25
s += chr(x)
return s
def encode2(ans):
s = ''
for i in ans:
x = ord(i) + 36
x = x ^ 36
s += chr(x)
return s
def encode3(ans):
return base64.b32encode(ans)
flag = ' '
print 'Please Input your flag:'
flag = raw_input()
final = 'UC7KOWVXWVNKNIC2XCXKHKK2W5NLBKNOUOSK3LNNVWW3E==='
if encode3(encode2(encode1(flag))) == final:
print 'correct'
else:
print 'wrong'
# okay decompiling 1.pyc
观察代码可以发现,UC7KOWVXWVNKNIC2XCXKHKK2W5NLBKNOUOSK3LNNVWW3E===
是一段base32代码,是经过了三次encode最终得到的结果,按照他的过程发过来解码一下就得到了flag
import base64
f='UC7KOWVXWVNKNIC2XCXKHKK2W5NLBKNOUOSK3LNNVWW3E==='
s=base64.b32decode(f)
print(''.join(chr((((i^36)-36)-25)^36) for i in s))
或者按照xctf-wp
给出的
import base64
s="UC7KOWVXWVNKNIC2XCXKHKK2W5NLBKNOUOSK3LNNVWW3E==="
s=base64.b32decode(s)
m = ''
for i in s:
x = ord(i) ^ 36
x = x - 36
m+= chr(x)
h = ''
for i in m:
x = ord(i) - 25
x = x ^ 36
h+= chr(x)
print h
得到flag。
010 转轮机加密
先从block2016了解一下:
转轮机是古典加密方法的集大成者,二战时轴心国普遍应用了该技术,可惜惨遭盟军攻破,德日还蒙在鼓里,一定程度上改变了最终的战局。
转轮机的原理概括起来就是循环置换的多表代换技术,尤其是多筒转轮机,可重复使用数以万计的字母替换表。
以三筒转轮机为例:
有三个可以独立旋转的圆筒,每个圆筒内部有26个输入引脚和26个输出引脚,内部连线使得输入与输出唯一连接。
每按一下输入键(旋转键),快速转子旋转一个引脚,当快速转子转满一轮(循环归位)时,带动中速转子旋转一个引脚,以此类推,类似钟表的秒分时。
今天,转轮机的意义在于它曾经给目前最广泛使用的密码--数据加密标准DES指明了方向。
打开附件以后可以看到:
1: < ZWAXJGDLUBVIQHKYPNTCRMOSFE <
2: < KPBELNACZDTRXMJQOYHGVSFUWI <
3: < BDMAIZVRNSJUWFHTEQGYXPLOCK <
4: < RPLNDVHGFCUKTEBSXQYIZMJWAO <
5: < IHFRLABEUOTSGJVDKCPMNZQWXY <
6: < AMKGHIWPNYCJBFZDRUSLOQXVET <
7: < GWTHSPYBXIZULVKMRAFDCEONJQ <
8: < NOZUTWDCVRJLXKISEFAPMYGHBQ <
9: < XPLTDSRFHENYVUBMCQWAOIKZGJ <
10: < UDNAJFBOWTGVRSCZQKELMXYIHP <
11: < MNBVCXZQWERTPOIUYALSKDJFHG <
12: < LVNCMXZPQOWEIURYTASBKJDFHG <
13: < JZQAWSXCDERFVBGTYHNUMKILOP <
密钥为:2,3,7,5,13,12,9,1,8,10,4,11,6
密文为:NFQKSEVOQOFNP
了解加密原理以后编写脚本求解即可:(别的师傅的wp)
import re
sss = '1: < ZWAXJGDLUBVIQHKYPNTCRMOSFE < 2: < KPBELNACZDTRXMJQOYHGVSFUWI < 3: < BDMAIZVRNSJUWFHTEQGYXPLOCK < 4: < RPLNDVHGFCUKTEBSXQYIZMJWAO < 5: < IHFRLABEUOTSGJVDKCPMNZQWXY < 6: < AMKGHIWPNYCJBFZDRUSLOQXVET < 7: < GWTHSPYBXIZULVKMRAFDCEONJQ < 8: < NOZUTWDCVRJLXKISEFAPMYGHBQ < 9: < XPLTDSRFHENYVUBMCQWAOIKZGJ < 10: < UDNAJFBOWTGVRSCZQKELMXYIHP < 11 < MNBVCXZQWERTPOIUYALSKDJFHG < 12 < LVNCMXZPQOWEIURYTASBKJDFHG < 13 < JZQAWSXCDERFVBGTYHNUMKILOP <'
m = 'NFQKSEVOQOFNP'
# 将sss转化为列表形式
content=re.findall(r'< (.*?) <',sss,re.S)
# re.S:DOTALL,此模式下,"."的匹配不受限制,可匹配任何字符,包括换行符
iv=[2,3,7,5,13,12,9,1,8,10,4,11,6]
print(content)
vvv=[]
for i in range(13):
index=content[iv[i]-1].index(m[i])
vvv.append(index)
print(vvv)
for i in range(0,26):
flag=""
for j in range(13):
flag += content[iv[j]-1][(vvv[j]+i)%26]
print(flag.lower())
知道原理直接手撕其实也是没毛病的。
手动转一下:
NACZDTRXMJQOYHGVSFUWIKPBEL
FHTEQGYXPLOCKBDMAIZVRNSJUW
QGWTHSPYBXIZULVKMRAFDCEONJ
KCPMNZQWXYIHFRLABEUOTSGJVD
SXCDERFVBGTYHNUMKILOPJZQAW
EIURYTASBKJDFHGLVNCMXZPQOW
VUBMCQWAOIKZGJXPLTDSRFHENY
OSFEZWAXJGDLUBVIQHKYPNTCRM
QNOZUTWDCVRJLXKISEFAPMYGHB
OWTGVRSCZQKELMXYIHPUDNAJFB
FCUKTEBSXQYIZMJWAORPLNDVHG
NBVCXZQWERTPOIUYALSKDJFHGM
PNYCJBFZDRUSLOQXVETAMKGHIW
在第 17 列发现有语义的英文:FIREINTHEHOLE
==cyberpeaceP{fireinthehole}==
011 Normal_RSA
打开附件可以看到:
这个类型里可以看到flag.enc
是一个wireshark的文件,那么打开看看:
这么看这个文件就不是wireshark的流量包,上网查找一下:
越看越离谱,算了,还是直接看师傅们的wp吧:
flag.enc
看后缀enc,分析是一个通过openssl加密后生成的文件
pubkey.pem
应该是一个公钥信息文件
官方wp里用到了CTF-RSA-tool
然后我这边就开始倒腾CTF-RSA-tool
,经过了我不懈努力,终于还是决定换一个工具!(这个工具用python2打开少了库,我给python2装了一个pip,然并卵,python3打开报错,可恶)
那么只好踏踏实实的按照上面得到的内容来继续解密,flag.enc
是openssl加密得到的东西,kali里面有这个,我们直接解密:
┌──(kali㉿kali)-[~]
└─$ openssl
OpenSSL> rsa -pubin -text -modulus -in warmup -in pubkey.pem
RSA Public-Key: (256 bit)
Modulus:
00:c2:63:6a:e5:c3:d8:e4:3f:fb:97:ab:09:02:8f:
1a:ac:6c:0b:f6:cd:3d:70:eb:ca:28:1b:ff:e9:7f:
be:30:dd
Exponent: 65537 (0x10001)
Modulus=C2636AE5C3D8E43FFB97AB09028F1AAC6C0BF6CD3D70EBCA281BFFE97FBE30DD
writing RSA key
-----BEGIN PUBLIC KEY-----
MDwwDQYJKoZIhvcNAQEBBQADKwAwKAIhAMJjauXD2OQ/+5erCQKPGqxsC/bNPXDr
yigb/+l/vjDdAgMBAAE=
-----END PUBLIC KEY-----
先将模数转化成10进制,然后借用在线质因数分解网站分解一下:
<img src="https://pic-for-be.oss-cn-hangzhou.aliyuncs.com/img/202205131510421.png" alt="image-20220207102812844" style="zoom:50%;" />
那么可以得到:
- p=275127860351348928173285174381581152299
- q=319576316814478949870590164193048041239
- e=65537
┌──(kali㉿kali)-[~/rsatool]
└─$ python rsatool.py -f PEM -o key.pem -p 275127860351348928173285174381581152299 -q 319576316814478949870590164193048041239
Using (p, q) to initialise RSA instance
n =c2636ae5c3d8e43ffb97ab09028f1aac6c0bf6cd3d70ebca281bffe97fbe30dd
e = 65537 (0x10001)
d =1806799bd44ce649122b78b43060c786f8b77fb1593e0842da063ba0d8728bf1
p = 275127860351348928173285174381581152299 (0xcefbb2cf7e18a98ebedc36e3e7c3b02b)
q = 319576316814478949870590164193048041239 (0xf06c28e91c8922b9c236e23560c09717)
Saving PEM as key.pem
┌──(kali㉿kali)-[~/rsatool]
└─$ openssl rsautl -decrypt -in flag.enc -inkey key.pem PCTF{256b_i5_m3dium}
终于还是师傅们的wp香!
012 easy_ECC
<img src="https://pic-for-be.oss-cn-hangzhou.aliyuncs.com/img/202205131510422.png" alt="image-20220207103914090" style="zoom:50%;" />
先了解一下ECC加密:
椭圆加密算法(ECC)是一种公钥加密体制,最初由Koblitz和Miller两人于1985年提出,其数学基础是利用椭圆曲线上的有理点构成Abel加法群上椭圆离散对数的计算困难性。公钥密码体制根据其所依据的难题一般分为三类:大素数分解问题类、离散对数问题类、椭圆曲线类。有时也把椭圆曲线类归为离散对数类。
原理方面可以参考https://blog.csdn.net/sitebus/article/details/82835492。
打开附件,可以看到:
已知椭圆曲线加密Ep(a,b)参数为
p = 15424654874903
a = 16546484
b = 4548674875
G(6478678675,5636379357093)
私钥为
k = 546768
求公钥K(x,y)
本题没得说,了解好原理以后直接编写脚本求解,然而我是菜鸡,编写脚本比较困难,所以只能白嫖大佬的wp了了:
p=15424654874903
a=16546484
b=4548674875
k=546768
gx=6478678675
gy=5636379357093
def ksm(a,b):
# print(a)
r=1
a=(a%p+p)%p
aa=a
while b:
if b&1:
r=r*a%p
a=a*a%p
b>>=1
print(aa*r%p)
return r
def add(x1,y1,x2,y2):
# k=((ay-by)*ksm((ax-bx+p)%p,p-1)%p+p)%p;
# a=((k*k-ax-bx)%p+p)%p
# b=(k*(ax-(a-p))%p+p)%p
# print(x1,end=" ")
# print(y1);
# print(x2,end=" ")
# print(y2);
if x1==None:
return x2,y2
if x2==None:
return x1,y1
if x1==x2 and y1!=y2:
return None,None
if x1==x2:
m=(3*x1*x1+a)*ksm(2*y1%p,p-2)
else:
m=(y1-y2)*ksm((x1-x2)%p,p-2)
# print(m%p)
x3=m*m-x1-x2
y3=y1+m*(x3-x1)
return x3%p,-y3%p
# k=k-1
rx=None
ry=None
while k:
if k&1:
rx,ry=add(rx,ry,gx,gy)
# print(gx,end=" ")
# print(gy)
gx,gy=add(gx,gy,gx,gy)
k>>=1
# print(rx,end=" ")
# print(ry)
print(rx+ry)
#19477226185390
那么flag就是cyberpeace{19477226185390}
。