记第一次为 CTF 比赛出题的经历和踩过的坑
起因
事情的起因是这样的,我们学校准备办一个什么IT科创嘉年华,然后想办一场名为“网安卫士”的比赛,所以理所应当地找到了我们学校的攻防工作室来出题,自然也就联系上了我
诶不是,有这等好事?那我当然要来掺和一脚嘛,顺带拉上了我们队的其他队员,我们一起为学校的比赛出题
筹备期
最开始告诉我们比赛的时间在 2025.4.25 - 2025.4.27,然后我们开了个在线文档就开始出题了,出题难度是这么跟我们说的
就是比 ADCTF 还要简单,要宝宝巴士难度,让我们弄一些能用常用工具一把梭的
但其实我已经有一些题目的雏形了,于是我先出了我的一道简单题
出题:Herta’s Voidterm
这道题的玩法参考了 Hackergame 2024 的那个终端题(忘了叫啥了),我前些阵子把我网站的 404 页面换成了 Voidterm(随便访问一个不存在的页面你就能看到了),然后我当时在我的这个终端里面塞了 3+1 个 flag(原来是 3 个,后面加了一个),我想把这个拿来出题,于是就有了 MISC 题:Herta’s Voidterm
这道题目分成了三部分,我先把题目描述放在下面
你发现你一不小心获取到了黑塔女士的终端权限,于是你决定寻找一下黑塔女士的小秘密~
- 据说环境中好像有什么不一样的东西?
- 终端里面好像有个网址无法访问?
- 好像有一张奇怪的图片诶?!
因为一开始就说了是宝宝巴士的难度,所以我第一个题目做的是 env 访问环境变量的解题方式,直接输入 env 查看环境变量就能看到 flag 了
这题我自认为确实是宝宝巴士难度,而且我给的提示够明显了
在考虑 flag 的内容的时候,我最开始想到的是小黑塔跟大黑塔编入同一队伍时会有的那个语音
小黑塔:黑塔女士举世无双,黑塔女士聪明绝顶,黑塔女士沉鱼落雁
然后我去搜了这个语音的英语原文,为
Herta: Madam Herta is a peerless gem. Madam Herta is an unrivalled genius. Madam Herta is an inimitable beauty.
然后简单 Leet 一下就有了第一个 flag
接着就开始考虑第二题,之前出那个自己网站上 +1 的题目的时候就想到了之前在 BaseCTF 上做过一道题目,给了一个域名但是无法访问,它那个题目把 flag 丢在了 txt 记录里面
所以我也学着做这样的一个题目,我把第二题的 flag 丢在了我的某个子域名上,然后把这个域名丢到了我这个模拟终端的 /etc/hosts
里面,于是你可以看到提示写的是 终端里面好像有个网址无法访问?
,使用 cat /etc/hosts
就能看到我这个域名了
1 | 100.100.100.100 th3-h3rt4.bili33.top |
于是我就可以打成让参赛选手用 nslookup
或者 dig
查询域名来得到 flag 的方法
接着就来到了第三部分,既然是 MISC 题,肯定不能少了传统的隐写。而且之前大黑塔的 PV 里面有一个很可爱的 Chibi 黑塔
于是我就拿着这张图来做图片隐写,实现了一张图两用:修改高度和文件尾藏脏数据
又刚好在 ADCTF 做了 rkk 的 Black MIDI 那个题目,那个题目采用了 AES 的加密方式,于是我也想用 AES 的加密方式
所以我就把 key 和 iv 一个藏在文件尾,一个藏在 IHDR 高度爆破的底下,但是怎么给加密的数据呢?于是我想到了可以直接在第一题的 env 里面塞,然后我又把加密后的内容放在了 env 里面名为 SECRET 的变量中,细心的参赛选手一定能解出来吧 (*^▽^*)
消息不同步
本来我们商定的比赛时间是 2025.4.25 - 2025.4.27,是四人团队赛,结果发推文的时候跟我说变成两周了???(WTF两周还打什么团队赛啊),于是我们决定提升产能并上难度了
出题:Play CS with Me
题目相关附件:https://github.com/GDUTMeow/Challenge-Play-CS-with-Me
这题的灵感来源于西湖论剑的 CSCS,那个题目是 Cobalt Strike + Counter Strike 1.6,说实话我到现在都还没弄明白 ReHLDs 怎么用,但是不妨碍我出这类型的取证,我先把题目描述丢在下面
Luminoria 在看色图的时候电脑中招啦,黑客从他的电脑里面偷走了一些东西,请你找到黑客拿的东西吧(哦内该
- 1、请你以木马的文件名(包括后缀)计算 md5 后,用
flag{}
包裹即为第一题的 flag- 2、请找到黑客拿走的日志文件,以其内容计算 md5 后,用
flag{}
包裹即为第二题的 flag- 3、请你找到 Luminroia 看的色图,色图即为
flag
如果黑客的木马文件名为
beacon.exe
,则应该使用beacon.exe
进行 md5 计算得到c834b9aa0d91d8a309db78786b7e3a03
,则这题的 flag 为flag{c834b9aa0d91d8a309db78786b7e3a03}
假设从流量中提取到的文件为 abc.txt,里面的内容为
1
2 Hello World!!!
THIS IS AN EXAMPLE LOL应该拿着此文件中的所有内容去计算 MD5,算得结果为
f9b80cd2e0116766a8729570cf036608
,则包裹后为flag{f9b80cd2e0116766a8729570cf036608}
即为本题的 flag
为了出这个取证,我先是去装了两台虚拟机(其实是装了一台,然后复制了),并且为了减少 Windows 系统自身的流量造成的干扰,我特意用了 Tiny11 来做这个题目的附件
然后我掏出了在我硬盘里吃灰的 Cobalt Strike,就开始出题了
本来我最开始的思路是只砍掉 ReHLDs 部分,所以我更换了 Cobalt Strike 的 key,结果我自己做的时候发现……
我!T!M!爆!不!出!来!私!钥!
那这宝宝巴士车更爆不出来了,所以我最后决定不更换这个 key,又因为我使用的 CS 是流传出来的一个版本,所以它的私钥是已知的,然后就省去了爆破的过程
1 | 0x0007 publickey 0x0003 0x0100 30819f300d06092a864886f70d010101050003818d0030818902818100a70991d69d816a601ffa80976473830f0d3b41276d2790401ddedb18e2d3cab3c315e3222325be42b65adb2878f33f5a03ff5010b23e842a510c1482ad6a42f1e7e5726eb31813e7437640ed7879955f401e172c34d3517241596dd41f8e48d3d1b1c288e6c8752ff65dc27acccba4ba9cd6d0e4de6196cea4da480d3b99d0ed020301000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000 Has known private key |
当参赛选手用 1768.py
分析的时候,就会出现上面这里最后写的 Has known private key
,用 -V
参数就可以提取出来,变相降低难度了
我最后想的攻击链路是这样的:
给肉鸡配置 SSLKEY 导出
-> 肉鸡打开wireshark开始抓包
-> 肉鸡开始访问我放在 Cloudflare R2 上的含有 flag 的图片
-> 关闭抓包和浏览器
-> 攻击机生成 Beacon
-> 再次打开肉鸡的 Wireshark 抓 CS 流量
-> 将 Beacon 复制到肉鸡并运行
-> 攻击机发送命令,下载文件
然后我也这么做了,实际操作也没什么问题(出了操作的次序出了问题然后我 retry 了好几次)
就在我自己做的时候,我发现一个问题:我导出来的访问 flag 图片的数据包中过滤 http 没有我的 flag 图啊喂!
我一开始以为是 Cloudflare 的问题,换了 Github Pages 来抓,结果还是没有,结果一看协议统计
这东西是 HTTP/2.0
流量!!!
好吧,HTTP/2.0 对参赛选手不是不能做,只是过滤参数从 HTTP
变成了 HTTP2
而已
于是这题就理所应当地出来了(坏笑٩(•̤̀ᵕ•̤́๑)ᵒᵏᵎᵎᵎᵎ
我把这题丢上了文档,并标注了三个 HARD
难度,等待这题能够爆零然后新生赛复用,诶嘿~☆
群里猫娘趣事
很快我们发现 web 题太少了,于是我们打算出点 web 题目,这个时候看到队友 Ron 的题目没起名字,于是我给了他一张图
你可以在我的 Telegram 频道中找到这张图:https://t.me/PaffChannel/2138
不过他好像没用上 =-=
Web 题都是简单题
很快 web 题就出来很多了,但是都标的 ez
于是我们决定给 web 题上点难度
升旗
没错,那一周刚好轮到我们计算机学院升旗了,还是周一(周一满课,早八高数)……好吧,睡个觉去
出题:你真的懂 Base 嘛
此时我发现我们 Crypto 没有题目,于是我打算来出第一题
题目内容如下
为什么我的 Base 是乱码?好像说来自一个小蓝鸟公司?还与 2 的 11 次方有关?最后还可以一把梭?
题目源码:https://github.com/GDUTMeow/Challenge-Do-You-Really-Know-Base
因为说了要宝宝巴士难度,所以我想到先来个 Base
但是只有 Base 也太太太太太简单了,所以我要来点好玩的
恰巧之前看过 Twitter 有个 Base2048,然后 Basecrack 可以一把梭,于是我就把这两个东西给结合起来,整了个两步梭的 Base 题目
我先把 flag 通过 Base62 -> Base64 -> Base58 -> Ascii85 -> Base92 -> Base32(就只要是不会让 BaseCrack 产生误判的方式都用上了),然后再套一个 Base2048,就完活啦!
出题:Data Cleaning
因为现在的 MISC 题目有点往取证、数据安全和 Web3 的趋势了,所以我也想来弄点数据安全的题目,于是就有了这道题
你的上司交给你了一份名单,这份名单是公司里面所有人员的个人信息,包含了以下内容,且有规则
- 序号
- 姓名:不能包含数字、字母
- 性别:只有男/女
- 身份证号:按照身份证号的校验规则合法
- 用户名:只包含字母和数字,数字不能作为开头
- 密码:随机生成的,题目保证一定不包含
,
'
"
三个符号- 签名:对于每个用户都有一个RSA证书,对应序号保存在cert文件夹中,使用此证书对
用户名_密码_身份证号
进行签名(签名传入的字符串中如规则所述用了下划线连接,使用的是最为常见的填充方式,可以搜搜Cryptographic Token Information Format Standard
)现在老板发现这份名单中有些问题(即不满足以上条件),请你把不符合条件的序号挑出来,用下划线从小到大连接
例如,不合法的序号有
114
514
1919
,则应该连接为114_514_1919
最后用连接后的字符串进行 md5 运算(小写,32位)后得到的结果,使用
flag{}
包裹后提交
这道题我是直接上网找出题脚本然后用 Deepseek 改了一下的,问就是我懒狗,然后第一次 Deepseek 给我改的是用的 MGF1,然后我们测题的时候就反映做不出来
那当然了,MGF1 的参数也太麻烦了
然后就回去找到对话,让 DS 给我改成了用 PKCS1_15,这样也好猜一点,就有了这一题,然后我又在签名那里加了 Cryptographic Token Information Format Standard
的提示
为了让宝宝巴士能够宝宝一点,我真是费尽了心思(擦汗
出题:登录 PRTS 1
普瑞赛斯(Priestess)在 Abyss 中封禁了刀客塔在 PRTS 中的账号,身为刀客塔的你要想尽一切办法获取 PRTS 的权限(但是一定要登录刀客塔的账号吗?
本题构建容器所需要的时间较长,请提前点击构建容器按钮!
- 刀客塔的账号密码
- Username: VFTS352
- Password: 48399110
- 不要在意网站壁纸,找不到好看的 PRTS 图了
这道题主要是因为明日方舟更新了第十五章,然后第十五章里面我们跟牢普操纵的 PRTS 来了一场酣畅淋漓的战斗,然后我就想用舟舟的这个出一个题目
恰好之前暑假参加山石的三天训练营的时候,我做的那一道 Web 题是在 Cookie 塞的目录穿越,然后我就想弄一个目录穿越,但是不太明显的那种
最开始我的设定是在 Cookie 中有个 user 字段,更改 user 字段来返回不同的文件,所以我的代码一开始是这样写的
1 |
|
但是我发现了一个问题,就是这样的话会固定带 .png
文件后缀,如果我输入的是 ../../../../../../etc/passwd
的话,会变成返回 static/img/../../../../../../etc/password.png
,这是有问题的
所以我最后只能改成参数给 filename
,变相的变简单了一点
1 |
|
这样就有了这道题的第一问
出题:登录 PRTS 2
本来这题没想出第二问的,但是但是,上面说到群里说 Web 都是简单题
,然后我就在这题的基础上上难度了
本来是想照搬 VNCTF 的思维导图的那个玩法的,但是我队友说建议放在新生赛,所以只好作罢
而刚好在 CCSSSC2025 的初赛,有一题叫 CachedVisitor,跟思维导图那个题有异曲同工之妙,都是利用了 SSRF + dict 协议的玩法,所以我就按照这个玩法来出了这个第二题,又因为 SSRF + dict 的打法一般都是 Redis 通过 cron 反弹 shell,所以我就按照这个思路来了
首先我又加了一个路由,可以实现 SSRF
1 |
|
然后很快我就发现一个问题,requests
库不支持 dict://
协议,而 httpx
库也是一样的
于是我就去看有没有什么现成的库能够实现 Python3 对 dict://
协议的支持,但是找到的基本都是 Python2 的
这时,我突然想起了我们平时用的 curl
,我在想这东西有没有可能支持 dict://
协议,然后我试了一下,果然可以,于是我的目标就转向了 curl
最开始我是用 os.popen
来运行 curl 的,但是好像有点问题,它会带着 curl 的那个请求时间什么的信息出来
1 | >>> os.popen("curl https://baidu.com").read() |
然后我还得自己手动处理,这会变得比较麻烦,后面查了一下发现有个 pycurl
库可以用
于是就有了第二版的路由
1 |
|
然后不出意外地就出意外了,file
协议有问题,然后我就把 file 单拎出来处理了(直接 open,read,返回)
最后完成了我的题目代码,进入了调试阶段
第一题还是很正常的,到了第二题我发现了一个问题
他喵的为什么我的 shell 反弹不出来啊喂!!!
然后我去搜了一下这个玩法大伙都是怎么玩的,看到了这么一条东西
没错,这个玩法要 CentOS,只有 CentOS 会忽略 crontab 文件里面的错误,挑出正确的来执行
那——好吧,我去换个系统不就完事了呗
这不换不要紧,一换就出事了
CentOS 停更了呀喂!!!
就导致了我 Dockerfile 最开头的 yum 根本就装不到依赖,找了一下得把镜像源的域名改成 vault.centos.org
才行
搞定了镜像源,又遇到了 Python 版本的问题,CentOS 预装 Python 3.6,这东西太老了,我的 Werkzeug==2.1.2
在 3.6 根本就装不上,然后我想的是那我就弄一个现场编译 Python 3.9 的呗,但是还是依赖问题,编译频频出错,直到我找到了有现成的
于是我直接从这里下载,然后创建软链接,才解决了 Python 的问题,测试了一下,这题终于出好了……嘛?
出题:Dino
到了我们要差不多上题测试的时间了,我们逐渐发现 Web 题没有最简单的那种题——F12 查看 flag,于是我又去弄了这一题
Dino
来玩经典的小恐龙吧!
这里我本来想用 2048 的,但是 2048 的 js 和 css 什么的太多了,而且整个 html 的代码量是偏大的,不适合宝宝巴士
然后我突然想起来谷歌小恐龙,于是就拿着小恐龙的代码出了这一题,简单的文本替换而已
出题:ez_traffic
流量分析很简单哦!
这题本来没想出的,但是群里面当时大伙这样说
然后我就出了一道宝宝 traffic,我直接在我的电脑上开了个 Python 的 http.server
,然后用我上面 CS 那道题的虚拟机抓的包,用这台机子访问我的 http.server 然后下载我含有 flag 的图片就搞定了
出题:为什么要演奏春日影!
为什么要演奏春日影!
Luminoria 听了春日影这首歌后,决定将 Soyo 的金句用工具写进春日影中,来帮助修复 Soyo 的心理阴影(真的修复了吗
最后 Luminoria 决定使用一个跟深度求索公司具有同样开头
Deep
的一个工具来将金句写入到春日影这首歌中Soyo: (冲向 Saki 酱,抓住她的手)「拜托了,求求你,要是没有 Saki 酱的话,我就…」
Saki:「放开我 」
Soyo:(跪下来求)「要我怎样做你才肯回来,只要是我能做的,我什么都愿意做 」
Saki:(不屑)「你是抱着多大的觉悟说出这样的话的?」
「你只不过是一个学生,有办法背负他人的人生吗?」
「“什么都愿意做”就是这么沉重的话。不要这么随便说出口。 」
Soyo:「但是,我真的…」
Saki:(甩开手)「你这个人,满脑子只会想到自己呢」(走开 )
Soyo:(跪在原地)
天空中下起了小雨,睦头人看着 Soyo,一言不发
这题是因为刚好在听春日影
而且发现 MISC 题目里面没有音频隐写,于是就出了这个题目
最开始本来想在频谱图里面塞 flag 的, 但是没有找到怎么在频谱图里面塞(经典会做题不会出题了),所以没办法
然后我尝试使用 MP3Stego 和 SlientEye,但是不知道为什么,我用 ffmpeg 转换出来的 wav 音频丢进这两个软件都无法识别是 wav 文件,不是少这个就是少那个
后来我就用 Deepsound 了,直接把 flag 文件塞进去就完事了
本来还想给 Deepsound 设置密码,但是我发现 wav 的备注无法在文件属性里面显示,所以只能不塞密码了,刚好也是宝宝巴士了
出题:Data Analysis
所有数据均为随机生成
校验规范
- 编号:纯数字,最后应该从小到大排列
- 用户名:由数字、字母组成
- 密码:密码 hash 值为 32 位小写 md5 值
- 姓名:由全中文组成
- 性别:只能为
男
或者女
,且身份证号中代表性别的那一位要对应上- 出生日期:由 8 位数字组成,和身份证号中的出生日期码保持一致
- 身份证号:应该符合国家对于身份证号的校验规则,本题中提供的身份证号均符合规则
- 手机号码为 11 位 10 进制数字字符串,前三位的号段限定在以下的集合中
734, 735, 736, 737, 738, 739, 747, 748, 750, 751, 752, 757, 758, 759, 772, 778, 782, 783, 784, 787, 788, 795, 798, 730, 731, 732, 740, 745, 746, 755, 756, 766, 767, 771, 775, 776, 785, 786, 796, 733, 749, 753, 773, 774, 777, 780, 781, 789, 790, 791, 793, 799
题目要求
你应该将每一行都变成与表头相同的顺序排列,表头顺序为
编号, 用户名, 密码, 姓名, 性别, 出生日期, 身份证号, 手机号码
,对应number
username
password
name
gender
birth
id
phone
例如,假设你拿到的数据为(下面数据为瞎编的)
1
2
3
4 编号,用户名,密码,姓名,性别,出生日期,身份证号,手机号码
Luminoria,79811451419,114514200002291919,20000229,小猪佩奇,1,男,e10adc3949ba59abbe56e057f20f883e
20050330,2,c4d038b4bed09fdb1471ef51ec3a32cd,7529876543,男,191981200503301155,刻晴,KeqingMoe则最后你应该把数据变成这样
1
2
3
4 number,username,password,name,gender,birth,id,phone
1,Luminoria,e10adc3949ba59abbe56e057f20f883e,小猪佩奇,男,20000229,114514200002291919,79811451419
2,KeqingMoe,c4d038b4bed09fdb1471ef51ec3a32cd,刻晴,男,20050330,191981200503301155,7529876543将数据以 UTF-8 编码方式保存后,确保最后含有一行空行,将文件内容进行 md5 运算,最后得到的值加上
flag{}
包裹即为最后的答案注意
- 你的换行应该使用
\n
,你可以在调试的时候使用print(repr(data))
来确认这一点- 在你进行 md5 运算的文件内容中,最后有一个空行,就例如上面给你处理后的例子中,最后一行有一个空行
- 你进行 md5 运算的文件内容中,你需要注意不要忘掉首行的表头
本来 DS 只有一道题目的,但是考虑到要每一批都至少有一个吧,所以就整多了两道 DS 的题目
这里的数据是用的 2024 羊城杯的数据(没办法它数据太好看了)
做法跟羊城杯的完全一致,出了没有验数据的平台和我把标头改了而已,因为一点不一样就会导致 md5 完全不一样,所以我对数据格式的要求也比较的严格
改了改就出了这道题目了
出题:Data from Log
所有数据均为随机生成
现在发生了一件很不幸的事情,数据库里面的数据丢失了,我们无法通过数据库来获取需要的内容,所幸的是,阿帕奇的 log 还在
题目要求
现在你需要做下面的这些事情
- 首先,你得从日志中还原出各个用户输入的个人信息,他们包含了
- 用户名:只能由字母和数字组成
- 正确示例:
admin
、Luminoria
、KeqingMoe
、h3ll0World
- 错误示例:
ad_min
、Zhang_san
- 姓名:全中文
- 正确示例:
张三
、李四
- 错误示例:
z三
、李4
- 身份证号:固定为 18 位,符合国家关于身份证的校验规则(本题不设置性别校验)
- 手机号码:为 11 位数字字符串,其中前三位固定在下面的集合中
734, 735, 736, 737, 738, 739, 747, 748, 750, 751, 752, 757, 758, 759, 772, 778, 782, 783, 784, 787, 788, 795, 798, 730, 731, 732, 740, 745, 746, 755, 756, 766, 767, 771, 775, 776, 785, 786, 796, 733, 749, 753, 773, 774, 777, 780, 781, 789, 790, 791, 793, 799
- 密码:由数字和字母组成,没有符号
- 接着,你要对数据进行脱敏
- 用户名:若只有两个字符则只对最后⼀位使⽤ * 号代替,否则只保留第⼀位和最后⼀位字符,其余都⽤ * 号代替,例如“ab”脱敏后就是“a”,“abcde”脱敏后就是“a**e”。
- 密码:对明文密码进行 md5 计算,例如
123456
计算后为e10adc3949ba59abbe56e057f20f883e
- 名字:⼆字姓名对最后⼀位使⽤ * 号代替,三字即以上姓名除第⼀位和最后⼀位以外都使⽤ * 号代替, 例如
张三
脱敏后就是张*
,王不⼆
脱敏后就是王*⼆
- 身份证号:只保留年份,其余都使⽤ * 号代替,例如
172865199108200356
脱敏后就是******1991********
- 手机号码:对 4-7 位的地区编码使⽤ * 号代替,例如
74580417166
脱敏后就是745****7166
- 最后,你应该将脱敏后的所有数据按照
username, password, name, idcard, phone
对应用户名、密码、名字、身份证号、手机号码
的顺序,将所有数据按照 UTF8 编码方式保存,文件的最后应该有一行空行- 表头应该为
username,password,name,idcard,phone
注意
- 你的换行应该使用
\n
,你可以在调试的时候使用print(repr(data))
来确认这一点- 你进行 md5 运算的文件内容中,你需要注意不要忘掉首行的表头
这题也是 2024 羊城杯的数据,而且是原题,我改都没改,要求都跟羊城杯的一致
还是因为每一批都要有一题,所以拿过来直接用,当然因为我懒没有写数据校验平台,所以就……嗯
出题:Is It Really Secure??
还是因为每一批都要有一题,所以我打算给取证加多一题
原题附件:https://github.com/GDUTMeow/Challenge-Is-It-Really-Secure
这题用的是 FTP,因为 FTP 具有明文传输的特性,所以其数据流很容易就能分析,而且也很容易拿到里面的文件
我先用我的服务器搭了一个 FTP 服务
1 | docker run -d -v /home/gamernotitle/docker/vsftpd:/home/vsftpd -v /var/log/vsftpd/:/var/log/vsftpd/ -p 20:20 -p 21:21 -p 20000:20000 -e FTP_USER=Luminoria -e FTP_PASS=my-Str0ng_p@55w0Rd -e PASV_MIN_PORT=20000 -e PASV_MAX_PORT=20000 -e PASV_ADDRESS=192.168.88.128 -e LOG_STDOUT=1 --name vsftpd --restart=always fauria/vsftpd |
这样就可以打开这个 ftp 服务,但是我用抓流量专用机(上面 CS 的机子)抓的时候,发现一直会弹连接被重置,但是这是内网,所以肯定不是我网络的问题
然后我尝试了一下 Filezilla,看到了更详细的内容,它推荐我使用 PASV_MODE 试试,于是我把 PASV_MODE 打开了,就可以了
然后就是正常的抓流量环节
这次为了与第一题进行区分,我还加了伪加密 zip 包
我把 flag 的二维码丢在了 zip 里面,然后用 010 Editor 更改了标头,让这个 zip 包进入伪加密的状态,把伪加密破了就能出 flag 了
修题:登录 PRTS 2
起因是群里 rkk 说有一个更简单的做法
sekaictf-2024 的 exp 是这样写的
1 | import threading |
而我当时出题的时候没有注意 /proc
这个特殊目录的问题,所以导致直接请求读取 /proc/self/environ
就能够出第二题的 flag
甚至甚至,拿着第一题的目录穿越任意文件读取都能够得到 flag,那这就是非预期解了,所以我加入了更多的权限校验,例如如果有 /proc
就直接 403,还有对普瑞赛斯的身份进行校验(下面是一个小片段
1 |
|
然后才把这个地方给堵上了
出题总结
怎么说呢,我真佩服我自己点子那么多
当然本次出题也出现了考虑不周全的问题,还有就是对环境不熟悉的问题(上面 CentOS 那个),不过这次出题确实出爽了,有简单的,也有难的
出题跟做题都是很有意思的事情,下次继续(诶嘿
现在就等比赛开始了,比赛打完了再来更下面吧
比赛中
这次比赛我们班其实有三个队伍,但是说实在的他们都比较小白,体现在什么方面呢?逆向没有 IDA,流量分析没有 Wireshark,就最基础的这些工具其实我们班的兄弟们也不知道,但是我是出题的我也不可能跟他们说这些东西
本次比赛的难度分级为 Easy
< Normal
< Hard
< Expert
< Master
第一批
第一批里面我的题是相对简单的,给了
- [easy] 签个到吧(关注公众号发关键词,上面没写)
- [easy] Dino(F12 看注释)
- [easy] ez_traffic(wireshark 打开后直接导出 HTTP 文件)
- [easy] 为什么要演奏春日影(Deepsound 提取文件)
- [easy] 你真的懂 Base 嘛(Base 大杂烩)
- [easy] Data Cleaning(数据清理,脚本题)
其中签到不必多说,Dino 也是上来就出了,这两个算比较简单的
其次是 ez_traffic 和 Data Cleaning,因为说实话,只要懂得处理拿到的文件就能够拿分,这两题,所以也是偏简单的
比较好玩的应该是春日影那个题,各种各样的 flag 都出来了
我承认你对本番的理解很到位,但是这不是正确答案 =-=
不过最令我惊奇的是 Base 大杂烩难倒了好多人,我原本的想法就是如果你去搜 Twitter
Base
2048
,很容易搜到 Base2048
这个东西,然后写一个简单的 Python 脚本先脱 2048 这一层
1 | import base2048 |
然后再去搜 Base
一把梭
搜到 Basecrack,直接就能够用 basecrack 解开这个大杂烩
但是好像我们的参赛选手好像不知道后面还有,认为解开 2048 出来的那串字符串就是 flag,然后就交上去了,所以就能看到这样的提交记录
到了大概 23:45 的时候,看着还是没人出,我就给了三个提示
💡提示1:将内容从乱码变成一串由 ASCII 字符组成的字符串后还有步骤,脱离不开题目名字,关注一下题目的最后一句话
💡提示2:当你解出来的内容是以
flag{
开头的,那你就得到 flag 了💡提示3:flag 是有意义的一句话
因为第二天要打蓝桥杯了(蓝桥的网安是屎,别报!信我!),所以我睡得比较早,早上起来一看已经有两个队伍做出来了,挺好的
第二批
第二批我给的题目有这些
- [easy*2] [normal] Herta’s Voidterm
- [normal] [hard] 登录 PRTS
- [easy] Data Analysis
- [easy] Is It Really Secure??
当我打完蓝桥杯的时候,登录 QQ 和微信发现群里有人艾特我,说 PRTS 题目出了问题
一看,发现是我忘记删掉注释了
好吧,重新弄了一下上线了……
我其实没太想到本次的 Herta’s Voidterm 能够难住不少人
第一问很简单,env
一下就出来了,这个没啥问题,但是第二问好像大伙都不知道域名还有 TXT
类型记录可以用来存内容
后面也是加了点提示
然后第三问因为我看到提交记录里面有交 AES 的向量的
于是我也给第三问来了点提示
说到简单题,还有一个简单题 Is It Really Secure??
,我特意在 ftp 里面留了坑,我的 ftp 认证密码是 my-Str0ng_p@55w0Rd
然后真有队伍交了 flag{my-Str0ng_p@55w0Rd}
看来这坑没白埋 (*^▽^*)
当然,还有中第二个坑的
估计可能大伙不知道什么叫 ZIP 伪加密吧
不过这一部分最令我开心的应该是 PRTS 有人做,而且有人出(虽然只出了第一题)
然后有个哥们想复杂了
我寻思我也没有 import pickle
啊 🤔
当然,在多方面的提示下,有一个队伍出了 PRTS 2
有人能对上电波我还是很开心的,不仅这题,黑塔终端 3 也有人对上电波了
可能是一张图两用太难想了?还有就是估计很多队伍第一问看到 SECRET 没当回事
Data Analysis 那个题目,我题目的要求是对内容进行 md5 计算,不过我当时是把文件丢进赛博厨子计算的,然后可能是不同系统对剪贴板的处理不一样,有人用 macOS 在数据正确的前提下出了错误的答案
看来下次还是不能省掉检验用的那个网页 =-=
第三批
第三批是难度比较高的,我的题目有这些
- [expert*2] [master] Play CS with Me
- [normal] Data from Log
因为劳动节补课,周日要上课,原定周日早上十点放题目的,放到了周六晚上七点放了
这里首先要给参赛选手道歉的是,我在题目 Data from Log 的附件里面给的 README.md
写的跟题目详情页面不一样,在这里向各位道个歉 orz
Data from Log 涉及到了从阿帕奇的日志中恢复数据,这题是从羊城杯偷的,所以数据上没什么好说的
不过让我欣喜的是 Play CS with Me 没有爆零,第一题有人在提示下出了
这个搜索能力挺不错的,在这里表扬一下 (๑•̀ㅂ•́)و✧
当然也少不了跳我挖好的坑
说实话,我也想改这个 evil.exe
为其他更具有迷惑力的名字,但是不管我怎么保存那个代表 beacon 的 hta 文件,这里都不会变,可能是 hta 类型文件最后在这里显示固定为 evil.exe
吧,这点我确实不太清楚
接着这个队伍又继续攻克第二问,但是但是,他们找的教程实在是……戛然而止
他们找的是这一篇:https://www.freebuf.com/articles/system/327060.html
然后我还是提醒了一嘴
他们应该是搜到后续了,快出了——确实出了,最后一分钟
好极限,恭喜这个队伍用 Play CS with Me 1 和 2 超过了原来的第一
收 Writeup
比赛完了以后最爽的应该是看各个队伍的 wp 了,看看他们有没有按照我们预定的思路去做题,其实大部分都是按照我的想法来的,不过也有一些跟我用的工具不太一样
例如说 base 那个题目,有一队就用的不是 basecrack 而是用的随波逐流,也是让我第一次知道随波逐流还有这功能了
总结
所以以上就是本次出题的经历啦,后面应该还会出更多的题目的٩(๑^o^๑)۶
下次再有出题的话再写这样的记录吧
题目源码
- 【MISC】Herta’s Voidterm https://github.com/GDUTMeow/Challenge-Hertas-Voidterm
- 【DS】Data from Log https://github.com/GDUTMeow/Challenge-Data-from-Log
- 【Web】登录 PRTS https://github.com/GDUTMeow/Challenge-Login-PRTS
- 【Forensic】Is It Really Secure?? https://github.com/GDUTMeow/Challenge-Is-It-Really-Secure
- 【DS】Data Analysis https://github.com/GDUTMeow/Challenge-Data-Analysis
- 【DS】Data Cleaning https://github.com/GDUTMeow/Challenge-DataCleaning
- 【MISC】为什么要演奏春日影! https://github.com/GDUTMeow/Challenge-Haruhikage
- 【Web】Dino https://github.com/GDUTMeow/Challenge-Dino
- 【Forensic】ez_traffic https://github.com/GDUTMeow/Challenge-eztraffic
- 【Crypto】你真的懂 Base 嘛 https://github.com/GDUTMeow/Challenge-Do-You-Really-Know-Base
- 【Forensic】Play CS with Me https://github.com/GDUTMeow/Challenge-Play-CS-with-Me