| Index: pkg/compiler/lib/src/ssa/graph_builder.dart
|
| diff --git a/pkg/compiler/lib/src/ssa/graph_builder.dart b/pkg/compiler/lib/src/ssa/graph_builder.dart
|
| index 22e6c308060c1aed9b9591099c733f244887f59d..7f112300128be9a7242f31585426ada8f9e9858f 100644
|
| --- a/pkg/compiler/lib/src/ssa/graph_builder.dart
|
| +++ b/pkg/compiler/lib/src/ssa/graph_builder.dart
|
| @@ -2,17 +2,25 @@
|
| // for details. All rights reserved. Use of this source code is governed by a
|
| // BSD-style license that can be found in the LICENSE file.
|
|
|
| +import '../closure.dart';
|
| +import '../common.dart';
|
| +import '../common/codegen.dart' show CodegenRegistry;
|
| import '../compiler.dart';
|
| +import '../dart_types.dart';
|
| import '../elements/elements.dart';
|
| import '../io/source_information.dart';
|
| import '../js_backend/js_backend.dart';
|
| import '../resolution/tree_elements.dart';
|
| import '../tree/tree.dart' as ast;
|
| import '../types/types.dart';
|
| +import '../universe/call_structure.dart' show CallStructure;
|
| +import '../universe/use.dart' show TypeUse;
|
| +import '../world.dart' show ClosedWorld;
|
| import 'jump_handler.dart';
|
| import 'locals_handler.dart';
|
| import 'nodes.dart';
|
| import 'ssa_branch_builder.dart';
|
| +import 'type_builder.dart';
|
|
|
| /// Base class for objects that build up an SSA graph.
|
| ///
|
| @@ -32,6 +40,8 @@ abstract class GraphBuilder {
|
| /// The tree elements for the element being built into an SSA graph.
|
| TreeElements get elements;
|
|
|
| + CodegenRegistry get registry;
|
| +
|
| /// Used to track the locals while building the graph.
|
| LocalsHandler localsHandler;
|
|
|
| @@ -182,4 +192,125 @@ abstract class GraphBuilder {
|
| if (expression == null) return null;
|
| return new HSubExpressionBlockInformation(expression);
|
| }
|
| +
|
| + HInstruction buildFunctionType(FunctionType type) {
|
| + type.accept(
|
| + new ReifiedTypeRepresentationBuilder(compiler.closedWorld), this);
|
| + return pop();
|
| + }
|
| +
|
| + HInstruction buildFunctionTypeConversion(
|
| + HInstruction original, DartType type, int kind);
|
| +
|
| + /// Returns the current source element.
|
| + ///
|
| + /// The returned element is a declaration element.
|
| + Element get sourceElement;
|
| +
|
| + // TODO(karlklose): this is needed to avoid a bug where the resolved type is
|
| + // not stored on a type annotation in the closure translator. Remove when
|
| + // fixed.
|
| + bool hasDirectLocal(Local local) {
|
| + return !localsHandler.isAccessedDirectly(local) ||
|
| + localsHandler.directLocals[local] != null;
|
| + }
|
| +
|
| + /// The element for which this SSA builder is being used.
|
| + Element get targetElement;
|
| + TypeBuilder get typeBuilder;
|
| +}
|
| +
|
| +class ReifiedTypeRepresentationBuilder
|
| + implements DartTypeVisitor<dynamic, GraphBuilder> {
|
| + final ClosedWorld closedWorld;
|
| +
|
| + ReifiedTypeRepresentationBuilder(this.closedWorld);
|
| +
|
| + void visit(DartType type, GraphBuilder builder) => type.accept(this, builder);
|
| +
|
| + void visitVoidType(VoidType type, GraphBuilder builder) {
|
| + ClassElement cls = builder.backend.helpers.VoidRuntimeType;
|
| + builder.push(new HVoidType(type, new TypeMask.exact(cls, closedWorld)));
|
| + }
|
| +
|
| + void visitTypeVariableType(TypeVariableType type, GraphBuilder builder) {
|
| + ClassElement cls = builder.backend.helpers.RuntimeType;
|
| + TypeMask instructionType = new TypeMask.subclass(cls, closedWorld);
|
| + if (!builder.sourceElement.enclosingElement.isClosure &&
|
| + builder.sourceElement.isInstanceMember) {
|
| + HInstruction receiver = builder.localsHandler.readThis();
|
| + builder.push(new HReadTypeVariable(type, receiver, instructionType));
|
| + } else {
|
| + builder.push(new HReadTypeVariable.noReceiver(
|
| + type,
|
| + builder.typeBuilder
|
| + .addTypeVariableReference(type, builder.sourceElement),
|
| + instructionType));
|
| + }
|
| + }
|
| +
|
| + void visitFunctionType(FunctionType type, GraphBuilder builder) {
|
| + type.returnType.accept(this, builder);
|
| + HInstruction returnType = builder.pop();
|
| + List<HInstruction> inputs = <HInstruction>[returnType];
|
| +
|
| + for (DartType parameter in type.parameterTypes) {
|
| + parameter.accept(this, builder);
|
| + inputs.add(builder.pop());
|
| + }
|
| +
|
| + for (DartType parameter in type.optionalParameterTypes) {
|
| + parameter.accept(this, builder);
|
| + inputs.add(builder.pop());
|
| + }
|
| +
|
| + List<DartType> namedParameterTypes = type.namedParameterTypes;
|
| + List<String> names = type.namedParameters;
|
| + for (int index = 0; index < names.length; index++) {
|
| + ast.DartString dartString = new ast.DartString.literal(names[index]);
|
| + inputs.add(builder.graph.addConstantString(dartString, builder.compiler));
|
| + namedParameterTypes[index].accept(this, builder);
|
| + inputs.add(builder.pop());
|
| + }
|
| +
|
| + ClassElement cls = builder.backend.helpers.RuntimeFunctionType;
|
| + builder.push(
|
| + new HFunctionType(inputs, type, new TypeMask.exact(cls, closedWorld)));
|
| + }
|
| +
|
| + void visitMalformedType(MalformedType type, GraphBuilder builder) {
|
| + visitDynamicType(const DynamicType(), builder);
|
| + }
|
| +
|
| + void visitStatementType(StatementType type, GraphBuilder builder) {
|
| + throw 'not implemented visitStatementType($type)';
|
| + }
|
| +
|
| + void visitInterfaceType(InterfaceType type, GraphBuilder builder) {
|
| + List<HInstruction> inputs = <HInstruction>[];
|
| + for (DartType typeArgument in type.typeArguments) {
|
| + typeArgument.accept(this, builder);
|
| + inputs.add(builder.pop());
|
| + }
|
| + ClassElement cls;
|
| + if (type.typeArguments.isEmpty) {
|
| + cls = builder.backend.helpers.RuntimeTypePlain;
|
| + } else {
|
| + cls = builder.backend.helpers.RuntimeTypeGeneric;
|
| + }
|
| + builder.push(
|
| + new HInterfaceType(inputs, type, new TypeMask.exact(cls, closedWorld)));
|
| + }
|
| +
|
| + void visitTypedefType(TypedefType type, GraphBuilder builder) {
|
| + DartType unaliased = type.unaliased;
|
| + if (unaliased is TypedefType) throw 'unable to unalias $type';
|
| + unaliased.accept(this, builder);
|
| + }
|
| +
|
| + void visitDynamicType(DynamicType type, GraphBuilder builder) {
|
| + JavaScriptBackend backend = builder.compiler.backend;
|
| + ClassElement cls = backend.helpers.DynamicRuntimeType;
|
| + builder.push(new HDynamicType(type, new TypeMask.exact(cls, closedWorld)));
|
| + }
|
| }
|
|
|