toilscript 0.0.1 → 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +201 -201
- package/NOTICE +94 -94
- package/README.md +101 -114
- package/bin/asc.js +0 -0
- package/bin/asinit.js +0 -0
- package/dist/asc.generated.d.ts +10022 -0
- package/dist/asc.js +24457 -0
- package/dist/asc.js.map +7 -0
- package/dist/importmap.json +9 -0
- package/dist/toilscript.generated.d.ts +11237 -0
- package/dist/toilscript.js +337 -0
- package/dist/toilscript.js.map +7 -0
- package/dist/web.js +22 -0
- package/lib/binaryen.d.ts +2 -2
- package/lib/binaryen.js +2 -2
- package/package.json +115 -114
- package/std/README.md +6 -6
- package/std/assembly/array.ts +550 -550
- package/std/assembly/arraybuffer.ts +77 -77
- package/std/assembly/atomics.ts +127 -127
- package/std/assembly/bindings/asyncify.ts +16 -16
- package/std/assembly/bindings/dom.ts +291 -291
- package/std/assembly/bindings/node.ts +6 -6
- package/std/assembly/bitflags.ts +53 -53
- package/std/assembly/builtins.ts +2650 -2650
- package/std/assembly/byteslice.ts +177 -177
- package/std/assembly/compat.ts +2 -2
- package/std/assembly/console.ts +42 -42
- package/std/assembly/crypto.ts +9 -9
- package/std/assembly/dataview.ts +181 -181
- package/std/assembly/date.ts +375 -375
- package/std/assembly/diagnostics.ts +11 -11
- package/std/assembly/encoding.ts +151 -151
- package/std/assembly/endian.ts +45 -45
- package/std/assembly/error.ts +44 -44
- package/std/assembly/fixedarray.ts +173 -173
- package/std/assembly/fixedmap.ts +326 -326
- package/std/assembly/fixedset.ts +275 -275
- package/std/assembly/function.ts +42 -42
- package/std/assembly/index.d.ts +2891 -2891
- package/std/assembly/iterator.ts +35 -35
- package/std/assembly/map.ts +269 -269
- package/std/assembly/math.ts +3289 -3289
- package/std/assembly/memory.ts +123 -123
- package/std/assembly/number.ts +388 -388
- package/std/assembly/object.ts +36 -36
- package/std/assembly/performance.ts +9 -9
- package/std/assembly/pointer.ts +80 -80
- package/std/assembly/polyfills.ts +27 -27
- package/std/assembly/process.ts +50 -50
- package/std/assembly/reference.ts +48 -48
- package/std/assembly/regexp.ts +12 -12
- package/std/assembly/rt/README.md +83 -83
- package/std/assembly/rt/common.ts +81 -81
- package/std/assembly/rt/index-incremental.ts +2 -2
- package/std/assembly/rt/index-memory.ts +1 -1
- package/std/assembly/rt/index-minimal.ts +2 -2
- package/std/assembly/rt/index-stub.ts +1 -1
- package/std/assembly/rt/index.d.ts +37 -37
- package/std/assembly/rt/itcms.ts +419 -419
- package/std/assembly/rt/memory-runtime.ts +94 -94
- package/std/assembly/rt/rtrace.ts +15 -15
- package/std/assembly/rt/stub.ts +133 -133
- package/std/assembly/rt/tcms.ts +254 -254
- package/std/assembly/rt/tlsf.ts +592 -592
- package/std/assembly/rt.ts +90 -90
- package/std/assembly/set.ts +225 -225
- package/std/assembly/shared/feature.ts +68 -68
- package/std/assembly/shared/runtime.ts +13 -13
- package/std/assembly/shared/target.ts +11 -11
- package/std/assembly/shared/tsconfig.json +11 -11
- package/std/assembly/shared/typeinfo.ts +72 -72
- package/std/assembly/staticarray.ts +423 -423
- package/std/assembly/string.ts +850 -850
- package/std/assembly/symbol.ts +114 -114
- package/std/assembly/table.ts +16 -16
- package/std/assembly/tsconfig.json +6 -6
- package/std/assembly/typedarray.ts +1954 -1954
- package/std/assembly/uri.ts +17 -17
- package/std/assembly/util/bytes.ts +107 -107
- package/std/assembly/util/casemap.ts +497 -497
- package/std/assembly/util/error.ts +58 -58
- package/std/assembly/util/hash.ts +117 -117
- package/std/assembly/util/math.ts +1922 -1922
- package/std/assembly/util/memory.ts +290 -290
- package/std/assembly/util/number.ts +873 -873
- package/std/assembly/util/sort.ts +313 -313
- package/std/assembly/util/string.ts +1202 -1202
- package/std/assembly/util/uri.ts +275 -275
- package/std/assembly/vector.ts +4 -4
- package/std/assembly.json +16 -16
- package/std/portable/index.d.ts +461 -461
- package/std/portable/index.js +416 -416
- package/std/portable.json +11 -11
- package/std/types/assembly/index.d.ts +1 -1
- package/std/types/assembly/package.json +2 -2
- package/std/types/portable/index.d.ts +1 -1
- package/std/types/portable/package.json +2 -2
- package/tsconfig-base.json +13 -13
- package/util/README.md +23 -23
- package/util/browser/fs.js +1 -1
- package/util/browser/module.js +5 -5
- package/util/browser/path.js +520 -520
- package/util/browser/process.js +59 -59
- package/util/browser/url.js +23 -23
- package/util/cpu.d.ts +9 -9
- package/util/cpu.js +42 -42
- package/util/find.d.ts +6 -6
- package/util/find.js +20 -20
- package/util/node.d.ts +21 -21
- package/util/node.js +34 -34
- package/util/options.d.ts +70 -70
- package/util/options.js +262 -262
- package/util/terminal.d.ts +52 -52
- package/util/terminal.js +35 -35
- package/util/text.d.ts +26 -26
- package/util/text.js +114 -114
- package/util/tsconfig.json +9 -9
- package/util/web.d.ts +11 -11
- package/util/web.js +33 -33
|
@@ -1,94 +1,94 @@
|
|
|
1
|
-
import { AL_MASK, OBJECT, OBJECT_OVERHEAD, BLOCK_MAXSIZE, BLOCK_OVERHEAD, BLOCK, OBJECT_MAXSIZE } from "./common";
|
|
2
|
-
import { E_ALLOCATION_TOO_LARGE } from "../util/error";
|
|
3
|
-
|
|
4
|
-
// === Runtime "none": memory only, no GC ===
|
|
5
|
-
|
|
6
|
-
// @ts-ignore: decorator
|
|
7
|
-
@lazy let offset: usize = ((__heap_base + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
8
|
-
|
|
9
|
-
function maybeGrowMemory(newOffset: usize): void {
|
|
10
|
-
let pagesBefore = memory.size();
|
|
11
|
-
let maxOffset = ((<usize>pagesBefore << 16) + AL_MASK) & ~AL_MASK;
|
|
12
|
-
if (newOffset > maxOffset) {
|
|
13
|
-
let pagesNeeded = <i32>(((newOffset - maxOffset + 0xffff) & ~0xffff) >>> 16);
|
|
14
|
-
let pagesWanted = max(pagesBefore, pagesNeeded);
|
|
15
|
-
if (memory.grow(pagesWanted) < 0) {
|
|
16
|
-
if (memory.grow(pagesNeeded) < 0) unreachable();
|
|
17
|
-
}
|
|
18
|
-
}
|
|
19
|
-
offset = newOffset;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
// @ts-ignore: decorator
|
|
23
|
-
@inline function computeSize(size: usize): usize {
|
|
24
|
-
return ((size + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
// @ts-ignore: decorator
|
|
28
|
-
@unsafe @global
|
|
29
|
-
export function __alloc(size: usize): usize {
|
|
30
|
-
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
31
|
-
let block = changetype<BLOCK>(offset);
|
|
32
|
-
let ptr = offset + BLOCK_OVERHEAD;
|
|
33
|
-
let payloadSize = computeSize(size);
|
|
34
|
-
maybeGrowMemory(ptr + payloadSize);
|
|
35
|
-
block.mmInfo = payloadSize;
|
|
36
|
-
return ptr;
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
// @ts-ignore: decorator
|
|
40
|
-
@unsafe @global
|
|
41
|
-
export function __realloc(ptr: usize, size: usize): usize {
|
|
42
|
-
assert(ptr != 0 && !(ptr & AL_MASK));
|
|
43
|
-
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
44
|
-
let actualSize = block.mmInfo;
|
|
45
|
-
let isLast = ptr + actualSize == offset;
|
|
46
|
-
let payloadSize = computeSize(size);
|
|
47
|
-
if (size > actualSize) {
|
|
48
|
-
if (isLast) {
|
|
49
|
-
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
50
|
-
maybeGrowMemory(ptr + payloadSize);
|
|
51
|
-
block.mmInfo = payloadSize;
|
|
52
|
-
} else {
|
|
53
|
-
let newPtr = __alloc(max<usize>(payloadSize, actualSize << 1));
|
|
54
|
-
memory.copy(newPtr, ptr, actualSize);
|
|
55
|
-
block = changetype<BLOCK>((ptr = newPtr) - BLOCK_OVERHEAD);
|
|
56
|
-
}
|
|
57
|
-
} else if (isLast) {
|
|
58
|
-
offset = ptr + payloadSize;
|
|
59
|
-
block.mmInfo = payloadSize;
|
|
60
|
-
}
|
|
61
|
-
return ptr;
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
// @ts-ignore: decorator
|
|
65
|
-
@unsafe @global
|
|
66
|
-
export function __free(ptr: usize): void {
|
|
67
|
-
assert(ptr != 0 && !(ptr & AL_MASK));
|
|
68
|
-
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
69
|
-
if (ptr + block.mmInfo == offset) {
|
|
70
|
-
offset = changetype<usize>(block);
|
|
71
|
-
}
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
// @ts-ignore: decorator
|
|
75
|
-
@unsafe @global
|
|
76
|
-
export function __new(size: usize, id: u32): usize {
|
|
77
|
-
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
78
|
-
let ptr = __alloc(OBJECT_OVERHEAD + size);
|
|
79
|
-
let object = changetype<OBJECT>(ptr - BLOCK_OVERHEAD);
|
|
80
|
-
object.gcInfo = 0;
|
|
81
|
-
object.gcInfo2 = 0;
|
|
82
|
-
object.rtId = id;
|
|
83
|
-
object.rtSize = <u32>size;
|
|
84
|
-
return ptr + OBJECT_OVERHEAD;
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
// @ts-ignore: decorator
|
|
88
|
-
@unsafe @global
|
|
89
|
-
export function __renew(oldPtr: usize, size: usize): usize {
|
|
90
|
-
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
91
|
-
let newPtr = __realloc(oldPtr - OBJECT_OVERHEAD, OBJECT_OVERHEAD + size);
|
|
92
|
-
changetype<OBJECT>(newPtr - BLOCK_OVERHEAD).rtSize = <u32>size;
|
|
93
|
-
return newPtr + OBJECT_OVERHEAD;
|
|
94
|
-
}
|
|
1
|
+
import { AL_MASK, OBJECT, OBJECT_OVERHEAD, BLOCK_MAXSIZE, BLOCK_OVERHEAD, BLOCK, OBJECT_MAXSIZE } from "./common";
|
|
2
|
+
import { E_ALLOCATION_TOO_LARGE } from "../util/error";
|
|
3
|
+
|
|
4
|
+
// === Runtime "none": memory only, no GC ===
|
|
5
|
+
|
|
6
|
+
// @ts-ignore: decorator
|
|
7
|
+
@lazy let offset: usize = ((__heap_base + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
8
|
+
|
|
9
|
+
function maybeGrowMemory(newOffset: usize): void {
|
|
10
|
+
let pagesBefore = memory.size();
|
|
11
|
+
let maxOffset = ((<usize>pagesBefore << 16) + AL_MASK) & ~AL_MASK;
|
|
12
|
+
if (newOffset > maxOffset) {
|
|
13
|
+
let pagesNeeded = <i32>(((newOffset - maxOffset + 0xffff) & ~0xffff) >>> 16);
|
|
14
|
+
let pagesWanted = max(pagesBefore, pagesNeeded);
|
|
15
|
+
if (memory.grow(pagesWanted) < 0) {
|
|
16
|
+
if (memory.grow(pagesNeeded) < 0) unreachable();
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
offset = newOffset;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
// @ts-ignore: decorator
|
|
23
|
+
@inline function computeSize(size: usize): usize {
|
|
24
|
+
return ((size + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
// @ts-ignore: decorator
|
|
28
|
+
@unsafe @global
|
|
29
|
+
export function __alloc(size: usize): usize {
|
|
30
|
+
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
31
|
+
let block = changetype<BLOCK>(offset);
|
|
32
|
+
let ptr = offset + BLOCK_OVERHEAD;
|
|
33
|
+
let payloadSize = computeSize(size);
|
|
34
|
+
maybeGrowMemory(ptr + payloadSize);
|
|
35
|
+
block.mmInfo = payloadSize;
|
|
36
|
+
return ptr;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
// @ts-ignore: decorator
|
|
40
|
+
@unsafe @global
|
|
41
|
+
export function __realloc(ptr: usize, size: usize): usize {
|
|
42
|
+
assert(ptr != 0 && !(ptr & AL_MASK));
|
|
43
|
+
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
44
|
+
let actualSize = block.mmInfo;
|
|
45
|
+
let isLast = ptr + actualSize == offset;
|
|
46
|
+
let payloadSize = computeSize(size);
|
|
47
|
+
if (size > actualSize) {
|
|
48
|
+
if (isLast) {
|
|
49
|
+
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
50
|
+
maybeGrowMemory(ptr + payloadSize);
|
|
51
|
+
block.mmInfo = payloadSize;
|
|
52
|
+
} else {
|
|
53
|
+
let newPtr = __alloc(max<usize>(payloadSize, actualSize << 1));
|
|
54
|
+
memory.copy(newPtr, ptr, actualSize);
|
|
55
|
+
block = changetype<BLOCK>((ptr = newPtr) - BLOCK_OVERHEAD);
|
|
56
|
+
}
|
|
57
|
+
} else if (isLast) {
|
|
58
|
+
offset = ptr + payloadSize;
|
|
59
|
+
block.mmInfo = payloadSize;
|
|
60
|
+
}
|
|
61
|
+
return ptr;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
// @ts-ignore: decorator
|
|
65
|
+
@unsafe @global
|
|
66
|
+
export function __free(ptr: usize): void {
|
|
67
|
+
assert(ptr != 0 && !(ptr & AL_MASK));
|
|
68
|
+
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
69
|
+
if (ptr + block.mmInfo == offset) {
|
|
70
|
+
offset = changetype<usize>(block);
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
// @ts-ignore: decorator
|
|
75
|
+
@unsafe @global
|
|
76
|
+
export function __new(size: usize, id: u32): usize {
|
|
77
|
+
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
78
|
+
let ptr = __alloc(OBJECT_OVERHEAD + size);
|
|
79
|
+
let object = changetype<OBJECT>(ptr - BLOCK_OVERHEAD);
|
|
80
|
+
object.gcInfo = 0;
|
|
81
|
+
object.gcInfo2 = 0;
|
|
82
|
+
object.rtId = id;
|
|
83
|
+
object.rtSize = <u32>size;
|
|
84
|
+
return ptr + OBJECT_OVERHEAD;
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
// @ts-ignore: decorator
|
|
88
|
+
@unsafe @global
|
|
89
|
+
export function __renew(oldPtr: usize, size: usize): usize {
|
|
90
|
+
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
91
|
+
let newPtr = __realloc(oldPtr - OBJECT_OVERHEAD, OBJECT_OVERHEAD + size);
|
|
92
|
+
changetype<OBJECT>(newPtr - BLOCK_OVERHEAD).rtSize = <u32>size;
|
|
93
|
+
return newPtr + OBJECT_OVERHEAD;
|
|
94
|
+
}
|
|
@@ -1,15 +1,15 @@
|
|
|
1
|
-
import { BLOCK } from "./common";
|
|
2
|
-
|
|
3
|
-
export declare function oninit(heapBase: usize): void;
|
|
4
|
-
|
|
5
|
-
// Memory Allocator
|
|
6
|
-
export declare function onalloc(block: BLOCK): void;
|
|
7
|
-
export declare function onresize(block: BLOCK, oldSizeInclOverhead: usize): void;
|
|
8
|
-
export declare function onmove(oldBlock: BLOCK, newBlock: BLOCK): void;
|
|
9
|
-
export declare function onfree(block: BLOCK): void;
|
|
10
|
-
|
|
11
|
-
// Garbage collector
|
|
12
|
-
export declare function onvisit(block: BLOCK): bool;
|
|
13
|
-
export declare function oncollect(total: usize): void;
|
|
14
|
-
export declare function oninterrupt(total: usize): void;
|
|
15
|
-
export declare function onyield(total: usize): void;
|
|
1
|
+
import { BLOCK } from "./common";
|
|
2
|
+
|
|
3
|
+
export declare function oninit(heapBase: usize): void;
|
|
4
|
+
|
|
5
|
+
// Memory Allocator
|
|
6
|
+
export declare function onalloc(block: BLOCK): void;
|
|
7
|
+
export declare function onresize(block: BLOCK, oldSizeInclOverhead: usize): void;
|
|
8
|
+
export declare function onmove(oldBlock: BLOCK, newBlock: BLOCK): void;
|
|
9
|
+
export declare function onfree(block: BLOCK): void;
|
|
10
|
+
|
|
11
|
+
// Garbage collector
|
|
12
|
+
export declare function onvisit(block: BLOCK): bool;
|
|
13
|
+
export declare function oncollect(total: usize): void;
|
|
14
|
+
export declare function oninterrupt(total: usize): void;
|
|
15
|
+
export declare function onyield(total: usize): void;
|
package/std/assembly/rt/stub.ts
CHANGED
|
@@ -1,133 +1,133 @@
|
|
|
1
|
-
import { AL_MASK, OBJECT, OBJECT_OVERHEAD, BLOCK_MAXSIZE, BLOCK_OVERHEAD, BLOCK, OBJECT_MAXSIZE } from "./common";
|
|
2
|
-
import { E_ALLOCATION_TOO_LARGE } from "../util/error";
|
|
3
|
-
|
|
4
|
-
// === A minimal runtime stub ===
|
|
5
|
-
|
|
6
|
-
// @ts-ignore: decorator
|
|
7
|
-
@lazy let startOffset: usize = ((__heap_base + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
8
|
-
// @ts-ignore: decorator
|
|
9
|
-
@lazy let offset: usize = startOffset;
|
|
10
|
-
|
|
11
|
-
function maybeGrowMemory(newOffset: usize): void {
|
|
12
|
-
// assumes newOffset is aligned
|
|
13
|
-
let pagesBefore = memory.size();
|
|
14
|
-
let maxOffset = ((<usize>pagesBefore << 16) + AL_MASK) & ~AL_MASK;
|
|
15
|
-
if (newOffset > maxOffset) {
|
|
16
|
-
let pagesNeeded = <i32>(((newOffset - maxOffset + 0xffff) & ~0xffff) >>> 16);
|
|
17
|
-
let pagesWanted = max(pagesBefore, pagesNeeded); // double memory
|
|
18
|
-
if (memory.grow(pagesWanted) < 0) {
|
|
19
|
-
if (memory.grow(pagesNeeded) < 0) unreachable(); // out of memory
|
|
20
|
-
}
|
|
21
|
-
}
|
|
22
|
-
offset = newOffset;
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
// @ts-ignore: decorator
|
|
26
|
-
@inline function computeSize(size: usize): usize {
|
|
27
|
-
return ((size + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
// @ts-ignore: decorator
|
|
31
|
-
@unsafe @global
|
|
32
|
-
export function __alloc(size: usize): usize {
|
|
33
|
-
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
34
|
-
let block = changetype<BLOCK>(offset);
|
|
35
|
-
let ptr = offset + BLOCK_OVERHEAD;
|
|
36
|
-
let payloadSize = computeSize(size);
|
|
37
|
-
maybeGrowMemory(ptr + payloadSize);
|
|
38
|
-
block.mmInfo = payloadSize;
|
|
39
|
-
return ptr;
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
// @ts-ignore: decorator
|
|
43
|
-
@unsafe @global
|
|
44
|
-
export function __realloc(ptr: usize, size: usize): usize {
|
|
45
|
-
assert(ptr != 0 && !(ptr & AL_MASK)); // must exist and be aligned
|
|
46
|
-
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
47
|
-
let actualSize = block.mmInfo;
|
|
48
|
-
let isLast = ptr + actualSize == offset;
|
|
49
|
-
let payloadSize = computeSize(size);
|
|
50
|
-
if (size > actualSize) {
|
|
51
|
-
if (isLast) { // last block: grow
|
|
52
|
-
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
53
|
-
maybeGrowMemory(ptr + payloadSize);
|
|
54
|
-
block.mmInfo = payloadSize;
|
|
55
|
-
} else { // copy to new block at least double the size
|
|
56
|
-
let newPtr = __alloc(max<usize>(payloadSize, actualSize << 1));
|
|
57
|
-
memory.copy(newPtr, ptr, actualSize);
|
|
58
|
-
block = changetype<BLOCK>((ptr = newPtr) - BLOCK_OVERHEAD);
|
|
59
|
-
}
|
|
60
|
-
} else if (isLast) { // last block: shrink
|
|
61
|
-
offset = ptr + payloadSize;
|
|
62
|
-
block.mmInfo = payloadSize;
|
|
63
|
-
}
|
|
64
|
-
return ptr;
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
// @ts-ignore: decorator
|
|
68
|
-
@unsafe @global
|
|
69
|
-
export function __free(ptr: usize): void {
|
|
70
|
-
assert(ptr != 0 && !(ptr & AL_MASK)); // must exist and be aligned
|
|
71
|
-
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
72
|
-
if (ptr + block.mmInfo == offset) { // last block: discard
|
|
73
|
-
offset = changetype<usize>(block);
|
|
74
|
-
}
|
|
75
|
-
}
|
|
76
|
-
|
|
77
|
-
// @ts-ignore: decorator
|
|
78
|
-
@unsafe @global
|
|
79
|
-
export function __reset(): void { // special
|
|
80
|
-
offset = startOffset;
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
// @ts-ignore: decorator
|
|
84
|
-
@unsafe @global
|
|
85
|
-
export function __new(size: usize, id: u32): usize {
|
|
86
|
-
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
87
|
-
let ptr = __alloc(OBJECT_OVERHEAD + size);
|
|
88
|
-
let object = changetype<OBJECT>(ptr - BLOCK_OVERHEAD);
|
|
89
|
-
object.gcInfo = 0;
|
|
90
|
-
object.gcInfo2 = 0;
|
|
91
|
-
object.rtId = id;
|
|
92
|
-
object.rtSize = <u32>size;
|
|
93
|
-
return ptr + OBJECT_OVERHEAD;
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
// @ts-ignore: decorator
|
|
97
|
-
@unsafe @global
|
|
98
|
-
export function __renew(oldPtr: usize, size: usize): usize {
|
|
99
|
-
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
100
|
-
let newPtr = __realloc(oldPtr - OBJECT_OVERHEAD, OBJECT_OVERHEAD + size);
|
|
101
|
-
changetype<OBJECT>(newPtr - BLOCK_OVERHEAD).rtSize = <u32>size;
|
|
102
|
-
return newPtr + OBJECT_OVERHEAD;
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
// @ts-ignore: decorator
|
|
106
|
-
@global @unsafe
|
|
107
|
-
export function __link(parentPtr: usize, childPtr: usize, expectMultiple: bool): void {
|
|
108
|
-
// nop
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
// @ts-ignore: decorator
|
|
112
|
-
@global @unsafe
|
|
113
|
-
export function __pin(ptr: usize): usize {
|
|
114
|
-
return ptr;
|
|
115
|
-
}
|
|
116
|
-
|
|
117
|
-
// @ts-ignore: decorator
|
|
118
|
-
@global @unsafe
|
|
119
|
-
export function __unpin(ptr: usize): void {
|
|
120
|
-
// nop
|
|
121
|
-
}
|
|
122
|
-
|
|
123
|
-
// @ts-ignore: decorator
|
|
124
|
-
@global @unsafe
|
|
125
|
-
function __visit(ptr: usize, cookie: u32): void { // eslint-disable-line @typescript-eslint/no-unused-vars
|
|
126
|
-
// nop
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
// @ts-ignore: decorator
|
|
130
|
-
@global @unsafe
|
|
131
|
-
export function __collect(): void {
|
|
132
|
-
// nop
|
|
133
|
-
}
|
|
1
|
+
import { AL_MASK, OBJECT, OBJECT_OVERHEAD, BLOCK_MAXSIZE, BLOCK_OVERHEAD, BLOCK, OBJECT_MAXSIZE } from "./common";
|
|
2
|
+
import { E_ALLOCATION_TOO_LARGE } from "../util/error";
|
|
3
|
+
|
|
4
|
+
// === A minimal runtime stub ===
|
|
5
|
+
|
|
6
|
+
// @ts-ignore: decorator
|
|
7
|
+
@lazy let startOffset: usize = ((__heap_base + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
8
|
+
// @ts-ignore: decorator
|
|
9
|
+
@lazy let offset: usize = startOffset;
|
|
10
|
+
|
|
11
|
+
function maybeGrowMemory(newOffset: usize): void {
|
|
12
|
+
// assumes newOffset is aligned
|
|
13
|
+
let pagesBefore = memory.size();
|
|
14
|
+
let maxOffset = ((<usize>pagesBefore << 16) + AL_MASK) & ~AL_MASK;
|
|
15
|
+
if (newOffset > maxOffset) {
|
|
16
|
+
let pagesNeeded = <i32>(((newOffset - maxOffset + 0xffff) & ~0xffff) >>> 16);
|
|
17
|
+
let pagesWanted = max(pagesBefore, pagesNeeded); // double memory
|
|
18
|
+
if (memory.grow(pagesWanted) < 0) {
|
|
19
|
+
if (memory.grow(pagesNeeded) < 0) unreachable(); // out of memory
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
offset = newOffset;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
// @ts-ignore: decorator
|
|
26
|
+
@inline function computeSize(size: usize): usize {
|
|
27
|
+
return ((size + BLOCK_OVERHEAD + AL_MASK) & ~AL_MASK) - BLOCK_OVERHEAD;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
// @ts-ignore: decorator
|
|
31
|
+
@unsafe @global
|
|
32
|
+
export function __alloc(size: usize): usize {
|
|
33
|
+
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
34
|
+
let block = changetype<BLOCK>(offset);
|
|
35
|
+
let ptr = offset + BLOCK_OVERHEAD;
|
|
36
|
+
let payloadSize = computeSize(size);
|
|
37
|
+
maybeGrowMemory(ptr + payloadSize);
|
|
38
|
+
block.mmInfo = payloadSize;
|
|
39
|
+
return ptr;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
// @ts-ignore: decorator
|
|
43
|
+
@unsafe @global
|
|
44
|
+
export function __realloc(ptr: usize, size: usize): usize {
|
|
45
|
+
assert(ptr != 0 && !(ptr & AL_MASK)); // must exist and be aligned
|
|
46
|
+
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
47
|
+
let actualSize = block.mmInfo;
|
|
48
|
+
let isLast = ptr + actualSize == offset;
|
|
49
|
+
let payloadSize = computeSize(size);
|
|
50
|
+
if (size > actualSize) {
|
|
51
|
+
if (isLast) { // last block: grow
|
|
52
|
+
if (size > BLOCK_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
53
|
+
maybeGrowMemory(ptr + payloadSize);
|
|
54
|
+
block.mmInfo = payloadSize;
|
|
55
|
+
} else { // copy to new block at least double the size
|
|
56
|
+
let newPtr = __alloc(max<usize>(payloadSize, actualSize << 1));
|
|
57
|
+
memory.copy(newPtr, ptr, actualSize);
|
|
58
|
+
block = changetype<BLOCK>((ptr = newPtr) - BLOCK_OVERHEAD);
|
|
59
|
+
}
|
|
60
|
+
} else if (isLast) { // last block: shrink
|
|
61
|
+
offset = ptr + payloadSize;
|
|
62
|
+
block.mmInfo = payloadSize;
|
|
63
|
+
}
|
|
64
|
+
return ptr;
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
// @ts-ignore: decorator
|
|
68
|
+
@unsafe @global
|
|
69
|
+
export function __free(ptr: usize): void {
|
|
70
|
+
assert(ptr != 0 && !(ptr & AL_MASK)); // must exist and be aligned
|
|
71
|
+
let block = changetype<BLOCK>(ptr - BLOCK_OVERHEAD);
|
|
72
|
+
if (ptr + block.mmInfo == offset) { // last block: discard
|
|
73
|
+
offset = changetype<usize>(block);
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
// @ts-ignore: decorator
|
|
78
|
+
@unsafe @global
|
|
79
|
+
export function __reset(): void { // special
|
|
80
|
+
offset = startOffset;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
// @ts-ignore: decorator
|
|
84
|
+
@unsafe @global
|
|
85
|
+
export function __new(size: usize, id: u32): usize {
|
|
86
|
+
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
87
|
+
let ptr = __alloc(OBJECT_OVERHEAD + size);
|
|
88
|
+
let object = changetype<OBJECT>(ptr - BLOCK_OVERHEAD);
|
|
89
|
+
object.gcInfo = 0;
|
|
90
|
+
object.gcInfo2 = 0;
|
|
91
|
+
object.rtId = id;
|
|
92
|
+
object.rtSize = <u32>size;
|
|
93
|
+
return ptr + OBJECT_OVERHEAD;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
// @ts-ignore: decorator
|
|
97
|
+
@unsafe @global
|
|
98
|
+
export function __renew(oldPtr: usize, size: usize): usize {
|
|
99
|
+
if (size > OBJECT_MAXSIZE) throw new Error(E_ALLOCATION_TOO_LARGE);
|
|
100
|
+
let newPtr = __realloc(oldPtr - OBJECT_OVERHEAD, OBJECT_OVERHEAD + size);
|
|
101
|
+
changetype<OBJECT>(newPtr - BLOCK_OVERHEAD).rtSize = <u32>size;
|
|
102
|
+
return newPtr + OBJECT_OVERHEAD;
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
// @ts-ignore: decorator
|
|
106
|
+
@global @unsafe
|
|
107
|
+
export function __link(parentPtr: usize, childPtr: usize, expectMultiple: bool): void {
|
|
108
|
+
// nop
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
// @ts-ignore: decorator
|
|
112
|
+
@global @unsafe
|
|
113
|
+
export function __pin(ptr: usize): usize {
|
|
114
|
+
return ptr;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// @ts-ignore: decorator
|
|
118
|
+
@global @unsafe
|
|
119
|
+
export function __unpin(ptr: usize): void {
|
|
120
|
+
// nop
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
// @ts-ignore: decorator
|
|
124
|
+
@global @unsafe
|
|
125
|
+
function __visit(ptr: usize, cookie: u32): void { // eslint-disable-line @typescript-eslint/no-unused-vars
|
|
126
|
+
// nop
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
// @ts-ignore: decorator
|
|
130
|
+
@global @unsafe
|
|
131
|
+
export function __collect(): void {
|
|
132
|
+
// nop
|
|
133
|
+
}
|