DLL Injection is a process injection technique that allows adversaries to execute malicious code by forcing a legitimate process to load a dynamic-link library (DLL) that contains harmful instructions. This technique is widely used in cyberattacks to evade detection, gain persistence, and execute unauthorized actions within the context of trusted applications. Since DLL files are essential components of many software applications, attackers exploit this mechanism to blend their malicious payloads with legitimate system activity.
In this blog post, we explain the T1055.001 DLL Injection technique of the MITRE ATT&CK® framework and explore how adversaries employ DLL injection with real-world attack examples in detail.
![]()
|
|
What is a Dynamic-Link Library (DLL)?
Dynamic-link libraries (DLLs) are a fundamental concept in the Windows operating system. DLLs are files that contain compiled code and data used by multiple programs and processes on a computer. When a process calls a function in a DLL, the operating system loads the DLL into memory and jumps to the function in the DLL. DLLs save users' time and effort by allowing them to use the same code in multiple programs without recompiling all of the code every time any change is made.
DLLs promote modular architecture by allowing software developers to compartmentalize functionalities into different DLL files. This feature also makes adding new functionalities and maintaining existing ones easier. When developers want to use a DLL in your program, they typically include a header file that declares the functions in the DLL and links their program to the DLL at runtime. The #include directive in C and C++, and the import statement in Python and Java are common examples of declaring DLLs in programs.
Adversary Use of DLL Injection
The main feature of DLLs can be a security risk in the wrong hands as they allow programs to use code from other programs. If a DLL contains malicious code, it can execute it when loaded into memory, which can compromise the security of your program.
Adversaries can manipulate DLLs in different ways to execute malicious actions on the target system. The most common method is injecting malicious code into a DLL that is already loaded in memory. This technique is called DLL injection, and it allows adversaries to execute their malicious code in the context of the program that is using the DLL, effectively masquerading the malicious activities as legitimate operations of the host application.
Once the adversary has successfully injected a malicious DLL into a process, they can perform a variety of actions depending on the nature of the injected code. For example, if the application has access to credentials, the malicious DLL may be able to capture and transmit these credentials. Moreover, malicious DLLs can hook into system calls and modify them to bypass security controls. To persist in the compromised system, injected DLLs can be used to ensure the adversary maintains access to the system even after reboots or updates.
A typical DLL injection attack follows these steps:
1. Identifying the target process: DLL injection starts with identifying the process to inject the malicious DLL. Adversaries search for processes on the system using various APIs:
-
CreateToolhelp32Snapshot - provides a snapshot of all running processes, threads, loaded modules, and heaps associated with processes.
-
Process32First - provides a way to access information about the first process encountered in the snapshot of all active processes on the system. Since a snapshot of all processes is a complex set of data, the Process32First is a useful function to retrieve information about each individual process.
-
Process32Next - helps in iterating through the list of processes, one by one, after the initial process has been accessed using Process32First.
These APIs allow adversaries to enumerate the list of processes currently running on the system and gather information about each process, such as its name, ID, and path.
2. Attaching to the process: After identifying the target process, adversaries use the OpenProcess function to obtain the target process's handle. This handle can then be used to perform various operations on the process, such as reading from or writing to its memory or querying for information.
3. Allocating memory within the process: Adversaries then call the VirtualAllocEx function with the target process's handle and allocate memory in the virtual address space of the process. The output of VirtualAllocEx is a pointer to the start of a block of memory allocated in another process's virtual address space. This pointer is a crucial handle for further operations on the allocated memory, enabling processes to interact with and manipulate memory in other processes within the security and operational confines set by the Windows operating system.
4. Copying DLL or the DLL path into process memory: To write into the allocated memory, adversaries use the WriteProcessMemory function and write the path to their malicious DLL. Adversaries also use the LoadLibraryA function in the kernel32.dll library to load a DLL at runtime. LoadLibraryA allows adversaries to write the DLL path or determine offset for writing full DLL. It accepts a filename as a parameter and returns a handle to the loaded module.
5. Executing the injected DLL: Instead of managing threads within the target process, adversaries often create their own threads using the CreateRemoteThread function. Additionally, the NtCreateThreadEx or RtlCreateUserThread API functions can be utilized to execute code in another process' memory. The method usually consists of passing the LoadLibrary address to one of these two APIs, which requires a remote process to execute the DLL on the malware's behalf [1].
Since the LoadLibrary function registers the loaded DLL with the program, security controls can detect malicious activity, presenting a challenge for adversaries. To avoid being detected, some adversaries load the entire DLL into memory and determine the offset to the DLL's entry point. This action may allow adversaries to inject the DLL into a process without registering it and remain hidden on the target system.
DLL injection is commonly employed by adversaries in the wild. In June 2024, the threat group GhostWriter, aka UAC-0057, was reportedly using a DLL injector to deploy PicassoLoader and Cobalt Strike beacon [2]. Adversaries used a DLL library called "ResetEngine.dll" for DLL injection. This malicious library includes typical DLL injection functions such as GetCurrentProcessId, OpenProcess, VirtualAllocEx, WriteProcessMemory, and CreateRemoteThread.
//Code snippet from ResetEngine.dll
WriteProcessMemory(hObject, IpStartAddress, &Buffer, nSize, 0); |
Beside standard DLL injection, adversaries exploit various DLL injection techniques leveraging different methods to load a DLL into a target process.
Reflective DLL Injection
Reflective DLL Injection is an alternative technique that allows adversaries to inject DLLs into processes. Instead of using standard Windows API functions like LoadLibrary() and GetProcAddress(), the DLL loads and executes itself within the target process using techniques like parsing the Export Address Table (EAT) to locate the addresses of key API functions like LoadLibraryA() and GetProcAddress(). With the Reflective DLL Injection technique, adversaries inject DLLs into the process without the need to call these functions directly.
Adversaries were observed to combine shellcode execution and reflective DLL injection. This method is called the Shellcode Reflective DLL Injection (sDRI) technique, and it allows adversaries to execute a DLL within the memory of a target process without having to rely on the standard Windows loading mechanisms. The Russian APT group RomCom was observed to exploit CVE-2024-9860 and CVE-2024-49039 vulnerabilities to perform a sandbox escape for Mozilla Firefox and deploy RomCom Backdoor using sDRI [3].
Hooking Injection
Hooking Injection leverages the Windows hooking mechanism to inject malicious DLLs into processes. Instead of directly loading a DLL, adversaries use functions like SetWindowsHookEx to attach a malicious DLL containing a hook procedure to a target thread or process. When the specified hook event (e.g., a keyboard or mouse event) occurs, the operating system loads the malicious DLL into the target process, allowing the attacker to execute their code.
Hooking injection is a common DLL injection technique among keyloggers. Adversaries utilize the SetWindowsHookEx API to monitor keyboard inputs. Agent Tesla stealer malware has the callback hook procedure given below to record its victim's keyboard input, time, and application title [4].
//Code snippet from Agent Tesla |
AppInit_DLL Injection
AppInit_DLLs Injection exploits a Windows registry feature that allows DLLs to be loaded into every process using User32.dll. Instead of targeting individual processes, adversaries specify a malicious DLL in the AppInit_DLLs registry value. When any application that uses User32.dll starts, the operating system automatically loads the specified DLL, providing attackers with persistent access across multiple processes.
AppInit_DLL technique leverages the AppInit_DLLs registry value, which specifies DLLs that the system should load when initializing a process using User32.dll. Adversaries typically use the command below to exploit this injection technique, forcing the operating system to load a malicious DLL into processes.
reg add "HKLM\Software\Microsoft\Windows NT\CurrentVersion\Windows" /v AppInit_DLLs /t REG_SZ /d "C:\tmp\malicious.dll" /f reg add "HKLM\Software\Microsoft\Windows NT\CurrentVersion\Windows" /v LoadAppInit_DLLs /t REG_DWORD /d 1 /f |
In March 2024, a browser search engine hijacker called SmashJacker was reported to use the App_Init DLL technique to establish persistence in compromised systems [5]. By exploiting this mechanism, SmashJacker ensures that its malicious code is executed whenever targeted applications are launched, effectively hijacking browser functionalities to redirect search results or inject advertisements.
Atom Bombing
Atom Bombing is a stealthy code injection technique that exploits the Windows Atom Table, a system feature used to store and retrieve data globally. It doesn't rely on WriteProcessMemory or CreateRemoteThread, making it harder for security tools to detect.
In Windows, atom tables are data structures that store strings and corresponding identifiers, known as atoms, which can be accessed globally or within a specific scope. These tables are primarily used to facilitate efficient string management and sharing across applications. The Atom Bombing technique manipulates these tables by injecting malicious code into them. Subsequently, the attacker triggers the execution of this code within a target process by invoking specific functions that retrieve and execute the data stored in the atom table. This approach allows the malicious code to run under the context of a legitimate process, effectively evading many security measures that monitor for unauthorized code execution.
Dridex, the notorious banking trojan, was observed leveraging the Atom Bombing technique in its fourth version [6]. Adversaries exploited atom tables along with NtQueueAPCThread to inject a payload and its import table into a read-write (RW) memory space within the target process, enabling stealthy execution while evading detection.
References
[1] "Windows DLL Injection Basics." Available: http://blog.opensecurityresearch.com/2013/01/windows-dll-injection-basics.html
[2] C. Lin, "Menace Unleashed: Excel File Deploys Cobalt Strike at Ukraine," Fortinet Blog, Jun. 03, 2024. Available: https://www.fortinet.com/blog/threat-research/menace-unleashed-excel-file-deploys-cobalt-strike-at-ukraine
[3] D. S. Dumont, "RomCom exploits Firefox and Windows zero days in the wild." https://www.welivesecurity.com/en/eset-research/romcom-exploits-firefox-and-windows-zero-days-in-the-wild/
[4] X. Zhang, "New Agent Tesla Variant Being Spread by Crafted Excel Document,"Fortinet Blog. https://www.fortinet.com/blog/threat-research/agent-tesla-variant-spread-by-crafted-excel-document
[5] "SmashJacker," Red Canary. https://redcanary.com/threat-detection-report/threats/smashjacker/
[6] M. Baz, "Dridex's Cold War: Enter AtomBombing," Security Intelligence, Feb. 28, 2017. Available: https://securityintelligence.com/dridexs-cold-war-enter-atombombing/