Skip to content

jemalloc Run header corruption

Bir run'ın region bitmap'ini (regs_mask/regs_minelm) corrupt et ki allocator canlı bir slot'u "force-use" etsin; bu da overlapping allocation'lar verir.

Mechanism

Kırılan invariant

Bir run, tek bir size class'ın region'larına hizmet eden bir page kümesidir. arena_run_t header'ı (run base'inde) bir bin pointer, bir free-region count ve bir region bitmap tutar — regs_mask[] artı regs_minelm, yani hâlâ free bit'i olan ilk bitmap element'inin index'i. Bitmap, hangi region slot'larının free vs in use olduğuna dair allocator'ın source of truth'udur. Onu corrupt etmek allocator'a aslında hâlâ canlı olan bir slot dağıttırır — double-free'nin jemalloc analogu, ama hiçbir unlink olmadan ve hiçbir şey free edilmeden.

Sonuç bir overlapping / "force-used" allocation'dır: aynı memory'ye iki canlı pointer; attacker bunu type ya da size'ı desync etmek ve uygulamanın kendi accessor'ları üzerinden kontrollü read/write'lara çevirmek için kullanır.

Walkthrough

Üst düzey, public Phrack #68 ve Black Hat USA 2012 write-up'larından:

  1. Run #1'in son region'ını komşu run #2'nin header'ının içine overflow et (en son allocate edilmiş region tam olarak sonraki run'ın header'ına ulaşabilen durumdur).
  2. Bitmap bookkeeping'ini corrupt et ki used bir slot free olarak okunsun. Phrack #68 temsili trick'i tarif eder: regs_minelm = -2 vermek regs_mask[regs_minelm]'in geri regs_minelm'in kendisine index'lemesini sağlar, böylece region-selection matematiği zaten allocate edilmiş alana geriye doğru offset'li bir pointer döndürür.
  3. Run #2'nin size class'ının sonraki malloc()'u run #1'deki hâlâ canlı bir region'a alias yapan bir pointer döndürür.

Warning

bin pointer zayıf bir target'tır (yalnızca bin->reg0_offset okunur, yalnızca free()'de, ve bir bin'i fake'lemek ekstra kontrol gerektirir), bu yüzden regs_minelm/bitmap path'i tercih edilir. Tam offset'ler kasıtlı olarak çıkarılmıştır.

Detection

  • regs_minelm ve free-region count'larını döndürülen bir pointer'ı hesaplamak için kullanmadan önce run'ın legal bound'larına karşı doğrula (negatif / oversized index'leri reddet).
  • Run header'ından önceki region'ı ve header'ın kendisini red-zone'la; free edilen region'ları junk-fill et ki overlap reuse corrupt edilmiş sentinel data olarak yüzeye çıksın.
  • Hâlâ canlıyken iki kez döndürülen aynı adresi flag'leyen double-allocation detector'ları / allocation-shadow tracking.

Mitigation

  • Run header'larını/bitmap'lerini region data'sından out-of-band tut (sonraki jemalloc run state'inin çoğunu contiguous user region'dan dışarı taşır).
  • Bitmap integrity: regs_minelm'i bounds-clamp et, bitmap'i checksum/canary'le, hesaplanan region pointer'ının run içine düştüğünü doğrula.
  • Region selection'ı randomize et ki corrupt edilmiş bir bitmap bile daha az öngörülebilir overlap'ler versin.

References