porffor 0.60.9 → 0.60.11
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/builtins.js +79 -69
- package/compiler/builtins_precompiled.js +1072 -1072
- package/compiler/codegen.js +62 -67
- package/compiler/precompile.js +3 -3
- package/foo.js +15 -0
- package/package.json +1 -1
- package/runtime/index.js +1 -1
package/compiler/codegen.js
CHANGED
@@ -73,23 +73,12 @@ export const allocStr = (scope, str, bytestring) => {
|
|
73
73
|
return allocBytes(scope, str, bytes);
|
74
74
|
};
|
75
75
|
|
76
|
-
const todo = (scope, msg, expectsValue = undefined) => {
|
77
|
-
msg = `todo: ${msg}`;
|
78
|
-
|
79
|
-
switch (Prefs.todoTime ?? 'runtime') {
|
80
|
-
case 'compile':
|
81
|
-
throw new Error(msg);
|
82
|
-
|
83
|
-
case 'runtime':
|
84
|
-
return internalThrow(scope, 'Error', msg, expectsValue);
|
85
|
-
}
|
86
|
-
};
|
87
76
|
|
88
77
|
const isFuncType = type =>
|
89
78
|
type === 'FunctionDeclaration' || type === 'FunctionExpression' || type === 'ArrowFunctionExpression' ||
|
90
79
|
type === 'ClassDeclaration' || type === 'ClassExpression';
|
91
80
|
const hasFuncWithName = name =>
|
92
|
-
|
81
|
+
name in funcIndex || name in builtinFuncs || name in importedFuncs || name in internalConstrs;
|
93
82
|
|
94
83
|
const astCache = new WeakMap();
|
95
84
|
const cacheAst = (decl, wasm) => {
|
@@ -443,7 +432,7 @@ const generate = (scope, decl, global = false, name = undefined, valueUnused = f
|
|
443
432
|
return cacheAst(decl, generateTaggedTemplate(scope, decl, global, name, valueUnused));
|
444
433
|
|
445
434
|
case 'ExportNamedDeclaration':
|
446
|
-
if (!decl.declaration) return
|
435
|
+
if (!decl.declaration) return internalThrow(scope, 'Error', 'porffor: unsupported export declaration', true);
|
447
436
|
|
448
437
|
const funcsBefore = funcs.map(x => x.name);
|
449
438
|
generate(scope, decl.declaration);
|
@@ -469,6 +458,12 @@ const generate = (scope, decl, global = false, name = undefined, valueUnused = f
|
|
469
458
|
if (Prefs.d) log.warning('codegen', 'with is not supported, treating as expression');
|
470
459
|
return cacheAst(decl, generate(scope, decl.body));
|
471
460
|
|
461
|
+
case 'PrivateIdentifier':
|
462
|
+
return cacheAst(decl, generate(scope, {
|
463
|
+
type: 'Literal',
|
464
|
+
value: privateIDName(decl.name)
|
465
|
+
}));
|
466
|
+
|
472
467
|
case 'TSEnumDeclaration':
|
473
468
|
return cacheAst(decl, generateEnum(scope, decl));
|
474
469
|
|
@@ -479,7 +474,7 @@ const generate = (scope, decl, global = false, name = undefined, valueUnused = f
|
|
479
474
|
return cacheAst(decl, [ number(UNDEFINED) ]);
|
480
475
|
}
|
481
476
|
|
482
|
-
return cacheAst(decl,
|
477
|
+
return cacheAst(decl, internalThrow(scope, 'Error', `porffor: no generation for ${decl.type}`, true));
|
483
478
|
}
|
484
479
|
};
|
485
480
|
|
@@ -541,8 +536,8 @@ const generateEnum = (scope, decl) => {
|
|
541
536
|
const optional = (op, clause = op.at(-1)) => clause || clause === 0 ? (Array.isArray(op[0]) ? op : [ op ]) : [];
|
542
537
|
|
543
538
|
const lookupName = (scope, name) => {
|
544
|
-
if (
|
545
|
-
if (
|
539
|
+
if (name in scope.locals) return [ scope.locals[name], false ];
|
540
|
+
if (name in globals) return [ globals[name], true ];
|
546
541
|
|
547
542
|
return [ undefined, undefined ];
|
548
543
|
};
|
@@ -608,7 +603,7 @@ const hoistLookupType = (scope, name) => {
|
|
608
603
|
const lookup = (scope, name, failEarly = false) => {
|
609
604
|
let local = scope.locals[name];
|
610
605
|
|
611
|
-
if (
|
606
|
+
if (name in builtinVars) {
|
612
607
|
let wasm = builtinVars[name];
|
613
608
|
if (wasm.usesImports) scope.usesImports = true;
|
614
609
|
|
@@ -616,9 +611,9 @@ const lookup = (scope, name, failEarly = false) => {
|
|
616
611
|
return wasm.slice();
|
617
612
|
}
|
618
613
|
|
619
|
-
if (!
|
614
|
+
if (!(name in funcIndex) && name in builtinFuncs) {
|
620
615
|
includeBuiltin(scope, name);
|
621
|
-
} else if (
|
616
|
+
} else if (name in internalConstrs) {
|
622
617
|
// todo: return an actual something
|
623
618
|
return [ number(1) ];
|
624
619
|
}
|
@@ -662,16 +657,16 @@ const lookup = (scope, name, failEarly = false) => {
|
|
662
657
|
}
|
663
658
|
|
664
659
|
// no local var with name
|
665
|
-
if (
|
666
|
-
if (
|
667
|
-
if (
|
660
|
+
if (name in globals) return [ [ Opcodes.global_get, globals[name].idx ] ];
|
661
|
+
if (name in funcIndex) return funcRef(funcByName(name));
|
662
|
+
if (name in importedFuncs) return [ number(importedFuncs[name] - importedFuncs.length) ];
|
668
663
|
|
669
664
|
if (name.startsWith('__')) {
|
670
665
|
// return undefined if unknown key in already known var
|
671
666
|
let parent = name.slice(2).split('_').slice(0, -1).join('_');
|
672
667
|
if (parent.includes('_')) parent = '__' + parent;
|
673
668
|
|
674
|
-
if (
|
669
|
+
if ((name + '$get') in builtinFuncs) {
|
675
670
|
// hack: force error as accessors should only be used with objects anyway
|
676
671
|
return internalThrow(scope, 'TypeError', 'Accessor called without object');
|
677
672
|
}
|
@@ -905,8 +900,6 @@ const performLogicOp = (scope, op, left, right, leftType, rightType) => {
|
|
905
900
|
'??': nullish
|
906
901
|
};
|
907
902
|
|
908
|
-
if (!checks[op]) return todo(scope, `logic operator ${op} not implemented yet`, true);
|
909
|
-
|
910
903
|
// generic structure for {a} OP {b}
|
911
904
|
// _ = {a}; if (OP_CHECK) {b} else _
|
912
905
|
|
@@ -1286,7 +1279,6 @@ const performOp = (scope, op, left, right, leftType, rightType) => {
|
|
1286
1279
|
|
1287
1280
|
// some complex ops are implemented in funcs
|
1288
1281
|
if (typeof ops === 'function') return finalize(asmFuncToAsm(scope, ops, { left, right }));
|
1289
|
-
if (!ops) return todo(scope, `operator ${op} not implemented yet`, true);
|
1290
1282
|
if (!Array.isArray(ops)) ops = [ ops ];
|
1291
1283
|
ops = [ ops ];
|
1292
1284
|
|
@@ -1474,7 +1466,7 @@ const asmFuncToAsm = (scope, func, extra) => func(scope, {
|
|
1474
1466
|
},
|
1475
1467
|
glbl: (opcode, name, type) => {
|
1476
1468
|
const globalName = '#porf#' + name; // avoid potential name clashing with user js
|
1477
|
-
if (!
|
1469
|
+
if (!(globalName in globals)) {
|
1478
1470
|
const idx = globals['#ind']++;
|
1479
1471
|
globals[globalName] = { idx, type };
|
1480
1472
|
|
@@ -1509,7 +1501,7 @@ const asmFuncToAsm = (scope, func, extra) => func(scope, {
|
|
1509
1501
|
return out;
|
1510
1502
|
},
|
1511
1503
|
loc: (name, type) => {
|
1512
|
-
if (!
|
1504
|
+
if (!(name in scope.locals)) {
|
1513
1505
|
const idx = scope.localInd++;
|
1514
1506
|
scope.locals[name] = { idx, type };
|
1515
1507
|
}
|
@@ -1551,7 +1543,7 @@ const asmFunc = (name, func) => {
|
|
1551
1543
|
if (existing) return existing;
|
1552
1544
|
|
1553
1545
|
const allLocals = params.concat(localTypes);
|
1554
|
-
const locals =
|
1546
|
+
const locals = Object.create(null);
|
1555
1547
|
for (let i = 0; i < allLocals.length; i++) {
|
1556
1548
|
locals[localNames[i] ?? `l${i}`] = { idx: i, type: allLocals[i] };
|
1557
1549
|
}
|
@@ -1646,14 +1638,14 @@ const getType = (scope, name, failEarly = false) => {
|
|
1646
1638
|
[ null, () => hoistLookupType(scope, name) ]
|
1647
1639
|
];
|
1648
1640
|
|
1649
|
-
if (
|
1641
|
+
if (name in builtinVars) return [ number(builtinVars[name].type ?? TYPES.number, Valtype.i32) ];
|
1650
1642
|
|
1651
1643
|
let metadata, typeLocal, global = null;
|
1652
|
-
if (
|
1644
|
+
if (name in scope.locals) {
|
1653
1645
|
metadata = scope.locals[name].metadata;
|
1654
1646
|
typeLocal = scope.locals[name + '#type'];
|
1655
1647
|
global = false;
|
1656
|
-
} else if (
|
1648
|
+
} else if (name in globals) {
|
1657
1649
|
metadata = globals[name].metadata;
|
1658
1650
|
typeLocal = globals[name + '#type'];
|
1659
1651
|
global = true;
|
@@ -1687,10 +1679,10 @@ const setType = (scope, name, type, noInfer = false) => {
|
|
1687
1679
|
const out = typeof type === 'number' ? [ number(type, Valtype.i32) ] : type;
|
1688
1680
|
|
1689
1681
|
let metadata, typeLocal, global = false;
|
1690
|
-
if (
|
1682
|
+
if (name in scope.locals) {
|
1691
1683
|
metadata = scope.locals[name].metadata;
|
1692
1684
|
typeLocal = scope.locals[name + '#type'];
|
1693
|
-
} else if (
|
1685
|
+
} else if (name in globals) {
|
1694
1686
|
metadata = globals[name].metadata;
|
1695
1687
|
typeLocal = globals[name + '#type'];
|
1696
1688
|
global = true;
|
@@ -1797,8 +1789,8 @@ const getNodeType = (scope, node) => {
|
|
1797
1789
|
if (func.returnType != null) return func.returnType;
|
1798
1790
|
}
|
1799
1791
|
|
1800
|
-
if (
|
1801
|
-
if (
|
1792
|
+
if (name in builtinFuncs && builtinFuncs[name].returnType != null) return builtinFuncs[name].returnType;
|
1793
|
+
if (name in internalConstrs && internalConstrs[name].type != null) return internalConstrs[name].type;
|
1802
1794
|
|
1803
1795
|
if (name.startsWith('__Porffor_wasm_')) {
|
1804
1796
|
// todo: return undefined for non-returning ops
|
@@ -1950,6 +1942,13 @@ const getNodeType = (scope, node) => {
|
|
1950
1942
|
return getNodeType(scope, node.body);
|
1951
1943
|
}
|
1952
1944
|
|
1945
|
+
if (node.type === 'PrivateIdentifier') {
|
1946
|
+
return getNodeType(scope, {
|
1947
|
+
type: 'Literal',
|
1948
|
+
value: privateIDName(node.name)
|
1949
|
+
});
|
1950
|
+
}
|
1951
|
+
|
1953
1952
|
if (node.type.endsWith('Statement') || node.type.endsWith('Declaration')) {
|
1954
1953
|
return TYPES.undefined;
|
1955
1954
|
}
|
@@ -2021,8 +2020,6 @@ const generateLiteral = (scope, decl, global, name) => {
|
|
2021
2020
|
]
|
2022
2021
|
});
|
2023
2022
|
}
|
2024
|
-
|
2025
|
-
return todo(scope, `cannot generate literal of type ${typeof decl.value}`, true);
|
2026
2023
|
};
|
2027
2024
|
|
2028
2025
|
const generateExp = (scope, decl) => {
|
@@ -2171,7 +2168,7 @@ const createThisArg = (scope, decl) => {
|
|
2171
2168
|
const name = decl.callee?.name;
|
2172
2169
|
if (decl._new) {
|
2173
2170
|
// if precompiling or builtin func, just make it null as unused
|
2174
|
-
if (!decl._forceCreateThis && (globalThis.precompile ||
|
2171
|
+
if (!decl._forceCreateThis && (globalThis.precompile || name in builtinFuncs)) return [
|
2175
2172
|
number(NULL),
|
2176
2173
|
number(TYPES.object, Valtype.i32)
|
2177
2174
|
];
|
@@ -2338,7 +2335,7 @@ const generateCall = (scope, decl, _global, _name, unusedValue = false) => {
|
|
2338
2335
|
target.name = spl.slice(0, -1).join('_');
|
2339
2336
|
|
2340
2337
|
if (builtinFuncs['__' + target.name + '_' + protoName]) protoName = null;
|
2341
|
-
else if (lookupName(scope, target.name)[0] == null && !
|
2338
|
+
else if (lookupName(scope, target.name)[0] == null && !(target.name in builtinFuncs)) {
|
2342
2339
|
if (lookupName(scope, '__' + target.name)[0] != null || builtinFuncs['__' + target.name]) target.name = '__' + target.name;
|
2343
2340
|
else protoName = null;
|
2344
2341
|
}
|
@@ -2478,18 +2475,18 @@ const generateCall = (scope, decl, _global, _name, unusedValue = false) => {
|
|
2478
2475
|
let idx;
|
2479
2476
|
if (decl._funcIdx) {
|
2480
2477
|
idx = decl._funcIdx;
|
2481
|
-
} else if (
|
2478
|
+
} else if (name in internalConstrs && !decl._noInternalConstr) {
|
2482
2479
|
if (decl._new && internalConstrs[name].notConstr) return internalThrow(scope, 'TypeError', `${unhackName(name)} is not a constructor`, true);
|
2483
2480
|
return internalConstrs[name].generate(scope, decl, _global, _name);
|
2484
|
-
} else if (
|
2481
|
+
} else if (name in funcIndex) {
|
2485
2482
|
idx = funcIndex[name];
|
2486
2483
|
} else if (scope.name === name) {
|
2487
2484
|
// fallback for own func but with a different var/id name
|
2488
2485
|
idx = scope.index;
|
2489
|
-
} else if (
|
2486
|
+
} else if (name in importedFuncs) {
|
2490
2487
|
idx = importedFuncs[name];
|
2491
2488
|
scope.usesImports = true;
|
2492
|
-
} else if (
|
2489
|
+
} else if (name in builtinFuncs) {
|
2493
2490
|
if (decl._new && !builtinFuncs[name].constr) return internalThrow(scope, 'TypeError', `${unhackName(name)} is not a constructor`, true);
|
2494
2491
|
|
2495
2492
|
includeBuiltin(scope, name);
|
@@ -3136,7 +3133,7 @@ const allocVar = (scope, name, global = false, type = true, redecl = false, i32
|
|
3136
3133
|
const target = global ? globals : scope.locals;
|
3137
3134
|
|
3138
3135
|
// already declared
|
3139
|
-
if (
|
3136
|
+
if (name in target) {
|
3140
3137
|
if (redecl) {
|
3141
3138
|
// force change old local name(s)
|
3142
3139
|
target['#redecl_' + name + uniqId()] = target[name];
|
@@ -3332,7 +3329,7 @@ const generateVarDstr = (scope, kind, pattern, init, defaultValue, global) => {
|
|
3332
3329
|
const [ _func, out ] = generateFunc(scope, init, true);
|
3333
3330
|
|
3334
3331
|
const funcName = init.id?.name;
|
3335
|
-
if (name !== funcName &&
|
3332
|
+
if (name !== funcName && funcName in funcIndex) {
|
3336
3333
|
funcIndex[name] = funcIndex[funcName];
|
3337
3334
|
delete funcIndex[funcName];
|
3338
3335
|
}
|
@@ -3347,7 +3344,7 @@ const generateVarDstr = (scope, kind, pattern, init, defaultValue, global) => {
|
|
3347
3344
|
}
|
3348
3345
|
|
3349
3346
|
let out = [];
|
3350
|
-
if (topLevel &&
|
3347
|
+
if (topLevel && name in builtinVars) {
|
3351
3348
|
// cannot redeclare
|
3352
3349
|
if (kind !== 'var') return internalThrow(scope, 'SyntaxError', `Identifier '${unhackName(name)}' has already been declared`);
|
3353
3350
|
|
@@ -3395,7 +3392,7 @@ const generateVarDstr = (scope, kind, pattern, init, defaultValue, global) => {
|
|
3395
3392
|
}
|
3396
3393
|
|
3397
3394
|
if (globalThis.precompile && global) {
|
3398
|
-
scope.globalInits ??=
|
3395
|
+
scope.globalInits ??= Object.create(null);
|
3399
3396
|
scope.globalInits[name] = newOut;
|
3400
3397
|
}
|
3401
3398
|
} else {
|
@@ -3525,8 +3522,6 @@ const generateVarDstr = (scope, kind, pattern, init, defaultValue, global) => {
|
|
3525
3522
|
]
|
3526
3523
|
}, undefined, global)
|
3527
3524
|
);
|
3528
|
-
} else {
|
3529
|
-
return todo(scope, `${prop.type} is not supported in object patterns`);
|
3530
3525
|
}
|
3531
3526
|
}
|
3532
3527
|
|
@@ -3567,8 +3562,6 @@ const generateVarDstr = (scope, kind, pattern, init, defaultValue, global) => {
|
|
3567
3562
|
}),
|
3568
3563
|
[ Opcodes.drop ]
|
3569
3564
|
];
|
3570
|
-
|
3571
|
-
return todo(scope, `variable declarators of type ${pattern.type} are not supported yet`);
|
3572
3565
|
}
|
3573
3566
|
|
3574
3567
|
const generateVar = (scope, decl) => {
|
@@ -4214,7 +4207,7 @@ const generateAssign = (scope, decl, _global, _name, valueUnused = false) => {
|
|
4214
4207
|
];
|
4215
4208
|
}
|
4216
4209
|
|
4217
|
-
if (
|
4210
|
+
if (name in builtinVars) {
|
4218
4211
|
if (scope.strict) return internalThrow(scope, 'TypeError', `Cannot assign to non-writable global ${name}`, true);
|
4219
4212
|
|
4220
4213
|
// just return rhs (eg `NaN = 2`)
|
@@ -4437,8 +4430,6 @@ const generateUnary = (scope, decl) => {
|
|
4437
4430
|
return out;
|
4438
4431
|
}
|
4439
4432
|
}
|
4440
|
-
|
4441
|
-
return todo(scope, `unary operator ${decl.operator} not implemented yet`, true);
|
4442
4433
|
};
|
4443
4434
|
|
4444
4435
|
const generateUpdate = (scope, decl, _global, _name, valueUnused = false) => {
|
@@ -5564,7 +5555,8 @@ const generateMeta = (scope, decl) => {
|
|
5564
5555
|
return [ number(UNDEFINED) ];
|
5565
5556
|
}
|
5566
5557
|
|
5567
|
-
|
5558
|
+
// todo: import.meta
|
5559
|
+
return internalThrow(scope, 'Error', `porffor: meta property ${decl.meta.name}.${decl.property.name} is not supported yet`, true);
|
5568
5560
|
};
|
5569
5561
|
|
5570
5562
|
const compileBytes = (val, itemType) => {
|
@@ -5845,7 +5837,7 @@ const wrapBC = (bc, { prelude = [], postlude = [] } = {}) => {
|
|
5845
5837
|
|
5846
5838
|
const countParams = (func, name = undefined) => {
|
5847
5839
|
if (!func) {
|
5848
|
-
if (
|
5840
|
+
if (name in importedFuncs) {
|
5849
5841
|
// reverse lookup then normal lookup
|
5850
5842
|
func = importedFuncs[importedFuncs[name]];
|
5851
5843
|
if (func) return func.params?.length ?? func.params;
|
@@ -6577,6 +6569,7 @@ const generateTemplate = (scope, decl) => {
|
|
6577
6569
|
|
6578
6570
|
const generateTaggedTemplate = (scope, decl, global = false, name = undefined, valueUnused = false) => {
|
6579
6571
|
const intrinsics = {
|
6572
|
+
__proto__: null,
|
6580
6573
|
__Porffor_wasm: str => {
|
6581
6574
|
let out = [];
|
6582
6575
|
|
@@ -6603,12 +6596,12 @@ const generateTaggedTemplate = (scope, decl, global = false, name = undefined, v
|
|
6603
6596
|
const immediates = asm.slice(1).map(x => {
|
6604
6597
|
const n = parseFloat(x);
|
6605
6598
|
if (Number.isNaN(n) && x !== 'NaN') {
|
6606
|
-
if (
|
6599
|
+
if (x in builtinFuncs) {
|
6607
6600
|
if (funcIndex[x] == null) includeBuiltin(scope, x);
|
6608
6601
|
return funcIndex[x];
|
6609
6602
|
}
|
6610
6603
|
|
6611
|
-
if (
|
6604
|
+
if (x in importedFuncs) {
|
6612
6605
|
scope.usesImports = true;
|
6613
6606
|
return importedFuncs[x];
|
6614
6607
|
}
|
@@ -6648,7 +6641,7 @@ const generateTaggedTemplate = (scope, decl, global = false, name = undefined, v
|
|
6648
6641
|
};
|
6649
6642
|
|
6650
6643
|
const { quasis, expressions } = decl.quasi;
|
6651
|
-
if (
|
6644
|
+
if (decl.tag.name in intrinsics) {
|
6652
6645
|
let str = quasis[0].value.raw;
|
6653
6646
|
|
6654
6647
|
for (let i = 0; i < expressions.length; i++) {
|
@@ -6732,7 +6725,7 @@ const objectHack = node => {
|
|
6732
6725
|
if (objectName !== 'Object_prototype' && (node.property.name === 'propertyIsEnumerable' || node.property.name === 'hasOwnProperty' || node.property.name === 'isPrototypeOf')) return abortOut;
|
6733
6726
|
|
6734
6727
|
const name = '__' + objectName + '_' + node.property.name;
|
6735
|
-
if ((!hasFuncWithName(name) && !
|
6728
|
+
if ((!hasFuncWithName(name) && !(name in builtinVars) && !hasFuncWithName(name + '$get')) && (hasFuncWithName(objectName) || objectName in builtinVars || hasFuncWithName('__' + objectName) || ('__' + objectName) in builtinVars)) return abortOut;
|
6736
6729
|
|
6737
6730
|
if (Prefs.codeLog) log('codegen', `object hack! ${node.object.name}.${node.property.name} -> ${name}`);
|
6738
6731
|
|
@@ -6795,7 +6788,7 @@ const generateFunc = (scope, decl, forceNoExpr = false) => {
|
|
6795
6788
|
const arrow = decl.type === 'ArrowFunctionExpression' || decl.type === 'Program';
|
6796
6789
|
const func = {
|
6797
6790
|
start: decl.start,
|
6798
|
-
locals:
|
6791
|
+
locals: Object.create(null),
|
6799
6792
|
localInd: 0,
|
6800
6793
|
returns: [ valtypeBinary, Valtype.i32 ], // value, type
|
6801
6794
|
name,
|
@@ -7005,7 +6998,7 @@ const generateFunc = (scope, decl, forceNoExpr = false) => {
|
|
7005
6998
|
wasm.push(...getNodeType(func, getLastNode(decl.body.body)));
|
7006
6999
|
|
7007
7000
|
// inject promise job runner func at the end of main if promises are made
|
7008
|
-
if (
|
7001
|
+
if (('Promise' in funcIndex) || ('__Promise_resolve' in funcIndex) || ('__Promise_reject' in funcIndex)) {
|
7009
7002
|
wasm.push(
|
7010
7003
|
[ Opcodes.call, includeBuiltin(func, '__Porffor_promise_runJobs').index ]
|
7011
7004
|
);
|
@@ -7180,6 +7173,7 @@ const generateBlock = (scope, decl) => {
|
|
7180
7173
|
};
|
7181
7174
|
|
7182
7175
|
const internalConstrs = {
|
7176
|
+
__proto__: null,
|
7183
7177
|
__Array_of: {
|
7184
7178
|
// this is not a constructor but best fits internal structure here
|
7185
7179
|
generate: (scope, decl, global, name) => {
|
@@ -7369,7 +7363,8 @@ const internalConstrs = {
|
|
7369
7363
|
|
7370
7364
|
let globals, tags, exceptions, funcs, indirectFuncs, funcIndex, currentFuncIndex, depth, pages, data, typeswitchDepth, usedTypes, coctc, globalInfer, builtinFuncs, builtinVars, lastValtype;
|
7371
7365
|
export default program => {
|
7372
|
-
globals =
|
7366
|
+
globals = Object.create(null);
|
7367
|
+
globals['#ind'] = 0;
|
7373
7368
|
tags = [];
|
7374
7369
|
exceptions = [];
|
7375
7370
|
funcs = []; indirectFuncs = [];
|
@@ -7377,7 +7372,7 @@ export default program => {
|
|
7377
7372
|
return indirectFuncs._bytesPerFuncLut ??=
|
7378
7373
|
Math.min(Math.floor((pageSize * 2) / indirectFuncs.length), indirectFuncs.reduce((acc, x) => x.name.length > acc ? x.name.length : acc, 0) + 8);
|
7379
7374
|
};
|
7380
|
-
funcIndex =
|
7375
|
+
funcIndex = Object.create(null);
|
7381
7376
|
depth = [];
|
7382
7377
|
pages = new Map();
|
7383
7378
|
data = [];
|
@@ -7404,8 +7399,8 @@ export default program => {
|
|
7404
7399
|
// keep builtins between compiles as much as possible
|
7405
7400
|
if (lastValtype !== valtypeBinary) {
|
7406
7401
|
lastValtype = valtypeBinary;
|
7407
|
-
builtinFuncs =
|
7408
|
-
builtinVars =
|
7402
|
+
builtinFuncs = BuiltinFuncs();
|
7403
|
+
builtinVars = BuiltinVars({ builtinFuncs });
|
7409
7404
|
|
7410
7405
|
const getObjectName = x => x.startsWith('__') && x.slice(2, x.indexOf('_', 2));
|
7411
7406
|
objectHackers = ['assert', 'compareArray', 'Test262Error', ...new Set(Object.keys(builtinFuncs).map(getObjectName).concat(Object.keys(builtinVars).map(getObjectName)).filter(x => x))];
|
package/compiler/precompile.js
CHANGED
@@ -57,7 +57,7 @@ const compile = async (file, _funcs) => {
|
|
57
57
|
first = source.slice(0, source.indexOf('\n'));
|
58
58
|
}
|
59
59
|
|
60
|
-
let args = ['--module', '--
|
60
|
+
let args = ['--module', '--truthy=no_nan_negative', '--no-rm-unused-types', '--fast-length', '--parse-types', '--opt-types', '--no-passive-data', '--active-data', '--no-treeshake-wasm-imports', '--no-coctc'];
|
61
61
|
if (first.startsWith('// @porf')) {
|
62
62
|
args = first.slice('// @porf '.length).split(' ').concat(args);
|
63
63
|
}
|
@@ -237,7 +237,7 @@ const precompile = async () => {
|
|
237
237
|
return `// autogenerated by compiler/precompile.js
|
238
238
|
import { number } from './encoding.js';
|
239
239
|
|
240
|
-
export const BuiltinFuncs =
|
240
|
+
export const BuiltinFuncs = x => {
|
241
241
|
${funcs.map(x => {
|
242
242
|
const rewriteWasm = wasm => {
|
243
243
|
const str = JSON.stringify(wasm.filter(x => x.length && (x[0] != null || typeof x[1] === 'string')), (k, v) => {
|
@@ -278,7 +278,7 @@ ${funcs.map(x => {
|
|
278
278
|
const name = x.name.includes('#') ? `['${x.name}']` : `.${x.name}`;
|
279
279
|
|
280
280
|
const returnTypes = [...(x.returnTypes ?? [])].filter(x => ![ TYPES.undefined, TYPES.number, TYPES.boolean, TYPES.function ].includes(x));
|
281
|
-
return `
|
281
|
+
return `x${name}={
|
282
282
|
wasm:${rewriteWasm(x.wasm)},
|
283
283
|
params:${JSON.stringify(x.params)},typedParams:1,returns:${JSON.stringify(x.returns)},${x.returnType != null ? `returnType:${JSON.stringify(x.returnType)},` : ''}${returnTypes.length > 0 ? `returnTypes:${JSON.stringify(returnTypes)},` : ''}jsLength:${x.jsLength},
|
284
284
|
locals:${JSON.stringify(locals.slice(x.params.length).map(x => x[1].type))},localNames:${JSON.stringify(locals.map(x => x[0]))},
|
package/foo.js
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
let count = 0;
|
2
|
+
|
3
|
+
class Class {
|
4
|
+
#method() {
|
5
|
+
count += 1;
|
6
|
+
}
|
7
|
+
|
8
|
+
static isNameIn(value) {
|
9
|
+
return #method in value;
|
10
|
+
}
|
11
|
+
}
|
12
|
+
|
13
|
+
console.log(Class.isNameIn({}), false);
|
14
|
+
console.log(Class.isNameIn(new Class()), true);
|
15
|
+
console.log(count, 0);
|
package/package.json
CHANGED