summaryrefslogtreecommitdiff
path: root/src/passes
diff options
context:
space:
mode:
Diffstat (limited to 'src/passes')
-rw-r--r--src/passes/Asyncify.cpp10
-rw-r--r--src/passes/CodeFolding.cpp2
-rw-r--r--src/passes/DeNaN.cpp6
-rw-r--r--src/passes/DeadArgumentElimination.cpp9
-rw-r--r--src/passes/Directize.cpp2
-rw-r--r--src/passes/DuplicateImportElimination.cpp2
-rw-r--r--src/passes/FuncCastEmulation.cpp4
-rw-r--r--src/passes/GenerateDynCalls.cpp31
-rw-r--r--src/passes/I64ToI32Lowering.cpp8
-rw-r--r--src/passes/Inlining.cpp8
-rw-r--r--src/passes/InstrumentLocals.cpp6
-rw-r--r--src/passes/InstrumentMemory.cpp6
-rw-r--r--src/passes/LegalizeJSInterface.cpp37
-rw-r--r--src/passes/LogExecution.cpp7
-rw-r--r--src/passes/Print.cpp10
-rw-r--r--src/passes/ReReloop.cpp4
-rw-r--r--src/passes/RemoveImports.cpp2
-rw-r--r--src/passes/ReorderLocals.cpp2
-rw-r--r--src/passes/SafeHeap.cpp44
-rw-r--r--src/passes/StackCheck.cpp6
-rw-r--r--src/passes/TrapMode.cpp18
-rw-r--r--src/passes/Vacuum.cpp4
22 files changed, 110 insertions, 118 deletions
diff --git a/src/passes/Asyncify.cpp b/src/passes/Asyncify.cpp
index 4bd9dee61..d0d03c9d1 100644
--- a/src/passes/Asyncify.cpp
+++ b/src/passes/Asyncify.cpp
@@ -862,7 +862,7 @@ struct AsyncifyFlow : public Pass {
State::Rewinding), // TODO: such checks can be !normal
makeCallIndexPop()),
process(func->body)});
- if (func->sig.results != Type::none) {
+ if (func->getResults() != Type::none) {
// Rewriting control flow may alter things; make sure the function ends in
// something valid (which the optimizer can remove later).
block->list.push_back(builder->makeUnreachable());
@@ -1204,7 +1204,7 @@ struct AsyncifyLocals : public WalkerPass<PostWalker<AsyncifyLocals>> {
walk(func->body);
// After the normal function body, emit a barrier before the postamble.
Expression* barrier;
- if (func->sig.results == Type::none) {
+ if (func->getResults() == Type::none) {
// The function may have ended without a return; ensure one.
barrier = builder->makeReturn();
} else {
@@ -1222,12 +1222,12 @@ struct AsyncifyLocals : public WalkerPass<PostWalker<AsyncifyLocals>> {
builder->makeSequence(func->body, barrier))),
makeCallIndexPush(unwindIndex),
makeLocalSaving()});
- if (func->sig.results != Type::none) {
+ if (func->getResults() != Type::none) {
// If we unwind, we must still "return" a value, even if it will be
// ignored on the outside.
newBody->list.push_back(
- LiteralUtils::makeZero(func->sig.results, *getModule()));
- newBody->finalize(func->sig.results);
+ LiteralUtils::makeZero(func->getResults(), *getModule()));
+ newBody->finalize(func->getResults());
}
func->body = newBody;
// Making things like returns conditional may alter types.
diff --git a/src/passes/CodeFolding.cpp b/src/passes/CodeFolding.cpp
index 5362e310d..5b7c88024 100644
--- a/src/passes/CodeFolding.cpp
+++ b/src/passes/CodeFolding.cpp
@@ -742,7 +742,7 @@ private:
mergeable.pop_back();
}
// ensure the replacement has the same type, so the outside is not surprised
- outer->finalize(getFunction()->sig.results);
+ outer->finalize(getFunction()->getResults());
getFunction()->body = outer;
return true;
}
diff --git a/src/passes/DeNaN.cpp b/src/passes/DeNaN.cpp
index 8dadb90de..44dd0bf15 100644
--- a/src/passes/DeNaN.cpp
+++ b/src/passes/DeNaN.cpp
@@ -120,9 +120,7 @@ struct DeNaN : public WalkerPass<
// Add helper functions after the walk, so they are not instrumented.
Builder builder(*module);
auto add = [&](Name name, Type type, Literal literal, BinaryOp op) {
- auto* func = new Function;
- func->name = name;
- func->sig = Signature(type, type);
+ auto func = Builder::makeFunction(name, Signature(type, type), {});
// Compare the value to itself to check if it is a NaN, and return 0 if
// so:
//
@@ -139,7 +137,7 @@ struct DeNaN : public WalkerPass<
op, builder.makeLocalGet(0, type), builder.makeLocalGet(0, type)),
builder.makeLocalGet(0, type),
builder.makeConst(literal));
- module->addFunction(func);
+ module->addFunction(std::move(func));
};
add(deNan32, Type::f32, Literal(float(0)), EqFloat32);
add(deNan64, Type::f64, Literal(double(0)), EqFloat64);
diff --git a/src/passes/DeadArgumentElimination.cpp b/src/passes/DeadArgumentElimination.cpp
index 33ca81dc7..a95d4f91a 100644
--- a/src/passes/DeadArgumentElimination.cpp
+++ b/src/passes/DeadArgumentElimination.cpp
@@ -405,7 +405,7 @@ struct DAE : public Pass {
// once to remove a param, once to drop the return value).
if (changed.empty()) {
for (auto& func : module->functions) {
- if (func->sig.results == Type::none) {
+ if (func->getResults() == Type::none) {
continue;
}
auto name = func->name;
@@ -451,10 +451,11 @@ private:
// Remove the parameter from the function. We must add a new local
// for uses of the parameter, but cannot make it use the same index
// (in general).
- std::vector<Type> params(func->sig.params.begin(), func->sig.params.end());
+ auto paramsType = func->getParams();
+ std::vector<Type> params(paramsType.begin(), paramsType.end());
auto type = params[i];
params.erase(params.begin() + i);
- func->sig.params = Type(params);
+ func->setParams(Type(params));
Index newIndex = Builder::addVar(func, type);
// Update local operations.
struct LocalUpdater : public PostWalker<LocalUpdater> {
@@ -482,7 +483,7 @@ private:
void
removeReturnValue(Function* func, std::vector<Call*>& calls, Module* module) {
- func->sig.results = Type::none;
+ func->setResults(Type::none);
Builder builder(*module);
// Remove any return values.
struct ReturnUpdater : public PostWalker<ReturnUpdater> {
diff --git a/src/passes/Directize.cpp b/src/passes/Directize.cpp
index 3a7ef1024..086cc88a5 100644
--- a/src/passes/Directize.cpp
+++ b/src/passes/Directize.cpp
@@ -66,7 +66,7 @@ struct FunctionDirectizer : public WalkerPass<PostWalker<FunctionDirectizer>> {
return;
}
auto* func = getModule()->getFunction(name);
- if (curr->sig != func->sig) {
+ if (curr->sig != func->getSig()) {
replaceWithUnreachable(curr);
return;
}
diff --git a/src/passes/DuplicateImportElimination.cpp b/src/passes/DuplicateImportElimination.cpp
index b917c5fe8..a4d9065c5 100644
--- a/src/passes/DuplicateImportElimination.cpp
+++ b/src/passes/DuplicateImportElimination.cpp
@@ -41,7 +41,7 @@ struct DuplicateImportElimination : public Pass {
auto previousFunc = module->getFunction(previousName);
// It is ok to import the same thing with multiple types; we can only
// merge if the types match, of course.
- if (previousFunc->sig == func->sig) {
+ if (previousFunc->type == func->type) {
replacements[func->name] = previousName;
toRemove.push_back(func->name);
continue;
diff --git a/src/passes/FuncCastEmulation.cpp b/src/passes/FuncCastEmulation.cpp
index e63375f2b..d8b9f9b1d 100644
--- a/src/passes/FuncCastEmulation.cpp
+++ b/src/passes/FuncCastEmulation.cpp
@@ -199,11 +199,11 @@ private:
}
// The item in the table may be a function or a function import.
auto* func = module->getFunction(name);
- Type type = func->sig.results;
+ Type type = func->getResults();
Builder builder(*module);
std::vector<Expression*> callOperands;
Index i = 0;
- for (const auto& param : func->sig.params) {
+ for (const auto& param : func->getParams()) {
callOperands.push_back(
fromABI(builder.makeLocalGet(i++, Type::i64), param, module));
}
diff --git a/src/passes/GenerateDynCalls.cpp b/src/passes/GenerateDynCalls.cpp
index 0f4934c06..2487085c0 100644
--- a/src/passes/GenerateDynCalls.cpp
+++ b/src/passes/GenerateDynCalls.cpp
@@ -40,8 +40,8 @@ struct GenerateDynCalls : public WalkerPass<PostWalker<GenerateDynCalls>> {
void doWalkModule(Module* wasm) {
PostWalker<GenerateDynCalls>::doWalkModule(wasm);
- for (auto& sig : invokeSigs) {
- generateDynCallThunk(sig);
+ for (auto& type : invokeTypes) {
+ generateDynCallThunk(type);
}
}
@@ -61,7 +61,7 @@ struct GenerateDynCalls : public WalkerPass<PostWalker<GenerateDynCalls>> {
std::vector<Name> tableSegmentData;
ElementUtils::iterElementSegmentFunctionNames(
it->get(), [&](Name name, Index) {
- generateDynCallThunk(wasm->getFunction(name)->sig);
+ generateDynCallThunk(wasm->getFunction(name)->type);
});
}
}
@@ -70,19 +70,19 @@ struct GenerateDynCalls : public WalkerPass<PostWalker<GenerateDynCalls>> {
// Generate dynCalls for invokes
if (func->imported() && func->module == ENV &&
func->base.startsWith("invoke_")) {
- Signature sig = func->sig;
+ Signature sig = func->type.getSignature();
// The first parameter is a pointer to the original function that's called
// by the invoke, so skip it
std::vector<Type> newParams(sig.params.begin() + 1, sig.params.end());
- invokeSigs.insert(Signature(Type(newParams), sig.results));
+ invokeTypes.insert(Signature(Type(newParams), sig.results));
}
}
- void generateDynCallThunk(Signature sig);
+ void generateDynCallThunk(HeapType funcType);
bool onlyI64;
- // The set of all invokes' signatures
- InsertOrderedSet<Signature> invokeSigs;
+ // The set of all invokes' signature types.
+ InsertOrderedSet<HeapType> invokeTypes;
};
static bool hasI64(Signature sig) {
@@ -116,7 +116,8 @@ static void exportFunction(Module& wasm, Name name, bool must_export) {
wasm.addExport(exp);
}
-void GenerateDynCalls::generateDynCallThunk(Signature sig) {
+void GenerateDynCalls::generateDynCallThunk(HeapType funcType) {
+ Signature sig = funcType.getSignature();
if (onlyI64 && !hasI64(sig)) {
return;
}
@@ -127,13 +128,17 @@ void GenerateDynCalls::generateDynCallThunk(Signature sig) {
if (wasm->getFunctionOrNull(name) || wasm->getExportOrNull(name)) {
return; // module already contains this dyncall
}
- std::vector<NameType> params;
- params.emplace_back("fptr", Type::i32); // function pointer param
+ std::vector<NameType> namedParams;
+ std::vector<Type> params;
+ namedParams.emplace_back("fptr", Type::i32); // function pointer param
+ params.push_back(Type::i32);
int p = 0;
for (const auto& param : sig.params) {
- params.emplace_back(std::to_string(p++), param);
+ namedParams.emplace_back(std::to_string(p++), param);
+ params.push_back(param);
}
- auto f = builder.makeFunction(name, std::move(params), sig.results, {});
+ auto f = builder.makeFunction(
+ name, std::move(namedParams), Signature(Type(params), sig.results), {});
Expression* fptr = builder.makeLocalGet(0, Type::i32);
std::vector<Expression*> args;
Index i = 0;
diff --git a/src/passes/I64ToI32Lowering.cpp b/src/passes/I64ToI32Lowering.cpp
index 36d0ce8f9..9b516342d 100644
--- a/src/passes/I64ToI32Lowering.cpp
+++ b/src/passes/I64ToI32Lowering.cpp
@@ -158,7 +158,7 @@ struct I64ToI32Lowering : public WalkerPass<PostWalker<I64ToI32Lowering>> {
freeTemps.clear();
Module temp;
auto* oldFunc = ModuleUtils::copyFunction(func, temp);
- func->sig.params = Type::none;
+ func->setParams(Type::none);
func->vars.clear();
func->localNames.clear();
func->localIndices.clear();
@@ -191,8 +191,8 @@ struct I64ToI32Lowering : public WalkerPass<PostWalker<I64ToI32Lowering>> {
if (func->imported()) {
return;
}
- if (func->sig.results == Type::i64) {
- func->sig.results = Type::i32;
+ if (func->getResults() == Type::i64) {
+ func->setResults(Type::i32);
// body may not have out param if it ends with control flow
if (hasOutParam(func->body)) {
TempVar highBits = fetchOutParam(func->body);
@@ -250,7 +250,7 @@ struct I64ToI32Lowering : public WalkerPass<PostWalker<I64ToI32Lowering>> {
}
void visitCall(Call* curr) {
if (curr->isReturn &&
- getModule()->getFunction(curr->target)->sig.results == Type::i64) {
+ getModule()->getFunction(curr->target)->getResults() == Type::i64) {
Fatal()
<< "i64 to i32 lowering of return_call values not yet implemented";
}
diff --git a/src/passes/Inlining.cpp b/src/passes/Inlining.cpp
index 8601b3409..1a84918bb 100644
--- a/src/passes/Inlining.cpp
+++ b/src/passes/Inlining.cpp
@@ -143,7 +143,7 @@ struct FunctionInfoScanner
// We cannot inline a function if we cannot handle placing it in a local, as
// all params become locals.
- for (auto param : curr->sig.params) {
+ for (auto param : curr->getParams()) {
if (!TypeUpdating::canHandleAsLocal(param)) {
info.uninlineable = true;
}
@@ -233,7 +233,7 @@ struct Updater : public PostWalker<Updater> {
}
void visitCall(Call* curr) {
if (curr->isReturn) {
- handleReturnCall(curr, module->getFunction(curr->target)->sig.results);
+ handleReturnCall(curr, module->getFunction(curr->target)->getResults());
}
}
void visitCallIndirect(CallIndirect* curr) {
@@ -262,7 +262,7 @@ doInlining(Module* module, Function* into, const InliningAction& action) {
Function* from = action.contents;
auto* call = (*action.callSite)->cast<Call>();
// Works for return_call, too
- Type retType = module->getFunction(call->target)->sig.results;
+ Type retType = module->getFunction(call->target)->getResults();
Builder builder(*module);
auto* block = builder.makeBlock();
block->name = Name(std::string("__inlined_func$") + from->name.str);
@@ -285,7 +285,7 @@ doInlining(Module* module, Function* into, const InliningAction& action) {
updater.localMapping[i] = builder.addVar(into, from->getLocalType(i));
}
// Assign the operands into the params
- for (Index i = 0; i < from->sig.params.size(); i++) {
+ for (Index i = 0; i < from->getParams().size(); i++) {
block->list.push_back(
builder.makeLocalSet(updater.localMapping[i], call->operands[i]));
}
diff --git a/src/passes/InstrumentLocals.cpp b/src/passes/InstrumentLocals.cpp
index 85da3bd9b..aab0ee3fe 100644
--- a/src/passes/InstrumentLocals.cpp
+++ b/src/passes/InstrumentLocals.cpp
@@ -245,12 +245,10 @@ private:
Index id = 0;
void addImport(Module* wasm, Name name, Type params, Type results) {
- auto import = new Function;
- import->name = name;
+ auto import = Builder::makeFunction(name, Signature(params, results), {});
import->module = ENV;
import->base = name;
- import->sig = Signature(params, results);
- wasm->addFunction(import);
+ wasm->addFunction(std::move(import));
}
};
diff --git a/src/passes/InstrumentMemory.cpp b/src/passes/InstrumentMemory.cpp
index 6c81f8588..38a23a658 100644
--- a/src/passes/InstrumentMemory.cpp
+++ b/src/passes/InstrumentMemory.cpp
@@ -158,12 +158,10 @@ private:
Index id;
void addImport(Module* curr, Name name, Type params, Type results) {
- auto import = new Function;
- import->name = name;
+ auto import = Builder::makeFunction(name, Signature(params, results), {});
import->module = ENV;
import->base = name;
- import->sig = Signature(params, results);
- curr->addFunction(import);
+ curr->addFunction(std::move(import));
}
};
diff --git a/src/passes/LegalizeJSInterface.cpp b/src/passes/LegalizeJSInterface.cpp
index 10e751701..e7a5f9220 100644
--- a/src/passes/LegalizeJSInterface.cpp
+++ b/src/passes/LegalizeJSInterface.cpp
@@ -157,12 +157,12 @@ private:
std::map<Name, Name> illegalImportsToLegal;
template<typename T> bool isIllegal(T* t) {
- for (const auto& param : t->sig.params) {
+ for (const auto& param : t->getParams()) {
if (param == Type::i64) {
return true;
}
}
- return t->sig.results == Type::i64;
+ return t->getResults() == Type::i64;
}
bool isDynCall(Name name) { return name.startsWith("dynCall_"); }
@@ -201,10 +201,10 @@ private:
auto* call = module->allocator.alloc<Call>();
call->target = func->name;
- call->type = func->sig.results;
+ call->type = func->getResults();
std::vector<Type> legalParams;
- for (const auto& param : func->sig.params) {
+ for (const auto& param : func->getParams()) {
if (param == Type::i64) {
call->operands.push_back(I64Utilities::recreateI64(
builder, legalParams.size(), legalParams.size() + 1));
@@ -216,12 +216,12 @@ private:
legalParams.push_back(param);
}
}
- legal->sig.params = Type(legalParams);
-
- if (func->sig.results == Type::i64) {
+ Type resultsType =
+ func->getResults() == Type::i64 ? Type::i32 : func->getResults();
+ legal->type = Signature(Type(legalParams), resultsType);
+ if (func->getResults() == Type::i64) {
Function* f =
getFunctionOrImport(module, SET_TEMP_RET0, Type::i32, Type::none);
- legal->sig.results = Type::i32;
auto index = Builder::addVar(legal, Name(), Type::i64);
auto* block = builder.makeBlock();
block->list.push_back(builder.makeLocalSet(index, call));
@@ -231,10 +231,8 @@ private:
block->finalize();
legal->body = block;
} else {
- legal->sig.results = func->sig.results;
legal->body = call;
}
-
return module->addFunction(legal)->name;
}
@@ -248,14 +246,14 @@ private:
legalIm->base = im->base;
auto stub = make_unique<Function>();
stub->name = Name(std::string("legalfunc$") + im->name.str);
- stub->sig = im->sig;
+ stub->type = im->type;
auto* call = module->allocator.alloc<Call>();
call->target = legalIm->name;
std::vector<Type> params;
Index i = 0;
- for (const auto& param : im->sig.params) {
+ for (const auto& param : im->getParams()) {
if (param == Type::i64) {
call->operands.push_back(I64Utilities::getI64Low(builder, i));
call->operands.push_back(I64Utilities::getI64High(builder, i));
@@ -268,17 +266,17 @@ private:
++i;
}
- if (im->sig.results == Type::i64) {
+ if (im->getResults() == Type::i64) {
Function* f =
getFunctionOrImport(module, GET_TEMP_RET0, Type::none, Type::i32);
call->type = Type::i32;
Expression* get = builder.makeCall(f->name, {}, call->type);
stub->body = I64Utilities::recreateI64(builder, call, get);
} else {
- call->type = im->sig.results;
+ call->type = im->getResults();
stub->body = call;
}
- legalIm->sig = Signature(Type(params), call->type);
+ legalIm->type = Signature(Type(params), call->type);
const auto& stubName = stub->name;
if (!module->getFunctionOrNull(stubName)) {
@@ -302,13 +300,12 @@ private:
return f;
}
// Failing that create a new function import.
- auto import = new Function;
- import->name = name;
+ auto import = Builder::makeFunction(name, Signature(params, results), {});
import->module = ENV;
import->base = name;
- import->sig = Signature(params, results);
- module->addFunction(import);
- return import;
+ auto* ret = import.get();
+ module->addFunction(std::move(import));
+ return ret;
}
};
diff --git a/src/passes/LogExecution.cpp b/src/passes/LogExecution.cpp
index b9b203d0b..5978ecc72 100644
--- a/src/passes/LogExecution.cpp
+++ b/src/passes/LogExecution.cpp
@@ -57,12 +57,11 @@ struct LogExecution : public WalkerPass<PostWalker<LogExecution>> {
void visitModule(Module* curr) {
// Add the import
- auto import = new Function;
- import->name = LOGGER;
+ auto import =
+ Builder::makeFunction(LOGGER, Signature(Type::i32, Type::none), {});
import->module = ENV;
import->base = LOGGER;
- import->sig = Signature(Type::i32, Type::none);
- curr->addFunction(import);
+ curr->addFunction(std::move(import));
}
private:
diff --git a/src/passes/Print.cpp b/src/passes/Print.cpp
index c6bf13f42..491e44ca2 100644
--- a/src/passes/Print.cpp
+++ b/src/passes/Print.cpp
@@ -2596,7 +2596,7 @@ struct PrintSExpression : public UnifiedExpressionVisitor<PrintSExpression> {
lastPrintedLocation = {0, 0, 0};
o << '(';
emitImportHeader(curr);
- handleSignature(curr->sig, curr->name);
+ handleSignature(curr->getSig(), curr->name);
o << ')';
o << maybeNewLine;
}
@@ -2613,9 +2613,9 @@ struct PrintSExpression : public UnifiedExpressionVisitor<PrintSExpression> {
if (!stackIR && curr->stackIR && !minify) {
o << " (; has Stack IR ;)";
}
- if (curr->sig.params.size() > 0) {
+ if (curr->getParams().size() > 0) {
Index i = 0;
- for (const auto& param : curr->sig.params) {
+ for (const auto& param : curr->getParams()) {
o << maybeSpace;
o << '(';
printMinor(o, "param ");
@@ -2625,9 +2625,9 @@ struct PrintSExpression : public UnifiedExpressionVisitor<PrintSExpression> {
++i;
}
}
- if (curr->sig.results != Type::none) {
+ if (curr->getResults() != Type::none) {
o << maybeSpace;
- printResultType(o, curr->sig.results, currModule);
+ printResultType(o, curr->getResults(), currModule);
}
incIndent();
for (size_t i = curr->getVarIndexBase(); i < curr->getNumLocals(); i++) {
diff --git a/src/passes/ReReloop.cpp b/src/passes/ReReloop.cpp
index 9a82d8b44..0559343d4 100644
--- a/src/passes/ReReloop.cpp
+++ b/src/passes/ReReloop.cpp
@@ -318,7 +318,7 @@ struct ReReloop final : public Pass {
for (auto& cfgBlock : relooper->Blocks) {
auto* block = cfgBlock->Code->cast<Block>();
if (cfgBlock->BranchesOut.empty() && block->type != Type::unreachable) {
- block->list.push_back(function->sig.results == Type::none
+ block->list.push_back(function->getResults() == Type::none
? (Expression*)builder->makeReturn()
: (Expression*)builder->makeUnreachable());
block->finalize();
@@ -351,7 +351,7 @@ struct ReReloop final : public Pass {
// because of the relooper's boilerplate switch-handling
// code, for example, which could be optimized out later
// but isn't yet), then make sure it has a proper type
- if (function->sig.results != Type::none &&
+ if (function->getResults() != Type::none &&
function->body->type == Type::none) {
function->body =
builder.makeSequence(function->body, builder.makeUnreachable());
diff --git a/src/passes/RemoveImports.cpp b/src/passes/RemoveImports.cpp
index 2a1c119fd..af216ecbd 100644
--- a/src/passes/RemoveImports.cpp
+++ b/src/passes/RemoveImports.cpp
@@ -35,7 +35,7 @@ struct RemoveImports : public WalkerPass<PostWalker<RemoveImports>> {
if (!func->imported()) {
return;
}
- Type type = func->sig.results;
+ Type type = func->getResults();
if (type == Type::none) {
replaceCurrent(getModule()->allocator.alloc<Nop>());
} else {
diff --git a/src/passes/ReorderLocals.cpp b/src/passes/ReorderLocals.cpp
index 8d7c0f1d9..b34eeb3bf 100644
--- a/src/passes/ReorderLocals.cpp
+++ b/src/passes/ReorderLocals.cpp
@@ -82,7 +82,7 @@ struct ReorderLocals : public WalkerPass<PostWalker<ReorderLocals>> {
return counts[a] > counts[b];
});
// sorting left params in front, perhaps slightly reordered. verify and fix.
- size_t numParams = curr->sig.params.size();
+ size_t numParams = curr->getParams().size();
for (size_t i = 0; i < numParams; i++) {
assert(newToOld[i] < numParams);
newToOld[i] = i;
diff --git a/src/passes/SafeHeap.cpp b/src/passes/SafeHeap.cpp
index 2eed23256..a3416afaf 100644
--- a/src/passes/SafeHeap.cpp
+++ b/src/passes/SafeHeap.cpp
@@ -134,32 +134,33 @@ struct SafeHeap : public Pass {
} else if (auto* existing = info.getImportedFunction(ENV, SBRK)) {
sbrk = existing->name;
} else {
- auto* import = new Function;
- import->name = getSbrkPtr = GET_SBRK_PTR;
+ auto import = Builder::makeFunction(
+ GET_SBRK_PTR, Signature(Type::none, indexType), {});
+ getSbrkPtr = GET_SBRK_PTR;
import->module = ENV;
import->base = GET_SBRK_PTR;
- import->sig = Signature(Type::none, indexType);
- module->addFunction(import);
+ module->addFunction(std::move(import));
}
if (auto* existing = info.getImportedFunction(ENV, SEGFAULT_IMPORT)) {
segfault = existing->name;
} else {
- auto* import = new Function;
- import->name = segfault = SEGFAULT_IMPORT;
+ auto import = Builder::makeFunction(
+ SEGFAULT_IMPORT, Signature(Type::none, Type::none), {});
+ segfault = SEGFAULT_IMPORT;
import->module = ENV;
import->base = SEGFAULT_IMPORT;
- import->sig = Signature(Type::none, Type::none);
- module->addFunction(import);
+ module->addFunction(std::move(import));
}
if (auto* existing = info.getImportedFunction(ENV, ALIGNFAULT_IMPORT)) {
alignfault = existing->name;
} else {
- auto* import = new Function;
- import->name = alignfault = ALIGNFAULT_IMPORT;
+ auto import = Builder::makeFunction(
+ ALIGNFAULT_IMPORT, Signature(Type::none, Type::none), {});
+
+ alignfault = ALIGNFAULT_IMPORT;
import->module = ENV;
import->base = ALIGNFAULT_IMPORT;
- import->sig = Signature(Type::none, Type::none);
- module->addFunction(import);
+ module->addFunction(std::move(import));
}
}
@@ -246,12 +247,10 @@ struct SafeHeap : public Pass {
if (module->getFunctionOrNull(name)) {
return;
}
- auto* func = new Function;
- func->name = name;
// pointer, offset
auto indexType = module->memory.indexType;
- func->sig = Signature({indexType, indexType}, style.type);
- func->vars.push_back(indexType); // pointer + offset
+ auto funcSig = Signature({indexType, indexType}, style.type);
+ auto func = Builder::makeFunction(name, funcSig, {indexType});
Builder builder(*module);
auto* block = builder.makeBlock();
block->list.push_back(builder.makeLocalSet(
@@ -279,7 +278,7 @@ struct SafeHeap : public Pass {
block->list.push_back(last);
block->finalize(style.type);
func->body = block;
- module->addFunction(func);
+ module->addFunction(std::move(func));
}
// creates a function for a particular type of store
@@ -288,12 +287,11 @@ struct SafeHeap : public Pass {
if (module->getFunctionOrNull(name)) {
return;
}
- auto* func = new Function;
- func->name = name;
- // pointer, offset, value
auto indexType = module->memory.indexType;
- func->sig = Signature({indexType, indexType, style.valueType}, Type::none);
- func->vars.push_back(indexType); // pointer + offset
+ // pointer, offset, value
+ auto funcSig =
+ Signature({indexType, indexType, style.valueType}, Type::none);
+ auto func = Builder::makeFunction(name, funcSig, {indexType});
Builder builder(*module);
auto* block = builder.makeBlock();
block->list.push_back(builder.makeLocalSet(
@@ -316,7 +314,7 @@ struct SafeHeap : public Pass {
block->list.push_back(store);
block->finalize(Type::none);
func->body = block;
- module->addFunction(func);
+ module->addFunction(std::move(func));
}
Expression*
diff --git a/src/passes/StackCheck.cpp b/src/passes/StackCheck.cpp
index 23fd5be3d..e7fc3c6b3 100644
--- a/src/passes/StackCheck.cpp
+++ b/src/passes/StackCheck.cpp
@@ -39,12 +39,10 @@ static void importStackOverflowHandler(Module& module, Name name) {
ImportInfo info(module);
if (!info.getImportedFunction(ENV, name)) {
- auto* import = new Function;
- import->name = name;
+ auto import = Builder::makeFunction(name, Signature(), {});
import->module = ENV;
import->base = name;
- import->sig = Signature(Type::none, Type::none);
- module.addFunction(import);
+ module.addFunction(std::move(import));
}
}
diff --git a/src/passes/TrapMode.cpp b/src/passes/TrapMode.cpp
index 9c9dee9ca..ee245af88 100644
--- a/src/passes/TrapMode.cpp
+++ b/src/passes/TrapMode.cpp
@@ -132,14 +132,14 @@ Function* generateBinaryFunc(Module& wasm, Binary* curr) {
builder.makeConst(zeroLit),
result);
}
- auto func = new Function;
- func->name = getBinaryFuncName(curr);
- func->sig = Signature({type, type}, type);
+ auto funcSig = Signature({type, type}, type);
+ auto func = Builder::makeFunction(getBinaryFuncName(curr), funcSig, {});
func->body =
builder.makeIf(builder.makeUnary(eqZOp, builder.makeLocalGet(1, type)),
builder.makeConst(zeroLit),
result);
- return func;
+ // TODO: use unique_ptr properly and do not release ownership.
+ return func.release();
}
template<typename IntType, typename FloatType>
@@ -193,9 +193,8 @@ Function* generateUnaryFunc(Module& wasm, Unary* curr) {
WASM_UNREACHABLE("unexpected op");
}
- auto func = new Function;
- func->name = getUnaryFuncName(curr);
- func->sig = Signature(type, retType);
+ auto func =
+ Builder::makeFunction(getUnaryFuncName(curr), Signature(type, retType), {});
func->body = builder.makeUnary(truncOp, builder.makeLocalGet(0, type));
// too small XXX this is different than asm.js, which does frem. here we
// clamp, which is much simpler/faster, and similar to native builds
@@ -218,7 +217,8 @@ Function* generateUnaryFunc(Module& wasm, Unary* curr) {
// NB: min here as well. anything invalid => to the min
builder.makeConst(iMin),
func->body);
- return func;
+ // TODO: use unique_ptr properly and do not release ownership.
+ return func.release();
}
void ensureBinaryFunc(Binary* curr,
@@ -251,7 +251,7 @@ void ensureF64ToI64JSImport(TrappingFunctionContainer& trappingFunctions) {
import->name = F64_TO_INT;
import->module = ASM2WASM;
import->base = F64_TO_INT;
- import->sig = Signature(Type::f64, Type::i32);
+ import->type = Signature(Type::f64, Type::i32);
trappingFunctions.addImport(import);
}
diff --git a/src/passes/Vacuum.cpp b/src/passes/Vacuum.cpp
index 506eee5e6..25b0116b3 100644
--- a/src/passes/Vacuum.cpp
+++ b/src/passes/Vacuum.cpp
@@ -355,13 +355,13 @@ struct Vacuum : public WalkerPass<ExpressionStackWalker<Vacuum>> {
void visitFunction(Function* curr) {
auto* optimized =
- optimize(curr->body, curr->sig.results != Type::none, true);
+ optimize(curr->body, curr->getResults() != Type::none, true);
if (optimized) {
curr->body = optimized;
} else {
ExpressionManipulator::nop(curr->body);
}
- if (curr->sig.results == Type::none &&
+ if (curr->getResults() == Type::none &&
!EffectAnalyzer(getPassOptions(), getModule()->features, curr->body)
.hasSideEffects()) {
ExpressionManipulator::nop(curr->body);