Implement post-MVP features and native stack overflow check (#243)
Implement native thread stack overflow check Implement post-MVP: Non-trapping float-to-int conversions Implement post-MVP: Sign-extension operators Enhance WASM loader checks
This commit is contained in:
@ -50,3 +50,12 @@ wasm_exec_env_get_module_inst(WASMExecEnv *exec_env)
|
||||
return exec_env->module_inst;
|
||||
}
|
||||
|
||||
void
|
||||
wasm_exec_env_set_thread_info(WASMExecEnv *exec_env)
|
||||
{
|
||||
exec_env->handle = os_self_thread();
|
||||
exec_env->native_stack_boundary = os_thread_get_stack_boundary()
|
||||
+ RESERVED_BYTES_TO_NATIVE_STACK_BOUNDARY;
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -20,12 +20,15 @@ struct WASMInterpFrame;
|
||||
|
||||
/* Execution environment */
|
||||
typedef struct WASMExecEnv {
|
||||
/* Next thread's exec env of a WASM module instance. */
|
||||
/* Next thread's exec env of a WASM module instance. */
|
||||
struct WASMExecEnv *next;
|
||||
|
||||
/* Previous thread's exec env of a WASM module instance. */
|
||||
/* Previous thread's exec env of a WASM module instance. */
|
||||
struct WASMExecEnv *prev;
|
||||
|
||||
/* Note: field module_inst, argv_buf and native_stack_boundary
|
||||
are used by AOTed code, don't change the places of them */
|
||||
|
||||
/* The WASM module instance of current thread */
|
||||
struct WASMModuleInstanceCommon *module_inst;
|
||||
|
||||
@ -33,6 +36,11 @@ typedef struct WASMExecEnv {
|
||||
uint32 *argv_buf;
|
||||
#endif
|
||||
|
||||
/* The boundary of native stack. When runtime detects that native
|
||||
frame may overrun this boundary, it throws stack overflow
|
||||
exception. */
|
||||
uint8 *native_stack_boundary;
|
||||
|
||||
/* attachment for native function */
|
||||
void *attachment;
|
||||
|
||||
@ -48,11 +56,6 @@ typedef struct WASMExecEnv {
|
||||
BlockAddr block_addr_cache[BLOCK_ADDR_CACHE_SIZE][BLOCK_ADDR_CONFLICT_SIZE];
|
||||
#endif
|
||||
|
||||
/* The boundary of native stack. When interpreter detects that native
|
||||
frame may overrun this boundary, it throws a stack overflow
|
||||
exception. */
|
||||
void *native_stack_boundary;
|
||||
|
||||
/* The WASM stack size */
|
||||
uint32 wasm_stack_size;
|
||||
|
||||
@ -61,13 +64,13 @@ typedef struct WASMExecEnv {
|
||||
uint64 __make_it_8_byte_aligned_;
|
||||
|
||||
struct {
|
||||
/* The top boundary of the stack. */
|
||||
/* The top boundary of the stack. */
|
||||
uint8 *top_boundary;
|
||||
|
||||
/* Top cell index which is free. */
|
||||
/* Top cell index which is free. */
|
||||
uint8 *top;
|
||||
|
||||
/* The Java stack. */
|
||||
/* The WASM stack. */
|
||||
uint8 bottom[1];
|
||||
} s;
|
||||
} wasm_stack;
|
||||
@ -159,6 +162,9 @@ wasm_exec_env_get_cur_frame(WASMExecEnv *exec_env)
|
||||
struct WASMModuleInstanceCommon *
|
||||
wasm_exec_env_get_module_inst(WASMExecEnv *exec_env);
|
||||
|
||||
void
|
||||
wasm_exec_env_set_thread_info(WASMExecEnv *exec_env);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -14,8 +14,10 @@ static NativeSymbolsList g_native_symbols_list_end = NULL;
|
||||
uint32
|
||||
get_libc_builtin_export_apis(NativeSymbol **p_libc_builtin_apis);
|
||||
|
||||
#if WASM_ENABLE_SPEC_TEST != 0
|
||||
uint32
|
||||
get_spectest_export_apis(NativeSymbol **p_libc_builtin_apis);
|
||||
#endif
|
||||
|
||||
uint32
|
||||
get_libc_wasi_export_apis(NativeSymbol **p_libc_wasi_apis);
|
||||
@ -242,11 +244,13 @@ wasm_native_init()
|
||||
native_symbols, n_native_symbols))
|
||||
return false;
|
||||
|
||||
#if WASM_ENABLE_SPEC_TEST
|
||||
n_native_symbols = get_spectest_export_apis(&native_symbols);
|
||||
if (!wasm_native_register_natives("spectest",
|
||||
native_symbols, n_native_symbols))
|
||||
return false;
|
||||
#endif
|
||||
#endif /* WASM_ENABLE_SPEC_TEST */
|
||||
#endif /* WASM_ENABLE_LIBC_BUILTIN */
|
||||
|
||||
#if WASM_ENABLE_LIBC_WASI != 0
|
||||
n_native_symbols = get_libc_wasi_export_apis(&native_symbols);
|
||||
|
||||
@ -292,7 +292,8 @@ wasm_runtime_call_wasm(WASMExecEnv *exec_env,
|
||||
return false;
|
||||
}
|
||||
|
||||
exec_env->handle = os_self_thread();
|
||||
/* set thread handle and stack boundary */
|
||||
wasm_exec_env_set_thread_info(exec_env);
|
||||
|
||||
#if WASM_ENABLE_INTERP != 0
|
||||
if (exec_env->module_inst->module_type == Wasm_Module_Bytecode)
|
||||
@ -1410,37 +1411,39 @@ wasm_application_execute_func(WASMModuleInstanceCommon *module_inst,
|
||||
}
|
||||
|
||||
/* print return value */
|
||||
switch (type->types[type->param_count]) {
|
||||
case VALUE_TYPE_I32:
|
||||
os_printf("0x%x:i32", argv1[0]);
|
||||
break;
|
||||
case VALUE_TYPE_I64:
|
||||
{
|
||||
union { uint64 val; uint32 parts[2]; } u;
|
||||
u.parts[0] = argv1[0];
|
||||
u.parts[1] = argv1[1];
|
||||
if (type->result_count > 0) {
|
||||
switch (type->types[type->param_count]) {
|
||||
case VALUE_TYPE_I32:
|
||||
os_printf("0x%x:i32", argv1[0]);
|
||||
break;
|
||||
case VALUE_TYPE_I64:
|
||||
{
|
||||
union { uint64 val; uint32 parts[2]; } u;
|
||||
u.parts[0] = argv1[0];
|
||||
u.parts[1] = argv1[1];
|
||||
#ifdef PRIx64
|
||||
os_printf("0x%"PRIx64":i64", u.val);
|
||||
os_printf("0x%"PRIx64":i64", u.val);
|
||||
#else
|
||||
char buf[16];
|
||||
if (sizeof(long) == 4)
|
||||
snprintf(buf, sizeof(buf), "%s", "0x%llx:i64");
|
||||
else
|
||||
snprintf(buf, sizeof(buf), "%s", "0x%lx:i64");
|
||||
os_printf(buf, u.val);
|
||||
char buf[16];
|
||||
if (sizeof(long) == 4)
|
||||
snprintf(buf, sizeof(buf), "%s", "0x%llx:i64");
|
||||
else
|
||||
snprintf(buf, sizeof(buf), "%s", "0x%lx:i64");
|
||||
os_printf(buf, u.val);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
case VALUE_TYPE_F32:
|
||||
os_printf("%.7g:f32", *(float32*)argv1);
|
||||
break;
|
||||
case VALUE_TYPE_F64:
|
||||
{
|
||||
union { float64 val; uint32 parts[2]; } u;
|
||||
u.parts[0] = argv1[0];
|
||||
u.parts[1] = argv1[1];
|
||||
os_printf("%.7g:f64", u.val);
|
||||
break;
|
||||
break;
|
||||
}
|
||||
case VALUE_TYPE_F32:
|
||||
os_printf("%.7g:f32", *(float32*)argv1);
|
||||
break;
|
||||
case VALUE_TYPE_F64:
|
||||
{
|
||||
union { float64 val; uint32 parts[2]; } u;
|
||||
u.parts[0] = argv1[0];
|
||||
u.parts[1] = argv1[1];
|
||||
os_printf("%.7g:f64", u.val);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
os_printf("\n");
|
||||
@ -2148,7 +2151,9 @@ wasm_runtime_call_indirect(WASMExecEnv *exec_env,
|
||||
return false;
|
||||
}
|
||||
|
||||
exec_env->handle = os_self_thread();
|
||||
/* this function is called from native code, so exec_env->handle and
|
||||
exec_env->native_stack_boundary must have been set, we don't set
|
||||
it again */
|
||||
|
||||
#if WASM_ENABLE_INTERP != 0
|
||||
if (exec_env->module_inst->module_type == Wasm_Module_Bytecode)
|
||||
|
||||
Reference in New Issue
Block a user