
ScareCrow - Marco de creación de payloads diseñado para la evasión de EDR.
Para ver la última versión de ScareCrow o reportar un problema, consulte https://github.com/Tylous/ScareCrow.
Si desea obtener más información sobre las técnicas utilizadas en este framework, consulte Parte 1 y Parte 2
ScareCrow es un framework de creación de payloads para side loading (no inyección) en un proceso legítimo de Windows (evitando los controles de Application Whitelisting). Una vez que el cargador DLL se carga en memoria, utiliza una técnica para eliminar los hooks de un EDR de las DLL del sistema que se ejecutan en la memoria del proceso. Esto funciona porque sabemos que los hooks del EDR se colocan cuando se crea un proceso.
ScareCrow puede apuntar a estas DLL y manipularlas en memoria utilizando la función de API VirtualProtect, que cambia los permisos de una sección de la memoria de un proceso a un valor diferente, específicamente de Ejecutar-Leer a Leer-Escribir-Ejecutar.
ScareCrow utiliza 1 de 2 métodos para desenganchar (unhook)
Cuando se ejecuta, ScareCrow copia los bytes de las DLL del sistema almacenadas en disco en C:\Windows\System32\. Estas DLL se almacenan en disco "limpias" de hooks del EDR porque son utilizadas por el sistema para cargar una copia sin alterar en un nuevo proceso cuando se crea. Dado que los EDR solo enganchan estos procesos en memoria, permanecen sin alterar. ScareCrow no copia todo el archivo DLL, sino que solo se centra en la sección .text de las DLL. Esta sección de una DLL contiene el ensamblado ejecutable, y al hacer esto, ScareCrow ayuda a reducir la probabilidad de detección, ya que releer archivos completos puede hacer que un EDR detecte una modificación en un recurso del sistema. Luego, los datos se copian en la región de memoria correcta utilizando el desplazamiento de cada función. Cada función tiene un desplazamiento que denota el número exacto de bytes desde la dirección base donde residen, proporcionando la ubicación de la función en la pila.
Para hacer esto, ScareCrow cambia los permisos de la región de memoria .text usando VirtualProtect. Aunque se trata de una DLL del sistema, dado que se ha cargado en nuestro proceso (que controlamos), podemos cambiar los permisos de memoria sin requerir privilegios elevados.
ScareCrow carga el shellcode en memoria descifrando primero el shellcode, que está cifrado mediante uno de tres métodos de cifrado (descritos a continuación). Una vez descifrado y cargado, el shellcode se ejecuta. Dependiendo de las opciones de cargador especificadas, ScareCrow configurará diferentes funciones de exportación para la DLL. La DLL cargada tampoco contiene la función DLLMain estándar que todas las DLL normalmente necesitan para funcionar. La DLL se ejecutará sin problemas porque el proceso en el que cargamos buscará esas funciones de exportación y no se preocupará por la presencia de DLLMain.
Después
KnownDLLs es una lista de DLL que Windows carga durante el inicio del sistema. Debido a que estas DLL se consideran esenciales para el funcionamiento del sistema operativo, se almacenan en caché para ayudar a reducir los tiempos de carga y mejorar el rendimiento cuando las aplicaciones se inician. KnownDLLs incluye DLL como kernel32.dll, kernelbase.dll y ntdll.dll.
Utilizando estos KnownDlls, ScareCrow mapea una copia de la DLL desde \KnownDlls\<dllname> usando una combinación de NtOpenSection y NtMapViewOfSection para cargarla en la memoria del proceso. ScareCrow no carga toda la DLL, sino que solo carga la sección .text de la DLL (ya que contiene todas las syscalls). A partir de ahí, ScareCrow utiliza llamadas indirectas al sistema (indirect syscalls) para llamar a NtProtectVirtualMemory y cambiar los permisos de la sección de memoria .text de la DLL para permitir que ScareCrow sobrescriba los hooks del EDR antes de restaurar los permisos.
Para obtener más información, puede leer el artículo detallado de modexp.
Una vez que se eliminan estos hooks, ScareCrow utiliza llamadas al sistema personalizadas para cargar y ejecutar shellcode en memoria. ScareCrow hace esto incluso después de eliminar los hooks del EDR para ayudar a evitar la detección por herramientas de recopilación de telemetría que no están basadas en el espacio de usuario (userland), como Event Tracing for Windows (ETW) u otros mecanismos de registro de eventos. Estas llamadas al sistema personalizadas también se utilizan para realizar la llamada VirtualProtect para eliminar los hooks colocados por los EDR, descrito anteriormente, para evitar la detección por los controles anti-manipulación de cualquier EDR. Esto se hace llamando a una versión personalizada de la syscall VirtualProtect, NtProtectVirtualMemory. ScareCrow utiliza Golang para generar estos cargadores y luego ensamblador para estas funciones de syscall personalizadas.
Durante el proceso de creación del cargador, ScareCrow utiliza una biblioteca para mimetizarse en segundo plano después de que un beacon se comunica con el centro de control. Esta biblioteca hace dos cosas:
Los archivos firmados con certificados de firma de código suelen recibir menos escrutinio, lo que facilita su ejecución sin ser cuestionados, ya que los archivos firmados por un nombre de confianza suelen ser menos sospechosos que otros. La mayoría de los productos antimalware no tienen tiempo para validar y verificar estos certificados (ahora algunos lo hacen, pero normalmente los nombres de proveedores comunes están incluidos en una lista blanca). ScareCrow crea estos certificados utilizando una versión en paquete de Go de la herramienta limelighter para crear un archivo pfx12. Este paquete toma un nombre de dominio ingresado por el usuario para crear un certificado de firma de código para ese dominio. Si es necesario, también puede usar su propio certificado de firma de código si tiene uno, usando la opción de línea de comandos valid.
clone, junto con la ruta al archivo del cual desea copiar el certificado. Al firmar el cargador con microsoft.com, usarlos contra productos de WINDOWS DEFENDER ATP puede no ser tan efectivo, ya que pueden validar el certificado porque les pertenece. Si está utilizando un cargador contra un producto de Windows, posiblemente use un dominio diferente.
Con estos archivos y el código Go, ScareCrow los compilará de forma cruzada en DLL utilizando la opción de biblioteca compartida c-shared. Una vez que la DLL se compila, se ofusca en una cadena base64 rota que se incrustará en un archivo. Esto permite que el archivo se recupere de forma remota, se acceda y se ejecute programáticamente.
Si bien ScareCrow tiene una extensa lista de atributos de archivo, hay algunas circunstancias en las que se requiere un conjunto de atributos personalizado (quizás específico del entorno). Para acomodar esto, ScareCrow permite la entrada de un archivo JSON que contiene atributos. Usando la opción de línea de comandos -configfile, ScareCrow utilizará estos atributos y el nombre de archivo en lugar de los preexistentes en ScareCrow. El archivo main.json contiene una plantilla de muestra de la estructura JSON que debe tener para funcionar correctamente. Tenga en cuenta que lo que use como "InternalName" será el nombre del archivo.
ScareCrow ahora requiere golang 1.19.1 o posterior para compilar cargadores. Si está ejecutando una versión anterior, use la versión 1.19.1 o posterior.
Consulte las nuevas versiones en: https://golang.org/dl/.
El primer paso, como siempre, es clonar el repositorio. Antes de compilar ScareCrow, deberá instalar las dependencias.
Para instalarlas, ejecute los siguientes comandos:``` go get github.com/fatih/color go get github.com/yeka/zip go get github.com/josephspurrier/goversioninfo go get github.com/Binject/debug/pe go get github.com/awgh/rawreader
Asegúrate de que lo siguiente esté instalado en tu sistema operativo:```
openssl
osslsigncode
mingw-w64
Luego, constrúyelo``` go build ScareCrow.go
Además, ScareCrow utiliza [Garble](https://github.com/burrowers/garble) para ofuscar todos los cargadores.
Nota: Varias de las dependencias no funcionan bien en Windows al compilar, por lo que se recomienda compilar sus cargadores en OSX o Linux.
## Help```
./ScareCrow -h
_________ _________
/ _____/ ____ _____ _______ ____ \_ ___ \_______ ______ _ __
\_____ \_/ ___\\__ \\_ __ \_/ __ \/ \ \/\_ __ \/ _ \ \/ \/ /
/ \ \___ / __ \| | \/\ ___/\ \____| | \( <_> ) /
/_______ /\___ >____ /__| \___ >\______ /|__| \____/ \/\_/
\/ \/ \/ \/ \/
(@Tyl0us)
“Fear, you must understand is more than a mere obstacle.
Fear is a TEACHER. the first one you ever had.”
Usage of ./ScareCrow:
-Evasion string
Sets the type of EDR unhooking technique:
[*] Disk - Retrives a clean version of the DLLs ".text" field from files stored on disk.
[*] KnownDLL - Retrives a clean version of the DLLs ".text" field from the KnownDLLs directory in the object namespace.
[*] None - The Loader that WILL NOT removing the EDR hooks in system DLLs and only use custom syscalls. (default "Disk")
-Exec string
Set the template to execute the shellcode:
[*] RtlCopy - Using RtlCopy to move the shellcode into the allocated address in the current running process by making a Syscall.
[*] ProcessInjection - Process Injection Mode.
[*] NtQueueApcThreadEx - Executes the shellcode by creating an asynchronous procedure call (APC) to a target thread.
[*] VirtualAlloc - Allocates shellcode into the process using custom syscalls in the current running process (default "RtlCopy")
-I string
Path to the raw 64-bit shellcode.
-Loader string
Sets the type of process that will sideload the malicious payload:
[*] binary - Generates a binary based payload. (This type does not benefit from any sideloading)
[*] control - Loads a hidden control applet - the process name would be rundll32 if -O is specified a JScript loader will be generated.
[*] dll - Generates just a DLL file. Can be executed with commands such as rundll32 or regsvr32 with DllRegisterServer, DllGetClassObject as export functions.
[*] excel - Loads into a hidden Excel process using a JScript loader.
[*] msiexec - Loads into MSIexec process using a JScript loader.
[*] wscript - Loads into WScript process using a JScript loader. (default "binary")
-O string
Name of output file (e.g. loader.js or loader.hta). If Loader is set to dll or binary this option is not required.
-clone string
Path to the file containing the certificate you want to clone
-configfile string
The path to a json based configuration file to generate custom file attributes. This will not use the default ones.
-console
Only for Binary Payloads - Generates verbose console information when the payload is executed. This will disable the hidden window feature.
-delivery string
Generates a one-liner command to download and execute the payload remotely:
[*] bits - Generates a Bitsadmin one liner command to download, execute and remove the loader (Compatible with Binary, Control, Excel, and Wscript Loaders).
[*] hta - Generates a blank hta file containing the loader along with an MSHTA command to execute the loader remotely in the background (Compatible with Control and Excel Loaders).
[*] macro - Generates an office macro that will download and execute the loader remotely (Compatible with Control, Excel, and Wscript Loaders).
-domain string
The domain name to use for creating a fake code signing cert. (e.g. www.acme.com)
-encryptionmode string
Sets the type of encryption to encrypt the shellcode:
[*] AES - Enables AES 256 encryption.
[*] ELZMA - Enables ELZMA encryption.
[*] RC4 - Enables RC4 encryption. (default "ELZMA")
-export string
For DLL Loaders Only - Specify an Export function for a loader to have.
-injection string
Enables Process Injection Mode and specify the path to the process to create/inject into (use \ for the path).
-noamsi
Disables the AMSI patching that prevents AMSI BufferScanner.
-noetw
Disables the ETW patching that prevents ETW events from being generated.
-nosign
Disables file signing, making -domain/-valid/-password parameters not required.
-nosleep
Disables the sleep delay before the loader unhooks and executes the shellcode.
-obfu
Enables Garbles Literal flag replaces golang libray strings with more complex variants, resolving to the same value at run-time. This creates a larger loader and times longer to compile
-outpath string
The path to put the final Payload/Loader once it's compiled.
-password string
The password for code signing cert. Required when -valid is used.
-sandbox
Enables sandbox evasion using IsDomainJoined calls.
-url string
URL associated with the Delivery option to retrieve the payload. (e.g. https://acme.com/)
-valid string
The path to a valid code signing cert. Used instead -domain if a valid code signing cert is desired.
El Cargador determina el tipo de técnica utilizada para cargar el shellcode en el sistema de destino. Si no se selecciona ninguna opción de Cargador, ScareCrow simplemente compilará un archivo DLL estándar, que puede ser utilizado por rundll32, regsvr32 u otras técnicas que utilicen un DLL. ScareCrow utiliza tres tipos diferentes de cargadores para cargar shellcode en memoria:
ScareCrow también puede generar payloads binarios si es necesario, utilizando la opción de línea de comandos -Loader. Estos binarios no se benefician de las técnicas de carga lado a lado, pero sirven como una técnica adicional para ejecutar shellcode según la situación.
ScareCrow utiliza una técnica para primero crear el proceso y luego moverlo al fondo. Esto logra dos cosas: primero, ayuda a mantener el proceso oculto y segundo, evita ser detectado por cualquier producto EDR. Generar un proceso inmediatamente en segundo plano puede ser muy sospechoso y un indicador de maliciosidad. ScareCrow lo hace llamando a las funciones de Windows GetConsoleWindow y ShowWindow después de que el proceso es creado y los hooks del EDR están cargados, y luego cambia los atributos de la ventana a oculto. ScareCrow utiliza estas API en lugar de usar el tradicional -ldflags -H=windowsgui, ya que esto está altamente firmado y clasificado en la mayoría de los productos de seguridad como un Indicador de Compromiso.
Si se selecciona la opción de línea de comandos -console, ScareCrow no ocultará el proceso en segundo plano. En su lugar, ScareCrow agregará varios mensajes de depuración que muestran lo que está haciendo el cargador.
ScareCrow utiliza diferentes plantillas para ejecutar shellcode. Para elegir qué plantilla usar, utilice la opción de línea de comandos -Exec. Estas plantillas incluyen:
ScareCrow tiene la capacidad de realizar ataques de inyección de procesos. Para evitar cualquier hook o detección tanto en el proceso cargador como en el propio proceso inyectado, ScareCrow primero desengancha el proceso cargador como lo haría normalmente, asegurándose de que no haya hooks en el proceso. Una vez completado, el cargador generará el proceso especificado en el comando de creación. Una vez generado, el cargador creará un identificador al proceso para obtener una lista de los DLLs cargados. Una vez que encuentra los DLLs, enumerará la dirección base de cada DLL en el proceso remoto. Utilizando la función WriteProcessMemory, el cargador escribirá los bytes de los DLLs del sistema almacenados en disco (ya que están "limpios" de hooks del EDR) sin necesidad de cambiar primero los permisos de memoria. ScareCrow usa WriteProcessMemory porque esta función contiene una característica utilizada principalmente en depuración: incluso si una sección de memoria es de solo lectura, si todo es correcto en la llamada a Write¬Process¬Memory, cambiará temporalmente el permiso a lectura-escritura, actualizará la sección de memoria y luego restaurará los permisos originales. Una vez hecho esto, el cargador puede inyectar shellcode en el proceso generado sin problemas, ya que no hay hooks del EDR en ninguno de los dos procesos.
Esta opción se puede usar con cualquiera de las opciones de cargador. Para habilitar la inyección de procesos, use la opción de línea de comandos -injection junto con la ruta completa al proceso que desea utilizar para inyectar. Al poner la ruta como argumento, es importante rodear la ruta completa con "" o usar doble \\ para cada directorio en la ruta.
ScareCrow tiene la capacidad de parchear las funciones de AMSI (Interfaz de Análisis Antimalware) y ETW, evitando que se genere cualquier evento desde el proceso.
AMSI es una API nativa de Windows que permite a Windows Defender (u otros productos antimalware) interactuar profundamente en el sistema operativo Windows y brindar protección mejorada, específicamente contra ataques basados en memoria. AMSI permite que los productos de seguridad detecten mejor los indicadores maliciosos y ayuden a detener las amenazas. Dado que AMSI es nativo de Windows, los productos no necesitan "enganchar" AMSI, sino que cargan el DLL necesario para obtener una visión mejorada del proceso. Debido a esto, ScareCrow carga el DLL AMSI.dll y luego lo parchea para asegurarse de que cualquier resultado de la interfaz de escaneo regrese limpio. Parchear AMSI está habilitado por defecto en todos los cargadores; si desea no parchear AMSI, use la opción de línea de comandos -noamsi para deshabilitarlo en su cargador.
ETW utiliza Syscalls incorporadas para generar esta telemetría. Dado que ETW también es una característica nativa integrada en Windows, los productos de seguridad no necesitan "enganchar" los syscalls de ETW para obtener la información. Como resultado, para evitar ETW, ScareCrow parchea numerosos syscalls de ETW, vaciando los registros y devolviendo el flujo de ejecución a la siguiente instrucción. Parchear ETW ahora está habilitado por defecto en todos los cargadores; si desea no parchear ETW, use la opción de línea de comandos -noetw para deshabilitarlo en su cargador.
Actualmente, estas opciones solo funcionan para el proceso padre; si se usa la opción de línea de comandos -injection, el proceso primario parcheará AMSI y ETW, pero el proceso inyectado
Cifrar el shellcode es una técnica importante para protegerlo de ser detectado y analizado por EDR y otros productos de seguridad. ScareCrow viene con múltiples métodos para cifrar shellcode, que incluyen AES, ELZMA y RC4.
AES (Estándar de Cifrado Avanzado) es un algoritmo de cifrado simétrico ampliamente utilizado para cifrar datos. ScareCrow utiliza un tamaño de clave AES de 256 bits para cifrar el shellcode. La ventaja de usar AES para cifrar shellcode es que proporciona un cifrado sólido y es ampliamente compatible con las bibliotecas criptográficas. Sin embargo, el uso de un tamaño de bloque fijo puede hacerlo vulnerable a ciertos ataques, como el ataque de relleno de Oracle.
ELZMA es un algoritmo de compresión y cifrado que se usa a menudo en malware para ofuscar el código. Para cifrar shellcode usando ELZMA, primero se comprime el shellcode usando el algoritmo ELZMA. Luego, los datos comprimidos se cifran usando una clave aleatoria. Los datos cifrados y la clave se incrustan en el código de explotación. La ventaja de usar ELZMA para cifrar shellcode es que proporciona tanto compresión como cifrado en un solo algoritmo. Esto puede ayudar a reducir el tamaño del código de explotación y hacerlo más difícil de detectar.
RC4 es un algoritmo de cifrado simétrico que se usa a menudo en malware para cifrar shellcode. Es un cifrado de flujo que puede usar claves de longitud variable y es conocido por su simplicidad y velocidad.
Usar la opción de línea de comandos -obfu habilita el indicador Literal de Garble durante el proceso de compilación. Esto reemplaza cualquier referencia de biblioteca de Go y cadenas con una versión más compleja que se resuelve al mismo valor durante la ejecución. Este proceso tarda más en completarse, lo que da como resultado un archivo GO más grande. Una vez que el archivo se compila, ScareCrow analiza el archivo recién creado, eliminando cualquier IOC basado en cadenas de Go.
El argumento de línea de comandos de entrega permite generar un comando o una cadena de código (en el caso de las macros) para extraer el archivo de forma remota desde una fuente remota al host de la víctima. Estos métodos de entrega incluyen: