Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(489)

Unified Diff: src/wasm/wasm-module.cc

Issue 2134593002: [wasm] cloning compiled module before instantiation (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: [wasm] cloning compiled module before instantiation Created 4 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/wasm/wasm-module.h ('k') | test/cctest/wasm/wasm-run-utils.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/wasm/wasm-module.cc
diff --git a/src/wasm/wasm-module.cc b/src/wasm/wasm-module.cc
index 27d9e63bc60cb00c4fbfea63c61680081f9dacfd..7123a127e648b3e58c3c03c0d6c1899a27e1e1b6 100644
--- a/src/wasm/wasm-module.cc
+++ b/src/wasm/wasm-module.cc
@@ -112,6 +112,21 @@ std::ostream& operator<<(std::ostream& os, const WasmFunctionName& pair) {
return os;
}
+Handle<JSFunction> WrapExportCodeAsJSFunction(
+ Isolate* isolate, Handle<Code> export_code, Handle<String> name, int arity,
+ Handle<JSObject> module_instance) {
+ Handle<SharedFunctionInfo> shared =
+ isolate->factory()->NewSharedFunctionInfo(name, export_code, false);
+ shared->set_length(arity);
+ shared->set_internal_formal_parameter_count(arity);
+ Handle<JSFunction> function = isolate->factory()->NewFunction(
+ isolate->wasm_function_map(), name, export_code);
+ function->set_shared(*shared);
+
+ function->SetInternalField(0, *module_instance);
+ return function;
+}
+
namespace {
// Internal constants for the layout of the module object.
const int kWasmModuleFunctionTable = 0;
@@ -131,14 +146,17 @@ const int kWasmModuleInternalFieldCount = 7;
// a snapshot produced by a compatible (==identical) v8 instance, we simply
// fail at instantiation time, in the face of invalid data.
enum CompiledWasmObjectFields {
- kFunctions, // FixedArray of Code
- kImportData, // maybe FixedArray of FixedArray respecting the
- // WasmImportMetadata structure.
- kExports, // maybe FixedArray of JSFunction
- kStartupFunction, // maybe JSFunction
- kModuleBytes, // maybe String
- kFunctionNameTable, // maybe ByteArray
- kMinRequiredMemory, // Smi. an uint32_t
+ kFunctions, // FixedArray of Code
+ kImportData, // maybe FixedArray of FixedArray respecting the
+ // WasmImportMetadata structure.
+ kExports, // maybe FixedArray of FixedArray of WasmExportMetadata
+ // structure
+ kStartupFunction, // maybe FixedArray of WasmExportMetadata structure
+ kIndirectFunctionTableSize, // Smi. Size of indirect function table.
+ kIndirectFunctionTablePrototype, // maybe FixedArray
+ kModuleBytes, // maybe String
+ kFunctionNameTable, // maybe ByteArray
+ kMinRequiredMemory, // Smi. an uint32_t
// The following 2 are either together present or absent:
kDataSegmentsInfo, // maybe FixedArray of FixedArray respecting the
// WasmSegmentInfo structure
@@ -158,6 +176,14 @@ enum WasmImportMetadata {
kWasmImportDataTableSize // Sentinel value.
};
+enum WasmExportMetadata {
+ kExportCode, // Code
+ kExportName, // String
+ kExportArity, // Smi, an int
+ kExportedFunctionIndex, // Smi, an uint32_t
+ kWasmExportMetadataTableSize // Sentinel value.
+};
+
enum WasmSegmentInfo {
kDestAddr, // Smi. an uint32_t
kSourceSize, // Smi. an uint32_t
@@ -229,22 +255,26 @@ void SaveDataSegmentInfo(Factory* factory, const WasmModule* module,
compiled_module->set(kDataSegments, *data);
}
-Handle<FixedArray> BuildFunctionTable(Isolate* isolate,
- const WasmModule* module) {
+MaybeHandle<FixedArray> BuildFunctionTable(Isolate* isolate,
+ const WasmModule* module) {
// Compute the size of the indirect function table
uint32_t table_size = module->FunctionTableSize();
if (table_size == 0) {
- return Handle<FixedArray>::null();
+ return MaybeHandle<FixedArray>();
}
+ DCHECK_GE(table_size, module->function_table.size());
+
Handle<FixedArray> fixed = isolate->factory()->NewFixedArray(2 * table_size);
- for (uint32_t i = 0;
- i < static_cast<uint32_t>(module->function_table.size());
- ++i) {
+ for (uint32_t i = 0; i < module->function_table.size(); ++i) {
const WasmFunction* function =
&module->functions[module->function_table[i]];
- fixed->set(i, Smi::FromInt(function->sig_index));
+ int fixed_array_index = static_cast<int>(i);
+ fixed->set(fixed_array_index, Smi::FromInt(function->sig_index));
+ fixed->set(fixed_array_index + table_size,
+ Smi::FromInt(module->function_table[fixed_array_index]));
}
+
// Set the remaining elements to -1 (instead of "undefined"). These
// elements are accessed directly as SMIs (without a check). On 64-bit
// platforms, it is possible to have the top bits of "undefined" take
@@ -258,6 +288,17 @@ Handle<FixedArray> BuildFunctionTable(Isolate* isolate,
return fixed;
}
+void PatchFunctionTable(Handle<Code> code,
+ Handle<FixedArray> old_indirect_table,
+ Handle<FixedArray> new_indirect_table) {
+ for (RelocIterator it(*code, 1 << RelocInfo::EMBEDDED_OBJECT); !it.done();
+ it.next()) {
+ if (it.rinfo()->target_object() == *old_indirect_table) {
+ it.rinfo()->set_target_object(*new_indirect_table);
+ }
+ }
+}
+
Handle<JSArrayBuffer> NewArrayBuffer(Isolate* isolate, size_t size) {
if (size > (WasmModule::kMaxMemPages * WasmModule::kPageSize)) {
// TODO(titzer): lift restriction on maximum memory allocated here.
@@ -386,11 +427,7 @@ void LinkModuleFunctions(Isolate* isolate,
std::vector<Handle<Code>>& functions) {
for (size_t i = 0; i < functions.size(); ++i) {
Handle<Code> code = functions[i];
- bool modified = LinkFunction(code, functions, Code::WASM_FUNCTION);
- if (modified) {
- Assembler::FlushICache(isolate, code->instruction_start(),
- code->instruction_size());
- }
+ LinkFunction(code, functions, Code::WASM_FUNCTION);
}
}
@@ -398,11 +435,15 @@ void LinkImports(Isolate* isolate, std::vector<Handle<Code>>& functions,
const std::vector<Handle<Code>>& imports) {
for (uint32_t i = 0; i < functions.size(); ++i) {
Handle<Code> code = functions[i];
- bool modified = LinkFunction(code, imports, Code::WASM_TO_JS_FUNCTION);
- if (modified) {
- Assembler::FlushICache(isolate, code->instruction_start(),
- code->instruction_size());
- }
+ LinkFunction(code, imports, Code::WASM_TO_JS_FUNCTION);
+ }
+}
+
+void FlushAssemblyCache(Isolate* isolate, Handle<FixedArray> functions) {
+ for (int i = 0; i < functions->length(); ++i) {
+ Handle<Code> code = functions->GetValueChecked<Code>(i);
+ Assembler::FlushICache(isolate, code->instruction_start(),
+ code->instruction_size());
}
}
@@ -424,8 +465,8 @@ WasmModule::WasmModule()
static MaybeHandle<JSFunction> ReportFFIError(
ErrorThrower& thrower, const char* error, uint32_t index,
Handle<String> module_name, MaybeHandle<String> function_name) {
- if (!function_name.is_null()) {
- Handle<String> function_name_handle = function_name.ToHandleChecked();
+ Handle<String> function_name_handle;
+ if (function_name.ToHandle(&function_name_handle)) {
thrower.Error("Import #%d module=\"%.*s\" function=\"%.*s\" error: %s",
index, module_name->length(), module_name->ToCString().get(),
function_name_handle->length(),
@@ -802,20 +843,6 @@ void CompileSequentially(Isolate* isolate, const WasmModule* module,
}
}
-void PopulateFunctionTable(WasmModuleInstance* instance) {
- if (!instance->function_table.is_null()) {
- uint32_t table_size = instance->module->FunctionTableSize();
- DCHECK_EQ(table_size * 2, instance->function_table->length());
- uint32_t populated_table_size =
- static_cast<uint32_t>(instance->module->function_table.size());
- for (uint32_t i = 0; i < populated_table_size; ++i) {
- instance->function_table->set(
- i + table_size,
- *instance->function_code[instance->module->function_table[i]]);
- }
- }
-}
-
void SetDebugSupport(Factory* factory, Handle<FixedArray> compiled_module,
Handle<JSObject> js_object) {
MaybeHandle<String> module_bytes_string =
@@ -901,8 +928,8 @@ bool SetupImports(Isolate* isolate, Handle<FixedArray> compiled_module,
std::vector<Handle<Code>> import_code;
MaybeHandle<FixedArray> maybe_import_data =
compiled_module->GetValue<FixedArray>(kImportData);
- if (!maybe_import_data.is_null()) {
- Handle<FixedArray> import_data = maybe_import_data.ToHandleChecked();
+ Handle<FixedArray> import_data;
+ if (maybe_import_data.ToHandle(&import_data)) {
if (!CompileWrappersToImportedFunctions(isolate, ffi, import_code,
import_data, thrower)) {
return false;
@@ -921,7 +948,6 @@ bool SetupImports(Isolate* isolate, Handle<FixedArray> compiled_module,
function_code[i] = code;
}
- instance->SetInternalField(kWasmModuleFunctionTable, Smi::FromInt(0));
LinkImports(isolate, function_code, import_code);
return true;
}
@@ -949,18 +975,21 @@ bool SetupExportsObject(Handle<FixedArray> compiled_module, Isolate* isolate,
Handle<String> exports_name = factory->InternalizeUtf8String("exports");
JSObject::AddProperty(instance, exports_name, exports_object, READ_ONLY);
}
- if (!maybe_exports.is_null()) {
- Handle<FixedArray> exports = maybe_exports.ToHandleChecked();
-
+ Handle<FixedArray> exports;
+ if (maybe_exports.ToHandle(&exports)) {
int exports_size = exports->length();
for (int i = 0; i < exports_size; ++i) {
if (thrower->error()) return false;
- Handle<JSFunction> function = exports->GetValueChecked<JSFunction>(i);
- RecordStats(isolate, function->code());
+ Handle<FixedArray> export_metadata =
+ exports->GetValueChecked<FixedArray>(i);
+ Handle<Code> export_code =
+ export_metadata->GetValueChecked<Code>(kExportCode);
+ RecordStats(isolate, *export_code);
Handle<String> name =
- Handle<String>(String::cast(function->shared()->name()));
- function->SetInternalField(0, *instance);
-
+ export_metadata->GetValueChecked<String>(kExportName);
+ int arity = Smi::cast(export_metadata->get(kExportArity))->value();
+ Handle<JSFunction> function = WrapExportCodeAsJSFunction(
+ isolate, export_code, name, arity, instance);
desc.set_value(function);
Maybe<bool> status = JSReceiver::DefineOwnProperty(
isolate, exports_object, name, &desc, Object::THROW_ON_ERROR);
@@ -991,13 +1020,17 @@ MaybeHandle<FixedArray> WasmModule::CompileFunctions(Isolate* isolate) const {
MaybeHandle<FixedArray> nothing;
WasmModuleInstance temp_instance_for_compilation(this);
- temp_instance_for_compilation.function_table =
- BuildFunctionTable(isolate, this);
temp_instance_for_compilation.context = isolate->native_context();
temp_instance_for_compilation.mem_size = GetMinModuleMemSize(this);
temp_instance_for_compilation.mem_start = nullptr;
temp_instance_for_compilation.globals_start = nullptr;
+ MaybeHandle<FixedArray> indirect_table = BuildFunctionTable(isolate, this);
+ if (!indirect_table.is_null()) {
+ temp_instance_for_compilation.function_table =
+ indirect_table.ToHandleChecked();
+ }
+
HistogramTimerScope wasm_compile_module_time_scope(
isolate->counters()->wasm_compile_module_time());
@@ -1028,8 +1061,6 @@ MaybeHandle<FixedArray> WasmModule::CompileFunctions(Isolate* isolate) const {
}
if (thrower.error()) return nothing;
- LinkModuleFunctions(isolate, temp_instance_for_compilation.function_code);
-
// At this point, compilation has completed. Update the code table.
for (size_t i = FLAG_skip_compiling_wasm_funcs;
i < temp_instance_for_compilation.function_code.size(); ++i) {
@@ -1037,8 +1068,6 @@ MaybeHandle<FixedArray> WasmModule::CompileFunctions(Isolate* isolate) const {
compiled_functions->set(static_cast<int>(i), code);
}
- PopulateFunctionTable(&temp_instance_for_compilation);
-
// Create the compiled module object, and populate with compiled functions
// and information needed at instantiation time. This object needs to be
// serializable. Instantiation may occur off a deserialized version of this
@@ -1046,27 +1075,41 @@ MaybeHandle<FixedArray> WasmModule::CompileFunctions(Isolate* isolate) const {
Handle<FixedArray> ret =
factory->NewFixedArray(kCompiledWasmObjectTableSize, TENURED);
ret->set(kFunctions, *compiled_functions);
-
+ ret->set(kIndirectFunctionTableSize,
+ Smi::FromInt(static_cast<int>(function_table.size())));
+ if (!indirect_table.is_null()) {
+ ret->set(kIndirectFunctionTablePrototype,
+ *indirect_table.ToHandleChecked());
+ }
Handle<FixedArray> import_data = GetImportsMetadata(factory, this);
ret->set(kImportData, *import_data);
// Compile export functions.
int export_size = static_cast<int>(export_table.size());
- Handle<JSFunction> startup_fct;
+ Handle<Code> startup_fct;
if (export_size > 0) {
Handle<FixedArray> exports = factory->NewFixedArray(export_size, TENURED);
for (int i = 0; i < export_size; ++i) {
+ Handle<FixedArray> export_metadata =
+ factory->NewFixedArray(kWasmExportMetadataTableSize, TENURED);
const WasmExport& exp = export_table[i];
WasmName str = GetName(exp.name_offset, exp.name_length);
Handle<String> name = factory->InternalizeUtf8String(str);
Handle<Code> code =
temp_instance_for_compilation.function_code[exp.func_index];
- Handle<JSFunction> function = compiler::CompileJSToWasmWrapper(
- isolate, &module_env, name, code, exp.func_index);
+ Handle<Code> export_code = compiler::CompileJSToWasmWrapper(
+ isolate, &module_env, code, exp.func_index);
if (thrower.error()) return nothing;
- exports->set(i, *function);
+ export_metadata->set(kExportCode, *export_code);
+ export_metadata->set(kExportName, *name);
+ export_metadata->set(
+ kExportArity, Smi::FromInt(static_cast<int>(
+ functions[exp.func_index].sig->parameter_count())));
+ export_metadata->set(kExportedFunctionIndex,
+ Smi::FromInt(static_cast<int>(exp.func_index)));
+ exports->set(i, *export_metadata);
if (exp.func_index == start_function_index) {
- startup_fct = function;
+ startup_fct = export_code;
}
}
ret->set(kExports, *exports);
@@ -1074,15 +1117,20 @@ MaybeHandle<FixedArray> WasmModule::CompileFunctions(Isolate* isolate) const {
// Compile startup function, if we haven't already.
if (start_function_index >= 0) {
+ uint32_t index = static_cast<uint32_t>(start_function_index);
HandleScope scope(isolate);
if (startup_fct.is_null()) {
- uint32_t index = static_cast<uint32_t>(start_function_index);
- Handle<String> name = factory->NewStringFromStaticChars("start");
Handle<Code> code = temp_instance_for_compilation.function_code[index];
- startup_fct = compiler::CompileJSToWasmWrapper(isolate, &module_env, name,
- code, index);
+ DCHECK_EQ(0, functions[index].sig->parameter_count());
+ startup_fct =
+ compiler::CompileJSToWasmWrapper(isolate, &module_env, code, index);
}
- ret->set(kStartupFunction, *startup_fct);
+ Handle<FixedArray> metadata =
+ factory->NewFixedArray(kWasmExportMetadataTableSize, TENURED);
+ metadata->set(kExportCode, *startup_fct);
+ metadata->set(kExportArity, Smi::FromInt(0));
+ metadata->set(kExportedFunctionIndex, Smi::FromInt(start_function_index));
+ ret->set(kStartupFunction, *metadata);
}
// TODO(wasm): saving the module bytes for debugging is wasteful. We should
@@ -1109,6 +1157,104 @@ MaybeHandle<FixedArray> WasmModule::CompileFunctions(Isolate* isolate) const {
return ret;
}
+void PatchJSWrapper(Isolate* isolate, Handle<Code> wrapper,
+ Handle<Code> new_target) {
+ AllowDeferredHandleDereference embedding_raw_address;
+ bool seen = false;
+ for (RelocIterator it(*wrapper, 1 << RelocInfo::CODE_TARGET); !it.done();
+ it.next()) {
+ Code* target = Code::GetCodeFromTargetAddress(it.rinfo()->target_address());
+ if (target->kind() == Code::WASM_FUNCTION) {
+ DCHECK(!seen);
+ seen = true;
+ it.rinfo()->set_target_address(new_target->instruction_start(),
+ UPDATE_WRITE_BARRIER, SKIP_ICACHE_FLUSH);
+ }
+ }
+ CHECK(seen);
+ Assembler::FlushICache(isolate, wrapper->instruction_start(),
+ wrapper->instruction_size());
+}
+
+Handle<FixedArray> CloneModuleForInstance(Isolate* isolate,
+ Handle<FixedArray> original) {
+ Factory* factory = isolate->factory();
+ Handle<FixedArray> clone = factory->CopyFixedArray(original);
+
+ Handle<FixedArray> orig_wasm_functions =
+ original->GetValueChecked<FixedArray>(kFunctions);
+ Handle<FixedArray> clone_wasm_functions =
+ factory->CopyFixedArray(orig_wasm_functions);
+ clone->set(kFunctions, *clone_wasm_functions);
+
+ MaybeHandle<FixedArray> maybe_indirect_table =
+ original->GetValue<FixedArray>(kIndirectFunctionTablePrototype);
+
+ Handle<FixedArray> indirect_table;
+ Handle<FixedArray> old_table;
+ if (maybe_indirect_table.ToHandle(&old_table)) {
+ indirect_table = factory->CopyFixedArray(old_table);
+ clone->set(kIndirectFunctionTablePrototype, *indirect_table);
+ }
+
+ for (int i = 0; i < orig_wasm_functions->length(); ++i) {
+ Handle<Code> orig_code = orig_wasm_functions->GetValueChecked<Code>(i);
+ Handle<Code> cloned_code = factory->CopyCode(orig_code);
+ clone_wasm_functions->set(i, *cloned_code);
+ if (!maybe_indirect_table.is_null()) {
+ PatchFunctionTable(cloned_code, old_table, indirect_table);
+ }
+ }
+
+ MaybeHandle<FixedArray> maybe_orig_exports =
+ original->GetValue<FixedArray>(kExports);
+ Handle<FixedArray> orig_exports;
+ if (maybe_orig_exports.ToHandle(&orig_exports)) {
+ Handle<FixedArray> cloned_exports = factory->CopyFixedArray(orig_exports);
+ clone->set(kExports, *cloned_exports);
+ for (int i = 0; i < orig_exports->length(); ++i) {
+ Handle<FixedArray> export_metadata =
+ orig_exports->GetValueChecked<FixedArray>(i);
+ Handle<FixedArray> clone_metadata =
+ factory->CopyFixedArray(export_metadata);
+ cloned_exports->set(i, *clone_metadata);
+ Handle<Code> orig_code =
+ export_metadata->GetValueChecked<Code>(kExportCode);
+ Handle<Code> cloned_code = factory->CopyCode(orig_code);
+ clone_metadata->set(kExportCode, *cloned_code);
+ // TODO(wasm): This is actually a uint32_t, but since FixedArray indexes
+ // in int, we are taking the risk of invalid values.
+ int exported_fct_index =
+ Smi::cast(export_metadata->get(kExportedFunctionIndex))->value();
+ CHECK_GE(exported_fct_index, 0);
+ CHECK_LT(exported_fct_index, clone_wasm_functions->length());
+ Handle<Code> new_target =
+ clone_wasm_functions->GetValueChecked<Code>(exported_fct_index);
+ PatchJSWrapper(isolate, cloned_code, new_target);
+ }
+ }
+
+ MaybeHandle<FixedArray> maybe_startup =
+ original->GetValue<FixedArray>(kStartupFunction);
+ if (!maybe_startup.is_null()) {
+ Handle<FixedArray> startup_metadata =
+ factory->CopyFixedArray(maybe_startup.ToHandleChecked());
+ Handle<Code> startup_fct_clone =
+ factory->CopyCode(startup_metadata->GetValueChecked<Code>(kExportCode));
+ startup_metadata->set(kExportCode, *startup_fct_clone);
+ clone->set(kStartupFunction, *startup_metadata);
+ // TODO(wasm): see todo above about int vs size_t indexing in FixedArray.
+ int startup_fct_index =
+ Smi::cast(startup_metadata->get(kExportedFunctionIndex))->value();
+ CHECK_GE(startup_fct_index, 0);
+ CHECK_LT(startup_fct_index, clone_wasm_functions->length());
+ Handle<Code> new_target =
+ clone_wasm_functions->GetValueChecked<Code>(startup_fct_index);
+ PatchJSWrapper(isolate, startup_fct_clone, new_target);
+ }
+ return clone;
+}
+
// Instantiates a wasm module as a JSObject.
// * allocates a backing store of {mem_size} bytes.
// * installs a named property "memory" for that buffer if exported
@@ -1122,10 +1268,21 @@ MaybeHandle<JSObject> WasmModule::Instantiate(
ErrorThrower thrower(isolate, "WasmModule::Instantiate()");
Factory* factory = isolate->factory();
+ compiled_module = CloneModuleForInstance(isolate, compiled_module);
+
// These fields are compulsory.
Handle<FixedArray> code_table =
compiled_module->GetValueChecked<FixedArray>(kFunctions);
+ {
+ std::vector<Handle<Code>> functions(
+ static_cast<size_t>(code_table->length()));
+ for (int i = 0; i < code_table->length(); ++i) {
+ functions[static_cast<size_t>(i)] = code_table->GetValueChecked<Code>(i);
+ }
+ LinkModuleFunctions(isolate, functions);
+ }
+
RecordStats(isolate, code_table);
MaybeHandle<JSObject> nothing;
@@ -1146,14 +1303,36 @@ MaybeHandle<JSObject> WasmModule::Instantiate(
SetDebugSupport(factory, compiled_module, js_object);
+ FlushAssemblyCache(isolate, code_table);
+
+ MaybeHandle<FixedArray> maybe_indirect_table =
+ compiled_module->GetValue<FixedArray>(kIndirectFunctionTablePrototype);
+ Handle<FixedArray> indirect_table;
+ if (maybe_indirect_table.ToHandle(&indirect_table)) {
+ int table_size =
+ Smi::cast(compiled_module->get(kIndirectFunctionTableSize))->value();
+ int half_point = indirect_table->length() / 2;
+ for (int i = half_point; i < half_point + table_size; ++i) {
+ int index = Smi::cast(indirect_table->get(i))->value();
+ DCHECK_GE(index, 0);
+ DCHECK_LT(index, code_table->length());
+ indirect_table->set(i, code_table->get(index));
+ }
+ js_object->SetInternalField(kWasmModuleFunctionTable, *indirect_table);
+ }
+
// Run the start function if one was specified.
- MaybeHandle<JSFunction> maybe_startup_fct =
- compiled_module->GetValue<JSFunction>(kStartupFunction);
- if (!maybe_startup_fct.is_null()) {
+ MaybeHandle<FixedArray> maybe_startup_fct =
+ compiled_module->GetValue<FixedArray>(kStartupFunction);
+ Handle<FixedArray> metadata;
+ if (maybe_startup_fct.ToHandle(&metadata)) {
HandleScope scope(isolate);
- Handle<JSFunction> startup_fct = maybe_startup_fct.ToHandleChecked();
- RecordStats(isolate, startup_fct->code());
- startup_fct->SetInternalField(0, *js_object);
+ Handle<Code> startup_code = metadata->GetValueChecked<Code>(kExportCode);
+ int arity = Smi::cast(metadata->get(kExportArity))->value();
+ Handle<JSFunction> startup_fct = WrapExportCodeAsJSFunction(
+ isolate, startup_code, factory->InternalizeUtf8String("start"), arity,
+ js_object);
+ RecordStats(isolate, *startup_code);
// Call the JS function.
Handle<Object> undefined = isolate->factory()->undefined_value();
MaybeHandle<Object> retval =
@@ -1334,10 +1513,9 @@ int32_t CompileAndRunWasmModule(Isolate* isolate, const byte* module_start,
if (compiled_module.is_null()) return -1;
Handle<JSObject> instance =
- module
- ->Instantiate(isolate, compiled_module.ToHandleChecked(),
- Handle<JSReceiver>::null(),
- Handle<JSArrayBuffer>::null())
+ WasmModule::Instantiate(isolate, compiled_module.ToHandleChecked(),
+ Handle<JSReceiver>::null(),
+ Handle<JSArrayBuffer>::null())
.ToHandleChecked();
Handle<Name> exports = isolate->factory()->InternalizeUtf8String("exports");
« no previous file with comments | « src/wasm/wasm-module.h ('k') | test/cctest/wasm/wasm-run-utils.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698