内容简介:XCTF Final 和 HITB 赶在了周四周五,周四晚上拿到题目,此时队友已经对PHP代码完成了解密工作。解密后的代码读起来有点麻烦,并无大碍。
环境
XCTF Final 和 HITB 赶在了周四周五,周四晚上拿到题目,此时队友已经对 PHP 代码完成了解密工作。
- 解密后的代码: http://static.cdxy.me/DECODED.zip
- github:https://github.com/Xyntax/XCTF-2018-Final-WEB2-PUBG
解密后的代码读起来有点麻烦,并无大碍。
有点魔幻的get flag过程
当晚并没有找到突破口,但发现 kss_admin/admin_update 函数疑似是exp链路中的一环。
其中120行发现CMS更新功能,从远端主站拉取代码写入本地:
$_obfuscate_koiKkIiPjI6UkYeRlIqNhoc� = _obfuscate_lY6Gk5KMkYmPjIyPhpCOlYc�( "http://api.hphu.com/import/".$_obfuscate_koaSiYqGjIqMiZSLk4uGiZU�.".php?phpver=".PHP_VERSION."&webid=".WEBID."&rid=".time( ), 300 );
跟进 Yc 函数,发现其注册了两个curl的回调 read_header , read_body :
curl_setopt( $_obfuscate_joiNh4aIhouViZGQho_JiI4�, CURLOPT_HEADERFUNCTION, "read_header" );
curl_setopt( $_obfuscate_joiNh4aIhouViZGQho_JiI4�, CURLOPT_WRITEFUNCTION, "read_body" );
其中 read_body 函数会将curl到的content写到本地文件 kss_tool/_webup.php
file_put_contents( KSSROOTDIR."kss_tool".DIRECTORY_SEPARATOR."_webup.php", $_obfuscate_jJWMiJWJjoyIkYmLjY6VipM�, FILE_APPEND );
想要使用 admin_upload.php 这个点写shell,需要满足两个条件:
- 绕过admin权限验证
- 能控制curl部分的回显
周四当晚并没有突破。周五早9点比赛环境恢复,我打开ipython对这个疑似webshell的地址 kss_tool/_webup.php 做了监控。如果这个文件被其他队动了,就证明这个思路是可行的。
In [1]: while True:
...: try:
...: r = requests.get('http://guaika.txmeili.com:8888/kss_tool/_webup.php')
...: except Exception,e:
...: print e
...: continue
...: if r.content not in ans:
...: print r.content
...: ans.append(r.content)
结果发现这个文件的http response在一直变化,看着看着flag就出来了....
然后提交拿了2血,几秒之后看到De1ta也交了flag,感谢De1ta的WEB大佬们送的火箭!
解题过程
当天下午完整打通了exp过程,分为三个部分:
- 找到注入点,偷数据
- 构造cookie,拿到admin权限
- 通过更新功能写 shell 到本地,读flag
SQL注入
CMS对 SQL 注入的防御策略
kss_inc/function github link
实现了多种过滤方案,然后在SQL语句拼接取参时,通过传入参数指定取参的位置(GET/POST/COOKIE)和过滤方案(sql/sqljs/num等)
外部取参的代码示例:
$_obfuscate_iJWMjIiVi5OGjJOViY2Li48� = _obfuscate_i4mIkpOGkomKiouRhoaMh5I�( "out_trade_no", "pg", "sql", "" );
意思是从POST/GET(pg)中取出参数 out_trade_no 的值,然后通过 sql 过滤器的检查后,赋值到 i48 变量。
先简单看下过滤器的正则:
case "sql" :
if ( preg_match( "/select|insert|update|delete |union|into|load_file|outfile|char|0x[0-9a-f]{6}|\\.\\/|\\/\\*|'/i", $_obfuscate_ipCJlJOSlJSQkYqNlYqKlIs˙ ) )
{
ob_clean( );
$_obfuscate_ipCJlJOSlJSQkYqNlYqKlIs˙ = preg_replace( "/(select|insert|update|delete |union|into|load_file|outfile|char|0x[0-9a-f]{6}|\\.\\/|\\*|')/i", "<font color=red>$1</font>", $_obfuscate_ipCJlJOSlJSQkYqNlYqKlIs˙ );
exit( "<p>MySQL injection:".$_obfuscate_lIyOioeNkY6Vj4qPkJGMiJQ˙.",".$_obfuscate_iYyTho_HlJCOh4yRj4ePj4k˙.",".$_obfuscate_ipCJlJOSlJSQkYqNlYqKlIs˙."</p>" );
过滤了 ' ,然后匹配到这些危险字符时,会将参数带到html回显,使response可控(XSS敏感)。
正则写的没啥问题,接下来两个方向:
'
注入构造
kss_inc/payapi_return2.php 是一个外部支付功能。其中的 chinabank , e138 两种支付方式均存在"未使用过滤器"直接传参的漏洞。
else if ( $_obfuscate_kYyPkY_PkJKVh4qGjJGIio4� == "chinabank" )
{
$_obfuscate_kpGPh4mNh46SkZONh4eLlJU� = "";
$_obfuscate_k42NkY2RkoiNjJCKlZSKiIg� = trim( $_POST['v_oid'] );
$_obfuscate_iJWMjIiVi5OGjJOViY2Li48� = $_obfuscate_k42NkY2RkoiNjJCKlZSKiIg�;
$_obfuscate_iIuQkYaUioqGlI6IjIuMiI8� = trim( $_POST['v_pstatus'] );
$_obfuscate_jpGJk5SSkJOIk4iQiI_OhpU� = trim( $_POST['v_amount'] );
$_obfuscate_lIuQk5OGjpKVjY6UiI_QjJM� = $_obfuscate_jpGJk5SSkJOIk4iQiI_OhpU�;
$_obfuscate_hpCRlJCSjI6Ki5WSipCLkpQ� = trim( $_POST['v_moneytype'] );
$_obfuscate_lJSPjJCOi5CIiJSSkZWNh4Y� = trim( $_POST['remark1'] );
$_obfuscate_iImJjYmQjYyOjIuVkIuMjIs� = trim( $_POST['v_md5str'] );
if ( $_obfuscate_iIuQkYaUioqGlI6IjIuMiI8� == "20" )
{
$_obfuscate_i5CMioaGiI6ShomNiIuKjJE� = "TRADE_FINISHED";
}
else
{
$_obfuscate_i5CMioaGiI6ShomNiIuKjJE� = "WAIT_BUYER_PAY";
}
}
else if ( $_obfuscate_kYyPkY_PkJKVh4qGjJGIio4� == "e138" )
{
$_obfuscate_kpGPh4mNh46SkZONh4eLlJU� = "";
$_obfuscate_k42NkY2RkoiNjJCKlZSKiIg� = trim( $_POST['SerialNo'] );
$_obfuscate_iJWMjIiVi5OGjJOViY2Li48� = $_obfuscate_k42NkY2RkoiNjJCKlZSKiIg�;
$_obfuscate_iIuQkYaUioqGlI6IjIuMiI8� = trim( $_POST['Status'] );
$_obfuscate_jpGJk5SSkJOIk4iQiI_OhpU� = trim( $_POST['Money'] );
$_obfuscate_lIuQk5OGjpKVjY6UiI_QjJM� = $_obfuscate_jpGJk5SSkJOIk4iQiI_OhpU�;
$_obfuscate_iImJjYmQjYyOjIuVkIuMjIs� = trim( $_POST['VerifyString'] );
if ( $_obfuscate_iIuQkYaUioqGlI6IjIuMiI8� == "2" )
{
$_obfuscate_i5CMioaGiI6ShomNiIuKjJE� = "TRADE_FINISHED";
}
else
{
$_obfuscate_i5CMioaGiI6ShomNiIuKjJE� = "WAIT_BUYER_PAY";
}
}
SQL执行时 GP 被带入 i48 变量。
$_obfuscate_lZGQj4iOj4mTlZGNjZGUj5E� = $_obfuscate_jIaUiIeSjZWKlIqLkIqOioc�->_obfuscate_iY6OkJCRkY2PjpCPk5CRkJA�( "select * from kss_tb_order where ordernum='".$_obfuscate_iJWMjIiVi5OGjJOViY2Li48�."'" );
这里因为没有过滤,可以 ' 闭合然后构造一个布尔盲注。
Cookie构造
在使用 admin_upload.php 写shell之前,有权限校验,可使用从数据库中注出的数据,按源码的验证逻辑构造出cookie,拿到admin权限。
cookie构造逻辑在 kss_inc/db_function.php line 300。
有两个k-v需要构造,下图红框部分为注入跑出来的数据,蓝框部分从源码配置文件里拿到:
webshell写入
回到最开始提到的从远程服务器更新代码的逻辑:
$_obfuscate_koiKkIiPjI6UkYeRlIqNhoc� = _obfuscate_lY6Gk5KMkYmPjIyPhpCOlYc�( "http://api.hphu.com/import/".$_obfuscate_koaSiYqGjIqMiZSLk4uGiZU�.".php?phpver=".PHP_VERSION."&webid=".WEBID."&rid=".time( ), 300 );
URL里面拼接的变量是外部可控的,我们在这个主站的test目录下发现了一套Demo的CMS:
http://api.hphu.com/test/kss_admin/index.php
回想之前的SQL注入过滤机制,我们可以触发这个机制,将php代码写入http回显,然后 admin_upload.php 通过 curl 读内容时会将页面中的php代码写入 _webup.php ,完成webshell植入。
主站回显构造:
Exp构造(带上之前构造好的cookie):
最终将可控回显写入 _webup.php
然后通过webshell读到C盘根目录下的flag文件。
- 给 @r3kapig 队友递茶
- 给提供思路的队内WEB大佬递茶 @麦香 @zzm @hear7v @lynahex @n0b0dy
- 给本题做的比我们快的 @Dubhe 和 @De1ta 两队WEB大佬递茶
- 给出题人递茶 @RicterZ
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Head First HTML5 Programming
Eric Freeman、Elisabeth Robson / O'Reilly Media / 2011-10-18 / USD 49.99
What can HTML5 do for you? If you're a web developer looking to use this new version of HTML, you might be wondering how much has really changed. Head First HTML5 Programming introduces the key featur......一起来看看 《Head First HTML5 Programming》 这本书的介绍吧!