From 2608864d6fc812a90d2e2594c70767f5fb4811a7 Mon Sep 17 00:00:00 2001 From: Alon Zakai Date: Mon, 9 Jan 2023 11:34:07 -0800 Subject: [Wasm GC] Refinalize in Vacuum (#5412) We use TypeUpdater there, which handles updating unreachability. But with wasm GC we also need to refinalize if we refine types. Somehow, this was not noticed until now, but the new ref.cast null assertion on not losing type info was enough to uncover this long-existing issue. --- src/passes/Vacuum.cpp | 13 +++++++++++++ 1 file changed, 13 insertions(+) (limited to 'src') diff --git a/src/passes/Vacuum.cpp b/src/passes/Vacuum.cpp index 44abed27b..84ae5199c 100644 --- a/src/passes/Vacuum.cpp +++ b/src/passes/Vacuum.cpp @@ -37,8 +37,18 @@ struct Vacuum : public WalkerPass> { TypeUpdater typeUpdater; + // The TypeUpdater class handles efficient updating of unreachability as we + // go, but we may also refine types, which requires refinalization. + bool refinalize = false; + Expression* replaceCurrent(Expression* expression) { auto* old = getCurrent(); + if (expression->type != old->type && + expression->type != Type::unreachable) { + // We are changing this to a new type that is not unreachable, so it is a + // refinement that we need to use refinalize to propagate up. + refinalize = true; + } super::replaceCurrent(expression); // also update the type updater typeUpdater.noteReplacement(old, expression); @@ -48,6 +58,9 @@ struct Vacuum : public WalkerPass> { void doWalkFunction(Function* func) { typeUpdater.walk(func->body); walk(func->body); + if (refinalize) { + ReFinalize().walkFunctionInModule(func, getModule()); + } } // Returns nullptr if curr is dead, curr if it must stay as is, or one of its -- cgit v1.2.3