hacktricks/binary-exploitation/libc-heap/off-by-one-overflow.md

136 lines
10 KiB
Markdown
Raw Normal View History

# Bir birim taşma
<details>
<summary><strong>AWS hacklemeyi sıfırdan kahramana öğrenin</strong> <a href="https://training.hacktricks.xyz/courses/arte"><strong>htARTE (HackTricks AWS Kırmızı Takım Uzmanı)</strong></a><strong> ile!</strong></summary>
HackTricks'i desteklemenin diğer yolları:
* **Şirketinizi HackTricks'te reklamını görmek istiyorsanız** veya **HackTricks'i PDF olarak indirmek istiyorsanız** [**ABONELİK PLANLARI**]'na(https://github.com/sponsors/carlospolop) göz atın!
* [**Resmi PEASS & HackTricks ürünleri**](https://peass.creator-spring.com) edinin
* [**PEASS Ailesi'ni**](https://opensea.io/collection/the-peass-family) keşfedin, özel [**NFT'lerimiz**](https://opensea.io/collection/the-peass-family) koleksiyonumuz
* **Katılın** 💬 [**Discord grubuna**](https://discord.gg/hRep4RUj7f) veya [**telegram grubuna**](https://t.me/peass) veya bizi **Twitter** 🐦 [**@hacktricks\_live**](https://twitter.com/hacktricks\_live)** takip edin.**
* **Hacking püf noktalarınızı paylaşarak PR göndererek** [**HackTricks**](https://github.com/carlospolop/hacktricks) ve [**HackTricks Cloud**](https://github.com/carlospolop/hacktricks-cloud) github depolarına katkıda bulunun.
</details>
## Temel Bilgiler
Yalnızca 1B taşma erişimi olan bir saldırganın, bir sonraki parçanın `boyut` alanını değiştirmesine olanak tanır. Bu, hangi parçaların gerçekten serbest bırakıldığını değiştirmeyi sağlar, potansiyel olarak başka bir meşru parçayı içeren bir parça oluşturabilir. Sömürü, [çift serbest bırakma](double-free.md) veya parçaların üst üste binmesiyle benzerdir.
İki tür bir birim taşma zafiyeti vardır:
* Keyfi bayt: Bu tür, o baytı herhangi bir değerle üzerine yazmayı sağlar
* Null baytı (off-by-null): Bu tür, o baytı yalnızca 0x00 ile üzerine yazmayı sağlar
* Bu zafiyetin yaygın bir örneği, `strlen` ve `strcpy` davranışının tutarsız olduğu aşağıdaki kodda görülebilir, bu da bir sonraki parçanın başında 0x00 baytını ayarlamayı sağlar.
* Bu, [House of Einherjar](house-of-einherjar.md) ile sömürülebilir.
* Tcache kullanılıyorsa, bu [çift serbest bırakma](double-free.md) durumuna dönüştürülebilir.
<details>
<summary>Off-by-null</summary>
```c
// From https://ctf-wiki.mahaloz.re/pwn/linux/glibc-heap/off_by_one/
int main(void)
{
char buffer[40]="";
void *chunk1;
chunk1 = malloc(24);
puts("Get Input");
gets(buffer);
if(strlen(buffer)==24)
{
strcpy(chunk1,buffer);
}
return 0;
}
```
</details>
Diğer kontroller arasında, artık bir parça serbest bırakıldığında önceki boyut, metadatadaki parçanın yapılandırılan boyutuyla karşılaştırılır, bu saldırı 2.28 sürümden itibaren oldukça karmaşık hale getirir.
### Kod örneği:
* [https://github.com/DhavalKapil/heap-exploitation/blob/d778318b6a14edad18b20421f5a06fa1a6e6920e/assets/files/shrinking\_free\_chunks.c](https://github.com/DhavalKapil/heap-exploitation/blob/d778318b6a14edad18b20421f5a06fa1a6e6920e/assets/files/shrinking\_free\_chunks.c)
* Bu saldırı artık Tcaches kullanıldığından çalışmamaktadır.
* Ayrıca, daha büyük parçalar kullanarak (bu durumda Tcaches devreye girmediği için) kötüye kullanmaya çalışırsanız, hata alırsınız: `malloc(): invalid next size (unsorted)`
### Amaç
* Bir parçanın başka bir parçanın içinde bulunmasını sağlamak, böylece ikinci parçanın üzerinde yazma erişimi, içerilen parçayı üzerine yazmamıza olanak tanır
### Gereksinimler
* Boyut metadatası bilgisini değiştirmek için bir adet yanlışlıkla bir taşma
### Genel off-by-one saldırısı
* Üç parça `A`, `B` ve `C` (örneğin boyutları 0x20) tahsis edilir ve üst parçayla birleşmeyi önlemek için başka bir parça tahsis edilir.
* `C` serbest bırakılır (0x20 Tcache serbest listesine eklendi).
* Parça `A`yı `B` üzerine taşır. `B`nin `size` alanını 0x21'den 0x41'e değiştirmek için yanlışlıkla bir taşma kötüye kullanılır.
* Şimdi `B`, serbest parça `C`'yi içeriyor
* `B` serbest bırakılır ve 0x40 parça tahsis edilir (buraya tekrar yerleştirilecektir)
* Hala serbest olan `C`nin `fd` işaretçisini değiştirebiliriz (Tcache zehirlenmesi)
### Off-by-null saldırısı
* Bellekte üç parça (a, b, c) ardışık olarak ayrılır. Sonra ortadaki parça serbest bırakılır. İlk parça bir yanlışlıkla bir taşma açığı içerir ve saldırgan bunu 0x00 ile kötüye kullanır (önceki bayt 0x10 ise, ortadaki parçanın gerçekten olduğundan 0x10 daha küçük olduğunu gösterir).
* Sonra, ortadaki serbest bırakılan parçaya (b) 2 daha küçük parça tahsis edilir, ancak `b + b->size` asla c parçasını güncellemez çünkü işaret edilen adres olması gereken adresten daha küçüktür.
* Sonra, b1 ve c serbest bırakılır. `c - c->prev_size` hala b'yi (şimdi b1) işaret ettiği için, her ikisi de bir parçada birleştirilir. Ancak, b2 hala b1 ve c arasında içindedir.
* Son olarak, bu bellek alanını geri kazanmak için yeni bir malloc işlemi gerçekleştirilir ve bu aslında b2'yi içerecek şekilde olacaktır, yeni malloc'un sahibine b2'nin içeriğini kontrol etme olanağı tanır.
Bu resim saldırıyı mükemmel bir şekilde açıklar:
<figure><img src="../../.gitbook/assets/image (1247).png" alt=""><figcaption><p><a href="https://heap-exploitation.dhavalkapil.com/attacks/shrinking_free_chunks">https://heap-exploitation.dhavalkapil.com/attacks/shrinking_free_chunks</a></p></figcaption></figure>
## Diğer Örnekler ve Referanslar
* [**https://heap-exploitation.dhavalkapil.com/attacks/shrinking\_free\_chunks**](https://heap-exploitation.dhavalkapil.com/attacks/shrinking\_free\_chunks)
* [**Bon-nie-appetit. HTB Cyber Apocalypse CTF 2022**](https://7rocky.github.io/en/ctf/htb-challenges/pwn/bon-nie-appetit/)
* `strlen`'in bir sonraki parçanın `size` alanını düşünmesinden kaynaklanan bir off-by-one.
* Tcache kullanılıyor, bu nedenle genel off-by-one saldırıları, Tcache zehirlenmesi ile keyfi yazma işlemi elde etmek için çalışır.
* [**Asis CTF 2016 b00ks**](https://ctf-wiki.mahaloz.re/pwn/linux/glibc-heap/off\_by\_one/#1-asis-ctf-2016-b00ks)
* Bir off-by-one'ı kötüye kullanarak bir adres sızdırmak mümkündür çünkü bir dizenin sonundaki 0x00 baytı bir sonraki alan tarafından üzerine yazılır.
* Keyfi yazma, işaretçiyi başka bir yere işaret etmek için off-by-one yazmayı kötüye kullanarak elde edilir. Ardından, bu işaretçinin işaret ettiği yapının işaretçisini takip ederek keyfi yazma elde etmek mümkündür.
* Libc adresi sızdırılır çünkü heap mmap kullanılarak genişletildiğinde, mmap tarafından ayrılan belleğin libc'den sabit bir ofseti vardır.
* Son olarak, keyfi yazma, \_\_free\_hook adresine bir tane araçla yazmak için kötüye kullanılır.
* [**plaidctf 2015 plaiddb**](https://ctf-wiki.mahaloz.re/pwn/linux/glibc-heap/off\_by\_one/#instance-2-plaidctf-2015-plaiddb)
* Kullanıcı giriş satırlarını okuyan `getline` işlevinde NULL off-by-one bir zayıflık vardır. Bu işlev, içeriğin "anahtarını" okumak için kullanılır.
* 5 başlangıç parçası oluşturulur:
* parça1 (0x200)
* parça2 (0x50)
* parça5 (0x68)
* parça3 (0x1f8)
* parça4 (0xf0)
* parça savunması (0x400) üst parçayla birleşmeyi önlemek için
* Ardından parça 1, 5 ve 3 serbest bırakılır, böylece:
* ```python
[ 0x200 Parça 1 (serbest) ] [ 0x50 Parça 2 ] [ 0x68 Parça 5 (serbest) ] [ 0x1f8 Parça 3 (serbest) ] [ 0xf0 Parça 4 ] [ 0x400 Parça savunması ]
```
* Sonra, parça3 (0x1f8) kötüye kullanılarak null off-by-one, prev\_size'ın `0x4e0` olarak yazılması kötüye kullanılır.
* Başlangıçta tahsis edilen parça1, 2, 5 ve 3'ün boyutlarının ve bu parçaların başlıklarının toplamının `0x4e0`'a eşit olduğuna dikkat edin: `hex(0x1f8 + 0x10 + 0x68 + 0x10 + 0x50 + 0x10 + 0x200) = 0x4e0`
* Sonra, parça 4 serbest bırakılır, tüm parçaları başlangıca kadar tüketen bir parça oluşturur:
* ```python
[ 0x4e0 Parça 1-2-5-3 (serbest) ] [ 0xf0 Parça 4 (bozuk) ] [ 0x400 Parça savunması ]
```
* ```python
[ 0x200 Parça 1 (serbest) ] [ 0x50 Parça 2 ] [ 0x68 Parça 5 (serbest) ] [ 0x1f8 Parça 3 (serbest) ] [ 0xf0 Parça 4 ] [ 0x400 Parça savunması ]
```
* Sonra, `0x200` bayt tahsis edilir ve orijinal parça 1 doldurulur
* Ve başka 0x200 bayt tahsis edilir ve parça2 yok edilir ve dolayısıyla hiçbir sızıntı yok ve bu işe yaramaz mı? Belki bunun yapılması gerekmeyebilir
* Sonra, 0x58 "a" ile başka bir parça tahsis edilir (parça2'yi üzerine yazarak parça5'e ulaşır) ve parça5'in hızlı bin parçasının `fd`si `__malloc_hook`'a işaret edecek şekilde değiştirilir
* Sonra, 0x68'lik bir parça tahsis edilir, böylece `__malloc_hook`'taki sahte hızlı bin parçası, takip eden hızlı bin parçasıdır
* Son olarak, 0x68'lik yeni bir hızlı bin parçası tahsis edilir ve `__malloc_hook` bir `one_gadget` adresiyle üzerine yazılır
<details>
<summary><strong>Sıfırdan başlayarak AWS hacklemeyi öğrenin</strong> <a href="https://training.hacktricks.xyz/courses/arte"><strong>htARTE (HackTricks AWS Red Team Expert)</strong></a><strong>!</strong></summary>
HackTricks'ı desteklemenin diğer yolları:
* **Şirketinizi HackTricks'te reklam görmek istiyorsanız** veya **HackTricks'i PDF olarak indirmek istiyorsanız** [**ABONELİK PLANLARI**](https://github.com/sponsors/carlospolop)'na göz atın!
* [**Resmi PEASS & HackTricks ürünlerini**](https://peass.creator-spring.com) edinin
* [**The PEASS Family**](https://opensea.io/collection/the-peass-family) koleksiyonumuzu keşfedin, özel [**NFT'lerimiz**](https://opensea.io/collection/the-peass-family)
* **💬 [Discord grubuna](https://discord.gg/hRep4RUj7f) katılın veya [telegram grubuna](https://t.me/peass) katılın veya** bizi **Twitter** 🐦 [**@hacktricks\_live**](https://twitter.com/hacktricks\_live)**'da takip edin.**
* **Hacking hilelerinizi göndererek PR'ler oluşturarak paylaşın** [**HackTricks**](https://github.com/carlospolop/hacktricks) ve [**HackTricks Cloud**](https://github.com/carlospolop/hacktricks-cloud) github depolarına.