DLL injekce
DLL injection ( angl. DLL injection ) - v programování metoda používaná ke spouštění kódu v adresovém prostoru jiného procesu, který jej nutí načíst dynamicky linkovanou knihovnu [1] . DLL injekce jsou často používány externími programy k ovlivnění chování jiného programu způsobem, který jeho autoři nezamýšleli nebo nezamýšleli [1] [2] [3] . Vložený kód může například zachytit systémová volání funkcí [4] [5] nebo číst obsah textových polí hesla, což nelze provést běžným způsobem [6] . Program používaný k vkládání libovolného kódu do libovolných procesů se nazývá DLL injektor..
Microsoft Windows
V systému Microsoft Windows existuje mnoho způsobů, jak přinutit proces načíst kód do knihovny DLL proti vůli autora aplikace:
- Soubory DLL uvedené v systémovém registru podle klíče HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Windows\AppInit_DLLsbudou načteny v každém procesu, který načte knihovnu User32.dll při svém počátečním volání. [7] [8] [9]
- Klíčové knihovny DLL HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\AppCertDLLsbudou načteny v každém procesu, který volá funkce CreateProcess, CreateProcessAsUser, CreateProcessWithLogonW, CreateProcessWithTokenW a WinExec Windows API . Toto je jedna z legitimních metod vkládání DLL v systému Windows 10 za předpokladu, že soubor DLL je podepsán správným certifikátem.
- Funkce pro manipulaci s procesy, jako je CreateRemoteThread, nebo technologie vkládání kódu, jako je AtomBombing [10] , které lze použít k vložení DLL do programu po jeho spuštění. [5] [6] [11] [12] [13] [14]
- Zachycování volání Windows, jako je SetWindowsHookEx. [2] [5] [6] [15] [16] [17]
- Použití funkcí SuspendThread nebo NtSuspendThread k pozastavení všech vláken a pomocí funkcí SetThreadContext nebo NtSetContextThread k úpravě kontextu existujících vláken v aplikaci ke spuštění vloženého kódu, který může načíst knihovnu DLL. [4] [18] [19]
- Využívejte omezení systému Windows a aplikace, které volají LoadLibrary nebo LoadLibraryEx bez zadání cesty k načtení DLL. [20] [21] [22]
- Práce s vrstvami systémové úrovně.
- Nahrazení jedné z aplikací závislých DLL za falešnou, která obsahuje stejné exportované objekty jako originál. [23]
Unixové operační systémy
V operačních systémech podobných Unixu můžete pomocí dynamického linkeru založeného na ld.so (na BSD ) a ld-linux.so (na Linuxu ) načíst libovolné knihovny do nového procesu zadáním cesty ke knihovně pomocí prostředí proměnná LD_PRELOAD, kterou lze přiřadit globálně nebo jednotlivě přiřadit konkrétnímu procesu. [24]
Například v systému Linux tento příkaz spustí proces „prog“ spolu se sdílenou knihovnou „test.so“ namapovanou v době spuštění:
LD_PRELOAD = "./test.so" prog
Takové knihovny se vytvářejí stejným způsobem jako sdílené objekty. Knihovna má přístup k externím symbolům specifikovaným v programu, stejně jako každá jiná knihovna.
V macOS tento příkaz spustí proces "prog" spolu se sdílenou knihovnou "test.dylib" namapovanou v době spuštění: [25]
DYLD_INSERT_LIBRARIES = "./test.dylib" DYLD_FORCE_FLAT_NAMESPACE = 1 program
Na unixových systémech je také možné použít metody založené na debuggerech. [26]
Ukázkový kód
Použití rozhraní LoadLibrary API
Níže uvedená ukázková funkce používá techniku vkládání DLL, která využívá skutečnosti, že kernel32.dll je mapován na stejnou adresu jako téměř všechny procesy. Proto je na stejnou adresu namapována i LoadLibrary (což je funkce z kernel32.dll). LoadLibrary je také vhodná pro rutinu spouštění vlákna vyžadovanou CreateRemoteThread.
#include <windows.h>
HANDLE inject_DLL ( const char * file_name , int PID )
{
HANDLE h_process , h_rThread ;
char fullDLLPath [ _MAX_PATH ];
LPVOID DLLPath_addr , LoadLib_addr ;
DWORD exit_code ;
/* Načte popisovač cílového procesu */
h_process = OpenProcess ( PROCESS_ALL_ACCESS , FALSE , PID );
/* Získejte úplnou cestu k souboru DLL */
GetFullPathName ( název_souboru , _MAX_PATH , úplná cesta k DLL , NULL );
/* Alokace paměti v cílovém procesu */
DLLPath_addr = VirtualAllocEx ( h_process , NULL , _MAX_PATH ,
MEM_COMMIT | MEM_RESERVE , PAGE_READWRITE );
/* Zapište cestu k souboru DLL do nově vytvořeného bloku paměti */
WriteProcessMemory ( h_process , DLLPath_addr , fullDLLPath ,
strlen ( fullDLLPath ), NULL );
/* Získejte adresu LoadLibraryA (stejná pro všechny procesy), abyste ji mohli spustit */
LoadLib_addr = GetProcAddress ( GetModuleHandle ( "Kernel32" ), "LoadLibraryA" );
/* Spusťte vzdálené vlákno v LoadLibraryA a předejte cestu ke knihovně DLL jako argument */
h_rThread = CreateRemoteThread ( h_process , NULL , 0 , ( LPTHREAD_START_ROUTINE ) LoadLib_addr , DLLPath_addr , 0 , NULL );
/* Počkejte na dokončení */
WaitForSingleObject ( h_rThread , INFINITE );
/* Získá výstupní kód (tj. hodnotu handle vráceného voláním LoadLibraryA */
GetExitCodeThread ( h_rThread , & exit_code );
/* Uvolní hostitele vloženého streamu. */
CloseHandle ( h_rThread );
/* Stejně jako paměť přidělená pro cestu k DLL */
VirtualFreeEx ( h_process , DLLPath_addr , 0 , MEM_RELEASE );
/* A také handle-id cílového procesu */
CloseHandle ( h_process );
return ( HANDLE ) exit_code ;
}
Poznámky
- ↑ 1 2 James Shewmaker. Analýza DLL injekce . GSM prezentace . bluenotch. Získáno 31. srpna 2008. Archivováno z originálu dne 3. prosince 2008. (neurčitý)
- ↑ 12 Iczelion . Kurz 24: Windows Hooks . Domovská stránka sestavy Win32 společnosti Iczelion (srpen 2002). Získáno 31. srpna 2008. Archivováno z originálu 1. srpna 2008. (neurčitý)
- ↑ Rocky Pulley. Rozšíření Správce úloh o DLL Injection . kódový projekt . CodeProject (19. května 2005). Získáno 1. září 2008. Archivováno z originálu 6. února 2009. (neurčitý)
- ↑ 1 2 Nasser R. Rowhani. Kurz injekce DLL a zachycení funkcí . kódový projekt . CodeProject (23. října 2003). Získáno 31. srpna 2008. Archivováno z originálu 15. června 2008. (neurčitý)
- ↑ 1 2 3 Ivo Ivanov. API hákování odhaleno . kódový projekt . CodeProject (2. prosince 2002). Získáno 31. srpna 2008. Archivováno z originálu 14. října 2008. (neurčitý)
- ↑ 1 2 3 Robert Kuster. Tři způsoby, jak vložit kód do jiného procesu . kódový projekt . CodeProject (20. srpna 2003). Získáno 31. srpna 2008. Archivováno z originálu dne 20. července 2008. (neurčitý)
- ↑ Práce s hodnotou registru AppInit_DLLs . Microsoft (21. listopadu 2006). Získáno 28. prosince 2021. Archivováno z originálu 1. ledna 2017.
- ↑ Raymond Chen. AppInit_DLLs by měly být přejmenovány na Deadlock_Or_Crash_Randomly_DLLs . Stará nová věc . Microsoft (13. prosince 2007). Získáno 28. prosince 2021. Archivováno z originálu dne 17. prosince 2007.
- ↑ dllmain.c (anglicky) (nepřístupný odkaz - historie ) . Reagovat OS . React OS Foundation.
- ↑ 'AtomBombing' Microsoft Windows Via Code Injection , Dark Reading (27. října 2016). Archivováno 17. května 2021. Staženo 28. prosince 2021.
- ↑ Trent Waddington. InjectDLL (anglicky) (downlink) (31. srpna 2008). Získáno 28. prosince 2021. Archivováno z originálu dne 30. prosince 2019.
- ↑ Dll Injection (anglicky) (downlink) . DreamInCode.net . MediaGroup1 (31. srpna 2008). Archivováno z originálu 2. září 2008.
- ↑ Greg Jenkins. DLL Injection Framework (anglicky) (nedostupný odkaz) . Cirkus Ring3 (1. listopadu 2007). Získáno 28. prosince 2021. Archivováno z originálu dne 28. června 2020.
- ↑ Drew Benton. Kompletnější řešení pro vkládání DLL pomocí CreateRemoteThread . kódový projekt . CodeProject (17. srpna 2007). Získáno 28. prosince 2021. Archivováno z originálu dne 28. prosince 2021.
- ↑ SetWindowsHookEx Function . Platform SDK pro Windows XP SP2 . Microsoft (31. srpna 2008). Získáno 28. prosince 2021. Archivováno z originálu dne 17. srpna 2016.
- ↑ Hodnota registru AppInit_DLLs a Windows 95 . Nápověda a podpora společnosti Microsoft . Microsoft (1. března 2005). Získáno 28. prosince 2021. Archivováno z originálu dne 20. března 2016.
- ↑ Dll Injection pomocí metody SetWindowsHookEx() . Zvrat hry (3. dubna 2008). Získáno 28. prosince 2021. Archivováno z originálu dne 4. dubna 2016.
- ↑ SetThreadContext DLL Injection ( 16. ledna 2007). Získáno 28. prosince 2021. Archivováno z originálu dne 28. prosince 2021.
- ↑ Ben Botto. DLL Injector (anglicky) (nedostupný odkaz) (6. září 2008). Archivováno z originálu 7. února 2009.
- ↑ Nezabezpečené načítání knihovny může umožnit vzdálené spuštění kódu . Microsoft (20. dubna 2016). Získáno 28. prosince 2021. Archivováno z originálu dne 2. července 2017.
- ↑ Bezpečné načítání knihoven , aby se zabránilo útokům před načítáním DLL . Microsoft (10. června 2011). Získáno 28. prosince 2021. Archivováno z originálu dne 23. září 2016.
- ↑ Microsoft Security Advisory: Nezabezpečené načítání knihovny může umožnit vzdálené spuštění kódu . support.microsoft.com . Získáno 28. prosince 2021. Archivováno z originálu dne 28. prosince 2021. (neurčitý)
- ↑ Endpoint Protection – Symantec Enterprise . community.broadcom.com . Získáno 28. prosince 2021. Archivováno z originálu dne 28. prosince 2021. (neurčitý)
- ↑ Torvalds, Linus; Linus Torvalds, David Engel, Eric Youngdale, Peter MacDonald, Hongjiu Lu, Lars Wirzenius, Mitch D'Souza. ld.so/ld-linux.so - dynamický linker/loader (anglicky) (nedostupný odkaz) . Manuálové stránky UNIX (14. března 1998). Archivováno z originálu 6. února 2009.
- ↑ Peter Goldsborough. Trik LD_PRELOAD . Peter Goldsborough . Získáno 28. prosince 2021. Archivováno z originálu dne 9. prosince 2021. (neurčitý)
- ↑ Vložení kódu do spuštěné linuxové aplikace ? . CodeProject (12. února 2009). Získáno 28. prosince 2021. Archivováno z originálu dne 28. prosince 2021. (neurčitý)