OLD | NEW |
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 part of ssa; | 5 part of ssa; |
6 | 6 |
7 /** | 7 /** |
8 * A special element for the extra parameter taken by intercepted | 8 * A special element for the extra parameter taken by intercepted |
9 * methods. We need to override [Element.computeType] because our | 9 * methods. We need to override [Element.computeType] because our |
10 * optimizers may look at its declared type. | 10 * optimizers may look at its declared type. |
(...skipping 1701 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1712 // Otherwise it is a lazy initializer which does not have parameters. | 1712 // Otherwise it is a lazy initializer which does not have parameters. |
1713 assert(element is VariableElement); | 1713 assert(element is VariableElement); |
1714 } | 1714 } |
1715 } | 1715 } |
1716 | 1716 |
1717 HInstruction buildTypeConversion(HInstruction original, | 1717 HInstruction buildTypeConversion(HInstruction original, |
1718 DartType type, | 1718 DartType type, |
1719 int kind) { | 1719 int kind) { |
1720 if (type == null) return original; | 1720 if (type == null) return original; |
1721 type = type.unalias(compiler); | 1721 type = type.unalias(compiler); |
1722 if (type.kind == TypeKind.INTERFACE && !type.isMalformed && !type.isRaw) { | 1722 if (type.kind == TypeKind.INTERFACE && !type.isRaw) { |
1723 HType subtype = new HType.subtype(type, compiler); | 1723 HType subtype = new HType.subtype(type, compiler); |
1724 HInstruction representations = buildTypeArgumentRepresentations(type); | 1724 HInstruction representations = buildTypeArgumentRepresentations(type); |
1725 add(representations); | 1725 add(representations); |
1726 return new HTypeConversion.withTypeRepresentation(type, kind, subtype, | 1726 return new HTypeConversion.withTypeRepresentation(type, kind, subtype, |
1727 original, representations); | 1727 original, representations); |
1728 } else if (type.kind == TypeKind.TYPE_VARIABLE) { | 1728 } else if (type.kind == TypeKind.TYPE_VARIABLE) { |
1729 HType subtype = original.instructionType; | 1729 HType subtype = original.instructionType; |
1730 HInstruction typeVariable = addTypeVariableReference(type); | 1730 HInstruction typeVariable = addTypeVariableReference(type); |
1731 return new HTypeConversion.withTypeRepresentation(type, kind, subtype, | 1731 return new HTypeConversion.withTypeRepresentation(type, kind, subtype, |
1732 original, typeVariable); | 1732 original, typeVariable); |
(...skipping 985 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2718 visitBinary(left, op, right, elements.getSelector(node), node); | 2718 visitBinary(left, op, right, elements.getSelector(node), node); |
2719 } | 2719 } |
2720 } | 2720 } |
2721 | 2721 |
2722 void visitIsSend(Send node) { | 2722 void visitIsSend(Send node) { |
2723 visit(node.receiver); | 2723 visit(node.receiver); |
2724 HInstruction expression = pop(); | 2724 HInstruction expression = pop(); |
2725 bool isNot = node.isIsNotCheck; | 2725 bool isNot = node.isIsNotCheck; |
2726 DartType type = elements.getType(node.typeAnnotationFromIsCheckOrCast); | 2726 DartType type = elements.getType(node.typeAnnotationFromIsCheckOrCast); |
2727 type = type.unalias(compiler); | 2727 type = type.unalias(compiler); |
2728 if (type.isMalformed) { | 2728 if (type.containsAmbiguousTypes) { |
2729 String reasons = Types.fetchReasonsFromMalformedType(type); | 2729 String reasons = Types.fetchReasonsFromAmbiguousType(type); |
2730 if (compiler.enableTypeAssertions) { | 2730 if (compiler.enableTypeAssertions) { |
2731 generateMalformedSubtypeError(node, expression, type, reasons); | 2731 generateMalformedSubtypeError(node, expression, type, reasons); |
2732 } else { | 2732 } else { |
2733 generateRuntimeError(node, '$type is malformed: $reasons'); | 2733 generateRuntimeError(node, '$type is ambiguous: $reasons'); |
2734 } | 2734 } |
2735 } else { | 2735 } else { |
2736 HInstruction instruction = buildIsNode(node, type, expression); | 2736 HInstruction instruction = buildIsNode(node, type, expression); |
2737 if (isNot) { | 2737 if (isNot) { |
2738 add(instruction); | 2738 add(instruction); |
2739 instruction = new HNot(instruction); | 2739 instruction = new HNot(instruction); |
2740 } | 2740 } |
2741 push(instruction); | 2741 push(instruction); |
2742 } | 2742 } |
2743 } | 2743 } |
(...skipping 588 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3332 element: type.element); | 3332 element: type.element); |
3333 } | 3333 } |
3334 } | 3334 } |
3335 | 3335 |
3336 /** | 3336 /** |
3337 * Documentation wanted -- johnniwinther | 3337 * Documentation wanted -- johnniwinther |
3338 * | 3338 * |
3339 * Invariant: [argument] must not be malformed in checked mode. | 3339 * Invariant: [argument] must not be malformed in checked mode. |
3340 */ | 3340 */ |
3341 HInstruction analyzeTypeArgument(DartType argument, Node currentNode) { | 3341 HInstruction analyzeTypeArgument(DartType argument, Node currentNode) { |
3342 assert(invariant(currentNode, | 3342 if (argument.treatAsDynamic) { |
3343 !compiler.enableTypeAssertions || !argument.isMalformed, | |
3344 message: '$argument is malformed in checked mode')); | |
3345 if (argument == compiler.types.dynamicType || argument.isMalformed) { | |
3346 // Represent [dynamic] as [null]. | 3343 // Represent [dynamic] as [null]. |
3347 return graph.addConstantNull(compiler); | 3344 return graph.addConstantNull(compiler); |
3348 } | 3345 } |
3349 | 3346 |
3350 List<HInstruction> inputs = <HInstruction>[]; | 3347 List<HInstruction> inputs = <HInstruction>[]; |
3351 | 3348 |
3352 String template = rti.getTypeRepresentation(argument, (variable) { | 3349 String template = rti.getTypeRepresentation(argument, (variable) { |
3353 inputs.add(addTypeVariableReference(variable)); | 3350 inputs.add(addTypeVariableReference(variable)); |
3354 }); | 3351 }); |
3355 | 3352 |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3391 pop(); | 3388 pop(); |
3392 } | 3389 } |
3393 | 3390 |
3394 /** | 3391 /** |
3395 * Documentation wanted -- johnniwinther | 3392 * Documentation wanted -- johnniwinther |
3396 * | 3393 * |
3397 * Invariant: [type] must not be malformed in checked mode. | 3394 * Invariant: [type] must not be malformed in checked mode. |
3398 */ | 3395 */ |
3399 handleNewSend(NewExpression node, InterfaceType type) { | 3396 handleNewSend(NewExpression node, InterfaceType type) { |
3400 Send send = node.send; | 3397 Send send = node.send; |
3401 assert(invariant(send, | |
3402 !compiler.enableTypeAssertions || !type.isMalformed, | |
3403 message: '$type is malformed in checked mode')); | |
3404 bool isListConstructor = false; | 3398 bool isListConstructor = false; |
3405 computeType(element) { | 3399 computeType(element) { |
3406 Element originalElement = elements[send]; | 3400 Element originalElement = elements[send]; |
3407 if (Elements.isFixedListConstructorCall(originalElement, send, compiler) | 3401 if (Elements.isFixedListConstructorCall(originalElement, send, compiler) |
3408 || Elements.isFilledListConstructorCall( | 3402 || Elements.isFilledListConstructorCall( |
3409 originalElement, send, compiler)) { | 3403 originalElement, send, compiler)) { |
3410 isListConstructor = true; | 3404 isListConstructor = true; |
3411 HType inferred = | 3405 HType inferred = |
3412 new HType.inferredForNode(currentElement, send, compiler); | 3406 new HType.inferredForNode(currentElement, send, compiler); |
3413 return inferred.isUnknown() ? backend.fixedArrayType : inferred; | 3407 return inferred.isUnknown() ? backend.fixedArrayType : inferred; |
(...skipping 298 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3712 Constant constant = handler.compileNodeWithDefinitions(node, elements); | 3706 Constant constant = handler.compileNodeWithDefinitions(node, elements); |
3713 stack.add(graph.addConstant(constant, compiler)); | 3707 stack.add(graph.addConstant(constant, compiler)); |
3714 if (isSymbolConstructor) { | 3708 if (isSymbolConstructor) { |
3715 ConstructedConstant symbol = constant; | 3709 ConstructedConstant symbol = constant; |
3716 StringConstant stringConstant = symbol.fields.single; | 3710 StringConstant stringConstant = symbol.fields.single; |
3717 String nameString = stringConstant.toDartString().slowToString(); | 3711 String nameString = stringConstant.toDartString().slowToString(); |
3718 compiler.enqueuer.codegen.registerConstSymbol(nameString, elements); | 3712 compiler.enqueuer.codegen.registerConstSymbol(nameString, elements); |
3719 } | 3713 } |
3720 } else { | 3714 } else { |
3721 DartType type = elements.getType(node); | 3715 DartType type = elements.getType(node); |
3722 if (compiler.enableTypeAssertions && type.isMalformed) { | 3716 if (compiler.enableTypeAssertions && type.containsAmbiguousTypes) { |
3723 String reasons = Types.fetchReasonsFromMalformedType(type); | 3717 String reasons = Types.fetchReasonsFromAmbiguousType(type); |
3724 // TODO(johnniwinther): Change to resemble type errors from bounds check | 3718 // TODO(johnniwinther): Change to resemble type errors from bounds check |
3725 // on type arguments. | 3719 // on type arguments. |
3726 generateRuntimeError(node, '$type is malformed: $reasons'); | 3720 generateRuntimeError(node, '$type is malformed: $reasons'); |
3727 } else { | 3721 } else { |
3728 // TODO(karlklose): move this type registration to the codegen. | 3722 // TODO(karlklose): move this type registration to the codegen. |
3729 compiler.codegenWorld.instantiatedTypes.add(type); | 3723 compiler.codegenWorld.instantiatedTypes.add(type); |
3730 handleNewSend(node, type); | 3724 handleNewSend(node, type); |
3731 } | 3725 } |
3732 } | 3726 } |
3733 } | 3727 } |
(...skipping 1112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4846 HInvokeStatic unwrappedException = pop(); | 4840 HInvokeStatic unwrappedException = pop(); |
4847 tryInstruction.exception = exception; | 4841 tryInstruction.exception = exception; |
4848 Link<Node> link = node.catchBlocks.nodes; | 4842 Link<Node> link = node.catchBlocks.nodes; |
4849 | 4843 |
4850 void pushCondition(CatchBlock catchBlock) { | 4844 void pushCondition(CatchBlock catchBlock) { |
4851 if (catchBlock.onKeyword != null) { | 4845 if (catchBlock.onKeyword != null) { |
4852 DartType type = elements.getType(catchBlock.type); | 4846 DartType type = elements.getType(catchBlock.type); |
4853 if (type == null) { | 4847 if (type == null) { |
4854 compiler.internalError('On with no type', node: catchBlock.type); | 4848 compiler.internalError('On with no type', node: catchBlock.type); |
4855 } | 4849 } |
4856 if (type.isMalformed) { | 4850 // TODO(karlkose): support type arguments here. |
4857 // TODO(johnniwinther): Handle malformed types in [HIs] instead. | 4851 HInstruction condition = new HIs(type, |
4858 HInstruction condition = | 4852 <HInstruction>[unwrappedException], |
4859 graph.addConstantBool(true, compiler); | 4853 HIs.RAW_CHECK); |
4860 stack.add(condition); | 4854 push(condition); |
4861 } else { | |
4862 // TODO(karlkose): support type arguments here. | |
4863 HInstruction condition = new HIs(type, | |
4864 <HInstruction>[unwrappedException], | |
4865 HIs.RAW_CHECK); | |
4866 push(condition); | |
4867 } | |
4868 } else { | 4855 } else { |
4869 VariableDefinitions declaration = catchBlock.formals.nodes.head; | 4856 VariableDefinitions declaration = catchBlock.formals.nodes.head; |
4870 HInstruction condition = null; | 4857 HInstruction condition = null; |
4871 if (declaration.type == null) { | 4858 if (declaration.type == null) { |
4872 condition = graph.addConstantBool(true, compiler); | 4859 condition = graph.addConstantBool(true, compiler); |
4873 stack.add(condition); | 4860 stack.add(condition); |
4874 } else { | 4861 } else { |
4875 // TODO(aprelev@gmail.com): Once old catch syntax is removed | 4862 // TODO(aprelev@gmail.com): Once old catch syntax is removed |
4876 // "if" condition above and this "else" branch should be deleted as | 4863 // "if" condition above and this "else" branch should be deleted as |
4877 // type of declared variable won't matter for the catch | 4864 // type of declared variable won't matter for the catch |
(...skipping 12 matching lines...) Expand all Loading... |
4890 | 4877 |
4891 void visitThen() { | 4878 void visitThen() { |
4892 CatchBlock catchBlock = link.head; | 4879 CatchBlock catchBlock = link.head; |
4893 link = link.tail; | 4880 link = link.tail; |
4894 | 4881 |
4895 if (compiler.enableTypeAssertions) { | 4882 if (compiler.enableTypeAssertions) { |
4896 // In checked mode: throw a type error if the on-catch type is | 4883 // In checked mode: throw a type error if the on-catch type is |
4897 // malformed. | 4884 // malformed. |
4898 if (catchBlock.onKeyword != null) { | 4885 if (catchBlock.onKeyword != null) { |
4899 DartType type = elements.getType(catchBlock.type); | 4886 DartType type = elements.getType(catchBlock.type); |
4900 if (type != null && type.isMalformed) { | 4887 if (type != null && type.containsAmbiguousTypes) { |
4901 String reasons = Types.fetchReasonsFromMalformedType(type); | 4888 String reasons = Types.fetchReasonsFromAmbiguousType(type); |
4902 generateMalformedSubtypeError(node, | 4889 generateMalformedSubtypeError(node, |
4903 unwrappedException, type, reasons); | 4890 unwrappedException, type, reasons); |
4904 pop(); | 4891 pop(); |
4905 return; | 4892 return; |
4906 } | 4893 } |
4907 } | 4894 } |
4908 } | 4895 } |
4909 if (catchBlock.exception != null) { | 4896 if (catchBlock.exception != null) { |
4910 localsHandler.updateLocal(elements[catchBlock.exception], | 4897 localsHandler.updateLocal(elements[catchBlock.exception], |
4911 unwrappedException); | 4898 unwrappedException); |
(...skipping 528 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5440 new HSubGraphBlockInformation(elseBranch.graph)); | 5427 new HSubGraphBlockInformation(elseBranch.graph)); |
5441 | 5428 |
5442 HBasicBlock conditionStartBlock = conditionBranch.block; | 5429 HBasicBlock conditionStartBlock = conditionBranch.block; |
5443 conditionStartBlock.setBlockFlow(info, joinBlock); | 5430 conditionStartBlock.setBlockFlow(info, joinBlock); |
5444 SubGraph conditionGraph = conditionBranch.graph; | 5431 SubGraph conditionGraph = conditionBranch.graph; |
5445 HIf branch = conditionGraph.end.last; | 5432 HIf branch = conditionGraph.end.last; |
5446 assert(branch is HIf); | 5433 assert(branch is HIf); |
5447 branch.blockInformation = conditionStartBlock.blockFlow; | 5434 branch.blockInformation = conditionStartBlock.blockFlow; |
5448 } | 5435 } |
5449 } | 5436 } |
OLD | NEW |