[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
** CVE added: https://cve.mitre.org/cgi-bin/cvename.cgi?name=2022-36648 -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Fix Released Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
Re: [Bug 1863025] Re: Use-after-free after flush in TCG accelerator
On Thu, Aug 31, 2023 at 3:57 PM Daniel P. Berrangé wrote: > > On Thu, Aug 31, 2023 at 03:40:25PM +0200, Philippe Mathieu-Daudé wrote: > > Hi Samuel, > > > > On 31/8/23 14:48, Samuel Henrique wrote: > > > CVE-2020-24165 was assigned to this: > > > https://nvd.nist.gov/vuln/detail/CVE-2020-24165 > > > > > > I had no involvement in the assignment, posting here for reference only. > > > > > > ** CVE added: https://cve.mitre.org/cgi-bin/cvename.cgi?name=2020-24165 > > > > QEMU 4.2.0 was released in 2019. The issue you report > > has been fixed in commit 886cc68943 ("accel/tcg: fix race > > in cpu_exec_step_atomic (bug 1863025)") which is included > > in QEMU v5.0, released in April 2020, more than 3 years ago. > > > > What do you expect us to do here? I'm not sure whether assigning > > CVE for 3 years old code is a good use of engineering time. > > In any case per our stated security policy, we do not consider TCG to > be providing a security boundary between host and guest, and thus bugs > in TCG aren't considered security flaws: > > > https://www.qemu.org/docs/master/system/security.html#non-virtualization-use-case Right, and it is clearly indicated in the referenced launchpad bug: 'The security list informed me "This can not be treated as a security issue"'. This adds up to CVE-2022-36648, which is also a mystery to me in terms of CVE assignment and CVSS scoring (rated as Critical). I don't know what's going on with NVD, there must be something wrong on their side. I disputed both CVEs via https://cveform.mitre.org/. > With regards, > Daniel > -- > |: https://berrange.com -o-https://www.flickr.com/photos/dberrange :| > |: https://libvirt.org -o-https://fstop138.berrange.com :| > |: https://entangle-photo.org-o-https://www.instagram.com/dberrange :| > -- Mauro Matteo Cascella Red Hat Product Security PGP-Key ID: BB3410B0
Re: [Bug 1863025] Re: Use-after-free after flush in TCG accelerator
On Thu, Aug 31, 2023 at 03:40:25PM +0200, Philippe Mathieu-Daudé wrote: > Hi Samuel, > > On 31/8/23 14:48, Samuel Henrique wrote: > > CVE-2020-24165 was assigned to this: > > https://nvd.nist.gov/vuln/detail/CVE-2020-24165 > > > > I had no involvement in the assignment, posting here for reference only. > > > > ** CVE added: https://cve.mitre.org/cgi-bin/cvename.cgi?name=2020-24165 > > QEMU 4.2.0 was released in 2019. The issue you report > has been fixed in commit 886cc68943 ("accel/tcg: fix race > in cpu_exec_step_atomic (bug 1863025)") which is included > in QEMU v5.0, released in April 2020, more than 3 years ago. > > What do you expect us to do here? I'm not sure whether assigning > CVE for 3 years old code is a good use of engineering time. In any case per our stated security policy, we do not consider TCG to be providing a security boundary between host and guest, and thus bugs in TCG aren't considered security flaws: https://www.qemu.org/docs/master/system/security.html#non-virtualization-use-case With regards, Daniel -- |: https://berrange.com -o-https://www.flickr.com/photos/dberrange :| |: https://libvirt.org -o-https://fstop138.berrange.com :| |: https://entangle-photo.org-o-https://www.instagram.com/dberrange :|
Re: [Bug 1863025] Re: Use-after-free after flush in TCG accelerator
Hi Samuel, On 31/8/23 14:48, Samuel Henrique wrote: CVE-2020-24165 was assigned to this: https://nvd.nist.gov/vuln/detail/CVE-2020-24165 I had no involvement in the assignment, posting here for reference only. ** CVE added: https://cve.mitre.org/cgi-bin/cvename.cgi?name=2020-24165 QEMU 4.2.0 was released in 2019. The issue you report has been fixed in commit 886cc68943 ("accel/tcg: fix race in cpu_exec_step_atomic (bug 1863025)") which is included in QEMU v5.0, released in April 2020, more than 3 years ago. What do you expect us to do here? I'm not sure whether assigning CVE for 3 years old code is a good use of engineering time. Regards, Phil.
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
CVE-2020-24165 was assigned to this: https://nvd.nist.gov/vuln/detail/CVE-2020-24165 I had no involvement in the assignment, posting here for reference only. ** CVE added: https://cve.mitre.org/cgi-bin/cvename.cgi?name=2020-24165 -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Fix Released Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
** Changed in: qemu Status: Fix Committed => Fix Released -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Fix Released Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
Fixed here: https://git.qemu.org/?p=qemu.git;a=commitdiff;h=886cc68943eb ** Changed in: qemu Status: Confirmed => Fix Committed -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Fix Committed Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
Apologies, the patch got messed up. diff --git a/accel/tcg/cpu-exec.c b/accel/tcg/cpu-exec.c index c01f59c743..7a9e8c94bd 100644 --- a/accel/tcg/cpu-exec.c +++ b/accel/tcg/cpu-exec.c @@ -238,8 +238,11 @@ void cpu_exec_step_atomic(CPUState *cpu) uint32_t flags; uint32_t cflags = 1; uint32_t cf_mask = cflags & CF_HASH_MASK; +unsigned flush_count; if (sigsetjmp(cpu->jmp_env, 0) == 0) { +retry: +flush_count = tb_flush_count(); tb = tb_lookup__cpu_state(cpu, &pc, &cs_base, &flags, cf_mask); if (tb == NULL) { mmap_lock(); @@ -248,6 +251,11 @@ void cpu_exec_step_atomic(CPUState *cpu) } start_exclusive(); +/* do_tb_flush() might run and make tb invalid */ +if (flush_count != tb_flush_count()) { +end_exclusive(); +goto retry; +} /* Since we got here, we know that parallel_cpus must be true. */ parallel_cpus = false; diff --git a/accel/tcg/translate-all.c b/accel/tcg/translate-all.c index 9f48da9472..2fb7da9b51 100644 --- a/accel/tcg/translate-all.c +++ b/accel/tcg/translate-all.c @@ -2674,3 +2674,8 @@ void tcg_flush_softmmu_tlb(CPUState *cs) tlb_flush(cs); #endif } + +unsigned tb_flush_count(void) +{ +return atomic_read(&tb_ctx.tb_flush_count); +} diff --git a/include/exec/exec-all.h b/include/exec/exec-all.h index d85e610e85..aa3c2d219a 100644 --- a/include/exec/exec-all.h +++ b/include/exec/exec-all.h @@ -579,6 +579,9 @@ void tlb_set_dirty(CPUState *cpu, target_ulong vaddr); /* exec.c */ void tb_flush_jmp_cache(CPUState *cpu, target_ulong addr); +/* translate-all.c */ +unsigned tb_flush_count(void); + MemoryRegionSection * address_space_translate_for_iotlb(CPUState *cpu, int asidx, hwaddr addr, hwaddr *xlat, hwaddr *plen, -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Confirmed Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
I found it just by launching Ubuntu 19.10 live cd with QXL driver. I will re-test this weekend. The workaround I had is to check the number of TLB flushes and to re-try obtaining the TB if the number changes. There is a penalty for the case where TLB is flushed but should not degrade performance in most cases. I think obtaining the lock earlier will slow down the VM if EXCP_ATOMIC is used often. Of course, I am assuming TLB flush is the only way to cause this bug. diff --git a/accel/tcg/cpu-exec.c b/accel/tcg/cpu-exec.c index d1c2b6ea1fd..d83b578299b 100644 --- a/accel/tcg/cpu-exec.c +++ b/accel/tcg/cpu-exec.c @@ -250,8 +250,11 @@ void cpu_exec_step_atomic(CPUState *cpu) uint32_t flags; uint32_t cflags = 1; uint32_t cf_mask = cflags & CF_HASH_MASK; +unsigned flush_count; if (sigsetjmp(cpu->jmp_env, 0) == 0) { +retry: +flush_count = tb_flush_count(); tb = tb_lookup__cpu_state(cpu, &pc, &cs_base, &flags, cf_mask); if (tb == NULL) { mmap_lock(); @@ -260,6 +263,11 @@ void cpu_exec_step_atomic(CPUState *cpu) } start_exclusive(); +/* do_tb_flush() might run and make tb invalid */ +if (flush_count != tb_flush_count()) { +end_exclusive(); +goto retry; +} /* Since we got here, we know that parallel_cpus must be true. */ parallel_cpus = false; diff --git a/accel/tcg/translate-all.c b/accel/tcg/translate-all.c index 4ed9d0abaf2..ecf7d3b53ff 100644 --- a/accel/tcg/translate-all.c +++ b/accel/tcg/translate-all.c @@ -2696,6 +2696,11 @@ void tcg_flush_softmmu_tlb(CPUState *cs) #endif } +unsigned tb_flush_count(void) +{ +return atomic_read(&tb_ctx.tb_flush_count); +} + #if defined(CONFIG_NO_RWX) void tb_exec_memory_lock(void) { diff --git a/include/exec/exec-all.h b/include/exec/exec-all.h index 5ccc9485812..1bc61fa6d76 100644 --- a/include/exec/exec-all.h +++ b/include/exec/exec-all.h @@ -584,6 +584,7 @@ void tlb_set_dirty(CPUState *cpu, target_ulong vaddr); void tb_flush_jmp_cache(CPUState *cpu, target_ulong addr); /* translate-all.c */ +unsigned tb_flush_count(void); #if defined(CONFIG_NO_RWX) void tb_exec_memory_lock(void); bool tb_is_exec(const TranslationBlock *tb); -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Confirmed Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
I've attached a variant of the suggested patch which simply expands the exclusive period. It's hard to test extensively as not many things use the EXCP_ATOMIC mechanism. Can I ask how you found the bug and if you can re-test with the suggested patch? -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Confirmed Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
** Changed in: qemu Assignee: (unassigned) => Alex Bennée (ajbennee) ** Changed in: qemu Status: New => Confirmed -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Confirmed Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions
[Bug 1863025] Re: Use-after-free after flush in TCG accelerator
** Tags added: tcg -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/1863025 Title: Use-after-free after flush in TCG accelerator Status in QEMU: Confirmed Bug description: I believe I found a UAF in TCG that can lead to a guest VM escape. The security list informed me "This can not be treated as a security issue." and to post it here. I am looking at the 4.2.0 source code. The issue requires a race and I will try to describe it in terms of three concurrent threads. Thread A: A1. qemu_tcg_cpu_thread_fn runs work loop A2. qemu_wait_io_event => qemu_wait_io_event_common => process_queued_cpu_work A3. start_exclusive critical section entered A4. do_tb_flush is called, TB memory freed/re-allocated A5. end_exclusive exits critical section Thread B: B1. qemu_tcg_cpu_thread_fn runs work loop B2. tcg_cpu_exec => cpu_exec => tb_find => tb_gen_code B3. tcg_tb_alloc obtains a new TB Thread C: C1. qemu_tcg_cpu_thread_fn runs work loop C2. cpu_exec_step_atomic executes C3. TB obtained with tb_lookup__cpu_state or tb_gen_code C4. start_exclusive critical section entered C5. cpu_tb_exec executes the TB code C6. end_exclusive exits critical section Consider the following sequence of events: B2 => B3 => C3 (same TB as B2) => A3 => A4 (TB freed) => A5 => B2 => B3 (re-allocates TB from B2) => C4 => C5 (freed/reused TB now executing) => C6 In short, because thread C uses the TB in the critical section, there is no guarantee that the pointer has not been "freed" (rather the memory is marked as re-usable) and therefore a use-after-free occurs. Since the TCG generated code can be in the same memory as the TB data structure, it is possible for an attacker to overwrite the UAF pointer with code generated from TCG. This can overwrite key pointer values and could lead to code execution on the host outside of the TCG sandbox. To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/1863025/+subscriptions