summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorAlon Zakai <alonzakai@gmail.com>2016-08-28 09:02:18 -0700
committerAlon Zakai <alonzakai@gmail.com>2016-09-07 09:55:55 -0700
commit42ad2cdbe5baa32dd1b0aea143a4e45f81e8b9b5 (patch)
treee3bc9183e04bd049d7b497c61425e44989f609fd /src
parent304fef1d997f1c43249996737ef7ce6deb961481 (diff)
downloadbinaryen-42ad2cdbe5baa32dd1b0aea143a4e45f81e8b9b5.tar.gz
binaryen-42ad2cdbe5baa32dd1b0aea143a4e45f81e8b9b5.tar.bz2
binaryen-42ad2cdbe5baa32dd1b0aea143a4e45f81e8b9b5.zip
import memory #684
Diffstat (limited to 'src')
-rw-r--r--src/asm2wasm.h11
-rw-r--r--src/js/wasm.js-post.js7
-rw-r--r--src/wasm-js.cpp29
3 files changed, 41 insertions, 6 deletions
diff --git a/src/asm2wasm.h b/src/asm2wasm.h
index f88bf9ffc..306a953a7 100644
--- a/src/asm2wasm.h
+++ b/src/asm2wasm.h
@@ -817,11 +817,22 @@ void Asm2WasmBuilder::processAsm(Ref ast) {
wasm.addExport(export_);
}
+#if 0
+ // export memory
auto memoryExport = make_unique<Export>();
memoryExport->name = MEMORY;
memoryExport->value = Name::fromInt(0);
memoryExport->kind = Export::Memory;
wasm.addExport(memoryExport.release());
+#else
+ // import memory
+ auto memoryImport = make_unique<Import>();
+ memoryImport->name = MEMORY;
+ memoryImport->module = ENV;
+ memoryImport->base = MEMORY;
+ memoryImport->kind = Import::Memory;
+ wasm.addImport(memoryImport.release());
+#endif
#if 0 // enable asm2wasm i64 optimizations when browsers have consistent i64 support in wasm
if (udivmoddi4.is() && getTempRet0.is()) {
diff --git a/src/js/wasm.js-post.js b/src/js/wasm.js-post.js
index 05c648ed0..dcffb1ee8 100644
--- a/src/js/wasm.js-post.js
+++ b/src/js/wasm.js-post.js
@@ -183,7 +183,7 @@ function integrateWasmJS(Module) {
return false;
}
exports = instance.exports;
- mergeMemory(exports.memory);
+ if (exports.memory) mergeMemory(exports.memory);
Module["usingWasm"] = true;
@@ -274,6 +274,11 @@ function integrateWasmJS(Module) {
global = fixImports(global);
env = fixImports(env);
+ // import memory
+ if (!env['memory']) {
+ env['memory'] = providedBuffer;
+ }
+
// try the methods. each should return the exports if it succeeded
var exports;
diff --git a/src/wasm-js.cpp b/src/wasm-js.cpp
index fc27bc37a..31448d2a0 100644
--- a/src/wasm-js.cpp
+++ b/src/wasm-js.cpp
@@ -169,17 +169,36 @@ extern "C" void EMSCRIPTEN_KEEPALIVE instantiate() {
struct JSExternalInterface : ModuleInstance::ExternalInterface {
void init(Module& wasm, ModuleInstance& instance) override {
- // create a new buffer here, just like native wasm support would.
- EM_ASM_({
- Module['outside']['newBuffer'] = new ArrayBuffer($0);
- }, wasm.memory.initial * Memory::kPageSize);
+ // look for imported memory
+ {
+ bool found = false;
+ for (auto& import : wasm.imports) {
+ if (import->module == ENV && import->base == MEMORY) {
+ assert(import->kind == Import::Memory);
+ // memory is imported
+ EM_ASM({
+ Module['outside']['tempBuffer'] = Module['lookupImport']('env', 'memory');
+ });
+ found = true;
+ }
+ }
+ if (!found) {
+ // no memory import; create a new buffer here, just like native wasm support would.
+ EM_ASM_({
+ Module['outside']['tempBuffer'] = Module['outside']['newBuffer'] = new ArrayBuffer($0);
+ }, wasm.memory.initial * Memory::kPageSize);
+ }
+ }
for (auto segment : wasm.memory.segments) {
EM_ASM_({
var source = Module['HEAP8'].subarray($1, $1 + $2);
- var target = new Int8Array(Module['outside']['newBuffer']);
+ var target = new Int8Array(Module['outside']['tempBuffer']);
target.set(source, $0);
}, ConstantExpressionRunner(instance.globals).visit(segment.offset).value.geti32(), &segment.data[0], segment.data.size());
}
+ EM_ASM({
+ Module['outside']['tempBuffer'] = null;
+ });
// Table support is in a JS array. If the entry is a number, it's a function pointer. If not, it's a JS method to be called directly
// TODO: make them all JS methods, wrapping a dynCall where necessary?
EM_ASM_({