summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/wasm-interpreter.h4
-rw-r--r--src/wasm-js.cpp63
2 files changed, 65 insertions, 2 deletions
diff --git a/src/wasm-interpreter.h b/src/wasm-interpreter.h
index ede2f00df..5d6130641 100644
--- a/src/wasm-interpreter.h
+++ b/src/wasm-interpreter.h
@@ -17,7 +17,7 @@ public:
typedef std::vector<Literal> LiteralList;
struct ExternalInterface {
- virtual Literal callImport(IString name, LiteralList& arguments) = 0;
+ virtual Literal callImport(Import* import, LiteralList& arguments) = 0;
virtual Literal load(Load* load, Literal ptr) = 0;
virtual Literal store(Store* store, Literal ptr, Literal value) = 0;
};
@@ -146,7 +146,7 @@ public:
LiteralList arguments;
Flow flow = generateArguments(curr->operands, arguments);
if (flow.breaking()) return flow;
- return instance.externalInterface->callImport(curr->target, arguments);
+ return instance.externalInterface->callImport(&instance.wasm.imports[curr->target], arguments);
}
Flow visitCallIndirect(CallIndirect *curr) override {
Flow target = visit(curr->target);
diff --git a/src/wasm-js.cpp b/src/wasm-js.cpp
index ccc589485..e2ef47bbb 100644
--- a/src/wasm-js.cpp
+++ b/src/wasm-js.cpp
@@ -1,4 +1,67 @@
+//
+// wasm intepreter for asm2wasm output, in a js environment. receives asm.js,
+// generates a runnable module suitable as a polyfill.
+//
+
+#include <emscripten.h>
+
+#include "asm2wasm.h"
#include "wasm-interpreter.h"
+using namespace cashew;
+using namespace wasm;
+
+// receives asm.js code, parses into wasm and returns an instance handle.
+// this creates a module, an external interface, and a module instance,
+// all of which are then the responsibility of the caller to free.
+// note: this modifies the input.
+extern "C" ModuleInstance* EMSCRIPTEN_KEEPALIVE load_asm(char *input) {
+ // emcc --separate-asm modules look like
+ //
+ // Module["asm"] = (function(global, env, buffer) {
+ // ..
+ // });
+ //
+ // we need to clean that up.
+ size_t num = strlen(input);
+ assert(*input == 'M');
+ while (*input != 'f') {
+ input++;
+ num--;
+ }
+ char *end = input + num - 1;
+ while (*end != '}') {
+ *end = 0;
+ end--;
+ }
+
+ if (debug) std::cerr << "parsing...\n";
+ cashew::Parser<Ref, DotZeroValueBuilder> builder;
+ Ref asmjs = builder.parseToplevel(input);
+
+ Module* wasm = new Module();
+
+ if (debug) std::cerr << "wasming...\n";
+ Asm2WasmBuilder asm2wasm(*wasm);
+ asm2wasm.processAsm(asmjs);
+
+ if (debug) std::cerr << "optimizing...\n";
+ asm2wasm.optimize();
+
+ if (debug) std::cerr << "returning instance.\n";
+
+ struct JSExternalInterface : ModuleInstance::ExternalInterface {
+ Literal callImport(Import *import, ModuleInstance::LiteralList& arguments) override {
+ }
+
+ Literal load(Load* load, Literal ptr) override {
+ }
+
+ Literal store(Store* store, Literal ptr, Literal value) override {
+ }
+ };
+
+ return new ModuleInstance(*wasm, new JSExternalInterface());
+}