@rollup/wasm-node 4.31.0-0 → 4.31.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.
@@ -1,7 +1,7 @@
1
1
  /*
2
2
  @license
3
- Rollup.js v4.31.0-0
4
- Tue, 14 Jan 2025 05:57:11 GMT - commit 8c80d5f657f0777d14bd75d446fee3fa4b7639fc
3
+ Rollup.js v4.31.0
4
+ Sun, 19 Jan 2025 12:56:16 GMT - commit 15c264d59e0768b7d283a7bb8ded0519d1b5199e
5
5
 
6
6
  https://github.com/rollup/rollup
7
7
 
@@ -17,7 +17,7 @@ const native_js = require('../native.js');
17
17
  const node_perf_hooks = require('node:perf_hooks');
18
18
  const promises = require('node:fs/promises');
19
19
 
20
- var version = "4.31.0-0";
20
+ var version = "4.31.0";
21
21
 
22
22
  function ensureArray$1(items) {
23
23
  if (Array.isArray(items)) {
@@ -3491,6 +3491,71 @@ function renderSystemExportSequenceBeforeExpression(exportedVariable, expression
3491
3491
  }
3492
3492
  }
3493
3493
 
3494
+ /** @import { Node } from 'estree' */
3495
+
3496
+ /**
3497
+ * @param {Node} node
3498
+ * @param {Node} parent
3499
+ * @returns {boolean}
3500
+ */
3501
+ function is_reference(node, parent) {
3502
+ if (node.type === 'MemberExpression') {
3503
+ return !node.computed && is_reference(node.object, node);
3504
+ }
3505
+
3506
+ if (node.type !== 'Identifier') return false;
3507
+
3508
+ switch (parent?.type) {
3509
+ // disregard `bar` in `foo.bar`
3510
+ case 'MemberExpression':
3511
+ return parent.computed || node === parent.object;
3512
+
3513
+ // disregard the `foo` in `class {foo(){}}` but keep it in `class {[foo](){}}`
3514
+ case 'MethodDefinition':
3515
+ return parent.computed;
3516
+
3517
+ // disregard the `meta` in `import.meta`
3518
+ case 'MetaProperty':
3519
+ return parent.meta === node;
3520
+
3521
+ // disregard the `foo` in `class {foo=bar}` but keep it in `class {[foo]=bar}` and `class {bar=foo}`
3522
+ case 'PropertyDefinition':
3523
+ return parent.computed || node === parent.value;
3524
+
3525
+ // disregard the `bar` in `{ bar: foo }`, but keep it in `{ [bar]: foo }`
3526
+ case 'Property':
3527
+ return parent.computed || node === parent.value;
3528
+
3529
+ // disregard the `bar` in `export { foo as bar }` or
3530
+ // the foo in `import { foo as bar }`
3531
+ case 'ExportSpecifier':
3532
+ case 'ImportSpecifier':
3533
+ return node === parent.local;
3534
+
3535
+ // disregard the `foo` in `foo: while (...) { ... break foo; ... continue foo;}`
3536
+ case 'LabeledStatement':
3537
+ case 'BreakStatement':
3538
+ case 'ContinueStatement':
3539
+ return false;
3540
+
3541
+ default:
3542
+ return true;
3543
+ }
3544
+ }
3545
+
3546
+ const PureFunctionKey = Symbol('PureFunction');
3547
+ const getPureFunctions = ({ treeshake }) => {
3548
+ const pureFunctions = Object.create(null);
3549
+ for (const functionName of treeshake ? treeshake.manualPureFunctions : []) {
3550
+ let currentFunctions = pureFunctions;
3551
+ for (const pathSegment of functionName.split('.')) {
3552
+ currentFunctions = currentFunctions[pathSegment] ||= Object.create(null);
3553
+ }
3554
+ currentFunctions[PureFunctionKey] = true;
3555
+ }
3556
+ return pureFunctions;
3557
+ };
3558
+
3494
3559
  const UnknownKey = Symbol('Unknown Key');
3495
3560
  const UnknownNonAccessorKey = Symbol('Unknown Non-Accessor Key');
3496
3561
  const UnknownInteger = Symbol('Unknown Integer');
@@ -3505,7 +3570,7 @@ const UNKNOWN_PATH = [UnknownKey];
3505
3570
  const UNKNOWN_NON_ACCESSOR_PATH = [UnknownNonAccessorKey];
3506
3571
  const UNKNOWN_INTEGER_PATH = [UnknownInteger];
3507
3572
  const EntitiesKey = Symbol('Entities');
3508
- class EntityPathTracker {
3573
+ class PathTracker {
3509
3574
  constructor() {
3510
3575
  this.entityPaths = Object.create(null, {
3511
3576
  [EntitiesKey]: { value: new Set() }
@@ -3530,14 +3595,14 @@ class EntityPathTracker {
3530
3595
  getEntities(path) {
3531
3596
  let currentPaths = this.entityPaths;
3532
3597
  for (const pathSegment of path) {
3533
- currentPaths = currentPaths[pathSegment] ||= Object.create(null, {
3534
- [EntitiesKey]: { value: new Set() }
3535
- });
3598
+ currentPaths = currentPaths[pathSegment] =
3599
+ currentPaths[pathSegment] ||
3600
+ Object.create(null, { [EntitiesKey]: { value: new Set() } });
3536
3601
  }
3537
3602
  return currentPaths[EntitiesKey];
3538
3603
  }
3539
3604
  }
3540
- const SHARED_RECURSION_TRACKER = new EntityPathTracker();
3605
+ const SHARED_RECURSION_TRACKER = new PathTracker();
3541
3606
  class DiscriminatedPathTracker {
3542
3607
  constructor() {
3543
3608
  this.entityPaths = Object.create(null, {
@@ -3547,9 +3612,9 @@ class DiscriminatedPathTracker {
3547
3612
  trackEntityAtPathAndGetIfTracked(path, discriminator, entity) {
3548
3613
  let currentPaths = this.entityPaths;
3549
3614
  for (const pathSegment of path) {
3550
- currentPaths = currentPaths[pathSegment] ||= Object.create(null, {
3551
- [EntitiesKey]: { value: new Map() }
3552
- });
3615
+ currentPaths = currentPaths[pathSegment] =
3616
+ currentPaths[pathSegment] ||
3617
+ Object.create(null, { [EntitiesKey]: { value: new Map() } });
3553
3618
  }
3554
3619
  const trackedEntities = getOrCreate(currentPaths[EntitiesKey], discriminator, (getNewSet));
3555
3620
  if (trackedEntities.has(entity))
@@ -3558,137 +3623,6 @@ class DiscriminatedPathTracker {
3558
3623
  return false;
3559
3624
  }
3560
3625
  }
3561
- const UNKNOWN_INCLUDED_PATH = Object.freeze({ [UnknownKey]: parseAst_js.EMPTY_OBJECT });
3562
- class IncludedPathTracker {
3563
- constructor() {
3564
- this.includedPaths = null;
3565
- }
3566
- includePathAndGetIfIncluded(path) {
3567
- let included = true;
3568
- let parent = this;
3569
- let parentSegment = 'includedPaths';
3570
- let currentPaths = (this.includedPaths ||=
3571
- ((included = false), Object.create(null)));
3572
- for (const pathSegment of path) {
3573
- // This means from here, all paths are included
3574
- if (currentPaths[UnknownKey]) {
3575
- return true;
3576
- }
3577
- // Including UnknownKey automatically includes all nested paths.
3578
- // From above, we know that UnknownKey is not included yet.
3579
- if (typeof pathSegment === 'symbol') {
3580
- // Hopefully, this saves some memory over just setting
3581
- // currentPaths[UnknownKey] = EMPTY_OBJECT
3582
- parent[parentSegment] = UNKNOWN_INCLUDED_PATH;
3583
- return false;
3584
- }
3585
- parent = currentPaths;
3586
- parentSegment = pathSegment;
3587
- currentPaths = currentPaths[pathSegment] ||= ((included = false), Object.create(null));
3588
- }
3589
- return included;
3590
- }
3591
- includeAllPaths(entity, context, basePath) {
3592
- const { includedPaths } = this;
3593
- if (includedPaths) {
3594
- includeAllPaths(entity, context, basePath, includedPaths);
3595
- }
3596
- }
3597
- }
3598
- function includeAllPaths(entity, context, basePath, currentPaths) {
3599
- if (currentPaths[UnknownKey]) {
3600
- return entity.includePath([...basePath, UnknownKey], context);
3601
- }
3602
- const keys = Object.keys(currentPaths);
3603
- if (keys.length === 0) {
3604
- return entity.includePath(basePath, context);
3605
- }
3606
- for (const key of keys) {
3607
- includeAllPaths(entity, context, [...basePath, key], currentPaths[key]);
3608
- }
3609
- }
3610
-
3611
- /** @import { Node } from 'estree' */
3612
-
3613
- /**
3614
- * @param {Node} node
3615
- * @param {Node} parent
3616
- * @returns {boolean}
3617
- */
3618
- function is_reference(node, parent) {
3619
- if (node.type === 'MemberExpression') {
3620
- return !node.computed && is_reference(node.object, node);
3621
- }
3622
-
3623
- if (node.type !== 'Identifier') return false;
3624
-
3625
- switch (parent?.type) {
3626
- // disregard `bar` in `foo.bar`
3627
- case 'MemberExpression':
3628
- return parent.computed || node === parent.object;
3629
-
3630
- // disregard the `foo` in `class {foo(){}}` but keep it in `class {[foo](){}}`
3631
- case 'MethodDefinition':
3632
- return parent.computed;
3633
-
3634
- // disregard the `meta` in `import.meta`
3635
- case 'MetaProperty':
3636
- return parent.meta === node;
3637
-
3638
- // disregard the `foo` in `class {foo=bar}` but keep it in `class {[foo]=bar}` and `class {bar=foo}`
3639
- case 'PropertyDefinition':
3640
- return parent.computed || node === parent.value;
3641
-
3642
- // disregard the `bar` in `{ bar: foo }`, but keep it in `{ [bar]: foo }`
3643
- case 'Property':
3644
- return parent.computed || node === parent.value;
3645
-
3646
- // disregard the `bar` in `export { foo as bar }` or
3647
- // the foo in `import { foo as bar }`
3648
- case 'ExportSpecifier':
3649
- case 'ImportSpecifier':
3650
- return node === parent.local;
3651
-
3652
- // disregard the `foo` in `foo: while (...) { ... break foo; ... continue foo;}`
3653
- case 'LabeledStatement':
3654
- case 'BreakStatement':
3655
- case 'ContinueStatement':
3656
- return false;
3657
-
3658
- default:
3659
- return true;
3660
- }
3661
- }
3662
-
3663
- function createInclusionContext() {
3664
- return {
3665
- brokenFlow: false,
3666
- hasBreak: false,
3667
- hasContinue: false,
3668
- includedCallArguments: new Set(),
3669
- includedLabels: new Set()
3670
- };
3671
- }
3672
- function createHasEffectsContext() {
3673
- return {
3674
- accessed: new EntityPathTracker(),
3675
- assigned: new EntityPathTracker(),
3676
- brokenFlow: false,
3677
- called: new DiscriminatedPathTracker(),
3678
- hasBreak: false,
3679
- hasContinue: false,
3680
- ignore: {
3681
- breaks: false,
3682
- continues: false,
3683
- labels: new Set(),
3684
- returnYield: false,
3685
- this: false
3686
- },
3687
- includedLabels: new Set(),
3688
- instantiated: new DiscriminatedPathTracker(),
3689
- replacedVariableInits: new Map()
3690
- };
3691
- }
3692
3626
 
3693
3627
  function isFlagSet(flags, flag) {
3694
3628
  return (flags & flag) !== 0;
@@ -3728,25 +3662,12 @@ class ExpressionEntity {
3728
3662
  hasEffectsOnInteractionAtPath(_path, _interaction, _context) {
3729
3663
  return true;
3730
3664
  }
3731
- include(context, _includeChildrenRecursively, _options) {
3732
- if (!this.included)
3733
- this.includeNode(context);
3734
- }
3735
- includeNode(_context) {
3665
+ include(_context, _includeChildrenRecursively, _options) {
3736
3666
  this.included = true;
3737
3667
  }
3738
- includePath(_path, context) {
3739
- if (!this.included)
3740
- this.includeNode(context);
3741
- }
3742
- /* We are both including and including an unknown path here as the former
3743
- * ensures that nested nodes are included while the latter ensures that all
3744
- * paths of the expression are included.
3745
- * */
3746
- includeCallArguments(context, interaction) {
3747
- for (const argument of interaction.args) {
3748
- argument?.includePath(UNKNOWN_PATH, context);
3749
- argument?.include(context, false);
3668
+ includeCallArguments(context, parameters) {
3669
+ for (const argument of parameters) {
3670
+ argument.include(context, false);
3750
3671
  }
3751
3672
  }
3752
3673
  shouldBeIncluded(_context) {
@@ -3785,19 +3706,6 @@ const NODE_INTERACTION_UNKNOWN_CALL = {
3785
3706
  withNew: false
3786
3707
  };
3787
3708
 
3788
- const PureFunctionKey = Symbol('PureFunction');
3789
- const getPureFunctions = ({ treeshake }) => {
3790
- const pureFunctions = Object.create(null);
3791
- for (const functionName of treeshake ? treeshake.manualPureFunctions : []) {
3792
- let currentFunctions = pureFunctions;
3793
- for (const pathSegment of functionName.split('.')) {
3794
- currentFunctions = currentFunctions[pathSegment] ||= Object.create(null);
3795
- }
3796
- currentFunctions[PureFunctionKey] = true;
3797
- }
3798
- return pureFunctions;
3799
- };
3800
-
3801
3709
  class Variable extends ExpressionEntity {
3802
3710
  markReassigned() {
3803
3711
  this.isReassigned = true;
@@ -3874,9 +3782,9 @@ class Variable extends ExpressionEntity {
3874
3782
  * has not been included previously. Once a variable is included, it should
3875
3783
  * take care all its declarations are included.
3876
3784
  */
3877
- includePath(path, context) {
3785
+ include() {
3878
3786
  this.included = true;
3879
- this.renderedLikeHoisted?.includePath(path, context);
3787
+ this.renderedLikeHoisted?.include();
3880
3788
  }
3881
3789
  /**
3882
3790
  * Links the rendered name of this variable to another variable and includes
@@ -3908,8 +3816,8 @@ class ExternalVariable extends Variable {
3908
3816
  hasEffectsOnInteractionAtPath(path, { type }) {
3909
3817
  return type !== INTERACTION_ACCESSED || path.length > (this.isNamespace ? 1 : 0);
3910
3818
  }
3911
- includePath(path, context) {
3912
- super.includePath(path, context);
3819
+ include() {
3820
+ super.include();
3913
3821
  this.module.used = true;
3914
3822
  }
3915
3823
  }
@@ -4208,6 +4116,36 @@ const childNodeKeys = {
4208
4116
  YieldExpression: ['argument']
4209
4117
  };
4210
4118
 
4119
+ function createInclusionContext() {
4120
+ return {
4121
+ brokenFlow: false,
4122
+ hasBreak: false,
4123
+ hasContinue: false,
4124
+ includedCallArguments: new Set(),
4125
+ includedLabels: new Set()
4126
+ };
4127
+ }
4128
+ function createHasEffectsContext() {
4129
+ return {
4130
+ accessed: new PathTracker(),
4131
+ assigned: new PathTracker(),
4132
+ brokenFlow: false,
4133
+ called: new DiscriminatedPathTracker(),
4134
+ hasBreak: false,
4135
+ hasContinue: false,
4136
+ ignore: {
4137
+ breaks: false,
4138
+ continues: false,
4139
+ labels: new Set(),
4140
+ returnYield: false,
4141
+ this: false
4142
+ },
4143
+ includedLabels: new Set(),
4144
+ instantiated: new DiscriminatedPathTracker(),
4145
+ replacedVariableInits: new Map()
4146
+ };
4147
+ }
4148
+
4211
4149
  const INCLUDE_PARAMETERS = 'variables';
4212
4150
  const IS_SKIPPED_CHAIN = Symbol('IS_SKIPPED_CHAIN');
4213
4151
  class NodeBase extends ExpressionEntity {
@@ -4277,37 +4215,20 @@ class NodeBase extends ExpressionEntity {
4277
4215
  this.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.assignmentInteraction, context));
4278
4216
  }
4279
4217
  include(context, includeChildrenRecursively, _options) {
4280
- if (!this.included)
4281
- this.includeNode(context);
4282
- for (const key of childNodeKeys[this.type]) {
4283
- const value = this[key];
4284
- if (value === null)
4285
- continue;
4286
- if (Array.isArray(value)) {
4287
- for (const child of value) {
4288
- child?.include(context, includeChildrenRecursively);
4289
- }
4290
- }
4291
- else {
4292
- value.include(context, includeChildrenRecursively);
4293
- }
4294
- }
4295
- }
4296
- includeNode(context) {
4297
- this.included = true;
4298
4218
  if (!this.deoptimized)
4299
4219
  this.applyDeoptimizations();
4220
+ this.included = true;
4300
4221
  for (const key of childNodeKeys[this.type]) {
4301
4222
  const value = this[key];
4302
4223
  if (value === null)
4303
4224
  continue;
4304
4225
  if (Array.isArray(value)) {
4305
4226
  for (const child of value) {
4306
- child?.includePath(UNKNOWN_PATH, context);
4227
+ child?.include(context, includeChildrenRecursively);
4307
4228
  }
4308
4229
  }
4309
4230
  else {
4310
- value.includePath(UNKNOWN_PATH, context);
4231
+ value.include(context, includeChildrenRecursively);
4311
4232
  }
4312
4233
  }
4313
4234
  }
@@ -4414,17 +4335,6 @@ class NodeBase extends ExpressionEntity {
4414
4335
  function createChildNodeKeysForNode(esTreeNode) {
4415
4336
  return Object.keys(esTreeNode).filter(key => typeof esTreeNode[key] === 'object' && key.charCodeAt(0) !== 95 /* _ */);
4416
4337
  }
4417
- function onlyIncludeSelf() {
4418
- this.included = true;
4419
- if (!this.deoptimized)
4420
- this.applyDeoptimizations();
4421
- }
4422
- function onlyIncludeSelfNoDeoptimize() {
4423
- this.included = true;
4424
- }
4425
- function doNotDeoptimize() {
4426
- this.deoptimized = true;
4427
- }
4428
4338
 
4429
4339
  function isObjectExpressionNode(node) {
4430
4340
  return node instanceof NodeBase && node.type === parseAst_js.ObjectExpression;
@@ -4437,8 +4347,8 @@ function assembleMemberDescriptions(memberDescriptions, inheritedDescriptions =
4437
4347
  return Object.create(inheritedDescriptions, memberDescriptions);
4438
4348
  }
4439
4349
  const UNDEFINED_EXPRESSION = new (class UndefinedExpression extends ExpressionEntity {
4440
- getLiteralValueAtPath(path) {
4441
- return path.length > 0 ? UnknownValue : undefined;
4350
+ getLiteralValueAtPath() {
4351
+ return undefined;
4442
4352
  }
4443
4353
  })();
4444
4354
  const returnsUnknown = {
@@ -4635,6 +4545,31 @@ function getMemberReturnExpressionWhenCalled(members, memberName) {
4635
4545
  return [members[memberName].returns, false];
4636
4546
  }
4637
4547
 
4548
+ class SpreadElement extends NodeBase {
4549
+ deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
4550
+ if (path.length > 0) {
4551
+ this.argument.deoptimizeArgumentsOnInteractionAtPath(interaction, UNKNOWN_PATH, recursionTracker);
4552
+ }
4553
+ }
4554
+ hasEffects(context) {
4555
+ if (!this.deoptimized)
4556
+ this.applyDeoptimizations();
4557
+ const { propertyReadSideEffects } = this.scope.context.options
4558
+ .treeshake;
4559
+ return (this.argument.hasEffects(context) ||
4560
+ (propertyReadSideEffects &&
4561
+ (propertyReadSideEffects === 'always' ||
4562
+ this.argument.hasEffectsOnInteractionAtPath(UNKNOWN_PATH, NODE_INTERACTION_UNKNOWN_ACCESS, context))));
4563
+ }
4564
+ applyDeoptimizations() {
4565
+ this.deoptimized = true;
4566
+ // Only properties of properties of the argument could become subject to reassignment
4567
+ // This will also reassign the return values of iterators
4568
+ this.argument.deoptimizePath([UnknownKey, UnknownKey]);
4569
+ this.scope.context.requestTreeshakingPass();
4570
+ }
4571
+ }
4572
+
4638
4573
  class Method extends ExpressionEntity {
4639
4574
  constructor(description) {
4640
4575
  super();
@@ -4760,7 +4695,6 @@ class ObjectEntity extends ExpressionEntity {
4760
4695
  this.unknownIntegerProps = [];
4761
4696
  this.unmatchableGetters = [];
4762
4697
  this.unmatchablePropertiesAndGetters = [];
4763
- this.unmatchablePropertiesAndSetters = [];
4764
4698
  this.unmatchableSetters = [];
4765
4699
  if (Array.isArray(properties)) {
4766
4700
  this.buildPropertyMaps(properties);
@@ -4917,12 +4851,7 @@ class ObjectEntity extends ExpressionEntity {
4917
4851
  }
4918
4852
  getLiteralValueAtPath(path, recursionTracker, origin) {
4919
4853
  if (path.length === 0) {
4920
- // This should actually be "UnknownTruthyValue". However, this currently
4921
- // causes an issue with TypeScript enums in files with moduleSideEffects:
4922
- // false because we cannot properly track whether a "var" has been
4923
- // initialized. This should be reverted once we can properly track this.
4924
- // return UnknownTruthyValue;
4925
- return UnknownValue;
4854
+ return UnknownTruthyValue;
4926
4855
  }
4927
4856
  const key = path[0];
4928
4857
  const expressionAtPath = this.getMemberExpressionAndTrackDeopt(key, origin);
@@ -5000,38 +4929,9 @@ class ObjectEntity extends ExpressionEntity {
5000
4929
  }
5001
4930
  return false;
5002
4931
  }
5003
- include(context, includeChildrenRecursively) {
5004
- this.included = true;
5005
- for (const property of this.allProperties) {
5006
- if (includeChildrenRecursively || property.shouldBeIncluded(context)) {
5007
- property.include(context, includeChildrenRecursively);
5008
- }
5009
- }
5010
- this.prototypeExpression?.include(context, includeChildrenRecursively);
5011
- }
5012
- includePath(path, context) {
5013
- this.included = true;
5014
- if (path.length === 0)
5015
- return;
5016
- const [key, ...subPath] = path;
5017
- const [includedMembers, includedPath] = typeof key === 'string'
5018
- ? [
5019
- [
5020
- ...new Set([
5021
- ...(this.propertiesAndGettersByKey[key] || this.unmatchablePropertiesAndGetters),
5022
- ...(this.propertiesAndSettersByKey[key] || this.unmatchablePropertiesAndSetters)
5023
- ])
5024
- ],
5025
- subPath
5026
- ]
5027
- : [this.allProperties, UNKNOWN_PATH];
5028
- for (const property of includedMembers) {
5029
- property.includePath(includedPath, context);
5030
- }
5031
- this.prototypeExpression?.includePath(path, context);
5032
- }
5033
4932
  buildPropertyMaps(properties) {
5034
- const { allProperties, propertiesAndGettersByKey, propertiesAndSettersByKey, settersByKey, gettersByKey, unknownIntegerProps, unmatchablePropertiesAndGetters, unmatchablePropertiesAndSetters, unmatchableGetters, unmatchableSetters } = this;
4933
+ const { allProperties, propertiesAndGettersByKey, propertiesAndSettersByKey, settersByKey, gettersByKey, unknownIntegerProps, unmatchablePropertiesAndGetters, unmatchableGetters, unmatchableSetters } = this;
4934
+ const unmatchablePropertiesAndSetters = [];
5035
4935
  for (let index = properties.length - 1; index >= 0; index--) {
5036
4936
  const { key, kind, property } = properties[index];
5037
4937
  allProperties.push(property);
@@ -5301,37 +5201,6 @@ const ARRAY_PROTOTYPE = new ObjectEntity({
5301
5201
  values: METHOD_DEOPTS_SELF_RETURNS_UNKNOWN
5302
5202
  }, OBJECT_PROTOTYPE, true);
5303
5203
 
5304
- class SpreadElement extends NodeBase {
5305
- deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
5306
- if (path.length > 0) {
5307
- this.argument.deoptimizeArgumentsOnInteractionAtPath(interaction, UNKNOWN_PATH, recursionTracker);
5308
- }
5309
- }
5310
- hasEffects(context) {
5311
- if (!this.deoptimized)
5312
- this.applyDeoptimizations();
5313
- const { propertyReadSideEffects } = this.scope.context.options
5314
- .treeshake;
5315
- return (this.argument.hasEffects(context) ||
5316
- (propertyReadSideEffects &&
5317
- (propertyReadSideEffects === 'always' ||
5318
- this.argument.hasEffectsOnInteractionAtPath(UNKNOWN_PATH, NODE_INTERACTION_UNKNOWN_ACCESS, context))));
5319
- }
5320
- includeNode(context) {
5321
- this.included = true;
5322
- if (!this.deoptimized)
5323
- this.applyDeoptimizations();
5324
- this.argument.includePath(UNKNOWN_PATH, context);
5325
- }
5326
- applyDeoptimizations() {
5327
- this.deoptimized = true;
5328
- // Only properties of properties of the argument could become subject to reassignment
5329
- // This will also reassign the return values of iterators
5330
- this.argument.deoptimizePath([UnknownKey, UnknownKey]);
5331
- this.scope.context.requestTreeshakingPass();
5332
- }
5333
- }
5334
-
5335
5204
  class ArrayExpression extends NodeBase {
5336
5205
  constructor() {
5337
5206
  super(...arguments);
@@ -5352,16 +5221,6 @@ class ArrayExpression extends NodeBase {
5352
5221
  hasEffectsOnInteractionAtPath(path, interaction, context) {
5353
5222
  return this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
5354
5223
  }
5355
- includeNode(context) {
5356
- this.included = true;
5357
- if (!this.deoptimized)
5358
- this.applyDeoptimizations();
5359
- for (const element of this.elements) {
5360
- if (element) {
5361
- element?.includePath(UNKNOWN_PATH, context);
5362
- }
5363
- }
5364
- }
5365
5224
  applyDeoptimizations() {
5366
5225
  this.deoptimized = true;
5367
5226
  let hasSpread = false;
@@ -6429,37 +6288,17 @@ class GlobalVariable extends Variable {
6429
6288
  }
6430
6289
  }
6431
6290
 
6432
- // To avoid infinite recursions
6433
- const MAX_PATH_DEPTH = 6;
6434
- // If a path is longer than MAX_PATH_DEPTH, it is truncated so that it is at
6435
- // most MAX_PATH_DEPTH long. The last element is always UnknownKey
6436
- const limitConcatenatedPathDepth = (path1, path2) => {
6437
- const { length: length1 } = path1;
6438
- const { length: length2 } = path2;
6439
- return length1 === 0
6440
- ? path2
6441
- : length2 === 0
6442
- ? path1
6443
- : length1 + length2 > MAX_PATH_DEPTH
6444
- ? [...path1, ...path2.slice(0, MAX_PATH_DEPTH - 1 - path1.length), 'UnknownKey']
6445
- : [...path1, ...path2];
6446
- };
6447
-
6448
6291
  class LocalVariable extends Variable {
6449
- constructor(name, declarator, init,
6450
- /** if this is non-empty, the actual init is this path of this.init */
6451
- initPath, context, kind) {
6292
+ constructor(name, declarator, init, context, kind) {
6452
6293
  super(name);
6453
6294
  this.init = init;
6454
- this.initPath = initPath;
6455
- this.kind = kind;
6456
6295
  this.calledFromTryStatement = false;
6457
6296
  this.additionalInitializers = null;
6458
- this.includedPathTracker = new IncludedPathTracker();
6459
6297
  this.expressionsToBeDeoptimized = [];
6460
6298
  this.declarations = declarator ? [declarator] : [];
6461
6299
  this.deoptimizationTracker = context.deoptimizationTracker;
6462
6300
  this.module = context.module;
6301
+ this.kind = kind;
6463
6302
  }
6464
6303
  addDeclaration(identifier, init) {
6465
6304
  this.declarations.push(identifier);
@@ -6470,16 +6309,15 @@ class LocalVariable extends Variable {
6470
6309
  for (const initializer of this.additionalInitializers) {
6471
6310
  initializer.deoptimizePath(UNKNOWN_PATH);
6472
6311
  }
6312
+ this.additionalInitializers = null;
6473
6313
  }
6474
6314
  }
6475
6315
  deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
6476
- if (this.isReassigned || path.length + this.initPath.length > MAX_PATH_DEPTH) {
6316
+ if (this.isReassigned) {
6477
6317
  deoptimizeInteraction(interaction);
6478
6318
  return;
6479
6319
  }
6480
- recursionTracker.withTrackedEntityAtPath(path, this.init, () => {
6481
- this.init.deoptimizeArgumentsOnInteractionAtPath(interaction, [...this.initPath, ...path], recursionTracker);
6482
- }, undefined);
6320
+ recursionTracker.withTrackedEntityAtPath(path, this.init, () => this.init.deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker), undefined);
6483
6321
  }
6484
6322
  deoptimizePath(path) {
6485
6323
  if (this.isReassigned ||
@@ -6493,40 +6331,37 @@ class LocalVariable extends Variable {
6493
6331
  for (const expression of expressionsToBeDeoptimized) {
6494
6332
  expression.deoptimizeCache();
6495
6333
  }
6496
- this.init.deoptimizePath([...this.initPath, UnknownKey]);
6334
+ this.init.deoptimizePath(UNKNOWN_PATH);
6497
6335
  }
6498
6336
  else {
6499
- this.init.deoptimizePath(limitConcatenatedPathDepth(this.initPath, path));
6337
+ this.init.deoptimizePath(path);
6500
6338
  }
6501
6339
  }
6502
6340
  getLiteralValueAtPath(path, recursionTracker, origin) {
6503
- if (this.isReassigned || path.length + this.initPath.length > MAX_PATH_DEPTH) {
6341
+ if (this.isReassigned) {
6504
6342
  return UnknownValue;
6505
6343
  }
6506
6344
  return recursionTracker.withTrackedEntityAtPath(path, this.init, () => {
6507
6345
  this.expressionsToBeDeoptimized.push(origin);
6508
- return this.init.getLiteralValueAtPath([...this.initPath, ...path], recursionTracker, origin);
6346
+ return this.init.getLiteralValueAtPath(path, recursionTracker, origin);
6509
6347
  }, UnknownValue);
6510
6348
  }
6511
6349
  getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
6512
- if (this.isReassigned || path.length + this.initPath.length > MAX_PATH_DEPTH) {
6350
+ if (this.isReassigned) {
6513
6351
  return UNKNOWN_RETURN_EXPRESSION;
6514
6352
  }
6515
6353
  return recursionTracker.withTrackedEntityAtPath(path, this.init, () => {
6516
6354
  this.expressionsToBeDeoptimized.push(origin);
6517
- return this.init.getReturnExpressionWhenCalledAtPath([...this.initPath, ...path], interaction, recursionTracker, origin);
6355
+ return this.init.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
6518
6356
  }, UNKNOWN_RETURN_EXPRESSION);
6519
6357
  }
6520
6358
  hasEffectsOnInteractionAtPath(path, interaction, context) {
6521
- if (path.length + this.initPath.length > MAX_PATH_DEPTH) {
6522
- return true;
6523
- }
6524
6359
  switch (interaction.type) {
6525
6360
  case INTERACTION_ACCESSED: {
6526
6361
  if (this.isReassigned)
6527
6362
  return true;
6528
6363
  return (!context.accessed.trackEntityAtPathAndGetIfTracked(path, this) &&
6529
- this.init.hasEffectsOnInteractionAtPath([...this.initPath, ...path], interaction, context));
6364
+ this.init.hasEffectsOnInteractionAtPath(path, interaction, context));
6530
6365
  }
6531
6366
  case INTERACTION_ASSIGNED: {
6532
6367
  if (this.included)
@@ -6536,63 +6371,44 @@ class LocalVariable extends Variable {
6536
6371
  if (this.isReassigned)
6537
6372
  return true;
6538
6373
  return (!context.assigned.trackEntityAtPathAndGetIfTracked(path, this) &&
6539
- this.init.hasEffectsOnInteractionAtPath([...this.initPath, ...path], interaction, context));
6374
+ this.init.hasEffectsOnInteractionAtPath(path, interaction, context));
6540
6375
  }
6541
6376
  case INTERACTION_CALLED: {
6542
6377
  if (this.isReassigned)
6543
6378
  return true;
6544
6379
  return (!(interaction.withNew ? context.instantiated : context.called).trackEntityAtPathAndGetIfTracked(path, interaction.args, this) &&
6545
- this.init.hasEffectsOnInteractionAtPath([...this.initPath, ...path], interaction, context));
6380
+ this.init.hasEffectsOnInteractionAtPath(path, interaction, context));
6546
6381
  }
6547
6382
  }
6548
6383
  }
6549
- includePath(path, context) {
6550
- if (!this.includedPathTracker.includePathAndGetIfIncluded(path)) {
6551
- this.module.scope.context.requestTreeshakingPass();
6552
- if (!this.included) {
6553
- // This will reduce the number of tree-shaking passes by eagerly
6554
- // including inits. By pushing this here instead of directly including
6555
- // we avoid deep call stacks.
6556
- this.module.scope.context.newlyIncludedVariableInits.add(this.init);
6557
- }
6558
- super.includePath(path, context);
6384
+ include() {
6385
+ if (!this.included) {
6386
+ super.include();
6559
6387
  for (const declaration of this.declarations) {
6560
6388
  // If node is a default export, it can save a tree-shaking run to include the full declaration now
6561
6389
  if (!declaration.included)
6562
- declaration.include(context, false);
6390
+ declaration.include(createInclusionContext(), false);
6563
6391
  let node = declaration.parent;
6564
6392
  while (!node.included) {
6565
6393
  // We do not want to properly include parents in case they are part of a dead branch
6566
6394
  // in which case .include() might pull in more dead code
6567
- node.includeNode(context);
6395
+ node.included = true;
6568
6396
  if (node.type === parseAst_js.Program)
6569
6397
  break;
6570
6398
  node = node.parent;
6571
6399
  }
6572
6400
  }
6573
- // We need to make sure we include the correct path of the init
6574
- if (path.length > 0) {
6575
- this.init.includePath(limitConcatenatedPathDepth(this.initPath, path), context);
6576
- this.additionalInitializers?.forEach(initializer => initializer.includePath(UNKNOWN_PATH, context));
6577
- }
6578
6401
  }
6579
6402
  }
6580
- includeCallArguments(context, interaction) {
6581
- if (this.isReassigned ||
6582
- context.includedCallArguments.has(this.init) ||
6583
- // This can be removed again once we can include arguments when called at
6584
- // a specific path
6585
- this.initPath.length > 0) {
6586
- for (const argument of interaction.args) {
6587
- if (argument) {
6588
- argument.includePath(UNKNOWN_PATH, context);
6589
- argument.include(context, false);
6590
- }
6403
+ includeCallArguments(context, parameters) {
6404
+ if (this.isReassigned || context.includedCallArguments.has(this.init)) {
6405
+ for (const argument of parameters) {
6406
+ argument.include(context, false);
6591
6407
  }
6592
6408
  }
6593
6409
  else {
6594
6410
  context.includedCallArguments.add(this.init);
6595
- this.init.includeCallArguments(context, interaction);
6411
+ this.init.includeCallArguments(context, parameters);
6596
6412
  context.includedCallArguments.delete(this.init);
6597
6413
  }
6598
6414
  }
@@ -6672,31 +6488,18 @@ class IdentifierBase extends NodeBase {
6672
6488
  }
6673
6489
  }
6674
6490
  }
6675
- include(context) {
6676
- if (!this.included)
6677
- this.includeNode(context);
6678
- }
6679
- includeNode(context) {
6680
- this.included = true;
6491
+ include() {
6681
6492
  if (!this.deoptimized)
6682
6493
  this.applyDeoptimizations();
6683
- if (this.variable !== null) {
6684
- this.scope.context.includeVariableInModule(this.variable, EMPTY_PATH, context);
6685
- }
6686
- }
6687
- includePath(path, context) {
6688
6494
  if (!this.included) {
6689
6495
  this.included = true;
6690
6496
  if (this.variable !== null) {
6691
- this.scope.context.includeVariableInModule(this.variable, path, context);
6497
+ this.scope.context.includeVariableInModule(this.variable);
6692
6498
  }
6693
6499
  }
6694
- else if (path.length > 0) {
6695
- this.variable?.includePath(path, context);
6696
- }
6697
6500
  }
6698
- includeCallArguments(context, interaction) {
6699
- this.variable.includeCallArguments(context, interaction);
6501
+ includeCallArguments(context, parameters) {
6502
+ this.variable.includeCallArguments(context, parameters);
6700
6503
  }
6701
6504
  isPossibleTDZ() {
6702
6505
  // return cached value to avoid issues with the next tree-shaking pass
@@ -6779,40 +6582,11 @@ function closestParentFunctionOrProgram(node) {
6779
6582
  return node;
6780
6583
  }
6781
6584
 
6782
- class ObjectMember extends ExpressionEntity {
6783
- constructor(object, path) {
6784
- super();
6785
- this.object = object;
6786
- this.path = path;
6787
- }
6788
- deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
6789
- this.object.deoptimizeArgumentsOnInteractionAtPath(interaction, [...this.path, ...path], recursionTracker);
6790
- }
6791
- deoptimizePath(path) {
6792
- this.object.deoptimizePath([...this.path, ...path]);
6793
- }
6794
- getLiteralValueAtPath(path, recursionTracker, origin) {
6795
- return this.object.getLiteralValueAtPath([...this.path, ...path], recursionTracker, origin);
6796
- }
6797
- getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
6798
- return this.object.getReturnExpressionWhenCalledAtPath([...this.path, ...path], interaction, recursionTracker, origin);
6799
- }
6800
- hasEffectsOnInteractionAtPath(path, interaction, context) {
6801
- return this.object.hasEffectsOnInteractionAtPath([...this.path, ...path], interaction, context);
6802
- }
6803
- }
6804
-
6805
6585
  class Identifier extends IdentifierBase {
6806
6586
  constructor() {
6807
6587
  super(...arguments);
6808
6588
  this.variable = null;
6809
6589
  }
6810
- get isDestructuringDeoptimized() {
6811
- return isFlagSet(this.flags, 16777216 /* Flag.destructuringDeoptimized */);
6812
- }
6813
- set isDestructuringDeoptimized(value) {
6814
- this.flags = setFlag(this.flags, 16777216 /* Flag.destructuringDeoptimized */, value);
6815
- }
6816
6590
  addExportedVariables(variables, exportNamesByVariable) {
6817
6591
  if (exportNamesByVariable.has(this.variable)) {
6818
6592
  variables.push(this.variable);
@@ -6825,52 +6599,42 @@ class Identifier extends IdentifierBase {
6825
6599
  this.isVariableReference = true;
6826
6600
  }
6827
6601
  }
6828
- declare(kind, destructuredInitPath, init) {
6602
+ declare(kind, init) {
6829
6603
  let variable;
6830
6604
  const { treeshake } = this.scope.context.options;
6831
- if (kind === 'parameter') {
6832
- variable = this.scope.addParameterDeclaration(this, destructuredInitPath);
6833
- }
6834
- else {
6835
- variable = this.scope.addDeclaration(this, this.scope.context, init, destructuredInitPath, kind);
6836
- if (kind === 'var' && treeshake && treeshake.correctVarValueBeforeDeclaration) {
6837
- // Necessary to make sure the init is deoptimized. We cannot call deoptimizePath here.
6838
- variable.markInitializersForDeoptimization();
6605
+ switch (kind) {
6606
+ case 'var': {
6607
+ variable = this.scope.addDeclaration(this, this.scope.context, init, kind);
6608
+ if (treeshake && treeshake.correctVarValueBeforeDeclaration) {
6609
+ // Necessary to make sure the init is deoptimized. We cannot call deoptimizePath here.
6610
+ variable.markInitializersForDeoptimization();
6611
+ }
6612
+ break;
6613
+ }
6614
+ case 'function': {
6615
+ // in strict mode, functions are only hoisted within a scope but not across block scopes
6616
+ variable = this.scope.addDeclaration(this, this.scope.context, init, kind);
6617
+ break;
6839
6618
  }
6840
- }
6841
- return [(this.variable = variable)];
6842
- }
6843
- deoptimizeAssignment(destructuredInitPath, init) {
6844
- this.deoptimizePath(EMPTY_PATH);
6845
- init.deoptimizePath([...destructuredInitPath, UnknownKey]);
6846
- }
6847
- hasEffectsWhenDestructuring(context, destructuredInitPath, init) {
6848
- return (destructuredInitPath.length > 0 &&
6849
- init.hasEffectsOnInteractionAtPath(destructuredInitPath, NODE_INTERACTION_UNKNOWN_ACCESS, context));
6850
- }
6851
- includeDestructuredIfNecessary(context, destructuredInitPath, init) {
6852
- if (destructuredInitPath.length > 0 && !this.isDestructuringDeoptimized) {
6853
- this.isDestructuringDeoptimized = true;
6854
- init.deoptimizeArgumentsOnInteractionAtPath({
6855
- args: [new ObjectMember(init, destructuredInitPath.slice(0, -1))],
6856
- type: INTERACTION_ACCESSED
6857
- }, destructuredInitPath, SHARED_RECURSION_TRACKER);
6858
- }
6859
- const { propertyReadSideEffects } = this.scope.context.options
6860
- .treeshake;
6861
- if ((this.included ||=
6862
- destructuredInitPath.length > 0 &&
6863
- !context.brokenFlow &&
6864
- propertyReadSideEffects &&
6865
- (propertyReadSideEffects === 'always' ||
6866
- init.hasEffectsOnInteractionAtPath(destructuredInitPath, NODE_INTERACTION_UNKNOWN_ACCESS, createHasEffectsContext())))) {
6867
- if (this.variable && !this.variable.included) {
6868
- this.scope.context.includeVariableInModule(this.variable, EMPTY_PATH, context);
6619
+ case 'let':
6620
+ case 'const':
6621
+ case 'using':
6622
+ case 'await using':
6623
+ case 'class': {
6624
+ variable = this.scope.addDeclaration(this, this.scope.context, init, kind);
6625
+ break;
6626
+ }
6627
+ case 'parameter': {
6628
+ variable = this.scope.addParameterDeclaration(this);
6629
+ break;
6630
+ }
6631
+ /* istanbul ignore next */
6632
+ default: {
6633
+ /* istanbul ignore next */
6634
+ throw new Error(`Internal Error: Unexpected identifier kind ${kind}.`);
6869
6635
  }
6870
- init.includePath(destructuredInitPath, context);
6871
- return true;
6872
6636
  }
6873
- return false;
6637
+ return [(this.variable = variable)];
6874
6638
  }
6875
6639
  markDeclarationReached() {
6876
6640
  this.variable.initReached = true;
@@ -6924,17 +6688,18 @@ class Scope {
6924
6688
  - then the variable is still declared in the hoisted outer scope, but the initializer is assigned to the parameter
6925
6689
  - const, let, class, and function except in the cases above cannot redeclare anything
6926
6690
  */
6927
- addDeclaration(identifier, context, init, destructuredInitPath, kind) {
6691
+ addDeclaration(identifier, context, init, kind) {
6928
6692
  const name = identifier.name;
6929
6693
  const existingVariable = this.hoistedVariables?.get(name) || this.variables.get(name);
6930
6694
  if (existingVariable) {
6931
- if (kind === 'var' && existingVariable.kind === 'var') {
6695
+ const existingKind = existingVariable.kind;
6696
+ if (kind === 'var' && existingKind === 'var') {
6932
6697
  existingVariable.addDeclaration(identifier, init);
6933
6698
  return existingVariable;
6934
6699
  }
6935
6700
  context.error(parseAst_js.logRedeclarationError(name), identifier.start);
6936
6701
  }
6937
- const newVariable = new LocalVariable(identifier.name, identifier, init, destructuredInitPath, context, kind);
6702
+ const newVariable = new LocalVariable(identifier.name, identifier, init, context, kind);
6938
6703
  this.variables.set(name, newVariable);
6939
6704
  return newVariable;
6940
6705
  }
@@ -7110,6 +6875,7 @@ class MethodBase extends NodeBase {
7110
6875
  }
7111
6876
  return this.getAccessedValue()[0].hasEffectsOnInteractionAtPath(path, interaction, context);
7112
6877
  }
6878
+ applyDeoptimizations() { }
7113
6879
  getAccessedValue() {
7114
6880
  if (this.accessedValue === null) {
7115
6881
  if (this.kind === 'get') {
@@ -7123,20 +6889,19 @@ class MethodBase extends NodeBase {
7123
6889
  return this.accessedValue;
7124
6890
  }
7125
6891
  }
7126
- MethodBase.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
7127
- MethodBase.prototype.applyDeoptimizations = doNotDeoptimize;
7128
6892
 
7129
6893
  class MethodDefinition extends MethodBase {
7130
6894
  hasEffects(context) {
7131
6895
  return super.hasEffects(context) || checkEffectForNodes(this.decorators, context);
7132
6896
  }
6897
+ applyDeoptimizations() { }
7133
6898
  }
7134
6899
 
7135
6900
  class BlockScope extends ChildScope {
7136
6901
  constructor(parent) {
7137
6902
  super(parent, parent.context);
7138
6903
  }
7139
- addDeclaration(identifier, context, init, destructuredInitPath, kind) {
6904
+ addDeclaration(identifier, context, init, kind) {
7140
6905
  if (kind === 'var') {
7141
6906
  const name = identifier.name;
7142
6907
  const existingVariable = this.hoistedVariables?.get(name) || this.variables.get(name);
@@ -7148,7 +6913,7 @@ class BlockScope extends ChildScope {
7148
6913
  }
7149
6914
  return context.error(parseAst_js.logRedeclarationError(name), identifier.start);
7150
6915
  }
7151
- const declaredVariable = this.parent.addDeclaration(identifier, context, init, destructuredInitPath, kind);
6916
+ const declaredVariable = this.parent.addDeclaration(identifier, context, init, kind);
7152
6917
  // Necessary to make sure the init is deoptimized for conditional declarations.
7153
6918
  // We cannot call deoptimizePath here.
7154
6919
  declaredVariable.markInitializersForDeoptimization();
@@ -7156,7 +6921,7 @@ class BlockScope extends ChildScope {
7156
6921
  this.addHoistedVariable(name, declaredVariable);
7157
6922
  return declaredVariable;
7158
6923
  }
7159
- return super.addDeclaration(identifier, context, init, destructuredInitPath, kind);
6924
+ return super.addDeclaration(identifier, context, init, kind);
7160
6925
  }
7161
6926
  }
7162
6927
 
@@ -7188,12 +6953,33 @@ class StaticBlock extends NodeBase {
7188
6953
  }
7189
6954
  }
7190
6955
  }
7191
- StaticBlock.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
7192
- StaticBlock.prototype.applyDeoptimizations = doNotDeoptimize;
7193
6956
  function isStaticBlock(statement) {
7194
6957
  return statement.type === parseAst_js.StaticBlock;
7195
6958
  }
7196
6959
 
6960
+ class ObjectMember extends ExpressionEntity {
6961
+ constructor(object, key) {
6962
+ super();
6963
+ this.object = object;
6964
+ this.key = key;
6965
+ }
6966
+ deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
6967
+ this.object.deoptimizeArgumentsOnInteractionAtPath(interaction, [this.key, ...path], recursionTracker);
6968
+ }
6969
+ deoptimizePath(path) {
6970
+ this.object.deoptimizePath([this.key, ...path]);
6971
+ }
6972
+ getLiteralValueAtPath(path, recursionTracker, origin) {
6973
+ return this.object.getLiteralValueAtPath([this.key, ...path], recursionTracker, origin);
6974
+ }
6975
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
6976
+ return this.object.getReturnExpressionWhenCalledAtPath([this.key, ...path], interaction, recursionTracker, origin);
6977
+ }
6978
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
6979
+ return this.object.hasEffectsOnInteractionAtPath([this.key, ...path], interaction, context);
6980
+ }
6981
+ }
6982
+
7197
6983
  class ClassNode extends NodeBase {
7198
6984
  constructor() {
7199
6985
  super(...arguments);
@@ -7234,20 +7020,21 @@ class ClassNode extends NodeBase {
7234
7020
  : this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
7235
7021
  }
7236
7022
  include(context, includeChildrenRecursively) {
7237
- if (!this.included)
7238
- this.includeNode(context);
7023
+ if (!this.deoptimized)
7024
+ this.applyDeoptimizations();
7025
+ this.included = true;
7239
7026
  this.superClass?.include(context, includeChildrenRecursively);
7240
7027
  this.body.include(context, includeChildrenRecursively);
7241
7028
  for (const decorator of this.decorators)
7242
7029
  decorator.include(context, includeChildrenRecursively);
7243
7030
  if (this.id) {
7244
7031
  this.id.markDeclarationReached();
7245
- this.id.include(context);
7032
+ this.id.include();
7246
7033
  }
7247
7034
  }
7248
7035
  initialise() {
7249
7036
  super.initialise();
7250
- this.id?.declare('class', EMPTY_PATH, this);
7037
+ this.id?.declare('class', this);
7251
7038
  for (const method of this.body.body) {
7252
7039
  if (method instanceof MethodDefinition && method.kind === 'constructor') {
7253
7040
  this.classConstructor = method;
@@ -7305,12 +7092,11 @@ class ClassNode extends NodeBase {
7305
7092
  staticProperties.unshift({
7306
7093
  key: 'prototype',
7307
7094
  kind: 'init',
7308
- property: new ObjectEntity(dynamicMethods, this.superClass ? new ObjectMember(this.superClass, ['prototype']) : OBJECT_PROTOTYPE)
7095
+ property: new ObjectEntity(dynamicMethods, this.superClass ? new ObjectMember(this.superClass, 'prototype') : OBJECT_PROTOTYPE)
7309
7096
  });
7310
7097
  return (this.objectEntity = new ObjectEntity(staticProperties, this.superClass || OBJECT_PROTOTYPE));
7311
7098
  }
7312
7099
  }
7313
- ClassNode.prototype.includeNode = onlyIncludeSelf;
7314
7100
 
7315
7101
  class ClassDeclaration extends ClassNode {
7316
7102
  initialise() {
@@ -7363,7 +7149,7 @@ class ClassDeclaration extends ClassNode {
7363
7149
 
7364
7150
  class ArgumentsVariable extends LocalVariable {
7365
7151
  constructor(context) {
7366
- super('arguments', null, UNKNOWN_EXPRESSION, EMPTY_PATH, context, 'other');
7152
+ super('arguments', null, UNKNOWN_EXPRESSION, context, 'other');
7367
7153
  this.deoptimizedArguments = [];
7368
7154
  }
7369
7155
  addArgumentToBeDeoptimized(argument) {
@@ -7377,8 +7163,8 @@ class ArgumentsVariable extends LocalVariable {
7377
7163
  hasEffectsOnInteractionAtPath(path, { type }) {
7378
7164
  return type !== INTERACTION_ACCESSED || path.length > 1;
7379
7165
  }
7380
- includePath(path, context) {
7381
- super.includePath(path, context);
7166
+ include() {
7167
+ super.include();
7382
7168
  for (const argument of this.deoptimizedArguments) {
7383
7169
  argument.deoptimizePath(UNKNOWN_PATH);
7384
7170
  }
@@ -7386,31 +7172,30 @@ class ArgumentsVariable extends LocalVariable {
7386
7172
  }
7387
7173
  }
7388
7174
 
7389
- const MAX_TRACKED_INTERACTIONS = 10;
7390
- const MAX_DEOPTIMIZED_FIELDS = 5;
7175
+ const MAX_TRACKED_INTERACTIONS = 20;
7391
7176
  const NO_INTERACTIONS = parseAst_js.EMPTY_ARRAY;
7392
7177
  const UNKNOWN_DEOPTIMIZED_FIELD = new Set([UnknownKey]);
7393
- const EMPTY_PATH_TRACKER = new EntityPathTracker();
7178
+ const EMPTY_PATH_TRACKER = new PathTracker();
7394
7179
  const UNKNOWN_DEOPTIMIZED_ENTITY = new Set([UNKNOWN_EXPRESSION]);
7395
7180
  class ParameterVariable extends LocalVariable {
7396
- constructor(name, declarator, argumentPath, context) {
7397
- super(name, declarator, UNKNOWN_EXPRESSION, argumentPath, context, 'parameter');
7398
- this.argumentsToBeDeoptimized = new Set();
7181
+ constructor(name, declarator, context) {
7182
+ super(name, declarator, UNKNOWN_EXPRESSION, context, 'parameter');
7399
7183
  this.deoptimizationInteractions = [];
7400
- this.deoptimizations = new EntityPathTracker();
7184
+ this.deoptimizations = new PathTracker();
7401
7185
  this.deoptimizedFields = new Set();
7402
- this.expressionsDependingOnKnownValue = [];
7186
+ this.entitiesToBeDeoptimized = new Set();
7187
+ this.expressionsUseTheKnownValue = [];
7403
7188
  this.knownValue = null;
7404
7189
  this.knownValueLiteral = UnknownValue;
7190
+ this.frozenValue = null;
7405
7191
  }
7406
- addArgumentValue(entity) {
7407
- this.updateKnownValue(entity);
7192
+ addEntityToBeDeoptimized(entity) {
7408
7193
  if (entity === UNKNOWN_EXPRESSION) {
7409
7194
  // As unknown expressions fully deoptimize all interactions, we can clear
7410
7195
  // the interaction cache at this point provided we keep this optimization
7411
7196
  // in mind when adding new interactions
7412
- if (!this.argumentsToBeDeoptimized.has(UNKNOWN_EXPRESSION)) {
7413
- this.argumentsToBeDeoptimized.add(UNKNOWN_EXPRESSION);
7197
+ if (!this.entitiesToBeDeoptimized.has(UNKNOWN_EXPRESSION)) {
7198
+ this.entitiesToBeDeoptimized.add(UNKNOWN_EXPRESSION);
7414
7199
  for (const { interaction } of this.deoptimizationInteractions) {
7415
7200
  deoptimizeInteraction(interaction);
7416
7201
  }
@@ -7420,30 +7205,27 @@ class ParameterVariable extends LocalVariable {
7420
7205
  else if (this.deoptimizedFields.has(UnknownKey)) {
7421
7206
  // This means that we already deoptimized all interactions and no longer
7422
7207
  // track them
7423
- entity.deoptimizePath([...this.initPath, UnknownKey]);
7208
+ entity.deoptimizePath(UNKNOWN_PATH);
7424
7209
  }
7425
- else if (!this.argumentsToBeDeoptimized.has(entity)) {
7426
- this.argumentsToBeDeoptimized.add(entity);
7210
+ else if (!this.entitiesToBeDeoptimized.has(entity)) {
7211
+ this.entitiesToBeDeoptimized.add(entity);
7427
7212
  for (const field of this.deoptimizedFields) {
7428
- entity.deoptimizePath([...this.initPath, field]);
7213
+ entity.deoptimizePath([field]);
7429
7214
  }
7430
7215
  for (const { interaction, path } of this.deoptimizationInteractions) {
7431
- entity.deoptimizeArgumentsOnInteractionAtPath(interaction, [...this.initPath, ...path], SHARED_RECURSION_TRACKER);
7216
+ entity.deoptimizeArgumentsOnInteractionAtPath(interaction, path, SHARED_RECURSION_TRACKER);
7432
7217
  }
7433
7218
  }
7434
7219
  }
7435
- /** This says we should not make assumptions about the value of the parameter.
7436
- * This is different from deoptimization that will also cause argument values
7437
- * to be deoptimized. */
7438
7220
  markReassigned() {
7439
7221
  if (this.isReassigned) {
7440
7222
  return;
7441
7223
  }
7442
7224
  super.markReassigned();
7443
- for (const expression of this.expressionsDependingOnKnownValue) {
7225
+ for (const expression of this.expressionsUseTheKnownValue) {
7444
7226
  expression.deoptimizeCache();
7445
7227
  }
7446
- this.expressionsDependingOnKnownValue = parseAst_js.EMPTY_ARRAY;
7228
+ this.expressionsUseTheKnownValue = parseAst_js.EMPTY_ARRAY;
7447
7229
  }
7448
7230
  deoptimizeCache() {
7449
7231
  this.markReassigned();
@@ -7460,7 +7242,7 @@ class ParameterVariable extends LocalVariable {
7460
7242
  }
7461
7243
  if (this.knownValue === null) {
7462
7244
  this.knownValue = argument;
7463
- this.knownValueLiteral = argument.getLiteralValueAtPath(this.initPath, SHARED_RECURSION_TRACKER, this);
7245
+ this.knownValueLiteral = argument.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, this);
7464
7246
  return;
7465
7247
  }
7466
7248
  // the same literal or identifier, do nothing
@@ -7470,10 +7252,14 @@ class ParameterVariable extends LocalVariable {
7470
7252
  this.knownValue.variable === argument.variable)) {
7471
7253
  return;
7472
7254
  }
7473
- const { knownValueLiteral } = this;
7474
- if (typeof knownValueLiteral === 'symbol' ||
7475
- argument.getLiteralValueAtPath(this.initPath, SHARED_RECURSION_TRACKER, this) !==
7476
- knownValueLiteral) {
7255
+ const oldValue = this.knownValueLiteral;
7256
+ if (typeof oldValue === 'symbol') {
7257
+ this.markReassigned();
7258
+ return;
7259
+ }
7260
+ // add tracking for the new argument
7261
+ const newValue = argument.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, this);
7262
+ if (newValue !== oldValue) {
7477
7263
  this.markReassigned();
7478
7264
  }
7479
7265
  }
@@ -7484,47 +7270,42 @@ class ParameterVariable extends LocalVariable {
7484
7270
  * @returns the frozen value
7485
7271
  */
7486
7272
  getKnownValue() {
7487
- return this.knownValue || UNKNOWN_EXPRESSION;
7273
+ if (this.frozenValue === null) {
7274
+ this.frozenValue = this.knownValue || UNKNOWN_EXPRESSION;
7275
+ }
7276
+ return this.frozenValue;
7488
7277
  }
7489
7278
  getLiteralValueAtPath(path, recursionTracker, origin) {
7490
- if (this.isReassigned || path.length + this.initPath.length > MAX_PATH_DEPTH) {
7279
+ if (this.isReassigned) {
7491
7280
  return UnknownValue;
7492
7281
  }
7493
7282
  const knownValue = this.getKnownValue();
7494
- this.expressionsDependingOnKnownValue.push(origin);
7495
- return recursionTracker.withTrackedEntityAtPath(path, knownValue, () => knownValue.getLiteralValueAtPath([...this.initPath, ...path], recursionTracker, origin), UnknownValue);
7283
+ this.expressionsUseTheKnownValue.push(origin);
7284
+ return recursionTracker.withTrackedEntityAtPath(path, knownValue, () => knownValue.getLiteralValueAtPath(path, recursionTracker, origin), UnknownValue);
7496
7285
  }
7497
7286
  hasEffectsOnInteractionAtPath(path, interaction, context) {
7498
- const { type } = interaction;
7499
- if (this.isReassigned ||
7500
- type === INTERACTION_ASSIGNED ||
7501
- path.length + this.initPath.length > MAX_PATH_DEPTH) {
7287
+ if (this.isReassigned || interaction.type === INTERACTION_ASSIGNED) {
7502
7288
  return super.hasEffectsOnInteractionAtPath(path, interaction, context);
7503
7289
  }
7504
- return (!(type === INTERACTION_CALLED
7505
- ? (interaction.withNew
7506
- ? context.instantiated
7507
- : context.called).trackEntityAtPathAndGetIfTracked(path, interaction.args, this)
7508
- : context.accessed.trackEntityAtPathAndGetIfTracked(path, this)) &&
7509
- this.getKnownValue().hasEffectsOnInteractionAtPath([...this.initPath, ...path], interaction, context));
7290
+ const knownValue = this.getKnownValue();
7291
+ return knownValue.hasEffectsOnInteractionAtPath(path, interaction, context);
7510
7292
  }
7511
7293
  deoptimizeArgumentsOnInteractionAtPath(interaction, path) {
7512
7294
  // For performance reasons, we fully deoptimize all deeper interactions
7513
7295
  if (path.length >= 2 ||
7514
- this.argumentsToBeDeoptimized.has(UNKNOWN_EXPRESSION) ||
7296
+ this.entitiesToBeDeoptimized.has(UNKNOWN_EXPRESSION) ||
7515
7297
  this.deoptimizationInteractions.length >= MAX_TRACKED_INTERACTIONS ||
7516
7298
  (path.length === 1 &&
7517
7299
  (this.deoptimizedFields.has(UnknownKey) ||
7518
- (interaction.type === INTERACTION_CALLED && this.deoptimizedFields.has(path[0])))) ||
7519
- this.initPath.length + path.length > MAX_PATH_DEPTH) {
7300
+ (interaction.type === INTERACTION_CALLED && this.deoptimizedFields.has(path[0]))))) {
7520
7301
  deoptimizeInteraction(interaction);
7521
7302
  return;
7522
7303
  }
7523
7304
  if (!this.deoptimizations.trackEntityAtPathAndGetIfTracked(path, interaction.args)) {
7524
- for (const entity of this.argumentsToBeDeoptimized) {
7525
- entity.deoptimizeArgumentsOnInteractionAtPath(interaction, [...this.initPath, ...path], SHARED_RECURSION_TRACKER);
7305
+ for (const entity of this.entitiesToBeDeoptimized) {
7306
+ entity.deoptimizeArgumentsOnInteractionAtPath(interaction, path, SHARED_RECURSION_TRACKER);
7526
7307
  }
7527
- if (!this.argumentsToBeDeoptimized.has(UNKNOWN_EXPRESSION)) {
7308
+ if (!this.entitiesToBeDeoptimized.has(UNKNOWN_EXPRESSION)) {
7528
7309
  this.deoptimizationInteractions.push({
7529
7310
  interaction,
7530
7311
  path
@@ -7540,27 +7321,22 @@ class ParameterVariable extends LocalVariable {
7540
7321
  if (this.deoptimizedFields.has(UnknownKey)) {
7541
7322
  return;
7542
7323
  }
7543
- let key = path[0];
7324
+ const key = path[0];
7544
7325
  if (this.deoptimizedFields.has(key)) {
7545
7326
  return;
7546
7327
  }
7547
- if (this.deoptimizedFields.size > MAX_DEOPTIMIZED_FIELDS) {
7548
- key = UnknownKey;
7549
- }
7550
- else {
7551
- this.deoptimizedFields.add(key);
7552
- }
7553
- for (const entity of this.argumentsToBeDeoptimized) {
7328
+ this.deoptimizedFields.add(key);
7329
+ for (const entity of this.entitiesToBeDeoptimized) {
7554
7330
  // We do not need a recursion tracker here as we already track whether
7555
7331
  // this field is deoptimized
7556
- entity.deoptimizePath([...this.initPath, key]);
7332
+ entity.deoptimizePath([key]);
7557
7333
  }
7558
7334
  if (key === UnknownKey) {
7559
7335
  // save some memory
7560
7336
  this.deoptimizationInteractions = NO_INTERACTIONS;
7561
7337
  this.deoptimizations = EMPTY_PATH_TRACKER;
7562
7338
  this.deoptimizedFields = UNKNOWN_DEOPTIMIZED_FIELD;
7563
- this.argumentsToBeDeoptimized = UNKNOWN_DEOPTIMIZED_ENTITY;
7339
+ this.entitiesToBeDeoptimized = UNKNOWN_DEOPTIMIZED_ENTITY;
7564
7340
  }
7565
7341
  }
7566
7342
  getReturnExpressionWhenCalledAtPath(path) {
@@ -7575,14 +7351,11 @@ class ParameterVariable extends LocalVariable {
7575
7351
  }
7576
7352
  return UNKNOWN_RETURN_EXPRESSION;
7577
7353
  }
7578
- includeArgumentPaths(entity, context) {
7579
- this.includedPathTracker.includeAllPaths(entity, context, this.initPath);
7580
- }
7581
7354
  }
7582
7355
 
7583
7356
  class ThisVariable extends ParameterVariable {
7584
7357
  constructor(context) {
7585
- super('this', null, EMPTY_PATH, context);
7358
+ super('this', null, context);
7586
7359
  }
7587
7360
  hasEffectsOnInteractionAtPath(path, interaction, context) {
7588
7361
  return (context.replacedVariableInits.get(this) || UNKNOWN_EXPRESSION).hasEffectsOnInteractionAtPath(path, interaction, context);
@@ -7594,7 +7367,7 @@ class CatchBodyScope extends ChildScope {
7594
7367
  super(parent, parent.context);
7595
7368
  this.parent = parent;
7596
7369
  }
7597
- addDeclaration(identifier, context, init, destructuredInitPath, kind) {
7370
+ addDeclaration(identifier, context, init, kind) {
7598
7371
  if (kind === 'var') {
7599
7372
  const name = identifier.name;
7600
7373
  const existingVariable = this.hoistedVariables?.get(name) || this.variables.get(name);
@@ -7607,7 +7380,7 @@ class CatchBodyScope extends ChildScope {
7607
7380
  // the assignment actually goes to the parameter and the var is
7608
7381
  // hoisted without assignment. Locally, it is shadowed by the
7609
7382
  // parameter
7610
- const declaredVariable = this.parent.parent.addDeclaration(identifier, context, UNDEFINED_EXPRESSION, destructuredInitPath, kind);
7383
+ const declaredVariable = this.parent.parent.addDeclaration(identifier, context, UNDEFINED_EXPRESSION, kind);
7611
7384
  // To avoid the need to rewrite the declaration, we link the variable
7612
7385
  // names. If we ever implement a logic that splits initialization and
7613
7386
  // assignment for hoisted vars, the "renderLikeHoisted" logic can be
@@ -7626,7 +7399,7 @@ class CatchBodyScope extends ChildScope {
7626
7399
  return context.error(parseAst_js.logRedeclarationError(name), identifier.start);
7627
7400
  }
7628
7401
  // We only add parameters to parameter scopes
7629
- const declaredVariable = this.parent.parent.addDeclaration(identifier, context, init, destructuredInitPath, kind);
7402
+ const declaredVariable = this.parent.parent.addDeclaration(identifier, context, init, kind);
7630
7403
  // Necessary to make sure the init is deoptimized for conditional declarations.
7631
7404
  // We cannot call deoptimizePath here.
7632
7405
  declaredVariable.markInitializersForDeoptimization();
@@ -7634,7 +7407,7 @@ class CatchBodyScope extends ChildScope {
7634
7407
  this.addHoistedVariable(name, declaredVariable);
7635
7408
  return declaredVariable;
7636
7409
  }
7637
- return super.addDeclaration(identifier, context, init, destructuredInitPath, kind);
7410
+ return super.addDeclaration(identifier, context, init, kind);
7638
7411
  }
7639
7412
  }
7640
7413
 
@@ -7644,7 +7417,7 @@ class FunctionBodyScope extends ChildScope {
7644
7417
  }
7645
7418
  // There is stuff that is only allowed in function scopes, i.e. functions can
7646
7419
  // be redeclared, functions and var can redeclare each other
7647
- addDeclaration(identifier, context, init, destructuredInitPath, kind) {
7420
+ addDeclaration(identifier, context, init, kind) {
7648
7421
  const name = identifier.name;
7649
7422
  const existingVariable = this.hoistedVariables?.get(name) || this.variables.get(name);
7650
7423
  if (existingVariable) {
@@ -7656,7 +7429,7 @@ class FunctionBodyScope extends ChildScope {
7656
7429
  }
7657
7430
  context.error(parseAst_js.logRedeclarationError(name), identifier.start);
7658
7431
  }
7659
- const newVariable = new LocalVariable(identifier.name, identifier, init, destructuredInitPath, context, kind);
7432
+ const newVariable = new LocalVariable(identifier.name, identifier, init, context, kind);
7660
7433
  this.variables.set(name, newVariable);
7661
7434
  return newVariable;
7662
7435
  }
@@ -7665,21 +7438,21 @@ class FunctionBodyScope extends ChildScope {
7665
7438
  class ParameterScope extends ChildScope {
7666
7439
  constructor(parent, isCatchScope) {
7667
7440
  super(parent, parent.context);
7668
- this.hasRest = false;
7669
7441
  this.parameters = [];
7442
+ this.hasRest = false;
7670
7443
  this.bodyScope = isCatchScope ? new CatchBodyScope(this) : new FunctionBodyScope(this);
7671
7444
  }
7672
7445
  /**
7673
7446
  * Adds a parameter to this scope. Parameters must be added in the correct
7674
7447
  * order, i.e. from left to right.
7675
7448
  */
7676
- addParameterDeclaration(identifier, argumentPath) {
7449
+ addParameterDeclaration(identifier) {
7677
7450
  const { name, start } = identifier;
7678
7451
  const existingParameter = this.variables.get(name);
7679
7452
  if (existingParameter) {
7680
7453
  return this.context.error(parseAst_js.logDuplicateArgumentNameError(name), start);
7681
7454
  }
7682
- const variable = new ParameterVariable(name, identifier, argumentPath, this.context);
7455
+ const variable = new ParameterVariable(name, identifier, this.context);
7683
7456
  this.variables.set(name, variable);
7684
7457
  // We also add it to the body scope to detect name conflicts with local
7685
7458
  // variables. We still need the intermediate scope, though, as parameter
@@ -7697,56 +7470,42 @@ class ParameterScope extends ChildScope {
7697
7470
  }
7698
7471
  this.hasRest = hasRest;
7699
7472
  }
7700
- includeCallArguments(context, interaction) {
7473
+ includeCallArguments(context, parameters) {
7701
7474
  let calledFromTryStatement = false;
7702
7475
  let argumentIncluded = false;
7703
7476
  const restParameter = this.hasRest && this.parameters[this.parameters.length - 1];
7704
- const { args } = interaction;
7705
- let lastExplicitlyIncludedIndex = args.length - 1;
7706
- // If there is a SpreadElement, we need to include all arguments after it
7707
- // because we no longer know which argument corresponds to which parameter.
7708
- for (let argumentIndex = 1; argumentIndex < args.length; argumentIndex++) {
7709
- const argument = args[argumentIndex];
7710
- if (argument instanceof SpreadElement && !argumentIncluded) {
7711
- argumentIncluded = true;
7712
- lastExplicitlyIncludedIndex = argumentIndex - 1;
7713
- }
7714
- if (argumentIncluded) {
7715
- argument.includePath(UNKNOWN_PATH, context);
7716
- argument.include(context, false);
7477
+ for (const checkedArgument of parameters) {
7478
+ if (checkedArgument instanceof SpreadElement) {
7479
+ for (const argument of parameters) {
7480
+ argument.include(context, false);
7481
+ }
7482
+ break;
7717
7483
  }
7718
7484
  }
7719
- // Now we go backwards either starting from the last argument or before the
7720
- // first SpreadElement to ensure all arguments before are included as needed
7721
- for (let index = lastExplicitlyIncludedIndex; index >= 1; index--) {
7722
- const parameterVariables = this.parameters[index - 1] || restParameter;
7723
- const argument = args[index];
7485
+ for (let index = parameters.length - 1; index >= 0; index--) {
7486
+ const parameterVariables = this.parameters[index] || restParameter;
7487
+ const argument = parameters[index];
7724
7488
  if (parameterVariables) {
7725
7489
  calledFromTryStatement = false;
7726
7490
  if (parameterVariables.length === 0) {
7727
- // handle empty destructuring to avoid destructuring undefined
7491
+ // handle empty destructuring
7728
7492
  argumentIncluded = true;
7729
7493
  }
7730
7494
  else {
7731
7495
  for (const variable of parameterVariables) {
7732
- if (variable.calledFromTryStatement) {
7733
- calledFromTryStatement = true;
7734
- }
7735
7496
  if (variable.included) {
7736
7497
  argumentIncluded = true;
7737
- if (calledFromTryStatement) {
7738
- argument.include(context, true);
7739
- }
7740
- else {
7741
- variable.includeArgumentPaths(argument, context);
7742
- argument.include(context, false);
7743
- }
7498
+ }
7499
+ if (variable.calledFromTryStatement) {
7500
+ calledFromTryStatement = true;
7744
7501
  }
7745
7502
  }
7746
7503
  }
7747
7504
  }
7748
- if (!argument.included && (argumentIncluded || argument.shouldBeIncluded(context))) {
7505
+ if (!argumentIncluded && argument.shouldBeIncluded(context)) {
7749
7506
  argumentIncluded = true;
7507
+ }
7508
+ if (argumentIncluded) {
7750
7509
  argument.include(context, calledFromTryStatement);
7751
7510
  }
7752
7511
  }
@@ -7762,62 +7521,11 @@ class ReturnValueScope extends ParameterScope {
7762
7521
  addReturnExpression(expression) {
7763
7522
  this.returnExpressions.push(expression);
7764
7523
  }
7765
- deoptimizeArgumentsOnCall(interaction) {
7766
- const { parameters } = this;
7767
- const { args } = interaction;
7768
- let position = 0;
7769
- for (; position < args.length - 1; position++) {
7770
- // Only the "this" argument arg[0] can be null
7771
- const argument = args[position + 1];
7772
- if (argument instanceof SpreadElement) {
7773
- // This deoptimizes the current and remaining parameters and arguments
7774
- for (; position < parameters.length; position++) {
7775
- args[position + 1]?.deoptimizePath(UNKNOWN_PATH);
7776
- parameters[position].forEach(variable => variable.markReassigned());
7777
- }
7778
- break;
7779
- }
7780
- if (this.hasRest && position >= parameters.length - 1) {
7781
- argument.deoptimizePath(UNKNOWN_PATH);
7782
- }
7783
- else {
7784
- const variables = parameters[position];
7785
- if (variables) {
7786
- for (const variable of variables) {
7787
- variable.addArgumentValue(argument);
7788
- }
7789
- }
7790
- this.addArgumentToBeDeoptimized(argument);
7791
- }
7792
- }
7793
- const nonRestParameterLength = this.hasRest ? parameters.length - 1 : parameters.length;
7794
- for (; position < nonRestParameterLength; position++) {
7795
- for (const variable of parameters[position]) {
7796
- variable.addArgumentValue(UNDEFINED_EXPRESSION);
7797
- }
7798
- }
7799
- }
7800
7524
  getReturnExpression() {
7801
7525
  if (this.returnExpression === null)
7802
7526
  this.updateReturnExpression();
7803
7527
  return this.returnExpression;
7804
7528
  }
7805
- deoptimizeAllParameters() {
7806
- for (const parameter of this.parameters) {
7807
- for (const variable of parameter) {
7808
- variable.deoptimizePath(UNKNOWN_PATH);
7809
- variable.markReassigned();
7810
- }
7811
- }
7812
- }
7813
- reassignAllParameters() {
7814
- for (const parameter of this.parameters) {
7815
- for (const variable of parameter) {
7816
- variable.markReassigned();
7817
- }
7818
- }
7819
- }
7820
- addArgumentToBeDeoptimized(_argument) { }
7821
7529
  updateReturnExpression() {
7822
7530
  if (this.returnExpressions.length === 1) {
7823
7531
  this.returnExpression = this.returnExpressions[0];
@@ -7833,30 +7541,24 @@ class ReturnValueScope extends ParameterScope {
7833
7541
 
7834
7542
  class FunctionScope extends ReturnValueScope {
7835
7543
  constructor(parent) {
7836
- super(parent, false);
7837
7544
  const { context } = parent;
7545
+ super(parent, false);
7838
7546
  this.variables.set('arguments', (this.argumentsVariable = new ArgumentsVariable(context)));
7839
7547
  this.variables.set('this', (this.thisVariable = new ThisVariable(context)));
7840
7548
  }
7841
7549
  findLexicalBoundary() {
7842
7550
  return this;
7843
7551
  }
7844
- includeCallArguments(context, interaction) {
7845
- super.includeCallArguments(context, interaction);
7552
+ includeCallArguments(context, parameters) {
7553
+ super.includeCallArguments(context, parameters);
7846
7554
  if (this.argumentsVariable.included) {
7847
- const { args } = interaction;
7848
- for (let argumentIndex = 1; argumentIndex < args.length; argumentIndex++) {
7849
- const argument = args[argumentIndex];
7850
- if (argument) {
7851
- argument.includePath(UNKNOWN_PATH, context);
7555
+ for (const argument of parameters) {
7556
+ if (!argument.included) {
7852
7557
  argument.include(context, false);
7853
7558
  }
7854
7559
  }
7855
7560
  }
7856
7561
  }
7857
- addArgumentToBeDeoptimized(argument) {
7858
- this.argumentsVariable.addArgumentToBeDeoptimized(argument);
7859
- }
7860
7562
  }
7861
7563
 
7862
7564
  class ExpressionStatement extends NodeBase {
@@ -7884,9 +7586,8 @@ class ExpressionStatement extends NodeBase {
7884
7586
  return this.parent.type !== parseAst_js.Program;
7885
7587
  return super.shouldBeIncluded(context);
7886
7588
  }
7589
+ applyDeoptimizations() { }
7887
7590
  }
7888
- ExpressionStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
7889
- ExpressionStatement.prototype.applyDeoptimizations = doNotDeoptimize;
7890
7591
 
7891
7592
  class BlockStatement extends NodeBase {
7892
7593
  get deoptimizeBody() {
@@ -7951,8 +7652,6 @@ class BlockStatement extends NodeBase {
7951
7652
  }
7952
7653
  }
7953
7654
  }
7954
- BlockStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
7955
- BlockStatement.prototype.applyDeoptimizations = doNotDeoptimize;
7956
7655
 
7957
7656
  class RestElement extends NodeBase {
7958
7657
  constructor() {
@@ -7962,12 +7661,9 @@ class RestElement extends NodeBase {
7962
7661
  addExportedVariables(variables, exportNamesByVariable) {
7963
7662
  this.argument.addExportedVariables(variables, exportNamesByVariable);
7964
7663
  }
7965
- declare(kind, destructuredInitPath, init) {
7664
+ declare(kind, init) {
7966
7665
  this.declarationInit = init;
7967
- return this.argument.declare(kind, getIncludedPatternPath$1(destructuredInitPath), init);
7968
- }
7969
- deoptimizeAssignment(destructuredInitPath, init) {
7970
- this.argument.deoptimizeAssignment(getIncludedPatternPath$1(destructuredInitPath), init);
7666
+ return this.argument.declare(kind, UNKNOWN_EXPRESSION);
7971
7667
  }
7972
7668
  deoptimizePath(path) {
7973
7669
  if (path.length === 0) {
@@ -7978,20 +7674,6 @@ class RestElement extends NodeBase {
7978
7674
  return (path.length > 0 ||
7979
7675
  this.argument.hasEffectsOnInteractionAtPath(EMPTY_PATH, interaction, context));
7980
7676
  }
7981
- hasEffectsWhenDestructuring(context, destructuredInitPath, init) {
7982
- return this.argument.hasEffectsWhenDestructuring(context, getIncludedPatternPath$1(destructuredInitPath), init);
7983
- }
7984
- includeDestructuredIfNecessary(context, destructuredInitPath, init) {
7985
- return (this.included =
7986
- this.argument.includeDestructuredIfNecessary(context, getIncludedPatternPath$1(destructuredInitPath), init) || this.included);
7987
- }
7988
- include(context, includeChildrenRecursively) {
7989
- if (!this.included)
7990
- this.includeNode(context);
7991
- // This should just include the identifier, its properties should be
7992
- // included where the variable is used.
7993
- this.argument.include(context, includeChildrenRecursively);
7994
- }
7995
7677
  markDeclarationReached() {
7996
7678
  this.argument.markDeclarationReached();
7997
7679
  }
@@ -8003,16 +7685,12 @@ class RestElement extends NodeBase {
8003
7685
  }
8004
7686
  }
8005
7687
  }
8006
- RestElement.prototype.includeNode = onlyIncludeSelf;
8007
- const getIncludedPatternPath$1 = (destructuredInitPath) => destructuredInitPath.at(-1) === UnknownKey
8008
- ? destructuredInitPath
8009
- : [...destructuredInitPath, UnknownKey];
8010
7688
 
8011
7689
  class FunctionBase extends NodeBase {
8012
7690
  constructor() {
8013
7691
  super(...arguments);
7692
+ this.objectEntity = null;
8014
7693
  this.parameterVariableValuesDeoptimized = false;
8015
- this.includeCallArguments = this.scope.includeCallArguments.bind(this.scope);
8016
7694
  }
8017
7695
  get async() {
8018
7696
  return isFlagSet(this.flags, 256 /* Flag.async */);
@@ -8032,15 +7710,53 @@ class FunctionBase extends NodeBase {
8032
7710
  set generator(value) {
8033
7711
  this.flags = setFlag(this.flags, 4194304 /* Flag.generator */, value);
8034
7712
  }
8035
- get hasCachedEffects() {
8036
- return isFlagSet(this.flags, 67108864 /* Flag.hasEffects */);
7713
+ updateParameterVariableValues(_arguments) {
7714
+ for (let position = 0; position < this.params.length; position++) {
7715
+ const parameter = this.params[position];
7716
+ if (!(parameter instanceof Identifier)) {
7717
+ continue;
7718
+ }
7719
+ const parameterVariable = parameter.variable;
7720
+ const argument = _arguments[position + 1] ?? UNDEFINED_EXPRESSION;
7721
+ parameterVariable.updateKnownValue(argument);
7722
+ }
8037
7723
  }
8038
- set hasCachedEffects(value) {
8039
- this.flags = setFlag(this.flags, 67108864 /* Flag.hasEffects */, value);
7724
+ deoptimizeParameterVariableValues() {
7725
+ for (const parameter of this.params) {
7726
+ if (parameter instanceof Identifier) {
7727
+ const parameterVariable = parameter.variable;
7728
+ parameterVariable.markReassigned();
7729
+ }
7730
+ }
8040
7731
  }
8041
7732
  deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
8042
- if (interaction.type === INTERACTION_CALLED && path.length === 0) {
8043
- this.scope.deoptimizeArgumentsOnCall(interaction);
7733
+ if (interaction.type === INTERACTION_CALLED) {
7734
+ const { parameters } = this.scope;
7735
+ const { args } = interaction;
7736
+ let hasRest = false;
7737
+ for (let position = 0; position < args.length - 1; position++) {
7738
+ const parameter = this.params[position];
7739
+ // Only the "this" argument arg[0] can be null
7740
+ const argument = args[position + 1];
7741
+ if (argument instanceof SpreadElement) {
7742
+ this.deoptimizeParameterVariableValues();
7743
+ }
7744
+ if (hasRest || parameter instanceof RestElement) {
7745
+ hasRest = true;
7746
+ argument.deoptimizePath(UNKNOWN_PATH);
7747
+ }
7748
+ else if (parameter instanceof Identifier) {
7749
+ parameters[position][0].addEntityToBeDeoptimized(argument);
7750
+ this.addArgumentToBeDeoptimized(argument);
7751
+ }
7752
+ else if (parameter) {
7753
+ argument.deoptimizePath(UNKNOWN_PATH);
7754
+ }
7755
+ else {
7756
+ this.addArgumentToBeDeoptimized(argument);
7757
+ }
7758
+ }
7759
+ this.updateParameterVariableValues(args);
8044
7760
  }
8045
7761
  else {
8046
7762
  this.getObjectEntity().deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker);
@@ -8052,7 +7768,12 @@ class FunctionBase extends NodeBase {
8052
7768
  // A reassignment of UNKNOWN_PATH is considered equivalent to having lost track
8053
7769
  // which means the return expression and parameters need to be reassigned
8054
7770
  this.scope.getReturnExpression().deoptimizePath(UNKNOWN_PATH);
8055
- this.scope.deoptimizeAllParameters();
7771
+ for (const parameterList of this.scope.parameters) {
7772
+ for (const parameter of parameterList) {
7773
+ parameter.deoptimizePath(UNKNOWN_PATH);
7774
+ parameter.markReassigned();
7775
+ }
7776
+ }
8056
7777
  }
8057
7778
  }
8058
7779
  getLiteralValueAtPath(path, recursionTracker, origin) {
@@ -8076,8 +7797,8 @@ class FunctionBase extends NodeBase {
8076
7797
  if (path.length > 0 || interaction.type !== INTERACTION_CALLED) {
8077
7798
  return this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
8078
7799
  }
8079
- if (this.hasCachedEffects) {
8080
- return true;
7800
+ if (this.annotationNoSideEffects) {
7801
+ return false;
8081
7802
  }
8082
7803
  if (this.async) {
8083
7804
  const { propertyReadSideEffects } = this.scope.context.options
@@ -8087,20 +7808,12 @@ class FunctionBase extends NodeBase {
8087
7808
  (propertyReadSideEffects &&
8088
7809
  (propertyReadSideEffects === 'always' ||
8089
7810
  returnExpression.hasEffectsOnInteractionAtPath(['then'], NODE_INTERACTION_UNKNOWN_ACCESS, context)))) {
8090
- this.hasCachedEffects = true;
8091
7811
  return true;
8092
7812
  }
8093
7813
  }
8094
- const { propertyReadSideEffects } = this.scope.context.options
8095
- .treeshake;
8096
- for (let index = 0; index < this.params.length; index++) {
8097
- const parameter = this.params[index];
8098
- if (parameter.hasEffects(context) ||
8099
- (propertyReadSideEffects &&
8100
- parameter.hasEffectsWhenDestructuring(context, EMPTY_PATH, interaction.args[index + 1] || UNDEFINED_EXPRESSION))) {
8101
- this.hasCachedEffects = true;
7814
+ for (const parameter of this.params) {
7815
+ if (parameter.hasEffects(context))
8102
7816
  return true;
8103
- }
8104
7817
  }
8105
7818
  return false;
8106
7819
  }
@@ -8118,17 +7831,21 @@ class FunctionBase extends NodeBase {
8118
7831
  return variable?.getOnlyFunctionCallUsed() ?? false;
8119
7832
  }
8120
7833
  include(context, includeChildrenRecursively) {
8121
- if (!this.included)
8122
- this.includeNode(context);
8123
- if (!(this.parameterVariableValuesDeoptimized || this.onlyFunctionCallUsed())) {
7834
+ if (!this.parameterVariableValuesDeoptimized && !this.onlyFunctionCallUsed()) {
8124
7835
  this.parameterVariableValuesDeoptimized = true;
8125
- this.scope.reassignAllParameters();
7836
+ this.deoptimizeParameterVariableValues();
8126
7837
  }
7838
+ if (!this.deoptimized)
7839
+ this.applyDeoptimizations();
7840
+ this.included = true;
8127
7841
  const { brokenFlow } = context;
8128
7842
  context.brokenFlow = false;
8129
7843
  this.body.include(context, includeChildrenRecursively);
8130
7844
  context.brokenFlow = brokenFlow;
8131
7845
  }
7846
+ includeCallArguments(context, parameters) {
7847
+ this.scope.includeCallArguments(context, parameters);
7848
+ }
8132
7849
  initialise() {
8133
7850
  super.initialise();
8134
7851
  if (this.body instanceof BlockStatement) {
@@ -8150,14 +7867,14 @@ class FunctionBase extends NodeBase {
8150
7867
  // so that the scope already knows all parameters and can detect conflicts
8151
7868
  // when parsing the body.
8152
7869
  const parameters = (this.params = params.map((parameter) => new (context.getNodeConstructor(parameter.type))(this, scope).parseNode(parameter)));
8153
- scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', EMPTY_PATH, UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
7870
+ scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
8154
7871
  this.body = new (context.getNodeConstructor(body.type))(this, bodyScope).parseNode(body);
8155
7872
  return super.parseNode(esTreeNode);
8156
7873
  }
7874
+ addArgumentToBeDeoptimized(_argument) { }
7875
+ applyDeoptimizations() { }
8157
7876
  }
8158
7877
  FunctionBase.prototype.preventChildBlockScope = true;
8159
- FunctionBase.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
8160
- FunctionBase.prototype.applyDeoptimizations = doNotDeoptimize;
8161
7878
 
8162
7879
  class FunctionNode extends FunctionBase {
8163
7880
  constructor() {
@@ -8169,31 +7886,30 @@ class FunctionNode extends FunctionBase {
8169
7886
  this.constructedEntity = new ObjectEntity(Object.create(null), OBJECT_PROTOTYPE);
8170
7887
  // This makes sure that all deoptimizations of "this" are applied to the
8171
7888
  // constructed entity.
8172
- this.scope.thisVariable.addArgumentValue(this.constructedEntity);
7889
+ this.scope.thisVariable.addEntityToBeDeoptimized(this.constructedEntity);
8173
7890
  }
8174
7891
  deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
8175
7892
  super.deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker);
8176
7893
  if (interaction.type === INTERACTION_CALLED && path.length === 0 && interaction.args[0]) {
8177
7894
  // args[0] is the "this" argument
8178
- this.scope.thisVariable.addArgumentValue(interaction.args[0]);
7895
+ this.scope.thisVariable.addEntityToBeDeoptimized(interaction.args[0]);
8179
7896
  }
8180
7897
  }
8181
7898
  hasEffects(context) {
7899
+ if (!this.deoptimized)
7900
+ this.applyDeoptimizations();
8182
7901
  if (this.annotationNoSideEffects) {
8183
7902
  return false;
8184
7903
  }
8185
7904
  return !!this.id?.hasEffects(context);
8186
7905
  }
8187
7906
  hasEffectsOnInteractionAtPath(path, interaction, context) {
8188
- if (this.annotationNoSideEffects &&
8189
- path.length === 0 &&
8190
- interaction.type === INTERACTION_CALLED) {
8191
- return false;
8192
- }
8193
- if (super.hasEffectsOnInteractionAtPath(path, interaction, context)) {
7907
+ if (super.hasEffectsOnInteractionAtPath(path, interaction, context))
8194
7908
  return true;
7909
+ if (this.annotationNoSideEffects) {
7910
+ return false;
8195
7911
  }
8196
- if (path.length === 0 && interaction.type === INTERACTION_CALLED) {
7912
+ if (interaction.type === INTERACTION_CALLED) {
8197
7913
  const thisInit = context.replacedVariableInits.get(this.scope.thisVariable);
8198
7914
  context.replacedVariableInits.set(this.scope.thisVariable, interaction.withNew ? this.constructedEntity : UNKNOWN_EXPRESSION);
8199
7915
  const { brokenFlow, ignore, replacedVariableInits } = context;
@@ -8204,10 +7920,8 @@ class FunctionNode extends FunctionBase {
8204
7920
  returnYield: true,
8205
7921
  this: interaction.withNew
8206
7922
  };
8207
- if (this.body.hasEffects(context)) {
8208
- this.hasCachedEffects = true;
7923
+ if (this.body.hasEffects(context))
8209
7924
  return true;
8210
- }
8211
7925
  context.brokenFlow = brokenFlow;
8212
7926
  if (thisInit) {
8213
7927
  replacedVariableInits.set(this.scope.thisVariable, thisInit);
@@ -8221,7 +7935,7 @@ class FunctionNode extends FunctionBase {
8221
7935
  }
8222
7936
  include(context, includeChildrenRecursively) {
8223
7937
  super.include(context, includeChildrenRecursively);
8224
- this.id?.include(context);
7938
+ this.id?.include();
8225
7939
  const hasArguments = this.scope.argumentsVariable.included;
8226
7940
  for (const parameter of this.params) {
8227
7941
  if (!(parameter instanceof Identifier) || hasArguments) {
@@ -8229,18 +7943,12 @@ class FunctionNode extends FunctionBase {
8229
7943
  }
8230
7944
  }
8231
7945
  }
8232
- includeNode(context) {
8233
- this.included = true;
8234
- const hasArguments = this.scope.argumentsVariable.included;
8235
- for (const parameter of this.params) {
8236
- if (!(parameter instanceof Identifier) || hasArguments) {
8237
- parameter.includePath(UNKNOWN_PATH, context);
8238
- }
8239
- }
8240
- }
8241
7946
  initialise() {
8242
7947
  super.initialise();
8243
- this.id?.declare('function', EMPTY_PATH, this);
7948
+ this.id?.declare('function', this);
7949
+ }
7950
+ addArgumentToBeDeoptimized(argument) {
7951
+ this.scope.argumentsVariable.addArgumentToBeDeoptimized(argument);
8244
7952
  }
8245
7953
  getObjectEntity() {
8246
7954
  if (this.objectEntity !== null) {
@@ -8290,16 +7998,11 @@ function getFunctionIdInsertPosition(code, start) {
8290
7998
  }
8291
7999
  class ExportDefaultDeclaration extends NodeBase {
8292
8000
  include(context, includeChildrenRecursively) {
8293
- this.included = true;
8294
- this.declaration.include(context, includeChildrenRecursively);
8001
+ super.include(context, includeChildrenRecursively);
8295
8002
  if (includeChildrenRecursively) {
8296
- this.scope.context.includeVariableInModule(this.variable, UNKNOWN_PATH, context);
8003
+ this.scope.context.includeVariableInModule(this.variable);
8297
8004
  }
8298
8005
  }
8299
- includePath(path, context) {
8300
- this.included = true;
8301
- this.declaration.includePath(path, context);
8302
- }
8303
8006
  initialise() {
8304
8007
  super.initialise();
8305
8008
  const declaration = this.declaration;
@@ -8344,6 +8047,7 @@ class ExportDefaultDeclaration extends NodeBase {
8344
8047
  }
8345
8048
  this.declaration.render(code, options);
8346
8049
  }
8050
+ applyDeoptimizations() { }
8347
8051
  renderNamedDeclaration(code, declarationStart, idInsertPosition, options) {
8348
8052
  const { exportNamesByVariable, format, snippets: { getPropertyAccess } } = options;
8349
8053
  const name = this.variable.getName(getPropertyAccess);
@@ -8374,8 +8078,6 @@ class ExportDefaultDeclaration extends NodeBase {
8374
8078
  }
8375
8079
  }
8376
8080
  ExportDefaultDeclaration.prototype.needsBoundaries = true;
8377
- ExportDefaultDeclaration.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
8378
- ExportDefaultDeclaration.prototype.applyDeoptimizations = doNotDeoptimize;
8379
8081
 
8380
8082
  const needsEscapeRegEx = /[\n\r'\\\u2028\u2029]/;
8381
8083
  const quoteNewlineRegEx = /([\n\r'\u2028\u2029])/g;
@@ -8645,7 +8347,6 @@ class Literal extends NodeBase {
8645
8347
  }
8646
8348
  }
8647
8349
  }
8648
- Literal.prototype.includeNode = onlyIncludeSelf;
8649
8350
 
8650
8351
  function getChainElementLiteralValueAtPath(element, object, path, recursionTracker, origin) {
8651
8352
  if ('getLiteralValueAtPathAsChainElement' in object) {
@@ -8661,6 +8362,8 @@ function getChainElementLiteralValueAtPath(element, object, path, recursionTrack
8661
8362
  return element.getLiteralValueAtPath(path, recursionTracker, origin);
8662
8363
  }
8663
8364
 
8365
+ // To avoid infinite recursions
8366
+ const MAX_PATH_DEPTH = 7;
8664
8367
  function getResolvablePropertyKey(memberExpression) {
8665
8368
  return memberExpression.computed
8666
8369
  ? getResolvableComputedPropertyKey(memberExpression.property)
@@ -8759,27 +8462,18 @@ class MemberExpression extends NodeBase {
8759
8462
  }
8760
8463
  else if (!this.isUndefined) {
8761
8464
  if (path.length < MAX_PATH_DEPTH) {
8762
- this.object.deoptimizeArgumentsOnInteractionAtPath(interaction, this.propertyKey === UnknownKey ? UNKNOWN_PATH : [this.propertyKey, ...path], recursionTracker);
8465
+ this.object.deoptimizeArgumentsOnInteractionAtPath(interaction, [this.getPropertyKey(), ...path], recursionTracker);
8763
8466
  }
8764
8467
  else {
8765
8468
  deoptimizeInteraction(interaction);
8766
8469
  }
8767
8470
  }
8768
8471
  }
8769
- deoptimizeAssignment(destructuredInitPath, init) {
8770
- this.deoptimizePath(EMPTY_PATH);
8771
- init.deoptimizePath([...destructuredInitPath, UnknownKey]);
8772
- }
8773
8472
  deoptimizeCache() {
8774
- if (this.propertyKey === this.dynamicPropertyKey)
8775
- return;
8776
8473
  const { expressionsToBeDeoptimized, object } = this;
8777
8474
  this.expressionsToBeDeoptimized = parseAst_js.EMPTY_ARRAY;
8778
- this.dynamicPropertyKey = this.propertyKey;
8475
+ this.propertyKey = UnknownKey;
8779
8476
  object.deoptimizePath(UNKNOWN_PATH);
8780
- if (this.included) {
8781
- object.includePath(UNKNOWN_PATH, createInclusionContext());
8782
- }
8783
8477
  for (const expression of expressionsToBeDeoptimized) {
8784
8478
  expression.deoptimizeCache();
8785
8479
  }
@@ -8790,13 +8484,11 @@ class MemberExpression extends NodeBase {
8790
8484
  if (this.variable) {
8791
8485
  this.variable.deoptimizePath(path);
8792
8486
  }
8793
- else if (!this.isUndefined) {
8794
- const { propertyKey } = this;
8487
+ else if (!this.isUndefined && path.length < MAX_PATH_DEPTH) {
8488
+ const propertyKey = this.getPropertyKey();
8795
8489
  this.object.deoptimizePath([
8796
8490
  propertyKey === UnknownKey ? UnknownNonAccessorKey : propertyKey,
8797
- ...(path.length < MAX_PATH_DEPTH
8798
- ? path
8799
- : [...path.slice(0, MAX_PATH_DEPTH), UnknownKey])
8491
+ ...path
8800
8492
  ]);
8801
8493
  }
8802
8494
  }
@@ -8807,11 +8499,9 @@ class MemberExpression extends NodeBase {
8807
8499
  if (this.isUndefined) {
8808
8500
  return undefined;
8809
8501
  }
8810
- const propertyKey = this.getDynamicPropertyKey();
8811
- if (propertyKey !== UnknownKey && path.length < MAX_PATH_DEPTH) {
8812
- if (propertyKey !== this.propertyKey)
8813
- this.expressionsToBeDeoptimized.push(origin);
8814
- return this.object.getLiteralValueAtPath([propertyKey, ...path], recursionTracker, origin);
8502
+ if (this.propertyKey !== UnknownKey && path.length < MAX_PATH_DEPTH) {
8503
+ this.expressionsToBeDeoptimized.push(origin);
8504
+ return this.object.getLiteralValueAtPath([this.getPropertyKey(), ...path], recursionTracker, origin);
8815
8505
  }
8816
8506
  return UnknownValue;
8817
8507
  }
@@ -8831,11 +8521,9 @@ class MemberExpression extends NodeBase {
8831
8521
  if (this.isUndefined) {
8832
8522
  return [UNDEFINED_EXPRESSION, false];
8833
8523
  }
8834
- const propertyKey = this.getDynamicPropertyKey();
8835
- if (propertyKey !== UnknownKey && path.length < MAX_PATH_DEPTH) {
8836
- if (propertyKey !== this.propertyKey)
8837
- this.expressionsToBeDeoptimized.push(origin);
8838
- return this.object.getReturnExpressionWhenCalledAtPath([propertyKey, ...path], interaction, recursionTracker, origin);
8524
+ if (this.propertyKey !== UnknownKey && path.length < MAX_PATH_DEPTH) {
8525
+ this.expressionsToBeDeoptimized.push(origin);
8526
+ return this.object.getReturnExpressionWhenCalledAtPath([this.getPropertyKey(), ...path], interaction, recursionTracker, origin);
8839
8527
  }
8840
8528
  return UNKNOWN_RETURN_EXPRESSION;
8841
8529
  }
@@ -8881,45 +8569,14 @@ class MemberExpression extends NodeBase {
8881
8569
  return true;
8882
8570
  }
8883
8571
  if (path.length < MAX_PATH_DEPTH) {
8884
- return this.object.hasEffectsOnInteractionAtPath([this.getDynamicPropertyKey(), ...path], interaction, context);
8572
+ return this.object.hasEffectsOnInteractionAtPath([this.getPropertyKey(), ...path], interaction, context);
8885
8573
  }
8886
8574
  return true;
8887
8575
  }
8888
- hasEffectsWhenDestructuring(context, destructuredInitPath, init) {
8889
- return (destructuredInitPath.length > 0 &&
8890
- init.hasEffectsOnInteractionAtPath(destructuredInitPath, NODE_INTERACTION_UNKNOWN_ACCESS, context));
8891
- }
8892
8576
  include(context, includeChildrenRecursively) {
8893
- if (!this.included)
8894
- this.includeNode(context);
8895
- this.object.include(context, includeChildrenRecursively);
8896
- this.property.include(context, includeChildrenRecursively);
8897
- }
8898
- includeNode(context) {
8899
- this.included = true;
8900
8577
  if (!this.deoptimized)
8901
8578
  this.applyDeoptimizations();
8902
- if (this.variable) {
8903
- this.scope.context.includeVariableInModule(this.variable, EMPTY_PATH, context);
8904
- }
8905
- else if (!this.isUndefined) {
8906
- this.object.includePath([this.propertyKey], context);
8907
- }
8908
- }
8909
- includePath(path, context) {
8910
- if (!this.included)
8911
- this.includeNode(context);
8912
- if (this.variable) {
8913
- this.variable?.includePath(path, context);
8914
- }
8915
- else if (!this.isUndefined) {
8916
- this.object.includePath([
8917
- this.propertyKey,
8918
- ...(path.length < MAX_PATH_DEPTH
8919
- ? path
8920
- : [...path.slice(0, MAX_PATH_DEPTH), UnknownKey])
8921
- ], context);
8922
- }
8579
+ this.includeProperties(context, includeChildrenRecursively);
8923
8580
  }
8924
8581
  includeAsAssignmentTarget(context, includeChildrenRecursively, deoptimizeAccess) {
8925
8582
  if (!this.assignmentDeoptimized)
@@ -8928,34 +8585,20 @@ class MemberExpression extends NodeBase {
8928
8585
  this.include(context, includeChildrenRecursively);
8929
8586
  }
8930
8587
  else {
8931
- if (!this.included)
8932
- this.includeNode(context);
8933
- this.object.include(context, includeChildrenRecursively);
8934
- this.property.include(context, includeChildrenRecursively);
8588
+ this.includeProperties(context, includeChildrenRecursively);
8935
8589
  }
8936
8590
  }
8937
- includeCallArguments(context, interaction) {
8591
+ includeCallArguments(context, parameters) {
8938
8592
  if (this.variable) {
8939
- this.variable.includeCallArguments(context, interaction);
8593
+ this.variable.includeCallArguments(context, parameters);
8940
8594
  }
8941
8595
  else {
8942
- super.includeCallArguments(context, interaction);
8943
- }
8944
- }
8945
- includeDestructuredIfNecessary(context, destructuredInitPath, init) {
8946
- if ((this.included ||=
8947
- destructuredInitPath.length > 0 &&
8948
- !context.brokenFlow &&
8949
- init.hasEffectsOnInteractionAtPath(destructuredInitPath, NODE_INTERACTION_UNKNOWN_ACCESS, createHasEffectsContext()))) {
8950
- init.include(context, false);
8951
- return true;
8596
+ super.includeCallArguments(context, parameters);
8952
8597
  }
8953
- return false;
8954
8598
  }
8955
8599
  initialise() {
8956
8600
  super.initialise();
8957
- this.dynamicPropertyKey = getResolvablePropertyKey(this);
8958
- this.propertyKey = this.dynamicPropertyKey === null ? UnknownKey : this.dynamicPropertyKey;
8601
+ this.propertyKey = getResolvablePropertyKey(this);
8959
8602
  this.accessInteraction = { args: [this.object], type: INTERACTION_ACCESSED };
8960
8603
  }
8961
8604
  render(code, options, { renderedParentType, isCalleeOfRenderedParent, renderedSurroundingElement } = parseAst_js.BLANK) {
@@ -8992,7 +8635,8 @@ class MemberExpression extends NodeBase {
8992
8635
  this.bound &&
8993
8636
  propertyReadSideEffects &&
8994
8637
  !(this.variable || this.isUndefined)) {
8995
- this.object.deoptimizeArgumentsOnInteractionAtPath(this.accessInteraction, [this.propertyKey], SHARED_RECURSION_TRACKER);
8638
+ const propertyKey = this.getPropertyKey();
8639
+ this.object.deoptimizeArgumentsOnInteractionAtPath(this.accessInteraction, [propertyKey], SHARED_RECURSION_TRACKER);
8996
8640
  this.scope.context.requestTreeshakingPass();
8997
8641
  }
8998
8642
  if (this.variable) {
@@ -9009,7 +8653,7 @@ class MemberExpression extends NodeBase {
9009
8653
  this.bound &&
9010
8654
  propertyReadSideEffects &&
9011
8655
  !(this.variable || this.isUndefined)) {
9012
- this.object.deoptimizeArgumentsOnInteractionAtPath(this.assignmentInteraction, [this.propertyKey], SHARED_RECURSION_TRACKER);
8656
+ this.object.deoptimizeArgumentsOnInteractionAtPath(this.assignmentInteraction, [this.getPropertyKey()], SHARED_RECURSION_TRACKER);
9013
8657
  this.scope.context.requestTreeshakingPass();
9014
8658
  }
9015
8659
  }
@@ -9018,24 +8662,24 @@ class MemberExpression extends NodeBase {
9018
8662
  const variable = this.scope.findVariable(this.object.name);
9019
8663
  if (variable.isNamespace) {
9020
8664
  if (this.variable) {
9021
- this.scope.context.includeVariableInModule(this.variable, UNKNOWN_PATH, createInclusionContext());
8665
+ this.scope.context.includeVariableInModule(this.variable);
9022
8666
  }
9023
8667
  this.scope.context.log(parseAst_js.LOGLEVEL_WARN, parseAst_js.logIllegalImportReassignment(this.object.name, this.scope.context.module.id), this.start);
9024
8668
  }
9025
8669
  }
9026
8670
  }
9027
- getDynamicPropertyKey() {
9028
- if (this.dynamicPropertyKey === null) {
9029
- this.dynamicPropertyKey = this.propertyKey;
8671
+ getPropertyKey() {
8672
+ if (this.propertyKey === null) {
8673
+ this.propertyKey = UnknownKey;
9030
8674
  const value = this.property.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, this);
9031
- return (this.dynamicPropertyKey =
8675
+ return (this.propertyKey =
9032
8676
  value === SymbolToStringTag
9033
8677
  ? value
9034
8678
  : typeof value === 'symbol'
9035
8679
  ? UnknownKey
9036
8680
  : String(value));
9037
8681
  }
9038
- return this.dynamicPropertyKey;
8682
+ return this.propertyKey;
9039
8683
  }
9040
8684
  hasAccessEffect(context) {
9041
8685
  const { propertyReadSideEffects } = this.scope.context.options
@@ -9043,7 +8687,17 @@ class MemberExpression extends NodeBase {
9043
8687
  return (!(this.variable || this.isUndefined) &&
9044
8688
  propertyReadSideEffects &&
9045
8689
  (propertyReadSideEffects === 'always' ||
9046
- this.object.hasEffectsOnInteractionAtPath([this.getDynamicPropertyKey()], this.accessInteraction, context)));
8690
+ this.object.hasEffectsOnInteractionAtPath([this.getPropertyKey()], this.accessInteraction, context)));
8691
+ }
8692
+ includeProperties(context, includeChildrenRecursively) {
8693
+ if (!this.included) {
8694
+ this.included = true;
8695
+ if (this.variable) {
8696
+ this.scope.context.includeVariableInModule(this.variable);
8697
+ }
8698
+ }
8699
+ this.object.include(context, includeChildrenRecursively);
8700
+ this.property.include(context, includeChildrenRecursively);
9047
8701
  }
9048
8702
  }
9049
8703
  function resolveNamespaceVariables(baseVariable, path, astContext) {
@@ -9087,20 +8741,18 @@ class MetaProperty extends NodeBase {
9087
8741
  return path.length > 1 || type !== INTERACTION_ACCESSED;
9088
8742
  }
9089
8743
  include() {
9090
- if (!this.included)
9091
- this.includeNode();
9092
- }
9093
- includeNode() {
9094
- this.included = true;
9095
- if (this.meta.name === IMPORT) {
9096
- this.scope.context.addImportMeta(this);
9097
- const parent = this.parent;
9098
- const metaProperty = (this.metaProperty =
9099
- parent instanceof MemberExpression && typeof parent.propertyKey === 'string'
9100
- ? parent.propertyKey
9101
- : null);
9102
- if (metaProperty?.startsWith(FILE_PREFIX)) {
9103
- this.referenceId = metaProperty.slice(FILE_PREFIX.length);
8744
+ if (!this.included) {
8745
+ this.included = true;
8746
+ if (this.meta.name === IMPORT) {
8747
+ this.scope.context.addImportMeta(this);
8748
+ const parent = this.parent;
8749
+ const metaProperty = (this.metaProperty =
8750
+ parent instanceof MemberExpression && typeof parent.propertyKey === 'string'
8751
+ ? parent.propertyKey
8752
+ : null);
8753
+ if (metaProperty?.startsWith(FILE_PREFIX)) {
8754
+ this.referenceId = metaProperty.slice(FILE_PREFIX.length);
8755
+ }
9104
8756
  }
9105
8757
  }
9106
8758
  }
@@ -9207,7 +8859,7 @@ class UndefinedVariable extends Variable {
9207
8859
 
9208
8860
  class ExportDefaultVariable extends LocalVariable {
9209
8861
  constructor(name, exportDefaultDeclaration, context) {
9210
- super(name, exportDefaultDeclaration, exportDefaultDeclaration.declaration, EMPTY_PATH, context, 'other');
8862
+ super(name, exportDefaultDeclaration, exportDefaultDeclaration.declaration, context, 'other');
9211
8863
  this.hasId = false;
9212
8864
  this.originalId = null;
9213
8865
  this.originalVariable = null;
@@ -9356,8 +9008,8 @@ class NamespaceVariable extends Variable {
9356
9008
  return (!memberVariable ||
9357
9009
  memberVariable.hasEffectsOnInteractionAtPath(path.slice(1), interaction, context));
9358
9010
  }
9359
- includePath(path, context) {
9360
- super.includePath(path, context);
9011
+ include() {
9012
+ super.include();
9361
9013
  this.context.includeAllExports();
9362
9014
  }
9363
9015
  prepare(accessedGlobalsByScope) {
@@ -9450,9 +9102,9 @@ class SyntheticNamedExportVariable extends Variable {
9450
9102
  getName(getPropertyAccess) {
9451
9103
  return `${this.syntheticNamespace.getName(getPropertyAccess)}${getPropertyAccess(this.name)}`;
9452
9104
  }
9453
- includePath(path, context) {
9454
- super.includePath(path, context);
9455
- this.context.includeVariableInModule(this.syntheticNamespace, path, context);
9105
+ include() {
9106
+ super.include();
9107
+ this.context.includeVariableInModule(this.syntheticNamespace);
9456
9108
  }
9457
9109
  setRenderNames(baseName, name) {
9458
9110
  super.setRenderNames(baseName, name);
@@ -12628,37 +12280,21 @@ class ArrayPattern extends NodeBase {
12628
12280
  element?.addExportedVariables(variables, exportNamesByVariable);
12629
12281
  }
12630
12282
  }
12631
- declare(kind, destructuredInitPath, init) {
12283
+ declare(kind) {
12632
12284
  const variables = [];
12633
- const includedPatternPath = getIncludedPatternPath(destructuredInitPath);
12634
12285
  for (const element of this.elements) {
12635
12286
  if (element !== null) {
12636
- variables.push(...element.declare(kind, includedPatternPath, init));
12287
+ variables.push(...element.declare(kind, UNKNOWN_EXPRESSION));
12637
12288
  }
12638
12289
  }
12639
12290
  return variables;
12640
12291
  }
12641
- deoptimizeAssignment(destructuredInitPath, init) {
12642
- const includedPatternPath = getIncludedPatternPath(destructuredInitPath);
12643
- for (const element of this.elements) {
12644
- element?.deoptimizeAssignment(includedPatternPath, init);
12645
- }
12646
- }
12647
12292
  // Patterns can only be deoptimized at the empty path at the moment
12648
12293
  deoptimizePath() {
12649
12294
  for (const element of this.elements) {
12650
12295
  element?.deoptimizePath(EMPTY_PATH);
12651
12296
  }
12652
12297
  }
12653
- hasEffectsWhenDestructuring(context, destructuredInitPath, init) {
12654
- const includedPatternPath = getIncludedPatternPath(destructuredInitPath);
12655
- for (const element of this.elements) {
12656
- if (element?.hasEffectsWhenDestructuring(context, includedPatternPath, init)) {
12657
- return true;
12658
- }
12659
- }
12660
- return false;
12661
- }
12662
12298
  // Patterns are only checked at the empty path at the moment
12663
12299
  hasEffectsOnInteractionAtPath(_path, interaction, context) {
12664
12300
  for (const element of this.elements) {
@@ -12667,38 +12303,12 @@ class ArrayPattern extends NodeBase {
12667
12303
  }
12668
12304
  return false;
12669
12305
  }
12670
- includeDestructuredIfNecessary(context, destructuredInitPath, init) {
12671
- let included = false;
12672
- const includedPatternPath = getIncludedPatternPath(destructuredInitPath);
12673
- for (const element of this.elements) {
12674
- if (element) {
12675
- element.included ||= included;
12676
- included =
12677
- element.includeDestructuredIfNecessary(context, includedPatternPath, init) || included;
12678
- }
12679
- }
12680
- if (included) {
12681
- // This is necessary so that if any pattern element is included, all are
12682
- // included for proper deconflicting
12683
- for (const element of this.elements) {
12684
- if (element && !element.included) {
12685
- element.included = true;
12686
- element.includeDestructuredIfNecessary(context, includedPatternPath, init);
12687
- }
12688
- }
12689
- }
12690
- return (this.included ||= included);
12691
- }
12692
12306
  markDeclarationReached() {
12693
12307
  for (const element of this.elements) {
12694
12308
  element?.markDeclarationReached();
12695
12309
  }
12696
12310
  }
12697
12311
  }
12698
- ArrayPattern.prototype.includeNode = onlyIncludeSelf;
12699
- const getIncludedPatternPath = (destructuredInitPath) => destructuredInitPath.at(-1) === UnknownKey
12700
- ? destructuredInitPath
12701
- : [...destructuredInitPath, UnknownInteger];
12702
12312
 
12703
12313
  class ArrowFunctionExpression extends FunctionBase {
12704
12314
  constructor() {
@@ -12715,17 +12325,17 @@ class ArrowFunctionExpression extends FunctionBase {
12715
12325
  this.scope = new ReturnValueScope(parentScope, false);
12716
12326
  }
12717
12327
  hasEffects() {
12328
+ if (!this.deoptimized)
12329
+ this.applyDeoptimizations();
12718
12330
  return false;
12719
12331
  }
12720
12332
  hasEffectsOnInteractionAtPath(path, interaction, context) {
12721
- if (this.annotationNoSideEffects &&
12722
- path.length === 0 &&
12723
- interaction.type === INTERACTION_CALLED) {
12724
- return false;
12725
- }
12726
12333
  if (super.hasEffectsOnInteractionAtPath(path, interaction, context)) {
12727
12334
  return true;
12728
12335
  }
12336
+ if (this.annotationNoSideEffects) {
12337
+ return false;
12338
+ }
12729
12339
  if (interaction.type === INTERACTION_CALLED) {
12730
12340
  const { ignore, brokenFlow } = context;
12731
12341
  context.ignore = {
@@ -12755,15 +12365,6 @@ class ArrowFunctionExpression extends FunctionBase {
12755
12365
  }
12756
12366
  }
12757
12367
  }
12758
- includeNode(context) {
12759
- this.included = true;
12760
- this.body.includePath(UNKNOWN_PATH, context);
12761
- for (const parameter of this.params) {
12762
- if (!(parameter instanceof Identifier)) {
12763
- parameter.includePath(UNKNOWN_PATH, context);
12764
- }
12765
- }
12766
- }
12767
12368
  getObjectEntity() {
12768
12369
  if (this.objectEntity !== null) {
12769
12370
  return this.objectEntity;
@@ -12783,18 +12384,13 @@ class ObjectPattern extends NodeBase {
12783
12384
  }
12784
12385
  }
12785
12386
  }
12786
- declare(kind, destructuredInitPath, init) {
12387
+ declare(kind, init) {
12787
12388
  const variables = [];
12788
12389
  for (const property of this.properties) {
12789
- variables.push(...property.declare(kind, destructuredInitPath, init));
12390
+ variables.push(...property.declare(kind, init));
12790
12391
  }
12791
12392
  return variables;
12792
12393
  }
12793
- deoptimizeAssignment(destructuredInitPath, init) {
12794
- for (const property of this.properties) {
12795
- property.deoptimizeAssignment(destructuredInitPath, init);
12796
- }
12797
- }
12798
12394
  deoptimizePath(path) {
12799
12395
  if (path.length === 0) {
12800
12396
  for (const property of this.properties) {
@@ -12812,46 +12408,12 @@ class ObjectPattern extends NodeBase {
12812
12408
  }
12813
12409
  return false;
12814
12410
  }
12815
- hasEffectsWhenDestructuring(context, destructuredInitPath, init) {
12816
- for (const property of this.properties) {
12817
- if (property.hasEffectsWhenDestructuring(context, destructuredInitPath, init))
12818
- return true;
12819
- }
12820
- return false;
12821
- }
12822
- includeDestructuredIfNecessary(context, destructuredInitPath, init) {
12823
- let included = false;
12824
- for (const property of this.properties) {
12825
- included =
12826
- property.includeDestructuredIfNecessary(context, destructuredInitPath, init) || included;
12827
- }
12828
- return (this.included ||= included);
12829
- }
12830
12411
  markDeclarationReached() {
12831
12412
  for (const property of this.properties) {
12832
12413
  property.markDeclarationReached();
12833
12414
  }
12834
12415
  }
12835
- render(code, options) {
12836
- if (this.properties.length > 0) {
12837
- const separatedNodes = getCommaSeparatedNodesWithBoundaries(this.properties, code, this.start + 1, this.end - 1);
12838
- let lastSeparatorPos = null;
12839
- for (const { node, separator, start, end } of separatedNodes) {
12840
- if (!node.included) {
12841
- treeshakeNode(node, code, start, end);
12842
- continue;
12843
- }
12844
- lastSeparatorPos = separator;
12845
- node.render(code, options);
12846
- }
12847
- if (lastSeparatorPos) {
12848
- code.remove(lastSeparatorPos, this.end - 1);
12849
- }
12850
- }
12851
- }
12852
12416
  }
12853
- ObjectPattern.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
12854
- ObjectPattern.prototype.applyDeoptimizations = doNotDeoptimize;
12855
12417
 
12856
12418
  class AssignmentExpression extends NodeBase {
12857
12419
  hasEffects(context) {
@@ -12860,9 +12422,7 @@ class AssignmentExpression extends NodeBase {
12860
12422
  this.applyDeoptimizations();
12861
12423
  // MemberExpressions do not access the property before assignments if the
12862
12424
  // operator is '='.
12863
- return (right.hasEffects(context) ||
12864
- left.hasEffectsAsAssignmentTarget(context, operator !== '=') ||
12865
- this.left.hasEffectsWhenDestructuring?.(context, EMPTY_PATH, right));
12425
+ return (right.hasEffects(context) || left.hasEffectsAsAssignmentTarget(context, operator !== '='));
12866
12426
  }
12867
12427
  hasEffectsOnInteractionAtPath(path, interaction, context) {
12868
12428
  return this.right.hasEffectsOnInteractionAtPath(path, interaction, context);
@@ -12871,24 +12431,15 @@ class AssignmentExpression extends NodeBase {
12871
12431
  const { deoptimized, left, right, operator } = this;
12872
12432
  if (!deoptimized)
12873
12433
  this.applyDeoptimizations();
12874
- if (!this.included)
12875
- this.includeNode(context);
12876
- const hasEffectsContext = createHasEffectsContext();
12434
+ this.included = true;
12877
12435
  if (includeChildrenRecursively ||
12878
12436
  operator !== '=' ||
12879
12437
  left.included ||
12880
- left.hasEffectsAsAssignmentTarget(hasEffectsContext, false) ||
12881
- left.hasEffectsWhenDestructuring?.(hasEffectsContext, EMPTY_PATH, right)) {
12438
+ left.hasEffectsAsAssignmentTarget(createHasEffectsContext(), false)) {
12882
12439
  left.includeAsAssignmentTarget(context, includeChildrenRecursively, operator !== '=');
12883
12440
  }
12884
12441
  right.include(context, includeChildrenRecursively);
12885
12442
  }
12886
- includeNode(context) {
12887
- this.included = true;
12888
- if (!this.deoptimized)
12889
- this.applyDeoptimizations();
12890
- this.right.includePath(UNKNOWN_PATH, context);
12891
- }
12892
12443
  initialise() {
12893
12444
  super.initialise();
12894
12445
  if (this.left instanceof Identifier) {
@@ -12949,7 +12500,8 @@ class AssignmentExpression extends NodeBase {
12949
12500
  }
12950
12501
  applyDeoptimizations() {
12951
12502
  this.deoptimized = true;
12952
- this.left.deoptimizeAssignment(EMPTY_PATH, this.right);
12503
+ this.left.deoptimizePath(EMPTY_PATH);
12504
+ this.right.deoptimizePath(UNKNOWN_PATH);
12953
12505
  this.scope.context.requestTreeshakingPass();
12954
12506
  }
12955
12507
  }
@@ -12958,11 +12510,8 @@ class AssignmentPattern extends NodeBase {
12958
12510
  addExportedVariables(variables, exportNamesByVariable) {
12959
12511
  this.left.addExportedVariables(variables, exportNamesByVariable);
12960
12512
  }
12961
- declare(kind, destructuredInitPath, init) {
12962
- return this.left.declare(kind, destructuredInitPath, init);
12963
- }
12964
- deoptimizeAssignment(destructuredInitPath, init) {
12965
- this.left.deoptimizeAssignment(destructuredInitPath, init);
12513
+ declare(kind, init) {
12514
+ return this.left.declare(kind, init);
12966
12515
  }
12967
12516
  deoptimizePath(path) {
12968
12517
  if (path.length === 0) {
@@ -12972,29 +12521,6 @@ class AssignmentPattern extends NodeBase {
12972
12521
  hasEffectsOnInteractionAtPath(path, interaction, context) {
12973
12522
  return (path.length > 0 || this.left.hasEffectsOnInteractionAtPath(EMPTY_PATH, interaction, context));
12974
12523
  }
12975
- hasEffectsWhenDestructuring(context, destructuredInitPath, init) {
12976
- return this.left.hasEffectsWhenDestructuring(context, destructuredInitPath, init);
12977
- }
12978
- includeDestructuredIfNecessary(context, destructuredInitPath, init) {
12979
- let included = this.left.includeDestructuredIfNecessary(context, destructuredInitPath, init) ||
12980
- this.included;
12981
- if ((included ||= this.right.shouldBeIncluded(context))) {
12982
- this.right.include(context, false);
12983
- if (!this.left.included) {
12984
- this.left.included = true;
12985
- // Unfortunately, we need to include the left side again now, so that
12986
- // any declared variables are properly included.
12987
- this.left.includeDestructuredIfNecessary(context, destructuredInitPath, init);
12988
- }
12989
- }
12990
- return (this.included = included);
12991
- }
12992
- includeNode(context) {
12993
- this.included = true;
12994
- if (!this.deoptimized)
12995
- this.applyDeoptimizations();
12996
- this.right.includePath(UNKNOWN_PATH, context);
12997
- }
12998
12524
  markDeclarationReached() {
12999
12525
  this.left.markDeclarationReached();
13000
12526
  }
@@ -13017,34 +12543,22 @@ class AwaitExpression extends NodeBase {
13017
12543
  return true;
13018
12544
  }
13019
12545
  include(context, includeChildrenRecursively) {
13020
- if (!this.included)
13021
- this.includeNode(context);
13022
- this.argument.include(context, includeChildrenRecursively);
13023
- }
13024
- includeNode(context) {
13025
- this.included = true;
13026
12546
  if (!this.deoptimized)
13027
12547
  this.applyDeoptimizations();
13028
- checkTopLevelAwait: if (!this.scope.context.usesTopLevelAwait) {
13029
- let parent = this.parent;
13030
- do {
13031
- if (parent instanceof FunctionNode || parent instanceof ArrowFunctionExpression)
13032
- break checkTopLevelAwait;
13033
- } while ((parent = parent.parent));
13034
- this.scope.context.usesTopLevelAwait = true;
12548
+ if (!this.included) {
12549
+ this.included = true;
12550
+ checkTopLevelAwait: if (!this.scope.context.usesTopLevelAwait) {
12551
+ let parent = this.parent;
12552
+ do {
12553
+ if (parent instanceof FunctionNode || parent instanceof ArrowFunctionExpression)
12554
+ break checkTopLevelAwait;
12555
+ } while ((parent = parent.parent));
12556
+ this.scope.context.usesTopLevelAwait = true;
12557
+ }
13035
12558
  }
13036
- // Thenables need to be included
13037
- this.argument.includePath(THEN_PATH, context);
13038
- }
13039
- includePath(path, context) {
13040
- if (!this.deoptimized)
13041
- this.applyDeoptimizations();
13042
- if (!this.included)
13043
- this.includeNode(context);
13044
- this.argument.includePath(path, context);
12559
+ this.argument.include(context, includeChildrenRecursively);
13045
12560
  }
13046
12561
  }
13047
- const THEN_PATH = ['then'];
13048
12562
 
13049
12563
  const binaryOperators = {
13050
12564
  '!=': (left, right) => left != right,
@@ -13100,12 +12614,6 @@ class BinaryExpression extends NodeBase {
13100
12614
  hasEffectsOnInteractionAtPath(path, { type }) {
13101
12615
  return type !== INTERACTION_ACCESSED || path.length > 1;
13102
12616
  }
13103
- includeNode(context) {
13104
- this.included = true;
13105
- if (this.operator === 'in') {
13106
- this.right.includePath(UNKNOWN_PATH, context);
13107
- }
13108
- }
13109
12617
  removeAnnotations(code) {
13110
12618
  this.left.removeAnnotations(code);
13111
12619
  }
@@ -13114,7 +12622,6 @@ class BinaryExpression extends NodeBase {
13114
12622
  this.right.render(code, options);
13115
12623
  }
13116
12624
  }
13117
- BinaryExpression.prototype.applyDeoptimizations = doNotDeoptimize;
13118
12625
 
13119
12626
  class BreakStatement extends NodeBase {
13120
12627
  hasEffects(context) {
@@ -13134,7 +12641,7 @@ class BreakStatement extends NodeBase {
13134
12641
  include(context) {
13135
12642
  this.included = true;
13136
12643
  if (this.label) {
13137
- this.label.include(context);
12644
+ this.label.include();
13138
12645
  context.includedLabels.add(this.label.name);
13139
12646
  }
13140
12647
  else {
@@ -13143,8 +12650,6 @@ class BreakStatement extends NodeBase {
13143
12650
  context.brokenFlow = true;
13144
12651
  }
13145
12652
  }
13146
- BreakStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13147
- BreakStatement.prototype.applyDeoptimizations = doNotDeoptimize;
13148
12653
 
13149
12654
  function renderCallArguments(code, options, node) {
13150
12655
  if (node.arguments.length > 0) {
@@ -13331,14 +12836,10 @@ class CallExpression extends CallExpressionBase {
13331
12836
  this.callee.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.interaction, context)));
13332
12837
  }
13333
12838
  include(context, includeChildrenRecursively) {
13334
- if (!this.included)
13335
- this.includeNode(context);
12839
+ if (!this.deoptimized)
12840
+ this.applyDeoptimizations();
13336
12841
  if (includeChildrenRecursively) {
13337
- this.callee.include(context, true);
13338
- for (const argument of this.arguments) {
13339
- argument.includePath(UNKNOWN_PATH, context);
13340
- argument.include(context, true);
13341
- }
12842
+ super.include(context, includeChildrenRecursively);
13342
12843
  if (includeChildrenRecursively === INCLUDE_PARAMETERS &&
13343
12844
  this.callee instanceof Identifier &&
13344
12845
  this.callee.variable) {
@@ -13346,24 +12847,10 @@ class CallExpression extends CallExpressionBase {
13346
12847
  }
13347
12848
  }
13348
12849
  else {
13349
- // If the callee is a member expression and does not have a variable, its
13350
- // object will already be included via the first argument of the
13351
- // interaction in includeCallArguments. Including it again can lead to
13352
- // severe performance problems.
13353
- if (this.callee instanceof MemberExpression && !this.callee.variable) {
13354
- this.callee.property.include(context, false);
13355
- }
13356
- else {
13357
- this.callee.include(context, false);
13358
- }
13359
- this.callee.includeCallArguments(context, this.interaction);
12850
+ this.included = true;
12851
+ this.callee.include(context, false);
13360
12852
  }
13361
- }
13362
- includeNode(context) {
13363
- this.included = true;
13364
- if (!this.deoptimized)
13365
- this.applyDeoptimizations();
13366
- this.callee.includePath(UNKNOWN_PATH, context);
12853
+ this.callee.includeCallArguments(context, this.arguments);
13367
12854
  }
13368
12855
  initialise() {
13369
12856
  super.initialise();
@@ -13402,14 +12889,13 @@ class CatchClause extends NodeBase {
13402
12889
  this.type = type;
13403
12890
  if (param) {
13404
12891
  this.param = new (this.scope.context.getNodeConstructor(param.type))(this, this.scope).parseNode(param);
13405
- this.param.declare('parameter', EMPTY_PATH, UNKNOWN_EXPRESSION);
12892
+ this.param.declare('parameter', UNKNOWN_EXPRESSION);
13406
12893
  }
13407
12894
  this.body = new BlockStatement(this, this.scope.bodyScope).parseNode(body);
13408
12895
  return super.parseNode(esTreeNode);
13409
12896
  }
13410
12897
  }
13411
12898
  CatchClause.prototype.preventChildBlockScope = true;
13412
- CatchClause.prototype.includeNode = onlyIncludeSelf;
13413
12899
 
13414
12900
  class ChainExpression extends NodeBase {
13415
12901
  // deoptimizations are not relevant as we are not caching values
@@ -13421,22 +12907,17 @@ class ChainExpression extends NodeBase {
13421
12907
  hasEffects(context) {
13422
12908
  return this.expression.hasEffectsAsChainElement(context) === true;
13423
12909
  }
13424
- includePath(path, context) {
13425
- this.included = true;
13426
- this.expression.includePath(path, context);
13427
- }
13428
12910
  removeAnnotations(code) {
13429
12911
  this.expression.removeAnnotations(code);
13430
12912
  }
12913
+ applyDeoptimizations() { }
13431
12914
  }
13432
- ChainExpression.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13433
- ChainExpression.prototype.applyDeoptimizations = doNotDeoptimize;
13434
12915
 
13435
12916
  class ClassBodyScope extends ChildScope {
13436
12917
  constructor(parent, classNode) {
13437
12918
  const { context } = parent;
13438
12919
  super(parent, context);
13439
- this.variables.set('this', (this.thisVariable = new LocalVariable('this', null, classNode, EMPTY_PATH, context, 'other')));
12920
+ this.variables.set('this', (this.thisVariable = new LocalVariable('this', null, classNode, context, 'other')));
13440
12921
  this.instanceScope = new ChildScope(this, context);
13441
12922
  this.instanceScope.variables.set('this', new ThisVariable(context));
13442
12923
  }
@@ -13451,7 +12932,7 @@ class ClassBody extends NodeBase {
13451
12932
  }
13452
12933
  include(context, includeChildrenRecursively) {
13453
12934
  this.included = true;
13454
- this.scope.context.includeVariableInModule(this.scope.thisVariable, UNKNOWN_PATH, context);
12935
+ this.scope.context.includeVariableInModule(this.scope.thisVariable);
13455
12936
  for (const definition of this.body) {
13456
12937
  definition.include(context, includeChildrenRecursively);
13457
12938
  }
@@ -13464,9 +12945,8 @@ class ClassBody extends NodeBase {
13464
12945
  }
13465
12946
  return super.parseNode(esTreeNode);
13466
12947
  }
12948
+ applyDeoptimizations() { }
13467
12949
  }
13468
- ClassBody.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13469
- ClassBody.prototype.applyDeoptimizations = doNotDeoptimize;
13470
12950
 
13471
12951
  class ClassExpression extends ClassNode {
13472
12952
  render(code, options, { renderedSurroundingElement } = parseAst_js.BLANK) {
@@ -13537,9 +13017,6 @@ class ConditionalExpression extends NodeBase {
13537
13017
  const unusedBranch = this.usedBranch === this.consequent ? this.alternate : this.consequent;
13538
13018
  this.usedBranch = null;
13539
13019
  unusedBranch.deoptimizePath(UNKNOWN_PATH);
13540
- if (this.included) {
13541
- unusedBranch.includePath(UNKNOWN_PATH, createInclusionContext());
13542
- }
13543
13020
  const { expressionsToBeDeoptimized } = this;
13544
13021
  this.expressionsToBeDeoptimized = parseAst_js.EMPTY_ARRAY;
13545
13022
  for (const expression of expressionsToBeDeoptimized) {
@@ -13597,7 +13074,7 @@ class ConditionalExpression extends NodeBase {
13597
13074
  include(context, includeChildrenRecursively) {
13598
13075
  this.included = true;
13599
13076
  const usedBranch = this.getUsedBranch();
13600
- if (usedBranch === null || includeChildrenRecursively || this.test.shouldBeIncluded(context)) {
13077
+ if (includeChildrenRecursively || this.test.shouldBeIncluded(context) || usedBranch === null) {
13601
13078
  this.test.include(context, includeChildrenRecursively);
13602
13079
  this.consequent.include(context, includeChildrenRecursively);
13603
13080
  this.alternate.include(context, includeChildrenRecursively);
@@ -13606,38 +13083,27 @@ class ConditionalExpression extends NodeBase {
13606
13083
  usedBranch.include(context, includeChildrenRecursively);
13607
13084
  }
13608
13085
  }
13609
- includePath(path, context) {
13610
- this.included = true;
13611
- const usedBranch = this.getUsedBranch();
13612
- if (usedBranch === null || this.test.shouldBeIncluded(context)) {
13613
- this.consequent.includePath(path, context);
13614
- this.alternate.includePath(path, context);
13615
- }
13616
- else {
13617
- usedBranch.includePath(path, context);
13618
- }
13619
- }
13620
- includeCallArguments(context, interaction) {
13086
+ includeCallArguments(context, parameters) {
13621
13087
  const usedBranch = this.getUsedBranch();
13622
13088
  if (usedBranch) {
13623
- usedBranch.includeCallArguments(context, interaction);
13089
+ usedBranch.includeCallArguments(context, parameters);
13624
13090
  }
13625
13091
  else {
13626
- this.consequent.includeCallArguments(context, interaction);
13627
- this.alternate.includeCallArguments(context, interaction);
13092
+ this.consequent.includeCallArguments(context, parameters);
13093
+ this.alternate.includeCallArguments(context, parameters);
13628
13094
  }
13629
13095
  }
13630
13096
  removeAnnotations(code) {
13631
13097
  this.test.removeAnnotations(code);
13632
13098
  }
13633
13099
  render(code, options, { isCalleeOfRenderedParent, preventASI, renderedParentType, renderedSurroundingElement } = parseAst_js.BLANK) {
13100
+ const usedBranch = this.getUsedBranch();
13634
13101
  if (this.test.included) {
13635
13102
  this.test.render(code, options, { renderedSurroundingElement });
13636
13103
  this.consequent.render(code, options);
13637
13104
  this.alternate.render(code, options);
13638
13105
  }
13639
13106
  else {
13640
- const usedBranch = this.getUsedBranch();
13641
13107
  const colonPos = findFirstOccurrenceOutsideComment(code.original, ':', this.consequent.end);
13642
13108
  const inclusionStart = findNonWhiteSpace(code.original, (this.consequent.included
13643
13109
  ? findFirstOccurrenceOutsideComment(code.original, '?', this.test.end)
@@ -13669,8 +13135,6 @@ class ConditionalExpression extends NodeBase {
13669
13135
  : (this.usedBranch = testValue ? this.consequent : this.alternate);
13670
13136
  }
13671
13137
  }
13672
- ConditionalExpression.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13673
- ConditionalExpression.prototype.applyDeoptimizations = doNotDeoptimize;
13674
13138
 
13675
13139
  class ContinueStatement extends NodeBase {
13676
13140
  hasEffects(context) {
@@ -13690,7 +13154,7 @@ class ContinueStatement extends NodeBase {
13690
13154
  include(context) {
13691
13155
  this.included = true;
13692
13156
  if (this.label) {
13693
- this.label.include(context);
13157
+ this.label.include();
13694
13158
  context.includedLabels.add(this.label.name);
13695
13159
  }
13696
13160
  else {
@@ -13699,15 +13163,12 @@ class ContinueStatement extends NodeBase {
13699
13163
  context.brokenFlow = true;
13700
13164
  }
13701
13165
  }
13702
- ContinueStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13703
- ContinueStatement.prototype.applyDeoptimizations = doNotDeoptimize;
13704
13166
 
13705
13167
  class DebuggerStatement extends NodeBase {
13706
13168
  hasEffects() {
13707
13169
  return true;
13708
13170
  }
13709
13171
  }
13710
- DebuggerStatement.prototype.includeNode = onlyIncludeSelf;
13711
13172
 
13712
13173
  class Decorator extends NodeBase {
13713
13174
  hasEffects(context) {
@@ -13715,7 +13176,6 @@ class Decorator extends NodeBase {
13715
13176
  this.expression.hasEffectsOnInteractionAtPath(EMPTY_PATH, NODE_INTERACTION_UNKNOWN_CALL, context));
13716
13177
  }
13717
13178
  }
13718
- Decorator.prototype.includeNode = onlyIncludeSelf;
13719
13179
 
13720
13180
  function hasLoopBodyEffects(context, body) {
13721
13181
  const { brokenFlow, hasBreak, hasContinue, ignore } = context;
@@ -13755,15 +13215,12 @@ class DoWhileStatement extends NodeBase {
13755
13215
  includeLoopBody(context, this.body, includeChildrenRecursively);
13756
13216
  }
13757
13217
  }
13758
- DoWhileStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13759
- DoWhileStatement.prototype.applyDeoptimizations = doNotDeoptimize;
13760
13218
 
13761
13219
  class EmptyStatement extends NodeBase {
13762
13220
  hasEffects() {
13763
13221
  return false;
13764
13222
  }
13765
13223
  }
13766
- EmptyStatement.prototype.includeNode = onlyIncludeSelf;
13767
13224
 
13768
13225
  class ExportAllDeclaration extends NodeBase {
13769
13226
  hasEffects() {
@@ -13776,10 +13233,9 @@ class ExportAllDeclaration extends NodeBase {
13776
13233
  render(code, _options, nodeRenderOptions) {
13777
13234
  code.remove(nodeRenderOptions.start, nodeRenderOptions.end);
13778
13235
  }
13236
+ applyDeoptimizations() { }
13779
13237
  }
13780
13238
  ExportAllDeclaration.prototype.needsBoundaries = true;
13781
- ExportAllDeclaration.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13782
- ExportAllDeclaration.prototype.applyDeoptimizations = doNotDeoptimize;
13783
13239
 
13784
13240
  class ExportNamedDeclaration extends NodeBase {
13785
13241
  bind() {
@@ -13806,15 +13262,13 @@ class ExportNamedDeclaration extends NodeBase {
13806
13262
  this.declaration.render(code, options, { end, start });
13807
13263
  }
13808
13264
  }
13265
+ applyDeoptimizations() { }
13809
13266
  }
13810
13267
  ExportNamedDeclaration.prototype.needsBoundaries = true;
13811
- ExportNamedDeclaration.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13812
- ExportNamedDeclaration.prototype.applyDeoptimizations = doNotDeoptimize;
13813
13268
 
13814
13269
  class ExportSpecifier extends NodeBase {
13270
+ applyDeoptimizations() { }
13815
13271
  }
13816
- ExportSpecifier.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13817
- ExportSpecifier.prototype.applyDeoptimizations = doNotDeoptimize;
13818
13272
 
13819
13273
  class ForInStatement extends NodeBase {
13820
13274
  createScope(parentScope) {
@@ -13832,18 +13286,11 @@ class ForInStatement extends NodeBase {
13832
13286
  const { body, deoptimized, left, right } = this;
13833
13287
  if (!deoptimized)
13834
13288
  this.applyDeoptimizations();
13835
- if (!this.included)
13836
- this.includeNode(context);
13289
+ this.included = true;
13837
13290
  left.includeAsAssignmentTarget(context, includeChildrenRecursively || true, false);
13838
13291
  right.include(context, includeChildrenRecursively);
13839
13292
  includeLoopBody(context, body, includeChildrenRecursively);
13840
13293
  }
13841
- includeNode(context) {
13842
- this.included = true;
13843
- if (!this.deoptimized)
13844
- this.applyDeoptimizations();
13845
- this.right.includePath(UNKNOWN_PATH, context);
13846
- }
13847
13294
  initialise() {
13848
13295
  super.initialise();
13849
13296
  this.left.setAssignedValue(UNKNOWN_EXPRESSION);
@@ -13884,18 +13331,11 @@ class ForOfStatement extends NodeBase {
13884
13331
  const { body, deoptimized, left, right } = this;
13885
13332
  if (!deoptimized)
13886
13333
  this.applyDeoptimizations();
13887
- if (!this.included)
13888
- this.includeNode(context);
13334
+ this.included = true;
13889
13335
  left.includeAsAssignmentTarget(context, includeChildrenRecursively || true, false);
13890
13336
  right.include(context, includeChildrenRecursively);
13891
13337
  includeLoopBody(context, body, includeChildrenRecursively);
13892
13338
  }
13893
- includeNode(context) {
13894
- this.included = true;
13895
- if (!this.deoptimized)
13896
- this.applyDeoptimizations();
13897
- this.right.includePath(UNKNOWN_PATH, context);
13898
- }
13899
13339
  initialise() {
13900
13340
  super.initialise();
13901
13341
  this.left.setAssignedValue(UNKNOWN_EXPRESSION);
@@ -13931,9 +13371,7 @@ class ForStatement extends NodeBase {
13931
13371
  }
13932
13372
  include(context, includeChildrenRecursively) {
13933
13373
  this.included = true;
13934
- this.init?.include(context, includeChildrenRecursively, {
13935
- asSingleStatement: true
13936
- });
13374
+ this.init?.include(context, includeChildrenRecursively, { asSingleStatement: true });
13937
13375
  this.test?.include(context, includeChildrenRecursively);
13938
13376
  this.update?.include(context, includeChildrenRecursively);
13939
13377
  includeLoopBody(context, this.body, includeChildrenRecursively);
@@ -13945,8 +13383,6 @@ class ForStatement extends NodeBase {
13945
13383
  this.body.render(code, options);
13946
13384
  }
13947
13385
  }
13948
- ForStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
13949
- ForStatement.prototype.applyDeoptimizations = doNotDeoptimize;
13950
13386
 
13951
13387
  class FunctionExpression extends FunctionNode {
13952
13388
  createScope(parentScope) {
@@ -13978,9 +13414,9 @@ class TrackingScope extends BlockScope {
13978
13414
  super(...arguments);
13979
13415
  this.hoistedDeclarations = [];
13980
13416
  }
13981
- addDeclaration(identifier, context, init, destructuredInitPath, kind) {
13417
+ addDeclaration(identifier, context, init, kind) {
13982
13418
  this.hoistedDeclarations.push(identifier);
13983
- return super.addDeclaration(identifier, context, init, destructuredInitPath, kind);
13419
+ return super.addDeclaration(identifier, context, init, kind);
13984
13420
  }
13985
13421
  }
13986
13422
 
@@ -14079,6 +13515,7 @@ class IfStatement extends NodeBase {
14079
13515
  }
14080
13516
  this.renderHoistedDeclarations(hoistedDeclarations, code, getPropertyAccess);
14081
13517
  }
13518
+ applyDeoptimizations() { }
14082
13519
  getTestValue() {
14083
13520
  if (this.testValue === unset) {
14084
13521
  return (this.testValue = tryCastLiteralValueToBoolean(this.test.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, this)));
@@ -14147,8 +13584,6 @@ class IfStatement extends NodeBase {
14147
13584
  return false;
14148
13585
  }
14149
13586
  }
14150
- IfStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
14151
- IfStatement.prototype.applyDeoptimizations = doNotDeoptimize;
14152
13587
 
14153
13588
  class ImportAttribute extends NodeBase {
14154
13589
  }
@@ -14166,15 +13601,13 @@ class ImportDeclaration extends NodeBase {
14166
13601
  render(code, _options, nodeRenderOptions) {
14167
13602
  code.remove(nodeRenderOptions.start, nodeRenderOptions.end);
14168
13603
  }
13604
+ applyDeoptimizations() { }
14169
13605
  }
14170
13606
  ImportDeclaration.prototype.needsBoundaries = true;
14171
- ImportDeclaration.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
14172
- ImportDeclaration.prototype.applyDeoptimizations = doNotDeoptimize;
14173
13607
 
14174
13608
  class ImportDefaultSpecifier extends NodeBase {
13609
+ applyDeoptimizations() { }
14175
13610
  }
14176
- ImportDefaultSpecifier.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
14177
- ImportDefaultSpecifier.prototype.applyDeoptimizations = doNotDeoptimize;
14178
13611
 
14179
13612
  function isReassignedExportsMember(variable, exportNamesByVariable) {
14180
13613
  return (variable.renderBaseName !== null && exportNamesByVariable.has(variable) && variable.isReassigned);
@@ -14183,33 +13616,28 @@ function isReassignedExportsMember(variable, exportNamesByVariable) {
14183
13616
  class VariableDeclarator extends NodeBase {
14184
13617
  declareDeclarator(kind, isUsingDeclaration) {
14185
13618
  this.isUsingDeclaration = isUsingDeclaration;
14186
- this.id.declare(kind, EMPTY_PATH, this.init || UNDEFINED_EXPRESSION);
13619
+ this.id.declare(kind, this.init || UNDEFINED_EXPRESSION);
14187
13620
  }
14188
13621
  deoptimizePath(path) {
14189
13622
  this.id.deoptimizePath(path);
14190
13623
  }
14191
13624
  hasEffects(context) {
13625
+ if (!this.deoptimized)
13626
+ this.applyDeoptimizations();
14192
13627
  const initEffect = this.init?.hasEffects(context);
14193
13628
  this.id.markDeclarationReached();
14194
- return (initEffect ||
14195
- this.isUsingDeclaration ||
14196
- this.id.hasEffects(context) ||
14197
- (this.scope.context.options.treeshake
14198
- .propertyReadSideEffects &&
14199
- this.id.hasEffectsWhenDestructuring(context, EMPTY_PATH, this.init || UNDEFINED_EXPRESSION)));
13629
+ return initEffect || this.id.hasEffects(context) || this.isUsingDeclaration;
14200
13630
  }
14201
13631
  include(context, includeChildrenRecursively) {
14202
- const { id, init } = this;
14203
- if (!this.included)
14204
- this.includeNode();
13632
+ const { deoptimized, id, init } = this;
13633
+ if (!deoptimized)
13634
+ this.applyDeoptimizations();
13635
+ this.included = true;
14205
13636
  init?.include(context, includeChildrenRecursively);
14206
13637
  id.markDeclarationReached();
14207
- if (includeChildrenRecursively) {
13638
+ if (includeChildrenRecursively || id.shouldBeIncluded(context)) {
14208
13639
  id.include(context, includeChildrenRecursively);
14209
13640
  }
14210
- else {
14211
- id.includeDestructuredIfNecessary(context, EMPTY_PATH, init || UNDEFINED_EXPRESSION);
14212
- }
14213
13641
  }
14214
13642
  removeAnnotations(code) {
14215
13643
  this.init?.removeAnnotations(code);
@@ -14239,8 +13667,8 @@ class VariableDeclarator extends NodeBase {
14239
13667
  code.appendLeft(end, `${_}=${_}void 0`);
14240
13668
  }
14241
13669
  }
14242
- includeNode() {
14243
- this.included = true;
13670
+ applyDeoptimizations() {
13671
+ this.deoptimized = true;
14244
13672
  const { id, init } = this;
14245
13673
  if (init && id instanceof Identifier && init instanceof ClassExpression && !init.id) {
14246
13674
  const { name, variable } = id;
@@ -14252,14 +13680,11 @@ class VariableDeclarator extends NodeBase {
14252
13680
  }
14253
13681
  }
14254
13682
  }
14255
- VariableDeclarator.prototype.applyDeoptimizations = doNotDeoptimize;
14256
13683
 
14257
13684
  class ImportExpression extends NodeBase {
14258
13685
  constructor() {
14259
13686
  super(...arguments);
14260
13687
  this.inlineNamespace = null;
14261
- this.hasUnknownAccessedKey = false;
14262
- this.accessedPropKey = new Set();
14263
13688
  this.attributes = null;
14264
13689
  this.mechanism = null;
14265
13690
  this.namespaceExportName = undefined;
@@ -14292,15 +13717,12 @@ class ImportExpression extends NodeBase {
14292
13717
  if (parent2 instanceof ExpressionStatement) {
14293
13718
  return parseAst_js.EMPTY_ARRAY;
14294
13719
  }
14295
- // Case 1: const { foo } / module = await import('bar')
13720
+ // Case 1: const { foo } = await import('bar')
14296
13721
  if (parent2 instanceof VariableDeclarator) {
14297
13722
  const declaration = parent2.id;
14298
- if (declaration instanceof Identifier) {
14299
- return this.hasUnknownAccessedKey ? undefined : [...this.accessedPropKey];
14300
- }
14301
- if (declaration instanceof ObjectPattern) {
14302
- return getDeterministicObjectDestructure(declaration);
14303
- }
13723
+ return declaration instanceof ObjectPattern
13724
+ ? getDeterministicObjectDestructure(declaration)
13725
+ : undefined;
14304
13726
  }
14305
13727
  // Case 2: (await import('bar')).foo
14306
13728
  if (parent2 instanceof MemberExpression) {
@@ -14350,29 +13772,12 @@ class ImportExpression extends NodeBase {
14350
13772
  return true;
14351
13773
  }
14352
13774
  include(context, includeChildrenRecursively) {
14353
- if (!this.included)
14354
- this.includeNode();
14355
- this.source.include(context, includeChildrenRecursively);
14356
- }
14357
- includeNode() {
14358
- this.included = true;
14359
- this.scope.context.includeDynamicImport(this);
14360
- this.scope.addAccessedDynamicImport(this);
14361
- }
14362
- includePath(path) {
14363
- if (!this.included)
14364
- this.includeNode();
14365
- // Technically, this is not correct as dynamic imports return a Promise.
14366
- if (this.hasUnknownAccessedKey)
14367
- return;
14368
- if (path[0] === UnknownKey) {
14369
- this.hasUnknownAccessedKey = true;
14370
- }
14371
- else if (typeof path[0] === 'string') {
14372
- this.accessedPropKey.add(path[0]);
13775
+ if (!this.included) {
13776
+ this.included = true;
13777
+ this.scope.context.includeDynamicImport(this);
13778
+ this.scope.addAccessedDynamicImport(this);
14373
13779
  }
14374
- // Update included paths
14375
- this.scope.context.includeDynamicImport(this);
13780
+ this.source.include(context, includeChildrenRecursively);
14376
13781
  }
14377
13782
  initialise() {
14378
13783
  super.initialise();
@@ -14442,6 +13847,7 @@ class ImportExpression extends NodeBase {
14442
13847
  setInternalResolution(inlineNamespace) {
14443
13848
  this.inlineNamespace = inlineNamespace;
14444
13849
  }
13850
+ applyDeoptimizations() { }
14445
13851
  getDynamicImportMechanismAndHelper(resolution, exportMode, { compact, dynamicImportInCjs, format, generatedCode: { arrowFunctions }, interop }, { _, getDirectReturnFunction, getDirectReturnIifeLeft }, pluginDriver) {
14446
13852
  const mechanism = pluginDriver.hookFirstSync('renderDynamicImport', [
14447
13853
  {
@@ -14531,7 +13937,6 @@ class ImportExpression extends NodeBase {
14531
13937
  return { helper: null, mechanism: null };
14532
13938
  }
14533
13939
  }
14534
- ImportExpression.prototype.applyDeoptimizations = doNotDeoptimize;
14535
13940
  function getInteropHelper(resolution, exportMode, interop) {
14536
13941
  return exportMode === 'external'
14537
13942
  ? namespaceInteropHelpersByInteropType[interop(resolution instanceof ExternalModule ? resolution.id : null)]
@@ -14555,14 +13960,12 @@ function getDeterministicObjectDestructure(objectPattern) {
14555
13960
  }
14556
13961
 
14557
13962
  class ImportNamespaceSpecifier extends NodeBase {
13963
+ applyDeoptimizations() { }
14558
13964
  }
14559
- ImportNamespaceSpecifier.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
14560
- ImportNamespaceSpecifier.prototype.applyDeoptimizations = doNotDeoptimize;
14561
13965
 
14562
13966
  class ImportSpecifier extends NodeBase {
13967
+ applyDeoptimizations() { }
14563
13968
  }
14564
- ImportSpecifier.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
14565
- ImportSpecifier.prototype.applyDeoptimizations = doNotDeoptimize;
14566
13969
 
14567
13970
  class JSXIdentifier extends IdentifierBase {
14568
13971
  constructor() {
@@ -14579,29 +13982,6 @@ class JSXIdentifier extends IdentifierBase {
14579
13982
  this.isNativeElement = true;
14580
13983
  }
14581
13984
  }
14582
- include(context) {
14583
- if (!this.included)
14584
- this.includeNode(context);
14585
- }
14586
- includeNode(context) {
14587
- this.included = true;
14588
- if (!this.deoptimized)
14589
- this.applyDeoptimizations();
14590
- if (this.variable !== null) {
14591
- this.scope.context.includeVariableInModule(this.variable, EMPTY_PATH, context);
14592
- }
14593
- }
14594
- includePath(path, context) {
14595
- if (!this.included) {
14596
- this.included = true;
14597
- if (this.variable !== null) {
14598
- this.scope.context.includeVariableInModule(this.variable, path, context);
14599
- }
14600
- }
14601
- else if (path.length > 0) {
14602
- this.variable?.includePath(path, context);
14603
- }
14604
- }
14605
13985
  render(code, { snippets: { getPropertyAccess }, useOriginalName }) {
14606
13986
  if (this.variable) {
14607
13987
  const name = this.variable.getName(getPropertyAccess, useOriginalName);
@@ -14663,7 +14043,6 @@ class JSXAttribute extends NodeBase {
14663
14043
  }
14664
14044
  }
14665
14045
  }
14666
- JSXAttribute.prototype.includeNode = onlyIncludeSelf;
14667
14046
 
14668
14047
  class JSXClosingBase extends NodeBase {
14669
14048
  render(code, options) {
@@ -14676,7 +14055,6 @@ class JSXClosingBase extends NodeBase {
14676
14055
  }
14677
14056
  }
14678
14057
  }
14679
- JSXClosingBase.prototype.includeNode = onlyIncludeSelf;
14680
14058
 
14681
14059
  class JSXClosingElement extends JSXClosingBase {
14682
14060
  }
@@ -14697,15 +14075,8 @@ class JSXSpreadAttribute extends NodeBase {
14697
14075
 
14698
14076
  class JSXEmptyExpression extends NodeBase {
14699
14077
  }
14700
- JSXEmptyExpression.prototype.includeNode = onlyIncludeSelf;
14701
14078
 
14702
14079
  class JSXExpressionContainer extends NodeBase {
14703
- includeNode(context) {
14704
- this.included = true;
14705
- if (!this.deoptimized)
14706
- this.applyDeoptimizations();
14707
- this.expression.includePath(UNKNOWN_PATH, context);
14708
- }
14709
14080
  render(code, options) {
14710
14081
  const { mode } = this.scope.context.options.jsx;
14711
14082
  if (mode !== 'preserve') {
@@ -14726,7 +14097,7 @@ function getRenderedJsxChildren(children) {
14726
14097
  return renderedChildren;
14727
14098
  }
14728
14099
 
14729
- function getAndIncludeFactoryVariable(factory, preserve, importSource, node, context) {
14100
+ function getAndIncludeFactoryVariable(factory, preserve, importSource, node) {
14730
14101
  const [baseName, nestedName] = factory.split('.');
14731
14102
  let factoryVariable;
14732
14103
  if (importSource) {
@@ -14734,7 +14105,7 @@ function getAndIncludeFactoryVariable(factory, preserve, importSource, node, con
14734
14105
  if (preserve) {
14735
14106
  // This pretends we are accessing an included global variable of the same name
14736
14107
  const globalVariable = node.scope.findGlobal(baseName);
14737
- globalVariable.includePath(UNKNOWN_PATH, context);
14108
+ globalVariable.include();
14738
14109
  // This excludes this variable from renaming
14739
14110
  factoryVariable.globalName = baseName;
14740
14111
  }
@@ -14742,7 +14113,7 @@ function getAndIncludeFactoryVariable(factory, preserve, importSource, node, con
14742
14113
  else {
14743
14114
  factoryVariable = node.scope.findGlobal(baseName);
14744
14115
  }
14745
- node.scope.context.includeVariableInModule(factoryVariable, UNKNOWN_PATH, context);
14116
+ node.scope.context.includeVariableInModule(factoryVariable);
14746
14117
  if (factoryVariable instanceof LocalVariable) {
14747
14118
  factoryVariable.consolidateInitializers();
14748
14119
  factoryVariable.addUsedPlace(node);
@@ -14765,20 +14136,16 @@ class JSXElementBase extends NodeBase {
14765
14136
  }
14766
14137
  }
14767
14138
  include(context, includeChildrenRecursively) {
14768
- if (!this.included)
14769
- this.includeNode(context);
14770
- for (const child of this.children) {
14771
- child.include(context, includeChildrenRecursively);
14772
- }
14773
- }
14774
- includeNode(context) {
14775
- this.included = true;
14776
- const { factory, importSource, mode } = this.jsxMode;
14777
- if (factory) {
14778
- this.factory = factory;
14779
- this.factoryVariable = getAndIncludeFactoryVariable(factory, mode === 'preserve', importSource, this, context);
14139
+ if (!this.included) {
14140
+ const { factory, importSource, mode } = this.jsxMode;
14141
+ if (factory) {
14142
+ this.factory = factory;
14143
+ this.factoryVariable = getAndIncludeFactoryVariable(factory, mode === 'preserve', importSource, this);
14144
+ }
14780
14145
  }
14146
+ super.include(context, includeChildrenRecursively);
14781
14147
  }
14148
+ applyDeoptimizations() { }
14782
14149
  getRenderingMode() {
14783
14150
  const jsx = this.scope.context.options.jsx;
14784
14151
  const { mode, factory, importSource } = jsx;
@@ -14816,14 +14183,8 @@ class JSXElementBase extends NodeBase {
14816
14183
  return { childrenEnd, firstChild, hasMultipleChildren };
14817
14184
  }
14818
14185
  }
14819
- JSXElementBase.prototype.applyDeoptimizations = doNotDeoptimize;
14820
14186
 
14821
14187
  class JSXElement extends JSXElementBase {
14822
- include(context, includeChildrenRecursively) {
14823
- super.include(context, includeChildrenRecursively);
14824
- this.openingElement.include(context, includeChildrenRecursively);
14825
- this.closingElement?.include(context, includeChildrenRecursively);
14826
- }
14827
14188
  render(code, options) {
14828
14189
  switch (this.jsxMode.mode) {
14829
14190
  case 'classic': {
@@ -14975,11 +14336,6 @@ class JSXElement extends JSXElementBase {
14975
14336
  }
14976
14337
 
14977
14338
  class JSXFragment extends JSXElementBase {
14978
- include(context, includeChildrenRecursively) {
14979
- super.include(context, includeChildrenRecursively);
14980
- this.openingFragment.include(context, includeChildrenRecursively);
14981
- this.closingFragment.include(context, includeChildrenRecursively);
14982
- }
14983
14339
  render(code, options) {
14984
14340
  switch (this.jsxMode.mode) {
14985
14341
  case 'classic': {
@@ -15029,22 +14385,10 @@ class JSXFragment extends JSXElementBase {
15029
14385
  }
15030
14386
 
15031
14387
  class JSXMemberExpression extends NodeBase {
15032
- includeNode(context) {
15033
- this.included = true;
15034
- if (!this.deoptimized)
15035
- this.applyDeoptimizations();
15036
- this.object.includePath([this.property.name], context);
15037
- }
15038
- includePath(path, context) {
15039
- if (!this.included)
15040
- this.includeNode(context);
15041
- this.object.includePath([this.property.name, ...path], context);
15042
- }
15043
14388
  }
15044
14389
 
15045
14390
  class JSXNamespacedName extends NodeBase {
15046
14391
  }
15047
- JSXNamespacedName.prototype.includeNode = onlyIncludeSelf;
15048
14392
 
15049
14393
  class JSXOpeningElement extends NodeBase {
15050
14394
  render(code, options, { jsxMode = this.scope.context.options.jsx.mode } = {}) {
@@ -15054,7 +14398,6 @@ class JSXOpeningElement extends NodeBase {
15054
14398
  }
15055
14399
  }
15056
14400
  }
15057
- JSXOpeningElement.prototype.includeNode = onlyIncludeSelf;
15058
14401
 
15059
14402
  class JSXOpeningFragment extends NodeBase {
15060
14403
  constructor() {
@@ -15062,22 +14405,22 @@ class JSXOpeningFragment extends NodeBase {
15062
14405
  this.fragment = null;
15063
14406
  this.fragmentVariable = null;
15064
14407
  }
15065
- includeNode(context) {
15066
- this.included = true;
15067
- if (!this.deoptimized)
15068
- this.applyDeoptimizations();
15069
- const jsx = this.scope.context.options.jsx;
15070
- if (jsx.mode === 'automatic') {
15071
- this.fragment = 'Fragment';
15072
- this.fragmentVariable = getAndIncludeFactoryVariable('Fragment', false, jsx.jsxImportSource, this, context);
15073
- }
15074
- else {
15075
- const { fragment, importSource, mode } = jsx;
15076
- if (fragment != null) {
15077
- this.fragment = fragment;
15078
- this.fragmentVariable = getAndIncludeFactoryVariable(fragment, mode === 'preserve', importSource, this, context);
14408
+ include(context, includeChildrenRecursively) {
14409
+ if (!this.included) {
14410
+ const jsx = this.scope.context.options.jsx;
14411
+ if (jsx.mode === 'automatic') {
14412
+ this.fragment = 'Fragment';
14413
+ this.fragmentVariable = getAndIncludeFactoryVariable('Fragment', false, jsx.jsxImportSource, this);
14414
+ }
14415
+ else {
14416
+ const { fragment, importSource, mode } = jsx;
14417
+ if (fragment != null) {
14418
+ this.fragment = fragment;
14419
+ this.fragmentVariable = getAndIncludeFactoryVariable(fragment, mode === 'preserve', importSource, this);
14420
+ }
15079
14421
  }
15080
14422
  }
14423
+ super.include(context, includeChildrenRecursively);
15081
14424
  }
15082
14425
  render(code, options) {
15083
14426
  const { mode } = this.scope.context.options.jsx;
@@ -15114,7 +14457,6 @@ class JSXText extends NodeBase {
15114
14457
  }
15115
14458
  }
15116
14459
  }
15117
- JSXText.prototype.includeNode = onlyIncludeSelf;
15118
14460
 
15119
14461
  class LabeledStatement extends NodeBase {
15120
14462
  hasEffects(context) {
@@ -15136,22 +14478,17 @@ class LabeledStatement extends NodeBase {
15136
14478
  return bodyHasEffects;
15137
14479
  }
15138
14480
  include(context, includeChildrenRecursively) {
15139
- if (!this.included)
15140
- this.includeNode(context);
14481
+ this.included = true;
15141
14482
  const { brokenFlow, includedLabels } = context;
15142
14483
  context.includedLabels = new Set();
15143
14484
  this.body.include(context, includeChildrenRecursively);
15144
14485
  if (includeChildrenRecursively || context.includedLabels.has(this.label.name)) {
15145
- this.label.include(context);
14486
+ this.label.include();
15146
14487
  context.includedLabels.delete(this.label.name);
15147
14488
  context.brokenFlow = brokenFlow;
15148
14489
  }
15149
14490
  context.includedLabels = new Set([...includedLabels, ...context.includedLabels]);
15150
14491
  }
15151
- includeNode(context) {
15152
- this.included = true;
15153
- this.body.includePath(UNKNOWN_PATH, context);
15154
- }
15155
14492
  render(code, options) {
15156
14493
  if (this.label.included) {
15157
14494
  this.label.render(code, options);
@@ -15162,7 +14499,6 @@ class LabeledStatement extends NodeBase {
15162
14499
  this.body.render(code, options);
15163
14500
  }
15164
14501
  }
15165
- LabeledStatement.prototype.applyDeoptimizations = doNotDeoptimize;
15166
14502
 
15167
14503
  class LogicalExpression extends NodeBase {
15168
14504
  constructor() {
@@ -15179,10 +14515,10 @@ class LogicalExpression extends NodeBase {
15179
14515
  this.flags = setFlag(this.flags, 65536 /* Flag.isBranchResolutionAnalysed */, value);
15180
14516
  }
15181
14517
  get hasDeoptimizedCache() {
15182
- return isFlagSet(this.flags, 33554432 /* Flag.hasDeoptimizedCache */);
14518
+ return isFlagSet(this.flags, 16777216 /* Flag.hasDeoptimizedCache */);
15183
14519
  }
15184
14520
  set hasDeoptimizedCache(value) {
15185
- this.flags = setFlag(this.flags, 33554432 /* Flag.hasDeoptimizedCache */, value);
14521
+ this.flags = setFlag(this.flags, 16777216 /* Flag.hasDeoptimizedCache */, value);
15186
14522
  }
15187
14523
  deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
15188
14524
  this.left.deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker);
@@ -15195,10 +14531,6 @@ class LogicalExpression extends NodeBase {
15195
14531
  const unusedBranch = this.usedBranch === this.left ? this.right : this.left;
15196
14532
  this.usedBranch = null;
15197
14533
  unusedBranch.deoptimizePath(UNKNOWN_PATH);
15198
- if (this.included) {
15199
- // As we are not tracking inclusions, we just include everything
15200
- unusedBranch.includePath(UNKNOWN_PATH, createInclusionContext());
15201
- }
15202
14534
  }
15203
14535
  const { scope: { context }, expressionsToBeDeoptimized } = this;
15204
14536
  this.expressionsToBeDeoptimized = parseAst_js.EMPTY_ARRAY;
@@ -15244,17 +14576,16 @@ class LogicalExpression extends NodeBase {
15244
14576
  }
15245
14577
  getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
15246
14578
  const usedBranch = this.getUsedBranch();
15247
- if (usedBranch) {
15248
- this.expressionsToBeDeoptimized.push(origin);
15249
- return usedBranch.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
15250
- }
15251
- return [
15252
- new MultiExpression([
15253
- this.left.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)[0],
15254
- this.right.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)[0]
15255
- ]),
15256
- false
15257
- ];
14579
+ if (!usedBranch)
14580
+ return [
14581
+ new MultiExpression([
14582
+ this.left.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)[0],
14583
+ this.right.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)[0]
14584
+ ]),
14585
+ false
14586
+ ];
14587
+ this.expressionsToBeDeoptimized.push(origin);
14588
+ return usedBranch.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
15258
14589
  }
15259
14590
  hasEffects(context) {
15260
14591
  if (this.left.hasEffects(context)) {
@@ -15267,18 +14598,18 @@ class LogicalExpression extends NodeBase {
15267
14598
  }
15268
14599
  hasEffectsOnInteractionAtPath(path, interaction, context) {
15269
14600
  const usedBranch = this.getUsedBranch();
15270
- if (usedBranch) {
15271
- return usedBranch.hasEffectsOnInteractionAtPath(path, interaction, context);
14601
+ if (!usedBranch) {
14602
+ return (this.left.hasEffectsOnInteractionAtPath(path, interaction, context) ||
14603
+ this.right.hasEffectsOnInteractionAtPath(path, interaction, context));
15272
14604
  }
15273
- return (this.left.hasEffectsOnInteractionAtPath(path, interaction, context) ||
15274
- this.right.hasEffectsOnInteractionAtPath(path, interaction, context));
14605
+ return usedBranch.hasEffectsOnInteractionAtPath(path, interaction, context);
15275
14606
  }
15276
14607
  include(context, includeChildrenRecursively) {
15277
14608
  this.included = true;
15278
14609
  const usedBranch = this.getUsedBranch();
15279
14610
  if (includeChildrenRecursively ||
15280
- !usedBranch ||
15281
- (usedBranch === this.right && this.left.shouldBeIncluded(context))) {
14611
+ (usedBranch === this.right && this.left.shouldBeIncluded(context)) ||
14612
+ !usedBranch) {
15282
14613
  this.left.include(context, includeChildrenRecursively);
15283
14614
  this.right.include(context, includeChildrenRecursively);
15284
14615
  }
@@ -15286,17 +14617,6 @@ class LogicalExpression extends NodeBase {
15286
14617
  usedBranch.include(context, includeChildrenRecursively);
15287
14618
  }
15288
14619
  }
15289
- includePath(path, context) {
15290
- this.included = true;
15291
- const usedBranch = this.getUsedBranch();
15292
- if (!usedBranch || (usedBranch === this.right && this.left.shouldBeIncluded(context))) {
15293
- this.left.includePath(path, context);
15294
- this.right.includePath(path, context);
15295
- }
15296
- else {
15297
- usedBranch.includePath(path, context);
15298
- }
15299
- }
15300
14620
  removeAnnotations(code) {
15301
14621
  this.left.removeAnnotations(code);
15302
14622
  }
@@ -15349,8 +14669,6 @@ class LogicalExpression extends NodeBase {
15349
14669
  return this.usedBranch;
15350
14670
  }
15351
14671
  }
15352
- LogicalExpression.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
15353
- LogicalExpression.prototype.applyDeoptimizations = doNotDeoptimize;
15354
14672
 
15355
14673
  class NewExpression extends NodeBase {
15356
14674
  hasEffects(context) {
@@ -15370,21 +14688,16 @@ class NewExpression extends NodeBase {
15370
14688
  return path.length > 0 || type !== INTERACTION_ACCESSED;
15371
14689
  }
15372
14690
  include(context, includeChildrenRecursively) {
14691
+ if (!this.deoptimized)
14692
+ this.applyDeoptimizations();
15373
14693
  if (includeChildrenRecursively) {
15374
14694
  super.include(context, includeChildrenRecursively);
15375
14695
  }
15376
14696
  else {
15377
- if (!this.included)
15378
- this.includeNode(context);
14697
+ this.included = true;
15379
14698
  this.callee.include(context, false);
15380
14699
  }
15381
- this.callee.includeCallArguments(context, this.interaction);
15382
- }
15383
- includeNode(context) {
15384
- this.included = true;
15385
- if (!this.deoptimized)
15386
- this.applyDeoptimizations();
15387
- this.callee.includePath(UNKNOWN_PATH, context);
14700
+ this.callee.includeCallArguments(context, this.arguments);
15388
14701
  }
15389
14702
  initialise() {
15390
14703
  super.initialise();
@@ -15413,7 +14726,6 @@ class ObjectExpression extends NodeBase {
15413
14726
  constructor() {
15414
14727
  super(...arguments);
15415
14728
  this.objectEntity = null;
15416
- this.protoProp = null;
15417
14729
  }
15418
14730
  deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
15419
14731
  this.getObjectEntity().deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker);
@@ -15433,43 +14745,15 @@ class ObjectExpression extends NodeBase {
15433
14745
  hasEffectsOnInteractionAtPath(path, interaction, context) {
15434
14746
  return this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
15435
14747
  }
15436
- include(context, includeChildrenRecursively) {
15437
- if (!this.included)
15438
- this.includeNode(context);
15439
- this.getObjectEntity().include(context, includeChildrenRecursively);
15440
- this.protoProp?.include(context, includeChildrenRecursively);
15441
- }
15442
- includeNode(context) {
15443
- this.included = true;
15444
- this.protoProp?.includePath(UNKNOWN_PATH, context);
15445
- }
15446
- includePath(path, context) {
15447
- if (!this.included)
15448
- this.includeNode(context);
15449
- this.getObjectEntity().includePath(path, context);
15450
- }
15451
14748
  render(code, options, { renderedSurroundingElement } = parseAst_js.BLANK) {
14749
+ super.render(code, options);
15452
14750
  if (renderedSurroundingElement === parseAst_js.ExpressionStatement ||
15453
14751
  renderedSurroundingElement === parseAst_js.ArrowFunctionExpression) {
15454
14752
  code.appendRight(this.start, '(');
15455
14753
  code.prependLeft(this.end, ')');
15456
14754
  }
15457
- if (this.properties.length > 0) {
15458
- const separatedNodes = getCommaSeparatedNodesWithBoundaries(this.properties, code, this.start + 1, this.end - 1);
15459
- let lastSeparatorPos = null;
15460
- for (const { node, separator, start, end } of separatedNodes) {
15461
- if (!node.included) {
15462
- treeshakeNode(node, code, start, end);
15463
- continue;
15464
- }
15465
- lastSeparatorPos = separator;
15466
- node.render(code, options);
15467
- }
15468
- if (lastSeparatorPos) {
15469
- code.remove(lastSeparatorPos, this.end - 1);
15470
- }
15471
- }
15472
14755
  }
14756
+ applyDeoptimizations() { }
15473
14757
  getObjectEntity() {
15474
14758
  if (this.objectEntity !== null) {
15475
14759
  return this.objectEntity;
@@ -15498,7 +14782,6 @@ class ObjectExpression extends NodeBase {
15498
14782
  ? property.key.name
15499
14783
  : String(property.key.value);
15500
14784
  if (key === '__proto__' && property.kind === 'init') {
15501
- this.protoProp = property;
15502
14785
  prototype =
15503
14786
  property.value instanceof Literal && property.value.value === null
15504
14787
  ? null
@@ -15511,7 +14794,6 @@ class ObjectExpression extends NodeBase {
15511
14794
  return (this.objectEntity = new ObjectEntity(properties, prototype));
15512
14795
  }
15513
14796
  }
15514
- ObjectExpression.prototype.applyDeoptimizations = doNotDeoptimize;
15515
14797
 
15516
14798
  class PanicError extends NodeBase {
15517
14799
  initialise() {
@@ -15538,7 +14820,6 @@ class ParseError extends NodeBase {
15538
14820
 
15539
14821
  class PrivateIdentifier extends NodeBase {
15540
14822
  }
15541
- PrivateIdentifier.prototype.includeNode = onlyIncludeSelf;
15542
14823
 
15543
14824
  class Program extends NodeBase {
15544
14825
  constructor() {
@@ -15606,11 +14887,14 @@ class Program extends NodeBase {
15606
14887
  super.render(code, options);
15607
14888
  }
15608
14889
  }
14890
+ applyDeoptimizations() { }
15609
14891
  }
15610
- Program.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
15611
- Program.prototype.applyDeoptimizations = doNotDeoptimize;
15612
14892
 
15613
14893
  class Property extends MethodBase {
14894
+ constructor() {
14895
+ super(...arguments);
14896
+ this.declarationInit = null;
14897
+ }
15614
14898
  //declare method: boolean;
15615
14899
  get method() {
15616
14900
  return isFlagSet(this.flags, 262144 /* Flag.method */);
@@ -15625,41 +14909,17 @@ class Property extends MethodBase {
15625
14909
  set shorthand(value) {
15626
14910
  this.flags = setFlag(this.flags, 524288 /* Flag.shorthand */, value);
15627
14911
  }
15628
- declare(kind, destructuredInitPath, init) {
15629
- return this.value.declare(kind, this.getPathInProperty(destructuredInitPath), init);
15630
- }
15631
- deoptimizeAssignment(destructuredInitPath, init) {
15632
- this.value.deoptimizeAssignment?.(this.getPathInProperty(destructuredInitPath), init);
14912
+ declare(kind, init) {
14913
+ this.declarationInit = init;
14914
+ return this.value.declare(kind, UNKNOWN_EXPRESSION);
15633
14915
  }
15634
14916
  hasEffects(context) {
15635
- return this.key.hasEffects(context) || this.value.hasEffects(context);
15636
- }
15637
- hasEffectsWhenDestructuring(context, destructuredInitPath, init) {
15638
- return this.value.hasEffectsWhenDestructuring?.(context, this.getPathInProperty(destructuredInitPath), init);
15639
- }
15640
- includeDestructuredIfNecessary(context, destructuredInitPath, init) {
15641
- const path = this.getPathInProperty(destructuredInitPath);
15642
- let included = this.value.includeDestructuredIfNecessary(context, path, init) ||
15643
- this.included;
15644
- if ((included ||= this.key.hasEffects(createHasEffectsContext()))) {
15645
- this.key.include(context, false);
15646
- if (!this.value.included) {
15647
- this.value.included = true;
15648
- // Unfortunately, we need to include the value again now, so that any
15649
- // declared variables are properly included.
15650
- this.value.includeDestructuredIfNecessary(context, path, init);
15651
- }
15652
- }
15653
- return (this.included = included);
15654
- }
15655
- include(context, includeChildrenRecursively) {
15656
- this.included = true;
15657
- this.key.include(context, includeChildrenRecursively);
15658
- this.value.include(context, includeChildrenRecursively);
15659
- }
15660
- includePath(path, context) {
15661
- this.included = true;
15662
- this.value.includePath(path, context);
14917
+ if (!this.deoptimized)
14918
+ this.applyDeoptimizations();
14919
+ const propertyReadSideEffects = this.scope.context.options.treeshake.propertyReadSideEffects;
14920
+ return ((this.parent.type === 'ObjectPattern' && propertyReadSideEffects === 'always') ||
14921
+ this.key.hasEffects(context) ||
14922
+ this.value.hasEffects(context));
15663
14923
  }
15664
14924
  markDeclarationReached() {
15665
14925
  this.value.markDeclarationReached();
@@ -15670,20 +14930,14 @@ class Property extends MethodBase {
15670
14930
  }
15671
14931
  this.value.render(code, options, { isShorthandProperty: this.shorthand });
15672
14932
  }
15673
- getPathInProperty(destructuredInitPath) {
15674
- return destructuredInitPath.at(-1) === UnknownKey
15675
- ? destructuredInitPath
15676
- : // For now, we only consider static paths as we do not know how to
15677
- // deoptimize the path in the dynamic case.
15678
- this.computed
15679
- ? [...destructuredInitPath, UnknownKey]
15680
- : this.key instanceof Identifier
15681
- ? [...destructuredInitPath, this.key.name]
15682
- : [...destructuredInitPath, String(this.key.value)];
14933
+ applyDeoptimizations() {
14934
+ this.deoptimized = true;
14935
+ if (this.declarationInit !== null) {
14936
+ this.declarationInit.deoptimizePath([UnknownKey, UnknownKey]);
14937
+ this.scope.context.requestTreeshakingPass();
14938
+ }
15683
14939
  }
15684
14940
  }
15685
- Property.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
15686
- Property.prototype.applyDeoptimizations = doNotDeoptimize;
15687
14941
 
15688
14942
  class PropertyDefinition extends NodeBase {
15689
14943
  get computed() {
@@ -15716,15 +14970,8 @@ class PropertyDefinition extends NodeBase {
15716
14970
  hasEffectsOnInteractionAtPath(path, interaction, context) {
15717
14971
  return !this.value || this.value.hasEffectsOnInteractionAtPath(path, interaction, context);
15718
14972
  }
15719
- includeNode(context) {
15720
- this.included = true;
15721
- this.value?.includePath(UNKNOWN_PATH, context);
15722
- for (const decorator of this.decorators) {
15723
- decorator.includePath(UNKNOWN_PATH, context);
15724
- }
15725
- }
14973
+ applyDeoptimizations() { }
15726
14974
  }
15727
- PropertyDefinition.prototype.applyDeoptimizations = doNotDeoptimize;
15728
14975
 
15729
14976
  class ReturnStatement extends NodeBase {
15730
14977
  hasEffects(context) {
@@ -15734,15 +14981,10 @@ class ReturnStatement extends NodeBase {
15734
14981
  return false;
15735
14982
  }
15736
14983
  include(context, includeChildrenRecursively) {
15737
- if (!this.included)
15738
- this.includeNode(context);
14984
+ this.included = true;
15739
14985
  this.argument?.include(context, includeChildrenRecursively);
15740
14986
  context.brokenFlow = true;
15741
14987
  }
15742
- includeNode(context) {
15743
- this.included = true;
15744
- this.argument?.includePath(UNKNOWN_PATH, context);
15745
- }
15746
14988
  initialise() {
15747
14989
  super.initialise();
15748
14990
  this.scope.addReturnExpression(this.argument || UNKNOWN_EXPRESSION);
@@ -15756,7 +14998,6 @@ class ReturnStatement extends NodeBase {
15756
14998
  }
15757
14999
  }
15758
15000
  }
15759
- ReturnStatement.prototype.applyDeoptimizations = doNotDeoptimize;
15760
15001
 
15761
15002
  class SequenceExpression extends NodeBase {
15762
15003
  deoptimizeArgumentsOnInteractionAtPath(interaction, path, recursionTracker) {
@@ -15784,15 +15025,10 @@ class SequenceExpression extends NodeBase {
15784
15025
  for (const expression of this.expressions) {
15785
15026
  if (includeChildrenRecursively ||
15786
15027
  (expression === lastExpression && !(this.parent instanceof ExpressionStatement)) ||
15787
- expression.shouldBeIncluded(context)) {
15028
+ expression.shouldBeIncluded(context))
15788
15029
  expression.include(context, includeChildrenRecursively);
15789
- }
15790
15030
  }
15791
15031
  }
15792
- includePath(path, context) {
15793
- this.included = true;
15794
- this.expressions[this.expressions.length - 1].includePath(path, context);
15795
- }
15796
15032
  removeAnnotations(code) {
15797
15033
  this.expressions[0].removeAnnotations(code);
15798
15034
  }
@@ -15827,8 +15063,6 @@ class SequenceExpression extends NodeBase {
15827
15063
  }
15828
15064
  }
15829
15065
  }
15830
- SequenceExpression.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
15831
- SequenceExpression.prototype.applyDeoptimizations = doNotDeoptimize;
15832
15066
 
15833
15067
  class Super extends NodeBase {
15834
15068
  bind() {
@@ -15840,15 +15074,11 @@ class Super extends NodeBase {
15840
15074
  deoptimizePath(path) {
15841
15075
  this.variable.deoptimizePath(path);
15842
15076
  }
15843
- include(context) {
15844
- if (!this.included)
15845
- this.includeNode(context);
15846
- }
15847
- includeNode(context) {
15848
- this.included = true;
15849
- if (!this.deoptimized)
15850
- this.applyDeoptimizations();
15851
- this.scope.context.includeVariableInModule(this.variable, EMPTY_PATH, context);
15077
+ include() {
15078
+ if (!this.included) {
15079
+ this.included = true;
15080
+ this.scope.context.includeVariableInModule(this.variable);
15081
+ }
15852
15082
  }
15853
15083
  }
15854
15084
 
@@ -15889,8 +15119,6 @@ class SwitchCase extends NodeBase {
15889
15119
  }
15890
15120
  }
15891
15121
  SwitchCase.prototype.needsBoundaries = true;
15892
- SwitchCase.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
15893
- SwitchCase.prototype.applyDeoptimizations = doNotDeoptimize;
15894
15122
 
15895
15123
  class SwitchStatement extends NodeBase {
15896
15124
  createScope(parentScope) {
@@ -15973,8 +15201,6 @@ class SwitchStatement extends NodeBase {
15973
15201
  }
15974
15202
  }
15975
15203
  }
15976
- SwitchStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
15977
- SwitchStatement.prototype.applyDeoptimizations = doNotDeoptimize;
15978
15204
 
15979
15205
  class TaggedTemplateExpression extends CallExpressionBase {
15980
15206
  bind() {
@@ -15998,8 +15224,8 @@ class TaggedTemplateExpression extends CallExpressionBase {
15998
15224
  this.tag.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.interaction, context));
15999
15225
  }
16000
15226
  include(context, includeChildrenRecursively) {
16001
- if (!this.included)
16002
- this.includeNode(context);
15227
+ if (!this.deoptimized)
15228
+ this.applyDeoptimizations();
16003
15229
  if (includeChildrenRecursively) {
16004
15230
  super.include(context, includeChildrenRecursively);
16005
15231
  }
@@ -16008,7 +15234,7 @@ class TaggedTemplateExpression extends CallExpressionBase {
16008
15234
  this.tag.include(context, includeChildrenRecursively);
16009
15235
  this.quasi.include(context, includeChildrenRecursively);
16010
15236
  }
16011
- this.tag.includeCallArguments(context, this.interaction);
15237
+ this.tag.includeCallArguments(context, this.args);
16012
15238
  const [returnExpression] = this.getReturnExpression();
16013
15239
  if (!returnExpression.included) {
16014
15240
  returnExpression.include(context, false);
@@ -16043,7 +15269,6 @@ class TaggedTemplateExpression extends CallExpressionBase {
16043
15269
  return this.returnExpression;
16044
15270
  }
16045
15271
  }
16046
- TaggedTemplateExpression.prototype.includeNode = onlyIncludeSelf;
16047
15272
 
16048
15273
  class TemplateElement extends NodeBase {
16049
15274
  get tail() {
@@ -16057,13 +15282,15 @@ class TemplateElement extends NodeBase {
16057
15282
  hasEffects() {
16058
15283
  return false;
16059
15284
  }
15285
+ include() {
15286
+ this.included = true;
15287
+ }
16060
15288
  parseNode(esTreeNode) {
16061
15289
  this.value = esTreeNode.value;
16062
15290
  return super.parseNode(esTreeNode);
16063
15291
  }
16064
15292
  render() { }
16065
15293
  }
16066
- TemplateElement.prototype.includeNode = onlyIncludeSelf;
16067
15294
 
16068
15295
  class TemplateLiteral extends NodeBase {
16069
15296
  deoptimizeArgumentsOnInteractionAtPath() { }
@@ -16088,14 +15315,6 @@ class TemplateLiteral extends NodeBase {
16088
15315
  }
16089
15316
  return true;
16090
15317
  }
16091
- includeNode(context) {
16092
- this.included = true;
16093
- if (!this.deoptimized)
16094
- this.applyDeoptimizations();
16095
- for (const node of this.expressions) {
16096
- node.includePath(UNKNOWN_PATH, context);
16097
- }
16098
- }
16099
15318
  render(code, options) {
16100
15319
  code.indentExclusionRanges.push([this.start, this.end]);
16101
15320
  super.render(code, options);
@@ -16105,13 +15324,13 @@ class TemplateLiteral extends NodeBase {
16105
15324
  class ModuleScope extends ChildScope {
16106
15325
  constructor(parent, context) {
16107
15326
  super(parent, context);
16108
- this.variables.set('this', new LocalVariable('this', null, UNDEFINED_EXPRESSION, EMPTY_PATH, context, 'other'));
15327
+ this.variables.set('this', new LocalVariable('this', null, UNDEFINED_EXPRESSION, context, 'other'));
16109
15328
  }
16110
- addDeclaration(identifier, context, init, destructuredInitPath, kind) {
15329
+ addDeclaration(identifier, context, init, kind) {
16111
15330
  if (this.context.module.importDescriptions.has(identifier.name)) {
16112
15331
  context.error(parseAst_js.logRedeclarationError(identifier.name), identifier.start);
16113
15332
  }
16114
- return super.addDeclaration(identifier, context, init, destructuredInitPath, kind);
15333
+ return super.addDeclaration(identifier, context, init, kind);
16115
15334
  }
16116
15335
  addExportDefaultDeclaration(name, exportDefaultDeclaration, context) {
16117
15336
  const variable = new ExportDefaultVariable(name, exportDefaultDeclaration, context);
@@ -16156,23 +15375,10 @@ class ThisExpression extends NodeBase {
16156
15375
  }
16157
15376
  return this.variable.hasEffectsOnInteractionAtPath(path, interaction, context);
16158
15377
  }
16159
- include(context) {
16160
- if (!this.included)
16161
- this.includeNode(context);
16162
- }
16163
- includeNode(context) {
16164
- this.included = true;
16165
- if (!this.deoptimized)
16166
- this.applyDeoptimizations();
16167
- this.scope.context.includeVariableInModule(this.variable, EMPTY_PATH, context);
16168
- }
16169
- includePath(path, context) {
15378
+ include() {
16170
15379
  if (!this.included) {
16171
15380
  this.included = true;
16172
- this.scope.context.includeVariableInModule(this.variable, path, context);
16173
- }
16174
- else if (path.length > 0) {
16175
- this.variable.includePath(path, context);
15381
+ this.scope.context.includeVariableInModule(this.variable);
16176
15382
  }
16177
15383
  }
16178
15384
  initialise() {
@@ -16200,8 +15406,7 @@ class ThrowStatement extends NodeBase {
16200
15406
  return true;
16201
15407
  }
16202
15408
  include(context, includeChildrenRecursively) {
16203
- if (!this.included)
16204
- this.includeNode(context);
15409
+ this.included = true;
16205
15410
  this.argument.include(context, includeChildrenRecursively);
16206
15411
  context.brokenFlow = true;
16207
15412
  }
@@ -16212,7 +15417,6 @@ class ThrowStatement extends NodeBase {
16212
15417
  }
16213
15418
  }
16214
15419
  }
16215
- ThrowStatement.prototype.includeNode = onlyIncludeSelf;
16216
15420
 
16217
15421
  class TryStatement extends NodeBase {
16218
15422
  constructor() {
@@ -16249,8 +15453,6 @@ class TryStatement extends NodeBase {
16249
15453
  this.finalizer?.include(context, includeChildrenRecursively);
16250
15454
  }
16251
15455
  }
16252
- TryStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
16253
- TryStatement.prototype.applyDeoptimizations = doNotDeoptimize;
16254
15456
 
16255
15457
  const unaryOperators = {
16256
15458
  '!': value => !value,
@@ -16357,7 +15559,6 @@ function getSimplifiedNumber(value) {
16357
15559
  const stringifiedValue = String(value).replace('+', '');
16358
15560
  return finalizedExp.length < stringifiedValue.length ? finalizedExp : stringifiedValue;
16359
15561
  }
16360
- UnaryExpression.prototype.includeNode = onlyIncludeSelf;
16361
15562
 
16362
15563
  class UpdateExpression extends NodeBase {
16363
15564
  hasEffects(context) {
@@ -16369,8 +15570,9 @@ class UpdateExpression extends NodeBase {
16369
15570
  return path.length > 1 || type !== INTERACTION_ACCESSED;
16370
15571
  }
16371
15572
  include(context, includeChildrenRecursively) {
16372
- if (!this.included)
16373
- this.includeNode(context);
15573
+ if (!this.deoptimized)
15574
+ this.applyDeoptimizations();
15575
+ this.included = true;
16374
15576
  this.argument.includeAsAssignmentTarget(context, includeChildrenRecursively, true);
16375
15577
  }
16376
15578
  initialise() {
@@ -16409,7 +15611,6 @@ class UpdateExpression extends NodeBase {
16409
15611
  this.scope.context.requestTreeshakingPass();
16410
15612
  }
16411
15613
  }
16412
- UpdateExpression.prototype.includeNode = onlyIncludeSelf;
16413
15614
 
16414
15615
  function areAllDeclarationsIncludedAndNotExported(declarations, exportNamesByVariable) {
16415
15616
  for (const declarator of declarations) {
@@ -16440,9 +15641,8 @@ class VariableDeclaration extends NodeBase {
16440
15641
  include(context, includeChildrenRecursively, { asSingleStatement } = parseAst_js.BLANK) {
16441
15642
  this.included = true;
16442
15643
  for (const declarator of this.declarations) {
16443
- if (includeChildrenRecursively || declarator.shouldBeIncluded(context)) {
15644
+ if (includeChildrenRecursively || declarator.shouldBeIncluded(context))
16444
15645
  declarator.include(context, includeChildrenRecursively);
16445
- }
16446
15646
  const { id, init } = declarator;
16447
15647
  if (asSingleStatement) {
16448
15648
  id.include(context, includeChildrenRecursively);
@@ -16480,6 +15680,7 @@ class VariableDeclaration extends NodeBase {
16480
15680
  this.renderReplacedDeclarations(code, options);
16481
15681
  }
16482
15682
  }
15683
+ applyDeoptimizations() { }
16483
15684
  renderDeclarationEnd(code, separatorString, lastSeparatorPos, actualContentEnd, renderedContentEnd, systemPatternExports, options) {
16484
15685
  if (code.original.charCodeAt(this.end - 1) === 59 /*";"*/) {
16485
15686
  code.remove(this.end - 1, this.end);
@@ -16522,7 +15723,8 @@ class VariableDeclaration extends NodeBase {
16522
15723
  const singleSystemExport = gatherSystemExportsAndGetSingleExport(separatedNodes, options, aggregatedSystemExports);
16523
15724
  for (const { node, start, separator, contentEnd, end } of separatedNodes) {
16524
15725
  if (!node.included) {
16525
- treeshakeNode(node, code, start, end);
15726
+ code.remove(start, end);
15727
+ node.removeAnnotations(code);
16526
15728
  continue;
16527
15729
  }
16528
15730
  node.render(code, options);
@@ -16592,8 +15794,6 @@ function gatherSystemExportsAndGetSingleExport(separatedNodes, options, aggregat
16592
15794
  }
16593
15795
  return singleSystemExport;
16594
15796
  }
16595
- VariableDeclaration.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
16596
- VariableDeclaration.prototype.applyDeoptimizations = doNotDeoptimize;
16597
15797
 
16598
15798
  class WhileStatement extends NodeBase {
16599
15799
  hasEffects(context) {
@@ -16607,25 +15807,13 @@ class WhileStatement extends NodeBase {
16607
15807
  includeLoopBody(context, this.body, includeChildrenRecursively);
16608
15808
  }
16609
15809
  }
16610
- WhileStatement.prototype.includeNode = onlyIncludeSelfNoDeoptimize;
16611
- WhileStatement.prototype.applyDeoptimizations = doNotDeoptimize;
16612
15810
 
16613
15811
  class YieldExpression extends NodeBase {
16614
- applyDeoptimizations() {
16615
- this.deoptimized = true;
16616
- this.argument?.deoptimizePath(UNKNOWN_PATH);
16617
- }
16618
15812
  hasEffects(context) {
16619
15813
  if (!this.deoptimized)
16620
15814
  this.applyDeoptimizations();
16621
15815
  return !(context.ignore.returnYield && !this.argument?.hasEffects(context));
16622
15816
  }
16623
- includeNode(context) {
16624
- this.included = true;
16625
- if (!this.deoptimized)
16626
- this.applyDeoptimizations();
16627
- this.argument?.includePath(UNKNOWN_PATH, context);
16628
- }
16629
15817
  render(code, options) {
16630
15818
  if (this.argument) {
16631
15819
  this.argument.render(code, options, { preventASI: true });
@@ -16859,7 +16047,7 @@ const bufferParsers = [
16859
16047
  const annotations = (node.annotations = parseAst_js.convertAnnotations(buffer[position + 1], buffer));
16860
16048
  node.annotationNoSideEffects = annotations.some(comment => comment.type === 'noSideEffects');
16861
16049
  const parameters = (node.params = convertNodeList(node, scope, buffer[position + 2], buffer));
16862
- scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', EMPTY_PATH, UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
16050
+ scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
16863
16051
  node.body = convertNode(node, scope.bodyScope, buffer[position + 3], buffer);
16864
16052
  },
16865
16053
  function assignmentExpression(node, position, buffer) {
@@ -16905,7 +16093,7 @@ const bufferParsers = [
16905
16093
  const parameterPosition = buffer[position];
16906
16094
  const parameter = (node.param =
16907
16095
  parameterPosition === 0 ? null : convertNode(node, scope, parameterPosition, buffer));
16908
- parameter?.declare('parameter', EMPTY_PATH, UNKNOWN_EXPRESSION);
16096
+ parameter?.declare('parameter', UNKNOWN_EXPRESSION);
16909
16097
  node.body = convertNode(node, scope.bodyScope, buffer[position + 1], buffer);
16910
16098
  },
16911
16099
  function chainExpression(node, position, buffer) {
@@ -17043,7 +16231,7 @@ const bufferParsers = [
17043
16231
  node.id =
17044
16232
  idPosition === 0 ? null : convertNode(node, scope.parent, idPosition, buffer);
17045
16233
  const parameters = (node.params = convertNodeList(node, scope, buffer[position + 3], buffer));
17046
- scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', EMPTY_PATH, UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
16234
+ scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
17047
16235
  node.body = convertNode(node, scope.bodyScope, buffer[position + 4], buffer);
17048
16236
  },
17049
16237
  function functionExpression(node, position, buffer) {
@@ -17056,7 +16244,7 @@ const bufferParsers = [
17056
16244
  const idPosition = buffer[position + 2];
17057
16245
  node.id = idPosition === 0 ? null : convertNode(node, node.idScope, idPosition, buffer);
17058
16246
  const parameters = (node.params = convertNodeList(node, scope, buffer[position + 3], buffer));
17059
- scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', EMPTY_PATH, UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
16247
+ scope.addParameterVariables(parameters.map(parameter => parameter.declare('parameter', UNKNOWN_EXPRESSION)), parameters[parameters.length - 1] instanceof RestElement);
17060
16248
  node.body = convertNode(node, scope.bodyScope, buffer[position + 4], buffer);
17061
16249
  },
17062
16250
  function identifier(node, position, buffer) {
@@ -17520,8 +16708,8 @@ class ExportShimVariable extends Variable {
17520
16708
  super(MISSING_EXPORT_SHIM_VARIABLE);
17521
16709
  this.module = module;
17522
16710
  }
17523
- includePath(path, context) {
17524
- super.includePath(path, context);
16711
+ include() {
16712
+ super.include();
17525
16713
  this.module.needsExportShim = true;
17526
16714
  }
17527
16715
  }
@@ -18212,15 +17400,16 @@ class Module {
18212
17400
  markModuleAndImpureDependenciesAsExecuted(this);
18213
17401
  this.graph.needsTreeshakingPass = true;
18214
17402
  }
18215
- const inclusionContext = createInclusionContext();
18216
17403
  for (const exportName of this.exports.keys()) {
18217
17404
  if (includeNamespaceMembers || exportName !== this.info.syntheticNamedExports) {
18218
17405
  const variable = this.getVariableForExportName(exportName)[0];
18219
17406
  if (!variable) {
18220
17407
  return parseAst_js.error(parseAst_js.logMissingEntryExport(exportName, this.id));
18221
17408
  }
18222
- this.includeVariable(variable, UNKNOWN_PATH, inclusionContext);
18223
17409
  variable.deoptimizePath(UNKNOWN_PATH);
17410
+ if (!variable.included) {
17411
+ this.includeVariable(variable);
17412
+ }
18224
17413
  }
18225
17414
  }
18226
17415
  for (const name of this.getReexports()) {
@@ -18228,7 +17417,7 @@ class Module {
18228
17417
  if (variable) {
18229
17418
  variable.deoptimizePath(UNKNOWN_PATH);
18230
17419
  if (!variable.included) {
18231
- this.includeVariable(variable, UNKNOWN_PATH, inclusionContext);
17420
+ this.includeVariable(variable);
18232
17421
  }
18233
17422
  if (variable instanceof ExternalVariable) {
18234
17423
  variable.module.reexported = true;
@@ -18249,12 +17438,13 @@ class Module {
18249
17438
  this.graph.needsTreeshakingPass = true;
18250
17439
  }
18251
17440
  let includeNamespaceMembers = false;
18252
- const inclusionContext = createInclusionContext();
18253
17441
  for (const name of names) {
18254
17442
  const variable = this.getVariableForExportName(name)[0];
18255
17443
  if (variable) {
18256
17444
  variable.deoptimizePath(UNKNOWN_PATH);
18257
- this.includeVariable(variable, UNKNOWN_PATH, inclusionContext);
17445
+ if (!variable.included) {
17446
+ this.includeVariable(variable);
17447
+ }
18258
17448
  }
18259
17449
  if (!this.exports.has(name) && !this.reexportDescriptions.has(name)) {
18260
17450
  includeNamespaceMembers = true;
@@ -18355,7 +17545,6 @@ class Module {
18355
17545
  manualPureFunctions: this.graph.pureFunctions,
18356
17546
  module: this,
18357
17547
  moduleContext: this.context,
18358
- newlyIncludedVariableInits: this.graph.newlyIncludedVariableInits,
18359
17548
  options: this.options,
18360
17549
  requestTreeshakingPass: () => (this.graph.needsTreeshakingPass = true),
18361
17550
  traceExport: (name) => this.getVariableForExportName(name)[0],
@@ -18696,13 +17885,13 @@ class Module {
18696
17885
  for (const module of [this, ...this.exportAllModules]) {
18697
17886
  if (module instanceof ExternalModule) {
18698
17887
  const [externalVariable] = module.getVariableForExportName('*');
18699
- externalVariable.includePath(UNKNOWN_PATH, createInclusionContext());
17888
+ externalVariable.include();
18700
17889
  this.includedImports.add(externalVariable);
18701
17890
  externalNamespaces.add(externalVariable);
18702
17891
  }
18703
17892
  else if (module.info.syntheticNamedExports) {
18704
17893
  const syntheticNamespace = module.getSyntheticNamespace();
18705
- syntheticNamespace.includePath(UNKNOWN_PATH, createInclusionContext());
17894
+ syntheticNamespace.include();
18706
17895
  this.includedImports.add(syntheticNamespace);
18707
17896
  syntheticNamespaces.add(syntheticNamespace);
18708
17897
  }
@@ -18712,9 +17901,7 @@ class Module {
18712
17901
  includeDynamicImport(node) {
18713
17902
  const resolution = this.dynamicImports.find(dynamicImport => dynamicImport.node === node).resolution;
18714
17903
  if (resolution instanceof Module) {
18715
- if (!resolution.includedDynamicImporters.includes(this)) {
18716
- resolution.includedDynamicImporters.push(this);
18717
- }
17904
+ resolution.includedDynamicImporters.push(this);
18718
17905
  const importedNames = this.options.treeshake
18719
17906
  ? node.getDeterministicImportedNames()
18720
17907
  : undefined;
@@ -18726,15 +17913,15 @@ class Module {
18726
17913
  }
18727
17914
  }
18728
17915
  }
18729
- includeVariable(variable, path, context) {
18730
- const { included, module: variableModule } = variable;
18731
- variable.includePath(path, context);
18732
- if (included) {
17916
+ includeVariable(variable) {
17917
+ const variableModule = variable.module;
17918
+ if (variable.included) {
18733
17919
  if (variableModule instanceof Module && variableModule !== this) {
18734
17920
  getAndExtendSideEffectModules(variable, this);
18735
17921
  }
18736
17922
  }
18737
17923
  else {
17924
+ variable.include();
18738
17925
  this.graph.needsTreeshakingPass = true;
18739
17926
  if (variableModule instanceof Module) {
18740
17927
  if (!variableModule.isExecuted) {
@@ -18751,8 +17938,8 @@ class Module {
18751
17938
  }
18752
17939
  }
18753
17940
  }
18754
- includeVariableInModule(variable, path, context) {
18755
- this.includeVariable(variable, path, context);
17941
+ includeVariableInModule(variable) {
17942
+ this.includeVariable(variable);
18756
17943
  const variableModule = variable.module;
18757
17944
  if (variableModule && variableModule !== this) {
18758
17945
  this.includedImports.add(variable);
@@ -21632,6 +20819,13 @@ async function findFile(file, preserveSymlinks) {
21632
20819
  }
21633
20820
  }
21634
20821
 
20822
+ function stripBom(content) {
20823
+ if (content.charCodeAt(0) === 0xfe_ff) {
20824
+ return stripBom(content.slice(1));
20825
+ }
20826
+ return content;
20827
+ }
20828
+
21635
20829
  async function transform(source, module, pluginDriver, log) {
21636
20830
  const id = module.id;
21637
20831
  const sourcemapChain = [];
@@ -21873,10 +21067,7 @@ class ModuleLoader {
21873
21067
  : source != null && typeof source === 'object' && typeof source.code === 'string'
21874
21068
  ? source
21875
21069
  : parseAst_js.error(parseAst_js.logBadLoader(id));
21876
- const code = sourceDescription.code;
21877
- if (code.charCodeAt(0) === 0xfe_ff) {
21878
- sourceDescription.code = code.slice(1);
21879
- }
21070
+ sourceDescription.code = stripBom(sourceDescription.code);
21880
21071
  const cachedModule = this.graph.cachedModules.get(id);
21881
21072
  if (cachedModule &&
21882
21073
  !cachedModule.customTransformCache &&
@@ -22257,11 +21448,10 @@ class Graph {
22257
21448
  this.options = options;
22258
21449
  this.astLru = flru(5);
22259
21450
  this.cachedModules = new Map();
22260
- this.deoptimizationTracker = new EntityPathTracker();
21451
+ this.deoptimizationTracker = new PathTracker();
22261
21452
  this.entryModules = [];
22262
21453
  this.modulesById = new Map();
22263
21454
  this.needsTreeshakingPass = false;
22264
- this.newlyIncludedVariableInits = new Set();
22265
21455
  this.phase = BuildPhase.LOAD_AND_PARSE;
22266
21456
  this.scope = new GlobalScope();
22267
21457
  this.watchFiles = Object.create(null);
@@ -22355,7 +21545,6 @@ class Graph {
22355
21545
  }
22356
21546
  if (this.options.treeshake) {
22357
21547
  let treeshakingPass = 1;
22358
- this.newlyIncludedVariableInits.clear();
22359
21548
  do {
22360
21549
  timeStart(`treeshaking pass ${treeshakingPass}`, 3);
22361
21550
  this.needsTreeshakingPass = false;
@@ -22368,10 +21557,6 @@ class Graph {
22368
21557
  else {
22369
21558
  module.include();
22370
21559
  }
22371
- for (const entity of this.newlyIncludedVariableInits) {
22372
- this.newlyIncludedVariableInits.delete(entity);
22373
- entity.include(createInclusionContext(), false);
22374
- }
22375
21560
  }
22376
21561
  }
22377
21562
  if (treeshakingPass === 1) {