support tail-call in AoT (#419)

This commit is contained in:
Xu Jun 2020-10-13 08:34:31 +08:00 committed by GitHub
parent cc0aab1063
commit c87f28eacd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 55 additions and 4 deletions

View File

@ -2093,8 +2093,14 @@ aot_convert_wasm_module(WASMModule *wasm_module,
}
option.is_jit_mode = true;
#if WASM_ENABLE_BULK_MEMORY != 0
option.enable_bulk_memory = true;
#endif
#if WASM_ENABLE_THREAD_MGR != 0
option.enable_thread_mgr = true;
#endif
#if WASM_ENABLE_TAIL_CALL != 0
option.enable_tail_call = true;
#endif
comp_ctx = aot_create_comp_context(comp_data, &option);
if (!comp_ctx) {

View File

@ -240,7 +240,7 @@ aot_compile_func(AOTCompContext *comp_ctx, uint32 func_index)
case WASM_OP_CALL:
read_leb_uint32(frame_ip, frame_ip_end, func_idx);
if (!aot_compile_op_call(comp_ctx, func_ctx, func_idx, &frame_ip))
if (!aot_compile_op_call(comp_ctx, func_ctx, func_idx, false))
return false;
break;
@ -251,6 +251,33 @@ aot_compile_func(AOTCompContext *comp_ctx, uint32 func_index)
return false;
break;
#if WASM_ENABLE_TAIL_CALL != 0
case WASM_OP_RETURN_CALL:
if (!comp_ctx->enable_tail_call) {
aot_set_last_error("unsupported opcode");
return false;
}
read_leb_uint32(frame_ip, frame_ip_end, func_idx);
if (!aot_compile_op_call(comp_ctx, func_ctx, func_idx, true))
return false;
if (!aot_compile_op_return(comp_ctx, func_ctx, &frame_ip))
return false;
break;
case WASM_OP_RETURN_CALL_INDIRECT:
if (!comp_ctx->enable_tail_call) {
aot_set_last_error("unsupported opcode");
return false;
}
read_leb_uint32(frame_ip, frame_ip_end, type_idx);
frame_ip++; /* skip 0x00 */
if (!aot_compile_op_call_indirect(comp_ctx, func_ctx, type_idx))
return false;
if (!aot_compile_op_return(comp_ctx, func_ctx, &frame_ip))
return false;
break;
#endif /* end of WASM_ENABLE_TAIL_CALL */
case WASM_OP_DROP:
if (!aot_compile_op_drop(comp_ctx, func_ctx, true))
return false;
@ -993,6 +1020,7 @@ build_atomic_rmw:
#endif /* end of WASM_ENABLE_SHARED_MEMORY */
default:
aot_set_last_error("unsupported opcode");
break;
}
}

View File

@ -304,7 +304,7 @@ check_stack_boundary(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
bool
aot_compile_op_call(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
uint32 func_idx, uint8 **p_frame_ip)
uint32 func_idx, bool tail_call)
{
uint32 import_func_count = comp_ctx->comp_data->import_func_count;
AOTImportFunc *import_funcs = comp_ctx->comp_data->import_funcs;
@ -476,8 +476,12 @@ aot_compile_op_call(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
/* Set calling convention for the call with the func's calling convention */
LLVMSetInstructionCallConv(value_ret, LLVMGetFunctionCallConv(func));
if (tail_call)
LLVMSetTailCall(value_ret, true);
/* Check whether there was exception thrown when executing the function */
if (!check_exception_thrown(comp_ctx, func_ctx))
if (!tail_call
&& !check_exception_thrown(comp_ctx, func_ctx))
goto fail;
}

View File

@ -14,7 +14,7 @@ extern "C" {
bool
aot_compile_op_call(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
uint32 func_idx, uint8 **p_frame_ip);
uint32 func_idx, bool tail_call);
bool
aot_compile_op_call_indirect(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,

View File

@ -1062,6 +1062,9 @@ aot_create_comp_context(AOTCompData *comp_data,
if (option->enable_thread_mgr)
comp_ctx->enable_thread_mgr = true;
if (option->enable_tail_call)
comp_ctx->enable_tail_call = true;
if (option->is_jit_mode) {
/* Create LLVM execution engine */
LLVMInitializeMCJITCompilerOptions(&jit_options, sizeof(jit_options));

View File

@ -204,6 +204,9 @@ typedef struct AOTCompContext {
/* Thread Manager */
bool enable_thread_mgr;
/* Tail Call */
bool enable_tail_call;
/* Whether optimize the JITed code */
bool optimize;
@ -244,6 +247,7 @@ typedef struct AOTCompOption{
char *cpu_features;
bool enable_bulk_memory;
bool enable_thread_mgr;
bool enable_tail_call;
bool is_sgx_platform;
uint32 opt_level;
uint32 size_level;

View File

@ -41,6 +41,7 @@ typedef struct AOTCompOption{
char *cpu_features;
bool enable_bulk_memory;
bool enable_thread_mgr;
bool enable_tail_call;
bool is_sgx_platform;
uint32_t opt_level;
uint32_t size_level;

View File

@ -26,6 +26,7 @@ add_definitions(-DWASM_ENABLE_BULK_MEMORY=1)
add_definitions(-DWASM_DISABLE_HW_BOUND_CHECK=1)
add_definitions(-DWASM_ENABLE_SHARED_MEMORY=1)
add_definitions(-DWASM_ENABLE_THREAD_MGR=1)
add_definitions(-DWASM_ENABLE_TAIL_CALL=1)
# Set WAMR_BUILD_TARGET, currently values supported:
# "X86_64", "AMD_64", "X86_32", "ARM_32", "MIPS_32", "XTENSA_32"

View File

@ -41,6 +41,7 @@ print_help()
printf(" llvmir-opt Optimized LLVM IR\n");
printf(" --enable-bulk-memory Enable the post-MVP bulk memory feature\n");
printf(" --enable-multi-thread Enable multi-thread feature, the dependent features bulk-memory and\n");
printf(" --enable-tail-call Enable the post-MVP tail call feature\n");
printf(" thread-mgr will be enabled automatically\n");
printf(" -v=n Set log verbose level (0 to 5, default is 2), larger with more log\n");
printf("Examples: wamrc -o test.aot test.wasm\n");
@ -146,6 +147,9 @@ main(int argc, char *argv[])
option.enable_bulk_memory = true;
option.enable_thread_mgr = true;
}
else if (!strcmp(argv[0], "--enable-tail-call")) {
option.enable_tail_call = true;
}
else
return print_help();
}