Skip to content

Commit 2d8e5a6

Browse files
stereotype441commit-bot@chromium.org
authored andcommitted
Revert "Flow analysis: Track expression variables separately from promotion info."
This reverts commit fd2a6c6. Reason for revert: Broke pkg/dds/test/sse_smoke_test Original change's description: > Flow analysis: Track expression variables separately from promotion info. > > Previously, we used a single class hierarchy, ExpressionInfo, to store > all the information that flow analysis needs to know about a variable, > including: > > 1. What is known about the program state if the expression evaluates > to true/false > > 2. Whether the expression is a `null` literal > > 3. Whether the expression is a reference to a variable. > > However, in order to address > dart-lang/language#1274 (Infer > non-nullability from local boolean variables), we'll need #3 to be > tracked orthogonally from #1, so that when a local boolean is referred > to later, we can track information of type #1 and #3 simultaneously. > > However, it makes sense to keep #1 and #2 in the same data structure, > because future work is planned to represent them in a more uniform > way, as part of addressing > dart-lang/language#1224 (Using `if (foo?.bar > == somethingNotNull)` should promote `foo`). > > Change-Id: I432f6e2e80543bb1d565b49403180c520eef66a5 > Bug: dart-lang/language#1274 > Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/175008 > Reviewed-by: Johnni Winther <[email protected]> > Commit-Queue: Paul Berry <[email protected]> [email protected],[email protected],[email protected] Change-Id: I70b4adaf13f412a42a8128b9c7b9583b4171158e No-Presubmit: true No-Tree-Checks: true No-Try: true Bug: dart-lang/language#1274 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/175321 Reviewed-by: Paul Berry <[email protected]> Commit-Queue: Paul Berry <[email protected]>
1 parent 2d0228e commit 2d8e5a6

File tree

1 file changed

+59
-67
lines changed

1 file changed

+59
-67
lines changed

pkg/_fe_analyzer_shared/lib/src/flow_analysis/flow_analysis.dart

Lines changed: 59 additions & 67 deletions
Original file line numberDiff line numberDiff line change
@@ -2566,12 +2566,8 @@ class _EqualityOpContext<Variable, Type> extends _BranchContext {
25662566
/// The type of the expression on the LHS of `==` or `!=`.
25672567
final Type _leftOperandType;
25682568

2569-
/// If the LHS of `==` or `!=` is a variable reference, the variable.
2570-
/// Otherwise `null`.
2571-
final Variable _leftOperandVariable;
2572-
2573-
_EqualityOpContext(ExpressionInfo<Variable, Type> conditionInfo,
2574-
this._leftOperandType, this._leftOperandVariable)
2569+
_EqualityOpContext(
2570+
ExpressionInfo<Variable, Type> conditionInfo, this._leftOperandType)
25752571
: super(conditionInfo);
25762572

25772573
@override
@@ -2606,14 +2602,6 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
26062602
/// corresponding to it. Otherwise `null`.
26072603
ExpressionInfo<Variable, Type> _expressionInfo;
26082604

2609-
/// The most recently visited expression which was a variable reference, or
2610-
/// `null` if no expression has been visited that was a variable reference.
2611-
Expression _expressionWithVariable;
2612-
2613-
/// If [_expressionVariable] is not `null`, the variable corresponding to it.
2614-
/// Otherwise `null`.
2615-
Variable _expressionVariable;
2616-
26172605
int _functionNestingLevel = 0;
26182606

26192607
final AssignedVariables<Node, Variable> _assignedVariables;
@@ -2627,8 +2615,14 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
26272615

26282616
@override
26292617
void asExpression_end(Expression subExpression, Type type) {
2630-
Variable variable = _getExpressionVariable(subExpression);
2631-
if (variable == null) return;
2618+
ExpressionInfo<Variable, Type> subExpressionInfo =
2619+
_getExpressionInfo(subExpression);
2620+
Variable variable;
2621+
if (subExpressionInfo is _VariableReadInfo<Variable, Type>) {
2622+
variable = subExpressionInfo._variable;
2623+
} else {
2624+
return;
2625+
}
26322626
_current = _current.tryPromoteForTypeCast(typeOperations, variable, type);
26332627
}
26342628

@@ -2736,10 +2730,8 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
27362730
_EqualityOpContext<Variable, Type> context =
27372731
_stack.removeLast() as _EqualityOpContext<Variable, Type>;
27382732
ExpressionInfo<Variable, Type> lhsInfo = context._conditionInfo;
2739-
Variable lhsVariable = context._leftOperandVariable;
27402733
Type leftOperandType = context._leftOperandType;
27412734
ExpressionInfo<Variable, Type> rhsInfo = _getExpressionInfo(rightOperand);
2742-
Variable rhsVariable = _getExpressionVariable(rightOperand);
27432735
TypeClassification leftOperandTypeClassification =
27442736
typeOperations.classifyType(leftOperandType);
27452737
TypeClassification rightOperandTypeClassification =
@@ -2757,16 +2749,18 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
27572749
// but weak mode it might produce an "equal" result. We don't want flow
27582750
// analysis behavior to depend on mode, so we conservatively assume that
27592751
// either result is possible.
2760-
} else if (lhsInfo is _NullInfo<Variable, Type> && rhsVariable != null) {
2752+
} else if (lhsInfo is _NullInfo<Variable, Type> &&
2753+
rhsInfo is _VariableReadInfo<Variable, Type>) {
27612754
assert(
27622755
leftOperandTypeClassification == TypeClassification.nullOrEquivalent);
27632756
ExpressionInfo<Variable, Type> equalityInfo =
2764-
_current.tryMarkNonNullable(typeOperations, rhsVariable);
2757+
_current.tryMarkNonNullable(typeOperations, rhsInfo._variable);
27652758
_storeExpressionInfo(wholeExpression,
27662759
notEqual ? equalityInfo : ExpressionInfo.invert(equalityInfo));
2767-
} else if (rhsInfo is _NullInfo<Variable, Type> && lhsVariable != null) {
2760+
} else if (rhsInfo is _NullInfo<Variable, Type> &&
2761+
lhsInfo is _VariableReadInfo<Variable, Type>) {
27682762
ExpressionInfo<Variable, Type> equalityInfo =
2769-
_current.tryMarkNonNullable(typeOperations, lhsVariable);
2763+
_current.tryMarkNonNullable(typeOperations, lhsInfo._variable);
27702764
_storeExpressionInfo(wholeExpression,
27712765
notEqual ? equalityInfo : ExpressionInfo.invert(equalityInfo));
27722766
}
@@ -2775,9 +2769,7 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
27752769
@override
27762770
void equalityOp_rightBegin(Expression leftOperand, Type leftOperandType) {
27772771
_stack.add(new _EqualityOpContext<Variable, Type>(
2778-
_getExpressionInfo(leftOperand),
2779-
leftOperandType,
2780-
_getExpressionVariable(leftOperand)));
2772+
_getExpressionInfo(leftOperand), leftOperandType));
27812773
}
27822774

27832775
@override
@@ -2852,9 +2844,6 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
28522844
if (identical(_expressionWithInfo, oldExpression)) {
28532845
_expressionWithInfo = newExpression;
28542846
}
2855-
if (identical(_expressionWithVariable, oldExpression)) {
2856-
_expressionWithVariable = newExpression;
2857-
}
28582847
}
28592848

28602849
@override
@@ -2912,12 +2901,12 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
29122901
@override
29132902
void ifNullExpression_rightBegin(
29142903
Expression leftHandSide, Type leftHandSideType) {
2915-
Variable lhsVariable = _getExpressionVariable(leftHandSide);
2904+
ExpressionInfo<Variable, Type> lhsInfo = _getExpressionInfo(leftHandSide);
29162905
FlowModel<Variable, Type> promoted;
29172906
_current = _current.split();
2918-
if (lhsVariable != null) {
2907+
if (lhsInfo is _VariableReadInfo<Variable, Type>) {
29192908
ExpressionInfo<Variable, Type> promotionInfo =
2920-
_current.tryMarkNonNullable(typeOperations, lhsVariable);
2909+
_current.tryMarkNonNullable(typeOperations, lhsInfo._variable);
29212910
_current = promotionInfo.ifFalse;
29222911
promoted = promotionInfo.ifTrue;
29232912
} else {
@@ -2970,10 +2959,12 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
29702959
@override
29712960
void isExpression_end(Expression isExpression, Expression subExpression,
29722961
bool isNot, Type type) {
2973-
Variable subExpressionVariable = _getExpressionVariable(subExpression);
2974-
if (subExpressionVariable != null) {
2975-
ExpressionInfo<Variable, Type> expressionInfo = _current
2976-
.tryPromoteForTypeCheck(typeOperations, subExpressionVariable, type);
2962+
ExpressionInfo<Variable, Type> subExpressionInfo =
2963+
_getExpressionInfo(subExpression);
2964+
if (subExpressionInfo is _VariableReadInfo<Variable, Type>) {
2965+
ExpressionInfo<Variable, Type> expressionInfo =
2966+
_current.tryPromoteForTypeCheck(
2967+
typeOperations, subExpressionInfo._variable, type);
29772968
_storeExpressionInfo(isExpression,
29782969
isNot ? ExpressionInfo.invert(expressionInfo) : expressionInfo);
29792970
}
@@ -3063,10 +3054,11 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
30633054

30643055
@override
30653056
void nonNullAssert_end(Expression operand) {
3066-
Variable operandVariable = _getExpressionVariable(operand);
3067-
if (operandVariable != null) {
3068-
_current =
3069-
_current.tryMarkNonNullable(typeOperations, operandVariable).ifTrue;
3057+
ExpressionInfo<Variable, Type> operandInfo = _getExpressionInfo(operand);
3058+
if (operandInfo is _VariableReadInfo<Variable, Type>) {
3059+
_current = _current
3060+
.tryMarkNonNullable(typeOperations, operandInfo._variable)
3061+
.ifTrue;
30703062
}
30713063
}
30723064

@@ -3083,10 +3075,11 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
30833075
_current = _current.split();
30843076
_stack.add(new _NullAwareAccessContext<Variable, Type>(_current));
30853077
if (target != null) {
3086-
Variable targetVariable = _getExpressionVariable(target);
3087-
if (targetVariable != null) {
3088-
_current =
3089-
_current.tryMarkNonNullable(typeOperations, targetVariable).ifTrue;
3078+
ExpressionInfo<Variable, Type> targetInfo = _getExpressionInfo(target);
3079+
if (targetInfo is _VariableReadInfo<Variable, Type>) {
3080+
_current = _current
3081+
.tryMarkNonNullable(typeOperations, targetInfo._variable)
3082+
.ifTrue;
30903083
}
30913084
}
30923085
}
@@ -3233,7 +3226,7 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
32333226

32343227
@override
32353228
Type variableRead(Expression expression, Variable variable) {
3236-
_storeExpressionVariable(expression, variable);
3229+
_storeExpressionInfo(expression, new _VariableReadInfo(_current, variable));
32373230
return _current.infoFor(variable).promotedTypes?.last;
32383231
}
32393232

@@ -3280,8 +3273,6 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
32803273
print(' current: $_current');
32813274
print(' expressionWithInfo: $_expressionWithInfo');
32823275
print(' expressionInfo: $_expressionInfo');
3283-
print(' expressionWithVariable: $_expressionWithVariable');
3284-
print(' expressionVariable: $_expressionVariable');
32853276
print(' stack:');
32863277
for (_FlowContext stackEntry in _stack.reversed) {
32873278
print(' $stackEntry');
@@ -3310,19 +3301,6 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
33103301
}
33113302
}
33123303

3313-
/// Gets the [Variable] associated with the [expression] (which should be the
3314-
/// last expression that was traversed). If there is no [Variable] associated
3315-
/// with the [expression], then `null` is returned.
3316-
Variable _getExpressionVariable(Expression expression) {
3317-
if (identical(expression, _expressionWithVariable)) {
3318-
Variable expressionVariable = _expressionVariable;
3319-
_expressionVariable = null;
3320-
return expressionVariable;
3321-
} else {
3322-
return null;
3323-
}
3324-
}
3325-
33263304
FlowModel<Variable, Type> _join(
33273305
FlowModel<Variable, Type> first, FlowModel<Variable, Type> second) =>
33283306
FlowModel.join(typeOperations, first, second, _current._emptyVariableMap);
@@ -3341,14 +3319,6 @@ class _FlowAnalysisImpl<Node, Statement extends Node, Expression, Variable,
33413319
_expressionInfo = expressionInfo;
33423320
_current = expressionInfo.after;
33433321
}
3344-
3345-
/// Associates [expression], which should be the most recently visited
3346-
/// expression, with the given [Variable] object.
3347-
void _storeExpressionVariable(
3348-
Expression expression, Variable expressionVariable) {
3349-
_expressionWithVariable = expression;
3350-
_expressionVariable = expressionVariable;
3351-
}
33523322
}
33533323

33543324
/// Base class for objects representing constructs in the Dart programming
@@ -3467,6 +3437,28 @@ class _TryContext<Variable, Type> extends _SimpleContext<Variable, Type> {
34673437
'afterBodyAndCatches: $_afterBodyAndCatches)';
34683438
}
34693439

3440+
/// [ExpressionInfo] representing an expression that reads the value of a
3441+
/// variable.
3442+
class _VariableReadInfo<Variable, Type>
3443+
implements ExpressionInfo<Variable, Type> {
3444+
@override
3445+
final FlowModel<Variable, Type> after;
3446+
3447+
/// The variable that is being read.
3448+
final Variable _variable;
3449+
3450+
_VariableReadInfo(this.after, this._variable);
3451+
3452+
@override
3453+
FlowModel<Variable, Type> get ifFalse => after;
3454+
3455+
@override
3456+
FlowModel<Variable, Type> get ifTrue => after;
3457+
3458+
@override
3459+
String toString() => '_VariableReadInfo(after: $after, variable: $_variable)';
3460+
}
3461+
34703462
/// [_FlowContext] representing a `while` loop (or a C-style `for` loop, which
34713463
/// is functionally similar).
34723464
class _WhileContext<Variable, Type>

0 commit comments

Comments
 (0)