Когда разрабы думают, что настроили CSP — в реальности они просто повесили вывеску «мы в безопасности» и ушли бухать. Но если среди script-src
торчит https://www.googletagmanager.com
, держись крепче: через GTM можно втащить полноценный XSS, и никаких unsafe-inline
.
Точка входа
• Что вижу: заголовок Content-Security-Policy
с script-src 'self' https://www.googletagmanager.com ...
.
• Как поймал: банальный curl -i target.com
и проверка CSP в ответе. Потом захожу в GTM-контейнер по id — вижу, что админы забыли ограничить доступ к тегам.
• Чем пахнет: классическая XSS через supply chain, вероятность 9/10, если GTM под контролем атакера.
Че почем
• Эксплойт:
Если сайт грузит:
1 |
<script src="https://www.googletagmanager.com/gtm.js?id=GTM-XXXX"></script> |
• и CSP доверяет GTM, а у атакера есть доступ к контейнеру (или уязвимость в GTM), достаточно вбросить кастомный тег:
1 |
<script>alert(document.domain)</script> |
• — и он легально прилетит с доверенного CDN, обходя CSP как knife through butter.
Обход защиты:
Даже если на стороне сайта CSP с nonce
или hash
, GTM-загрузка всё равно валидируется, потому что идёт из «trusted source». Google сам не ставит nonce/hashes, а тег-менеджер пихает JS пачками.
Трюк старый: подсовываешь «Custom HTML Tag» в GTM-аккаунт, и CSP уже не твой друг.
• Доказательство:
Пруф на скрине: страница с CSP, где у пользователя стоит script-src 'self' https://www.googletagmanager.com
, а я открываю консоль и вижу alert(1337)
от кода, инжекнутого через GTM. Доверенные источники? Ха-ха.
Советы
• 3 вектора для добивания:
1. Если GTM недоступен, ищи в CSP другие «trusted» CDN: cdnjs.cloudflare.com
, ajax.googleapis.com
— вставь свой файлик, если есть доступ.
2. Попробуй украсть токен Google Tag Manager у жертв через фишинг/идоров. У админов обычно права «раздают» без пардона.
3. Если сайт тянет «Google Analytics» (https://www.google-analytics.com
), у них тоже можно под шумок гонять хитрый beacon.
План атаки:
1. Парсим CSP, выписываем все доверенные CDN.
2. Проверяем, кто реально контролирует GTM-контейнер. Если он уязвим — всё, ол-ин.
3. В GTM создаём «Custom HTML» тег, кидаем свою JS-пэйлоадину.
4. Включаем триггер «All Pages», пушим контейнер.
5. Радуемся: XSS работает «легально» через CSP.
Мораль: доверять выдаче из GTM или чужим CDN — это как доверять незнакомцу с фаерволом у подъезда. CSP перестаёт быть обузой и превращается в фантик.