
MSF 및 *기타* 공격을 모의하고 분석하세요.
Windows 셸코드나 Metasploit Framework 또는 Cobalt Strike(또는 다른 악성 또는 난독화된 코드)로부터의 공격을 분석하는 데 도움이 필요하십니까? 간단한 스크립팅으로 작업을 자동화해야 합니까? 페이로드에서 키를 추출하여 MSF 생성 트래픽을 복호화하는 데 도움을 원하십니까?
REW-sploit이 블루 팀을 돕기 위해 여기 있습니다!
빠른 데모:
도구에 대한 소개가 Insomni'hack 2022에서 등록되었습니다:
https://www.youtube.com/watch?v=-sjM0k0hvMU
설치는 매우 쉽습니다. 전용 Python 환경을 만드는 것을 강력히 권장합니다:
# python -m venv <your-env-path>/rew-sploit
# source <your-env-path>/rew-sploit/bin/activate
# git clone https://github.com/REW-sploit/REW-sploit.git
# cd REW-sploit
# pip install -U setuptools
# pip install -r requirements.txt
# ./apply_patch.py -f
# ./rew-sploit
원한다면 Dockerfile을 사용할 수도 있습니다. 이미지를 만들려면:
docker build -t rew-sploit/rew-sploit .
그런 다음 시작합니다 (/tmp/ 폴더 공유):
docker run --rm -it --name rew-sploit -v /tmp:/tmp rew-sploit/rew-sploit
설치 시퀀스에서 apply_patch.py 스크립트를 볼 수 있습니다. 이는 speakeasy-emulator(https://github.com/fireeye/speakeasy/)에 작은 패치를 적용하여 REW-sploit과 호환되게 하는 데 필요합니다. 필요한 경우 ./apply_patch.py -r로 쉽게 패치를 되돌릴 수 있습니다.
선택적으로 Cobalt-Strike Parser도 설치할 수 있습니다:
# cd REW-sploit/extras
# git clone https://github.com/Sentinel-One/CobaltStrikeParser.git
참고: 버전 0.4.2부터 안정 릴리스 대신 Speakeasy-Emulator의 최신 커밋을 사용하도록 전환했습니다. 안정 릴리스를 사용하려면 다음을 사용하십시오:
pip install -r requirements_stable.txt
REW-sploit은 두 개의 훌륭한 프레임워크인 Unicorn과 speakeasy-emulator(그리고 다른 라이브러리들)를 기반으로 합니다. 모든 분들과 OSS 운동에 감사드립니다!
일반적으로 레드 팀은 공격을 "자동화"하는 데 도움이 되는 많은 도구를 가지고 있는 반면, 블루 팀은 도구가 다소 부족하다고 말할 수 있습니다. 그래서 블루 팀 분석을 돕기 위한 무언가를 구축하는 것을 생각했습니다.
REW-sploit은 셸코드/DLL/EXE를 가져와 실행을 에뮬레이션하고, 무슨 일이 일어나고 있는지 이해하는 데 도움이 되는 정보 집합을 제공합니다. 추출된 정보의 예는 다음과 같습니다:
아래에서 현재 기능에 대한 몇 가지 예를 찾을 수 있습니다:
EXE, DLL, VBScript 및 JScript에서 PIC를 생성할 수 있는 Donut 패키지를 확실히 알고 계실 것입니다.
Donut은 탐지를 회피하기 위해 많은 PIC가 그렇듯 모든 API 이름에 대해 계산된 해시를 기반으로 한 API 내보내기 열거를 사용합니다. 이는 CPU 집약적입니다(특히 REW-sploit과 같은 에뮬레이션 환경에서). 그래서 Donut 스텁이 감지될 때 에뮬레이션의 가장 느린 부분 중 일부를 해제하는 일종의 바로가기를 구현했습니다(0.3.3 릴리스부터 변경됨).
또한 에뮬레이션을 올바르게 완료할 수 있으려면 Speakeasy에 DLL을 제공하여 완전한 내보내기를 얻어야 합니다. 다음 DLL을 복사하십시오:
kernel32.dll
mscoree.dll
ole32.dll
oleaut32.dll
wininet.dll
Speakeasy 폴더 winenv/decoys/amd64 및/또는 winenv/decoys/x86에 넣으십시오 (자세한 내용은 Speakeasy README 참조). 필요하지 않으면 DLL을 그대로 두지 마십시오. 그렇지 않으면 에뮬레이션이 느려질 수 있습니다.
Donut 1.0의 경우 다음 DLL도 추가할 수 있습니다:
combase.dll
shell32.dll
ntdll.dll
이 Shikata Ga Nai 구현은 대부분 잘 작동합니다. 경우에 따라 invalid read로 실패하므로 이를 위해 Fixup #4를 구현했습니다.
버전 0.4부터 emulate_antidebug 명령이 추가되었습니다. 이는 분석된 코드에서 사용되는 안티디버그 트릭을 식별하는 데 도움이 되어 실제 디버그 환경에서 실행할 때 패치할 수 있도록 합니다. 다음은 구현된 예입니다:
[#] Call to QueryPerformanceCounter() at 0x414049
[#] IsDebuggerPresent() at 0x4157e7
[#] CheckRemoteDebuggerPresent() at 0x415828
[#] Suspect NtQueryInformationProcess() at 0x4158b3
[#] Suspect NtQuerySystemInformation() at 0x415a22
[#] Direct access to PEB!BeingDebugged at 0x415a6a
[#] Direct access to PEB!NtGlobalFlag at 0x415a9e
[#] Suspect access to HeapBase (may be used to access Flags and ForceFlags) at 0x415b17
[#] GetProcAddress() of CRSS.EXE at 0x415b75
[#] Exclusive CreateFileA() on current process at 0x415bc4
[#] Call to GetLocalTime() at 0x415bfd
[#] Call to GetSystemTime() at 0x415c20
[#] Call to GetTickCount() at 0x415c52
[#] Call to QueryPerformanceCounter() at 0x415ca6
[#] Call to timeGetTime() at 0x415cd7
[#] Call to VirtualProtect() on "Return Address" at 0x4120b9
emulate_payload 명령에는 여러 아티팩트의 콘텐츠를 덤프하는 3가지 옵션이 있습니다:
-T, --thread lpStartAddress에서 CreateThread API 콘텐츠 덤프
-W, --writefile WriteFile API 콘텐츠 덤프
-M, --writemem VirtualAlloc API로 할당된 콘텐츠 덤프
이 옵션을 사용하면 에뮬레이션 중에 메모리 영역 또는 파일의 콘텐츠를 덤프할 수 있습니다. 예를 들어 --writemem 옵션을 사용하면 읽기 또는 실행 시 액세스된 모든 할당된 메모리를 덤프할 수 있습니다(예: 영역으로의 JMP). 악성 코드의 일반적인 동작은 메모리를 할당하고, 복호화한 다음 실행하거나 추가 작업에 사용하는 것입니다. 이 옵션을 사용하면 복호화 후 이 콘텐츠를 얻을 수 있습니다.
분명히 에뮬레이션은 모든 것을 느리게 만듭니다. 게다가 실행과 상호 작용하기 위해 모든 명령을 후킹하면 훨씬 더 느려집니다. 일반적으로 이는 작은 셸코드에서는 잘 작동하지만 복잡한 코드에서는 몇 가지 문제가 있습니다. 그래서 실행 속도를 높이기 위해 후킹을 끄는 옵션을 추가했습니다:
emulate_payload -P <path_to_filename> -U 0
이렇게 하면 에뮬레이션된 코드가 무엇을 하고 있는지에 대한 개요를 얻을 수 있지만(API 추적 포함), 그 외에는 아무것도 수행되지 않습니다 (수정, 키 추출 등 없음). 0 이외의 값을 지정하면 IP(명령 포인터)가 지정된 주소에 도달할 때 후킹이 다시 활성화됩니다(해당 주소에서 수정이 적용됨).
일부 경우 에뮬레이션이 다양한 이유로 중단되었습니다. 어떤 경우에는 난독화가 에뮬레이션 엔진을 혼란스럽게 하는 기술을 사용했습니다. 그래서 몇 가지 특수 수정을 구현했습니다 (emulate_payload 명령의 -F 옵션으로 활성화 가능). 수정은 modules/emulate_fixups.py에 구현되어 있습니다. 현재 다음과 같은 것들이 있습니다:
Unicorn 문제 #1092:
#
# Fixup #1
# Unicorn 문제 #1092 (XOR 명령이 두 번 실행됨)
# https://github.com/unicorn-engine/unicorn/issues/1092
# #820 (자체 수정 코드 실행 후 잘못된 메모리 보기)
# https://github.com/unicorn-engine/unicorn/issues/820
# 문제: 동일한 번역 블록(16바이트?) 내에서 자체 수정 코드
# 예, 압니다... 이것은 거대한 꼼수입니다... :-/
#
FPU 에뮬레이션 문제:
#
# Fixup #2
# EIP 복구에 사용되는 "fpu" 관련 명령어(FPU/FNSTENV)가 때때로
# 잘못된 주소를 반환합니다.
# 이 경우 첫 번째 FPU 명령어를 추적한 다음 FNSTENV가 호출될 때
# 해당 주소를 STACK에 배치해야 합니다.
#
트랩 플래그 회피:
#
# Fixup #3
# 트랩 플래그 회피 기술
# https://unit42.paloaltonetworks.com/single-bit-trap-flag-intel-cpu/
#
# 트랩 플래그가 활성화된 상태에서 RDTSC 호출은 처리되지 않은
# 인터럽트를 발생시킵니다. 예제 코드:
# pushf
# or dword [esp], 0x100
# popf
# rdtsc
#
# 트랩 플래그가 설정된 RDTSC 호출은 가로채어 TF가 지워집니다
#
스택에 값이 너무 적음:
#
# Fixup #4
# 스택이 너무 작음 (저장된 값이 충분하지 않음)
#
# 일부 난독화/회피 기술은 스택의 일부 값에 액세스하려고 시도합니다
# (예: SGN https://github.com/EgeBalci/sgn.git):
#
# cmovne ax, word ptr [esp + 0xfa]
#
# 이 경우 ESP가 스택 상단에 너무 가까워 에뮬레이션이 "invalid_read"로
# 실패합니다. 이는 일부 '가짜' 값을 생성합니다.
#
modules/emulate_rules.py 파일에는 코드의 흥미로운 부분을 가로채기 위해 사용되는 YARA 규칙이 포함되어 있습니다. 계측을 구현하기 위해 이러한 섹션을 최대한 주석 처리하여 자신만의 규칙을 만들 수 있도록 했습니다 (다른 사람에게 도움이 될 것 같으면 풀 리퀘스트로 공유해 주세요). 예를 들어:
#
# 페이로드 이름: [MSF] windows/meterpreter/reverse_tcp_rc4
# 검색 대상 : mov esi,dword ptr [esi]
# xor esi,0x<const>
# 용도 : 이 xor 명령어에는 2단계로 전송될 페이로드 길이를 암호화하는
# 상수가 포함되어 있습니다.
# 아키텍처: x32
#
yara_reverse_tcp_rc4_xor_32 = 'rule reverse_tcp_rc4_xor { \
strings: \
$opcodes_1 = { 8b 36 \
81 f6 ?? ?? ?? ?? } \
condition: \
$opcodes_1 }'
작동하지 않거나 개선할 수 있는 부분을 발견하면 이슈를 열어 주세요. 감사합니다!