diff --git a/src/binaryen-c.cpp b/src/binaryen-c.cpp index 8cbb969d6a1..69f964cf36e 100644 --- a/src/binaryen-c.cpp +++ b/src/binaryen-c.cpp @@ -5337,6 +5337,7 @@ void BinaryenSetMemory(BinaryenModuleRef module, BinaryenIndex numSegments, bool shared, bool memory64, + bool keepSegment, const char* name) { auto memory = std::make_unique(); memory->name = name ? name : "0"; @@ -5351,20 +5352,22 @@ void BinaryenSetMemory(BinaryenModuleRef module, memoryExport->kind = ExternalKind::Memory; ((Module*)module)->addExport(memoryExport.release()); } - ((Module*)module)->removeDataSegments([&](DataSegment* curr) { - return true; - }); - for (BinaryenIndex i = 0; i < numSegments; i++) { - auto explicitName = segmentNames && segmentNames[i]; - auto name = explicitName ? Name(segmentNames[i]) : Name::fromInt(i); - auto curr = Builder::makeDataSegment(name, - memory->name, - segmentPassives[i], - (Expression*)segmentOffsets[i], - segmentDatas[i], - segmentSizes[i]); - curr->hasExplicitName = explicitName; - ((Module*)module)->addDataSegment(std::move(curr)); + if (!keepSegment) { + ((Module*)module)->removeDataSegments([&](DataSegment* curr) { + return true; + }); + for (BinaryenIndex i = 0; i < numSegments; i++) { + auto explicitName = segmentNames && segmentNames[i]; + auto name = explicitName ? Name(segmentNames[i]) : Name::fromInt(i); + auto curr = Builder::makeDataSegment(name, + memory->name, + segmentPassives[i], + (Expression*)segmentOffsets[i], + segmentDatas[i], + segmentSizes[i]); + curr->hasExplicitName = explicitName; + ((Module*)module)->addDataSegment(std::move(curr)); + } } ((Module*)module)->removeMemories([&](Memory* curr) { return true; }); ((Module*)module)->addMemory(std::move(memory)); diff --git a/src/binaryen-c.h b/src/binaryen-c.h index 07a81a4c80d..383fe57e01e 100644 --- a/src/binaryen-c.h +++ b/src/binaryen-c.h @@ -2910,6 +2910,8 @@ BinaryenGetElementSegmentByIndex(BinaryenModuleRef module, BinaryenIndex index); // a start offset in segmentOffsets, a passive flag in segmentPassives // and a size in segmentSizes. segmentNames and exportName can be NULL // If segmentNames is null, BinaryenSetMemory creates names from indices +// If keepSegment is true, BinaryenSetMemory will not operate on memory +// segments. BINARYEN_API void BinaryenSetMemory(BinaryenModuleRef module, BinaryenIndex initial, BinaryenIndex maximum, @@ -2922,6 +2924,7 @@ BINARYEN_API void BinaryenSetMemory(BinaryenModuleRef module, BinaryenIndex numSegments, bool shared, bool memory64, + bool keepSegment, const char* name); BINARYEN_API bool BinaryenHasMemory(BinaryenModuleRef module); diff --git a/src/js/binaryen.js-post.js b/src/js/binaryen.js-post.js index 111c020b3a0..e33305c188c 100644 --- a/src/js/binaryen.js-post.js +++ b/src/js/binaryen.js-post.js @@ -2561,7 +2561,7 @@ function wrapModule(module, self = {}) { self['removeExport'] = function(externalName) { return preserveStack(() => Module['_BinaryenRemoveExport'](module, strToStack(externalName))); }; - self['setMemory'] = function(initial, maximum, exportName, segments = [], shared = false, memory64 = false, internalName = null) { + self['setMemory'] = function(initial, maximum, exportName, segments = [], shared = false, memory64 = false, keepSegment = false, internalName = null) { // segments are assumed to be { passive: bool, offset: expression ref, data: array of 8-bit data } return preserveStack(() => { const segmentsLen = segments.length; @@ -2589,6 +2589,7 @@ function wrapModule(module, self = {}) { segmentsLen, shared, memory64, + keepSegment, strToStack(internalName) ); for (let i = 0; i < segmentsLen; i++) { diff --git a/test/example/c-api-kitchen-sink.c b/test/example/c-api-kitchen-sink.c index d5681097c82..8facf061c7e 100644 --- a/test/example/c-api-kitchen-sink.c +++ b/test/example/c-api-kitchen-sink.c @@ -548,6 +548,7 @@ void test_core() { 2, 1, 0, + 0, "0"); BinaryenExpressionRef valueList[] = { @@ -2108,6 +2109,7 @@ void test_for_each() { 2, 0, 0, + 0, "0"); BinaryenAddGlobal(module, "a-global", @@ -2124,6 +2126,11 @@ void test_for_each() { BinaryenCopyMemorySegmentData(module, segmentNames[i], out); assert(0 == strcmp(segmentDatas[i], out)); } + + BinaryenIndex numSegments = BinaryenGetNumMemorySegments(module); + BinaryenSetMemory( + module, 1, 256, NULL, NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 1, "0"); + assert(numSegments == BinaryenGetNumMemorySegments(module)); } { const char* funcNames[] = {BinaryenFunctionGetName(fns[0]), diff --git a/test/example/c-api-relooper-unreachable-if.cpp b/test/example/c-api-relooper-unreachable-if.cpp index 96c6c114976..8e9005de22a 100644 --- a/test/example/c-api-relooper-unreachable-if.cpp +++ b/test/example/c-api-relooper-unreachable-if.cpp @@ -32,6 +32,7 @@ int main() { 0, 0, 0, + 0, "0"); } the_relooper = RelooperCreate(the_module); @@ -604,6 +605,7 @@ int main() { 0, 0, 0, + 0, "0"); } expressions[157] = BinaryenConst(the_module, BinaryenLiteralInt32(65535)); diff --git a/test/example/c-api-unused-mem.cpp b/test/example/c-api-unused-mem.cpp index 750f3b703bc..74b6c5beefc 100644 --- a/test/example/c-api-unused-mem.cpp +++ b/test/example/c-api-unused-mem.cpp @@ -33,6 +33,7 @@ int main() { 0, 0, 0, + 0, "0"); } the_relooper = RelooperCreate(the_module); @@ -100,6 +101,7 @@ int main() { 0, 0, 0, + 0, "0"); } expressions[11] = BinaryenConst(the_module, BinaryenLiteralInt32(65535)); diff --git a/test/example/relooper-fuzz.c b/test/example/relooper-fuzz.c index afa8e7ec167..916050a1114 100644 --- a/test/example/relooper-fuzz.c +++ b/test/example/relooper-fuzz.c @@ -370,7 +370,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); assert(BinaryenModuleValidate(module)); diff --git a/test/example/relooper-fuzz1.c b/test/example/relooper-fuzz1.c index a2594407aee..eacfa3b0b02 100644 --- a/test/example/relooper-fuzz1.c +++ b/test/example/relooper-fuzz1.c @@ -367,7 +367,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); assert(BinaryenModuleValidate(module)); diff --git a/test/example/relooper-fuzz2.c b/test/example/relooper-fuzz2.c index 9ccba34d77b..461d12bd753 100644 --- a/test/example/relooper-fuzz2.c +++ b/test/example/relooper-fuzz2.c @@ -691,7 +691,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); // optionally, optimize if (0) diff --git a/test/example/relooper-merge1.c b/test/example/relooper-merge1.c index d571696f893..80d63996c2c 100644 --- a/test/example/relooper-merge1.c +++ b/test/example/relooper-merge1.c @@ -233,7 +233,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); // optionally, optimize if (0) diff --git a/test/example/relooper-merge2.c b/test/example/relooper-merge2.c index c70ef5601a0..997bb905541 100644 --- a/test/example/relooper-merge2.c +++ b/test/example/relooper-merge2.c @@ -248,7 +248,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); // optionally, optimize if (0) diff --git a/test/example/relooper-merge3.c b/test/example/relooper-merge3.c index 93373925424..1045666c0a0 100644 --- a/test/example/relooper-merge3.c +++ b/test/example/relooper-merge3.c @@ -232,7 +232,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); // optionally, optimize if (0) diff --git a/test/example/relooper-merge4.c b/test/example/relooper-merge4.c index 6fc36be36c8..1a71a0e6ab0 100644 --- a/test/example/relooper-merge4.c +++ b/test/example/relooper-merge4.c @@ -232,7 +232,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); // optionally, optimize if (0) diff --git a/test/example/relooper-merge5.c b/test/example/relooper-merge5.c index 7e4fbee0f81..4d836c81b01 100644 --- a/test/example/relooper-merge5.c +++ b/test/example/relooper-merge5.c @@ -232,7 +232,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); // optionally, optimize if (0) diff --git a/test/example/relooper-merge6.c b/test/example/relooper-merge6.c index 93043ef32b1..2f4afb71dc6 100644 --- a/test/example/relooper-merge6.c +++ b/test/example/relooper-merge6.c @@ -235,7 +235,7 @@ int main() { // memory BinaryenSetMemory( - module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, "0"); + module, 1, 1, "mem", NULL, NULL, NULL, NULL, NULL, 0, 0, 0, 0, "0"); // optionally, optimize if (0)