Skip to content

Commit 41ebb1b

Browse files
authored
fix an iterator invalidation regression from #1678 (#1684)
Fixes the 3 regressions mentioned in a comment on #1678
1 parent fe88b47 commit 41ebb1b

File tree

1 file changed

+24
-5
lines changed

1 file changed

+24
-5
lines changed

src/wasm/wasm-emscripten.cpp

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -377,11 +377,16 @@ struct AsmConstWalker : public PostWalker<AsmConstWalker> {
377377

378378
void visitCall(Call* curr);
379379

380+
void process();
381+
380382
private:
381383
Literal idLiteralForCode(std::string code);
382384
std::string asmConstSig(std::string baseSig);
383385
Name nameForImportWithSig(std::string sig);
384-
void addImport(Name importName, std::string baseSig);
386+
void queueImport(Name importName, std::string baseSig);
387+
void addImports();
388+
389+
std::vector<std::unique_ptr<Function>> queuedImports;
385390
};
386391

387392
void AsmConstWalker::visitCall(Call* curr) {
@@ -398,11 +403,19 @@ void AsmConstWalker::visitCall(Call* curr) {
398403

399404
if (allSigs.count(sig) == 0) {
400405
allSigs.insert(sig);
401-
addImport(importName, baseSig);
406+
queueImport(importName, baseSig);
402407
}
403408
}
404409
}
405410

411+
void AsmConstWalker::process() {
412+
// Find and queue necessary imports
413+
walkModule(&wasm);
414+
// Add them after the walk, to avoid iterator invalidation on
415+
// the list of functions.
416+
addImports();
417+
}
418+
406419
Literal AsmConstWalker::idLiteralForCode(std::string code) {
407420
int32_t id;
408421
if (ids.count(code) == 0) {
@@ -430,12 +443,18 @@ Name AsmConstWalker::nameForImportWithSig(std::string sig) {
430443
return Name(fixedTarget.c_str());
431444
}
432445

433-
void AsmConstWalker::addImport(Name importName, std::string baseSig) {
446+
void AsmConstWalker::queueImport(Name importName, std::string baseSig) {
434447
auto import = new Function;
435448
import->name = import->base = importName;
436449
import->module = ENV;
437450
import->type = ensureFunctionType(baseSig, &wasm)->name;
438-
wasm.addFunction(import);
451+
queuedImports.push_back(std::unique_ptr<Function>(import));
452+
}
453+
454+
void AsmConstWalker::addImports() {
455+
for (auto& import : queuedImports) {
456+
wasm.addFunction(import.release());
457+
}
439458
}
440459

441460
AsmConstWalker fixEmAsmConstsAndReturnWalker(Module& wasm) {
@@ -450,7 +469,7 @@ AsmConstWalker fixEmAsmConstsAndReturnWalker(Module& wasm) {
450469

451470
// Walk the module, generate _sig versions of EM_ASM functions
452471
AsmConstWalker walker(wasm);
453-
walker.walkModule(&wasm);
472+
walker.process();
454473

455474
// Remove the base functions that we didn't generate
456475
for (auto importName : toRemove) {

0 commit comments

Comments
 (0)