8.8 KiB
House of Orange
htARTE (HackTricks AWS Red Team 전문가)로부터 제로에서 영웅까지 AWS 해킹 배우기
HackTricks를 지원하는 다른 방법:
- 회사가 HackTricks에 광고되길 원하거나 HackTricks를 PDF로 다운로드하려면 구독 요금제를 확인하세요!
- 공식 PEASS & HackTricks 스왜그를 얻으세요
- The PEASS Family를 발견하세요, 우리의 독점 NFTs 컬렉션
- 💬 Discord 그룹 또는 텔레그램 그룹에 가입하거나 트위터 🐦 @hacktricks_live를 팔로우하세요.
- HackTricks 및 HackTricks Cloud 깃허브 저장소에 PR을 제출하여 해킹 트릭을 공유하세요.
기본 정보
코드
- 예제 찾기: https://github.com/shellphish/how2heap/blob/master/glibc_2.23/house_of_orange.c
- 이 패치에서 취약점이 수정되었으므로 더 이상 작동하지 않음 (2.26 이전 버전에서 작동)
- 더 많은 주석이 달린 동일한 예제: https://guyinatuxedo.github.io/43-house_of_orange/house_orange_exp/index.html
목표
malloc_printerr
함수 남용
요구 사항
- 최상위 청크 크기 덮어쓰기
- Libc 및 힙 누출
배경
이 예제의 주석에서 필요한 배경 사항:
과거의 libc 버전에서 malloc_printerr
함수가 호출될 때 _IO_list_all
에 저장된 _IO_FILE
구조체 목록을 반복하고 실제로 그 구조체 내의 명령 포인터를 실행했습니다.
이 공격은 우리가 _IO_list_all
에 쓸 가짜 _IO_FILE
구조체를 조작하고 malloc_printerr
가 실행되도록 만들 것입니다.
그런 다음 우리가 _IO_FILE
구조체의 점프 테이블에 저장된 주소를 실행하고 코드 실행을 얻을 것입니다.
공격
공격은 unsorted bin 내부에 top chunk을 얻는 것으로 시작합니다. 현재의 top chunk 크기보다 크지만 mmp_.mmap_threshold
(기본값은 128K)보다 작은 크기로 malloc
을 호출하여 이루어집니다. Top chunk 크기가 수정될 때, top chunk + 크기가 페이지 정렬되어 있고 prev_inuse 비트가 항상 설정되어 있는지 확인하는 것이 중요합니다.
unsorted bin 내부에 top chunk을 얻으려면 top chunk을 만들기 위해 청크를 할당하고, 새로운 top chunk 크기보다 큰 청크를 할당한 후 top chunk 크기를 변경해야 합니다. 이때 free
가 호출되지 않아야 합니다.
이제 이전의 top chunk는 unsorted bin에 있습니다. 이것을 읽을 수 있다고 가정하면(오버플로우를 일으킨 취약점 때문일 수 있음), libc 주소를 누출하고 _IO_list_all의 주소를 얻을 수 있습니다.
unsorted bin 공격은 오버플로우를 남용하여 topChunk->bk->fwd = _IO_list_all - 0x10
를 쓰는 것으로 수행됩니다. 새로운 청크가 할당되면 이전의 top chunk가 분할되고 unsorted bin에 대한 포인터가 **_IO_list_all
**에 쓰여집니다.
다음 단계는 이전의 top chunk 크기를 작은 bin에 맞도록 줄이는 것입니다. 특히 크기를 0x61로 설정하는 것은 두 가지 목적을 가집니다:
- Small Bin 4에 삽입:
malloc
이 unsorted bin을 스캔하고 이 청크를 볼 때, 크기가 작기 때문에 이를 small bin 4에 삽입하려고 시도할 것입니다. 이로 인해 이 청크는 small bin 4 목록의 헤드에 놓이게 되며, 이는 우리가 unsorted bin 공격을 통해 **_IO_list_all
**의 청크의 FD 포인터 위치에 가까운 주소를 썼기 때문입니다. - Malloc Check 트리거: 이 청크 크기 조작은
malloc
이 내부적인 체크를 수행하도록 만듭니다. 청크 크기가 0인 가짜 포워드 청크의 크기를 확인하면 오류가 발생하고malloc_printerr
가 호출됩니다.
Small bin의 조작을 통해 청크의 포워드 포인터를 제어할 수 있습니다. _IO_list_all과의 중첩은 가짜 _IO_FILE 구조체를 조작하는 데 사용됩니다. 이 구조체는 libc에서 내부 체크를 통과하는 값으로 설정된 _IO_write_base
및 _IO_write_ptr
와 같은 주요 필드를 포함하도록 주의 깊게 제작되었습니다. 또한 가짜 구조체 내에 점프 테이블이 생성되어, 명령 포인터가 임의의 코드(예: system
함수)가 실행될 수 있는 주소로 설정됩니다.
기술의 나머지 부분을 요약하면:
- 이전의 Top Chunk 축소: 이전의 top chunk 크기를 0x61로 조정하여 작은 bin에 맞춥니다.
- 가짜
_IO_FILE
구조체 설정: 이전의 top chunk과 중첩된 가짜 _IO_FILE 구조체를 설정하고 실행 흐름을 탈취합니다.
다음 단계는 현재 unsorted bin에 있는 이전의 top chunk과 중첩되는 가짜 _IO_FILE 구조체를 조작하는 것입니다. 이 구조체의 처음 바이트는 조심스럽게 제작되어야 하며, 실행될 명령(예: "/bin/sh")을 가리키는 포인터를 포함해야 합니다.
가짜 _IO_FILE 구조체의 중요한 필드인 _IO_write_base
및 _IO_write_ptr
와 같은 키 필드는 libc에서 내부 체크를 통과하는 값으로 설정됩니다. 또한 가짜 구조체 내에 점프 테이블이 생성되어, 명령 포인터가 임의의 코드(예: system
함수)가 실행될 수 있는 주소로 설정됩니다.
호출된 malloc
이 가짜 _IO_FILE 구조체를 통해 코드 실행을 트리거하면 공격이 완료됩니다. 이를 통해 임의의 코드 실행이 가능해지며, 일반적으로 쉘이 생성되거나 다른 악의적인 페이로드가 실행됩니다.
공격 요약:
- Top Chunk 설정: 청크를 할당하고 top chunk 크기를 수정합니다.
- Top Chunk을 unsorted bin으로 강제 이동: 더 큰 청크를 할당합니다.
- Libc 주소 누출: unsorted bin에서 읽기 위해 취약점 사용
- Unsorted bin 공격 수행: 오버플로우를 사용하여 _IO_list_all에 쓰기
- 이전의 Top Chunk 축소: 작은 bin에 맞도록 크기 조정
- 가짜 _IO_FILE 구조체 설정: 제어 흐름을 탈취하기 위해 가짜 파일 구조체 조작
- 코드 실행 트리거: 공격을 실행하고 임의의 코드 실행
이 접근 방식은 free
를 직접 호출하지 않고도 코드 실행을 달성하기 위해 힙 관리 메커니즘, libc 정보 누출 및 힙 오버플로우를 악용합니다. 가짜 _IO_FILE 구조체를 주의 깊게 제작하고 올바른 위치에 배치하여 공격이 표준 메모리 할당 작업 중에 제어 흐름을 탈취할 수 있습니다. 이를 통해 임의의 코드 실행이 가능해지며, 일반적으로 쉘 또는 다른 악의적인 활동이 실행됩니다.
참고 자료
- https://ctf-wiki.mahaloz.re/pwn/linux/glibc-heap/house_of_orange/
- https://guyinatuxedo.github.io/43-house_of_orange/house_orange_exp/index.html
htARTE (HackTricks AWS Red Team Expert)를 통해 제로부터 영웅이 되는 AWS 해킹을 배우세요
HackTricks를 지원하는 다른 방법:
- 회사가 HackTricks에 광고되길 원하거나 HackTricks를 PDF로 다운로드하길 원한다면 구독 요금제를 확인하세요!
- 공식 PEASS & HackTricks 스왜그를 구매하세요
- The PEASS Family를 발견하세요, 우리의 독점 NFTs 컬렉션
- 💬 디스코드 그룹이나 텔레그램 그룹에 가입하거나 트위터** 🐦 @hacktricks_live를 팔로우하세요.
- HackTricks 및 HackTricks Cloud 깃허브 저장소에 PR을 제출하여 해킹 트릭을 공유하세요.