JWT Vulnerabilities (Json Web Tokens)
Last updated
Last updated
Вивчайте та практикуйте Hacking AWS:HackTricks Training AWS Red Team Expert (ARTE) Вивчайте та практикуйте Hacking GCP: HackTricks Training GCP Red Team Expert (GRTE)
Якщо ви зацікавлені в кар'єрі в хакерстві та хочете зламати незламне - ми наймаємо! (вимагається вільне володіння польською мовою в письмовій та усній формі).
Частина цього посту базується на чудовому пості: https://github.com/ticarpi/jwt_tool/wiki/Attack-Methodology Автор чудового інструменту для тестування JWT https://github.com/ticarpi/jwt_tool
Запустіть jwt_tool в режимі All Tests!
і чекайте на зелені рядки
Якщо вам пощастить, інструмент знайде випадок, коли веб-додаток неправильно перевіряє JWT:
Тоді ви можете знайти запит у вашому проксі або вивантажити використаний JWT для цього запиту, використовуючи jwt_ tool:
Ви також можете використовувати Burp Extension SignSaboteur для запуску атак JWT з Burp.
Ви можете просто змінити дані, залишаючи підпис без змін, і перевірити, чи сервер перевіряє підпис. Спробуйте змінити своє ім'я користувача на "admin", наприклад.
Щоб перевірити, чи перевіряється підпис JWT:
Повідомлення про помилку вказує на те, що триває перевірка; чутливі деталі у детальних помилках слід переглянути.
Зміна на повернутій сторінці також вказує на перевірку.
Відсутність змін вказує на відсутність перевірки; це момент для експериментів із зміною навантаження.
Важливо визначити, чи токен був згенерований на стороні сервера чи клієнта, перевіривши історію запитів проксі.
Токени, вперше побачені з боку клієнта, вказують на те, що ключ може бути відкритий для коду на стороні клієнта, що потребує подальшого розслідування.
Токени, що походять з боку сервера, вказують на безпечний процес.
Перевірте, чи токен діє більше 24 годин... можливо, він ніколи не закінчується. Якщо є поле "exp", перевірте, чи сервер правильно його обробляє.
Встановіть використовуваний алгоритм як "None" і видаліть частину підпису.
Використовуйте розширення Burp під назвою "JSON Web Token", щоб спробувати цю вразливість і змінити різні значення всередині JWT (надішліть запит до Repeater, і на вкладці "JSON Web Token" ви можете змінити значення токена. Ви також можете вибрати, щоб встановити значення поля "Alg" на "None").
Алгоритм HS256 використовує секретний ключ для підпису та перевірки кожного повідомлення. Алгоритм RS256 використовує приватний ключ для підпису повідомлення та використовує публічний ключ для аутентифікації.
Якщо ви зміните алгоритм з RS256 на HS256, код на бекенді використовує публічний ключ як секретний ключ, а потім використовує алгоритм HS256 для перевірки підпису.
Тоді, використовуючи публічний ключ і змінюючи RS256 на HS256, ми могли б створити дійсний підпис. Ви можете отримати сертифікат веб-сервера, виконавши це:
Зловмисник вбудовує новий ключ у заголовок токена, і сервер використовує цей новий ключ для перевірки підпису (CVE-2018-0114).
Це можна зробити за допомогою розширення "JSON Web Tokens" для Burp. (Відправте запит до Repeater, у вкладці JSON Web Token виберіть "CVE-2018-0114" і надішліть запит).
Інструкції детально описують метод оцінки безпеки JWT токенів, зокрема тих, що використовують заяву заголовка "jku". Ця заява повинна посилатися на файл JWKS (JSON Web Key Set), який містить публічний ключ, необхідний для перевірки токена.
Оцінка токенів з заголовком "jku":
Перевірте URL заяви "jku", щоб переконатися, що він веде до відповідного файлу JWKS.
Змініть значення "jku" токена, щоб направити його на контрольовану веб-службу, що дозволяє спостерігати за трафіком.
Моніторинг HTTP-взаємодії:
Спостереження за HTTP-запитами до вашого вказаного URL вказує на спроби сервера отримати ключі з наданого вами посилання.
Коли ви використовуєте jwt_tool
для цього процесу, важливо оновити файл jwtconf.ini
з вашим особистим розташуванням JWKS для полегшення тестування.
Команда для jwt_tool
:
Виконайте наступну команду, щоб змоделювати сценарій з jwt_tool
:
Додаткова заявка заголовка, відома як kid
, використовується для ідентифікації конкретного ключа, що стає особливо важливим у середовищах, де існує кілька ключів для перевірки підпису токена. Ця заява допомагає вибрати відповідний ключ для перевірки підпису токена.
Коли заява kid
присутня в заголовку, рекомендується шукати у веб-директорії відповідний файл або його варіації. Наприклад, якщо вказано "kid":"key/12345"
, слід шукати файли /key/12345 та /key/12345.pem у кореневій директорії веб-сайту.
Заява kid
також може бути використана для навігації по файловій системі, потенційно дозволяючи вибір довільного файлу. Можливо протестувати на наявність з'єднання або виконати атаки Server-Side Request Forgery (SSRF), змінивши значення kid
, щоб націлитися на конкретні файли або служби. Зміна JWT для зміни значення kid
, зберігаючи оригінальний підпис, може бути досягнута за допомогою прапора -T
у jwt_tool, як показано нижче:
Націлюючись на файли з передбачуваним вмістом, можна підробити дійсний JWT. Наприклад, файл /proc/sys/kernel/randomize_va_space
в системах Linux, відомий тим, що містить значення 2, можна використовувати в параметрі kid
з 2 як симетричним паролем для генерації JWT.
Якщо вміст заяви kid
використовується для отримання пароля з бази даних, SQL-ін'єкція може бути здійснена шляхом модифікації корисного навантаження kid
. Приклад корисного навантаження, яке використовує SQL-ін'єкцію для зміни процесу підписання JWT, включає:
non-existent-index' UNION SELECT 'ATTACKER';-- -
Ця зміна змушує використовувати відомий секретний ключ, ATTACKER
, для підписання JWT.
Сценарій, в якому параметр kid
вказує на шлях до файлу, що використовується в контексті виконання команди, може призвести до вразливостей віддаленого виконання коду (RCE). Впроваджуючи команди в параметр kid
, можна розкрити приватні ключі. Приклад корисного навантаження для досягнення RCE та розкриття ключа:
/root/res/keys/secret7.key; cd /root/res/keys/ && python -m SimpleHTTPServer 1337&
jku означає JWK Set URL. Якщо токен використовує заяву “jku” Header, тоді перевірте наданий URL. Це має вказувати на URL, що містить файл JWKS, який містить публічний ключ для перевірки токена. Змініть токен, щоб вказати значення jku на веб-сервіс, за яким ви можете контролювати трафік.
Спочатку вам потрібно створити новий сертифікат з новими приватними та публічними ключами.
Тоді ви можете використовувати, наприклад, jwt.io, щоб створити новий JWT з створеними публічними та приватними ключами та вказуючи параметр jku на створений сертифікат. Щоб створити дійсний сертифікат jku, ви можете завантажити оригінальний і змінити необхідні параметри.
Ви можете отримати параметри "e" та "n" з публічного сертифіката, використовуючи:
X.509 URL. URI, що вказує на набір публічних сертифікатів X.509 (стандарт формату сертифіката), закодованих у формі PEM. Перший сертифікат у наборі повинен бути тим, що використовується для підписання цього JWT. Наступні сертифікати підписують попередній, таким чином завершуючи ланцюг сертифікатів. X.509 визначено в RFC 52807. Для передачі сертифікатів потрібна транспортна безпека.
Спробуйте змінити цей заголовок на URL під вашим контролем і перевірте, чи буде отримано будь-який запит. У такому випадку ви можете підробити JWT.
Щоб підробити новий токен, використовуючи сертифікат, контрольований вами, вам потрібно створити сертифікат і витягти публічні та приватні ключі:
Тоді ви можете використовувати, наприклад, jwt.io для створення нового JWT з створеними публічними та приватними ключами та вказуючи параметр x5u на сертифікат .crt, що був створений.
Ви також можете зловживати обома цими вразливостями для SSRFs.
Цей параметр може містити сертифікат у base64:
Якщо зловмисник генерує самопідписаний сертифікат і створює підроблений токен, використовуючи відповідний приватний ключ, і замінює значення параметра "x5c" на новостворений сертифікат та модифікує інші параметри, а саме n, e та x5t, то, по суті, підроблений токен буде прийнятий сервером.
Якщо JWT вбудував відкритий ключ, як у наступному сценарії:
Використовуючи наступний скрипт nodejs, можна згенерувати відкритий ключ з цих даних:
Можливо згенерувати новий приватний/публічний ключ, вбудувати новий публічний ключ всередину токена і використовувати його для генерації нового підпису:
Ви можете отримати "n" та "e", використовуючи цей скрипт nodejs:
Нарешті, використовуючи публічний та приватний ключі та нові значення "n" і "e", ви можете використовувати jwt.io для підробки нового дійсного JWT з будь-якою інформацією.
Якщо деякі програми використовують ES256 і використовують однаковий nonce для генерації двох jwt, приватний ключ може бути відновлений.
Ось приклад: ECDSA: Виявлення приватного ключа, якщо використано однаковий nonce (з SECP256k1)
Заява JTI (JWT ID) надає унікальний ідентифікатор для токена JWT. Його можна використовувати для запобігання повторному використанню токена. Однак уявіть ситуацію, коли максимальна довжина ID становить 4 (0001-9999). Запити 0001 і 10001 будуть використовувати однаковий ID. Тому, якщо бекенд збільшує ID з кожним запитом, ви могли б зловживати цим, щоб повторити запит (потрібно надіслати 10000 запитів між кожним успішним повтором).
Атаки перехресного реле
Було помічено, що деякі веб-додатки покладаються на надійний сервіс JWT для генерації та управління своїми токенами. Зафіксовано випадки, коли токен, згенерований для одного клієнта сервісом JWT, був прийнятий іншим клієнтом того ж сервісу JWT. Якщо спостерігається видача або поновлення JWT через сторонній сервіс, слід дослідити можливість реєстрації облікового запису на іншому клієнті цього сервісу, використовуючи те саме ім'я користувача/електронну пошту. Потім слід спробувати повторити отриманий токен у запиті до цілі, щоб перевірити, чи буде він прийнятий.
Критична проблема може бути вказана прийняттям вашого токена, що потенційно дозволяє підробку облікового запису будь-якого користувача. Однак слід зазначити, що для більш широкого тестування може знадобитися дозвіл, якщо реєстрація на сторонньому додатку, оскільки це може потрапити в юридичну сіру зону.
Перевірка терміну дії токенів
Термін дії токена перевіряється за допомогою заяви "exp" Payload. Оскільки JWT часто використовуються без інформації про сесію, потрібна обережна обробка. У багатьох випадках захоплення та повторне використання JWT іншого користувача може дозволити видавати себе за цього користувача. Рекомендації JWT RFC пропонують пом'якшити атаки повторного використання JWT, використовуючи заяву "exp" для встановлення часу закінчення дії токена. Крім того, реалізація відповідних перевірок додатком для забезпечення обробки цього значення та відхилення прострочених токенів є критично важливою. Якщо токен містить заяву "exp" і обмеження часу тестування дозволяють, рекомендується зберігати токен і повторно використовувати його після закінчення терміну дії. Зміст токена, включаючи парсинг мітки часу та перевірку терміну дії (мітка часу в UTC), можна прочитати за допомогою прапора -R інструмента jwt_tool.
Існує ризик безпеки, якщо додаток все ще перевіряє токен, оскільки це може означати, що токен ніколи не може закінчитися.
Якщо вас цікавить кар'єра в хакерстві і ви хочете зламати незламне - ми наймаємо! (вимагається вільне володіння польською мовою в письмовій та усній формі).
Вчіться та практикуйте AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE) Вчіться та практикуйте GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)