
Agente C2 multiplataforma para Mythic com carregamento dinâmico de funções, proxy SOCKS5, operações de arquivos, injeção de shellcode e módulos de pós-exploração para macOS/Windows.
Medusa é um agente multiplataforma compatível com Python 3.8 e Python 2.7.
Para instalar a Medusa, você precisará ter o Mythic v3 instalado em um computador remoto. Você pode encontrar instruções de instalação do Mythic na página do projeto Mythic.
A partir da raiz de instalação do Mythic, execute o comando:
./mythic-cli install github https://github.com/MythicAgents/Medusa.git
Após a instalação, reinicie o Mythic para compilar um novo agente.
O arquivo Payload_Type/medusa/rabbitmq_config.json é um modelo e deve corresponder ao seu ambiente Mythic.
rabbitmq_password com o valor do seu RABBITMQ_PASSWORD do Mythic (normalmente do .env do Mythic).rabbitmq_host com o nome do host/container do RabbitMQ (geralmente mythic_rabbitmq em configurações docker-compose, ou 127.0.0.1 para binds locais).mythic_server_host com o nome do host/container do servidor Mythic (geralmente mythic_server em configurações docker-compose, ou 127.0.0.1 para binds locais).O agente base e os comandos incluídos usam bibliotecas Python nativas, portanto, não precisam de pacotes adicionais para funcionar. Os agentes executarão os comandos em threads, então uploads ou downloads longos não bloquearão o agente principal.
Ambas as versões do agente Medusa usam uma implementação AES256 HMAC escrita com bibliotecas nativas (adaptada de aqui), eliminando a necessidade de dependências adicionais além de uma instalação padrão do Python. Portanto, o agente deve funcionar em hosts Windows, Linux e macOS. Vale mencionar que essa implementação criptográfica introduz alguma sobrecarga ao lidar com arquivos grandes (capturas de tela, downloads, etc.), mas é funcional.
Dentro do diretório Payload_Type/Medusa/agent_code, você verá arquivos base_agent com sufixos py2 e py3. Da mesma forma, extensões de arquivo semelhantes podem ser vistas para arquivos de funções individuais.
Eles são lidos pelo script builder.py para primeiro selecionar a versão correta do Python base do agente Medusa. O builder.py então incluirá comandos específicos para a versão escolhida do Python. No caso em que um comando tem apenas a extensão .py, ele será usado por padrão, assumindo que nenhum código alternativo é necessário entre as versões Py2 e Py3.
A Medusa usa threading básico para execução de tarefas. Onde as tarefas são potencialmente de longa duração, elas podem ser implementadas com uma 'verificação de parada' para responder a um sinal da tarefa jobkill. Isso pode ser implementado com um trecho de código semelhante ao mostrado abaixo:
if [task for task in self.taskings if task["task_id"] == task_id][0]["stopped"]:
# Alguma limpeza específica da tarefa
return "Tarefa interrompida."
Este manipulador pode ser visto implementado nos comandos download, upload, watch_dir e screenshot.
Além disso, se a tarefa de longa duração deve fornecer saída contínua, a função sendTaskOutputUpdate - incluída no agente base - pode ser usada para atualizar o Mythic antes da conclusão da tarefa. Uma função fictícia que fornece saída contínua e pode ser interrompida com jobkill pode ser vista abaixo.
def dummyFunction(self, task_id):
while(True):
# Verifica se recebemos um sinal de parada.
if [task for task in self.taskings if task["task_id"] == task_id][0]["stopped"]: return "Tarefa interrompida."
# Envia saída de volta para o Mythic
self.sendTaskOutputUpdate(task_id, "Ainda estamos em execução")
time.sleep(10)
A Medusa atualmente suporta dois perfis C2: http (com e sem criptografia AES256 HMAC) e azure_blob.
O perfil HTTP faz callback para o servidor Mythic através do perfil básico, não dinâmico. Requisições GET para tarefas, requisições POST com respostas.
| Comando | Sintaxe | Descrição |
|---|
| cat | cat caminho/para/arquivo | Ler e exibir o conteúdo do arquivo. |
| cd | cd [.. diretório] | Alterar diretório de trabalho (.. para subir um nível). |
| cp | cp origem_arquivo_ou_pasta destino_arquivo_ou_pasta | Copiar arquivo ou pasta para o destino. |
| cwd | cwd | Exibir diretório de trabalho atual. |
| download | download [caminho] | Baixar um arquivo do sistema alvo. |
| download_bulk | download_bulk [caminho1] [caminho2] ... | Baixar múltiplos arquivos do sistema alvo em uma única tarefa. |
| exit | exit | Encerrar um callback. |
| env | env | Exibir variáveis de ambiente. |
| eval_code | eval_code [comandos] | Executar código Python e retornar a saída. |
| jobkill | jobkill [id da tarefa] | Enviar sinal de parada para tarefa de longa duração. |
| jobs | jobs | Listar tarefas de longa duração, como downloads. |
| list_modules | list_modules [nome_do_módulo] | Listar módulos na memória ou a listagem completa de arquivos de um módulo específico. |
| load | load comando | Carregar uma nova capacidade em um agente. |
| load_module | load_module | Carregar um módulo Python compactado (.zip) na memória (adaptado de aqui e aqui). |
| load_script | load_script | Carregar e executar um script Python através do agente. |
| ls | ls [. caminho] | Listar arquivos e pastas em [caminho] ou use . para o diretório atual. |
| mv | mv origem_arquivo_ou_pasta destino_arquivo_ou_pasta | Mover arquivo ou pasta para o destino. |
| pip_freeze | pip_freeze | Listar programaticamente os pacotes instalados no sistema. |
| pty | pty [/bin/bash] / pty self / pty fork | Abrir uma sessão PTY interativa. Modos: spawn executa um programa com PTY, self abre um REPL Python no processo com estado do agente ao vivo, fork bifurca o agente em um REPL Python com estado snapshot (apenas Linux/macOS). |
| rm | rm arquivo_ou_pasta | Excluir arquivo ou pasta. |
| shell | shell [comando] | Executar um comando shell que será iniciado usando subprocess.Popen(). Observe que isso aguardará o comando terminar, então tome cuidado para não bloquear seu agente. |
| socks | socks start/stop [porta] | Iniciar/parar proxy SOCKS5 através do agente Medusa. |
| sleep | sleep [segundos] [porcentagem de jitter] | Definir o intervalo de callback do agente em segundos. |
| unload | unload comando | Remover uma capacidade existente de um agente. |
| unload_module | unload_module nome_do_módulo | Remover um módulo Python previamente carregado na memória. |
| upload | upload | Fazer upload de um arquivo para um caminho remoto na máquina. |
| watch_dir | watch_dir caminho segundos | Monitorar alterações no diretório alvo, verificando alterações em uma taxa especificada. |
| Comando | Sintaxe | Descrição |
|---|
| clipboard | clipboard | Exibir o conteúdo da área de transferência (usa API Objective-C, conforme descrito por Cedric Owens aqui. Apenas macOS, apenas Python 2.7). |
| list_apps | list_apps | Listar aplicativos macOS (apenas Python 2.7, apenas macOS). |
| list_tcc | list_tcc [caminho] | Listar entradas no banco de dados TCC do macOS (requer acesso total ao disco e apenas Big Sur por enquanto). |
| screenshot | screenshot | Tirar uma captura de tela (usa API Objective-C, apenas macOS, apenas Python 2.7). |
| spawn_jxa | spawn_jxa | Iniciar um processo osascript e enviar conteúdo Javascript para ele. |
| vscode_list_recent | vscode_list_recent [state_db] | Listar arquivos e pastas abertos recentemente com VSCode. |
| vscode_open_edits | vscode_open_edits [caminho_do_diretório_de_backup] | Listar alterações não salvas em arquivos no VSCode. |
| vscode_watch_edits | vscode_watch_edits [caminho para diretório remoto] [intervalo_de_polling] | Monitorar o diretório de backups do VSCode em um intervalo determinado por alterações não salvas. |
| Comando | Sintaxe | Descrição |
|---|
| shinject | shinject | Injetar shellcode em um PID alvo usando CreateRemoteThread (apenas Windows - adaptado de aqui). |
| load_dll | load_dll caminho_da_dll export_da_dll | Carregar uma DLL do disco e executar uma função exportada (NOTA: Esta DLL deve retornar um valor int ao finalizar; uma DLL criada com msfvenom, por exemplo, matará seu agente ao finalizar). |
| list_dlls | list_dlls [pid] | Ler a memória do processo (PEB) do processo local ou alvo para obter lista de DLLs carregadas (apenas Python 3) |
| ps | ps | Obter informações limitadas do processo, ex.: PID, nomes de processos, arquitetura e caminhos de binários (apenas Python 3) |
| ps_full | ps_full | Obter informações completas do processo, incluindo PPID, nível de integridade e linha de comando (apenas Python 3) |
| kill | kill | Encerrar um processo pelo ID do processo (apenas Python 3) |