Skip to content

Commit

Permalink
Merge pull request #104 from turbolent/improve-data-segment-declaration
Browse files Browse the repository at this point in the history
  • Loading branch information
turbolent authored Oct 13, 2024
2 parents 3b18f55 + b2496ea commit 2a4684e
Show file tree
Hide file tree
Showing 3 changed files with 109 additions and 74 deletions.
177 changes: 103 additions & 74 deletions w2c2/c.c
Original file line number Diff line number Diff line change
Expand Up @@ -5116,52 +5116,66 @@ wasmCWriteDataSegments(
) {
const U32 dataSegmentCount = module->dataSegments.count;

{
U32 dataSegmentIndex = 0;
for (; dataSegmentIndex < dataSegmentCount; dataSegmentIndex++) {
const WasmDataSegment dataSegment = module->dataSegments.dataSegments[dataSegmentIndex];

switch (mode) {
case wasmDataSegmentModeArrays: {
fputs("const U8 ", file);
/* TODO: add support for multiple modules */
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
if (pretty) {
fputs("[] = {\n", file);
} else {
fputs("[]={\n", file);
}
if (pretty) {
fputs(indentation, file);
}
{
U32 byteIndex = 0;
for (; byteIndex < dataSegment.bytes.length; byteIndex++) {
fprintf(file, "0x%x", dataSegment.bytes.data[byteIndex]);
if (pretty) {
fputs(", ", file);
} else {
fputc(',', file);
}
switch (mode) {
case wasmDataSegmentModeArrays: {
U32 dataSegmentIndex = 0;
for (; dataSegmentIndex < dataSegmentCount; dataSegmentIndex++) {
const WasmDataSegment dataSegment = module->dataSegments.dataSegments[dataSegmentIndex];

fputs("const U8 ", file);
/* TODO: add support for multiple modules */
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
if (pretty) {
fputs("[] = {\n", file);
} else {
fputs("[]={\n", file);
}
if (pretty) {
fputs(indentation, file);
}
{
U32 byteIndex = 0;
for (; byteIndex < dataSegment.bytes.length; byteIndex++) {
fprintf(file, "0x%x", dataSegment.bytes.data[byteIndex]);
if (pretty) {
fputs(", ", file);
} else {
fputc(',', file);
}
}
fputs("\n};\n\n", file);
break;
}
case wasmDataSegmentModeGNULD:
case wasmDataSegmentModeSectcreate1:
case wasmDataSegmentModeSectcreate2: {
fputs("U8* ", file);
/* TODO: add support for multiple modules */
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
fputs(";\n", file);
break;
fputs("\n};\n\n", file);
}
break;
}
case wasmDataSegmentModeGNULD:
case wasmDataSegmentModeSectcreate1:
case wasmDataSegmentModeSectcreate2: {
U32 writtenCount = 0;
U32 dataSegmentIndex = 0;
for (; dataSegmentIndex < dataSegmentCount; dataSegmentIndex++) {
const WasmDataSegment dataSegment = module->dataSegments.dataSegments[dataSegmentIndex];
if (!dataSegment.passive) {
continue;
}
default: {
fprintf(stderr, "w2c2: unsupported data segment mode: %d\n", mode);
abort();
if (writtenCount == 0) {
fputs("U8 ", file);
} else {
fputc(',', file);
}
fputc('*', file);
/* TODO: add support for multiple modules */
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
writtenCount += 1;
}
if (writtenCount > 0) {
fputs(";\n", file);
}
break;
}
default: {
fprintf(stderr, "w2c2: unsupported data segment mode: %d\n", mode);
abort();
}
}
}
Expand All @@ -5181,13 +5195,13 @@ wasmCWriteDataSegmentsFromSection(

switch (mode) {
case wasmDataSegmentModeGNULD: {
fputs("extern char _binary_datasegments_start[];\n\n", file);
fputs("static char* ds = _binary_datasegments_start;\n", file);
fputs("extern U8 _binary_datasegments_start[];\n\n", file);
fputs("static U8* ds = _binary_datasegments_start;\n", file);
break;
}
case wasmDataSegmentModeSectcreate1: {
fputs("extern char data_segments_data __asm(\"section$start$__DATA$__datasegments\");\n\n", file);
fputs("static char* ds = &data_segments_data;\n", file);
fputs("extern U8 data_segments_data __asm(\"section$start$__DATA$__datasegments\");\n\n", file);
fputs("static U8* ds = &data_segments_data;\n", file);
break;
}
case wasmDataSegmentModeSectcreate2: {
Expand Down Expand Up @@ -5383,43 +5397,58 @@ wasmCWriteInitMemories(
const size_t dataSegmentLength = dataSegment.bytes.length;
const Buffer code = dataSegment.offset;

switch (dataSegmentMode) {
case wasmDataSegmentModeGNULD:
case wasmDataSegmentModeSectcreate1:
case wasmDataSegmentModeSectcreate2: {
/* TODO: add support for multiple modules */
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
if (pretty) {
fprintf(file, " = ds + %llu", byteOffset);
} else {
fprintf(file, "=ds+%llu", byteOffset);
if (dataSegment.passive) {
switch (dataSegmentMode) {
case wasmDataSegmentModeGNULD:
case wasmDataSegmentModeSectcreate1:
case wasmDataSegmentModeSectcreate2: {
/* Initialize the data segment variable */
/* TODO: add support for multiple modules */
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
if (pretty) {
fprintf(file, " = ds + %llu", byteOffset);
} else {
fprintf(file, "=ds+%llu", byteOffset);
}
fputs(";\n", file);
break;
}
fputs(";\n", file);
break;
}
}

/* Load active segments */
if (code.data != NULL) {
if (pretty) {
fputs(indentation, file);
case wasmDataSegmentModeArrays:
/* The data segment variable is already initialized */
break;
}
fputs("LOAD_DATA(", file);
wasmCWriteFileMemoryUse(
} else {
/* Load active segments */
if (code.data != NULL) {
if (pretty) {
fputs(indentation, file);
}
fputs("LOAD_DATA(", file);
wasmCWriteFileMemoryUse(
file,
module,
dataSegment.memoryIndex,
NULL,
false
);
fputs(", ", file);
MUST (stringBuilderReset(&stringBuilder))
MUST (wasmCWriteConstantExpr(&stringBuilder, module, code))
fputs(stringBuilder.string, file);
fputs(", ", file);
/* TODO: add support for multiple modules */
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
fprintf(file, ", %lu);\n", (unsigned long) dataSegmentLength);
);
fputs(", ", file);
MUST (stringBuilderReset(&stringBuilder))
MUST (wasmCWriteConstantExpr(&stringBuilder, module, code))
fputs(stringBuilder.string, file);
/* TODO: add support for multiple modules */
switch (dataSegmentMode) {
case wasmDataSegmentModeGNULD:
case wasmDataSegmentModeSectcreate1:
case wasmDataSegmentModeSectcreate2:
fprintf(file, ", ds+%llu", byteOffset);
break;
case wasmDataSegmentModeArrays:
fputs(", ", file);
wasmCWriteFileDataSegmentName(file, dataSegmentIndex);
break;
}
fprintf(file, ", %lu);\n", (unsigned long) dataSegmentLength);
}
}

byteOffset += dataSegment.bytes.length;
Expand Down
1 change: 1 addition & 0 deletions w2c2/datasegment.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ typedef struct WasmDataSegment {
U32 memoryIndex;
Buffer offset;
Buffer bytes;
bool passive;
} WasmDataSegment;

static const WasmDataSegment wasmEmptyDataSegment = {0, {0, false}, {0, false}};
Expand Down
5 changes: 5 additions & 0 deletions w2c2/reader.c
Original file line number Diff line number Diff line change
Expand Up @@ -1530,6 +1530,7 @@ wasmReadDataSegment(
U8 kind = 0;
bool readMemoryIndex = false;
bool readOffsetExpression = false;
bool passive = false;
U32 memoryIndex = 0;
Buffer offset = {NULL, 0};
Buffer bytes = {NULL, 0};
Expand All @@ -1546,15 +1547,18 @@ wasmReadDataSegment(
case 0x0: {
readMemoryIndex = false;
readOffsetExpression = true;
passive = false;
break;
}
case 0x1:
readMemoryIndex = false;
readOffsetExpression = false;
passive = true;
break;
case 0x2:
readMemoryIndex = true;
readOffsetExpression = true;
passive = false;
break;
default: {
static WasmModuleReaderError wasmModuleReaderError = {
Expand Down Expand Up @@ -1603,6 +1607,7 @@ wasmReadDataSegment(
result->memoryIndex = memoryIndex;
result->offset = offset;
result->bytes = bytes;
result->passive = passive;
}

static
Expand Down

0 comments on commit 2a4684e

Please sign in to comment.