Skip to content
KitploitKITPLOIT
도구블로그
제출
도구블로그
제출

해킹, 침투 테스트 및 사이버 보안 도구를 당신의 보안 무기고에!

Kitploit은 해킹, 사이버 보안 및 침투 테스트 도구 디렉토리입니다. 최신 프로젝트 업데이트를 발견하여 취약점을 찾고, 시스템을 분석하고, 테스트를 자동화하고, 보안을 강화하세요.

··피드·문의·개인정보·© 2026 Kitploit

도구 디렉토리

카테고리

모든 카테고리 보기
Loading categories
secure-by-default-rce-demo — Secure-by-default 데모 랩으로, 컨테이너 하드닝(distroless 이미지, non-root, 읽기 전용 파일시스템, 런타임 주입 시크릿)이 치명적인 Next.js/React Server Actions RCE(CVE-2025-55182 “React2Shell”)를 무력화할 수 있음을 보여주며, 안전한 배포와 안전하지 않은 배포 및 익스플로잇 로그를 나란히 비교합니다. | Kitploit
도구/GitHubGitHub/meganekos/secure-by-default-rce-demo
Container SecurityVulnerability AnalysisExploitationWeb SecurityCloud SecurityDevSecOpsMisconfigurationLearning & EducationLabs & Practice

인기

모두 보기 →

커뮤니티에서 가장 많이 사용되는 도구를 찾아보세요.

모든 도구 탐색

도구 컬렉션을 둘러보세요

모든 도구 보기 →
공유
GitHubmeganekos/secure-by-default-rce-demo

secure-by-default-rce-demo

Secure-by-default 데모 랩으로, 컨테이너 하드닝(distroless 이미지, non-root, 읽기 전용 파일시스템, 런타임 주입 시크릿)이 치명적인 Next.js/React Server Actions RCE(CVE-2025-55182 “React2Shell”)를 무력화할 수 있음을 보여주며, 안전한 배포와 안전하지 않은 배포 및 익스플로잇 로그를 나란히 비교합니다.

저장소 보기
7개월 전아직 검토되지 않음

Node.js RCE 완화: DevOps, 최후의 방어선

이 프로젝트는 Next.js 애플리케이션(특히 Server Actions)의 심각한 원격 코드 실행(RCE) 취약점과 코드 취약점이 남아 있더라도 인프라 강화가 어떻게 공격을 효과적으로 무력화하는지 보여줍니다.

표준 "안전하지 않은" 배포와 Distroless 이미지 및 읽기 전용 파일 시스템을 사용한 강화된 "안전한" 배포를 대조합니다.

🛡️ 개념: "심층 방어"

소프트웨어 취약점은 피할 수 없습니다. 코드가 실패할 때, 인프라는 공격자가 발판을 넓히는 것을 막아야 합니다.

취약점

Next.js에서 사용하는 React Server Components(RSC) 구현에 **심각한 RCE(CVE-2025-55182, 일명 React2Shell)**가 존재합니다.

  • CVSS: 10.0 (심각)
  • 근본 원인: "Flight" 프로토콜의 안전하지 않은 역직렬화로 인해 공격자가 Server Action 처리 중 내부 객체를 조작(프로토타입 오염 등)할 수 있습니다.
  • 영향: 인증 없이 임의 코드 실행(spawnSync 등)이 가능합니다.

공격 벡터

  1. 생존 기술(LotL): OS에 이미 존재하는 도구(curl, wget, ls, cat)를 사용하여 비밀을 탈취하거나 악성코드를 다운로드합니다.
    • 메커니즘: 익스플로잇은 Node.js child_process.spawnSync()를 사용합니다. 이는 셸(/bin/sh) 없이 직접 바이너리를 실행합니다.
  2. 자가 공급(BYOL): 표준 도구가 없으면 공격자가 자신의 바이너리(예: 컴파일된 Go 실행 파일)를 업로드하고 실행 권한을 부여한 후(chmod +x) 실행합니다.

🏗️ 아키텍처 비교


📝 애플리케이션 로그 분석

다음 로그는 애플리케이션 관점에서 공격 시도가 어떻게 보이는지 보여줍니다. 이 대비는 보안 조치의 효과를 생생하게 강조합니다.

안전한 앱 로그 (logs/server.safe.log)

로그는 반복적인 실패(ENOENT)를 보여줍니다.

  • 이유? spawnSync가 ls, id, curl을 실행하려고 시도합니다. Distroless 이미지에는 이러한 바이너리가 없습니다. 단순히 셸이 없는 것이 아니라 도구 자체가 없습니다.
root@kitploit:~
[Instrumentation] Logging initialized. Writing to: /app/logs/server.safe.log
 ⨯ Error: NEXT_REDIRECT
    ... digest: '`{"step":"1. Write Initial Chunk to /tmp/hello_test","success":true}`'
 ⨯ Error: NEXT_REDIRECT
    ... digest: '`{"step":"2. Verify Binary was Written","verification":{...},"success":true}`'
 ⨯ Error: NEXT_REDIRECT
    ... digest: '`{"step":"4. Execute Binary","stdout":"","stderr":"","error_obj":{"message":"spawnSync /tmp/hello_test EACCES","code":"EACCES"},"success":true}`'

안전하지 않은 앱 로그 (logs/server.unsafe.log)

로그는 명령 실행 성공과 파일 시스템 조작을 확인합니다.

root@kitploit:~
[Instrumentation] Logging initialized. Writing to: /app/logs/server.unsafe.log
 ⨯ Error: NEXT_REDIRECT
    ... digest: '`{"step":"1. Write Initial Chunk to /tmp/hello_test","success":true}`'
 ⨯ Error: NEXT_REDIRECT
    ... digest: '`{"step":"4. Execute Binary","stdout":"Hello from Go binary!\\n","stderr":"","error_obj":null,"success":true}`'
 ⨯ Error: NEXT_REDIRECT
    ... digest: '`{"command":"id","args":[],"stdout":"uid=0(root) gid=0(root) ...","stderr":"","status":0,"signal":null}`'
 ⨯ Error: NEXT_REDIRECT
    ... digest: '`{"command":"cat","args":["/app/.env"],"stdout":"","stderr":"cat: can\'t open \'/app/.env\': No such file or directory\n","status":1,"signal":null}`'

(참고: 안전하지 않은 로그에서 cat /app/.env가 위에서 실패하는 이유는 파일 이름이 루트에 .env이기 때문입니다. 전체 로그의 ls -la는 디렉터리 구조를 드러냅니다.)


💥 PoC 결과

1. 표준 RCE (생존 기술)

표준 셸 명령 실행 시도.

  • 안전하지 않음: ✅ 성공. 공격자가 id, ls, cat .env를 실행하고 민감한 데이터에 접근할 수 있습니다.
  • 안전함: ❌ 차단됨. spawnSync /bin/sh ENOENT. 명령을 실행할 셸이 없습니다.

2. 고급 공격 (자가 공급)

"도구 부족"을 우회하기 위해 사용자 정의 바이너리 업로드 시도.

  • 안전하지 않음: ✅ 성공.
    1. 공격자가 바이너리를 청크로 나눕니다(페이로드 제한 우회).
    2. /tmp/malware에 씁니다.
    3. chmod +x를 실행합니다.
    4. 바이너리를 실행합니다.
  • 안전함: ❌ 차단됨.
    • 쓰기 실패: EROFS: read-only file system.
    • 공격자는 어디에도 파일을 드롭할 수 없어 BYOL 공격을 효과적으로 무력화합니다.

3. "완전 파일리스" 실행 분석

공격자가 바이너리를 변수에 로드하여 메모리에서 직접 실행할 수 있을까요?

  • 개념: 바이너리 청크를 전역 JavaScript 변수(예: global.payload = "...")에 연결한 후 실행합니다.
  • 현실: 실패.
    • Node.js child_process 함수(spawn, exec)는 파일 경로가 필요합니다. 버퍼나 문자열을 직접 실행할 수 없습니다.
    • Linux에서 이를 우회하려면 memfd_create(RAM에 익명 파일을 생성하는 syscall)가 필요합니다.
    • 장벽: Node.js는 기본적으로 memfd_create를 노출하지 않습니다. 접근하려면 C++ 애드온(예: ffi-napi)이 node_modules에 미리 설치되어 있어야 합니다.
    • Distroless의 영향: 이미지에 컴파일러(gcc, make)가 없으므로 공격자는 이 애드온을 즉석에서 빌드할 수 없습니다.

🔐 입증된 모범 사례

1. Distroless 이미지 사용

"Distroless" 이미지에는 오직 애플리케이션과 그 런타임 종속성만 포함됩니다. 패키지 관리자, 셸, 표준 UNIX 도구가 없습니다.

  • 이유? 공격자가 RCE를 얻더라도 둘러볼 수 없고(ls), 파일을 다운로드할 수 없으며(curl), 권한을 쉽게 상승시킬 수 없습니다.

2. 읽기 전용 파일 시스템

컨테이너 런타임이 루트 파일 시스템을 읽기 전용으로 마운트하도록 구성합니다.

  • 이유? 공격자가 애플리케이션 코드를 다운로드하거나(BYOL) 수정하는 것을 방지합니다(지속성).
  • 방법? docker-compose.yml에서:
    root@kitploit:~
    read_only: true
    tmpfs:
      - /tmp:noexec # 중요: 실행을 명시적으로 차단!
    
    관찰: 이 설정으로 PoC는 공격자가 /tmp에 바이너리를 쓸 수 있지만(쓰기 성공), noexec 플래그로 인해 실행은 EACCES(권한 거부)로 실패함을 보여줍니다. 이는 기능(쓰기 가능한 tmp)과 보안 사이의 균형을 유지합니다.

3. 기본 환경 변수 ("Export" 공간)

컨테이너 이미지에 .env 파일을 절대 포함하지 마십시오. 공격자가 파일을 읽을 수 있으면(예: cat .env) 비밀이 손상됩니다.

  • 안전한 접근 방식: 런타임에 변수를 프로세스 환경에 직접 주입합니다(예: Kubernetes Secrets, AWS Parameter Store, Docker의 environment 키).
  • 이유? 단일 파일을 읽는 것에 비해 공격자가 모든 비밀을 한 번에 덤프하기가 훨씬 어렵습니다.

🚀 실행 방법

  1. 환경 시작: 안전한 앱과 안전하지 않은 앱이 모두 단일 docker-compose.yml 파일에 정의되어 있습니다.

    root@kitploit:~
    docker compose up --build -d
    
  2. 익스플로잇 실행: 특정 포트에 대해 익스플로잇을 실행하여 차이를 확인할 수 있습니다.

    • 안전하지 않은 앱 대상 (포트 3001):

      root@kitploit:~
      # 1. 표준 RCE (LotL) - 성공
      python exploit/poc.py http://localhost:3001
      
      # 2. 고급 공격 (BYOL) - 성공
      python exploit/poc_advanced.py http://localhost:3001
      
    • 안전한 앱 대상 (포트 3000):

      root@kitploit:~
      # 1. 표준 RCE (LotL) - 실패 (ENOENT)
      python exploit/poc.py http://localhost:3000
      
      # 2. 고급 공격 (BYOL) - 실패 (EACCES/EROFS)
      python exploit/poc_advanced.py http://localhost:3000
      
  3. 정리:

    root@kitploit:~
    docker compose down
    
도구 다운로드
기능❌ 안전하지 않은 환경 (포트 3001)✅ 안전한 환경 (포트 3000)
베이스 이미지node:20-alpine (ls, curl, wget 등 포함)gcr.io/distroless/nodejs20-debian12 (셸, 도구 없음)
파일 시스템쓰기 가능 (기본 Docker 기본값)읽기 전용 (read_only: true)
비밀디스크의 .env 파일 (cat .env에 취약)환경 변수 (런타임에 주입)
사용자root (기본값)비-root (Distroless가 강제)