porffor 0.17.0-c2dd8f88f → 0.17.0-cbb73d209
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/codegen.js +136 -5
- package/compiler/opt.js +3 -0
- package/package.json +1 -1
package/compiler/codegen.js
CHANGED
@@ -2083,12 +2083,24 @@ const generateCall = (scope, decl, _global, _name, unusedValue = false) => {
|
|
2083
2083
|
} else if (decl._new)
|
2084
2084
|
return internalThrow(scope, 'TypeError', `${unhackName(name)} is not a constructor`, true);
|
2085
2085
|
|
2086
|
-
let args = decl.arguments;
|
2087
|
-
if (func && args.length < paramCount) {
|
2086
|
+
let args = [...decl.arguments];
|
2087
|
+
if (func && !func.hasRestArgument && args.length < paramCount) {
|
2088
2088
|
// too little args, push undefineds
|
2089
2089
|
args = args.concat(new Array(paramCount - args.length).fill(DEFAULT_VALUE));
|
2090
2090
|
}
|
2091
2091
|
|
2092
|
+
if (func && func.hasRestArgument) {
|
2093
|
+
if (args.length < paramCount) {
|
2094
|
+
args = args.concat(new Array(paramCount - 1 - args.length).fill(DEFAULT_VALUE));
|
2095
|
+
}
|
2096
|
+
const restArgs = args.slice(paramCount - 1);
|
2097
|
+
args = args.slice(0, paramCount - 1);
|
2098
|
+
args.push({
|
2099
|
+
type: 'ArrayExpression',
|
2100
|
+
elements: restArgs
|
2101
|
+
})
|
2102
|
+
}
|
2103
|
+
|
2092
2104
|
if (func && args.length > paramCount) {
|
2093
2105
|
// too many args, slice extras off
|
2094
2106
|
args = args.slice(0, paramCount);
|
@@ -2403,9 +2415,120 @@ const generateVar = (scope, decl) => {
|
|
2403
2415
|
const global = topLevel || decl._bare;
|
2404
2416
|
|
2405
2417
|
for (const x of decl.declarations) {
|
2406
|
-
|
2418
|
+
if (x.id.type === 'ArrayPattern') {
|
2419
|
+
const decls = [];
|
2420
|
+
const tmpName = '#destructure' + randId();
|
2421
|
+
|
2422
|
+
let i = 0;
|
2423
|
+
const elements = [...x.id.elements];
|
2424
|
+
for (const e of elements) {
|
2425
|
+
switch (e?.type) {
|
2426
|
+
case 'RestElement': { // let [ ...foo ] = []
|
2427
|
+
if (e.argument.type === 'ArrayPattern') {
|
2428
|
+
// let [ ...[a, b, c] ] = []
|
2429
|
+
elements.push(...e.argument.elements);
|
2430
|
+
} else {
|
2431
|
+
decls.push({
|
2432
|
+
type: 'VariableDeclarator',
|
2433
|
+
id: { type: 'Identifier', name: e.argument.name },
|
2434
|
+
init: {
|
2435
|
+
type: 'CallExpression',
|
2436
|
+
callee: {
|
2437
|
+
type: 'Identifier',
|
2438
|
+
name: '__Array_prototype_slice'
|
2439
|
+
},
|
2440
|
+
arguments: [
|
2441
|
+
{ type: 'Identifier', name: tmpName },
|
2442
|
+
{ type: 'Literal', value: i },
|
2443
|
+
{
|
2444
|
+
type: 'MemberExpression',
|
2445
|
+
object: { type: 'Identifier', name: tmpName, },
|
2446
|
+
property: { type: 'Identifier', name: 'length', }
|
2447
|
+
}
|
2448
|
+
]
|
2449
|
+
}
|
2450
|
+
});
|
2451
|
+
}
|
2452
|
+
|
2453
|
+
continue; // skip i++
|
2454
|
+
}
|
2455
|
+
|
2456
|
+
case 'Identifier': { // let [ foo ] = []
|
2457
|
+
decls.push({
|
2458
|
+
type: 'VariableDeclarator',
|
2459
|
+
id: e,
|
2460
|
+
init: {
|
2461
|
+
type: 'MemberExpression',
|
2462
|
+
object: { type: 'Identifier', name: tmpName },
|
2463
|
+
property: { type: 'Literal', value: i }
|
2464
|
+
}
|
2465
|
+
});
|
2407
2466
|
|
2408
|
-
|
2467
|
+
break;
|
2468
|
+
}
|
2469
|
+
|
2470
|
+
case 'AssignmentPattern': { // let [ foo = defaultValue ] = []
|
2471
|
+
decls.push({
|
2472
|
+
type: 'VariableDeclarator',
|
2473
|
+
id: e.left,
|
2474
|
+
init: {
|
2475
|
+
type: 'LogicalExpression',
|
2476
|
+
operator: '??',
|
2477
|
+
left: {
|
2478
|
+
type: 'MemberExpression',
|
2479
|
+
object: { type: 'Identifier', name: tmpName },
|
2480
|
+
property: { type: 'Literal', value: i }
|
2481
|
+
},
|
2482
|
+
right: e.right
|
2483
|
+
}
|
2484
|
+
});
|
2485
|
+
|
2486
|
+
break;
|
2487
|
+
}
|
2488
|
+
|
2489
|
+
case 'ArrayPattern': { // let [ [ foo, bar ] ] = []
|
2490
|
+
decls.push({
|
2491
|
+
type: 'VariableDeclarator',
|
2492
|
+
id: e,
|
2493
|
+
init: {
|
2494
|
+
type: 'MemberExpression',
|
2495
|
+
object: { type: 'Identifier', name: tmpName },
|
2496
|
+
property: { type: 'Literal', value: i }
|
2497
|
+
}
|
2498
|
+
});
|
2499
|
+
|
2500
|
+
break;
|
2501
|
+
}
|
2502
|
+
|
2503
|
+
case 'ObjectPattern':
|
2504
|
+
return todo(scope, 'object destructuring is not supported yet')
|
2505
|
+
}
|
2506
|
+
|
2507
|
+
i++;
|
2508
|
+
}
|
2509
|
+
|
2510
|
+
out = out.concat([
|
2511
|
+
...generateVar(scope, {
|
2512
|
+
type: 'VariableDeclaration',
|
2513
|
+
declarations: [{
|
2514
|
+
type: 'VariableDeclarator',
|
2515
|
+
id: { type: 'Identifier', name: tmpName },
|
2516
|
+
init: x.init
|
2517
|
+
}],
|
2518
|
+
kind: decl.kind
|
2519
|
+
}),
|
2520
|
+
...generateVar(scope, {
|
2521
|
+
type: 'VariableDeclaration',
|
2522
|
+
declarations: decls,
|
2523
|
+
kind: decl.kind
|
2524
|
+
})
|
2525
|
+
]);
|
2526
|
+
|
2527
|
+
continue;
|
2528
|
+
}
|
2529
|
+
|
2530
|
+
const name = mapName(x.id.name);
|
2531
|
+
if (!name) return todo(scope, 'object destructuring is not supported yet')
|
2409
2532
|
|
2410
2533
|
if (x.init && isFuncType(x.init.type)) {
|
2411
2534
|
// hack for let a = function () { ... }
|
@@ -2440,7 +2563,9 @@ const generateVar = (scope, decl) => {
|
|
2440
2563
|
// hack to set local as pointer before
|
2441
2564
|
out.push(...number(scope.arrays.get(name)), [ global ? Opcodes.global_set : Opcodes.local_set, idx ]);
|
2442
2565
|
if (generated.at(-1) == Opcodes.i32_from_u) generated.pop();
|
2443
|
-
generated.pop();
|
2566
|
+
// generated.pop();
|
2567
|
+
generated.push([ Opcodes.drop ]);
|
2568
|
+
|
2444
2569
|
out = out.concat(generated);
|
2445
2570
|
} else {
|
2446
2571
|
out = out.concat(generated);
|
@@ -4277,6 +4402,12 @@ const generateFunc = (scope, decl) => {
|
|
4277
4402
|
defaultValues[name] = x.right;
|
4278
4403
|
break;
|
4279
4404
|
}
|
4405
|
+
|
4406
|
+
case 'RestElement': {
|
4407
|
+
name = x.argument.name;
|
4408
|
+
func.hasRestArgument = true;
|
4409
|
+
break;
|
4410
|
+
}
|
4280
4411
|
}
|
4281
4412
|
|
4282
4413
|
// if (name == null) return todo('non-identifier args are not supported');
|
package/compiler/opt.js
CHANGED
@@ -203,6 +203,9 @@ export default (funcs, globals, pages, tags, exceptions) => {
|
|
203
203
|
if (type === 'Array') missing = !pages.hasArray;
|
204
204
|
if (type === 'String') missing = !pages.hasString;
|
205
205
|
if (type === 'ByteString') missing = !pages.hasByteString;
|
206
|
+
if (['Set', 'Uint8Array', 'Int8Array', 'Uint8ClampedArray', 'Uint16Array', 'Int16Array', 'Uint32Array', 'Int32Array', 'Float32Array', 'Float64Array'].includes(type)) {
|
207
|
+
missing = funcs.find(x => x.name === type) == null;
|
208
|
+
}
|
206
209
|
|
207
210
|
if (missing) {
|
208
211
|
let j = i, depth = 0;
|
package/package.json
CHANGED