diff --git a/README.md b/README.md index 2b5fc40..5b92747 100644 --- a/README.md +++ b/README.md @@ -25,7 +25,14 @@ * Расшифровывает TLS на RSA при наличии приватного ключа ![Скриншот главного окна](screenshots/Screenshot.png) -## Клонирование + +## Быстрый запуск +Для быстрого запуска Packmate следует использовать [этот стартер](https://gitlab.com/packmate/starter/-/blob/master/README.md). + +## Полный запуск +Ниже следует инструкция для тех, кто хочет собрать Packmate самостоятельно. + +### Клонирование Поскольку этот репозиторий содержит фронтенд как git submodule, его необходимо клонировать так: ```bash git clone --recurse-submodules https://gitlab.com/packmate/Packmate.git @@ -40,102 +47,20 @@ git pull # Забираем свежую версию мастер-репы и git submodule update --init --recursive ``` -## Подготовка -В этом ПО используется Docker и docker-compose. В образ `packmate-app` пробрасывается -сетевой интерфейс хоста, его название указывается переменной окружения (об этом ниже). - -`packmate-db` настроен на прослушивание порта 65001 с локальным IP. -Файлы БД сохраняются в ./data, поэтому для обнуления базы нужно удалить эту папку. - ### Настройка -Программа берет основные настройки из переменных окружения, поэтому для удобства -можно создать env-файл. -Он должен называться `.env` и лежать в корневой директории проекта. - -В файле необходимо прописать: -```dotenv -# Локальный IP сервера на указанном интерфейсе или в pcap файле -PACKMATE_LOCAL_IP=192.168.1.124 -# Имя пользователя для web-авторизации -PACKMATE_WEB_LOGIN=SomeUser -# Пароль для web-авторизации -PACKMATE_WEB_PASSWORD=SomeSecurePassword -``` - -Если мы перехватываем трафик сервера (лучший вариант, если есть возможность): -```dotenv -# Режим работы - перехват -PACKMATE_MODE=LIVE -# Интерфейс, на котором производится перехват трафика -PACKMATE_INTERFACE=wlan0 -``` -Если мы анализируем pcap дамп: -```dotenv -# Режим работы - анализ файла -PACKMATE_MODE=FILE -# Путь до файла от корня проекта -PACKMATE_PCAP_FILE=dump.pcap -``` - -Или если мы хотим посмотреть уже обработанный трафик (например, для разбора после игры): -```dotenv -PACKMATE_MODE=VIEW -``` - -При захвате живого трафика рекомендуется включать удаление старых стримов, иначе ближе к концу -соревнования анализатор будет медленнее работать. -```dotenv -PACKMATE_OLD_STREAMS_CLEANUP_ENABLED=true -# Интервал удаления старых стримов (в минутах). -# Лучше ставить маленькое число, чтобы стримы удалялись маленькими кусками, и это не нагружало систему -PACKMATE_OLD_STREAMS_CLEANUP_INTERVAL=1 -# Насколько старым стрим должен быть для удаления (в минутах от текущего времени) -PACKMATE_OLD_STREAMS_CLEANUP_THRESHOLD=240 -``` - -Чтобы использовать расшифровку TLS, нужно положить соответствующий приватный ключ, который -использовался для генерации сертификата, в папку `rsa_keys`. +[Инструкция](docs/SETUP.md) ### Запуск После указания нужных настроек в env-файле, можно запустить приложение: ```bash -sudo docker-compose up --build -d +sudo docker compose up --build -d ``` При успешном запуске Packmate будет видно с любого хоста на порту `65000`. - -### Начало работы -При попытке зайти в web-интерфейс впервые, браузер спросит логин и пароль, -который указывался в env-файле. -При необходимости можно настроить дополнительные параметры по кнопке с шестеренками в верхнем -правом углу экрана. - -![Скриншот настроек](screenshots/Screenshot_Settings.png) - -Все настройки сохраняются в local storage и теряются только при смене IP-адреса или порта сервера. +БД будет слушать на порту 65001, но будет разрешать подключения только с localhost. ## Использование -Сначала нужно создать сервисы, находящиеся в игре. -Для этого вызывается диалоговое окно по нажатию кнопки `+` в навбаре, -где можно указать название и порт сервиса, а также дополнительные опции. - -Для удобного отлова флагов в приложении существует система паттернов. -Чтобы создать паттерн, нужно открыть выпадающее меню `Patterns` и нажать кнопку `+`, -затем указать нужный тип поиска, сам паттерн, цвет подсветки в тексте и прочее. -Если выбрать тип паттерна IGNORE, то стримы, попадающие под шаблон, автоматически будут удаляться. -Это может пригодиться, чтобы не засорять БД трафиком с эксплоитами, которые уже были запатчены. - -В режиме LIVE система начнет автоматически захватывать стримы и отображать их в сайдбаре. -В режиме FILE для начала обработки файла нужно нажать соответствующую кнопку в сайдбаре. -При нажатии на стрим в главном контейнере выводится список пакетов; -между бинарным и текстовым представлением можно переключиться по кнопке в сайдбаре. - -### Горячие клавиши -Для быстрой навигации по стримам можно использовать следующие горячие клавиши: -* `Ctrl+Up` -- переместиться на один стрим выше -* `Ctrl+Down` -- переместиться на один стрим ниже -* `Ctrl+Home` -- перейти на последний стрим -* `Ctrl+End` -- перейти на первый стрим +[Инструкция](docs/USAGE.md)
diff --git a/README_EN.md b/README_EN.md index abec29e..6384dde 100644 --- a/README_EN.md +++ b/README_EN.md @@ -25,7 +25,14 @@ Advanced network traffic flow analyzer for A/D CTFs. * Can automatically decrypt TLS with RSA using given private key (like Wireshark) ![Main window](screenshots/Screenshot.png) -## Cloning + +## Quick Start +To quickly start using Packmate, use [this starter](https://gitlab.com/packmate/starter/-/blob/master/README_EN.md). + +## Full Build +Below are the instructions for those who want to build Packmate on their own. + +### Cloning As this repository contains frontend part as a git submodule, it has to be cloned like this: ```bash git clone --recurse-submodules https://gitlab.com/packmate/Packmate.git @@ -40,54 +47,8 @@ git pull git submodule update --init --recursive ``` -## Preparation -This program uses Docker and docker-compose. - -`packmate-db` will listen to port 65001 at localhost. -Database files are saved in ./data, so in order to reset database you'll have to delete that directory. - -### Settings -This program retrieves settings from environment variables, -so it would be convenient to create an env file; -It must be called `.env` and located at the root of the project. - -Contents of the file: -```bash -# Local IP on network interface or in pcap file to tell incoming packets from outgoing -PACKMATE_LOCAL_IP=192.168.1.124 -# Username for the web interface -PACKMATE_WEB_LOGIN=SomeUser -# Password for the web interface -PACKMATE_WEB_PASSWORD=SomeSecurePassword -``` - -If we are capturing live traffic (best option if possible): -```bash -# Mode: capturing -PACKMATE_MODE=LIVE -# Interface to capture on -PACKMATE_INTERFACE=wlan0 -``` -If we are analyzing pcap dump: -```bash -# Mode: dump analyzing -PACKMATE_MODE=FILE -# Path to pcap file from project root -PACKMATE_PCAP_FILE=dump.pcap -``` - -When capturing live traffic it's better to turn on old streams removal. Otherwise, after some time Packmate -will start working slower. -```dotenv -PACKMATE_OLD_STREAMS_CLEANUP_ENABLED=true -# Old streams removal interval (in minutes). -# It's better to use small numbers so the streams are removed in small chunks and don't overload the server. -PACKMATE_OLD_STREAMS_CLEANUP_INTERVAL=1 -# How old the stream must be to be removed (in minutes before current time) -PACKMATE_OLD_STREAMS_CLEANUP_THRESHOLD=240 -``` - -To decrypt TLS, put the private key used to generate a certificate into the `rsa_keys` folder. +### Setup +[Instructions](docs/SETUP_EN.md) ### Launch After filling in env file you can launch the app: @@ -95,42 +56,11 @@ After filling in env file you can launch the app: sudo docker-compose up --build -d ``` -If everything went fine, Packmate will be available on port `65000` from any host - -### Accessing the web interface -When you open a web interface for the first time, you will be asked for a login and password -you specified in the env file. -After entering the credentials, open the settings by clicking the cogs -in the top right corner and modify additional parameters. - -![Settings](screenshots/Screenshot_Settings.png) - -All settings are saved in the local storage and will be -lost only upon changing server IP or port. +If everything went fine, Packmate will be available on port `65000` from any host. +Database with listen on port 65001, but will only accept connections from localhost. ## Usage -First of all, you should create game services. -To do that, click `+` in the navbar, -then fill in the service name, port, and optimizations to perform on streams. - -For a simple monitoring of flags, there is a system of patterns. -To create a pattern, open `Patterns` dropdown menu, press `+`, then -specify the type of pattern, the pattern itself, highlight color and other things. -If you choose IGNORE as the type of a pattern, all matching streams will be automatically deleted. -This can be useful to filter out exploits you have already patched against. - -In LIVE mode the system will automatically capture streams and show them in a sidebar. -In FILE mode you'll have to press appropriate button in a sidebar to start processing a file. -Note that you should only do that after all services are created. -Click at a stream to view a list of packets; -you can click a button in the sidebar to switch between binary and text views. - -### Shortcuts -To quickly navigate streams you can use the following shortcuts: -* `Ctrl+Up` -- go to the next stream -* `Ctrl+Down` -- go to the previous stream -* `Ctrl+Home` -- go to the latest stream -* `Ctrl+End` -- go to the first stream +[Instructions](docs/USAGE_EN.md)
diff --git a/docker-compose.yml b/docker-compose.yml index 46dc091..cb42a90 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -2,7 +2,6 @@ services: packmate: # port = 65000 environment: DB_PASSWORD: ${PACKMATE_DB_PASSWORD:-K604YnL3G1hp2RDkCZNjGpxbyNpNHTRb} - DB_NAME: ${PACKMATE_DB_NAME:-packmate} INTERFACE: ${PACKMATE_INTERFACE:-} LOCAL_IP: ${PACKMATE_LOCAL_IP} MODE: ${PACKMATE_MODE:-LIVE} @@ -20,16 +19,9 @@ services: dockerfile: docker/Dockerfile_app network_mode: "host" image: registry.gitlab.com/packmate/packmate:${BUILD_TAG:-latest} - command: [ - "java", "-Djava.net.preferIPv4Stack=true", "-Djava.net.preferIPv4Addresses=true", - "-jar", "/app/app.jar", "--spring.datasource.url=jdbc:postgresql://127.0.0.1:65001/$${DB_NAME}", - "--spring.datasource.password=$${DB_PASSWORD}", - "--capture-mode=$${MODE}", "--pcap-file=$${PCAP_FILE}", - "--interface-name=$${INTERFACE}", "--local-ip=$${LOCAL_IP}", "--account-login=$${WEB_LOGIN}", - "--old-streams-cleanup-enabled=$${OLD_STREAMS_CLEANUP_ENABLED}", "--cleanup-interval=$${OLD_STREAMS_CLEANUP_INTERVAL}", - "--old-streams-threshold=$${OLD_STREAMS_CLEANUP_THRESHOLD}", - "--account-password=$${WEB_PASSWORD}", "--server.port=65000", "--server.address=0.0.0.0" - ] + volumes: + - "./pcaps/:/app/pcaps/:ro" + - "./rsa_keys/:/app/rsa_keys/:ro" depends_on: db: condition: service_healthy @@ -38,7 +30,7 @@ services: environment: POSTGRES_USER: packmate POSTGRES_PASSWORD: ${PACKMATE_DB_PASSWORD:-K604YnL3G1hp2RDkCZNjGpxbyNpNHTRb} - POSTGRES_DB: ${PACKMATE_DB_NAME:-packmate} + POSTGRES_DB: packmate env_file: - .env volumes: diff --git a/docker/Dockerfile_app b/docker/Dockerfile_app index 0ce06dd..ac38120 100644 --- a/docker/Dockerfile_app +++ b/docker/Dockerfile_app @@ -13,4 +13,15 @@ FROM eclipse-temurin:17-jre WORKDIR /app RUN apt update && apt install -y libpcap0.8 && rm -rf /var/lib/apt/lists/* COPY --from=1 /tmp/compile/build/libs/packmate-*-SNAPSHOT.jar app.jar + +CMD [ "java", "-Djava.net.preferIPv4Stack=true", "-Djava.net.preferIPv4Addresses=true", \ + "-jar", "/app/app.jar", "--spring.datasource.url=jdbc:postgresql://127.0.0.1:65001/packmate", \ + "--spring.datasource.password=${DB_PASSWORD}", \ + "--capture-mode=${MODE}", "--pcap-file=${PCAP_FILE}", \ + "--interface-name=${INTERFACE}", "--local-ip=${LOCAL_IP}", "--account-login=${WEB_LOGIN}", \ + "--old-streams-cleanup-enabled=${OLD_STREAMS_CLEANUP_ENABLED}", "--cleanup-interval=${OLD_STREAMS_CLEANUP_INTERVAL}", \ + "--old-streams-threshold=${OLD_STREAMS_CLEANUP_THRESHOLD}", \ + "--account-password=${WEB_PASSWORD}", "--server.port=65000", "--server.address=0.0.0.0" \ +] + EXPOSE 65000 \ No newline at end of file diff --git a/docs/SETUP.md b/docs/SETUP.md new file mode 100644 index 0000000..d7c67ff --- /dev/null +++ b/docs/SETUP.md @@ -0,0 +1,89 @@ +## Настройка + +Packmate использует настройки из файла `.env` (в той же папке, что и `docker-compose.yml`) + +### Основные настройки +```dotenv +# Локальный IP сервера, на который приходит игровой трафик +PACKMATE_LOCAL_IP=10.20.1.1 +# Имя пользователя для web-авторизации +PACKMATE_WEB_LOGIN=SomeUser +# Пароль для web-авторизации +PACKMATE_WEB_PASSWORD=SomeSecurePassword +``` + +### Режим работы +Packmate поддерживает три основных режима работы: `LIVE`, `FILE` и `VIEW`. +1. `LIVE` - это основной режим работы во время CTF. Packmate обрабатывает живой трафик и сразу выводит результаты. +2. `FILE` - обрабатывает трафик из pcap файлов. Полезен для анализа трафика с прошедших CTF, где не был запущен Packmate, или тех, где невозможно запустить его на вулнбоксе. +3. `VIEW` - Packmate не обрабатывает трафик, а только показывает уже обработанные стримы. Полезен для разборов после завершения CTF. + +
+ Настройка LIVE + +Необходимо указать интерфейс, через который проходит игровой трафик. +На этом же интерфейсе должен располагаться ip, указанный в параметре `PACKMATE_LOCAL_IP` + +```dotenv +# Режим работы - перехват +PACKMATE_MODE=LIVE +# Интерфейс, на котором производится перехват трафика +PACKMATE_INTERFACE=game +``` + +
+ +
+ Настройка FILE + +Необходимо указать название pcap файла, лежащего в папке pcaps. +После запуска в веб-интерфейсе появится кнопка, активирующая чтение файла. +Важно, чтобы к этому моменту уже были созданы сервисы и паттерны (см. раздел Использование). + +```dotenv +# Режим работы - анализ файла +PACKMATE_MODE=FILE +# Название файла в папке pcaps +PACKMATE_PCAP_FILE=dump.pcap +``` + +
+ +
+ Настройка VIEW + +В этом режиме Packmate просто показывает уже имеющиеся данные. + +```dotenv +# Режим работы - просмотр +PACKMATE_MODE=VIEW +``` + +
+ +### Очистка БД +На крупных CTF через какое-то время накапливается большое количество трафика. Это замедляет работу Packmate и занимает много места на диске. + +Для оптимизации работы, рекомендуется включить регулярную очистку БД от старых стримов. Это будет работать только в режиме `LIVE`. +```dotenv +PACKMATE_OLD_STREAMS_CLEANUP_ENABLED=true +# Интервал удаления старых стримов (в минутах). +# Лучше ставить маленькое число, чтобы стримы удалялись маленькими кусками, и это не нагружало систему +PACKMATE_OLD_STREAMS_CLEANUP_INTERVAL=1 +# Насколько старым стрим должен быть для удаления (в минутах от текущего времени) +PACKMATE_OLD_STREAMS_CLEANUP_THRESHOLD=240 +``` + +### Дополнительные настройки + +```dotenv +# Пароль от БД. Из-за того, что БД принимает подключения только с localhost, менять его необязательно, но можно, для дополнительной безопасности. +PACKMATE_DB_PASSWORD=K604YnL3G1hp2RDkCZNjGpxbyNpNHTRb +# Версия Packmate. Можно изменить, если нужно использовать другой образ из docker registry. +BUILD_TAG=latest +``` + +Чтобы использовать расшифровку TLS (с RSA), нужно положить соответствующий приватный ключ, который +использовался для генерации сертификата, в папку `rsa_keys`. + +Файлы БД сохраняются в ./data, поэтому для обнуления базы нужно удалить эту папку. \ No newline at end of file diff --git a/docs/SETUP_EN.md b/docs/SETUP_EN.md new file mode 100644 index 0000000..6b12da6 --- /dev/null +++ b/docs/SETUP_EN.md @@ -0,0 +1,88 @@ +## Setup + +Packmate uses properties from the `.env` file (in the same directory as `docker-compose.yml`) + +### Primary settings +```dotenv +# Local IP of a server on which the traffic in directed. Used to tell incoming packets from outgoing. +PACKMATE_LOCAL_IP=10.20.1.1 +# Username for the web interface +PACKMATE_WEB_LOGIN=SomeUser +# Password for the web interface +PACKMATE_WEB_PASSWORD=SomeSecurePassword +``` + +### Modes of operation +Packmate supports 3 modes of operation: `LIVE`, `FILE` и `VIEW`. +1. `LIVE` - the usual mode during a CTF. Packmate processes live traffic and instantly displays the results. +2. `FILE` - processes traffic from pcap files. Useful to analyze traffic from past CTFs where Packmate wasn't launched, or CTFs where it's impossible to use it on the vulnbox. +3. `VIEW` - Packmate does not process any traffic, but simply shows already processed streams. Useful for post-game analyses. + +
+ LIVE setup + +Set the interface through which the game traffic passes. +IP address from `PACKMATE_LOCAL_IP` should be bound to the same interface. + +```dotenv +# Mode: capturing +PACKMATE_MODE=LIVE +# Interface to capture on +PACKMATE_INTERFACE=game +``` + +
+ +
+ FILE setup + +Set the name of the pcap file in the `pcaps` directory. +After the startup, in the web interface, you will see the button that activates the file processing. +It's important that by this moment all services and patterns are already created (see Usage). + +```dotenv +# Mode: pcap file anysis +PACKMATE_MODE=FILE +# Path to pcap file in the pcaps directory +PACKMATE_PCAP_FILE=dump.pcap +``` + +
+ +
+ VIEW setup + +In that mode, Packmate simply shows already existing data. + +```dotenv +# Mode: viewing the data +PACKMATE_MODE=VIEW +``` + +
+ +### Database cleanup +On large CTFsб after some time a lot of traffic will pile up. This can slow Packmate down and take a lot of drive space. + +To optimize the workflow, it is recommended to enable periodical database cleanup of old streams. It will only work in the `LIVE` mode. +```dotenv +PACKMATE_OLD_STREAMS_CLEANUP_ENABLED=true +# Old streams removal interval (in minutes). +# It's better to use small numbers so the streams are removed in small chunks and don't overload the server. +PACKMATE_OLD_STREAMS_CLEANUP_INTERVAL=1 +# How old the stream must be to be removed (in minutes before current time) +PACKMATE_OLD_STREAMS_CLEANUP_THRESHOLD=240 +``` + +### Additional settings + +```dotenv +# Database password. Considering it only listens on localhost, it's not mandatory to change it, but you can do it for additional security. +PACKMATE_DB_PASSWORD=K604YnL3G1hp2RDkCZNjGpxbyNpNHTRb +# Packmate version. Change it if you want to use a different version from the docker registry. +BUILD_TAG=latest +``` + +To use the TLS decryption, you have to put the matching private key in the `rsa_keys` directory. + +Database files are being saved in `./data`, so to reset the database, you need to delete this directory. \ No newline at end of file diff --git a/docs/USAGE.md b/docs/USAGE.md new file mode 100644 index 0000000..a378b13 --- /dev/null +++ b/docs/USAGE.md @@ -0,0 +1,117 @@ +## Использование +### Настройки +При попытке зайти в web-интерфейс впервые, браузер спросит логин и пароль, +который указывался в env-файле. +При необходимости можно настроить дополнительные параметры по кнопке с шестеренками в верхнем +правом углу экрана. + +Скриншот настроек + +### Создание сервисов +Сначала нужно создать сервисы, находящиеся в игре. Если не сделать этого, то никакие стримы не будут сохраняться! +Для этого вызывается диалоговое окно по нажатию кнопки `+` в навбаре, +где можно указать название и порт сервиса, а также дополнительные опции. + +Скриншот окна создания сервиса + +#### Параметры сервиса: +1. Имя +2. Порт (если сервис использует несколько портов, нужно создать по сервису на каждый порт) +3. Chunked transfer encoding: автоматически раскодировать [подобные](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Transfer-Encoding#chunked_encoding) http пакеты +4. Urldecode: автоматически проводить urldecode пакетов. Стоит включать по умолчанию в http сервисах. +5. Merge adjacent packets: автоматически склеивать соседние пакеты в одном направлении. Стоит включать по умолчанию в небинарных сервисах. +6. Inflate WebSockets: автоматически разархивировать [сжатые](https://www.rfc-editor.org/rfc/rfc7692) websocket-пакеты. +7. Decrypt TLS: автоматически расшифровывать TLS-трафик (HTTPS). +Работает только с типами шифрования TLS_RSA_WITH_AES_*, и при наличии приватного ключа, который использовался в сертификате сервера (как Wireshark). + +### Создание паттернов +Для удобного отлова эксплоитов в приложении существует система паттернов. +Чтобы создать паттерн, нужно открыть выпадающее меню `Patterns` и нажать кнопку `+`, +затем указать параметры паттерна и сохранить. + +Важно: паттерн начнет действовать только на стримы, захваченные после его создания. Но можно использовать Lookback, чтобы проанализировать и стримы в прошлом. + +Скриншот окна создания паттерна + +#### Параметры паттерна: +1. Имя: оно отображается в списке на стримах, которые содержат этот паттерн. +2. Паттерн: само содержимое паттерна. Может быть строкой, регулярным выражением или hex-строкой в зависимости от типа паттерна. +3. Действие паттерна + 1. Highlight подсветит найденный паттерн. Пример: поиск флагов. + 2. Ignore удалит стрим, содержащий этот паттерн. + Пример: вы запатчили сервис от определенной уязвимости и больше не хотите видеть определенный эксплоит в трафике. Можно добавить этот эксплоит как паттерн с типом IGNORE, и он больше не будет сохраняться. +4. Цвет: этим цветом будут подсвечиваться паттерны с типом Highlight +5. Метод поиска: подстрока, регулярное выражение, бинарная подстрока +6. Направление поиска: везде, только в запросах, только в ответах +7. Сервис: искать в трафике всех сервисов или в каком-то конкретном + +### Начало игры +В режиме LIVE система начнет автоматически захватывать стримы и отображать их в сайдбаре. +В режиме FILE для начала обработки файла нужно нажать соответствующую кнопку в сайдбаре. +При нажатии на стрим в главном окне выводится список пакетов; +между бинарным и текстовым представлением можно переключиться по кнопке в сайдбаре. + +### Обзор навбара +![Скриншот навбара](../screenshots/Screenshot_Navbar.png) + +1. Заголовок +2. Счетчик SPM - Streams Per Minute, стримов в минуту +3. Счетчик PPS - Packets Per Stream, среднее количество пакетов в стриме +4. Кнопка открытия списка паттернов +5. Список сервисов. В каждом сервисе: + 1. Название + 2. Порт + 3. Счетчик SPM сервиса - позволяет определить наиболее популярные сервисы + 4. Кнопка редактирования сервиса +6. Кнопка добавления нового сервиса +7. Кнопка открытия настроек + + +### Обзор сайдбара +![Скриншот сайдбара](../screenshots/Screenshot_Sidebar.png) + +В левой панели Packmate находятся стримы выбранного сервиса. +Отображается номер стрима, протокол, TTL, сервис, время, хэш User-Agent (для http сервисов) и найденные паттерны. + +Совет: иногда на CTF забывают перезаписать TTL пакетов внутри сети. В таком случае по TTL можно отличить запросы от чекеров и от других команд. + +Совет #2: по User-Agent можно отличать запросы из разных источников. К примеру, можно предположить, что на скриншоте выше запросы 4 и 5 пришли из разных источников. + +Совет #3: нажимайте на звездочку, чтобы добавить интересный стрим в избранное. Этот стрим будет выделен в списке, и появится в списке избранных стримов. + +#### Управление просмотром + +Панель управления + +1. Пауза: Остановить/возобновить показ новых стримов на экране. Не останавливает перехват стримов и показ другим пользователям! Полезно, если стримы летят слишком быстро. +2. Избранные: показать только стримы, отмеченные как избранные +3. Переключить текстовый/hexdump вид +4. Начать анализ: появляется только при запуске в режиме `FILE` +5. Промотать список стримов до самого нового + +### Обзор меню паттернов +![Список паттернов](../screenshots/Screenshot_Patterns.png) + +1. Кнопка добавления паттерна +2. Выбор всех стримов (убрать фильтрацию по паттерну) +3. Список паттернов. В каждой строчке: + 1. Описание паттерна + 2. Кнопка Lookback - позволяет применить паттерн к стримам, обработанным до создания паттерна. + 3. Пауза - паттерн нельзя удалить, но можно поставить на паузу. После этого он не будет применяться к новым стримам. + +Совет: создавайте отдельные паттерны для входящих и исходящих флагов. Так легче отличать чекер, кладущий флаги, от эксплоитов. + +Совет #2: используйте Lookback для исследования найденных эксплоитов. + +Пример: вы обнаружили, что сервис только что отдал флаг пользователю `abc123` без видимых причин. +Можно предположить, что атакующая команда создала этого пользователя и подготовила эксплоит в другом стриме. +Но в игре слишком много трафика, чтобы найти этот стрим вручную. +Тогда можно создать `SUBSTRING` паттерн со значением `abc123` и активировать Lookback на несколько минут назад. +После этого со включенным фильтром по паттерну будут отображаться только стримы, где упоминался этот пользователь. + +### Горячие клавиши +Для быстрой навигации по стримам можно использовать следующие горячие клавиши: +* `Ctrl+Up` -- переместиться на один стрим выше +* `Ctrl+Down` -- переместиться на один стрим ниже +* `Ctrl+Home` -- перейти на последний стрим +* `Ctrl+End` -- перейти на первый стрим \ No newline at end of file diff --git a/docs/USAGE_EN.md b/docs/USAGE_EN.md new file mode 100644 index 0000000..e642620 --- /dev/null +++ b/docs/USAGE_EN.md @@ -0,0 +1,110 @@ +## Usage +### Settings +When attempting to access the web interface for the first time, your browser will prompt for a login and password, which were specified in the env file. +If necessary, additional parameters can be configured via the gear icon in the top right corner of the screen. + +Screenshot of settings + +### Creating Services +First, you need to create services that are present in the game. If you don't do this, no streams will be saved! +To do this, a dialog box is called by clicking the `+` button in the navbar, +where you can specify the name and port of the service, as well as additional options. + +Screenshot of service creation window + +#### Service Parameters: +1. Name +2. Port (if the service uses multiple ports, you need to create a Packmate service for each port) +3. Chunked transfer encoding: automatically decode [chunked](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Transfer-Encoding#chunked_encoding) HTTP packets +4. Urldecode: automatically perform URL decoding of packets. Should be enabled by default for HTTP services. +5. Merge adjacent packets: automatically merge adjacent packets in the same direction. Should be enabled by default for non-binary services. +6. Inflate WebSockets: automatically decompress [compressed](https://www.rfc-editor.org/rfc/rfc7692) WebSocket packets. +7. Decrypt TLS: automatically decrypt TLS traffic (HTTPS). Only works with TLS_RSA_WITH_AES_* cipher suites and requires the private key used in the server's certificate (just like Wireshark). + +### Creating Patterns +To conveniently capture exploits in the application, a pattern system exists. +To create a pattern, open the dropdown menu `Patterns` and click the `+` button, +then specify the pattern parameters and save. + +Important: the pattern will only apply to streams captured after its creation. But you can use Lookback to analyze past streams. + +Screenshot of pattern creation window + +#### Pattern Parameters: +1. Name: it will be displayed in the list on streams that contain this pattern. +2. Pattern: the content of the pattern itself. It can be a string, a regular expression, or a hex string depending on the pattern type. +3. Pattern ation: + 1. Highlight will highlight the found pattern. Example: searching for flags. + 2. Ignore will delete the stream containing this pattern. + Example: you patched a service from a certain vulnerability and no longer want to see a specific exploit in the traffic. You can add this exploit as a pattern with IGNORE type, and it will no longer be saved. +4. Color: the color with which patterns of Highlight type will be highlighted. +5. Search method: substring, regular expression, binary substring +6. Search type: everywhere, only in requests, only in responses +7. Service: search in the traffic of all services or in a specific one. + +### Game Start +In LIVE mode, the system will automatically capture streams and display them in the sidebar. +In FILE mode, click the corresponding button in the sidebar to start processing a file. +When you click on a stream in the main window, a list of packets is displayed; +you can switch between binary and text representation using the button in the sidebar. + +### Navbar Overview +![Navbar screenshot](../screenshots/Screenshot_Navbar.png) + +1. Title +2. SPM counter - Streams Per Minute +3. PPS counter - (average number of) Packets Per Stream +4. Button to open the list of patterns +5. List of services. In each service: + 1. Name + 2. Port + 3. SPM counter for the service - allows you to determine the most popular services + 4. Service edit button +6. Button to add a new service +7. Button to open settings + +### Sidebar Overview +![Sidebar screenshot](../screenshots/Screenshot_Sidebar.png) + +Tip: Sometimes during CTFs, admins forget to overwrite the TTL of packets inside the network. In such cases, you can differentiate requests from checkers and other teams based on TTL. + +Tip #2: User-Agent can be used to differentiate requests from different sources. For example, in the screenshot above, requests 4 and 5 may have come from different sources. + +Tip #3: Click on the star icon to add an interesting stream to your favorites. This stream will be highlighted in the list and will appear in the list of favorite streams. + +#### Control Panel + +Control Panel + +1. Pause: Stop/resume displaying new streams on the screen. It does not stop intercepting streams or showing them to other users! Useful if streams are flying by too quickly. +2. Favorites: Show only streams marked as favorites. +3. Switch text/hexdump view. +4. Start analysis: Only appears when running in `FILE` mode. +5. Scroll stream list to the newest. + +### Pattern Menu Overview +![Pattern List](../screenshots/Screenshot_Patterns.png) + +1. Add Pattern Button +2. Select All Streams (do not filter by pattern) +3. Pattern List. Each line contains: + 1. Pattern Description + 2. Lookback Button - applies the pattern to streams processed before the pattern creation. + 3. Pause - pattern cannot be deleted, but can be paused. It will not be applied to new streams after pausing. + +Tip: Create separate patterns for incoming and outgoing flags to easily distinguish between flag checkers and exploits. + +Tip #2: Use Lookback to investigate discovered exploits. + +Example: You found that the service just handed out a flag to user `abc123` without an apparent reason. +You can assume that the attacking team created this user and prepared an exploit in another stream. +But there is too much traffic in the game to manually find this stream. +Then you can create a `SUBSTRING` pattern with the value `abc123` and activate Lookback for a few minutes back. +After that, with the pattern filter enabled, only streams mentioning this user will be displayed. + +### Hotkeys +Use the following hotkeys for quick navigation through streams: +* `Ctrl+Up` -- Move one stream up. +* `Ctrl+Down` -- Move one stream down. +* `Ctrl+Home` -- Go to the last stream. +* `Ctrl+End` -- Go to the first stream. \ No newline at end of file diff --git a/pcaps/dump.pcap b/pcaps/dump.pcap new file mode 100644 index 0000000..733d568 Binary files /dev/null and b/pcaps/dump.pcap differ diff --git a/screenshots/Screenshot.png b/screenshots/Screenshot.png index 520e3ca..88b69ec 100644 Binary files a/screenshots/Screenshot.png and b/screenshots/Screenshot.png differ diff --git a/screenshots/Screenshot_Navbar.png b/screenshots/Screenshot_Navbar.png new file mode 100644 index 0000000..beb213a Binary files /dev/null and b/screenshots/Screenshot_Navbar.png differ diff --git a/screenshots/Screenshot_Pattern.png b/screenshots/Screenshot_Pattern.png new file mode 100644 index 0000000..4dbf338 Binary files /dev/null and b/screenshots/Screenshot_Pattern.png differ diff --git a/screenshots/Screenshot_Patterns.png b/screenshots/Screenshot_Patterns.png new file mode 100644 index 0000000..a36218f Binary files /dev/null and b/screenshots/Screenshot_Patterns.png differ diff --git a/screenshots/Screenshot_Service.png b/screenshots/Screenshot_Service.png new file mode 100644 index 0000000..5720e5d Binary files /dev/null and b/screenshots/Screenshot_Service.png differ diff --git a/screenshots/Screenshot_Sidebar.png b/screenshots/Screenshot_Sidebar.png new file mode 100644 index 0000000..6ef2baf Binary files /dev/null and b/screenshots/Screenshot_Sidebar.png differ diff --git a/screenshots/Screenshot_Sidebar_header.png b/screenshots/Screenshot_Sidebar_header.png new file mode 100644 index 0000000..a800d6d Binary files /dev/null and b/screenshots/Screenshot_Sidebar_header.png differ diff --git a/src/main/java/ru/serega6531/packmate/pcap/FilePcapWorker.java b/src/main/java/ru/serega6531/packmate/pcap/FilePcapWorker.java index 0f9e178..6eb2b2a 100644 --- a/src/main/java/ru/serega6531/packmate/pcap/FilePcapWorker.java +++ b/src/main/java/ru/serega6531/packmate/pcap/FilePcapWorker.java @@ -16,6 +16,7 @@ import ru.serega6531.packmate.service.SubscriptionService; import java.io.EOFException; import java.io.File; import java.net.UnknownHostException; +import java.util.Arrays; @Slf4j public class FilePcapWorker extends AbstractPcapWorker { @@ -31,8 +32,9 @@ public class FilePcapWorker extends AbstractPcapWorker { super(servicesService, streamService, localIpString); this.subscriptionService = subscriptionService; - file = new File(filename); + file = new File("pcaps", filename); if (!file.exists()) { + log.info("Existing files: " + Arrays.toString(new File("pcaps").listFiles())); throw new IllegalArgumentException("File " + file.getAbsolutePath() + " does not exist"); } diff --git a/src/main/java/ru/serega6531/packmate/service/optimization/TlsDecryptor.java b/src/main/java/ru/serega6531/packmate/service/optimization/TlsDecryptor.java index e36e9b5..d743ec9 100644 --- a/src/main/java/ru/serega6531/packmate/service/optimization/TlsDecryptor.java +++ b/src/main/java/ru/serega6531/packmate/service/optimization/TlsDecryptor.java @@ -107,7 +107,7 @@ public class TlsDecryptor { int blockCipherSize = Integer.parseInt(blockCipherParts[1]); String blockCipherMode = blockCipherParts[2]; - if (!blockCipherAlgo.equals("AES")) { //TODO использовать не только AES256 + if (!blockCipherAlgo.equals("AES")) { return; } diff --git a/src/main/java/ru/serega6531/packmate/tasks/OldStreamsCleanupTask.java b/src/main/java/ru/serega6531/packmate/tasks/OldStreamsCleanupTask.java index 7635a3b..f98a21d 100644 --- a/src/main/java/ru/serega6531/packmate/tasks/OldStreamsCleanupTask.java +++ b/src/main/java/ru/serega6531/packmate/tasks/OldStreamsCleanupTask.java @@ -2,7 +2,7 @@ package ru.serega6531.packmate.tasks; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Value; -import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; import org.springframework.scheduling.annotation.Scheduled; import org.springframework.stereotype.Component; import ru.serega6531.packmate.service.StreamService; @@ -12,7 +12,7 @@ import java.time.temporal.ChronoUnit; @Component @Slf4j -@ConditionalOnProperty(name = "old-streams-cleanup-enabled", havingValue = "true") +@ConditionalOnExpression("${old-streams-cleanup-enabled:false} && '${capture-mode}' == 'LIVE'") public class OldStreamsCleanupTask { private final StreamService service; diff --git a/src/test/java/ru/serega6531/packmate/StreamOptimizerTest.java b/src/test/java/ru/serega6531/packmate/StreamOptimizerTest.java index 6f7cd21..c7d01e0 100644 --- a/src/test/java/ru/serega6531/packmate/StreamOptimizerTest.java +++ b/src/test/java/ru/serega6531/packmate/StreamOptimizerTest.java @@ -3,6 +3,7 @@ package ru.serega6531.packmate; import org.apache.commons.lang3.ArrayUtils; import org.junit.jupiter.api.Test; import ru.serega6531.packmate.model.Packet; +import ru.serega6531.packmate.service.optimization.HttpChunksProcessor; import ru.serega6531.packmate.service.optimization.HttpGzipProcessor; import ru.serega6531.packmate.service.optimization.HttpUrldecodeProcessor; import ru.serega6531.packmate.service.optimization.PacketsMerger; @@ -67,6 +68,18 @@ class StreamOptimizerTest { assertEquals(2, list.get(3).getContent().length); } + @Test + void testChunkedTransferEncoding() { + String content = "HTTP/1.1 200 OK\r\nTransfer-Encoding: chunked\r\n\r\n" + + "6\r\nChunk1\r\n6\r\nChunk2\r\n0\r\n\r\n"; + + List packets = new ArrayList<>(List.of(createPacket(content.getBytes(), false))); + new HttpChunksProcessor(packets).processChunkedEncoding(); + + assertEquals(1, packets.size()); + assertTrue(packets.get(0).getContentString().contains("Chunk1Chunk2")); + } + private Packet createPacket(int content, boolean incoming) { return createPacket(new byte[] {(byte) content}, incoming); }