mirror of
https://github.com/bytecodealliance/wasm-micro-runtime.git
synced 2025-05-09 13:16:26 +00:00
Refine aot memory boundary check, add more llvm passes (#236)
Fix issue of some error info mismatch with spec cases
This commit is contained in:
parent
f8442340fe
commit
f72e848114
|
@ -127,6 +127,8 @@ handle_next_reachable_block(AOTCompContext *comp_ctx,
|
||||||
AOTBlock *block_prev;
|
AOTBlock *block_prev;
|
||||||
uint8 *frame_ip;
|
uint8 *frame_ip;
|
||||||
|
|
||||||
|
aot_checked_addr_list_destroy(func_ctx);
|
||||||
|
|
||||||
if (block->block_type == BLOCK_TYPE_IF
|
if (block->block_type == BLOCK_TYPE_IF
|
||||||
&& block->llvm_else_block
|
&& block->llvm_else_block
|
||||||
&& !block->skip_wasm_code_else
|
&& !block->skip_wasm_code_else
|
||||||
|
@ -233,6 +235,8 @@ aot_compile_op_block(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
/* Start to translate the block */
|
/* Start to translate the block */
|
||||||
SET_BUILDER_POS(block->llvm_entry_block);
|
SET_BUILDER_POS(block->llvm_entry_block);
|
||||||
aot_block_stack_push(&func_ctx->block_stack, block);
|
aot_block_stack_push(&func_ctx->block_stack, block);
|
||||||
|
if (block_type == BLOCK_TYPE_LOOP)
|
||||||
|
aot_checked_addr_list_destroy(func_ctx);
|
||||||
}
|
}
|
||||||
else if (block_type == BLOCK_TYPE_IF) {
|
else if (block_type == BLOCK_TYPE_IF) {
|
||||||
POP_COND(value);
|
POP_COND(value);
|
||||||
|
@ -373,6 +377,7 @@ aot_compile_op_else(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
/* Clear value stack and start to translate else branch */
|
/* Clear value stack and start to translate else branch */
|
||||||
aot_value_stack_destroy(&block->value_stack);
|
aot_value_stack_destroy(&block->value_stack);
|
||||||
SET_BUILDER_POS(block->llvm_else_block);
|
SET_BUILDER_POS(block->llvm_else_block);
|
||||||
|
aot_checked_addr_list_destroy(func_ctx);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -82,6 +82,7 @@ check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
LLVMValueRef mem_base_addr, mem_check_bound, total_mem_size;
|
LLVMValueRef mem_base_addr, mem_check_bound, total_mem_size;
|
||||||
LLVMBasicBlockRef block_curr = LLVMGetInsertBlock(comp_ctx->builder);
|
LLVMBasicBlockRef block_curr = LLVMGetInsertBlock(comp_ctx->builder);
|
||||||
LLVMBasicBlockRef check_succ, check_mem_space;
|
LLVMBasicBlockRef check_succ, check_mem_space;
|
||||||
|
AOTValue *aot_value;
|
||||||
|
|
||||||
CHECK_LLVM_CONST(offset_const);
|
CHECK_LLVM_CONST(offset_const);
|
||||||
CHECK_LLVM_CONST(bytes_const);
|
CHECK_LLVM_CONST(bytes_const);
|
||||||
|
@ -100,6 +101,8 @@ check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
aot_value = func_ctx->block_stack.block_list_end->value_stack.value_list_end;
|
||||||
|
|
||||||
POP_I32(addr);
|
POP_I32(addr);
|
||||||
/* offset1 = offset + addr; */
|
/* offset1 = offset + addr; */
|
||||||
BUILD_OP(Add, offset_const, addr, offset1, "offset1");
|
BUILD_OP(Add, offset_const, addr, offset1, "offset1");
|
||||||
|
@ -152,28 +155,38 @@ check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
SET_BUILD_POS(check_mem_space);
|
SET_BUILD_POS(check_mem_space);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* offset2 = offset1 - heap_base_offset; */
|
if (!(aot_value->is_local
|
||||||
BUILD_OP(Sub, offset1, heap_base_offset, offset2, "offset2");
|
&& aot_checked_addr_list_find(func_ctx, aot_value->local_idx,
|
||||||
|
offset, bytes))) {
|
||||||
|
/* offset2 = offset1 - heap_base_offset; */
|
||||||
|
BUILD_OP(Sub, offset1, heap_base_offset, offset2, "offset2");
|
||||||
|
|
||||||
if (!(mem_check_bound =
|
if (!(mem_check_bound =
|
||||||
get_memory_check_bound(comp_ctx, func_ctx, bytes))) {
|
get_memory_check_bound(comp_ctx, func_ctx, bytes))) {
|
||||||
goto fail;
|
goto fail;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Add basic blocks */
|
||||||
|
ADD_BASIC_BLOCK(check_succ, "check_succ");
|
||||||
|
LLVMMoveBasicBlockAfter(check_succ, block_curr);
|
||||||
|
|
||||||
|
/* offset2 > bound ? */
|
||||||
|
BUILD_ICMP(LLVMIntUGT, offset2, mem_check_bound, cmp, "cmp");
|
||||||
|
if (!aot_emit_exception(comp_ctx, func_ctx,
|
||||||
|
EXCE_OUT_OF_BOUNDS_MEMORY_ACCESS,
|
||||||
|
true, cmp, check_succ)) {
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
|
||||||
|
SET_BUILD_POS(check_succ);
|
||||||
|
|
||||||
|
if (aot_value->is_local) {
|
||||||
|
if (!aot_checked_addr_list_add(func_ctx, aot_value->local_idx,
|
||||||
|
offset, bytes))
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Add basic blocks */
|
|
||||||
ADD_BASIC_BLOCK(check_succ, "check_succ");
|
|
||||||
LLVMMoveBasicBlockAfter(check_succ, block_curr);
|
|
||||||
|
|
||||||
/* offset2 > bound ? */
|
|
||||||
BUILD_ICMP(LLVMIntUGT, offset2, mem_check_bound, cmp, "cmp");
|
|
||||||
if (!aot_emit_exception(comp_ctx, func_ctx,
|
|
||||||
EXCE_OUT_OF_BOUNDS_MEMORY_ACCESS,
|
|
||||||
true, cmp, check_succ)) {
|
|
||||||
goto fail;
|
|
||||||
}
|
|
||||||
|
|
||||||
SET_BUILD_POS(check_succ);
|
|
||||||
|
|
||||||
/* maddr = mem_base_addr + offset1 */
|
/* maddr = mem_base_addr + offset1 */
|
||||||
if (!(maddr = LLVMBuildInBoundsGEP(comp_ctx->builder, mem_base_addr,
|
if (!(maddr = LLVMBuildInBoundsGEP(comp_ctx->builder, mem_base_addr,
|
||||||
&offset1, 1, "maddr"))) {
|
&offset1, 1, "maddr"))) {
|
||||||
|
|
|
@ -30,6 +30,7 @@ aot_compile_op_get_local(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
{
|
{
|
||||||
char name[32];
|
char name[32];
|
||||||
LLVMValueRef value;
|
LLVMValueRef value;
|
||||||
|
AOTValue *aot_value;
|
||||||
|
|
||||||
CHECK_LOCAL(local_idx);
|
CHECK_LOCAL(local_idx);
|
||||||
|
|
||||||
|
@ -42,6 +43,10 @@ aot_compile_op_get_local(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
}
|
}
|
||||||
|
|
||||||
PUSH(value, get_local_type(func_ctx, local_idx));
|
PUSH(value, get_local_type(func_ctx, local_idx));
|
||||||
|
|
||||||
|
aot_value = func_ctx->block_stack.block_list_end->value_stack.value_list_end;
|
||||||
|
aot_value->is_local = true;
|
||||||
|
aot_value->local_idx = local_idx;
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
fail:
|
fail:
|
||||||
|
@ -65,6 +70,7 @@ aot_compile_op_set_local(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
aot_checked_addr_list_del(func_ctx, local_idx);
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
fail:
|
fail:
|
||||||
|
@ -92,6 +98,7 @@ aot_compile_op_tee_local(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
|
||||||
}
|
}
|
||||||
|
|
||||||
PUSH(value, type);
|
PUSH(value, type);
|
||||||
|
aot_checked_addr_list_del(func_ctx, local_idx);
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
fail:
|
fail:
|
||||||
|
|
|
@ -629,6 +629,7 @@ aot_destroy_func_contexts(AOTFuncContext **func_ctxes, uint32 count)
|
||||||
if (func_ctxes[i]->exception_blocks)
|
if (func_ctxes[i]->exception_blocks)
|
||||||
wasm_runtime_free(func_ctxes[i]->exception_blocks);
|
wasm_runtime_free(func_ctxes[i]->exception_blocks);
|
||||||
aot_block_stack_destroy(&func_ctxes[i]->block_stack);
|
aot_block_stack_destroy(&func_ctxes[i]->block_stack);
|
||||||
|
aot_checked_addr_list_destroy(func_ctxes[i]);
|
||||||
wasm_runtime_free(func_ctxes[i]);
|
wasm_runtime_free(func_ctxes[i]);
|
||||||
}
|
}
|
||||||
wasm_runtime_free(func_ctxes);
|
wasm_runtime_free(func_ctxes);
|
||||||
|
@ -1119,11 +1120,15 @@ aot_create_comp_context(AOTCompData *comp_data,
|
||||||
aot_set_last_error("create LLVM pass manager failed.");
|
aot_set_last_error("create LLVM pass manager failed.");
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
LLVMAddBasicAliasAnalysisPass(comp_ctx->pass_mgr);
|
||||||
LLVMAddPromoteMemoryToRegisterPass(comp_ctx->pass_mgr);
|
LLVMAddPromoteMemoryToRegisterPass(comp_ctx->pass_mgr);
|
||||||
LLVMAddInstructionCombiningPass(comp_ctx->pass_mgr);
|
LLVMAddInstructionCombiningPass(comp_ctx->pass_mgr);
|
||||||
LLVMAddCFGSimplificationPass(comp_ctx->pass_mgr);
|
|
||||||
LLVMAddJumpThreadingPass(comp_ctx->pass_mgr);
|
LLVMAddJumpThreadingPass(comp_ctx->pass_mgr);
|
||||||
LLVMAddConstantPropagationPass(comp_ctx->pass_mgr);
|
LLVMAddConstantPropagationPass(comp_ctx->pass_mgr);
|
||||||
|
LLVMAddReassociatePass(comp_ctx->pass_mgr);
|
||||||
|
LLVMAddGVNPass(comp_ctx->pass_mgr);
|
||||||
|
LLVMAddCFGSimplificationPass(comp_ctx->pass_mgr);
|
||||||
|
|
||||||
/* Create metadata for llvm float experimental constrained intrinsics */
|
/* Create metadata for llvm float experimental constrained intrinsics */
|
||||||
if (!(comp_ctx->fp_rounding_mode =
|
if (!(comp_ctx->fp_rounding_mode =
|
||||||
|
@ -1298,3 +1303,80 @@ aot_block_destroy(AOTBlock *block)
|
||||||
aot_value_stack_destroy(&block->value_stack);
|
aot_value_stack_destroy(&block->value_stack);
|
||||||
wasm_runtime_free(block);
|
wasm_runtime_free(block);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
aot_checked_addr_list_add(AOTFuncContext *func_ctx,
|
||||||
|
uint32 local_idx, uint32 offset, uint32 bytes)
|
||||||
|
{
|
||||||
|
AOTCheckedAddr *node = func_ctx->checked_addr_list;
|
||||||
|
|
||||||
|
if (!(node = wasm_runtime_malloc(sizeof(AOTCheckedAddr)))) {
|
||||||
|
aot_set_last_error("allocate memory failed.");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
node->local_idx = local_idx;
|
||||||
|
node->offset = offset;
|
||||||
|
node->bytes = bytes;
|
||||||
|
|
||||||
|
node->next = func_ctx->checked_addr_list;
|
||||||
|
func_ctx->checked_addr_list = node;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
aot_checked_addr_list_del(AOTFuncContext *func_ctx, uint32 local_idx)
|
||||||
|
{
|
||||||
|
AOTCheckedAddr *node = func_ctx->checked_addr_list;
|
||||||
|
AOTCheckedAddr *node_prev = NULL, *node_next;
|
||||||
|
|
||||||
|
while (node) {
|
||||||
|
node_next = node->next;
|
||||||
|
|
||||||
|
if (node->local_idx == local_idx) {
|
||||||
|
if (!node_prev)
|
||||||
|
func_ctx->checked_addr_list = node_next;
|
||||||
|
else
|
||||||
|
node_prev->next = node_next;
|
||||||
|
wasm_runtime_free(node);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
node_prev = node;
|
||||||
|
}
|
||||||
|
|
||||||
|
node = node_next;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
aot_checked_addr_list_find(AOTFuncContext *func_ctx,
|
||||||
|
uint32 local_idx, uint32 offset, uint32 bytes)
|
||||||
|
{
|
||||||
|
AOTCheckedAddr *node = func_ctx->checked_addr_list;
|
||||||
|
|
||||||
|
while (node) {
|
||||||
|
if (node->local_idx == local_idx
|
||||||
|
&& node->offset == offset
|
||||||
|
&& node->bytes >= bytes) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
node = node->next;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
aot_checked_addr_list_destroy(AOTFuncContext *func_ctx)
|
||||||
|
{
|
||||||
|
AOTCheckedAddr *node = func_ctx->checked_addr_list, *node_next;
|
||||||
|
|
||||||
|
while (node) {
|
||||||
|
node_next = node->next;
|
||||||
|
wasm_runtime_free(node);
|
||||||
|
node = node_next;
|
||||||
|
}
|
||||||
|
|
||||||
|
func_ctx->checked_addr_list = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
|
@ -30,6 +30,8 @@ typedef struct AOTValue {
|
||||||
LLVMValueRef value;
|
LLVMValueRef value;
|
||||||
/* VALUE_TYPE_I32/I64/F32/F64/VOID */
|
/* VALUE_TYPE_I32/I64/F32/F64/VOID */
|
||||||
uint8 type;
|
uint8 type;
|
||||||
|
bool is_local;
|
||||||
|
uint32 local_idx;
|
||||||
} AOTValue;
|
} AOTValue;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -84,6 +86,13 @@ typedef struct AOTBlockStack {
|
||||||
uint32 block_index[3];
|
uint32 block_index[3];
|
||||||
} AOTBlockStack;
|
} AOTBlockStack;
|
||||||
|
|
||||||
|
typedef struct AOTCheckedAddr {
|
||||||
|
struct AOTCheckedAddr *next;
|
||||||
|
uint32 local_idx;
|
||||||
|
uint32 offset;
|
||||||
|
uint32 bytes;
|
||||||
|
} AOTCheckedAddr, *AOTCheckedAddrList;
|
||||||
|
|
||||||
typedef struct AOTFuncContext {
|
typedef struct AOTFuncContext {
|
||||||
AOTFunc *aot_func;
|
AOTFunc *aot_func;
|
||||||
LLVMValueRef func;
|
LLVMValueRef func;
|
||||||
|
@ -105,6 +114,7 @@ typedef struct AOTFuncContext {
|
||||||
LLVMValueRef cur_exception;
|
LLVMValueRef cur_exception;
|
||||||
|
|
||||||
bool mem_space_unchanged;
|
bool mem_space_unchanged;
|
||||||
|
AOTCheckedAddrList checked_addr_list;
|
||||||
|
|
||||||
LLVMBasicBlockRef *exception_blocks;
|
LLVMBasicBlockRef *exception_blocks;
|
||||||
LLVMBasicBlockRef got_exception_block;
|
LLVMBasicBlockRef got_exception_block;
|
||||||
|
@ -258,6 +268,20 @@ aot_block_destroy(AOTBlock *block);
|
||||||
LLVMTypeRef
|
LLVMTypeRef
|
||||||
wasm_type_to_llvm_type(AOTLLVMTypes *llvm_types, uint8 wasm_type);
|
wasm_type_to_llvm_type(AOTLLVMTypes *llvm_types, uint8 wasm_type);
|
||||||
|
|
||||||
|
bool
|
||||||
|
aot_checked_addr_list_add(AOTFuncContext *func_ctx,
|
||||||
|
uint32 local_idx, uint32 offset, uint32 bytes);
|
||||||
|
|
||||||
|
void
|
||||||
|
aot_checked_addr_list_del(AOTFuncContext *func_ctx, uint32 local_idx);
|
||||||
|
|
||||||
|
bool
|
||||||
|
aot_checked_addr_list_find(AOTFuncContext *func_ctx,
|
||||||
|
uint32 local_idx, uint32 offset, uint32 bytes);
|
||||||
|
|
||||||
|
void
|
||||||
|
aot_checked_addr_list_destroy(AOTFuncContext *func_ctx);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
} /* end of extern "C" */
|
} /* end of extern "C" */
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -419,7 +419,7 @@ load_type_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
read_leb_uint32(p, p_end, result_count);
|
read_leb_uint32(p, p_end, result_count);
|
||||||
if (result_count > 1) {
|
if (result_count > 1) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load type section failed: invalid result count.");
|
"Load type section failed: invalid result arity.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
CHECK_BUF(p, p_end, result_count);
|
CHECK_BUF(p, p_end, result_count);
|
||||||
|
@ -485,6 +485,36 @@ load_table_import(const uint8 **p_buf, const uint8 *buf_end,
|
||||||
unsigned
|
unsigned
|
||||||
wasm_runtime_memory_pool_size();
|
wasm_runtime_memory_pool_size();
|
||||||
|
|
||||||
|
static bool
|
||||||
|
check_memory_init_size(uint32 init_size,
|
||||||
|
char *error_buf, uint32 error_buf_size)
|
||||||
|
{
|
||||||
|
if (init_size > 65536) {
|
||||||
|
set_error_buf(error_buf, error_buf_size,
|
||||||
|
"memory size must be at most 65536 pages (4GiB)");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
check_memory_max_size(uint32 init_size, uint32 max_size,
|
||||||
|
char *error_buf, uint32 error_buf_size)
|
||||||
|
{
|
||||||
|
if (max_size < init_size) {
|
||||||
|
set_error_buf(error_buf, error_buf_size,
|
||||||
|
"size minimum must not be greater than maximum");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (max_size > 65536) {
|
||||||
|
set_error_buf(error_buf, error_buf_size,
|
||||||
|
"memory size must be at most 65536 pages (4GiB)");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
static bool
|
static bool
|
||||||
load_memory_import(const uint8 **p_buf, const uint8 *buf_end,
|
load_memory_import(const uint8 **p_buf, const uint8 *buf_end,
|
||||||
WASMMemoryImport *memory,
|
WASMMemoryImport *memory,
|
||||||
|
@ -501,8 +531,16 @@ load_memory_import(const uint8 **p_buf, const uint8 *buf_end,
|
||||||
|
|
||||||
read_leb_uint32(p, p_end, memory->flags);
|
read_leb_uint32(p, p_end, memory->flags);
|
||||||
read_leb_uint32(p, p_end, memory->init_page_count);
|
read_leb_uint32(p, p_end, memory->init_page_count);
|
||||||
|
if (!check_memory_init_size(memory->init_page_count,
|
||||||
|
error_buf, error_buf_size))
|
||||||
|
return false;
|
||||||
|
|
||||||
if (memory->flags & 1) {
|
if (memory->flags & 1) {
|
||||||
read_leb_uint32(p, p_end, memory->max_page_count);
|
read_leb_uint32(p, p_end, memory->max_page_count);
|
||||||
|
if (!check_memory_max_size(memory->init_page_count,
|
||||||
|
memory->max_page_count,
|
||||||
|
error_buf, error_buf_size))
|
||||||
|
return false;
|
||||||
if (memory->max_page_count > max_page_count)
|
if (memory->max_page_count > max_page_count)
|
||||||
memory->max_page_count = max_page_count;
|
memory->max_page_count = max_page_count;
|
||||||
}
|
}
|
||||||
|
@ -552,8 +590,16 @@ load_memory(const uint8 **p_buf, const uint8 *buf_end, WASMMemory *memory,
|
||||||
|
|
||||||
read_leb_uint32(p, p_end, memory->flags);
|
read_leb_uint32(p, p_end, memory->flags);
|
||||||
read_leb_uint32(p, p_end, memory->init_page_count);
|
read_leb_uint32(p, p_end, memory->init_page_count);
|
||||||
|
if (!check_memory_init_size(memory->init_page_count,
|
||||||
|
error_buf, error_buf_size))
|
||||||
|
return false;
|
||||||
|
|
||||||
if (memory->flags & 1) {
|
if (memory->flags & 1) {
|
||||||
read_leb_uint32(p, p_end, memory->max_page_count);
|
read_leb_uint32(p, p_end, memory->max_page_count);
|
||||||
|
if (!check_memory_max_size(memory->init_page_count,
|
||||||
|
memory->max_page_count,
|
||||||
|
error_buf, error_buf_size))
|
||||||
|
return false;
|
||||||
if (memory->max_page_count > max_page_count)
|
if (memory->max_page_count > max_page_count)
|
||||||
memory->max_page_count = max_page_count;
|
memory->max_page_count = max_page_count;
|
||||||
}
|
}
|
||||||
|
@ -715,7 +761,7 @@ load_import_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
if (type_index >= module->type_count) {
|
if (type_index >= module->type_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load import section failed: "
|
"Load import section failed: "
|
||||||
"function type index out of range.");
|
"unknown type.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
import->u.function.func_type = module->types[type_index];
|
import->u.function.func_type = module->types[type_index];
|
||||||
|
@ -898,7 +944,7 @@ load_function_section(const uint8 *buf, const uint8 *buf_end,
|
||||||
if (type_index >= module->type_count) {
|
if (type_index >= module->type_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load function section failed: "
|
"Load function section failed: "
|
||||||
"function type index out of range.");
|
"unknown type.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1017,7 +1063,7 @@ load_table_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
if (table_count) {
|
if (table_count) {
|
||||||
if (table_count > 1) {
|
if (table_count > 1) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load table section failed: multiple memories");
|
"Load table section failed: multiple tables");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
module->table_count = table_count;
|
module->table_count = table_count;
|
||||||
|
@ -1194,7 +1240,7 @@ load_export_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
if (index >= module->function_count + module->import_function_count) {
|
if (index >= module->function_count + module->import_function_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load export section failed: "
|
"Load export section failed: "
|
||||||
"function index out of range.");
|
"unknown function.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -1203,7 +1249,7 @@ load_export_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
if (index >= module->table_count + module->import_table_count) {
|
if (index >= module->table_count + module->import_table_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load export section failed: "
|
"Load export section failed: "
|
||||||
"table index out of range.");
|
"unknown table.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -1212,7 +1258,7 @@ load_export_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
if (index >= module->memory_count + module->import_memory_count) {
|
if (index >= module->memory_count + module->import_memory_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load export section failed: "
|
"Load export section failed: "
|
||||||
"memory index out of range.");
|
"unknown memory.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -1221,7 +1267,7 @@ load_export_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
if (index >= module->global_count + module->import_global_count) {
|
if (index >= module->global_count + module->import_global_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load export section failed: "
|
"Load export section failed: "
|
||||||
"global index out of range.");
|
"unknown global.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -1273,7 +1319,7 @@ load_table_segment_section(const uint8 *buf, const uint8 *buf_end, WASMModule *m
|
||||||
if (p >= p_end) {
|
if (p >= p_end) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load table segment section failed: "
|
"Load table segment section failed: "
|
||||||
"invalid value type");
|
"unexpected end");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
read_leb_uint32(p, p_end, table_index);
|
read_leb_uint32(p, p_end, table_index);
|
||||||
|
@ -1417,7 +1463,7 @@ load_start_section(const uint8 *buf, const uint8 *buf_end, WASMModule *module,
|
||||||
if (start_function >= module->function_count + module->import_function_count) {
|
if (start_function >= module->function_count + module->import_function_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"Load start section failed: "
|
"Load start section failed: "
|
||||||
"function index out of range.");
|
"unknown function.");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
module->start_function = start_function;
|
module->start_function = start_function;
|
||||||
|
@ -2703,7 +2749,7 @@ wasm_loader_check_br(WASMLoaderContext *ctx, uint32 depth,
|
||||||
{
|
{
|
||||||
if (ctx->csp_num < depth + 1) {
|
if (ctx->csp_num < depth + 1) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM module load failed: type mismatch: "
|
"WASM module load failed: unknown label, "
|
||||||
"unexpected end of section or function");
|
"unexpected end of section or function");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -3405,7 +3451,7 @@ fail:
|
||||||
if (local_idx >= param_count + local_count) { \
|
if (local_idx >= param_count + local_count) { \
|
||||||
set_error_buf(error_buf, error_buf_size, \
|
set_error_buf(error_buf, error_buf_size, \
|
||||||
"WASM module load failed: " \
|
"WASM module load failed: " \
|
||||||
"local index out of range"); \
|
"unknown local."); \
|
||||||
goto fail; \
|
goto fail; \
|
||||||
} \
|
} \
|
||||||
local_type = local_idx < param_count \
|
local_type = local_idx < param_count \
|
||||||
|
@ -3427,8 +3473,7 @@ check_memory(WASMModule *module,
|
||||||
if (module->memory_count == 0
|
if (module->memory_count == 0
|
||||||
&& module->import_memory_count == 0) {
|
&& module->import_memory_count == 0) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM module load failed: "
|
"WASM module load failed: unknown memory");
|
||||||
"load or store in module without default memory");
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
@ -3848,7 +3893,7 @@ handle_next_reachable_block:
|
||||||
if (func_idx >= module->import_function_count + module->function_count) {
|
if (func_idx >= module->import_function_count + module->function_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM loader prepare bytecode failed: "
|
"WASM loader prepare bytecode failed: "
|
||||||
"function index out of range");
|
"unknown function.");
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3888,7 +3933,7 @@ handle_next_reachable_block:
|
||||||
&& module->import_table_count == 0) {
|
&& module->import_table_count == 0) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM loader prepare bytecode failed: "
|
"WASM loader prepare bytecode failed: "
|
||||||
"call indirect without default table");
|
"call indirect with unknown table");
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3911,7 +3956,7 @@ handle_next_reachable_block:
|
||||||
if (type_idx >= module->type_count) {
|
if (type_idx >= module->type_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM loader prepare bytecode failed: "
|
"WASM loader prepare bytecode failed: "
|
||||||
"function index out of range");
|
"unknown type");
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3992,7 +4037,8 @@ handle_next_reachable_block:
|
||||||
if (loader_ctx->stack_cell_num <= 0) {
|
if (loader_ctx->stack_cell_num <= 0) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM loader prepare bytecode failed: "
|
"WASM loader prepare bytecode failed: "
|
||||||
"opcode select was found but stack was empty");
|
"type mismatch, opcode select was found "
|
||||||
|
"but stack was empty");
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4175,7 +4221,7 @@ handle_next_reachable_block:
|
||||||
if (global_idx >= global_count) {
|
if (global_idx >= global_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM loader prepare bytecode failed: "
|
"WASM loader prepare bytecode failed: "
|
||||||
"global index out of range");
|
"unknown global.");
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4197,7 +4243,7 @@ handle_next_reachable_block:
|
||||||
if (global_idx >= global_count) {
|
if (global_idx >= global_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"WASM loader prepare bytecode failed: "
|
"WASM loader prepare bytecode failed: "
|
||||||
"global index out of range");
|
"unknown global.");
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -753,7 +753,7 @@ wasm_instantiate(WASMModule *module,
|
||||||
for (j = 0; j < length; j++) {
|
for (j = 0; j < length; j++) {
|
||||||
if (table_seg->func_indexes[j] >= module_inst->function_count) {
|
if (table_seg->func_indexes[j] >= module_inst->function_count) {
|
||||||
set_error_buf(error_buf, error_buf_size,
|
set_error_buf(error_buf, error_buf_size,
|
||||||
"function index is overflow");
|
"WASM instantiate failed: unknown function");
|
||||||
wasm_deinstantiate(module_inst);
|
wasm_deinstantiate(module_inst);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user