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

Side by Side Diff: lib/compiler/implementation/ssa/optimize.dart

Issue 10353014: Start implementing checked mode and tools support for using it. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 8 years, 7 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) 2011, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2011, 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 interface OptimizationPhase { 5 interface OptimizationPhase {
6 String get name(); 6 String get name();
7 void visitGraph(HGraph graph); 7 void visitGraph(HGraph graph);
8 } 8 }
9 9
10 class SsaOptimizerTask extends CompilerTask { 10 class SsaOptimizerTask extends CompilerTask {
(...skipping 112 matching lines...) Expand 10 before | Expand all | Expand 10 after
123 HInstruction visitInstruction(HInstruction node) { 123 HInstruction visitInstruction(HInstruction node) {
124 return node; 124 return node;
125 } 125 }
126 126
127 HInstruction visitBoolify(HBoolify node) { 127 HInstruction visitBoolify(HBoolify node) {
128 List<HInstruction> inputs = node.inputs; 128 List<HInstruction> inputs = node.inputs;
129 assert(inputs.length == 1); 129 assert(inputs.length == 1);
130 HInstruction input = inputs[0]; 130 HInstruction input = inputs[0];
131 if (input.isBoolean()) return input; 131 if (input.isBoolean()) return input;
132 // All values !== true are boolified to false. 132 // All values !== true are boolified to false.
133 if (input.propagatedType.isUseful()) { 133 Type type = input.propagatedType.computeType(compiler);
134 if (type !== null && type.element !== compiler.boolClass) {
134 return graph.addConstantBool(false); 135 return graph.addConstantBool(false);
135 } 136 }
136 return node; 137 return node;
137 } 138 }
138 139
139 HInstruction visitNot(HNot node) { 140 HInstruction visitNot(HNot node) {
140 List<HInstruction> inputs = node.inputs; 141 List<HInstruction> inputs = node.inputs;
141 assert(inputs.length == 1); 142 assert(inputs.length == 1);
142 HInstruction input = inputs[0]; 143 HInstruction input = inputs[0];
143 if (input is HConstant) { 144 if (input is HConstant) {
(...skipping 286 matching lines...) Expand 10 before | Expand all | Expand 10 after
430 } else if (right.isConstantNull()) { 431 } else if (right.isConstantNull()) {
431 return graph.addConstantBool(false); 432 return graph.addConstantBool(false);
432 } else { 433 } else {
433 // We can just emit an identity check because the type does 434 // We can just emit an identity check because the type does
434 // not implement operator=. 435 // not implement operator=.
435 return foldBuiltinEqualsCheck(node); 436 return foldBuiltinEqualsCheck(node);
436 } 437 }
437 } 438 }
438 439
439 if (right.isConstantNull()) { 440 if (right.isConstantNull()) {
440 if (left.propagatedType.isUseful()) { 441 if (!left.propagatedType.canBeNull()) {
floitsch 2012/05/07 09:50:07 I would prefer switching to the new semantics in a
ngeoffray 2012/05/07 13:15:42 This should have been if (leg.propagatedType.isPri
441 return graph.addConstantBool(false); 442 return graph.addConstantBool(false);
442 } else { 443 } else {
443 // TODO(floitsch): cache interceptors. 444 // TODO(floitsch): cache interceptors.
444 Interceptors interceptors = compiler.builder.interceptors; 445 Interceptors interceptors = compiler.builder.interceptors;
445 Element equalsElement = interceptors.getEqualsInterceptor(); 446 Element equalsElement = interceptors.getEqualsInterceptor();
446 // If we have a different element than [equalsElement], we 447 // If we have a different element than [equalsElement], we
447 // don't need to optimize this instruction to use another 448 // don't need to optimize this instruction to use another
448 // element: we know the element is either eqNull or eqNullB. 449 // element: we know the element is either eqNull or eqNullB.
449 if (node.element === equalsElement) { 450 if (node.element === equalsElement) {
450 Element targetElement = interceptors.getEqualsNullInterceptor(); 451 Element targetElement = interceptors.getEqualsNullInterceptor();
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after
525 } 526 }
526 } else if (expressionType.isArray()) { 527 } else if (expressionType.isArray()) {
527 if (element === compiler.listClass 528 if (element === compiler.listClass
528 || Elements.isListSupertype(element, compiler)) { 529 || Elements.isListSupertype(element, compiler)) {
529 return graph.addConstantBool(true); 530 return graph.addConstantBool(true);
530 } else { 531 } else {
531 return graph.addConstantBool(false); 532 return graph.addConstantBool(false);
532 } 533 }
533 // TODO(karlklose): remove the hasTypeArguments check. 534 // TODO(karlklose): remove the hasTypeArguments check.
534 } else if (expressionType.isUseful() 535 } else if (expressionType.isUseful()
536 && !expressionType.canBeNull()
floitsch 2012/05/07 09:50:07 you could move that check into the 'true' section.
ngeoffray 2012/05/07 13:15:42 Done.
535 && !compiler.universe.rti.hasTypeArguments(type)) { 537 && !compiler.universe.rti.hasTypeArguments(type)) {
536 Type receiverType = expressionType.computeType(compiler); 538 Type receiverType = expressionType.computeType(compiler);
537 if (receiverType !== null) { 539 if (receiverType !== null) {
538 if (compiler.types.isSubtype(receiverType, type)) { 540 if (compiler.types.isSubtype(receiverType, type)) {
539 return graph.addConstantBool(true); 541 return graph.addConstantBool(true);
540 } else if (expressionType.isExact()) { 542 } else if (expressionType.isExact()) {
541 return graph.addConstantBool(false); 543 return graph.addConstantBool(false);
542 } 544 }
543 } 545 }
544 } 546 }
(...skipping 502 matching lines...) Expand 10 before | Expand all | Expand 10 after
1047 newInput = new HTypeConversion(convertedType, input); 1049 newInput = new HTypeConversion(convertedType, input);
1048 dominator.addBefore(dominator.first, newInput); 1050 dominator.addBefore(dominator.first, newInput);
1049 } 1051 }
1050 user.changeUse(input, newInput); 1052 user.changeUse(input, newInput);
1051 } 1053 }
1052 } 1054 }
1053 } 1055 }
1054 1056
1055 void visitIs(HIs instruction) { 1057 void visitIs(HIs instruction) {
1056 HInstruction input = instruction.expression; 1058 HInstruction input = instruction.expression;
1059 HType convertedType =
1060 new HType.fromBoundedType(instruction.typeExpression, compiler);
1061 if (convertedType === null) return;
1062
1057 List<HInstruction> ifUsers = <HInstruction>[]; 1063 List<HInstruction> ifUsers = <HInstruction>[];
1058 List<HInstruction> notIfUsers = <HInstruction>[]; 1064 List<HInstruction> notIfUsers = <HInstruction>[];
1059 1065
1060 for (HInstruction user in instruction.usedBy) { 1066 for (HInstruction user in instruction.usedBy) {
1061 if (user is HIf) { 1067 if (user is HIf) {
1062 ifUsers.add(user); 1068 ifUsers.add(user);
1063 } else if (user is HNot) { 1069 } else if (user is HNot) {
1064 for (HInstruction notUser in user.usedBy) { 1070 for (HInstruction notUser in user.usedBy) {
1065 if (notUser is HIf) notIfUsers.add(notUser); 1071 if (notUser is HIf) notIfUsers.add(notUser);
1066 } 1072 }
1067 } 1073 }
1068 } 1074 }
1069 1075
1070 if (ifUsers.isEmpty() && notIfUsers.isEmpty()) return; 1076 if (ifUsers.isEmpty() && notIfUsers.isEmpty()) return;
1071 1077
1072 HType convertedType =
1073 new HType.fromBoundedType(instruction.typeExpression, compiler);
1074
1075 for (HIf ifUser in ifUsers) { 1078 for (HIf ifUser in ifUsers) {
1076 changeUsesDominatedBy(ifUser.thenBlock, input, convertedType); 1079 changeUsesDominatedBy(ifUser.thenBlock, input, convertedType);
1077 // TODO(ngeoffray): Also change uses for the else block on a HType 1080 // TODO(ngeoffray): Also change uses for the else block on a HType
1078 // that knows it is not of a specific Type. 1081 // that knows it is not of a specific Type.
1079 } 1082 }
1080 1083
1081 for (HIf ifUser in notIfUsers) { 1084 for (HIf ifUser in notIfUsers) {
1082 if (ifUser.hasElse) { 1085 if (ifUser.hasElse) {
1083 changeUsesDominatedBy(ifUser.elseBlock, input, convertedType); 1086 changeUsesDominatedBy(ifUser.elseBlock, input, convertedType);
1084 } else if (ifUser.joinBlock.predecessors.length == 1) { 1087 } else if (ifUser.joinBlock.predecessors.length == 1) {
1085 // If the join block has only one predecessor, then we know 1088 // If the join block has only one predecessor, then we know
1086 // the if block terminates. So any use of the instruction 1089 // the if block terminates. So any use of the instruction
1087 // after the join block should be changed to the new 1090 // after the join block should be changed to the new
1088 // instruction. 1091 // instruction.
1089 changeUsesDominatedBy(ifUser.joinBlock, input, convertedType); 1092 changeUsesDominatedBy(ifUser.joinBlock, input, convertedType);
1090 } 1093 }
1091 // TODO(ngeoffray): Also change uses for the then block on a HType 1094 // TODO(ngeoffray): Also change uses for the then block on a HType
1092 // that knows it is not of a specific Type. 1095 // that knows it is not of a specific Type.
1093 } 1096 }
1094 } 1097 }
1095 } 1098 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698