Heap/Stack Spray to Reduce ASLR Entropy¶
Kör tahmin edilen bir address'in büyük olasılıkla attacker-controlled belleğe düşmesi için address space'in devasa region'larını NOP sled'leri ve shellcode ile doldurmak, böylece ASLR'ın sağladığı sınırlı entropy'yi nötralize etmek.
Scope
Burada "spray", ASLR entropy'sini düşürmek için kullanılan userspace heap/data spraying varyantını anlatır. Bu, use-before-initialization bug'larını hedefleyen kernel-level stack-spraying tekniğiyle karıştırılmamalıdır; ikisi ilişkisiz spray kavramlarıdır ve bu belge yalnızca heap/ASLR varyantını kapsar.
Mechanism¶
ASLR'ın koruması, bir attacker'ın tahmin etmesi gereken randomize edilmiş bit sayısıyla ölçeklenir. Spraying saldırıları bu denklemin olasılık tarafına saldırır: tam bir address tahmin etmek yerine attacker, address space'in büyük bir kısmını geçerli kılar, böylece tek bir tahmin (veya corrupt edilmiş bir pointer dereference) büyük olasılıkla işe yarar bir hedefe çarpar.
Invariant the bypass breaks
ASLR, attacker'ın işe yarar byte'ların nerede bulunduğunu tahmin edemeyeceğini varsayar. Bir spray, çoğu makul address'in attacker byte'ları içermesini sağlayarak o tahmini gereksiz kılar. Büyük heap allocation'ları tahmin edilebilir ve ardışık allocation'lar kabaca sıralı olduğu için sprayed region her seferinde kabaca aynı konumda biter ve sprayed byte'lar hem geçerli bir address hem de NOP benzeri bir instruction olarak çift işlev görür (ör. x86'da 0x0c0c0c0c, çok büyük bir NOP sled oluşturur). Kalan entropy, spray'in kapatamadığı space kesri kadarına etkin biçimde düşer.
Shacham et al. (CCS 2004), bu fikrin brute-force kuzeni için altta yatan zayıflığı niceledi: 32-bit Linux'ta PaX ASLR yalnızca ~16 bit entropy sağlar ve re-randomization sıklığını artırmak "en fazla 1 bit güvenlik ekler". 32-bit Windows heap'lerinde entropy daha da küçüktür (~8 bit / ~256 konum), dolayısıyla yeterince bellek spray eden bir attacker istatistiksel olarak her olası konumu kapatır.
Walkthrough¶
Bu bir bypass tekniğidir. Spray bir bug'ı kendisi exploit etmez; mevcut bir control-flow hijack'inin başarı olasılığını yükseltir.
- Agresifçe allocate et. Script'ten (klasik browser durumu) veya bir memory-pressure primitive'i üzerinden birçok büyük heap block'u allocate et.
- Sled + payload ile doldur. Her block
NOP sled || shellcode, tekrarlanır. Payload'dan önceki uzun bir sled kabul edilebilir landing zone'unu genişletir. - Tahmin space'ini kapla. Herhangi bir makul jump target'ının sprayed bellek içinde olacağı kadar block inject et. Low-entropy 32-bit bir heap'te yüzlerce MB mertebesinde spray etmek etkin biçimde tüm heap konumlarını kapatabilir.
- Hijack'i tetikle. Execution'ı (corrupt edilmiş vtable/function pointer) sabit, hard-coded bir tahmin address'ine yönlendir.
- Sled'e düş. Tahmin sapsa bile sled'in ortasına düşer ve shellcode'a kayar.
Browser heap spray (conceptual)
Warning
Spraying olasılıksaldır ve en iyi low-entropy hedeflere karşı çalışır. 64-bit ASLR çok daha fazla entropy sunar, dolayısıyla modern hedeflerde spraying tek başına genellikle bir info leak ile birleştirilir ya da onunla ikame edilir. Teknik ayrıca sprayed page'lerin executable olduğunu varsayar, dolayısıyla NX/DEP ile zayıflatılır (ROP tabanlı payload'lara kaymayı tetikleyerek).
Beklenen sonuç: heap doygunken sabit-address bir jump güvenilir biçimde attacker byte'larına düşer, dolayısıyla ASLR artık attacker'ı gerçek randomize edilmiş base'i geri kazanmaya zorlamaz.
Mitigation¶
- Entropy'yi yükselt: 64-bit ASLR / KASLR, spraying ile tam kapsamayı pratik olmaktan çıkarır.
- Executable spray'leri reddet:
no-execute-data-execution-prevention(W^X), sprayed data page'lerinden execution'ı durdurur. - Bayat/uninitialized belleği sıfırla, böylece sprayed kalıntılar daha az güvenilir olur:
init-on-alloc,init-on-free. - Randomize edilmiş binary'ler build et:
position-independent-executable.