Share non-generic signatures through init.types

Change-Id: Ie132bbe805780022c91e5578c8dc4636c3c4cc8b
Reviewed-on: https://dart-review.googlesource.com/56671
Commit-Queue: Johnni Winther <johnniwinther@google.com>
Reviewed-by: Stephen Adams <sra@google.com>
diff --git a/pkg/compiler/lib/src/common_elements.dart b/pkg/compiler/lib/src/common_elements.dart
index 1c4eac2..884aadb 100644
--- a/pkg/compiler/lib/src/common_elements.dart
+++ b/pkg/compiler/lib/src/common_elements.dart
@@ -1118,6 +1118,9 @@
   FunctionEntity get instantiatedGenericFunctionType =>
       _findHelperFunction('instantiatedGenericFunctionType');
 
+  FunctionEntity get extractFunctionTypeObjectFromInternal =>
+      _findHelperFunction('extractFunctionTypeObjectFromInternal');
+
   // From dart:_internal
 
   ClassEntity _symbolImplementationClass;
diff --git a/pkg/compiler/lib/src/js_backend/backend_impact.dart b/pkg/compiler/lib/src/js_backend/backend_impact.dart
index 71bec0c..90bc21f 100644
--- a/pkg/compiler/lib/src/js_backend/backend_impact.dart
+++ b/pkg/compiler/lib/src/js_backend/backend_impact.dart
@@ -774,6 +774,7 @@
         _commonElements.instantiate2,
         _commonElements.instantiate3,
         _commonElements.instantiatedGenericFunctionType,
+        _commonElements.extractFunctionTypeObjectFromInternal,
       ], instantiatedClasses: [
         _commonElements.instantiation1Class,
         _commonElements.instantiation2Class,
diff --git a/pkg/compiler/lib/src/js_backend/codegen_listener.dart b/pkg/compiler/lib/src/js_backend/codegen_listener.dart
index 461bd279..bb430e2 100644
--- a/pkg/compiler/lib/src/js_backend/codegen_listener.dart
+++ b/pkg/compiler/lib/src/js_backend/codegen_listener.dart
@@ -155,6 +155,7 @@
         _customElementsAnalysis.registerTypeConstant(representedType.element);
       }
     } else if (constant is InstantiationConstantValue) {
+      // TODO(johnniwinther): Register these using `BackendImpact`.
       impactBuilder.registerTypeUse(new TypeUse.instantiation(
           _elementEnvironment
               .getThisType(_commonElements.instantiation1Class)));
@@ -167,6 +168,9 @@
       impactBuilder.registerStaticUse(new StaticUse.staticInvoke(
           _commonElements.instantiatedGenericFunctionType,
           CallStructure.TWO_ARGS));
+      impactBuilder.registerStaticUse(new StaticUse.staticInvoke(
+          _commonElements.extractFunctionTypeObjectFromInternal,
+          CallStructure.ONE_ARG));
     }
   }
 
diff --git a/pkg/compiler/lib/src/js_backend/runtime_types.dart b/pkg/compiler/lib/src/js_backend/runtime_types.dart
index 2364c42..1281eb9 100644
--- a/pkg/compiler/lib/src/js_backend/runtime_types.dart
+++ b/pkg/compiler/lib/src/js_backend/runtime_types.dart
@@ -1571,6 +1571,26 @@
       typeVariableTestsForTesting = typeVariableTests;
     }
 
+    /*print(typeVariableTests.dump());
+    print('------------------------------------------------------------------');
+    print('classesNeedingTypeArguments:');
+    classesNeedingTypeArguments.forEach((e) => print('  $e'));
+    print('------------------------------------------------------------------');
+    print('methodsNeedingSignature:');
+    methodsNeedingSignature.forEach((e) => print('  $e'));
+    print('------------------------------------------------------------------');
+    print('methodsNeedingTypeArguments:');
+    methodsNeedingTypeArguments.forEach((e) => print('  $e'));
+    print('------------------------------------------------------------------');
+    print('localFunctionsNeedingSignature:');
+    localFunctionsNeedingSignature.forEach((e) => print('  $e'));
+    print('------------------------------------------------------------------');
+    print('localFunctionsNeedingTypeArguments:');
+    localFunctionsNeedingTypeArguments.forEach((e) => print('  $e'));
+    print('------------------------------------------------------------------');
+    print('selectorsNeedingTypeArguments:');
+    selectorsNeedingTypeArguments.forEach((e) => print('  $e'));*/
+
     return _createRuntimeTypesNeed(
         _elementEnvironment,
         closedWorld.backendUsage,
diff --git a/pkg/compiler/lib/src/js_emitter/instantiation_stub_generator.dart b/pkg/compiler/lib/src/js_emitter/instantiation_stub_generator.dart
index 865fc15..477ced0 100644
--- a/pkg/compiler/lib/src/js_emitter/instantiation_stub_generator.dart
+++ b/pkg/compiler/lib/src/js_emitter/instantiation_stub_generator.dart
@@ -104,18 +104,19 @@
   /// ```
   /// $signature:: function() {
   ///   return H.instantiatedGenericFunctionType(
-  ///       this._genericClosure.$signature(),
+  ///       H.extractFunctionTypeObjectFromInternal(this._genericClosure),
   ///       this.$ti);
   /// }
   /// ```
   ParameterStubMethod _generateSignatureStub(FieldEntity functionField) {
     jsAst.Name operatorSignature = _namer.asName(_namer.operatorSignature);
 
-    jsAst.Fun function = js('function() { return #(this.#.#(), this.#); }', [
+    jsAst.Fun function = js('function() { return #(#(this.#), this.#); }', [
       _emitter.staticFunctionAccess(
           _commonElements.instantiatedGenericFunctionType),
+      _emitter.staticFunctionAccess(
+          _commonElements.extractFunctionTypeObjectFromInternal),
       _namer.fieldPropertyName(functionField),
-      operatorSignature,
       _namer.rtiFieldJsName,
     ]);
     // TODO(sra): Generate source information for stub that has no member.
diff --git a/pkg/compiler/lib/src/js_emitter/runtime_type_generator.dart b/pkg/compiler/lib/src/js_emitter/runtime_type_generator.dart
index 3615c8c..e76a39d 100644
--- a/pkg/compiler/lib/src/js_emitter/runtime_type_generator.dart
+++ b/pkg/compiler/lib/src/js_emitter/runtime_type_generator.dart
@@ -101,6 +101,7 @@
   final RuntimeTypesEncoder _rtiEncoder;
   final JsInteropAnalysis _jsInteropAnalysis;
   final bool _strongMode;
+  final _TypeContainedInOutputUnitVisitor _outputUnitVisitor;
 
   RuntimeTypeGenerator(
       this._commonElements,
@@ -111,7 +112,9 @@
       this._rtiChecks,
       this._rtiEncoder,
       this._jsInteropAnalysis,
-      this._strongMode);
+      this._strongMode)
+      : _outputUnitVisitor = new _TypeContainedInOutputUnitVisitor(
+            _commonElements, _outputUnitData);
 
   /**
    * Generate "is tests" for [cls] itself, and the "is tests" for the
@@ -145,19 +148,28 @@
       // signatures. We either need them for mirrors or because [type] is
       // potentially a subtype of a checked function. Currently we eagerly
       // generate a function type index or signature for all callable classes.
-      if (storeFunctionTypeInMetadata && !type.containsTypeVariables) {
-        // TODO(johnniwinther,efortuna): Should we use the scheme for Dart 2?
-        // TODO(sigmund): use output unit of `method` (Issue #31032)
-        OutputUnit outputUnit = _outputUnitData.mainOutputUnit;
-        result.functionTypeIndex =
-            emitterTask.metadataCollector.reifyType(type, outputUnit);
+      jsAst.Expression functionTypeIndex;
+      if (!type.containsTypeVariables) {
+        // TODO(sigmund): use output unit of [method] when the classes mentioned
+        // in [type] aren't in the main output unit. (Issue #31032)
+        OutputUnit mainOutputUnit = _outputUnitData.mainOutputUnit;
+        if (_outputUnitVisitor.isTypeContainedIn(type, mainOutputUnit)) {
+          functionTypeIndex =
+              emitterTask.metadataCollector.reifyType(type, mainOutputUnit);
+        }
+      }
+      if (storeFunctionTypeInMetadata && functionTypeIndex != null) {
+        result.functionTypeIndex = functionTypeIndex;
       } else {
         jsAst.Expression encoding =
             generatedCode[classFunctionType.signatureFunction];
-        if (classFunctionType.signatureFunction != null) {
-          // Use precomputed signature function if live.
-        } else {
-          assert(!_strongMode);
+        if (_strongMode) {
+          if (classFunctionType.signatureFunction == null) {
+            // The signature function isn't live.
+            return;
+          }
+          encoding = functionTypeIndex ?? encoding;
+        } else if (encoding == null) {
           // Generate the signature on the fly. This is only supported for
           // Dart 1.
 
@@ -240,3 +252,84 @@
     }
   }
 }
+
+/// Visitor that checks whether a type is contained within one output unit.
+class _TypeContainedInOutputUnitVisitor
+    implements DartTypeVisitor<bool, OutputUnit> {
+  final CommonElements _commonElements;
+  final OutputUnitData _outputUnitData;
+
+  _TypeContainedInOutputUnitVisitor(this._commonElements, this._outputUnitData);
+
+  /// Returns `true` if all classes mentioned in [type] are in [outputUnit].
+  bool isTypeContainedIn(DartType type, OutputUnit outputUnit) =>
+      visit(type, outputUnit);
+
+  @override
+  bool visit(DartType type, OutputUnit argument) => type.accept(this, argument);
+
+  bool visitList(List<DartType> types, OutputUnit argument) {
+    for (DartType type in types) {
+      if (!visit(type, argument)) {
+        return false;
+      }
+    }
+    return true;
+  }
+
+  @override
+  bool visitFutureOrType(FutureOrType type, OutputUnit argument) {
+    if (_outputUnitData.outputUnitForClass(_commonElements.functionClass) !=
+        argument) {
+      return false;
+    }
+    return visit(type.typeArgument, argument);
+  }
+
+  @override
+  bool visitDynamicType(DynamicType type, OutputUnit argument) => true;
+
+  @override
+  bool visitTypedefType(TypedefType type, OutputUnit argument) {
+    return visit(type.unaliased, argument);
+  }
+
+  @override
+  bool visitInterfaceType(InterfaceType type, OutputUnit argument) {
+    if (_outputUnitData.outputUnitForClass(type.element) != argument) {
+      return false;
+    }
+    return visitList(type.typeArguments, argument);
+  }
+
+  @override
+  bool visitFunctionType(FunctionType type, OutputUnit argument) {
+    bool result = visit(type.returnType, argument) &&
+        visitList(type.parameterTypes, argument) &&
+        visitList(type.optionalParameterTypes, argument) &&
+        visitList(type.namedParameterTypes, argument);
+    if (!result) return false;
+    for (FunctionTypeVariable typeVariable in type.typeVariables) {
+      if (!visit(typeVariable.bound, argument)) {
+        return false;
+      }
+    }
+    return true;
+  }
+
+  @override
+  bool visitFunctionTypeVariable(
+      FunctionTypeVariable type, OutputUnit argument) {
+    return true;
+  }
+
+  @override
+  bool visitTypeVariableType(TypeVariableType type, OutputUnit argument) {
+    return false;
+  }
+
+  @override
+  bool visitVoidType(VoidType type, OutputUnit argument) {
+    return true;
+  }
+}
diff --git a/sdk/lib/_internal/js_runtime/lib/js_helper.dart b/sdk/lib/_internal/js_runtime/lib/js_helper.dart
index af67c0e..4896e9d 100644
--- a/sdk/lib/_internal/js_runtime/lib/js_helper.dart
+++ b/sdk/lib/_internal/js_runtime/lib/js_helper.dart
@@ -3447,10 +3447,20 @@
 
 extractFunctionTypeObjectFrom(o) {
   var interceptor = getInterceptor(o);
+  return extractFunctionTypeObjectFromInternal(interceptor);
+}
+
+extractFunctionTypeObjectFromInternal(o) {
   var signatureName = JS_GET_NAME(JsGetName.SIGNATURE_NAME);
-  return JS('bool', '# in #', signatureName, interceptor)
-      ? JS('', '#[#]()', interceptor, signatureName)
-      : null;
+  if (JS('bool', '# in #', signatureName, o)) {
+    var signature = JS('', '#[#]', o, signatureName);
+    if (JS('bool', 'typeof # == "number"', signature)) {
+      return getType(signature);
+    } else {
+      return JS('', '#[#]()', o, signatureName);
+    }
+  }
+  return null;
 }
 
 functionTypeTest(value, functionTypeRti) {
diff --git a/sdk/lib/_internal/js_runtime/lib/js_rti.dart b/sdk/lib/_internal/js_runtime/lib/js_rti.dart
index d6be639..09f2df3 100644
--- a/sdk/lib/_internal/js_runtime/lib/js_rti.dart
+++ b/sdk/lib/_internal/js_runtime/lib/js_rti.dart
@@ -859,10 +859,8 @@
   if (isDartFunctionType(t)) {
     // Functions are treated specially and have their type information stored
     // directly in the instance.
-    var targetSignatureFunction =
-        getField(o, '${JS_GET_NAME(JsGetName.SIGNATURE_NAME)}');
-    if (targetSignatureFunction == null) return false;
-    type = invokeOn(targetSignatureFunction, o, null);
+    type = extractFunctionTypeObjectFromInternal(o);
+    if (type == null) return false;
     return isFunctionSubtype(type, t);
   }
   return isSubtype(type, t);
diff --git a/tests/compiler/dart2js_extra/deferred_function_types1_test.dart b/tests/compiler/dart2js_extra/deferred_function_types1_test.dart
new file mode 100644
index 0000000..91c9075
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types1_test.dart
@@ -0,0 +1,18 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.method1() is int Function(int));
+  Expect.isFalse(lib1.method1() is String Function(String));
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method2() is int Function(int));
+  Expect.isTrue(lib2.method2() is String Function(String));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types2_test.dart b/tests/compiler/dart2js_extra/deferred_function_types2_test.dart
new file mode 100644
index 0000000..4336421
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types2_test.dart
@@ -0,0 +1,18 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method2() is int Function(int));
+  Expect.isTrue(lib2.method2() is String Function(String));
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.method1() is int Function(int));
+  Expect.isFalse(lib1.method1() is String Function(String));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types3_test.dart b/tests/compiler/dart2js_extra/deferred_function_types3_test.dart
new file mode 100644
index 0000000..98a6de8
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types3_test.dart
@@ -0,0 +1,18 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.method3() is Object Function(Null));
+  Expect.isFalse(lib1.method3() is Object Function(Null, Null));
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method4() is Object Function(Null));
+  Expect.isTrue(lib2.method4() is Object Function(Null, Null));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types4_test.dart b/tests/compiler/dart2js_extra/deferred_function_types4_test.dart
new file mode 100644
index 0000000..fc78d96
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types4_test.dart
@@ -0,0 +1,18 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method4() is Object Function(Null));
+  Expect.isTrue(lib2.method4() is Object Function(Null, Null));
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.method3() is Object Function(Null));
+  Expect.isFalse(lib1.method3() is Object Function(Null, Null));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types5_test.dart b/tests/compiler/dart2js_extra/deferred_function_types5_test.dart
new file mode 100644
index 0000000..998d678
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types5_test.dart
@@ -0,0 +1,18 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.test3(lib1.method3()));
+  Expect.isFalse(lib1.method3() is Object Function(String));
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method4() is Object Function(String, String));
+  Expect.isTrue(lib2.test4(lib2.method4()));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types6_test.dart b/tests/compiler/dart2js_extra/deferred_function_types6_test.dart
new file mode 100644
index 0000000..2423b52
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types6_test.dart
@@ -0,0 +1,18 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method4() is Object Function(String, String));
+  Expect.isTrue(lib2.test4(lib2.method4()));
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.test3(lib1.method3()));
+  Expect.isFalse(lib1.method3() is Object Function(String));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types7_test.dart b/tests/compiler/dart2js_extra/deferred_function_types7_test.dart
new file mode 100644
index 0000000..c3e8de0
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types7_test.dart
@@ -0,0 +1,22 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.method1() is int Function(int));
+  Expect.isFalse(lib1.method1() is String Function(String));
+  Expect.isTrue(lib1.method5 is Object Function(Null, String, int));
+  Expect.isFalse(lib1.method5 is Object Function(Null, int, String));
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method2() is int Function(int));
+  Expect.isTrue(lib2.method2() is String Function(String));
+  Expect.isFalse(lib2.method6 is Object Function(Null, String, int));
+  Expect.isTrue(lib2.method6 is Object Function(Null, int, String));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types8_test.dart b/tests/compiler/dart2js_extra/deferred_function_types8_test.dart
new file mode 100644
index 0000000..eaa89ca
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types8_test.dart
@@ -0,0 +1,22 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+import 'deferred_function_types_lib1.dart' deferred as lib1;
+import 'deferred_function_types_lib2.dart' deferred as lib2;
+
+main() async {
+  await lib2.loadLibrary();
+  Expect.isFalse(lib2.method2() is int Function(int));
+  Expect.isTrue(lib2.method2() is String Function(String));
+  Expect.isFalse(lib2.method6 is Object Function(Null, String, int));
+  Expect.isTrue(lib2.method6 is Object Function(Null, int, String));
+  await lib1.loadLibrary();
+  Expect.isTrue(lib1.method1() is int Function(int));
+  Expect.isFalse(lib1.method1() is String Function(String));
+  Expect.isTrue(lib1.method5 is Object Function(Null, String, int));
+  Expect.isFalse(lib1.method5 is Object Function(Null, int, String));
+}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types_lib1.dart b/tests/compiler/dart2js_extra/deferred_function_types_lib1.dart
new file mode 100644
index 0000000..4bacb61
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types_lib1.dart
@@ -0,0 +1,17 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+method1() {
+  return (int i) => i;
+}
+
+class Class1 {}
+
+method3() {
+  return (Class1 c) => c;
+}
+
+test3(o) => o is Class1 Function(Class1);
+
+method5(Class1 c, String s, int i) {}
diff --git a/tests/compiler/dart2js_extra/deferred_function_types_lib2.dart b/tests/compiler/dart2js_extra/deferred_function_types_lib2.dart
new file mode 100644
index 0000000..a8abb54
--- /dev/null
+++ b/tests/compiler/dart2js_extra/deferred_function_types_lib2.dart
@@ -0,0 +1,17 @@
+// Copyright (c) 2018, the Dart project authors.  Please see the AUTHORS file
+// 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.
+
+method2() {
+  return (String s) => s;
+}
+
+class Class2 {}
+
+method4() {
+  return (Class2 c1, Class2 c2) => c1;
+}
+
+test4(o) => o is Class2 Function(Class2, Class2);
+
+method6(Class2 c, int i, String s) {}
diff --git a/tests/corelib_2/corelib_2.status b/tests/corelib_2/corelib_2.status
index 740c6c6..71ce2bf 100644
--- a/tests/corelib_2/corelib_2.status
+++ b/tests/corelib_2/corelib_2.status
@@ -196,10 +196,6 @@
 map_test: Crash # tests/corelib_2/map_test.dart:903:7: Internal problem: Unhandled Null in installDefaultConstructor.
 symbol_reserved_word_test/03: RuntimeError # Issue 19972, new Symbol('void') should be allowed.
 
-[ $compiler == dart2js && $fast_startup ]
-apply3_test: RuntimeError
-dynamic_nosuchmethod_test: RuntimeError
-
 [ $compiler == dart2js && $fast_startup && $fasta && $strong ]
 cast_test: RuntimeError
 error_stack_trace1_test: RuntimeError
diff --git a/tests/language_2/language_2_dart2js.status b/tests/language_2/language_2_dart2js.status
index 953e7a2..830d006 100644
--- a/tests/language_2/language_2_dart2js.status
+++ b/tests/language_2/language_2_dart2js.status
@@ -486,7 +486,6 @@
 stacktrace_rethrow_error_test/withtraceparameter: RuntimeError # Issue 12698
 stacktrace_rethrow_nonerror_test: RuntimeError # Issue 12698
 stacktrace_test: RuntimeError # Issue 12698
-super_call4_test: Crash # NoSuchMethodError: The getter 'thisLocal' was called on null.
 switch_bad_case_test/01: MissingCompileTimeError
 switch_bad_case_test/02: MissingCompileTimeError
 switch_case_test/00: MissingCompileTimeError
@@ -808,7 +807,6 @@
 string_split_test: CompileTimeError
 string_supertype_checked_test: CompileTimeError
 super_bound_closure_test/none: CompileTimeError
-super_call4_test: Crash # NoSuchMethodError: The getter 'thisLocal' was called on null.
 super_no_such_method1_test: CompileTimeError
 super_no_such_method2_test: CompileTimeError
 super_no_such_method3_test: CompileTimeError