diff options
author | Ashley Nelson <nashley@google.com> | 2022-08-17 18:44:29 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-08-17 18:44:29 -0700 |
commit | 3aff4c6e85623c970280219c6699a66bc9de5f9b (patch) | |
tree | e5440bc966e523a7404ae2cec3458dacbe1281d1 /src/wasm-binary.h | |
parent | b70fe755aa4c90727edfd91dc0a9a51febf0239d (diff) | |
download | binaryen-3aff4c6e85623c970280219c6699a66bc9de5f9b.tar.gz binaryen-3aff4c6e85623c970280219c6699a66bc9de5f9b.tar.bz2 binaryen-3aff4c6e85623c970280219c6699a66bc9de5f9b.zip |
Mutli-Memories Support in IR (#4811)
This PR removes the single memory restriction in IR, adding support for a single module to reference multiple memories. To support this change, a new memory name field was added to 13 memory instructions in order to identify the memory for the instruction.
It is a goal of this PR to maintain backwards compatibility with existing text and binary wasm modules, so memory indexes remain optional for memory instructions. Similarly, the JS API makes assumptions about which memory is intended when only one memory is present in the module. Another goal of this PR is that existing tests behavior be unaffected. That said, tests must now explicitly define a memory before invoking memory instructions or exporting a memory, and memory names are now printed for each memory instruction in the text format.
There remain quite a few places where a hardcoded reference to the first memory persist (memory flattening, for example, will return early if more than one memory is present in the module). Many of these call-sites, particularly within passes, will require us to rethink how the optimization works in a multi-memories world. Other call-sites may necessitate more invasive code restructuring to fully convert away from relying on a globally available, single memory pointer.
Diffstat (limited to 'src/wasm-binary.h')
-rw-r--r-- | src/wasm-binary.h | 19 |
1 files changed, 16 insertions, 3 deletions
diff --git a/src/wasm-binary.h b/src/wasm-binary.h index 6b05c38cc..9424f6fda 100644 --- a/src/wasm-binary.h +++ b/src/wasm-binary.h @@ -1187,6 +1187,7 @@ class WasmBinaryWriter { std::unordered_map<Name, Index> globalIndexes; std::unordered_map<Name, Index> tableIndexes; std::unordered_map<Name, Index> elemIndexes; + std::unordered_map<Name, Index> memoryIndexes; std::unordered_map<Name, Index> dataIndexes; BinaryIndexes(Module& wasm) { @@ -1209,6 +1210,7 @@ class WasmBinaryWriter { addIndexes(wasm.functions, functionIndexes); addIndexes(wasm.tags, tagIndexes); addIndexes(wasm.tables, tableIndexes); + addIndexes(wasm.memories, memoryIndexes); for (auto& curr : wasm.elementSegments) { auto index = elemIndexes.size(); @@ -1281,7 +1283,7 @@ public: int32_t startSubsection(BinaryConsts::UserSections::Subsection code); void finishSubsection(int32_t start); void writeStart(); - void writeMemory(); + void writeMemories(); void writeTypes(); void writeImports(); @@ -1297,6 +1299,7 @@ public: uint32_t getFunctionIndex(Name name) const; uint32_t getTableIndex(Name name) const; + uint32_t getMemoryIndex(Name name) const; uint32_t getGlobalIndex(Name name) const; uint32_t getTagIndex(Name name) const; uint32_t getTypeIndex(HeapType type) const; @@ -1466,12 +1469,13 @@ public: void verifyInt64(int64_t x); void readHeader(); void readStart(); - void readMemory(); + void readMemories(); void readTypes(); // gets a name in the combined import+defined space Name getFunctionName(Index index); Name getTableName(Index index); + Name getMemoryName(Index index); Name getGlobalName(Index index); Name getTagName(Index index); @@ -1526,6 +1530,15 @@ public: // names std::vector<std::unique_ptr<ElementSegment>> elementSegments; + // we store memories here after being read from binary, before we know their + // names + std::vector<std::unique_ptr<Memory>> memories; + // we store memory imports here before wasm.addMemoryImport after we know + // their names + std::vector<Memory*> memoryImports; + // at index i we have all references to the memory i + std::map<Index, std::vector<wasm::Name*>> memoryRefs; + // we store data here after being read from binary, before we know their names std::vector<std::unique_ptr<DataSegment>> dataSegments; @@ -1646,7 +1659,7 @@ public: BreakTarget getBreakTarget(int32_t offset); Name getExceptionTargetName(int32_t offset); - void readMemoryAccess(Address& alignment, Address& offset); + Index readMemoryAccess(Address& alignment, Address& offset); void visitIf(If* curr); void visitLoop(Loop* curr); |