Chromium Code Reviews| Index: pkg/compiler/lib/src/ssa/builder.dart |
| diff --git a/pkg/compiler/lib/src/ssa/builder.dart b/pkg/compiler/lib/src/ssa/builder.dart |
| index 3cb1c8246b7d9ae19b5968cbcfffd8543e427521..bee2049053a400789d96686ace4e64e0c31f6376 100644 |
| --- a/pkg/compiler/lib/src/ssa/builder.dart |
| +++ b/pkg/compiler/lib/src/ssa/builder.dart |
| @@ -141,7 +141,16 @@ class SsaBuilder extends ast.Visitor |
| // used only for codegen, but currently we want to experiment using it for |
| // code-analysis too. |
| final CodegenRegistry registry; |
| + |
| + /// All results from the global type-inference analysis. |
| final GlobalTypeInferenceResults inferenceResults; |
| + |
| + /// Results from the global type-inference analysis corresponding to the |
| + /// current element being visited. |
| + /// |
| + /// Invariant: this property is updated together with [resolvedAst]. |
| + GlobalTypeInferenceElementResult elementInferenceResults; |
| + |
| final JavaScriptBackend backend; |
| final ConstantSystem constantSystem; |
| final RuntimeTypes rti; |
| @@ -193,6 +202,8 @@ class SsaBuilder extends ast.Visitor |
| this.inferenceResults = backend.compiler.globalInference.results { |
| assert(target.isImplementation); |
| compiler = backend.compiler; |
| + elementInferenceResults = inferenceResults.resultOf(target); |
| + assert(elementInferenceResults != null); |
| graph.element = target; |
| sourceElementStack.add(target); |
| sourceInformationBuilder = |
| @@ -436,7 +447,7 @@ class SsaBuilder extends ast.Visitor |
| // A generative constructor body is not seen by global analysis, |
| // so we should not query for its type. |
| if (!element.isGenerativeConstructorBody) { |
| - if (inferenceResults.throwsAlways(element)) { |
| + if (inferenceResults.resultOf(element).throwsAlways) { |
| isReachable = false; |
| return false; |
| } |
| @@ -568,12 +579,10 @@ class SsaBuilder extends ast.Visitor |
| return inliningStack.isEmpty || inliningStack.last.allFunctionsCalledOnce; |
| } |
| - bool isFunctionCalledOnce(Element element) { |
| - if (element is ConstructorBodyElement) { |
| - // ConstructorBodyElements are not in the type inference graph. |
| - return false; |
| - } |
| - return inferenceResults.isCalledOnce(element); |
| + bool isFunctionCalledOnce(element) { |
| + // ConstructorBodyElements are not in the type inference graph. |
| + if (element is ConstructorBodyElement) return false; |
| + return inferenceResults.resultOf(element).isCalledOnce; |
| } |
| bool isCalledOnce(Element element) { |
| @@ -759,8 +768,8 @@ class SsaBuilder extends ast.Visitor |
| } |
| } |
| - closeAndGotoExit(new HReturn(value, sourceInformationBuilder.buildReturn( |
| - sourceInfoNode))); |
| + closeAndGotoExit(new HReturn( |
| + value, sourceInformationBuilder.buildReturn(sourceInfoNode))); |
| return closeFunction(); |
| } |
| @@ -868,6 +877,7 @@ class SsaBuilder extends ast.Visitor |
| returnLocal = state.oldReturnLocal; |
| inTryStatement = state.inTryStatement; |
| resolvedAst = state.oldResolvedAst; |
| + elementInferenceResults = state.oldElementInferenceResults; |
| returnType = state.oldReturnType; |
| assert(stack.isEmpty); |
| stack = state.oldStack; |
| @@ -1000,6 +1010,8 @@ class SsaBuilder extends ast.Visitor |
| // Build the initializers in the context of the new constructor. |
| ResolvedAst oldResolvedAst = resolvedAst; |
| resolvedAst = callee.resolvedAst; |
| + final oldElementInferenceResults = elementInferenceResults; |
| + elementInferenceResults = inferenceResults.resultOf(callee); |
| ClosureClassMap oldClosureData = localsHandler.closureData; |
| ClosureClassMap newClosureData = |
| compiler.closureToClassMapper.getClosureToClassMapping(resolvedAst); |
| @@ -1010,6 +1022,7 @@ class SsaBuilder extends ast.Visitor |
| buildInitializers(callee, constructorResolvedAsts, fieldValues); |
| localsHandler.closureData = oldClosureData; |
| resolvedAst = oldResolvedAst; |
| + elementInferenceResults = oldElementInferenceResults; |
| }); |
| } |
| @@ -1172,11 +1185,14 @@ class SsaBuilder extends ast.Visitor |
| ast.Node right = initializer; |
| ResolvedAst savedResolvedAst = resolvedAst; |
| resolvedAst = fieldResolvedAst; |
| + final oldElementInferenceResults = elementInferenceResults; |
| + elementInferenceResults = inferenceResults.resultOf(member); |
| // In case the field initializer uses closures, run the |
| // closure to class mapper. |
| compiler.closureToClassMapper.getClosureToClassMapping(resolvedAst); |
| inlinedFrom(fieldResolvedAst, () => right.accept(this)); |
| resolvedAst = savedResolvedAst; |
| + elementInferenceResults = oldElementInferenceResults; |
| fieldValues[member] = pop(); |
| } |
| }); |
| @@ -2069,7 +2085,7 @@ class SsaBuilder extends ast.Visitor |
| } |
| pushInvokeDynamic(node, elements.getSelector(node), |
| - inferenceResults.typeOfSend(node, elements), [operand], |
| + elementInferenceResults.typeOfSend(node), [operand], |
| sourceInformation: sourceInformationBuilder.buildGeneric(node)); |
| } |
| @@ -2100,7 +2116,7 @@ class SsaBuilder extends ast.Visitor |
| visitAndPop(left), |
| visitAndPop(right), |
| elements.getSelector(node), |
| - inferenceResults.typeOfSend(node, elements), |
| + elementInferenceResults.typeOfSend(node), |
| node, |
| sourceInformation: |
| sourceInformationBuilder.buildGeneric(node.selector)); |
| @@ -2263,7 +2279,7 @@ class SsaBuilder extends ast.Visitor |
| void generateDynamicGet(ast.Send node) { |
| HInstruction receiver = generateInstanceSendReceiver(node); |
| generateInstanceGetterWithCompiledReceiver(node, elements.getSelector(node), |
| - inferenceResults.typeOfSend(node, elements), receiver); |
| + elementInferenceResults.typeOfSend(node), receiver); |
| } |
| /// Generate a closurization of the static or top level [function]. |
| @@ -2312,7 +2328,7 @@ class SsaBuilder extends ast.Visitor |
| generateInstanceGetterWithCompiledReceiver( |
| node, |
| elements.getSelector(node), |
| - inferenceResults.typeOfSend(node, elements), |
| + elementInferenceResults.typeOfSend(node), |
| expression); |
| }); |
| } |
| @@ -2377,7 +2393,7 @@ class SsaBuilder extends ast.Visitor |
| if (selector == null) { |
| assert(send != null); |
| selector = elements.getSelector(send); |
| - mask ??= inferenceResults.typeOfSend(send, elements); |
| + mask ??= elementInferenceResults.typeOfSend(send); |
| } |
| if (location == null) { |
| assert(send != null); |
| @@ -2648,7 +2664,7 @@ class SsaBuilder extends ast.Visitor |
| void _generateDynamicSend(ast.Send node, HInstruction receiver) { |
| Selector selector = elements.getSelector(node); |
| - TypeMask mask = inferenceResults.typeOfSend(node, elements); |
| + TypeMask mask = elementInferenceResults.typeOfSend(node); |
| SourceInformation sourceInformation = |
| sourceInformationBuilder.buildCall(node, node.selector); |
| @@ -4427,7 +4443,7 @@ class SsaBuilder extends ast.Visitor |
| receiver, |
| rhs, |
| elements.getOperatorSelectorInComplexSendSet(node), |
| - inferenceResults.typeOfOperator(node, elements), |
| + elementInferenceResults.typeOfOperator(node), |
| node, |
| sourceInformation: |
| sourceInformationBuilder.buildGeneric(node.assignmentOperator)); |
| @@ -4790,7 +4806,7 @@ class SsaBuilder extends ast.Visitor |
| } |
| pushInvokeDynamic(node, elements.getGetterSelectorInComplexSendSet(node), |
| - inferenceResults.typeOfGetter(node, elements), [receiver, index]); |
| + elementInferenceResults.typeOfGetter(node), [receiver, index]); |
| HInstruction getterInstruction = pop(); |
| if (node.isIfNullAssignment) { |
| // Compile x[i] ??= e as: |
| @@ -4805,7 +4821,7 @@ class SsaBuilder extends ast.Visitor |
| pushInvokeDynamic( |
| node, |
| elements.getSelector(node), |
| - inferenceResults.typeOfSend(node, elements), |
| + elementInferenceResults.typeOfSend(node), |
| [receiver, index, value]); |
| pop(); |
| stack.add(value); |
| @@ -4813,11 +4829,8 @@ class SsaBuilder extends ast.Visitor |
| } else { |
| handleComplexOperatorSend(node, getterInstruction, arguments); |
| HInstruction value = pop(); |
| - pushInvokeDynamic( |
| - node, |
| - elements.getSelector(node), |
| - inferenceResults.typeOfSend(node, elements), |
| - [receiver, index, value]); |
| + pushInvokeDynamic(node, elements.getSelector(node), |
| + elementInferenceResults.typeOfSend(node), [receiver, index, value]); |
| pop(); |
| if (node.isPostfix) { |
| stack.add(getterInstruction); |
| @@ -5021,7 +5034,7 @@ class SsaBuilder extends ast.Visitor |
| generateInstanceGetterWithCompiledReceiver( |
| node, |
| elements.getGetterSelectorInComplexSendSet(node), |
| - inferenceResults.typeOfGetter(node, elements), |
| + elementInferenceResults.typeOfGetter(node), |
| receiver); |
| HInstruction getterInstruction = pop(); |
| if (node.isIfNullAssignment) { |
| @@ -5484,7 +5497,7 @@ class SsaBuilder extends ast.Visitor |
| } |
| _inferredTypeOfNewList(ast.Node node) => |
| - inferenceResults.typeOfNewList(sourceElement, node) ?? |
| + inferenceResults.resultOf(sourceElement).typeOfNewList(node) ?? |
| compiler.commonMasks.dynamicType; |
| visitConditional(ast.Conditional node) { |
| @@ -5580,7 +5593,7 @@ class SsaBuilder extends ast.Visitor |
| HInstruction buildCondition() { |
| Selector selector = Selectors.moveNext; |
| - TypeMask mask = inferenceResults.typeOfIteratorMoveNext(node, elements); |
| + TypeMask mask = elementInferenceResults.typeOfIteratorMoveNext(node); |
| pushInvokeDynamic(node, selector, mask, [streamIterator]); |
| HInstruction future = pop(); |
| push(new HAwait( |
| @@ -5592,8 +5605,7 @@ class SsaBuilder extends ast.Visitor |
| void buildBody() { |
| Selector call = Selectors.current; |
| - TypeMask callMask = |
| - inferenceResults.typeOfIteratorCurrent(node, elements); |
| + TypeMask callMask = elementInferenceResults.typeOfIteratorCurrent(node); |
| pushInvokeDynamic(node, call, callMask, [streamIterator]); |
| ast.Node identifier = node.declaredIdentifier; |
| @@ -5602,7 +5614,7 @@ class SsaBuilder extends ast.Visitor |
| HInstruction value = pop(); |
| if (identifier.asSend() != null && |
| Elements.isInstanceSend(identifier, elements)) { |
| - TypeMask mask = inferenceResults.typeOfSend(identifier, elements); |
| + TypeMask mask = elementInferenceResults.typeOfSend(identifier); |
| HInstruction receiver = generateInstanceSendReceiver(identifier); |
| assert(receiver != null); |
| generateInstanceSetterWithCompiledReceiver(null, receiver, value, |
| @@ -5641,7 +5653,7 @@ class SsaBuilder extends ast.Visitor |
| // method is inlined. We would require full scalar replacement in that |
| // case. |
| - TypeMask mask = inferenceResults.typeOfIterator(node, elements); |
| + TypeMask mask = elementInferenceResults.typeOfIterator(node); |
| ClosedWorld closedWorld = compiler.closedWorld; |
| if (mask != null && |
| @@ -5666,7 +5678,7 @@ class SsaBuilder extends ast.Visitor |
| void buildInitializer() { |
| Selector selector = Selectors.iterator; |
| - TypeMask mask = inferenceResults.typeOfIterator(node, elements); |
| + TypeMask mask = elementInferenceResults.typeOfIterator(node); |
| visit(node.expression); |
| HInstruction receiver = pop(); |
| pushInvokeDynamic(node, selector, mask, [receiver]); |
| @@ -5675,14 +5687,14 @@ class SsaBuilder extends ast.Visitor |
| HInstruction buildCondition() { |
| Selector selector = Selectors.moveNext; |
| - TypeMask mask = inferenceResults.typeOfIteratorMoveNext(node, elements); |
| + TypeMask mask = elementInferenceResults.typeOfIteratorMoveNext(node); |
| pushInvokeDynamic(node, selector, mask, [iterator]); |
| return popBoolified(); |
| } |
| void buildBody() { |
| Selector call = Selectors.current; |
| - TypeMask mask = inferenceResults.typeOfIteratorCurrent(node, elements); |
| + TypeMask mask = elementInferenceResults.typeOfIteratorCurrent(node); |
| pushInvokeDynamic(node, call, mask, [iterator]); |
| buildAssignLoopVariable(node, pop()); |
| visit(node.body); |
| @@ -5699,7 +5711,7 @@ class SsaBuilder extends ast.Visitor |
| if (identifier.asSend() != null && |
| Elements.isInstanceSend(identifier, elements)) { |
| - TypeMask mask = inferenceResults.typeOfSend(identifier, elements); |
| + TypeMask mask = elementInferenceResults.typeOfSend(identifier); |
| HInstruction receiver = generateInstanceSendReceiver(identifier); |
| assert(receiver != null); |
| generateInstanceSetterWithCompiledReceiver(null, receiver, value, |
| @@ -6638,8 +6650,10 @@ class SsaBuilder extends ast.Visitor |
| stack, |
| localsHandler, |
| inTryStatement, |
| - allInlinedFunctionsCalledOnce && isFunctionCalledOnce(function)); |
| + isCalledOnce(function), |
|
Johnni Winther
2016/11/03 08:50:21
Reinsert the transfer of the `allInlinedFunctionsC
Siggi Cherem (dart-lang)
2016/11/03 21:12:15
Note that I replaced "isFunctionCalledOnce" with "
Johnni Winther
2016/11/04 07:30:52
Acknowledged.
|
| + elementInferenceResults); |
| resolvedAst = functionResolvedAst; |
| + elementInferenceResults = inferenceResults.resultOf(function); |
| inliningStack.add(state); |
| // Setting up the state of the (AST) builder is performed even when the |
| @@ -6960,6 +6974,7 @@ class AstInliningState extends InliningState { |
| final LocalsHandler oldLocalsHandler; |
| final bool inTryStatement; |
| final bool allFunctionsCalledOnce; |
| + final GlobalTypeInferenceElementResult oldElementInferenceResults; |
| AstInliningState( |
| FunctionElement function, |
| @@ -6969,7 +6984,8 @@ class AstInliningState extends InliningState { |
| this.oldStack, |
| this.oldLocalsHandler, |
| this.inTryStatement, |
| - this.allFunctionsCalledOnce) |
| + this.allFunctionsCalledOnce, |
| + this.oldElementInferenceResults) |
| : super(function); |
| } |