From 471cac47194e3145c33229c9682d9812f3b0d194 Mon Sep 17 00:00:00 2001 From: Xu Jun <693788454@qq.com> Date: Sat, 25 Jun 2022 21:38:43 +0800 Subject: [PATCH 1/3] Enable dump call stack to a buffer (#1244) Enable dump call stack to a buffer, use API `wasm_runtime_get_call_stack_buf_size` to get the required buffer size and use API `wasm_runtime_dump_call_stack_to_buf` to dump call stack to a buffer --- core/iwasm/aot/aot_runtime.c | 101 +++++++++++++++---- core/iwasm/aot/aot_runtime.h | 20 +++- core/iwasm/common/wasm_runtime_common.c | 69 ++++++++++++- core/iwasm/common/wasm_runtime_common.h | 23 +++++ core/iwasm/include/wasm_export.h | 37 ++++++- core/iwasm/interpreter/wasm_interp_classic.c | 4 +- core/iwasm/interpreter/wasm_interp_fast.c | 4 +- core/iwasm/interpreter/wasm_runtime.c | 94 ++++++++++++++--- core/iwasm/interpreter/wasm_runtime.h | 21 +++- 9 files changed, 327 insertions(+), 46 deletions(-) diff --git a/core/iwasm/aot/aot_runtime.c b/core/iwasm/aot/aot_runtime.c index 606ffa05c..64024ce07 100644 --- a/core/iwasm/aot/aot_runtime.c +++ b/core/iwasm/aot/aot_runtime.c @@ -1511,7 +1511,9 @@ aot_call_function(WASMExecEnv *exec_env, AOTFunctionInstance *function, #if WASM_ENABLE_DUMP_CALL_STACK != 0 if (!ret) { - aot_dump_call_stack(exec_env); + if (aot_create_call_stack(exec_env)) { + aot_dump_call_stack(exec_env, true, NULL, 0); + } } #endif @@ -1568,7 +1570,9 @@ aot_call_function(WASMExecEnv *exec_env, AOTFunctionInstance *function, #if WASM_ENABLE_DUMP_CALL_STACK != 0 if (aot_get_exception(module_inst)) { - aot_dump_call_stack(exec_env); + if (aot_create_call_stack(exec_env)) { + aot_dump_call_stack(exec_env, true, NULL, 0); + } } #endif @@ -3018,38 +3022,24 @@ aot_free_frame(WASMExecEnv *exec_env) || (WASM_ENABLE_PERF_PROFILING != 0) */ #if WASM_ENABLE_DUMP_CALL_STACK != 0 -void -aot_dump_call_stack(WASMExecEnv *exec_env) +bool +aot_create_call_stack(struct WASMExecEnv *exec_env) { AOTFrame *cur_frame = (AOTFrame *)exec_env->cur_frame, *first_frame = cur_frame; AOTModuleInstance *module_inst = (AOTModuleInstance *)exec_env->module_inst; - const char *func_name; uint32 n = 0; - os_printf("\n"); while (cur_frame) { - func_name = - get_func_name_from_index(module_inst, cur_frame->func_index); - - /* function name not exported, print number instead */ - if (func_name == NULL) { - os_printf("#%02d $f%d \n", n, cur_frame->func_index); - } - else { - os_printf("#%02d %s \n", n, func_name); - } - cur_frame = cur_frame->prev_frame; n++; } - os_printf("\n"); /* release previous stack frames and create new ones */ if (!bh_vector_destroy(module_inst->frames.ptr) || !bh_vector_init(module_inst->frames.ptr, n, sizeof(WASMCApiFrame), false)) { - return; + return false; } cur_frame = first_frame; @@ -3059,14 +3049,85 @@ aot_dump_call_stack(WASMExecEnv *exec_env) frame.module_offset = 0; frame.func_index = cur_frame->func_index; frame.func_offset = 0; + frame.func_name_wp = + get_func_name_from_index(module_inst, cur_frame->func_index); if (!bh_vector_append(module_inst->frames.ptr, &frame)) { bh_vector_destroy(module_inst->frames.ptr); - return; + return false; } cur_frame = cur_frame->prev_frame; } + + return true; +} + +#define PRINT_OR_DUMP() \ + do { \ + total_len += \ + wasm_runtime_dump_line_buf_impl(line_buf, print, &buf, &len); \ + if ((!print) && buf && (len == 0)) { \ + return total_len; \ + } \ + } while (0) + +uint32 +aot_dump_call_stack(WASMExecEnv *exec_env, bool print, char *buf, uint32 len) +{ + AOTModuleInstance *module_inst = (AOTModuleInstance *)exec_env->module_inst; + uint32 n = 0, total_len = 0, total_frames; + /* reserve 256 bytes for line buffer, any line longer than 256 bytes + * will be truncated */ + char line_buf[256]; + + if (!module_inst->frames.ptr) { + return 0; + } + + total_frames = bh_vector_size(module_inst->frames.ptr); + if (total_frames == 0) { + return 0; + } + + snprintf(line_buf, sizeof(line_buf), "\n"); + PRINT_OR_DUMP(); + + while (n < total_frames) { + WASMCApiFrame frame = { 0 }; + uint32 line_length, i; + + if (!bh_vector_get(module_inst->frames.ptr, n, &frame)) { + return 0; + } + + /* function name not exported, print number instead */ + if (frame.func_name_wp == NULL) { + line_length = snprintf(line_buf, sizeof(line_buf), "#%02d $f%d\n", + n, frame.func_index); + } + else { + line_length = snprintf(line_buf, sizeof(line_buf), "#%02d %s\n", n, + frame.func_name_wp); + } + + if (line_length >= sizeof(line_buf)) { + uint32 line_buffer_len = sizeof(line_buf); + /* If line too long, ensure the last character is '\n' */ + for (i = line_buffer_len - 5; i < line_buffer_len - 2; i++) { + line_buf[i] = '.'; + } + line_buf[line_buffer_len - 2] = '\n'; + } + + PRINT_OR_DUMP(); + + n++; + } + snprintf(line_buf, sizeof(line_buf), "\n"); + PRINT_OR_DUMP(); + + return total_len + 1; } #endif /* end of WASM_ENABLE_DUMP_CALL_STACK */ diff --git a/core/iwasm/aot/aot_runtime.h b/core/iwasm/aot/aot_runtime.h index 0aa4edeae..c3838b585 100644 --- a/core/iwasm/aot/aot_runtime.h +++ b/core/iwasm/aot/aot_runtime.h @@ -731,8 +731,24 @@ aot_alloc_frame(WASMExecEnv *exec_env, uint32 func_index); void aot_free_frame(WASMExecEnv *exec_env); -void -aot_dump_call_stack(WASMExecEnv *exec_env); +bool +aot_create_call_stack(struct WASMExecEnv *exec_env); + +/** + * @brief Dump wasm call stack or get the size + * + * @param exec_env the execution environment + * @param print whether to print to stdout or not + * @param buf buffer to store the dumped content + * @param len length of the buffer + * + * @return when print is true, return the bytes printed out to stdout; when + * print is false and buf is NULL, return the size required to store the + * callstack content; when print is false and buf is not NULL, return the size + * dumped to the buffer, 0 means error and data in buf may be invalid + */ +uint32 +aot_dump_call_stack(WASMExecEnv *exec_env, bool print, char *buf, uint32 len); void aot_dump_perf_profiling(const AOTModuleInstance *module_inst); diff --git a/core/iwasm/common/wasm_runtime_common.c b/core/iwasm/common/wasm_runtime_common.c index ca8d02d25..cd1d56d04 100644 --- a/core/iwasm/common/wasm_runtime_common.c +++ b/core/iwasm/common/wasm_runtime_common.c @@ -4527,6 +4527,30 @@ wasm_externref_retain(uint32 externref_idx) #endif /* end of WASM_ENABLE_REF_TYPES */ #if WASM_ENABLE_DUMP_CALL_STACK != 0 +uint32 +wasm_runtime_dump_line_buf_impl(const char *line_buf, bool dump_or_print, + char **buf, uint32 *len) +{ + if (dump_or_print) { + return (uint32)os_printf("%s", line_buf); + } + else if (*buf) { + uint32 dump_len; + + dump_len = snprintf(*buf, *len, "%s", line_buf); + if (dump_len >= *len) { + dump_len = *len; + } + + *len = *len - dump_len; + *buf = *buf + dump_len; + return dump_len; + } + else { + return strlen(line_buf); + } +} + void wasm_runtime_dump_call_stack(WASMExecEnv *exec_env) { @@ -4534,15 +4558,56 @@ wasm_runtime_dump_call_stack(WASMExecEnv *exec_env) wasm_exec_env_get_module_inst(exec_env); #if WASM_ENABLE_INTERP != 0 if (module_inst->module_type == Wasm_Module_Bytecode) { - wasm_interp_dump_call_stack(exec_env); + wasm_interp_dump_call_stack(exec_env, true, NULL, 0); } #endif #if WASM_ENABLE_AOT != 0 if (module_inst->module_type == Wasm_Module_AoT) { - aot_dump_call_stack(exec_env); + aot_dump_call_stack(exec_env, true, NULL, 0); } #endif } + +uint32 +wasm_runtime_get_call_stack_buf_size(wasm_exec_env_t exec_env) +{ + WASMModuleInstanceCommon *module_inst = + wasm_exec_env_get_module_inst(exec_env); + +#if WASM_ENABLE_INTERP != 0 + if (module_inst->module_type == Wasm_Module_Bytecode) { + return wasm_interp_dump_call_stack(exec_env, false, NULL, 0); + } +#endif +#if WASM_ENABLE_AOT != 0 + if (module_inst->module_type == Wasm_Module_AoT) { + return aot_dump_call_stack(exec_env, false, NULL, 0); + } +#endif + + return 0; +} + +uint32 +wasm_runtime_dump_call_stack_to_buf(wasm_exec_env_t exec_env, char *buf, + uint32 len) +{ + WASMModuleInstanceCommon *module_inst = + wasm_exec_env_get_module_inst(exec_env); + +#if WASM_ENABLE_INTERP != 0 + if (module_inst->module_type == Wasm_Module_Bytecode) { + return wasm_interp_dump_call_stack(exec_env, false, buf, len); + } +#endif +#if WASM_ENABLE_AOT != 0 + if (module_inst->module_type == Wasm_Module_AoT) { + return aot_dump_call_stack(exec_env, false, buf, len); + } +#endif + + return 0; +} #endif /* end of WASM_ENABLE_DUMP_CALL_STACK */ bool diff --git a/core/iwasm/common/wasm_runtime_common.h b/core/iwasm/common/wasm_runtime_common.h index 7ef8f69c1..87a2e4aaf 100644 --- a/core/iwasm/common/wasm_runtime_common.h +++ b/core/iwasm/common/wasm_runtime_common.h @@ -404,6 +404,7 @@ typedef struct wasm_frame_t { uint32 module_offset; uint32 func_index; uint32 func_offset; + const char *func_name_wp; } WASMCApiFrame; /* See wasm_export.h for description */ @@ -803,6 +804,28 @@ void wasm_externref_cleanup(WASMModuleInstanceCommon *module_inst); #endif /* end of WASM_ENABLE_REF_TYPES */ +#if WASM_ENABLE_DUMP_CALL_STACK != 0 +/** + * @brief Internal implementation for dumping or printing callstack line + * + * @note if dump_or_print is true, then print to stdout directly; + * if dump_or_print is false, but *buf is NULL, then return the length of the + * line; + * if dump_or_print is false, and *buf is not NULL, then dump content to + * the memory pointed by *buf, and adjust *buf and *len according to actual + * bytes dumped, and return the actual dumped length + * + * @param line_buf current line to dump or print + * @param dump_or_print whether to print to stdout or dump to buf + * @param buf [INOUT] pointer to the buffer + * @param len [INOUT] pointer to remaining length + * @return bytes printed to stdout or dumped to buf + */ +uint32 +wasm_runtime_dump_line_buf_impl(const char *line_buf, bool dump_or_print, + char **buf, uint32 *len); +#endif /* end of WASM_ENABLE_DUMP_CALL_STACK != 0 */ + /* Get module of the current exec_env */ WASMModuleCommon * wasm_exec_env_get_module(WASMExecEnv *exec_env); diff --git a/core/iwasm/include/wasm_export.h b/core/iwasm/include/wasm_export.h index 9b1481d72..ed7a865b8 100644 --- a/core/iwasm/include/wasm_export.h +++ b/core/iwasm/include/wasm_export.h @@ -919,6 +919,7 @@ wasm_runtime_get_function_attachment(wasm_exec_env_t exec_env); */ WASM_RUNTIME_API_EXTERN void wasm_runtime_set_user_data(wasm_exec_env_t exec_env, void *user_data); + /** * Get the user data within execution environment. * @@ -963,7 +964,7 @@ WASM_RUNTIME_API_EXTERN void wasm_runtime_set_max_thread_num(uint32_t num); /** - * spawn a new exec_env, the spawned exec_env + * Spawn a new exec_env, the spawned exec_env * can be used in other threads * * @param num the original exec_env @@ -982,7 +983,7 @@ WASM_RUNTIME_API_EXTERN void wasm_runtime_destroy_spawned_exec_env(wasm_exec_env_t exec_env); /** - * spawn a thread from the given exec_env + * Spawn a thread from the given exec_env * * @param exec_env the original exec_env * @param tid thread id to be returned to the caller @@ -996,7 +997,7 @@ wasm_runtime_spawn_thread(wasm_exec_env_t exec_env, wasm_thread_t *tid, wasm_thread_callback_t callback, void *arg); /** - * waits a spawned thread to terminate + * Waits a spawned thread to terminate * * @param tid thread id * @param retval if not NULL, output the return value of the thread @@ -1046,13 +1047,41 @@ WASM_RUNTIME_API_EXTERN bool wasm_externref_retain(uint32_t externref_idx); /** - * dump the call stack + * Dump the call stack to stdout * * @param exec_env the execution environment */ WASM_RUNTIME_API_EXTERN void wasm_runtime_dump_call_stack(wasm_exec_env_t exec_env); +/** + * Get the size required to store the call stack contents, including + * the space for terminating null byte ('\0') + * + * @param exec_env the execution environment + * + * @return size required to store the contents, 0 means error + */ +WASM_RUNTIME_API_EXTERN uint32_t +wasm_runtime_get_call_stack_buf_size(wasm_exec_env_t exec_env); + +/** + * Dump the call stack to buffer. + * + * @note this function is not thread-safe, please only use this API + * when the exec_env is not executing + * + * @param exec_env the execution environment + * @param buf buffer to store the dumped content + * @param len length of the buffer + * + * @return bytes dumped to the buffer, including the terminating null + * byte ('\0'), 0 means error and data in buf may be invalid + */ +WASM_RUNTIME_API_EXTERN uint32_t +wasm_runtime_dump_call_stack_to_buf(wasm_exec_env_t exec_env, char *buf, + uint32_t len); + /** * Get a custom section by name * diff --git a/core/iwasm/interpreter/wasm_interp_classic.c b/core/iwasm/interpreter/wasm_interp_classic.c index 0c97df44d..7510698eb 100644 --- a/core/iwasm/interpreter/wasm_interp_classic.c +++ b/core/iwasm/interpreter/wasm_interp_classic.c @@ -3834,7 +3834,9 @@ wasm_interp_call_wasm(WASMModuleInstance *module_inst, WASMExecEnv *exec_env, } else { #if WASM_ENABLE_DUMP_CALL_STACK != 0 - wasm_interp_dump_call_stack(exec_env); + if (wasm_interp_create_call_stack(exec_env)) { + wasm_interp_dump_call_stack(exec_env, true, NULL, 0); + } #endif LOG_DEBUG("meet an exception %s", wasm_get_exception(module_inst)); } diff --git a/core/iwasm/interpreter/wasm_interp_fast.c b/core/iwasm/interpreter/wasm_interp_fast.c index b64609d7a..45e8401bc 100644 --- a/core/iwasm/interpreter/wasm_interp_fast.c +++ b/core/iwasm/interpreter/wasm_interp_fast.c @@ -3847,7 +3847,9 @@ wasm_interp_call_wasm(WASMModuleInstance *module_inst, WASMExecEnv *exec_env, } else { #if WASM_ENABLE_DUMP_CALL_STACK != 0 - wasm_interp_dump_call_stack(exec_env); + if (wasm_interp_create_call_stack(exec_env)) { + wasm_interp_dump_call_stack(exec_env, true, NULL, 0); + } #endif } diff --git a/core/iwasm/interpreter/wasm_runtime.c b/core/iwasm/interpreter/wasm_runtime.c index c6b77f0a7..deba92dca 100644 --- a/core/iwasm/interpreter/wasm_runtime.c +++ b/core/iwasm/interpreter/wasm_runtime.c @@ -2485,8 +2485,8 @@ wasm_get_module_inst_mem_consumption(const WASMModuleInstance *module_inst, || (WASM_ENABLE_MEMORY_TRACING != 0) */ #if WASM_ENABLE_DUMP_CALL_STACK != 0 -void -wasm_interp_dump_call_stack(struct WASMExecEnv *exec_env) +bool +wasm_interp_create_call_stack(struct WASMExecEnv *exec_env) { WASMModuleInstance *module_inst = (WASMModuleInstance *)wasm_exec_env_get_module_inst(exec_env); @@ -2507,12 +2507,12 @@ wasm_interp_dump_call_stack(struct WASMExecEnv *exec_env) if (!bh_vector_destroy(module_inst->frames) || !bh_vector_init(module_inst->frames, n, sizeof(WASMCApiFrame), false)) { - return; + return false; } cur_frame = first_frame; n = 0; - os_printf("\n"); + while (cur_frame) { WASMCApiFrame frame = { 0 }; WASMFunctionInstance *func_inst = cur_frame->function; @@ -2560,20 +2560,86 @@ wasm_interp_dump_call_stack(struct WASMExecEnv *exec_env) } } - /* function name not exported, print number instead */ - if (func_name == NULL) { - os_printf("#%02d $f%d \n", n, func_inst - module_inst->functions); - } - else { - os_printf("#%02d %s \n", n, func_name); - } + frame.func_name_wp = func_name; - /* keep print */ - bh_vector_append(module_inst->frames, &frame); + if (!bh_vector_append(module_inst->frames, &frame)) { + bh_vector_destroy(module_inst->frames); + return false; + } cur_frame = cur_frame->prev_frame; n++; } - os_printf("\n"); + + return true; +} + +#define PRINT_OR_DUMP() \ + do { \ + total_len += \ + wasm_runtime_dump_line_buf_impl(line_buf, print, &buf, &len); \ + if ((!print) && buf && (len == 0)) { \ + return total_len; \ + } \ + } while (0) + +uint32 +wasm_interp_dump_call_stack(struct WASMExecEnv *exec_env, bool print, char *buf, + uint32 len) +{ + WASMModuleInstance *module_inst = + (WASMModuleInstance *)wasm_exec_env_get_module_inst(exec_env); + uint32 n = 0, total_len = 0, total_frames; + /* reserve 256 bytes for line buffer, any line longer than 256 bytes + * will be truncated */ + char line_buf[256]; + + if (!module_inst->frames) { + return 0; + } + + total_frames = bh_vector_size(module_inst->frames); + if (total_frames == 0) { + return 0; + } + + snprintf(line_buf, sizeof(line_buf), "\n"); + PRINT_OR_DUMP(); + + while (n < total_frames) { + WASMCApiFrame frame = { 0 }; + uint32 line_length, i; + + if (!bh_vector_get(module_inst->frames, n, &frame)) { + return 0; + } + + /* function name not exported, print number instead */ + if (frame.func_name_wp == NULL) { + line_length = snprintf(line_buf, sizeof(line_buf), "#%02d $f%d\n", + n, frame.func_index); + } + else { + line_length = snprintf(line_buf, sizeof(line_buf), "#%02d %s\n", n, + frame.func_name_wp); + } + + if (line_length >= sizeof(line_buf)) { + uint32 line_buffer_len = sizeof(line_buf); + /* If line too long, ensure the last character is '\n' */ + for (i = line_buffer_len - 5; i < line_buffer_len - 2; i++) { + line_buf[i] = '.'; + } + line_buf[line_buffer_len - 2] = '\n'; + } + + PRINT_OR_DUMP(); + + n++; + } + snprintf(line_buf, sizeof(line_buf), "\n"); + PRINT_OR_DUMP(); + + return total_len + 1; } #endif /* end of WASM_ENABLE_DUMP_CALL_STACK */ diff --git a/core/iwasm/interpreter/wasm_runtime.h b/core/iwasm/interpreter/wasm_runtime.h index ccdf538aa..c780e6a11 100644 --- a/core/iwasm/interpreter/wasm_runtime.h +++ b/core/iwasm/interpreter/wasm_runtime.h @@ -432,8 +432,25 @@ wasm_get_table_inst(const WASMModuleInstance *module_inst, const uint32 tbl_idx) } #if WASM_ENABLE_DUMP_CALL_STACK != 0 -void -wasm_interp_dump_call_stack(struct WASMExecEnv *exec_env); +bool +wasm_interp_create_call_stack(struct WASMExecEnv *exec_env); + +/** + * @brief Dump wasm call stack or get the size + * + * @param exec_env the execution environment + * @param print whether to print to stdout or not + * @param buf buffer to store the dumped content + * @param len length of the buffer + * + * @return when print is true, return the bytes printed out to stdout; when + * print is false and buf is NULL, return the size required to store the + * callstack content; when print is false and buf is not NULL, return the size + * dumped to the buffer, 0 means error and data in buf may be invalid + */ +uint32 +wasm_interp_dump_call_stack(struct WASMExecEnv *exec_env, bool print, char *buf, + uint32 len); #endif const uint8 * From 114bf9408bbfbf623cd6d7185393a49663e75213 Mon Sep 17 00:00:00 2001 From: Wenyong Huang Date: Sun, 26 Jun 2022 09:33:54 +0800 Subject: [PATCH 2/3] Fix get invokeNative float ret value issue with clang compiler (#1248) When using clang compiler, the f32/f64 return value might be invalid when calling invokeNative asm code. Declare the return type of invokeNative as void, and set volatile for the converted function pointers to resolve the issue. --- core/iwasm/common/wasm_runtime_common.c | 54 ++++++++++++------------- 1 file changed, 26 insertions(+), 28 deletions(-) diff --git a/core/iwasm/common/wasm_runtime_common.c b/core/iwasm/common/wasm_runtime_common.c index cd1d56d04..fea9987a3 100644 --- a/core/iwasm/common/wasm_runtime_common.c +++ b/core/iwasm/common/wasm_runtime_common.c @@ -3049,7 +3049,7 @@ fail: || defined(BUILD_TARGET_RISCV32_ILP32D) \ || defined(BUILD_TARGET_RISCV32_ILP32) || defined(BUILD_TARGET_ARC) typedef void (*GenericFunctionPointer)(); -int64 +void invokeNative(GenericFunctionPointer f, uint32 *args, uint32 n_stacks); typedef float64 (*Float64FuncPtr)(GenericFunctionPointer, uint32 *, uint32); @@ -3058,13 +3058,16 @@ typedef int64 (*Int64FuncPtr)(GenericFunctionPointer, uint32 *, uint32); typedef int32 (*Int32FuncPtr)(GenericFunctionPointer, uint32 *, uint32); typedef void (*VoidFuncPtr)(GenericFunctionPointer, uint32 *, uint32); -static Float64FuncPtr invokeNative_Float64 = +static volatile Float64FuncPtr invokeNative_Float64 = (Float64FuncPtr)(uintptr_t)invokeNative; -static Float32FuncPtr invokeNative_Float32 = +static volatile Float32FuncPtr invokeNative_Float32 = (Float32FuncPtr)(uintptr_t)invokeNative; -static Int64FuncPtr invokeNative_Int64 = (Int64FuncPtr)(uintptr_t)invokeNative; -static Int32FuncPtr invokeNative_Int32 = (Int32FuncPtr)(uintptr_t)invokeNative; -static VoidFuncPtr invokeNative_Void = (VoidFuncPtr)(uintptr_t)invokeNative; +static volatile Int64FuncPtr invokeNative_Int64 = + (Int64FuncPtr)(uintptr_t)invokeNative; +static volatile Int32FuncPtr invokeNative_Int32 = + (Int32FuncPtr)(uintptr_t)invokeNative; +static volatile VoidFuncPtr invokeNative_Void = + (VoidFuncPtr)(uintptr_t)invokeNative; #if defined(BUILD_TARGET_ARM_VFP) || defined(BUILD_TARGET_THUMB_VFP) #define MAX_REG_INTS 4 @@ -3520,7 +3523,7 @@ fail: || defined(BUILD_TARGET_THUMB) || defined(BUILD_TARGET_MIPS) \ || defined(BUILD_TARGET_XTENSA) typedef void (*GenericFunctionPointer)(); -int64 +void invokeNative(GenericFunctionPointer f, uint32 *args, uint32 sz); typedef float64 (*Float64FuncPtr)(GenericFunctionPointer f, uint32 *, uint32); @@ -3529,13 +3532,16 @@ typedef int64 (*Int64FuncPtr)(GenericFunctionPointer f, uint32 *, uint32); typedef int32 (*Int32FuncPtr)(GenericFunctionPointer f, uint32 *, uint32); typedef void (*VoidFuncPtr)(GenericFunctionPointer f, uint32 *, uint32); -static Int64FuncPtr invokeNative_Int64 = (Int64FuncPtr)invokeNative; -static Int32FuncPtr invokeNative_Int32 = (Int32FuncPtr)(uintptr_t)invokeNative; -static Float64FuncPtr invokeNative_Float64 = +static volatile Int64FuncPtr invokeNative_Int64 = + (Int64FuncPtr)(uintptr_t)invokeNative; +static volatile Int32FuncPtr invokeNative_Int32 = + (Int32FuncPtr)(uintptr_t)invokeNative; +static volatile Float64FuncPtr invokeNative_Float64 = (Float64FuncPtr)(uintptr_t)invokeNative; -static Float32FuncPtr invokeNative_Float32 = +static volatile Float32FuncPtr invokeNative_Float32 = (Float32FuncPtr)(uintptr_t)invokeNative; -static VoidFuncPtr invokeNative_Void = (VoidFuncPtr)(uintptr_t)invokeNative; +static volatile VoidFuncPtr invokeNative_Void = + (VoidFuncPtr)(uintptr_t)invokeNative; static inline void word_copy(uint32 *dest, uint32 *src, unsigned num) @@ -3762,19 +3768,8 @@ typedef uint32x4_t __m128i; #endif /* end of WASM_ENABLE_SIMD != 0 */ typedef void (*GenericFunctionPointer)(); -#if defined(__APPLE__) || defined(__MACH__) -/** - * Define the return type as 'void' in MacOS, since after converting - * 'int64 invokeNative' into 'float64 invokeNative_Float64', the - * return value passing might be invalid, the caller reads the return - * value from register rax but not xmm0. - */ void invokeNative(GenericFunctionPointer f, uint64 *args, uint64 n_stacks); -#else -int64 -invokeNative(GenericFunctionPointer f, uint64 *args, uint64 n_stacks); -#endif typedef float64 (*Float64FuncPtr)(GenericFunctionPointer, uint64 *, uint64); typedef float32 (*Float32FuncPtr)(GenericFunctionPointer, uint64 *, uint64); @@ -3782,13 +3777,16 @@ typedef int64 (*Int64FuncPtr)(GenericFunctionPointer, uint64 *, uint64); typedef int32 (*Int32FuncPtr)(GenericFunctionPointer, uint64 *, uint64); typedef void (*VoidFuncPtr)(GenericFunctionPointer, uint64 *, uint64); -static Float64FuncPtr invokeNative_Float64 = +static volatile Float64FuncPtr invokeNative_Float64 = (Float64FuncPtr)(uintptr_t)invokeNative; -static Float32FuncPtr invokeNative_Float32 = +static volatile Float32FuncPtr invokeNative_Float32 = (Float32FuncPtr)(uintptr_t)invokeNative; -static Int64FuncPtr invokeNative_Int64 = (Int64FuncPtr)(uintptr_t)invokeNative; -static Int32FuncPtr invokeNative_Int32 = (Int32FuncPtr)(uintptr_t)invokeNative; -static VoidFuncPtr invokeNative_Void = (VoidFuncPtr)(uintptr_t)invokeNative; +static volatile Int64FuncPtr invokeNative_Int64 = + (Int64FuncPtr)(uintptr_t)invokeNative; +static volatile Int32FuncPtr invokeNative_Int32 = + (Int32FuncPtr)(uintptr_t)invokeNative; +static volatile VoidFuncPtr invokeNative_Void = + (VoidFuncPtr)(uintptr_t)invokeNative; #if WASM_ENABLE_SIMD != 0 typedef v128 (*V128FuncPtr)(GenericFunctionPointer, uint64 *, uint64); From eb3cdaaf3206cbe7c0173b87c6a1bd553d8b5fa4 Mon Sep 17 00:00:00 2001 From: YAMAMOTO Takashi Date: Sun, 26 Jun 2022 11:06:34 +0900 Subject: [PATCH 3/3] Fix macro redifinition warning for NuttX (#1250) Fix the following warning introduced by the recent change. ``` In file included from wamr/core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/locking.h:17, from wamr/core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/posix.h:18, from wamr/core/iwasm/aot/../common/wasm_runtime_common.h:18, from wamr/core/iwasm/aot/aot_runtime.h:10, from wamr/core/iwasm/aot/aot_loader.c:6: wamr/core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/ssp_config.h:55: error: "CONFIG_HAS_ISATTY" redefined [-Werror] #define CONFIG_HAS_ISATTY 1 In file included from wamr/core/shared/utils/../platform/include/platform_common.h:13, from wamr/core/shared/utils/bh_platform.h:9, from wamr/core/iwasm/aot/aot_runtime.h:9, from wamr/core/iwasm/aot/aot_loader.c:6: wamr/core/shared/platform/nuttx/platform_internal.h:75: note: this is the location of the previous definition #define CONFIG_HAS_ISATTY 0 ``` --- .../libc-wasi/sandboxed-system-primitives/src/ssp_config.h | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/ssp_config.h b/core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/ssp_config.h index 5ffcb6b37..47b65ca82 100644 --- a/core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/ssp_config.h +++ b/core/iwasm/libraries/libc-wasi/sandboxed-system-primitives/src/ssp_config.h @@ -51,11 +51,17 @@ #define CONFIG_HAS_FDATASYNC 0 #endif +/* + * For NuttX, CONFIG_HAS_ISATTY is provided by its platform header. + * (platform_internal.h) + */ +#ifndef __NuttX__ #ifndef __CloudABI__ #define CONFIG_HAS_ISATTY 1 #else #define CONFIG_HAS_ISATTY 0 #endif +#endif #ifndef __APPLE__ #define CONFIG_HAS_POSIX_FALLOCATE 1