summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlon Zakai <azakai@google.com>2022-11-29 09:23:05 -0800
committerGitHub <noreply@github.com>2022-11-29 09:23:05 -0800
commit83cceaca5c9ce53ba4115aa732e7196db67bc493 (patch)
tree6796ae9682e7e1db46f3ce3c354f10def34298bd
parent17a698807c5b898abe9b1c98eab5f3f89bc1c877 (diff)
downloadbinaryen-83cceaca5c9ce53ba4115aa732e7196db67bc493.tar.gz
binaryen-83cceaca5c9ce53ba4115aa732e7196db67bc493.tar.bz2
binaryen-83cceaca5c9ce53ba4115aa732e7196db67bc493.zip
[NFC] Refactor GlobalTypeRewriter to split out the type mapping logic (#5295)
The logic that is split out into mapTypes gets a map of old type => new type and then updates the module to replace the old with the new. This will be useful in a future pass to merge types. We will tell it to map the types to be merged with the types we want to merge them into. This removes an assert on all types being in the map to allow some of them not to be. (the new pass that will use this will only want to map some types).
-rw-r--r--src/ir/type-updating.cpp33
-rw-r--r--src/ir/type-updating.h10
2 files changed, 30 insertions, 13 deletions
diff --git a/src/ir/type-updating.cpp b/src/ir/type-updating.cpp
index 2d75f0951..08c04e8d4 100644
--- a/src/ir/type-updating.cpp
+++ b/src/ir/type-updating.cpp
@@ -97,21 +97,33 @@ void GlobalTypeRewriter::update() {
// Map the old types to the new ones. This uses the fact that type indices
// are the same in the old and new types, that is, we have not added or
// removed types, just modified them.
- using OldToNewTypes = std::unordered_map<HeapType, HeapType>;
- OldToNewTypes oldToNewTypes;
+ TypeMap oldToNewTypes;
for (Index i = 0; i < indexedTypes.types.size(); i++) {
oldToNewTypes[indexedTypes.types[i]] = newTypes[i];
}
+ // Update type names (doing it before mapTypes can help debugging there, but
+ // has no other effect; mapTypes does not look at type names).
+ for (auto& [old, new_] : oldToNewTypes) {
+ if (wasm.typeNames.count(old)) {
+ wasm.typeNames[new_] = wasm.typeNames[old];
+ }
+ }
+
+ mapTypes(oldToNewTypes);
+}
+
+void GlobalTypeRewriter::mapTypes(const TypeMap& oldToNewTypes) {
+
// Replace all the old types in the module with the new ones.
struct CodeUpdater
: public WalkerPass<
PostWalker<CodeUpdater, UnifiedExpressionVisitor<CodeUpdater>>> {
bool isFunctionParallel() override { return true; }
- OldToNewTypes& oldToNewTypes;
+ const TypeMap& oldToNewTypes;
- CodeUpdater(OldToNewTypes& oldToNewTypes) : oldToNewTypes(oldToNewTypes) {}
+ CodeUpdater(const TypeMap& oldToNewTypes) : oldToNewTypes(oldToNewTypes) {}
std::unique_ptr<Pass> create() override {
return std::make_unique<CodeUpdater>(oldToNewTypes);
@@ -136,8 +148,10 @@ void GlobalTypeRewriter::update() {
return type;
}
if (type.isFunction() || type.isData()) {
- assert(oldToNewTypes.count(type));
- return oldToNewTypes[type];
+ auto iter = oldToNewTypes.find(type);
+ if (iter != oldToNewTypes.end()) {
+ return iter->second;
+ }
}
return type;
}
@@ -228,13 +242,6 @@ void GlobalTypeRewriter::update() {
for (auto& tag : wasm.tags) {
tag->sig = updater.getNew(tag->sig);
}
-
- // Update type names.
- for (auto& [old, new_] : oldToNewTypes) {
- if (wasm.typeNames.count(old)) {
- wasm.typeNames[new_] = wasm.typeNames[old];
- }
- }
}
Type GlobalTypeRewriter::getTempType(Type type) {
diff --git a/src/ir/type-updating.h b/src/ir/type-updating.h
index 50ba9efca..8da84ceb6 100644
--- a/src/ir/type-updating.h
+++ b/src/ir/type-updating.h
@@ -337,6 +337,16 @@ public:
// the module.
void update();
+ using TypeMap = std::unordered_map<HeapType, HeapType>;
+
+ // Given a map of old type => new type to use instead, this rewrites all type
+ // uses in the module to apply that map. This is used internally in update()
+ // but may be useful by itself as well.
+ //
+ // The input map does not need to contain all the types. Whenever a type does
+ // not appear, it is mapped to itself.
+ void mapTypes(const TypeMap& oldToNewTypes);
+
// Subclasses can implement these methods to modify the new set of types that
// we map to. By default, we simply copy over the types, and these functions
// are the hooks to apply changes through. The methods receive as input the