比赛之后才知道自己有多菜。
目录
0×00 web1 ezphp
<?php
header("Content-type: text/html; charset=utf-8");
highlight_file(__FILE__);
include("flag.php");
$ip=$_REQUEST['ip'];
if($ip){
shell_exec("ping -c 4 ".$ip);
}
?>
提示:这是一个ping测试程序,但我为什么看不到ping之后的结果呢?
其实这就告诉了我们是无回显命令执行。
我们使用重写
cat flag.php >> flag.txt
写进去之后,再访问flag.txt进行了。
获得flag
0×01 web2 ezBypass
<?php
error_reporting(1);
highlight_file(__FILE__);
include('flag.php');
if ($_GET["shy1"] != hash("md4", $_GET["shy1"]))
{
echo "<br>";
die('Theshy is locked');
}
if (isset($_GET['shy2'])) {
$message = json_decode($_GET['shy2']);
$password ="*********";
if ($message->password == $password) {
$s = $_SERVER['QUERY_STRING'];
if( substr_count($s, '_') !== 0 || substr_count($s, '%5f') != 0 ){
exit('hahahahahaha!');
}
if($_GET['s_h_y_3'] !== '857857' && preg_match('/^857857$/', $_GET['s_h_y_3'])){
echo $flag;
}
}
else {
echo "NONONO";
}
}
else{
echo "GOGOGO";
}
?>
这道题是学长出的ciscn的半决赛的原题的waf,我在网上搜出来了,但是没解析。我只好自己肝了。
这道题考了md4的绕过, json_decode编码,还有个弱类型绕过。
我们主要看shy1,shy2,shy3这三个变量。
md4绕过
if ($_GET["shy1"] != hash("md4", $_GET["shy1"]))
{
echo "<br>";
die('Theshy is locked');
}
md4可以使用科学计数法绕过。我们需要找一个明文是一个科学计数法0e开头的,其加密后密文仍然为0e开头的。
plaintext : 0e001233333333333334557778889
md4 hash : 0e434041524824285414215559233446
这个就符合条件。
json_decode编码绕过
if (isset($_GET['shy2'])) {
$message = json_decode($_GET['shy2']);
$password ="*********";
我们传入的shy2变量会经过json编码,变量password是一串字符串。
JSON在RESTful的网站中是很常用的一种数据传输的格式。这个表单会把一个name为key的input的数据作为json传到服务端。
格式:{“key”:“your input”}
在这里说一下(自己也经常忘):
“= =”与“= = =”比较操作符问题
php有两种比较方式,一种是“= =”一种是“= = =”这两种都可以比较两个数字的大小,但是有很明显的区别。
“= =”:会把两端变量类型转换成相同的,在进行比较。
“= = =”:会先判断两端变量类型是否相同,在进行比较。
注意:这里明确说明,在两个相等的符号中,一个字符串与一个数字相比较时,字符串会转换成数值。
那么password就会被强制转换成数值0。
所以我们构造的payload:shy2={“key”:0}
注意:格式:在**{“key”:“your input”}**里,传入的是字符变量0,我们还需要通过抓包去掉双引号。
弱类型绕过
只有绕过json编码才能进行下一步。
if ($message->password == $password) {
$s = $_SERVER['QUERY_STRING']; //get或者post传参都可以接受
if( substr_count($s, '_') !== 0 || substr_count($s, '%5f') != 0 ){
exit('hahahahahaha!');
}
if($_GET['s_h_y_3'] !== '857857' && preg_match('/^857857$/', $_GET['s_h_y_3'])){
echo $flag; //符 ^ 和 $ 同时使用时,表示精确匹配
}
上面的语句本来就很矛盾。
我们输入的变量里不能有_,但我们的变量是s_h_y_3。
变量不能等于857857但是正则匹配需要匹配到857857才会输出flag。
$_SERVER[‘QUERY_STRING’]不会urlencode。这里主要匹配了_字符,而get会urlencode 本来应该用url绕过但是这里过滤了。
因为在URL中GET请求当输入.或空格或_都会被忽略,所以s_h_y_3即s h y 3或s.h.y.3,我们可以使用s.h.y.3绕过。
url的%0a为换行污染,可以绕过正则,且值为857857。
payload:
s.h.y.3=857857%0a
最终构造payload:
?shy1=0e001233333333333334557778889­2={“password”:0}&s.h.y.3=857857%a
得到flag。
Crypto就不多说了,原题。
0×02 MISC1 ezPNG
图片是这样。
每个最低位图片最上面都有这种情况,应该是最低位隐写。
save bin保存为png图片,就可以得到flag。
0×03 MISC2 ezJPG
这个表情包也被做成了题。
这道题有两种方法。
一个是stegsolve抽帧分析
另一种就是foremost分离图片
时间长都忘了怎么写的了
0×03 MISC3 日志分析
第一问就是让我们找出攻击者的两个IP地址。
找到攻击者第一个IP,同时也解决了问题二攻击者开始爆破的时间。
图片上攻击者开始爆破目录,测试页面。
第二个就是找到secure-20201031(个人理解日志里的安全记录)
攻击者开始对ssh进行暴力破解。找到第二个IP
0×03 MISC3 密码密码密码!!!
是一道取证题,当初没有做出了(kail工具出了问题),现在来弥补一下遗憾。
会写一篇独立的内存取证博客,这里就不详细记录了。