3333#include " wasm-builder.h"
3434#include " ast/memory-utils.h"
3535#include " ast/global-utils.h"
36+ #include " ast/import-utils.h"
37+ #include " ast/literal-utils.h"
3638
3739using namespace wasm ;
3840
@@ -78,11 +80,6 @@ class EvallingGlobalManager {
7880 }
7981 throw FailToEvalException (std::string (" tried to access a dangerous (import-initialized) global: " ) + name.str + extra);
8082 }
81- if (sealed) {
82- if (globals.find (name) == globals.end ()) {
83- throw FailToEvalException (std::string (" tried to access missing global: " ) + name.str );
84- }
85- }
8683 return globals[name];
8784 }
8885
@@ -114,6 +111,13 @@ class EvallingGlobalManager {
114111 }
115112};
116113
114+ enum {
115+ // put the stack in some ridiculously high location
116+ STACK_START = 0x40000000 ,
117+ // use a ridiculously large stack size
118+ STACK_SIZE = 32 * 1024 * 1024
119+ };
120+
117121class EvallingModuleInstance : public ModuleInstanceBase <EvallingGlobalManager, EvallingModuleInstance> {
118122public:
119123 EvallingModuleInstance (Module& wasm, ExternalInterface* externalInterface) : ModuleInstanceBase(wasm, externalInterface) {
@@ -138,13 +142,6 @@ class EvallingModuleInstance : public ModuleInstanceBase<EvallingGlobalManager,
138142 }
139143 }
140144
141- enum {
142- // put the stack in some ridiculously high location
143- STACK_START = 0x40000000 ,
144- // use a ridiculously large stack size
145- STACK_SIZE = 32 * 1024 * 1024
146- };
147-
148145 std::vector<char > stack;
149146
150147 // create C stack space for us to use. We do *NOT* care about their contents,
@@ -153,13 +150,6 @@ class EvallingModuleInstance : public ModuleInstanceBase<EvallingGlobalManager,
153150 void setupEnvironment () {
154151 // prepare scratch memory
155152 stack.resize (STACK_SIZE);
156- // fill usable values for stack imports
157- if (auto * stackTop = GlobalUtils::getGlobalInitializedToImport (wasm, " env" , " STACKTOP" )) {
158- globals[stackTop->name ] = Literal (int32_t (STACK_START));
159- }
160- if (auto * stackMax = GlobalUtils::getGlobalInitializedToImport (wasm, " env" , " STACK_MAX" )) {
161- globals[stackMax->name ] = Literal (int32_t (STACK_START));
162- }
163153 // tell the module to accept writes up to the stack end
164154 auto total = STACK_START + STACK_SIZE;
165155 memorySize = total / Memory::kPageSize ;
@@ -181,6 +171,32 @@ struct CtorEvalExternalInterface : EvallingModuleInstance::ExternalInterface {
181171 }
182172
183173 void importGlobals (EvallingGlobalManager& globals, Module& wasm_) override {
174+ // fill usable values for stack imports, and globals initialized to them
175+ if (auto * stackTop = ImportUtils::getImport (wasm_, " env" , " STACKTOP" )) {
176+ globals[stackTop->name ] = Literal (int32_t (STACK_START));
177+ if (auto * stackTop = GlobalUtils::getGlobalInitializedToImport (wasm_, " env" , " STACKTOP" )) {
178+ globals[stackTop->name ] = Literal (int32_t (STACK_START));
179+ }
180+ }
181+ if (auto * stackMax = ImportUtils::getImport (wasm_, " env" , " STACK_MAX" )) {
182+ globals[stackMax->name ] = Literal (int32_t (STACK_START));
183+ if (auto * stackMax = GlobalUtils::getGlobalInitializedToImport (wasm_, " env" , " STACK_MAX" )) {
184+ globals[stackMax->name ] = Literal (int32_t (STACK_START));
185+ }
186+ }
187+ // fill in fake values for everything else, which is dangerous to use
188+ for (auto & global : wasm_.globals ) {
189+ if (globals.find (global->name ) == globals.end ()) {
190+ globals[global->name ] = LiteralUtils::makeLiteralZero (global->type );
191+ }
192+ }
193+ for (auto & import : wasm_.imports ) {
194+ if (import ->kind == ExternalKind::Global) {
195+ if (globals.find (import ->name ) == globals.end ()) {
196+ globals[import ->name ] = LiteralUtils::makeLiteralZero (import ->globalType );
197+ }
198+ }
199+ }
184200 }
185201
186202 Literal callImport (Import *import , LiteralList& arguments) override {
@@ -248,9 +264,9 @@ struct CtorEvalExternalInterface : EvallingModuleInstance::ExternalInterface {
248264 template <typename T>
249265 T* getMemory (Address address) {
250266 // if memory is on the stack, use the stack
251- if (address >= instance-> STACK_START ) {
252- Address relative = address - instance-> STACK_START ;
253- if (relative + sizeof (T) > instance-> STACK_SIZE ) {
267+ if (address >= STACK_START) {
268+ Address relative = address - STACK_START;
269+ if (relative + sizeof (T) > STACK_SIZE) {
254270 throw FailToEvalException (" stack usage too high" );
255271 }
256272 // in range, all is good, use the stack
0 commit comments