Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1)

Side by Side Diff: sdk/lib/_internal/compiler/implementation/ssa/builder.dart

Issue 24282005: Move compile-time constant registrations to the backend. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Update status Created 7 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
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 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
50 } else { 50 } else {
51 compiler.internalErrorOnElement(element, 51 compiler.internalErrorOnElement(element,
52 'unexpected element kind $kind'); 52 'unexpected element kind $kind');
53 } 53 }
54 assert(graph.isValid()); 54 assert(graph.isValid());
55 if (!identical(kind, ElementKind.FIELD)) { 55 if (!identical(kind, ElementKind.FIELD)) {
56 FunctionElement function = element; 56 FunctionElement function = element;
57 FunctionSignature signature = function.computeSignature(compiler); 57 FunctionSignature signature = function.computeSignature(compiler);
58 signature.forEachOptionalParameter((Element parameter) { 58 signature.forEachOptionalParameter((Element parameter) {
59 // This ensures the default value will be computed. 59 // This ensures the default value will be computed.
60 builder.compileVariable(parameter); 60 Constant constant =
61 compiler.constantHandler.getConstantForVariable(parameter);
62 backend.registerCompileTimeConstant(constant, work.resolutionTree);
63 compiler.constantHandler.addCompileTimeConstantForEmission(
64 constant);
61 }); 65 });
62 } 66 }
63
64 if (compiler.tracer.enabled) { 67 if (compiler.tracer.enabled) {
65 String name; 68 String name;
66 if (element.isMember()) { 69 if (element.isMember()) {
67 String className = element.getEnclosingClass().name.slowToString(); 70 String className = element.getEnclosingClass().name.slowToString();
68 String memberName = element.name.slowToString(); 71 String memberName = element.name.slowToString();
69 name = "$className.$memberName"; 72 name = "$className.$memberName";
70 if (element.isGenerativeConstructorBody()) { 73 if (element.isGenerativeConstructorBody()) {
71 name = "$name (body)"; 74 name = "$name (body)";
72 } 75 }
73 } else { 76 } else {
(...skipping 872 matching lines...) Expand 10 before | Expand all | Expand 10 after
946 949
947 bool inTryStatement = false; 950 bool inTryStatement = false;
948 int loopNesting = 0; 951 int loopNesting = 0;
949 952
950 HBasicBlock get current => _current; 953 HBasicBlock get current => _current;
951 void set current(c) { 954 void set current(c) {
952 isReachable = c != null; 955 isReachable = c != null;
953 _current = c; 956 _current = c;
954 } 957 }
955 958
956 /** 959 Constant getConstantForNode(Node node) {
957 * Compiles compile-time constants. Never returns [:null:]. If the 960 ConstantHandler handler = compiler.constantHandler;
958 * initial value is not a compile-time constants, it reports an 961 Constant constant = elements.getConstant(node);
959 * internal error. 962 assert(invariant(node, constant != null,
960 */ 963 message: 'No constant computed for $node'));
961 Constant compileConstant(VariableElement element) { 964 return constant;
962 return compiler.constantHandler.compileConstant(element);
963 } 965 }
964 966
965 Constant compileVariable(VariableElement element) { 967 HInstruction addConstant(Node node) {
966 return compiler.constantHandler.compileVariable(element); 968 return graph.addConstant(getConstantForNode(node), compiler);
967 } 969 }
968 970
969 bool isLazilyInitialized(VariableElement element) { 971 bool isLazilyInitialized(VariableElement element) {
970 Constant initialValue = compileVariable(element); 972 Constant initialValue =
973 compiler.constantHandler.getConstantForVariable(element);
971 return initialValue == null; 974 return initialValue == null;
972 } 975 }
973 976
974 HType cachedTypeOfThis; 977 HType cachedTypeOfThis;
975 978
976 HType getTypeOfThis() { 979 HType getTypeOfThis() {
977 HType result = cachedTypeOfThis; 980 HType result = cachedTypeOfThis;
978 if (result == null) { 981 if (result == null) {
979 Element element = localsHandler.closureData.thisElement; 982 Element element = localsHandler.closureData.thisElement;
980 ClassElement cls = element.enclosingElement.getEnclosingClass(); 983 ClassElement cls = element.enclosingElement.getEnclosingClass();
(...skipping 1636 matching lines...) Expand 10 before | Expand all | Expand 10 after
2617 assert(selector.isGetter()); 2620 assert(selector.isGetter());
2618 pushInvokeDynamic(send, selector, [receiver]); 2621 pushInvokeDynamic(send, selector, [receiver]);
2619 } 2622 }
2620 2623
2621 void generateGetter(Send send, Element element) { 2624 void generateGetter(Send send, Element element) {
2622 if (Elements.isStaticOrTopLevelField(element)) { 2625 if (Elements.isStaticOrTopLevelField(element)) {
2623 Constant value; 2626 Constant value;
2624 if (element.isField() && !element.isAssignable()) { 2627 if (element.isField() && !element.isAssignable()) {
2625 // A static final or const. Get its constant value and inline it if 2628 // A static final or const. Get its constant value and inline it if
2626 // the value can be compiled eagerly. 2629 // the value can be compiled eagerly.
2627 value = compileVariable(element); 2630 value = compiler.constantHandler.getConstantForVariable(element);
2628 } 2631 }
2629 if (value != null) { 2632 if (value != null) {
2630 HInstruction instruction = graph.addConstant(value, compiler); 2633 HInstruction instruction = graph.addConstant(value, compiler);
2631 stack.add(instruction); 2634 stack.add(instruction);
2632 // The inferrer may have found a better type than the constant 2635 // The inferrer may have found a better type than the constant
2633 // handler in the case of lists, because the constant handler 2636 // handler in the case of lists, because the constant handler
2634 // does not look at elements in the list. 2637 // does not look at elements in the list.
2635 HType type = new HType.inferredTypeForElement(element, compiler); 2638 HType type = new HType.inferredTypeForElement(element, compiler);
2636 if (!type.isUnknown()) instruction.instructionType = type; 2639 if (!type.isUnknown()) instruction.instructionType = type;
2637 } else if (element.isField() && isLazilyInitialized(element)) { 2640 } else if (element.isField() && isLazilyInitialized(element)) {
(...skipping 306 matching lines...) Expand 10 before | Expand all | Expand 10 after
2944 // of instructions, in an order that can be shared with 2947 // of instructions, in an order that can be shared with
2945 // selectors with the same named arguments. 2948 // selectors with the same named arguments.
2946 List<SourceString> orderedNames = selector.getOrderedNamedArguments(); 2949 List<SourceString> orderedNames = selector.getOrderedNamedArguments();
2947 for (SourceString name in orderedNames) { 2950 for (SourceString name in orderedNames) {
2948 list.add(instructions[name]); 2951 list.add(instructions[name]);
2949 } 2952 }
2950 } 2953 }
2951 } 2954 }
2952 2955
2953 HInstruction handleConstantForOptionalParameter(Element parameter) { 2956 HInstruction handleConstantForOptionalParameter(Element parameter) {
2954 Constant constant = compileConstant(parameter); 2957 Constant constant =
2958 compiler.constantHandler.getConstantForVariable(parameter);
2959 assert(invariant(parameter, constant != null,
2960 message: 'No constant computed for $parameter'));
2955 return graph.addConstant(constant, compiler); 2961 return graph.addConstant(constant, compiler);
2956 } 2962 }
2957 2963
2958 /** 2964 /**
2959 * Returns true if the arguments were compatible with the function signature. 2965 * Returns true if the arguments were compatible with the function signature.
2960 * 2966 *
2961 * Invariant: [element] must be an implementation element. 2967 * Invariant: [element] must be an implementation element.
2962 */ 2968 */
2963 bool addStaticSendArgumentsToList(Selector selector, 2969 bool addStaticSendArgumentsToList(Selector selector,
2964 Link<Node> arguments, 2970 Link<Node> arguments,
(...skipping 697 matching lines...) Expand 10 before | Expand all | Expand 10 after
3662 HConstant addConstantString(Node node, String string) { 3668 HConstant addConstantString(Node node, String string) {
3663 DartString dartString = new DartString.literal(string); 3669 DartString dartString = new DartString.literal(string);
3664 Constant constant = constantSystem.createString(dartString, node); 3670 Constant constant = constantSystem.createString(dartString, node);
3665 return graph.addConstant(constant, compiler); 3671 return graph.addConstant(constant, compiler);
3666 } 3672 }
3667 3673
3668 visitTypeReferenceSend(Send node) { 3674 visitTypeReferenceSend(Send node) {
3669 Element element = elements[node]; 3675 Element element = elements[node];
3670 if (element.isClass() || element.isTypedef()) { 3676 if (element.isClass() || element.isTypedef()) {
3671 // TODO(karlklose): add type representation 3677 // TODO(karlklose): add type representation
3672 ConstantHandler handler = compiler.constantHandler; 3678 stack.add(addConstant(node));
3673 Constant constant = handler.compileNodeWithDefinitions(node, elements);
3674 stack.add(graph.addConstant(constant, compiler));
3675 } else if (element.isTypeVariable()) { 3679 } else if (element.isTypeVariable()) {
3676 HInstruction value = 3680 HInstruction value =
3677 addTypeVariableReference(element.computeType(compiler)); 3681 addTypeVariableReference(element.computeType(compiler));
3678 pushInvokeStatic(node, 3682 pushInvokeStatic(node,
3679 backend.getRuntimeTypeToString(), 3683 backend.getRuntimeTypeToString(),
3680 [value], 3684 [value],
3681 backend.stringType); 3685 backend.stringType);
3682 pushInvokeStatic(node, 3686 pushInvokeStatic(node,
3683 backend.getCreateRuntimeType(), 3687 backend.getCreateRuntimeType(),
3684 [pop()]); 3688 [pop()]);
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after
3795 ErroneousElement error = element; 3799 ErroneousElement error = element;
3796 if (error.messageKind == MessageKind.CANNOT_FIND_CONSTRUCTOR.error) { 3800 if (error.messageKind == MessageKind.CANNOT_FIND_CONSTRUCTOR.error) {
3797 generateThrowNoSuchMethod(node.send, 3801 generateThrowNoSuchMethod(node.send,
3798 getTargetName(error, 'constructor'), 3802 getTargetName(error, 'constructor'),
3799 argumentNodes: node.send.arguments); 3803 argumentNodes: node.send.arguments);
3800 } else { 3804 } else {
3801 Message message = error.messageKind.message(error.messageArguments); 3805 Message message = error.messageKind.message(error.messageArguments);
3802 generateRuntimeError(node.send, message.toString()); 3806 generateRuntimeError(node.send, message.toString());
3803 } 3807 }
3804 } else if (node.isConst()) { 3808 } else if (node.isConst()) {
3805 ConstantHandler handler = compiler.constantHandler; 3809 stack.add(addConstant(node));
3806 Constant constant = handler.compileNodeWithDefinitions(node, elements);
3807 stack.add(graph.addConstant(constant, compiler));
3808 if (isSymbolConstructor) { 3810 if (isSymbolConstructor) {
3809 ConstructedConstant symbol = constant; 3811 ConstructedConstant symbol = elements.getConstant(node);
3810 StringConstant stringConstant = symbol.fields.single; 3812 StringConstant stringConstant = symbol.fields.single;
3811 String nameString = stringConstant.toDartString().slowToString(); 3813 String nameString = stringConstant.toDartString().slowToString();
3812 compiler.enqueuer.codegen.registerConstSymbol(nameString, elements); 3814 compiler.enqueuer.codegen.registerConstSymbol(nameString, elements);
3813 } 3815 }
3814 } else { 3816 } else {
3815 handleNewSend(node); 3817 handleNewSend(node);
3816 } 3818 }
3817 } 3819 }
3818 3820
3819 void pushInvokeDynamic(Node node, 3821 void pushInvokeDynamic(Node node,
(...skipping 295 matching lines...) Expand 10 before | Expand all | Expand 10 after
4115 4117
4116 void visitLiteralBool(LiteralBool node) { 4118 void visitLiteralBool(LiteralBool node) {
4117 stack.add(graph.addConstantBool(node.value, compiler)); 4119 stack.add(graph.addConstantBool(node.value, compiler));
4118 } 4120 }
4119 4121
4120 void visitLiteralString(LiteralString node) { 4122 void visitLiteralString(LiteralString node) {
4121 stack.add(graph.addConstantString(node.dartString, node, compiler)); 4123 stack.add(graph.addConstantString(node.dartString, node, compiler));
4122 } 4124 }
4123 4125
4124 void visitLiteralSymbol(LiteralSymbol node) { 4126 void visitLiteralSymbol(LiteralSymbol node) {
4125 ConstantHandler handler = compiler.constantHandler; 4127 stack.add(addConstant(node));
4126 ConstructedConstant constant = 4128 compiler.enqueuer.codegen.registerConstSymbol(
4127 handler.compileNodeWithDefinitions(node, elements); 4129 node.slowNameString, elements);
4128 stack.add(graph.addConstant(constant, compiler));
4129 compiler.enqueuer.codegen.registerConstSymbol(node.slowNameString, elements) ;
4130 } 4130 }
4131 4131
4132 void visitStringJuxtaposition(StringJuxtaposition node) { 4132 void visitStringJuxtaposition(StringJuxtaposition node) {
4133 if (!node.isInterpolation) { 4133 if (!node.isInterpolation) {
4134 // This is a simple string with no interpolations. 4134 // This is a simple string with no interpolations.
4135 stack.add(graph.addConstantString(node.dartString, node, compiler)); 4135 stack.add(graph.addConstantString(node.dartString, node, compiler));
4136 return; 4136 return;
4137 } 4137 }
4138 StringBuilderVisitor stringBuilder = new StringBuilderVisitor(this, node); 4138 StringBuilderVisitor stringBuilder = new StringBuilderVisitor(this, node);
4139 stringBuilder.visit(node); 4139 stringBuilder.visit(node);
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
4193 closeAndGotoExit(new HThrow(exception, isRethrow: true)); 4193 closeAndGotoExit(new HThrow(exception, isRethrow: true));
4194 } 4194 }
4195 4195
4196 visitReturn(Return node) { 4196 visitReturn(Return node) {
4197 if (identical(node.getBeginToken().stringValue, 'native')) { 4197 if (identical(node.getBeginToken().stringValue, 'native')) {
4198 native.handleSsaNative(this, node.expression); 4198 native.handleSsaNative(this, node.expression);
4199 return; 4199 return;
4200 } 4200 }
4201 HInstruction value; 4201 HInstruction value;
4202 if (node.isRedirectingFactoryBody) { 4202 if (node.isRedirectingFactoryBody) {
4203 FunctionElement element = elements[node.expression]; 4203 FunctionElement element = elements[node.expression].implementation;
4204 FunctionElement function = currentElement; 4204 FunctionElement function = currentElement;
4205 List<HInstruction> inputs = <HInstruction>[]; 4205 List<HInstruction> inputs = <HInstruction>[];
4206 FunctionSignature calleeSignature = element.functionSignature; 4206 FunctionSignature calleeSignature = element.functionSignature;
4207 FunctionSignature callerSignature = function.functionSignature; 4207 FunctionSignature callerSignature = function.functionSignature;
4208 callerSignature.forEachRequiredParameter((Element element) { 4208 callerSignature.forEachRequiredParameter((Element element) {
4209 inputs.add(localsHandler.readLocal(element)); 4209 inputs.add(localsHandler.readLocal(element));
4210 }); 4210 });
4211 List<Element> calleeOptionals = 4211 List<Element> calleeOptionals =
4212 calleeSignature.orderedOptionalParameters; 4212 calleeSignature.orderedOptionalParameters;
4213 List<Element> callerOptionals = 4213 List<Element> callerOptionals =
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after
4277 visitSendSet(definition); 4277 visitSendSet(definition);
4278 pop(); // Discard value. 4278 pop(); // Discard value.
4279 } 4279 }
4280 } 4280 }
4281 } 4281 }
4282 4282
4283 visitLiteralList(LiteralList node) { 4283 visitLiteralList(LiteralList node) {
4284 HInstruction instruction; 4284 HInstruction instruction;
4285 4285
4286 if (node.isConst()) { 4286 if (node.isConst()) {
4287 ConstantHandler handler = compiler.constantHandler; 4287 instruction = addConstant(node);
4288 Constant constant = handler.compileNodeWithDefinitions(node, elements);
4289 instruction = graph.addConstant(constant, compiler);
4290 } else { 4288 } else {
4291 List<HInstruction> inputs = <HInstruction>[]; 4289 List<HInstruction> inputs = <HInstruction>[];
4292 for (Link<Node> link = node.elements.nodes; 4290 for (Link<Node> link = node.elements.nodes;
4293 !link.isEmpty; 4291 !link.isEmpty;
4294 link = link.tail) { 4292 link = link.tail) {
4295 visit(link.head); 4293 visit(link.head);
4296 inputs.add(pop()); 4294 inputs.add(pop());
4297 } 4295 }
4298 instruction = buildLiteralList(inputs); 4296 instruction = buildLiteralList(inputs);
4299 add(instruction); 4297 add(instruction);
(...skipping 176 matching lines...) Expand 10 before | Expand all | Expand 10 after
4476 entryBlock.setBlockFlow( 4474 entryBlock.setBlockFlow(
4477 new HLabeledBlockInformation(new HSubGraphBlockInformation(bodyGraph), 4475 new HLabeledBlockInformation(new HSubGraphBlockInformation(bodyGraph),
4478 handler.labels()), 4476 handler.labels()),
4479 joinBlock); 4477 joinBlock);
4480 } 4478 }
4481 handler.close(); 4479 handler.close();
4482 } 4480 }
4483 4481
4484 visitLiteralMap(LiteralMap node) { 4482 visitLiteralMap(LiteralMap node) {
4485 if (node.isConst()) { 4483 if (node.isConst()) {
4486 ConstantHandler handler = compiler.constantHandler; 4484 stack.add(addConstant(node));
4487 Constant constant = handler.compileNodeWithDefinitions(node, elements);
4488 stack.add(graph.addConstant(constant, compiler));
4489 return; 4485 return;
4490 } 4486 }
4491 List<HInstruction> inputs = <HInstruction>[]; 4487 List<HInstruction> inputs = <HInstruction>[];
4492 for (Link<Node> link = node.entries.nodes; 4488 for (Link<Node> link = node.entries.nodes;
4493 !link.isEmpty; 4489 !link.isEmpty;
4494 link = link.tail) { 4490 link = link.tail) {
4495 visit(link.head); 4491 visit(link.head);
4496 inputs.add(pop()); 4492 inputs.add(pop());
4497 inputs.add(pop()); 4493 inputs.add(pop());
4498 } 4494 }
(...skipping 17 matching lines...) Expand all
4516 // First check whether all case expressions are compile-time constants, 4512 // First check whether all case expressions are compile-time constants,
4517 // and all have the same type that doesn't override operator==. 4513 // and all have the same type that doesn't override operator==.
4518 // TODO(lrn): Move the constant resolution to the resolver, so 4514 // TODO(lrn): Move the constant resolution to the resolver, so
4519 // we can report an error before reaching the backend. 4515 // we can report an error before reaching the backend.
4520 DartType firstConstantType = null; 4516 DartType firstConstantType = null;
4521 bool failure = false; 4517 bool failure = false;
4522 for (SwitchCase switchCase in node.cases) { 4518 for (SwitchCase switchCase in node.cases) {
4523 for (Node labelOrCase in switchCase.labelsAndCases) { 4519 for (Node labelOrCase in switchCase.labelsAndCases) {
4524 if (labelOrCase is CaseMatch) { 4520 if (labelOrCase is CaseMatch) {
4525 CaseMatch match = labelOrCase; 4521 CaseMatch match = labelOrCase;
4526 Constant constant = 4522 Constant constant = getConstantForNode(match.expression);
4527 compiler.constantHandler.compileNodeWithDefinitions(
4528 match.expression, elements, isConst: true);
4529 if (firstConstantType == null) { 4523 if (firstConstantType == null) {
4530 firstConstantType = constant.computeType(compiler); 4524 firstConstantType = constant.computeType(compiler);
4531 if (nonPrimitiveTypeOverridesEquals(constant)) { 4525 if (nonPrimitiveTypeOverridesEquals(constant)) {
4532 compiler.reportFatalError( 4526 compiler.reportFatalError(
4533 match.expression, 4527 match.expression,
4534 MessageKind.SWITCH_CASE_VALUE_OVERRIDES_EQUALS); 4528 MessageKind.SWITCH_CASE_VALUE_OVERRIDES_EQUALS);
4535 failure = true; 4529 failure = true;
4536 } 4530 }
4537 } 4531 }
4538 constants[labelOrCase] = constant; 4532 constants[labelOrCase] = constant;
(...skipping 1016 matching lines...) Expand 10 before | Expand all | Expand 10 after
5555 new HSubGraphBlockInformation(elseBranch.graph)); 5549 new HSubGraphBlockInformation(elseBranch.graph));
5556 5550
5557 HBasicBlock conditionStartBlock = conditionBranch.block; 5551 HBasicBlock conditionStartBlock = conditionBranch.block;
5558 conditionStartBlock.setBlockFlow(info, joinBlock); 5552 conditionStartBlock.setBlockFlow(info, joinBlock);
5559 SubGraph conditionGraph = conditionBranch.graph; 5553 SubGraph conditionGraph = conditionBranch.graph;
5560 HIf branch = conditionGraph.end.last; 5554 HIf branch = conditionGraph.end.last;
5561 assert(branch is HIf); 5555 assert(branch is HIf);
5562 branch.blockInformation = conditionStartBlock.blockFlow; 5556 branch.blockInformation = conditionStartBlock.blockFlow;
5563 } 5557 }
5564 } 5558 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698