This commit sets the address field sizes in CPUTLBEntry based on the value of TCG_VADDR_BITS. For non-wasm hosts, TCG_VADDR_BITS matches the pointer size so this change preserves the original behaviour.
WebAssembly supports 64bit atomics even though sizeof(void *) is 4. This commit also updates ATOMIC_REG_SIZE value for the wasm build to ensure assertions pass. Signed-off-by: Kohei Tokunaga <ktokunaga.m...@gmail.com> --- accel/tcg/cputlb.c | 8 ++++---- include/exec/tlb-common.h | 18 +++++++++++++----- include/qemu/atomic.h | 4 ++++ 3 files changed, 21 insertions(+), 9 deletions(-) diff --git a/accel/tcg/cputlb.c b/accel/tcg/cputlb.c index 5f6d7c601c..b15e9e80ee 100644 --- a/accel/tcg/cputlb.c +++ b/accel/tcg/cputlb.c @@ -109,13 +109,13 @@ static inline uint64_t tlb_read_idx(const CPUTLBEntry *entry, { /* Do not rearrange the CPUTLBEntry structure members. */ QEMU_BUILD_BUG_ON(offsetof(CPUTLBEntry, addr_read) != - MMU_DATA_LOAD * sizeof(uintptr_t)); + MMU_DATA_LOAD * sizeof(tlb_addr)); QEMU_BUILD_BUG_ON(offsetof(CPUTLBEntry, addr_write) != - MMU_DATA_STORE * sizeof(uintptr_t)); + MMU_DATA_STORE * sizeof(tlb_addr)); QEMU_BUILD_BUG_ON(offsetof(CPUTLBEntry, addr_code) != - MMU_INST_FETCH * sizeof(uintptr_t)); + MMU_INST_FETCH * sizeof(tlb_addr)); - const uintptr_t *ptr = &entry->addr_idx[access_type]; + const tlb_addr *ptr = &entry->addr_idx[access_type]; /* ofs might correspond to .addr_write, so use qatomic_read */ return qatomic_read(ptr); } diff --git a/include/exec/tlb-common.h b/include/exec/tlb-common.h index 03b5a8ffc7..87f8beab9a 100644 --- a/include/exec/tlb-common.h +++ b/include/exec/tlb-common.h @@ -19,14 +19,22 @@ #ifndef EXEC_TLB_COMMON_H #define EXEC_TLB_COMMON_H 1 -#define CPU_TLB_ENTRY_BITS (HOST_LONG_BITS == 32 ? 4 : 5) +#if TCG_VADDR_BITS == 32 +#define CPU_TLB_ENTRY_BITS 4 +typedef uint32_t tlb_addr; +#elif TCG_VADDR_BITS == 64 +#define CPU_TLB_ENTRY_BITS 5 +typedef uint64_t tlb_addr; +#else +#error Unknown pointer size +#endif /* Minimalized TLB entry for use by TCG fast path. */ typedef union CPUTLBEntry { struct { - uintptr_t addr_read; - uintptr_t addr_write; - uintptr_t addr_code; + tlb_addr addr_read; + tlb_addr addr_write; + tlb_addr addr_code; /* * Addend to virtual address to get host address. IO accesses * use the corresponding iotlb value. @@ -37,7 +45,7 @@ typedef union CPUTLBEntry { * Padding to get a power of two size, as well as index * access to addr_{read,write,code}. */ - uintptr_t addr_idx[(1 << CPU_TLB_ENTRY_BITS) / sizeof(uintptr_t)]; + tlb_addr addr_idx[(1 << CPU_TLB_ENTRY_BITS) / sizeof(tlb_addr)]; } CPUTLBEntry; QEMU_BUILD_BUG_ON(sizeof(CPUTLBEntry) != (1 << CPU_TLB_ENTRY_BITS)); diff --git a/include/qemu/atomic.h b/include/qemu/atomic.h index f80cba24cf..76a8fbcd8c 100644 --- a/include/qemu/atomic.h +++ b/include/qemu/atomic.h @@ -56,6 +56,7 @@ */ #define signal_barrier() __atomic_signal_fence(__ATOMIC_SEQ_CST) +#ifndef EMSCRIPTEN /* * Sanity check that the size of an atomic operation isn't "overly large". * Despite the fact that e.g. i686 has 64-bit atomic operations, we do not @@ -63,6 +64,9 @@ * bit of sanity checking that other 32-bit hosts might build. */ #define ATOMIC_REG_SIZE sizeof(void *) +#else +#define ATOMIC_REG_SIZE 8 /* wasm supports 64bit atomics */ +#endif /* Weak atomic operations prevent the compiler moving other * loads/stores past the atomic operation load/store. However there is -- 2.43.0