| diff --git a/core/iwasm/aot/aot_runtime.h b/core/iwasm/aot/aot_runtime.h | |
| index d06cd10..c9bf9ed 100644 | |
| --- a/core/iwasm/aot/aot_runtime.h | |
| +++ b/core/iwasm/aot/aot_runtime.h | |
| @@ -349,6 +349,13 @@ typedef struct AOTModule { | |
| /* Whether the underlying wasm binary buffer can be freed */ | |
| bool is_binary_freeable; | |
| + /* rive patch: artifact compiled without sw bounds checks, so exceptions | |
| + unwind through the exce_check guard page; sw artifacts unwind by | |
| + checked returns and must never take that longjmp. Set by the embedder | |
| + via wasm_runtime_set_module_hw_bounds; the file format records | |
| + nothing. */ | |
| + bool rive_hw_bounds; | |
| + | |
| /* `.data` sections merged into one mmaped to reduce the tlb cache miss */ | |
| uint8 *merged_data_sections; | |
| uint32 merged_data_sections_size; | |
| diff --git a/core/iwasm/common/wasm_runtime_common.c b/core/iwasm/common/wasm_runtime_common.c | |
| index 5853813..a5a2e24 100644 | |
| --- a/core/iwasm/common/wasm_runtime_common.c | |
| +++ b/core/iwasm/common/wasm_runtime_common.c | |
| @@ -2331,10 +2331,27 @@ wasm_runtime_set_native_stack_boundary(WASMExecEnv *exec_env, | |
| } | |
| #ifdef OS_ENABLE_HW_BOUND_CHECK | |
| +/* rive patch: only hw-bounds AOT artifacts unwind through the guard page; | |
| + sw artifacts emit checked returns after every call and a longjmp here | |
| + would skip native frames between nested wasm entries (the sjlj glue). */ | |
| +static bool | |
| +module_inst_uses_hw_unwind(WASMModuleInstanceCommon *module_inst) | |
| +{ | |
| +#if WASM_ENABLE_AOT != 0 | |
| + if (module_inst && module_inst->module_type == Wasm_Module_AoT) { | |
| + AOTModule *module = | |
| + (AOTModule *)((AOTModuleInstance *)module_inst)->module; | |
| + return module && module->rive_hw_bounds; | |
| + } | |
| +#endif | |
| + return false; | |
| +} | |
| + | |
| void | |
| wasm_runtime_access_exce_check_guard_page() | |
| { | |
| - if (exec_env_tls && exec_env_tls->handle == os_self_thread()) { | |
| + if (exec_env_tls && exec_env_tls->handle == os_self_thread() | |
| + && module_inst_uses_hw_unwind(exec_env_tls->module_inst)) { | |
| uint32 page_size = os_getpagesize(); | |
| memset(exec_env_tls->exce_check_guard_page, 0, page_size); | |
| } | |
| @@ -2350,6 +2367,19 @@ wasm_runtime_set_instruction_count_limit(WASMExecEnv *exec_env, | |
| } | |
| #endif | |
| +void | |
| +wasm_runtime_set_module_hw_bounds(WASMModuleCommon *module, bool hw_bounds) | |
| +{ | |
| +#if WASM_ENABLE_AOT != 0 | |
| + if (module && module->module_type == Wasm_Module_AoT) { | |
| + ((AOTModule *)module)->rive_hw_bounds = hw_bounds; | |
| + } | |
| +#else | |
| + (void)module; | |
| +#endif | |
| + (void)hw_bounds; | |
| +} | |
| + | |
| WASMFuncType * | |
| wasm_runtime_get_function_type(const WASMFunctionInstanceCommon *function, | |
| uint32 module_type) | |
| diff --git a/core/iwasm/include/wasm_export.h b/core/iwasm/include/wasm_export.h | |
| index 81efb8f..a510f3c 100644 | |
| --- a/core/iwasm/include/wasm_export.h | |
| +++ b/core/iwasm/include/wasm_export.h | |
| @@ -2287,6 +2287,13 @@ wasm_runtime_set_module_name(wasm_module_t module, const char *name, | |
| WASM_RUNTIME_API_EXTERN const char * | |
| wasm_runtime_get_module_name(wasm_module_t module); | |
| +/* rive patch: mark an AOT module as compiled without sw bounds checks | |
| + (wamrc --bounds-checks=0) so runtime exceptions unwind through the hw | |
| + trap guard page. Default false: sw artifacts unwind by checked returns. | |
| + The AOT file format records nothing, so the embedder must know. */ | |
| +WASM_RUNTIME_API_EXTERN void | |
| +wasm_runtime_set_module_hw_bounds(wasm_module_t module, bool hw_bounds); | |
| + | |
| /* | |
| * wasm_runtime_detect_native_stack_overflow | |
| * |