Windows LFH BlockStride / FirstAllocationOffset Corruption¶
LFH'nin bir sonraki allocation adresini hesaplamak için kullandığı subsegment geometry alanlarını corrupt ederek, allocator'ın attacker tarafından kaydırılmış, out-of-bounds bir pointer döndürmesini sağlamak.
Mechanism¶
Bozulan invariant
Low Fragmentation Heap, same-size istekleri bir _HEAP_SUBSEGMENT tarafından
tanımlanan bir UserBlocks region'ından (_HEAP_USERDATA_HEADER) karşılar.
LFH saklanmış bir pointer'ı çekmek yerine, sonraki block'u hesaplar:
Invariant, FirstAllocationOffset ve BlockStride'ın region'ı dürüstçe
sınırlamasıdır. Subsegment metadata'sına bu alanlardan birini değiştiren linear
bir overflow, bu çarp-ve-topla işleminin out-of-bounds / attacker tarafından
kaydırılmış bir pointer döndürmesini sağlar; program da bunun içine write
yapar — free-list unlink'i gerektirmeyen controlled bir write.
Heap başına RtlpLFHKey önemlidir: subsegment back-pointer'ları (ve Windows
8.1+'da geometry alanlarının kendisi) XOR-encoded'dur, dolayısıyla key olmadan
yapılan blind bir overwrite, kullanılabilir bir offset üretmek yerine consistency
check'i geçemez.
Walkthrough¶
Kavramsal reproduction (bkz. Rapid7 ve Valasek public yazıları):
- Bucket için LFH'yi aktive etmek üzere yeterince same-size allocation (~18) yap (bkz. LFH bucket grooming).
- Subsegment metadata'sına bitişik overflow edilebilir bir chunk groom et (bkz. LFH UserBlocks manipulation).
-
FirstAllocationOffset/BlockStride'ı overflow et: -
Bir block daha iste — allocator kaydırılmış pointer'ı döndürür.
- Bitişik bir object'in vtable'ına / function pointer'ına düşmek için onun üzerinden write yap.
Sertleştirilmiş build'lerde bu, encoded alanları forge etmek ve allocation-order randomization'ını yenmek için ek olarak bir info leak gerektirir.
Detection¶
- Full PageHeap (
gflags /p /enable img /full) overflow noktasında fault verir. - Metadata hataları
STATUS_HEAP_CORRUPTION/FAST_FAIL_HEAP_METADATA_CORRUPTION(kernel bugcheck0x13A) yükseltir. - WinDbg
!heap/dt _HEAP_SUBSEGMENT, chunk'ı sınırlamayan bir stride/offset gösterir. ntdllLFH routine'lerindeki heap fast-fail'lerinde EDR/WER kümelenmesi; izlenen herhangi bir segment'in dışında döndürülen allocation'lar.
Mitigation¶
- Windows 8.1+,
FirstAllocationOffsetveBlockStride'ı encode eder. - Windows 8+ LFH allocation-order randomization'ı deterministik indexing'i kırar (Rapid7, offset tahmin edilebilirliğinin Win7'de ~%97,8'den Win10'da ~%6'ya düştüğünü ölçtü).
- Random
RtlpLFHKey+ encoded back-pointer'lar; büyük allocation'larda/ subsegment'lerde guard page'ler. - HeapEnableTerminationOnCorruption (modern process'ler için varsayılan); birçok system process için 19H1 Segment Heap.