[destructuring] Cleanup InstructionValue type definition
Joe Savona committed
Feb 17, 2023 at 15:30 UTC
256071460d8ca646e820596e5fc8ac8ccab6b43b
1 file changed
+80
-24
compiler/forget/src/HIR/HIR.ts
+80
-24
@@ -373,17 +373,12 @@ export enum InstructionKind {
373
Reassign = "Reassign",
374
}
375
376
-/**
377
- * A value that may be assigned to a place. Similar to instructions, values
378
- * are not recursive: complex values such as objects or arrays are always
379
- * defined by Instructions to construct a temporary Place, and then referring
380
- * to that Place.
381
- *
382
- * Values are therefore only a Place or a primitive value.
383
- */
384
-export type InstructionValue =
385
- | (InstructionData & { loc: SourceLocation })
386
- | Place;
376
+function _staticInvariantInstructionValueHasLocation(
377
+ value: InstructionValue
378
+): SourceLocation {
379
+ // If this fails, it is because a variant of InstructionValue is missing a .loc - add it!
380
+ return value.loc;
381
+}
382
383
export type Phi = {
384
kind: "Phi";
@@ -392,68 +387,127 @@ export type Phi = {
387
type: Type;
388
};
389
395
-export type InstructionData =
396
- | { kind: "Primitive"; value: number | boolean | string | null | undefined }
397
- | { kind: "JSXText"; value: string }
390
+/**
391
+ * The value of a given instruction. Note that values are not recursive: complex
392
+ * values such as objects or arrays are always defined by instructions to define
393
+ * their operands (saving to a temporary), then passing those temporaries as
394
+ * the operands to the final instruction (ObjectExpression, ArrayExpression, etc).
395
+ *
396
+ * Operands are therefore always a Place.
397
+ */
398
+export type InstructionValue =
399
+ | Place
400
+ | {
401
+ kind: "Primitive";
402
+ value: number | boolean | string | null | undefined;
403
+ loc: SourceLocation;
404
+ }
405
+ | { kind: "JSXText"; value: string; loc: SourceLocation }
406
| {
407
kind: "BinaryExpression";
408
operator: t.BinaryExpression["operator"];
409
left: Place;
410
right: Place;
411
+ loc: SourceLocation;
412
+ }
413
+ | {
414
+ kind: "NewExpression";
415
+ callee: Place;
416
+ args: Array<Place>;
417
+ loc: SourceLocation;
418
}
404
- | { kind: "NewExpression"; callee: Place; args: Array<Place> }
419
| {
420
kind: "CallExpression";
421
callee: Place;
422
args: Array<Place>;
423
+ loc: SourceLocation;
424
}
425
| {
426
kind: "PropertyCall";
427
receiver: Place;
428
property: string;
429
args: Array<Place>;
430
+ loc: SourceLocation;
431
}
432
| {
433
kind: "ComputedCall";
434
receiver: Place;
435
property: Place;
436
args: Array<Place>;
437
+ loc: SourceLocation;
438
+ }
439
+ | {
440
+ kind: "UnaryExpression";
441
+ operator: string;
442
+ value: Place;
443
+ loc: SourceLocation;
444
+ }
445
+ | {
446
+ kind: "TypeCastExpression";
447
+ value: Place;
448
+ type: t.TypeAnnotation;
449
+ loc: SourceLocation;
450
}
422
- | { kind: "UnaryExpression"; operator: string; value: Place }
423
- | { kind: "TypeCastExpression"; value: Place; type: t.TypeAnnotation }
451
| {
452
kind: "JsxExpression";
453
tag: Place;
454
props: Array<JsxAttribute>;
455
children: Array<Place> | null; // null === no children
456
+ loc: SourceLocation;
457
}
458
| {
459
kind: "ObjectExpression";
460
properties: Map<string, Place> | null; // null === empty object
461
+ loc: SourceLocation;
462
}
434
- | { kind: "ArrayExpression"; elements: Array<Place> }
435
- | { kind: "JsxFragment"; children: Array<Place> }
463
+ | { kind: "ArrayExpression"; elements: Array<Place>; loc: SourceLocation }
464
+ | { kind: "JsxFragment"; children: Array<Place>; loc: SourceLocation }
465
466
// store `object.property = value`
438
- | { kind: "PropertyStore"; object: Place; property: string; value: Place }
467
+ | {
468
+ kind: "PropertyStore";
469
+ object: Place;
470
+ property: string;
471
+ value: Place;
472
+ loc: SourceLocation;
473
+ }
474
// load `object.property`
440
- | { kind: "PropertyLoad"; object: Place; property: string; optional: boolean }
475
+ | {
476
+ kind: "PropertyLoad";
477
+ object: Place;
478
+ property: string;
479
+ optional: boolean;
480
+ loc: SourceLocation;
481
+ }
482
483
// store `object[index] = value` - like PropertyStore but with a dynamic property
443
- | { kind: "ComputedStore"; object: Place; property: Place; value: Place }
484
+ | {
485
+ kind: "ComputedStore";
486
+ object: Place;
487
+ property: Place;
488
+ value: Place;
489
+ loc: SourceLocation;
490
+ }
491
// load `object[index]` - like PropertyLoad but with a dynamic property
445
- | { kind: "ComputedLoad"; object: Place; property: Place }
446
- | { kind: "LoadGlobal"; name: string }
492
+ | {
493
+ kind: "ComputedLoad";
494
+ object: Place;
495
+ property: Place;
496
+ loc: SourceLocation;
497
+ }
498
+ | { kind: "LoadGlobal"; name: string; loc: SourceLocation }
499
| FunctionExpression
500
| {
501
kind: "TaggedTemplateExpression";
502
tag: Place;
503
value: { raw: string; cooked?: string };
504
+ loc: SourceLocation;
505
}
506
| {
507
kind: "TemplateLiteral";
508
subexprs: Array<Place>;
509
quasis: Array<{ raw: string; cooked?: string }>;
510
+ loc: SourceLocation;
511
}
512
/**
513
* Catch-all for statements such as type imports, nested class declarations, etc
@@ -463,6 +517,7 @@ export type InstructionData =
517
| {
518
kind: "UnsupportedNode";
519
node: t.Node;
520
+ loc: SourceLocation;
521
};
522
523
export type JsxAttribute =
@@ -475,6 +530,7 @@ export type FunctionExpression = {
530
dependencies: Array<Place>;
531
loweredFunc: HIRFunction;
532
expr: t.ArrowFunctionExpression | t.FunctionExpression;
533
+ loc: SourceLocation;
534
};
535
/**
536
* A place where data may be read from / written to: