48 lines
6.1 KiB
Markdown

# Tcache Bin Attack
{{#include ../../banners/hacktricks-training.md}}
## Basic Information
Tcache bin에 대한 자세한 정보는 이 페이지를 확인하세요:
{{#ref}}
bins-and-memory-allocations.md
{{#endref}}
우선, Tcache는 Glibc 버전 2.26에서 도입되었다는 점에 유의하세요.
**Tcache attack**(또는 **Tcache poisoning**)은 [**guyinatuxido 페이지**](https://guyinatuxedo.github.io/29-tcache/tcache_explanation/index.html)에서 제안된 것으로, 목표는 해제된 청크 내의 빈에서 다음 청크에 대한 포인터를 임의의 주소로 덮어쓰는 것으로, 이후 특정 주소를 **할당하고 포인터를 덮어쓸 수 있게** 하는 것과 매우 유사합니다.
하지만 현재로서는 언급된 코드를 실행하면 다음과 같은 오류가 발생합니다: **`malloc(): unaligned tcache chunk detected`**. 따라서 새로운 포인터에 주소를 쓸 때 정렬된 주소를 사용해야 합니다(또는 이진 파일을 충분히 실행하여 작성된 주소가 실제로 정렬되도록 해야 합니다).
### Tcache indexes attack
일반적으로 힙의 시작 부분에서 **tcache 내 인덱스당 청크 수**와 각 tcache 인덱스의 **헤드 청크 주소**를 포함하는 청크를 찾을 수 있습니다. 어떤 이유로 이 정보를 수정할 수 있다면, **어떤 인덱스의 헤드 청크를 원하는 주소**(예: `__malloc_hook`)를 가리키게 할 수 있으며, 이후 인덱스 크기의 청크를 할당하고 이 경우 `__malloc_hook`의 내용을 덮어쓸 수 있습니다.
## Examples
- CTF [https://guyinatuxedo.github.io/29-tcache/dcquals19_babyheap/index.html](https://guyinatuxedo.github.io/29-tcache/dcquals19_babyheap/index.html)
- **Libc info leak**: tcaches를 채우고, 정렬되지 않은 리스트에 청크를 추가한 후, tcache를 비우고 **정렬되지 않은 빈에서 청크를 다시 할당**하여 첫 8B만 덮어쓰고, **청크의 두 번째 주소를 libc에서 그대로 두어 읽을 수 있게** 합니다.
- **Tcache attack**: 이 이진 파일은 1B 힙 오버플로우에 취약합니다. 이를 악용하여 할당된 청크의 **크기 헤더**를 변경하여 더 크게 만듭니다. 그런 다음 이 청크를 **해제**하고, 가짜 크기의 청크 tcache에 추가합니다. 이후 가짜 크기로 청크를 할당하면 이전 청크가 **반환되며 이 청크는 실제로 더 작았던 것을 알고 있습니다**. 이는 **메모리의 다음 청크를 덮어쓸 기회를 제공합니다**.\
이를 악용하여 **다음 청크의 FD 포인터를** **`malloc_hook`**를 가리키도록 덮어씁니다. 그러면 두 개의 포인터를 할당할 수 있습니다: 첫 번째는 우리가 방금 수정한 정당한 포인터이고, 두 번째 할당은 **`malloc_hook`**에 있는 청크를 반환하여 **one gadget**를 작성할 수 있습니다.
- CTF [https://guyinatuxedo.github.io/29-tcache/plaid19_cpp/index.html](https://guyinatuxedo.github.io/29-tcache/plaid19_cpp/index.html)
- **Libc info leak**: 사용 후 해제와 이중 해제가 있습니다. 이 글에서 저자는 작은 빈에 배치된 청크의 주소를 읽어 libc의 주소를 유출했습니다(정렬되지 않은 빈에서 유출하는 것과 비슷하지만 작은 빈에서).
- **Tcache attack**: Tcache는 **이중 해제**를 통해 수행됩니다. 동일한 청크가 두 번 해제되므로 Tcache 내에서 청크가 자기 자신을 가리키게 됩니다. 그런 다음 할당되고, FD 포인터가 **free hook**을 가리키도록 수정된 후 다시 할당되어 리스트의 다음 청크가 free hook에 있게 됩니다. 그런 다음 이것도 할당되어 `system`의 주소를 여기에 쓸 수 있으므로 `"/bin/sh"`를 포함하는 malloc이 해제될 때 셸을 얻습니다.
- CTF [https://guyinatuxedo.github.io/44-more_tcache/csaw19_popping_caps0/index.html](https://guyinatuxedo.github.io/44-more_tcache/csaw19_popping_caps0/index.html)
- 여기서 주요 취약점은 오프셋을 지정하여 힙의 **어떤 주소든 `free`**할 수 있는 능력입니다.
- **Tcache indexes attack**: tcache 청크(청크 정보가 포함된 청크) 내에 저장될 때 **값이 0x100인 주소**를 생성하는 크기의 청크를 할당하고 해제할 수 있습니다. 이는 tcache가 각 빈의 청크 수를 서로 다른 바이트에 저장하기 때문이며, 따라서 특정 인덱스의 청크가 0x100 값을 생성합니다.
- 그런 다음 이 값은 0x100 크기의 청크가 있는 것처럼 보입니다. 이를 통해 이 주소를 `free`하여 **tcache의 0x100 크기 청크 인덱스에 해당 주소를 추가**할 수 있습니다.
- 그런 다음 **0x100 크기의** 청크를 **할당하면**, 이전 주소가 청크로 반환되어 다른 tcache 인덱스를 덮어쓸 수 있습니다.\
예를 들어, 그 중 하나에 malloc hook의 주소를 넣고 해당 인덱스 크기의 청크를 할당하면 calloc hook에 청크가 할당되어 **one gadget**를 작성하여 셸을 얻을 수 있습니다.
- CTF [https://guyinatuxedo.github.io/44-more_tcache/csaw19_popping_caps1/index.html](https://guyinatuxedo.github.io/44-more_tcache/csaw19_popping_caps1/index.html)
- 이전과 동일한 취약점에 추가 제한이 있습니다.
- **Tcache indexes attack**: 이전과 유사한 공격이지만 **tcache 정보를 포함하는 청크를 해제**하여 그 주소가 해당 크기의 tcache 인덱스에 추가되도록 하여 해당 크기를 할당하고 tcache 청크 정보를 청크로 가져올 수 있습니다. 이를 통해 free hook을 인덱스의 주소로 추가하고 할당하여 그 위에 **one gadget**를 쓸 수 있습니다.
- [**Math Door. HTB Cyber Apocalypse CTF 2023**](https://7rocky.github.io/en/ctf/other/htb-cyber-apocalypse/math-door/)
- `fd` 포인터에 숫자를 추가하기 위한 **Write After Free**.
- 이 도전 과제에서는 많은 **heap feng-shui**가 필요합니다. 이 글에서는 **Tcache**의 헤드를 제어하는 것이 매우 유용하다는 것을 보여줍니다.
- `stdout`를 통한 **Glibc leak** (FSOP).
- 임의의 쓰기 원시를 얻기 위한 **Tcache poisoning**.
{{#include ../../banners/hacktricks-training.md}}