Назад к обновлениям
New releaseAug 27, 2026

droidground v1.0.14

Гибкая площадка для Android CTF-задач.

Поделиться


droidground

DroidGround


Website | Demo

В традиционных CTF-задачах принято прятать флаги в файлах на системе, заставляя атакующих эксплуатировать уязвимости для их извлечения. Однако в мире Android такой подход плохо работает. APK-файлы легко скачиваются и реверсируются, поэтому размещение флага на устройстве обычно делает его извлечение тривиальным с помощью статического анализа или трюков с эмулятором. Это серьёзно ограничивает возможность создавать реалистичные задачи, ориентированные на время выполнения.

DroidGround создан для решения этой проблемы.

Это специально разработанная платформа для проведения задач по взлому Android-приложений в контролируемой и реалистичной среде, где атакующие ограничены ровно настолько, чтобы решать задачи предполагаемым способом.

Что важно, участники могут быть заперты внутри среды приложения. Модульность инструмента позволяет настроить, может ли пользователь запустить шелл, читать произвольные файлы или устанавливать сторонние инструменты. Всё можно настроить так, чтобы единственным способом получить флаг было понимание и эксплуатация самого приложения.

📋 Содержание

🧭 Обзор

DroidGround позволяет реализовать широкий спектр задач для Android, которые иначе сложно реализовать в традиционных CTF-сетапах. Например, в задаче на удалённое выполнение кода (RCE) игроки могут получить APK для локального анализа. Обнаружив уязвимость, они могут разработать скрипт Frida и запустить его через DroidGround на реальном целевом устройстве, чтобы извлечь флаг из внутреннего хранилища. Другие типы задач могут включать скрытые активности, пользовательские broadcast-интенты, эксплуатацию сервисов или динамический анализ с использованием предзагруженных инструментов.

Благодаря потоковой передаче экрана устройства в реальном времени, тонкой настройке функций, интеграции с Frida и настраиваемым скриптам установки и сброса, DroidGround даёт организаторам CTF возможность создавать безопасные, гибкие и реалистичные задачи для Android, выходящие далеко за рамки обычного.

✨ Возможности

DroidGround предоставляет богатый набор функций, управляемых с сервера.

  • Экран устройства в реальном времени (через scrcpy), с опциональным управлением мышью, касаниями и клавиатурой
  • Сброс состояния задачи
  • Перезапуск приложения / Запуск активности / Запуск сервиса
  • Отправка broadcast-интента
  • Выключение / Перезагрузка устройства
  • Скачивание bugreport (bugreportz)
  • Скриптинг Frida
    • Запуск из предзагруженной библиотеки (режим jail)
    • Запуск произвольных скриптов (полный режим)
  • Файловый браузер
  • Доступ к терминалу
  • Управление APK
  • Просмотр Logcat
  • Сервер эксплойтов (если включён командный режим)

Почти все функции модульные и определяются через переменные окружения, что обеспечивает точный контроль над рамками задачи.

📸 Скриншоты

Screenshot OverviewScreenshot Start Activity
ОбзорЗапуск активности
Screenshot Frida Jailed ModeScreenshot Frida Full Mode
Режим Frida JailПолный режим Frida
Screenshot File BrowserScreenshot App Manager
Файловый браузерМенеджер приложений
Screenshot TerminalScreenshot Logs
ТерминалЛоги

⚙️ Конфигурация

Файл .env.sample в корневой директории — хорошая отправная точка. Ниже приведён полный список всех поддерживаемых на данный момент переменных окружения:

ПеременнаяОписаниеПо умолчанию
DROIDGROUND_BASE_PATHПуть веб-приложения (полезно для размещения на подпутях)-
DROIDGROUND_APP_PACKAGE_NAMEИмя пакета целевого приложения-
DROIDGROUND_ADB_HOSTХост ADBlocalhost
DROIDGROUND_ADB_PORTПорт ADB5037
DROIDGROUND_ADB_SERIALОпциональный серийный номер ADB-устройства для подключения-
DROIDGROUND_DEVICE_TYPEusb или networkusb
DROIDGROUND_DEVICE_HOSTIP-адрес Android-устройства (adb) (только в сетевом режиме)-
DROIDGROUND_DEVICE_PORTПорт Android-устройства (adb) (только в сетевом режиме)-
DROIDGROUND_INIT_SCRIPTS_FOLDERПапка, содержащая setup.sh и reset.sh/init.d
DROIDGROUND_HOSTАдрес привязки0.0.0.0
DROIDGROUND_PORTПорт привязки4242
DROIDGROUND_RESTART_APP_DISABLEDОтключить перезапуск приложенияfalse
DROIDGROUND_APP_MANAGER_DISABLEDОтключить менеджер приложенийfalse
DROIDGROUND_BUG_REPORT_DISABLEDОтключить bugreportfalse
DROIDGROUND_FILE_BROWSER_DISABLEDОтключить файловый браузерfalse
DROIDGROUND_FRIDA_DISABLEDОтключить поддержку Fridafalse
DROIDGROUND_FRIDA_TYPEjail или fulljail
DROIDGROUND_FRIDA_INJECTIONserver или gadgetserver
DROIDGROUND_LOGCAT_DISABLEDОтключить logcatfalse
DROIDGROUND_REBOOT_ENABLEDВключить перезагрузкуfalse
DROIDGROUND_SHUTDOWN_ENABLEDВключить выключениеfalse
DROIDGROUND_START_ACTIVITY_DISABLEDОтключить startActivityfalse
DROIDGROUND_START_RECEIVER_DISABLEDОтключить broadcastfalse
DROIDGROUND_START_SERVICE_DISABLEDОтключить startServicefalse
DROIDGROUND_TERMINAL_DISABLEDОтключить терминалfalse
DROIDGROUND_RESET_DISABLEDОтключить сбросfalse
DROIDGROUND_SCRCPY_CONTROL_ENABLEDВключить ввод мышью, касаниями и клавиатурой через экран устройстваfalse
DROIDGROUND_SCRCPY_MAX_SIZEМаксимальный размер видео в пикселях; 0 сохраняет полное разрешение устройства1280
DROIDGROUND_SCRCPY_MAX_FPSМаксимальная частота кадров видео; 0 оставляет её неограниченной60
DROIDGROUND_SCRCPY_VIDEO_BIT_RATEБитрейт видео в битах в секунду4000000
DROIDGROUND_EXPLOIT_APP_DURATIONВремя (в секундах), в течение которого эксплойт-приложение будет активно10
DROIDGROUND_EXPLOIT_APP_MAX_SIZEМаксимальный размер (в МБ) эксплойт-приложения50
DROIDGROUND_NUM_TEAMSКоличество команд, играющих одновременно-
DROIDGROUND_TEAM_TOKEN_<N>Токен для n-й команды. Генерируется автоматически при отсутствии-
DROIDGROUND_IP_STATICСтатический IP-адрес для отображения. Имеет приоритет над DROIDGROUND_IP_IFACE-
DROIDGROUND_IP_IFACEСетевой интерфейс для отображаемого IP-адреса-
DROIDGROUND_LOGO_LINKОпционально задаёт ссылку при клике на логотип (например, главную страницу вашего CTF)-

Установите DROIDGROUND_SCRCPY_CONTROL_ENABLED=true и перезапустите DroidGround, чтобы сделать экран устройства интерактивным. Кликните или коснитесь экрана, чтобы сфокусировать его, затем кликайте, перетаскивайте, свайпайте, используйте несколько точек касания, прокручивайте колесом мыши или вводите текст. Правый клик или Escape — кнопка «Назад» в Android. Tab и Shift+Tab перемещают фокус за пределы экрана. Ввод разделяется всеми, кто просматривает устройство, в том числе в командном режиме. По умолчанию экран остаётся доступным только для просмотра. Ввод текста использует инъекцию клавиш Android от scrcpy, поэтому поддержка символов зависит от раскладки клавиатуры устройства.

DROIDGROUND_IP_IFACE сначала ищет точное совпадение и при неудаче переходит к первому интерфейсу, который начинается с указанного значения, поскольку Docker позволяет указать внутри контейнера только префикс сетевого интерфейса.

Потоковая передача экрана по умолчанию использует максимальный размер 1280 пикселей, до 60 fps и 4 Мбит/с, чтобы снизить нагрузку на кодирование, сеть и браузер. Это идёт на компромисс между детализацией и отзывчивостью во встроенном представлении устройства. Установите DROIDGROUND_SCRCPY_MAX_SIZE=0 и DROIDGROUND_SCRCPY_VIDEO_BIT_RATE=10000000, чтобы вернуть прежние настройки качества с полным разрешением. Для медленных соединений или браузеров попробуйте максимальный размер 1024, 30 fps и 2000000 бит в секунду. Перезапустите DroidGround после изменения этих настроек.

Браузер использует WebCodecs, когда он доступен, и в противном случае переключается на программный декодер H.264. WebCodecs требует защищённого контекста: используйте HTTPS для удалённых развёртываний (localhost также подходит). Обычный HTTP на удалённом IP или имени хоста использует программное декодирование. Медленные зрители пропускают кадры до свежего ключевого кадра вместо накопления отставания видео; подключение или восстановление может занять около одного интервала ключевых кадров (одна секунда). См. спецификацию WebCodecs и документацию по видео scrcpy для получения информации о базовых настройках браузера и видео.

Использование переменной DROIDGROUND_NUM_TEAMS немного меняет поведение приложения под капотом. Если эта опция задана:

  1. Включается функция сервера эксплойтов, позволяя каждой команде использовать свой собственный (очень простой) сервер эксплойтов через свой токен команды.
  2. Токен команды будет обязателен для установки и запуска эксплойт-приложений. Каждое установленное приложение будет привязано к команде, и другие команды не смогут его запустить.

Это позволяет использовать один и тот же экземпляр DroidGround несколькими командами в задачах, где флаг можно вынести через сетевой запрос. Это значительно снижает затраты на развёртывание DroidGround для CTF-соревнований.

Кроме того, если значение установлено в -1, включается так называемый режим Unlimited Teams. В этом режиме на странице Обзор появится кнопка для генерации нового токена команды. Все переменные DROIDGROUND_TEAM_TOKEN_<N> игнорируются, если этот режим включён.

🧩 Сценарии использования

Вот несколько способов использования DroidGround:

  1. Скрытая активность: найдите и запустите неэкспортируемую активность, чтобы увидеть флаг (приложение игрока содержит фиктивный флаг).
  2. RCE: приложение уязвимо к RCE, а флаг хранится на устройстве.
  3. Инструментирование Frida: перегрузите метод и извлеките флаг из приватной памяти с помощью скрипта.

⚙️ Использование

Несколько примеров файлов Docker Compose предоставлены в папке examples. Они используют приложения из репозитория примеров DroidGround, который будет постепенно дополняться для демонстрации всех ключевых функций. Они также являются хорошей отправной точкой для понимания того, как настроить собственный CTF.

При загрузке DroidGround выполняет следующее:

  1. Устанавливает соединение с adb
  2. Запускает setup.sh в папке, указанной в DROIDGROUND_INIT_SCRIPTS_FOLDER, если он присутствует. Этот скрипт можно использовать для установки целевого приложения и всего остального, что нужно для инициализации CTF (например, размещения флага в известном месте)
  3. (если Frida включена) Скачивает правильный frida-server на основе установленной версии и архитектуры устройства и запускает его
  4. Запускает целевое приложение (то, что указано через DROIDGROUND_APP_PACKAGE_NAME). Если приложение не установлено, DroidGround завершит работу.
  5. Настраивает REST API, серверы WebSocket и потоковую передачу экрана

Вот пример скрипта setup.sh:

#!/usr/bin/env bash

adb shell pm uninstall com.example.app # To do some cleanup
echo "Sleep for 2 seconds before installing app"
sleep 2
echo "Installing app..."
adb install ./flag.apk # The cwd is set to the "init.d" folder, so the apk file can be accessed with the relative path
echo "Install command executed"

Для продакшн-развёртывания (в реальном CTF) вы можете захотеть заранее подготовить определённое количество экземпляров DroidGround или разрешить пользователям создавать экземпляры (с ограничением или, возможно, связав каждую команду/пользователя с конкретным экземпляром). По этой причине мы также добавили простой пример спавнера.

Как уже упоминалось, в качестве альтернативы вы можете создать задачу, где флаг можно вынести через сетевой запрос, и использовать переменную окружения DROIDGROUND_NUM_TEAMS, чтобы избежать создания множества экземпляров (что может быть дорого). Папка net-multi-step предоставляет хороший пример того, как реализовать такие задачи.

💡 Советы

Вот несколько рекомендаций по настройке вашего Android CTF:

  • Будьте осторожны при включении Frida Full Mode — игрок получит полный контроль над устройством (именно поэтому мы сделали Frida Jail Mode, как описано в Библиотеке Frida).
  • Будьте осторожны при включении Терминала — игрок получит полный контроль над устройством.
  • Будьте осторожны при включении функции Выключение.
  • Если вы планируете сделать флаг видимым прямо в UI, вам, возможно, стоит найти способ создавать разные экземпляры (по одному на команду/игрока)

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

Поэтому предоставляется endpoint GET, доступный по адресу /attackSurface, защищённый токеном (который нужно использовать как значение заголовка Authorization), случайно генерируемым при загрузке и выводимым в логи (следовательно, доступным только системным администраторам).

Если вы хотите использовать свои собственные скрипты Frida в режиме jail, вам просто нужно примонтировать папку, содержащую их, в Docker-контейнер:

volumes:
  - <Frida library folder>:/droidground/library

Файл library.json (как в library) необходим, чтобы сообщить приложению список доступных скриптов.

🛠 Разработка

Запустить всё это не должно быть слишком сложно, но перед началом у вас должны быть установлены следующие инструменты:

  • frida (только если вы включаете Frida)
  • node (это Node-приложение, он вам нужен!)
  • adb (ну, мы полагаемся на него для связи с устройством)
  • JDK (нужен для сборки companion-приложения)

После этого вы можете просто выполнить следующее:

git clone https://github.com/SECFORCE/droidground.git
cd droidground

# Install without running scripts
npm install --ignore-scripts
# Rebuild frida to get the bindings
npm rebuild frida
# Build companion app
npm run companion
# Get scrcpy
npm run scrcpy

После этого вам просто нужно задать переменные env, а затем запустить npm run dev, и всё готово. Удачного режима разработки!

🤝 Участие в разработке

Pull request'ы приветствуются! Пожалуйста, сначала откройте issue для обсуждения крупных изменений. Особенно приветствуются идеи для новых CTF-воркфлоу или типов задач.

📚 Благодарности

Разработано Angelo Delicato @SECFORCE.

Раздел server во многом опирается на потрясающую работу @yume-chan; вероятно, это приложение не существовало бы без его замечательной работы.

Приложение companion во многом основано на aya server, который работает так же, как scrcpy server. Более подробную информацию можно найти в соответствующем README.

🪪 Лицензия

DroidGround выпущен под лицензией GPL-3.0

Категории