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

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

Issue 11273034: Make unmatched static call a runtime error. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Remove isValid. Created 8 years, 1 month 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 class Interceptors { 7 class Interceptors {
8 Compiler compiler; 8 Compiler compiler;
9 Interceptors(Compiler this.compiler); 9 Interceptors(Compiler this.compiler);
10 10
(...skipping 2282 matching lines...) Expand 10 before | Expand all | Expand 10 after
2293 2293
2294 void pushInvokeHelper3(Element helper, HInstruction a0, HInstruction a1, 2294 void pushInvokeHelper3(Element helper, HInstruction a0, HInstruction a1,
2295 HInstruction a2) { 2295 HInstruction a2) {
2296 HInstruction reference = new HStatic(helper); 2296 HInstruction reference = new HStatic(helper);
2297 add(reference); 2297 add(reference);
2298 List<HInstruction> inputs = <HInstruction>[reference, a0, a1, a2]; 2298 List<HInstruction> inputs = <HInstruction>[reference, a0, a1, a2];
2299 HInstruction result = new HInvokeStatic(inputs); 2299 HInstruction result = new HInvokeStatic(inputs);
2300 push(result); 2300 push(result);
2301 } 2301 }
2302 2302
2303 void pushInvokeHelper4(Element helper, HInstruction a0, HInstruction a1,
2304 HInstruction a2, HInstruction a3) {
2305 HInstruction reference = new HStatic(helper);
2306 add(reference);
2307 List<HInstruction> inputs = <HInstruction>[reference, a0, a1, a2, a3];
2308 HInstruction result = new HInvokeStatic(inputs);
2309 push(result);
2310 }
2311
2303 visitOperatorSend(node) { 2312 visitOperatorSend(node) {
2304 assert(node.selector is Operator); 2313 assert(node.selector is Operator);
2305 if (!methodInterceptionEnabled) { 2314 if (!methodInterceptionEnabled) {
2306 visitDynamicSend(node); 2315 visitDynamicSend(node);
2307 return; 2316 return;
2308 } 2317 }
2309 2318
2310 Operator op = node.selector; 2319 Operator op = node.selector;
2311 if (const SourceString("[]") == op.source) { 2320 if (const SourceString("[]") == op.source) {
2312 HStatic target = new HStatic(interceptors.getIndexInterceptor()); 2321 HStatic target = new HStatic(interceptors.getIndexInterceptor());
(...skipping 413 matching lines...) Expand 10 before | Expand all | Expand 10 after
2726 // creating an [HStatic]. 2735 // creating an [HStatic].
2727 HInstruction target = new HStatic(element.declaration); 2736 HInstruction target = new HStatic(element.declaration);
2728 HInstruction context = localsHandler.readThis(); 2737 HInstruction context = localsHandler.readThis();
2729 add(target); 2738 add(target);
2730 var inputs = <HInstruction>[target, context]; 2739 var inputs = <HInstruction>[target, context];
2731 if (node.isPropertyAccess) { 2740 if (node.isPropertyAccess) {
2732 push(new HInvokeSuper(inputs)); 2741 push(new HInvokeSuper(inputs));
2733 } else if (element.isFunction() || element.isGenerativeConstructor()) { 2742 } else if (element.isFunction() || element.isGenerativeConstructor()) {
2734 // TODO(5347): Try to avoid the need for calling [implementation] before 2743 // TODO(5347): Try to avoid the need for calling [implementation] before
2735 // calling [addStaticSendArgumentsToList]. 2744 // calling [addStaticSendArgumentsToList].
2745 FunctionElement function = element.implementation;
2736 bool succeeded = addStaticSendArgumentsToList(selector, node.arguments, 2746 bool succeeded = addStaticSendArgumentsToList(selector, node.arguments,
2737 element.implementation, 2747 function, inputs);
2738 inputs);
2739 if (!succeeded) { 2748 if (!succeeded) {
2740 // TODO(ngeoffray): Match the VM behavior and throw an 2749 generateWrongArgumentCountError(node, element, node.arguments);
2741 // exception at runtime. 2750 } else {
2742 compiler.cancel('Unimplemented non-matching static call', node: node); 2751 push(new HInvokeSuper(inputs));
2743 } 2752 }
2744 push(new HInvokeSuper(inputs));
2745 } else { 2753 } else {
2746 target = new HInvokeSuper(inputs); 2754 target = new HInvokeSuper(inputs);
2747 add(target); 2755 add(target);
2748 inputs = <HInstruction>[target]; 2756 inputs = <HInstruction>[target];
2749 addDynamicSendArgumentsToList(node, inputs); 2757 addDynamicSendArgumentsToList(node, inputs);
2750 push(new HInvokeClosure(selector, inputs)); 2758 push(new HInvokeClosure(selector, inputs));
2751 } 2759 }
2752 } 2760 }
2753 2761
2754 HInstruction analyzeTypeArgument(DartType argument, Node currentNode) { 2762 HInstruction analyzeTypeArgument(DartType argument, Node currentNode) {
(...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after
2933 HInstruction target = new HStatic(constructor.declaration); 2941 HInstruction target = new HStatic(constructor.declaration);
2934 add(target); 2942 add(target);
2935 var inputs = <HInstruction>[]; 2943 var inputs = <HInstruction>[];
2936 inputs.add(target); 2944 inputs.add(target);
2937 // TODO(5347): Try to avoid the need for calling [implementation] before 2945 // TODO(5347): Try to avoid the need for calling [implementation] before
2938 // calling [addStaticSendArgumentsToList]. 2946 // calling [addStaticSendArgumentsToList].
2939 bool succeeded = addStaticSendArgumentsToList(selector, node.arguments, 2947 bool succeeded = addStaticSendArgumentsToList(selector, node.arguments,
2940 constructor.implementation, 2948 constructor.implementation,
2941 inputs); 2949 inputs);
2942 if (!succeeded) { 2950 if (!succeeded) {
2943 // TODO(ngeoffray): Match the VM behavior and throw an 2951 generateWrongArgumentCountError(node, constructor, node.arguments);
2944 // exception at runtime. 2952 return;
2945 compiler.cancel('Unimplemented non-matching static call', node: node);
2946 } 2953 }
2947 2954
2948 TypeAnnotation annotation = node.getTypeAnnotation(); 2955 TypeAnnotation annotation = node.getTypeAnnotation();
2949 if (annotation == null) { 2956 if (annotation == null) {
2950 compiler.internalError("malformed send in new expression"); 2957 compiler.internalError("malformed send in new expression");
2951 } 2958 }
2952 InterfaceType type = elements.getType(annotation); 2959 InterfaceType type = elements.getType(annotation);
2953 if (type.element.modifiers.isAbstract() && 2960 if (type.element.modifiers.isAbstract() &&
2954 constructor.isGenerativeConstructor()) { 2961 constructor.isGenerativeConstructor()) {
2955 generateAbstractClassInstantiationError(node, type.name.slowToString()); 2962 generateAbstractClassInstantiationError(node, type.name.slowToString());
(...skipping 20 matching lines...) Expand all
2976 2983
2977 visitStaticSend(Send node) { 2984 visitStaticSend(Send node) {
2978 Selector selector = elements.getSelector(node); 2985 Selector selector = elements.getSelector(node);
2979 Element element = elements[node]; 2986 Element element = elements[node];
2980 if (element.isErroneous()) { 2987 if (element.isErroneous()) {
2981 generateThrowNoSuchMethod(node, 2988 generateThrowNoSuchMethod(node,
2982 getTargetName(element), 2989 getTargetName(element),
2983 argumentNodes: node.arguments); 2990 argumentNodes: node.arguments);
2984 return; 2991 return;
2985 } 2992 }
2986 if (identical(element, compiler.assertMethod) && !compiler.enableUserAsserti ons) { 2993 if (identical(element, compiler.assertMethod)
2994 && !compiler.enableUserAssertions) {
2987 stack.add(graph.addConstantNull(constantSystem)); 2995 stack.add(graph.addConstantNull(constantSystem));
2988 return; 2996 return;
2989 } 2997 }
2990 compiler.ensure(!element.isGenerativeConstructor()); 2998 compiler.ensure(!element.isGenerativeConstructor());
2991 if (element.isFunction()) { 2999 if (element.isFunction()) {
2992 if (tryInlineMethod(element, selector, node.arguments)) { 3000 if (tryInlineMethod(element, selector, node.arguments)) {
2993 return; 3001 return;
2994 } 3002 }
2995 3003
2996 HInstruction target = new HStatic(element); 3004 HInstruction target = new HStatic(element);
2997 add(target); 3005 add(target);
2998 var inputs = <HInstruction>[target]; 3006 var inputs = <HInstruction>[target];
2999 // TODO(5347): Try to avoid the need for calling [implementation] before 3007 // TODO(5347): Try to avoid the need for calling [implementation] before
3000 // calling [addStaticSendArgumentsToList]. 3008 // calling [addStaticSendArgumentsToList].
3001 bool succeeded = addStaticSendArgumentsToList(selector, node.arguments, 3009 bool succeeded = addStaticSendArgumentsToList(selector, node.arguments,
3002 element.implementation, 3010 element.implementation,
3003 inputs); 3011 inputs);
3004 if (!succeeded) { 3012 if (!succeeded) {
3005 // TODO(ngeoffray): Match the VM behavior and throw an 3013 generateWrongArgumentCountError(node, element, node.arguments);
3006 // exception at runtime. 3014 return;
3007 compiler.cancel('Unimplemented non-matching static call', node: node);
3008 } 3015 }
3009 3016
3010 // TODO(kasperl): Try to use the general inlining infrastructure for 3017 // TODO(kasperl): Try to use the general inlining infrastructure for
3011 // inlining the identical function. 3018 // inlining the identical function.
3012 if (identical(element, compiler.identicalFunction)) { 3019 if (identical(element, compiler.identicalFunction)) {
3013 pushWithPosition(new HIdentity(target, inputs[1], inputs[2]), node); 3020 pushWithPosition(new HIdentity(target, inputs[1], inputs[2]), node);
3014 return; 3021 return;
3015 } 3022 }
3016 3023
3017 HInvokeStatic instruction = new HInvokeStatic(inputs); 3024 HInvokeStatic instruction = new HInvokeStatic(inputs);
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
3053 3060
3054 void generateAbstractClassInstantiationError(Node node, String message) { 3061 void generateAbstractClassInstantiationError(Node node, String message) {
3055 generateError(node, 3062 generateError(node,
3056 message, 3063 message,
3057 interceptors.getThrowAbstractClassInstantiationError()); 3064 interceptors.getThrowAbstractClassInstantiationError());
3058 } 3065 }
3059 3066
3060 void generateThrowNoSuchMethod(Node diagnosticNode, 3067 void generateThrowNoSuchMethod(Node diagnosticNode,
3061 String methodName, 3068 String methodName,
3062 {Link<Node> argumentNodes, 3069 {Link<Node> argumentNodes,
3063 List<HInstruction> argumentValues}) { 3070 List<HInstruction> argumentValues,
3071 List<String> existingArguments}) {
3064 Element helper = 3072 Element helper =
3065 compiler.findHelper(const SourceString('throwNoSuchMethod')); 3073 compiler.findHelper(const SourceString('throwNoSuchMethod'));
3066 Constant receiverConstant = 3074 Constant receiverConstant =
3067 constantSystem.createString(new DartString.empty(), diagnosticNode); 3075 constantSystem.createString(new DartString.empty(), diagnosticNode);
3068 HInstruction receiver = graph.addConstant(receiverConstant); 3076 HInstruction receiver = graph.addConstant(receiverConstant);
3069 DartString dartString = new DartString.literal(methodName); 3077 DartString dartString = new DartString.literal(methodName);
3070 Constant nameConstant = 3078 Constant nameConstant =
3071 constantSystem.createString(dartString, diagnosticNode); 3079 constantSystem.createString(dartString, diagnosticNode);
3072 HInstruction name = graph.addConstant(nameConstant); 3080 HInstruction name = graph.addConstant(nameConstant);
3073 if (argumentValues == null) { 3081 if (argumentValues == null) {
3074 argumentValues = <HInstruction>[]; 3082 argumentValues = <HInstruction>[];
3075 argumentNodes.forEach((argumentNode) { 3083 argumentNodes.forEach((argumentNode) {
3076 visit(argumentNode); 3084 visit(argumentNode);
3077 HInstruction value = pop(); 3085 HInstruction value = pop();
3078 argumentValues.add(value); 3086 argumentValues.add(value);
3079 }); 3087 });
3080 } 3088 }
3081 HInstruction arguments = new HLiteralList(argumentValues); 3089 HInstruction arguments = new HLiteralList(argumentValues);
3082 add(arguments); 3090 add(arguments);
3083 pushInvokeHelper3(helper, receiver, name, arguments); 3091 HInstruction existingNamesList;
3092 if (existingArguments != null) {
3093 List<HInstruction> existingNames = <HInstruction>[];
3094 for (String name in existingArguments) {
3095 HInstruction nameConstant =
3096 graph.addConstantString(new DartString.literal(name),
3097 diagnosticNode, constantSystem);
3098 existingNames.add(nameConstant);
3099 }
3100 existingNamesList = new HLiteralList(existingNames);
3101 add(existingNamesList);
3102 } else {
3103 existingNamesList = graph.addConstantNull(constantSystem);
3104 }
3105 pushInvokeHelper4(helper, receiver, name, arguments, existingNamesList);
3106 }
3107
3108 /**
3109 * Generate code to throw a [NoSuchMethodError] exception for calling a
3110 * method with a wrong number of arguments or mismatching named optional
3111 * arguments.
3112 */
3113 void generateWrongArgumentCountError(Node diagnosticNode,
3114 FunctionElement function,
3115 Link<Node> argumentNodes) {
3116 List<String> existingArguments = <String>[];
3117 FunctionSignature signature = function.computeSignature(compiler);
3118 signature.forEachParameter((Element parameter) {
3119 existingArguments.add(parameter.name.slowToString());
3120 });
3121 generateThrowNoSuchMethod(diagnosticNode,
3122 function.name.slowToString(),
3123 argumentNodes: argumentNodes,
3124 existingArguments: existingArguments);
3084 } 3125 }
3085 3126
3086 visitNewExpression(NewExpression node) { 3127 visitNewExpression(NewExpression node) {
3087 Element element = elements[node.send]; 3128 Element element = elements[node.send];
3088 if (Elements.isErroneousElement(element)) { 3129 if (Elements.isErroneousElement(element)) {
3089 ErroneousElement error = element; 3130 ErroneousElement error = element;
3090 if (error.messageKind == MessageKind.CANNOT_FIND_CONSTRUCTOR) { 3131 if (error.messageKind == MessageKind.CANNOT_FIND_CONSTRUCTOR) {
3091 generateThrowNoSuchMethod(node.send, 3132 generateThrowNoSuchMethod(node.send,
3092 getTargetName(error, 'constructor'), 3133 getTargetName(error, 'constructor'),
3093 argumentNodes: node.send.arguments); 3134 argumentNodes: node.send.arguments);
(...skipping 1415 matching lines...) Expand 10 before | Expand all | Expand 10 after
4509 new HSubGraphBlockInformation(elseBranch.graph)); 4550 new HSubGraphBlockInformation(elseBranch.graph));
4510 4551
4511 HBasicBlock conditionStartBlock = conditionBranch.block; 4552 HBasicBlock conditionStartBlock = conditionBranch.block;
4512 conditionStartBlock.setBlockFlow(info, joinBlock); 4553 conditionStartBlock.setBlockFlow(info, joinBlock);
4513 SubGraph conditionGraph = conditionBranch.graph; 4554 SubGraph conditionGraph = conditionBranch.graph;
4514 HIf branch = conditionGraph.end.last; 4555 HIf branch = conditionGraph.end.last;
4515 assert(branch is HIf); 4556 assert(branch is HIf);
4516 branch.blockInformation = conditionStartBlock.blockFlow; 4557 branch.blockInformation = conditionStartBlock.blockFlow;
4517 } 4558 }
4518 } 4559 }
OLDNEW
« no previous file with comments | « lib/compiler/implementation/resolution/members.dart ('k') | lib/compiler/implementation/universe/universe.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698