🪟Windows API confidence abuse basics
In this article i will focus on how to use the legitimate Windows API functions like EnumUILanguagesW
to execute shellcode in a more stealthy manner than a simple CreateThread
. Unlike traditional shellcode execution techniques, this approach utilizes a "begnin" system function commonly employed for enumerating available UI languages making it much harder to detect.
Step 1: Injecting Shellcode into Memory
Once the shellcode is decrypted (using a method like ROT1 decryption), it is injected into memory, ready for execution. The shellcode needs to be placed in executable memory as described before. For simplicity purposes we will keep use a "dirty" way to allocate it, so we can focus on the important part of the execution chain. (not much a problem in Go beacause memory management is automated)
ptr := unsafe.Pointer(addr)
copy((*[1 << 30]byte)(ptr)[:], shellcode)
Step 2: Stealthy Execution via EnumUILanguagesW
EnumUILanguagesW
The core of this technique lies in calling EnumUILanguagesW
, a function typically used to enumerate the languages installed on a system. While this function is legitimate (and so poorly monitored), it can be repurposed to execute shellcode stored in memory, which significantly reduces the chances of detection.
Using EnumUILanguagesW
to Execute Shellcode
//windows API functions definition
kernel32 := windows.NewLazySystemDLL("kernel32.dll")
procEnumUILanguagesW := kernel32.NewProc("EnumUILanguagesW")
// Calling EnumUILanguagesW, passing the shellcode memory address
_, _, err := procEnumUILanguagesW.Call(
addr, // Address of shellcode in memory
0, // MUI_LANGUAGE_ID - not needed in this case
0, // lParam - null
)
Why functions like EnumUILanguagesW
are better
EnumUILanguagesW
are betterUsing a common and legitimate Windows function like EnumUILanguagesW
for executing shellcode provides several advantages:
Legitimate Function:
EnumUILanguagesW
is part of the Windows API and is used by various applications, making it a low-profile function that’s often overlooked by security tools.No Suspicious Behavior: Unlike functions that spawn new threads with
CreateThread
, this technique doesn’t trigger obvious flags for most security products that monitor such behaviors.Minimal Footprint: The shellcode executes within the context of the calling application, without spawning new processes or threads, making it much harder to detect through traditional monitoring methods.
Bypassing Detection: Security tools focused on detecting malicious use of process creation may miss this technique, as the shellcode is executed via a common API used in many legitimate processes.
Credits
This trick is not a result of my own researches, i just implemented it in go (and that obiously was quite simple as you can see). the function i taken in example is a kind of "LOLBin', you can retrieve a non exhastive list with cpp implementations at this link The full code is available here
Last updated