porffor 0.14.0-4e46400a9 → 0.14.0-a24ac8cf2
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/compiler/assemble.js +12 -1
- package/compiler/codegen.js +38 -10
- package/compiler/index.js +3 -8
- package/compiler/precompile.js +1 -1
- package/compiler/prefs.js +1 -1
- package/package.json +1 -1
package/compiler/assemble.js
CHANGED
@@ -65,6 +65,7 @@ export default (funcs, globals, tags, pages, data, flags) => {
|
|
65
65
|
importFuncs = [...imports.values()];
|
66
66
|
|
67
67
|
// fix call indexes for non-imports
|
68
|
+
// also fix call_indirect types
|
68
69
|
const delta = importedFuncs.length - importFuncs.length;
|
69
70
|
for (const f of funcs) {
|
70
71
|
f.originalIndex = f.index;
|
@@ -74,6 +75,16 @@ export default (funcs, globals, tags, pages, data, flags) => {
|
|
74
75
|
if ((inst[0] === Opcodes.call || inst[0] === Opcodes.return_call) && inst[1] >= importedFuncs.length) {
|
75
76
|
inst[1] -= delta;
|
76
77
|
}
|
78
|
+
|
79
|
+
if (inst[0] === Opcodes.call_indirect) {
|
80
|
+
const params = [];
|
81
|
+
for (let i = 0; i < inst[1]; i++) {
|
82
|
+
params.push(valtypeBinary, Valtype.i32);
|
83
|
+
}
|
84
|
+
|
85
|
+
const returns = [ valtypeBinary, Valtype.i32 ];
|
86
|
+
inst[1] = getType(params, returns);
|
87
|
+
}
|
77
88
|
}
|
78
89
|
}
|
79
90
|
}
|
@@ -101,7 +112,7 @@ export default (funcs, globals, tags, pages, data, flags) => {
|
|
101
112
|
encodeVector([ [
|
102
113
|
0x00,
|
103
114
|
Opcodes.i32_const, 0, Opcodes.end,
|
104
|
-
encodeVector(funcs.map(x => x.index))
|
115
|
+
...encodeVector(funcs.map(x => x.index))
|
105
116
|
] ])
|
106
117
|
);
|
107
118
|
|
package/compiler/codegen.js
CHANGED
@@ -351,9 +351,7 @@ const generateReturn = (scope, decl) => {
|
|
351
351
|
|
352
352
|
return [
|
353
353
|
...generate(scope, decl.argument),
|
354
|
-
...(scope.returnType != null ? [] :
|
355
|
-
...getNodeType(scope, decl.argument)
|
356
|
-
]),
|
354
|
+
...(scope.returnType != null ? [] : getNodeType(scope, decl.argument)),
|
357
355
|
[ Opcodes.return ]
|
358
356
|
];
|
359
357
|
};
|
@@ -1451,6 +1449,10 @@ const countLeftover = wasm => {
|
|
1451
1449
|
} else count--;
|
1452
1450
|
if (func) count += func.returns.length;
|
1453
1451
|
}
|
1452
|
+
} else if (inst[0] === Opcodes.call_indirect) {
|
1453
|
+
count--; // funcidx
|
1454
|
+
count -= inst[1] * 2; // params * 2 (typed)
|
1455
|
+
count += 2; // fixed return (value, type)
|
1454
1456
|
} else count--;
|
1455
1457
|
|
1456
1458
|
// console.log(count, decompile([ inst ]).slice(0, -1));
|
@@ -1833,22 +1835,44 @@ const generateCall = (scope, decl, _global, _name, unusedValue = false) => {
|
|
1833
1835
|
|
1834
1836
|
if (idx === undefined) {
|
1835
1837
|
if (scope.locals[name] !== undefined || globals[name] !== undefined || builtinVars[name] !== undefined) {
|
1836
|
-
if (!Prefs.indirectCalls) return internalThrow(scope, 'TypeError', `${unhackName(name)} is not a function`, true);
|
1837
|
-
|
1838
1838
|
const [ local, global ] = lookupName(scope, name);
|
1839
|
-
|
1839
|
+
if (!Prefs.indirectCalls || local == null) return internalThrow(scope, 'TypeError', `${unhackName(name)} is not a function`, true);
|
1840
1840
|
|
1841
1841
|
// todo: only works when:
|
1842
1842
|
// 1. arg count matches arg count of function
|
1843
1843
|
// 2. function uses typedParams and typedReturns
|
1844
|
-
|
1844
|
+
|
1845
|
+
funcs.table = true;
|
1846
|
+
|
1847
|
+
let args = decl.arguments;
|
1848
|
+
let argWasm = [];
|
1849
|
+
|
1850
|
+
for (let i = 0; i < args.length; i++) {
|
1851
|
+
const arg = args[i];
|
1852
|
+
argWasm = argWasm.concat(generate(scope, arg));
|
1853
|
+
|
1854
|
+
if (valtypeBinary !== Valtype.i32 && (
|
1855
|
+
(builtinFuncs[name] && builtinFuncs[name].params[i * (typedParams ? 2 : 1)] === Valtype.i32) ||
|
1856
|
+
(importedFuncs[name] && name.startsWith('profile'))
|
1857
|
+
)) {
|
1858
|
+
argWasm.push(Opcodes.i32_to);
|
1859
|
+
}
|
1860
|
+
|
1861
|
+
argWasm = argWasm.concat(getNodeType(scope, arg));
|
1862
|
+
}
|
1863
|
+
|
1864
|
+
return typeSwitch(scope, getNodeType(scope, decl.callee), {
|
1845
1865
|
[TYPES.function]: [
|
1866
|
+
...argWasm,
|
1846
1867
|
[ global ? Opcodes.global_get : Opcodes.local_get, local.idx ],
|
1847
|
-
|
1868
|
+
Opcodes.i32_to_u,
|
1869
|
+
[ Opcodes.call_indirect, args.length, 0 ],
|
1870
|
+
...setLastType(scope)
|
1848
1871
|
],
|
1849
1872
|
default: internalThrow(scope, 'TypeError', `${unhackName(name)} is not a function`, true)
|
1850
1873
|
});
|
1851
1874
|
}
|
1875
|
+
|
1852
1876
|
return internalThrow(scope, 'ReferenceError', `${unhackName(name)} is not defined`, true);
|
1853
1877
|
}
|
1854
1878
|
|
@@ -3628,8 +3652,10 @@ const internalConstrs = {
|
|
3628
3652
|
}),
|
3629
3653
|
|
3630
3654
|
// print space
|
3631
|
-
...
|
3632
|
-
|
3655
|
+
...(i !== decl.arguments.length - 1 ? [
|
3656
|
+
...number(32),
|
3657
|
+
[ Opcodes.call, importedFuncs.printChar ]
|
3658
|
+
] : [])
|
3633
3659
|
);
|
3634
3660
|
}
|
3635
3661
|
|
@@ -3639,6 +3665,8 @@ const internalConstrs = {
|
|
3639
3665
|
[ Opcodes.call, importedFuncs.printChar ]
|
3640
3666
|
);
|
3641
3667
|
|
3668
|
+
out.push(...number(UNDEFINED));
|
3669
|
+
|
3642
3670
|
return out;
|
3643
3671
|
},
|
3644
3672
|
type: TYPES.undefined,
|
package/compiler/index.js
CHANGED
@@ -12,14 +12,7 @@ globalThis.decompile = decompile;
|
|
12
12
|
const logFuncs = (funcs, globals, exceptions) => {
|
13
13
|
console.log('\n' + underline(bold('funcs')));
|
14
14
|
|
15
|
-
const startIndex = funcs.sort((a, b) => a.index - b.index)[0].index;
|
16
15
|
for (const f of funcs) {
|
17
|
-
console.log(`${underline(f.name)} (${f.index - startIndex})`);
|
18
|
-
|
19
|
-
console.log(`params: ${f.params.map((_, i) => Object.keys(f.locals)[Object.values(f.locals).indexOf(Object.values(f.locals).find(x => x.idx === i))]).join(', ')}`);
|
20
|
-
console.log(`returns: ${f.returns.length > 0 ? true : false}`);
|
21
|
-
console.log(`locals: ${Object.keys(f.locals).sort((a, b) => f.locals[a].idx - f.locals[b].idx).map(x => `${x} (${f.locals[x].idx})`).join(', ')}`);
|
22
|
-
console.log();
|
23
16
|
console.log(decompile(f.wasm, f.name, f.index, f.locals, f.params, f.returns, funcs, globals, exceptions));
|
24
17
|
}
|
25
18
|
|
@@ -44,12 +37,14 @@ export default (code, flags) => {
|
|
44
37
|
opt(funcs, globals, pages, tags, exceptions);
|
45
38
|
if (Prefs.profileCompiler) console.log(`3. optimized in ${(performance.now() - t2).toFixed(2)}ms`);
|
46
39
|
|
47
|
-
if (Prefs.optFuncs) logFuncs(funcs, globals, exceptions);
|
40
|
+
// if (Prefs.optFuncs) logFuncs(funcs, globals, exceptions);
|
48
41
|
|
49
42
|
const t3 = performance.now();
|
50
43
|
const wasm = assemble(funcs, globals, tags, pages, data, flags);
|
51
44
|
if (Prefs.profileCompiler) console.log(`4. assembled in ${(performance.now() - t3).toFixed(2)}ms`);
|
52
45
|
|
46
|
+
if (Prefs.optFuncs) logFuncs(funcs, globals, exceptions);
|
47
|
+
|
53
48
|
if (Prefs.allocLog) {
|
54
49
|
const wasmPages = Math.ceil((pages.size * pageSize) / 65536);
|
55
50
|
const bytes = wasmPages * 65536;
|
package/compiler/precompile.js
CHANGED
@@ -18,7 +18,7 @@ const compile = async (file, [ _funcs, _globals ]) => {
|
|
18
18
|
first = source.slice(0, source.indexOf('\n'));
|
19
19
|
}
|
20
20
|
|
21
|
-
let args = ['--bytestring', '--todo-time=compile', '--no-aot-pointer-opt', '--no-treeshake-wasm-imports', '--no-rm-unused-types', '--scoped-page-names', '--funsafe-no-unlikely-proto-checks', '--parse-types', '--opt-types'];
|
21
|
+
let args = ['--bytestring', '--todo-time=compile', '--no-aot-pointer-opt', '--no-indirect-calls', '--no-treeshake-wasm-imports', '--no-rm-unused-types', '--scoped-page-names', '--funsafe-no-unlikely-proto-checks', '--parse-types', '--opt-types'];
|
22
22
|
if (first.startsWith('// @porf')) {
|
23
23
|
args = args.concat(first.slice('// @porf '.length).split(' '));
|
24
24
|
}
|
package/compiler/prefs.js
CHANGED
package/package.json
CHANGED