Skip to content

Commit 6416611

Browse files
wip
1 parent 9656b8e commit 6416611

File tree

4 files changed

+61
-78
lines changed

4 files changed

+61
-78
lines changed

src/tools/wasm-ctor-eval.cpp

Lines changed: 57 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -68,40 +68,6 @@ bool isNullableAndMutable(Expression* ref, Index fieldIndex) {
6868
// the output.
6969
#define RECOMMENDATION "\n recommendation: "
7070

71-
class EvallingImportResolver : public ImportResolver {
72-
public:
73-
EvallingImportResolver() : stubLiteral({Literal(0)}) {};
74-
75-
// Return an unused stub value. We throw FailToEvalException on reading any
76-
// imported globals. We ignore the type and return an i32 literal since some
77-
// types can't be created anyway (e.g. ref none).
78-
Literals* getGlobalOrNull(ImportNames name, Type type) const override {
79-
return &stubLiteral;
80-
}
81-
82-
RuntimeTable* getTableOrNull(ImportNames name,
83-
const Table& type) const override {
84-
throw FailToEvalException{"Imported table access."};
85-
}
86-
87-
// We assume that each tag import is distinct. This is wrong if the same tag
88-
// instantiation is imported twice with different import names.
89-
Tag* getTagOrNull(ImportNames name,
90-
const Signature& signature) const override {
91-
auto [it, inserted] = importedTags.try_emplace(name, Tag{});
92-
if (inserted) {
93-
auto& tag = it->second;
94-
tag.type = HeapType(signature);
95-
}
96-
97-
return &it->second;
98-
}
99-
100-
private:
101-
mutable Literals stubLiteral;
102-
mutable std::unordered_map<ImportNames, Tag> importedTags;
103-
};
104-
10571
class EvallingRuntimeTable : public RuntimeTable {
10672
public:
10773
// TODO: putting EvallingModuleRunner into its own header would allow us to
@@ -180,6 +146,53 @@ class EvallingRuntimeTable : public RuntimeTable {
180146
const std::function<Literal(Name, Type)> makeFuncData;
181147
};
182148

149+
class EvallingImportResolver : public ImportResolver {
150+
public:
151+
EvallingImportResolver(const bool& instanceInitialized,
152+
const Module& wasm,
153+
std::function<Literal(Name, Type)> makeFuncData)
154+
: stubLiteral({Literal(0)}), instanceInitialized(instanceInitialized),
155+
wasm(wasm), makeFuncData(makeFuncData) {};
156+
157+
// Return an unused stub value. We throw FailToEvalException on reading any
158+
// imported globals. We ignore the type and return an i32 literal since some
159+
// types can't be created anyway (e.g. ref none).
160+
Literals* getGlobalOrNull(ImportNames name, Type type) const override {
161+
return &stubLiteral;
162+
}
163+
164+
RuntimeTable* getTableOrNull(ImportNames name,
165+
const Table& type) const override {
166+
auto [it, inserted] =
167+
tables.emplace(name,
168+
std::make_unique<EvallingRuntimeTable>(
169+
type, instanceInitialized, wasm, makeFuncData));
170+
return it->second.get();
171+
}
172+
173+
// We assume that each tag import is distinct. This is wrong if the same tag
174+
// instantiation is imported twice with different import names.
175+
Tag* getTagOrNull(ImportNames name,
176+
const Signature& signature) const override {
177+
auto [it, inserted] = importedTags.try_emplace(name, Tag{});
178+
if (inserted) {
179+
auto& tag = it->second;
180+
tag.type = HeapType(signature);
181+
}
182+
183+
return &it->second;
184+
}
185+
186+
private:
187+
mutable Literals stubLiteral;
188+
mutable std::unordered_map<ImportNames, std::unique_ptr<EvallingRuntimeTable>>
189+
tables;
190+
const bool& instanceInitialized;
191+
const Module& wasm;
192+
const std::function<Literal(Name, Type)> makeFuncData;
193+
mutable std::unordered_map<ImportNames, Tag> importedTags;
194+
};
195+
183196
class EvallingModuleRunner : public ModuleRunnerBase<EvallingModuleRunner> {
184197
public:
185198
EvallingModuleRunner(
@@ -190,17 +203,11 @@ class EvallingModuleRunner : public ModuleRunnerBase<EvallingModuleRunner> {
190203
: ModuleRunnerBase(
191204
wasm,
192205
externalInterface,
193-
std::make_shared<EvallingImportResolver>(),
194-
linkedInstances_,
195-
// TODO: Only use EvallingRuntimeTable for table imports. We can use
196-
// RealRuntimeTable for non-imported tables.
197-
[this, &instanceInitialized](Literal initial, Table table) {
198-
return std::make_unique<EvallingRuntimeTable>(
199-
table,
200-
instanceInitialized,
201-
this->wasm,
202-
[this](Name name, Type type) { return makeFuncData(name, type); });
203-
}) {}
206+
std::make_shared<EvallingImportResolver>(
207+
instanceInitialized,
208+
wasm,
209+
[this](Name name, Type type) { return makeFuncData(name, type); }),
210+
linkedInstances_) {}
204211

205212
Flow visitGlobalGet(GlobalGet* curr) {
206213
// Error on reads of imported globals.
@@ -1166,6 +1173,11 @@ EvalCtorOutcome evalCtor(EvallingModuleRunner& instance,
11661173
std::cout << " ...stopping due to non-constant func\n";
11671174
}
11681175
break;
1176+
} catch (TrapException& trap) {
1177+
if (!quiet) {
1178+
std::cout << " ...stopping due to trap\n";
1179+
}
1180+
break;
11691181
}
11701182

11711183
if (flow.breakTo == NONCONSTANT_FLOW) {

src/wasm-interpreter.h

Lines changed: 4 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -3177,25 +3177,15 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
31773177

31783178
std::unordered_map<Name, Tag*> allTags;
31793179

3180-
using CreateTableFunc = std::unique_ptr<RuntimeTable>(Literal, Table);
3181-
31823180
ModuleRunnerBase(
31833181
Module& wasm,
31843182
ExternalInterface* externalInterface,
31853183
std::shared_ptr<ImportResolver> importResolver,
3186-
std::map<Name, std::shared_ptr<SubType>> linkedInstances_ = {},
3187-
std::function<CreateTableFunc> createTable = {})
3184+
std::map<Name, std::shared_ptr<SubType>> linkedInstances_ = {})
31883185
: ExpressionRunner<SubType>(&wasm), wasm(wasm),
31893186
externalInterface(externalInterface),
31903187
linkedInstances(std::move(linkedInstances_)),
3191-
importResolver(std::move(importResolver)),
3192-
createTable(
3193-
createTable != nullptr
3194-
? std::move(createTable)
3195-
: static_cast<std::function<CreateTableFunc>>(
3196-
[](Literal initial, Table t) -> std::unique_ptr<RuntimeTable> {
3197-
return std::make_unique<RealRuntimeTable>(initial, t);
3198-
})) {
3188+
importResolver(std::move(importResolver)) {
31993189
// Set up a single shared CurrContinuations for all these linked instances,
32003190
// reusing one if it exists.
32013191
std::shared_ptr<ContinuationStore> shared;
@@ -3533,8 +3523,8 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
35333523
"We only support nullable tables today");
35343524

35353525
auto null = Literal::makeNull(table->type.getHeapType());
3536-
auto& runtimeTable =
3537-
definedTables.emplace_back(createTable(null, *table));
3526+
auto& runtimeTable = definedTables.emplace_back(
3527+
std::make_unique<RealRuntimeTable>(null, *table));
35383528
[[maybe_unused]] auto [_, inserted] =
35393529
allTables.try_emplace(table->name, runtimeTable.get());
35403530
assert(inserted && "Unexpected repeated table name");
@@ -5245,7 +5235,6 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
52455235
ExternalInterface* externalInterface;
52465236
std::map<Name, std::shared_ptr<SubType>> linkedInstances;
52475237
std::shared_ptr<ImportResolver> importResolver;
5248-
std::function<CreateTableFunc> createTable;
52495238
};
52505239

52515240
class ModuleRunner : public ModuleRunnerBase<ModuleRunner> {

test/lit/ctor-eval/table.init.wat

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@
1111
;; CHECK: (elem $init (i32.const 0) $nop)
1212
(elem $init (i32.const 0) $nop)
1313

14-
;; CHECK: (elem $later func $trap)
1514
(elem $later $trap)
1615

1716
(export "run" (func $run))
@@ -43,19 +42,11 @@
4342
(nop)
4443
)
4544

46-
;; CHECK: (func $trap (type $none_=>_none)
47-
;; CHECK-NEXT: (unreachable)
48-
;; CHECK-NEXT: )
4945
(func $trap (type $none_=>_none)
5046
(unreachable)
5147
)
5248
)
5349
;; CHECK: (func $run_3 (type $none_=>_none)
54-
;; CHECK-NEXT: (table.init $table $later
55-
;; CHECK-NEXT: (i32.const 0)
56-
;; CHECK-NEXT: (i32.const 0)
57-
;; CHECK-NEXT: (i32.const 1)
58-
;; CHECK-NEXT: )
5950
;; CHECK-NEXT: (call_indirect $table (type $none_=>_none)
6051
;; CHECK-NEXT: (i32.const 0)
6152
;; CHECK-NEXT: )

test/lit/ctor-eval/table.wat

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -32,8 +32,6 @@
3232

3333
;; CHECK: (elem $0 (i32.const 0) $nop)
3434

35-
;; CHECK: (elem declare func $trap)
36-
3735
;; CHECK: (export "run" (func $run_3))
3836

3937
;; CHECK: (func $nop (type $none_=>_none)
@@ -43,18 +41,11 @@
4341
(nop)
4442
)
4543

46-
;; CHECK: (func $trap (type $none_=>_none)
47-
;; CHECK-NEXT: (unreachable)
48-
;; CHECK-NEXT: )
4944
(func $trap (type $none_=>_none)
5045
(unreachable)
5146
)
5247
)
5348
;; CHECK: (func $run_3 (type $none_=>_none)
54-
;; CHECK-NEXT: (table.set $0
55-
;; CHECK-NEXT: (i32.const 0)
56-
;; CHECK-NEXT: (ref.func $trap)
57-
;; CHECK-NEXT: )
5849
;; CHECK-NEXT: (call_indirect $0 (type $none_=>_none)
5950
;; CHECK-NEXT: (i32.const 0)
6051
;; CHECK-NEXT: )

0 commit comments

Comments
 (0)