Перейти к содержимому

Поиск по платформе

Promo Code Race

Состояние гонки при активации промокодов (Python).

Автор: Hack & Fix
Освоишь: SELECT FOR UPDATEadvisory-lockidempotency key
Средне+60 XP ~45 мин python
CWE-362 · A04:2021 Pro
Обложка: Promo Code Race Обложка: Promo Code Race
Задача
# Состояние гонки (многократная активация промокода) ## Сценарий Вы — специалист по безопасности, приглашённый на аудит в **BitBasket** — интернет-магазин гаджетов и мерча для инженеров. Бухгалтерия заметила аномалию: начислений на балансы клиентов по итогам промо-кампании вышло больше, чем активаций кодов, хотя правило гласит «один код — одно начисление на пользователя». Основатель просит проверить механизм промокодов до запуска новой акции, и вы начинаете с обработчика активации в корзине. ## Цель 1. Войдите под демо-аккаунтом и изучите механику активации промокода в корзине: как проверяется «уже использован» и когда происходит начисление. 2. Обойдите ограничение «один промокод — одно начисление на пользователя», воспользовавшись параллельными запросами. 3. Раскачайте баланс до суммы, достаточной для товара **CTF Flag** ($1999) — один залп из ~20 одновременных запросов поднимает баланс примерно до $2500. 4. Оформите заказ — флаг появится на странице профиля. ## Теория Состояние гонки возникает, когда корректность операции зависит от порядка выполнения конкурентных действий. Классическая разновидность — уязвимость TOCTOU (time-of-check to time-of-use): проверка условия и действие по её результату разнесены во времени, и за это окно состояние успевает измениться. В активации промокода проверка «этот пользователь уже применял этот код?» и само начисление выполняются как два независимых шага, а обращение к медленному внешнему сервису начислений заметно расширяет паузу между ними. **Уязвимый паттерн:** ```python usage = db.execute('SELECT count(*) FROM used_coupons WHERE user_id=? AND code=?', ...).fetchone() if usage['cnt'] > 0: return redirect('/cart') # проверка «уже использован» redeem_coupon(db, user['id'], code, value) # применение — отдельным шагом ``` Чтобы выиграть гонку, отправьте на активацию одного и того же кода несколько запросов одновременно из одной сессии: пока первый запрос находится на пути к начислению, остальные успевают пройти проверку и тоже пополнить баланс. ## Точка входа атаки `POST /cart/coupon` — форма активации промокода в корзине; поля: `code` и скрытый `csrf_token`. Требуется вход в систему (сессионная cookie). * **Обычный пользователь:** `demo` / `demo` (стартовый баланс: $500) * **Администратор:** `admin` / `???` * **Промокоды:** `PROMO50` (+$50), `PROMO100` (+$100)

Похожие лабораторные (4)

другие лабы по этой уязвимости
Обложка лабы: Race Condition: Double-spend баланса Обложка лабы: Race Condition: Double-spend баланса
Race

Race Condition: Double-spend баланса

Race condition: чтение и списание баланса без транзакции позволяет двойную трату при параллельных запросах.

+60 XP
Go Pro
Exploit Fix
Обложка лабы: Promo Code Race Обложка лабы: Promo Code Race
Race

Promo Code Race

Состояние гонки при активации промокодов.

+60 XP
Go Pro
Exploit Fix
Обложка лабы: Promo Code Race Обложка лабы: Promo Code Race
Race

Promo Code Race

Состояние гонки при активации промокодов (PHP).

+60 XP
PHP Pro
Exploit Fix
Обложка лабы: Race Condition: Гонка при активации промокода в Express Обложка лабы: Race Condition: Гонка при активации промокода в Express
Race

Race Condition: Гонка при активации промокода в Express

Эндпоинт активации промокода в Express + better-sqlite3 содержит TOCTOU между проверкой счётчика и обновлением баланса. Получи бонус несколько раз параллельными запросами, накопи баланс и открой VIP-функцию с флагом.

+90 XP
Node.js Pro
Exploit Fix