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

Unified Diff: dart/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart

Issue 50313007: Implement dynamic function checks. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge
Patch Set: Merged with r30897. Created 7 years 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 side-by-side diff with in-line comments
Download patch
Index: dart/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart
diff --git a/dart/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart b/dart/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart
index 50aabfc6d416aa4067ced372769abc678dc9303c..9772a235f5951a603a647411c194f6718883a654 100644
--- a/dart/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart
+++ b/dart/sdk/lib/_internal/compiler/implementation/ssa/codegen.dart
@@ -2524,7 +2524,6 @@ class SsaCodeGenerator implements HVisitor, HBlockInformationVisitor {
world.registerIsCheck(type, work.resolutionTree);
CheckedModeHelper helper;
- FunctionElement helperElement;
if (node.isBooleanConversionCheck) {
helper =
const CheckedModeHelper('boolConversionCheck');
@@ -2533,13 +2532,121 @@ class SsaCodeGenerator implements HVisitor, HBlockInformationVisitor {
backend.getCheckedModeHelper(type, typeCast: node.isCastTypeCheck);
}
- push(helper.generateCall(this, node));
+ if (helper == null) {
+ assert(type.kind == TypeKind.FUNCTION);
+ use(node.inputs[0]);
+ } else {
+ push(helper.generateCall(this, node));
+ }
}
void visitTypeKnown(HTypeKnown node) {
// [HTypeKnown] instructions are removed before generating code.
assert(false);
}
+
+ void visitFunctionType(HFunctionType node) {
+ FunctionType type = node.dartType;
+ int inputCount = 0;
+ use(node.inputs[inputCount++]);
+ js.Expression returnType = pop();
+
+ List<js.Expression> parameterTypes = <js.Expression>[];
+ for (var _ in type.parameterTypes) {
+ use(node.inputs[inputCount++]);
+ parameterTypes.add(pop());
+ }
+
+ List<js.Expression> optionalParameterTypes = <js.Expression>[];
+ for (var _ in type.optionalParameterTypes) {
+ use(node.inputs[inputCount++]);
+ optionalParameterTypes.add(pop());
+ }
+
+ List<js.Property> namedParameters = <js.Property>[];
+ for (var _ in type.namedParameters) {
+ use(node.inputs[inputCount++]);
+ js.Expression name = pop();
+ use(node.inputs[inputCount++]);
+ namedParameters.add(new js.Property(name, pop()));
+ }
+
+ if (namedParameters.isEmpty) {
+ var arguments = [returnType];
+ if (!parameterTypes.isEmpty || !optionalParameterTypes.isEmpty) {
+ arguments.add(new js.ArrayInitializer.from(parameterTypes));
+ }
+ if (!optionalParameterTypes.isEmpty) {
+ arguments.add(new js.ArrayInitializer.from(optionalParameterTypes));
+ }
+ push(accessHelper('buildFunctionType')(arguments));
+ } else {
+ var arguments = [
+ returnType,
+ new js.ArrayInitializer.from(parameterTypes),
+ new js.ObjectInitializer(namedParameters)];
+ push(accessHelper('buildNamedFunctionType')(arguments));
+ }
+ }
+
+ void visitReadTypeVariable(HReadTypeVariable node) {
+ TypeVariableElement element = node.dartType.element;
+ Element helperElement = compiler.findHelper('convertRtiToRuntimeType');
+ world.registerStaticUse(helperElement);
+
+ use(node.inputs[0]);
+ if (node.hasReceiver) {
+ if (backend.isInterceptorClass(element.getEnclosingClass())) {
+ int index = RuntimeTypes.getTypeVariableIndex(element);
+ js.Expression receiver = pop();
+ js.Expression helper = backend.namer.elementAccess(helperElement);
+ push(helper(js.js(r'#.$builtinTypeInfo && #.$builtinTypeInfo[#]',
+ [receiver, receiver, js.js.toExpression(index)])));
+ } else {
+ backend.emitter.registerReadTypeVariable(element);
+ push(
+ js.js('#.${backend.namer.readTypeVariableName(element)}()', pop()));
+ }
+ } else {
+ push(
+ backend.namer.elementAccess(
+ compiler.findHelper('convertRtiToRuntimeType'))(pop()));
+ }
+ }
+
+ void visitInterfaceType(HInterfaceType node) {
+ List<js.Expression> typeArguments = <js.Expression>[];
+ for (HInstruction type in node.inputs) {
+ use(type);
+ typeArguments.add(pop());
+ }
+
+ ClassElement cls = node.dartType.element;
+ var arguments = [
+ backend.namer.elementAccess(backend.getImplementationClass(cls))];
+ if (!typeArguments.isEmpty) {
+ arguments.add(new js.ArrayInitializer.from(typeArguments));
+ }
+ push(accessHelper('buildInterfaceType')(arguments));
+ }
+
+ void visitVoidType(HVoidType node) {
+ push(accessHelper('getVoidRuntimeType')());
+ }
+
+ void visitDynamicType(HDynamicType node) {
+ push(accessHelper('getDynamicRuntimeType')());
+ }
+
+ js.PropertyAccess accessHelper(String name) {
+ Element helper = compiler.findHelper(name);
+ if (helper == null) {
+ // For mocked-up tests.
+ return js.js('(void 0).$name');
+ }
+ world.registerStaticUse(helper);
+ return backend.namer.elementAccess(helper);
+ }
}
String singleIdentityComparison(HInstruction left,

Powered by Google App Engine
This is Rietveld 408576698