accel/tcg: move jit thread manipulation into do_tb_phys_invalidate

To invalidate a TB on MacOS we need to enable write access to the JIT
buffer. We were doing this for tb_phys_invalidate__locked but that is
not the only path into do_tb_phys_invalidate. Move the manipulation
into the shared function that does the work.

As a result we can drop the tb_phys_invalidate__locked function and
update the calls directly.

This enables watchpoints to work in MacOS TCG guests.

Resolves: https://gitlab.com/qemu-project/qemu/-/work_items/3444
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Message-ID: <20260526110243.470002-5-alex.bennee@linaro.org>
Signed-off-by: Alex Bennée <alex.bennee@linaro.org>
(cherry picked from commit 78420b59f0)
Signed-off-by: Michael Tokarev <mjt@tls.msk.ru>
This commit is contained in:
Alex Bennée 2026-05-26 12:02:32 +01:00 committed by Michael Tokarev
parent cb1b5319cb
commit df91e7249b

View file

@ -925,6 +925,7 @@ static void do_tb_phys_invalidate(TranslationBlock *tb, bool rm_from_page_list)
uint32_t orig_cflags = tb_cflags(tb);
assert_memory_lock();
qemu_thread_jit_write();
/* make sure no further incoming jumps will be chained to this TB */
qemu_spin_lock(&tb->jmp_lock);
@ -935,33 +936,27 @@ static void do_tb_phys_invalidate(TranslationBlock *tb, bool rm_from_page_list)
phys_pc = tb_page_addr0(tb);
h = tb_hash_func(phys_pc, (orig_cflags & CF_PCREL ? 0 : tb->pc),
tb->flags, tb->cs_base, orig_cflags);
if (!qht_remove(&tb_ctx.htable, tb, h)) {
return;
if (qht_remove(&tb_ctx.htable, tb, h)) {
/* remove the TB from the page list */
if (rm_from_page_list) {
tb_remove(tb);
}
/* remove the TB from the hash list */
tb_jmp_cache_inval_tb(tb);
/* suppress this TB from the two jump lists */
tb_remove_from_jmp_list(tb, 0);
tb_remove_from_jmp_list(tb, 1);
/* suppress any remaining jumps to this TB */
tb_jmp_unlink(tb);
qatomic_set(&tb_ctx.tb_phys_invalidate_count,
tb_ctx.tb_phys_invalidate_count + 1);
}
/* remove the TB from the page list */
if (rm_from_page_list) {
tb_remove(tb);
}
/* remove the TB from the hash list */
tb_jmp_cache_inval_tb(tb);
/* suppress this TB from the two jump lists */
tb_remove_from_jmp_list(tb, 0);
tb_remove_from_jmp_list(tb, 1);
/* suppress any remaining jumps to this TB */
tb_jmp_unlink(tb);
qatomic_set(&tb_ctx.tb_phys_invalidate_count,
tb_ctx.tb_phys_invalidate_count + 1);
}
static void tb_phys_invalidate__locked(TranslationBlock *tb)
{
qemu_thread_jit_write();
do_tb_phys_invalidate(tb, true);
qemu_thread_jit_execute();
}
@ -1030,7 +1025,7 @@ void tb_invalidate_phys_range(CPUState *cpu, tb_page_addr_t start,
assert_memory_lock();
PAGE_FOR_EACH_TB(start, last, unused, tb, n) {
tb_phys_invalidate__locked(tb);
do_tb_phys_invalidate(tb, true);
}
}
@ -1091,7 +1086,7 @@ bool tb_invalidate_phys_page_unwind(CPUState *cpu, tb_page_addr_t addr,
current_tb_modified = true;
cpu_restore_state_from_tb(cpu, current_tb, pc);
}
tb_phys_invalidate__locked(tb);
do_tb_phys_invalidate(tb, true);
}
if (current_tb_modified) {
@ -1156,7 +1151,7 @@ tb_invalidate_phys_page_range__locked(CPUState *cpu,
current_tb_modified = true;
cpu_restore_state_from_tb(cpu, current_tb, retaddr);
}
tb_phys_invalidate__locked(tb);
do_tb_phys_invalidate(tb, true);
}
}