QEMU eth_get_gso_type reachable assertion (CVE-2020-27617)¶
QEMU'nun network helper katmanında guest-to-host bir denial of service; burada tanınan bir Layer-3 protokolünden yoksun bir paket
eth_get_gso_type()'a ulaşır, birg_assert'i tetikler ve host QEMU process'ini abort eder.
Mechanism¶
Note
Emüle bir NIC segmentation offload (TSO/GSO) sunduğunda, QEMU'nun net/eth.c
içindeki paylaşılan Ethernet helper'ı eth_get_gso_type(), paketin Layer-3
EtherType'ını bir GSO type'a map'ler. Kod, L3 protokolünün her zaman tanıdığı bir
şey (IPv4 / IPv6) olduğunu varsaydı ve bu varsayımı bir runtime check yerine bir
assertion olarak kodladı. Bir guest, L3 protokol değeri ikisi de olmayan bir
frame gönderebilir — assertion'ın koşulu false olur, g_assert tetiklenir ve QEMU
abort() çağırır. Bu bir reachable assertion (CWE-617): attacker-controlled
input, yalnızca "imkânsız" internal state'leri yakalamak için tasarlanmış bir
assert'i sürer. Abort host QEMU process'ini öldürdüğü için, unprivileged bir
guest guest→host sınırını temiz bir denial of service olarak aşar.
Bir reachable assertion, memory corruption'ın daha yumuşak bir kuzenidir: OOB write yok, ama aynı sınır aşımı ve DoS sonucu. OOB device durumları qemu-es1370-audio-oob-access ve qemu-arm-gic-oob-heap-access ile karşılaştırın.
Walkthrough¶
Public, hâlihazırda patch'lenmiş advisory'den (QEMU launchpad bug 1878067, oss-security, Red Hat / SUSE). Yalnızca kavramsal reproduction.
- Guest, transmit path'i paketleri GSO/offload helper'ı üzerinden çalıştıran bir emüle NIC'i sürer.
- Ethernet payload'ı geçerli bir L3 protokolüne sahip olmayan (IPv4/IPv6'nın varsayıldığı yerde eksik ya da tanınmayan bir EtherType) bir frame gönderir.
- Send path
eth_get_gso_type()'a ulaşır; protokol varsayılan durumu sağlamaz, assertion'ın koşulu false olur veg_assert,abort()'u tetikler. - Host QEMU process'i sonlanır — tek bir hazırlanmış paketten bir host DoS.
Warning
Tarihsel, patch'lenmiş bir sorun (QEMU ~4.2.1 / 5.0, fuzzing yoluyla bulundu). Bu giriş kavramsal kalır; tetikleyici basitçe "geçerli L3 protokolü olmayan bir paket"tir.
Reachable-assertion → graceful-handling (shape of the fix)
Detection¶
- Host tarafı: QEMU,
eth_get_gso_type(net/eth.c) üzerinden geçen bir backtrace ileabort()/ SIGABRT yoluyla çıkar; host loglarında glib "assertion failed" mesajları. - Behavioral: QEMU ölümünden hemen önce offload-capable bir NIC'e malformed/yok L3 EtherType'lı frame'ler yayan bir guest, sinyaldir.
- Tek bir guest'e bağlı crash-loop, bir tesadüf yerine kasıtlı bir DoS'a işaret eder.
Mitigation¶
eth_get_gso_type()içindeki assert'i kaldıran ve beklenmeyen L3 protokolünü zarif bir şekilde ele alan CVE-2020-27617 için upstream QEMU fix'ini uygulayın (distro backport'ları: Debian, Ubuntu, Red Hat, SUSE).- Defense-in-depth: QEMU'yu confine edin (seccomp, SELinux/sVirt) ve otomatik restart/quarantine uygulayın ki bir assert-abort sınırlı bir kesinti olsun.
- Mümkün olan yerde QEMU'yu, network path'inde assertion'ları process abort'ları yerine kurtarılabilir hatalar olarak ele alacak şekilde derleyin.
References¶
- QEMU launchpad bug 1878067 — assertion failure in eth_get_gso_type: https://bugs.launchpad.net/qemu/+bug/1878067
- oss-security — CVE-2020-27617 (assert failure via eth_get_gso_type): https://www.openwall.com/lists/oss-security/2020/11/02/1
- Red Hat Bugzilla 1891668 — CVE-2020-27617: https://bugzilla.redhat.com/show_bug.cgi?id=1891668