summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/wasm-ast-checker.c3
-rw-r--r--src/wasm-ast-parser.y3
-rw-r--r--src/wasm-ast-writer.c240
-rw-r--r--src/wasm-ast.c3
-rw-r--r--src/wasm-binary-reader-ast.c260
-rw-r--r--src/wasm-binary-reader.c151
-rw-r--r--src/wasm-binary-reader.h16
-rw-r--r--src/wasm-binary-writer.c3
-rw-r--r--src/wasm-common.h11
-rw-r--r--src/wasm-interpreter.h12
10 files changed, 462 insertions, 240 deletions
diff --git a/src/wasm-ast-checker.c b/src/wasm-ast-checker.c
index 82eee30d..fb51b5c7 100644
--- a/src/wasm-ast-checker.c
+++ b/src/wasm-ast-checker.c
@@ -1111,6 +1111,9 @@ static void check_import(Context* ctx,
case WASM_EXTERNAL_KIND_GLOBAL:
check_global(ctx, loc, &import->global);
break;
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
}
}
diff --git a/src/wasm-ast-parser.y b/src/wasm-ast-parser.y
index da274389..2054b4ab 100644
--- a/src/wasm-ast-parser.y
+++ b/src/wasm-ast-parser.y
@@ -1187,6 +1187,9 @@ module_fields :
&field->import.global);
INSERT_BINDING($$, global, globals, @2, *$2);
break;
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
}
wasm_free(parser->allocator, $2);
APPEND_ITEM_TO_VECTOR($$, Import, import, imports, &field->import);
diff --git a/src/wasm-ast-writer.c b/src/wasm-ast-writer.c
index 76f7f9dc..4b71746e 100644
--- a/src/wasm-ast-writer.c
+++ b/src/wasm-ast-writer.c
@@ -66,6 +66,13 @@ typedef struct Context {
NextChar next_char;
int depth;
WasmStringSliceVector index_to_name;
+
+ int func_index;
+ int global_index;
+ int export_index;
+ int table_index;
+ int memory_index;
+ int func_type_index;
} Context;
static void indent(Context* ctx) {
@@ -254,44 +261,58 @@ static void write_type(Context* ctx, WasmType type, NextChar next_char) {
write_puts(ctx, s_types[type], next_char);
}
-static void write_func_sig_space(Context* ctx,
- const WasmFuncSignature* func_sig) {
- if (func_sig->param_types.size) {
+static void write_types(Context* ctx,
+ const WasmTypeVector* types,
+ const char* name) {
+ if (types->size) {
size_t i;
- write_open_space(ctx, "param");
- for (i = 0; i < func_sig->param_types.size; ++i) {
- write_type(ctx, func_sig->param_types.data[i], NEXT_CHAR_SPACE);
- }
+ if (name)
+ write_open_space(ctx, name);
+ for (i = 0; i < types->size; ++i)
+ write_type(ctx, types->data[i], NEXT_CHAR_SPACE);
write_close_space(ctx);
}
+}
- if (func_sig->result_type != WASM_TYPE_VOID) {
- write_open_space(ctx, "result");
- write_type(ctx, func_sig->result_type, NEXT_CHAR_NONE);
- write_close_space(ctx);
- }
+static void write_func_sig_space(Context* ctx,
+ const WasmFuncSignature* func_sig) {
+ write_types(ctx, &func_sig->param_types, "param");
+ write_types(ctx, &func_sig->result_types, "result");
}
static void write_expr_list(Context* ctx, const WasmExpr* first);
static void write_expr(Context* ctx, const WasmExpr* expr);
-static void write_block(Context* ctx,
- const WasmBlock* block,
- const char* start_text,
- const char* end_text) {
- if (start_text)
- write_puts_space(ctx, start_text);
- if (!write_string_slice_opt(ctx, &block->label, NEXT_CHAR_SPACE))
+static void write_begin_block(Context* ctx,
+ const WasmBlock* block,
+ const char* text) {
+ if (text)
+ write_puts_space(ctx, text);
+ WasmBool has_label =
+ write_string_slice_opt(ctx, &block->label, NEXT_CHAR_SPACE);
+ write_types(ctx, &block->sig, NULL);
+ if (!has_label)
writef(ctx, " ;; exit = @%d", ctx->depth);
write_newline(ctx, FORCE_NEWLINE);
ctx->depth++;
indent(ctx);
- write_expr_list(ctx, block->first);
+}
+
+static void write_end_block(Context* ctx, const char* text) {
dedent(ctx);
ctx->depth--;
- if (end_text)
- write_puts_newline(ctx, end_text);
+ if (text)
+ write_puts_newline(ctx, text);
+}
+
+static void write_block(Context* ctx,
+ const WasmBlock* block,
+ const char* start_text,
+ const char* end_text) {
+ write_begin_block(ctx, block, start_text);
+ write_expr_list(ctx, block->first);
+ write_end_block(ctx, end_text);
}
static void write_const(Context* ctx, const WasmConst* const_) {
@@ -345,19 +366,16 @@ static void write_expr(Context* ctx, const WasmExpr* expr) {
case WASM_EXPR_TYPE_BR:
write_puts_space(ctx, s_opcode_name[WASM_OPCODE_BR]);
- writef(ctx, "%d", expr->br.arity);
write_br_var(ctx, &expr->br.var, NEXT_CHAR_NEWLINE);
break;
case WASM_EXPR_TYPE_BR_IF:
write_puts_space(ctx, s_opcode_name[WASM_OPCODE_BR_IF]);
- writef(ctx, "%d", expr->br_if.arity);
write_br_var(ctx, &expr->br_if.var, NEXT_CHAR_NEWLINE);
break;
case WASM_EXPR_TYPE_BR_TABLE: {
write_puts_space(ctx, s_opcode_name[WASM_OPCODE_BR_TABLE]);
- writef(ctx, "%d", expr->br_table.arity);
size_t i;
for (i = 0; i < expr->br_table.targets.size; ++i)
write_br_var(ctx, &expr->br_table.targets.data[i], NEXT_CHAR_SPACE);
@@ -370,11 +388,6 @@ static void write_expr(Context* ctx, const WasmExpr* expr) {
write_var(ctx, &expr->call.var, NEXT_CHAR_NEWLINE);
break;
- case WASM_EXPR_TYPE_CALL_IMPORT:
- write_puts_space(ctx, s_opcode_name[WASM_OPCODE_CALL_IMPORT]);
- write_var(ctx, &expr->call_import.var, NEXT_CHAR_NEWLINE);
- break;
-
case WASM_EXPR_TYPE_CALL_INDIRECT:
write_puts_space(ctx, s_opcode_name[WASM_OPCODE_CALL_INDIRECT]);
write_var(ctx, &expr->call_indirect.var, NEXT_CHAR_NEWLINE);
@@ -411,15 +424,16 @@ static void write_expr(Context* ctx, const WasmExpr* expr) {
break;
case WASM_EXPR_TYPE_IF:
- write_block(ctx, &expr->if_.true_, s_opcode_name[WASM_OPCODE_IF],
- s_opcode_name[WASM_OPCODE_END]);
- break;
-
- case WASM_EXPR_TYPE_IF_ELSE:
- write_block(ctx, &expr->if_else.true_, s_opcode_name[WASM_OPCODE_IF],
- NULL);
- write_block(ctx, &expr->if_else.false_, s_opcode_name[WASM_OPCODE_ELSE],
- s_opcode_name[WASM_OPCODE_END]);
+ write_begin_block(ctx, &expr->if_.true_, s_opcode_name[WASM_OPCODE_IF]);
+ write_expr_list(ctx, expr->if_.true_.first);
+ if (expr->if_.false_) {
+ dedent(ctx);
+ write_puts_space(ctx, s_opcode_name[WASM_OPCODE_ELSE]);
+ indent(ctx);
+ write_newline(ctx, FORCE_NEWLINE);
+ write_expr_list(ctx, expr->if_.false_);
+ }
+ write_end_block(ctx, s_opcode_name[WASM_OPCODE_END]);
break;
case WASM_EXPR_TYPE_LOAD:
@@ -542,10 +556,10 @@ static void write_type_bindings(Context* ctx,
static void write_func(Context* ctx,
const WasmModule* module,
- int func_index,
const WasmFunc* func) {
write_open_space(ctx, "func");
- write_string_slice_or_index(ctx, &func->name, func_index, NEXT_CHAR_SPACE);
+ write_string_slice_or_index(ctx, &func->name, ctx->func_index,
+ NEXT_CHAR_SPACE);
if (wasm_decl_has_func_type(&func->decl)) {
write_open_space(ctx, "type");
write_var(ctx, &func->decl.type_var, NEXT_CHAR_NONE);
@@ -553,11 +567,7 @@ static void write_func(Context* ctx,
}
write_type_bindings(ctx, "param", func, &func->decl.sig.param_types,
&func->param_bindings);
- if (wasm_get_result_type(module, func) != WASM_TYPE_VOID) {
- write_open_space(ctx, "result");
- write_type(ctx, wasm_get_result_type(module, func), NEXT_CHAR_NONE);
- write_close_space(ctx);
- }
+ write_types(ctx, &func->decl.sig.result_types, "result");
write_newline(ctx, NO_FORCE_NEWLINE);
if (func->local_types.size) {
write_type_bindings(ctx, "local", func, &func->local_types,
@@ -569,49 +579,18 @@ static void write_func(Context* ctx,
write_close_newline(ctx);
}
-static void write_global(Context* ctx,
- const WasmModule* module,
- int global_index,
- const WasmGlobal* global) {
+static void write_begin_global(Context* ctx, const WasmGlobal* global) {
write_open_space(ctx, "global");
- write_string_slice_or_index(ctx, &global->name, global_index,
+ if (global->mutable_)
+ write_puts(ctx, "mut", NEXT_CHAR_SPACE);
+ write_string_slice_or_index(ctx, &global->name, ctx->global_index++,
NEXT_CHAR_SPACE);
write_type(ctx, global->type, NEXT_CHAR_SPACE);
- write_init_expr(ctx, global->init_expr);
- write_close_newline(ctx);
-}
-
-static void write_import(Context* ctx,
- int import_index,
- const WasmImport* import) {
- write_open_space(ctx, "import");
- write_string_slice_or_index(ctx, &import->name, import_index,
- NEXT_CHAR_SPACE);
- write_quoted_string_slice(ctx, &import->module_name, NEXT_CHAR_SPACE);
- write_quoted_string_slice(ctx, &import->func_name, NEXT_CHAR_SPACE);
- if (wasm_decl_has_func_type(&import->decl)) {
- write_open_space(ctx, "type");
- write_var(ctx, &import->decl.type_var, NEXT_CHAR_NONE);
- write_close_space(ctx);
- } else {
- write_func_sig_space(ctx, &import->decl.sig);
- }
- write_close_newline(ctx);
}
-static void write_export(Context* ctx,
- int export_index,
- const WasmExport* export) {
- write_open_space(ctx, "export");
- write_quoted_string_slice(ctx, &export->name, NEXT_CHAR_SPACE);
- write_var(ctx, &export->var, NEXT_CHAR_SPACE);
- write_close_newline(ctx);
-}
-
-static void write_export_memory(Context* ctx, const WasmExportMemory* export) {
- write_open_space(ctx, "export");
- write_quoted_string_slice(ctx, &export->name, NEXT_CHAR_SPACE);
- write_puts_space(ctx, "memory");
+static void write_global(Context* ctx, const WasmGlobal* global) {
+ write_begin_global(ctx, global);
+ write_init_expr(ctx, global->init_expr);
write_close_newline(ctx);
}
@@ -623,6 +602,8 @@ static void write_limits(Context* ctx, const WasmLimits* limits) {
static void write_table(Context* ctx, const WasmTable* table) {
write_open_space(ctx, "table");
+ write_string_slice_or_index(ctx, &table->name, ctx->table_index++,
+ NEXT_CHAR_SPACE);
write_limits(ctx, &table->elem_limits);
write_puts_space(ctx, "anyfunc");
write_close_newline(ctx);
@@ -639,6 +620,8 @@ static void write_elem_segment(Context* ctx, const WasmElemSegment* segment) {
static void write_memory(Context* ctx, const WasmMemory* memory) {
write_open_space(ctx, "memory");
+ write_string_slice_or_index(ctx, &memory->name, ctx->memory_index++,
+ NEXT_CHAR_SPACE);
write_limits(ctx, &memory->page_limits);
write_close_newline(ctx);
}
@@ -650,11 +633,74 @@ static void write_data_segment(Context* ctx, const WasmDataSegment* segment) {
write_close_newline(ctx);
}
-static void write_func_type(Context* ctx,
- int func_type_index,
- const WasmFuncType* func_type) {
+static void write_import(Context* ctx, const WasmImport* import) {
+ write_open_space(ctx, "import");
+ uint32_t index = 0;
+ switch (import->kind) {
+ case WASM_EXTERNAL_KIND_FUNC:
+ index = ctx->func_index;
+ break;
+ case WASM_EXTERNAL_KIND_TABLE:
+ index = ctx->table_index;
+ break;
+ case WASM_EXTERNAL_KIND_MEMORY:
+ index = ctx->memory_index;
+ break;
+ case WASM_EXTERNAL_KIND_GLOBAL:
+ index = ctx->global_index;
+ break;
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
+ }
+ write_string_slice_or_index(ctx, &import->name, index, NEXT_CHAR_SPACE);
+ write_quoted_string_slice(ctx, &import->module_name, NEXT_CHAR_SPACE);
+ write_quoted_string_slice(ctx, &import->field_name, NEXT_CHAR_SPACE);
+ switch (import->kind) {
+ case WASM_EXTERNAL_KIND_FUNC:
+ if (wasm_decl_has_func_type(&import->func.decl)) {
+ write_open_space(ctx, "type");
+ write_var(ctx, &import->func.decl.type_var, NEXT_CHAR_NONE);
+ write_close_space(ctx);
+ } else {
+ write_func_sig_space(ctx, &import->func.decl.sig);
+ }
+ break;
+
+ case WASM_EXTERNAL_KIND_TABLE:
+ write_open_space(ctx, "table");
+ write_table(ctx, &import->table);
+ write_close_space(ctx);
+ break;
+
+ case WASM_EXTERNAL_KIND_MEMORY:
+ write_open_space(ctx, "memory");
+ write_memory(ctx, &import->memory);
+ write_close_space(ctx);
+ break;
+
+ case WASM_EXTERNAL_KIND_GLOBAL:
+ write_begin_global(ctx, &import->global);
+ write_close_space(ctx);
+ break;
+
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
+ }
+ write_close_newline(ctx);
+}
+
+static void write_export(Context* ctx, const WasmExport* export) {
+ write_open_space(ctx, "export");
+ write_quoted_string_slice(ctx, &export->name, NEXT_CHAR_SPACE);
+ write_var(ctx, &export->var, NEXT_CHAR_SPACE);
+ write_close_newline(ctx);
+}
+
+static void write_func_type(Context* ctx, const WasmFuncType* func_type) {
write_open_space(ctx, "type");
- write_string_slice_or_index(ctx, &func_type->name, func_type_index,
+ write_string_slice_or_index(ctx, &func_type->name, ctx->func_type_index++,
NEXT_CHAR_SPACE);
write_open_space(ctx, "func");
write_func_sig_space(ctx, &func_type->sig);
@@ -671,27 +717,19 @@ static void write_start_function(Context* ctx, const WasmVar* start) {
static void write_module(Context* ctx, const WasmModule* module) {
write_open_newline(ctx, "module");
const WasmModuleField* field;
- int func_index = 0;
- int global_index = 0;
- int import_index = 0;
- int export_index = 0;
- int func_type_index = 0;
for (field = module->first_field; field != NULL; field = field->next) {
switch (field->type) {
case WASM_MODULE_FIELD_TYPE_FUNC:
- write_func(ctx, module, func_index++, &field->func);
+ write_func(ctx, module, &field->func);
break;
case WASM_MODULE_FIELD_TYPE_GLOBAL:
- write_global(ctx, module, global_index++, &field->global);
+ write_global(ctx, &field->global);
break;
case WASM_MODULE_FIELD_TYPE_IMPORT:
- write_import(ctx, import_index++, &field->import);
+ write_import(ctx, &field->import);
break;
case WASM_MODULE_FIELD_TYPE_EXPORT:
- write_export(ctx, export_index++, &field->export_);
- break;
- case WASM_MODULE_FIELD_TYPE_EXPORT_MEMORY:
- write_export_memory(ctx, &field->export_memory);
+ write_export(ctx, &field->export_);
break;
case WASM_MODULE_FIELD_TYPE_TABLE:
write_table(ctx, &field->table);
@@ -706,7 +744,7 @@ static void write_module(Context* ctx, const WasmModule* module) {
write_data_segment(ctx, &field->data_segment);
break;
case WASM_MODULE_FIELD_TYPE_FUNC_TYPE:
- write_func_type(ctx, func_type_index++, &field->func_type);
+ write_func_type(ctx, &field->func_type);
break;
case WASM_MODULE_FIELD_TYPE_START:
write_start_function(ctx, &field->start);
diff --git a/src/wasm-ast.c b/src/wasm-ast.c
index a44957e1..f6353bff 100644
--- a/src/wasm-ast.c
+++ b/src/wasm-ast.c
@@ -505,6 +505,9 @@ void wasm_destroy_import(WasmAllocator* allocator, WasmImport* import) {
case WASM_EXTERNAL_KIND_GLOBAL:
wasm_destroy_global(allocator, &import->global);
break;
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
}
}
diff --git a/src/wasm-binary-reader-ast.c b/src/wasm-binary-reader-ast.c
index eeb05b19..f0665d05 100644
--- a/src/wasm-binary-reader-ast.c
+++ b/src/wasm-binary-reader-ast.c
@@ -130,9 +130,10 @@ static WasmResult on_signature_count(uint32_t count, void* user_data) {
}
static WasmResult on_signature(uint32_t index,
- WasmType result_type,
uint32_t param_count,
WasmType* param_types,
+ uint32_t result_count,
+ WasmType* result_types,
void* user_data) {
Context* ctx = user_data;
WasmModuleField* field =
@@ -141,13 +142,18 @@ static WasmResult on_signature(uint32_t index,
WasmFuncType* func_type = &field->func_type;
WASM_ZERO_MEMORY(*func_type);
- func_type->sig.result_type = result_type;
wasm_reserve_types(ctx->allocator, &func_type->sig.param_types, param_count);
func_type->sig.param_types.size = param_count;
memcpy(func_type->sig.param_types.data, param_types,
param_count * sizeof(WasmType));
+ wasm_reserve_types(ctx->allocator, &func_type->sig.result_types,
+ result_count);
+ func_type->sig.result_types.size = result_count;
+ memcpy(func_type->sig.result_types.data, result_types,
+ result_count * sizeof(WasmType));
+
assert(index < ctx->module->func_types.capacity);
WasmFuncTypePtr* func_type_ptr =
wasm_append_func_type_ptr(ctx->allocator, &ctx->module->func_types);
@@ -162,13 +168,11 @@ static WasmResult on_import_count(uint32_t count, void* user_data) {
}
static WasmResult on_import(uint32_t index,
- uint32_t sig_index,
WasmStringSlice module_name,
- WasmStringSlice function_name,
+ WasmStringSlice field_name,
void* user_data) {
Context* ctx = user_data;
assert(index < ctx->module->imports.capacity);
- assert(sig_index < ctx->module->func_types.size);
WasmModuleField* field =
wasm_append_module_field(ctx->allocator, ctx->module);
@@ -177,12 +181,7 @@ static WasmResult on_import(uint32_t index,
WasmImport* import = &field->import;
WASM_ZERO_MEMORY(*import);
import->module_name = wasm_dup_string_slice(ctx->allocator, module_name);
- import->func_name = wasm_dup_string_slice(ctx->allocator, function_name);
- import->decl.flags = WASM_FUNC_DECLARATION_FLAG_HAS_FUNC_TYPE |
- WASM_FUNC_DECLARATION_FLAG_SHARED_SIGNATURE;
- import->decl.type_var.type = WASM_VAR_TYPE_INDEX;
- import->decl.type_var.index = sig_index;
- import->decl.sig = ctx->module->func_types.data[sig_index]->sig;
+ import->field_name = wasm_dup_string_slice(ctx->allocator, field_name);
WasmImportPtr* import_ptr =
wasm_append_import_ptr(ctx->allocator, &ctx->module->imports);
@@ -190,6 +189,58 @@ static WasmResult on_import(uint32_t index,
return WASM_OK;
}
+static WasmResult on_import_func(uint32_t index,
+ uint32_t sig_index,
+ void* user_data) {
+ Context* ctx = user_data;
+ assert(index == ctx->module->imports.size - 1);
+ assert(sig_index < ctx->module->func_types.size);
+ WasmImport* import = ctx->module->imports.data[index];
+
+ import->func.decl.flags = WASM_FUNC_DECLARATION_FLAG_HAS_FUNC_TYPE |
+ WASM_FUNC_DECLARATION_FLAG_SHARED_SIGNATURE;
+ import->func.decl.type_var.type = WASM_VAR_TYPE_INDEX;
+ import->func.decl.type_var.index = sig_index;
+ import->func.decl.sig = ctx->module->func_types.data[sig_index]->sig;
+ return WASM_OK;
+}
+
+static WasmResult on_import_table(uint32_t index,
+ uint32_t elem_type,
+ const WasmLimits* elem_limits,
+ void* user_data) {
+ Context* ctx = user_data;
+ assert(index == ctx->module->imports.size - 1);
+ WasmImport* import = ctx->module->imports.data[index];
+
+ import->table.elem_limits = *elem_limits;
+ return WASM_OK;
+}
+
+static WasmResult on_import_memory(uint32_t index,
+ const WasmLimits* page_limits,
+ void* user_data) {
+ Context* ctx = user_data;
+ assert(index == ctx->module->imports.size - 1);
+ WasmImport* import = ctx->module->imports.data[index];
+
+ import->memory.page_limits = *page_limits;
+ return WASM_OK;
+}
+
+static WasmResult on_import_global(uint32_t index,
+ WasmType type,
+ WasmBool mutable_,
+ void* user_data) {
+ Context* ctx = user_data;
+ assert(index == ctx->module->imports.size - 1);
+ WasmImport* import = ctx->module->imports.data[index];
+
+ import->global.type = type;
+ import->global.mutable_ = mutable_;
+ return WASM_OK;
+}
+
static WasmResult on_function_signatures_count(uint32_t count,
void* user_data) {
Context* ctx = user_data;
@@ -222,47 +273,56 @@ static WasmResult on_function_signature(uint32_t index,
return WASM_OK;
}
-static WasmResult begin_table_section(void* user_data) {
+static WasmResult on_table_count(uint32_t count, void* user_data) {
+ Context* ctx = user_data;
+ wasm_reserve_table_ptrs(ctx->allocator, &ctx->module->tables, count);
+ return WASM_OK;
+}
+
+static WasmResult on_table(uint32_t index,
+ uint32_t elem_type,
+ const WasmLimits* elem_limits,
+ void* user_data) {
Context* ctx = user_data;
+ assert(index < ctx->module->tables.capacity);
+
WasmModuleField* field =
wasm_append_module_field(ctx->allocator, ctx->module);
field->type = WASM_MODULE_FIELD_TYPE_TABLE;
- assert(ctx->module->table == NULL);
- ctx->module->table = &field->table;
+
+ WasmTable* table = &field->table;
+ WASM_ZERO_MEMORY(*table);
+ table->elem_limits = *elem_limits;
+
+ WasmTablePtr* table_ptr =
+ wasm_append_table_ptr(ctx->allocator, &ctx->module->tables);
+ *table_ptr = table;
return WASM_OK;
}
-static WasmResult on_table_limits(WasmBool has_max,
- uint32_t initial,
- uint32_t max,
- void* user_data) {
+static WasmResult on_memory_count(uint32_t count, void* user_data) {
Context* ctx = user_data;
- WasmLimits* limits = &ctx->module->table->elem_limits;
- limits->has_max = has_max;
- limits->initial = initial;
- limits->max = max;
+ wasm_reserve_memory_ptrs(ctx->allocator, &ctx->module->memories, count);
return WASM_OK;
}
-static WasmResult begin_memory_section(void* user_data) {
+static WasmResult on_memory(uint32_t index,
+ const WasmLimits* page_limits,
+ void* user_data) {
Context* ctx = user_data;
+ assert(index < ctx->module->memories.capacity);
+
WasmModuleField* field =
wasm_append_module_field(ctx->allocator, ctx->module);
field->type = WASM_MODULE_FIELD_TYPE_MEMORY;
- assert(ctx->module->memory == NULL);
- ctx->module->memory = &field->memory;
- return WASM_OK;
-}
-static WasmResult on_memory_limits(WasmBool has_max,
- uint32_t initial,
- uint32_t max,
- void* user_data) {
- Context* ctx = user_data;
- WasmLimits* limits = &ctx->module->memory->page_limits;
- limits->has_max = has_max;
- limits->initial = initial;
- limits->max = max;
+ WasmMemory* memory = &field->memory;
+ WASM_ZERO_MEMORY(*memory);
+ memory->page_limits = *page_limits;
+
+ WasmMemoryPtr* memory_ptr =
+ wasm_append_memory_ptr(ctx->allocator, &ctx->module->memories);
+ *memory_ptr = memory;
return WASM_OK;
}
@@ -272,7 +332,10 @@ static WasmResult on_global_count(uint32_t count, void* user_data) {
return WASM_OK;
}
-static WasmResult begin_global(uint32_t index, WasmType type, void* user_data) {
+static WasmResult begin_global(uint32_t index,
+ WasmType type,
+ WasmBool mutable_,
+ void* user_data) {
Context* ctx = user_data;
assert(index < ctx->module->globals.capacity);
@@ -283,6 +346,7 @@ static WasmResult begin_global(uint32_t index, WasmType type, void* user_data) {
WasmGlobal* global = &field->global;
WASM_ZERO_MEMORY(*global);
global->type = type;
+ global->mutable_ = mutable_;
WasmGlobalPtr* global_ptr =
wasm_append_global_ptr(ctx->allocator, &ctx->module->globals);
@@ -312,7 +376,8 @@ static WasmResult on_export_count(uint32_t count, void* user_data) {
}
static WasmResult on_export(uint32_t index,
- uint32_t func_index,
+ WasmExternalKind kind,
+ uint32_t item_index,
WasmStringSlice name,
void* user_data) {
Context* ctx = user_data;
@@ -323,9 +388,26 @@ static WasmResult on_export(uint32_t index,
WasmExport* export = &field->export_;
WASM_ZERO_MEMORY(*export);
export->name = wasm_dup_string_slice(ctx->allocator, name);
+ switch (kind) {
+ case WASM_EXTERNAL_KIND_FUNC:
+ assert(item_index < ctx->module->funcs.size);
+ break;
+ case WASM_EXTERNAL_KIND_TABLE:
+ assert(item_index < ctx->module->funcs.size);
+ break;
+ case WASM_EXTERNAL_KIND_MEMORY:
+ assert(item_index < ctx->module->memories.size);
+ break;
+ case WASM_EXTERNAL_KIND_GLOBAL:
+ assert(item_index < ctx->module->globals.size);
+ break;
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
+ }
export->var.type = WASM_VAR_TYPE_INDEX;
- assert(func_index < ctx->module->funcs.size);
- export->var.index = func_index;
+ export->var.index = item_index;
+ export->kind = kind;
assert(index < ctx->module->exports.capacity);
WasmExportPtr* export_ptr =
@@ -386,43 +468,44 @@ static WasmResult on_binary_expr(WasmOpcode opcode, void* user_data) {
return append_expr(ctx, expr);
}
-static WasmResult on_block_expr(void* user_data) {
+static WasmResult on_block_expr(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data) {
Context* ctx = user_data;
WasmExpr* expr = wasm_new_block_expr(ctx->allocator);
+ WasmTypeVector src;
+ WASM_ZERO_MEMORY(src);
+ src.size = num_types;
+ src.data = sig_types;
+ wasm_extend_types(ctx->allocator, &expr->block.sig, &src);
append_expr(ctx, expr);
push_label(ctx, &expr->block.first);
return WASM_OK;
}
-static WasmResult on_br_expr(uint8_t arity, uint32_t depth, void* user_data) {
+static WasmResult on_br_expr(uint32_t depth, void* user_data) {
Context* ctx = user_data;
WasmExpr* expr = wasm_new_br_expr(ctx->allocator);
expr->br.var.type = WASM_VAR_TYPE_INDEX;
- expr->br.arity = arity;
expr->br.var.index = depth;
return append_expr(ctx, expr);
}
-static WasmResult on_br_if_expr(uint8_t arity,
- uint32_t depth,
- void* user_data) {
+static WasmResult on_br_if_expr(uint32_t depth, void* user_data) {
Context* ctx = user_data;
WasmExpr* expr = wasm_new_br_if_expr(ctx->allocator);
- expr->br_if.arity = arity;
expr->br_if.var.type = WASM_VAR_TYPE_INDEX;
expr->br_if.var.index = depth;
return append_expr(ctx, expr);
}
-static WasmResult on_br_table_expr(uint8_t arity,
- uint32_t num_targets,
+static WasmResult on_br_table_expr(uint32_t num_targets,
uint32_t* target_depths,
uint32_t default_target_depth,
void* user_data) {
Context* ctx = user_data;
WasmExpr* expr = wasm_new_br_table_expr(ctx->allocator);
wasm_reserve_vars(ctx->allocator, &expr->br_table.targets, num_targets);
- expr->br_table.arity = arity;
expr->br_table.targets.size = num_targets;
uint32_t i;
for (i = 0; i < num_targets; ++i) {
@@ -444,15 +527,6 @@ static WasmResult on_call_expr(uint32_t func_index, void* user_data) {
return append_expr(ctx, expr);
}
-static WasmResult on_call_import_expr(uint32_t import_index, void* user_data) {
- Context* ctx = user_data;
- assert(import_index < ctx->module->imports.size);
- WasmExpr* expr = wasm_new_call_import_expr(ctx->allocator);
- expr->call_import.var.type = WASM_VAR_TYPE_INDEX;
- expr->call_import.var.index = import_index;
- return append_expr(ctx, expr);
-}
-
static WasmResult on_call_indirect_expr(uint32_t sig_index, void* user_data) {
Context* ctx = user_data;
assert(sig_index < ctx->module->func_types.size);
@@ -489,11 +563,7 @@ static WasmResult on_drop_expr(void* user_data) {
}
static WasmResult on_else_expr(void* user_data) {
- /* destroy the if expr, replace it with an if_else */
- /* TODO(binji): remove if_else and just have false branch be an empty block
- * for if without else? */
Context* ctx = user_data;
- CHECK_RESULT(pop_label(ctx));
LabelNode* label;
CHECK_RESULT(top_label(ctx, &label));
WasmExpr* if_expr = label->last;
@@ -501,25 +571,6 @@ static WasmResult on_else_expr(void* user_data) {
print_error(ctx, "else expression without matching if");
return WASM_ERROR;
}
-
- WasmExpr* if_else_expr = wasm_new_if_else_expr(ctx->allocator);
- if_else_expr->if_else.true_.first = if_expr->if_.true_.first;
-
- /* find the expression that points to the if_expr, and have it point to the
- * new if_else_expr instead */
- WasmExpr* prev = NULL;
- if (prev == if_expr) {
- *label->first = if_else_expr;
- } else {
- for (prev = *label->first; prev && prev->next != if_expr;
- prev = prev->next) {
- }
- assert(prev);
- prev->next = if_else_expr;
- }
- label->last = if_else_expr;
- wasm_free(ctx->allocator, if_expr);
- push_label(ctx, &if_else_expr->if_else.false_.first);
return WASM_OK;
}
@@ -582,9 +633,16 @@ static WasmResult on_i64_const_expr(uint64_t value, void* user_data) {
return append_expr(ctx, expr);
}
-static WasmResult on_if_expr(void* user_data) {
+static WasmResult on_if_expr(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data) {
Context* ctx = user_data;
WasmExpr* expr = wasm_new_if_expr(ctx->allocator);
+ WasmTypeVector src;
+ WASM_ZERO_MEMORY(src);
+ src.size = num_types;
+ src.data = sig_types;
+ wasm_extend_types(ctx->allocator, &expr->if_.true_.sig, &src);
append_expr(ctx, expr);
push_label(ctx, &expr->if_.true_.first);
return WASM_OK;
@@ -602,9 +660,16 @@ static WasmResult on_load_expr(WasmOpcode opcode,
return append_expr(ctx, expr);
}
-static WasmResult on_loop_expr(void* user_data) {
+static WasmResult on_loop_expr(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data) {
Context* ctx = user_data;
WasmExpr* expr = wasm_new_loop_expr(ctx->allocator);
+ WasmTypeVector src;
+ WASM_ZERO_MEMORY(src);
+ src.size = num_types;
+ src.data = sig_types;
+ wasm_extend_types(ctx->allocator, &expr->loop.sig, &src);
append_expr(ctx, expr);
push_label(ctx, &expr->loop.first);
return WASM_OK;
@@ -701,6 +766,9 @@ static WasmResult begin_elem_segment(uint32_t index,
WasmElemSegment* segment = &field->elem_segment;
WASM_ZERO_MEMORY(*segment);
+ segment->table_var.type = WASM_VAR_TYPE_INDEX;
+ segment->table_var.index = table_index;
+
assert(index == ctx->module->elem_segments.size);
assert(index < ctx->module->elem_segments.capacity);
WasmElemSegmentPtr* segment_ptr =
@@ -753,7 +821,9 @@ static WasmResult on_data_segment_count(uint32_t count, void* user_data) {
return WASM_OK;
}
-static WasmResult begin_data_segment(uint32_t index, void* user_data) {
+static WasmResult begin_data_segment(uint32_t index,
+ uint32_t memory_index,
+ void* user_data) {
Context* ctx = user_data;
WasmModuleField* field =
wasm_append_module_field(ctx->allocator, ctx->module);
@@ -761,6 +831,9 @@ static WasmResult begin_data_segment(uint32_t index, void* user_data) {
WasmDataSegment* segment = &field->data_segment;
WASM_ZERO_MEMORY(*segment);
+ segment->memory_var.type = WASM_VAR_TYPE_INDEX;
+ segment->memory_var.index = memory_index;
+
assert(index == ctx->module->data_segments.size);
assert(index < ctx->module->data_segments.capacity);
WasmDataSegmentPtr* segment_ptr =
@@ -832,7 +905,7 @@ static WasmResult on_local_names_count(uint32_t index,
WasmModule* module = ctx->module;
assert(index < module->funcs.size);
WasmFunc* func = module->funcs.data[index];
- uint32_t num_params_and_locals = wasm_get_num_params_and_locals(module, func);
+ uint32_t num_params_and_locals = wasm_get_num_params_and_locals(func);
if (count > num_params_and_locals) {
print_error(ctx, "expected local name count (%d) <= local count (%d)",
count, num_params_and_locals);
@@ -903,7 +976,7 @@ static WasmResult on_local_name(uint32_t func_index,
Context* ctx = user_data;
WasmModule* module = ctx->module;
WasmFunc* func = module->funcs.data[func_index];
- uint32_t num_params = wasm_get_num_params(module, func);
+ uint32_t num_params = wasm_get_num_params(func);
WasmStringSlice new_name;
dup_name(ctx, &name, &new_name);
WasmBindingHash* bindings;
@@ -932,15 +1005,19 @@ static WasmBinaryReader s_binary_reader = {
.on_import_count = on_import_count,
.on_import = on_import,
+ .on_import_func = on_import_func,
+ .on_import_table = on_import_table,
+ .on_import_memory = on_import_memory,
+ .on_import_global = on_import_global,
.on_function_signatures_count = on_function_signatures_count,
.on_function_signature = on_function_signature,
- .begin_table_section = begin_table_section,
- .on_table_limits = on_table_limits,
+ .on_table_count = on_table_count,
+ .on_table = on_table,
- .begin_memory_section = begin_memory_section,
- .on_memory_limits = on_memory_limits,
+ .on_memory_count = on_memory_count,
+ .on_memory = on_memory,
.on_global_count = on_global_count,
.begin_global = begin_global,
@@ -961,7 +1038,6 @@ static WasmBinaryReader s_binary_reader = {
.on_br_if_expr = on_br_if_expr,
.on_br_table_expr = on_br_table_expr,
.on_call_expr = on_call_expr,
- .on_call_import_expr = on_call_import_expr,
.on_call_indirect_expr = on_call_indirect_expr,
.on_compare_expr = on_compare_expr,
.on_convert_expr = on_convert_expr,
diff --git a/src/wasm-binary-reader.c b/src/wasm-binary-reader.c
index 8ab50a22..5b3bea6c 100644
--- a/src/wasm-binary-reader.c
+++ b/src/wasm-binary-reader.c
@@ -85,6 +85,11 @@ static const char* s_opcode_name[] = {WASM_FOREACH_OPCODE(V)};
static const char* s_section_name[] = {WASM_FOREACH_BINARY_SECTION(V)};
#undef V
+static const char* s_external_kind_name[] = {"func", "table", "memory",
+ "global"};
+WASM_STATIC_ASSERT(WASM_ARRAY_SIZE(s_external_kind_name) ==
+ WASM_NUM_EXTERNAL_KINDS);
+
typedef struct Context {
const uint8_t* data;
size_t size;
@@ -315,10 +320,18 @@ static void in_bytes(Context* ctx,
ctx->offset += data_size;
}
+static WasmBool is_valid_external_kind(uint8_t kind) {
+ return kind < WASM_NUM_EXTERNAL_KINDS;
+}
+
static WasmBool is_concrete_type(uint8_t type) {
return type != WASM_TYPE_VOID && type < WASM_NUM_TYPES;
}
+static WasmBool is_inline_sig_type(uint8_t type) {
+ return type < WASM_NUM_TYPES;
+}
+
static WasmBool skip_until_section(Context* ctx,
WasmBinarySection expected_code,
const char* expected_name) {
@@ -426,13 +439,6 @@ static void logging_on_error(uint32_t offset,
FORWARD0(end_##name); \
}
-#define LOGGING_UINT8_DESC(name, desc) \
- static WasmResult logging_##name(uint8_t value, void* user_data) { \
- LoggingContext* ctx = user_data; \
- LOGF(#name "(" desc ": %u)\n", value); \
- FORWARD(name, value); \
- }
-
#define LOGGING_UINT32(name) \
static WasmResult logging_##name(uint32_t value, void* user_data) { \
LoggingContext* ctx = user_data; \
@@ -505,7 +511,6 @@ LOGGING_UINT32(begin_function_body)
LOGGING_UINT32(end_function_body)
LOGGING_UINT32(on_local_decl_count)
LOGGING_OPCODE(on_binary_expr)
-LOGGING_UINT8_DESC(on_block_expr, "sig_type")
LOGGING_UINT32_DESC(on_call_expr, "func_index")
LOGGING_UINT32_DESC(on_call_import_expr, "import_index")
LOGGING_UINT32_DESC(on_call_indirect_expr, "sig_index")
@@ -518,8 +523,6 @@ LOGGING0(on_end_expr)
LOGGING_UINT32_DESC(on_get_global_expr, "index")
LOGGING_UINT32_DESC(on_get_local_expr, "index")
LOGGING0(on_grow_memory_expr)
-LOGGING_UINT8_DESC(on_if_expr, "sig_type")
-LOGGING_UINT8_DESC(on_loop_expr, "sig_type")
LOGGING0(on_nop_expr)
LOGGING0(on_return_expr)
LOGGING0(on_select_expr)
@@ -562,21 +565,33 @@ static void sprint_limits(char* dst, size_t size, const WasmLimits* limits) {
assert((size_t)result < size);
}
+static void log_types(LoggingContext* ctx,
+ uint32_t type_count,
+ WasmType* types) {
+ uint32_t i;
+ LOGF_NOINDENT("[");
+ for (i = 0; i < type_count; ++i) {
+ LOGF_NOINDENT("%s", s_type_names[types[i]]);
+ if (i != type_count - 1)
+ LOGF_NOINDENT(", ");
+ }
+ LOGF_NOINDENT("]");
+}
+
static WasmResult logging_on_signature(uint32_t index,
- WasmType result_type,
uint32_t param_count,
WasmType* param_types,
+ uint32_t result_count,
+ WasmType* result_types,
void* user_data) {
LoggingContext* ctx = user_data;
- LOGF("on_signature(index: %u, %s (", index, s_type_names[result_type]);
- uint32_t i;
- for (i = 0; i < param_count; ++i) {
- LOGF_NOINDENT("%s", s_type_names[result_type]);
- if (i != param_count - 1)
- LOGF_NOINDENT(", ");
- }
- LOGF_NOINDENT("))\n");
- FORWARD(on_signature, index, result_type, param_count, param_types);
+ LOGF("on_signature(index: %u, params: ", index);
+ log_types(ctx, param_count, param_types);
+ LOGF_NOINDENT(", results: ");
+ log_types(ctx, result_count, result_types);
+ LOGF_NOINDENT(")\n");
+ FORWARD(on_signature, index, param_count, param_types, result_count,
+ result_types);
}
static WasmResult logging_on_import(uint32_t index,
@@ -655,13 +670,16 @@ static WasmResult logging_begin_global(uint32_t index,
}
static WasmResult logging_on_export(uint32_t index,
- uint32_t func_index,
+ WasmExternalKind kind,
+ uint32_t item_index,
WasmStringSlice name,
void* user_data) {
LoggingContext* ctx = user_data;
- LOGF("on_export(index: %u, func_index: %u, name: \"" PRIstringslice "\")\n",
- index, func_index, WASM_PRINTF_STRING_SLICE_ARG(name));
- FORWARD(on_export, index, func_index, name);
+ LOGF("on_export(index: %u, kind: %s, item_index: %u, name: \"" PRIstringslice
+ "\")\n",
+ index, s_external_kind_name[kind], item_index,
+ WASM_PRINTF_STRING_SLICE_ARG(name));
+ FORWARD(on_export, index, kind, item_index, name);
}
static WasmResult logging_begin_function_body_pass(uint32_t index,
@@ -683,6 +701,16 @@ static WasmResult logging_on_local_decl(uint32_t decl_index,
FORWARD(on_local_decl, decl_index, count, type);
}
+static WasmResult logging_on_block_expr(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data) {
+ LoggingContext* ctx = user_data;
+ LOGF("on_block_expr(sig: ");
+ log_types(ctx, num_types, sig_types);
+ LOGF(")");
+ FORWARD(on_block_expr, num_types, sig_types);
+}
+
static WasmResult logging_on_br_expr(uint32_t depth, void* user_data) {
LoggingContext* ctx = user_data;
LOGF("on_br_expr(depth: %u)\n", depth);
@@ -741,6 +769,16 @@ static WasmResult logging_on_i64_const_expr(uint64_t value, void* user_data) {
FORWARD(on_i64_const_expr, value);
}
+static WasmResult logging_on_if_expr(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data) {
+ LoggingContext* ctx = user_data;
+ LOGF("on_if_expr(sig: ");
+ log_types(ctx, num_types, sig_types);
+ LOGF(")");
+ FORWARD(on_if_expr, num_types, sig_types);
+}
+
static WasmResult logging_on_load_expr(WasmOpcode opcode,
uint32_t alignment_log2,
uint32_t offset,
@@ -751,6 +789,16 @@ static WasmResult logging_on_load_expr(WasmOpcode opcode,
FORWARD(on_load_expr, opcode, alignment_log2, offset);
}
+static WasmResult logging_on_loop_expr(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data) {
+ LoggingContext* ctx = user_data;
+ LOGF("on_loop_expr(sig: ");
+ log_types(ctx, num_types, sig_types);
+ LOGF(")");
+ FORWARD(on_loop_expr, num_types, sig_types);
+}
+
static WasmResult logging_on_store_expr(WasmOpcode opcode,
uint32_t alignment_log2,
uint32_t offset,
@@ -1156,8 +1204,8 @@ WasmResult wasm_read_binary(WasmAllocator* allocator,
"expected valid result type");
}
- CALLBACK(on_signature, i, (WasmType)result_type, num_params,
- ctx->param_types.data);
+ CALLBACK(on_signature, i, num_params, ctx->param_types.data, num_results,
+ &result_type);
}
CALLBACK0(end_signature_section);
}
@@ -1296,15 +1344,39 @@ WasmResult wasm_read_binary(WasmAllocator* allocator,
in_u32_leb128(ctx, &num_exports, "export count");
CALLBACK(on_export_count, num_exports);
for (i = 0; i < num_exports; ++i) {
- uint32_t func_index;
- in_u32_leb128(ctx, &func_index, "export function index");
- RAISE_ERROR_UNLESS(func_index < num_function_signatures,
- "invalid export function index");
-
WasmStringSlice name;
in_str(ctx, &name, "export item name");
- CALLBACK(on_export, i, func_index, name);
+ uint8_t external_kind;
+ in_u8(ctx, &external_kind, "export external kind");
+ RAISE_ERROR_UNLESS(is_valid_external_kind(external_kind),
+ "invalid export external kind");
+
+ uint32_t item_index;
+ in_u32_leb128(ctx, &item_index, "export item index");
+ switch (external_kind) {
+ case WASM_EXTERNAL_KIND_FUNC:
+ RAISE_ERROR_UNLESS(item_index < num_function_signatures,
+ "invalid export func index");
+ break;
+ case WASM_EXTERNAL_KIND_TABLE:
+ RAISE_ERROR_UNLESS(item_index < num_tables,
+ "invalid export table index");
+ break;
+ case WASM_EXTERNAL_KIND_MEMORY:
+ RAISE_ERROR_UNLESS(item_index < num_memories,
+ "invalid export memory index");
+ break;
+ case WASM_EXTERNAL_KIND_GLOBAL:
+ RAISE_ERROR_UNLESS(item_index < num_globals,
+ "invalid export global index");
+ break;
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
+ }
+
+ CALLBACK(on_export, i, external_kind, item_index, name);
}
CALLBACK0(end_export_section);
}
@@ -1366,21 +1438,30 @@ WasmResult wasm_read_binary(WasmAllocator* allocator,
case WASM_OPCODE_BLOCK: {
uint8_t sig_type;
in_u8(ctx, &sig_type, "block signature type");
- CALLBACK(on_block_expr, sig_type);
+ RAISE_ERROR_UNLESS(is_inline_sig_type(sig_type),
+ "expected valid block signature type");
+ uint32_t num_types = sig_type == WASM_TYPE_VOID ? 0 : 1;
+ CALLBACK(on_block_expr, num_types, &sig_type);
break;
}
case WASM_OPCODE_LOOP: {
uint8_t sig_type;
in_u8(ctx, &sig_type, "loop signature type");
- CALLBACK(on_loop_expr, sig_type);
+ RAISE_ERROR_UNLESS(is_inline_sig_type(sig_type),
+ "expected valid block signature type");
+ uint32_t num_types = sig_type == WASM_TYPE_VOID ? 0 : 1;
+ CALLBACK(on_loop_expr, num_types, &sig_type);
break;
}
case WASM_OPCODE_IF: {
uint8_t sig_type;
in_u8(ctx, &sig_type, "if signature type");
- CALLBACK(on_if_expr, sig_type);
+ RAISE_ERROR_UNLESS(is_inline_sig_type(sig_type),
+ "expected valid block signature type");
+ uint32_t num_types = sig_type == WASM_TYPE_VOID ? 0 : 1;
+ CALLBACK(on_if_expr, num_types, &sig_type);
break;
}
diff --git a/src/wasm-binary-reader.h b/src/wasm-binary-reader.h
index 76d72b18..b24aae4a 100644
--- a/src/wasm-binary-reader.h
+++ b/src/wasm-binary-reader.h
@@ -47,9 +47,10 @@ typedef struct WasmBinaryReader {
WasmResult (*begin_signature_section)(void* user_data);
WasmResult (*on_signature_count)(uint32_t count, void* user_data);
WasmResult (*on_signature)(uint32_t index,
- WasmType result_type,
uint32_t param_count,
WasmType* param_types,
+ uint32_t result_count,
+ WasmType* result_types,
void* user_data);
WasmResult (*end_signature_section)(void* user_data);
@@ -118,6 +119,7 @@ typedef struct WasmBinaryReader {
WasmResult (*begin_export_section)(void* user_data);
WasmResult (*on_export_count)(uint32_t count, void* user_data);
WasmResult (*on_export)(uint32_t index,
+ WasmExternalKind kind,
uint32_t item_index,
WasmStringSlice name,
void* user_data);
@@ -145,7 +147,9 @@ typedef struct WasmBinaryReader {
/* function expressions; called between begin_function_body and
end_function_body */
WasmResult (*on_binary_expr)(WasmOpcode opcode, void* user_data);
- WasmResult (*on_block_expr)(uint8_t sig_type, void* user_data);
+ WasmResult (*on_block_expr)(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data);
WasmResult (*on_br_expr)(uint32_t depth, void* user_data);
WasmResult (*on_br_if_expr)(uint32_t depth, void* user_data);
WasmResult (*on_br_table_expr)(uint32_t num_targets,
@@ -167,12 +171,16 @@ typedef struct WasmBinaryReader {
WasmResult (*on_grow_memory_expr)(void* user_data);
WasmResult (*on_i32_const_expr)(uint32_t value, void* user_data);
WasmResult (*on_i64_const_expr)(uint64_t value, void* user_data);
- WasmResult (*on_if_expr)(uint8_t sig_type, void* user_data);
+ WasmResult (*on_if_expr)(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data);
WasmResult (*on_load_expr)(WasmOpcode opcode,
uint32_t alignment_log2,
uint32_t offset,
void* user_data);
- WasmResult (*on_loop_expr)(uint8_t sig_type, void* user_data);
+ WasmResult (*on_loop_expr)(uint32_t num_types,
+ WasmType* sig_types,
+ void* user_data);
WasmResult (*on_current_memory_expr)(void* user_data);
WasmResult (*on_nop_expr)(void* user_data);
WasmResult (*on_return_expr)(void* user_data);
diff --git a/src/wasm-binary-writer.c b/src/wasm-binary-writer.c
index 2fb7fe5c..9d47a558 100644
--- a/src/wasm-binary-writer.c
+++ b/src/wasm-binary-writer.c
@@ -677,6 +677,9 @@ static void write_module(Context* ctx, const WasmModule* module) {
case WASM_EXTERNAL_KIND_GLOBAL:
write_global_header(ctx, &import->global);
break;
+ case WASM_NUM_EXTERNAL_KINDS:
+ assert(0);
+ break;
}
}
end_section(ctx);
diff --git a/src/wasm-common.h b/src/wasm-common.h
index 3634fd5d..5a698bbe 100644
--- a/src/wasm-common.h
+++ b/src/wasm-common.h
@@ -125,11 +125,11 @@ typedef struct WasmBinaryErrorHandler {
/* matches binary format, do not change */
enum {
- WASM_TYPE_VOID,
- WASM_TYPE_I32,
- WASM_TYPE_I64,
- WASM_TYPE_F32,
- WASM_TYPE_F64,
+ WASM_TYPE_VOID = 0,
+ WASM_TYPE_I32 = 1,
+ WASM_TYPE_I64 = 2,
+ WASM_TYPE_F32 = 3,
+ WASM_TYPE_F64 = 4,
WASM_NUM_TYPES,
WASM_TYPE____ = WASM_TYPE_VOID, /* convenient for the opcode table below */
/* used when parsing multiple return types to signify an error */
@@ -144,6 +144,7 @@ typedef enum WasmExternalKind {
WASM_EXTERNAL_KIND_TABLE = 1,
WASM_EXTERNAL_KIND_MEMORY = 2,
WASM_EXTERNAL_KIND_GLOBAL = 3,
+ WASM_NUM_EXTERNAL_KINDS,
} WasmExternalKind;
typedef struct WasmLimits {
diff --git a/src/wasm-interpreter.h b/src/wasm-interpreter.h
index 8fc5f5c4..ca546216 100644
--- a/src/wasm-interpreter.h
+++ b/src/wasm-interpreter.h
@@ -81,8 +81,8 @@ WASM_DEFINE_VECTOR(uint8, WasmUint8);
/* TODO(binji): identical to WasmFuncSignature. Share? */
typedef struct WasmInterpreterFuncSignature {
- WasmType result_type;
WasmTypeVector param_types;
+ WasmTypeVector result_types;
} WasmInterpreterFuncSignature;
WASM_DEFINE_ARRAY(interpreter_func_signature, WasmInterpreterFuncSignature);
@@ -114,6 +114,12 @@ typedef struct WasmInterpreterTypedValue {
} WasmInterpreterTypedValue;
WASM_DEFINE_ARRAY(interpreter_typed_value, WasmInterpreterTypedValue);
+typedef struct WasmInterpreterGlobal {
+ WasmInterpreterTypedValue typed_value;
+ WasmBool mutable_;
+} WasmInterpreterGlobal;
+WASM_DEFINE_ARRAY(interpreter_global, WasmInterpreterGlobal);
+
struct WasmInterpreterModule;
struct WasmInterpreterImport;
@@ -127,7 +133,7 @@ typedef WasmResult (*WasmInterpreterImportCallback)(
typedef struct WasmInterpreterImport {
WasmStringSlice module_name;
- WasmStringSlice func_name;
+ WasmStringSlice field_name;
uint32_t sig_index;
WasmInterpreterImportCallback callback;
void* user_data;
@@ -148,7 +154,7 @@ typedef struct WasmInterpreterModule {
WasmInterpreterFuncTableEntryArray func_table;
WasmInterpreterImportArray imports;
WasmInterpreterExportArray exports;
- WasmInterpreterTypedValueArray globals;
+ WasmInterpreterGlobalArray globals;
WasmOutputBuffer istream;
uint32_t start_func_offset; /* == WASM_INVALID_OFFSET if not defined */
} WasmInterpreterModule;