Skip to content

Commit

Permalink
[wasm] use sbrk instead of emscripten mmap or malloc when loading byt…
Browse files Browse the repository at this point in the history
…es into heap (#100106)

Use sbrk to allocate persistent space for large load_bytes_into_heap calls to avoid the startup overhead of emscripten's malloc and memset for the new space
  • Loading branch information
kg authored Apr 9, 2024
1 parent 89ab2a9 commit 001d60a
Show file tree
Hide file tree
Showing 5 changed files with 23 additions and 3 deletions.
1 change: 1 addition & 0 deletions src/mono/browser/browser.proj
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,7 @@
<EmccExportedFunction Include="_free" />
<EmccExportedFunction Include="_htons" />
<EmccExportedFunction Include="_malloc" />
<EmccExportedFunction Include="_sbrk" />
<EmccExportedFunction Include="_memalign" />
<EmccExportedFunction Include="_memset" />
<EmccExportedFunction Include="_ntohs" />
Expand Down
4 changes: 2 additions & 2 deletions src/mono/browser/runtime/assets.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import cwraps from "./cwraps";
import { mono_wasm_load_icu_data } from "./icu";
import { Module, loaderHelpers, mono_assert, runtimeHelpers } from "./globals";
import { mono_log_info, mono_log_debug, parseSymbolMapFile } from "./logging";
import { mono_wasm_load_bytes_into_heap } from "./memory";
import { mono_wasm_load_bytes_into_heap_persistent } from "./memory";
import { endMeasure, MeasuredBlock, startMeasure } from "./profiler";
import { AssetEntry } from "./types";
import { VoidPtr } from "./types/emscripten";
Expand Down Expand Up @@ -37,7 +37,7 @@ export function instantiate_asset (asset: AssetEntry, url: string, bytes: Uint8A
// falls through
case "heap":
case "icu":
offset = mono_wasm_load_bytes_into_heap(bytes);
offset = mono_wasm_load_bytes_into_heap_persistent(bytes);
break;

case "vfs": {
Expand Down
1 change: 1 addition & 0 deletions src/mono/browser/runtime/dotnet.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ declare interface Int32Ptr extends NativePointer {
declare interface EmscriptenModule {
_malloc(size: number): VoidPtr;
_free(ptr: VoidPtr): void;
_sbrk(size: number): VoidPtr;
out(message: string): void;
err(message: string): void;
ccall<T>(ident: string, returnType?: string | null, argTypes?: string[], args?: any[], opts?: any): T;
Expand Down
19 changes: 18 additions & 1 deletion src/mono/browser/runtime/memory.ts
Original file line number Diff line number Diff line change
Expand Up @@ -325,7 +325,24 @@ export function withStackAlloc<T1, T2, T3, TResult> (bytesWanted: number, f: (pt
// @bytes must be a typed array. space is allocated for it in the native heap
// and it is copied to that location. returns the address of the allocation.
export function mono_wasm_load_bytes_into_heap (bytes: Uint8Array): VoidPtr {
const memoryOffset = Module._malloc(bytes.length);
// pad sizes by 16 bytes for simd
const memoryOffset = Module._malloc(bytes.length + 16);
const heapBytes = new Uint8Array(localHeapViewU8().buffer, <any>memoryOffset, bytes.length);
heapBytes.set(bytes);
return memoryOffset;
}

// @bytes must be a typed array. space is allocated for it in memory
// and it is copied to that location. returns the address of the data.
// the result pointer *cannot* be freed because malloc is bypassed for speed.
export function mono_wasm_load_bytes_into_heap_persistent (bytes: Uint8Array): VoidPtr {
// pad sizes by 16 bytes for simd
const desiredSize = bytes.length + 16;
// wasm memory page size is 64kb. allocations smaller than that are probably best
// serviced by malloc
const memoryOffset = (desiredSize < (64 * 1024))
? Module._malloc(desiredSize)
: Module._sbrk(desiredSize);
const heapBytes = new Uint8Array(localHeapViewU8().buffer, <any>memoryOffset, bytes.length);
heapBytes.set(bytes);
return memoryOffset;
Expand Down
1 change: 1 addition & 0 deletions src/mono/browser/runtime/types/emscripten.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ export declare interface EmscriptenModule {
// this should match emcc -s EXPORTED_FUNCTIONS
_malloc(size: number): VoidPtr;
_free(ptr: VoidPtr): void;
_sbrk(size: number): VoidPtr;

// this should match emcc -s EXPORTED_RUNTIME_METHODS
out(message: string): void;
Expand Down

0 comments on commit 001d60a

Please sign in to comment.