DOM XSS
Reading time: 10 minutes
tip
Вивчайте та практикуйте AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Вивчайте та практикуйте GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Вивчайте та практикуйте Azure Hacking:
HackTricks Training Azure Red Team Expert (AzRTE)
Підтримайте HackTricks
- Перевірте плани підписки!
- Приєднуйтесь до 💬 групи Discord або групи telegram або слідкуйте за нами в Twitter 🐦 @hacktricks_live.
- Діліться хакерськими трюками, надсилаючи PR до HackTricks та HackTricks Cloud репозиторіїв на github.
DOM Вразливості
DOM вразливості виникають, коли дані з джерел, контрольованих зловмисником sources (як-от location.search
, document.referrer
або document.cookie
), небезпечно передаються до sinks. Sinks — це функції або об'єкти (наприклад, eval()
, document.body.innerHTML
), які можуть виконувати або відображати шкідливий контент, якщо отримують зловмисні дані.
- Sources — це вхідні дані, які можуть бути маніпульовані зловмисниками, включаючи URL-адреси, куки та веб-повідомлення.
- Sinks — це потенційно небезпечні кінцеві точки, де зловмисні дані можуть призвести до негативних наслідків, таких як виконання скриптів.
Ризик виникає, коли дані течуть з джерела до sink без належної валідації або очищення, що дозволяє атакам, таким як XSS.
tip
Ви можете знайти більш актуальний список джерел і sinks на https://github.com/wisec/domxsswiki/wiki
Звичайні джерела:
document.URL
document.documentURI
document.URLUnencoded
document.baseURI
location
document.cookie
document.referrer
window.name
history.pushState
history.replaceState
localStorage
sessionStorage
IndexedDB(mozIndexedDB, webkitIndexedDB, msIndexedDB)
Database
Загальні місця витоку:
Відкритий редирект | Впровадження Javascript | Маніпуляція даними DOM | jQuery |
---|---|---|---|
location | eval() | scriptElement.src | add() |
location.host | Function() constructor | scriptElement.text | after() |
location.hostname | setTimeout() | scriptElement.textContent | append() |
location.href | setInterval() | scriptElement.innerText | animate() |
location.pathname | setImmediate() | someDOMElement.setAttribute() | insertAfter() |
location.search | execCommand() | someDOMElement.search | insertBefore() |
location.protocol | execScript() | someDOMElement.text | before() |
location.assign() | msSetImmediate() | someDOMElement.textContent | html() |
location.replace() | range.createContextualFragment() | someDOMElement.innerText | prepend() |
open() | crypto.generateCRMFRequest() | someDOMElement.outerText | replaceAll() |
domElem.srcdoc | ``Маніпуляція локальним шляхом файлу | someDOMElement.value | replaceWith() |
XMLHttpRequest.open() | FileReader.readAsArrayBuffer() | someDOMElement.name | wrap() |
XMLHttpRequest.send() | FileReader.readAsBinaryString() | someDOMElement.target | wrapInner() |
jQuery.ajax() | FileReader.readAsDataURL() | someDOMElement.method | wrapAll() |
$.ajax() | FileReader.readAsText() | someDOMElement.type | has() |
``Маніпуляція Ajax запитами | FileReader.readAsFile() | someDOMElement.backgroundImage | constructor() |
XMLHttpRequest.setRequestHeader() | FileReader.root.getFile() | someDOMElement.cssText | init() |
XMLHttpRequest.open() | FileReader.root.getFile() | someDOMElement.codebase | index() |
XMLHttpRequest.send() | Маніпуляція посиланнями | someDOMElement.innerHTML | jQuery.parseHTML() |
jQuery.globalEval() | someDOMElement.href | someDOMElement.outerHTML | $.parseHTML() |
$.globalEval() | someDOMElement.src | someDOMElement.insertAdjacentHTML | Впровадження JSON на стороні клієнта |
``Маніпуляція HTML5-сховищем | someDOMElement.action | someDOMElement.onevent | JSON.parse() |
sessionStorage.setItem() | Впровадження XPath | document.write() | jQuery.parseJSON() |
localStorage.setItem() | document.evaluate() | document.writeln() | $.parseJSON() |
**[**`Відмова в обслуговуванні`**](dom-xss.md#denial-of-service)** | someDOMElement.evaluate() | document.title | ``Маніпуляція куками |
requestFileSystem() | ``Маніпуляція доменом документа | document.implementation.createHTMLDocument() | document.cookie |
RegExp() | document.domain | history.pushState() | Отруєння URL WebSocket |
Впровадження SQl на стороні клієнта | Маніпуляція веб-повідомленнями | history.replaceState() | WebSocket |
executeSql() | postMessage() | `` | `` |
Синк innerHTML
не приймає script
елементи в жодному сучасному браузері, і події svg onload
не спрацюють. Це означає, що вам потрібно буде використовувати альтернативні елементи, такі як img
або iframe
.
Цей вид XSS, ймовірно, є найскладнішим для виявлення, оскільки вам потрібно заглянути в код JS, перевірити, чи використовується будь-який об'єкт, значення якого ви контролюєте, і в такому випадку перевірити, чи є будь-який спосіб зловживання ним для виконання довільного JS.
Інструменти для їх виявлення
- https://github.com/mozilla/eslint-plugin-no-unsanitized
- Розширення браузера для перевірки всіх даних, які досягають потенційного місця витоку: https://github.com/kevin-mizu/domloggerpp
Приклади
Відкритий редирект
З: https://portswigger.net/web-security/dom-based/open-redirection
Вразливості відкритого редиректу в DOM виникають, коли скрипт записує дані, які може контролювати зловмисник, у місце витоку, здатне ініціювати навігацію між доменами.
Важливо розуміти, що виконання довільного коду, такого як javascript:alert(1)
, можливе, якщо ви контролюєте початок URL, де відбувається редирект.
Місця витоку:
location
location.host
location.hostname
location.href
location.pathname
location.search
location.protocol
location.assign()
location.replace()
open()
domElem.srcdoc
XMLHttpRequest.open()
XMLHttpRequest.send()
jQuery.ajax()
$.ajax()
Маніпуляція з куками
З: https://portswigger.net/web-security/dom-based/cookie-manipulation
Вразливості маніпуляції з куками на основі DOM виникають, коли скрипт включає дані, які можуть контролюватися зловмисником, у значення куки. Ця вразливість може призвести до несподіваної поведінки веб-сторінки, якщо кука використовується на сайті. Крім того, її можна експлуатувати для проведення атаки фіксації сесії, якщо кука залучена до відстеження сесій користувачів. Основний "синк", пов'язаний з цією вразливістю, це:
Синки:
document.cookie
JavaScript Injection
From: https://portswigger.net/web-security/dom-based/javascript-injection
Вразливості DOM-орієнтованої ін'єкції JavaScript виникають, коли скрипт виконує дані, які можуть контролюватися зловмисником, як код JavaScript.
Sinks:
eval()
Function() constructor
setTimeout()
setInterval()
setImmediate()
execCommand()
execScript()
msSetImmediate()
range.createContextualFragment()
crypto.generateCRMFRequest()
Маніпуляція з документом-доменом
From: https://portswigger.net/web-security/dom-based/document-domain-manipulation
Вразливості маніпуляції з документом-доменом виникають, коли скрипт встановлює властивість document.domain
, використовуючи дані, якими може керувати зловмисник.
Властивість document.domain
відіграє ключову роль у забезпеченні політики однакового походження браузерами. Коли дві сторінки з різних походжень встановлюють свій document.domain
на однакове значення, вони можуть взаємодіяти без обмежень. Хоча браузери накладають певні обмеження на значення, які можна призначити document.domain
, заважаючи призначенню абсолютно несумісних значень фактичному походженню сторінки, існують винятки. Зазвичай браузери дозволяють використання дочірніх або батьківських доменів.
Sinks:
document.domain
WebSocket-URL poisoning
From: https://portswigger.net/web-security/dom-based/websocket-url-poisoning
WebSocket-URL poisoning відбувається, коли скрипт використовує керовані дані як цільовий URL для з'єднання WebSocket.
Sinks:
Конструктор WebSocket
може призвести до вразливостей WebSocket-URL poisoning.
Link manipulation
From: https://portswigger.net/web-security/dom-based/link-manipulation
Вразливості маніпуляції з посиланнями на основі DOM виникають, коли скрипт записує дані, контрольовані атакуючим, до цільового навігаційного елемента на поточній сторінці, такого як клікабельне посилання або URL для відправки форми.
Sinks:
someDOMElement.href
someDOMElement.src
someDOMElement.action
Маніпуляція запитом Ajax
З: https://portswigger.net/web-security/dom-based/ajax-request-header-manipulation
Вразливості маніпуляції запитом Ajax виникають, коли скрипт записує дані, контрольовані атакуючими, у запит Ajax, який надсилається за допомогою об'єкта XmlHttpRequest
.
Синьки:
XMLHttpRequest.setRequestHeader()
XMLHttpRequest.open()
XMLHttpRequest.send()
jQuery.globalEval()
$.globalEval()
Локальна маніпуляція шляхом до файлу
З: https://portswigger.net/web-security/dom-based/local-file-path-manipulation
Вразливості локальної маніпуляції шляхом до файлу виникають, коли скрипт передає дані, контрольовані атакуючим, до API обробки файлів як параметр filename
. Цю вразливість може експлуатувати атакуючий, щоб створити URL, який, якщо його відвідає інший користувач, може призвести до відкриття або запису випадкового локального файлу в браузері користувача.
Sinks:
FileReader.readAsArrayBuffer()
FileReader.readAsBinaryString()
FileReader.readAsDataURL()
FileReader.readAsText()
FileReader.readAsFile()
FileReader.root.getFile()
FileReader.root.getFile()
Client-Side SQl injection
From: https://portswigger.net/web-security/dom-based/client-side-sql-injection
Вразливості SQL-ін'єкцій на стороні клієнта виникають, коли скрипт включає дані, контрольовані атакуючим, у SQL-запит на стороні клієнта ненадійним способом.
Sinks:
executeSql()
HTML5-storage manipulation
From: https://portswigger.net/web-security/dom-based/html5-storage-manipulation
Вразливості маніпуляцій з HTML5-сховищем виникають, коли скрипт зберігає дані, контрольовані атакуючим, у HTML5-сховищі веб-браузера (localStorage
або sessionStorage
). Хоча ця дія сама по собі не є вразливістю безпеки, вона стає проблематичною, якщо програма потім читає збережені дані та обробляє їх ненадійно. Це може дозволити атакуючому використовувати механізм сховища для проведення інших атак на основі DOM, таких як міжсайтове скриптування та ін'єкція JavaScript.
Sinks:
sessionStorage.setItem()
localStorage.setItem()
XPath ін'єкція
From: https://portswigger.net/web-security/dom-based/client-side-xpath-injection
Вразливості DOM-ін'єкції XPath виникають, коли скрипт включає дані, контрольовані атакуючими, в запит XPath.
Sinks:
document.evaluate()
someDOMElement.evaluate()
Впровадження JSON на стороні клієнта
З: https://portswigger.net/web-security/dom-based/client-side-json-injection
Вразливості впровадження JSON на основі DOM виникають, коли скрипт включає дані, контрольовані зловмисником, у рядок, який розбирається як структура даних JSON, а потім обробляється додатком.
Синки:
JSON.parse()
jQuery.parseJSON()
$.parseJSON()
Веб-маніпуляція повідомленнями
From: https://portswigger.net/web-security/dom-based/web-message-manipulation
Вразливості веб-повідомлень виникають, коли скрипт надсилає дані, контрольовані зловмисником, як веб-повідомлення до іншого документа в браузері. Приклад вразливої маніпуляції веб-повідомленнями можна знайти в Web Security Academy PortSwigger.
Sinks:
Метод postMessage()
для надсилання веб-повідомлень може призвести до вразливостей, якщо обробник подій для отримання повідомлень обробляє вхідні дані ненадійним способом.
Маніпуляція даними DOM
From: https://portswigger.net/web-security/dom-based/dom-data-manipulation
Вразливості маніпуляції даними DOM виникають, коли скрипт записує дані, контрольовані зловмисником, у поле в DOM, яке використовується в видимому інтерфейсі або логіці на стороні клієнта. Цю вразливість може експлуатувати зловмисник, щоб створити URL, який, якщо його відвідає інший користувач, може змінити вигляд або поведінку інтерфейсу на стороні клієнта.
Sinks:
scriptElement.src
scriptElement.text
scriptElement.textContent
scriptElement.innerText
someDOMElement.setAttribute()
someDOMElement.search
someDOMElement.text
someDOMElement.textContent
someDOMElement.innerText
someDOMElement.outerText
someDOMElement.value
someDOMElement.name
someDOMElement.target
someDOMElement.method
someDOMElement.type
someDOMElement.backgroundImage
someDOMElement.cssText
someDOMElement.codebase
document.title
document.implementation.createHTMLDocument()
history.pushState()
history.replaceState()
Denial of Service
From: https://portswigger.net/web-security/dom-based/denial-of-service
Уразливості відмови в обслуговуванні на основі DOM виникають, коли скрипт передає дані, контрольовані зловмисником, небезпечно до проблемного API платформи. Це включає API, які, коли їх викликають, можуть призвести до споживання надмірної кількості процесорного часу або дискового простору на комп'ютері користувача. Такі уразливості можуть мати значні побічні ефекти, такі як обмеження функціональності веб-сайту браузером шляхом відхилення спроб зберегти дані в localStorage
або завершення зайнятих скриптів.
Sinks:
requestFileSystem()
RegExp()
Dom Clobbering
tip
Вивчайте та практикуйте AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Вивчайте та практикуйте GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Вивчайте та практикуйте Azure Hacking:
HackTricks Training Azure Red Team Expert (AzRTE)
Підтримайте HackTricks
- Перевірте плани підписки!
- Приєднуйтесь до 💬 групи Discord або групи telegram або слідкуйте за нами в Twitter 🐦 @hacktricks_live.
- Діліться хакерськими трюками, надсилаючи PR до HackTricks та HackTricks Cloud репозиторіїв на github.