mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-05-03 19:29:03 -05:00
* fix CFA for BindingElement. #49759 * fix Parameter * fix controlFlowBindingPatternOrder * fix bindParameterFlow * add tests * refactor * refactor * refactor
This commit is contained in:
@@ -850,6 +850,9 @@ namespace ts {
|
||||
case SyntaxKind.BindingElement:
|
||||
bindBindingElementFlow(node as BindingElement);
|
||||
break;
|
||||
case SyntaxKind.Parameter:
|
||||
bindParameterFlow(node as ParameterDeclaration);
|
||||
break;
|
||||
case SyntaxKind.ObjectLiteralExpression:
|
||||
case SyntaxKind.ArrayLiteralExpression:
|
||||
case SyntaxKind.PropertyAssignment:
|
||||
@@ -1655,20 +1658,40 @@ namespace ts {
|
||||
}
|
||||
|
||||
function bindBindingElementFlow(node: BindingElement) {
|
||||
if (isBindingPattern(node.name)) {
|
||||
// When evaluating a binding pattern, the initializer is evaluated before the binding pattern, per:
|
||||
// - https://tc39.es/ecma262/#sec-destructuring-binding-patterns-runtime-semantics-iteratorbindinginitialization
|
||||
// - `BindingElement: BindingPattern Initializer?`
|
||||
// - https://tc39.es/ecma262/#sec-runtime-semantics-keyedbindinginitialization
|
||||
// - `BindingElement: BindingPattern Initializer?`
|
||||
bind(node.dotDotDotToken);
|
||||
bind(node.propertyName);
|
||||
bind(node.initializer);
|
||||
bind(node.name);
|
||||
// When evaluating a binding pattern, the initializer is evaluated before the binding pattern, per:
|
||||
// - https://tc39.es/ecma262/#sec-destructuring-binding-patterns-runtime-semantics-iteratorbindinginitialization
|
||||
// - `BindingElement: BindingPattern Initializer?`
|
||||
// - https://tc39.es/ecma262/#sec-runtime-semantics-keyedbindinginitialization
|
||||
// - `BindingElement: BindingPattern Initializer?`
|
||||
bind(node.dotDotDotToken);
|
||||
bind(node.propertyName);
|
||||
bindInitializer(node.initializer);
|
||||
bind(node.name);
|
||||
}
|
||||
|
||||
function bindParameterFlow(node: ParameterDeclaration) {
|
||||
bindEach(node.modifiers);
|
||||
bind(node.dotDotDotToken);
|
||||
bind(node.questionToken);
|
||||
bind(node.type);
|
||||
bindInitializer(node.initializer);
|
||||
bind(node.name);
|
||||
}
|
||||
|
||||
// a BindingElement/Parameter does not have side effects if initializers are not evaluated and used. (see GH#49759)
|
||||
function bindInitializer(node: Expression | undefined) {
|
||||
if (!node) {
|
||||
return;
|
||||
}
|
||||
else {
|
||||
bindEachChild(node);
|
||||
const entryFlow = currentFlow;
|
||||
bind(node);
|
||||
if (entryFlow === unreachableFlow || entryFlow === currentFlow) {
|
||||
return;
|
||||
}
|
||||
const exitFlow = createBranchLabel();
|
||||
addAntecedent(exitFlow, entryFlow);
|
||||
addAntecedent(exitFlow, currentFlow);
|
||||
currentFlow = finishFlowLabel(exitFlow);
|
||||
}
|
||||
|
||||
function bindJSDocTypeAlias(node: JSDocTypedefTag | JSDocCallbackTag | JSDocEnumTag) {
|
||||
|
||||
Reference in New Issue
Block a user