프로세스 마이그레이션 및 회피

LinuxBeginner
지금 연습하기

소개

이 실습에서는 공격자가 어떻게 지속적인 액세스를 유지하고 기본적인 탐지를 회피하는지 배웁니다. Metasploit 과 같은 자동화된 프레임워크는 Meterpreter 를 사용하여 페이로드를 explorer.exe나 svchost와 같은 안정적인 Windows 프로세스로 원활하게 마이그레이션하지만, Linux 환경에서는 다른 접근 방식이 필요합니다.

일반적인 원칙은 플랫폼과 무관합니다. 공격자는 불안정하거나 명백히 의심스러운 실행 컨텍스트 대신, 오래 지속되고 평범해 보이는 실행 컨텍스트 내부에 숨는 것을 선호합니다.

Linux 에서 공격자는 안정적인 시스템 프로세스를 식별하고 "프로세스 이름 스푸핑 (Process Name Spoofing)"을 사용하여 악성 페이로드를 위장함으로써 동일한 회피 목표를 달성합니다. 실행 중인 프로세스를 정찰하고, 신뢰할 수 있는 시스템 구성 요소를 식별하며, 합법적인 커널 스레드로 위장하여 탐지를 회피하는 페이로드를 실행하는 방법을 배웁니다.

이는 부분적으로는 안정성에 관한 것이며, 부분적으로는 인간의 인식에 관한 것입니다. 방대한 프로세스 목록을 확인하는 방어자는 시스템의 일반적인 노이즈 속에 섞여 있는 이름을 간과할 가능성이 높습니다.

실행 중인 프로세스 확인 (ps)

이 단계에서는 Linux 시스템에서 실행 중인 프로세스를 나열하고 분석하는 방법을 배웁니다. 공격자는 이 정찰 단계를 사용하여 환경을 파악하고 사칭할 수 있는 합법적인 프로세스를 찾습니다.

다시 말하지만, 열거가 우선입니다. 호스트에서 무엇이 "정상"인지 모르면 믿을 만한 위장 프로세스를 선택할 수 없습니다.

ps (process status) 명령어는 활성 프로세스를 확인하는 표준 도구입니다. 시스템에서 실행 중인 모든 프로세스를 포괄적으로 보려면 aux 플래그를 사용할 수 있습니다.

터미널에서 다음 명령어를 실행하여 실행 중인 프로세스를 확인하세요.

ps aux | head -n 15

a 플래그는 모든 사용자의 프로세스를 보여주고, u는 사용자 중심 형식 (CPU 및 메모리 사용량 포함) 으로 표시하며, x는 터미널에 연결되지 않은 프로세스를 보여줍니다. 출력을 head -n 15로 파이핑하여 처음 15 줄만 표시함으로써 출력을 관리하기 쉽게 만듭니다.

다음과 유사한 출력이 나타날 것입니다.

USER         PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
root           1  0.0  0.1 167008 11468 ?        Ss   10:00   0:01 /sbin/init
root           2  0.0  0.0      0     0 ?        S    10:00   0:00 [kthreadd]
root           3  0.0  0.0      0     0 ?        I<   10:00   0:00 [rcu_gp]
root           4  0.0  0.0      0     0 ?        I<   10:00   0:00 [rcu_par_gp]
root           5  0.0  0.0      0     0 ?        I<   10:00   0:00 [slub_flushwq]
root           6  0.0  0.0      0     0 ?        I<   10:00   0:00 [netns]
root           8  0.0  0.0      0     0 ?        I<   10:00   0:00 [kworker/0:0H-events_highpri]
root          10  0.0  0.0      0     0 ?        I<   10:00   0:00 [mm_percpu_wq]
root          11  0.0  0.0      0     0 ?        S    10:00   0:00 [rcu_tasks_rude_]
root          12  0.0  0.0      0     0 ?        S    10:00   0:00 [rcu_tasks_trace]
root          13  0.0  0.0      0     0 ?        S    10:00   0:00 [ksoftirqd/0]
root          14  0.0  0.0      0     0 ?        I    10:00   0:00 [rcu_sched]
root          15  0.0  0.0      0     0 ?        S    10:00   0:00 [migration/0]
root          16  0.0  0.0      0     0 ?        S    10:00   0:00 [idle_inject/0]

[kthreadd] 또는 [kworker/0:0H-events_highpri]와 같이 대괄호로 묶인 프로세스에 주목하세요. 이들은 커널 스레드입니다. 매우 안정적이고 지속적으로 실행되며 시스템 관리자가 거의 검사하지 않기 때문에 회피를 위한 완벽한 후보입니다.

안정적인 대상 프로세스 식별

이 단계에서는 회피에 이상적인 특정 프로세스를 식별합니다. 안정적인 프로세스는 일반적으로 자동으로 시작되어 오랫동안 실행되는 시스템 데몬이나 데스크톱 서비스입니다.

공격자의 페이로드가 충돌하면 액세스 권한을 잃게 됩니다. 페이로드를 안정적인 프로세스로 위장하면 의심을 피할 수 있습니다. 일부 Linux 환경에서는 kworker 항목을 관찰하기 쉽고, 이름이 기술적으로 보이며 긴 프로세스 목록에 자연스럽게 섞이기 때문에 편리한 명명 모델이 됩니다.

이 환경에서 kworker 스타일의 이름이 표시되는지 확인해 보겠습니다. 다음 명령어를 실행하세요.

ps -ef | grep kworker | head -n 5

-e 플래그는 모든 프로세스를 선택하고, -f는 전체 형식으로 나열합니다. grep을 사용하여 "kworker"가 포함된 줄만 필터링합니다.

환경이 커널 워커 항목을 노출하는 경우 다음과 유사한 출력이 보일 수 있습니다.

root           8       2  0 10:00 ?        00:00:00 [kworker/0:0H-events_highpri]
root          25       2  0 10:00 ?        00:00:00 [kworker/1:0H-events_highpri]
root          31       2  0 10:00 ?        00:00:00 [kworker/2:0H-events_highpri]
root          37       2  0 10:00 ?        00:00:00 [kworker/3:0H-events_highpri]
root          43       2  0 10:00 ?        00:00:00 [kworker/0:1-events]

grep 명령어만 보이고 실제 kworker 항목이 없더라도 이 실습 환경에서는 괜찮습니다. 다음 단계에서는 특정 커널 스레드가 보이는지에 의존하는 것이 아니라 프로세스 이름 스푸핑이 어떻게 작동하는지 배우는 것이 목표이므로 익숙한 [kworker/X:Y] 명명 스타일을 계속 사용할 것입니다.

안정적인 프로세스로 마이그레이션

이 단계에서는 장기 실행 프로세스를 시작하고 프로세스 이름을 스푸핑하여 프로세스 마이그레이션을 시뮬레이션합니다.

~/project에 malicious_payload.sh라는 더미 페이로드가 준비되어 있지만, 여기에는 중요한 Linux 세부 사항이 있습니다. 셸 스크립트를 실행하면 프로세스 목록에는 일반적으로 /bin/bash /home/labex/project/malicious_payload.sh와 같은 인터프리터가 표시됩니다. 이러한 동작으로 인해 이 환경에서는 스푸핑된 이름을 명확하게 관찰하기 어렵습니다.

스푸핑을 쉽게 확인하기 위해 대신 간단한 장기 실행 명령어를 사용하겠습니다. 보안 개념은 동일합니다. 프로세스 목록에 자연스럽게 섞이도록 프로세스에 오해의 소지가 있는 가시적인 이름을 부여하는 것입니다.

다음 명령어를 실행하여 위장된 백그라운드 프로세스를 시작하세요.

bash -c 'exec -a "[kworker/u4:2]" sleep 600' &

bash -c 부분은 새로운 Bash 프로세스를 시작하고 뒤따르는 명령어 문자열을 실행합니다. exec -a "[kworker/u4:2]"는 해당 Bash 프로세스를 sleep 600으로 대체하지만, 운영 체제에 프로세스 이름을 [kworker/u4:2]로 표시하도록 지시합니다. sleep 600 명령어는 프로세스를 검사할 수 있을 만큼 충분히 오래 유지합니다. 마지막의 &는 프로세스를 백그라운드에서 실행합니다.

백그라운드 작업 번호와 프로세스 ID(PID) 를 나타내는 짧은 출력이 표시됩니다. 예:

[1] 1337

이제 위장된 프로세스가 백그라운드에서 조용히 실행 중이며 스푸핑된 이름으로 나타날 것입니다.

지속성 및 액세스 확인

마지막 단계에서는 위장된 프로세스가 스푸핑된 ID 로 표시되는지 확인하고 정리합니다.

이전 단계에서 할당한 스푸핑된 이름을 검색하세요.

ps aux | grep "kworker/u4:2"

다음과 유사한 출력이 나타날 것입니다.

labex       1337  0.0  0.0   7008  1536 pts/0    S    10:15   0:00 [kworker/u4:2]
labex       1345  0.0  0.0   6480  2272 pts/0    S+   10:16   0:00 grep --color=auto kworker/u4:2

이 환경에서 위장된 프로세스는 sleep으로 생성된 데모일 뿐 실제 커널 워커는 아닙니다. 중요한 점은 프로세스 목록에 표시되는 이름이 이제 신뢰할 수 있는 시스템 구성 요소처럼 보인다는 것입니다.

마지막으로 스푸핑된 이름이 포함된 명령줄을 종료하여 데모 프로세스를 정리합니다. 다음 명령어를 실행하세요.

pkill -f "kworker/u4:2"

ps aux | grep "kworker/u4:2"를 한 번 더 실행하여 위장된 프로세스가 성공적으로 종료되었는지 확인할 수 있습니다.

요약

축하합니다! 프로세스 마이그레이션 및 회피 실습을 성공적으로 완료했습니다.

공격자가 실행 중인 프로세스를 분석하여 안정적이고 신뢰할 수 있는 시스템 구성 요소를 식별하는 방법을 배웠습니다. 또한 프로세스 이름 스푸핑 (exec -a) 을 사용하여 악성 페이로드를 합법적인 커널 스레드로 위장함으로써 Meterpreter 와 같은 고급 프레임워크에서 사용하는 회피 기술을 효과적으로 시뮬레이션하는 방법을 배웠습니다. 마지막으로 스푸핑된 프로세스의 은밀함을 확인하고 이를 올바르게 종료하는 방법을 배웠습니다. 이러한 기술은 지속적인 위협이 Linux 환경 내부에 어떻게 숨어 있는지 이해하는 데 필수적입니다.