XSS-Jquery.html()+DOM破坏


靶场:https://xss.pwnfunction.com/challenges/ww3

代码

<!-- Challenge -->
<div>
    <h4>Meme Code</h4>
    <textarea class="form-control" id="meme-code" rows="4"></textarea>
    <div id="notify"></div>
</div>

<script>
    /* Utils */
    const escape = (dirty) => unescape(dirty).replace(/[<>'"=]/g, '');
    const memeTemplate = (img, text) => {
        return (`<style>@import url('https://fonts.googleapis.com/css?family=Oswald:700&display=swap');`+
            `.meme-card{margin:0 auto;width:300px}.meme-card>img{width:300px}`+
            `.meme-card>h1{text-align:center;color:#fff;background:black;margin-top:-5px;`+
            `position:relative;font-family:Oswald,sans-serif;font-weight:700}</style>`+
            `<div class="meme-card"><img src="${img}"><h1>${text}</h1></div>`)
    }
    const memeGen = (that, notify) => {
        if (text && img) {
            template = memeTemplate(img, text)

            if (notify) {
                html = (`<div class="alert alert-warning" role="alert"><b>Meme</b> created from ${DOMPurify.sanitize(text)}</div>`)
            }

            setTimeout(_ => {
                $('#status').remove()
                notify ? ($('#notify').html(html)) : ''
                $('#meme-code').text(template)
            }, 1000)
        }
    }
</script>

<script>
    /* Main */
    let notify = false;
    let text = new URL(location).searchParams.get('text')
    let img = new URL(location).searchParams.get('img')
    if (text && img) {
        document.write(
            `<div class="alert alert-primary" role="alert" id="status">`+
            `<img class="circle" src="${escape(img)}" οnlοad="memeGen(this, notify)">`+
            `Creating meme... (${DOMPurify.sanitize(text)})</div>`
        )
    } else {
        $('#meme-code').text(memeTemplate('https://i.imgur.com/PdbDexI.jpg', 'When you get that WW3 draft letter'))
    }
</script>

在这里插入图片描述
限制为

  • 弹出一个 .alert(1337)sandbox.pwnfunction.com
  • 没有用户交互。
  • 不能使用 。https://sandbox.pwnfunction.com/?html=&js=&css=

在这里插入图片描述 img作为img标签的src属性被写入,且被过滤了关键符号。
在这里插入图片描述
text作为文本被渲染,渲染前都经过一次DOMPurify.sanitize处理

从代码中,我们可以看到一个JavaScript生成的HTML页面,包含用于生成图片和文字的meme模板,以及一个使用DOMPurify来清理输入的防护机制。

分析代码

  1. memeTemplate函数: 用于生成包含图片和文本的meme模板,使用了用户传入的imgtext参数,模板中有一些样式和布局定义。

  2. 输入过滤:

    • escape函数用于清理用户传入的imgtext,去掉了<, >, ', ", =等可能用于XSS攻击的字符。
    • DOMPurify.sanitize()用于防止插入恶意HTML或JavaScript。
  3. 主逻辑

    • 通过URL的参数textimg生成meme。如果这两个参数存在,会使用模板生成一条警告,并在图片加载完成后触发memeGen函数,最终显示meme。

挑战目标

挑战的目的是在不与页面进行交互的情况下触发一个alert(1337)。需要绕过现有的防护措施,比如escapeDOMPurify.sanitize,这两个工具通常会防止注入恶意代码。

绕过方法

  1. 可能的攻击向量

    • escape只去除了几个特定字符,其他的字符可能被忽略。
    • img标签中,当图片加载完成时,memeGen函数会被触发,并且不会对图片的实际内容做进一步验证。
  2. 利用事件属性

    • 我们可以尝试使用其他事件属性,如onerror,因为onload会在图片成功加载时触发,而onerror在图片加载失败时触发。

    • escape不会过滤冒号(:),因此可以尝试使用javascript:协议在图片URL中插入恶意代码。

解决方案

我们可以在img参数中注入一个无效的图片URL,并利用onerror来执行JavaScript代码。

payload
  • ?img=https://i.imgur.com/PdbDexI.jpg&text=<img%20name%3dnotify><style><style%2F><script>alert(1337)%2F%2F

在这里插入图片描述

关键部分:
  1. img=https://i.imgur.com/PdbDexI.jpg:

    • 这是一个合法的图片URL,加载时不会触发onerror,确保图片可以正常显示并调用页面中的逻辑处理。
  2. text=<img%20name%3dnotify><style><style%2F><script>alert(1337)%2F%2F:

    • text参数中的内容包含了<img name="notify">、一个嵌套的<style>标签关闭和一个嵌套的<script>标签。
    • 关键在于这个<style><style/><script>alert(1337)//部分。
如何绕过过滤机制
  • escape()函数用来去掉<, >, ', ", =等字符,但它不会对/, %等符号进行处理。
  • 通过URL编码(即%20表示空格,%3d表示=)成功混淆并避开了过滤机制的限制。
输入解析过程:
  • escape()函数去掉部分特殊字符后,text参数在页面中仍然保留了有用的HTML结构:
    • <img name=notify>:这是一个有效的img标签,它本身不会执行任何恶意代码。
    • <style><style/>:嵌套的style标签被浏览器解析为一个标签的结束,而后一个标签未关闭(<style/>),实际上结束了样式声明的范围。
    • <script>alert(1337)//:接下来,是一个<script>标签,紧随其后的alert(1337)会被执行,后面的//是JavaScript注释符,注释掉后续代码防止报错。
为什么这段代码会执行?
浏览器的宽容性解析
  • 浏览器对不规范的HTML有一定的容错能力。虽然<style>标签是嵌套的,它最终会被解析为合法的样式标签闭合。后续出现的<script>标签会被浏览器认为是一个合法的JavaScript块,从而执行其中的alert(1337)
绕过DOMPurify的清理
  • 使用的<img name=notify>和嵌套<style>标签没有被DOMPurify清理掉。这是因为它们被认为是普通HTML标签,符合预期的内容格式。
  • DOMPurify主要会清理尝试注入的危险内容(如<script>标签),但它可能忽略了嵌套的情况,尤其是在<style>标签后紧跟的<script>标签。浏览器在解析这些HTML时,会按照顺序处理,最终执行<script>标签中的JavaScript。
涉及的安全漏洞与技术知识
XSS (跨站脚本攻击)
  • 成功触发的是一种经典的XSS攻击,通过将恶意JavaScript代码注入到网页中,使其在用户的浏览器中执行。这种攻击类型广泛用于窃取用户信息、会话劫持、恶意重定向等。
HTML的容错机制
  • 浏览器对不完全规范的HTML有很大的容错性。比如,嵌套的<style>标签本来是无效的,但浏览器会自动关闭外层<style>,继续解析内部的标签。

  • 这个宽容的解析机制让<script>标签成功执行,因为浏览器自动处理了<style>标签的闭合,并解析出了有效的<script>块。

DOMPurify绕过
  • DOMPurify 是一个用来防止XSS攻击的工具,它的工作机制是通过清理危险的HTML标签和属性来确保页面安全。然而,在某些复杂的情况下,它可能会被绕过。

  • 本例中,嵌套的<style><script>标签巧妙地利用了DOM解析的特性,使得DOMPurify没有完全过滤掉后续的<script>标签。

总结

  • 利用了浏览器对HTML和CSS解析的容错性。
  • 巧妙地利用了嵌套的<style><script>标签,让过滤器漏掉了恶意代码。
  • 通过混淆和编码的手段避开了部分过滤机制,使得恶意代码最终在用户的浏览器中执行。

这是一种典型的基于XSS的攻击,展示了如何通过不同方式绕过安全措施执行JavaScript代码。

  • 3
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值