Merge branch main into dev/wasi-libc-windows

This commit is contained in:
Wenyong Huang
2023-11-09 10:13:59 +08:00
48 changed files with 900 additions and 512 deletions

View File

@ -312,7 +312,6 @@ execute_func(WASMModuleInstanceCommon *module_inst, const char *name,
#endif
int32 i, p, module_type;
uint64 total_size;
const char *exception;
char buf[128];
bh_assert(argc >= 0);
@ -647,9 +646,7 @@ fail:
if (argv1)
wasm_runtime_free(argv1);
exception = wasm_runtime_get_exception(module_inst);
bh_assert(exception);
os_printf("%s\n", exception);
bh_assert(wasm_runtime_get_exception(module_inst));
return false;
}

View File

@ -298,10 +298,15 @@ wasm_runtime_validate_app_addr(WASMModuleInstanceCommon *module_inst_comm,
goto fail;
}
SHARED_MEMORY_LOCK(memory_inst);
if (app_offset + size <= memory_inst->memory_data_size) {
SHARED_MEMORY_UNLOCK(memory_inst);
return true;
}
SHARED_MEMORY_UNLOCK(memory_inst);
fail:
wasm_set_exception(module_inst, "out of bounds memory access");
return false;
@ -364,11 +369,16 @@ wasm_runtime_validate_native_addr(WASMModuleInstanceCommon *module_inst_comm,
goto fail;
}
SHARED_MEMORY_LOCK(memory_inst);
if (memory_inst->memory_data <= addr
&& addr + size <= memory_inst->memory_data_end) {
SHARED_MEMORY_UNLOCK(memory_inst);
return true;
}
SHARED_MEMORY_UNLOCK(memory_inst);
fail:
wasm_set_exception(module_inst, "out of bounds memory access");
return false;
@ -393,20 +403,24 @@ wasm_runtime_addr_app_to_native(WASMModuleInstanceCommon *module_inst_comm,
return NULL;
}
SHARED_MEMORY_LOCK(memory_inst);
addr = memory_inst->memory_data + app_offset;
if (bounds_checks) {
if (memory_inst->memory_data <= addr
&& addr < memory_inst->memory_data_end) {
SHARED_MEMORY_UNLOCK(memory_inst);
return addr;
}
}
/* If bounds checks is disabled, return the address directly */
else if (app_offset != 0) {
SHARED_MEMORY_UNLOCK(memory_inst);
return addr;
}
SHARED_MEMORY_UNLOCK(memory_inst);
return NULL;
}
@ -418,6 +432,7 @@ wasm_runtime_addr_native_to_app(WASMModuleInstanceCommon *module_inst_comm,
WASMMemoryInstance *memory_inst;
uint8 *addr = (uint8 *)native_ptr;
bool bounds_checks;
uint32 ret;
bh_assert(module_inst_comm->module_type == Wasm_Module_Bytecode
|| module_inst_comm->module_type == Wasm_Module_AoT);
@ -429,16 +444,24 @@ wasm_runtime_addr_native_to_app(WASMModuleInstanceCommon *module_inst_comm,
return 0;
}
SHARED_MEMORY_LOCK(memory_inst);
if (bounds_checks) {
if (memory_inst->memory_data <= addr
&& addr < memory_inst->memory_data_end)
return (uint32)(addr - memory_inst->memory_data);
&& addr < memory_inst->memory_data_end) {
ret = (uint32)(addr - memory_inst->memory_data);
SHARED_MEMORY_UNLOCK(memory_inst);
return ret;
}
}
/* If bounds checks is disabled, return the offset directly */
else if (addr != NULL) {
return (uint32)(addr - memory_inst->memory_data);
ret = (uint32)(addr - memory_inst->memory_data);
SHARED_MEMORY_UNLOCK(memory_inst);
return ret;
}
SHARED_MEMORY_UNLOCK(memory_inst);
return 0;
}
@ -459,6 +482,8 @@ wasm_runtime_get_app_addr_range(WASMModuleInstanceCommon *module_inst_comm,
return false;
}
SHARED_MEMORY_LOCK(memory_inst);
memory_data_size = memory_inst->memory_data_size;
if (app_offset < memory_data_size) {
@ -466,9 +491,11 @@ wasm_runtime_get_app_addr_range(WASMModuleInstanceCommon *module_inst_comm,
*p_app_start_offset = 0;
if (p_app_end_offset)
*p_app_end_offset = memory_data_size;
SHARED_MEMORY_UNLOCK(memory_inst);
return true;
}
SHARED_MEMORY_UNLOCK(memory_inst);
return false;
}
@ -490,15 +517,19 @@ wasm_runtime_get_native_addr_range(WASMModuleInstanceCommon *module_inst_comm,
return false;
}
SHARED_MEMORY_LOCK(memory_inst);
if (memory_inst->memory_data <= addr
&& addr < memory_inst->memory_data_end) {
if (p_native_start_addr)
*p_native_start_addr = memory_inst->memory_data;
if (p_native_end_addr)
*p_native_end_addr = memory_inst->memory_data_end;
SHARED_MEMORY_UNLOCK(memory_inst);
return true;
}
SHARED_MEMORY_UNLOCK(memory_inst);
return false;
}
@ -512,7 +543,8 @@ wasm_check_app_addr_and_convert(WASMModuleInstance *module_inst, bool is_str,
bool bounds_checks;
if (!memory_inst) {
goto fail;
wasm_set_exception(module_inst, "out of bounds memory access");
return false;
}
native_addr = memory_inst->memory_data + app_buf_addr;
@ -529,6 +561,8 @@ wasm_check_app_addr_and_convert(WASMModuleInstance *module_inst, bool is_str,
/* No need to check the app_offset and buf_size if memory access
boundary check with hardware trap is enabled */
#ifndef OS_ENABLE_HW_BOUND_CHECK
SHARED_MEMORY_LOCK(memory_inst);
if (app_buf_addr >= memory_inst->memory_data_size) {
goto fail;
}
@ -549,14 +583,20 @@ wasm_check_app_addr_and_convert(WASMModuleInstance *module_inst, bool is_str,
if (str == str_end)
goto fail;
}
SHARED_MEMORY_UNLOCK(memory_inst);
#endif
success:
*p_native_addr = (void *)native_addr;
return true;
#ifndef OS_ENABLE_HW_BOUND_CHECK
fail:
SHARED_MEMORY_UNLOCK(memory_inst);
wasm_set_exception(module_inst, "out of bounds memory access");
return false;
#endif
}
WASMMemoryInstance *
@ -568,6 +608,27 @@ wasm_get_default_memory(WASMModuleInstance *module_inst)
return NULL;
}
void
wasm_runtime_set_mem_bound_check_bytes(WASMMemoryInstance *memory,
uint64 memory_data_size)
{
#if WASM_ENABLE_FAST_JIT != 0 || WASM_ENABLE_JIT != 0 || WASM_ENABLE_AOT != 0
#if UINTPTR_MAX == UINT64_MAX
memory->mem_bound_check_1byte.u64 = memory_data_size - 1;
memory->mem_bound_check_2bytes.u64 = memory_data_size - 2;
memory->mem_bound_check_4bytes.u64 = memory_data_size - 4;
memory->mem_bound_check_8bytes.u64 = memory_data_size - 8;
memory->mem_bound_check_16bytes.u64 = memory_data_size - 16;
#else
memory->mem_bound_check_1byte.u32[0] = (uint32)memory_data_size - 1;
memory->mem_bound_check_2bytes.u32[0] = (uint32)memory_data_size - 2;
memory->mem_bound_check_4bytes.u32[0] = (uint32)memory_data_size - 4;
memory->mem_bound_check_8bytes.u32[0] = (uint32)memory_data_size - 8;
memory->mem_bound_check_16bytes.u32[0] = (uint32)memory_data_size - 16;
#endif
#endif
}
#ifndef OS_ENABLE_HW_BOUND_CHECK
bool
wasm_enlarge_memory_internal(WASMModuleInstance *module, uint32 inc_page_count)
@ -625,9 +686,10 @@ wasm_enlarge_memory_internal(WASMModuleInstance *module, uint32 inc_page_count)
memory->num_bytes_per_page = num_bytes_per_page;
memory->cur_page_count = total_page_count;
memory->max_page_count = max_page_count;
/* No need to update memory->memory_data_size as it is
initialized with the maximum memory data size for
shared memory */
memory->memory_data_size = (uint32)total_size_new;
memory->memory_data_end = memory->memory_data + (uint32)total_size_new;
wasm_runtime_set_mem_bound_check_bytes(memory, total_size_new);
return true;
}
#endif
@ -679,21 +741,7 @@ wasm_enlarge_memory_internal(WASMModuleInstance *module, uint32 inc_page_count)
memory->memory_data = memory_data_new;
memory->memory_data_end = memory_data_new + (uint32)total_size_new;
#if WASM_ENABLE_FAST_JIT != 0 || WASM_ENABLE_JIT != 0 || WASM_ENABLE_AOT != 0
#if UINTPTR_MAX == UINT64_MAX
memory->mem_bound_check_1byte.u64 = total_size_new - 1;
memory->mem_bound_check_2bytes.u64 = total_size_new - 2;
memory->mem_bound_check_4bytes.u64 = total_size_new - 4;
memory->mem_bound_check_8bytes.u64 = total_size_new - 8;
memory->mem_bound_check_16bytes.u64 = total_size_new - 16;
#else
memory->mem_bound_check_1byte.u32[0] = (uint32)total_size_new - 1;
memory->mem_bound_check_2bytes.u32[0] = (uint32)total_size_new - 2;
memory->mem_bound_check_4bytes.u32[0] = (uint32)total_size_new - 4;
memory->mem_bound_check_8bytes.u32[0] = (uint32)total_size_new - 8;
memory->mem_bound_check_16bytes.u32[0] = (uint32)total_size_new - 16;
#endif
#endif
wasm_runtime_set_mem_bound_check_bytes(memory, total_size_new);
#if defined(os_writegsbase)
/* write base addr of linear memory to GS segment register */
@ -799,13 +847,7 @@ wasm_enlarge_memory_internal(WASMModuleInstance *module, uint32 inc_page_count)
memory->memory_data_size = (uint32)total_size_new;
memory->memory_data_end = memory->memory_data + (uint32)total_size_new;
#if WASM_ENABLE_FAST_JIT != 0 || WASM_ENABLE_JIT != 0 || WASM_ENABLE_AOT != 0
memory->mem_bound_check_1byte.u64 = total_size_new - 1;
memory->mem_bound_check_2bytes.u64 = total_size_new - 2;
memory->mem_bound_check_4bytes.u64 = total_size_new - 4;
memory->mem_bound_check_8bytes.u64 = total_size_new - 8;
memory->mem_bound_check_16bytes.u64 = total_size_new - 16;
#endif
wasm_runtime_set_mem_bound_check_bytes(memory, total_size_new);
return_func:
if (!ret && enlarge_memory_error_cb) {

View File

@ -24,6 +24,10 @@ wasm_runtime_memory_destroy();
unsigned
wasm_runtime_memory_pool_size();
void
wasm_runtime_set_mem_bound_check_bytes(WASMMemoryInstance *memory,
uint64 memory_data_size);
void
wasm_runtime_set_enlarge_mem_error_callback(
const enlarge_memory_error_callback_t callback, void *user_data);

View File

@ -542,8 +542,7 @@ void
wasm_runtime_set_wasi_ctx(WASMModuleInstanceCommon *module_inst_comm,
WASIContext *wasi_ctx)
{
return wasm_native_set_context(module_inst_comm, g_wasi_context_key,
wasi_ctx);
wasm_native_set_context(module_inst_comm, g_wasi_context_key, wasi_ctx);
}
static void

View File

@ -3037,6 +3037,74 @@ wasm_runtime_init_wasi(WASMModuleInstanceCommon *module_inst,
}
}
for (i = 0; i < map_dir_count; i++, wasm_fd++) {
char mapping_copy_buf[256];
char *mapping_copy = mapping_copy_buf;
char *map_mapped = NULL, *map_host = NULL;
const unsigned long max_len = strlen(map_dir_list[i]) * 2 + 3;
/* Allocation limit for runtime environments with reduced stack size */
if (max_len > 256) {
if (!(mapping_copy = wasm_runtime_malloc(max_len))) {
snprintf(error_buf, error_buf_size,
"error while allocating for directory mapping\n");
goto fail;
}
}
bh_memcpy_s(mapping_copy, max_len, map_dir_list[i],
(uint32)(strlen(map_dir_list[i]) + 1));
map_mapped = strtok(mapping_copy, "::");
map_host = strtok(NULL, "::");
if (!map_mapped || !map_host) {
if (error_buf)
snprintf(error_buf, error_buf_size,
"error while pre-opening mapped directory: "
"invalid map\n");
if (mapping_copy != mapping_copy_buf)
wasm_runtime_free(mapping_copy);
goto fail;
}
path = os_realpath(map_host, resolved_path);
if (!path) {
if (error_buf)
snprintf(error_buf, error_buf_size,
"error while pre-opening mapped directory %s: %d\n",
map_host, errno);
if (mapping_copy != mapping_copy_buf)
wasm_runtime_free(mapping_copy);
goto fail;
}
__wasi_errno_t error = os_open_preopendir(path, &file_handle);
if (error != __WASI_ESUCCESS) {
if (error_buf)
snprintf(error_buf, error_buf_size,
"error while pre-opening mapped directory %s: %d\n",
map_host, errno);
if (mapping_copy != mapping_copy_buf)
wasm_runtime_free(mapping_copy);
goto fail;
}
if (!fd_table_insert_existing(curfds, wasm_fd, file_handle, false)
|| !fd_prestats_insert(prestats, map_mapped, wasm_fd)) {
if (error_buf)
snprintf(error_buf, error_buf_size,
"error while pre-opening mapped directory %s: "
"insertion failed\n",
dir_list[i]);
if (mapping_copy != mapping_copy_buf)
wasm_runtime_free(mapping_copy);
goto fail;
}
if (mapping_copy != mapping_copy_buf)
wasm_runtime_free(mapping_copy);
}
/* addr_pool(textual) -> apool */
for (i = 0; i < addr_pool_size; i++) {
char *cp, *address, *mask;
@ -4361,10 +4429,12 @@ static V128FuncPtr invokeNative_V128 = (V128FuncPtr)(uintptr_t)invokeNative;
|| defined(BUILD_TARGET_RISCV64_LP64) */
#endif /* end of defined(_WIN32) || defined(_WIN32_) */
/* ASAN is not designed to work with custom stack unwind or other low-level \
things. > Ignore a function that does some low-level magic. (e.g. walking \
through the thread's stack bypassing the frame boundaries) */
#if defined(__GNUC__)
/*
* ASAN is not designed to work with custom stack unwind or other low-level
* things. Ignore a function that does some low-level magic. (e.g. walking
* through the thread's stack bypassing the frame boundaries)
*/
#if defined(__GNUC__) || defined(__clang__)
__attribute__((no_sanitize_address))
#endif
bool

View File

@ -12,6 +12,7 @@
#include "wasm_native.h"
#include "../include/wasm_export.h"
#include "../interpreter/wasm.h"
#if WASM_ENABLE_LIBC_WASI != 0
#if WASM_ENABLE_UVWASI == 0
#include "posix.h"
@ -43,15 +44,16 @@ extern "C" {
/* For STORE opcodes */
#define STORE_I64 PUT_I64_TO_ADDR
#define STORE_U32(addr, value) \
do { \
*(uint32 *)(addr) = (uint32)(value); \
} while (0)
#define STORE_U16(addr, value) \
do { \
*(uint16 *)(addr) = (uint16)(value); \
} while (0)
static inline void
STORE_U32(void *addr, uint32_t value)
{
*(uint32_t *)(addr) = (uint32_t)(value);
}
static inline void
STORE_U16(void *addr, uint16_t value)
{
*(uint16_t *)(addr) = (uint16_t)(value);
}
/* For LOAD opcodes */
#define LOAD_I64(addr) (*(int64 *)(addr))
#define LOAD_F64(addr) (*(float64 *)(addr))
@ -146,42 +148,42 @@ GET_F64_FROM_ADDR(uint32 *addr)
} \
} while (0)
#define STORE_U32(addr, value) \
do { \
uintptr_t addr_ = (uintptr_t)(addr); \
union { \
uint32 val; \
uint16 u16[2]; \
uint8 u8[4]; \
} u; \
if ((addr_ & (uintptr_t)3) == 0) \
*(uint32 *)(addr) = (uint32)(value); \
else { \
u.val = (uint32)(value); \
if ((addr_ & (uintptr_t)1) == 0) { \
((uint16 *)(addr))[0] = u.u16[0]; \
((uint16 *)(addr))[1] = u.u16[1]; \
} \
else { \
((uint8 *)(addr))[0] = u.u8[0]; \
((uint8 *)(addr))[1] = u.u8[1]; \
((uint8 *)(addr))[2] = u.u8[2]; \
((uint8 *)(addr))[3] = u.u8[3]; \
} \
} \
} while (0)
#define STORE_U16(addr, value) \
do { \
union { \
uint16 val; \
uint8 u8[2]; \
} u; \
u.val = (uint16)(value); \
((uint8 *)(addr))[0] = u.u8[0]; \
((uint8 *)(addr))[1] = u.u8[1]; \
} while (0)
static inline void
STORE_U32(void *addr, uint32_t value)
{
uintptr_t addr_ = (uintptr_t)(addr);
union {
uint32_t val;
uint16_t u16[2];
uint8_t u8[4];
} u;
if ((addr_ & (uintptr_t)3) == 0)
*(uint32_t *)(addr) = (uint32_t)(value);
else {
u.val = (uint32_t)(value);
if ((addr_ & (uintptr_t)1) == 0) {
((uint16_t *)(addr))[0] = u.u16[0];
((uint16_t *)(addr))[1] = u.u16[1];
}
else {
((uint8_t *)(addr))[0] = u.u8[0];
((uint8_t *)(addr))[1] = u.u8[1];
((uint8_t *)(addr))[2] = u.u8[2];
((uint8_t *)(addr))[3] = u.u8[3];
}
}
}
static inline void
STORE_U16(void *addr, uint16_t value)
{
union {
uint16_t val;
uint8_t u8[2];
} u;
u.val = (uint16_t)(value);
((uint8_t *)(addr))[0] = u.u8[0];
((uint8_t *)(addr))[1] = u.u8[1];
}
/* For LOAD opcodes */
static inline int64
LOAD_I64(void *addr)
@ -297,6 +299,14 @@ LOAD_I16(void *addr)
#endif /* WASM_CPU_SUPPORTS_UNALIGNED_ADDR_ACCESS != 0 */
#if WASM_ENABLE_SHARED_MEMORY != 0
#define SHARED_MEMORY_LOCK(memory) shared_memory_lock(memory)
#define SHARED_MEMORY_UNLOCK(memory) shared_memory_unlock(memory)
#else
#define SHARED_MEMORY_LOCK(memory) (void)0
#define SHARED_MEMORY_UNLOCK(memory) (void)0
#endif
typedef struct WASMModuleCommon {
/* Module type, for module loaded from WASM bytecode binary,
this field is Wasm_Module_Bytecode, and this structure should

View File

@ -18,7 +18,7 @@
* - If you care performance, it's better to make the interpreters
* use atomic ops.
*/
static korp_mutex _shared_memory_lock;
korp_mutex g_shared_memory_lock;
/* clang-format off */
enum {
@ -55,13 +55,13 @@ destroy_wait_info(void *wait_info);
bool
wasm_shared_memory_init()
{
if (os_mutex_init(&_shared_memory_lock) != 0)
if (os_mutex_init(&g_shared_memory_lock) != 0)
return false;
/* wait map not exists, create new map */
if (!(wait_map = bh_hash_map_create(32, true, (HashFunc)wait_address_hash,
(KeyEqualFunc)wait_address_equal, NULL,
destroy_wait_info))) {
os_mutex_destroy(&_shared_memory_lock);
os_mutex_destroy(&g_shared_memory_lock);
return false;
}
return true;
@ -71,79 +71,47 @@ void
wasm_shared_memory_destroy()
{
bh_hash_map_destroy(wait_map);
os_mutex_destroy(&_shared_memory_lock);
os_mutex_destroy(&g_shared_memory_lock);
}
uint32
uint16
shared_memory_inc_reference(WASMMemoryInstance *memory)
{
bh_assert(shared_memory_is_shared(memory));
uint32 old;
#if BH_ATOMIC_32_IS_ATOMIC == 0
os_mutex_lock(&_shared_memory_lock);
uint16 old;
#if BH_ATOMIC_16_IS_ATOMIC == 0
os_mutex_lock(&g_shared_memory_lock);
#endif
old = BH_ATOMIC_32_FETCH_ADD(memory->ref_count, 1);
#if BH_ATOMIC_32_IS_ATOMIC == 0
os_mutex_unlock(&_shared_memory_lock);
old = BH_ATOMIC_16_FETCH_ADD(memory->ref_count, 1);
#if BH_ATOMIC_16_IS_ATOMIC == 0
os_mutex_unlock(&g_shared_memory_lock);
#endif
bh_assert(old >= 1);
bh_assert(old < UINT32_MAX);
bh_assert(old < UINT16_MAX);
return old + 1;
}
uint32
uint16
shared_memory_dec_reference(WASMMemoryInstance *memory)
{
bh_assert(shared_memory_is_shared(memory));
uint32 old;
#if BH_ATOMIC_32_IS_ATOMIC == 0
os_mutex_lock(&_shared_memory_lock);
uint16 old;
#if BH_ATOMIC_16_IS_ATOMIC == 0
os_mutex_lock(&g_shared_memory_lock);
#endif
old = BH_ATOMIC_32_FETCH_SUB(memory->ref_count, 1);
#if BH_ATOMIC_32_IS_ATOMIC == 0
os_mutex_unlock(&_shared_memory_lock);
old = BH_ATOMIC_16_FETCH_SUB(memory->ref_count, 1);
#if BH_ATOMIC_16_IS_ATOMIC == 0
os_mutex_unlock(&g_shared_memory_lock);
#endif
bh_assert(old > 0);
return old - 1;
}
bool
shared_memory_is_shared(WASMMemoryInstance *memory)
{
uint32 old;
#if BH_ATOMIC_32_IS_ATOMIC == 0
os_mutex_lock(&_shared_memory_lock);
#endif
old = BH_ATOMIC_32_LOAD(memory->ref_count);
#if BH_ATOMIC_32_IS_ATOMIC == 0
os_mutex_unlock(&_shared_memory_lock);
#endif
return old > 0;
}
static korp_mutex *
shared_memory_get_lock_pointer(WASMMemoryInstance *memory)
{
bh_assert(memory != NULL);
return &_shared_memory_lock;
}
void
shared_memory_lock(WASMMemoryInstance *memory)
{
/*
* Note: exception logic is currently abusing this lock.
* cf. https://github.com/bytecodealliance/wasm-micro-runtime/issues/2407
*/
bh_assert(memory != NULL);
os_mutex_lock(&_shared_memory_lock);
}
void
shared_memory_unlock(WASMMemoryInstance *memory)
{
bh_assert(memory != NULL);
os_mutex_unlock(&_shared_memory_lock);
return &g_shared_memory_lock;
}
/* Atomics wait && notify APIs */
@ -301,12 +269,15 @@ wasm_runtime_atomic_wait(WASMModuleInstanceCommon *module, void *address,
return -1;
}
shared_memory_lock(module_inst->memories[0]);
if ((uint8 *)address < module_inst->memories[0]->memory_data
|| (uint8 *)address + (wait64 ? 8 : 4)
> module_inst->memories[0]->memory_data_end) {
shared_memory_unlock(module_inst->memories[0]);
wasm_runtime_set_exception(module, "out of bounds memory access");
return -1;
}
shared_memory_unlock(module_inst->memories[0]);
#if WASM_ENABLE_THREAD_MGR != 0
exec_env =
@ -423,9 +394,11 @@ wasm_runtime_atomic_notify(WASMModuleInstanceCommon *module, void *address,
bh_assert(module->module_type == Wasm_Module_Bytecode
|| module->module_type == Wasm_Module_AoT);
shared_memory_lock(module_inst->memories[0]);
out_of_bounds =
((uint8 *)address < module_inst->memories[0]->memory_data
|| (uint8 *)address + 4 > module_inst->memories[0]->memory_data_end);
shared_memory_unlock(module_inst->memories[0]);
if (out_of_bounds) {
wasm_runtime_set_exception(module, "out of bounds memory access");

View File

@ -14,26 +14,39 @@
extern "C" {
#endif
extern korp_mutex g_shared_memory_lock;
bool
wasm_shared_memory_init();
void
wasm_shared_memory_destroy();
uint32
uint16
shared_memory_inc_reference(WASMMemoryInstance *memory);
uint32
uint16
shared_memory_dec_reference(WASMMemoryInstance *memory);
bool
shared_memory_is_shared(WASMMemoryInstance *memory);
#define shared_memory_is_shared(memory) memory->is_shared_memory
void
shared_memory_lock(WASMMemoryInstance *memory);
#define shared_memory_lock(memory) \
do { \
/* \
* Note: exception logic is currently abusing this lock. \
* cf. \
* https://github.com/bytecodealliance/wasm-micro-runtime/issues/2407 \
*/ \
bh_assert(memory != NULL); \
if (memory->is_shared_memory) \
os_mutex_lock(&g_shared_memory_lock); \
} while (0)
void
shared_memory_unlock(WASMMemoryInstance *memory);
#define shared_memory_unlock(memory) \
do { \
if (memory->is_shared_memory) \
os_mutex_unlock(&g_shared_memory_lock); \
} while (0)
uint32
wasm_runtime_atomic_wait(WASMModuleInstanceCommon *module, void *address,