]> git.lizzy.rs Git - rust.git/blob - src/librustc_binaryen/BinaryenWrapper.cpp
Auto merge of #47956 - retep998:is-nibbles, r=BurntSushi
[rust.git] / src / librustc_binaryen / BinaryenWrapper.cpp
1 // Copyright 2017 The Rust Project Developers. See the COPYRIGHT
2 // file at the top-level directory of this distribution and at
3 // http://rust-lang.org/COPYRIGHT.
4 //
5 // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6 // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7 // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8 // option. This file may not be copied, modified, or distributed
9 // except according to those terms.
10
11 // This is a small C API inserted on top of the Binaryen C++ API which we use
12 // from Rust. Once we have a real linker for we'll be able to remove all this,
13 // and otherwise this is just all on a "as we need it" basis for now.
14
15 #include <stdint.h>
16 #include <string>
17 #include <sstream>
18 #include <stdlib.h>
19
20 #include "s2wasm.h"
21 #include "wasm-binary.h"
22 #include "wasm-linker.h"
23
24 using namespace wasm;
25
26 struct BinaryenRustModule {
27   BufferWithRandomAccess buffer;
28   std::string sourceMapJSON;
29 };
30
31 struct BinaryenRustModuleOptions {
32   uint64_t globalBase;
33   bool debug;
34   uint64_t stackAllocation;
35   uint64_t initialMem;
36   uint64_t maxMem;
37   bool importMemory;
38   bool ignoreUnknownSymbols;
39   bool debugInfo;
40   std::string startFunction;
41   std::string sourceMapUrl;
42
43   BinaryenRustModuleOptions() :
44     globalBase(0),
45     debug(false),
46     stackAllocation(0),
47     initialMem(0),
48     maxMem(0),
49     importMemory(false),
50     ignoreUnknownSymbols(false),
51     debugInfo(false),
52     startFunction(""),
53     sourceMapUrl("")
54   {}
55
56 };
57
58 extern "C" BinaryenRustModuleOptions*
59 BinaryenRustModuleOptionsCreate() {
60   return new BinaryenRustModuleOptions;
61 }
62
63 extern "C" void
64 BinaryenRustModuleOptionsFree(BinaryenRustModuleOptions *options) {
65   delete options;
66 }
67
68 extern "C" void
69 BinaryenRustModuleOptionsSetDebugInfo(BinaryenRustModuleOptions *options,
70                                       bool debugInfo) {
71   options->debugInfo = debugInfo;
72 }
73
74 extern "C" void
75 BinaryenRustModuleOptionsSetStart(BinaryenRustModuleOptions *options,
76                                   char *start) {
77   options->startFunction = start;
78 }
79
80 extern "C" void
81 BinaryenRustModuleOptionsSetSourceMapUrl(BinaryenRustModuleOptions *options,
82                                          char *sourceMapUrl) {
83   options->sourceMapUrl = sourceMapUrl;
84 }
85
86 extern "C" void
87 BinaryenRustModuleOptionsSetStackAllocation(BinaryenRustModuleOptions *options,
88                                             uint64_t stack) {
89   options->stackAllocation = stack;
90 }
91
92 extern "C" void
93 BinaryenRustModuleOptionsSetImportMemory(BinaryenRustModuleOptions *options,
94                                          bool import) {
95   options->importMemory = import;
96 }
97
98 extern "C" BinaryenRustModule*
99 BinaryenRustModuleCreate(const BinaryenRustModuleOptions *options,
100                          const char *assembly) {
101   Linker linker(
102       options->globalBase,
103       options->stackAllocation,
104       options->initialMem,
105       options->maxMem,
106       options->importMemory,
107       options->ignoreUnknownSymbols,
108       options->startFunction,
109       options->debug);
110
111   S2WasmBuilder mainbuilder(assembly, options->debug);
112   linker.linkObject(mainbuilder);
113   linker.layout();
114
115   auto ret = make_unique<BinaryenRustModule>();
116   {
117     WasmBinaryWriter writer(&linker.getOutput().wasm, ret->buffer, options->debug);
118     writer.setNamesSection(options->debugInfo);
119
120     std::unique_ptr<std::ostringstream> sourceMapStream = nullptr;
121     {
122       sourceMapStream = make_unique<std::ostringstream>();
123       writer.setSourceMap(sourceMapStream.get(), options->sourceMapUrl);
124     }
125
126     // FIXME: support symbol maps?
127     // writer.setSymbolMap(symbolMap);
128     writer.write();
129
130     if (sourceMapStream) {
131       ret->sourceMapJSON = sourceMapStream->str();
132     }
133   }
134   return ret.release();
135 }
136
137 extern "C" const uint8_t*
138 BinaryenRustModulePtr(const BinaryenRustModule *M) {
139   return M->buffer.data();
140 }
141
142 extern "C" size_t
143 BinaryenRustModuleLen(const BinaryenRustModule *M) {
144   return M->buffer.size();
145 }
146
147 extern "C" const char*
148 BinaryenRustModuleSourceMapPtr(const BinaryenRustModule *M) {
149   return M->sourceMapJSON.data();
150 }
151
152 extern "C" size_t
153 BinaryenRustModuleSourceMapLen(const BinaryenRustModule *M) {
154   return M->sourceMapJSON.length();
155 }
156
157 extern "C" void
158 BinaryenRustModuleFree(BinaryenRustModule *M) {
159   delete M;
160 }