
Injeção de shellcode usando a Windows Debugging API
DbgNexum é uma Prova de Conceito para injetar shellcode usando a API de Depuração do Windows e Memória Compartilhada (Mapeamento de Arquivo). Ele evita escrever e ler memória remota diretamente, utilizando manipulação de contexto para forçar o processo alvo a carregar e executar o payload por conta própria.
O injetor anexa a um processo alvo e cria uma thread suspensa. Por meio de um loop de depuração, ele define um Ponto de Interrupção de Hardware (HWBP) para capturar a execução em um endereço de retorno específico. A cada captura, o injetor modifica os registradores da CPU para simular chamadas de função, orquestrando uma sequência de chamadas de função da API do Windows dentro do processo alvo.
No momento em que este README foi escrito, testei a técnica contra o MDE e o Elastic, e nenhum deles a detectou.
WriteProcessMemory / VirtualAllocEx: O payload é transferido via CreateFileMapping e MapViewOfFile.ReadProcessMemory: A abordagem obtém todas as informações principais do contexto da thread.A PoC usa um shellcode XORado do msfvenom que abre "calc.exe". Mas use seu próprio shellcode!
shellcode.hDbgNexum.exe <PID>
Exemplo de Saída:
[i] Section 'MZ' created and shellcode copied
[+] Bait thread created. Setting HWBP on FileTimeToSystemTime
[i] Execution Redirected:
|-> [0] Preparation & anchoring stack
|-> [1] Setting HWBP & buffer alloc
|-> [2] Copying File-Mapping name
|-> [3] Zeroing stack slot
|-> [4] Opening handle to named file mapping
|-> [5] Mapping payload into mem. with exec. perm.
|-> [6] Cleanup & shellcode execution
[+] Successfully detached from process 19256
[i] Orchestration complete.
O fluxo de execução é uma constante troca entre o Loop de Depuração do injetor e o processo alvo.
Estágios da Injeção
A função DebugLoop contém a lógica principal da injeção e orquestra a "máquina de estados":
0. Preparação:
ret instantânea.1. Alocação:
LocalAlloc para (obviamente) alocar um pequeno buffer.2. Configuração de Dados:
memcpy para copiar a string MZ para o buffer previamente alocado.3. Preparação da Pilha:
memset para zerar um slot da pilha. Isso é preparação para o estágio 5, que chamará MapViewOfFile. Como a função usará mais de 4 argumentos, o 5º argumento é passado pela pilha (que definimos aqui).4. Abrir Mapeamento:
OpenFileMappingA usando o nome MZ, "criado" nos estágios 2 e 3.5. Mapear Payload:
MapViewOfFile. Isso mapeia a seção de memória compartilhada (contendo o shellcode) no espaço de endereçamento do alvo com permissões EXECUTE.6. Execução:
RIP para o endereço retornado por MapViewOfFile.