PAC (arm64e Pointer Authentication)¶
Apple'ın arm64e platformunda Armv8.3 Pointer Authentication kullanımı: return address'ler ile function/data pointer'lar, bir pointer'ın kullanılmayan üst bitlerinde tutulan key'li kriptografik bir kodla (PAC) imzalanır ve kullanılmadan önce authenticate edilir — böylece bozulmuş bir pointer, control flow'u yönlendirmek yerine fault verir.
Mechanism¶
Kapsam farkı
Bu not özellikle Apple arm64e'nin sertleştirilmiş konuşlandırmasına odaklanır (per-boot key re-randomization, userspace/kernel ayrı key'leri, Project Zero iPhone XS analizi). Generic ARMv8.3-A mimarisi — QARMA cipher, ARMv8.6 FPAC fault-on-fail ve PACStack/PARTS/PACtight gibi akademik hardened şemalar — için bkz. Pointer Authentication (PAC).
Sınır neden tutuyor
64-bit bir virtual address, 64 bitin çok azını kullanır ve geriye boş üst bitler bırakır. PAC bunları, pointer değeri ile 64-bit bir context/modifier üzerinden hesaplanan key'li bir imzayla doldurur. Kullanılabilir bir pointer forge etmek için saldırganın doğru PAC'i üretmesi gerekir — secret key olmadan bu pratikte imkansızdır.
PAC*(örn.PACIA,PACDA) imzalar;AUT*(örn.AUTIA) authenticate eder ve PAC'i çıkarır;XPAC*kontrol etmeden çıkarır. Birleşik branch/return/load varyantları (BLRA*,RETA*,LDRA*) auth'u işlemin içine katar.- Beş adet 128-bit key: instruction key'leri APIAKey/APIBKey, data key'leri APDAKey/APDBKey ve generic APGAKey.
- Authentication başarısız olunca hardware branch almaz — pointer'ın extension bitlerini poison eder, böylece bir sonraki dereference bir translation fault doğurur (saldırgan koduna atlama değil, bir crash).
Apple'ın arm64e'si referans tasarımı sertleştirir: key'ler her boot'ta
yeniden randomize edilir (yani bir leak kalıcı olmaz), architectural
register'ları paylaşmalarına rağmen userspace ve kernel ayrı key'ler
kullanır ve farklı key'ler key-substitution'ı engellemek için ilişkisiz
çıktılar üretir. Invariant şudur: yalnızca key'i elinde tutan kod,
authenticate olan bir pointer üretebilir, dolayısıyla saldırgan adreslerini
yerleştiren ROP / JOP, AUT*'ta
takılır.
Walkthrough¶
Yüksek seviyeli; herkese açık Project Zero analizinden — çalışan bir forgery yok.
1. Pointer'lar tanımda imzalanır, kullanımda authenticate edilir. Bir return address prologue'da imzalanır, epilogue'da authenticate edilir:
foo:
paciasp ; sign LR with APIAKey, context = SP
... ; (function body)
autiasp ; authenticate LR; corrupted -> poisoned pointer
ret ; ret to non-canonical addr -> translation fault
2. Forgery için key — ya da bir oracle — gerekir. Key secret ve her boot'a özel olduğundan, saldırgan bir PAC'i offline hesaplayamaz.
3. Bypass denemeleri cipher'ı değil, boru tesisatını hedef alır. Project Zero'nun iPhone XS çalışması gösterdi ki gerçekçi saldırılar signing gadget'lar (saldırganın etkilediği bir pointer'ı imzalayıp geri yazan kod, yani bir signing oracle) ve pointer reuse'dur (geçerli şekilde imzalanmış bir pointer'ın, farklı bir tanesinin beklendiği yere takılması; çünkü PAC yalnızca bir geçerli imzanın var olup olmadığını kontrol eder, hangi pointer olduğunu değil).
PAC neden yine de çıtayı yükseltiyor
Bypass edildiği yerlerde bile saldırganın bir signing gadget'a veya bir
oracle'a ihtiyacı oldu — bunlar "software ile yamanması kolay" şeyler. Apple
tam da bu tür düzeltmeleri (örn. bir AUTIA/PACIZA etkileşimini
sıkılaştırma) kriptografik bir kırılma olmadan gönderdi.
Key'ler, oracle'lar ve reuse
PAC'in gücü key'in gizliliği ve context'in benzersizliğindedir. Eğer bir
(pointer, PAC) çifti başka bir context'te reuse edilebiliyorsa veya kod,
saldırgan verisini imzalayıp sonucu ifşa etmeye zorlanabiliyorsa, key
bilinmeden control-flow integrity düşebilir. PACMAN
gibi speculative saldırılar da AUT* kontrolünü bir guess-verification
oracle'ına dönüştürebilir. Same-context pointer swap'ları bilinen bir
zayıflıktır.
Detection¶
- PAC authentication fault'ları.
AUT*/RETA*üzerindeki crash'ler (poison'lanmış, non-canonical bir adrese atlama) control-flow tampering'in yüksek sinyalli kanıtıdır — bunları generic SIGSEGV değil, security event olarak ele alın. - Signing-gadget isabetleri. Pointer'ları imzalayıp depoladığı bilinen bir fonksiyonun, özellikle saldırganın etkilediği girdilerle, tekrar tekrar çağrılması oracle suistimaline işaret eder.
- Speculative-probe desenleri (tahmin edilen pointer'ları tekrar tekrar authenticate eden sıkı loop'lar) PACMAN tarzı bir saldırıya işaret edebilir.
- Beklenmedik key state değişiklikleri (örn. control register'lar üzerinden PAC'in devre dışı bırakılması) arm64e'yi zorunlu kılması gereken bir cihazda.
Mitigation¶
PAC'in kendisi zaten mitigation'dır; konuşlandırma ve sınırlar:
- Branch protection ile derle. Return address'lerin imzalanması için
-mbranch-protection=pac-ret(veyapac-ret+bti) ile compile edin; arm64e imzalamayı birçok data/function pointer'a genişletir. - Sıkı, benzersiz context'lerle imzala. Bir imzalanmış pointer'ın başka yerde reuse edilememesi için pointer sınıfı başına ayrı modifier'lar kullanın; saldırgan kontrolündeki verinin generic imzalanmasını asla açığa çıkarmayın.
- Signing gadget / oracle'ları bulundukça yamayın — pratik attack surface cipher değil, software'dir.
- Diğer savunmalarla birleştir: forward edge için BTI, memory safety için MTE ve OS seviyesi integrity (operating-system-integrity-os-integrity-protections).
- Artık risk: signing oracle'lar, pointer reuse, authenticate edilmemiş pointer'lar ve speculative oracle'lar (PACMAN) hâlâ geçerlidir.