Team82 로고 Claroty
블로그로 돌아가기

Pwn2Own: WAN-to-LAN 익스플로잇 쇼케이스, 1부

/

경영진 요약

  • Claroty Team82는 지난 가을 Pwn2Own 2023 토론토 IoT 해킹 대회에 참가하여 TP-Link ER605 라우터와 Synology BC500 IP 카메라를 악용했습니다.

  • 이 연구를 통해 공격자가 광역 네트워크에 연결된 디바이스를 침해하고 로컬 네트워크로 이동하여 연결된 IoT 디바이스를 침해할 수 있는 방법을 보여줍니다.

  • 이 시리즈의 1부에서는 TP-Link ER605 공유기에 대한 연구와 공격에 대해 설명합니다. 2부에서는 라우터에서 로컬 네트워크로 이동하여 Synology BC500 IP 카메라를 손상시킨 방법을 다룹니다. 

  • TP-Link는 펌웨어 버전 ER605 (UN) V22에서 보고된 취약점을 수정했습니다 . 2.4 빌드 20240119

  • Synology는 펌웨어 버전 1.0.7-0298에서 보고된 취약점을 수정하고 보안 권고를 발표했습니다.

Pwn2Own 토론토 2023: IoT 에디션 | 소호 매시업 익스플로잇

소개

소규모 사무실/홈 오피스(SOHO) 네트워크에서 인터넷에 연결하는 거의 모든 사람이 비슷한 네트워크 레이아웃을 사용합니다. 로컬 네트워크와 인터넷 사이를 연결하는 가장 필수적인 장치는 라우터입니다. 라우터는 네트워크 트래픽을 라우팅할 뿐만 아니라 내부 로컬 네트워크(LAN)와 외부 인터넷인 광역 네트워크(WAN)를 구분하여 내부 기기에 대한 원치 않는 외부 액세스를 방지하는 보호 장치 역할을 합니다. 따라서 WAN에서 라우터를 악용하여 NAT(네트워크 주소 변환)를 우회하는 것은 위험하며 로컬 네트워크에 심각한 위험을 초래할 수 있습니다.

2023년 Pwn2Own 토론토 대회에서 저희는 WAN에서 TP-Link 라우터를 악용하는 WAN-to-LAN 피벗 공격을 시연했습니다. 저희는 연구를 통해 공격자가 WAN에서 LAN으로 침투할 수 있는 방법을 조사하여 공격자가 NAT 보호를 우회할 수 있는 TP-Link 라우터의 취약점을 발견했습니다. 라우터에서 원격 코드 실행(RCE)을 확보한 후, LAN으로 전환하여 네트워크 내부로 측면 이동하여 Synology IP 카메라에 대한 익스플로잇을 개발했습니다.

이 블로그에서는 고급 임베디드 익스플로잇 기법, 새로운 NAT 우회 및 IoT 디바이스 취약점을 발견하기 위한 접근 방식과 방법론 등 저희의 연구 결과를 소개합니다.

2부로 구성된 이 시리즈의 1부에서는 라우터를 악용하는 기술을 다루고, 2부에서는 라우터를 사용하여 WAN에서 LAN으로 이동하는 방법을 설명합니다. 

긴 여정이니 안전벨트를 매세요!

WAN 익스플로잇: TP-Link ER605 공유기

TP-Link ER605 공유기는 소비자와 소규모 기업을 위한 VPN 공유기로 추천합니다.

이 장치에는 방화벽 정책 및 서비스 거부(DoS) 방어와 같은 보안 조치가 있는 것으로 설명되어 있습니다. 이 라우터에는 클라우드 기반 관리 인터페이스도 있습니다.

기술 세부 정보

WAN 익스플로잇을 달성하고 싶었기 때문에 WAN 관련 공격 표면을 검색했습니다. 라우터가 지원하는 기능 중 하나는 동적 DNS(DDNS) 서비스입니다. DDNS를 사용하면 동적 IP를 사용하는 디바이스가 IP가 변경될 때 동적으로 변경되는 도메인 이름 레코드를 보유할 수 있습니다. TP-Link가 지원하기로 선택한 DDNS 제공 업체 중 하나는 다음과 같습니다. Comexe를 사용하여 사용자 정의 DDNS 프로토콜을 사용하여 제공업체의 서버와 통신합니다. 서비스 제공업체와 상호 작용하기 위해 장치는 다음 위치에 있는 바이너리를 사용합니다. /usr/sbin/cmxddnsd. 연구하는 동안 cmxddnsd 바이너리에서 세 가지 취약점을 발견했는데, 이 취약점들을 서로 연결하면 WAN 측에서 원격 코드 실행이 가능했습니다.

취약점 #1: 부적절한 서버 인증 유효성 검사(CVE-2024-5242)

먼저 바이너리 cmxddnsd. 부팅 중 및 이후 주기적으로 바이너리는 DDNS 연결을 시작하고 외부 IP 주소를 업데이트하기 위해 DDNS 서버에 액세스하려고 시도합니다. 기본적으로 라우터는 두 개의 Comexe DDNS 서버로 구성됩니다. Dns1.comexe.net, Dns1.comexe.cn.

서버의 IP 주소를 얻으려면, cmxddnsd 는 라우터의 DNS 확인자를 쿼리하여 DDNS 서버의 DNS 이름을 확인하려고 시도합니다. IP 주소를 검색한 후 바이너리는 다음을 통해 DDNS 서버에 대한 UDP 연결을 시작합니다. UDP/9994. DDNS 서버와 통신하는 데 사용되는 프로토콜은 독점적이기 때문에 프로토콜을 더 잘 이해하기 위해 바이너리를 조사해야 했습니다. 

조사 결과, DDNS 통신에 사용되는 프로토콜은 다음과 같으며 각 메시지는 두 개의 세그먼트로 구성된다는 사실을 발견했습니다:

  1. 암호화된 데이터 세그먼트

  2. 'C'라는 메시지 세그먼트(C=1 예를 들어) 메시지 방향(서버에서 클라이언트 또는 클라이언트에서 서버)을 나타냅니다. 서로 다른 메시지 부분을 분리하기 위해 Comexe는 단일 바이트의 \x01 를 사용하여 다른 부분을 분리합니다. 

요청의 암호화된 데이터 세그먼트가 포함된 DDNS 요청 및 응답입니다.

메시지의 데이터 세그먼트를 암호화/복호화하기 위해 Comexe는 3DES 스키마를 사용하여 하드코딩된 8바이트 키를 사용하여 대칭 암호화를 수행합니다:  \x53\x76********* [검열됨]. 암호화 루틴이 끝나면 데이터는 다음을 사용하여 인코딩됩니다. Base64 를 사용자 지정 base64 문자 매핑으로 변환합니다. 복호화 프로세스가 완료되면 해독된 콘텐츠가 DATA 세그먼트에 저장됩니다. 복호화된 콘텐츠는 메시지 유형(인증 요청, 인증 응답 등), ASCII 기반 매개변수(사용자 이름/비밀번호 쌍, IP 주소 등), 요청의 오류 코드 등 메시지의 여러 부분으로 구성됩니다.


조사하여 cmxddnsd 바이너리를 사용하는 경우, Comexe DDNS 프로토콜의 일부로 실제 호스트 유효성 검사가 발생하지 않는다는 사실을 발견했습니다. 이 DDNS 프로토콜에서 클라이언트/서버를 가장하는 데 필요한 것은 암호화 절차와 서로 다른 당사자가 사용하는 하드코딩된 키를 아는 것뿐입니다. 즉, 공급자 서버를 가장하여 클라이언트 디바이스로 요청을 수신하고 전송할 수 있습니다.

스크립트에서 사용되는 암호화/복호화 상수입니다.

클라이언트가 연결 중에 서버의 신원을 확인하기 위해 대부분의 프로토콜은 SSL 또는 비대칭 암호화 알고리즘을 사용하여 양측의 실제 신원을 확인합니다. 그러나 Comexe는 대칭 암호화 알고리즘을 사용하기 때문에 암호화 키(장치 내부에 내장되어 있음)에 대한 지식이 있는 사람이라면 누구나 양쪽을 사칭할 수 있습니다.

취약점 #2: 스택 기반 오버플로로 인한 원격 코드 실행(CVE-2024-5243)

DDNS 공급자를 가장할 수 있는 기능을 확보한 후, 다음에서 구문 분석 흐름과 DDNS 기능을 조사하기 시작했습니다. cmxddnsd. 곧 바이너리 내부에서 DDNS 패킷 처리를 처리하는 함수를 확인했습니다: _chkPkt.

데이터 암호 해독을 처리하는 _chkPkt 함수의 일부입니다.

통신 프로토콜의 일부로 서버는 여러 세그먼트로 구성된 ASCII 기반 페이로드를 전송하며, 각 세그먼트는 특정 메시지 유형 및 매개변수와 관련이 있습니다. 예를 들어 DDNS 서버는 오류 코드 매개변수 또는 발생한 특정 오류를 나타내는 updateSvr 매개 변수를 사용하여 클라이언트가 공급자의 서버 도메인 버전을 업데이트하도록 지시합니다. Dns1.comexe.cnmynewdomain.com.

특정 메시지 부분의 구문 분석 루틴 중에 서버가 수신된 매개변수 버퍼를 바운드 검사나 안전성 검증 없이 복사하는 것을 발견했습니다. 예를 들어 오류 코드 매개 변수를 사용하면 서버는 strncpy 를 사용하여 버퍼를 4바이트의 스택 변수에 복사할 수 있습니다. 그러나 복사에는 대상 버퍼가 아닌 수신된 파라미터의 길이가 사용되므로 더 작을 수 있습니다. 즉, 라우터가 수신된 매개 변수의 길이가 오류 코드 4자보다 큰 크기의 데이터를 입력하면 버퍼 오버런이 발생합니다.

우리가 악용한 오버플로 버그의 원인이 되는 코드는 _chkPkt 함수 내부에 있습니다.

공격자가 페이로드를 완전히 제어하기 때문에, 페이로드 내부에 큰 크기의 콘텐츠를 전송할 수 있습니다. 오류 코드 매개변수의 최대 패킷 크기 0x800으로만 제한됩니다. 이렇게 하면 스택 기반 버퍼 오버플로가 트리거되어 결과적으로 애플리케이션의 코드 실행 흐름에 영향을 미칠 수 있습니다.

오류 코드 구문 분석 흐름에서 오버플로우가 발생하기 전의 스택 상태는 _chkPkt입니다. 유효한 애플리케이션 주소가 현재 스택 포인터 앞과 $ra 레지스터 안에 저장되어 있음을 알 수 있습니다.
오류 코드 구문 분석 흐름에서 _chkPkt의 오버플로 후 스택 상태입니다. 우리가 제어하는 값(0x77fa62f0)으로 반환 주소 레지스터를 오버플로하여 실행 흐름을 추월했음을 알 수 있습니다.

유사한 버퍼 오버플로 취약점이 DDNS 프로토콜 내부의 다른 명령어에도 존재했습니다. 예를 들어 UpdateSvr1 그리고 UpdateSvr2 매개 변수를 사용하면, 사용자 제어 버퍼가 전역 섹션의 작은 버퍼에 0x80 바이트 길이의 일정한 길이로 복사되어 프로그램의 전역 섹션을 사용자 제어 새로운 Comexe DNS 서버 도메인.

공격자는 UpdateSvr1을 악용하여 0x80보다 큰 페이로드를 전송하여 전역 메모리 섹션을 오버플로하고 다른 구조체를 덮어쓸 수 있습니다.

다양한 스택 기반 버퍼 오버플로우를 검증한 후, 우리는 오류 코드 매개변수(cmxddnsd ! 0x2d8a)의 전체 스택을 덮어쓰는 동시에 _checkPkt 프레임으로 이동합니다. 이를 보호하는 스택 카나리아가 없으므로 이제 실행 흐름을 제어하고 제어된 프레임으로 이동할 수 있게 되었습니다. pc (프로그램 카운터)를 클릭합니다.

성공적인 익스플로잇과 원격 코드 실행을 위한 우리의 계획은 ROP 체인(반환 지향 프로그래밍)을 만드는 것이었습니다. 시스템 (명령). 우리가 직면한 문제는 주소 공간 레이아웃 무작위화(ASLR)였습니다. 스택/ 힙/ 라이브러리의 기본 주소를 추측할 수 없었고, 많은 운영 체제에서 메모리 기반 코드 실행 공격에 대한 완화책인 ASLR을 무력화하기 위해 이를 유출할 방법을 찾아야 했습니다.

취약점 #3: OOB 읽기로 인한 ASLR 우회(CVE-2024-5244)

프로그램의 실행 흐름을 제어한 후, 프로그램이 점프할 주소를 제공하고 그 주소에서 실행을 계속할 수 있습니다. 그러나 최신 OS에서는 ASLR이 프로그램 주소 레이아웃을 무작위화하여 라이브러리, 힙, 스택과 같은 다양한 섹션을 실행할 때마다 임의의 위치에 로드함으로써 이와 같은 공격을 완화합니다. 위의 취약점을 성공적으로 악용하여 임의의 코드를 실행하기 위해서는 ROP 체인에 유효한 주소를 확보하기 위해 ASLR을 우회해야 했습니다.

ASLR 보호를 우회하려면 프로그램 메모리에서 무작위 메모리 섹션을 가리키는 유효한 주소를 유출해야 했습니다. 이렇게 유출된 포인터를 통해 라이브러리의 기본 주소를 계산할 수 있었기 때문입니다. 이 목표를 달성하기 위해 유효한 주소에 대한 포인터가 포함된 아웃오브바운드 메모리를 유출하는 방법을 찾았습니다. 

먼저 원격 서버로 데이터를 전송하는 프로그램의 코드 섹션을 조사했습니다. 얼마 지나지 않아 cmxddnsd 바이너리는 두 가지 프로토콜로만 통신합니다: DDNS(컴엑스의 독점적인 UDP/9994) 및 DNS(UDP/53). 이러한 프로토콜에서 메모리 누수를 찾기 위해 이러한 요청을 처리하는 함수와 절차를 살펴보기 시작했습니다.

기능을 검사할 때 sndDnsQuery함수가 스택 기반 버퍼 오버플로우에 취약하다는 사실을 발견했습니다. 이 함수의 오버플로는 프로그램이 메모리의 전역 섹션에서 DNS 이름을 읽고 한 번에 한 문자씩 스택에 복사할 때 발생합니다.

일반적으로 DNS 이름은 다음과 같은 크기로 제한되지만 0x80를 사용하여 전역 섹션 변수를 오버플로했기 때문에 UpdateSvr1 그리고 UpdateSvr2 업데이트를 통해 훨씬 더 큰 DNS 이름을 제공할 수 있었습니다.

함수가 실행되는 동안 오버플로된 전역 변수에서 스택으로 한 번에 한 바이트씩 복사하기 때문에 스택 기반 버퍼 오버플로가 발생할 수 있습니다. 각 바이트 복사가 중단되는 유일한 경우는 함수가 슬래시(/) 문자 또는 널 바이트(\x00)를 만날 때입니다. DNS 이름과 그 크기를 제어하기 때문에 sndDnsQuery 프레임의 스택에 있는 모든 것을 오버플로할 수 있습니다.

_sndDnsQuery() 함수, DNS 서버 이름을 스택 변수에 복사하여 스택 기반 오버플로에 취약함

저희는 이 스택 기반 버퍼 오버플로를 악용하여 특정 스택 변수를 오버플로하고 다시 썼습니다, sendSize. 그런 다음 이 변수는 프로그램이 DNS 쿼리에서 보낼 바이트 수를 지정하는 데 사용됩니다. 이 변수의 아래쪽 2바이트를 수정함으로써 실제 도메인 및 DNS 페이로드보다 훨씬 더 큰 숫자를 덮어쓸 수 있었습니다.

따라서 프로그램이 DNS 쿼리를 보내려고 할 때마다 sendSize 정수가 더 크면 스택에서 데이터를 계속 전송하고, 내부 숫자만큼의 바이트를 전송합니다. sendSize. 이러한 접근 방식은 DNS를 사용하는 스택에서 범위를 벗어난 메모리 읽기 및 포인터 누출로 이어집니다.

sndDnsQuery 함수의 스택 레이아웃. domain_name 변수에서 오버플로를 시작하고 send_size의 하위 2바이트를 오버플로합니다.

유출 크기를 제어하기 위한 특정 오버플로우를 포함한 _sndDnsQuery 함수의 스택 레이아웃에 대한 또 다른 보기

범위를 벗어난 읽기를 사용하여 스택에 있는 많은 포인터가 유출되었습니다. 이러한 포인터는 스택 자체, 힙, 심지어 다음과 같은 다양한 라이브러리를 포함한 다양한 메모리 영역을 가리킵니다. libc. 이 포인터를 사용하여 이러한 메모리 영역의 현재 기본 주소를 계산하여 ASLR 기능을 우회할 수 있었습니다.

전체 WAN 익스플로잇 체인

위에 표시된 취약점 체인을 완전히 익스플로잇하려면 공격자는 먼저 라우터와 Comexe DDNS 서버(이슈 #1의 취약점 사용).

그런 다음 공격자는 악의적인 UpdateSvr1 값을 이 변수의 최대 크기보다 크게 서버에 전송하면 버퍼 오버플로가 발생합니다. sndDnsQuery 절차가 넘쳐서 sendSize 변수를 사용하여 범위를 벗어난 읽기 취약점(이슈 #3)을 트리거합니다.

마지막으로 공격자는 3번 이슈를 통해 유출한 기본 주소를 사용하여 특별히 조작된 악성 DDNS 응답을 전송합니다. 오류 코드 매개 변수를 사용하여 이슈 2에 표시된 것처럼 스택 기반 버퍼 오버플로를 트리거합니다. 이렇게 하면 프로그램이 공격자가 만든 ROP 체인을 실행하여 실행 흐름을 공격자에게 넘기고 공격자의 제어 하에 OS 명령을 트리거하게 됩니다. 즉, 공격자는 이제 공격받은 라우터에 대한 모든 권한을 갖게 되어 루트 사용자의 권한으로 임의의 OS 명령을 실행할 수 있게 됩니다.

WAN 익스플로잇 요약

  1. 라우터의 WAN 뒤에 위치 - MITM

  2. 오버플로된 도메인이 있는 UpdateSvr1, UpdateSvr2를 사용하여 DDNS 도메인 업데이트 시작

  3. 애플리케이션 충돌 및 스택에서 포인터 유출 없이 sndDnsQuery의 스택을 오버플로합니다.

  4. 스택과 라이브러리의 기본 주소 계산하기

  5. 악성 errorCode가 포함된 DDNS 요청을 전송하여 _checkPkt 프레임의 스택을 오버플로합니다.

  6. 스택 오버플로 및 ROP 체인 시작

  7. 페이로드가 있는 통화 시스템

랜 공격으로 전환하기 위한 준비

이제 라우터에 대한 완전한 원격 루트 액세스 권한을 갖게 되었습니다. 지배권을 확보해야 했기 때문에 방화벽 규칙을 완전히 개방했습니다( iptables)을 설정하고 연결이 닫힐 경우 당사에 연결을 시도하는 리버스 셸을 구성했습니다.


다음으로, 랜에서 라우터 뒤에 어떤 장치가 있는지 찾아야 했으므로 둘 다 냄새를 맡고 다음을 수행했습니다. arp -an 를 검색한 결과 우리가 찾고 있던 IoT 장치인 Synology BC500 IP 카메라를 발견했습니다. 일단 감지되면 라우터에서 SOCAT(수신 연결)을 사용하여 카메라의 웹 포트를 노출하는 '프록시'를 생성하고 2단계로 넘어가 LAN으로 피벗하는 작업을 계속했습니다.

최신 소식 받기

Team82 뉴스레터 받기

관련 취약점 공개

Claroty
LinkedIn Twitter YouTube Facebook