@@ -570,6 +570,31 @@ namespace ts {
570
570
}
571
571
}
572
572
573
+ function bindEach ( nodes : NodeArray < Node > ) {
574
+ if ( nodes === undefined ) {
575
+ return ;
576
+ }
577
+
578
+ if ( skipTransformFlagAggregation ) {
579
+ forEach ( nodes , bind ) ;
580
+ }
581
+ else {
582
+ const savedSubtreeTransformFlags = subtreeTransformFlags ;
583
+ subtreeTransformFlags = TransformFlags . None ;
584
+ let nodeArrayFlags = TransformFlags . None ;
585
+ for ( const node of nodes ) {
586
+ bind ( node ) ;
587
+ nodeArrayFlags |= node . transformFlags & ~ TransformFlags . HasComputedFlags ;
588
+ }
589
+ nodes . transformFlags = nodeArrayFlags | TransformFlags . HasComputedFlags ;
590
+ subtreeTransformFlags |= savedSubtreeTransformFlags ;
591
+ }
592
+ }
593
+
594
+ function bindEachChild ( node : Node ) {
595
+ forEachChild ( node , bind , bindEach ) ;
596
+ }
597
+
573
598
function bindChildrenWorker ( node : Node ) : void {
574
599
// Binding of JsDocComment should be done before the current block scope container changes.
575
600
// because the scope of JsDocComment should not be affected by whether the current node is a
@@ -578,7 +603,7 @@ namespace ts {
578
603
forEach ( node . jsDocComments , bind ) ;
579
604
}
580
605
if ( checkUnreachable ( node ) ) {
581
- forEachChild ( node , bind ) ;
606
+ bindEachChild ( node ) ;
582
607
return ;
583
608
}
584
609
switch ( node . kind ) {
@@ -643,7 +668,7 @@ namespace ts {
643
668
bindCallExpressionFlow ( < CallExpression > node ) ;
644
669
break ;
645
670
default :
646
- forEachChild ( node , bind ) ;
671
+ bindEachChild ( node ) ;
647
672
break ;
648
673
}
649
674
}
@@ -976,7 +1001,7 @@ namespace ts {
976
1001
return undefined ;
977
1002
}
978
1003
979
- function bindbreakOrContinueFlow ( node : BreakOrContinueStatement , breakTarget : FlowLabel , continueTarget : FlowLabel ) {
1004
+ function bindBreakOrContinueFlow ( node : BreakOrContinueStatement , breakTarget : FlowLabel , continueTarget : FlowLabel ) {
980
1005
const flowLabel = node . kind === SyntaxKind . BreakStatement ? breakTarget : continueTarget ;
981
1006
if ( flowLabel ) {
982
1007
addAntecedent ( flowLabel , currentFlow ) ;
@@ -990,11 +1015,11 @@ namespace ts {
990
1015
const activeLabel = findActiveLabel ( node . label . text ) ;
991
1016
if ( activeLabel ) {
992
1017
activeLabel . referenced = true ;
993
- bindbreakOrContinueFlow ( node , activeLabel . breakTarget , activeLabel . continueTarget ) ;
1018
+ bindBreakOrContinueFlow ( node , activeLabel . breakTarget , activeLabel . continueTarget ) ;
994
1019
}
995
1020
}
996
1021
else {
997
- bindbreakOrContinueFlow ( node , currentBreakTarget , currentContinueTarget ) ;
1022
+ bindBreakOrContinueFlow ( node , currentBreakTarget , currentContinueTarget ) ;
998
1023
}
999
1024
}
1000
1025
@@ -1062,6 +1087,8 @@ namespace ts {
1062
1087
}
1063
1088
1064
1089
function bindCaseBlock ( node : CaseBlock ) : void {
1090
+ const savedSubtreeTransformFlags = subtreeTransformFlags ;
1091
+ subtreeTransformFlags = 0 ;
1065
1092
const clauses = node . clauses ;
1066
1093
let fallthroughFlow = unreachableFlow ;
1067
1094
for ( let i = 0 ; i < clauses . length ; i ++ ) {
@@ -1081,14 +1108,16 @@ namespace ts {
1081
1108
errorOnFirstToken ( clause , Diagnostics . Fallthrough_case_in_switch ) ;
1082
1109
}
1083
1110
}
1111
+ clauses . transformFlags = subtreeTransformFlags | TransformFlags . HasComputedFlags ;
1112
+ subtreeTransformFlags |= savedSubtreeTransformFlags ;
1084
1113
}
1085
1114
1086
1115
function bindCaseClause ( node : CaseClause ) : void {
1087
1116
const saveCurrentFlow = currentFlow ;
1088
1117
currentFlow = preSwitchCaseFlow ;
1089
1118
bind ( node . expression ) ;
1090
1119
currentFlow = saveCurrentFlow ;
1091
- forEach ( node . statements , bind ) ;
1120
+ bindEach ( node . statements ) ;
1092
1121
}
1093
1122
1094
1123
function pushActiveLabel ( name : string , breakTarget : FlowLabel , continueTarget : FlowLabel ) : ActiveLabel {
@@ -1180,20 +1209,20 @@ namespace ts {
1180
1209
const saveTrueTarget = currentTrueTarget ;
1181
1210
currentTrueTarget = currentFalseTarget ;
1182
1211
currentFalseTarget = saveTrueTarget ;
1183
- forEachChild ( node , bind ) ;
1212
+ bindEachChild ( node ) ;
1184
1213
currentFalseTarget = currentTrueTarget ;
1185
1214
currentTrueTarget = saveTrueTarget ;
1186
1215
}
1187
1216
else {
1188
- forEachChild ( node , bind ) ;
1217
+ bindEachChild ( node ) ;
1189
1218
if ( node . operator === SyntaxKind . PlusPlusToken || node . operator === SyntaxKind . MinusMinusToken ) {
1190
1219
bindAssignmentTargetFlow ( node . operand ) ;
1191
1220
}
1192
1221
}
1193
1222
}
1194
1223
1195
1224
function bindPostfixUnaryExpressionFlow ( node : PostfixUnaryExpression ) {
1196
- forEachChild ( node , bind ) ;
1225
+ bindEachChild ( node ) ;
1197
1226
if ( node . operator === SyntaxKind . PlusPlusToken || node . operator === SyntaxKind . MinusMinusToken ) {
1198
1227
bindAssignmentTargetFlow ( node . operand ) ;
1199
1228
}
@@ -1212,7 +1241,7 @@ namespace ts {
1212
1241
}
1213
1242
}
1214
1243
else {
1215
- forEachChild ( node , bind ) ;
1244
+ bindEachChild ( node ) ;
1216
1245
if ( isAssignmentOperator ( operator ) && ! isAssignmentTarget ( node ) ) {
1217
1246
bindAssignmentTargetFlow ( node . left ) ;
1218
1247
if ( operator === SyntaxKind . EqualsToken && node . left . kind === SyntaxKind . ElementAccessExpression ) {
@@ -1226,7 +1255,7 @@ namespace ts {
1226
1255
}
1227
1256
1228
1257
function bindDeleteExpressionFlow ( node : DeleteExpression ) {
1229
- forEachChild ( node , bind ) ;
1258
+ bindEachChild ( node ) ;
1230
1259
if ( node . expression . kind === SyntaxKind . PropertyAccessExpression ) {
1231
1260
bindAssignmentTargetFlow ( node . expression ) ;
1232
1261
}
@@ -1261,7 +1290,7 @@ namespace ts {
1261
1290
}
1262
1291
1263
1292
function bindVariableDeclarationFlow ( node : VariableDeclaration ) {
1264
- forEachChild ( node , bind ) ;
1293
+ bindEachChild ( node ) ;
1265
1294
if ( node . initializer || node . parent . parent . kind === SyntaxKind . ForInStatement || node . parent . parent . kind === SyntaxKind . ForOfStatement ) {
1266
1295
bindInitializedVariableFlow ( node ) ;
1267
1296
}
@@ -1276,12 +1305,12 @@ namespace ts {
1276
1305
expr = ( < ParenthesizedExpression > expr ) . expression ;
1277
1306
}
1278
1307
if ( expr . kind === SyntaxKind . FunctionExpression || expr . kind === SyntaxKind . ArrowFunction ) {
1279
- forEach ( node . typeArguments , bind ) ;
1280
- forEach ( node . arguments , bind ) ;
1308
+ bindEach ( node . typeArguments ) ;
1309
+ bindEach ( node . arguments ) ;
1281
1310
bind ( node . expression ) ;
1282
1311
}
1283
1312
else {
1284
- forEachChild ( node , bind ) ;
1313
+ bindEachChild ( node ) ;
1285
1314
}
1286
1315
if ( node . expression . kind === SyntaxKind . PropertyAccessExpression ) {
1287
1316
const propertyAccess = < PropertyAccessExpression > node . expression ;
@@ -2514,7 +2543,7 @@ namespace ts {
2514
2543
transformFlags |= TransformFlags . AssertTypeScript ;
2515
2544
}
2516
2545
2517
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression
2546
+ if ( subtreeFlags & TransformFlags . ContainsSpread
2518
2547
|| isSuperOrSuperProperty ( expression , expressionKind ) ) {
2519
2548
// If the this node contains a SpreadExpression, or is a super call, then it is an ES6
2520
2549
// node.
@@ -2545,7 +2574,7 @@ namespace ts {
2545
2574
if ( node . typeArguments ) {
2546
2575
transformFlags |= TransformFlags . AssertTypeScript ;
2547
2576
}
2548
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2577
+ if ( subtreeFlags & TransformFlags . ContainsSpread ) {
2549
2578
// If the this node contains a SpreadElementExpression then it is an ES6
2550
2579
// node.
2551
2580
transformFlags |= TransformFlags . AssertES2015 ;
@@ -2554,7 +2583,6 @@ namespace ts {
2554
2583
return transformFlags & ~ TransformFlags . ArrayLiteralOrCallOrNewExcludes ;
2555
2584
}
2556
2585
2557
-
2558
2586
function computeBinaryExpression ( node : BinaryExpression , subtreeFlags : TransformFlags ) {
2559
2587
let transformFlags = subtreeFlags ;
2560
2588
const operatorTokenKind = node . operatorToken . kind ;
@@ -2601,7 +2629,7 @@ namespace ts {
2601
2629
}
2602
2630
2603
2631
// parameters with object rest destructuring are ES Next syntax
2604
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2632
+ if ( subtreeFlags & ( TransformFlags . ContainsRest | TransformFlags . ContainsObjectRest ) ) {
2605
2633
transformFlags |= TransformFlags . AssertESNext ;
2606
2634
}
2607
2635
@@ -2723,7 +2751,7 @@ namespace ts {
2723
2751
}
2724
2752
2725
2753
node . transformFlags = transformFlags | TransformFlags . HasComputedFlags ;
2726
- return transformFlags & ~ TransformFlags . NodeExcludes ;
2754
+ return transformFlags & ~ TransformFlags . CatchClauseExcludes ;
2727
2755
}
2728
2756
2729
2757
function computeExpressionWithTypeArguments ( node : ExpressionWithTypeArguments , subtreeFlags : TransformFlags ) {
@@ -2839,7 +2867,7 @@ namespace ts {
2839
2867
}
2840
2868
2841
2869
// function declarations with object rest destructuring are ES Next syntax
2842
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2870
+ if ( subtreeFlags & ( TransformFlags . ContainsRest | TransformFlags . ContainsObjectRest ) ) {
2843
2871
transformFlags |= TransformFlags . AssertESNext ;
2844
2872
}
2845
2873
@@ -2881,7 +2909,7 @@ namespace ts {
2881
2909
}
2882
2910
2883
2911
// function expressions with object rest destructuring are ES Next syntax
2884
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2912
+ if ( subtreeFlags & ( TransformFlags . ContainsRest | TransformFlags . ContainsObjectRest ) ) {
2885
2913
transformFlags |= TransformFlags . AssertESNext ;
2886
2914
}
2887
2915
@@ -2924,7 +2952,7 @@ namespace ts {
2924
2952
}
2925
2953
2926
2954
// arrow functions with object rest destructuring are ES Next syntax
2927
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2955
+ if ( subtreeFlags & ( TransformFlags . ContainsRest | TransformFlags . ContainsObjectRest ) ) {
2928
2956
transformFlags |= TransformFlags . AssertESNext ;
2929
2957
}
2930
2958
@@ -3178,16 +3206,19 @@ namespace ts {
3178
3206
break ;
3179
3207
3180
3208
case SyntaxKind . SpreadElement :
3209
+ transformFlags |= TransformFlags . AssertES2015 | TransformFlags . ContainsSpread ;
3210
+ break ;
3211
+
3181
3212
case SyntaxKind . SpreadAssignment :
3182
- // This node is ES6 or ES next syntax, but is handled by a containing node.
3183
- transformFlags |= TransformFlags . ContainsSpreadExpression ;
3213
+ transformFlags |= TransformFlags . AssertESNext | TransformFlags . ContainsSpread | TransformFlags . ContainsObjectSpread ;
3184
3214
break ;
3185
3215
3186
3216
case SyntaxKind . BindingElement :
3187
- if ( ( node as BindingElement ) . dotDotDotToken ) {
3188
- // this node is ES2015 or ES next syntax, but is handled by a containing node.
3189
- transformFlags |= TransformFlags . ContainsSpreadExpression ;
3217
+ transformFlags |= TransformFlags . AssertES2015 ;
3218
+ if ( ( < BindingElement > node ) . dotDotDotToken ) {
3219
+ transformFlags |= TransformFlags . ContainsRest ;
3190
3220
}
3221
+ break ;
3191
3222
3192
3223
case SyntaxKind . SuperKeyword :
3193
3224
// This node is ES6 syntax.
@@ -3200,14 +3231,16 @@ namespace ts {
3200
3231
break ;
3201
3232
3202
3233
case SyntaxKind . ObjectBindingPattern :
3203
- case SyntaxKind . ArrayBindingPattern :
3204
- // These nodes are ES2015 or ES Next syntax.
3205
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
3206
- transformFlags |= TransformFlags . AssertESNext | TransformFlags . ContainsBindingPattern ;
3207
- }
3208
- else {
3209
- transformFlags |= TransformFlags . AssertES2015 | TransformFlags . ContainsBindingPattern ;
3234
+ transformFlags |= TransformFlags . AssertES2015 | TransformFlags . ContainsBindingPattern ;
3235
+ if ( subtreeFlags & TransformFlags . ContainsSpread ) {
3236
+ transformFlags |= TransformFlags . AssertESNext | TransformFlags . ContainsObjectRest ;
3210
3237
}
3238
+ excludeFlags = TransformFlags . BindingPatternExcludes ;
3239
+ break ;
3240
+
3241
+ case SyntaxKind . ArrayBindingPattern :
3242
+ transformFlags |= TransformFlags . AssertES2015 | TransformFlags . ContainsBindingPattern ;
3243
+ excludeFlags = TransformFlags . BindingPatternExcludes ;
3211
3244
break ;
3212
3245
3213
3246
case SyntaxKind . Decorator :
@@ -3229,18 +3262,18 @@ namespace ts {
3229
3262
transformFlags |= TransformFlags . ContainsLexicalThis ;
3230
3263
}
3231
3264
3232
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
3265
+ if ( subtreeFlags & TransformFlags . ContainsSpread ) {
3233
3266
// If an ObjectLiteralExpression contains a spread element, then it
3234
3267
// is an ES next node.
3235
- transformFlags |= TransformFlags . AssertESNext ;
3268
+ transformFlags |= TransformFlags . AssertESNext | TransformFlags . ContainsObjectSpread ;
3236
3269
}
3237
3270
3238
3271
break ;
3239
3272
3240
3273
case SyntaxKind . ArrayLiteralExpression :
3241
3274
case SyntaxKind . NewExpression :
3242
3275
excludeFlags = TransformFlags . ArrayLiteralOrCallOrNewExcludes ;
3243
- if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
3276
+ if ( subtreeFlags & TransformFlags . ContainsSpread ) {
3244
3277
// If the this node contains a SpreadExpression, then it is an ES6
3245
3278
// node.
3246
3279
transformFlags |= TransformFlags . AssertES2015 ;
@@ -3333,6 +3366,11 @@ namespace ts {
3333
3366
return TransformFlags . TypeExcludes ;
3334
3367
case SyntaxKind . ObjectLiteralExpression :
3335
3368
return TransformFlags . ObjectLiteralExcludes ;
3369
+ case SyntaxKind . CatchClause :
3370
+ return TransformFlags . CatchClauseExcludes ;
3371
+ case SyntaxKind . ObjectBindingPattern :
3372
+ case SyntaxKind . ArrayBindingPattern :
3373
+ return TransformFlags . BindingPatternExcludes ;
3336
3374
default :
3337
3375
return TransformFlags . NodeExcludes ;
3338
3376
}
0 commit comments