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

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

Issue 12334070: Support runtime check of function types. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Register dependency Created 7 years, 9 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 2230 matching lines...) Expand 10 before | Expand all | Expand 10 after
2241 if (member.isField()) { 2241 if (member.isField()) {
2242 Element capturedLocal = nestedClosureData.capturedFieldMapping[member]; 2242 Element capturedLocal = nestedClosureData.capturedFieldMapping[member];
2243 assert(capturedLocal != null); 2243 assert(capturedLocal != null);
2244 capturedVariables.add(localsHandler.readLocal(capturedLocal)); 2244 capturedVariables.add(localsHandler.readLocal(capturedLocal));
2245 } 2245 }
2246 }); 2246 });
2247 2247
2248 HType type = new HType.nonNullExact( 2248 HType type = new HType.nonNullExact(
2249 compiler.functionClass.computeType(compiler), 2249 compiler.functionClass.computeType(compiler),
2250 compiler); 2250 compiler);
2251 push(new HForeignNew(closureClassElement, type, capturedVariables)); 2251 HInstruction newClosure =
2252 new HForeignNew(closureClassElement, type, capturedVariables);
2253 ClassElement thisClass = work.element.getEnclosingClass();
ngeoffray 2013/03/13 09:30:46 thisClass can be null right? Don't you need to che
Johnni Winther 2013/03/22 07:30:24 Stale
2254 if (compiler.world.needsRti(thisClass) &&
2255 callElement.computeType(compiler).containsTypeVariables) {
2256 add(newClosure);
2257
2258 Element forwardRuntimeTypeInfo = backend.getForwardRuntimeTypeInfo();
2259 HInstruction forwardRuntimeTypeInfoCall =
2260 new HStatic(forwardRuntimeTypeInfo);
2261 add(forwardRuntimeTypeInfoCall);
2262
2263 String substitutionName = backend.namer.substitutionName(thisClass);
2264 HInstruction substitution =
2265 createForeign('this.$substitutionName', HType.UNKNOWN, []);
ngeoffray 2013/03/13 09:30:46 Change "this" to use #.
Johnni Winther 2013/03/22 07:30:24 Stale
2266 add(substitution);
2267
2268 HInstruction context = new HThis(thisClass, HType.UNKNOWN);
2269 add(context);
2270
2271 List<HInstruction> inputs = <HInstruction>[forwardRuntimeTypeInfoCall,
2272 newClosure,
2273 substitution,
2274 context];
2275 push(new HInvokeStatic(inputs, HType.UNKNOWN));
2276 } else {
2277 push(newClosure);
2278 }
2252 } 2279 }
2253 2280
2254 visitFunctionDeclaration(FunctionDeclaration node) { 2281 visitFunctionDeclaration(FunctionDeclaration node) {
2255 visit(node.function); 2282 visit(node.function);
2256 localsHandler.updateLocal(elements[node], pop()); 2283 localsHandler.updateLocal(elements[node], pop());
2257 } 2284 }
2258 2285
2259 visitIdentifier(Identifier node) { 2286 visitIdentifier(Identifier node) {
2260 if (node.isThis()) { 2287 if (node.isThis()) {
2261 stack.add(localsHandler.readThis()); 2288 stack.add(localsHandler.readThis());
(...skipping 376 matching lines...) Expand 10 before | Expand all | Expand 10 after
2638 Node argument = node.arguments.head; 2665 Node argument = node.arguments.head;
2639 TypeAnnotation typeAnnotation = argument.asTypeAnnotation(); 2666 TypeAnnotation typeAnnotation = argument.asTypeAnnotation();
2640 bool isNot = false; 2667 bool isNot = false;
2641 // TODO(ngeoffray): Duplicating pattern in resolver. We should 2668 // TODO(ngeoffray): Duplicating pattern in resolver. We should
2642 // add a new kind of node. 2669 // add a new kind of node.
2643 if (typeAnnotation == null) { 2670 if (typeAnnotation == null) {
2644 typeAnnotation = argument.asSend().receiver; 2671 typeAnnotation = argument.asSend().receiver;
2645 isNot = true; 2672 isNot = true;
2646 } 2673 }
2647 DartType type = elements.getType(typeAnnotation); 2674 DartType type = elements.getType(typeAnnotation);
2675 type = type.unalias(compiler);
2648 if (type.isMalformed) { 2676 if (type.isMalformed) {
2649 String reasons = Types.fetchReasonsFromMalformedType(type); 2677 String reasons = Types.fetchReasonsFromMalformedType(type);
2650 if (compiler.enableTypeAssertions) { 2678 if (compiler.enableTypeAssertions) {
2651 generateMalformedSubtypeError(node, expression, type, reasons); 2679 generateMalformedSubtypeError(node, expression, type, reasons);
2652 } else { 2680 } else {
2653 generateRuntimeError(node, '$type is malformed: $reasons'); 2681 generateRuntimeError(node, '$type is malformed: $reasons');
2654 } 2682 }
2655 return; 2683 return;
2656 } 2684 }
2657 2685
2658 HInstruction instruction; 2686 HInstruction instruction;
2659 if (type.kind == TypeKind.TYPE_VARIABLE) { 2687 if (type is FunctionType) {
ngeoffray 2013/03/13 09:30:46 Use the kind instead?
Johnni Winther 2013/03/22 07:30:24 Done.
2688 compiler.enqueuer.codegen.registerIsCheck(type, work.resolutionTree);
ngeoffray 2013/03/13 09:30:46 Add a TODO that this should be done in codegen.
Johnni Winther 2013/06/21 12:19:14 Stale.
2689
2690 void functionTypeCheck() {
2691 Element checkFunctionSubtype = backend.getCheckFunctionSubtype();
2692 HInstruction isFuncSubtypeCall = new HStatic(checkFunctionSubtype);
2693 add(isFuncSubtypeCall);
2694
2695 String typeSignatureName;
2696 HInstruction context;
2697 ClassElement contextClass = Types.getClassContext(type);
ngeoffray 2013/03/13 09:30:46 What is this?
Johnni Winther 2013/03/22 07:30:24 The class which declared the used type variables,
2698 if (contextClass != null) {
2699 typeSignatureName = backend.namer.signatureName(type);
2700 context = new HThis(contextClass, HType.UNKNOWN);
ngeoffray 2013/03/13 09:30:46 What's this HThis? Why isn't it the one of the bui
Johnni Winther 2013/03/22 07:30:24 Changed.
2701 add(context);
2702 } else {
2703 typeSignatureName = backend.namer.signatureName(type);
2704 context = graph.addConstantNull(constantSystem);
2705 }
2706 HInstruction typeSignature =
2707 createForeign('$typeSignatureName', HType.UNKNOWN, []);
2708 add(typeSignature);
2709
2710 List<HInstruction> inputs = <HInstruction>[isFuncSubtypeCall,
2711 expression,
2712 typeSignature,
2713 context];
2714 push(new HInvokeStatic(inputs, HType.UNKNOWN));
2715 }
2716
2717 void classCheck() { push(new HIs(type, <HInstruction>[expression])); }
2718
2719 SsaBranchBuilder branchBuilder = new SsaBranchBuilder(this, node);
2720 branchBuilder.handleLogicalAndOr(
2721 classCheck, functionTypeCheck, isAnd: true);
2722 instruction = pop();
2723 } else if (type.kind == TypeKind.TYPE_VARIABLE) {
2660 HInstruction runtimeType = addTypeVariableReference(type); 2724 HInstruction runtimeType = addTypeVariableReference(type);
2661 Element helper = backend.getGetObjectIsSubtype(); 2725 Element helper = backend.getGetObjectIsSubtype();
2662 HInstruction helperCall = new HStatic(helper); 2726 HInstruction helperCall = new HStatic(helper);
2663 add(helperCall); 2727 add(helperCall);
2664 List<HInstruction> inputs = <HInstruction>[helperCall, expression, 2728 List<HInstruction> inputs = <HInstruction>[helperCall, expression,
2665 runtimeType]; 2729 runtimeType];
2666 instruction = new HInvokeStatic(inputs, HType.BOOLEAN); 2730 instruction = new HInvokeStatic(inputs, HType.BOOLEAN);
2667 add(instruction); 2731 add(instruction);
2668 compiler.enqueuer.codegen.registerIsCheck(type, elements); 2732 compiler.enqueuer.codegen.registerIsCheck(type, elements);
2669 2733
(...skipping 2440 matching lines...) Expand 10 before | Expand all | Expand 10 after
5110 new HSubGraphBlockInformation(elseBranch.graph)); 5174 new HSubGraphBlockInformation(elseBranch.graph));
5111 5175
5112 HBasicBlock conditionStartBlock = conditionBranch.block; 5176 HBasicBlock conditionStartBlock = conditionBranch.block;
5113 conditionStartBlock.setBlockFlow(info, joinBlock); 5177 conditionStartBlock.setBlockFlow(info, joinBlock);
5114 SubGraph conditionGraph = conditionBranch.graph; 5178 SubGraph conditionGraph = conditionBranch.graph;
5115 HIf branch = conditionGraph.end.last; 5179 HIf branch = conditionGraph.end.last;
5116 assert(branch is HIf); 5180 assert(branch is HIf);
5117 branch.blockInformation = conditionStartBlock.blockFlow; 5181 branch.blockInformation = conditionStartBlock.blockFlow;
5118 } 5182 }
5119 } 5183 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698