第三届“泉信杯”网络空间安全技能大赛
Access
下载附件
https://wwqo.lanzouy.com/iPLQF1glc9fa
打开文件结合文件后缀可以判断这是个日志文件,
看到这底下有个爆破密码的操作,结合题目username和password,应该就是找出这个黑客成功登录后台的账号密码,
我当时就让别人去找了,最后找到一条302
其他的都是200的状态码,只有这个是302状态码
GET /ll/login.php?username=cXp4eA%3d%3d&password=cmpnYw%3d%3d
这里以看就不正常有很多百分号,应该要先来一遍url解码
cXp4eA==和cmpnYw==
一眼丁真,鉴定为base64编码
再次对其解码
qzxx和rjgc
成功拿到flag
Easy JWT
进入页面
就按照他的步骤来吧
先访问第一个链接获取JWT
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoidXNlcm5hbWUifQ.vte7P1fj7SmMpHb4e3jHzeshSkxQl21-yTa9rpPIZOw
找一个在线JWT解密工具
可以在头部看到采用HS256加密,把载荷里的username改成admin
先把密钥留空试试,然后访问第二步的网页
http://120.36.155.11:40510/get_flag/eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1lIjoidXNlcm5hbWUifQ.iDwpHmMRFyuNV4TkM9yFpBwkoh5a5Vi_uE1xIfh5hqc
根本打不开,这里是要有密钥的
当时我根本不知道密钥是什么,看了官方的wp才知道密钥是qziedu
按照官方的密钥
带入第二个网址
那就把username改成admin
最后也是解出来了
Easy PHP
直接进入页面
获取到源码
<?php
highlight_file(__FILE__);
$flag = null;
include '/flag_change';
$a = $_SERVER['argv'][0];
$b = $_SERVER['argv'][1];
$c = $_SERVER['HTTP_CLIENT_IP'];
if ($a == md5($b) && $a != $b && $a == md5($a)) {
if (isset($c)) {
echo $flag;
} else {
echo '请提供一个 client-ip ';
}
}
?>
有a,b,c三个变量。传入的第一个参数为a,第二个参数为b,客户端的ip为c
$_SERVER['argv'][0]的用法:
在web网页模式下:
php.ini里的register_argc_argv配置项是打开的(register_argc_argv = On)
这时候$_SERVER[‘argv’][0]= $_SERVER[‘QUERY_STRING’]
也就是说传入的第一个参数就是$_SERVER[‘argv’][0],而第二个参数时$_SERVER[‘argv’][1]
注意:传参之间用+号隔开
具体参考:https://blog.csdn.net/csdn_azuo/article/details/79092479
首先进行一次if语句的md5绕过,然后要满足c不为空
if的判断:
- a若等于b的md5值
- a不等于b
- a的值与md5后值相等
最后一个c可以在报头里添加client-ip,至此题目思路已经出来了。
我在这里碰到的问题是找不到这个0e在md5后会等于自身的数,在网上找不到这种数,然后也试了几十个数,忘记可以自己写脚本了
还有一点就是两个参数之间用+号隔开
前置知识参考
php弱相等:https://blog.csdn.net/weixin_43836806/article/details/107340486PHP中$_SERVER["QUERY_STRING"]函数: https://www.cnblogs.com/thinksasa/archive/2012/11/11/2765141.html
payload:?0e215962017+s1502113478a
最后加上client-ip就出来了
Stego_text
打开我就觉得不对劲里面有很多方块,跟我之前做的一题有点像,我就在想会不会是不可打印的Unicode字符在里面隐藏了信息
我之前做的那一题:https://www.cnblogs.com/redfish404/articles/17838384.html里面的chekin ktrol
于是我把这些文本放入vscode
确实发现了不少,我在想这会不会是某种加密,把[U+200F]复制下来百度
也知道了它是0宽字符加密
找了几个网站也解密不了,当时也没时间去了解他的加密原理,这题就跳了
接下来开始研究什么是0宽字符加密
关于0宽字符加密和字符编码
前置参考
下面是我自己整理的一点:
[字符编码]链接待补
[0宽字符加解密]链接待补
开始解题
首先要从文本中找出用了几种编码方式
- U+200C ZERO WIDTH NON-JOINER
- U+200E LEFT-TO-RIGHT MARK
- U+200F LEFT-TO-RIGHT MARK
- U+202C POP DIRECTIONAL FORMATTING
- U+FEFF ZERO WIDTH NO-BREAK SPACE
至于U+FEFF是怎么找出来的等会说
然后用写脚本解密或者直接到在线网站上解密都可以
然后把几种出现的编码方式勾选上去
最后一个U+FEFF不确定的话可以先不勾选确定一下然后再勾选确定一
成功拿下flag
----------------------其实应该放到vim里面更好,看到的更全,但是我懒得改了
菜刀
附件下载:https://wwqo.lanzouy.com/iwDPz1gpuzxg
密码:d6ch
很明显这是一道流量分析题,里面大多数为tcp
其中有个这个留意一下
先随便分析一个tcp包
根据返回的报文可以判断它应该是在查目录
要是不确定的话可以把里面的内容解密一下
cmd=%40eval%01%28base64_decode%28%24_POST%5Bz0%5D%29%29%3B&z0=QGluaV9zZXQoImRpc3BsYXlfZXJyb3JzIiwiMCIpO0BzZXRfdGltZV9saW1pdCgwKTtAc2V0X21hZ2ljX3F1b3Rlc19ydW50aW1lKDApO2VjaG8oIi0%2BfCIpOzskRD1iYXNlNjRfZGVjb2RlKCRfUE9TVFsiejEiXSk7JEY9QG9wZW5kaXIoJEQpO2lmKCRGPT1OVUxMKXtlY2hvKCJFUlJPUjovLyBQYXRoIE5vdCBGb3VuZCBPciBObyBQZXJtaXNzaW9uISIpO31lbHNleyRNPU5VTEw7JEw9TlVMTDt3aGlsZSgkTj1AcmVhZGRpcigkRikpeyRQPSRELiIvIi4kTjskVD1AZGF0ZSgiWS1tLWQgSDppOnMiLEBmaWxlbXRpbWUoJFApKTtAJEU9c3Vic3RyKGJhc2VfY29udmVydChAZmlsZXBlcm1zKCRQKSwxMCw4KSwtNCk7JFI9Ilx0Ii4kVC4iXHQiLkBmaWxlc2l6ZSgkUCkuIlx0Ii4kRS4iCiI7aWYoQGlzX2RpcigkUCkpJE0uPSROLiIvIi4kUjtlbHNlICRMLj0kTi4kUjt9ZWNobyAkTS4kTDtAY2xvc2VkaXIoJEYpO307ZWNobygifDwtIik7ZGllKCk7&z1=QzpcXA%3D%3D
首先有很多百分号,先进行url解码
解码后
cmd=@eval(base64_decode($_POST[z0]));&z0=QGluaV9zZXQoImRpc3BsYXlfZXJyb3JzIiwiMCIpO0BzZXRfdGltZV9saW1pdCgwKTtAc2V0X21hZ2ljX3F1b3Rlc19ydW50aW1lKDApO2VjaG8oIi0+fCIpOzskRD1iYXNlNjRfZGVjb2RlKCRfUE9TVFsiejEiXSk7JEY9QG9wZW5kaXIoJEQpO2lmKCRGPT1OVUxMKXtlY2hvKCJFUlJPUjovLyBQYXRoIE5vdCBGb3VuZCBPciBObyBQZXJtaXNzaW9uISIpO31lbHNleyRNPU5VTEw7JEw9TlVMTDt3aGlsZSgkTj1AcmVhZGRpcigkRikpeyRQPSRELiIvIi4kTjskVD1AZGF0ZSgiWS1tLWQgSDppOnMiLEBmaWxlbXRpbWUoJFApKTtAJEU9c3Vic3RyKGJhc2VfY29udmVydChAZmlsZXBlcm1zKCRQKSwxMCw4KSwtNCk7JFI9Ilx0Ii4kVC4iXHQiLkBmaWxlc2l6ZSgkUCkuIlx0Ii4kRS4iCiI7aWYoQGlzX2RpcigkUCkpJE0uPSROLiIvIi4kUjtlbHNlICRMLj0kTi4kUjt9ZWNobyAkTS4kTDtAY2xvc2VkaXIoJEYpO307ZWNobygifDwtIik7ZGllKCk7&z1=QzpcXA==
再进行部分字符base64解码
@ini_set("display_errors","0");
@set_time_limit(0);@set_magic_quotes_runtime(0);
echo("->|");
;$D=base64_decode($_POST["z1"]);$F=@opendir($D);
if($F==NULL){echo("ERROR:// Path Not Found Or No Permission!");}else{$M=NULL;$L=NULL;while($N=@readdir($F)){$P=$D."/".$N;
$T=@date("Y-m-d H:i:s",@filemtime($P));@$E=substr(base_convert(@fileperms($P),10,8),-4);
$R="\t".$T."\t".@filesize($P)."\t".$E."
";
if(@is_dir($P))$M.=$N."/".$R;else $L.=$N.$R;}echo $M.$L;@closedir($F);};echo("|<-");die();π
看不懂。。。
那就继续往后看吧
到后面看到这个,逻辑是就是下载一个hello.rar的文件
下面就是服务器响应的内容
这里因为服务器在响应时使用了Transfer-Encoding选项,所以这里不能直接使用“Save as”保存数据包中的内容再用winhex提取出来(可以是可以,但是这种方式保存下来的数据需要自己写个脚本进行处理然后才能用winhex提取文件,太麻烦)。
如何导出文件?选择“File”->“Export Objects”->“Http”通过这种方式提取出来的http数据,wiresahrk会自动帮我们解决采用Transfer-encoding传输的问题,而不需要我们自己去解决)
这是第五个流所以选择第六个
另存为rar后用16进制打开
把头和尾的|-> <-|去掉
保存
压缩包里面只有一张半个flag的图
所以我们还要分析一下上传逻辑
在这里z2是以89504E470D0A1A0A开头的
这是png的文件头
直接复制出来放到010里面
注意:粘贴的时候要用control+shift+v
最后另一张也出来了
Ez_pic
下载后发现是一张空白的图片
可以直接用binwalk分离
这里我用手动的办法演示一遍
前置知识
常见文件头:
jpg/jpeg
以FFD8开头FFD9结尾
zip
50 4B开头
这里我们找到FFD9,后面跟的是压缩包直接提取出来
把提取的压缩包解压出来后里面有一个getflag.py
#!/usr/bin/env python3
with open('white.jpg', 'rb') as f://以二进制模式打开white.jpg
data = f.read()//把读入的数据存到data
pos = 0xA6 //定义位置在0xA6
data = data[:pos] + b'\x10' + data[pos+1:]//保留pos位置之前的数据,加上0x10的二进制数据,再加上pos+1后的数据
//实际上就是替换pos位置数据为0x10
with open('flag.jpg', 'wb') as f://新建一个flag.jpg将数据移入
f.write(data)
我们找到0xA6的位置,果真被替换成了10
这时候我们就要分析0xA6这个位置到底是存储什么东西的
用010editor的模版分析
将0XA6位置框中然后选择跳转到变量
可以看到0XA6在A5到A7之间,说明它是存储宽度的
这时候可以先猜测一下宽度为500
可以看到flag直接出来了
但是如果宽不为500那要怎么办呢?
我们可以写一个脚本进行宽度爆破
源码如下
import struct
filename = input("file:")//通过input获取用户输入的文件名
with open(filename, 'rb') as f://以rb(二进制读取模式)打开用户提供的文件
all_b = f.read() //把读入的所有二进制数据存入all_b
#w = all_b[165:167] //这里是图片的宽高储存位置,要自己找
#h = all_b[163:165]
for i in range(490,520)://i从490到520
name = str(i) + ".jpg"//文件名等于i加上.jpg
f1 = open(r"./output/" + name,"wb")//打开一个文件用于写入二进制数据,并将文件对象赋值给变量 f1。
im = all_b[:165]+struct.pack('>h',i)+all_b[167:]//将保留文件中165位置以前的数据加上i变成二进制的数据,在加上167位置以后的数据,这个要根据文件填写
//注意这里是[:165]和[167:]一个在数字前加冒号,一个在数字后加冒号
f1.write(im) //最后,代码将修改后的图像数据写入到新创建的文件中,并关闭文件
f1.close()
注意,运行这个脚本的时候,文件夹底下要有output文件夹
改进后的代码
import struct
import os
filename = input("请输入文件名")
output_folder = "./output2/"
os.makedirs(output_folder, exist_ok=True)
with open(filename, 'rb') as f:
all_b = f.read()
#w = all_b[165:167]
#h = all_b[163:165]
for i in range(490,520):
name = str(i) + ".jpg"
f1 = open(r"./output2/" + name,"wb")
im = all_b[:165]+struct.pack('>h',i)+all_b[167:]
f1.write(im)
f1.close()
根据自己的需要调整代码
在生成的文件夹中找到了flag
Easy PHP
直接进入页面
获取到源码
<?php
highlight_file(__FILE__);
$flag = null;
include '/flag_change';
$a = $_SERVER['argv'][0];
$b = $_SERVER['argv'][1];
$c = $_SERVER['HTTP_CLIENT_IP'];
if ($a == md5($b) && $a != $b && $a == md5($a)) {
if (isset($c)) {
echo $flag;
} else {
echo '请提供一个 client-ip ';
}
}
?>
有a,b,c三个变量。传入的第一个参数为a,第二个参数为b,客户端的ip为c
$_SERVER['argv'][0]的用法:
在web网页模式下:
php.ini里的register_argc_argv配置项是打开的(register_argc_argv = On)
这时候$_SERVER[‘argv’][0]= $_SERVER[‘QUERY_STRING’]
也就是说传入的第一个参数就是$_SERVER[‘argv’][0],而第二个参数时$_SERVER[‘argv’][1]
注意:传参之间用+号隔开
具体参考:https://blog.csdn.net/csdn_azuo/article/details/79092479
首先进行一次if语句的md5绕过,然后要满足c不为空
if的判断:
- a若等于b的md5值
- a不等于b
- a的值与md5后值相等
最后一个c可以在报头里添加client-ip,至此题目思路已经出来了。
我在这里碰到的问题是找不到这个0e在md5后会等于自身的数,在网上找不到这种数,然后也试了几十个数,忘记可以自己写脚本了
还有一点就是两个参数之间用+号隔开
前置知识参考
php弱相等:https://blog.csdn.net/weixin_43836806/article/details/107340486PHP中$_SERVER["QUERY_STRING"]函数: https://www.cnblogs.com/thinksasa/archive/2012/11/11/2765141.html
payload:?0e215962017+s1502113478a
最后加上client-ip就出来了
隐流
全是mqtt
随便点一个跟踪tcp流
看官方的wp是说替换0.../python/mqtt为空
我在想为什么要替换这个,后来我想了下,肯是因为除了这个地方其他的都不一样,中间是用这个隔开
把它们提取出来放到txt中替换
得到结果
可以直接搜冒号":"
直接根据冒号分割
base64解码
data.zip base64解码两次
rsa.key base64解码一次
secrets.txt base64解码两次
若解密完有不可打印字符则要用linux命令解密
其中rsa.key的内容是这样的
这个时候就不要再解码了它的格式有
-----BEGIN PRIVATE KEY-----
xxxxxxxxxxx
-----END PRIVATE KEY-----
保存ras.key
data.zip和secret解密出来有不可打印字符
要放到linux里面解密
cat data1.txt | base64 -d>hexdump secret.txt -C
cat secret1.txt | base64 -d>secret.txt
查看它的16进制确认一下
hexdump secret.txt -C
hexdump data.zip -C
//以十六进制和 ASCII 字符混合的形式显示文件内容。它会显示文件内容的十六进制表示和对应的 ASCII 字符。
确保都是正常的
使用 OpenSSL 中的 rsautl
工具来进行 RSA 解密
openssl rsautl -decrypt -in secret.txt -inkey rsa.key
得到解压码
b4ddfa11-4c91-48da-8e57-37d86a3f40ee
flag在1.txt里