예전에부터 해왔던건데 ㅠㅠ Native 함수 후킹 시 함수호출 규약 Calling Convention 을 무시한결과.. 엄청난 삽질을 동반한 시간적 낭비가 있어서 이제 올려보네요.. 아 ㅠㅠ API 후킹 시 함수호출 규약 잘 지킵시다..헝헝..
한가지 궁금한 점은.. NtOpenFile일 경우 커널이나 유저나 함수호출 규약은 __stdcall로 같은데
왜 후킹할 때 user에선 __stdcall을 붙혀줘야되고 kernel에선 안붙혀줘도 되는건지..;
다시 본론으로 돌아와서 Remote Library Injection은 나름 괜찮은 기술입니다.
디스크에 읽고 쓰여짐을 탐지하는 모니터링 툴들을 우회할 수 있기 때문이죠.
간략한 그림을 보시겠습니다.
보통 몇몇 악성코드가 작동하는 방식입니다. 먼저 Dropper는 백신에 걸리지 않기 때문에 안전하게 메모리에 올라올 수 있고 그 다음에 악성 dll을 소켓 통신을 통해 받던 Dropper내부적으로 인코딩되어 있던 것을 디코딩하던 한 다음 Disk상에 드랍 시킵니다. 그 다음에 LoadLibrary를 통해 악성 dll을 로드시키는 것이지요.
하지만 이 방법은 백신에 걸리기 쉽습니다. 만약 백신이 Disk에 생성되는 모든 파일들에 대해서 모니터링을 하고 있다면?
아마 Virus.dll이 잡힐 확율은 상당히 높을 것입니다. 그러면 다른 방법으로 Virus.dll을 로드 시킬 방법을 생각해봐야겠군요.
아래 그림을 봐보아요~
상당히 그림을 발로 그렸지만.. 보면 Dropper.exe 내부적으로 소켓통신으로 받았던 원래 가지고 있던 아무튼 해당 Virus.dll을 Disk에 드랍하지 않고 자체적으로 메모리상에서 바로 로드해 버리는 것입니다.
이렇게 구현될 경우 당연히 Disk에 생성되는 모든 파일에 대해서 감시하고 있는 백신은 당연히 농락시킬 수 있는 것입니다.
제가 ezbeat.dll로 로드가 되면 단순히 메시지 박스만 띄우는 dll을 하나 만들어 보았습니다. 이제 이 dll을 로드해보겠습니다.
간단히 LoadLibrary를 사용해 "c:\ezbeat.dll" 을 로드하는 방법입니다. 누구나 dll을 로드할 때 이러한 방법을 많이 사용하죠.
당연히 "c:\ezbeat.dll" 는 Disk상 해당 경로에 존재합니다.
로드가 된 후 올디로 상태를 확인해보았습니다.
파란색으로 네모친 부분을 보면 잘 로드가 되었고 Entry 또한 잘 나와 있군요.
이번엔 Remote Library Injection을 사용해서 로드하는 방법입니다.
EmulateFileToMemory() 함수와 InitHook() 가 추가가 되었군요.
그리고 LoadLibrary 할 때 넘어가는 인자가 "K:\ezbeat.dll" 입니다. 하지만 제 컴퓨터에는 K 드라이버는 없습니다.
즉.. "K:\ezbeat.dll" 은 하드에 존재하지 않는 그냥 가짜 이름입니다. 해당 파일의 내용은 LoadLibrary 호출자 프로세스가 가지고 있습니다. 그러면 실패할까요? 실행해보죠.
잘 되는군요. 이것도 올디로 봐보겠습니다.
로드도 잘 되었고 dll 내부적으로 있는 메시지박스도 잘 실행되었지만.. Entry가 없습니다...
바로 이게 Remote Library Injection 입니다.
방법은?
끝입니다.
아래는 영상..
일부러 백신에 잡히게 dll을 만들어보고 해당 dll을 가지고 테스트 해봐야겠네요.
아무튼 다른 실시간 모니터링 부분은 몰라도 디스크 모니터링 하는 부분은 우회가 가능한 방법입니다.
한가지 궁금한 점은.. NtOpenFile일 경우 커널이나 유저나 함수호출 규약은 __stdcall로 같은데
왜 후킹할 때 user에선 __stdcall을 붙혀줘야되고 kernel에선 안붙혀줘도 되는건지..;
다시 본론으로 돌아와서 Remote Library Injection은 나름 괜찮은 기술입니다.
디스크에 읽고 쓰여짐을 탐지하는 모니터링 툴들을 우회할 수 있기 때문이죠.
간략한 그림을 보시겠습니다.
보통 몇몇 악성코드가 작동하는 방식입니다. 먼저 Dropper는 백신에 걸리지 않기 때문에 안전하게 메모리에 올라올 수 있고 그 다음에 악성 dll을 소켓 통신을 통해 받던 Dropper내부적으로 인코딩되어 있던 것을 디코딩하던 한 다음 Disk상에 드랍 시킵니다. 그 다음에 LoadLibrary를 통해 악성 dll을 로드시키는 것이지요.
하지만 이 방법은 백신에 걸리기 쉽습니다. 만약 백신이 Disk에 생성되는 모든 파일들에 대해서 모니터링을 하고 있다면?
아마 Virus.dll이 잡힐 확율은 상당히 높을 것입니다. 그러면 다른 방법으로 Virus.dll을 로드 시킬 방법을 생각해봐야겠군요.
아래 그림을 봐보아요~
상당히 그림을 발로 그렸지만.. 보면 Dropper.exe 내부적으로 소켓통신으로 받았던 원래 가지고 있던 아무튼 해당 Virus.dll을 Disk에 드랍하지 않고 자체적으로 메모리상에서 바로 로드해 버리는 것입니다.
이렇게 구현될 경우 당연히 Disk에 생성되는 모든 파일에 대해서 감시하고 있는 백신은 당연히 농락시킬 수 있는 것입니다.
제가 ezbeat.dll로 로드가 되면 단순히 메시지 박스만 띄우는 dll을 하나 만들어 보았습니다. 이제 이 dll을 로드해보겠습니다.
간단히 LoadLibrary를 사용해 "c:\ezbeat.dll" 을 로드하는 방법입니다. 누구나 dll을 로드할 때 이러한 방법을 많이 사용하죠.
당연히 "c:\ezbeat.dll" 는 Disk상 해당 경로에 존재합니다.
로드가 된 후 올디로 상태를 확인해보았습니다.
파란색으로 네모친 부분을 보면 잘 로드가 되었고 Entry 또한 잘 나와 있군요.
이번엔 Remote Library Injection을 사용해서 로드하는 방법입니다.
EmulateFileToMemory() 함수와 InitHook() 가 추가가 되었군요.
그리고 LoadLibrary 할 때 넘어가는 인자가 "K:\ezbeat.dll" 입니다. 하지만 제 컴퓨터에는 K 드라이버는 없습니다.
즉.. "K:\ezbeat.dll" 은 하드에 존재하지 않는 그냥 가짜 이름입니다. 해당 파일의 내용은 LoadLibrary 호출자 프로세스가 가지고 있습니다. 그러면 실패할까요? 실행해보죠.
잘 되는군요. 이것도 올디로 봐보겠습니다.
로드도 잘 되었고 dll 내부적으로 있는 메시지박스도 잘 실행되었지만.. Entry가 없습니다...
바로 이게 Remote Library Injection 입니다.
방법은?
1. 로드시키려는 dll 파일 내용을 메모리 상에 지니게 있도록 한다. ( 소켓으로 받던.. 애당초 인코딩해서 가지고 있던.. )
2. dll 내용을 메모리 상에 올라왔을 때와 똑같이 에뮬레이팅 해준다.
3. LoadLibrary 내부적으로 호출되는
NtQueryAttributesFile, NtOpenFile, NtCreateSection, NtMapViewOfSection 을 후킹
4. LoadLibrary가 호출되 각 후킹된 Nt 함수들 내부적으로 들어오면
파라미터와 리턴 값을 적절히 조작해 성공하게 만든다.
끝입니다.
아래는 영상..
일부러 백신에 잡히게 dll을 만들어보고 해당 dll을 가지고 테스트 해봐야겠네요.
아무튼 다른 실시간 모니터링 부분은 몰라도 디스크 모니터링 하는 부분은 우회가 가능한 방법입니다.
'My Study > Programming&Theory' 카테고리의 다른 글
My BSOD (2) | 2012.01.08 |
---|---|
SwapContext를 이용한 프로세스 찾기 (7) | 2012.01.04 |
OpenProcess를 막는 방법은?? (11) | 2011.12.20 |
Immunity Debugger Hard Hooking (2) | 2011.12.08 |
ScreenSaver 만들어보기 (3) | 2011.11.30 |