DLL 인젝션
컴퓨터 프로그래밍에서 DLL 인젝션(DLL injection)은 다른 프로세스의 주소 공간 내에서 DLL을 강제로 로드시킴으로써 코드를 실행시키는 기술이다.[1] DLL 인젝션은 외부 프로그램을 통해 다른 프로그램에 저작자가 의도하거나 예상하지 않은 영향을 미치기 위해 사용된다.[1][2][3] 예를 들면 삽입된 코드는 시스템 함수 호출을 후킹 하거나[4][5] 또는 보통 방식으로는 읽을 수 없는 패스워드 텍스트 박스의 내용을 읽을 수 있다.[6] 임의적인 코드를 삽입하는데 사용되는 프로그램을 DLL injector라고 부른다.
마이크로소프트 윈도우에서의 접근
편집마이크로소프트 윈도우에는 프로세스에게 DLL의 코드를 로드하고 실행시키는 여러 방법이 있다.
- 레지스트리 엔트리
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Windows\AppInit_DLLs
에 목록화 된 DLL들은 User32.dll(이것이 프로세스에 부착되는 순간)을 로드하는 모든 프로세스에서 로드된다.[5][7][8][9] 윈도우 비스타를 시작으로, AppInit_DLL들은 기본 설정으로 비활성화되어 있다.[10] Windows 7 이후로, AppInit_DLL 하부 구조는 code signing을 지원한다. - 레지스트리 키
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\AppCertDLLs
아래 목록화 된 DLL들은 Win32 API 함수들인 CreateProcess, CreateProcessAsUser, CreateProcessWithLogonW, CreateProcessWithTokenW 그리고 WinExec를 호출할 때 로드된다. - CreateRemoteThread 같은 프로세스 조작 함수들은 실행 중인 프로그램에 DLL을 삽입하기 위해서 사용될 수 있다.[5][6][11][12][13][14]
- 타겟 프로세스의 handle을 오픈한다. 이것은 프로세스를 생겨나게 하거나[15][16] 프로세스에 의해 생겨났으며 존재한다고 알려진 것(예를 들면 예상 가능한 타이틀을 가진 윈도우[17])을 키 오프하거나, 실행중인 프로세스들[18]의 목록을 얻고 타겟 실행 파일의 이름을 조사함으로써 이루어된다.[19]
- 타겟 프로세스에서 메모리를 할당하고,[20] 할당받은 메모리에 인젝트될 DLL의 이름을 쓴다.[11][21]
- 이 단계는 만약 적절한 DLL 이름이 이미 타겟 프로세스 안에서 사용 가능하다면 건너뛸 수 있다. 예를 들면, 프로세스가 ‘User32.dll’, ‘GDI32.dll’, ‘Kernel32.dll’ 또는 ‘32.dll’로 끝나는 다른 라이브러리와 링크되어 있다면, 로드하는 것이 가능하다. 이 기술은 과거에는 DLL 인젝션에서 프로세스들을 지키는 방식에 대해 효과적이라고 입증되었다.[22]
- 타겟 프로세스에 새로운 스레드를[23] (스레드의 시작 주소는 LoadLibrary의 주소로, 인수는 타겟에 업로드되는 문자열의 주소로 해서) 생성한다.[11][24]
- 로드될 DLL의 이름을 쓰고 LoadLibrary에서 새로운 스레드를 시작하는 것 대신, 실행 가능한 코드를 타겟에 넣고, 그 코드를 실행시키는 것도 가능하다.[6]
- 운영체제는 이제 삽입된 DLL에서 DllMain을 호출할 것이다.[11][25]
- 경계 없이, 이 접근은 (스레드 시작 시 모든 로드된 모듈에 보내지는) DLL_THREAD_ATTACH 알림 때문에 타겟 프로세스에게 발견될 수 있다.[25]
- SetWindowsHookEx 같은 윈도우 후킹 함수.[2][5][6][26][27][28]
- 모든 스레드들을 중지시키기 위해 SuspendThread 또는 NtSuspendThread 함수를 사용하고 삽입된 코드를 실행할 목적으로, 존재하는 응용 프로그램 내의 스레드의 문맥을 수정하기 위해 SetThreadContext나 NtSetContextThread 함수를 사용하면 DLL이 로드된다.[29]
- 익스플로잇은 윈도우에서 한계치들을 디자인하고 모든 검증된 DLL 경로 명시 없이 LoadLibrary() 함수를 호출하는 응용 프로그램들을 로드된다.[30]
- 응용 프로그램에 명시된 DLL을 원본 같이 똑같은 함수 호출을 내보내게 구현된 로그 교체로 대체하는 것.[31]
유닉스 계열에서의 접근
편집유닉스 계열 운영체제에서 (ld.so (on BSD) 또는 ld-linux.so (on 리눅스)를 기반으로 한 동적 링커와 함께) 임의적인 라이브러리들은 LD_PRELOAD 환경 변수 내에 있는라이브러리의 경로 이름을 줌으로써 새로운 프로세스에 링크될 수 있다. 이것은 한 프로세스 안에서 전역적으로 또는 개별적으로 세팅될 수 있다.[32]
예를 들면, 배시 셸에서, 이 명령어는 실행 시 링크되는 "test.so" 파일에서 공유 라이브러리와 함께 "prog" 명령어를 실행한다.
LD_PRELOAD="./test.so" prog
이러한 라이브러리는 GCC에 의해서 -fpic or -fPIC 옵션을 통해 링크될 새로운 전역변수를 포함하는 소스 파일을 컴파일하고,[33] -shared
옵션으로 링크함으로써 생성될 수 있다.[34] 이 라이브러리는 프로그램에서 선언된 외부 심볼들에 대한 접근을 갖는다.
각주
편집- ↑ 가 나 James Shewmaker (2006). “Analyzing DLL Injection” (PDF). 《GSM Presentation》. Bluenotch. 2008년 12월 3일에 원본 문서 (PDF)에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ 가 나 Iczelion (August 2002). “Tutorial 24: Windows Hooks”. 《Iczelion's Win32 Assembly Homepage》. 2008년 8월 1일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ Rocky Pulley (2005년 5월 19일). “Extending Task Manager with DLL Injection”. 《CodeProject》. CodeProject. 2009년 2월 6일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ Nasser R. Rowhani (2003년 10월 23일). “DLL Injection and function interception tutorial”. 《CodeProject》. CodeProject. 2008년 6월 15일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ 가 나 다 라 Ivo Ivanov (2002년 12월 2일). “API hooking revealed”. 《CodeProject》. CodeProject. 2008년 10월 14일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ 가 나 다 라 Robert Kuster (2003년 8월 20일). “Three Ways to Inject Your Code into Another Process”. 《CodeProject》. CodeProject. 2008년 7월 20일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ “Working with the AppInit_DLLs registry value”. 《Microsoft Help and Support》. 마이크로소프트. 2006년 11월 21일. 2016년 2월 11일에 확인함.
- ↑ Raymond Chen (2007년 12월 13일). “AppInit_DLLs should be renamed Deadlock_Or_Crash_Randomly_DLLs”. 《The Old New Thing》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “dllmain.c”. 《ReactOS》. ReactOS Foundation. 2008년 7월 8일. 2016년 2월 11일에 확인함.[깨진 링크(과거 내용 찾기)]
- ↑ AppInit_DLLs in Windows 7 and Windows Server 2008 R2
- ↑ 가 나 다 라 Trent Waddington. “InjectDLL”. 2019년 12월 30일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ “Dll Injection”. 《DreamInCode.net》. MediaGroup1. 2006년 5월 4일. 2008년 9월 2일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ Greg Jenkins (November 2007). “DLL Injection Framework”. 《Ring3 Circus》. WordPress. 2020년 6월 28일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ Drew Benton (2007년 8월 17일). “A More Complete DLL Injection Solution Using CreateRemoteThread”. 《CodeProject》. CodeProject. 2016년 2월 11일에 확인함.
- ↑ “CreateProcess”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “PROCESS_INFORMATION”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 20일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ “GetWindowThreadProcessId Function”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “EnumProcesses”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “GetModuleBaseName”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “VirtualAllocEx”. 《Platform SDK for Windows XP SP2》. Microsoft. 2016년 2월 11일에 확인함.
- ↑ “WriteProcessMemory”. 《Platform SDK for Windows XP SP2》. Microsoft. 2016년 2월 11일에 확인함.
- ↑ “Outpost Bypassing Self-Protection via Advanced DLL injection with handle stealing Vulnerability”. 《Matousec》. 2006년 12월 1일. 2016년 2월 11일에 확인함.
- ↑ “CreateRemoteThread”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “LoadLibrary”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ 가 나 “DllMain”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “SetWindowsHookEx Function”. 《Platform SDK for Windows XP SP2》. 마이크로소프트. 2016년 2월 11일에 확인함.
- ↑ “AppInit_DLLs Registry Value and Windows 95”. 《Microsoft Help and Support》. 마이크로소프트. 2005년 3월 1일. 2016년 2월 11일에 확인함.
- ↑ “Dll Injection using SetWindowsHookEx() Method”. 《Game Reversal》. 2008년 4월 3일. 2016년 2월 11일에 확인함.
- ↑ Ben Botto (2008년 9월 6일). “DLL Injector”. 2009년 2월 7일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ “Secure loading of libraries to prevent DLL preloading attacks”. 마이크로소프트. 2011년 6월 10일. 2016년 2월 11일에 확인함.
- ↑ Nicolas Falliere (2010년 9월 26일). “Stuxnet Infection of Step 7 Projects”. Symantec.
- ↑ Linus Torvalds; David Engel; Eric Youngdale; Peter MacDonald; Hongjiu Lu; Lars Wirzenius; Mitch D'Souza (1998년 3월 14일). “ld.so/ld-linux.so – dynamic linker/loader”. 《UNIX man pages》. 2009년 2월 6일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.
- ↑ “Code Gen Options”. 《Using the GNU Compiler Collection (GCC)》. Free Software Foundation. 2016년 2월 11일에 확인함.
-fpic
Generate position-independent code (PIC) suitable for use in a shared library, if supported for the target machine. sqq. - ↑ “Link Options”. 《Using the GNU Compiler Collection (GCC)》. Free Software Foundation. 2016년 2월 11일에 확인함.
-shared
Produce a shared object which can then be linked with other objects to form an executable. sqq. - ↑ Gregory Shpitalnik (2009년 2월 12일). “Code Injection into Running Linux Application”. 《Code Project》. 2010년 6월 12일에 원본 문서에서 보존된 문서. 2016년 2월 11일에 확인함.