Version 2.0.0-dev.62.0

Merge commit 'baef792361626c0c7ba10046784f0b6715e618e1' into dev
diff --git a/.gitconfig b/.gitconfig
index 7df539b..5a8aa94 100644
--- a/.gitconfig
+++ b/.gitconfig
@@ -1,2 +1,4 @@
+# Add this to your Git config to set the section header as function context for status files.
+# git config --add --local include.path ../.gitconfig
 [diff "status"]
 	xfuncname = "^\\[.*\\]$"
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 79549fe..d84689d 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,57 @@
+## 2.0.0-dev.62.0
+
+### Language
+
+Inference chooses `void` when combining `Object` or `dynamic` and `void` ([issue
+3341]).  When combining with other top types, inference now prefers `void`.  So
+for example, given:
+
+```dart
+void foo() {};
+dynamic bar() {};
+var a = [foo(), bar()];
+```
+
+the variable `a` would previously have been inferred as `dynamic`, and will now
+be inferred as `void`.
+
+[issue 3341]: https://github.com/dart-lang/sdk/issues/33341
+
+
+#### Strong Mode
+
+### Dart VM
+
+* The dart VM will no longer attempt to perform `packages/` directory
+  resolution (for loading scripts, and in `Isolate.resolveUri`). Users
+  relying on `packages/` directories should switch to `.packages` files.
+
+### Tool Changes
+
+#### Pub
+
+* Fix an error on `pub get` when running with Dart 2 mode and already existing
+  snapshots of executables.
+
+#### Other Tools
+
+### Core library changes
+
+* `dart:core`/`dart:collection`
+  * Remove the `retype` method on iterables and maps again. Use `cast` instead.
+  * Deprecated `Platform.packageRoot`, which is only used for `packages/`
+    directory resolution which is no longer supported. It will now always
+    return null, which is a value that was always possible for it to return
+    previously.
+* `dart:isolate`
+  * Deprecated `Isolate.packageRoot`, which is only used for `packages/`
+    directory resolution which is no longer supported. It will now always
+    return null, which is a value that was always possible for it to return
+    previously.
+  * Deprecated `packageRoot` parameter in `Isolate.spawnUri`, which is was
+    previously used only for `packages/` directory resolution. That style
+    of resolution is no longer supported in dart 2.
+
 ## 2.0.0-dev.61.0
 
 ### Dart VM
diff --git a/DEPS b/DEPS
index 544ccdc..a7da2e0 100644
--- a/DEPS
+++ b/DEPS
@@ -59,7 +59,7 @@
   "charcode_tag": "v1.1.1",
   "chrome_rev" : "19997",
   "cli_util_tag" : "0.1.2+1",
-  "collection_tag": "1.14.9",
+  "collection_tag": "1.14.10",
   "convert_tag": "2.0.1",
   "crypto_tag" : "2.0.2+1",
   "csslib_tag" : "0.14.1",
@@ -110,7 +110,7 @@
   "ply_rev": "604b32590ffad5cbb82e4afef1d305512d06ae93",
   "pool_tag": "1.3.4",
   "protobuf_tag": "0.7.1",
-  "pub_rev": "d84173eeb03c328ed533469108ce81b11d736a80",
+  "pub_rev": "881a0c3fbe63af07dd043b3f5e6cbe74eacb377c",
   "pub_semver_tag": "1.4.1",
   "quiver_tag": "5aaa3f58c48608af5b027444d561270b53f15dbf",
   "resource_rev":"af5a5bf65511943398146cf146e466e5f0b95cb9",
diff --git a/WATCHLISTS b/WATCHLISTS
index fb38b83..418192d 100644
--- a/WATCHLISTS
+++ b/WATCHLISTS
@@ -27,6 +27,9 @@
     'kernel': {
       'filepath': '^pkg/kernel',
     },
+    'package_vm': {
+      'filepath': '^pkg/vm',
+    },
     'messages_review': {
       'filepath': (
         '^('
@@ -62,10 +65,12 @@
     'build': [ 'zra@google.com', 'keertip@google.com' ],
     'front_end': [ 'dart-fe-team+reviews@google.com' ],
     'http': [ 'zra@google.com' ],
-    'kernel': [ 'karlklose@google.com', 'jensj@google.com', 'kmillikin@google.com' ],
+    'kernel': [ 'karlklose@google.com', 'jensj@google.com', 'kmillikin@google.com',
+                'alexmarkov@google.com' ],
     'messages_review': [ 'dart-uxr+reviews@google.com' ],
     'mirrors' : [ 'rmacnak@google.com' ],
     'observatory': [ 'rmacnak@google.com' ],
+    'package_vm': [ 'alexmarkov@google.com' ],
     'runtime': [ 'vm-dev@dartlang.org' ],
   },
 }
diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn
index e9129e3..3ad0c96 100644
--- a/build/config/BUILDCONFIG.gn
+++ b/build/config/BUILDCONFIG.gn
@@ -292,11 +292,16 @@
     "//build/config/mac:mac_dynamic_flags",
     "//build/config/mac:mac_executable_flags",
   ]
-} else if (is_linux || is_android) {
-  _executable_configs += [ "//build/config/gcc:executable_ldconfig" ]
-  if (is_android) {
-    _executable_configs += [ "//build/config/android:executable_config" ]
-  }
+} else if (is_linux) {
+  _executable_configs += [
+    "//build/config/gcc:executable_ldconfig",
+    "//build/config/linux:executable_config",
+  ]
+} else if (is_android) {
+  _executable_configs += [
+    "//build/config/gcc:executable_ldconfig",
+    "//build/config/android:executable_config",
+  ]
 }
 set_defaults("executable") {
   configs = _executable_configs
diff --git a/build/config/compiler/BUILD.gn b/build/config/compiler/BUILD.gn
index eeece1c..8154e4e 100644
--- a/build/config/compiler/BUILD.gn
+++ b/build/config/compiler/BUILD.gn
@@ -234,7 +234,7 @@
   # 3. When using the sanitizers.
   # Otherwise there is a performance hit, in particular on ia32.
   if (is_android || is_asan || is_lsan || is_msan || is_tsan ||
-      (is_linux && current_cpu == "arm")) {
+      (is_linux && current_cpu != "x86")) {
     cflags += [ "-fPIC" ]
     ldflags += [ "-fPIC" ]
   }
diff --git a/build/config/linux/BUILD.gn b/build/config/linux/BUILD.gn
index 051809a..215025b 100644
--- a/build/config/linux/BUILD.gn
+++ b/build/config/linux/BUILD.gn
@@ -28,3 +28,10 @@
     }
   }
 }
+
+config("executable_config") {
+  if (current_cpu != "x86") {
+    cflags = [ "-fPIE" ]
+    ldflags = [ "-pie" ]
+  }
+}
diff --git a/docs/language/dartLangSpec.tex b/docs/language/dartLangSpec.tex
index 17d6731..f06888f 100644
--- a/docs/language/dartLangSpec.tex
+++ b/docs/language/dartLangSpec.tex
@@ -55,6 +55,7 @@
 % - Specify variance and super-bounded types.
 % - Introduce `subterm` and `immediate subterm`.
 % - Introduce `top type`.
+% - Specify configurable imports.
 %
 % 1.15
 % - Change how language specification describes control flow.
@@ -8829,12 +8830,15 @@
 {\bf scriptTag:}`\#!' {\escapegrammar (\~{}NEWLINE)*} NEWLINE
   .
 
-{\bf libraryName:}metadata \LIBRARY{} identifier (`{\escapegrammar .}' identifier)* `{\escapegrammar ;}'
+{\bf libraryName:}metadata \LIBRARY{} dottedIdentifierList `{\escapegrammar ;}'
   .
 
 {\bf importOrExport:}libraryImport;
   libraryExport
   .
+
+{\bf dottedIdentifierList:} identifier (`{\escapegrammar .}' identifier)*
+  .
 \end{grammar}
 
 \LMHash{}
@@ -8891,7 +8895,7 @@
 {\bf libraryImport:}metadata importSpecification
   .
 
-{\bf importSpecification:}\IMPORT{} uri (\AS{} identifier)? combinator* `{\escapegrammar ;}';
+{\bf importSpecification:}\IMPORT{} configurableUri (\AS{} identifier)? combinator* `{\escapegrammar ;}';
   \IMPORT{} uri \DEFERRED{} \AS{} identifier combinator* `{\escapegrammar ;}'
   .
 
@@ -9156,7 +9160,7 @@
 The namespace that $L$ exports is known as its {\em exported namespace}.
 
 \begin{grammar}
-{\bf libraryExport:}metadata \EXPORT{} uri combinator* `{\escapegrammar ;}'
+{\bf libraryExport:}metadata \EXPORT{} configurableUri combinator* `{\escapegrammar ;}'
   .
 \end{grammar}
 
@@ -9318,12 +9322,50 @@
 \begin{grammar}
 {\bf uri:}stringLiteral
   .
+{\bf configurableUri:} uri configurationUri*
+  .
+{\bf configurationUri:} \IF{} `(' uriTest `)' uri
+  .
+{\bf uriTest:} dottedIdentifierList (`==' stringLiteral)?
+  .
 \end{grammar}
 
 \LMHash{}
 It is a compile-time error if the string literal $x$ that describes a URI is not a compile-time constant, or if $x$ involves string interpolation.
 
 \LMHash{}
+It is a compile-time error if the string literal $x$ that is used in a {\em uriTest} is not a compile-time constant, or if $x$ involves string interpolation.
+
+\LMHash{} A {\em configurable URI} $c$ of the form \code{\metavar{uri} $\metavar{configurationUri}_1$ \ldots $\metavar{configurationUri}_n$} {\em specifies a URI} as follows:
+\begin{itemize}
+\item{} Let $u$ be \metavar{uri}.
+\item{} For each of the following configuration URIs of the form \code{\IF{} ($\metavar{test}_i$) $\metavar{uri}_i$}, in source order, do the following.
+\begin{itemize}
+  \item{} If $\metavar{test}_i$ is \code{\metavar{ids}} with no \code{==} clause, it is
+  equivalent to \code{\metavar{ids} == "true"}.
+  \item{} If $\metavar{test}_i$ is \code{\metavar{ids} == \metavar{string}},
+  then create a string, \metavar{key}, from \metavar{ids}
+  by concatenating the identfiers and dots,
+  omitting any spaces between them that may occur in the source.
+  \item{} Look up \metavar{key} in the available compilation {\em environment}.
+  \commentary{
+  The compilation environment is provided by the platform.
+  It maps some string keys to string values,
+  and can be accessed programmatically using the
+  \code{const String.fromEnvironment} constructor.
+  Tools may choose to only make some parts of the compilation environment
+  available for choosing configuration URIs.
+  }
+  \item{} If the environment contains an entry for \metavar{key} and the
+  associated value is equal, as a constant string value, to the value of
+  the string literal \metavar{string},
+  then let $u$ be $\metavar{uri}_i$ and stop iterating the configuration URIs.
+  \item{} Otherwise proceed to the next configuration URI.
+\end{itemize}
+\item{} The URI specified by $c$ is $u$.
+\end{itemize}
+
+\LMHash{}
 This specification does not discuss the interpretation of URIs, with the following exceptions.
 
 \rationale{
diff --git a/pkg/analyzer/CHANGELOG.md b/pkg/analyzer/CHANGELOG.md
index 29228c2..e81260f 100644
--- a/pkg/analyzer/CHANGELOG.md
+++ b/pkg/analyzer/CHANGELOG.md
@@ -1,5 +1,7 @@
 ## 0.32.1
 
+* The Parser() class now by default will parse with optional new or const. This
+  affects many APIs, for instance, `analyzer.dart`'s `parseCompilationUnit()`.
 * Add the ability to specify a pathContext when creating a ContextRoot (not part
   of the officially supported API, but needed by some clients).
 * AnalysisSession now exports resourceProvider.
diff --git a/pkg/analyzer/lib/src/fasta/ast_builder.dart b/pkg/analyzer/lib/src/fasta/ast_builder.dart
index 2f76c16..ce8de6c 100644
--- a/pkg/analyzer/lib/src/fasta/ast_builder.dart
+++ b/pkg/analyzer/lib/src/fasta/ast_builder.dart
@@ -33,7 +33,6 @@
 import 'package:front_end/src/fasta/messages.dart'
     show
         Message,
-        codeExpectedFunctionBody,
         messageConstConstructorWithBody,
         messageConstMethod,
         messageConstructorWithReturnType,
@@ -510,9 +509,8 @@
     debugEvent("ExpressionFunctionBody");
 
     Expression expression = pop();
-    Token star = pop();
+    pop(); // star (*)
     Token asyncKeyword = pop();
-    assert(star == null);
     if (parseFunctionBodies) {
       push(ast.expressionFunctionBody(
           asyncKeyword, arrowToken, expression, semicolon));
@@ -1440,24 +1438,6 @@
     push(ast.blockFunctionBody(asyncKeyword, star, block));
   }
 
-  @override
-  Token handleUnrecoverableError(Token token, Message message) {
-    if (message.code == codeExpectedFunctionBody) {
-      if (identical('native', token.stringValue) && parser != null) {
-        Token nativeKeyword = token;
-        Token semicolon = parser.parseLiteralString(token).next;
-        // TODO(brianwilkerson) Should this be using ensureSemicolon?
-        token = parser.expectSemicolon(semicolon);
-        StringLiteral name = pop();
-        pop(); // star
-        pop(); // async
-        push(ast.nativeFunctionBody(nativeKeyword, name, semicolon));
-        return token;
-      }
-    }
-    return super.handleUnrecoverableError(token, message);
-  }
-
   void handleUnaryPrefixExpression(Token operator) {
     assert(operator.type.isUnaryPrefixOperator);
     debugEvent("UnaryPrefixExpression");
diff --git a/pkg/analyzer/lib/src/fasta/error_converter.dart b/pkg/analyzer/lib/src/fasta/error_converter.dart
index 8fd383e..acfe8432 100644
--- a/pkg/analyzer/lib/src/fasta/error_converter.dart
+++ b/pkg/analyzer/lib/src/fasta/error_converter.dart
@@ -509,7 +509,14 @@
         return;
       case "RETURN_IN_GENERATOR":
         errorReporter?.reportErrorForOffset(
-            CompileTimeErrorCode.RETURN_IN_GENERATOR, offset, length);
+            CompileTimeErrorCode.RETURN_IN_GENERATOR, offset, length,
+            // TODO(danrubel): Update the parser to report the modifier
+            // involved in this error... either async* or sync*
+            ['async*']);
+        return;
+      case "STACK_OVERFLOW":
+        errorReporter?.reportErrorForOffset(
+            ParserErrorCode.STACK_OVERFLOW, offset, length);
         return;
       case "STATIC_AFTER_CONST":
         errorReporter?.reportErrorForOffset(
diff --git a/pkg/analyzer/lib/src/generated/parser.dart b/pkg/analyzer/lib/src/generated/parser.dart
index 854fb69..1a5a68a 100644
--- a/pkg/analyzer/lib/src/generated/parser.dart
+++ b/pkg/analyzer/lib/src/generated/parser.dart
@@ -212,7 +212,7 @@
    * A flag indicating whether the parser should parse instance creation
    * expressions that lack either the `new` or `const` keyword.
    */
-  bool _enableOptionalNewAndConst = false;
+  bool _enableOptionalNewAndConst = true;
 
   /**
    * A flag indicating whether parser is to parse function bodies.
diff --git a/pkg/analyzer/lib/src/generated/type_system.dart b/pkg/analyzer/lib/src/generated/type_system.dart
index 5656daf..e54318a 100644
--- a/pkg/analyzer/lib/src/generated/type_system.dart
+++ b/pkg/analyzer/lib/src/generated/type_system.dart
@@ -35,9 +35,9 @@
   assert(_isTop(t), 'only Top types have a topiness');
 
   // Highest top
-  if (t.isDynamic) return 3;
-  if (t.isObject) return 2;
-  if (t.isVoid) return 1;
+  if (t.isVoid) return 3;
+  if (t.isDynamic) return 2;
+  if (t.isObject) return 1;
   if (t.isDartAsyncFutureOr)
     return -3 + _getTopiness((t as InterfaceType).typeArguments[0]);
   // Lowest top
diff --git a/pkg/analyzer/test/generated/parser_fasta_test.dart b/pkg/analyzer/test/generated/parser_fasta_test.dart
index d5e8886..fabf804 100644
--- a/pkg/analyzer/test/generated/parser_fasta_test.dart
+++ b/pkg/analyzer/test/generated/parser_fasta_test.dart
@@ -97,28 +97,17 @@
 class ErrorParserTest_Fasta extends FastaParserTestCase
     with ErrorParserTestMixin {
   @override
-  @failingTest
   void test_expectedListOrMapLiteral() {
-    // TODO(brianwilkerson) Does not recover.
-    //   type 'IntegerLiteralImpl' is not a subtype of type 'TypedLiteral' in type cast where
-    //   IntegerLiteralImpl is from package:analyzer/src/dart/ast/ast.dart
-    //   TypedLiteral is from package:analyzer/dart/ast/ast.dart
-    //
-    //   dart:core                                                          Object._as
-    //   test/generated/parser_fasta_test.dart 2480:48                      FastaParserTestCase.parseListOrMapLiteral
-    super.test_expectedListOrMapLiteral();
+    // The fasta parser returns an 'IntegerLiteralImpl' when parsing '1'.
+    // This test is not expected to ever pass.
+    //super.test_expectedListOrMapLiteral();
   }
 
   @override
-  @failingTest
   void test_expectedStringLiteral() {
-    // TODO(brianwilkerson) Does not recover.
-    //   type 'IntegerLiteralImpl' is not a subtype of type 'StringLiteral' of 'literal' where
-    //   IntegerLiteralImpl is from package:analyzer/src/dart/ast/ast.dart
-    //   StringLiteral is from package:analyzer/dart/ast/ast.dart
-    //
-    //   test/generated/parser_test.dart 2652:29                            FastaParserTestCase&ErrorParserTestMixin.test_expectedStringLiteral
-    super.test_expectedStringLiteral();
+    // The fasta parser returns an 'IntegerLiteralImpl' when parsing '1'.
+    // This test is not expected to ever pass.
+    //super.test_expectedStringLiteral();
   }
 
   void test_getterNativeWithBody() {
@@ -163,34 +152,6 @@
 
   @override
   @failingTest
-  void test_invalidCommentReference__new_nonIdentifier() {
-    // TODO(brianwilkerson) Parsing comment references not yet supported.
-    super.test_invalidCommentReference__new_nonIdentifier();
-  }
-
-  @override
-  @failingTest
-  void test_invalidCommentReference__new_tooMuch() {
-    // TODO(brianwilkerson) Parsing comment references not yet supported.
-    super.test_invalidCommentReference__new_tooMuch();
-  }
-
-  @override
-  @failingTest
-  void test_invalidCommentReference__nonNew_nonIdentifier() {
-    // TODO(brianwilkerson) Parsing comment references not yet supported.
-    super.test_invalidCommentReference__nonNew_nonIdentifier();
-  }
-
-  @override
-  @failingTest
-  void test_invalidCommentReference__nonNew_tooMuch() {
-    // TODO(brianwilkerson) Parsing comment references not yet supported.
-    super.test_invalidCommentReference__nonNew_tooMuch();
-  }
-
-  @override
-  @failingTest
   void test_invalidHexEscape_invalidDigit() {
     // TODO(brianwilkerson) Does not recover.
     //   Internal problem: Compiler cannot run without a compiler context.
@@ -241,44 +202,6 @@
 
   @override
   @failingTest
-  void test_invalidOperatorAfterSuper_primaryExpression() {
-    // TODO(brianwilkerson) Does not recover.
-    //   Expected: true
-    //   Actual: <false>
-    //
-    //   package:test                                                       expect
-    //   test/generated/parser_fasta_test.dart 3197:5                       ParserProxy._run
-    super.test_invalidOperatorAfterSuper_primaryExpression();
-  }
-
-  @override
-  @failingTest
-  void test_invalidStarAfterAsync() {
-    // TODO(brianwilkerson) Does not recover.
-    //   Expected: an object with length of <1>
-    //   Actual: <Instance of 'Stack'>
-    //   Which: has length of <0>
-    //
-    //   package:test                                                       expect
-    //   test/generated/parser_fasta_test.dart 3290:7                       ParserProxy._run
-    super.test_invalidStarAfterAsync();
-  }
-
-  @override
-  @failingTest
-  void test_invalidSync() {
-    // TODO(brianwilkerson) Does not recover.
-    //   Expected: an object with length of <1>
-    //   Actual: <Instance of 'Stack'>
-    //   Which: has length of <0>
-    //
-    //   package:test                                                       expect
-    //   test/generated/parser_fasta_test.dart 3290:7                       ParserProxy._run
-    super.test_invalidSync();
-  }
-
-  @override
-  @failingTest
   void test_invalidUnicodeEscape_incomplete_noDigits() {
     // TODO(brianwilkerson) Does not recover.
     //   Internal problem: Compiler cannot run without a compiler context.
diff --git a/pkg/analyzer/test/generated/parser_test.dart b/pkg/analyzer/test/generated/parser_test.dart
index f92a657..f9edf37 100644
--- a/pkg/analyzer/test/generated/parser_test.dart
+++ b/pkg/analyzer/test/generated/parser_test.dart
@@ -4132,10 +4132,10 @@
   }
 
   void test_invalidOperatorAfterSuper_primaryExpression() {
-    Expression expression = parsePrimaryExpression('super?.v');
+    Expression expression = parseExpression('super?.v', errors: [
+      expectedError(ParserErrorCode.INVALID_OPERATOR_FOR_SUPER, 5, 2)
+    ]);
     expectNotNullIfNoErrors(expression);
-    listener.assertErrors(
-        [expectedError(ParserErrorCode.INVALID_OPERATOR_FOR_SUPER, 5, 2)]);
   }
 
   void test_invalidOperatorForSuper() {
@@ -4150,18 +4150,21 @@
   }
 
   void test_invalidStarAfterAsync() {
-    createParser('async* => 0;');
-    FunctionBody functionBody = parser.parseFunctionBody(false, null, false);
-    expectNotNullIfNoErrors(functionBody);
-    listener.assertErrors(
-        [expectedError(ParserErrorCode.INVALID_STAR_AFTER_ASYNC, 5, 1)]);
+    createParser('foo() async* => 0;');
+    CompilationUnit unit = parser.parseCompilationUnit2();
+    expectNotNullIfNoErrors(unit);
+    listener.assertErrors(usingFastaParser
+        ? [expectedError(CompileTimeErrorCode.RETURN_IN_GENERATOR, 13, 2)]
+        : [expectedError(ParserErrorCode.INVALID_STAR_AFTER_ASYNC, 11, 1)]);
   }
 
   void test_invalidSync() {
-    createParser('sync* => 0;');
-    FunctionBody functionBody = parser.parseFunctionBody(false, null, false);
-    expectNotNullIfNoErrors(functionBody);
-    listener.assertErrors([expectedError(ParserErrorCode.INVALID_SYNC, 0, 4)]);
+    createParser('foo() sync* => 0;');
+    CompilationUnit unit = parser.parseCompilationUnit2();
+    expectNotNullIfNoErrors(unit);
+    listener.assertErrors(usingFastaParser
+        ? [expectedError(CompileTimeErrorCode.RETURN_IN_GENERATOR, 12, 2)]
+        : [expectedError(ParserErrorCode.INVALID_SYNC, 0, 4)]);
   }
 
   void test_invalidTopLevelSetter() {
diff --git a/pkg/analyzer/test/generated/type_system_test.dart b/pkg/analyzer/test/generated/type_system_test.dart
index a7ec816..f3e44dd 100644
--- a/pkg/analyzer/test/generated/type_system_test.dart
+++ b/pkg/analyzer/test/generated/type_system_test.dart
@@ -637,7 +637,7 @@
 
   void test_dynamic_void() {
     // Note: _checkLeastUpperBound tests `LUB(x, y)` as well as `LUB(y, x)`
-    _checkLeastUpperBound(dynamicType, voidType, dynamicType);
+    _checkLeastUpperBound(dynamicType, voidType, voidType);
   }
 
   void test_functionsDifferentRequiredArity() {
@@ -1553,15 +1553,15 @@
 
     final orderedTops = [
       // Lower index, so lower Top
+      voidType,
       dynamicType,
       objectType,
-      voidType,
+      futureOrVoidType,
       futureOrDynamicType,
       futureOrObjectType,
-      futureOrVoidType,
+      futureOrFutureOrVoidType,
       futureOrFutureOrDynamicType,
       futureOrFutureOrObjectType,
-      futureOrFutureOrVoidType,
       // Higher index, higher Top
     ];
 
@@ -1593,7 +1593,7 @@
     // Sanity check specific cases of top for GLB/LUB.
     _checkLeastUpperBound(objectType, dynamicType, dynamicType);
     _checkGreatestLowerBound(objectType, dynamicType, objectType);
-    _checkLeastUpperBound(objectType, voidType, objectType);
+    _checkLeastUpperBound(objectType, voidType, voidType);
     _checkLeastUpperBound(futureOrDynamicType, dynamicType, dynamicType);
     _checkGreatestLowerBound(
         futureOrDynamicType, objectType, futureOrDynamicType);
@@ -1644,7 +1644,7 @@
 
   void test_dynamic_void() {
     // Note: _checkGreatestLowerBound tests `GLB(x, y)` as well as `GLB(y, x)`
-    _checkGreatestLowerBound(dynamicType, voidType, voidType);
+    _checkGreatestLowerBound(dynamicType, voidType, dynamicType);
   }
 
   void test_functionsDifferentNamedTakeUnion() {
diff --git a/pkg/compiler/lib/src/common/codegen.dart b/pkg/compiler/lib/src/common/codegen.dart
index 208d40f..a0c99af 100644
--- a/pkg/compiler/lib/src/common/codegen.dart
+++ b/pkg/compiler/lib/src/common/codegen.dart
@@ -7,6 +7,7 @@
 import '../common_elements.dart';
 import '../elements/entities.dart';
 import '../elements/types.dart' show DartType, InterfaceType;
+import '../universe/feature.dart';
 import '../universe/use.dart' show ConstantUse, DynamicUse, StaticUse, TypeUse;
 import '../universe/world_impact.dart'
     show WorldImpact, WorldImpactBuilderImpl, WorldImpactVisitor;
@@ -29,7 +30,10 @@
 
   bool get usesInterceptor => false;
 
-  Iterable<AsyncMarker> get asyncMarkers => <AsyncMarker>[];
+  Iterable<AsyncMarker> get asyncMarkers => const <AsyncMarker>[];
+
+  Iterable<GenericInstantiation> get genericInstantiations =>
+      const <GenericInstantiation>[];
 }
 
 class _CodegenImpact extends WorldImpactBuilderImpl implements CodegenImpact {
@@ -38,6 +42,7 @@
   List<Set<ClassEntity>> _specializedGetInterceptors;
   bool _usesInterceptor = false;
   EnumSet<AsyncMarker> _asyncMarkers;
+  Set<GenericInstantiation> _genericInstantiations;
 
   _CodegenImpact();
 
@@ -49,9 +54,7 @@
 
   void registerTypeVariableBoundsSubtypeCheck(
       DartType subtype, DartType supertype) {
-    if (_typeVariableBoundsSubtypeChecks == null) {
-      _typeVariableBoundsSubtypeChecks = new Setlet<Pair<DartType, DartType>>();
-    }
+    _typeVariableBoundsSubtypeChecks ??= new Setlet<Pair<DartType, DartType>>();
     _typeVariableBoundsSubtypeChecks
         .add(new Pair<DartType, DartType>(subtype, supertype));
   }
@@ -63,9 +66,7 @@
   }
 
   void registerConstSymbol(String name) {
-    if (_constSymbols == null) {
-      _constSymbols = new Setlet<String>();
-    }
+    _constSymbols ??= new Setlet<String>();
     _constSymbols.add(name);
   }
 
@@ -74,9 +75,7 @@
   }
 
   void registerSpecializedGetInterceptor(Set<ClassEntity> classes) {
-    if (_specializedGetInterceptors == null) {
-      _specializedGetInterceptors = <Set<ClassEntity>>[];
-    }
+    _specializedGetInterceptors ??= <Set<ClassEntity>>[];
     _specializedGetInterceptors.add(classes);
   }
 
@@ -93,9 +92,7 @@
   bool get usesInterceptor => _usesInterceptor;
 
   void registerAsyncMarker(AsyncMarker asyncMarker) {
-    if (_asyncMarkers == null) {
-      _asyncMarkers = new EnumSet<AsyncMarker>();
-    }
+    _asyncMarkers ??= new EnumSet<AsyncMarker>();
     _asyncMarkers.add(asyncMarker);
   }
 
@@ -104,6 +101,16 @@
         ? _asyncMarkers.iterable(AsyncMarker.values)
         : const <AsyncMarker>[];
   }
+
+  void registerGenericInstantiation(GenericInstantiation instantiation) {
+    _genericInstantiations ??= new Set<GenericInstantiation>();
+    _genericInstantiations.add(instantiation);
+  }
+
+  @override
+  Iterable<GenericInstantiation> get genericInstantiations {
+    return _genericInstantiations ?? const <GenericInstantiation>[];
+  }
 }
 
 // TODO(johnniwinther): Split this class into interface and implementation.
@@ -169,6 +176,10 @@
   void registerAsyncMarker(AsyncMarker asyncMarker) {
     worldImpact.registerAsyncMarker(asyncMarker);
   }
+
+  void registerGenericInstantiation(GenericInstantiation instantiation) {
+    worldImpact.registerGenericInstantiation(instantiation);
+  }
 }
 
 /// [WorkItem] used exclusively by the [CodegenEnqueuer].
diff --git a/pkg/compiler/lib/src/common/resolution.dart b/pkg/compiler/lib/src/common/resolution.dart
index b0eb1ac..cf2ed2c 100644
--- a/pkg/compiler/lib/src/common/resolution.dart
+++ b/pkg/compiler/lib/src/common/resolution.dart
@@ -21,4 +21,7 @@
   Iterable<ClassEntity> get seenClasses => const <ClassEntity>[];
 
   Iterable<dynamic> get nativeData => const <dynamic>[];
+
+  Iterable<GenericInstantiation> get genericInstantiations =>
+      const <GenericInstantiation>[];
 }
diff --git a/pkg/compiler/lib/src/common_elements.dart b/pkg/compiler/lib/src/common_elements.dart
index c4419b5..738bd388 100644
--- a/pkg/compiler/lib/src/common_elements.dart
+++ b/pkg/compiler/lib/src/common_elements.dart
@@ -1455,6 +1455,12 @@
   /// `Object`.
   DartType getTypeVariableBound(TypeVariableEntity typeVariable);
 
+  /// The default type of the [typeVariable].
+  ///
+  /// This is the type used as the default type argument when no explicit type
+  /// argument is passed.
+  DartType getTypeVariableDefaultType(TypeVariableEntity typeVariable);
+
   /// Returns the type of [function].
   FunctionType getFunctionType(FunctionEntity function);
 
diff --git a/pkg/compiler/lib/src/helpers/debug_collection.dart b/pkg/compiler/lib/src/helpers/debug_collection.dart
index 03ac0e9..c7b9f79 100644
--- a/pkg/compiler/lib/src/helpers/debug_collection.dart
+++ b/pkg/compiler/lib/src/helpers/debug_collection.dart
@@ -22,10 +22,6 @@
   }
 
   Map<RK, RV> cast<RK, RV>() => Map.castFrom<K, V, RK, RV>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<RK, RV> retype<RK, RV>() => cast<RK, RV>();
-
   bool containsValue(Object value) {
     return sourceMap.containsValue(value);
   }
@@ -108,10 +104,6 @@
   Iterator<E> get iterator => iterable.iterator;
 
   Iterable<R> cast<R>() => Iterable.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Iterable<R> retype<R>() => cast<R>();
-
   Iterable<T> map<T>(T f(E element)) => iterable.map(f);
 
   Iterable<E> where(bool test(E element)) => iterable.where(test);
@@ -190,10 +182,6 @@
   List<E> get list => iterable;
 
   List<R> cast<R>() => List.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   List<E> operator +(List<E> other) => list + other;
 
   E operator [](int index) => list[index];
@@ -297,10 +285,6 @@
   Set<E> get set => iterable;
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   bool contains(Object value) => set.contains(value);
 
   bool add(E value) {
diff --git a/pkg/compiler/lib/src/helpers/expensive_map.dart b/pkg/compiler/lib/src/helpers/expensive_map.dart
index 48be384..5f5cb44 100644
--- a/pkg/compiler/lib/src/helpers/expensive_map.dart
+++ b/pkg/compiler/lib/src/helpers/expensive_map.dart
@@ -69,10 +69,6 @@
   }
 
   Map<KR, VR> cast<KR, VR>() => Map.castFrom<K, V, KR, VR>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<KR, VR> retype<KR, VR>() => cast<KR, VR>();
-
   Iterable<MapEntry<K, V>> get entries => _maps[0].entries;
 
   void addEntries(Iterable<MapEntry<K, V>> entries) {
diff --git a/pkg/compiler/lib/src/helpers/track_map.dart b/pkg/compiler/lib/src/helpers/track_map.dart
index 0a87cf5..7c2eb86 100644
--- a/pkg/compiler/lib/src/helpers/track_map.dart
+++ b/pkg/compiler/lib/src/helpers/track_map.dart
@@ -98,10 +98,6 @@
   }
 
   Map<KR, VR> cast<KR, VR>() => _map.cast<KR, VR>();
-
-  @Deprecated("Use cast instead.")
-  Map<KR, VR> retype<KR, VR>() => cast<KR, VR>();
-
   Iterable<MapEntry<K, V>> get entries => _map.entries;
 
   void addEntries(Iterable<MapEntry<K, V>> entries) {
diff --git a/pkg/compiler/lib/src/inferrer/builder_kernel.dart b/pkg/compiler/lib/src/inferrer/builder_kernel.dart
index fe24043..a6e885a1 100644
--- a/pkg/compiler/lib/src/inferrer/builder_kernel.dart
+++ b/pkg/compiler/lib/src/inferrer/builder_kernel.dart
@@ -28,6 +28,10 @@
 import 'type_graph_nodes.dart';
 import 'type_system.dart';
 
+/// Whether the static type of property gets and method invocations is used
+/// to narrow the inferred type in strong mode.
+bool useStaticResultTypes = false;
+
 /// [KernelTypeGraphBuilder] constructs a type-inference graph for a particular
 /// element.
 ///
@@ -739,8 +743,12 @@
         return _types.dynamicType;
       }
 
-      return handleStaticInvoke(
-          node, selector, mask, info.callMethod, arguments);
+      TypeInformation type =
+          handleStaticInvoke(node, selector, mask, info.callMethod, arguments);
+      if (_options.strongMode && useStaticResultTypes) {
+        type = _types.narrowType(type, _elementMap.getStaticType(node));
+      }
+      return type;
     }
 
     TypeInformation receiverType = visit(receiver);
@@ -760,8 +768,12 @@
       _checkIfExposesThis(
           selector, _types.newTypedSelector(receiverType, mask));
     }
-    return handleDynamicInvoke(
+    TypeInformation type = handleDynamicInvoke(
         CallType.access, node, selector, mask, receiverType, arguments);
+    if (_options.strongMode && useStaticResultTypes) {
+      type = _types.narrowType(type, _elementMap.getStaticType(node));
+    }
+    return type;
   }
 
   TypeInformation _handleDynamic(
@@ -1155,9 +1167,19 @@
       return handleConstructorInvoke(
           node, node.arguments, selector, mask, member, arguments);
     } else if (member.isFunction) {
-      return handleStaticInvoke(node, selector, mask, member, arguments);
+      TypeInformation type =
+          handleStaticInvoke(node, selector, mask, member, arguments);
+      if (_options.strongMode && useStaticResultTypes) {
+        type = _types.narrowType(type, _elementMap.getStaticType(node));
+      }
+      return type;
     } else {
-      return handleClosureCall(node, selector, mask, member, arguments);
+      TypeInformation type =
+          handleClosureCall(node, selector, mask, member, arguments);
+      if (_options.strongMode && useStaticResultTypes) {
+        type = _types.narrowType(type, _elementMap.getStaticType(node));
+      }
+      return type;
     }
   }
 
@@ -1171,8 +1193,12 @@
   TypeInformation visitStaticGet(ir.StaticGet node) {
     MemberEntity member = _elementMap.getMember(node.target);
     AbstractValue mask = _memberData.typeOfSend(node);
-    return handleStaticInvoke(
+    TypeInformation type = handleStaticInvoke(
         node, new Selector.getter(member.memberName), mask, member, null);
+    if (_options.strongMode && useStaticResultTypes) {
+      type = _types.narrowType(type, _elementMap.getStaticType(node));
+    }
+    return type;
   }
 
   @override
@@ -1199,7 +1225,11 @@
       _checkIfExposesThis(
           selector, _types.newTypedSelector(receiverType, mask));
     }
-    return handleDynamicGet(node, selector, mask, receiverType);
+    TypeInformation type = handleDynamicGet(node, selector, mask, receiverType);
+    if (_options.strongMode && useStaticResultTypes) {
+      type = _types.narrowType(type, _elementMap.getStaticType(node));
+    }
+    return type;
   }
 
   @override
@@ -1210,7 +1240,11 @@
     // TODO(johnniwinther): Use `node.target` to narrow the receiver type.
     Selector selector = new Selector.getter(member.memberName);
     _checkIfExposesThis(selector, _types.newTypedSelector(receiverType, mask));
-    return handleDynamicGet(node, selector, mask, receiverType);
+    TypeInformation type = handleDynamicGet(node, selector, mask, receiverType);
+    if (_options.strongMode && useStaticResultTypes) {
+      type = _types.narrowType(type, _elementMap.getStaticType(node));
+    }
+    return type;
   }
 
   @override
@@ -1634,7 +1668,12 @@
     if (member == null) {
       return handleSuperNoSuchMethod(node, selector, mask, null);
     } else {
-      return handleStaticInvoke(node, selector, mask, member, null);
+      TypeInformation type =
+          handleStaticInvoke(node, selector, mask, member, null);
+      if (_options.strongMode && useStaticResultTypes) {
+        type = _types.narrowType(type, _elementMap.getStaticType(node));
+      }
+      return type;
     }
   }
 
@@ -1676,10 +1715,20 @@
       if (isIncompatibleInvoke(member, arguments)) {
         return handleSuperNoSuchMethod(node, selector, mask, arguments);
       } else {
-        return handleStaticInvoke(node, selector, mask, member, arguments);
+        TypeInformation type =
+            handleStaticInvoke(node, selector, mask, member, arguments);
+        if (_options.strongMode && useStaticResultTypes) {
+          type = _types.narrowType(type, _elementMap.getStaticType(node));
+        }
+        return type;
       }
     } else {
-      return handleClosureCall(node, selector, mask, member, arguments);
+      TypeInformation type =
+          handleClosureCall(node, selector, mask, member, arguments);
+      if (_options.strongMode && useStaticResultTypes) {
+        type = _types.narrowType(type, _elementMap.getStaticType(node));
+      }
+      return type;
     }
   }
 
diff --git a/pkg/compiler/lib/src/js_backend/backend_usage.dart b/pkg/compiler/lib/src/js_backend/backend_usage.dart
index 8af1da3..7e2065e 100644
--- a/pkg/compiler/lib/src/js_backend/backend_usage.dart
+++ b/pkg/compiler/lib/src/js_backend/backend_usage.dart
@@ -43,9 +43,6 @@
 
   /// `true` if `noSuchMethod` is used.
   bool get isNoSuchMethodUsed;
-
-  /// `true` if generic instantiation is used.
-  bool get isGenericInstantiationUsed;
 }
 
 abstract class BackendUsageBuilder {
@@ -83,9 +80,6 @@
   /// `true` if `noSuchMethod` is used.
   bool isNoSuchMethodUsed;
 
-  /// `true` if generic instantiation is used.
-  bool isGenericInstantiationUsed;
-
   BackendUsage close();
 }
 
@@ -122,9 +116,6 @@
   /// `true` if `noSuchMethod` is used.
   bool isNoSuchMethodUsed = false;
 
-  /// `true` if generic instantiation is used.
-  bool isGenericInstantiationUsed = false;
-
   BackendUsageBuilderImpl(this._commonElements);
 
   @override
@@ -280,8 +271,7 @@
         isRuntimeTypeUsed: isRuntimeTypeUsed,
         isFunctionApplyUsed: isFunctionApplyUsed,
         isMirrorsUsed: isMirrorsUsed,
-        isNoSuchMethodUsed: isNoSuchMethodUsed,
-        isGenericInstantiationUsed: isGenericInstantiationUsed);
+        isNoSuchMethodUsed: isNoSuchMethodUsed);
   }
 }
 
@@ -317,9 +307,6 @@
   /// `true` if `noSuchMethod` is used.
   final bool isNoSuchMethodUsed;
 
-  /// `true` if generic instantiation is used.
-  final bool isGenericInstantiationUsed;
-
   BackendUsageImpl(
       {Set<FunctionEntity> globalFunctionDependencies,
       Set<ClassEntity> globalClassDependencies,
@@ -332,8 +319,7 @@
       this.isRuntimeTypeUsed,
       this.isFunctionApplyUsed,
       this.isMirrorsUsed,
-      this.isNoSuchMethodUsed,
-      this.isGenericInstantiationUsed})
+      this.isNoSuchMethodUsed})
       : this._globalFunctionDependencies = globalFunctionDependencies,
         this._globalClassDependencies = globalClassDependencies,
         this._helperFunctionsUsed = helperFunctionsUsed,
diff --git a/pkg/compiler/lib/src/js_backend/impact_transformer.dart b/pkg/compiler/lib/src/js_backend/impact_transformer.dart
index 70e8d1a..8d6506d 100644
--- a/pkg/compiler/lib/src/js_backend/impact_transformer.dart
+++ b/pkg/compiler/lib/src/js_backend/impact_transformer.dart
@@ -104,10 +104,6 @@
               new TypeUse.instantiation(_commonElements.nullType));
           registerImpact(_impacts.nullLiteral);
           break;
-        case Feature.GENERIC_INSTANTIATION:
-          registerImpact(_impacts.genericInstantiation);
-          _backendUsageBuilder.isGenericInstantiationUsed = true;
-          break;
         case Feature.LAZY_FIELD:
           registerImpact(_impacts.lazyField);
           break;
@@ -292,6 +288,14 @@
       _classHierarchyBuilder.registerClass(classEntity);
     }
 
+    if (worldImpact.genericInstantiations.isNotEmpty) {
+      registerImpact(_impacts.genericInstantiation);
+      for (GenericInstantiation instantiation
+          in worldImpact.genericInstantiations) {
+        _rtiNeedBuilder.registerGenericInstantiation(instantiation);
+      }
+    }
+
     return transformed;
   }
 
@@ -460,6 +464,10 @@
       }
     }
 
+    for (GenericInstantiation instantiation in impact.genericInstantiations) {
+      _rtiChecksBuilder.registerGenericInstantiation(instantiation);
+    }
+
     // TODO(johnniwinther): Remove eager registration.
     return transformed;
   }
diff --git a/pkg/compiler/lib/src/js_backend/runtime_types.dart b/pkg/compiler/lib/src/js_backend/runtime_types.dart
index d637cb1..332926b 100644
--- a/pkg/compiler/lib/src/js_backend/runtime_types.dart
+++ b/pkg/compiler/lib/src/js_backend/runtime_types.dart
@@ -13,6 +13,7 @@
 import '../js/js.dart' show js;
 import '../js_emitter/js_emitter.dart' show Emitter;
 import '../options.dart';
+import '../universe/feature.dart';
 import '../universe/selector.dart';
 import '../universe/world_builder.dart';
 import '../world.dart' show JClosedWorld, KClosedWorld;
@@ -95,6 +96,13 @@
   /// Returns `true` if a dynamic call of [selector] needs to pass type
   /// arguments.
   bool selectorNeedsTypeArguments(Selector selector);
+
+  /// Returns `true` if a generic instantiation on an expression of type
+  /// [functionType] with the given [typeArgumentCount] needs to pass type
+  /// arguments.
+  // TODO(johnniwinther): Use [functionType].
+  bool instantiationNeedsTypeArguments(
+      DartType functionType, int typeArgumentCount);
 }
 
 class TrivialRuntimeTypesNeed implements RuntimeTypesNeed {
@@ -117,6 +125,12 @@
 
   @override
   bool selectorNeedsTypeArguments(Selector selector) => true;
+
+  @override
+  bool instantiationNeedsTypeArguments(
+      DartType functionType, int typeArgumentCount) {
+    return true;
+  }
 }
 
 /// Interface for computing classes and methods that need runtime types.
@@ -131,6 +145,9 @@
   /// literal.
   void registerLocalFunctionUsingTypeVariableLiteral(Local localFunction);
 
+  /// Registers that a generic [instantiation] is used.
+  void registerGenericInstantiation(GenericInstantiation instantiation);
+
   /// Computes the [RuntimeTypesNeed] for the data registered with this builder.
   RuntimeTypesNeed computeRuntimeTypesNeed(
       ResolutionWorldBuilder resolutionWorldBuilder,
@@ -151,6 +168,9 @@
   void registerLocalFunctionUsingTypeVariableLiteral(Local localFunction) {}
 
   @override
+  void registerGenericInstantiation(GenericInstantiation instantiation) {}
+
+  @override
   RuntimeTypesNeed computeRuntimeTypesNeed(
       ResolutionWorldBuilder resolutionWorldBuilder,
       KClosedWorld closedWorld,
@@ -194,6 +214,9 @@
   void registerTypeVariableBoundsSubtypeCheck(
       DartType typeArgument, DartType bound);
 
+  /// Registers that a generic [instantiation] is used.
+  void registerGenericInstantiation(GenericInstantiation instantiation);
+
   /// Computes the [RuntimeTypesChecks] for the data in this builder.
   RuntimeTypesChecks computeRequiredChecks(
       CodegenWorldBuilder codegenWorldBuilder, CompilerOptions options);
@@ -215,6 +238,9 @@
       DartType typeArgument, DartType bound) {}
 
   @override
+  void registerGenericInstantiation(GenericInstantiation instantiation) {}
+
+  @override
   RuntimeTypesChecks computeRequiredChecks(
       CodegenWorldBuilder codegenWorldBuilder, CompilerOptions options) {
     rtiChecksBuilderClosed = true;
@@ -700,6 +726,7 @@
   final Set<Local> localFunctionsNeedingSignature;
   final Set<Local> localFunctionsNeedingTypeArguments;
   final Set<Selector> selectorsNeedingTypeArguments;
+  final Set<int> instantiationsNeedingTypeArguments;
 
   RuntimeTypesNeedImpl(
       this._elementEnvironment,
@@ -709,7 +736,8 @@
       this.methodsNeedingTypeArguments,
       this.localFunctionsNeedingSignature,
       this.localFunctionsNeedingTypeArguments,
-      this.selectorsNeedingTypeArguments);
+      this.selectorsNeedingTypeArguments,
+      this.instantiationsNeedingTypeArguments);
 
   bool checkClass(covariant ClassEntity cls) => true;
 
@@ -749,6 +777,12 @@
     if (_backendUsage.isRuntimeTypeUsed) return true;
     return selectorsNeedingTypeArguments.contains(selector);
   }
+
+  @override
+  bool instantiationNeedsTypeArguments(
+      DartType functionType, int typeArgumentCount) {
+    return instantiationsNeedingTypeArguments.contains(typeArgumentCount);
+  }
 }
 
 class TypeVariableTests {
@@ -756,6 +790,7 @@
   Map<ClassEntity, ClassNode> _classes = <ClassEntity, ClassNode>{};
   Map<Entity, MethodNode> _methods = <Entity, MethodNode>{};
   Map<Selector, Set<Entity>> _appliedSelectorMap;
+  Map<GenericInstantiation, Set<Entity>> _instantiationMap;
 
   /// All explicit is-tests.
   final Set<DartType> explicitIsChecks;
@@ -763,11 +798,17 @@
   /// All implicit is-tests.
   final Set<DartType> implicitIsChecks = new Set<DartType>();
 
-  TypeVariableTests(ElementEnvironment elementEnvironment,
-      CommonElements commonElements, DartTypes types, WorldBuilder worldBuilder,
+  TypeVariableTests(
+      ElementEnvironment elementEnvironment,
+      CommonElements commonElements,
+      DartTypes types,
+      WorldBuilder worldBuilder,
+      Set<GenericInstantiation> genericInstantiations,
       {bool forRtiNeeds: true})
       : explicitIsChecks = new Set<DartType>.from(worldBuilder.isChecks) {
-    _setupDependencies(elementEnvironment, commonElements, worldBuilder);
+    _setupDependencies(
+        elementEnvironment, commonElements, worldBuilder, genericInstantiations,
+        forRtiNeeds: forRtiNeeds);
     _propagateTests(commonElements, elementEnvironment, worldBuilder);
     if (forRtiNeeds) {
       _propagateLiterals(elementEnvironment, worldBuilder);
@@ -867,6 +908,13 @@
     _appliedSelectorMap.forEach(f);
   }
 
+  /// Calls [f] for each generic instantiation that applies to generic
+  /// closurized [targets].
+  void forEachGenericInstantiation(
+      void f(GenericInstantiation instantiation, Set<Entity> targets)) {
+    _instantiationMap?.forEach(f);
+  }
+
   ClassNode _getClassNode(ClassEntity cls) {
     return _classes.putIfAbsent(cls, () {
       ClassNode node = new ClassNode(cls);
@@ -905,8 +953,12 @@
     });
   }
 
-  void _setupDependencies(ElementEnvironment elementEnvironment,
-      CommonElements commonElements, WorldBuilder worldBuilder) {
+  void _setupDependencies(
+      ElementEnvironment elementEnvironment,
+      CommonElements commonElements,
+      WorldBuilder worldBuilder,
+      Set<GenericInstantiation> genericInstantiations,
+      {bool forRtiNeeds: true}) {
     /// Register that if `node.entity` needs type arguments then so do entities
     /// whose type variables occur in [type].
     ///
@@ -1018,6 +1070,31 @@
       worldBuilder.closurizedStatics.forEach(processEntity);
       worldBuilder.userNoSuchMethods.forEach(processEntity);
     });
+
+    for (GenericInstantiation instantiation in genericInstantiations) {
+      void processEntity(Entity entity) {
+        MethodNode node =
+            _getMethodNode(elementEnvironment, worldBuilder, entity);
+        if (node.parameterStructure.typeParameters ==
+            instantiation.typeArguments.length) {
+          if (forRtiNeeds) {
+            _instantiationMap ??= <GenericInstantiation, Set<Entity>>{};
+            _instantiationMap
+                .putIfAbsent(instantiation, () => new Set<Entity>())
+                .add(entity);
+          }
+          for (DartType type in instantiation.typeArguments) {
+            // Register that if `node.entity` needs type arguments then so do
+            // the entities that declare type variables occurring in [type].
+            registerDependencies(node, type);
+          }
+        }
+      }
+
+      worldBuilder.closurizedMembers.forEach(processEntity);
+      worldBuilder.closurizedStatics.forEach(processEntity);
+      worldBuilder.genericLocalFunctions.forEach(processEntity);
+    }
   }
 
   void _propagateTests(CommonElements commonElements,
@@ -1339,6 +1416,12 @@
 
   Map<Selector, Set<Entity>> selectorsNeedingTypeArgumentsForTesting;
 
+  Map<GenericInstantiation, Set<Entity>>
+      instantiationsNeedingTypeArgumentsForTesting;
+
+  final Set<GenericInstantiation> _genericInstantiations =
+      new Set<GenericInstantiation>();
+
   TypeVariableTests typeVariableTestsForTesting;
 
   RuntimeTypesNeedBuilderImpl(this._elementEnvironment, DartTypes types)
@@ -1360,6 +1443,11 @@
   }
 
   @override
+  void registerGenericInstantiation(GenericInstantiation instantiation) {
+    _genericInstantiations.add(instantiation);
+  }
+
+  @override
   RuntimeTypesNeed computeRuntimeTypesNeed(
       ResolutionWorldBuilder resolutionWorldBuilder,
       KClosedWorld closedWorld,
@@ -1368,7 +1456,8 @@
         closedWorld.elementEnvironment,
         closedWorld.commonElements,
         closedWorld.dartTypes,
-        resolutionWorldBuilder);
+        resolutionWorldBuilder,
+        _genericInstantiations);
     Set<ClassEntity> classesNeedingTypeArguments = new Set<ClassEntity>();
     Set<FunctionEntity> methodsNeedingSignature = new Set<FunctionEntity>();
     Set<FunctionEntity> methodsNeedingTypeArguments = new Set<FunctionEntity>();
@@ -1440,8 +1529,9 @@
           if (potentialSubtypeOf == null ||
               closedWorld.dartTypes.isPotentialSubtype(
                   functionType, potentialSubtypeOf,
-                  assumeInstantiations:
-                      closedWorld.backendUsage.isGenericInstantiationUsed)) {
+                  // TODO(johnniwinther): Use register generic instantiations
+                  // instead.
+                  assumeInstantiations: _genericInstantiations.isNotEmpty)) {
             functionType.forEachTypeVariable((TypeVariableType typeVariable) {
               Entity typeDeclaration = typeVariable.element.typeDeclaration;
               if (!processedEntities.contains(typeDeclaration)) {
@@ -1571,6 +1661,28 @@
         }
       }
     });
+    Set<int> instantiationsNeedingTypeArguments = new Set<int>();
+    typeVariableTests.forEachGenericInstantiation(
+        (GenericInstantiation instantiation, Set<Entity> targets) {
+      for (Entity target in targets) {
+        if (methodsNeedingTypeArguments.contains(target) ||
+            localFunctionsNeedingTypeArguments.contains(target)) {
+          // TODO(johnniwinther): Use the static type of the instantiated
+          // expression.
+          instantiationsNeedingTypeArguments
+              .add(instantiation.typeArguments.length);
+          if (cacheRtiDataForTesting) {
+            instantiationsNeedingTypeArgumentsForTesting ??=
+                <GenericInstantiation, Set<Entity>>{};
+            instantiationsNeedingTypeArgumentsForTesting
+                .putIfAbsent(instantiation, () => new Set<Entity>())
+                .add(target);
+          } else {
+            return;
+          }
+        }
+      }
+    });
 
     if (cacheRtiDataForTesting) {
       typeVariableTestsForTesting = typeVariableTests;
@@ -1594,9 +1706,11 @@
     localFunctionsNeedingTypeArguments.forEach((e) => print('  $e'));
     print('------------------------------------------------------------------');
     print('selectorsNeedingTypeArguments:');
-    selectorsNeedingTypeArguments.forEach((e) => print('  $e'));*/
+    selectorsNeedingTypeArguments.forEach((e) => print('  $e'));
+    print('instantiationsNeedingTypeArguments: '
+        '$instantiationsNeedingTypeArguments');*/
 
-    return _createRuntimeTypesNeed(
+    return new RuntimeTypesNeedImpl(
         _elementEnvironment,
         closedWorld.backendUsage,
         classesNeedingTypeArguments,
@@ -1604,27 +1718,8 @@
         methodsNeedingTypeArguments,
         localFunctionsNeedingSignature,
         localFunctionsNeedingTypeArguments,
-        selectorsNeedingTypeArguments);
-  }
-
-  RuntimeTypesNeed _createRuntimeTypesNeed(
-      ElementEnvironment elementEnvironment,
-      BackendUsage backendUsage,
-      Set<ClassEntity> classesNeedingTypeArguments,
-      Set<FunctionEntity> methodsNeedingSignature,
-      Set<FunctionEntity> methodsNeedingTypeArguments,
-      Set<Local> localFunctionsNeedingSignature,
-      Set<Local> localFunctionsNeedingTypeArguments,
-      Set<Selector> selectorsNeedingTypeArguments) {
-    return new RuntimeTypesNeedImpl(
-        _elementEnvironment,
-        backendUsage,
-        classesNeedingTypeArguments,
-        methodsNeedingSignature,
-        methodsNeedingTypeArguments,
-        localFunctionsNeedingSignature,
-        localFunctionsNeedingTypeArguments,
-        selectorsNeedingTypeArguments);
+        selectorsNeedingTypeArguments,
+        instantiationsNeedingTypeArguments);
   }
 }
 
@@ -1672,6 +1767,9 @@
 
   Map<ClassEntity, ClassUse> classUseMapForTesting;
 
+  final Set<GenericInstantiation> _genericInstantiations =
+      new Set<GenericInstantiation>();
+
   @override
   void registerTypeVariableBoundsSubtypeCheck(
       DartType typeArgument, DartType bound) {
@@ -1679,10 +1777,19 @@
     checkedBounds.add(bound);
   }
 
+  @override
+  void registerGenericInstantiation(GenericInstantiation instantiation) {
+    _genericInstantiations.add(instantiation);
+  }
+
   RuntimeTypesChecks computeRequiredChecks(
       CodegenWorldBuilder codegenWorldBuilder, CompilerOptions options) {
     TypeVariableTests typeVariableTests = new TypeVariableTests(
-        _elementEnvironment, _commonElements, _types, codegenWorldBuilder,
+        _elementEnvironment,
+        _commonElements,
+        _types,
+        codegenWorldBuilder,
+        _genericInstantiations,
         forRtiNeeds: false);
     Set<DartType> explicitIsChecks = typeVariableTests.explicitIsChecks;
     Set<DartType> implicitIsChecks = typeVariableTests.implicitIsChecks;
diff --git a/pkg/compiler/lib/src/js_emitter/class_stub_generator.dart b/pkg/compiler/lib/src/js_emitter/class_stub_generator.dart
index 93f1a0a..b816f95 100644
--- a/pkg/compiler/lib/src/js_emitter/class_stub_generator.dart
+++ b/pkg/compiler/lib/src/js_emitter/class_stub_generator.dart
@@ -237,6 +237,7 @@
 ///    member that is torn off. There can be more than one, since a member
 ///    can have several stubs.
 ///    Each function must have the `$callName` property set.
+///   * `applyTrampolineIndex` is the index of the stub to be used for Function.apply
 ///   * `reflectionInfo`: contains reflective information, and the function
 ///    type. TODO(floitsch): point to where this is specified.
 ///   * `isStatic`.
@@ -268,22 +269,22 @@
     jsAst.Expression tearOffAccessText = new jsAst.UnparsedNode(
         tearOffAccessExpression, options.enableMinification, false);
     tearOffGetter = js.statement('''
-function tearOffGetter(funcs, reflectionInfo, name, isIntercepted) {
+function tearOffGetter(funcs, applyTrampolineIndex, reflectionInfo, name, isIntercepted) {
   return isIntercepted
-      ? new Function("funcs", "reflectionInfo", "name",
+      ? new Function("funcs", "applyTrampolineIndex", "reflectionInfo", "name",
                      #tearOffGlobalObjectString, "c",
           "return function tearOff_" + name + (functionCounter++) + "(x) {" +
             "if (c === null) c = " + #tearOffAccessText + "(" +
-                "this, funcs, reflectionInfo, false, [x], name);" +
+                "this, funcs, applyTrampolineIndex, reflectionInfo, false, [x], name);" +
                 "return new c(this, funcs[0], x, name);" +
-                "}")(funcs, reflectionInfo, name, #tearOffGlobalObject, null)
-      : new Function("funcs", "reflectionInfo", "name",
+           "}")(funcs, applyTrampolineIndex, reflectionInfo, name, #tearOffGlobalObject, null)
+      : new Function("funcs", "applyTrampolineIndex", "reflectionInfo", "name",
                      #tearOffGlobalObjectString, "c",
           "return function tearOff_" + name + (functionCounter++)+ "() {" +
             "if (c === null) c = " + #tearOffAccessText + "(" +
-                "this, funcs, reflectionInfo, false, [], name);" +
+                "this, funcs, applyTrampolineIndex, reflectionInfo, false, [], name);" +
                 "return new c(this, funcs[0], null, name);" +
-                "}")(funcs, reflectionInfo, name, #tearOffGlobalObject, null);
+             "}")(funcs, applyTrampolineIndex, reflectionInfo, name, #tearOffGlobalObject, null);
 }''', {
       'tearOffAccessText': tearOffAccessText,
       'tearOffGlobalObject': tearOffGlobalObject,
@@ -291,32 +292,35 @@
     });
   } else {
     tearOffGetter = js.statement('''
-      function tearOffGetter(funcs, reflectionInfo, name, isIntercepted) {
+        function tearOffGetter(funcs, applyTrampolineIndex, reflectionInfo, name, isIntercepted) {
         var cache = null;
         return isIntercepted
             ? function(x) {
                 if (cache === null) cache = #(
-                    this, funcs, reflectionInfo, false, [x], name);
+                    this, funcs, applyTrampolineIndex, reflectionInfo, false, [x], name);
                 return new cache(this, funcs[0], x, name);
               }
             : function() {
                 if (cache === null) cache = #(
-                    this, funcs, reflectionInfo, false, [], name);
+                    this, funcs, applyTrampolineIndex, reflectionInfo, false, [], name);
                 return new cache(this, funcs[0], null, name);
               };
       }''', [tearOffAccessExpression, tearOffAccessExpression]);
   }
 
   jsAst.Statement tearOff = js.statement('''
-    function tearOff(funcs, reflectionInfo, isStatic, name, isIntercepted) {
+      function tearOff(funcs, applyTrampolineIndex,
+          reflectionInfo, isStatic, name, isIntercepted) {
       var cache;
       return isStatic
           ? function() {
               if (cache === void 0) cache = #tearOff(
-                  this, funcs, reflectionInfo, true, [], name).prototype;
+                  this, funcs, applyTrampolineIndex,
+                  reflectionInfo, true, [], name).prototype;
               return cache;
             }
-          : tearOffGetter(funcs, reflectionInfo, name, isIntercepted);
+          : tearOffGetter(funcs, applyTrampolineIndex,
+              reflectionInfo, name, isIntercepted);
     }''', {'tearOff': tearOffAccessExpression});
 
   return <jsAst.Statement>[tearOffGetter, tearOff];
diff --git a/pkg/compiler/lib/src/js_emitter/full_emitter/container_builder.dart b/pkg/compiler/lib/src/js_emitter/full_emitter/container_builder.dart
index 144f886..572b1b8 100644
--- a/pkg/compiler/lib/src/js_emitter/full_emitter/container_builder.dart
+++ b/pkg/compiler/lib/src/js_emitter/full_emitter/container_builder.dart
@@ -64,9 +64,10 @@
     // The information is stored in an array with this format:
     //
     // 1.   The alias name for this function (optional).
-    // 2.   The JS function for this member.
-    // 3.   First stub.
-    // 4.   Name of first stub.
+    // 2.   Index into the functions and stubs of the apply stub (optional).
+    // 3.   The JS function for this member.
+    // 4.   First stub.
+    // 5.   Name of first stub.
     // ...
     // M.   Call name of this member.
     // M+1. Call name of first stub.
@@ -94,6 +95,12 @@
       expressions.add(js.quoteName(superAlias));
     }
 
+    if (canBeApplied && parameters.typeParameters > 0) {
+      // The first stub is the one that has all the value parameters parameters
+      // but no type parameters. This is the entry point for Function.apply.
+      expressions.add(js.number(1));
+    }
+
     expressions.add(code);
 
     bool onlyNeedsSuperAlias = !(canTearOff || canBeApplied || needsStubs);
diff --git a/pkg/compiler/lib/src/js_emitter/full_emitter/setup_program_builder.dart b/pkg/compiler/lib/src/js_emitter/full_emitter/setup_program_builder.dart
index acb5308..3017abe 100644
--- a/pkg/compiler/lib/src/js_emitter/full_emitter/setup_program_builder.dart
+++ b/pkg/compiler/lib/src/js_emitter/full_emitter/setup_program_builder.dart
@@ -211,6 +211,7 @@
       for (var i = 0; i < fields.length; i++) {
         var fieldDescriptor = fields[i];
         if (fieldDescriptor.charCodeAt(0) == 48) {
+          // null-initialized field.
           fieldDescriptor = fieldDescriptor.substring(1);
           var field = generateAccessor(fieldDescriptor, accessors, name);
           body += ("this." + field + " = null;\\n");
@@ -489,7 +490,7 @@
               descriptor[property];
           var optionalMethods = descriptor.$methodsWithOptionalArgumentsField;
           if (!optionalMethods) {
-            descriptor.$methodsWithOptionalArgumentsField = optionalMethods={}
+            descriptor.$methodsWithOptionalArgumentsField = optionalMethods = {}
           }
           optionalMethods[property] = previousProperty;
         } else {
@@ -604,14 +605,19 @@
     // the information is thrown away at the call site. This is to avoid
     // conditionals.
     function addStubs(prototype, array, name, isStatic, functions) {
-      var index = $FUNCTION_INDEX, alias = array[index], f;
+      var index = $FUNCTION_INDEX, applyTrampolineIndex = index, alias = array[index], f;
       if (typeof alias == "string") {
         f = array[++index];
       } else {
         f = alias;
         alias = name;
       }
-      var funcs = [prototype[name] = prototype[alias] = f];
+      if (typeof f == "number") {
+        applyTrampolineIndex = f;
+        f = array[++index];
+      }
+      prototype[name] = prototype[alias] = f;
+      var funcs = [f];
       f.\$stubName = name;
       functions.push(name);
       for (index++; index < array.length; index++) {
@@ -665,7 +671,7 @@
       var unmangledNameIndex = $unmangledNameIndex;
 
       if (getterStubName) {
-        f = tearOff(funcs, array, isStatic, name, isIntercepted);
+        f = tearOff(funcs, applyTrampolineIndex, array, isStatic, name, isIntercepted);
         prototype[name].\$getter = f;
         f.\$getterStub = true;
         if (isStatic) {
@@ -712,7 +718,7 @@
           funcs[0].$metadataIndexField = unmangledNameIndex + 1;
           // The following line installs the [${JsGetName.CALL_CATCH_ALL}]
           // property for closures.
-          if (optionalParameterCount) prototype[unmangledName + "*"] = funcs[0];
+          if (optionalParameterCount) prototype[unmangledName + "*"] = funcs[applyTrampolineIndex];
         }
       }
     }
diff --git a/pkg/compiler/lib/src/js_emitter/model.dart b/pkg/compiler/lib/src/js_emitter/model.dart
index b1436c5..467648f 100644
--- a/pkg/compiler/lib/src/js_emitter/model.dart
+++ b/pkg/compiler/lib/src/js_emitter/model.dart
@@ -433,6 +433,7 @@
   final js.Name tearOffName;
   final List<ParameterStubMethod> parameterStubs;
   final bool canBeApplied;
+  final int applyIndex;
 
   // Is non-null if [needsTearOff].
   //
@@ -458,7 +459,8 @@
       this.canBeApplied,
       this.requiredParameterCount,
       this.optionalParameterDefaultValues,
-      this.functionType})
+      this.functionType,
+      this.applyIndex})
       : super(element, name, code) {
     assert(needsTearOff != null);
     assert(!needsTearOff || tearOffName != null);
@@ -486,6 +488,9 @@
   /// True if the interceptor calling convention is used for this method.
   final bool isIntercepted;
 
+  /// Name called via the general 'catch all' path of Function.apply.
+  ///final js.Name applyName;
+
   InstanceMethod(FunctionEntity element, js.Name name, js.Expression code,
       List<ParameterStubMethod> parameterStubs, js.Name callName,
       {bool needsTearOff,
@@ -496,14 +501,16 @@
       /* List | Map */ optionalParameterDefaultValues,
       this.isClosureCallMethod,
       this.isIntercepted,
-      js.Expression functionType})
+      js.Expression functionType,
+      int applyIndex})
       : super(element, name, code, parameterStubs, callName,
             needsTearOff: needsTearOff,
             tearOffName: tearOffName,
             canBeApplied: canBeApplied,
             requiredParameterCount: requiredParameterCount,
             optionalParameterDefaultValues: optionalParameterDefaultValues,
-            functionType: functionType) {
+            functionType: functionType,
+            applyIndex: applyIndex) {
     assert(isClosureCallMethod != null);
   }
 
@@ -549,8 +556,9 @@
       : super(name, code);
 
   String toString() {
-    return 'ParameterStubMethod(name=${name.key},element=${element}'
-        ',code=${js.nodeToString(code)})';
+    return 'ParameterStubMethod(name=${name.key}, callName=${callName?.key}'
+        ', element=${element}'
+        ', code=${js.nodeToString(code)})';
   }
 }
 
@@ -573,14 +581,16 @@
       bool canBeApplied,
       int requiredParameterCount,
       /* List | Map */ optionalParameterDefaultValues,
-      js.Expression functionType})
+      js.Expression functionType,
+      int applyIndex})
       : super(element, name, code, parameterStubs, callName,
             needsTearOff: needsTearOff,
             tearOffName: tearOffName,
             canBeApplied: canBeApplied,
             requiredParameterCount: requiredParameterCount,
             optionalParameterDefaultValues: optionalParameterDefaultValues,
-            functionType: functionType);
+            functionType: functionType,
+            applyIndex: applyIndex);
 
   bool get isStatic => true;
 
diff --git a/pkg/compiler/lib/src/js_emitter/parameter_stub_generator.dart b/pkg/compiler/lib/src/js_emitter/parameter_stub_generator.dart
index 4b173c6..0492ada 100644
--- a/pkg/compiler/lib/src/js_emitter/parameter_stub_generator.dart
+++ b/pkg/compiler/lib/src/js_emitter/parameter_stub_generator.dart
@@ -170,8 +170,12 @@
           targetArguments[count++] = _rtiEncoder.getTypeRepresentation(
               _emitter,
               _closedWorld.elementEnvironment
-                  .getTypeVariableBound(typeVariable.element),
-              (_) => _emitter.constantReference(new NullConstantValue()));
+                  .getTypeVariableDefaultType(typeVariable.element),
+              (_) => _emitter.constantReference(
+                  // TODO(33422): Support type variables in default
+                  // types. Temporarily using the "any" type (encoded as -2) to
+                  // avoid failing on bounds checks.
+                  new IntConstantValue(new BigInt.from(-2))));
         } else {
           String jsName = '\$${typeVariable.element.name}';
           stubParameters[parameterIndex++] = new jsAst.Parameter(jsName);
@@ -257,7 +261,9 @@
   // (2) foo$3$c(a, b, c) => MyClass.foo$4$c$d(this, a, b, c, null);
   // (3) foo$3$d(a, b, d) => MyClass.foo$4$c$d(this, a, b, null, d);
   List<ParameterStubMethod> generateParameterStubs(FunctionEntity member,
-      {bool canTearOff: true}) {
+      {bool canTearOff, bool canBeApplied}) {
+    assert(canTearOff != null);
+    assert(canBeApplied != null);
     // The set of selectors that apply to `member`. For example, for
     // a member `foo(x, [y])` the following selectors may apply:
     // `foo(x)`, and `foo(x, y)`.
@@ -270,6 +276,8 @@
     // call-selectors: `call(x)`, and `call(x, y)`.
     Map<Selector, SelectorConstraints> callSelectors;
 
+    int memberTypeParameters = member.parameterStructure.typeParameters;
+
     // Only instance members (not static methods) need stubs.
     if (member.isInstanceMember) {
       liveSelectors = _codegenWorldBuilder.invocationsByName(member.name);
@@ -286,7 +294,10 @@
 
     List<ParameterStubMethod> stubs = <ParameterStubMethod>[];
 
-    if (liveSelectors.isEmpty && callSelectors.isEmpty) {
+    if (liveSelectors.isEmpty &&
+        callSelectors.isEmpty &&
+        // Function.apply might need a stub to default the type parameter.
+        !(canBeApplied && memberTypeParameters > 0)) {
       return stubs;
     }
 
@@ -295,13 +306,28 @@
     //
     // For example, for the call-selector `call(x, y)` the renamed selector
     // for member `foo` would be `foo(x, y)`.
-    Set<Selector> renamedCallSelectors =
-        callSelectors.isEmpty ? emptySelectorSet : new Set<Selector>();
+    Set<Selector> renamedCallSelectors = new Set<Selector>();
 
     Set<Selector> stubSelectors = new Set<Selector>();
 
-    // Start with the callSelectors since they imply the generation of the
-    // non-call version.
+    // Start with closure-call selectors, since since they imply the generation
+    // of the non-call version.
+    if (canBeApplied && memberTypeParameters > 0) {
+      // Function.apply calls the function with no type arguments, so generic
+      // methods need the stub to default the type arguments.
+      // This has to be the first stub.
+      Selector namedSelector = new Selector.fromElement(member).toNonGeneric();
+      Selector closureSelector =
+          namedSelector.isClosureCall ? null : namedSelector.toCallSelector();
+
+      renamedCallSelectors.add(namedSelector);
+      stubSelectors.add(namedSelector);
+      ParameterStubMethod stub =
+          generateParameterStub(member, namedSelector, closureSelector);
+      assert(stub != null);
+      stubs.add(stub);
+    }
+
     for (Selector selector in callSelectors.keys) {
       Selector renamedSelector =
           new Selector.call(member.memberName, selector.callStructure);
@@ -326,12 +352,11 @@
       //
       // This is basically the same logic as above, but with type arguments.
       if (selector.callStructure.typeArgumentCount == 0) {
-        ParameterStructure parameterStructure = member.parameterStructure;
-        if (parameterStructure.typeParameters > 0) {
+        if (memberTypeParameters > 0) {
           Selector renamedSelectorWithTypeArguments = new Selector.call(
               member.memberName,
               selector.callStructure
-                  .withTypeArgumentCount(parameterStructure.typeParameters));
+                  .withTypeArgumentCount(memberTypeParameters));
           renamedCallSelectors.add(renamedSelectorWithTypeArguments);
 
           if (stubSelectors.add(renamedSelectorWithTypeArguments)) {
@@ -348,8 +373,8 @@
     }
 
     // Now run through the actual member selectors (eg. `foo$2(x, y)` and not
-    // `call$2(x, y)`. Some of them have already been generated because of the
-    // call-selectors (and they are in the renamedCallSelectors set.
+    // `call$2(x, y)`). Some of them have already been generated because of the
+    // call-selectors and they are in the renamedCallSelectors set.
     for (Selector selector in liveSelectors.keys) {
       if (renamedCallSelectors.contains(selector)) continue;
       if (!selector.appliesUnnamed(member)) continue;
diff --git a/pkg/compiler/lib/src/js_emitter/program_builder/program_builder.dart b/pkg/compiler/lib/src/js_emitter/program_builder/program_builder.dart
index 09d4947..051d3e7 100644
--- a/pkg/compiler/lib/src/js_emitter/program_builder/program_builder.dart
+++ b/pkg/compiler/lib/src/js_emitter/program_builder/program_builder.dart
@@ -677,8 +677,10 @@
 
     void visitMember(MemberEntity member) {
       if (member.isInstanceMember && !member.isAbstract && !member.isField) {
-        Method method = _buildMethod(member);
-        if (method != null && member is! JSignatureMethod) methods.add(method);
+        if (member is! JSignatureMethod) {
+          Method method = _buildMethod(member);
+          if (method != null) methods.add(method);
+        }
       }
       if (member.isGetter || member.isField) {
         Map<Selector, SelectorConstraints> selectors =
@@ -924,16 +926,21 @@
 
     int requiredParameterCount;
     var /* List | Map */ optionalParameterDefaultValues;
+    int applyIndex = 0;
     if (canBeApplied) {
       // TODO(redemption): Handle function entities.
       FunctionEntity method = element;
       ParameterStructure parameterStructure = method.parameterStructure;
       requiredParameterCount = parameterStructure.requiredParameters;
       optionalParameterDefaultValues = _computeParameterDefaultValues(method);
+
+      if (element.parameterStructure.typeParameters > 0) {
+        applyIndex = 1;
+      }
     }
 
     return new InstanceMethod(element, name, code,
-        _generateParameterStubs(element, canTearOff), callName,
+        _generateParameterStubs(element, canTearOff, canBeApplied), callName,
         needsTearOff: canTearOff,
         tearOffName: tearOffName,
         isClosureCallMethod: isClosureCallMethod,
@@ -942,7 +949,8 @@
         canBeApplied: canBeApplied,
         requiredParameterCount: requiredParameterCount,
         optionalParameterDefaultValues: optionalParameterDefaultValues,
-        functionType: functionType);
+        functionType: functionType,
+        applyIndex: applyIndex);
   }
 
   js.Expression _generateFunctionType(
@@ -956,7 +964,7 @@
   }
 
   List<ParameterStubMethod> _generateParameterStubs(
-      FunctionEntity element, bool canTearOff) {
+      FunctionEntity element, bool canTearOff, bool canBeApplied) {
     if (!_methodNeedsStubs(element)) return const <ParameterStubMethod>[];
 
     ParameterStubGenerator generator = new ParameterStubGenerator(
@@ -968,7 +976,8 @@
         _worldBuilder,
         _closedWorld,
         _sourceInformationStrategy);
-    return generator.generateParameterStubs(element, canTearOff: canTearOff);
+    return generator.generateParameterStubs(element,
+        canTearOff: canTearOff, canBeApplied: canBeApplied);
   }
 
   List<StubMethod> _generateInstantiationStubs(ClassEntity instantiationClass) {
@@ -1146,24 +1155,34 @@
 
     int requiredParameterCount;
     var /* List | Map */ optionalParameterDefaultValues;
+    int applyIndex = 0;
     if (canBeApplied) {
       // TODO(redemption): Support entities;
       FunctionEntity method = element;
       ParameterStructure parameterStructure = method.parameterStructure;
       requiredParameterCount = parameterStructure.requiredParameters;
       optionalParameterDefaultValues = _computeParameterDefaultValues(method);
+      if (parameterStructure.typeParameters > 0) {
+        applyIndex = 1;
+      }
     }
 
     // TODO(floitsch): we shouldn't update the registry in the middle of
     // building a static method.
-    return new StaticDartMethod(element, name, _registry.registerHolder(holder),
-        code, _generateParameterStubs(element, needsTearOff), callName,
+    return new StaticDartMethod(
+        element,
+        name,
+        _registry.registerHolder(holder),
+        code,
+        _generateParameterStubs(element, needsTearOff, canBeApplied),
+        callName,
         needsTearOff: needsTearOff,
         tearOffName: tearOffName,
         canBeApplied: canBeApplied,
         requiredParameterCount: requiredParameterCount,
         optionalParameterDefaultValues: optionalParameterDefaultValues,
-        functionType: functionType);
+        functionType: functionType,
+        applyIndex: applyIndex);
   }
 
   void _registerConstants(
diff --git a/pkg/compiler/lib/src/js_emitter/startup_emitter/fragment_emitter.dart b/pkg/compiler/lib/src/js_emitter/startup_emitter/fragment_emitter.dart
index b0356e6..2fc04b0 100644
--- a/pkg/compiler/lib/src/js_emitter/startup_emitter/fragment_emitter.dart
+++ b/pkg/compiler/lib/src/js_emitter/startup_emitter/fragment_emitter.dart
@@ -204,7 +204,7 @@
 // different tearOffCode?
 function installTearOff(
     container, getterName, isStatic, isIntercepted, requiredParameterCount,
-    optionalParameterDefaultValues, callNames, funsOrNames, funType) {
+    optionalParameterDefaultValues, callNames, funsOrNames, funType, applyIndex) {
   // A function can have several stubs (for example to fill in optional
   // arguments). We collect these functions in the `funs` array.
   var funs = [];
@@ -230,7 +230,7 @@
   var name = funsOrNames[0];
   fun.#stubName = name;
   var getterFunction =
-      tearOff(funs, reflectionInfo, isStatic, name, isIntercepted);
+      tearOff(funs, applyIndex || 0, reflectionInfo, isStatic, name, isIntercepted);
   container[getterName] = getterFunction;
   if (isStatic) {
     fun.$tearOffPropertyName = getterFunction;
@@ -825,17 +825,40 @@
       thisRef = js.js('this');
     }
 
+    // Chain assignments of the same value, e.g. `this.b = this.a = null`.
+    // Limit chain length so that the JavaScript parser has bounded recursion.
+    const int maxChainLength = 30;
+    js.Expression assignment = null;
+    int chainLength = 0;
+    bool previousIsNull = false;
+    void flushAssignment() {
+      if (assignment != null) {
+        statements.add(js.js.statement('#;', assignment));
+        assignment = null;
+        chainLength = 0;
+        previousIsNull = false;
+      }
+    }
+
     for (Field field in cls.fields) {
       if (field.nullInitializerInAllocator) {
-        // TODO(sra): Chain initializations, e.g. `this.b = this.a = null;`.
-        statements.add(js.js.statement('#.# = null', [thisRef, field.name]));
+        if (previousIsNull && chainLength < maxChainLength) {
+          assignment = js.js('#.# = #', [thisRef, field.name, assignment]);
+        } else {
+          flushAssignment();
+          assignment = js.js('#.# = null', [thisRef, field.name]);
+        }
+        ++chainLength;
+        previousIsNull = true;
       } else {
+        flushAssignment();
         js.Parameter parameter = new js.Parameter('t${parameters.length}');
         parameters.add(parameter);
         statements.add(
             js.js.statement('#.# = #', [thisRef, field.name, parameter.name]));
       }
     }
+    flushAssignment();
 
     if (cls.hasRtiField) {
       js.Parameter parameter = new js.Parameter('t${parameters.length}');
@@ -1011,8 +1034,10 @@
         // complex cases. [forceAdd] might be true when this is fixed.
         bool forceAdd = !method.isClosureCallMethod;
 
-        properties[js.string(namer.callCatchAllName)] =
-            js.quoteName(method.name);
+        properties[js.string(namer.callCatchAllName)] = js.quoteName(
+            method.applyIndex == 0
+                ? method.name
+                : method.parameterStubs[method.applyIndex - 1].name);
         properties[js.string(namer.requiredParameterField)] =
             js.number(method.requiredParameterCount);
 
@@ -1210,10 +1235,12 @@
           _encodeOptionalParameterDefaultValues(method);
     }
 
+    var applyIndex = js.number(method.applyIndex);
+
     return js.js.statement('''
         installTearOff(#container, #getterName, #isStatic, #isIntercepted,
                        #requiredParameterCount, #optionalParameterDefaultValues,
-                       #callNames, #funsOrNames, #funType)''', {
+                       #callNames, #funsOrNames, #funType, #applyIndex)''', {
       "container": container,
       "getterName": js.quoteName(method.tearOffName),
       // 'Truthy' values are ok for `isStatic` and `isIntercepted`.
@@ -1224,6 +1251,7 @@
       "callNames": callNameArray,
       "funsOrNames": funsOrNamesArray,
       "funType": method.functionType,
+      "applyIndex": applyIndex,
     });
   }
 
diff --git a/pkg/compiler/lib/src/js_model/closure.dart b/pkg/compiler/lib/src/js_model/closure.dart
index b1c32aa..e6cd967 100644
--- a/pkg/compiler/lib/src/js_model/closure.dart
+++ b/pkg/compiler/lib/src/js_model/closure.dart
@@ -199,6 +199,13 @@
               return true;
             }
             break;
+          case VariableUseKind.instantiationTypeArgument:
+            // TODO(johnniwinther): Use the static type of the expression.
+            if (rtiNeed.instantiationNeedsTypeArguments(
+                null, usage.instantiation.typeArguments.length)) {
+              return true;
+            }
+            break;
         }
       }
       return false;
@@ -428,6 +435,9 @@
 
   /// A type variable in a field type.
   fieldType,
+
+  /// A type argument of an generic instantiation.
+  instantiationTypeArgument,
 }
 
 class VariableUse {
@@ -436,21 +446,25 @@
   final ir.TreeNode /*ir.FunctionDeclaration|ir.FunctionExpression*/
       localFunction;
   final ir.MethodInvocation invocation;
+  final ir.Instantiation instantiation;
 
   const VariableUse._simple(this.kind)
       : this.member = null,
         this.localFunction = null,
-        this.invocation = null;
+        this.invocation = null,
+        this.instantiation = null;
 
   VariableUse.memberParameter(this.member)
       : this.kind = VariableUseKind.memberParameter,
         this.localFunction = null,
-        this.invocation = null;
+        this.invocation = null,
+        this.instantiation = null;
 
   VariableUse.localParameter(this.localFunction)
       : this.kind = VariableUseKind.localParameter,
         this.member = null,
-        this.invocation = null {
+        this.invocation = null,
+        this.instantiation = null {
     assert(localFunction is ir.FunctionDeclaration ||
         localFunction is ir.FunctionExpression);
   }
@@ -458,12 +472,14 @@
   VariableUse.memberReturnType(this.member)
       : this.kind = VariableUseKind.memberReturnType,
         this.localFunction = null,
-        this.invocation = null;
+        this.invocation = null,
+        this.instantiation = null;
 
   VariableUse.localReturnType(this.localFunction)
       : this.kind = VariableUseKind.localReturnType,
         this.member = null,
-        this.invocation = null {
+        this.invocation = null,
+        this.instantiation = null {
     assert(localFunction is ir.FunctionDeclaration ||
         localFunction is ir.FunctionExpression);
   }
@@ -471,25 +487,35 @@
   VariableUse.constructorTypeArgument(this.member)
       : this.kind = VariableUseKind.constructorTypeArgument,
         this.localFunction = null,
-        this.invocation = null;
+        this.invocation = null,
+        this.instantiation = null;
 
   VariableUse.staticTypeArgument(this.member)
       : this.kind = VariableUseKind.staticTypeArgument,
         this.localFunction = null,
-        this.invocation = null;
+        this.invocation = null,
+        this.instantiation = null;
 
   VariableUse.instanceTypeArgument(this.invocation)
       : this.kind = VariableUseKind.instanceTypeArgument,
         this.member = null,
-        this.localFunction = null;
+        this.localFunction = null,
+        this.instantiation = null;
 
   VariableUse.localTypeArgument(this.localFunction, this.invocation)
       : this.kind = VariableUseKind.localTypeArgument,
-        this.member = null {
+        this.member = null,
+        this.instantiation = null {
     assert(localFunction is ir.FunctionDeclaration ||
         localFunction is ir.FunctionExpression);
   }
 
+  VariableUse.instantiationTypeArgument(this.instantiation)
+      : this.kind = VariableUseKind.instantiationTypeArgument,
+        this.member = null,
+        this.localFunction = null,
+        this.invocation = null;
+
   static const VariableUse explicit =
       const VariableUse._simple(VariableUseKind.explicit);
 
@@ -512,7 +538,8 @@
       kind.hashCode * 11 +
       member.hashCode * 13 +
       localFunction.hashCode * 17 +
-      invocation.hashCode * 19;
+      invocation.hashCode * 19 +
+      instantiation.hashCode * 23;
 
   bool operator ==(other) {
     if (identical(this, other)) return true;
@@ -520,11 +547,13 @@
     return kind == other.kind &&
         member == other.member &&
         localFunction == other.localFunction &&
-        invocation == other.invocation;
+        invocation == other.invocation &&
+        instantiation == other.instantiation;
   }
 
   String toString() => 'VariableUse(kind=$kind,member=$member,'
-      'localFunction=$localFunction,invocation=$invocation)';
+      'localFunction=$localFunction,invocation=$invocation,'
+      'instantiation=$instantiation)';
 }
 
 class KernelScopeInfo {
@@ -1150,4 +1179,7 @@
   bool localFunctionNeedsSignature(ir.Node node);
 
   bool selectorNeedsTypeArguments(Selector selector);
+
+  bool instantiationNeedsTypeArguments(
+      DartType functionType, int typeArgumentCount);
 }
diff --git a/pkg/compiler/lib/src/js_model/closure_visitors.dart b/pkg/compiler/lib/src/js_model/closure_visitors.dart
index 5868aea..9c1dfbb 100644
--- a/pkg/compiler/lib/src/js_model/closure_visitors.dart
+++ b/pkg/compiler/lib/src/js_model/closure_visitors.dart
@@ -631,7 +631,8 @@
 
   @override
   visitInstantiation(ir.Instantiation node) {
-    visitChildrenInContext(node, VariableUse.explicit);
+    visitChildrenInContext(
+        node, new VariableUse.instantiationTypeArgument(node));
   }
 
   /// Returns true if the node is a field, or a constructor (factory or
diff --git a/pkg/compiler/lib/src/js_model/js_strategy.dart b/pkg/compiler/lib/src/js_model/js_strategy.dart
index d8a72c6..e1779e6 100644
--- a/pkg/compiler/lib/src/js_model/js_strategy.dart
+++ b/pkg/compiler/lib/src/js_model/js_strategy.dart
@@ -416,7 +416,6 @@
         map.toBackendFunctionSet(backendUsage.helperFunctionsUsed);
     Set<ClassEntity> helperClassesUsed =
         map.toBackendClassSet(backendUsage.helperClassesUsed);
-
     return new BackendUsageImpl(
         globalFunctionDependencies: globalFunctionDependencies,
         globalClassDependencies: globalClassDependencies,
@@ -572,7 +571,8 @@
         methodsNeedingTypeArguments,
         null,
         null,
-        selectorsNeedingTypeArguments);
+        selectorsNeedingTypeArguments,
+        rtiNeed.instantiationsNeedingTypeArguments);
   }
 
   /// Construct a closure class and set up the necessary class inference
@@ -829,12 +829,28 @@
 class TrivialClosureRtiNeed implements ClosureRtiNeed {
   const TrivialClosureRtiNeed();
 
+  @override
   bool localFunctionNeedsSignature(ir.Node node) => true;
+
+  @override
   bool classNeedsTypeArguments(ClassEntity cls) => true;
+
+  @override
   bool methodNeedsTypeArguments(FunctionEntity method) => true;
+
+  @override
   bool localFunctionNeedsTypeArguments(ir.Node node) => true;
+
+  @override
   bool selectorNeedsTypeArguments(Selector selector) => true;
+
+  @override
   bool methodNeedsSignature(MemberEntity method) => true;
+
+  @override
+  bool instantiationNeedsTypeArguments(
+          DartType functionType, int typeArgumentCount) =>
+      true;
 }
 
 class JsClosureRtiNeed implements ClosureRtiNeed {
@@ -849,6 +865,7 @@
       this.localFunctionsNodesNeedingTypeArguments,
       this.localFunctionsNodesNeedingSignature);
 
+  @override
   bool localFunctionNeedsSignature(ir.Node node) {
     assert(node is ir.FunctionDeclaration || node is ir.FunctionExpression);
     return backendUsage.isRuntimeTypeUsed
@@ -856,12 +873,15 @@
         : localFunctionsNodesNeedingSignature.contains(node);
   }
 
+  @override
   bool classNeedsTypeArguments(ClassEntity cls) =>
       rtiNeed.classNeedsTypeArguments(cls);
 
+  @override
   bool methodNeedsTypeArguments(FunctionEntity method) =>
       rtiNeed.methodNeedsTypeArguments(method);
 
+  @override
   bool localFunctionNeedsTypeArguments(ir.Node node) {
     assert(node is ir.FunctionDeclaration || node is ir.FunctionExpression);
     return backendUsage.isRuntimeTypeUsed
@@ -869,9 +889,16 @@
         : localFunctionsNodesNeedingTypeArguments.contains(node);
   }
 
+  @override
   bool selectorNeedsTypeArguments(Selector selector) =>
       rtiNeed.selectorNeedsTypeArguments(selector);
 
+  @override
   bool methodNeedsSignature(MemberEntity method) =>
       rtiNeed.methodNeedsSignature(method);
+
+  @override
+  bool instantiationNeedsTypeArguments(
+          DartType functionType, int typeArgumentCount) =>
+      rtiNeed.instantiationNeedsTypeArguments(functionType, typeArgumentCount);
 }
diff --git a/pkg/compiler/lib/src/kernel/element_map.dart b/pkg/compiler/lib/src/kernel/element_map.dart
index dc54118..128db95 100644
--- a/pkg/compiler/lib/src/kernel/element_map.dart
+++ b/pkg/compiler/lib/src/kernel/element_map.dart
@@ -123,6 +123,10 @@
 
   /// Returns the definition information for [cls].
   ClassDefinition getClassDefinition(covariant ClassEntity cls);
+
+  /// Returns the static type of [node].
+  // TODO(johnniwinther): This should be provided directly from kernel.
+  DartType getStaticType(ir.Expression node);
 }
 
 /// Interface that translates between Kernel IR nodes and entities used for
@@ -188,10 +192,6 @@
   /// Returns the definition information for [member].
   MemberDefinition getMemberDefinition(covariant MemberEntity member);
 
-  /// Returns the static type of [node].
-  // TODO(johnniwinther): This should be provided directly from kernel.
-  DartType getStaticType(ir.Expression node);
-
   /// Returns the element type of a async/sync*/async* function.
   DartType getFunctionAsyncOrSyncStarElementType(ir.FunctionNode functionNode);
 }
diff --git a/pkg/compiler/lib/src/kernel/element_map_impl.dart b/pkg/compiler/lib/src/kernel/element_map_impl.dart
index e566ff0..e66871d 100644
--- a/pkg/compiler/lib/src/kernel/element_map_impl.dart
+++ b/pkg/compiler/lib/src/kernel/element_map_impl.dart
@@ -81,6 +81,8 @@
   DartTypeConverter _typeConverter;
   KernelConstantEnvironment _constantEnvironment;
   _KernelDartTypes _types;
+  ir.TypeEnvironment _typeEnvironment;
+  bool _isStaticTypePrepared = false;
 
   /// Library environment. Used for fast lookup.
   ProgramEnv _env = new ProgramEnv();
@@ -682,6 +684,12 @@
     return data.getBound(this);
   }
 
+  DartType _getTypeVariableDefaultType(IndexedTypeVariable typeVariable) {
+    assert(checkFamily(typeVariable));
+    TypeVariableData data = _typeVariables.getData(typeVariable);
+    return data.getDefaultType(this);
+  }
+
   ClassEntity _getAppliedMixin(IndexedClass cls) {
     assert(checkFamily(cls));
     ClassData data = _classes.getData(cls);
@@ -834,6 +842,36 @@
     LibraryData data = _libraries.getData(_getLibrary(library));
     return data.imports[node];
   }
+
+  DartType getStaticType(ir.Expression node) {
+    if (!_isStaticTypePrepared) {
+      _isStaticTypePrepared = true;
+      try {
+        _typeEnvironment ??= new ir.TypeEnvironment(
+            new ir.CoreTypes(_env.mainComponent),
+            new ir.ClassHierarchy(_env.mainComponent),
+            strongMode: options.strongMode);
+      } catch (e) {}
+    }
+    if (_typeEnvironment == null) {
+      // The class hierarchy crashes on multiple inheritance. Use `dynamic`
+      // as static type.
+      return commonElements.dynamicType;
+    }
+    ir.TreeNode enclosingClass = node;
+    while (enclosingClass != null && enclosingClass is! ir.Class) {
+      enclosingClass = enclosingClass.parent;
+    }
+    try {
+      _typeEnvironment.thisType =
+          enclosingClass is ir.Class ? enclosingClass.thisType : null;
+      return getDartType(node.getStaticType(_typeEnvironment));
+    } catch (e) {
+      // The static type computation crashes on type errors. Use `dynamic`
+      // as static type.
+      return commonElements.dynamicType;
+    }
+  }
 }
 
 /// Mixin that implements the abstract methods in [KernelToElementMapBase].
@@ -1235,37 +1273,11 @@
         KElementCreatorMixin {
   native.BehaviorBuilder _nativeBehaviorBuilder;
   FrontendStrategy _frontendStrategy;
-  ir.TypeEnvironment _typeEnvironment;
-  bool _isStaticTypePrepared = false;
 
   KernelToElementMapForImpactImpl(DiagnosticReporter reporter,
       Environment environment, this._frontendStrategy, CompilerOptions options)
       : super(options, reporter, environment);
 
-  DartType getStaticType(ir.Expression node) {
-    if (!_isStaticTypePrepared) {
-      _isStaticTypePrepared = true;
-      try {
-        _typeEnvironment ??= new ir.TypeEnvironment(
-            new ir.CoreTypes(_env.mainComponent),
-            new ir.ClassHierarchy(_env.mainComponent),
-            strongMode: options.strongMode);
-      } catch (e) {}
-    }
-    if (_typeEnvironment == null) {
-      // The class hierarchy crashes on multiple inheritance. Use `dynamic`
-      // as static type.
-      return commonElements.dynamicType;
-    }
-    ir.TreeNode enclosingClass = node;
-    while (enclosingClass != null && enclosingClass is! ir.Class) {
-      enclosingClass = enclosingClass.parent;
-    }
-    _typeEnvironment.thisType =
-        enclosingClass is ir.Class ? enclosingClass.thisType : null;
-    return getDartType(node.getStaticType(_typeEnvironment));
-  }
-
   @override
   bool checkFamily(Entity entity) {
     assert(
@@ -1280,6 +1292,11 @@
     return super._getTypeVariableBound(typeVariable);
   }
 
+  DartType _getTypeVariableDefaultType(TypeVariableEntity typeVariable) {
+    if (typeVariable is KLocalTypeVariable) return typeVariable.defaultType;
+    return super._getTypeVariableDefaultType(typeVariable);
+  }
+
   @override
   void _forEachNestedClosure(
       MemberEntity member, void f(FunctionEntity closure)) {
@@ -1373,6 +1390,8 @@
       index = 0;
       for (ir.TypeParameter typeParameter in function.typeParameters) {
         typeVariables[index].bound = getDartType(typeParameter.bound);
+        typeVariables[index].defaultType =
+            getDartType(typeParameter.defaultType);
         index++;
       }
       localFunction.functionType = getFunctionType(function);
@@ -1488,6 +1507,11 @@
   }
 
   @override
+  DartType getTypeVariableDefaultType(TypeVariableEntity typeVariable) {
+    return elementMap._getTypeVariableDefaultType(typeVariable);
+  }
+
+  @override
   InterfaceType createInterfaceType(
       ClassEntity cls, List<DartType> typeArguments) {
     return new InterfaceType(cls, typeArguments);
diff --git a/pkg/compiler/lib/src/kernel/env.dart b/pkg/compiler/lib/src/kernel/env.dart
index dde76e85..dcef78f 100644
--- a/pkg/compiler/lib/src/kernel/env.dart
+++ b/pkg/compiler/lib/src/kernel/env.dart
@@ -1014,6 +1014,7 @@
 class TypeVariableData {
   final ir.TypeParameter node;
   DartType _bound;
+  DartType _defaultType;
 
   TypeVariableData(this.node);
 
@@ -1021,6 +1022,10 @@
     return _bound ??= elementMap.getDartType(node.bound);
   }
 
+  DartType getDefaultType(KernelToElementMap elementMap) {
+    return _defaultType ??= elementMap.getDartType(node.defaultType);
+  }
+
   TypeVariableData copy() {
     return new TypeVariableData(node);
   }
diff --git a/pkg/compiler/lib/src/kernel/front_end_adapter.dart b/pkg/compiler/lib/src/kernel/front_end_adapter.dart
index 2b00b61..808404d 100644
--- a/pkg/compiler/lib/src/kernel/front_end_adapter.dart
+++ b/pkg/compiler/lib/src/kernel/front_end_adapter.dart
@@ -96,9 +96,6 @@
     case fe.Severity.warning:
       reporter.reportWarningMessage(span, kind, {'text': message.message});
       break;
-    case fe.Severity.nit:
-      reporter.reportHintMessage(span, kind, {'text': message.message});
-      break;
     case fe.Severity.context:
       reporter.reportInfo(span, kind, {'text': message.message});
       break;
diff --git a/pkg/compiler/lib/src/kernel/kelements.dart b/pkg/compiler/lib/src/kernel/kelements.dart
index 3b18fbc..38d7dd6 100644
--- a/pkg/compiler/lib/src/kernel/kelements.dart
+++ b/pkg/compiler/lib/src/kernel/kelements.dart
@@ -293,6 +293,7 @@
   final String name;
   final int index;
   DartType bound;
+  DartType defaultType;
 
   KLocalTypeVariable(this.typeDeclaration, this.name, this.index);
 
diff --git a/pkg/compiler/lib/src/resolution/registry.dart b/pkg/compiler/lib/src/resolution/registry.dart
index 2d713f1..ecdf526 100644
--- a/pkg/compiler/lib/src/resolution/registry.dart
+++ b/pkg/compiler/lib/src/resolution/registry.dart
@@ -22,6 +22,7 @@
   Setlet<ConstantExpression> _constantLiterals;
   Setlet<dynamic> _nativeData;
   Setlet<ClassEntity> _seenClasses;
+  Set<GenericInstantiation> _genericInstantiations;
 
   ResolutionWorldImpactBuilder(this.name);
 
@@ -30,9 +31,7 @@
 
   void registerMapLiteral(MapLiteralUse mapLiteralUse) {
     assert(mapLiteralUse != null);
-    if (_mapLiterals == null) {
-      _mapLiterals = new Setlet<MapLiteralUse>();
-    }
+    _mapLiterals ??= new Setlet<MapLiteralUse>();
     _mapLiterals.add(mapLiteralUse);
   }
 
@@ -43,9 +42,7 @@
 
   void registerListLiteral(ListLiteralUse listLiteralUse) {
     assert(listLiteralUse != null);
-    if (_listLiterals == null) {
-      _listLiterals = new Setlet<ListLiteralUse>();
-    }
+    _listLiterals ??= new Setlet<ListLiteralUse>();
     _listLiterals.add(listLiteralUse);
   }
 
@@ -55,9 +52,7 @@
   }
 
   void registerConstSymbolName(String name) {
-    if (_constSymbolNames == null) {
-      _constSymbolNames = new Setlet<String>();
-    }
+    _constSymbolNames ??= new Setlet<String>();
     _constSymbolNames.add(name);
   }
 
@@ -67,9 +62,7 @@
   }
 
   void registerFeature(Feature feature) {
-    if (_features == null) {
-      _features = new EnumSet<Feature>();
-    }
+    _features ??= new EnumSet<Feature>();
     _features.add(feature);
   }
 
@@ -81,9 +74,7 @@
   }
 
   void registerConstantLiteral(ConstantExpression constant) {
-    if (_constantLiterals == null) {
-      _constantLiterals = new Setlet<ConstantExpression>();
-    }
+    _constantLiterals ??= new Setlet<ConstantExpression>();
     _constantLiterals.add(constant);
   }
 
@@ -95,9 +86,7 @@
 
   void registerNativeData(dynamic nativeData) {
     assert(nativeData != null);
-    if (_nativeData == null) {
-      _nativeData = new Setlet<dynamic>();
-    }
+    _nativeData ??= new Setlet<dynamic>();
     _nativeData.add(nativeData);
   }
 
@@ -107,9 +96,7 @@
   }
 
   void registerSeenClass(ClassEntity seenClass) {
-    if (_seenClasses == null) {
-      _seenClasses = new Setlet<ClassEntity>();
-    }
+    _seenClasses ??= new Setlet<ClassEntity>();
     _seenClasses.add(seenClass);
   }
 
@@ -118,6 +105,16 @@
     return _seenClasses ?? const <ClassEntity>[];
   }
 
+  void registerInstantiation(GenericInstantiation instantiation) {
+    _genericInstantiations ??= new Set<GenericInstantiation>();
+    _genericInstantiations.add(instantiation);
+  }
+
+  @override
+  Iterable<GenericInstantiation> get genericInstantiations {
+    return _genericInstantiations ?? const <GenericInstantiation>[];
+  }
+
   String toString() {
     StringBuffer sb = new StringBuffer();
     sb.write('_ResolutionWorldImpact($name)');
@@ -155,6 +152,12 @@
         sb.write('\n  $data');
       }
     }
+    if (_genericInstantiations != null) {
+      sb.write('\n instantiations:');
+      for (var data in _genericInstantiations) {
+        sb.write('\n  $data');
+      }
+    }
     return sb.toString();
   }
 }
diff --git a/pkg/compiler/lib/src/ssa/builder_kernel.dart b/pkg/compiler/lib/src/ssa/builder_kernel.dart
index 079f4c0..2ad67c8 100644
--- a/pkg/compiler/lib/src/ssa/builder_kernel.dart
+++ b/pkg/compiler/lib/src/ssa/builder_kernel.dart
@@ -35,6 +35,7 @@
 import '../types/abstract_value_domain.dart';
 import '../types/types.dart';
 import '../universe/call_structure.dart';
+import '../universe/feature.dart';
 import '../universe/selector.dart';
 import '../universe/side_effects.dart' show SideEffects;
 import '../universe/target_checks.dart' show TargetChecks;
@@ -4234,9 +4235,20 @@
     var arguments = <HInstruction>[];
     node.expression.accept(this);
     arguments.add(pop());
-    for (ir.DartType type in node.typeArguments) {
-      HInstruction instruction = typeBuilder.analyzeTypeArgument(
-          _elementMap.getDartType(type), sourceElement);
+    // TODO(johnniwinther): Use the static type of the expression.
+    bool typeArgumentsNeeded = rtiNeed.instantiationNeedsTypeArguments(
+        null, node.typeArguments.length);
+    List<DartType> typeArguments = node.typeArguments
+        .map((type) => typeArgumentsNeeded
+            ? _elementMap.getDartType(type)
+            : _commonElements.dynamicType)
+        .toList();
+    registry.registerGenericInstantiation(
+        new GenericInstantiation(null, typeArguments));
+    // TODO(johnniwinther): Can we avoid creating the instantiation object?
+    for (DartType type in typeArguments) {
+      HInstruction instruction =
+          typeBuilder.analyzeTypeArgument(type, sourceElement);
       arguments.add(instruction);
     }
     int typeArgumentCount = node.typeArguments.length;
@@ -5180,10 +5192,20 @@
       } else {
         assert(callStructure.typeArgumentCount == 0);
         // Pass type variable bounds as type arguments.
-        for (int i = 0; i < parameterStructure.typeParameters; i++) {
-          // TODO(johnniwinther): Pass type variable bounds.
-          compiledArguments[compiledArgumentIndex++] =
-              graph.addConstantNull(closedWorld);
+        for (TypeVariableType typeVariable in _elementMap.elementEnvironment
+            .getFunctionTypeVariables(function)) {
+          DartType bound = _elementMap.elementEnvironment
+              .getTypeVariableDefaultType(typeVariable.element);
+          if (bound.containsTypeVariables) {
+            // TODO(33422): Support type variables in default
+            // types. Temporarily using the "any" type (encoded as -2) to
+            // avoid failing on bounds checks.
+            compiledArguments[compiledArgumentIndex++] =
+                graph.addConstantInt(-2, closedWorld);
+          } else {
+            compiledArguments[compiledArgumentIndex++] =
+                typeBuilder.analyzeTypeArgument(bound, function);
+          }
         }
       }
     }
diff --git a/pkg/compiler/lib/src/ssa/kernel_impact.dart b/pkg/compiler/lib/src/ssa/kernel_impact.dart
index 2352143..0c3846e 100644
--- a/pkg/compiler/lib/src/ssa/kernel_impact.dart
+++ b/pkg/compiler/lib/src/ssa/kernel_impact.dart
@@ -680,7 +680,9 @@
   @override
   void visitInstantiation(ir.Instantiation node) {
     // TODO(johnniwinther): Track which arities are used in instantiation.
-    impactBuilder.registerFeature(Feature.GENERIC_INSTANTIATION);
+    impactBuilder.registerInstantiation(new GenericInstantiation(
+        elementMap.getStaticType(node.expression),
+        node.typeArguments.map(elementMap.getDartType).toList()));
     node.visitChildren(this);
   }
 
diff --git a/pkg/compiler/lib/src/universe/feature.dart b/pkg/compiler/lib/src/universe/feature.dart
index d63fa34..3d4f018 100644
--- a/pkg/compiler/lib/src/universe/feature.dart
+++ b/pkg/compiler/lib/src/universe/feature.dart
@@ -8,7 +8,8 @@
 /// compilation pipeline, for example during resolution.
 library compiler.universe.feature;
 
-import '../elements/types.dart' show InterfaceType;
+import '../elements/types.dart' show DartType, InterfaceType;
+import '../util/util.dart';
 
 /// A language feature that may be seen in the program.
 // TODO(johnniwinther): Should mirror usage be part of this?
@@ -43,9 +44,6 @@
   /// A field without an initializer.
   FIELD_WITHOUT_INITIALIZER,
 
-  /// A generic instantiation (application of type parameters).
-  GENERIC_INSTANTIATION,
-
   /// A field whose initialization is not a constant.
   LAZY_FIELD,
 
@@ -149,3 +147,33 @@
     return 'ListLiteralUse($type,isConstant:$isConstant,isEmpty:$isEmpty)';
   }
 }
+
+/// A generic instantiation of an expression of type [functionType] with the
+/// given [typeArguments].
+class GenericInstantiation {
+  /// The static type of the instantiated expression.
+  final DartType functionType;
+
+  /// The type arguments of the instantiation.
+  final List<DartType> typeArguments;
+
+  GenericInstantiation(this.functionType, this.typeArguments);
+
+  /// Short textual representation use for testing.
+  String get shortText => '<${typeArguments.join(',')}>';
+
+  int get hashCode =>
+      Hashing.listHash(typeArguments, Hashing.objectHash(functionType));
+
+  bool operator ==(other) {
+    if (identical(this, other)) return true;
+    if (other is! GenericInstantiation) return false;
+    return functionType == other.functionType &&
+        equalElements(typeArguments, other.typeArguments);
+  }
+
+  String toString() {
+    return 'GenericInstantiation(functionType:$functionType,'
+        'typeArguments:$typeArguments)';
+  }
+}
diff --git a/pkg/compiler/lib/src/universe/world_impact.dart b/pkg/compiler/lib/src/universe/world_impact.dart
index 3620b85..af5eaae 100644
--- a/pkg/compiler/lib/src/universe/world_impact.dart
+++ b/pkg/compiler/lib/src/universe/world_impact.dart
@@ -99,9 +99,7 @@
 
   void registerDynamicUse(DynamicUse dynamicUse) {
     assert(dynamicUse != null);
-    if (_dynamicUses == null) {
-      _dynamicUses = new Setlet<DynamicUse>();
-    }
+    _dynamicUses ??= new Setlet<DynamicUse>();
     _dynamicUses.add(dynamicUse);
   }
 
@@ -111,9 +109,7 @@
 
   void registerTypeUse(TypeUse typeUse) {
     assert(typeUse != null);
-    if (_typeUses == null) {
-      _typeUses = new Setlet<TypeUse>();
-    }
+    _typeUses ??= new Setlet<TypeUse>();
     _typeUses.add(typeUse);
   }
 
@@ -123,9 +119,7 @@
 
   void registerStaticUse(StaticUse staticUse) {
     assert(staticUse != null);
-    if (_staticUses == null) {
-      _staticUses = new Setlet<StaticUse>();
-    }
+    _staticUses ??= new Setlet<StaticUse>();
     _staticUses.add(staticUse);
   }
 
@@ -135,9 +129,7 @@
 
   void registerConstantUse(ConstantUse constantUse) {
     assert(constantUse != null);
-    if (_constantUses == null) {
-      _constantUses = new Setlet<ConstantUse>();
-    }
+    _constantUses ??= new Setlet<ConstantUse>();
     _constantUses.add(constantUse);
   }
 
diff --git a/pkg/compiler/lib/src/util/emptyset.dart b/pkg/compiler/lib/src/util/emptyset.dart
index 1fa3dba..796498b 100644
--- a/pkg/compiler/lib/src/util/emptyset.dart
+++ b/pkg/compiler/lib/src/util/emptyset.dart
@@ -10,10 +10,6 @@
   const ImmutableEmptySet();
 
   Set<R> cast<R>() => new ImmutableEmptySet<R>();
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   get iterator => const _EmptySetIterator();
   int get length => 0;
   bool get isEmpty => true;
diff --git a/pkg/compiler/lib/src/util/setlet.dart b/pkg/compiler/lib/src/util/setlet.dart
index 62ccde0..7335c77 100644
--- a/pkg/compiler/lib/src/util/setlet.dart
+++ b/pkg/compiler/lib/src/util/setlet.dart
@@ -30,10 +30,6 @@
   static Set<R> _newSet<R>() => new Setlet<R>();
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this, newSet: _newSet);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   Iterator<E> get iterator {
     if (_extra == null) {
       return new _SetletSingleIterator<E>(_contents);
diff --git a/pkg/dev_compiler/lib/src/analyzer/code_generator.dart b/pkg/dev_compiler/lib/src/analyzer/code_generator.dart
index 707576a..a4f0d88 100644
--- a/pkg/dev_compiler/lib/src/analyzer/code_generator.dart
+++ b/pkg/dev_compiler/lib/src/analyzer/code_generator.dart
@@ -868,17 +868,6 @@
     return _emitClassDeclaration(node, node.element as ClassElement, []);
   }
 
-  JS.Statement _emitJSType(Element e) {
-    var jsTypeName = getAnnotationName(e, isJSAnnotation);
-    if (jsTypeName == null || jsTypeName == e.name) return null;
-
-    // We export the JS type as if it was a Dart type. For example this allows
-    // `dom.InputElement` to actually be HTMLInputElement.
-    // TODO(jmesserly): if we had the JS name on the Element, we could just
-    // generate it correctly when we refer to it.
-    return js.statement('# = #;', [_emitTopLevelName(e), jsTypeName]);
-  }
-
   @override
   JS.Statement visitClassDeclaration(ClassDeclaration node) {
     return _emitClassDeclaration(node, node.element, node.members);
@@ -889,10 +878,6 @@
     // If this class is annotated with `@JS`, then there is nothing to emit.
     if (_hasJSInteropAnnotation(classElem)) return null;
 
-    // If this is a JavaScript type, emit it now and then exit.
-    var jsTypeDef = _emitJSType(classElem);
-    if (jsTypeDef != null) return jsTypeDef;
-
     // Generic classes will be defined inside a function that closes over the
     // type parameter. So we can use their local variable name directly.
     //
diff --git a/pkg/dev_compiler/lib/src/kernel/compiler.dart b/pkg/dev_compiler/lib/src/kernel/compiler.dart
index bf7fea8..6a21ffb 100644
--- a/pkg/dev_compiler/lib/src/kernel/compiler.dart
+++ b/pkg/dev_compiler/lib/src/kernel/compiler.dart
@@ -521,10 +521,6 @@
     // If this class is annotated with `@JS`, then there is nothing to emit.
     if (findAnnotation(c, isPublicJSAnnotation) != null) return null;
 
-    // If this is a JavaScript type, emit it now and then exit.
-    var jsTypeDef = _emitJSType(c);
-    if (jsTypeDef != null) return jsTypeDef;
-
     // Generic classes will be defined inside a function that closes over the
     // type parameter. So we can use their local variable name directly.
     //
@@ -1946,17 +1942,6 @@
         'registerExtension(#, #)', [js.string(jsPeerName), className]));
   }
 
-  JS.Statement _emitJSType(Class c) {
-    var jsTypeName = getAnnotationName(c, isJSAnnotation);
-    if (jsTypeName == null || jsTypeName == c.name) return null;
-
-    // We export the JS type as if it was a Dart type. For example this allows
-    // `dom.InputElement` to actually be HTMLInputElement.
-    // TODO(jmesserly): if we had the JS name on the Element, we could just
-    // generate it correctly when we refer to it.
-    return js.statement('# = #;', [_emitTopLevelName(c), jsTypeName]);
-  }
-
   void _emitTypedef(Typedef t) {
     var savedUri = _currentUri;
     _currentUri = t.fileUri;
diff --git a/pkg/dev_compiler/tool/input_sdk/patch/core_patch.dart b/pkg/dev_compiler/tool/input_sdk/patch/core_patch.dart
index 24d3768..13b9a49 100644
--- a/pkg/dev_compiler/tool/input_sdk/patch/core_patch.dart
+++ b/pkg/dev_compiler/tool/input_sdk/patch/core_patch.dart
@@ -2811,10 +2811,11 @@
   int convert(_BigIntImpl x, Uint16List resultDigits) {
     var digits;
     var used;
-    if (x._isNegative || x.compareTo(_modulus) >= 0) {
+    if (x._isNegative || x._absCompare(_modulus) >= 0) {
       var remainder = x._rem(_modulus);
-      if (x._isNegative && !remainder._isNegative && remainder._used > 0) {
-        remainder = _modulus - remainder;
+      if (x._isNegative && remainder._used > 0) {
+        assert(remainder._isNegative);
+        remainder += _modulus;
       }
       assert(!remainder._isNegative);
       used = remainder._used;
diff --git a/pkg/dev_compiler/tool/input_sdk/private/js_array.dart b/pkg/dev_compiler/tool/input_sdk/private/js_array.dart
index e392cfb..7dba1a8 100644
--- a/pkg/dev_compiler/tool/input_sdk/private/js_array.dart
+++ b/pkg/dev_compiler/tool/input_sdk/private/js_array.dart
@@ -69,10 +69,6 @@
   }
 
   List<R> cast<R>() => List.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   void add(E value) {
     checkGrowable('add');
     JS('void', r'#.push(#)', this, value);
diff --git a/pkg/front_end/lib/src/api_prototype/compiler_options.dart b/pkg/front_end/lib/src/api_prototype/compiler_options.dart
index c39a398..dd5a2e7 100644
--- a/pkg/front_end/lib/src/api_prototype/compiler_options.dart
+++ b/pkg/front_end/lib/src/api_prototype/compiler_options.dart
@@ -212,10 +212,4 @@
   ///
   /// Typically used by developers to debug internals of the compiler.
   bool throwOnWarningsForDebugging = false;
-
-  /// Whether the compiler should throw as soon as it encounters a
-  /// compilation nit.
-  ///
-  /// Typically used by developers to debug internals of the compiler.
-  bool throwOnNitsForDebugging = false;
 }
diff --git a/pkg/front_end/lib/src/base/processed_options.dart b/pkg/front_end/lib/src/base/processed_options.dart
index 08b6057..adb0ca4 100644
--- a/pkg/front_end/lib/src/base/processed_options.dart
+++ b/pkg/front_end/lib/src/base/processed_options.dart
@@ -170,8 +170,6 @@
 
   bool get throwOnWarningsForDebugging => _raw.throwOnWarningsForDebugging;
 
-  bool get throwOnNitsForDebugging => _raw.throwOnNitsForDebugging;
-
   /// The entry-points provided to the compiler.
   final List<Uri> inputs;
 
@@ -630,7 +628,6 @@
 
     sb.writeln('throwOnErrorsForDebugging: ${throwOnErrorsForDebugging}');
     sb.writeln('throwOnWarningsForDebugging: ${throwOnWarningsForDebugging}');
-    sb.writeln('throwOnNitsForDebugging: ${throwOnNitsForDebugging}');
     sb.writeln('exit on problem: ${setExitCodeOnProblem}');
     sb.writeln('Embed sources: ${embedSourceText}');
     sb.writeln('debugDump: ${debugDump}');
diff --git a/pkg/front_end/lib/src/fasta/builder/builtin_type_builder.dart b/pkg/front_end/lib/src/fasta/builder/builtin_type_builder.dart
index 40e9cdf..b362d75 100644
--- a/pkg/front_end/lib/src/fasta/builder/builtin_type_builder.dart
+++ b/pkg/front_end/lib/src/fasta/builder/builtin_type_builder.dart
@@ -6,7 +6,7 @@
 
 import 'builder.dart' show LibraryBuilder, TypeBuilder, TypeDeclarationBuilder;
 
-class BuiltinTypeBuilder<T extends TypeBuilder, R>
+abstract class BuiltinTypeBuilder<T extends TypeBuilder, R>
     extends TypeDeclarationBuilder<T, R> {
   final R type;
 
diff --git a/pkg/front_end/lib/src/fasta/builder/class_builder.dart b/pkg/front_end/lib/src/fasta/builder/class_builder.dart
index 1fc5bc5..a0d314c 100644
--- a/pkg/front_end/lib/src/fasta/builder/class_builder.dart
+++ b/pkg/front_end/lib/src/fasta/builder/class_builder.dart
@@ -225,7 +225,5 @@
     library.addProblem(message, charOffset, length, fileUri, context: context);
   }
 
-  int get typeVariablesCount;
-
   void prepareTopLevelInference() {}
 }
diff --git a/pkg/front_end/lib/src/fasta/builder/named_type_builder.dart b/pkg/front_end/lib/src/fasta/builder/named_type_builder.dart
index a302a71..f430cfc 100644
--- a/pkg/front_end/lib/src/fasta/builder/named_type_builder.dart
+++ b/pkg/front_end/lib/src/fasta/builder/named_type_builder.dart
@@ -4,7 +4,7 @@
 
 library fasta.named_type_builder;
 
-import '../fasta_codes.dart' show Message;
+import '../fasta_codes.dart' show Message, templateTypeArgumentMismatch;
 
 import 'builder.dart'
     show
@@ -53,6 +53,27 @@
     declaration = buildInvalidType(charOffset, fileUri);
   }
 
+  @override
+  void check(int charOffset, Uri fileUri) {
+    if (arguments != null &&
+        arguments.length != declaration.typeVariablesCount) {
+      declaration = buildInvalidType(
+          charOffset,
+          fileUri,
+          templateTypeArgumentMismatch.withArguments(
+              name, declaration.typeVariablesCount));
+    }
+  }
+
+  @override
+  void normalize(int charOffset, Uri fileUri) {
+    if (arguments != null &&
+        arguments.length != declaration.typeVariablesCount) {
+      // [arguments] will be normalized later if they are null.
+      arguments = null;
+    }
+  }
+
   String get debugName => "NamedTypeBuilder";
 
   StringBuffer printOn(StringBuffer buffer) {
diff --git a/pkg/front_end/lib/src/fasta/builder/type_builder.dart b/pkg/front_end/lib/src/fasta/builder/type_builder.dart
index 273009a..0b2d80a 100644
--- a/pkg/front_end/lib/src/fasta/builder/type_builder.dart
+++ b/pkg/front_end/lib/src/fasta/builder/type_builder.dart
@@ -12,6 +12,12 @@
 
   void resolveIn(Scope scope, int charOffset, Uri fileUri) {}
 
+  /// See `UnresolvedType.checkType`.
+  void check(int charOffset, Uri fileUri) {}
+
+  /// See `UnresolvedType.normalizeType`.
+  void normalize(int charOffset, Uri fileUri) {}
+
   void bind(TypeDeclarationBuilder builder) {}
 
   /// May return null, for example, for mixin applications.
diff --git a/pkg/front_end/lib/src/fasta/builder/type_declaration_builder.dart b/pkg/front_end/lib/src/fasta/builder/type_declaration_builder.dart
index c8ec2d5..a7a9771 100644
--- a/pkg/front_end/lib/src/fasta/builder/type_declaration_builder.dart
+++ b/pkg/front_end/lib/src/fasta/builder/type_declaration_builder.dart
@@ -31,11 +31,13 @@
 
   bool get isMixinApplication => false;
 
+  @override
+  String get fullNameForErrors => name;
+
+  int get typeVariablesCount => 0;
+
   R buildType(LibraryBuilder library, List<T> arguments);
 
   /// [arguments] have already been built.
   R buildTypesWithBuiltArguments(LibraryBuilder library, List<R> arguments);
-
-  @override
-  String get fullNameForErrors => name;
 }
diff --git a/pkg/front_end/lib/src/fasta/builder/unresolved_type.dart b/pkg/front_end/lib/src/fasta/builder/unresolved_type.dart
index afe2060..392e15e 100644
--- a/pkg/front_end/lib/src/fasta/builder/unresolved_type.dart
+++ b/pkg/front_end/lib/src/fasta/builder/unresolved_type.dart
@@ -4,16 +4,7 @@
 
 library fasta.unresolved_type;
 
-import '../fasta_codes.dart' show templateTypeArgumentMismatch;
-
-import 'builder.dart'
-    show
-        ClassBuilder,
-        FunctionTypeAliasBuilder,
-        NamedTypeBuilder,
-        Scope,
-        TypeBuilder,
-        TypeDeclarationBuilder;
+import 'builder.dart' show Scope, TypeBuilder;
 
 /// A wrapper around a type that is yet to be resolved.
 class UnresolvedType<T extends TypeBuilder> {
@@ -26,50 +17,8 @@
   void resolveIn(Scope scope) => builder.resolveIn(scope, charOffset, fileUri);
 
   /// Performs checks on the type after it's resolved.
-  void checkType() {
-    TypeBuilder resolvedType = builder;
-    if (resolvedType is NamedTypeBuilder) {
-      TypeDeclarationBuilder declaration = resolvedType.declaration;
-      if (declaration is ClassBuilder) {
-        if (resolvedType.arguments != null &&
-            resolvedType.arguments.length != declaration.typeVariablesCount) {
-          resolvedType.declaration = resolvedType.buildInvalidType(
-              charOffset,
-              fileUri,
-              templateTypeArgumentMismatch.withArguments(
-                  resolvedType.name, "${declaration.typeVariablesCount}"));
-        }
-      } else if (declaration is FunctionTypeAliasBuilder) {
-        if (resolvedType.arguments != null &&
-            resolvedType.arguments.length != declaration.typeVariablesCount) {
-          resolvedType.declaration = resolvedType.buildInvalidType(
-              charOffset,
-              fileUri,
-              templateTypeArgumentMismatch.withArguments(
-                  resolvedType.name, "${declaration.typeVariablesCount}"));
-        }
-      }
-    }
-  }
+  void checkType() => builder.check(charOffset, fileUri);
 
   /// Normalizes the type arguments in accordance with Dart 1 semantics.
-  void normalizeType() {
-    TypeBuilder resolvedType = builder;
-    if (resolvedType is NamedTypeBuilder) {
-      TypeDeclarationBuilder declaration = resolvedType.declaration;
-      if (declaration is ClassBuilder) {
-        if (resolvedType.arguments != null &&
-            resolvedType.arguments.length != declaration.typeVariablesCount) {
-          // [resolveType.arguments] will be normalized later if they are null.
-          resolvedType.arguments = null;
-        }
-      } else if (declaration is FunctionTypeAliasBuilder) {
-        if (resolvedType.arguments != null &&
-            resolvedType.arguments.length != declaration.typeVariablesCount) {
-          // [resolveType.arguments] will be normalized later if they are null.
-          resolvedType.arguments = null;
-        }
-      }
-    }
-  }
+  void normalizeType() => builder.normalize(charOffset, fileUri);
 }
diff --git a/pkg/front_end/lib/src/fasta/command_line_reporting.dart b/pkg/front_end/lib/src/fasta/command_line_reporting.dart
index fe28e9c..c7f93ee 100644
--- a/pkg/front_end/lib/src/fasta/command_line_reporting.dart
+++ b/pkg/front_end/lib/src/fasta/command_line_reporting.dart
@@ -12,7 +12,7 @@
 
 import 'package:kernel/ast.dart' show Location;
 
-import 'colors.dart' show cyan, green, magenta, red;
+import 'colors.dart' show green, magenta, red;
 
 import 'compiler_context.dart' show CompilerContext;
 
@@ -23,7 +23,7 @@
 
 import 'messages.dart' show getLocation, getSourceLine, isVerbose;
 
-import 'problems.dart' show unexpected;
+import 'problems.dart' show unhandled;
 
 import 'severity.dart' show Severity;
 
@@ -54,10 +54,6 @@
           text = red(text);
           break;
 
-        case Severity.nit:
-          text = cyan(text);
-          break;
-
         case Severity.warning:
           text = magenta(text);
           break;
@@ -67,7 +63,7 @@
           break;
 
         default:
-          return unexpected("$severity", "format", -1, null);
+          return unhandled("$severity", "format", -1, null);
       }
     }
 
@@ -95,7 +91,7 @@
         sourceLine = "\n$sourceLine\n$pointer";
       }
       String position =
-          location == null ? "" : ":${location.line}:${location.column}";
+          location == null ? ":1" : ":${location.line}:${location.column}";
       return "$path$position: $text$sourceLine";
     } else {
       return text;
@@ -117,14 +113,11 @@
     case Severity.context:
       return false;
 
-    case Severity.nit:
-      return !isVerbose;
-
     case Severity.warning:
       return hideWarnings;
 
     default:
-      return unexpected("$severity", "isHidden", -1, null);
+      return unhandled("$severity", "isHidden", -1, null);
   }
 }
 
@@ -138,9 +131,6 @@
     case Severity.internalProblem:
       return true;
 
-    case Severity.nit:
-      return CompilerContext.current.options.throwOnNitsForDebugging;
-
     case Severity.warning:
       return CompilerContext.current.options.throwOnWarningsForDebugging;
 
@@ -148,7 +138,7 @@
       return false;
 
     default:
-      return unexpected("$severity", "shouldThrowOn", -1, null);
+      return unhandled("$severity", "shouldThrowOn", -1, null);
   }
 }
 
@@ -161,9 +151,6 @@
     case Severity.internalProblem:
       return capitalized ? "Internal problem" : "internal problem";
 
-    case Severity.nit:
-      return capitalized ? "Nit" : "nit";
-
     case Severity.warning:
       return capitalized ? "Warning" : "warning";
 
@@ -171,7 +158,7 @@
       return capitalized ? "Context" : "context";
 
     default:
-      return unexpected("$severity", "severityName", -1, null);
+      return unhandled("$severity", "severityName", -1, null);
   }
 }
 
@@ -208,12 +195,14 @@
     case Severity.errorLegacyWarning:
       return CompilerContext.current.options.strongMode;
 
-    case Severity.nit:
     case Severity.warning:
     case Severity.context:
       return false;
+
+    case Severity.ignored:
+      break; // Fall-through to unhandled below.
   }
-  return unexpected("$severity", "isCompileTimeError", -1, null);
+  return unhandled("$severity", "isCompileTimeError", -1, null);
 }
 
 /// Report [message] unless [severity] is suppressed (see [isHidden]). Throws
diff --git a/pkg/front_end/lib/src/fasta/fasta_codes.dart b/pkg/front_end/lib/src/fasta/fasta_codes.dart
index 6e7dbc1..05f3cde 100644
--- a/pkg/front_end/lib/src/fasta/fasta_codes.dart
+++ b/pkg/front_end/lib/src/fasta/fasta_codes.dart
@@ -159,5 +159,4 @@
   return util.relativizeUri(uri, base: Uri.base);
 }
 
-typedef Message SummaryTemplate(
-    int count, int count2, String string, String string2, String string3);
+typedef SummaryTemplate = Message Function(int, int, num, num, num);
diff --git a/pkg/front_end/lib/src/fasta/fasta_codes_generated.dart b/pkg/front_end/lib/src/fasta/fasta_codes_generated.dart
index a9ab933..87a1acc 100644
--- a/pkg/front_end/lib/src/fasta/fasta_codes_generated.dart
+++ b/pkg/front_end/lib/src/fasta/fasta_codes_generated.dart
@@ -26,7 +26,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsAbstractClassInstantiation(String name) {
   return new Message(codeAbstractClassInstantiation,
-      message: """The class '$name' is abstract and can't be instantiated.""",
+      message: """The class '${name}' is abstract and can't be instantiated.""",
       arguments: {'name': name});
 }
 
@@ -72,7 +72,7 @@
 Message _withArgumentsAbstractRedirectedClassInstantiation(String name) {
   return new Message(codeAbstractRedirectedClassInstantiation,
       message:
-          """Factory redirects to class '$name', which is abstract and can't be instantiated.""",
+          """Factory redirects to class '${name}', which is abstract and can't be instantiated.""",
       arguments: {'name': name});
 }
 
@@ -92,7 +92,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsAccessError(String name) {
   return new Message(codeAccessError,
-      message: """Access error: '$name'.""", arguments: {'name': name});
+      message: """Access error: '${name}'.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -123,7 +123,7 @@
   String type2 = '$buffer';
 
   return new Message(codeAmbiguousSupertypes,
-      message: """'$name' can't implement both '$type' and '$type2'""",
+      message: """'${name}' can't implement both '${type}' and '${type2}'""",
       arguments: {'name': name, 'type': _type, 'type2': _type2});
 }
 
@@ -149,7 +149,7 @@
       "U+${codePoint.toRadixString(16).toUpperCase().padLeft(4, '0')}";
   return new Message(codeAsciiControlCharacter,
       message:
-          """The control character $unicode can only be used in strings and comments.""",
+          """The control character ${unicode} can only be used in strings and comments.""",
       arguments: {'codePoint': codePoint});
 }
 
@@ -245,7 +245,8 @@
 Message _withArgumentsBuiltInIdentifierAsType(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeBuiltInIdentifierAsType,
-      message: """The built-in identifier '$lexeme' can't be used as a type.""",
+      message:
+          """The built-in identifier '${lexeme}' can't be used as a type.""",
       tip: """Try correcting the name to match an existing type.""",
       arguments: {'token': token});
 }
@@ -268,7 +269,7 @@
 Message _withArgumentsBuiltInIdentifierInDeclaration(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeBuiltInIdentifierInDeclaration,
-      message: """Can't use '$lexeme' as a name here.""",
+      message: """Can't use '${lexeme}' as a name here.""",
       arguments: {'token': token});
 }
 
@@ -300,7 +301,7 @@
 Message _withArgumentsCandidateFoundIsDefaultConstructor(String name) {
   return new Message(codeCandidateFoundIsDefaultConstructor,
       message:
-          """The class '$name' has a constructor that takes no arguments.""",
+          """The class '${name}' has a constructor that takes no arguments.""",
       arguments: {'name': name});
 }
 
@@ -321,7 +322,7 @@
 Message _withArgumentsCannotReadPackagesFile(String string) {
   return new Message(codeCannotReadPackagesFile,
       message: """Unable to read '.packages' file:
-  $string.""", arguments: {'string': string});
+  ${string}.""", arguments: {'string': string});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -344,7 +345,7 @@
 Message _withArgumentsCannotReadSdkSpecification(String string) {
   return new Message(codeCannotReadSdkSpecification,
       message: """Unable to read the 'libraries.json' specification file:
-  $string.""", arguments: {'string': string});
+  ${string}.""", arguments: {'string': string});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -389,7 +390,7 @@
 Message _withArgumentsCantInferTypeDueToCircularity(String string) {
   return new Message(codeCantInferTypeDueToCircularity,
       message:
-          """Can't infer the type of '$string': circularity found during type inference.""",
+          """Can't infer the type of '${string}': circularity found during type inference.""",
       tip: """Specify the type explicitly.""",
       arguments: {'string': string});
 }
@@ -415,7 +416,7 @@
 Message _withArgumentsCantInferTypeDueToInconsistentOverrides(String string) {
   return new Message(codeCantInferTypeDueToInconsistentOverrides,
       message:
-          """Can't infer the type of '$string': overridden members must all have the same type.""",
+          """Can't infer the type of '${string}': overridden members must all have the same type.""",
       tip: """Specify the type explicitly.""",
       arguments: {'string': string});
 }
@@ -449,7 +450,7 @@
 
   return new Message(codeCantUseSuperBoundedTypeForInstanceCreation,
       message:
-          """Can't use a super-bounded type for instance creation. Got '$type'.""",
+          """Can't use a super-bounded type for instance creation. Got '${type}'.""",
       tip: """Specify a regular-bounded type instead of the super-bounded type. Note that the latter may be due to type inference.""",
       arguments: {'type': _type});
 }
@@ -502,7 +503,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConflictsWithConstructor(String name) {
   return new Message(codeConflictsWithConstructor,
-      message: """Conflicts with constructor '$name'.""",
+      message: """Conflicts with constructor '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -521,7 +522,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConflictsWithFactory(String name) {
   return new Message(codeConflictsWithFactory,
-      message: """Conflicts with factory '$name'.""",
+      message: """Conflicts with factory '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -540,7 +541,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConflictsWithMember(String name) {
   return new Message(codeConflictsWithMember,
-      message: """Conflicts with member '$name'.""", arguments: {'name': name});
+      message: """Conflicts with member '${name}'.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -559,7 +561,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConflictsWithMemberWarning(String name) {
   return new Message(codeConflictsWithMemberWarning,
-      message: """Conflicts with member '$name'.""", arguments: {'name': name});
+      message: """Conflicts with member '${name}'.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -577,7 +580,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConflictsWithSetter(String name) {
   return new Message(codeConflictsWithSetter,
-      message: """Conflicts with setter '$name'.""", arguments: {'name': name});
+      message: """Conflicts with setter '${name}'.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -596,7 +600,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConflictsWithSetterWarning(String name) {
   return new Message(codeConflictsWithSetterWarning,
-      message: """Conflicts with setter '$name'.""", arguments: {'name': name});
+      message: """Conflicts with setter '${name}'.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -615,7 +620,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConflictsWithTypeVariable(String name) {
   return new Message(codeConflictsWithTypeVariable,
-      message: """Conflicts with type variable '$name'.""",
+      message: """Conflicts with type variable '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -741,7 +746,7 @@
 Message _withArgumentsConstEvalDuplicateKey(Constant constant) {
   return new Message(codeConstEvalDuplicateKey,
       message:
-          """The key '$constant' conflicts with another existing key in the map.""",
+          """The key '${constant}' conflicts with another existing key in the map.""",
       arguments: {'constant': constant});
 }
 
@@ -772,7 +777,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConstEvalFailedAssertionWithMessage(String string) {
   return new Message(codeConstEvalFailedAssertionWithMessage,
-      message: """This assertion failed with message: $string""",
+      message: """This assertion failed with message: ${string}""",
       arguments: {'string': string});
 }
 
@@ -815,7 +820,7 @@
 
   return new Message(codeConstEvalInvalidBinaryOperandType,
       message:
-          """Binary operator '$string' on '$constant' requires operand of type '$type', but was of type '$type2'.""",
+          """Binary operator '${string}' on '${constant}' requires operand of type '${type}', but was of type '${type2}'.""",
       arguments: {
         'string': string,
         'constant': constant,
@@ -848,7 +853,7 @@
     String string, Constant constant) {
   return new Message(codeConstEvalInvalidMethodInvocation,
       message:
-          """The method '$string' can't be invoked on '$constant' within a const context.""",
+          """The method '${string}' can't be invoked on '${constant}' within a const context.""",
       arguments: {'string': string, 'constant': constant});
 }
 
@@ -873,7 +878,7 @@
 Message _withArgumentsConstEvalInvalidStaticInvocation(String name) {
   return new Message(codeConstEvalInvalidStaticInvocation,
       message:
-          """The invocation of '$name' is not allowed within a const context.""",
+          """The invocation of '${name}' is not allowed within a const context.""",
       arguments: {'name': name});
 }
 
@@ -899,7 +904,7 @@
     Constant constant) {
   return new Message(codeConstEvalInvalidStringInterpolationOperand,
       message:
-          """The '$constant' can't be used as part of a string interpolation within a const context, only values of type 'null', 'bool', 'int', 'double', or 'String' can be used.""",
+          """The '${constant}' can't be used as part of a string interpolation within a const context, only values of type 'null', 'bool', 'int', 'double', or 'String' can be used.""",
       arguments: {'constant': constant});
 }
 
@@ -937,7 +942,7 @@
 
   return new Message(codeConstEvalInvalidType,
       message:
-          """Expected constant '$constant' to be of type '$type', but was of type '$type2'.""",
+          """Expected constant '${constant}' to be of type '${type}', but was of type '${type2}'.""",
       arguments: {'constant': constant, 'type': _type, 'type2': _type2});
 }
 
@@ -961,7 +966,7 @@
 Message _withArgumentsConstEvalNonConstantLiteral(String string) {
   return new Message(codeConstEvalNonConstantLiteral,
       message:
-          """Can't have a non-constant $string literal within a const context.""",
+          """Can't have a non-constant ${string} literal within a const context.""",
       arguments: {'string': string});
 }
 
@@ -997,7 +1002,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConstFieldWithoutInitializer(String name) {
   return new Message(codeConstFieldWithoutInitializer,
-      message: """The const variable '$name' must be initialized.""",
+      message: """The const variable '${name}' must be initialized.""",
       tip:
           """Try adding an initializer ('= <expression>') to the declaration.""",
       arguments: {'name': name});
@@ -1029,7 +1034,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConstructorNotFound(String name) {
   return new Message(codeConstructorNotFound,
-      message: """Couldn't find constructor '$name'.""",
+      message: """Couldn't find constructor '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -1083,7 +1088,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsConstructorWithWrongNameContext(String name) {
   return new Message(codeConstructorWithWrongNameContext,
-      message: """The name of the enclosing class is '$name'.""",
+      message: """The name of the enclosing class is '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -1131,8 +1136,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsCouldNotParseUri(String string, String string2) {
   return new Message(codeCouldNotParseUri,
-      message: """Couldn't parse URI '$string':
-  $string2.""", arguments: {'string': string, 'string2': string2});
+      message: """Couldn't parse URI '${string}':
+  ${string2}.""", arguments: {'string': string, 'string2': string2});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -1200,7 +1205,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsCyclicClassHierarchy(String name, String string) {
   return new Message(codeCyclicClassHierarchy,
-      message: """'$name' is a supertype of itself via '$string'.""",
+      message: """'${name}' is a supertype of itself via '${string}'.""",
       arguments: {'name': name, 'string': string});
 }
 
@@ -1220,7 +1225,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsCyclicTypedef(String name) {
   return new Message(codeCyclicTypedef,
-      message: """The typedef '$name' has a reference to itself.""",
+      message: """The typedef '${name}' has a reference to itself.""",
       arguments: {'name': name});
 }
 
@@ -1278,7 +1283,7 @@
 Message _withArgumentsDeferredPrefixDuplicated(String name) {
   return new Message(codeDeferredPrefixDuplicated,
       message:
-          """Can't use the name '$name' for a deferred library, as the name is used elsewhere.""",
+          """Can't use the name '${name}' for a deferred library, as the name is used elsewhere.""",
       arguments: {'name': name});
 }
 
@@ -1298,7 +1303,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDeferredPrefixDuplicatedCause(String name) {
   return new Message(codeDeferredPrefixDuplicatedCause,
-      message: """'$name' is used here.""", arguments: {'name': name});
+      message: """'${name}' is used here.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -1332,47 +1337,50 @@
 
   return new Message(codeDeferredTypeAnnotation,
       message:
-          """The type '$type' is deferred loaded via prefix '$name' and can't be used as a type annotation.""",
-      tip: """Try removing 'deferred' from the import of '$name' or use a supertype of '$type' that isn't deferred.""",
+          """The type '${type}' is deferred loaded via prefix '${name}' and can't be used as a type annotation.""",
+      tip: """Try removing 'deferred' from the import of '${name}' or use a supertype of '${type}' that isn't deferred.""",
       arguments: {'type': _type, 'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const Template<
-        Message Function(int count, int count2, String string, String string2,
-            String string3)> templateDillOutlineSummary =
-    const Template<
-            Message Function(int count, int count2, String string,
-                String string2, String string3)>(
+        Message Function(
+            int count, int count2, num _num1, num _num2, num _num3)>
+    templateDillOutlineSummary = const Template<
+            Message Function(
+                int count, int count2, num _num1, num _num2, num _num3)>(
         messageTemplate:
-            r"""Indexed #count libraries (#count2 bytes) in #string, that is,
-#string2 bytes/ms, and
-#string3 ms/libraries.""",
+            r"""Indexed #count libraries (#count2 bytes) in #num1%.3ms, that is,
+#num2%12.3 bytes/ms, and
+#num3%12.3 ms/libraries.""",
         withArguments: _withArgumentsDillOutlineSummary);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const Code<
-    Message Function(int count, int count2, String string, String string2,
-        String string3)> codeDillOutlineSummary = const Code<
-    Message Function(
-        int count, int count2, String string, String string2, String string3)>(
+    Message Function(int count, int count2, num _num1, num _num2,
+        num _num3)> codeDillOutlineSummary = const Code<
+    Message Function(int count, int count2, num _num1, num _num2, num _num3)>(
   "DillOutlineSummary",
   templateDillOutlineSummary,
 );
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDillOutlineSummary(
-    int count, int count2, String string, String string2, String string3) {
+    int count, int count2, num _num1, num _num2, num _num3) {
+  String num1 = _num1.toStringAsFixed(3);
+  String num2 = _num2.toStringAsFixed(3).padLeft(12);
+  String num3 = _num3.toStringAsFixed(3).padLeft(12);
   return new Message(codeDillOutlineSummary,
-      message: """Indexed $count libraries ($count2 bytes) in $string, that is,
-$string2 bytes/ms, and
-$string3 ms/libraries.""",
+      message:
+          """Indexed ${count} libraries (${count2} bytes) in ${num1}ms, that is,
+${num2} bytes/ms, and
+${num3} ms/libraries.""",
       arguments: {
         'count': count,
         'count2': count2,
-        'string': string,
-        'string2': string2,
-        'string3': string3
+        'num1': _num1,
+        'num2': _num2,
+        'num3': _num3
       });
 }
 
@@ -1419,7 +1427,7 @@
 Message _withArgumentsDuplicateLabelInSwitchStatement(String name) {
   return new Message(codeDuplicateLabelInSwitchStatement,
       message:
-          """The label '$name' was already used in this switch statement.""",
+          """The label '${name}' was already used in this switch statement.""",
       tip: """Try choosing a different name for this label.""",
       arguments: {'name': name});
 }
@@ -1450,7 +1458,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedDefinition(String name) {
   return new Message(codeDuplicatedDefinition,
-      message: """Duplicated definition of '$name'.""",
+      message: """Duplicated definition of '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -1469,14 +1477,14 @@
         "DuplicatedExport", templateDuplicatedExport,
         analyzerCode: "AMBIGUOUS_EXPORT",
         dart2jsCode: "*ignored*",
-        severity: Severity.nit);
+        severity: Severity.ignored);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedExport(String name, Uri uri_, Uri uri2_) {
   String uri = relativizeUri(uri_);
   String uri2 = relativizeUri(uri2_);
   return new Message(codeDuplicatedExport,
-      message: """'$name' is exported from both '$uri' and '$uri2'.""",
+      message: """'${name}' is exported from both '${uri}' and '${uri2}'.""",
       arguments: {'name': name, 'uri': uri_, 'uri2': uri2_});
 }
 
@@ -1500,7 +1508,7 @@
   String uri = relativizeUri(uri_);
   String uri2 = relativizeUri(uri2_);
   return new Message(codeDuplicatedExportInType,
-      message: """'$name' is exported from both '$uri' and '$uri2'.""",
+      message: """'${name}' is exported from both '${uri}' and '${uri2}'.""",
       arguments: {'name': name, 'uri': uri_, 'uri2': uri2_});
 }
 
@@ -1517,14 +1525,14 @@
     codeDuplicatedImport =
     const Code<Message Function(String name, Uri uri_, Uri uri2_)>(
         "DuplicatedImport", templateDuplicatedImport,
-        severity: Severity.nit);
+        severity: Severity.ignored);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedImport(String name, Uri uri_, Uri uri2_) {
   String uri = relativizeUri(uri_);
   String uri2 = relativizeUri(uri2_);
   return new Message(codeDuplicatedImport,
-      message: """'$name' is imported from both '$uri' and '$uri2'.""",
+      message: """'${name}' is imported from both '${uri}' and '${uri2}'.""",
       arguments: {'name': name, 'uri': uri_, 'uri2': uri2_});
 }
 
@@ -1548,7 +1556,7 @@
   String uri = relativizeUri(uri_);
   String uri2 = relativizeUri(uri2_);
   return new Message(codeDuplicatedImportInType,
-      message: """'$name' is imported from both '$uri' and '$uri2'.""",
+      message: """'${name}' is imported from both '${uri}' and '${uri2}'.""",
       arguments: {'name': name, 'uri': uri_, 'uri2': uri2_});
 }
 
@@ -1570,7 +1578,7 @@
 Message _withArgumentsDuplicatedModifier(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeDuplicatedModifier,
-      message: """The modifier '$lexeme' was already specified.""",
+      message: """The modifier '${lexeme}' was already specified.""",
       tip: """Try removing all but one occurance of the modifier.""",
       arguments: {'token': token});
 }
@@ -1590,7 +1598,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedName(String name) {
   return new Message(codeDuplicatedName,
-      message: """'$name' is already declared in this scope.""",
+      message: """'${name}' is already declared in this scope.""",
       arguments: {'name': name});
 }
 
@@ -1609,7 +1617,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedNameCause(String name) {
   return new Message(codeDuplicatedNameCause,
-      message: """Previous declaration of '$name'.""",
+      message: """Previous declaration of '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -1635,7 +1643,7 @@
 Message _withArgumentsDuplicatedNamePreviouslyUsed(String name) {
   return new Message(codeDuplicatedNamePreviouslyUsed,
       message:
-          """Can't declare '$name' because it was already used in this scope.""",
+          """Can't declare '${name}' because it was already used in this scope.""",
       arguments: {'name': name});
 }
 
@@ -1657,7 +1665,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedNamePreviouslyUsedCause(String name) {
   return new Message(codeDuplicatedNamePreviouslyUsedCause,
-      message: """Previous use of '$name'.""", arguments: {'name': name});
+      message: """Previous use of '${name}'.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -1676,7 +1684,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedParameterName(String name) {
   return new Message(codeDuplicatedParameterName,
-      message: """Duplicated parameter name '$name'.""",
+      message: """Duplicated parameter name '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -1696,7 +1704,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsDuplicatedParameterNameCause(String name) {
   return new Message(codeDuplicatedParameterNameCause,
-      message: """Other parameter named '$name'.""", arguments: {'name': name});
+      message: """Other parameter named '${name}'.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -1750,7 +1759,7 @@
 Message _withArgumentsEnumConstantSameNameAsEnclosing(String name) {
   return new Message(codeEnumConstantSameNameAsEnclosing,
       message:
-          """Name of enum constant '$name' can't be the same as the enum's own name.""",
+          """Name of enum constant '${name}' can't be the same as the enum's own name.""",
       arguments: {'name': name});
 }
 
@@ -1844,7 +1853,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsExpectedButGot(String string) {
   return new Message(codeExpectedButGot,
-      message: """Expected '$string' before this.""",
+      message: """Expected '${string}' before this.""",
       arguments: {'string': string});
 }
 
@@ -1864,7 +1873,7 @@
 Message _withArgumentsExpectedClassBody(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedClassBody,
-      message: """Expected a class body, but got '$lexeme'.""",
+      message: """Expected a class body, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -1884,7 +1893,7 @@
 Message _withArgumentsExpectedClassBodyToSkip(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedClassBodyToSkip,
-      message: """Expected a class body, but got '$lexeme'.""",
+      message: """Expected a class body, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -1904,7 +1913,7 @@
 Message _withArgumentsExpectedClassMember(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedClassMember,
-      message: """Expected a class member, but got '$lexeme'.""",
+      message: """Expected a class member, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -1924,7 +1933,7 @@
 Message _withArgumentsExpectedDeclaration(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedDeclaration,
-      message: """Expected a declaration, but got '$lexeme'.""",
+      message: """Expected a declaration, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -1947,7 +1956,7 @@
 Message _withArgumentsExpectedEnumBody(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedEnumBody,
-      message: """Expected a enum body, but got '$lexeme'.""",
+      message: """Expected a enum body, but got '${lexeme}'.""",
       tip:
           """An enum definition must have a body with at least one constant name.""",
       arguments: {'token': token});
@@ -1969,7 +1978,7 @@
 Message _withArgumentsExpectedFunctionBody(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedFunctionBody,
-      message: """Expected a function body, but got '$lexeme'.""",
+      message: """Expected a function body, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -2001,7 +2010,7 @@
 Message _withArgumentsExpectedIdentifier(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedIdentifier,
-      message: """Expected an identifier, but got '$lexeme'.""",
+      message: """Expected an identifier, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -2049,7 +2058,7 @@
 Message _withArgumentsExpectedString(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedString,
-      message: """Expected a String, but got '$lexeme'.""",
+      message: """Expected a String, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -2068,7 +2077,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsExpectedToken(String string) {
   return new Message(codeExpectedToken,
-      message: """Expected to find '$string'.""",
+      message: """Expected to find '${string}'.""",
       arguments: {'string': string});
 }
 
@@ -2090,7 +2099,7 @@
 Message _withArgumentsExpectedType(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExpectedType,
-      message: """Expected a type, but got '$lexeme'.""",
+      message: """Expected a type, but got '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -2124,14 +2133,15 @@
     codeExportHidesExport =
     const Code<Message Function(String name, Uri uri_, Uri uri2_)>(
         "ExportHidesExport", templateExportHidesExport,
-        severity: Severity.nit);
+        severity: Severity.ignored);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsExportHidesExport(String name, Uri uri_, Uri uri2_) {
   String uri = relativizeUri(uri_);
   String uri2 = relativizeUri(uri2_);
   return new Message(codeExportHidesExport,
-      message: """Export of '$name' (from '$uri') hides export from '$uri2'.""",
+      message:
+          """Export of '${name}' (from '${uri}') hides export from '${uri2}'.""",
       arguments: {'name': name, 'uri': uri_, 'uri2': uri2_});
 }
 
@@ -2161,7 +2171,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsExtendingEnum(String name) {
   return new Message(codeExtendingEnum,
-      message: """'$name' is an enum and can't be extended or implemented.""",
+      message: """'${name}' is an enum and can't be extended or implemented.""",
       arguments: {'name': name});
 }
 
@@ -2182,7 +2192,7 @@
 Message _withArgumentsExtendingRestricted(String name) {
   return new Message(codeExtendingRestricted,
       message:
-          """'$name' is restricted and can't be extended or implemented.""",
+          """'${name}' is restricted and can't be extended or implemented.""",
       arguments: {'name': name});
 }
 
@@ -2327,8 +2337,8 @@
 Message _withArgumentsExtraneousModifier(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeExtraneousModifier,
-      message: """Can't have modifier '$lexeme' here.""",
-      tip: """Try removing '$lexeme'.""",
+      message: """Can't have modifier '${lexeme}' here.""",
+      tip: """Try removing '${lexeme}'.""",
       arguments: {'token': token});
 }
 
@@ -2368,7 +2378,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsFastaCLIArgumentRequired(String name) {
   return new Message(codeFastaCLIArgumentRequired,
-      message: """Expected value after '$name'.""", arguments: {'name': name});
+      message: """Expected value after '${name}'.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -2422,7 +2433,6 @@
 
   --fatal=errors
   --fatal=warnings
-  --fatal=nits
     Makes messages of the given kinds fatal, that is, immediately stop the
     compiler with a non-zero exit-code. In --verbose mode, also display an
     internal stack trace from the compiler. Multiple kinds can be separated by
@@ -2492,7 +2502,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsFinalFieldWithoutInitializer(String name) {
   return new Message(codeFinalFieldWithoutInitializer,
-      message: """The final variable '$name' must be initialized.""",
+      message: """The final variable '${name}' must be initialized.""",
       tip:
           """Try adding an initializer ('= <expression>') to the declaration.""",
       arguments: {'name': name});
@@ -2518,7 +2528,7 @@
 Message _withArgumentsFinalInstanceVariableAlreadyInitialized(String name) {
   return new Message(codeFinalInstanceVariableAlreadyInitialized,
       message:
-          """'$name' is a final instance variable that has already been initialized.""",
+          """'${name}' is a final instance variable that has already been initialized.""",
       arguments: {'name': name});
 }
 
@@ -2542,7 +2552,8 @@
 Message _withArgumentsFinalInstanceVariableAlreadyInitializedCause(
     String name) {
   return new Message(codeFinalInstanceVariableAlreadyInitializedCause,
-      message: """'$name' was initialized here.""", arguments: {'name': name});
+      message: """'${name}' was initialized here.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -2613,7 +2624,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsGetterNotFound(String name) {
   return new Message(codeGetterNotFound,
-      message: """Getter not found: '$name'.""", arguments: {'name': name});
+      message: """Getter not found: '${name}'.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -2654,7 +2665,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsIllegalMixin(String name) {
   return new Message(codeIllegalMixin,
-      message: """The type '$name' can't be mixed in.""",
+      message: """The type '${name}' can't be mixed in.""",
       arguments: {'name': name});
 }
 
@@ -2676,7 +2687,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsIllegalMixinDueToConstructors(String name) {
   return new Message(codeIllegalMixinDueToConstructors,
-      message: """Can't use '$name' as a mixin because it has constructors.""",
+      message:
+          """Can't use '${name}' as a mixin because it has constructors.""",
       arguments: {'name': name});
 }
 
@@ -2699,7 +2711,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsIllegalMixinDueToConstructorsCause(String name) {
   return new Message(codeIllegalMixinDueToConstructorsCause,
-      message: """This constructor prevents using '$name' as a mixin.""",
+      message: """This constructor prevents using '${name}' as a mixin.""",
       arguments: {'name': name});
 }
 
@@ -2751,7 +2763,7 @@
 
   return new Message(codeImplicitCallOfNonMethod,
       message:
-          """Can't invoke the type '$type' because its declaration of `.call` is not a method.""",
+          """Can't invoke the type '${type}' because its declaration of `.call` is not a method.""",
       tip: """Change .call to a method or explicitly invoke .call.""",
       arguments: {'type': _type});
 }
@@ -2779,14 +2791,15 @@
     codeImportHidesImport =
     const Code<Message Function(String name, Uri uri_, Uri uri2_)>(
         "ImportHidesImport", templateImportHidesImport,
-        severity: Severity.nit);
+        severity: Severity.ignored);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsImportHidesImport(String name, Uri uri_, Uri uri2_) {
   String uri = relativizeUri(uri_);
   String uri2 = relativizeUri(uri2_);
   return new Message(codeImportHidesImport,
-      message: """Import of '$name' (from '$uri') hides import from '$uri2'.""",
+      message:
+          """Import of '${name}' (from '${uri}') hides import from '${uri2}'.""",
       arguments: {'name': name, 'uri': uri_, 'uri2': uri2_});
 }
 
@@ -2870,8 +2883,8 @@
 
   return new Message(codeInitializingFormalTypeMismatch,
       message:
-          """The type of parameter '$name' ($type) is not a subtype of the corresponding field's type ($type2).""",
-      tip: """Try changing the type of parameter '$name' to a subtype of $type2.""",
+          """The type of parameter '${name}' (${type}) is not a subtype of the corresponding field's type (${type2}).""",
+      tip: """Try changing the type of parameter '${name}' to a subtype of ${type2}.""",
       arguments: {'name': name, 'type': _type, 'type2': _type2});
 }
 
@@ -2902,7 +2915,7 @@
 Message _withArgumentsInputFileNotFound(Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeInputFileNotFound,
-      message: """Input file not found: $uri.""", arguments: {'uri': uri_});
+      message: """Input file not found: ${uri}.""", arguments: {'uri': uri_});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -2928,7 +2941,7 @@
   String lexeme = token.lexeme;
   return new Message(codeIntegerLiteralIsOutOfRange,
       message:
-          """The integer literal $lexeme can't be represented in 64 bits.""",
+          """The integer literal ${lexeme} can't be represented in 64 bits.""",
       tip:
           """Try using the BigInt class if you need an integer larger than 9,223,372,036,854,775,807 or less than -9,223,372,036,854,775,808.""",
       arguments: {'token': token});
@@ -2974,7 +2987,7 @@
     String name, Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeInternalProblemConstructorNotFound,
-      message: """No constructor named '$name' in '$uri'.""",
+      message: """No constructor named '${name}' in '${uri}'.""",
       arguments: {'name': name, 'uri': uri_});
 }
 
@@ -2996,7 +3009,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemContextSeverity(String string) {
   return new Message(codeInternalProblemContextSeverity,
-      message: """Non-context message has context severity: $string""",
+      message: """Non-context message has context severity: ${string}""",
       arguments: {'string': string});
 }
 
@@ -3039,7 +3052,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemMissingSeverity(String string) {
   return new Message(codeInternalProblemMissingSeverity,
-      message: """Message code missing severity: $string""",
+      message: """Message code missing severity: ${string}""",
       arguments: {'string': string});
 }
 
@@ -3058,7 +3071,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemNotFound(String name) {
   return new Message(codeInternalProblemNotFound,
-      message: """Couldn't find '$name'.""", arguments: {'name': name});
+      message: """Couldn't find '${name}'.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3078,7 +3091,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemNotFoundIn(String name, String name2) {
   return new Message(codeInternalProblemNotFoundIn,
-      message: """Couldn't find '$name' in '$name2'.""",
+      message: """Couldn't find '${name}' in '${name2}'.""",
       arguments: {'name': name, 'name2': name2});
 }
 
@@ -3110,7 +3123,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemPrivateConstructorAccess(String name) {
   return new Message(codeInternalProblemPrivateConstructorAccess,
-      message: """Can't access private constructor '$name'.""",
+      message: """Can't access private constructor '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -3142,8 +3155,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemStackNotEmpty(String name, String string) {
   return new Message(codeInternalProblemStackNotEmpty,
-      message: """$name.stack isn't empty:
-  $string""", arguments: {'name': name, 'string': string});
+      message: """${name}.stack isn't empty:
+  ${string}""", arguments: {'name': name, 'string': string});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3164,7 +3177,8 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemSuperclassNotFound(String name) {
   return new Message(codeInternalProblemSuperclassNotFound,
-      message: """Superclass not found '$name'.""", arguments: {'name': name});
+      message: """Superclass not found '${name}'.""",
+      arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3184,7 +3198,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemUnexpected(String string, String string2) {
   return new Message(codeInternalProblemUnexpected,
-      message: """Expected '$string', but got '$string2'.""",
+      message: """Expected '${string}', but got '${string2}'.""",
       arguments: {'string': string, 'string2': string2});
 }
 
@@ -3205,7 +3219,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemUnhandled(String string, String string2) {
   return new Message(codeInternalProblemUnhandled,
-      message: """Unhandled $string in $string2.""",
+      message: """Unhandled ${string} in ${string2}.""",
       arguments: {'string': string, 'string2': string2});
 }
 
@@ -3225,7 +3239,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemUnimplemented(String string) {
   return new Message(codeInternalProblemUnimplemented,
-      message: """Unimplemented $string.""", arguments: {'string': string});
+      message: """Unimplemented ${string}.""", arguments: {'string': string});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3244,7 +3258,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsInternalProblemUnsupported(String name) {
   return new Message(codeInternalProblemUnsupported,
-      message: """Unsupported operation: '$name'.""",
+      message: """Unsupported operation: '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -3265,7 +3279,7 @@
 Message _withArgumentsInternalProblemUriMissingScheme(Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeInternalProblemUriMissingScheme,
-      message: """The URI '$uri' has no scheme.""", arguments: {'uri': uri_});
+      message: """The URI '${uri}' has no scheme.""", arguments: {'uri': uri_});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3286,7 +3300,7 @@
 Message _withArgumentsInternalVerificationError(String string) {
   return new Message(codeInternalVerificationError,
       message: """Verification of the generated program failed:
-$string""", arguments: {'string': string});
+${string}""", arguments: {'string': string});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3313,7 +3327,7 @@
 Message _withArgumentsInternalVisitorUnsupportedDefault(String string) {
   return new Message(codeInternalVisitorUnsupportedDefault,
       message:
-          """Trying to invoke a default visiting method of a visitor on a node $string.""",
+          """Trying to invoke a default visiting method of a visitor on a node ${string}.""",
       tip: """Try invoking one of the specialized 'visit' methods instead.""",
       arguments: {'string': string});
 }
@@ -3361,8 +3375,8 @@
 
   return new Message(codeInvalidAssignment,
       message:
-          """A value of type '$type' can't be assigned to a variable of type '$type2'.""",
-      tip: """Try changing the type of the left hand side, or casting the right hand side to '$type2'.""",
+          """A value of type '${type}' can't be assigned to a variable of type '${type2}'.""",
+      tip: """Try changing the type of the left hand side, or casting the right hand side to '${type2}'.""",
       arguments: {'type': _type, 'type2': _type2});
 }
 
@@ -3410,7 +3424,7 @@
 
   return new Message(codeInvalidCastFunctionExpr,
       message:
-          """The function expression type '$type' isn't of expected type '$type2'.""",
+          """The function expression type '${type}' isn't of expected type '${type2}'.""",
       tip: """Change the type of the function expression or the context in which it is used.""",
       arguments: {'type': _type, 'type2': _type2});
 }
@@ -3448,9 +3462,8 @@
 
   return new Message(codeInvalidCastLiteralList,
       message:
-          """The list literal type '$type' isn't of expected type '$type2'.""",
-      tip:
-          """Change the type of the list literal or the context in which it is used.""",
+          """The list literal type '${type}' isn't of expected type '${type2}'.""",
+      tip: """Change the type of the list literal or the context in which it is used.""",
       arguments: {'type': _type, 'type2': _type2});
 }
 
@@ -3487,9 +3500,8 @@
 
   return new Message(codeInvalidCastLiteralMap,
       message:
-          """The map literal type '$type' isn't of expected type '$type2'.""",
-      tip:
-          """Change the type of the map literal or the context in which it is used.""",
+          """The map literal type '${type}' isn't of expected type '${type2}'.""",
+      tip: """Change the type of the map literal or the context in which it is used.""",
       arguments: {'type': _type, 'type2': _type2});
 }
 
@@ -3527,7 +3539,7 @@
 
   return new Message(codeInvalidCastLocalFunction,
       message:
-          """The local function has type '$type' that isn't of expected type '$type2'.""",
+          """The local function has type '${type}' that isn't of expected type '${type2}'.""",
       tip: """Change the type of the function or the context in which it is used.""",
       arguments: {'type': _type, 'type2': _type2});
 }
@@ -3565,7 +3577,7 @@
 
   return new Message(codeInvalidCastNewExpr,
       message:
-          """The constructor returns type '$type' that isn't of expected type '$type2'.""",
+          """The constructor returns type '${type}' that isn't of expected type '${type2}'.""",
       tip: """Change the type of the object being constructed or the context in which it is used.""",
       arguments: {'type': _type, 'type2': _type2});
 }
@@ -3603,7 +3615,7 @@
 
   return new Message(codeInvalidCastStaticMethod,
       message:
-          """The static method has type '$type' that isn't of expected type '$type2'.""",
+          """The static method has type '${type}' that isn't of expected type '${type2}'.""",
       tip: """Change the type of the method or the context in which it is used.""",
       arguments: {'type': _type, 'type2': _type2});
 }
@@ -3642,7 +3654,7 @@
 
   return new Message(codeInvalidCastTopLevelFunction,
       message:
-          """The top level function has type '$type' that isn't of expected type '$type2'.""",
+          """The top level function has type '${type}' that isn't of expected type '${type2}'.""",
       tip: """Change the type of the function or the context in which it is used.""",
       arguments: {'type': _type, 'type2': _type2});
 }
@@ -3685,7 +3697,7 @@
 Message _withArgumentsInvalidOperator(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeInvalidOperator,
-      message: """The string '$lexeme' isn't a user-definable operator.""",
+      message: """The string '${lexeme}' isn't a user-definable operator.""",
       arguments: {'token': token});
 }
 
@@ -3707,8 +3719,8 @@
 Message _withArgumentsInvalidPackageUri(Uri uri_, String string) {
   String uri = relativizeUri(uri_);
   return new Message(codeInvalidPackageUri,
-      message: """Invalid package URI '$uri':
-  $string.""", arguments: {'uri': uri_, 'string': string});
+      message: """Invalid package URI '${uri}':
+  ${string}.""", arguments: {'uri': uri_, 'string': string});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3751,7 +3763,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsLabelNotFound(String name) {
   return new Message(codeLabelNotFound,
-      message: """Can't find label '$name'.""",
+      message: """Can't find label '${name}'.""",
       tip:
           """Try defining the label, or correcting the name to match an existing label.""",
       arguments: {'name': name});
@@ -3802,14 +3814,14 @@
 const Code<Message Function(Uri uri_)> codeLoadLibraryHidesMember =
     const Code<Message Function(Uri uri_)>(
         "LoadLibraryHidesMember", templateLoadLibraryHidesMember,
-        severity: Severity.nit);
+        severity: Severity.ignored);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsLoadLibraryHidesMember(Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeLoadLibraryHidesMember,
       message:
-          """The library '$uri' defines a top-level member named 'loadLibrary'. This member is hidden by the special member 'loadLibrary' that the language adds to support deferred loading.""",
+          """The library '${uri}' defines a top-level member named 'loadLibrary'. This member is hidden by the special member 'loadLibrary' that the language adds to support deferred loading.""",
       tip: """Try to rename or hide the member.""",
       arguments: {'uri': uri_});
 }
@@ -3837,13 +3849,13 @@
     codeLocalDefinitionHidesExport =
     const Code<Message Function(String name, Uri uri_)>(
         "LocalDefinitionHidesExport", templateLocalDefinitionHidesExport,
-        severity: Severity.nit);
+        severity: Severity.ignored);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsLocalDefinitionHidesExport(String name, Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeLocalDefinitionHidesExport,
-      message: """Local definition of '$name' hides export from '$uri'.""",
+      message: """Local definition of '${name}' hides export from '${uri}'.""",
       arguments: {'name': name, 'uri': uri_});
 }
 
@@ -3860,13 +3872,13 @@
     codeLocalDefinitionHidesImport =
     const Code<Message Function(String name, Uri uri_)>(
         "LocalDefinitionHidesImport", templateLocalDefinitionHidesImport,
-        severity: Severity.nit);
+        severity: Severity.ignored);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsLocalDefinitionHidesImport(String name, Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeLocalDefinitionHidesImport,
-      message: """Local definition of '$name' hides import from '$uri'.""",
+      message: """Local definition of '${name}' hides import from '${uri}'.""",
       arguments: {'name': name, 'uri': uri_});
 }
 
@@ -3904,7 +3916,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsMethodNotFound(String name) {
   return new Message(codeMethodNotFound,
-      message: """Method not found: '$name'.""", arguments: {'name': name});
+      message: """Method not found: '${name}'.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -3998,7 +4010,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsMissingImplementationCause(String name) {
   return new Message(codeMissingImplementationCause,
-      message: """'$name' is defined here.""", arguments: {'name': name});
+      message: """'${name}' is defined here.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -4034,8 +4046,8 @@
     String name, String string) {
   return new Message(codeMissingImplementationNotAbstract,
       message:
-          """The non-abstract class '$name' is missing implementations for these members:
-  $string.""",
+          """The non-abstract class '${name}' is missing implementations for these members:
+  ${string}.""",
       tip: """Try to either
  - provide an implementation,
  - inherit an implementation from a superclass or mixin,
@@ -4104,7 +4116,7 @@
   String uri = relativizeUri(uri_);
   return new Message(codeMissingPartOf,
       message:
-          """Can't use '$uri' as a part, because it has no 'part of' declaration.""",
+          """Can't use '${uri}' as a part, because it has no 'part of' declaration.""",
       arguments: {'uri': uri_});
 }
 
@@ -4161,8 +4173,8 @@
 
   return new Message(codeMixinInferenceNoMatchingClass,
       message:
-          """Type parameters could not be inferred for the mixin '$name' because
-'$name2' does not implement the mixin's supertype constraint '$type'.""",
+          """Type parameters could not be inferred for the mixin '${name}' because
+'${name2}' does not implement the mixin's supertype constraint '${type}'.""",
       arguments: {'name': name, 'name2': name2, 'type': _type});
 }
 
@@ -4255,7 +4267,7 @@
   return new Message(codeNoFormals,
       message: """A function should have formal parameters.""",
       tip:
-          """Try adding '()' after '$lexeme', or add 'get' before '$lexeme' to declare a getter.""",
+          """Try adding '()' after '${lexeme}', or add 'get' before '${lexeme}' to declare a getter.""",
       arguments: {'token': token});
 }
 
@@ -4274,7 +4286,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsNoSuchNamedParameter(String name) {
   return new Message(codeNoSuchNamedParameter,
-      message: """No named parameter with the name '$name'.""",
+      message: """No named parameter with the name '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -4313,7 +4325,7 @@
       "U+${codePoint.toRadixString(16).toUpperCase().padLeft(4, '0')}";
   return new Message(codeNonAsciiIdentifier,
       message:
-          """The non-ASCII character '$character' ($unicode) can't be used in identifiers, only in strings and comments.""",
+          """The non-ASCII character '${character}' (${unicode}) can't be used in identifiers, only in strings and comments.""",
       tip: """Try using an US-ASCII letter, a digit, '_' (an underscore), or '\$' (a dollar sign).""",
       arguments: {'character': character, 'codePoint': codePoint});
 }
@@ -4340,7 +4352,7 @@
       "U+${codePoint.toRadixString(16).toUpperCase().padLeft(4, '0')}";
   return new Message(codeNonAsciiWhitespace,
       message:
-          """The non-ASCII space character $unicode can only be used in strings and comments.""",
+          """The non-ASCII space character ${unicode} can only be used in strings and comments.""",
       arguments: {'codePoint': codePoint});
 }
 
@@ -4390,7 +4402,7 @@
 Message _withArgumentsNotAPrefixInTypeAnnotation(String name, String name2) {
   return new Message(codeNotAPrefixInTypeAnnotation,
       message:
-          """'$name.$name2' can't be used as a type because '$name' doesn't refer to an import prefix.""",
+          """'${name}.${name2}' can't be used as a type because '${name}' doesn't refer to an import prefix.""",
       arguments: {'name': name, 'name2': name2});
 }
 
@@ -4410,7 +4422,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsNotAType(String name) {
   return new Message(codeNotAType,
-      message: """'$name' isn't a type.""", arguments: {'name': name});
+      message: """'${name}' isn't a type.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -4452,7 +4464,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsOperatorMinusParameterMismatch(String name) {
   return new Message(codeOperatorMinusParameterMismatch,
-      message: """Operator '$name' should have zero or one parameter.""",
+      message: """Operator '${name}' should have zero or one parameter.""",
       tip:
           """With zero parameters, it has the syntactic form '-a', formally known as 'unary-'. With one parameter, it has the syntactic form 'a - b', formally known as '-'.""",
       arguments: {'name': name});
@@ -4475,7 +4487,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsOperatorParameterMismatch0(String name) {
   return new Message(codeOperatorParameterMismatch0,
-      message: """Operator '$name' shouldn't have any parameters.""",
+      message: """Operator '${name}' shouldn't have any parameters.""",
       arguments: {'name': name});
 }
 
@@ -4497,7 +4509,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsOperatorParameterMismatch1(String name) {
   return new Message(codeOperatorParameterMismatch1,
-      message: """Operator '$name' should have exactly one parameter.""",
+      message: """Operator '${name}' should have exactly one parameter.""",
       arguments: {'name': name});
 }
 
@@ -4519,7 +4531,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsOperatorParameterMismatch2(String name) {
   return new Message(codeOperatorParameterMismatch2,
-      message: """Operator '$name' should have exactly two parameters.""",
+      message: """Operator '${name}' should have exactly two parameters.""",
       arguments: {'name': name});
 }
 
@@ -4547,7 +4559,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsOverriddenMethodCause(String name) {
   return new Message(codeOverriddenMethodCause,
-      message: """This is the overriden method ('$name').""",
+      message: """This is the overriden method ('${name}').""",
       arguments: {'name': name});
 }
 
@@ -4573,7 +4585,7 @@
 Message _withArgumentsOverrideFewerNamedArguments(String name, String name2) {
   return new Message(codeOverrideFewerNamedArguments,
       message:
-          """The method '$name' has fewer named arguments than those of overridden method '$name2'.""",
+          """The method '${name}' has fewer named arguments than those of overridden method '${name2}'.""",
       arguments: {'name': name, 'name2': name2});
 }
 
@@ -4601,7 +4613,7 @@
     String name, String name2) {
   return new Message(codeOverrideFewerPositionalArguments,
       message:
-          """The method '$name' has fewer positional arguments than those of overridden method '$name2'.""",
+          """The method '${name}' has fewer positional arguments than those of overridden method '${name2}'.""",
       arguments: {'name': name, 'name2': name2});
 }
 
@@ -4630,7 +4642,7 @@
     String name, String name2, String name3) {
   return new Message(codeOverrideMismatchNamedParameter,
       message:
-          """The method '$name' doesn't have the named parameter '$name2' of overriden method '$name3'.""",
+          """The method '${name}' doesn't have the named parameter '${name2}' of overriden method '${name3}'.""",
       arguments: {'name': name, 'name2': name2, 'name3': name3});
 }
 
@@ -4656,7 +4668,7 @@
 Message _withArgumentsOverrideMoreRequiredArguments(String name, String name2) {
   return new Message(codeOverrideMoreRequiredArguments,
       message:
-          """The method '$name' has more required arguments than those of overridden method '$name2'.""",
+          """The method '${name}' has more required arguments than those of overridden method '${name2}'.""",
       arguments: {'name': name, 'name2': name2});
 }
 
@@ -4700,8 +4712,8 @@
 
   return new Message(codeOverrideTypeMismatchParameter,
       message:
-          """The parameter '$name' of the method '$name2' has type $type, which does not match the corresponding type in the overridden method ($type2).""",
-      tip: """Change to a supertype of $type2 (or, for a covariant parameter, a subtype).""",
+          """The parameter '${name}' of the method '${name2}' has type ${type}, which does not match the corresponding type in the overridden method (${type2}).""",
+      tip: """Change to a supertype of ${type2} (or, for a covariant parameter, a subtype).""",
       arguments: {
         'name': name,
         'name2': name2,
@@ -4746,8 +4758,8 @@
 
   return new Message(codeOverrideTypeMismatchReturnType,
       message:
-          """The return type of the method '$name' is $type, which does not match the return type of the overridden method ($type2).""",
-      tip: """Change to a subtype of $type2.""",
+          """The return type of the method '${name}' is ${type}, which does not match the return type of the overridden method (${type2}).""",
+      tip: """Change to a subtype of ${type2}.""",
       arguments: {'name': name, 'type': _type, 'type2': _type2});
 }
 
@@ -4773,7 +4785,7 @@
 Message _withArgumentsOverrideTypeVariablesMismatch(String name, String name2) {
   return new Message(codeOverrideTypeVariablesMismatch,
       message:
-          """Declared type variables of '$name' doesn't match those on overridden method '$name2'.""",
+          """Declared type variables of '${name}' doesn't match those on overridden method '${name2}'.""",
       arguments: {'name': name, 'name2': name2});
 }
 
@@ -4796,7 +4808,7 @@
 Message _withArgumentsPackageNotFound(String name, Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codePackageNotFound,
-      message: """Could not resolve the package '$name' in '$uri'.""",
+      message: """Could not resolve the package '${name}' in '${uri}'.""",
       arguments: {'name': name, 'uri': uri_});
 }
 
@@ -4825,7 +4837,7 @@
   String uri = relativizeUri(uri_);
   return new Message(codePartOfLibraryNameMismatch,
       message:
-          """Using '$uri' as part of '$name' but its 'part of' declaration says '$name2'.""",
+          """Using '${uri}' as part of '${name}' but its 'part of' declaration says '${name2}'.""",
       arguments: {'uri': uri_, 'name': name, 'name2': name2});
 }
 
@@ -4847,6 +4859,27 @@
     tip: r"""Try removing all but one of the part-of directives.""");
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
+const Code<Null> codePartOfTwoLibraries = messagePartOfTwoLibraries;
+
+// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
+const MessageCode messagePartOfTwoLibraries = const MessageCode(
+    "PartOfTwoLibraries",
+    severity: Severity.error,
+    message: r"""A file can't be part of more than one library.""",
+    tip:
+        r"""Try moving the shared declarations into the libraries, or into a new library.""");
+
+// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
+const Code<Null> codePartOfTwoLibrariesContext =
+    messagePartOfTwoLibrariesContext;
+
+// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
+const MessageCode messagePartOfTwoLibrariesContext = const MessageCode(
+    "PartOfTwoLibrariesContext",
+    severity: Severity.context,
+    message: r"""Used as a part in this library.""");
+
+// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const Template<
     Message Function(
         Uri uri_,
@@ -4872,7 +4905,7 @@
   String uri3 = relativizeUri(uri3_);
   return new Message(codePartOfUriMismatch,
       message:
-          """Using '$uri' as part of '$uri2' but its 'part of' declaration says '$uri3'.""",
+          """Using '${uri}' as part of '${uri2}' but its 'part of' declaration says '${uri3}'.""",
       arguments: {'uri': uri_, 'uri2': uri2_, 'uri3': uri3_});
 }
 
@@ -4903,7 +4936,7 @@
   String uri2 = relativizeUri(uri2_);
   return new Message(codePartOfUseUri,
       message:
-          """Using '$uri' as part of '$uri2' but its 'part of' declaration says '$name'.""",
+          """Using '${uri}' as part of '${uri2}' but its 'part of' declaration says '${name}'.""",
       tip: """Try changing the 'part of' declaration to use a relative file name.""",
       arguments: {'uri': uri_, 'uri2': uri2_, 'name': name});
 }
@@ -4925,7 +4958,7 @@
 Message _withArgumentsPartTwice(Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codePartTwice,
-      message: """Can't use '$uri' as a part more than once.""",
+      message: """Can't use '${uri}' as a part more than once.""",
       arguments: {'uri': uri_});
 }
 
@@ -4984,7 +5017,7 @@
 Message _withArgumentsPatchInjectionFailed(String name, Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codePatchInjectionFailed,
-      message: """Can't inject '$name' into '$uri'.""",
+      message: """Can't inject '${name}' into '${uri}'.""",
       tip: """Try adding '@patch'.""",
       arguments: {'name': name, 'uri': uri_});
 }
@@ -5097,7 +5130,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsRedirectionTargetNotFound(String name) {
   return new Message(codeRedirectionTargetNotFound,
-      message: """Redirection constructor target not found: '$name'""",
+      message: """Redirection constructor target not found: '${name}'""",
       arguments: {'name': name});
 }
 
@@ -5142,7 +5175,7 @@
 Message _withArgumentsSdkRootNotFound(Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeSdkRootNotFound,
-      message: """SDK root directory not found: $uri.""",
+      message: """SDK root directory not found: ${uri}.""",
       arguments: {'uri': uri_});
 }
 
@@ -5168,7 +5201,7 @@
 Message _withArgumentsSdkSpecificationNotFound(Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeSdkSpecificationNotFound,
-      message: """SDK libraries specification not found: $uri.""",
+      message: """SDK libraries specification not found: ${uri}.""",
       tip:
           """Normally, the specification is a file named 'libraries.json' in the Dart SDK install location.""",
       arguments: {'uri': uri_});
@@ -5191,7 +5224,7 @@
 Message _withArgumentsSdkSummaryNotFound(Uri uri_) {
   String uri = relativizeUri(uri_);
   return new Message(codeSdkSummaryNotFound,
-      message: """SDK summary not found: $uri.""", arguments: {'uri': uri_});
+      message: """SDK summary not found: ${uri}.""", arguments: {'uri': uri_});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -5209,7 +5242,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSetterNotFound(String name) {
   return new Message(codeSetterNotFound,
-      message: """Setter not found: '$name'.""", arguments: {'name': name});
+      message: """Setter not found: '${name}'.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -5237,42 +5270,44 @@
     Message Function(
         int count,
         int count2,
-        String string,
-        String string2,
-        String
-            string3)> templateSourceBodySummary = const Template<
-        Message Function(int count, int count2, String string, String string2,
-            String string3)>(
+        num _num1,
+        num _num2,
+        num
+            _num3)> templateSourceBodySummary = const Template<
+        Message Function(
+            int count, int count2, num _num1, num _num2, num _num3)>(
     messageTemplate:
-        r"""Built bodies for #count compilation units (#count2 bytes) in #string, that is,
-#string2 bytes/ms, and
-#string3 ms/compilation unit.""",
+        r"""Built bodies for #count compilation units (#count2 bytes) in #num1%.3ms, that is,
+#num2%12.3 bytes/ms, and
+#num3%12.3 ms/compilation unit.""",
     withArguments: _withArgumentsSourceBodySummary);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const Code<
-    Message Function(int count, int count2, String string, String string2,
-        String string3)> codeSourceBodySummary = const Code<
-    Message Function(
-        int count, int count2, String string, String string2, String string3)>(
+    Message Function(int count, int count2, num _num1, num _num2,
+        num _num3)> codeSourceBodySummary = const Code<
+    Message Function(int count, int count2, num _num1, num _num2, num _num3)>(
   "SourceBodySummary",
   templateSourceBodySummary,
 );
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSourceBodySummary(
-    int count, int count2, String string, String string2, String string3) {
+    int count, int count2, num _num1, num _num2, num _num3) {
+  String num1 = _num1.toStringAsFixed(3);
+  String num2 = _num2.toStringAsFixed(3).padLeft(12);
+  String num3 = _num3.toStringAsFixed(3).padLeft(12);
   return new Message(codeSourceBodySummary,
       message:
-          """Built bodies for $count compilation units ($count2 bytes) in $string, that is,
-$string2 bytes/ms, and
-$string3 ms/compilation unit.""",
+          """Built bodies for ${count} compilation units (${count2} bytes) in ${num1}ms, that is,
+${num2} bytes/ms, and
+${num3} ms/compilation unit.""",
       arguments: {
         'count': count,
         'count2': count2,
-        'string': string,
-        'string2': string2,
-        'string3': string3
+        'num1': _num1,
+        'num2': _num2,
+        'num3': _num3
       });
 }
 
@@ -5281,42 +5316,44 @@
     Message Function(
         int count,
         int count2,
-        String string,
-        String string2,
-        String
-            string3)> templateSourceOutlineSummary = const Template<
-        Message Function(int count, int count2, String string, String string2,
-            String string3)>(
+        num _num1,
+        num _num2,
+        num
+            _num3)> templateSourceOutlineSummary = const Template<
+        Message Function(
+            int count, int count2, num _num1, num _num2, num _num3)>(
     messageTemplate:
-        r"""Built outlines for #count compilation units (#count2 bytes) in #string, that is,
-#string2 bytes/ms, and
-#string3 ms/compilation unit.""",
+        r"""Built outlines for #count compilation units (#count2 bytes) in #num1%.3ms, that is,
+#num2%12.3 bytes/ms, and
+#num3%12.3 ms/compilation unit.""",
     withArguments: _withArgumentsSourceOutlineSummary);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const Code<
-    Message Function(int count, int count2, String string, String string2,
-        String string3)> codeSourceOutlineSummary = const Code<
-    Message Function(
-        int count, int count2, String string, String string2, String string3)>(
+    Message Function(int count, int count2, num _num1, num _num2,
+        num _num3)> codeSourceOutlineSummary = const Code<
+    Message Function(int count, int count2, num _num1, num _num2, num _num3)>(
   "SourceOutlineSummary",
   templateSourceOutlineSummary,
 );
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSourceOutlineSummary(
-    int count, int count2, String string, String string2, String string3) {
+    int count, int count2, num _num1, num _num2, num _num3) {
+  String num1 = _num1.toStringAsFixed(3);
+  String num2 = _num2.toStringAsFixed(3).padLeft(12);
+  String num3 = _num3.toStringAsFixed(3).padLeft(12);
   return new Message(codeSourceOutlineSummary,
       message:
-          """Built outlines for $count compilation units ($count2 bytes) in $string, that is,
-$string2 bytes/ms, and
-$string3 ms/compilation unit.""",
+          """Built outlines for ${count} compilation units (${count2} bytes) in ${num1}ms, that is,
+${num2} bytes/ms, and
+${num3} ms/compilation unit.""",
       arguments: {
         'count': count,
         'count2': count2,
-        'string': string,
-        'string2': string2,
-        'string3': string3
+        'num1': _num1,
+        'num2': _num2,
+        'num3': _num3
       });
 }
 
@@ -5325,7 +5362,9 @@
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const MessageCode messageStackOverflow = const MessageCode("StackOverflow",
-    dart2jsCode: "GENERIC", message: r"""Stack overflow.""");
+    analyzerCode: "STACK_OVERFLOW",
+    dart2jsCode: "GENERIC",
+    message: r"""Stack overflow.""");
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const Code<Null> codeStaticAfterConst = messageStaticAfterConst;
@@ -5433,7 +5472,7 @@
 Message _withArgumentsSuperclassHasNoDefaultConstructor(String name) {
   return new Message(codeSuperclassHasNoDefaultConstructor,
       message:
-          """The superclass, '$name', has no unnamed constructor that takes no arguments.""",
+          """The superclass, '${name}', has no unnamed constructor that takes no arguments.""",
       arguments: {'name': name});
 }
 
@@ -5452,7 +5491,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSuperclassHasNoGetter(String name) {
   return new Message(codeSuperclassHasNoGetter,
-      message: """Superclass has no getter named '$name'.""",
+      message: """Superclass has no getter named '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -5473,7 +5512,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSuperclassHasNoMethod(String name) {
   return new Message(codeSuperclassHasNoMethod,
-      message: """Superclass has no method named '$name'.""",
+      message: """Superclass has no method named '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -5492,7 +5531,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSuperclassHasNoSetter(String name) {
   return new Message(codeSuperclassHasNoSetter,
-      message: """Superclass has no setter named '$name'.""",
+      message: """Superclass has no setter named '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -5517,7 +5556,7 @@
 Message _withArgumentsSuperclassMethodArgumentMismatch(String name) {
   return new Message(codeSuperclassMethodArgumentMismatch,
       message:
-          """Superclass doesn't have a method named '$name' with matching arguments.""",
+          """Superclass doesn't have a method named '${name}' with matching arguments.""",
       arguments: {'name': name});
 }
 
@@ -5545,7 +5584,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSupertypeIsIllegal(String name) {
   return new Message(codeSupertypeIsIllegal,
-      message: """The type '$name' can't be used as supertype.""",
+      message: """The type '${name}' can't be used as supertype.""",
       arguments: {'name': name});
 }
 
@@ -5566,7 +5605,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsSupertypeIsTypeVariable(String name) {
   return new Message(codeSupertypeIsTypeVariable,
-      message: """The type variable '$name' can't be used as supertype.""",
+      message: """The type variable '${name}' can't be used as supertype.""",
       arguments: {'name': name});
 }
 
@@ -5623,7 +5662,7 @@
 Message _withArgumentsThisAccessInFieldInitializer(String name) {
   return new Message(codeThisAccessInFieldInitializer,
       message:
-          """Can't access 'this' in a field initializer to read '$name'.""",
+          """Can't access 'this' in a field initializer to read '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -5656,7 +5695,7 @@
 Message _withArgumentsTooFewArguments(int count, int count2) {
   return new Message(codeTooFewArguments,
       message:
-          """Too few positional arguments: $count required, $count2 given.""",
+          """Too few positional arguments: ${count} required, ${count2} given.""",
       arguments: {'count': count, 'count2': count2});
 }
 
@@ -5681,7 +5720,7 @@
 Message _withArgumentsTooManyArguments(int count, int count2) {
   return new Message(codeTooManyArguments,
       message:
-          """Too many positional arguments: $count allowed, $count2 given.""",
+          """Too many positional arguments: ${count} allowed, ${count2} given.""",
       arguments: {'count': count, 'count2': count2});
 }
 
@@ -5708,24 +5747,23 @@
     tip: r"""Try removing 'var.'""");
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
-const Template<Message Function(String name, String string)>
+const Template<Message Function(String name, int count)>
     templateTypeArgumentMismatch =
-    const Template<Message Function(String name, String string)>(
-        messageTemplate: r"""'#name' expects #string type arguments.""",
+    const Template<Message Function(String name, int count)>(
+        messageTemplate: r"""'#name' expects #count type arguments.""",
         withArguments: _withArgumentsTypeArgumentMismatch);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
-const Code<Message Function(String name, String string)>
-    codeTypeArgumentMismatch =
-    const Code<Message Function(String name, String string)>(
+const Code<Message Function(String name, int count)> codeTypeArgumentMismatch =
+    const Code<Message Function(String name, int count)>(
         "TypeArgumentMismatch", templateTypeArgumentMismatch,
         severity: Severity.errorLegacyWarning);
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
-Message _withArgumentsTypeArgumentMismatch(String name, String string) {
+Message _withArgumentsTypeArgumentMismatch(String name, int count) {
   return new Message(codeTypeArgumentMismatch,
-      message: """'$name' expects $string type arguments.""",
-      arguments: {'name': name, 'string': string});
+      message: """'${name}' expects ${count} type arguments.""",
+      arguments: {'name': name, 'count': count});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -5748,7 +5786,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsTypeArgumentsOnTypeVariable(String name) {
   return new Message(codeTypeArgumentsOnTypeVariable,
-      message: """Can't use type arguments with type variable '$name'.""",
+      message: """Can't use type arguments with type variable '${name}'.""",
       tip: """Try removing the type arguments.""",
       arguments: {'name': name});
 }
@@ -5768,7 +5806,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsTypeNotFound(String name) {
   return new Message(codeTypeNotFound,
-      message: """Type '$name' not found.""", arguments: {'name': name});
+      message: """Type '${name}' not found.""", arguments: {'name': name});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -5796,7 +5834,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsTypeVariableDuplicatedNameCause(String name) {
   return new Message(codeTypeVariableDuplicatedNameCause,
-      message: """The other type variable named '$name'.""",
+      message: """The other type variable named '${name}'.""",
       arguments: {'name': name});
 }
 
@@ -5867,9 +5905,10 @@
   String type = '$buffer';
 
   return new Message(codeUndefinedGetter,
-      message: """The getter '$name' isn't defined for the class '$type'.""",
+      message:
+          """The getter '${name}' isn't defined for the class '${type}'.""",
       tip:
-          """Try correcting the name to the name of an existing getter, or defining a getter or field named '$name'.""",
+          """Try correcting the name to the name of an existing getter, or defining a getter or field named '${name}'.""",
       arguments: {'name': name, 'type': _type});
 }
 
@@ -5900,9 +5939,10 @@
   String type = '$buffer';
 
   return new Message(codeUndefinedMethod,
-      message: """The method '$name' isn't defined for the class '$type'.""",
+      message:
+          """The method '${name}' isn't defined for the class '${type}'.""",
       tip:
-          """Try correcting the name to the name of an existing method, or defining a method named '$name'.""",
+          """Try correcting the name to the name of an existing method, or defining a method named '${name}'.""",
       arguments: {'name': name, 'type': _type});
 }
 
@@ -5933,9 +5973,10 @@
   String type = '$buffer';
 
   return new Message(codeUndefinedSetter,
-      message: """The setter '$name' isn't defined for the class '$type'.""",
+      message:
+          """The setter '${name}' isn't defined for the class '${type}'.""",
       tip:
-          """Try correcting the name to the name of an existing setter, or defining a setter or field named '$name'.""",
+          """Try correcting the name to the name of an existing setter, or defining a setter or field named '${name}'.""",
       arguments: {'name': name, 'type': _type});
 }
 
@@ -5966,7 +6007,8 @@
 Message _withArgumentsUnexpectedToken(Token token) {
   String lexeme = token.lexeme;
   return new Message(codeUnexpectedToken,
-      message: """Unexpected token '$lexeme'.""", arguments: {'token': token});
+      message: """Unexpected token '${lexeme}'.""",
+      arguments: {'token': token});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -5986,7 +6028,7 @@
 Message _withArgumentsUnmatchedToken(String string, Token token) {
   String lexeme = token.lexeme;
   return new Message(codeUnmatchedToken,
-      message: """Can't find '$string' to match '$lexeme'.""",
+      message: """Can't find '${string}' to match '${lexeme}'.""",
       arguments: {'string': string, 'token': token});
 }
 
@@ -6016,7 +6058,7 @@
     String name, String name2) {
   return new Message(codeUnresolvedPrefixInTypeAnnotation,
       message:
-          """'$name.$name2' can't be used as a type because '$name' isn't defined.""",
+          """'${name}.${name2}' can't be used as a type because '${name}' isn't defined.""",
       arguments: {'name': name, 'name2': name2});
 }
 
@@ -6035,7 +6077,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsUnspecified(String string) {
   return new Message(codeUnspecified,
-      message: """$string""", arguments: {'string': string});
+      message: """${string}""", arguments: {'string': string});
 }
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
@@ -6078,7 +6120,7 @@
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 Message _withArgumentsUnterminatedString(String string, String string2) {
   return new Message(codeUnterminatedString,
-      message: """String starting with $string must end with $string2.""",
+      message: """String starting with ${string} must end with ${string2}.""",
       arguments: {'string': string, 'string2': string2});
 }
 
@@ -6092,6 +6134,25 @@
     message: r"""Incomplete token.""");
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
+const Template<Message Function(String name)>
+    templateUseOfDeprecatedIdentifier =
+    const Template<Message Function(String name)>(
+        messageTemplate: r"""'#name' is deprecated.""",
+        withArguments: _withArgumentsUseOfDeprecatedIdentifier);
+
+// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
+const Code<Message Function(String name)> codeUseOfDeprecatedIdentifier =
+    const Code<Message Function(String name)>(
+        "UseOfDeprecatedIdentifier", templateUseOfDeprecatedIdentifier,
+        severity: Severity.ignored);
+
+// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
+Message _withArgumentsUseOfDeprecatedIdentifier(String name) {
+  return new Message(codeUseOfDeprecatedIdentifier,
+      message: """'${name}' is deprecated.""", arguments: {'name': name});
+}
+
+// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
 const Code<Null> codeVarReturnType = messageVarReturnType;
 
 // DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
diff --git a/pkg/front_end/lib/src/fasta/kernel/body_builder.dart b/pkg/front_end/lib/src/fasta/kernel/body_builder.dart
index c5612e8..e165386 100644
--- a/pkg/front_end/lib/src/fasta/kernel/body_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/body_builder.dart
@@ -234,35 +234,27 @@
         typePromoter = _typeInferrer?.typePromoter,
         super(enclosingScope);
 
-  BodyBuilder.withParents(
-      KernelFieldBuilder field,
-      KernelLibraryBuilder part,
-      KernelClassBuilder classBuilder,
-      ClassHierarchy hierarchy,
-      CoreTypes coreTypes,
-      TypeInferrer typeInferrer)
+  BodyBuilder.withParents(KernelFieldBuilder field, KernelLibraryBuilder part,
+      KernelClassBuilder classBuilder, TypeInferrer typeInferrer)
       : this(
             part,
             field,
             classBuilder?.scope ?? field.library.scope,
             null,
-            hierarchy,
-            coreTypes,
+            part.loader.hierarchy,
+            part.loader.coreTypes,
             classBuilder,
             field.isInstanceMember,
             field.fileUri,
             typeInferrer);
 
-  BodyBuilder.forField(KernelFieldBuilder field, ClassHierarchy hierarchy,
-      CoreTypes coreTypes, TypeInferrer typeInferrer)
+  BodyBuilder.forField(KernelFieldBuilder field, TypeInferrer typeInferrer)
       : this.withParents(
             field,
             field.parent is KernelClassBuilder
                 ? field.parent.parent
                 : field.parent,
             field.parent is KernelClassBuilder ? field.parent : null,
-            hierarchy,
-            coreTypes,
             typeInferrer);
 
   bool get hasParserError => recoverableErrors.isNotEmpty;
@@ -1265,7 +1257,7 @@
   @override
   void warnTypeArgumentsMismatch(String name, int expected, int charOffset) {
     addProblemErrorIfConst(
-        fasta.templateTypeArgumentMismatch.withArguments(name, '${expected}'),
+        fasta.templateTypeArgumentMismatch.withArguments(name, expected),
         charOffset,
         name.length);
   }
@@ -1360,6 +1352,10 @@
   void handleIdentifier(Token token, IdentifierContext context) {
     debugEvent("handleIdentifier");
     String name = token.lexeme;
+    if (name.startsWith("deprecated_")) {
+      addProblem(fasta.templateUseOfDeprecatedIdentifier.withArguments(name),
+          offsetForToken(token), lengthForToken(token));
+    }
     if (context.isScopeReference) {
       assert(!inInitializer ||
           this.scope == enclosingScope ||
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_body_builder.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_body_builder.dart
index 9b1651a..a1c93b1 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_body_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_body_builder.dart
@@ -40,9 +40,8 @@
       : super(library, member, scope, formalParameterScope, hierarchy,
             coreTypes, classBuilder, isInstanceMember, uri, typeInferrer);
 
-  KernelBodyBuilder.forField(ModifierBuilder member, ClassHierarchy hierarchy,
-      CoreTypes coreTypes, TypeInferrer typeInferrer)
-      : super.forField(member, hierarchy, coreTypes, typeInferrer);
+  KernelBodyBuilder.forField(ModifierBuilder member, TypeInferrer typeInferrer)
+      : super.forField(member, typeInferrer);
 
   @override
   void enterThenForTypePromotion(Expression condition) {
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_class_builder.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_class_builder.dart
index efd77e8..1cb2acc 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_class_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_class_builder.dart
@@ -148,7 +148,7 @@
       // That should be caught and reported as a compile-time error earlier.
       return unhandled(
           templateTypeArgumentMismatch
-              .withArguments(name, typeVariables.length.toString())
+              .withArguments(name, typeVariables.length)
               .message,
           "buildTypeArguments",
           -1,
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_field_builder.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_field_builder.dart
index 873d0f0..c74aa4b 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_field_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_field_builder.dart
@@ -87,17 +87,10 @@
   @override
   void prepareTopLevelInference() {
     if (!isEligibleForInference) return;
-    var typeInferenceEngine = library.loader.typeInferenceEngine;
-    var typeInferrer = typeInferenceEngine.createTopLevelTypeInferrer(
-        field.enclosingClass?.thisType, field);
+    var typeInferrer = library.loader.typeInferenceEngine
+        .createTopLevelTypeInferrer(field.enclosingClass?.thisType, field);
     if (hasInitializer) {
-      initializer = new KernelBodyBuilder.forField(
-              this,
-              // TODO(ahe): Why can't we use the loader's classHierarchy and
-              // coreTypes?
-              typeInferenceEngine.classHierarchy,
-              typeInferenceEngine.coreTypes,
-              typeInferrer)
+      initializer = new KernelBodyBuilder.forField(this, typeInferrer)
           .parseFieldInitializer(initializerTokenForInference);
     }
   }
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_function_type_alias_builder.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_function_type_alias_builder.dart
index b83c6d6..0210fc4 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_function_type_alias_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_function_type_alias_builder.dart
@@ -112,7 +112,7 @@
       // That should be caught and reported as a compile-time error earlier.
       return unhandled(
           templateTypeArgumentMismatch
-              .withArguments(name, typeVariables.length.toString())
+              .withArguments(name, typeVariables.length)
               .message,
           "buildTypeArguments",
           -1,
diff --git a/pkg/front_end/lib/src/fasta/kernel/kernel_library_builder.dart b/pkg/front_end/lib/src/fasta/kernel/kernel_library_builder.dart
index b2905ca..1e5c95a 100644
--- a/pkg/front_end/lib/src/fasta/kernel/kernel_library_builder.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/kernel_library_builder.dart
@@ -6,7 +6,26 @@
 
 import 'dart:convert' show jsonEncode;
 
-import 'package:kernel/ast.dart';
+import 'package:kernel/ast.dart'
+    show
+        Arguments,
+        Class,
+        ConstructorInvocation,
+        DartType,
+        Expression,
+        Field,
+        Library,
+        LibraryDependency,
+        LibraryPart,
+        Member,
+        Name,
+        Procedure,
+        ProcedureKind,
+        StaticInvocation,
+        StringLiteral,
+        TreeNode,
+        Typedef,
+        VoidType;
 
 import '../../scanner/token.dart' show Token;
 
diff --git a/pkg/front_end/lib/src/fasta/kernel/metadata_collector.dart b/pkg/front_end/lib/src/fasta/kernel/metadata_collector.dart
index 2b73d92..6a15522 100644
--- a/pkg/front_end/lib/src/fasta/kernel/metadata_collector.dart
+++ b/pkg/front_end/lib/src/fasta/kernel/metadata_collector.dart
@@ -2,7 +2,7 @@
 // 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 'package:kernel/kernel.dart';
+import 'package:kernel/kernel.dart' show Member, MetadataRepository, NamedNode;
 
 /// The collector to add target specific metadata to.
 abstract class MetadataCollector {
diff --git a/pkg/front_end/lib/src/fasta/loader.dart b/pkg/front_end/lib/src/fasta/loader.dart
index d2e21c5..b86ce27 100644
--- a/pkg/front_end/lib/src/fasta/loader.dart
+++ b/pkg/front_end/lib/src/fasta/loader.dart
@@ -26,6 +26,8 @@
 
 import 'problems.dart' show internalProblem;
 
+import 'rewrite_severity.dart' show rewriteSeverity;
+
 import 'severity.dart' show Severity;
 
 import 'target_implementation.dart' show TargetImplementation;
@@ -185,11 +187,7 @@
       });
       double ms = elapsed.inMicroseconds / Duration.microsecondsPerMillisecond;
       Message message = template.withArguments(
-          libraryCount,
-          byteCount,
-          "${format(ms, 3, 0)}ms",
-          format(byteCount / ms, 3, 12),
-          format(ms / libraryCount, 3, 12));
+          libraryCount, byteCount, ms, byteCount / ms, ms / libraryCount);
       print("$sinceStart: ${message.message}");
     });
   }
@@ -241,6 +239,8 @@
   bool addMessage(Message message, int charOffset, int length, Uri fileUri,
       Severity severity,
       {bool wasHandled: false, List<LocatedMessage> context}) {
+    severity = rewriteSeverity(severity, message.code, fileUri);
+    if (severity == Severity.ignored) return false;
     String trace = """
 message: ${message.message}
 charOffset: $charOffset
@@ -283,7 +283,3 @@
       int length, Uri fileUri,
       {List<LocatedMessage> context}) {}
 }
-
-String format(double d, int fractionDigits, int width) {
-  return d.toStringAsFixed(fractionDigits).padLeft(width);
-}
diff --git a/pkg/front_end/lib/src/fasta/parser/parser.dart b/pkg/front_end/lib/src/fasta/parser/parser.dart
index e4e0063..0501d8b 100644
--- a/pkg/front_end/lib/src/fasta/parser/parser.dart
+++ b/pkg/front_end/lib/src/fasta/parser/parser.dart
@@ -10,7 +10,7 @@
 
 import '../scanner.dart' show ErrorToken, Token;
 
-import '../scanner/recover.dart' show closeBraceFor, skipToEof;
+import '../scanner/recover.dart' show skipToEof;
 
 import '../../scanner/token.dart'
     show
@@ -49,8 +49,6 @@
         STRING_INTERPOLATION_TOKEN,
         STRING_TOKEN;
 
-import '../scanner/characters.dart' show $CLOSE_CURLY_BRACKET;
-
 import '../util/link.dart' show Link;
 
 import 'assert.dart' show Assert;
@@ -96,7 +94,7 @@
         noType,
         noTypeParamOrArg;
 
-import 'util.dart' show findNonSyntheticToken, optional;
+import 'util.dart' show findNonSyntheticToken, isOneOf, optional;
 
 /// An event generating parser of Dart programs. This parser expects all tokens
 /// in a linked list (aka a token stream).
@@ -1585,13 +1583,8 @@
   }
 
   Token skipBlock(Token token) {
-    token = ensureBlock(token, null);
-    Token closeBrace = token.endGroup;
-    if (closeBrace == null ||
-        !identical(closeBrace.kind, $CLOSE_CURLY_BRACKET)) {
-      return reportUnmatchedToken(token).next;
-    }
-    return closeBrace;
+    // The scanner ensures that `{` always has a closing `}`.
+    return ensureBlock(token, null).endGroup;
   }
 
   /// ```
@@ -2848,10 +2841,6 @@
     return token;
   }
 
-  Token expectSemicolon(Token token) {
-    return expect(';', token);
-  }
-
   Token parseNativeClause(Token token) {
     Token nativeToken = token = token.next;
     assert(optional('native', nativeToken));
@@ -2867,17 +2856,8 @@
   }
 
   Token skipClassBody(Token token) {
-    Token previousToken = token;
-    token = token.next;
-    if (!optional('{', token)) {
-      token = ensureBlock(previousToken, fasta.templateExpectedClassBody);
-    }
-    Token closeBrace = token.endGroup;
-    if (closeBrace == null ||
-        !identical(closeBrace.kind, $CLOSE_CURLY_BRACKET)) {
-      return reportUnmatchedToken(token).next;
-    }
-    return closeBrace;
+    // The scanner ensures that `{` always has a closing `}`.
+    return ensureBlock(token, fasta.templateExpectedClassBody);
   }
 
   /// ```
@@ -3820,13 +3800,33 @@
       // This happens in degenerate programs, for example, with a lot of nested
       // list literals. This is provoked by, for example, the language test
       // deep_nesting1_negative_test.
-      return reportUnmatchedToken(token.next);
+      Token next = token.next;
+      reportRecoverableError(next, fasta.messageStackOverflow);
+
+      // Recovery
+      Token endGroup = next.endGroup;
+      if (endGroup != null) {
+        while (!next.isEof && !identical(next, endGroup)) {
+          token = next;
+          next = token.next;
+        }
+      } else {
+        while (!isOneOf(next, const [')', ']', '}', ';'])) {
+          token = next;
+          next = token.next;
+        }
+      }
+      if (!token.isEof) {
+        token = rewriter.insertSyntheticIdentifier(token);
+        listener.handleIdentifier(token, IdentifierContext.expression);
+      }
+    } else {
+      token = optional('throw', token.next)
+          ? parseThrowExpression(token, true)
+          : parsePrecedenceExpression(token, ASSIGNMENT_PRECEDENCE, true);
     }
-    Token result = optional('throw', token.next)
-        ? parseThrowExpression(token, true)
-        : parsePrecedenceExpression(token, ASSIGNMENT_PRECEDENCE, true);
     expressionDepth--;
-    return result;
+    return token;
   }
 
   Token parseExpressionWithoutCascade(Token token) {
@@ -6090,13 +6090,6 @@
     return next;
   }
 
-  Token reportUnmatchedToken(BeginToken token) {
-    return reportUnrecoverableError(
-        token,
-        fasta.templateUnmatchedToken
-            .withArguments(closeBraceFor(token.lexeme), token));
-  }
-
   Token reportUnexpectedToken(Token token) {
     return reportUnrecoverableErrorWithToken(
         token, fasta.templateUnexpectedToken);
diff --git a/pkg/front_end/lib/src/fasta/rewrite_severity.dart b/pkg/front_end/lib/src/fasta/rewrite_severity.dart
new file mode 100644
index 0000000..5238c7d
--- /dev/null
+++ b/pkg/front_end/lib/src/fasta/rewrite_severity.dart
@@ -0,0 +1,43 @@
+// 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.
+
+import 'severity.dart' show Severity;
+
+import 'messages.dart' as msg;
+
+Severity rewriteSeverity(
+    Severity severity, msg.Code<Object> code, Uri fileUri) {
+  if (severity == Severity.ignored &&
+      fileUri.path.contains("/pkg/front_end/lib/src/fasta/")) {
+    String path = fileUri.path;
+    if (code == msg.codeUseOfDeprecatedIdentifier) {
+      // TODO(ahe): Remove the exceptions below.
+      // We plan to remove all uses of deprecated identifiers from Fasta. The
+      // strategy is to remove files from the list below one by one. To get
+      // started on cleaning up a given file, simply remove it from the list
+      // below and compile Fasta with itself to get a list of remaining call
+      // sites.
+      if (path.endsWith("/command_line_reporting.dart")) return severity;
+      if (path.endsWith("/deprecated_problems.dart")) return severity;
+      if (path.endsWith("/kernel/body_builder.dart")) return severity;
+      if (path.endsWith("/kernel/expression_generator.dart")) return severity;
+      if (path.endsWith("/kernel/kernel_expression_generator.dart"))
+        return severity;
+      if (path.endsWith("/kernel/kernel_expression_generator_impl.dart"))
+        return severity;
+      if (path.endsWith("/kernel/kernel_procedure_builder.dart"))
+        return severity;
+      if (path.endsWith("/kernel/kernel_target.dart")) return severity;
+      if (path.endsWith("/kernel/kernel_type_variable_builder.dart"))
+        return severity;
+      if (path.endsWith("/quote.dart")) return severity;
+      if (path.endsWith("/source/diet_listener.dart")) return severity;
+      if (path.endsWith("/source/source_library_builder.dart")) return severity;
+      if (path.endsWith("/source/source_loader.dart")) return severity;
+      if (path.endsWith("/source/stack_listener.dart")) return severity;
+    }
+    return Severity.error;
+  }
+  return severity;
+}
diff --git a/pkg/front_end/lib/src/fasta/severity.dart b/pkg/front_end/lib/src/fasta/severity.dart
index fb1fb5a..9a29a74 100644
--- a/pkg/front_end/lib/src/fasta/severity.dart
+++ b/pkg/front_end/lib/src/fasta/severity.dart
@@ -8,8 +8,8 @@
   context,
   error,
   errorLegacyWarning,
+  ignored,
   internalProblem,
-  nit,
   warning,
 }
 
@@ -17,8 +17,8 @@
   'CONTEXT': 'context',
   'ERROR': 'error',
   'ERROR_LEGACY_WARNING': 'errorLegacyWarning',
+  'IGNORED': 'ignored',
   'INTERNAL_PROBLEM': 'internalProblem',
-  'NIT': 'nit',
   'WARNING': 'warning',
 };
 
@@ -26,7 +26,7 @@
   'CONTEXT': Severity.context,
   'ERROR': Severity.error,
   'ERROR_LEGACY_WARNING': Severity.errorLegacyWarning,
+  'IGNORED': Severity.ignored,
   'INTERNAL_PROBLEM': Severity.internalProblem,
-  'NIT': Severity.nit,
   'WARNING': Severity.warning,
 };
diff --git a/pkg/front_end/lib/src/fasta/source/source_library_builder.dart b/pkg/front_end/lib/src/fasta/source/source_library_builder.dart
index 93390f9..9b5db36 100644
--- a/pkg/front_end/lib/src/fasta/source/source_library_builder.dart
+++ b/pkg/front_end/lib/src/fasta/source/source_library_builder.dart
@@ -43,6 +43,8 @@
         messageExpectedUri,
         messageMemberWithSameNameAsClass,
         messagePartOfSelf,
+        messagePartOfTwoLibraries,
+        messagePartOfTwoLibrariesContext,
         noLength,
         templateConflictsWithMember,
         templateConflictsWithSetter,
@@ -589,11 +591,23 @@
 
   void includeParts() {
     Set<Uri> seenParts = new Set<Uri>();
-    for (SourceLibraryBuilder<T, R> part in parts.toList()) {
+    for (SourceLibraryBuilder<T, R> part in parts) {
       if (part == this) {
         addCompileTimeError(messagePartOfSelf, -1, noLength, fileUri);
       } else if (seenParts.add(part.fileUri)) {
-        includePart(part);
+        if (part.partOfLibrary != null &&
+            // TODO(askesc): Remove this hack when co19 fix is rolled in.
+            !part.fileUri.path.endsWith("/co19/src/Utils/expect_common.dart")) {
+          addProblem(messagePartOfTwoLibraries, -1, noLength, part.fileUri,
+              context: [
+                messagePartOfTwoLibrariesContext.withLocation(
+                    part.partOfLibrary.fileUri, -1, noLength),
+                messagePartOfTwoLibrariesContext.withLocation(
+                    this.fileUri, -1, noLength)
+              ]);
+        } else {
+          includePart(part);
+        }
       } else {
         addCompileTimeError(templatePartTwice.withArguments(part.fileUri), -1,
             noLength, fileUri);
diff --git a/pkg/front_end/lib/src/fasta/source/source_loader.dart b/pkg/front_end/lib/src/fasta/source/source_loader.dart
index 7d6952a..f3952c9 100644
--- a/pkg/front_end/lib/src/fasta/source/source_loader.dart
+++ b/pkg/front_end/lib/src/fasta/source/source_loader.dart
@@ -80,7 +80,7 @@
 
 import '../parser.dart' show Parser, lengthForToken, offsetForToken;
 
-import '../problems.dart' show internalProblem;
+import '../problems.dart' show internalProblem, unhandled;
 
 import '../scanner.dart' show ErrorToken, ScannerResult, Token, scan;
 
@@ -206,6 +206,10 @@
       DietParser parser = new DietParser(listener);
       parser.parseUnit(tokens);
       for (SourceLibraryBuilder part in library.parts) {
+        if (part.partOfLibrary != library) {
+          // Part was included in multiple libraries. Skip it here.
+          continue;
+        }
         Token tokens = await tokenize(part);
         if (tokens != null) {
           listener.uri = part.fileUri;
@@ -755,16 +759,16 @@
       for (int i = 0; i < sourceClasses.length; i++) {
         classes[i] = sourceClasses[i].target;
       }
+      orderedClasses = null;
       List<ClassBuilder> result = new List<ClassBuilder>(sourceClasses.length);
       int i = 0;
-      for (Class cls in hierarchy.getOrderedClasses(classes)) {
-        result[i++] = ShadowClass.getClassInferenceInfo(cls).builder;
+      for (Class cls
+          in new List<Class>.from(hierarchy.getOrderedClasses(classes))) {
+        result[i++] = ShadowClass.getClassInferenceInfo(cls).builder
+          ..prepareTopLevelInference();
       }
       orderedClasses = result;
     }
-    for (ClassBuilder cls in orderedClasses) {
-      cls.prepareTopLevelInference();
-    }
     typeInferenceEngine.isTypeInferencePrepared = true;
     ticker.logMs("Prepared top level inference");
 
@@ -862,8 +866,7 @@
     if (instrumentation == null) return;
 
     if (charOffset == -1 &&
-        (severity == Severity.nit ||
-            message.code == fasta_codes.codeConstConstructorWithBody ||
+        (message.code == fasta_codes.codeConstConstructorWithBody ||
             message.code == fasta_codes.codeConstructorNotFound ||
             message.code == fasta_codes.codeSuperclassHasNoDefaultConstructor ||
             message.code == fasta_codes.codeTypeArgumentsOnTypeVariable ||
@@ -883,10 +886,6 @@
         severityString = "internal problem";
         break;
 
-      case Severity.nit:
-        severityString = "nit";
-        break;
-
       case Severity.warning:
         severityString = "warning";
         break;
@@ -900,6 +899,10 @@
       case Severity.context:
         severityString = "context";
         break;
+
+      case Severity.ignored:
+        unhandled("IGNORED", "recordMessage", charOffset, fileUri);
+        return;
     }
     instrumentation.record(
         fileUri,
diff --git a/pkg/front_end/lib/src/fasta/target.dart b/pkg/front_end/lib/src/fasta/target.dart
index ecf29f9..f2b0740 100644
--- a/pkg/front_end/lib/src/fasta/target.dart
+++ b/pkg/front_end/lib/src/fasta/target.dart
@@ -6,7 +6,8 @@
 
 import 'dart:async' show Future;
 
-import 'package:kernel/ast.dart';
+import 'package:kernel/ast.dart' show Component;
+
 import 'ticker.dart' show Ticker;
 
 /// A compilation target.
diff --git a/pkg/front_end/lib/src/fasta/type_inference/interface_resolver.dart b/pkg/front_end/lib/src/fasta/type_inference/interface_resolver.dart
index dd6fb0f..9b4bf82 100644
--- a/pkg/front_end/lib/src/fasta/type_inference/interface_resolver.dart
+++ b/pkg/front_end/lib/src/fasta/type_inference/interface_resolver.dart
@@ -2,20 +2,84 @@
 // for details. All rights reserved. Use of this source code is governed by a
 // BSD-style license that can be found in the LICENSE.md file.
 
-import 'package:front_end/src/base/instrumentation.dart';
-import 'package:front_end/src/fasta/builder/library_builder.dart';
-import 'package:front_end/src/fasta/kernel/kernel_shadow_ast.dart';
-import 'package:front_end/src/fasta/messages.dart';
-import 'package:front_end/src/fasta/names.dart';
-import 'package:front_end/src/fasta/problems.dart';
-import 'package:front_end/src/fasta/type_inference/type_inference_engine.dart';
-import 'package:front_end/src/fasta/type_inference/type_inferrer.dart';
-import 'package:front_end/src/fasta/type_inference/type_schema_environment.dart';
-import 'package:kernel/ast.dart';
-import 'package:kernel/class_hierarchy.dart';
+import 'package:kernel/ast.dart'
+    show
+        Arguments,
+        Class,
+        DartType,
+        DynamicType,
+        Expression,
+        Field,
+        FunctionNode,
+        FunctionType,
+        Member,
+        Name,
+        NamedExpression,
+        Procedure,
+        ProcedureKind,
+        ReturnStatement,
+        SuperMethodInvocation,
+        SuperPropertyGet,
+        SuperPropertySet,
+        TypeParameter,
+        TypeParameterType,
+        VariableDeclaration,
+        VariableGet,
+        VoidType;
+
+import 'package:kernel/class_hierarchy.dart' show ClassHierarchy;
+
 import 'package:kernel/transformations/flags.dart' show TransformerFlag;
-import 'package:kernel/type_algebra.dart';
-import 'package:kernel/type_environment.dart';
+
+import 'package:kernel/type_algebra.dart' show Substitution;
+
+import 'package:kernel/type_environment.dart' show TypeEnvironment;
+
+import '../../base/instrumentation.dart'
+    show
+        Instrumentation,
+        InstrumentationValueForForwardingStub,
+        InstrumentationValueLiteral;
+
+import '../builder/builder.dart' show LibraryBuilder;
+
+import '../kernel/kernel_shadow_ast.dart'
+    show
+        ShadowClass,
+        ShadowField,
+        ShadowMember,
+        ShadowProcedure,
+        ShadowVariableDeclaration;
+
+import '../messages.dart'
+    show
+        messageDeclaredMemberConflictsWithInheritedMember,
+        messageDeclaredMemberConflictsWithInheritedMemberCause,
+        messageInheritedMembersConflict,
+        messageInheritedMembersConflictCause1,
+        messageInheritedMembersConflictCause2,
+        noLength,
+        templateCantInferTypeDueToCircularity,
+        templateCantInferTypeDueToInconsistentOverrides;
+
+import '../names.dart' show indexSetName;
+
+import '../problems.dart' show unhandled;
+
+import 'type_inference_engine.dart'
+    show
+        FieldInitializerInferenceNode,
+        IncludesTypeParametersCovariantly,
+        InferenceNode,
+        TypeInferenceEngine;
+
+import 'type_inferrer.dart' show getNamedFormal;
+
+import 'type_schema_environment.dart'
+    show
+        getNamedParameterType,
+        getPositionalParameterType,
+        substituteTypeParams;
 
 /// Concrete class derived from [InferenceNode] to represent type inference of
 /// getters, setters, and fields based on inheritance.
diff --git a/pkg/front_end/lib/src/fasta/type_inference/type_constraint_gatherer.dart b/pkg/front_end/lib/src/fasta/type_inference/type_constraint_gatherer.dart
index 0b8d427..300dd31 100644
--- a/pkg/front_end/lib/src/fasta/type_inference/type_constraint_gatherer.dart
+++ b/pkg/front_end/lib/src/fasta/type_inference/type_constraint_gatherer.dart
@@ -2,10 +2,23 @@
 // for details. All rights reserved. Use of this source code is governed by a
 // BSD-style license that can be found in the LICENSE.md file.
 
-import 'package:front_end/src/fasta/type_inference/type_schema.dart';
-import 'package:front_end/src/fasta/type_inference/type_schema_environment.dart';
-import 'package:kernel/ast.dart';
-import 'package:kernel/type_algebra.dart';
+import 'package:kernel/ast.dart'
+    show
+        DartType,
+        DynamicType,
+        FunctionType,
+        InterfaceType,
+        NamedType,
+        TypeParameter,
+        TypeParameterType,
+        VoidType;
+
+import 'package:kernel/type_algebra.dart' show substitute;
+
+import 'type_schema.dart' show UnknownType;
+
+import 'type_schema_environment.dart'
+    show TypeConstraint, TypeSchemaEnvironment, substituteTypeParams;
 
 /// Creates a collection of [TypeConstraint]s corresponding to type parameters,
 /// based on an attempt to make one type schema a subtype of another.
diff --git a/pkg/front_end/lib/src/fasta/type_inference/type_promotion.dart b/pkg/front_end/lib/src/fasta/type_inference/type_promotion.dart
index 0665ed5..791a584 100644
--- a/pkg/front_end/lib/src/fasta/type_inference/type_promotion.dart
+++ b/pkg/front_end/lib/src/fasta/type_inference/type_promotion.dart
@@ -2,12 +2,14 @@
 // for details. All rights reserved. Use of this source code is governed by a
 // BSD-style license that can be found in the LICENSE.md file.
 
-import 'package:front_end/src/fasta/fasta_codes.dart'
-    show templateInternalProblemStackNotEmpty;
-import 'package:front_end/src/fasta/problems.dart' show internalProblem;
-import 'package:front_end/src/fasta/type_inference/type_inferrer.dart';
-import 'package:front_end/src/fasta/type_inference/type_schema_environment.dart';
-import 'package:kernel/ast.dart';
+import 'package:kernel/ast.dart'
+    show DartType, Expression, TypeParameterType, VariableDeclaration;
+
+import '../fasta_codes.dart' show templateInternalProblemStackNotEmpty;
+
+import '../problems.dart' show internalProblem;
+
+import 'type_schema_environment.dart' show TypeSchemaEnvironment;
 
 /// Keeps track of the state necessary to perform type promotion.
 ///
diff --git a/pkg/front_end/lib/src/fasta/type_inference/type_schema.dart b/pkg/front_end/lib/src/fasta/type_inference/type_schema.dart
index 8342a2b..060aad1 100644
--- a/pkg/front_end/lib/src/fasta/type_inference/type_schema.dart
+++ b/pkg/front_end/lib/src/fasta/type_inference/type_schema.dart
@@ -2,9 +2,19 @@
 // for details. All rights reserved. Use of this source code is governed by a
 // BSD-style license that can be found in the LICENSE.md file.
 
-import 'package:kernel/ast.dart';
-import 'package:kernel/import_table.dart';
-import 'package:kernel/text/ast_to_text.dart';
+import 'package:kernel/ast.dart'
+    show
+        DartType,
+        DartTypeVisitor,
+        FunctionType,
+        InterfaceType,
+        TypedefType,
+        Visitor;
+
+import 'package:kernel/import_table.dart' show ImportTable;
+
+import 'package:kernel/text/ast_to_text.dart'
+    show Annotator, NameSystem, Printer, globalDebuggingNames;
 
 /// Determines whether a type schema contains `?` somewhere inside it.
 bool isKnown(DartType schema) => schema.accept(new _IsKnownVisitor());
diff --git a/pkg/front_end/lib/src/fasta/type_inference/type_schema_elimination.dart b/pkg/front_end/lib/src/fasta/type_inference/type_schema_elimination.dart
index 8c1f522..519c3df 100644
--- a/pkg/front_end/lib/src/fasta/type_inference/type_schema_elimination.dart
+++ b/pkg/front_end/lib/src/fasta/type_inference/type_schema_elimination.dart
@@ -2,9 +2,12 @@
 // for details. All rights reserved. Use of this source code is governed by a
 // BSD-style license that can be found in the LICENSE.md file.
 
-import 'package:front_end/src/fasta/type_inference/type_schema.dart';
-import 'package:kernel/ast.dart';
-import 'package:kernel/core_types.dart';
+import 'package:kernel/ast.dart'
+    show DartType, DynamicType, FunctionType, InterfaceType, NamedType;
+
+import 'package:kernel/core_types.dart' show CoreTypes;
+
+import 'type_schema.dart' show TypeSchemaVisitor, UnknownType;
 
 /// Returns the greatest closure of the given type [schema] with respect to `?`.
 ///
diff --git a/pkg/front_end/lib/src/fasta/type_inference/type_schema_environment.dart b/pkg/front_end/lib/src/fasta/type_inference/type_schema_environment.dart
index 0297c47..5577ced 100644
--- a/pkg/front_end/lib/src/fasta/type_inference/type_schema_environment.dart
+++ b/pkg/front_end/lib/src/fasta/type_inference/type_schema_environment.dart
@@ -4,14 +4,32 @@
 
 import 'dart:math' as math;
 
-import 'package:front_end/src/fasta/type_inference/type_constraint_gatherer.dart';
-import 'package:front_end/src/fasta/type_inference/type_schema.dart';
-import 'package:front_end/src/fasta/type_inference/type_schema_elimination.dart';
-import 'package:kernel/ast.dart';
-import 'package:kernel/class_hierarchy.dart';
-import 'package:kernel/core_types.dart';
-import 'package:kernel/type_algebra.dart';
-import 'package:kernel/type_environment.dart';
+import 'package:kernel/ast.dart'
+    show
+        BottomType,
+        DartType,
+        DynamicType,
+        FunctionType,
+        InterfaceType,
+        NamedType,
+        Procedure,
+        TypeParameter,
+        TypeParameterType,
+        VoidType;
+
+import 'package:kernel/class_hierarchy.dart' show ClassHierarchy;
+
+import 'package:kernel/core_types.dart' show CoreTypes;
+
+import 'package:kernel/type_algebra.dart' show Substitution;
+
+import 'package:kernel/type_environment.dart' show TypeEnvironment;
+
+import 'type_constraint_gatherer.dart' show TypeConstraintGatherer;
+
+import 'type_schema.dart' show UnknownType, typeSchemaToString, isKnown;
+
+import 'type_schema_elimination.dart' show greatestClosure, leastClosure;
 
 // TODO(paulberry): try to push this functionality into kernel.
 FunctionType substituteTypeParams(
diff --git a/pkg/front_end/messages.status b/pkg/front_end/messages.status
index 47d7166..d308900 100644
--- a/pkg/front_end/messages.status
+++ b/pkg/front_end/messages.status
@@ -113,11 +113,8 @@
 DuplicatePrefix/example: Fail
 DuplicatedDefinition/analyzerCode: Fail
 DuplicatedDefinition/example: Fail
-DuplicatedExport/example: Fail
 DuplicatedExportInType/analyzerCode: Fail
 DuplicatedExportInType/example: Fail
-DuplicatedImport/analyzerCode: Fail
-DuplicatedImport/example: Fail
 DuplicatedImportInType/analyzerCode: Fail
 DuplicatedImportInType/example: Fail
 DuplicatedModifier/script1: Fail
@@ -150,8 +147,6 @@
 ExpectedUri/analyzerCode: Fail
 ExpectedUri/example: Fail
 ExportAfterPart/script1: Fail
-ExportHidesExport/analyzerCode: Fail
-ExportHidesExport/example: Fail
 ExpressionNotMetadata/analyzerCode: Fail
 ExpressionNotMetadata/example: Fail
 ExtendingEnum/analyzerCode: Fail
@@ -210,8 +205,6 @@
 ImplicitCallOfNonMethod/analyzerCode: Fail
 ImplicitCallOfNonMethod/example: Fail
 ImportAfterPart/script1: Fail
-ImportHidesImport/analyzerCode: Fail
-ImportHidesImport/example: Fail
 InheritedMembersConflict/analyzerCode: Fail
 InputFileNotFound/analyzerCode: Fail
 InputFileNotFound/example: Fail
@@ -241,14 +234,8 @@
 ListLiteralTooManyTypeArguments/example: Fail
 ListLiteralTypeArgumentMismatch/analyzerCode: Fail
 ListLiteralTypeArgumentMismatch/example: Fail
-LoadLibraryHidesMember/analyzerCode: Fail
-LoadLibraryHidesMember/example: Fail
 LoadLibraryTakesNoArguments/analyzerCode: Fail
 LoadLibraryTakesNoArguments/example: Fail
-LocalDefinitionHidesExport/analyzerCode: Fail
-LocalDefinitionHidesExport/example: Fail
-LocalDefinitionHidesImport/analyzerCode: Fail
-LocalDefinitionHidesImport/example: Fail
 MemberWithSameNameAsClass/analyzerCode: Fail
 MemberWithSameNameAsClass/example: Fail
 MetadataTypeArguments/analyzerCode: Fail
@@ -313,6 +300,8 @@
 PartOfLibraryNameMismatch/example: Fail
 PartOfSelf/analyzerCode: Fail
 PartOfSelf/example: Fail
+PartOfTwoLibraries/analyzerCode: Fail # Issue 33227
+PartOfTwoLibraries/example: Fail # Needs multiple files
 PartOfUriMismatch/analyzerCode: Fail
 PartOfUriMismatch/example: Fail
 PartOfUseUri/analyzerCode: Fail
@@ -355,7 +344,6 @@
 SourceBodySummary/example: Fail
 SourceOutlineSummary/analyzerCode: Fail
 SourceOutlineSummary/example: Fail
-StackOverflow/analyzerCode: Fail
 StackOverflow/example: Fail
 StaticAfterConst/script1: Fail
 SuperAsExpression/analyzerCode: Fail
diff --git a/pkg/front_end/messages.yaml b/pkg/front_end/messages.yaml
index 4eb8ac6..af33dd73 100644
--- a/pkg/front_end/messages.yaml
+++ b/pkg/front_end/messages.yaml
@@ -59,17 +59,22 @@
 # `#unicode` a Unicode short identifier (U+xxxx). We use this to represent code
 #  units or code points.
 #
-# `#name` a name (a string).
-#
-# `#name2` another name (a string).
+# `#name`, `#name2`, `#name3`: names (as strings).
 #
 # `#lexeme` a token. The token's `lexeme` property is used.
 #
-# `#string` a string.
+# `#string`, `#string2`, `#string3`: strings (that aren't names).
 #
-# `#string2` another string.
+# `#type`, #type2`: Kernel types.
 #
-# `#uri` a Uri.
+# `#uri`, `#uri2`, `#uri3`: URIs.
+#
+# `#count`, `#count2`: counts (as integers)
+#
+# `#constant` a Kernel constant.
+#
+# `#num1%N.M`, `#num2%N.M`, `#num3%N.M`: numbers (doubles) formatted to minimum
+# width N and with M fraction digits.
 
 AsciiControlCharacter:
   template: "The control character #unicode can only be used in strings and comments."
@@ -758,6 +763,7 @@
 
 StackOverflow:
   template: "Stack overflow."
+  analyzerCode: STACK_OVERFLOW
   dart2jsCode: GENERIC
 
 UnexpectedDollarInString:
@@ -1143,11 +1149,10 @@
 LoadLibraryHidesMember:
   template: "The library '#uri' defines a top-level member named 'loadLibrary'. This member is hidden by the special member 'loadLibrary' that the language adds to support deferred loading."
   tip: "Try to rename or hide the member."
-  severity: NIT
+  severity: IGNORED
 
 TypeArgumentMismatch:
-  # TODO(sigmund): #string should be a number instead.
-  template: "'#name' expects #string type arguments."
+  template: "'#name' expects #count type arguments."
   severity: ERROR_LEGACY_WARNING
 
 NotAType:
@@ -1224,7 +1229,6 @@
 
       --fatal=errors
       --fatal=warnings
-      --fatal=nits
         Makes messages of the given kinds fatal, that is, immediately stop the
         compiler with a non-zero exit-code. In --verbose mode, also display an
         internal stack trace from the compiler. Multiple kinds can be separated by
@@ -1338,19 +1342,19 @@
 
 LocalDefinitionHidesExport:
   template: "Local definition of '#name' hides export from '#uri'."
-  severity: NIT
+  severity: IGNORED
 
 LocalDefinitionHidesImport:
   template: "Local definition of '#name' hides import from '#uri'."
-  severity: NIT
+  severity: IGNORED
 
 ExportHidesExport:
   template: "Export of '#name' (from '#uri') hides export from '#uri2'."
-  severity: NIT
+  severity: IGNORED
 
 ImportHidesImport:
   template: "Import of '#name' (from '#uri') hides import from '#uri2'."
-  severity: NIT
+  severity: IGNORED
 
 MissingPrefixInDeferredImport:
   template: "Deferred imports should have a prefix."
@@ -1391,7 +1395,7 @@
 
 DuplicatedExport:
   template: "'#name' is exported from both '#uri' and '#uri2'."
-  severity: NIT
+  severity: IGNORED
   analyzerCode: AMBIGUOUS_EXPORT
   dart2jsCode: "*ignored*"
 
@@ -1401,7 +1405,7 @@
 
 DuplicatedImport:
   template: "'#name' is imported from both '#uri' and '#uri2'."
-  severity: NIT
+  severity: IGNORED
 
 DuplicatedImportInType:
   template: "'#name' is imported from both '#uri' and '#uri2'."
@@ -1700,6 +1704,15 @@
 PartTwice:
   template: "Can't use '#uri' as a part more than once."
 
+PartOfTwoLibraries:
+  template: "A file can't be part of more than one library."
+  tip: "Try moving the shared declarations into the libraries, or into a new library."
+  severity: ERROR
+
+PartOfTwoLibrariesContext:
+  template: "Used as a part in this library."
+  severity: CONTEXT
+
 FactoryTopLevelDeclaration:
   template: "Top-level declarations can't be declared to be 'factory'."
   tip: "Try removing the keyword 'factory'."
@@ -2162,21 +2175,21 @@
 
 SourceOutlineSummary:
   template: |
-    Built outlines for #count compilation units (#count2 bytes) in #string, that is,
-    #string2 bytes/ms, and
-    #string3 ms/compilation unit.
+    Built outlines for #count compilation units (#count2 bytes) in #num1%.3ms, that is,
+    #num2%12.3 bytes/ms, and
+    #num3%12.3 ms/compilation unit.
 
 SourceBodySummary:
   template: |
-    Built bodies for #count compilation units (#count2 bytes) in #string, that is,
-    #string2 bytes/ms, and
-    #string3 ms/compilation unit.
+    Built bodies for #count compilation units (#count2 bytes) in #num1%.3ms, that is,
+    #num2%12.3 bytes/ms, and
+    #num3%12.3 ms/compilation unit.
 
 DillOutlineSummary:
   template: |
-    Indexed #count libraries (#count2 bytes) in #string, that is,
-    #string2 bytes/ms, and
-    #string3 ms/libraries.
+    Indexed #count libraries (#count2 bytes) in #num1%.3ms, that is,
+    #num2%12.3 bytes/ms, and
+    #num3%12.3 ms/libraries.
 
 CantInferTypeDueToInconsistentOverrides:
   template: "Can't infer the type of '#string': overridden members must all have the same type."
@@ -2242,3 +2255,7 @@
 InitializingFormalTypeMismatchField:
   template: "The field that corresponds to the parameter."
   severity: CONTEXT
+
+UseOfDeprecatedIdentifier:
+  template: "'#name' is deprecated."
+  severity: IGNORED
diff --git a/pkg/front_end/test/fasta/incremental_test.dart b/pkg/front_end/test/fasta/incremental_test.dart
index d6e5f8d..3609b70 100644
--- a/pkg/front_end/test/fasta/incremental_test.dart
+++ b/pkg/front_end/test/fasta/incremental_test.dart
@@ -220,8 +220,7 @@
     ..fileSystem = fs
     ..sdkSummary = sdkSummary
     ..onError = (CompilationMessage message) {
-      if (message.severity != Severity.nit &&
-          message.severity != Severity.warning) {
+      if (message.severity != Severity.warning) {
         errors.add(message);
       }
     };
diff --git a/pkg/front_end/test/fasta/messages_test.dart b/pkg/front_end/test/fasta/messages_test.dart
index 334a62f..e1a706c 100644
--- a/pkg/front_end/test/fasta/messages_test.dart
+++ b/pkg/front_end/test/fasta/messages_test.dart
@@ -219,8 +219,9 @@
               : null,
           location: badSeverity?.span?.start);
 
-      bool exampleAndAnalyzerCodeRequired = (severity != Severity.context &&
-          severity != Severity.internalProblem);
+      bool exampleAndAnalyzerCodeRequired = severity != Severity.context &&
+          severity != Severity.internalProblem &&
+          severity != Severity.ignored;
 
       yield createDescription(
           "externalexample",
diff --git a/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.expect b/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.expect
index 09a7e0c..e72d620 100644
--- a/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.expect
+++ b/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.expect
@@ -19,7 +19,7 @@
     for (final dynamic #t3 = let dynamic _ = null in invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:17:10: Error: Can't assign to this, so it can't be used in a for-in loop.
     for (collection in x) {
          ^^^^^^^^^^" in x) {
-      core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart: Error: A library can't be used as an expression.");
+      core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:1: Error: A library can't be used as an expression.");
     }
     for (final dynamic #t4 in x) {
       let dynamic _ = null in throw new core::NoSuchMethodError::withInvocation(null, new core::_InvocationMirror::_withType(#VoidFunction, 34, const <core::Type>[], core::List::unmodifiable<dynamic>(<dynamic>[#t4]), core::Map::unmodifiable<core::Symbol, dynamic>(const <core::Symbol, dynamic>{})));
@@ -50,7 +50,7 @@
   for (final dynamic #t8 = let dynamic _ = null in invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:37:8: Error: Can't assign to this, so it can't be used in a for-in loop.
   for (collection in arguments) {
        ^^^^^^^^^^" in arguments) {
-    core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart: Error: A library can't be used as an expression.");
+    core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:1: Error: A library can't be used as an expression.");
   }
   for (final dynamic #t9 in arguments) {
     let dynamic _ = null in throw new core::NoSuchMethodError::withInvocation(null, new core::_InvocationMirror::_withType(#VoidFunction, 34, const <core::Type>[], core::List::unmodifiable<dynamic>(<dynamic>[#t9]), core::Map::unmodifiable<core::Symbol, dynamic>(const <core::Symbol, dynamic>{})));
diff --git a/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.transformed.expect b/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.transformed.expect
index 09a7e0c..e72d620 100644
--- a/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.transformed.expect
+++ b/pkg/front_end/testcases/rasta/unresolved_for_in.dart.direct.transformed.expect
@@ -19,7 +19,7 @@
     for (final dynamic #t3 = let dynamic _ = null in invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:17:10: Error: Can't assign to this, so it can't be used in a for-in loop.
     for (collection in x) {
          ^^^^^^^^^^" in x) {
-      core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart: Error: A library can't be used as an expression.");
+      core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:1: Error: A library can't be used as an expression.");
     }
     for (final dynamic #t4 in x) {
       let dynamic _ = null in throw new core::NoSuchMethodError::withInvocation(null, new core::_InvocationMirror::_withType(#VoidFunction, 34, const <core::Type>[], core::List::unmodifiable<dynamic>(<dynamic>[#t4]), core::Map::unmodifiable<core::Symbol, dynamic>(const <core::Symbol, dynamic>{})));
@@ -50,7 +50,7 @@
   for (final dynamic #t8 = let dynamic _ = null in invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:37:8: Error: Can't assign to this, so it can't be used in a for-in loop.
   for (collection in arguments) {
        ^^^^^^^^^^" in arguments) {
-    core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart: Error: A library can't be used as an expression.");
+    core::print(invalid-expression "pkg/front_end/testcases/rasta/unresolved_for_in.dart:1: Error: A library can't be used as an expression.");
   }
   for (final dynamic #t9 in arguments) {
     let dynamic _ = null in throw new core::NoSuchMethodError::withInvocation(null, new core::_InvocationMirror::_withType(#VoidFunction, 34, const <core::Type>[], core::List::unmodifiable<dynamic>(<dynamic>[#t9]), core::Map::unmodifiable<core::Symbol, dynamic>(const <core::Symbol, dynamic>{})));
diff --git a/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.expect b/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.expect
index bdc26f1..7073760 100644
--- a/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.expect
+++ b/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.expect
@@ -2,5 +2,5 @@
 import self as self;
 
 static method #main() → dynamic {
-  throw "dart:html: Error: Not found: dart:html.";
+  throw "dart:html:1: Error: Not found: dart:html.";
 }
diff --git a/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.transformed.expect b/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.transformed.expect
index bdc26f1..7073760 100644
--- a/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.transformed.expect
+++ b/pkg/front_end/testcases/rasta/unsupported_platform_library.dart.direct.transformed.expect
@@ -2,5 +2,5 @@
 import self as self;
 
 static method #main() → dynamic {
-  throw "dart:html: Error: Not found: dart:html.";
+  throw "dart:html:1: Error: Not found: dart:html.";
 }
diff --git a/pkg/front_end/testcases/regress/issue_31190.dart.strong.expect b/pkg/front_end/testcases/regress/issue_31190.dart.strong.expect
index 9387690..9fbedf8 100644
--- a/pkg/front_end/testcases/regress/issue_31190.dart.strong.expect
+++ b/pkg/front_end/testcases/regress/issue_31190.dart.strong.expect
@@ -8,7 +8,7 @@
     : super core::Object::•()
     ;
 }
-static const field dynamic #errors = const <dynamic>["pkg/front_end/testcases/regress/issue_31190.dart: Error: Can't use type arguments with type variable 'T'.
+static const field dynamic #errors = const <dynamic>["pkg/front_end/testcases/regress/issue_31190.dart:1: Error: Can't use type arguments with type variable 'T'.
 Try removing the type arguments.", "pkg/front_end/testcases/regress/issue_31190.dart:6:5: Error: 'U' isn't a type.
   T<U> v;
     ^", "pkg/front_end/testcases/regress/issue_31190.dart:6:3: Error: 'T' expects 0 type arguments.
diff --git a/pkg/front_end/testcases/regress/issue_31190.dart.strong.transformed.expect b/pkg/front_end/testcases/regress/issue_31190.dart.strong.transformed.expect
index 9387690..9fbedf8 100644
--- a/pkg/front_end/testcases/regress/issue_31190.dart.strong.transformed.expect
+++ b/pkg/front_end/testcases/regress/issue_31190.dart.strong.transformed.expect
@@ -8,7 +8,7 @@
     : super core::Object::•()
     ;
 }
-static const field dynamic #errors = const <dynamic>["pkg/front_end/testcases/regress/issue_31190.dart: Error: Can't use type arguments with type variable 'T'.
+static const field dynamic #errors = const <dynamic>["pkg/front_end/testcases/regress/issue_31190.dart:1: Error: Can't use type arguments with type variable 'T'.
 Try removing the type arguments.", "pkg/front_end/testcases/regress/issue_31190.dart:6:5: Error: 'U' isn't a type.
   T<U> v;
     ^", "pkg/front_end/testcases/regress/issue_31190.dart:6:3: Error: 'T' expects 0 type arguments.
diff --git a/pkg/front_end/tool/_fasta/command_line.dart b/pkg/front_end/tool/_fasta/command_line.dart
index b34bcdf..daceb3cd 100644
--- a/pkg/front_end/tool/_fasta/command_line.dart
+++ b/pkg/front_end/tool/_fasta/command_line.dart
@@ -277,8 +277,6 @@
 
   final bool warningsAreFatal = fatal.contains("warnings");
 
-  final bool nitsAreFatal = fatal.contains("nits");
-
   final bool compileSdk = options.containsKey("--compile-sdk");
 
   if (programName == "compile_platform") {
@@ -305,7 +303,6 @@
           ..target = target
           ..throwOnErrorsForDebugging = errorsAreFatal
           ..throwOnWarningsForDebugging = warningsAreFatal
-          ..throwOnNitsForDebugging = nitsAreFatal
           ..embedSourceText = !excludeSource
           ..debugDump = dumpIr
           ..verbose = verbose
@@ -336,7 +333,6 @@
     ..target = target
     ..throwOnErrorsForDebugging = errorsAreFatal
     ..throwOnWarningsForDebugging = warningsAreFatal
-    ..throwOnNitsForDebugging = nitsAreFatal
     ..embedSourceText = !excludeSource
     ..debugDump = dumpIr
     ..verbose = verbose
diff --git a/pkg/front_end/tool/_fasta/generate_messages.dart b/pkg/front_end/tool/_fasta/generate_messages.dart
index 397bded..5b2e15c 100644
--- a/pkg/front_end/tool/_fasta/generate_messages.dart
+++ b/pkg/front_end/tool/_fasta/generate_messages.dart
@@ -61,7 +61,8 @@
   return new DartFormatter().format("$sb");
 }
 
-final RegExp placeholderPattern = new RegExp("#[a-zA-Z0-9_]+");
+final RegExp placeholderPattern =
+    new RegExp("#\([-a-zA-Z0-9_]+\)(?:%\([0-9]*\)\.\([0-9]+\))?");
 
 String compileTemplate(String name, String template, String tip,
     String analyzerCode, String dart2jsCode, String severity) {
@@ -78,13 +79,34 @@
   var conversions = new Set<String>();
   var arguments = new Set<String>();
   for (Match match in placeholderPattern.allMatches("$template${tip ?? ''}")) {
-    switch (match[0]) {
-      case "#character":
+    String name = match[1];
+    String padding = match[2];
+    String fractionDigits = match[3];
+
+    String format(String name) {
+      String conversion;
+      if (fractionDigits == null) {
+        conversion = "'\$$name'";
+      } else {
+        conversion = "$name.toStringAsFixed($fractionDigits)";
+      }
+      if (padding.isNotEmpty) {
+        if (padding.startsWith("0")) {
+          conversion += ".padLeft(${int.parse(padding)}, '0')";
+        } else {
+          conversion += ".padLeft(${int.parse(padding)})";
+        }
+      }
+      return conversion;
+    }
+
+    switch (name) {
+      case "character":
         parameters.add("String character");
         arguments.add("'character': character");
         break;
 
-      case "#unicode":
+      case "unicode":
         // Write unicode value using at least four (but otherwise no more than
         // necessary) hex digits, using uppercase letters.
         // http://www.unicode.org/versions/Unicode10.0.0/appA.pdf
@@ -94,43 +116,43 @@
         arguments.add("'codePoint': codePoint");
         break;
 
-      case "#name":
+      case "name":
         parameters.add("String name");
         arguments.add("'name': name");
         break;
 
-      case "#name2":
+      case "name2":
         parameters.add("String name2");
         arguments.add("'name2': name2");
         break;
 
-      case "#name3":
+      case "name3":
         parameters.add("String name3");
         arguments.add("'name3': name3");
         break;
 
-      case "#lexeme":
+      case "lexeme":
         parameters.add("Token token");
         conversions.add("String lexeme = token.lexeme;");
         arguments.add("'token': token");
         break;
 
-      case "#string":
+      case "string":
         parameters.add("String string");
         arguments.add("'string': string");
         break;
 
-      case "#string2":
+      case "string2":
         parameters.add("String string2");
         arguments.add("'string2': string2");
         break;
 
-      case "#string3":
+      case "string3":
         parameters.add("String string3");
         arguments.add("'string3': string3");
         break;
 
-      case "#type":
+      case "type":
         parameters.add("DartType _type");
         conversions.add(r"""
 NameSystem nameSystem = new NameSystem();
@@ -141,7 +163,7 @@
         arguments.add("'type': _type");
         break;
 
-      case "#type2":
+      case "type2":
         parameters.add("DartType _type2");
         conversions.add(r"""
 buffer = new StringBuffer();
@@ -151,47 +173,67 @@
         arguments.add("'type2': _type2");
         break;
 
-      case "#uri":
+      case "uri":
         parameters.add("Uri uri_");
         conversions.add("String uri = relativizeUri(uri_);");
         arguments.add("'uri': uri_");
         break;
 
-      case "#uri2":
+      case "uri2":
         parameters.add("Uri uri2_");
         conversions.add("String uri2 = relativizeUri(uri2_);");
         arguments.add("'uri2': uri2_");
         break;
 
-      case "#uri3":
+      case "uri3":
         parameters.add("Uri uri3_");
         conversions.add("String uri3 = relativizeUri(uri3_);");
         arguments.add("'uri3': uri3_");
         break;
 
-      case "#count":
+      case "count":
         parameters.add("int count");
         arguments.add("'count': count");
         break;
 
-      case "#count2":
+      case "count2":
         parameters.add("int count2");
         arguments.add("'count2': count2");
         break;
 
-      case "#constant":
+      case "constant":
         parameters.add("Constant constant");
         arguments.add("'constant': constant");
         break;
 
+      case "num1":
+        parameters.add("num _num1");
+        conversions.add("String num1 = ${format('_num1')};");
+        arguments.add("'num1': _num1");
+        break;
+
+      case "num2":
+        parameters.add("num _num2");
+        conversions.add("String num2 = ${format('_num2')};");
+        arguments.add("'num2': _num2");
+        break;
+
+      case "num3":
+        parameters.add("num _num3");
+        conversions.add("String num3 = ${format('_num3')};");
+        arguments.add("'num3': _num3");
+        break;
+
       default:
-        throw "Unhandled placeholder in template: ${match[0]}";
+        throw "Unhandled placeholder in template: '$name'";
     }
   }
 
   String interpolate(String name, String text) {
-    return "$name: "
-        "\"\"\"${text.replaceAll(r'$', r'\$').replaceAll('#', '\$')}\"\"\"";
+    text = text
+        .replaceAll(r"$", r"\$")
+        .replaceAllMapped(placeholderPattern, (Match m) => "\${${m[1]}}");
+    return "$name: \"\"\"$text\"\"\"";
   }
 
   List<String> codeArguments = <String>[];
diff --git a/pkg/kernel/lib/external_name.dart b/pkg/kernel/lib/external_name.dart
new file mode 100644
index 0000000..4da52a8
--- /dev/null
+++ b/pkg/kernel/lib/external_name.dart
@@ -0,0 +1,41 @@
+// 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.
+
+library kernel.external_name;
+
+import 'ast.dart';
+
+/// Returns external (native) name of given [Member].
+String getExternalName(Member procedure) {
+  // Native procedures are marked as external and have an annotation,
+  // which looks like this:
+  //
+  //    import 'dart:_internal' as internal;
+  //
+  //    @internal.ExternalName("<name-of-native>")
+  //    external Object foo(arg0, ...);
+  //
+  if (!procedure.isExternal) {
+    return null;
+  }
+  for (final Expression annotation in procedure.annotations) {
+    if (annotation is ConstructorInvocation) {
+      if (_isExternalName(annotation.target.enclosingClass)) {
+        return (annotation.arguments.positional.single as StringLiteral).value;
+      }
+    } else if (annotation is ConstantExpression) {
+      final constant = annotation.constant;
+      if (constant is InstanceConstant) {
+        if (_isExternalName(constant.klass)) {
+          return (constant.fieldValues.values.single as StringConstant).value;
+        }
+      }
+    }
+  }
+  return null;
+}
+
+bool _isExternalName(Class klass) =>
+    klass.name == 'ExternalName' &&
+    klass.enclosingLibrary.importUri.toString() == 'dart:_internal';
diff --git a/pkg/kernel/lib/transformations/constants.dart b/pkg/kernel/lib/transformations/constants.dart
index de851c6..b8a3aa8 100644
--- a/pkg/kernel/lib/transformations/constants.dart
+++ b/pkg/kernel/lib/transformations/constants.dart
@@ -20,13 +20,13 @@
 
 import 'dart:io' as io;
 
-import '../kernel.dart';
 import '../ast.dart';
+import '../class_hierarchy.dart';
 import '../core_types.dart';
+import '../external_name.dart' show getExternalName;
+import '../kernel.dart';
 import '../type_algebra.dart';
 import '../type_environment.dart';
-import '../class_hierarchy.dart';
-import 'treeshaker.dart' show findNativeName;
 
 Component transformComponent(Component component, ConstantsBackend backend,
     {bool keepFields: false,
@@ -940,7 +940,7 @@
   visitStaticInvocation(StaticInvocation node) {
     final Procedure target = node.target;
     if (target.kind == ProcedureKind.Factory) {
-      final String nativeName = findNativeName(target);
+      final String nativeName = getExternalName(target);
       if (nativeName != null) {
         final Constant constant = backend.buildConstantForNative(
             nativeName,
diff --git a/pkg/kernel/lib/transformations/treeshaker.dart b/pkg/kernel/lib/transformations/treeshaker.dart
index f708bd9..2d50eda 100644
--- a/pkg/kernel/lib/transformations/treeshaker.dart
+++ b/pkg/kernel/lib/transformations/treeshaker.dart
@@ -1246,37 +1246,3 @@
 /// Exception that is thrown to stop the tree shaking analysis when a use
 /// of `dart:mirrors` is found.
 class _UsingMirrorsException {}
-
-String findNativeName(Member procedure) {
-  // Native procedures are marked as external and have an annotation,
-  // which looks like this:
-  //
-  //    import 'dart:_internal' as internal;
-  //
-  //    @internal.ExternalName("<name-of-native>")
-  //    external Object foo(arg0, ...);
-  //
-  if (procedure.isExternal) {
-    for (final Expression annotation in procedure.annotations) {
-      if (annotation is ConstructorInvocation) {
-        final Class klass = annotation.target.enclosingClass;
-        if (klass.name == 'ExternalName' &&
-            klass.enclosingLibrary.importUri.toString() == 'dart:_internal') {
-          assert(annotation.arguments.positional.length == 1);
-          return (annotation.arguments.positional[0] as StringLiteral).value;
-        }
-      } else if (annotation is ConstantExpression) {
-        final constant = annotation.constant;
-        if (constant is InstanceConstant) {
-          final Class klass = constant.klass;
-          if (klass.name == 'ExternalName' &&
-              klass.enclosingLibrary.importUri.toString() == 'dart:_internal') {
-            assert(constant.fieldValues.length == 1);
-            return (constant.fieldValues.values.single as StringConstant).value;
-          }
-        }
-      }
-    }
-  }
-  return null;
-}
diff --git a/pkg/vm/bin/gen_kernel.dart b/pkg/vm/bin/gen_kernel.dart
index 151be0e..7d91811 100644
--- a/pkg/vm/bin/gen_kernel.dart
+++ b/pkg/vm/bin/gen_kernel.dart
@@ -15,7 +15,7 @@
     show globalDebuggingNames, NameSystem;
 import 'package:vm/bytecode/gen_bytecode.dart' show isKernelBytecodeEnabled;
 import 'package:vm/kernel_front_end.dart'
-    show compileToKernel, ErrorDetector, ErrorPrinter;
+    show compileToKernel, ErrorDetector, ErrorPrinter, parseCommandLineDefines;
 
 final ArgParser _argParser = new ArgParser(allowTrailingOptions: true)
   ..addOption('platform',
@@ -93,7 +93,7 @@
   final bool enableConstantEvaluation = options['enable-constant-evaluation'];
   final Map<String, String> environmentDefines = {};
 
-  if (!_parseDefines(options['define'], environmentDefines)) {
+  if (!parseCommandLineDefines(options['define'], environmentDefines, _usage)) {
     return _badUsageExitCode;
   }
 
@@ -179,22 +179,3 @@
     }
   });
 }
-
-bool _parseDefines(
-    List<String> dFlags, Map<String, String> environmentDefines) {
-  for (final String dflag in dFlags) {
-    final equalsSignIndex = dflag.indexOf('=');
-    if (equalsSignIndex < 0) {
-      environmentDefines[dflag] = '';
-    } else if (equalsSignIndex > 0) {
-      final key = dflag.substring(0, equalsSignIndex);
-      final value = dflag.substring(equalsSignIndex + 1);
-      environmentDefines[key] = value;
-    } else {
-      print('The environment constant options must have a key (was: "$dflag")');
-      print(_usage);
-      return false;
-    }
-  }
-  return true;
-}
diff --git a/pkg/vm/bin/kernel_service.dart b/pkg/vm/bin/kernel_service.dart
index 8bd4fe4..eedfdee 100644
--- a/pkg/vm/bin/kernel_service.dart
+++ b/pkg/vm/bin/kernel_service.dart
@@ -21,6 +21,7 @@
 library runtime.tools.kernel_service;
 
 import 'dart:async' show Future, ZoneSpecification, runZoned;
+import 'dart:convert' show utf8;
 import 'dart:io' show Platform, stderr hide FileSystemEntity;
 import 'dart:isolate';
 import 'dart:typed_data' show Uint8List;
@@ -38,7 +39,7 @@
 import 'package:kernel/target/vm.dart' show VmTarget;
 import 'package:vm/incremental_compiler.dart';
 
-const bool verbose = const bool.fromEnvironment('DFE_VERBOSE');
+final bool verbose = new bool.fromEnvironment('DFE_VERBOSE');
 const String platformKernelFile = 'virtual_platform_kernel.dill';
 
 // NOTE: Any changes to these tags need to be reflected in kernel_isolate.cc
@@ -51,11 +52,13 @@
 //   3 - APP JIT snapshot training run for kernel_service.
 //   4 - Compile an individual expression in some context (for debugging
 //       purposes).
+//   5 - List program dependencies (for creating depfiles)
 const int kCompileTag = 0;
 const int kUpdateSourcesTag = 1;
 const int kAcceptTag = 2;
 const int kTrainTag = 3;
 const int kCompileExpressionTag = 4;
+const int kListDependenciesTag = 5;
 
 bool allowDartInternalImport = false;
 
@@ -106,14 +109,12 @@
             printMessage = false; // errors are printed by VM
             errors.add(message.formatted);
             break;
-          case Severity.nit:
-            printMessage = false;
-            break;
           case Severity.warning:
             printMessage = !suppressWarnings;
             break;
           case Severity.errorLegacyWarning:
           case Severity.context:
+          case Severity.ignored:
             throw "Unexpected severity: $severity";
         }
         if (printMessage) {
@@ -182,8 +183,10 @@
   }
 }
 
+// TODO(33428): This state is leaked on isolate shutdown.
 final Map<int, IncrementalCompilerWrapper> isolateCompilers =
     new Map<int, IncrementalCompilerWrapper>();
+final Map<int, List<Uri>> isolateDependencies = new Map<int, List<Uri>>();
 
 IncrementalCompilerWrapper lookupIncrementalCompiler(int isolateId) {
   return isolateCompilers[isolateId];
@@ -294,6 +297,54 @@
   port.send(result.toResponse());
 }
 
+void _recordDependencies(
+    int isolateId, Component component, String packageConfig) {
+  final dependencies = isolateDependencies[isolateId] ??= new List<Uri>();
+
+  for (var lib in component.libraries) {
+    if (lib.importUri.scheme == "dart") continue;
+
+    dependencies.add(lib.fileUri);
+    for (var part in lib.parts) {
+      final fileUri = lib.fileUri.resolve(part.partUri);
+      if (fileUri.scheme != "" && fileUri.scheme != "file") {
+        // E.g. part 'package:foo/foo.dart';
+        // Maybe the front end should resolve this?
+        continue;
+      }
+      dependencies.add(fileUri);
+    }
+  }
+
+  if (packageConfig != null) {
+    dependencies.add(Uri.parse(packageConfig));
+  }
+}
+
+String _escapeDependency(Uri uri) {
+  return uri.toFilePath().replaceAll("\\", "\\\\").replaceAll(" ", "\\ ");
+}
+
+List<int> _serializeDependencies(List<Uri> uris) {
+  return utf8.encode(uris.map(_escapeDependency).join(" "));
+}
+
+Future _processListDependenciesRequest(request) async {
+  final SendPort port = request[1];
+  final int isolateId = request[6];
+
+  final List<Uri> dependencies = isolateDependencies[isolateId] ?? <Uri>[];
+
+  CompilationResult result;
+  try {
+    result = new CompilationResult.ok(_serializeDependencies(dependencies));
+  } catch (error, stack) {
+    result = new CompilationResult.crash(error, stack);
+  }
+
+  port.send(result.toResponse());
+}
+
 Future _processLoadRequest(request) async {
   if (verbose) print("DFE: request: $request");
 
@@ -304,6 +355,11 @@
     return;
   }
 
+  if (tag == kListDependenciesTag) {
+    await _processListDependenciesRequest(request);
+    return;
+  }
+
   final SendPort port = request[1];
   final String inputFileUri = request[2];
   final Uri script =
@@ -387,6 +443,7 @@
     }
 
     Component component = await compiler.compile(script);
+    _recordDependencies(isolateId, component, packageConfig);
 
     if (compiler.errors.isNotEmpty) {
       result = new CompilationResult.errors(compiler.errors,
diff --git a/pkg/vm/lib/bytecode/assembler.dart b/pkg/vm/lib/bytecode/assembler.dart
index fdf239e..d5fa43b 100644
--- a/pkg/vm/lib/bytecode/assembler.dart
+++ b/pkg/vm/lib/bytecode/assembler.dart
@@ -246,8 +246,8 @@
     emitWord(_encodeAD(Opcode.kPushPolymorphicInstanceCallByRange, ra, rd));
   }
 
-  void emitNativeCall(int ra, int rb, int rc) {
-    emitWord(_encodeABC(Opcode.kNativeCall, ra, rb, rc));
+  void emitNativeCall(int rd) {
+    emitWord(_encodeD(Opcode.kNativeCall, rd));
   }
 
   void emitOneByteStringFromCharCode(int ra, int rx) {
diff --git a/pkg/vm/lib/bytecode/constant_pool.dart b/pkg/vm/lib/bytecode/constant_pool.dart
index 6de7663..b6b0ad1 100644
--- a/pkg/vm/lib/bytecode/constant_pool.dart
+++ b/pkg/vm/lib/bytecode/constant_pool.dart
@@ -153,6 +153,11 @@
   Byte tag = 22;
 }
 
+type ConstantNativeEntry extends ConstantPoolEntry {
+  Byte tag = 23;
+  StringReference nativeName;
+}
+
 */
 
 enum ConstantTag {
@@ -179,6 +184,7 @@
   kContextOffset,
   kClosureFunction,
   kEndClosureFunctionScope,
+  kNativeEntry,
 }
 
 abstract class ConstantPoolEntry {
@@ -243,6 +249,8 @@
         return new ConstantClosureFunction.readFromBinary(source);
       case ConstantTag.kEndClosureFunctionScope:
         return new ConstantEndClosureFunctionScope.readFromBinary(source);
+      case ConstantTag.kNativeEntry:
+        return new ConstantNativeEntry.readFromBinary(source);
     }
     throw 'Unexpected constant tag $tag';
   }
@@ -1006,6 +1014,33 @@
   // [hashCode] and [operator ==].
 }
 
+class ConstantNativeEntry extends ConstantPoolEntry {
+  final String nativeName;
+
+  ConstantNativeEntry(this.nativeName);
+
+  @override
+  ConstantTag get tag => ConstantTag.kNativeEntry;
+
+  @override
+  void writeValueToBinary(BinarySink sink) {
+    sink.writeStringReference(nativeName);
+  }
+
+  ConstantNativeEntry.readFromBinary(BinarySource source)
+      : nativeName = source.readStringReference();
+
+  @override
+  String toString() => 'NativeEntry $nativeName';
+
+  @override
+  int get hashCode => nativeName.hashCode;
+
+  @override
+  bool operator ==(other) =>
+      other is ConstantNativeEntry && this.nativeName == other.nativeName;
+}
+
 class ConstantPool {
   final List<ConstantPoolEntry> entries = <ConstantPoolEntry>[];
   final Map<ConstantPoolEntry, int> _canonicalizationCache =
diff --git a/pkg/vm/lib/bytecode/dbc.dart b/pkg/vm/lib/bytecode/dbc.dart
index 53a6975..c2e6216 100644
--- a/pkg/vm/lib/bytecode/dbc.dart
+++ b/pkg/vm/lib/bytecode/dbc.dart
@@ -15,6 +15,9 @@
 //    parameters. This DBC instruction was removed at
 //    https://github.com/dart-lang/sdk/commit/cf1de7d46cd88e204380e8f96a993439be56b24c
 //
+// 3. NativeCall instruction is modified to have 'D' format and take 1 argument:
+//    D = index of NativeEntry constant pool entry
+//
 
 enum Opcode {
   kTrap,
@@ -302,7 +305,7 @@
   Opcode.kPushPolymorphicInstanceCallByRange: const Format(
       Encoding.kAD, const [Operand.imm, Operand.imm, Operand.none]),
   Opcode.kNativeCall: const Format(
-      Encoding.kABC, const [Operand.imm, Operand.imm, Operand.imm]),
+      Encoding.kD, const [Operand.lit, Operand.none, Operand.none]),
   Opcode.kOneByteStringFromCharCode: const Format(
       Encoding.kAX, const [Operand.reg, Operand.xeg, Operand.none]),
   Opcode.kStringToCharCode: const Format(
diff --git a/pkg/vm/lib/bytecode/gen_bytecode.dart b/pkg/vm/lib/bytecode/gen_bytecode.dart
index d2d12b3..797bc67 100644
--- a/pkg/vm/lib/bytecode/gen_bytecode.dart
+++ b/pkg/vm/lib/bytecode/gen_bytecode.dart
@@ -8,6 +8,7 @@
 import 'package:kernel/class_hierarchy.dart' show ClassHierarchy;
 import 'package:kernel/clone.dart';
 import 'package:kernel/core_types.dart' show CoreTypes;
+import 'package:kernel/external_name.dart' show getExternalName;
 import 'package:kernel/library_index.dart' show LibraryIndex;
 import 'package:kernel/transformations/constants.dart'
     show ConstantEvaluator, ConstantsBackend, EvaluationEnvironment;
@@ -103,7 +104,7 @@
 
   @override
   defaultMember(Member node) {
-    if (node.isAbstract || node.isExternal) {
+    if (node.isAbstract) {
       return;
     }
     try {
@@ -124,9 +125,17 @@
         if (node is Constructor) {
           _genConstructorInitializers(node);
         }
-        node.function?.body?.accept(this);
-        // TODO(alexmarkov): figure out when 'return null' should be generated.
-        _genPushNull();
+        if (node.isExternal) {
+          final String nativeName = getExternalName(node);
+          if (nativeName == null) {
+            return;
+          }
+          _genNativeCall(nativeName);
+        } else {
+          node.function?.body?.accept(this);
+          // TODO(alexmarkov): figure out when 'return null' should be generated.
+          _genPushNull();
+        }
         _genReturnTOS();
         end(node);
       }
@@ -137,6 +146,27 @@
     }
   }
 
+  void _genNativeCall(String nativeName) {
+    final function = enclosingMember.function;
+    assert(function != null);
+
+    if (locals.hasTypeArgsVar) {
+      asm.emitPush(locals.typeArgsVarIndexInFrame);
+    }
+    if (locals.hasReceiver) {
+      asm.emitPush(locals.getVarIndexInFrame(locals.receiverVar));
+    }
+    for (var param in function.positionalParameters) {
+      asm.emitPush(locals.getVarIndexInFrame(param));
+    }
+    for (var param in function.namedParameters) {
+      asm.emitPush(locals.getVarIndexInFrame(param));
+    }
+
+    final nativeEntryCpIndex = cp.add(new ConstantNativeEntry(nativeName));
+    asm.emitNativeCall(nativeEntryCpIndex);
+  }
+
   LibraryIndex _libraryIndex;
   LibraryIndex get libraryIndex =>
       _libraryIndex ??= new LibraryIndex.coreLibraries(component);
diff --git a/pkg/vm/lib/frontend_server.dart b/pkg/vm/lib/frontend_server.dart
index 38b2e10..e484146 100644
--- a/pkg/vm/lib/frontend_server.dart
+++ b/pkg/vm/lib/frontend_server.dart
@@ -29,7 +29,8 @@
 import 'package:path/path.dart' as path;
 import 'package:usage/uuid/uuid.dart';
 import 'package:vm/incremental_compiler.dart' show IncrementalCompiler;
-import 'package:vm/kernel_front_end.dart' show compileToKernel;
+import 'package:vm/kernel_front_end.dart'
+    show compileToKernel, parseCommandLineDefines;
 
 ArgParser argParser = new ArgParser(allowTrailingOptions: true)
   ..addFlag('train',
@@ -92,7 +93,10 @@
       help: 'Normally the output dill is used to specify which dill to '
           'initialize from, but it can be overwritten here.',
       defaultsTo: null,
-      hide: true);
+      hide: true)
+  ..addMultiOption('define',
+      abbr: 'D',
+      help: 'The values for the environment constants (e.g. -Dkey=value).');
 
 String usage = '''
 Usage: server [options] [input.dart]
@@ -259,14 +263,12 @@
             printMessage = true;
             errors.add(message.formatted);
             break;
-          case Severity.nit:
-            printMessage = false;
-            break;
           case Severity.warning:
             printMessage = true;
             break;
           case Severity.errorLegacyWarning:
           case Severity.context:
+          case Severity.ignored:
             throw 'Unexpected severity: $severity';
         }
         if (printMessage) {
@@ -292,6 +294,12 @@
       }
     }
 
+    final Map<String, String> environmentDefines = {};
+    if (!parseCommandLineDefines(
+        options['define'], environmentDefines, usage)) {
+      return false;
+    }
+
     final TargetFlags targetFlags = new TargetFlags(
         strongMode: options['strong'], syncAsync: options['sync-async']);
     compilerOptions.target = getTarget(options['target'], targetFlags);
@@ -322,7 +330,8 @@
           _mainSource, compilerOptions,
           aot: options['aot'],
           useGlobalTypeFlowAnalysis: options['tfa'],
-          entryPoints: options['entry-points']));
+          entryPoints: options['entry-points'],
+          environmentDefines: environmentDefines));
     }
     if (component != null) {
       if (transformer != null) {
diff --git a/pkg/vm/lib/kernel_front_end.dart b/pkg/vm/lib/kernel_front_end.dart
index 72a6607..928cac8 100644
--- a/pkg/vm/lib/kernel_front_end.dart
+++ b/pkg/vm/lib/kernel_front_end.dart
@@ -330,3 +330,22 @@
     return node == null ? TreeNode.noOffset : node.fileOffset;
   }
 }
+
+bool parseCommandLineDefines(
+    List<String> dFlags, Map<String, String> environmentDefines, String usage) {
+  for (final String dflag in dFlags) {
+    final equalsSignIndex = dflag.indexOf('=');
+    if (equalsSignIndex < 0) {
+      environmentDefines[dflag] = '';
+    } else if (equalsSignIndex > 0) {
+      final key = dflag.substring(0, equalsSignIndex);
+      final value = dflag.substring(equalsSignIndex + 1);
+      environmentDefines[key] = value;
+    } else {
+      print('The environment constant options must have a key (was: "$dflag")');
+      print(usage);
+      return false;
+    }
+  }
+  return true;
+}
diff --git a/pkg/vm/lib/transformations/type_flow/native_code.dart b/pkg/vm/lib/transformations/type_flow/native_code.dart
index 8e4a171..cc078c6 100644
--- a/pkg/vm/lib/transformations/type_flow/native_code.dart
+++ b/pkg/vm/lib/transformations/type_flow/native_code.dart
@@ -10,12 +10,9 @@
 import 'dart:io' show File;
 
 import 'package:kernel/ast.dart';
-import 'package:kernel/library_index.dart' show LibraryIndex;
 import 'package:kernel/core_types.dart' show CoreTypes;
-
-// TODO(alexmarkov): Move findNativeName out of treeshaker and avoid dependency
-// on unrelated transformation.
-import 'package:kernel/transformations/treeshaker.dart' show findNativeName;
+import 'package:kernel/external_name.dart' show getExternalName;
+import 'package:kernel/library_index.dart' show LibraryIndex;
 
 import 'calls.dart';
 import 'types.dart';
@@ -108,7 +105,7 @@
   /// using [entryPointsListener]. Returns result type of the native method.
   Type handleNativeProcedure(
       Member member, EntryPointsListener entryPointsListener) {
-    final String nativeName = findNativeName(member);
+    final String nativeName = getExternalName(member);
     Type returnType = null;
 
     final nativeActions = _nativeMethods[nativeName];
diff --git a/pkg/vm/testcases/bytecode/bootstrapping.dart.expect b/pkg/vm/testcases/bytecode/bootstrapping.dart.expect
index c6c2c4e..8df59b8 100644
--- a/pkg/vm/testcases/bytecode/bootstrapping.dart.expect
+++ b/pkg/vm/testcases/bytecode/bootstrapping.dart.expect
@@ -67,11 +67,44 @@
 ]  constructor _() → void
     : super core::Object::•()
     ;
-  @_in::ExternalName::•("Namespace_Create")
+[@vm.bytecode=
+Bytecode {
+  Entry                0
+  CheckStack
+  Push                 FP[-6]
+  Push                 FP[-5]
+  NativeCall           CP#0
+  ReturnTOS
+}
+ConstantPool {
+  [0] = NativeEntry Namespace_Create
+}
+]  @_in::ExternalName::•("Namespace_Create")
   external static method _create(self::_NamespaceImpl namespace, dynamic n) → self::_NamespaceImpl;
-  @_in::ExternalName::•("Namespace_GetPointer")
+[@vm.bytecode=
+Bytecode {
+  Entry                0
+  CheckStack
+  Push                 FP[-5]
+  NativeCall           CP#0
+  ReturnTOS
+}
+ConstantPool {
+  [0] = NativeEntry Namespace_GetPointer
+}
+]  @_in::ExternalName::•("Namespace_GetPointer")
   external static method _getPointer(self::_NamespaceImpl namespace) → core::int;
-  @_in::ExternalName::•("Namespace_GetDefault")
+[@vm.bytecode=
+Bytecode {
+  Entry                0
+  CheckStack
+  NativeCall           CP#0
+  ReturnTOS
+}
+ConstantPool {
+  [0] = NativeEntry Namespace_GetDefault
+}
+]  @_in::ExternalName::•("Namespace_GetDefault")
   external static method _getDefault() → core::int;
 [@vm.bytecode=
 Bytecode {
@@ -512,7 +545,18 @@
 }
 ]static field core::int _stderrFD = 2;
 static field core::String _rawScript;
-@_in::ExternalName::•("Builtin_PrintString")
+[@vm.bytecode=
+Bytecode {
+  Entry                0
+  CheckStack
+  Push                 FP[-5]
+  NativeCall           CP#0
+  ReturnTOS
+}
+ConstantPool {
+  [0] = NativeEntry Builtin_PrintString
+}
+]@_in::ExternalName::•("Builtin_PrintString")
 external static method _printString(core::String s) → void;
 [@vm.bytecode=
 Bytecode {
diff --git a/runtime/BUILD.gn b/runtime/BUILD.gn
index 2d4aa56..29f6545 100644
--- a/runtime/BUILD.gn
+++ b/runtime/BUILD.gn
@@ -229,19 +229,15 @@
 }
 
 action("generate_version_cc_file") {
-  deps = [
-    "third_party/double-conversion/src:libdouble_conversion",
-    "vm:libdart_lib_jit",
-    "vm:libdart_lib_nosnapshot_with_precompiler",
-    "vm:libdart_vm_jit",
-    "vm:libdart_vm_nosnapshot_with_precompiler",
-  ]
   inputs = [
     "../tools/utils.py",
     "../tools/print_version.py",
     "../tools/VERSION",
     "vm/version_in.cc",
   ]
+  if (dart_version_git_info) {
+    inputs += [ "../.git/logs/HEAD" ]
+  }
   output = "$target_gen_dir/version.cc"
   outputs = [
     output,
diff --git a/runtime/bin/builtin.dart b/runtime/bin/builtin.dart
index 811ed14..b562e34 100644
--- a/runtime/bin/builtin.dart
+++ b/runtime/bin/builtin.dart
@@ -52,7 +52,9 @@
 // either a Uri or a List<int>.
 Future<T> _makeLoaderRequest<T>(int tag, String uri) {
   assert(_isolateId != null);
-  assert(_loadPort != null);
+  if (_loadPort == null) {
+    throw new UnsupportedError("Service isolate is not available.");
+  }
   Completer completer = new Completer<T>();
   RawReceivePort port = new RawReceivePort();
   port.handler = (msg) {
@@ -331,11 +333,13 @@
   }
 }
 
+// TODO(mfairhurst): remove this
 Future<Uri> _getPackageRootFuture() {
   if (_traceLoading) {
     _log("Request for package root from user code.");
   }
-  return _makeLoaderRequest<Uri>(_Dart_kGetPackageRootUri, null);
+  // Return null, as the `packages/` directory is not supported in dart 2.
+  return new Future.value(null);
 }
 
 Future<Uri> _getPackageConfigFuture() {
diff --git a/runtime/bin/crypto_fuchsia.cc b/runtime/bin/crypto_fuchsia.cc
index fed07cf..d5297ae 100644
--- a/runtime/bin/crypto_fuchsia.cc
+++ b/runtime/bin/crypto_fuchsia.cc
@@ -18,12 +18,11 @@
     const intptr_t remaining = count - read;
     const intptr_t len =
         (ZX_CPRNG_DRAW_MAX_LEN < remaining) ? ZX_CPRNG_DRAW_MAX_LEN : remaining;
-    size_t res = 0;
-    const zx_status_t status = zx_cprng_draw(buffer + read, len, &res);
+    const zx_status_t status = zx_cprng_draw_new(buffer + read, len);
     if (status != ZX_OK) {
       return false;
     }
-    read += res;
+    read += len;
   }
   return true;
 }
diff --git a/runtime/bin/gen_snapshot.cc b/runtime/bin/gen_snapshot.cc
index dd01633..4bddd36a 100644
--- a/runtime/bin/gen_snapshot.cc
+++ b/runtime/bin/gen_snapshot.cc
@@ -1528,12 +1528,19 @@
   if (app_script_name != NULL) {
     dfe.ReadScript(app_script_name, &kernel_buffer, &kernel_buffer_size);
   }
-  if (kernel_buffer != NULL && !SnapshotKindAllowedFromKernel()) {
-    // TODO(sivachandra): Add check for the kernel program format (incremental
-    // vs batch).
-    Log::PrintErr(
-        "Can only generate core or aot snapshots from a kernel file.\n");
-    return kErrorExitCode;
+  if (kernel_buffer != NULL) {
+    if (!SnapshotKindAllowedFromKernel()) {
+      // TODO(sivachandra): Add check for the kernel program format (incremental
+      // vs batch).
+      Log::PrintErr(
+          "Can only generate core or aot snapshots from a kernel file.\n");
+      return kErrorExitCode;
+    }
+    if ((dependencies_filename != NULL) || print_dependencies ||
+        dependencies_only) {
+      Log::PrintErr("Depfiles are not supported in Dart 2.\n");
+      return kErrorExitCode;
+    }
   }
 
   if (!Platform::Initialize()) {
@@ -1684,8 +1691,7 @@
     CHECK_RESULT(result);
 
     // Setup package root if specified.
-    result = DartUtils::SetupPackageRoot(commandline_package_root,
-                                         commandline_packages_file);
+    result = DartUtils::SetupPackageRoot(NULL, commandline_packages_file);
     CHECK_RESULT(result);
 
     UriResolverIsolateScope::isolate = isolate;
diff --git a/runtime/bin/main.cc b/runtime/bin/main.cc
index 59b994e..b3c71de 100644
--- a/runtime/bin/main.cc
+++ b/runtime/bin/main.cc
@@ -37,6 +37,8 @@
 #include "bin/gzip.h"
 #endif
 
+#include "vm/flags.h"
+
 extern "C" {
 extern const uint8_t kDartVmSnapshotData[];
 extern const uint8_t kDartVmSnapshotInstructions[];
@@ -191,6 +193,17 @@
     success &= file->Print("%s ", dep);
     free(dep);
   }
+  if (Options::preview_dart_2()) {
+    Dart_KernelCompilationResult result = Dart_KernelListDependencies();
+    if (result.status != Dart_KernelCompilationStatus_Ok) {
+      ErrorExit(
+          kErrorExitCode,
+          "Error: Failed to fetch dependencies from kernel service: %s\n\n",
+          result.error);
+    }
+    success &= file->WriteFully(result.kernel, result.kernel_size);
+    free(result.kernel);
+  }
   success &= file->Print("\n");
   if (!success) {
     ErrorExit(kErrorExitCode, "Error: Unable to write snapshot depfile: %s\n\n",
@@ -291,13 +304,15 @@
   result = DartUtils::PrepareForScriptLoading(false, Options::trace_loading());
   CHECK_RESULT(result);
 
-  // Set up the load port provided by the service isolate so that we can
-  // load scripts.
-  result = DartUtils::SetupServiceLoadPort();
-  CHECK_RESULT(result);
+  if (FLAG_support_service || !kDartPrecompiledRuntime) {
+    // Set up the load port provided by the service isolate so that we can
+    // load scripts.
+    result = DartUtils::SetupServiceLoadPort();
+    CHECK_RESULT(result);
+  }
 
   // Setup package root if specified.
-  result = DartUtils::SetupPackageRoot(package_root, packages_config);
+  result = DartUtils::SetupPackageRoot(NULL, packages_config);
   CHECK_RESULT(result);
   const char* resolved_packages_config = NULL;
   if (!Dart_IsNull(result)) {
@@ -363,11 +378,15 @@
     CHECK_RESULT(result);
   }
 
+  const char* namespc =
+      Dart_IsKernelIsolate(isolate) ? NULL : Options::namespc();
   if (isolate_run_app_snapshot) {
-    result = DartUtils::SetupIOLibrary(Options::namespc(), script_uri,
+    result = DartUtils::SetupIOLibrary(namespc, script_uri,
                                        Options::exit_disabled());
     CHECK_RESULT(result);
-    Loader::InitForSnapshot(script_uri);
+    if (FLAG_support_service || !kDartPrecompiledRuntime) {
+      Loader::InitForSnapshot(script_uri);
+    }
 #if !defined(DART_PRECOMPILED_RUNTIME)
     if (is_main_isolate) {
       // Find the canonical uri of the app snapshot. We'll use this to decide if
@@ -405,7 +424,7 @@
                        Dart_GetMainPortId(), Dart_Timeline_Event_Async_End, 0,
                        NULL, NULL);
 
-    result = DartUtils::SetupIOLibrary(Options::namespc(), script_uri,
+    result = DartUtils::SetupIOLibrary(namespc, script_uri,
                                        Options::exit_disabled());
     CHECK_RESULT(result);
 #else
diff --git a/runtime/bin/main_options.cc b/runtime/bin/main_options.cc
index 4fca3b2..0282762 100644
--- a/runtime/bin/main_options.cc
+++ b/runtime/bin/main_options.cc
@@ -352,25 +352,8 @@
       // Check if this flag is a potentially valid VM flag.
       const char* kChecked = "-c";
       const char* kCheckedFull = "--checked";
-      const char* kPackageRoot = "-p";
-      if (strncmp(argv[i], kPackageRoot, strlen(kPackageRoot)) == 0) {
-        // If argv[i] + strlen(kPackageRoot) is \0, then look in argv[i + 1]
-        // Otherwise set Option::package_root_ = argv[i] + strlen(kPackageRoot)
-        const char* opt = argv[i] + strlen(kPackageRoot);
-        if (opt[0] == '\0') {
-          i++;
-          opt = argv[i];
-          if ((opt == NULL) || (opt[0] == '-')) {
-            Log::PrintErr("Invalid option specification : '%s'\n", argv[i - 1]);
-            i++;
-            break;
-          }
-        }
-        package_root_ = opt;
-        i++;
-        continue;  // '-p' is not a VM flag so don't add to vm options.
-      } else if ((strncmp(argv[i], kChecked, strlen(kChecked)) == 0) ||
-                 (strncmp(argv[i], kCheckedFull, strlen(kCheckedFull)) == 0)) {
+      if ((strncmp(argv[i], kChecked, strlen(kChecked)) == 0) ||
+          (strncmp(argv[i], kCheckedFull, strlen(kCheckedFull)) == 0)) {
         checked_set = true;
         vm_options->AddArgument(kCheckedFull);
         i++;
diff --git a/runtime/bin/vmservice/loader.dart b/runtime/bin/vmservice/loader.dart
index 81d9529..e1b1468 100644
--- a/runtime/bin/vmservice/loader.dart
+++ b/runtime/bin/vmservice/loader.dart
@@ -279,7 +279,7 @@
       // Explicitly specified .packages path.
       _handlePackagesRequest(sp, _traceLoading, -2, packageConfig);
     } else {
-      // Search for .packages or packages/ starting at the root script.
+      // Search for .packages starting at the root script.
       _handlePackagesRequest(sp, _traceLoading, -1, _rootScript);
     }
 
@@ -806,24 +806,6 @@
         _loadPackagesFile(sp, traceLoading, packagesFile);
         return;
       }
-      // On the first loop try whether there is a packages/ directory instead.
-      if (prev == null) {
-        var packageRoot = dirUri.resolve("packages/");
-        if (traceLoading) {
-          _log("Checking for $packageRoot directory.");
-        }
-        exists = await new Directory.fromUri(packageRoot).exists();
-        if (traceLoading) {
-          _log("$packageRoot exists: $exists");
-        }
-        if (exists) {
-          if (traceLoading) {
-            _log("Found a package root at: $packageRoot");
-          }
-          sp.send([packageRoot.toString()]);
-          return;
-        }
-      }
       // Move up one level.
       prev = dir;
       dir = dir.parent;
@@ -911,10 +893,8 @@
         var packagesUri = resource.resolve(".packages");
         var exists = await _loadHttpPackagesFile(sp, traceLoading, packagesUri);
         if (!exists) {
-          // If the loading of the .packages file failed for http/https based
-          // scripts then setup the package root.
-          var packageRoot = resource.resolve('packages/');
-          sp.send([packageRoot.toString()]);
+          // Loading of the .packages file failed for http/https based scripts
+          sp.send([null]);
         }
       } else {
         sp.send("Unsupported scheme used to locate .packages file: "
@@ -1058,8 +1038,8 @@
       break;
     case _Dart_kGetPackageRootUri:
       loaderState._triggerPackageResolution(() {
-        // Respond with the package root (if any) after package resolution.
-        sp.send(loaderState._packageRoot);
+        // The package root is deprecated and now always returns null.
+        sp.send(null);
       });
       break;
     case _Dart_kGetPackageConfigUri:
diff --git a/runtime/bin/vmservice/vmservice_io.dart b/runtime/bin/vmservice/vmservice_io.dart
index 9dc5954..3747f4e 100644
--- a/runtime/bin/vmservice/vmservice_io.dart
+++ b/runtime/bin/vmservice/vmservice_io.dart
@@ -220,7 +220,7 @@
   _signalSubscription = _signalWatch(ProcessSignal.SIGQUIT).listen(_onSignal);
 }
 
-@pragma("vm.entry_point")
+@pragma("vm.entry_point", !const bool.fromEnvironment("dart.vm.product"))
 main() {
   // Set embedder hooks.
   VMServiceEmbedderHooks.cleanup = cleanupCallback;
diff --git a/runtime/include/dart_api.h b/runtime/include/dart_api.h
index b5bdd1a..d7734c1 100644
--- a/runtime/include/dart_api.h
+++ b/runtime/include/dart_api.h
@@ -1508,6 +1508,51 @@
  */
 DART_EXPORT Dart_Handle Dart_InstanceGetType(Dart_Handle instance);
 
+/**
+ * Returns the name for the provided function or method.
+ *
+ * \return A valid string handle if no error occurs during the
+ *   operation.
+ */
+DART_EXPORT Dart_Handle Dart_FunctionName(Dart_Handle function);
+
+/**
+ * Returns a handle to the owner of a function.
+ *
+ * The owner of an instance method or a static method is its defining
+ * class. The owner of a top-level function is its defining
+ * library. The owner of the function of a non-implicit closure is the
+ * function of the method or closure that defines the non-implicit
+ * closure.
+ *
+ * \return A valid handle to the owner of the function, or an error
+ *   handle if the argument is not a valid handle to a function.
+ */
+DART_EXPORT Dart_Handle Dart_FunctionOwner(Dart_Handle function);
+
+/**
+ * Determines whether a function handle referes to a static function
+ * of method.
+ *
+ * For the purposes of the embedding API, a top-level function is
+ * implicitly declared static.
+ *
+ * \param function A handle to a function or method declaration.
+ * \param is_static Returns whether the function or method is declared static.
+ *
+ * \return A valid handle if no error occurs during the operation.
+ */
+DART_EXPORT Dart_Handle Dart_FunctionIsStatic(Dart_Handle function,
+                                              bool* is_static);
+
+/**
+ * Retrieves the function of a closure.
+ *
+ * \return A handle to the function of the closure, or an error handle if the
+ *   argument is not a closure.
+ */
+DART_EXPORT Dart_Handle Dart_ClosureFunction(Dart_Handle closure);
+
 /*
  * =============================
  * Numbers, Integers and Doubles
@@ -3199,6 +3244,8 @@
  *
  */
 
+// TODO(33433): Remove kernel service from the embedding API.
+
 typedef enum {
   Dart_KernelCompilationStatus_Unknown = -1,
   Dart_KernelCompilationStatus_Ok = 0,
@@ -3237,6 +3284,8 @@
                             bool incremental_compile,
                             const char* package_config);
 
+DART_EXPORT Dart_KernelCompilationResult Dart_KernelListDependencies();
+
 #define DART_KERNEL_ISOLATE_NAME "kernel-service"
 
 /*
diff --git a/runtime/lib/bigint_patch.dart b/runtime/lib/bigint_patch.dart
index 0b0cd0f..78b4298 100644
--- a/runtime/lib/bigint_patch.dart
+++ b/runtime/lib/bigint_patch.dart
@@ -2735,10 +2735,11 @@
   int _convert(_BigIntImpl x, Uint32List resultDigits) {
     var digits;
     var used;
-    if (x._isNegative || x.compareTo(_modulus) >= 0) {
+    if (x._isNegative || x._absCompare(_modulus) >= 0) {
       var remainder = x._rem(_modulus);
-      if (x._isNegative && !remainder._isNegative && remainder._used > 0) {
-        remainder = _modulus - remainder;
+      if (x._isNegative && remainder._used > 0) {
+        assert(remainder._isNegative);
+        remainder += _modulus;
       }
       assert(!remainder._isNegative);
       used = remainder._used;
diff --git a/runtime/lib/compact_hash.dart b/runtime/lib/compact_hash.dart
index fb3d938..21179eb 100644
--- a/runtime/lib/compact_hash.dart
+++ b/runtime/lib/compact_hash.dart
@@ -461,10 +461,6 @@
   static Set<R> _newEmpty<R>() => new _CompactLinkedHashSet<R>();
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this, newSet: _newEmpty);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   int get length => _usedData - _deletedKeys;
 
   E get first {
@@ -622,9 +618,6 @@
   static Set<R> _newEmpty<R>() => new _CompactLinkedIdentityHashSet<R>();
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this, newSet: _newEmpty);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
 }
 
 class _CompactLinkedCustomHashSet<E> extends _CompactLinkedHashSet<E> {
@@ -643,10 +636,6 @@
       : _validKey = (validKey != null) ? validKey : new _TypeTest<E>().test;
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   Set<E> toSet() =>
       new _CompactLinkedCustomHashSet<E>(_equality, _hasher, _validKey)
         ..addAll(this);
diff --git a/runtime/lib/immutable_map.dart b/runtime/lib/immutable_map.dart
index 2057a57..c9d51a8 100644
--- a/runtime/lib/immutable_map.dart
+++ b/runtime/lib/immutable_map.dart
@@ -14,10 +14,6 @@
       : _kvPairs = keyValuePairs;
 
   Map<K2, V2> cast<K2, V2>() => Map.castFrom<K, V, K2, V2>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<K2, V2> retype<K2, V2>() => cast<K2, V2>();
-
   V operator [](Object key) {
     // To preserve the key-value order of the map literal, the keys are
     // not sorted. Need to do linear search or implement an additional
diff --git a/runtime/lib/isolate.cc b/runtime/lib/isolate.cc
index f4f53b2..289c4aa 100644
--- a/runtime/lib/isolate.cc
+++ b/runtime/lib/isolate.cc
@@ -217,8 +217,8 @@
             message, ILLEGAL_PORT, Message::kNormalPriority));
       }
 
-      const char* utf8_package_root =
-          packageRoot.IsNull() ? NULL : String2UTF8(packageRoot);
+      // TODO(mfairhurst) remove package_root, as it no longer does anything.
+      const char* utf8_package_root = NULL;
       const char* utf8_package_config =
           packageConfig.IsNull() ? NULL : String2UTF8(packageConfig);
 
@@ -343,8 +343,8 @@
     ThrowIsolateSpawnException(msg);
   }
 
-  const char* utf8_package_root =
-      packageRoot.IsNull() ? NULL : String2UTF8(packageRoot);
+  // TODO(mfairhurst) remove package_root, as it no longer does anything.
+  const char* utf8_package_root = NULL;
   const char* utf8_package_config =
       packageConfig.IsNull() ? NULL : String2UTF8(packageConfig);
 
diff --git a/runtime/lib/isolate_patch.dart b/runtime/lib/isolate_patch.dart
index 354aa46..67be54a 100644
--- a/runtime/lib/isolate_patch.dart
+++ b/runtime/lib/isolate_patch.dart
@@ -343,10 +343,8 @@
       // The VM will invoke [_startIsolate] with entryPoint as argument.
       readyPort = new RawReceivePort();
 
-      // We do not inherit the package root or package config settings
-      // from the parent isolate, instead we use the values that were
-      // set on the command line.
-      var packageRoot = VMLibraryHooks.packageRootString;
+      // We do not inherit the package config settings from the parent isolate,
+      // instead we use the values that were set on the command line.
       var packageConfig = VMLibraryHooks.packageConfigString;
       var script = VMLibraryHooks.platformScript;
       if (script == null) {
@@ -359,7 +357,7 @@
       }
 
       _spawnFunction(readyPort.sendPort, script.toString(), entryPoint, message,
-          paused, errorsAreFatal, onExit, onError, packageRoot, packageConfig);
+          paused, errorsAreFatal, onExit, onError, null, packageConfig);
       return await _spawnCommon(readyPort);
     } catch (e, st) {
       if (readyPort != null) {
@@ -419,11 +417,9 @@
 
       // Ensure to resolve package: URIs being handed in as parameters.
       if (packageRoot != null) {
-        // Avoid calling resolvePackageUri if not stricly necessary in case
-        // the API is not supported.
-        if (packageRoot.scheme == "package") {
-          packageRoot = await Isolate.resolvePackageUri(packageRoot);
-        }
+        // `packages/` directory is no longer supported. Force it null.
+        // TODO(mfairhurst) Should this throw an exception?
+        packageRoot = null;
       } else if (packageConfig != null) {
         // Avoid calling resolvePackageUri if not strictly necessary in case
         // the API is not supported.
diff --git a/runtime/lib/typed_data_patch.dart b/runtime/lib/typed_data_patch.dart
index b3aaf23..29ab7b7 100644
--- a/runtime/lib/typed_data_patch.dart
+++ b/runtime/lib/typed_data_patch.dart
@@ -124,10 +124,6 @@
       new FollowedByIterable<int>.firstEfficient(this, other);
 
   List<R> cast<R>() => List.castFrom<int, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   void set first(int value) {
     if (this.length == 0) throw new RangeError.index(0, this);
     this[0] = value;
@@ -485,10 +481,6 @@
       new FollowedByIterable<double>.firstEfficient(this, other);
 
   List<R> cast<R>() => List.castFrom<double, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   void set first(double value) {
     if (this.length == 0) throw new RangeError.index(0, this);
     this[0] = value;
@@ -849,10 +841,6 @@
       new FollowedByIterable<Float32x4>.firstEfficient(this, other);
 
   List<R> cast<R>() => List.castFrom<Float32x4, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   void set first(Float32x4 value) {
     if (this.length == 0) throw new RangeError.index(0, this);
     this[0] = value;
@@ -1217,10 +1205,6 @@
       new FollowedByIterable<Int32x4>.firstEfficient(this, other);
 
   List<R> cast<R>() => List.castFrom<Int32x4, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   void set first(Int32x4 value) {
     if (this.length == 0) throw new RangeError.index(0, this);
     this[0] = value;
@@ -1584,10 +1568,6 @@
       new FollowedByIterable<Float64x2>.firstEfficient(this, other);
 
   List<R> cast<R>() => List.castFrom<Float64x2, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   void set first(Float64x2 value) {
     if (this.length == 0) throw new RangeError.index(0, this);
     this[0] = value;
diff --git a/runtime/observatory/tests/service/external_service_asynchronous_invocation_test.dart b/runtime/observatory/tests/service/external_service_asynchronous_invocation_test.dart
index c467159..fb56834 100644
--- a/runtime/observatory/tests/service/external_service_asynchronous_invocation_test.dart
+++ b/runtime/observatory/tests/service/external_service_asynchronous_invocation_test.dart
@@ -24,7 +24,7 @@
 
     // Avoid to manually encode and decode messages from the stream
     Stream<String> stream = socket.stream.map(jsonEncode);
-    stream.retype<Object>().pipe(_socket);
+    stream.cast<Object>().pipe(_socket);
     dynamic _decoder(dynamic obj) {
       return jsonDecode(obj);
     }
diff --git a/runtime/observatory/tests/service/external_service_disappear_test.dart b/runtime/observatory/tests/service/external_service_disappear_test.dart
index 7f39fad..5c9764e 100644
--- a/runtime/observatory/tests/service/external_service_disappear_test.dart
+++ b/runtime/observatory/tests/service/external_service_disappear_test.dart
@@ -24,7 +24,7 @@
 
     // Avoid to manually encode and decode messages from the stream
     Stream<String> stream = socket.stream.map(jsonEncode);
-    stream.retype<Object>().pipe(_socket);
+    stream.cast<Object>().pipe(_socket);
     dynamic _decoder(dynamic obj) {
       return jsonDecode(obj);
     }
diff --git a/runtime/observatory/tests/service/external_service_notification_invocation_test.dart b/runtime/observatory/tests/service/external_service_notification_invocation_test.dart
index 2c064af..cab8b5b 100644
--- a/runtime/observatory/tests/service/external_service_notification_invocation_test.dart
+++ b/runtime/observatory/tests/service/external_service_notification_invocation_test.dart
@@ -27,10 +27,10 @@
 
     // Avoid to manually encode and decode messages from the stream
     Stream<String> socket_stream = socket.stream.map(jsonEncode);
-    socket_stream.retype<Object>().pipe(_socket);
+    socket_stream.cast<Object>().pipe(_socket);
     Stream<String> socket_invoker_stream =
         socket_invoker.stream.map(jsonEncode);
-    socket_invoker_stream.retype<Object>().pipe(_socket_invoker);
+    socket_invoker_stream.cast<Object>().pipe(_socket_invoker);
     dynamic _decoder(dynamic obj) {
       return jsonDecode(obj);
     }
diff --git a/runtime/observatory/tests/service/external_service_registration_test.dart b/runtime/observatory/tests/service/external_service_registration_test.dart
index 3b6cfa0..7fb325b 100644
--- a/runtime/observatory/tests/service/external_service_registration_test.dart
+++ b/runtime/observatory/tests/service/external_service_registration_test.dart
@@ -27,7 +27,7 @@
 
     // Avoid to manually encode and decode messages from the stream
     Stream<String> socket_stream = socket.stream.map(jsonEncode);
-    socket_stream.retype<Object>().pipe(_socket);
+    socket_stream.cast<Object>().pipe(_socket);
     dynamic _decoder(dynamic obj) {
       return jsonDecode(obj);
     }
diff --git a/runtime/observatory/tests/service/external_service_registration_via_notification_test.dart b/runtime/observatory/tests/service/external_service_registration_via_notification_test.dart
index 846f28b..0f05750 100644
--- a/runtime/observatory/tests/service/external_service_registration_via_notification_test.dart
+++ b/runtime/observatory/tests/service/external_service_registration_via_notification_test.dart
@@ -27,7 +27,7 @@
 
     // Avoid to manually encode and decode messages from the stream
     Stream<String> stream = socket.stream.map(jsonEncode);
-    stream.retype<Object>().pipe(_socket);
+    stream.cast<Object>().pipe(_socket);
     dynamic _decoder(dynamic obj) {
       return jsonDecode(obj);
     }
diff --git a/runtime/observatory/tests/service/external_service_synchronous_invocation_test.dart b/runtime/observatory/tests/service/external_service_synchronous_invocation_test.dart
index 43405ad..b16e5ff 100644
--- a/runtime/observatory/tests/service/external_service_synchronous_invocation_test.dart
+++ b/runtime/observatory/tests/service/external_service_synchronous_invocation_test.dart
@@ -24,7 +24,7 @@
 
     // Avoid to manually encode and decode messages from the stream
     Stream<String> stream = socket.stream.map(jsonEncode);
-    stream.retype<Object>().pipe(_socket);
+    stream.cast<Object>().pipe(_socket);
     dynamic _decoder(dynamic obj) {
       return jsonDecode(obj);
     }
diff --git a/runtime/vm/compiler/aot/precompiler.cc b/runtime/vm/compiler/aot/precompiler.cc
index e419327..ff286b6 100644
--- a/runtime/vm/compiler/aot/precompiler.cc
+++ b/runtime/vm/compiler/aot/precompiler.cc
@@ -342,7 +342,6 @@
       I->object_store()->set_future_class(null_class);
       I->object_store()->set_pragma_class(null_class);
       I->object_store()->set_completer_class(null_class);
-      I->object_store()->set_stream_iterator_class(null_class);
       I->object_store()->set_symbol_class(null_class);
       I->object_store()->set_compiletime_error_class(null_class);
       I->object_store()->set_simple_instance_of_function(null_function);
diff --git a/runtime/vm/compiler/assembler/assembler_arm.h b/runtime/vm/compiler/assembler/assembler_arm.h
index ab6f811..10b2c61 100644
--- a/runtime/vm/compiler/assembler/assembler_arm.h
+++ b/runtime/vm/compiler/assembler/assembler_arm.h
@@ -767,6 +767,13 @@
 
   void LoadIsolate(Register rd);
 
+  // Load word from pool from the given offset using encoding that
+  // InstructionPattern::DecodeLoadWordFromPool can decode.
+  void LoadWordFromPoolOffset(Register rd,
+                              int32_t offset,
+                              Register pp,
+                              Condition cond);
+
   void LoadObject(Register rd, const Object& object, Condition cond = AL);
   void LoadUniqueObject(Register rd, const Object& object, Condition cond = AL);
   void LoadFunctionFromCalleePool(Register dst,
@@ -1110,11 +1117,6 @@
   void BindARMv6(Label* label);
   void BindARMv7(Label* label);
 
-  void LoadWordFromPoolOffset(Register rd,
-                              int32_t offset,
-                              Register pp,
-                              Condition cond);
-
   void BranchLink(const ExternalLabel* label);
 
   class CodeComment : public ZoneAllocated {
diff --git a/runtime/vm/compiler/assembler/assembler_arm64.h b/runtime/vm/compiler/assembler/assembler_arm64.h
index b0d94c2..368e4a3 100644
--- a/runtime/vm/compiler/assembler/assembler_arm64.h
+++ b/runtime/vm/compiler/assembler/assembler_arm64.h
@@ -1493,6 +1493,10 @@
   void LoadImmediate(Register reg, int64_t imm);
   void LoadDImmediate(VRegister reg, double immd);
 
+  // Load word from pool from the given offset using encoding that
+  // InstructionPattern::DecodeLoadWordFromPool can decode.
+  void LoadWordFromPoolOffset(Register dst, uint32_t offset, Register pp = PP);
+
   void PushObject(const Object& object) {
     LoadObject(TMP, object);
     Push(TMP);
@@ -1618,7 +1622,6 @@
 
   bool constant_pool_allowed_;
 
-  void LoadWordFromPoolOffset(Register dst, uint32_t offset, Register pp = PP);
   void LoadWordFromPoolOffsetFixed(Register dst, uint32_t offset);
 
   void LoadObjectHelper(Register dst, const Object& obj, bool is_unique);
diff --git a/runtime/vm/compiler/backend/flow_graph.cc b/runtime/vm/compiler/backend/flow_graph.cc
index 510052d..5f55e9f 100644
--- a/runtime/vm/compiler/backend/flow_graph.cc
+++ b/runtime/vm/compiler/backend/flow_graph.cc
@@ -2266,6 +2266,144 @@
   InsertAfter(instr, extract, NULL, FlowGraph::kValue);
 }
 
+//
+// Static helpers for the flow graph utilities.
+//
+
+static TargetEntryInstr* NewTarget(FlowGraph* graph, Instruction* inherit) {
+  TargetEntryInstr* target = new (graph->zone())
+      TargetEntryInstr(graph->allocate_block_id(),
+                       inherit->GetBlock()->try_index(), Thread::kNoDeoptId);
+  target->InheritDeoptTarget(graph->zone(), inherit);
+  return target;
+}
+
+static JoinEntryInstr* NewJoin(FlowGraph* graph, Instruction* inherit) {
+  JoinEntryInstr* join = new (graph->zone())
+      JoinEntryInstr(graph->allocate_block_id(),
+                     inherit->GetBlock()->try_index(), Thread::kNoDeoptId);
+  join->InheritDeoptTarget(graph->zone(), inherit);
+  return join;
+}
+
+static GotoInstr* NewGoto(FlowGraph* graph,
+                          JoinEntryInstr* target,
+                          Instruction* inherit) {
+  GotoInstr* got = new (graph->zone()) GotoInstr(target, Thread::kNoDeoptId);
+  got->InheritDeoptTarget(graph->zone(), inherit);
+  return got;
+}
+
+static BranchInstr* NewBranch(FlowGraph* graph,
+                              ComparisonInstr* cmp,
+                              Instruction* inherit) {
+  BranchInstr* bra = new (graph->zone()) BranchInstr(cmp, Thread::kNoDeoptId);
+  bra->InheritDeoptTarget(graph->zone(), inherit);
+  return bra;
+}
+
+//
+// Flow graph utilities.
+//
+
+// Constructs new diamond decision at the given instruction.
+//
+//               ENTRY
+//             instruction
+//            if (compare)
+//              /   \
+//           B_TRUE B_FALSE
+//              \   /
+//               JOIN
+//
+JoinEntryInstr* FlowGraph::NewDiamond(Instruction* instruction,
+                                      Instruction* inherit,
+                                      ComparisonInstr* compare,
+                                      TargetEntryInstr** b_true,
+                                      TargetEntryInstr** b_false) {
+  BlockEntryInstr* entry = instruction->GetBlock();
+
+  TargetEntryInstr* bt = NewTarget(this, inherit);
+  TargetEntryInstr* bf = NewTarget(this, inherit);
+  JoinEntryInstr* join = NewJoin(this, inherit);
+  GotoInstr* gotot = NewGoto(this, join, inherit);
+  GotoInstr* gotof = NewGoto(this, join, inherit);
+  BranchInstr* bra = NewBranch(this, compare, inherit);
+
+  instruction->AppendInstruction(bra);
+  entry->set_last_instruction(bra);
+
+  *bra->true_successor_address() = bt;
+  *bra->false_successor_address() = bf;
+
+  bt->AppendInstruction(gotot);
+  bt->set_last_instruction(gotot);
+
+  bf->AppendInstruction(gotof);
+  bf->set_last_instruction(gotof);
+
+  // Update dominance relation incrementally.
+  for (intptr_t i = 0, n = entry->dominated_blocks().length(); i < n; ++i) {
+    join->AddDominatedBlock(entry->dominated_blocks()[i]);
+  }
+  entry->ClearDominatedBlocks();
+  entry->AddDominatedBlock(bt);
+  entry->AddDominatedBlock(bf);
+  entry->AddDominatedBlock(join);
+
+  // TODO(ajcbik): update pred/succ/ordering incrementally too.
+
+  // Return new blocks.
+  *b_true = bt;
+  *b_false = bf;
+  return join;
+}
+
+JoinEntryInstr* FlowGraph::NewDiamond(Instruction* instruction,
+                                      Instruction* inherit,
+                                      const LogicalAnd& condition,
+                                      TargetEntryInstr** b_true,
+                                      TargetEntryInstr** b_false) {
+  // First diamond for first comparison.
+  TargetEntryInstr* bt = nullptr;
+  TargetEntryInstr* bf = nullptr;
+  JoinEntryInstr* mid_point =
+      NewDiamond(instruction, inherit, condition.oper1, &bt, &bf);
+
+  // Short-circuit second comparison and connect through phi.
+  condition.oper2->InsertAfter(bt);
+  AllocateSSAIndexes(condition.oper2);
+  condition.oper2->InheritDeoptTarget(zone(), inherit);  // must inherit
+  PhiInstr* phi =
+      AddPhi(mid_point, condition.oper2, GetConstant(Bool::False()));
+  StrictCompareInstr* circuit = new (zone()) StrictCompareInstr(
+      inherit->token_pos(), Token::kEQ_STRICT, new (zone()) Value(phi),
+      new (zone()) Value(GetConstant(Bool::True())), false,
+      Thread::kNoDeoptId);  // don't inherit
+
+  // Return new blocks through the second diamond.
+  return NewDiamond(mid_point, inherit, circuit, b_true, b_false);
+}
+
+PhiInstr* FlowGraph::AddPhi(JoinEntryInstr* join,
+                            Definition* d1,
+                            Definition* d2) {
+  PhiInstr* phi = new (zone()) PhiInstr(join, 2);
+  Value* v1 = new (zone()) Value(d1);
+  Value* v2 = new (zone()) Value(d2);
+
+  AllocateSSAIndexes(phi);
+
+  phi->mark_alive();
+  phi->SetInputAt(0, v1);
+  phi->SetInputAt(1, v2);
+  d1->AddInputUse(v1);
+  d2->AddInputUse(v2);
+  join->InsertPhi(phi);
+
+  return phi;
+}
+
 }  // namespace dart
 
 #endif  // !defined(DART_PRECOMPILED_RUNTIME)
diff --git a/runtime/vm/compiler/backend/flow_graph.h b/runtime/vm/compiler/backend/flow_graph.h
index dbd7564..d82b788 100644
--- a/runtime/vm/compiler/backend/flow_graph.h
+++ b/runtime/vm/compiler/backend/flow_graph.h
@@ -351,6 +351,37 @@
 
   bool should_print() const { return should_print_; }
 
+  //
+  // High-level utilities.
+  //
+
+  // Logical-AND (for use in short-circuit diamond).
+  struct LogicalAnd {
+    LogicalAnd(ComparisonInstr* x, ComparisonInstr* y) : oper1(x), oper2(y) {}
+    ComparisonInstr* oper1;
+    ComparisonInstr* oper2;
+  };
+
+  // Constructs a diamond control flow at the instruction, inheriting
+  // properties from inherit and using the given compare. Returns the
+  // join (and true/false blocks in out parameters). Updates dominance
+  // relation, but not the succ/pred ordering on block.
+  JoinEntryInstr* NewDiamond(Instruction* instruction,
+                             Instruction* inherit,
+                             ComparisonInstr* compare,
+                             TargetEntryInstr** block_true,
+                             TargetEntryInstr** block_false);
+
+  // As above, but with a short-circuit on two comparisons.
+  JoinEntryInstr* NewDiamond(Instruction* instruction,
+                             Instruction* inherit,
+                             const LogicalAnd& condition,
+                             TargetEntryInstr** block_true,
+                             TargetEntryInstr** block_false);
+
+  // Adds a 2-way phi.
+  PhiInstr* AddPhi(JoinEntryInstr* join, Definition* d1, Definition* d2);
+
  private:
   friend class IfConverter;
   friend class BranchSimplifier;
diff --git a/runtime/vm/compiler/backend/flow_graph_compiler.cc b/runtime/vm/compiler/backend/flow_graph_compiler.cc
index 9b611ee..9716e1c 100644
--- a/runtime/vm/compiler/backend/flow_graph_compiler.cc
+++ b/runtime/vm/compiler/backend/flow_graph_compiler.cc
@@ -631,8 +631,8 @@
                                       TokenPosition token_pos,
                                       intptr_t try_index) {
   code_source_map_builder_->NoteDescriptor(kind, pc_offset, token_pos);
-  // When running with optimizations disabled, don't emit deopt-descriptors.
-  if (!CanOptimize() && (kind == RawPcDescriptors::kDeopt)) return;
+  // Don't emit deopt-descriptors in AOT mode.
+  if (FLAG_precompiled_mode && (kind == RawPcDescriptors::kDeopt)) return;
   pc_descriptors_list_->AddDescriptor(kind, pc_offset, deopt_id, token_pos,
                                       try_index);
 }
diff --git a/runtime/vm/compiler/backend/flow_graph_compiler_arm.cc b/runtime/vm/compiler/backend/flow_graph_compiler_arm.cc
index 6d150d3..6233ee3 100644
--- a/runtime/vm/compiler/backend/flow_graph_compiler_arm.cc
+++ b/runtime/vm/compiler/backend/flow_graph_compiler_arm.cc
@@ -743,7 +743,8 @@
   __ LoadField(R9,
                FieldAddress(kDstTypeReg,
                             AbstractType::type_test_stub_entry_point_offset()));
-  __ ldr(kSubtypeTestCacheReg, Address(PP, sub_type_cache_offset));
+  __ LoadWordFromPoolOffset(kSubtypeTestCacheReg, sub_type_cache_offset, PP,
+                            AL);
   __ blx(R9);
   EmitCallsiteMetadata(token_pos, deopt_id, RawPcDescriptors::kOther, locs);
   __ Bind(&done);
diff --git a/runtime/vm/compiler/backend/flow_graph_compiler_arm64.cc b/runtime/vm/compiler/backend/flow_graph_compiler_arm64.cc
index cef314e..d46f351 100644
--- a/runtime/vm/compiler/backend/flow_graph_compiler_arm64.cc
+++ b/runtime/vm/compiler/backend/flow_graph_compiler_arm64.cc
@@ -721,7 +721,7 @@
   __ LoadField(R9,
                FieldAddress(kDstTypeReg,
                             AbstractType::type_test_stub_entry_point_offset()));
-  __ ldr(kSubtypeTestCacheReg, Address(PP, sub_type_cache_offset));
+  __ LoadWordFromPoolOffset(kSubtypeTestCacheReg, sub_type_cache_offset);
   __ blr(R9);
   EmitCallsiteMetadata(token_pos, deopt_id, RawPcDescriptors::kOther, locs);
   __ Bind(&done);
diff --git a/runtime/vm/compiler/backend/inliner.cc b/runtime/vm/compiler/backend/inliner.cc
index 2643894..65f2d38 100644
--- a/runtime/vm/compiler/backend/inliner.cc
+++ b/runtime/vm/compiler/backend/inliner.cc
@@ -1708,8 +1708,8 @@
 
 bool PolymorphicInliner::TryInlineRecognizedMethod(intptr_t receiver_cid,
                                                    const Function& target) {
-  TargetEntryInstr* entry;
-  Definition* last;
+  TargetEntryInstr* entry = nullptr;
+  Instruction* last = nullptr;
   // Replace the receiver argument with a redefinition to prevent code from
   // the inlined body from being hoisted above the inlined entry.
   GrowableArray<Definition*> arguments(call_->ArgumentCount());
@@ -1723,14 +1723,14 @@
           call_->instance_call()->token_pos(),
           call_->instance_call()->ic_data(), &entry, &last,
           owner_->inliner_->speculative_policy())) {
+    ASSERT(last->IsDefinition());
     // Create a graph fragment.
     redefinition->InsertAfter(entry);
     InlineExitCollector* exit_collector =
         new (Z) InlineExitCollector(owner_->caller_graph(), call_);
-
-    ReturnInstr* result =
-        new (Z) ReturnInstr(call_->instance_call()->token_pos(),
-                            new (Z) Value(last), Thread::kNoDeoptId);
+    ReturnInstr* result = new (Z)
+        ReturnInstr(call_->instance_call()->token_pos(),
+                    new (Z) Value(last->AsDefinition()), Thread::kNoDeoptId);
     owner_->caller_graph()->AppendTo(
         last, result,
         call_->env(),  // Return can become deoptimization target.
@@ -1838,15 +1838,18 @@
     } else {
       // For all variants except the last, use a branch on the loaded class
       // id.
+      //
+      // TODO(ajcbik): see if this can use the NewDiamond() utility.
+      //
       const Smi& cid = Smi::ZoneHandle(Smi::New(variant.cid_start));
       ConstantInstr* cid_constant = owner_->caller_graph()->GetConstant(cid);
       BranchInstr* branch;
       BranchInstr* upper_limit_branch = NULL;
       BlockEntryInstr* cid_test_entry_block = current_block;
       if (test_is_range) {
-        // Double branch for testing a range of Cids.  TODO(erikcorry): Make a
-        // special instruction that uses subtraction and unsigned comparison to
-        // do this with a single branch.
+        // Double branch for testing a range of Cids.
+        // TODO(ajcbik): Make a special instruction that uses subtraction
+        // and unsigned comparison to do this with a single branch.
         const Smi& cid_end = Smi::ZoneHandle(Smi::New(variant.cid_end));
         ConstantInstr* cid_constant_end =
             owner_->caller_graph()->GetConstant(cid_end);
@@ -2320,7 +2323,7 @@
                              Instruction* call,
                              Definition* receiver,
                              TargetEntryInstr** entry,
-                             Definition** last,
+                             Instruction** last,
                              bool can_speculate) {
   intptr_t array_cid = MethodRecognizer::MethodKindToReceiverCid(kind);
 
@@ -2344,15 +2347,16 @@
 
   // Array load and return.
   intptr_t index_scale = Instance::ElementSizeFor(array_cid);
-  *last = new (Z)
+  LoadIndexedInstr* load = new (Z)
       LoadIndexedInstr(new (Z) Value(array), new (Z) Value(index), index_scale,
                        array_cid, kAlignedAccess, deopt_id, call->token_pos());
+  *last = load;
   cursor = flow_graph->AppendTo(
-      cursor, *last, deopt_id != Thread::kNoDeoptId ? call->env() : NULL,
+      cursor, load, deopt_id != Thread::kNoDeoptId ? call->env() : NULL,
       FlowGraph::kValue);
 
   if (array_cid == kTypedDataFloat32ArrayCid) {
-    *last = new (Z) FloatToDoubleInstr(new (Z) Value(*last), deopt_id);
+    *last = new (Z) FloatToDoubleInstr(new (Z) Value(load), deopt_id);
     flow_graph->AppendTo(cursor, *last,
                          deopt_id != Thread::kNoDeoptId ? call->env() : NULL,
                          FlowGraph::kValue);
@@ -2368,7 +2372,7 @@
                              TokenPosition token_pos,
                              const Cids* value_check,
                              TargetEntryInstr** entry,
-                             Definition** last) {
+                             Instruction** last) {
   intptr_t array_cid = MethodRecognizer::MethodKindToReceiverCid(kind);
 
   Definition* array = receiver;
@@ -2507,7 +2511,7 @@
                            Instruction* call,
                            Definition* receiver,
                            TargetEntryInstr** entry,
-                           Definition** last) {
+                           Instruction** last) {
   if (!CanUnboxDouble()) {
     return false;
   }
@@ -2533,7 +2537,7 @@
                                Definition* receiver,
                                MethodRecognizer::Kind kind,
                                TargetEntryInstr** entry,
-                               Definition** last) {
+                               Instruction** last) {
   if (!CanUnboxDouble()) {
     return false;
   }
@@ -2556,7 +2560,7 @@
                                    Instruction* call,
                                    Definition* receiver,
                                    TargetEntryInstr** entry,
-                                   Definition** last) {
+                                   Instruction** last) {
   Definition* left = receiver;
   Definition* right = call->ArgumentAt(1);
 
@@ -2580,7 +2584,7 @@
                                       Instruction* call,
                                       Definition* receiver,
                                       TargetEntryInstr** entry,
-                                      Definition** last) {
+                                      Instruction** last) {
   Definition* array = receiver;
   Definition* value = call->ArgumentAt(1);
 
@@ -2599,82 +2603,152 @@
   return true;
 }
 
-static void PrepareInlineByteArrayBaseOp(FlowGraph* flow_graph,
-                                         Instruction* call,
-                                         intptr_t array_cid,
-                                         intptr_t view_cid,
-                                         Definition** array,
-                                         Definition* byte_index,
-                                         Instruction** cursor,
-                                         bool needs_bounds_check) {
-  if (needs_bounds_check) {
-    LoadFieldInstr* length = new (Z) LoadFieldInstr(
-        new (Z) Value(*array), CheckArrayBoundInstr::LengthOffsetFor(array_cid),
-        Type::ZoneHandle(Z, Type::SmiType()), call->token_pos());
-    length->set_is_immutable(true);
-    length->set_result_cid(kSmiCid);
-    length->set_recognized_kind(
-        LoadFieldInstr::RecognizedKindFromArrayCid(array_cid));
-    *cursor = flow_graph->AppendTo(*cursor, length, NULL, FlowGraph::kValue);
+// Adds an explicit bounds check for a typed getter/setter.
+static void PrepareInlineTypedArrayBoundsCheck(FlowGraph* flow_graph,
+                                               Instruction* call,
+                                               intptr_t array_cid,
+                                               intptr_t view_cid,
+                                               Definition* array,
+                                               Definition* byte_index,
+                                               Instruction** cursor) {
+  ASSERT(array_cid != kDynamicCid);
 
-    intptr_t element_size = Instance::ElementSizeFor(array_cid);
-    ConstantInstr* bytes_per_element =
-        flow_graph->GetConstant(Smi::Handle(Z, Smi::New(element_size)));
-    BinarySmiOpInstr* len_in_bytes = new (Z)
-        BinarySmiOpInstr(Token::kMUL, new (Z) Value(length),
-                         new (Z) Value(bytes_per_element), call->deopt_id());
-    *cursor = flow_graph->AppendTo(*cursor, len_in_bytes, call->env(),
+  LoadFieldInstr* length = new (Z) LoadFieldInstr(
+      new (Z) Value(array), CheckArrayBoundInstr::LengthOffsetFor(array_cid),
+      Type::ZoneHandle(Z, Type::SmiType()), call->token_pos());
+  length->set_is_immutable(true);
+  length->set_result_cid(kSmiCid);
+  length->set_recognized_kind(
+      LoadFieldInstr::RecognizedKindFromArrayCid(array_cid));
+  *cursor = flow_graph->AppendTo(*cursor, length, NULL, FlowGraph::kValue);
+
+  intptr_t element_size = Instance::ElementSizeFor(array_cid);
+  ConstantInstr* bytes_per_element =
+      flow_graph->GetConstant(Smi::Handle(Z, Smi::New(element_size)));
+  BinarySmiOpInstr* len_in_bytes = new (Z)
+      BinarySmiOpInstr(Token::kMUL, new (Z) Value(length),
+                       new (Z) Value(bytes_per_element), call->deopt_id());
+  *cursor = flow_graph->AppendTo(*cursor, len_in_bytes, call->env(),
+                                 FlowGraph::kValue);
+
+  // adjusted_length = len_in_bytes - (element_size - 1).
+  Definition* adjusted_length = len_in_bytes;
+  intptr_t adjustment = Instance::ElementSizeFor(view_cid) - 1;
+  if (adjustment > 0) {
+    ConstantInstr* length_adjustment =
+        flow_graph->GetConstant(Smi::Handle(Z, Smi::New(adjustment)));
+    adjusted_length = new (Z)
+        BinarySmiOpInstr(Token::kSUB, new (Z) Value(len_in_bytes),
+                         new (Z) Value(length_adjustment), call->deopt_id());
+    *cursor = flow_graph->AppendTo(*cursor, adjusted_length, call->env(),
                                    FlowGraph::kValue);
-
-    // adjusted_length = len_in_bytes - (element_size - 1).
-    Definition* adjusted_length = len_in_bytes;
-    intptr_t adjustment = Instance::ElementSizeFor(view_cid) - 1;
-    if (adjustment > 0) {
-      ConstantInstr* length_adjustment =
-          flow_graph->GetConstant(Smi::Handle(Z, Smi::New(adjustment)));
-      adjusted_length = new (Z)
-          BinarySmiOpInstr(Token::kSUB, new (Z) Value(len_in_bytes),
-                           new (Z) Value(length_adjustment), call->deopt_id());
-      *cursor = flow_graph->AppendTo(*cursor, adjusted_length, call->env(),
-                                     FlowGraph::kValue);
-    }
-
-    // Check adjusted_length > 0.
-    ConstantInstr* zero = flow_graph->GetConstant(Smi::Handle(Z, Smi::New(0)));
-    *cursor = flow_graph->AppendTo(
-        *cursor,
-        new (Z) CheckArrayBoundInstr(new (Z) Value(adjusted_length),
-                                     new (Z) Value(zero), call->deopt_id()),
-        call->env(), FlowGraph::kEffect);
-    // Check 0 <= byte_index < adjusted_length.
-    *cursor = flow_graph->AppendTo(
-        *cursor,
-        new (Z)
-            CheckArrayBoundInstr(new (Z) Value(adjusted_length),
-                                 new (Z) Value(byte_index), call->deopt_id()),
-        call->env(), FlowGraph::kEffect);
   }
 
-  if (RawObject::IsExternalTypedDataClassId(array_cid)) {
+  // Check adjusted_length > 0.
+  ConstantInstr* zero = flow_graph->GetConstant(Smi::Handle(Z, Smi::New(0)));
+  *cursor = flow_graph->AppendTo(
+      *cursor,
+      new (Z) CheckArrayBoundInstr(new (Z) Value(adjusted_length),
+                                   new (Z) Value(zero), call->deopt_id()),
+      call->env(), FlowGraph::kEffect);
+
+  // Check 0 <= byte_index < adjusted_length.
+  *cursor = flow_graph->AppendTo(
+      *cursor,
+      new (Z) CheckArrayBoundInstr(new (Z) Value(adjusted_length),
+                                   new (Z) Value(byte_index), call->deopt_id()),
+      call->env(), FlowGraph::kEffect);
+}
+
+// Emits preparatory code for a typed getter/setter.
+// Handles three cases:
+//   (1) dynamic:  generates a conditional on the receiver cid
+//                 that handles external (load untagged) and
+//                 internal storage at runtime.
+//   (2) external: generates load untagged.
+//   (3) internal: no code required.
+static void PrepareInlineByteArrayBaseOp(FlowGraph* flow_graph,
+                                         Instruction* call,
+                                         Definition* receiver,
+                                         intptr_t array_cid,
+                                         Definition** array,
+                                         Instruction** cursor,
+                                         TargetEntryInstr** block_external,
+                                         TargetEntryInstr** block_internal) {
+  if (array_cid == kDynamicCid) {
+    // Dynamic case:   runtime resolution between external/internal typed data.
+    //                 cid = LoadCid
+    //                 if cid in [ kExternalTypedDataInt8ArrayCid,
+    //                             kExternalTypedDataFloat64x2ArrayCid ]
+    // block_external: LoadUntagged
+    //                 ..
+    //                 else
+    // block_internal: ..
+    //
+    // TODO(ajcbik): as suggested above, subtract + single unsigned test.
+    //
+    LoadClassIdInstr* load_cid =
+        new (Z) LoadClassIdInstr(new (Z) Value(receiver));
+    *cursor = flow_graph->AppendTo(*cursor, load_cid, NULL, FlowGraph::kValue);
+    ConstantInstr* cid_lo = flow_graph->GetConstant(
+        Smi::ZoneHandle(Smi::New(kExternalTypedDataInt8ArrayCid)));
+    RelationalOpInstr* le_lo = new (Z)
+        RelationalOpInstr(call->token_pos(), Token::kLTE, new (Z) Value(cid_lo),
+                          new (Z) Value(load_cid), kSmiCid, call->deopt_id());
+    ConstantInstr* cid_hi = flow_graph->GetConstant(
+        Smi::ZoneHandle(Smi::New(kExternalTypedDataFloat64x2ArrayCid)));
+    RelationalOpInstr* le_hi = new (Z) RelationalOpInstr(
+        call->token_pos(), Token::kLTE, new (Z) Value(load_cid),
+        new (Z) Value(cid_hi), kSmiCid, call->deopt_id());
+    *cursor = flow_graph->NewDiamond(*cursor, call,
+                                     FlowGraph::LogicalAnd(le_lo, le_hi),
+                                     block_external, block_internal);
+    LoadUntaggedInstr* elements = new (Z) LoadUntaggedInstr(
+        new (Z) Value(*array), ExternalTypedData::data_offset());
+    flow_graph->InsertAfter(*block_external, elements, NULL, FlowGraph::kValue);
+    *array = elements;  // return load untagged definition in array
+  } else if (RawObject::IsExternalTypedDataClassId(array_cid)) {
+    // External typed data: load untagged.
     LoadUntaggedInstr* elements = new (Z) LoadUntaggedInstr(
         new (Z) Value(*array), ExternalTypedData::data_offset());
     *cursor = flow_graph->AppendTo(*cursor, elements, NULL, FlowGraph::kValue);
     *array = elements;
+  } else {
+    // Internal typed data: no action.
   }
 }
 
+static LoadIndexedInstr* NewLoad(FlowGraph* flow_graph,
+                                 Instruction* call,
+                                 Definition* array,
+                                 Definition* index,
+                                 intptr_t view_cid) {
+  return new (Z) LoadIndexedInstr(new (Z) Value(array), new (Z) Value(index),
+                                  1,  // Index scale
+                                  view_cid, kUnalignedAccess,
+                                  Thread::kNoDeoptId, call->token_pos());
+}
+
 static bool InlineByteArrayBaseLoad(FlowGraph* flow_graph,
                                     Instruction* call,
                                     Definition* receiver,
                                     intptr_t array_cid,
                                     intptr_t view_cid,
                                     TargetEntryInstr** entry,
-                                    Definition** last) {
+                                    Instruction** last) {
   ASSERT(array_cid != kIllegalCid);
+
+  // Dynamic calls are polymorphic due to:
+  // (A) extra bounds check computations (length stored in receiver),
+  // (B) external/internal typed data in receiver.
+  // For Dart2, both issues are resolved in the inlined code.
   if (array_cid == kDynamicCid) {
     ASSERT(call->IsStaticCall());
-    return false;
+    if (!FLAG_strong) {
+      return false;
+    }
   }
+
   Definition* array = receiver;
   Definition* index = call->ArgumentAt(1);
   *entry = new (Z)
@@ -2684,36 +2758,73 @@
   Instruction* cursor = *entry;
 
   // All getters that go through InlineByteArrayBaseLoad() have explicit
-  // bounds checks in all their clients in the library, so we can omit
-  // yet another inlined bounds check when compiling for Dart2.
+  // bounds checks in all their clients in the library, so we can omit yet
+  // another inlined bounds check when compiling for Dart2 (resolves (A)).
   const bool needs_bounds_check = !FLAG_strong;
-
-  PrepareInlineByteArrayBaseOp(flow_graph, call, array_cid, view_cid, &array,
-                               index, &cursor, needs_bounds_check);
-
-  intptr_t deopt_id = Thread::kNoDeoptId;
-  if ((array_cid == kTypedDataInt32ArrayCid) ||
-      (array_cid == kTypedDataUint32ArrayCid)) {
-    // Deoptimization may be needed if result does not always fit in a Smi.
-    deopt_id = (kSmiBits >= 32) ? Thread::kNoDeoptId : call->deopt_id();
+  if (needs_bounds_check) {
+    PrepareInlineTypedArrayBoundsCheck(flow_graph, call, array_cid, view_cid,
+                                       array, index, &cursor);
   }
 
-  *last = new (Z)
-      LoadIndexedInstr(new (Z) Value(array), new (Z) Value(index), 1, view_cid,
-                       kUnalignedAccess, deopt_id, call->token_pos());
-  cursor = flow_graph->AppendTo(
-      cursor, *last, deopt_id != Thread::kNoDeoptId ? call->env() : NULL,
-      FlowGraph::kValue);
+  // Generates a template for the load, either a dynamic conditional
+  // that dispatches on external and internal storage, or a single
+  // case that deals with either external or internal storage.
+  TargetEntryInstr* block_external = nullptr;
+  TargetEntryInstr* block_internal = nullptr;
+  PrepareInlineByteArrayBaseOp(flow_graph, call, receiver, array_cid, &array,
+                               &cursor, &block_external, &block_internal);
+
+  // Fill out the generated template with loads.
+  if (array_cid == kDynamicCid) {
+    ASSERT(block_external != nullptr && block_internal != nullptr);
+    // Load from external in block_external and internal in block_internal
+    // (resolves (B)). The former loads from "array", which is the returned
+    // load untagged definition. The latter loads from the original "receiver".
+    LoadIndexedInstr* load1 = NewLoad(flow_graph, call, array, index, view_cid);
+    ASSERT(block_external->next() == array);
+    flow_graph->InsertAfter(
+        block_external->next(), load1,
+        call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
+        FlowGraph::kValue);
+    LoadIndexedInstr* load2 =
+        NewLoad(flow_graph, call, receiver, index, view_cid);
+    flow_graph->InsertAfter(
+        block_internal, load2,
+        call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
+        FlowGraph::kValue);
+    // Construct phi of external and internal load.
+    *last = flow_graph->AddPhi(cursor->AsJoinEntry(), load1, load2);
+  } else {
+    ASSERT(block_external == nullptr && block_internal == nullptr);
+    // Load from either external or internal.
+    LoadIndexedInstr* load = NewLoad(flow_graph, call, array, index, view_cid);
+    flow_graph->AppendTo(
+        cursor, load,
+        call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
+        FlowGraph::kValue);
+    cursor = *last = load;
+  }
 
   if (view_cid == kTypedDataFloat32ArrayCid) {
-    *last = new (Z) FloatToDoubleInstr(new (Z) Value(*last), deopt_id);
-    flow_graph->AppendTo(cursor, *last,
-                         deopt_id != Thread::kNoDeoptId ? call->env() : NULL,
-                         FlowGraph::kValue);
+    *last = new (Z) FloatToDoubleInstr(new (Z) Value((*last)->AsDefinition()),
+                                       Thread::kNoDeoptId);
+    flow_graph->AppendTo(cursor, *last, nullptr, FlowGraph::kValue);
   }
   return true;
 }
 
+static StoreIndexedInstr* NewStore(FlowGraph* flow_graph,
+                                   Instruction* call,
+                                   Definition* array,
+                                   Definition* index,
+                                   Definition* stored_value,
+                                   intptr_t view_cid) {
+  return new (Z) StoreIndexedInstr(
+      new (Z) Value(array), new (Z) Value(index), new (Z) Value(stored_value),
+      kNoStoreBarrier, 1,  // Index scale
+      view_cid, kUnalignedAccess, call->deopt_id(), call->token_pos());
+}
+
 static bool InlineByteArrayBaseStore(FlowGraph* flow_graph,
                                      const Function& target,
                                      Instruction* call,
@@ -2721,12 +2832,20 @@
                                      intptr_t array_cid,
                                      intptr_t view_cid,
                                      TargetEntryInstr** entry,
-                                     Definition** last) {
+                                     Instruction** last) {
   ASSERT(array_cid != kIllegalCid);
+
+  // Dynamic calls are polymorphic due to:
+  // (A) extra bounds check computations (length stored in receiver),
+  // (B) external/internal typed data in receiver.
+  // For Dart2, both issues are resolved in the inlined code.
   if (array_cid == kDynamicCid) {
     ASSERT(call->IsStaticCall());
-    return false;
+    if (!FLAG_strong) {
+      return false;
+    }
   }
+
   Definition* array = receiver;
   Definition* index = call->ArgumentAt(1);
   *entry = new (Z)
@@ -2735,15 +2854,16 @@
   (*entry)->InheritDeoptTarget(Z, call);
   Instruction* cursor = *entry;
 
-  // All setters that go through InlineByteArrayBaseStore() have explicit
-  // bounds checks in all their clients in the library, so we can omit
-  // yet another inlined bounds check when compiling for Dart2.
+  // All setters that go through InlineByteArrayBaseLoad() have explicit
+  // bounds checks in all their clients in the library, so we can omit yet
+  // another inlined bounds check when compiling for Dart2 (resolves (A)).
   const bool needs_bounds_check = !FLAG_strong;
+  if (needs_bounds_check) {
+    PrepareInlineTypedArrayBoundsCheck(flow_graph, call, array_cid, view_cid,
+                                       array, index, &cursor);
+  }
 
-  PrepareInlineByteArrayBaseOp(flow_graph, call, array_cid, view_cid, &array,
-                               index, &cursor, needs_bounds_check);
-
-  Cids* value_check = NULL;
+  Cids* value_check = nullptr;
   switch (view_cid) {
     case kTypedDataInt8ArrayCid:
     case kTypedDataUint8ArrayCid:
@@ -2789,7 +2909,7 @@
   }
 
   Definition* stored_value = call->ArgumentAt(2);
-  if (value_check != NULL) {
+  if (value_check != nullptr) {
     Instruction* check = flow_graph->CreateCheckClass(
         stored_value, *value_check, call->deopt_id(), call->token_pos());
     cursor =
@@ -2800,7 +2920,7 @@
     stored_value = new (Z)
         DoubleToFloatInstr(new (Z) Value(stored_value), call->deopt_id());
     cursor =
-        flow_graph->AppendTo(cursor, stored_value, NULL, FlowGraph::kValue);
+        flow_graph->AppendTo(cursor, stored_value, nullptr, FlowGraph::kValue);
   } else if (view_cid == kTypedDataInt32ArrayCid) {
     stored_value =
         new (Z) UnboxInt32Instr(UnboxInt32Instr::kTruncate,
@@ -2815,17 +2935,43 @@
                                   FlowGraph::kValue);
   }
 
-  StoreBarrierType needs_store_barrier = kNoStoreBarrier;
-  *last = new (Z) StoreIndexedInstr(
-      new (Z) Value(array), new (Z) Value(index), new (Z) Value(stored_value),
-      needs_store_barrier,
-      1,  // Index scale
-      view_cid, kUnalignedAccess, call->deopt_id(), call->token_pos());
+  // Generates a template for the store, either a dynamic conditional
+  // that dispatches on external and internal storage, or a single
+  // case that deals with either external or internal storage.
+  TargetEntryInstr* block_external = nullptr;
+  TargetEntryInstr* block_internal = nullptr;
+  PrepareInlineByteArrayBaseOp(flow_graph, call, receiver, array_cid, &array,
+                               &cursor, &block_external, &block_internal);
 
-  flow_graph->AppendTo(
-      cursor, *last,
-      call->deopt_id() != Thread::kNoDeoptId ? call->env() : NULL,
-      FlowGraph::kEffect);
+  // Fill out the generated template with stores.
+  if (array_cid == kDynamicCid) {
+    ASSERT(block_external != nullptr && block_internal != nullptr);
+    // Store to external in block_external and internal in block_internal
+    // (resolves (B)). The former stores to "array", which is the returned
+    // load untagged definition. The latter stores to the original "receiver".
+    ASSERT(block_external->next() == array);
+    flow_graph->InsertAfter(
+        block_external->next(),
+        NewStore(flow_graph, call, array, index, stored_value, view_cid),
+        call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
+        FlowGraph::kEffect);
+    flow_graph->InsertAfter(
+        block_internal,
+        NewStore(flow_graph, call, receiver, index, stored_value, view_cid),
+        call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
+        FlowGraph::kEffect);
+    *last = cursor;
+  } else {
+    ASSERT(block_external == nullptr && block_internal == nullptr);
+    // Store on either external or internal.
+    StoreIndexedInstr* store =
+        NewStore(flow_graph, call, array, index, stored_value, view_cid);
+    flow_graph->AppendTo(
+        cursor, store,
+        call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
+        FlowGraph::kEffect);
+    *last = store;
+  }
   return true;
 }
 
@@ -2876,7 +3022,7 @@
                                    Definition* receiver,
                                    intptr_t cid,
                                    TargetEntryInstr** entry,
-                                   Definition** last) {
+                                   Instruction** last) {
   if ((cid != kOneByteStringCid) && (cid != kExternalOneByteStringCid)) {
     return false;
   }
@@ -2890,8 +3036,8 @@
 
   *last = PrepareInlineStringIndexOp(flow_graph, call, cid, str, index, *entry);
 
-  OneByteStringFromCharCodeInstr* char_at =
-      new (Z) OneByteStringFromCharCodeInstr(new (Z) Value(*last));
+  OneByteStringFromCharCodeInstr* char_at = new (Z)
+      OneByteStringFromCharCodeInstr(new (Z) Value((*last)->AsDefinition()));
 
   flow_graph->AppendTo(*last, char_at, NULL, FlowGraph::kValue);
   *last = char_at;
@@ -2904,7 +3050,7 @@
                                    Definition* receiver,
                                    intptr_t cid,
                                    TargetEntryInstr** entry,
-                                   Definition** last) {
+                                   Instruction** last) {
   if (cid == kDynamicCid) {
     ASSERT(call->IsStaticCall());
     return false;
@@ -2935,9 +3081,8 @@
   GrowableArray<intptr_t> class_ids;
   call->ic_data()->GetCheckAt(0, &class_ids, &target);
   const intptr_t receiver_cid = class_ids[0];
-
-  TargetEntryInstr* entry;
-  Definition* last;
+  TargetEntryInstr* entry = nullptr;
+  Instruction* last = nullptr;
   if (FlowGraphInliner::TryInlineRecognizedMethod(
           flow_graph, receiver_cid, target, call,
           call->Receiver()->definition(), call->token_pos(), call->ic_data(),
@@ -2959,7 +3104,7 @@
     }
     // Replace all uses of this definition with the result.
     if (call->HasUses()) {
-      call->ReplaceUsesWith(last);
+      call->ReplaceUsesWith(last->AsDefinition());
     }
     // Finally insert the sequence other definition in place of this one in the
     // graph.
@@ -2968,6 +3113,7 @@
     }
     entry->UnuseAllInputs();  // Entry block is not in the graph.
     if (last != NULL) {
+      ASSERT(call->GetBlock() == last->GetBlock());
       last->LinkTo(call);
     }
     // Remove through the iterator.
@@ -2985,9 +3131,9 @@
     ForwardInstructionIterator* iterator,
     StaticCallInstr* call,
     SpeculativeInliningPolicy* policy) {
-  TargetEntryInstr* entry;
-  Definition* last;
-  Definition* receiver = NULL;
+  TargetEntryInstr* entry = nullptr;
+  Instruction* last = nullptr;
+  Definition* receiver = nullptr;
   intptr_t receiver_cid = kIllegalCid;
   if (!call->function().is_static()) {
     receiver = call->Receiver()->definition();
@@ -3004,7 +3150,8 @@
     }
     // Replace all uses of this definition with the result.
     if (call->HasUses()) {
-      call->ReplaceUsesWith(last);
+      ASSERT(last->IsDefinition());
+      call->ReplaceUsesWith(last->AsDefinition());
     }
     // Finally insert the sequence other definition in place of this one in the
     // graph.
@@ -3013,7 +3160,25 @@
     }
     entry->UnuseAllInputs();  // Entry block is not in the graph.
     if (last != NULL) {
-      last->LinkTo(call);
+      BlockEntryInstr* link = call->GetBlock();
+      Instruction* exit = last->GetBlock();
+      if (link != exit) {
+        // Dominance relation and SSA are updated incrementally when
+        // conditionals are inserted. But succ/pred and ordering needs
+        // to be redone. TODO(ajcbik): do this incrementally too.
+        link->ClearDominatedBlocks();
+        for (intptr_t i = 0, n = entry->dominated_blocks().length(); i < n;
+             ++i) {
+          link->AddDominatedBlock(entry->dominated_blocks()[i]);
+        }
+        while (exit->next()) {
+          exit = exit->next();
+        }
+        exit->LinkTo(call);
+        flow_graph->DiscoverBlocks();
+      } else {
+        last->LinkTo(call);
+      }
     }
     // Remove through the iterator.
     if (iterator != NULL) {
@@ -3045,7 +3210,7 @@
                          Definition* receiver,
                          MethodRecognizer::Kind kind,
                          TargetEntryInstr** entry,
-                         Definition** last) {
+                         Instruction** last) {
   if (!ShouldInlineSimd()) {
     return false;
   }
@@ -3115,7 +3280,7 @@
                                 Instruction* call,
                                 MethodRecognizer::Kind kind,
                                 TargetEntryInstr** entry,
-                                Definition** last) {
+                                Instruction** last) {
   if (!CanUnboxDouble()) {
     return false;
   }
@@ -3159,7 +3324,7 @@
     TokenPosition token_pos,
     const ICData* ic_data,
     TargetEntryInstr** entry,
-    Definition** last,
+    Instruction** last,
     SpeculativeInliningPolicy* policy) {
   const bool can_speculate = policy->IsAllowedForInlining(call->deopt_id());
 
diff --git a/runtime/vm/compiler/backend/inliner.h b/runtime/vm/compiler/backend/inliner.h
index 9c2664e..542f8c4 100644
--- a/runtime/vm/compiler/backend/inliner.h
+++ b/runtime/vm/compiler/backend/inliner.h
@@ -130,7 +130,7 @@
                                         TokenPosition token_pos,
                                         const ICData* ic_data,
                                         TargetEntryInstr** entry,
-                                        Definition** last,
+                                        Instruction** last,
                                         SpeculativeInliningPolicy* policy);
 
  private:
diff --git a/runtime/vm/compiler/call_specializer.cc b/runtime/vm/compiler/call_specializer.cc
index f6d8cac..41b3027 100644
--- a/runtime/vm/compiler/call_specializer.cc
+++ b/runtime/vm/compiler/call_specializer.cc
@@ -1,6 +1,7 @@
 // Copyright (c) 2017, 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.
+
 #ifndef DART_PRECOMPILED_RUNTIME
 #include "vm/compiler/call_specializer.h"
 
@@ -211,7 +212,14 @@
   }
 
   const Token::Kind op_kind = call->token_kind();
-  if (FLAG_guess_icdata_cid) {
+  if (FLAG_precompiled_mode && FLAG_strong && kBitsPerWord == 64) {
+    // Avoid speculation for AOT Dart2 64-bit targets.
+    //
+    // TODO(ajcbik): expand this to more and more targets as we
+    // investigate the performance impact of moving smi decision
+    // into a later phase.
+    //
+  } else if (FLAG_guess_icdata_cid) {
     if (FLAG_precompiled_mode) {
       // In precompiler speculate that both sides of bitwise operation
       // are Smi-s.
@@ -220,7 +228,6 @@
         class_ids[1] = kSmiCid;
       }
     }
-
     if (Token::IsRelationalOperator(op_kind) ||
         Token::IsEqualityOperator(op_kind) ||
         Token::IsBinaryOperator(op_kind)) {
diff --git a/runtime/vm/compiler/frontend/kernel_binary_flowgraph.cc b/runtime/vm/compiler/frontend/kernel_binary_flowgraph.cc
index 23c595e..b100719 100644
--- a/runtime/vm/compiler/frontend/kernel_binary_flowgraph.cc
+++ b/runtime/vm/compiler/frontend/kernel_binary_flowgraph.cc
@@ -3,6 +3,7 @@
 // BSD-style license that can be found in the LICENSE file.
 
 #include "vm/compiler/frontend/kernel_binary_flowgraph.h"
+#include "vm/code_descriptors.h"
 #include "vm/compiler/aot/precompiler.h"
 #include "vm/compiler/assembler/disassembler_kbc.h"
 #include "vm/compiler/frontend/prologue_builder.h"
@@ -1168,7 +1169,7 @@
           elem = pool.ObjectAt(elem_index);
           array.SetAt(j, elem);
         }
-        obj = H.Canonicalize(Array::Cast(obj));
+        obj = H.Canonicalize(Array::Cast(array));
         ASSERT(!obj.IsNull());
       } break;
       case ConstantPoolTag::kInstance: {
@@ -1354,37 +1355,62 @@
 }
 
 void BytecodeMetadataHelper::ReadExceptionsTable(const Code& bytecode) {
-  const ObjectPool& pool =
-      ObjectPool::Handle(builder_->zone_, bytecode.object_pool());
-  AbstractType& handled_type = AbstractType::Handle(builder_->zone_);
+  const intptr_t try_block_count = builder_->reader_.ReadListLength();
+  if (try_block_count > 0) {
+    const ObjectPool& pool =
+        ObjectPool::Handle(builder_->zone_, bytecode.object_pool());
+    AbstractType& handler_type = AbstractType::Handle(builder_->zone_);
+    Array& handler_types = Array::Handle(builder_->zone_);
+    DescriptorList* pc_descriptors_list =
+        new (builder_->zone_) DescriptorList(64);
+    ExceptionHandlerList* exception_handlers_list =
+        new (builder_->zone_) ExceptionHandlerList();
 
-  // Encoding of ExceptionsTable is described in
-  // pkg/vm/lib/bytecode/exceptions.dart.
-  intptr_t try_block_count = builder_->reader_.ReadListLength();
-  for (intptr_t i = 0; i < try_block_count; i++) {
-    intptr_t outer_try_index_plus1 = builder_->reader_.ReadUInt();
-    intptr_t outer_try_index = outer_try_index_plus1 - 1;
-    USE(outer_try_index);
-    intptr_t start_pc = builder_->reader_.ReadUInt();
-    USE(start_pc);
-    intptr_t end_pc = builder_->reader_.ReadUInt();
-    USE(end_pc);
-    intptr_t handler_pc = builder_->reader_.ReadUInt();
-    USE(handler_pc);
-    uint8_t flags = builder_->reader_.ReadByte();
-    // flagNeedsStackTrace = 1 << 0;
-    // flagIsSynthetic = 1 << 1;
-    USE(flags);
+    // Encoding of ExceptionsTable is described in
+    // pkg/vm/lib/bytecode/exceptions.dart.
+    for (intptr_t try_index = 0; try_index < try_block_count; try_index++) {
+      intptr_t outer_try_index_plus1 = builder_->reader_.ReadUInt();
+      intptr_t outer_try_index = outer_try_index_plus1 - 1;
+      intptr_t start_pc = builder_->reader_.ReadUInt();
+      intptr_t end_pc = builder_->reader_.ReadUInt();
+      intptr_t handler_pc = builder_->reader_.ReadUInt();
+      uint8_t flags = builder_->reader_.ReadByte();
+      const uint8_t kFlagNeedsStackTrace = 1 << 0;
+      const uint8_t kFlagIsSynthetic = 1 << 1;
+      const bool needs_stacktrace = (flags & kFlagNeedsStackTrace) != 0;
+      const bool is_generated = (flags & kFlagIsSynthetic) != 0;
+      intptr_t type_count = builder_->reader_.ReadListLength();
+      ASSERT(type_count > 0);
+      handler_types = Array::New(type_count, Heap::kOld);
+      for (intptr_t i = 0; i < type_count; i++) {
+        intptr_t type_index = builder_->reader_.ReadUInt();
+        ASSERT(type_index < pool.Length());
+        handler_type ^= pool.ObjectAt(type_index);
+        handler_types.SetAt(i, handler_type);
+      }
+      pc_descriptors_list->AddDescriptor(RawPcDescriptors::kOther, start_pc,
+                                         Thread::kNoDeoptId,
+                                         TokenPosition::kNoSource, try_index);
+      pc_descriptors_list->AddDescriptor(RawPcDescriptors::kOther, end_pc,
+                                         Thread::kNoDeoptId,
+                                         TokenPosition::kNoSource, -1);
 
-    intptr_t type_count = builder_->reader_.ReadListLength();
-    for (intptr_t j = 0; j < type_count; j++) {
-      intptr_t type_index = builder_->reader_.ReadUInt();
-      ASSERT(type_index < pool.Length());
-      handled_type ^= pool.ObjectAt(type_index);
+      exception_handlers_list->AddHandler(
+          try_index, outer_try_index, handler_pc, TokenPosition::kNoSource,
+          is_generated, handler_types, needs_stacktrace);
     }
+    const PcDescriptors& descriptors = PcDescriptors::Handle(
+        builder_->zone_,
+        pc_descriptors_list->FinalizePcDescriptors(bytecode.PayloadStart()));
+    bytecode.set_pc_descriptors(descriptors);
+    const ExceptionHandlers& handlers = ExceptionHandlers::Handle(
+        builder_->zone_, exception_handlers_list->FinalizeExceptionHandlers(
+                             bytecode.PayloadStart()));
+    bytecode.set_exception_handlers(handlers);
+  } else {
+    bytecode.set_pc_descriptors(Object::empty_descriptors());
+    bytecode.set_exception_handlers(Object::empty_exception_handlers());
   }
-  // TODO(regis): Generate exception handlers (as well as pc descriptors)
-  // and store in bytecode: bytecode.set_exception_handlers(exception_handlers);
 }
 #endif  // defined(DART_USE_INTERPRETER)
 
diff --git a/runtime/vm/dart.cc b/runtime/vm/dart.cc
index 034de31..6318284 100644
--- a/runtime/vm/dart.cc
+++ b/runtime/vm/dart.cc
@@ -307,15 +307,11 @@
     Service::SetGetServiceAssetsCallback(get_service_assets);
   }
 
-#if defined(DART_PRECOMPILED_RUNTIME)
-  const bool is_precompiled_runtime = true;
-#else
-  const bool is_precompiled_runtime = false;
-#endif
-
   const bool is_dart2_aot_precompiler =
-      FLAG_strong && FLAG_precompiled_mode && !is_precompiled_runtime;
-  if (!is_dart2_aot_precompiler) {
+      FLAG_strong && FLAG_precompiled_mode && !kDartPrecompiledRuntime;
+
+  if (!is_dart2_aot_precompiler &&
+      (FLAG_support_service || !kDartPrecompiledRuntime)) {
     ServiceIsolate::Run();
   }
 
diff --git a/runtime/vm/dart_api_impl.cc b/runtime/vm/dart_api_impl.cc
index 201b5b9..3109abd 100644
--- a/runtime/vm/dart_api_impl.cc
+++ b/runtime/vm/dart_api_impl.cc
@@ -2057,6 +2057,69 @@
   return Api::NewHandle(T, type.Canonicalize());
 }
 
+DART_EXPORT Dart_Handle Dart_FunctionName(Dart_Handle function) {
+  DARTSCOPE(Thread::Current());
+  const Function& func = Api::UnwrapFunctionHandle(Z, function);
+  if (func.IsNull()) {
+    RETURN_TYPE_ERROR(Z, function, Function);
+  }
+  return Api::NewHandle(T, func.UserVisibleName());
+}
+
+DART_EXPORT Dart_Handle Dart_FunctionOwner(Dart_Handle function) {
+  DARTSCOPE(Thread::Current());
+  const Function& func = Api::UnwrapFunctionHandle(Z, function);
+  if (func.IsNull()) {
+    RETURN_TYPE_ERROR(Z, function, Function);
+  }
+  if (func.IsNonImplicitClosureFunction()) {
+    RawFunction* parent_function = func.parent_function();
+    return Api::NewHandle(T, parent_function);
+  }
+  const Class& owner = Class::Handle(Z, func.Owner());
+  ASSERT(!owner.IsNull());
+  if (owner.IsTopLevel()) {
+// Top-level functions are implemented as members of a hidden class. We hide
+// that class here and instead answer the library.
+#if defined(DEBUG)
+    const Library& lib = Library::Handle(Z, owner.library());
+    if (lib.IsNull()) {
+      ASSERT(owner.IsDynamicClass() || owner.IsVoidClass());
+    }
+#endif
+    return Api::NewHandle(T, owner.library());
+  } else {
+    return Api::NewHandle(T, owner.RareType());
+  }
+}
+
+DART_EXPORT Dart_Handle Dart_FunctionIsStatic(Dart_Handle function,
+                                              bool* is_static) {
+  DARTSCOPE(Thread::Current());
+  if (is_static == NULL) {
+    RETURN_NULL_ERROR(is_static);
+  }
+  const Function& func = Api::UnwrapFunctionHandle(Z, function);
+  if (func.IsNull()) {
+    RETURN_TYPE_ERROR(Z, function, Function);
+  }
+  *is_static = func.is_static();
+  return Api::Success();
+}
+
+DART_EXPORT Dart_Handle Dart_ClosureFunction(Dart_Handle closure) {
+  DARTSCOPE(Thread::Current());
+  const Instance& closure_obj = Api::UnwrapInstanceHandle(Z, closure);
+  if (closure_obj.IsNull() || !closure_obj.IsClosure()) {
+    RETURN_TYPE_ERROR(Z, closure, Instance);
+  }
+
+  ASSERT(ClassFinalizer::AllClassesFinalized());
+
+  RawFunction* rf = Closure::Cast(closure_obj).function();
+  return Api::NewHandle(T, rf);
+}
+
 // --- Numbers, Integers and Doubles ----
 
 DART_EXPORT Dart_Handle Dart_IntegerFitsIntoInt64(Dart_Handle integer,
@@ -5905,7 +5968,6 @@
 #if defined(DART_PRECOMPILED_RUNTIME)
   result.status = Dart_KernelCompilationStatus_Unknown;
   result.error = strdup("Dart_CompileToKernel is unsupported.");
-  return result;
 #else
   result = KernelIsolate::CompileToKernel(script_uri, platform_kernel,
                                           platform_kernel_size, 0, NULL,
@@ -5918,8 +5980,8 @@
           " compilation results.");
     }
   }
-  return result;
 #endif
+  return result;
 }
 
 DART_EXPORT Dart_KernelCompilationResult
@@ -5934,7 +5996,6 @@
 #if defined(DART_PRECOMPILED_RUNTIME)
   result.status = Dart_KernelCompilationStatus_Unknown;
   result.error = strdup("Dart_CompileSourcesToKernel is unsupported.");
-  return result;
 #else
   result = KernelIsolate::CompileToKernel(
       script_uri, platform_kernel, platform_kernel_size, source_files_count,
@@ -5947,9 +6008,19 @@
           " compilation results.");
     }
   }
-  return result;
-
 #endif
+  return result;
+}
+
+DART_EXPORT Dart_KernelCompilationResult Dart_KernelListDependencies() {
+  Dart_KernelCompilationResult result;
+#if defined(DART_PRECOMPILED_RUNTIME)
+  result.status = Dart_KernelCompilationStatus_Unknown;
+  result.error = strdup("Dart_KernelListDependencies is unsupported.");
+#else
+  result = KernelIsolate::ListDependencies();
+#endif
+  return result;
 }
 
 // --- Service support ---
diff --git a/runtime/vm/dart_api_impl_test.cc b/runtime/vm/dart_api_impl_test.cc
index 7569556..ee787e4 100644
--- a/runtime/vm/dart_api_impl_test.cc
+++ b/runtime/vm/dart_api_impl_test.cc
@@ -788,6 +788,116 @@
                "type Instance.");
 }
 
+TEST_CASE(DartAPI_FunctionName) {
+  const char* kScriptChars = "int getInt() { return 1; }\n";
+  // Create a test library and Load up a test script in it.
+  Dart_Handle lib = TestCase::LoadTestScript(kScriptChars, NULL);
+  EXPECT_VALID(lib);
+
+  Dart_Handle closure = Dart_GetClosure(lib, NewString("getInt"));
+  EXPECT_VALID(closure);
+  if (Dart_IsClosure(closure)) {
+    closure = Dart_ClosureFunction(closure);
+    EXPECT_VALID(closure);
+  }
+
+  Dart_Handle name = Dart_FunctionName(closure);
+  EXPECT_VALID(name);
+  const char* result_str = "";
+  Dart_StringToCString(name, &result_str);
+  EXPECT_STREQ(result_str, "getInt");
+}
+
+TEST_CASE(DartAPI_FunctionOwner) {
+  const char* kScriptChars = "int getInt() { return 1; }\n";
+  // Create a test library and Load up a test script in it.
+  Dart_Handle lib = TestCase::LoadTestScript(kScriptChars, NULL);
+  EXPECT_VALID(lib);
+
+  Dart_Handle closure = Dart_GetClosure(lib, NewString("getInt"));
+  EXPECT_VALID(closure);
+  if (Dart_IsClosure(closure)) {
+    closure = Dart_ClosureFunction(closure);
+    EXPECT_VALID(closure);
+  }
+
+  const char* url = "";
+  Dart_Handle owner = Dart_FunctionOwner(closure);
+  EXPECT_VALID(owner);
+  Dart_Handle owner_url = Dart_LibraryUrl(owner);
+  EXPECT_VALID(owner_url);
+  Dart_StringToCString(owner_url, &url);
+
+  const char* lib_url = "";
+  Dart_Handle library_url = Dart_LibraryUrl(lib);
+  EXPECT_VALID(library_url);
+  Dart_StringToCString(library_url, &lib_url);
+
+  EXPECT_STREQ(url, lib_url);
+}
+
+TEST_CASE(DartAPI_FunctionIsStatic) {
+  const char* kScriptChars =
+      "int getInt() { return 1; }\n"
+      "class Foo { String getString() => 'foobar'; }\n";
+  // Create a test library and Load up a test script in it.
+  Dart_Handle lib = TestCase::LoadTestScript(kScriptChars, NULL);
+  EXPECT_VALID(lib);
+
+  Dart_Handle closure = Dart_GetClosure(lib, NewString("getInt"));
+  EXPECT_VALID(closure);
+  if (Dart_IsClosure(closure)) {
+    closure = Dart_ClosureFunction(closure);
+    EXPECT_VALID(closure);
+  }
+
+  bool is_static = false;
+  Dart_Handle result = Dart_FunctionIsStatic(closure, &is_static);
+  EXPECT_VALID(result);
+  EXPECT(is_static);
+
+  // TODO(bkonyi): uncomment when issue 33417 is resolved.
+  /*
+  Dart_Handle klass = Dart_GetType(lib, NewString("Foo"), 0, NULL);
+  EXPECT_VALID(klass);
+
+  Dart_Handle instance = Dart_Allocate(klass);
+
+  closure = Dart_GetField(instance, NewString("getString"));
+  EXPECT_VALID(closure);
+  if (Dart_IsClosure(closure)) {
+    closure = Dart_ClosureFunction(closure);
+    EXPECT_VALID(closure);
+  }
+
+  result = Dart_FunctionIsStatic(closure, &is_static);
+  EXPECT_VALID(result);
+  EXPECT(!is_static);
+*/
+}
+
+TEST_CASE(DartAPI_ClosureFunction) {
+  const char* kScriptChars = "int getInt() { return 1; }\n";
+  // Create a test library and Load up a test script in it.
+  Dart_Handle lib = TestCase::LoadTestScript(kScriptChars, NULL);
+  EXPECT_VALID(lib);
+
+  Dart_Handle closure = Dart_GetClosure(lib, NewString("getInt"));
+  EXPECT_VALID(closure);
+  EXPECT(Dart_IsClosure(closure));
+  Dart_Handle closure_str = Dart_ToString(closure);
+  const char* result = "";
+  Dart_StringToCString(closure_str, &result);
+  EXPECT(strstr(result, "getInt") != NULL);
+
+  Dart_Handle function = Dart_ClosureFunction(closure);
+  EXPECT_VALID(function);
+  EXPECT(Dart_IsFunction(function));
+  Dart_Handle func_str = Dart_ToString(function);
+  Dart_StringToCString(func_str, &result);
+  EXPECT(strstr(result, "getInt"));
+}
+
 TEST_CASE(DartAPI_BooleanValues) {
   Dart_Handle str = NewString("test");
   EXPECT(!Dart_IsBoolean(str));
diff --git a/runtime/vm/flag_list.h b/runtime/vm/flag_list.h
index 432e3d3..7dd0cc2 100644
--- a/runtime/vm/flag_list.h
+++ b/runtime/vm/flag_list.h
@@ -26,6 +26,12 @@
 #define USING_PRODUCT false
 #endif
 
+#if defined(DART_PRECOMPILED_RUNTIME)
+constexpr bool kDartPrecompiledRuntime = true;
+#else
+constexpr bool kDartPrecompiledRuntime = false;
+#endif
+
 // List of all flags in the VM.
 // Flags can be one of three categories:
 // * P roduct flags: Can be set in any of the deployment modes, including in
diff --git a/runtime/vm/instructions_arm.h b/runtime/vm/instructions_arm.h
index 0738d64..e11c947 100644
--- a/runtime/vm/instructions_arm.h
+++ b/runtime/vm/instructions_arm.h
@@ -42,6 +42,10 @@
   // address of the first instruction in the sequence.  Returns the register
   // being loaded and the index in the pool being read from in the output
   // parameters 'reg' and 'index' respectively.
+  // IMPORANT: When generating code loading values from pool on ARM use
+  // LoadWordFromPool macro instruction instead of emitting direct load.
+  // The macro instruction takes care of pool offsets that can't be
+  // encoded as immediates.
   static uword DecodeLoadWordFromPool(uword end,
                                       Register* reg,
                                       intptr_t* index);
diff --git a/runtime/vm/instructions_arm64.h b/runtime/vm/instructions_arm64.h
index 10c74f5..1355cfe 100644
--- a/runtime/vm/instructions_arm64.h
+++ b/runtime/vm/instructions_arm64.h
@@ -42,6 +42,10 @@
   // address of the first instruction in the sequence.  Returns the register
   // being loaded and the index in the pool being read from in the output
   // parameters 'reg' and 'index' respectively.
+  // IMPORANT: When generating code loading values from pool on ARM64 use
+  // LoadWordFromPool macro instruction instead of emitting direct load.
+  // The macro instruction takes care of pool offsets that can't be
+  // encoded as immediates.
   static uword DecodeLoadWordFromPool(uword end,
                                       Register* reg,
                                       intptr_t* index);
diff --git a/runtime/vm/interpreter.cc b/runtime/vm/interpreter.cc
index fdbc665..c61a2d5 100644
--- a/runtime/vm/interpreter.cc
+++ b/runtime/vm/interpreter.cc
@@ -841,6 +841,42 @@
   *SP = fp - kKBCDartFrameFixedSize;
 }
 
+// Note: functions below are marked DART_NOINLINE to recover performance on
+// ARM where inlining these functions into the interpreter loop seemed to cause
+// some code quality issues.
+static DART_NOINLINE bool InvokeRuntime(Thread* thread,
+                                        Interpreter* interpreter,
+                                        RuntimeFunction drt,
+                                        const NativeArguments& args) {
+  InterpreterSetjmpBuffer buffer(interpreter);
+  if (!setjmp(buffer.buffer_)) {
+    thread->set_vm_tag(reinterpret_cast<uword>(drt));
+    drt(args);
+    thread->set_vm_tag(VMTag::kDartTagId);
+    thread->set_top_exit_frame_info(0);
+    return true;
+  } else {
+    return false;
+  }
+}
+
+static DART_NOINLINE bool InvokeNative(Thread* thread,
+                                       Interpreter* interpreter,
+                                       NativeFunctionWrapper wrapper,
+                                       Dart_NativeFunction function,
+                                       Dart_NativeArguments args) {
+  InterpreterSetjmpBuffer buffer(interpreter);
+  if (!setjmp(buffer.buffer_)) {
+    thread->set_vm_tag(reinterpret_cast<uword>(function));
+    wrapper(args, function);
+    thread->set_vm_tag(VMTag::kDartTagId);
+    thread->set_top_exit_frame_info(0);
+    return true;
+  } else {
+    return false;
+  }
+}
+
 DART_NOINLINE bool Interpreter::InvokeCompiled(Thread* thread,
                                                RawFunction* function,
                                                RawArray* argdesc,
@@ -849,64 +885,79 @@
                                                uint32_t** pc,
                                                RawObject*** FP,
                                                RawObject*** SP) {
-  InterpreterSetjmpBuffer buffer(this);
-  if (!setjmp(buffer.buffer_)) {
 #if defined(USING_SIMULATOR) || defined(TARGET_ARCH_DBC)
-    // TODO(regis): Revisit.
-    UNIMPLEMENTED();
+  // TODO(regis): Revisit.
+  UNIMPLEMENTED();
 #endif
-    ASSERT(thread->vm_tag() == VMTag::kDartTagId);
-    ASSERT(thread->execution_state() == Thread::kThreadInGenerated);
-    if (!Function::HasCode(function)) {
-      ASSERT(!Function::HasBytecode(function));
-      call_top[1] = 0;  // Code result.
-      call_top[2] = function;
-      CallRuntime(thread, *FP, call_top + 3, *pc, 1, call_top + 2, call_top + 1,
-                  reinterpret_cast<uword>(DRT_CompileFunction));
+  if (!Function::HasCode(function)) {
+    ASSERT(!Function::HasBytecode(function));
+    call_top[1] = 0;  // Code result.
+    call_top[2] = function;
+    Exit(thread, *FP, call_top + 3, *pc);
+    NativeArguments native_args(thread, 1, call_top + 2, call_top + 1);
+    if (!InvokeRuntime(thread, this, DRT_CompileFunction, native_args)) {
+      return false;
     }
-    if (Function::HasCode(function)) {
-      RawCode* code = function->ptr()->code_;
-      ASSERT(code != StubCode::LazyCompile_entry()->code());
-      // TODO(regis): Once we share the same stack, try to invoke directly.
-
-      // On success, returns a RawInstance.  On failure, a RawError.
-      typedef RawObject* (*invokestub)(RawCode * code, RawArray * argdesc,
-                                       RawObject * *arg0, Thread * thread);
-      invokestub entrypoint = reinterpret_cast<invokestub>(
-          StubCode::InvokeDartCodeFromBytecode_entry()->EntryPoint());
-      RawObject* result = entrypoint(code, argdesc, call_base, thread);
-
-      // Pop args and push result.
-      *SP = call_base;
-      **SP = result;
-    } else {
-      ASSERT(Function::HasBytecode(function));
-      // Bytecode was loaded in the above compilation step.
-      // Stay in interpreter.
-      RawCode* bytecode = function->ptr()->bytecode_;
-      RawObject** callee_fp = call_top + kKBCDartFrameFixedSize;
-      callee_fp[kKBCPcMarkerSlotFromFp] = bytecode;
-      callee_fp[kKBCSavedCallerPcSlotFromFp] =
-          reinterpret_cast<RawObject*>(*pc);
-      callee_fp[kKBCSavedCallerFpSlotFromFp] =
-          reinterpret_cast<RawObject*>(*FP);
-      pp_ = bytecode->ptr()->object_pool_;
-      *pc = reinterpret_cast<uint32_t*>(bytecode->ptr()->entry_point_);
-      pc_ = reinterpret_cast<uword>(*pc);  // For the profiler.
-      *FP = callee_fp;
-      *SP = *FP - 1;
-      // Dispatch will interpret function.
-    }
-    ASSERT(thread->vm_tag() == VMTag::kDartTagId);
-    ASSERT(thread->execution_state() == Thread::kThreadInGenerated);
-    thread->set_top_exit_frame_info(0);
-    return true;
-  } else {
-    return false;
   }
+  if (Function::HasCode(function)) {
+    RawCode* code = function->ptr()->code_;
+    ASSERT(code != StubCode::LazyCompile_entry()->code());
+    // TODO(regis): Once we share the same stack, try to invoke directly.
+
+    // On success, returns a RawInstance.  On failure, a RawError.
+    typedef RawObject* (*invokestub)(RawCode * code, RawArray * argdesc,
+                                     RawObject * *arg0, Thread * thread);
+    invokestub entrypoint = reinterpret_cast<invokestub>(
+        StubCode::InvokeDartCodeFromBytecode_entry()->EntryPoint());
+    Exit(thread, *FP, call_top + 1, *pc);
+    {
+      InterpreterSetjmpBuffer buffer(this);
+      if (!setjmp(buffer.buffer_)) {
+        thread->set_vm_tag(reinterpret_cast<uword>(entrypoint));
+        RawObject* result = entrypoint(code, argdesc, call_base, thread);
+        thread->set_vm_tag(VMTag::kDartTagId);
+        thread->set_top_exit_frame_info(0);
+        ASSERT(thread->execution_state() == Thread::kThreadInGenerated);
+
+        // It is legit to call the constructor of an error object, however a
+        // result of class UnhandledException must be propagated.
+        if (result->IsHeapObject() &&
+            result->GetClassId() == kUnhandledExceptionCid) {
+          // TODO(regis): Shoudn't the callee have set these and thrown?
+          special_[kExceptionSpecialIndex] = result;
+          special_[kStackTraceSpecialIndex] = Object::null();
+          return false;
+        }
+
+        // Pop args and push result.
+        *SP = call_base;
+        **SP = result;
+        return true;
+      } else {
+        return false;
+      }
+    }
+  }
+  ASSERT(Function::HasBytecode(function));
+  // Bytecode was loaded in the above compilation step.
+  // Stay in interpreter.
+  RawCode* bytecode = function->ptr()->bytecode_;
+  RawObject** callee_fp = call_top + kKBCDartFrameFixedSize;
+  callee_fp[kKBCPcMarkerSlotFromFp] = bytecode;
+  callee_fp[kKBCSavedCallerPcSlotFromFp] = reinterpret_cast<RawObject*>(*pc);
+  callee_fp[kKBCSavedCallerFpSlotFromFp] = reinterpret_cast<RawObject*>(*FP);
+  pp_ = bytecode->ptr()->object_pool_;
+  *pc = reinterpret_cast<uint32_t*>(bytecode->ptr()->entry_point_);
+  pc_ = reinterpret_cast<uword>(*pc);  // For the profiler.
+  *FP = callee_fp;
+  *SP = *FP - 1;
+  // Dispatch will interpret function.
+  ASSERT(thread->vm_tag() == VMTag::kDartTagId);
+  ASSERT(thread->top_exit_frame_info() == 0);
+  return true;
 }
 
-DART_FORCE_INLINE void Interpreter::Invoke(Thread* thread,
+DART_FORCE_INLINE bool Interpreter::Invoke(Thread* thread,
                                            RawObject** call_base,
                                            RawObject** call_top,
                                            uint32_t** pc,
@@ -923,25 +974,19 @@
 #endif
   if (Function::HasCode(function) || !Function::HasBytecode(function)) {
     // TODO(regis): If the function is a dispatcher, execute the dispatch here.
-    if (!InvokeCompiled(thread, function, argdesc_, call_base, call_top, pc, FP,
-                        SP)) {
-      // Handle exception
-      *FP = reinterpret_cast<RawObject**>(fp_);
-      *pc = reinterpret_cast<uint32_t*>(pc_);
-      pp_ = InterpreterHelpers::FrameCode(*FP)->ptr()->object_pool_;
-      *SP = *FP - 1;
-    }
-  } else {
-    RawCode* bytecode = function->ptr()->bytecode_;
-    callee_fp[kKBCPcMarkerSlotFromFp] = bytecode;
-    callee_fp[kKBCSavedCallerPcSlotFromFp] = reinterpret_cast<RawObject*>(*pc);
-    callee_fp[kKBCSavedCallerFpSlotFromFp] = reinterpret_cast<RawObject*>(*FP);
-    pp_ = bytecode->ptr()->object_pool_;
-    *pc = reinterpret_cast<uint32_t*>(bytecode->ptr()->entry_point_);
-    pc_ = reinterpret_cast<uword>(*pc);  // For the profiler.
-    *FP = callee_fp;
-    *SP = *FP - 1;
+    return InvokeCompiled(thread, function, argdesc_, call_base, call_top, pc,
+                          FP, SP);
   }
+  RawCode* bytecode = function->ptr()->bytecode_;
+  callee_fp[kKBCPcMarkerSlotFromFp] = bytecode;
+  callee_fp[kKBCSavedCallerPcSlotFromFp] = reinterpret_cast<RawObject*>(*pc);
+  callee_fp[kKBCSavedCallerFpSlotFromFp] = reinterpret_cast<RawObject*>(*FP);
+  pp_ = bytecode->ptr()->object_pool_;
+  *pc = reinterpret_cast<uint32_t*>(bytecode->ptr()->entry_point_);
+  pc_ = reinterpret_cast<uword>(*pc);  // For the profiler.
+  *FP = callee_fp;
+  *SP = *FP - 1;
+  return true;
 }
 
 void Interpreter::InlineCacheMiss(int checked_args,
@@ -978,7 +1023,7 @@
               result, reinterpret_cast<uword>(handler));
 }
 
-DART_FORCE_INLINE void Interpreter::InstanceCall1(Thread* thread,
+DART_FORCE_INLINE bool Interpreter::InstanceCall1(Thread* thread,
                                                   RawICData* icdata,
                                                   RawObject** call_base,
                                                   RawObject** top,
@@ -1020,10 +1065,10 @@
                     *pc, *FP, *SP);
   }
 
-  Invoke(thread, call_base, top, pc, FP, SP);
+  return Invoke(thread, call_base, top, pc, FP, SP);
 }
 
-DART_FORCE_INLINE void Interpreter::InstanceCall2(Thread* thread,
+DART_FORCE_INLINE bool Interpreter::InstanceCall2(Thread* thread,
                                                   RawICData* icdata,
                                                   RawObject** call_base,
                                                   RawObject** top,
@@ -1068,7 +1113,7 @@
                     *pc, *FP, *SP);
   }
 
-  Invoke(thread, call_base, top, pc, FP, SP);
+  return Invoke(thread, call_base, top, pc, FP, SP);
 }
 
 DART_FORCE_INLINE void Interpreter::PrepareForTailCall(
@@ -1089,42 +1134,6 @@
   argdesc_ = args_desc;
 }
 
-// Note: functions below are marked DART_NOINLINE to recover performance on
-// ARM where inlining these functions into the interpreter loop seemed to cause
-// some code quality issues.
-static DART_NOINLINE bool InvokeRuntime(Thread* thread,
-                                        Interpreter* interpreter,
-                                        RuntimeFunction drt,
-                                        const NativeArguments& args) {
-  InterpreterSetjmpBuffer buffer(interpreter);
-  if (!setjmp(buffer.buffer_)) {
-    thread->set_vm_tag(reinterpret_cast<uword>(drt));
-    drt(args);
-    thread->set_vm_tag(VMTag::kDartTagId);
-    thread->set_top_exit_frame_info(0);
-    return true;
-  } else {
-    return false;
-  }
-}
-
-static DART_NOINLINE bool InvokeNative(Thread* thread,
-                                       Interpreter* interpreter,
-                                       NativeFunctionWrapper wrapper,
-                                       Dart_NativeFunction function,
-                                       Dart_NativeArguments args) {
-  InterpreterSetjmpBuffer buffer(interpreter);
-  if (!setjmp(buffer.buffer_)) {
-    thread->set_vm_tag(reinterpret_cast<uword>(function));
-    wrapper(args, function);
-    thread->set_vm_tag(VMTag::kDartTagId);
-    thread->set_top_exit_frame_info(0);
-    return true;
-  } else {
-    return false;
-  }
-}
-
 // Note:
 // All macro helpers are intended to be used only inside Interpreter::Call.
 
@@ -1965,7 +1974,9 @@
       RawObject** call_base = SP - argc;
       RawObject** call_top = SP;  // *SP contains function
       argdesc_ = static_cast<RawArray*>(LOAD_CONSTANT(rD));
-      Invoke(thread, call_base, call_top, &pc, &FP, &SP);
+      if (!Invoke(thread, call_base, call_top, &pc, &FP, &SP)) {
+        HANDLE_EXCEPTION;
+      }
     }
 
     DISPATCH();
@@ -1977,7 +1988,9 @@
     RawObject** call_base = SP - argc;
     RawObject** call_top = SP;  // *SP contains function
     argdesc_ = static_cast<RawArray*>(LOAD_CONSTANT(rD));
-    Invoke(thread, call_base, call_top, &pc, &FP, &SP);
+    if (!Invoke(thread, call_base, call_top, &pc, &FP, &SP)) {
+      HANDLE_EXCEPTION;
+    }
     DISPATCH();
   }
 
@@ -2001,8 +2014,10 @@
       RawICData* icdata = RAW_CAST(ICData, LOAD_CONSTANT(kidx));
       InterpreterHelpers::IncrementUsageCounter(
           RAW_CAST(Function, icdata->ptr()->owner_));
-      InstanceCall1(thread, icdata, call_base, call_top, &pc, &FP, &SP,
-                    false /* optimized */);
+      if (!InstanceCall1(thread, icdata, call_base, call_top, &pc, &FP, &SP,
+                         false /* optimized */)) {
+        HANDLE_EXCEPTION;
+      }
     }
 
     DISPATCH();
@@ -2026,8 +2041,10 @@
       RawICData* icdata = RAW_CAST(ICData, LOAD_CONSTANT(kidx));
       InterpreterHelpers::IncrementUsageCounter(
           RAW_CAST(Function, icdata->ptr()->owner_));
-      InstanceCall2(thread, icdata, call_base, call_top, &pc, &FP, &SP,
-                    false /* optimized */);
+      if (!InstanceCall2(thread, icdata, call_base, call_top, &pc, &FP, &SP,
+                         false /* optimized */)) {
+        HANDLE_EXCEPTION;
+      }
     }
 
     DISPATCH();
@@ -2045,8 +2062,10 @@
 
       RawICData* icdata = RAW_CAST(ICData, LOAD_CONSTANT(kidx));
       InterpreterHelpers::IncrementUsageCounter(FrameFunction(FP));
-      InstanceCall1(thread, icdata, call_base, call_top, &pc, &FP, &SP,
-                    true /* optimized */);
+      if (!InstanceCall1(thread, icdata, call_base, call_top, &pc, &FP, &SP,
+                         true /* optimized */)) {
+        HANDLE_EXCEPTION;
+      }
     }
 
     DISPATCH();
@@ -2064,8 +2083,10 @@
 
       RawICData* icdata = RAW_CAST(ICData, LOAD_CONSTANT(kidx));
       InterpreterHelpers::IncrementUsageCounter(FrameFunction(FP));
-      InstanceCall2(thread, icdata, call_base, call_top, &pc, &FP, &SP,
-                    true /* optimized */);
+      if (!InstanceCall2(thread, icdata, call_base, call_top, &pc, &FP, &SP,
+                         true /* optimized */)) {
+        HANDLE_EXCEPTION;
+      }
     }
 
     DISPATCH();
@@ -2990,7 +3011,7 @@
   }
 
   {
-    BYTECODE(StoreFieldTOS, A_D);
+    BYTECODE(StoreFieldTOS, __D);
     const uword offset_in_words =
         static_cast<uword>(Smi::Value(RAW_CAST(Smi, LOAD_CONSTANT(rD))));
     RawInstance* instance = reinterpret_cast<RawInstance*>(SP[-1]);
diff --git a/runtime/vm/interpreter.h b/runtime/vm/interpreter.h
index 517cbaa..0a87cc4 100644
--- a/runtime/vm/interpreter.h
+++ b/runtime/vm/interpreter.h
@@ -132,7 +132,7 @@
                    RawObject** result,
                    uword target);
 
-  void Invoke(Thread* thread,
+  bool Invoke(Thread* thread,
               RawObject** call_base,
               RawObject** call_top,
               uint32_t** pc,
@@ -163,7 +163,7 @@
                        RawObject** FP,
                        RawObject** SP);
 
-  void InstanceCall1(Thread* thread,
+  bool InstanceCall1(Thread* thread,
                      RawICData* icdata,
                      RawObject** call_base,
                      RawObject** call_top,
@@ -172,7 +172,7 @@
                      RawObject*** SP,
                      bool optimized);
 
-  void InstanceCall2(Thread* thread,
+  bool InstanceCall2(Thread* thread,
                      RawICData* icdata,
                      RawObject** call_base,
                      RawObject** call_top,
diff --git a/runtime/vm/kernel_isolate.cc b/runtime/vm/kernel_isolate.cc
index f0b47d5..64b6982 100644
--- a/runtime/vm/kernel_isolate.cc
+++ b/runtime/vm/kernel_isolate.cc
@@ -53,6 +53,7 @@
 const int KernelIsolate::kAcceptTag = 2;
 const int KernelIsolate::kTrainTag = 3;
 const int KernelIsolate::kCompileExpressionTag = 4;
+const int KernelIsolate::kListDependenciesTag = 5;
 
 Dart_IsolateCreateCallback KernelIsolate::create_callback_ = NULL;
 Monitor* KernelIsolate::monitor_ = new Monitor();
@@ -716,6 +717,20 @@
                                         incremental_compile, package_config);
 }
 
+Dart_KernelCompilationResult KernelIsolate::ListDependencies() {
+  Dart_Port kernel_port = WaitForKernelPort();
+  if (kernel_port == ILLEGAL_PORT) {
+    Dart_KernelCompilationResult result;
+    result.status = Dart_KernelCompilationStatus_Unknown;
+    result.error = strdup("Error while initializing Kernel isolate");
+    return result;
+  }
+
+  KernelCompilationRequest request;
+  return request.SendAndWaitForResponse(kListDependenciesTag, kernel_port, NULL,
+                                        NULL, 0, 0, NULL, false, NULL);
+}
+
 Dart_KernelCompilationResult KernelIsolate::AcceptCompilation() {
   // This must be the main script to be loaded. Wait for Kernel isolate
   // to finish initialization.
diff --git a/runtime/vm/kernel_isolate.h b/runtime/vm/kernel_isolate.h
index 2e45b52..d888630 100644
--- a/runtime/vm/kernel_isolate.h
+++ b/runtime/vm/kernel_isolate.h
@@ -16,6 +16,8 @@
 
 namespace dart {
 
+// TODO(33433): The kernel service does not belong in the VM.
+
 class KernelIsolate : public AllStatic {
  public:
   static const char* kName;
@@ -24,6 +26,7 @@
   static const int kAcceptTag;
   static const int kTrainTag;
   static const int kCompileExpressionTag;
+  static const int kListDependenciesTag;
 
   static void Run();
 
@@ -56,6 +59,8 @@
       const char* klass,
       bool is_static);
 
+  static Dart_KernelCompilationResult ListDependencies();
+
  protected:
   static Monitor* monitor_;
   static Dart_IsolateCreateCallback create_callback_;
diff --git a/runtime/vm/object_store.cc b/runtime/vm/object_store.cc
index e2d676d..b9eeeba 100644
--- a/runtime/vm/object_store.cc
+++ b/runtime/vm/object_store.cc
@@ -149,9 +149,6 @@
   cls = async_lib.LookupClass(Symbols::Completer());
   ASSERT(!cls.IsNull());
   set_completer_class(cls);
-  cls = async_lib.LookupClass(Symbols::StreamIterator());
-  ASSERT(!cls.IsNull());
-  set_stream_iterator_class(cls);
 
   String& function_name = String::Handle(zone);
   Function& function = Function::Handle(zone);
diff --git a/runtime/vm/object_store.h b/runtime/vm/object_store.h
index 74f3dfb..01b5a52 100644
--- a/runtime/vm/object_store.h
+++ b/runtime/vm/object_store.h
@@ -58,7 +58,6 @@
   RW(Class, pragma_class)                                                      \
   RW(Class, future_class)                                                      \
   RW(Class, completer_class)                                                   \
-  RW(Class, stream_iterator_class)                                             \
   RW(Class, symbol_class)                                                      \
   RW(Class, one_byte_string_class)                                             \
   RW(Class, two_byte_string_class)                                             \
diff --git a/runtime/vm/os_fuchsia.cc b/runtime/vm/os_fuchsia.cc
index 605e2dd..e8ed9aa 100644
--- a/runtime/vm/os_fuchsia.cc
+++ b/runtime/vm/os_fuchsia.cc
@@ -14,7 +14,7 @@
 #include <zircon/syscalls/object.h>
 #include <zircon/types.h>
 
-#include <time_zone/cpp/fidl.h>
+#include <fuchsia/timezone/cpp/fidl.h>
 
 #include "lib/app/cpp/environment_services.h"
 
@@ -43,7 +43,7 @@
 static zx_status_t GetLocalAndDstOffsetInSeconds(int64_t seconds_since_epoch,
                                                  int32_t* local_offset,
                                                  int32_t* dst_offset) {
-  time_zone::TimezoneSyncPtr time_svc;
+  fuchsia::timezone::TimezoneSyncPtr time_svc;
   fuchsia::sys::ConnectToEnvironmentService(time_svc.NewRequest());
   if (!time_svc->GetTimezoneOffsetMinutes(seconds_since_epoch * 1000,
                                           local_offset, dst_offset))
@@ -56,7 +56,7 @@
 const char* OS::GetTimeZoneName(int64_t seconds_since_epoch) {
   // TODO(abarth): Handle time zone changes.
   static const auto* tz_name = new std::string([] {
-    time_zone::TimezoneSyncPtr time_svc;
+    fuchsia::timezone::TimezoneSyncPtr time_svc;
     fuchsia::sys::ConnectToEnvironmentService(time_svc.NewRequest());
     fidl::StringPtr result;
     time_svc->GetTimezoneId(&result);
diff --git a/runtime/vm/parser.cc b/runtime/vm/parser.cc
index 80b7358..08388da 100644
--- a/runtime/vm/parser.cc
+++ b/runtime/vm/parser.cc
@@ -9290,7 +9290,7 @@
   // Build creation of implicit StreamIterator.
   // var :for-in-iter = new StreamIterator(stream_expr).
   const Class& stream_iterator_cls =
-      Class::ZoneHandle(Z, I->object_store()->stream_iterator_class());
+      Class::ZoneHandle(Z, async_lib.LookupClass(Symbols::StreamIterator()));
   ASSERT(!stream_iterator_cls.IsNull());
   const Function& iterator_ctor = Function::ZoneHandle(
       Z,
diff --git a/runtime/vm/simulator_dbc.cc b/runtime/vm/simulator_dbc.cc
index 7e4ca4e..21d5e11 100644
--- a/runtime/vm/simulator_dbc.cc
+++ b/runtime/vm/simulator_dbc.cc
@@ -2667,7 +2667,7 @@
   }
 
   {
-    BYTECODE(StoreFieldTOS, A_D);
+    BYTECODE(StoreFieldTOS, __D);
     const uint16_t offset_in_words = rD;
     RawInstance* instance = reinterpret_cast<RawInstance*>(SP[-1]);
     RawObject* value = reinterpret_cast<RawObject*>(SP[0]);
diff --git a/runtime/vm/stack_frame.cc b/runtime/vm/stack_frame.cc
index 9cec45e..63e6fb4 100644
--- a/runtime/vm/stack_frame.cc
+++ b/runtime/vm/stack_frame.cc
@@ -325,19 +325,44 @@
   PcDescriptors& descriptors = reused_pc_descriptors_handle.Handle();
   descriptors = code.pc_descriptors();
   PcDescriptors::Iterator iter(descriptors, RawPcDescriptors::kAnyKind);
-  while (iter.MoveNext()) {
-    const intptr_t current_try_index = iter.TryIndex();
-    if ((iter.PcOffset() == pc_offset) && (current_try_index != -1)) {
-      ExceptionHandlerInfo handler_info;
-      handlers.GetHandlerInfo(current_try_index, &handler_info);
-      *handler_pc = code.PayloadStart() + handler_info.handler_pc_offset;
-      *needs_stacktrace = handler_info.needs_stacktrace;
-      *has_catch_all = handler_info.has_catch_all;
-      cache->Insert(pc(), handler_info);
-      return true;
+  intptr_t try_index = -1;
+  if (is_interpreted()) {
+    while (iter.MoveNext()) {
+      // PC descriptors for try blocks in bytecode are generated in pairs,
+      // marking start and end of a try block.
+      // See BytecodeMetadataHelper::ReadExceptionsTable for details.
+      const intptr_t current_try_index = iter.TryIndex();
+      const uword start_pc = iter.PcOffset();
+      if (pc_offset < start_pc) {
+        break;
+      }
+      const bool has_next = iter.MoveNext();
+      ASSERT(has_next);
+      const uword end_pc = iter.PcOffset();
+      if (start_pc <= pc_offset && pc_offset < end_pc) {
+        ASSERT(try_index < current_try_index);
+        try_index = current_try_index;
+      }
+    }
+  } else {
+    while (iter.MoveNext()) {
+      const intptr_t current_try_index = iter.TryIndex();
+      if ((iter.PcOffset() == pc_offset) && (current_try_index != -1)) {
+        try_index = current_try_index;
+        break;
+      }
     }
   }
-  return false;
+  if (try_index == -1) {
+    return false;
+  }
+  ExceptionHandlerInfo handler_info;
+  handlers.GetHandlerInfo(try_index, &handler_info);
+  *handler_pc = code.PayloadStart() + handler_info.handler_pc_offset;
+  *needs_stacktrace = handler_info.needs_stacktrace;
+  *has_catch_all = handler_info.has_catch_all;
+  cache->Insert(pc(), handler_info);
+  return true;
 }
 
 TokenPosition StackFrame::GetTokenPos() const {
diff --git a/samples-dev/swarm/swarm_ui_lib/observable/observable.dart b/samples-dev/swarm/swarm_ui_lib/observable/observable.dart
index 4ae4097..6f48db9 100644
--- a/samples-dev/swarm/swarm_ui_lib/observable/observable.dart
+++ b/samples-dev/swarm/swarm_ui_lib/observable/observable.dart
@@ -147,10 +147,6 @@
   int get length => _internal.length;
 
   List<R> cast<R>() => _internal.cast<R>();
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   Iterable<R> whereType<R>() => _internal.whereType<R>();
 
   List<T> operator +(List<T> other) => _internal + other;
diff --git a/sdk/BUILD.gn b/sdk/BUILD.gn
index 6f84167..a15213c 100644
--- a/sdk/BUILD.gn
+++ b/sdk/BUILD.gn
@@ -845,6 +845,7 @@
   visibility = [ ":create_common_sdk" ]
   inputs = [
     "../tools/VERSION",
+    "../.git/logs/HEAD",
   ]
   output = "$root_out_dir/dart-sdk/version"
   outputs = [
@@ -860,6 +861,9 @@
 # This rule writes the revision file.
 action("write_revision_file") {
   visibility = [ ":create_common_sdk" ]
+  inputs = [
+    "../.git/logs/HEAD",
+  ]
   output = "$root_out_dir/dart-sdk/revision"
   outputs = [
     output,
diff --git a/sdk/lib/_http/http_session.dart b/sdk/lib/_http/http_session.dart
index baca21b..3907609 100644
--- a/sdk/lib/_http/http_session.dart
+++ b/sdk/lib/_http/http_session.dart
@@ -78,10 +78,6 @@
   }
 
   Map<K, V> cast<K, V>() => _data.cast<K, V>();
-
-  @Deprecated("Use cast instead.")
-  Map<K, V> retype<K, V>() => cast<K, V>();
-
   update(key, update(value), {ifAbsent()}) =>
       _data.update(key, update, ifAbsent: ifAbsent);
 
diff --git a/sdk/lib/_internal/js_runtime/lib/constant_map.dart b/sdk/lib/_internal/js_runtime/lib/constant_map.dart
index 6047b2d..f7c7936 100644
--- a/sdk/lib/_internal/js_runtime/lib/constant_map.dart
+++ b/sdk/lib/_internal/js_runtime/lib/constant_map.dart
@@ -48,10 +48,6 @@
   const ConstantMap._();
 
   Map<RK, RV> cast<RK, RV>() => Map.castFrom<K, V, RK, RV>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<RK, RV> retype<RK, RV>() => cast<RK, RV>();
-
   bool get isEmpty => length == 0;
 
   bool get isNotEmpty => !isEmpty;
diff --git a/sdk/lib/_internal/js_runtime/lib/core_patch.dart b/sdk/lib/_internal/js_runtime/lib/core_patch.dart
index c6ffb11..e590c9c 100644
--- a/sdk/lib/_internal/js_runtime/lib/core_patch.dart
+++ b/sdk/lib/_internal/js_runtime/lib/core_patch.dart
@@ -2895,10 +2895,11 @@
   int convert(_BigIntImpl x, Uint16List resultDigits) {
     var digits;
     var used;
-    if (x._isNegative || x.compareTo(_modulus) >= 0) {
+    if (x._isNegative || x._absCompare(_modulus) >= 0) {
       var remainder = x._rem(_modulus);
-      if (x._isNegative && !remainder._isNegative && remainder._used > 0) {
-        remainder = _modulus - remainder;
+      if (x._isNegative && remainder._used > 0) {
+        assert(remainder._isNegative);
+        remainder += _modulus;
       }
       assert(!remainder._isNegative);
       used = remainder._used;
diff --git a/sdk/lib/_internal/js_runtime/lib/isolate_patch.dart b/sdk/lib/_internal/js_runtime/lib/isolate_patch.dart
index 37e6090..78cbf61 100644
--- a/sdk/lib/_internal/js_runtime/lib/isolate_patch.dart
+++ b/sdk/lib/_internal/js_runtime/lib/isolate_patch.dart
@@ -146,5 +146,4 @@
 /// This is used by `Isolate.resolvePackageUri` to load resources. The default
 /// value is `packages/` but users can override this by using the
 /// `defaultPackagesBase` hook.
-Uri _packagesBase =
-    Uri.base.resolve(JS('String', r'self.defaultPackagesBase || "packages/"'));
+Uri _packagesBase = Uri.base.resolve(JS('String', r'self.defaultPackagesBase'));
diff --git a/sdk/lib/_internal/js_runtime/lib/js_array.dart b/sdk/lib/_internal/js_runtime/lib/js_array.dart
index df03003..9d0a48e 100644
--- a/sdk/lib/_internal/js_runtime/lib/js_array.dart
+++ b/sdk/lib/_internal/js_runtime/lib/js_array.dart
@@ -120,10 +120,6 @@
   }
 
   List<R> cast<R>() => List.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   void add(E value) {
     checkGrowable('add');
     JS('void', r'#.push(#)', this, value);
diff --git a/sdk/lib/_internal/js_runtime/lib/js_helper.dart b/sdk/lib/_internal/js_runtime/lib/js_helper.dart
index 7ae0796..fd9e485 100644
--- a/sdk/lib/_internal/js_runtime/lib/js_helper.dart
+++ b/sdk/lib/_internal/js_runtime/lib/js_helper.dart
@@ -2515,8 +2515,15 @@
    * Caution: this function may be called when building constants.
    * TODO(ahe): Don't call this function when building constants.
    */
-  static fromTearOff(receiver, List functions, var reflectionInfo,
-      bool isStatic, jsArguments, String propertyName) {
+  static fromTearOff(
+    receiver,
+    List functions,
+    int applyTrampolineIndex,
+    var reflectionInfo,
+    bool isStatic,
+    jsArguments,
+    String propertyName,
+  ) {
     JS_EFFECT(() {
       // The functions are called here to model the calls from JS forms below.
       // The types in the JS forms in the arguments are propagated in type
@@ -2648,20 +2655,24 @@
 
     JS('', '#[#] = #', prototype, JS_GET_NAME(JsGetName.SIGNATURE_NAME),
         signatureFunction);
-
+    var applyTrampoline = trampoline;
     JS('', '#[#] = #', prototype, callName, trampoline);
     for (int i = 1; i < functions.length; i++) {
       var stub = functions[i];
       var stubCallName = JS('String|Null', '#[#]', stub,
           JS_GET_NAME(JsGetName.CALL_NAME_PROPERTY));
       if (stubCallName != null) {
-        JS('', '#[#] = #', prototype, stubCallName,
-            isStatic ? stub : forwardCallTo(receiver, stub, isIntercepted));
+        stub = isStatic ? stub : forwardCallTo(receiver, stub, isIntercepted);
+        JS('', '#[#] = #', prototype, stubCallName, stub);
+      }
+      if (i == applyTrampolineIndex) {
+        applyTrampoline = stub;
+        JS('', '#.\$reflectionInfo = #', applyTrampoline, reflectionInfo);
       }
     }
 
     JS('', '#[#] = #', prototype, JS_GET_NAME(JsGetName.CALL_CATCH_ALL),
-        trampoline);
+        applyTrampoline);
     String reqArgProperty = JS_GET_NAME(JsGetName.REQUIRED_PARAMETER_PROPERTY);
     String defValProperty = JS_GET_NAME(JsGetName.DEFAULT_VALUES_PROPERTY);
     JS('', '#.# = #.#', prototype, reqArgProperty, function, reqArgProperty);
@@ -2938,11 +2949,12 @@
 }
 
 /// Called from implicit method getter (aka tear-off).
-closureFromTearOff(
-    receiver, functions, reflectionInfo, isStatic, jsArguments, name) {
+closureFromTearOff(receiver, functions, applyTrampolineIndex, reflectionInfo,
+    isStatic, jsArguments, name) {
   return Closure.fromTearOff(
       receiver,
       JSArray.markFixedList(functions),
+      applyTrampolineIndex,
       reflectionInfo is List
           ? JSArray.markFixedList(reflectionInfo)
           : reflectionInfo,
diff --git a/sdk/lib/_internal/js_runtime/lib/js_rti.dart b/sdk/lib/_internal/js_runtime/lib/js_rti.dart
index 5e2b7f4..795a5f2 100644
--- a/sdk/lib/_internal/js_runtime/lib/js_rti.dart
+++ b/sdk/lib/_internal/js_runtime/lib/js_rti.dart
@@ -241,6 +241,9 @@
     // A reference to the constructor.
     return rawRtiToJsConstructorName(rti);
   }
+  if (isDartJsInteropTypeArgumentRti(rti)) {
+    return 'dynamic';
+  }
   if (isGenericFunctionTypeParameter(rti)) {
     int index = rti;
     if (genericContext == null || index < 0 || index >= genericContext.length) {
@@ -256,9 +259,6 @@
     var typeArgument = getFutureOrArgument(rti);
     return 'FutureOr<${runtimeTypeToStringV2(typeArgument, genericContext)}>';
   }
-  if (isDartJsInteropTypeArgumentRti(rti)) {
-    return 'dynamic';
-  }
   // We should not get here.
   return 'unknown-reified-type';
 }
diff --git a/sdk/lib/async/stream.dart b/sdk/lib/async/stream.dart
index 5df84c5..a5a0055 100644
--- a/sdk/lib/async/stream.dart
+++ b/sdk/lib/async/stream.dart
@@ -939,10 +939,6 @@
    * each data event emitted by this stream is also an instance of [R].
    */
   Stream<R> cast<R>() => Stream.castFrom<T, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Stream<R> retype<R>() => cast<R>();
-
   /**
    * Collects all elements of this stream in a [List].
    *
@@ -2020,9 +2016,6 @@
    * are acually instances of [RT].
    */
   StreamTransformer<RS, RT> cast<RS, RT>();
-
-  @Deprecated("Use cast instead.")
-  StreamTransformer<RS, RT> retype<RS, RT>();
 }
 
 /**
@@ -2035,9 +2028,6 @@
 
   StreamTransformer<RS, RT> cast<RS, RT>() =>
       StreamTransformer.castFrom<S, T, RS, RT>(this);
-
-  @Deprecated("Use cast instead.")
-  StreamTransformer<RS, RT> retype<RS, RT>() => cast<RS, RT>();
 }
 
 /**
diff --git a/sdk/lib/collection/collections.dart b/sdk/lib/collection/collections.dart
index f20b5ce..d02257b 100644
--- a/sdk/lib/collection/collections.dart
+++ b/sdk/lib/collection/collections.dart
@@ -22,10 +22,6 @@
   UnmodifiableListView(Iterable<E> source) : _source = source;
 
   List<R> cast<R>() => new UnmodifiableListView(_source.cast<R>());
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   int get length => _source.length;
 
   E operator [](int index) => _source.elementAt(index);
diff --git a/sdk/lib/collection/hash_set.dart b/sdk/lib/collection/hash_set.dart
index b75dc44..8f3f715 100644
--- a/sdk/lib/collection/hash_set.dart
+++ b/sdk/lib/collection/hash_set.dart
@@ -15,10 +15,6 @@
   Set<R> _newSimilarSet<R>();
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this, newSet: _newSimilarSet);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   Set<E> difference(Set<Object> other) {
     Set<E> result = _newSet();
     for (var element in this) {
diff --git a/sdk/lib/collection/iterable.dart b/sdk/lib/collection/iterable.dart
index fe1873a..fcad61f 100644
--- a/sdk/lib/collection/iterable.dart
+++ b/sdk/lib/collection/iterable.dart
@@ -16,10 +16,6 @@
   // If changing a method here, also change the other copies.
 
   Iterable<R> cast<R>() => Iterable.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Iterable<R> retype<R>() => cast<R>();
-
   Iterable<T> map<T>(T f(E element)) => new MappedIterable<E, T>(this, f);
 
   Iterable<E> where(bool f(E element)) => new WhereIterable<E>(this, f);
diff --git a/sdk/lib/collection/list.dart b/sdk/lib/collection/list.dart
index fb430a7..644d4b7 100644
--- a/sdk/lib/collection/list.dart
+++ b/sdk/lib/collection/list.dart
@@ -330,10 +330,6 @@
   }
 
   List<R> cast<R>() => List.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>() => cast<R>();
-
   E removeLast() {
     if (length == 0) {
       throw IterableElementError.noElement();
diff --git a/sdk/lib/collection/maps.dart b/sdk/lib/collection/maps.dart
index 5bc178d..795a2e3 100644
--- a/sdk/lib/collection/maps.dart
+++ b/sdk/lib/collection/maps.dart
@@ -119,10 +119,6 @@
   void clear();
 
   Map<RK, RV> cast<RK, RV>() => Map.castFrom<K, V, RK, RV>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<RK, RV> retype<RK, RV>() => cast<RK, RV>();
-
   void forEach(void action(K key, V value)) {
     for (K key in keys) {
       action(key, this[key]);
@@ -315,10 +311,6 @@
   const MapView(Map<K, V> map) : _map = map;
 
   Map<RK, RV> cast<RK, RV>() => _map.cast<RK, RV>();
-
-  @Deprecated("Use cast instead.")
-  Map<RK, RV> retype<RK, RV>() => cast<RK, RV>();
-
   V operator [](Object key) => _map[key];
   void operator []=(K key, V value) {
     _map[key] = value;
@@ -381,7 +373,4 @@
 
   Map<RK, RV> cast<RK, RV>() =>
       new UnmodifiableMapView<RK, RV>(_map.cast<RK, RV>());
-
-  @Deprecated("Use cast instead.")
-  Map<RK, RV> retype<RK, RV>() => cast<RK, RV>();
 }
diff --git a/sdk/lib/collection/queue.dart b/sdk/lib/collection/queue.dart
index 2242fb2..30239cb 100644
--- a/sdk/lib/collection/queue.dart
+++ b/sdk/lib/collection/queue.dart
@@ -78,10 +78,6 @@
    * this queue as well.
    */
   Queue<R> cast<R>();
-
-  @Deprecated("Use cast instead.")
-  Queue<R> retype<R>();
-
   /**
    * Removes and returns the first element of this queue.
    *
@@ -344,10 +340,6 @@
       new DoubleLinkedQueue<E>()..addAll(elements);
 
   Queue<R> cast<R>() => Queue.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Queue<R> retype<R>() => cast<R>();
-
   int get length => _elementCount;
 
   void addLast(E value) {
@@ -643,10 +635,6 @@
   // Iterable interface.
 
   Queue<R> cast<R>() => Queue.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Queue<R> retype<R>() => cast<R>();
-
   Iterator<E> get iterator => new _ListQueueIterator<E>(this);
 
   void forEach(void f(E element)) {
diff --git a/sdk/lib/collection/set.dart b/sdk/lib/collection/set.dart
index 86e8329..6481a56 100644
--- a/sdk/lib/collection/set.dart
+++ b/sdk/lib/collection/set.dart
@@ -48,10 +48,6 @@
   bool get isNotEmpty => length != 0;
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   Iterable<E> followedBy(Iterable<E> other) =>
       new FollowedByIterable<E>.firstEfficient(this, other);
 
diff --git a/sdk/lib/collection/splay_tree.dart b/sdk/lib/collection/splay_tree.dart
index dce7dc5..b61f37a 100644
--- a/sdk/lib/collection/splay_tree.dart
+++ b/sdk/lib/collection/splay_tree.dart
@@ -766,10 +766,6 @@
       new SplayTreeSet<T>((T a, T b) => _comparator(a as E, b as E), _validKey);
 
   Set<R> cast<R>() => Set.castFrom<E, R>(this, newSet: _newSet);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   int _compare(E e1, E e2) => _comparator(e1, e2);
 
   // From Iterable.
diff --git a/sdk/lib/convert/converter.dart b/sdk/lib/convert/converter.dart
index 3fdcb4c..e0aeeb4 100644
--- a/sdk/lib/convert/converter.dart
+++ b/sdk/lib/convert/converter.dart
@@ -65,9 +65,6 @@
    * are acually instances of [RT].
    */
   Converter<RS, RT> cast<RS, RT>() => Converter.castFrom<S, T, RS, RT>(this);
-
-  @Deprecated("Use cast instead.")
-  Converter<RS, RT> retype<RS, RT>() => cast<RS, RT>();
 }
 
 /**
diff --git a/sdk/lib/core/annotations.dart b/sdk/lib/core/annotations.dart
index c0234f5..4c7c812 100644
--- a/sdk/lib/core/annotations.dart
+++ b/sdk/lib/core/annotations.dart
@@ -248,6 +248,7 @@
  * function foo is annotated with a pragma 'other-pragma' specific to OtherTool.
  *
  */
+@pragma('vm.entry_point')
 class pragma {
   /**
    * The name of the hint.
diff --git a/sdk/lib/core/iterable.dart b/sdk/lib/core/iterable.dart
index 99361f7..8aaf8e6a 100644
--- a/sdk/lib/core/iterable.dart
+++ b/sdk/lib/core/iterable.dart
@@ -164,10 +164,6 @@
    * the type [R], e.g., from [toList], it will have exactly the type [R].
    */
   Iterable<R> cast<R>() => Iterable.castFrom<E, R>(this);
-
-  @Deprecated("Use cast instead.")
-  Iterable<R> retype<R>() => cast<R>();
-
   /**
    * Returns the lazy concatentation of this iterable and [other].
    *
diff --git a/sdk/lib/core/list.dart b/sdk/lib/core/list.dart
index bff5b31..3e4feae 100644
--- a/sdk/lib/core/list.dart
+++ b/sdk/lib/core/list.dart
@@ -268,10 +268,6 @@
    * Typically implemented as `List.castFrom<E, R>(this)`.
    */
   List<R> cast<R>();
-
-  @Deprecated("Use cast instead.")
-  List<R> retype<R>();
-
   /**
    * Returns the object at the given [index] in the list
    * or throws a [RangeError] if [index] is out of bounds.
diff --git a/sdk/lib/core/map.dart b/sdk/lib/core/map.dart
index 51fda37f..e122688 100644
--- a/sdk/lib/core/map.dart
+++ b/sdk/lib/core/map.dart
@@ -192,10 +192,6 @@
    * `Map<RK, RV>`.
    */
   Map<RK, RV> cast<RK, RV>();
-
-  @Deprecated("Use cast instead.")
-  Map<RK, RV> retype<RK, RV>();
-
   /**
    * Returns true if this map contains the given [value].
    *
diff --git a/sdk/lib/core/set.dart b/sdk/lib/core/set.dart
index d85ae2b..78f82ab 100644
--- a/sdk/lib/core/set.dart
+++ b/sdk/lib/core/set.dart
@@ -126,10 +126,6 @@
    * this set as well.
    */
   Set<R> cast<R>();
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>();
-
   /**
    * Provides an iterator that iterates over the elements of this set.
    *
diff --git a/sdk/lib/html/dart2js/html_dart2js.dart b/sdk/lib/html/dart2js/html_dart2js.dart
index a695e1f..843e633 100644
--- a/sdk/lib/html/dart2js/html_dart2js.dart
+++ b/sdk/lib/html/dart2js/html_dart2js.dart
@@ -46684,10 +46684,6 @@
   }
 
   Map<K, V> cast<K, V>() => Map.castFrom<String, String, K, V>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<K, V> retype<K, V>() => cast<K, V>();
-
   bool containsValue(Object value) {
     for (var v in this.values) {
       if (value == v) {
@@ -46849,10 +46845,6 @@
   }
 
   Map<K, V> cast<K, V>() => Map.castFrom<String, String, K, V>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<K, V> retype<K, V>() => cast<K, V>();
-
   // TODO: Use lazy iterator when it is available on Map.
   bool containsValue(Object value) => values.any((v) => v == value);
 
diff --git a/sdk/lib/internal/async_cast.dart b/sdk/lib/internal/async_cast.dart
index eee09b9..cb1e112 100644
--- a/sdk/lib/internal/async_cast.dart
+++ b/sdk/lib/internal/async_cast.dart
@@ -19,9 +19,6 @@
   }
 
   Stream<R> cast<R>() => new CastStream<S, R>(_source);
-
-  @Deprecated("Use cast instead.")
-  Stream<R> retype<R>() => cast<R>();
 }
 
 class CastStreamSubscription<S, T> implements StreamSubscription<T> {
@@ -64,10 +61,6 @@
 
   StreamTransformer<RS, RT> cast<RS, RT>() =>
       new CastStreamTransformer<SS, ST, RS, RT>(_source);
-
-  @Deprecated("Use cast instead.")
-  StreamTransformer<RS, RT> retype<RS, RT>() => cast<RS, RT>();
-
   Stream<TT> bind(Stream<TS> stream) =>
       _source.bind(stream.cast<SS>()).cast<TT>();
 }
@@ -85,7 +78,4 @@
 
   Converter<RS, RT> cast<RS, RT>() =>
       new CastConverter<SS, ST, RS, RT>(_source);
-
-  @Deprecated("Use cast instead.")
-  Converter<RS, RT> retype<RS, RT>() => cast<RS, RT>();
 }
diff --git a/sdk/lib/internal/cast.dart b/sdk/lib/internal/cast.dart
index c2a6ce4..8d10ce4 100644
--- a/sdk/lib/internal/cast.dart
+++ b/sdk/lib/internal/cast.dart
@@ -189,10 +189,6 @@
   static Set<R> _defaultEmptySet<R>() => new Set<R>();
 
   Set<R> cast<R>() => new CastSet<S, R>(_source, _emptySet);
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
-
   bool add(T value) => _source.add(value as S);
 
   void addAll(Iterable<T> elements) {
@@ -368,9 +364,6 @@
   final Queue<S> _source;
   CastQueue(this._source);
   Queue<R> cast<R>() => new CastQueue<S, R>(_source);
-
-  @Deprecated("Use cast instead.")
-  Queue<R> retype<R>() => cast<R>();
 }
 
 // TODO(lrn): Use when ListQueue implements List.
diff --git a/sdk/lib/io/platform.dart b/sdk/lib/io/platform.dart
index a5978e6..f7c9053 100644
--- a/sdk/lib/io/platform.dart
+++ b/sdk/lib/io/platform.dart
@@ -204,14 +204,11 @@
   static List<String> get executableArguments => _Platform.executableArguments;
 
   /**
-   * The `--package-root` flag passed to the executable used to run the script
-   * in this isolate.
+   * This returns `null`, as `packages/` directories are no longer supported.
    *
-   * If present, it specifies the directory where Dart packages are looked up.
-   *
-   * Is `null` if there is no `--package-root` flag.
    */
-  static String get packageRoot => _Platform.packageRoot;
+  @Deprecated('packages/ directory resolution is not supported in Dart 2')
+  static String get packageRoot => null; // TODO(mfairhurst): remove this
 
   /**
    * The `--packages` flag passed to the executable used to run the script
diff --git a/sdk/lib/io/platform_impl.dart b/sdk/lib/io/platform_impl.dart
index 4dd898d..5853d89 100644
--- a/sdk/lib/io/platform_impl.dart
+++ b/sdk/lib/io/platform_impl.dart
@@ -30,7 +30,7 @@
    */
   external static _environment();
   external static List<String> _executableArguments();
-  external static String _packageRoot();
+  external static String _packageRoot(); // TODO(mfairhurst): remove this
   external static String _packageConfig();
   external static String _version();
   external static String _localeName();
@@ -38,7 +38,7 @@
 
   static String executable = _executable();
   static String resolvedExecutable = _resolvedExecutable();
-  static String packageRoot = _packageRoot();
+  static String packageRoot = null; // TODO(mfairhurst): remove this
   static String packageConfig = _packageConfig();
 
   static String Function() _localeClosure;
diff --git a/sdk/lib/isolate/isolate.dart b/sdk/lib/isolate/isolate.dart
index 7a677b0..92cf074 100644
--- a/sdk/lib/isolate/isolate.dart
+++ b/sdk/lib/isolate/isolate.dart
@@ -160,11 +160,10 @@
   /**
    * The location of the package configuration of the current isolate, if any.
    *
-   * If the isolate is using a [packageConfig] or the isolate has not been
-   * setup for package resolution, this getter returns `null`, otherwise it
-   * returns the package root - a directory that package URIs are resolved
-   * against.
+   * This getter returns `null`, as the `packages/` directory is not supported
+   * in Dart 2.
    */
+  @Deprecated('packages/ directory resolution is not supported in Dart 2.')
   external static Future<Uri> get packageRoot;
 
   /**
@@ -286,16 +285,6 @@
    *
    * WARNING: The [checked] parameter is not implemented on all platforms yet.
    *
-   * If the [packageRoot] parameter is provided, it is used to find the location
-   * of package sources in the spawned isolate.
-   *
-   * The `packageRoot` URI must be a "file" or "http"/"https" URI that specifies
-   * a directory. If it doesn't end in a slash, one will be added before
-   * using the URI, and any query or fragment parts are ignored.
-   * Package imports (like `"package:foo/bar.dart"`) in the new isolate are
-   * resolved against this location, as by
-   * `packageRoot.resolve("foo/bar.dart")`.
-   *
    * If the [packageConfig] parameter is provided, then it is used to find the
    * location of a package resolution configuration file for the spawned
    * isolate.
@@ -317,14 +306,17 @@
    * spawning succeeded. It will complete with an error otherwise.
    */
   external static Future<Isolate> spawnUri(
-      Uri uri, List<String> args, var message,
+      Uri uri,
+      List<String> args,
+      var message,
       {bool paused: false,
       SendPort onExit,
       SendPort onError,
       bool errorsAreFatal,
       bool checked,
       Map<String, String> environment,
-      Uri packageRoot,
+      @Deprecated('The packages/ dir is not supported in Dart 2')
+          Uri packageRoot,
       Uri packageConfig,
       bool automaticPackageResolution: false});
 
diff --git a/tests/compiler/dart2js/closure/closure_test.dart b/tests/compiler/dart2js/closure/closure_test.dart
index dfc8631..819890e 100644
--- a/tests/compiler/dart2js/closure/closure_test.dart
+++ b/tests/compiler/dart2js/closure/closure_test.dart
@@ -25,7 +25,7 @@
   asyncTest(() async {
     Directory dataDir = new Directory.fromUri(Platform.script.resolve('data'));
     await checkTests(dataDir, computeKernelClosureData,
-        skipForKernel: skipForKernel, args: args);
+        skipForKernel: skipForKernel, args: args, testOmit: true);
   });
 }
 
diff --git a/tests/compiler/dart2js/closure/data/generic_strong.dart b/tests/compiler/dart2js/closure/data/generic_strong.dart
index 1fbe9ca..8823cb6 100644
--- a/tests/compiler/dart2js/closure/data/generic_strong.dart
+++ b/tests/compiler/dart2js/closure/data/generic_strong.dart
@@ -55,8 +55,14 @@
       return /*fields=[S,U],free=[S,U],hasThis*/ () => '$S$U';
     }
 
-    var local2 = /*fields=[S,this],free=[S,this],hasThis*/ (o) {
-      return /*fields=[S,this],free=[S,this],hasThis*/ () => new Map<T, S>();
+    var local2 =
+        /*strong.fields=[S,this],free=[S,this],hasThis*/
+        /*omit.hasThis*/
+        (o) {
+      return
+          /*strong.fields=[S,this],free=[S,this],hasThis*/
+          /*omit.hasThis*/
+          () => new Map<T, S>();
     };
     return local2(local<double>());
   }
diff --git a/tests/compiler/dart2js/closure/data/instantiation1.dart b/tests/compiler/dart2js/closure/data/instantiation1.dart
new file mode 100644
index 0000000..9e86e11
--- /dev/null
+++ b/tests/compiler/dart2js/closure/data/instantiation1.dart
@@ -0,0 +1,26 @@
+// 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.
+
+int f<T>(T a) => null;
+
+typedef int F<R>(R a);
+
+/*element: B.:hasThis*/
+class B<S> {
+  /*element: B.method:hasThis*/
+  method() {
+    return
+        /*kernel.hasThis*/
+        /*strong.fields=[this],free=[this],hasThis*/
+        /*omit.hasThis*/
+        () {
+      F<S> c = f;
+      return c;
+    };
+  }
+}
+
+main() {
+  new B().method();
+}
diff --git a/tests/compiler/dart2js/closure/data/instantiation2.dart b/tests/compiler/dart2js/closure/data/instantiation2.dart
new file mode 100644
index 0000000..4fd81d1
--- /dev/null
+++ b/tests/compiler/dart2js/closure/data/instantiation2.dart
@@ -0,0 +1,25 @@
+// 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.
+
+bool f<T>(T a) => a is T;
+
+typedef bool F<R>(R a);
+
+/*element: B.:hasThis*/
+class B<S> {
+  /*element: B.method:hasThis*/
+  method() {
+    return
+        /*kernel.hasThis*/
+        /*!kernel.fields=[this],free=[this],hasThis*/
+        () {
+      F<S> c = f;
+      return c;
+    };
+  }
+}
+
+main() {
+  new B().method();
+}
diff --git a/tests/compiler/dart2js/closure/data/instantiation3.dart b/tests/compiler/dart2js/closure/data/instantiation3.dart
new file mode 100644
index 0000000..aeeee92
--- /dev/null
+++ b/tests/compiler/dart2js/closure/data/instantiation3.dart
@@ -0,0 +1,21 @@
+// 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.
+
+int f<T>(T a) => null;
+
+typedef int F<R>(R a);
+
+method<S>() {
+  return
+      /*strong.fields=[S],free=[S]*/
+      /*omit.*/
+      () {
+    F<S> c = f;
+    return c;
+  };
+}
+
+main() {
+  method();
+}
diff --git a/tests/compiler/dart2js/closure/data/instantiation4.dart b/tests/compiler/dart2js/closure/data/instantiation4.dart
new file mode 100644
index 0000000..957eca0
--- /dev/null
+++ b/tests/compiler/dart2js/closure/data/instantiation4.dart
@@ -0,0 +1,21 @@
+// 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.
+
+bool f<T>(T a) => a is T;
+
+typedef bool F<R>(R a);
+
+method<S>() {
+  return
+      /*strong.fields=[S],free=[S]*/
+      /*omit.fields=[S],free=[S]*/
+      () {
+    F<S> c = f;
+    return c;
+  };
+}
+
+main() {
+  method();
+}
diff --git a/tests/compiler/dart2js/closure/data/instantiation_strong.dart b/tests/compiler/dart2js/closure/data/instantiation_strong.dart
index 10b70e9..8f95b60 100644
--- a/tests/compiler/dart2js/closure/data/instantiation_strong.dart
+++ b/tests/compiler/dart2js/closure/data/instantiation_strong.dart
@@ -5,7 +5,8 @@
 T id<T>(T t) => t;
 
 method<S>(S s) {
-  /*fields=[S],free=[S]*/
+  /*strong.fields=[S],free=[S]*/
+  /*omit.*/
   S Function(S) getId() => id;
   return getId();
 }
diff --git a/tests/compiler/dart2js/closure/data/list_literal_untested_strong_trust.dart b/tests/compiler/dart2js/closure/data/list_literal_untested_strong_trust.dart
index 55e709a..52788fc 100644
--- a/tests/compiler/dart2js/closure/data/list_literal_untested_strong_trust.dart
+++ b/tests/compiler/dart2js/closure/data/list_literal_untested_strong_trust.dart
@@ -6,7 +6,9 @@
 
 @NoInline()
 method<T>() {
-  /**/ dynamic local() => <T>[];
+  /*!strong.*/
+  /*strong.fields=[T],free=[T]*/
+  dynamic local() => <T>[];
   return local;
 }
 
diff --git a/tests/compiler/dart2js/closure/data/list_literal_untested_trust.dart b/tests/compiler/dart2js/closure/data/list_literal_untested_trust.dart
index 92b057e..89fe422 100644
--- a/tests/compiler/dart2js/closure/data/list_literal_untested_trust.dart
+++ b/tests/compiler/dart2js/closure/data/list_literal_untested_trust.dart
@@ -9,7 +9,9 @@
   /*element: A.method:hasThis*/
   @NoInline()
   method() {
-    /*hasThis*/ dynamic local() => <T>[];
+    /*!strong.hasThis*/
+    /*strong.fields=[this],free=[this],hasThis*/
+    dynamic local() => <T>[];
     return local;
   }
 }
diff --git a/tests/compiler/dart2js/closure/data/map_literal_untested_strong_trust.dart b/tests/compiler/dart2js/closure/data/map_literal_untested_strong_trust.dart
index 8793b90..6cfb9e9 100644
--- a/tests/compiler/dart2js/closure/data/map_literal_untested_strong_trust.dart
+++ b/tests/compiler/dart2js/closure/data/map_literal_untested_strong_trust.dart
@@ -6,7 +6,9 @@
 
 @NoInline()
 method<T>() {
-  /**/ dynamic local() => <T, int>{};
+  /*!strong.*/
+  /*strong.fields=[T],free=[T]*/
+  dynamic local() => <T, int>{};
   return local;
 }
 
diff --git a/tests/compiler/dart2js/closure/data/map_literal_untested_trust.dart b/tests/compiler/dart2js/closure/data/map_literal_untested_trust.dart
index 958da83..146de88 100644
--- a/tests/compiler/dart2js/closure/data/map_literal_untested_trust.dart
+++ b/tests/compiler/dart2js/closure/data/map_literal_untested_trust.dart
@@ -9,7 +9,9 @@
   /*element: A.method:hasThis*/
   @NoInline()
   method() {
-    /*hasThis*/ dynamic local() => <T, int>{};
+    /*!strong.hasThis*/
+    /*strong.fields=[this],free=[this],hasThis*/
+    dynamic local() => <T, int>{};
     return local;
   }
 }
diff --git a/tests/compiler/dart2js/closure/data/test_type.dart b/tests/compiler/dart2js/closure/data/test_type.dart
index aaadba2..1cd8aef 100644
--- a/tests/compiler/dart2js/closure/data/test_type.dart
+++ b/tests/compiler/dart2js/closure/data/test_type.dart
@@ -38,7 +38,7 @@
 class Class3<T> {
   /*element: Class3.method3:hasThis*/
   method3(dynamic o) {
-    /*kernel.fields=[o],free=[o],hasThis*/
+    /*!strong.fields=[o],free=[o],hasThis*/
     /*strong.fields=[o,this],free=[o,this],hasThis*/
     T local() => o;
     return local;
diff --git a/tests/compiler/dart2js/closure/data/test_type_strong.dart b/tests/compiler/dart2js/closure/data/test_type_strong.dart
index 93dcec0..cb8f88d 100644
--- a/tests/compiler/dart2js/closure/data/test_type_strong.dart
+++ b/tests/compiler/dart2js/closure/data/test_type_strong.dart
@@ -30,7 +30,8 @@
 
 /*element: method3:*/
 method3<T>(dynamic o) {
-  /*fields=[T,o],free=[T,o]*/
+  /*strong.fields=[T,o],free=[T,o]*/
+  /*omit.fields=[o],free=[o]*/
   T local() => o;
   return local;
 }
diff --git a/tests/compiler/dart2js/closure/data/test_type_strong_trust.dart b/tests/compiler/dart2js/closure/data/test_type_strong_trust.dart
deleted file mode 100644
index abb909b..0000000
--- a/tests/compiler/dart2js/closure/data/test_type_strong_trust.dart
+++ /dev/null
@@ -1,42 +0,0 @@
-// 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.
-
-////////////////////////////////////////////////////////////////////////////////
-/// Explicit is-test is required even with --omit-implicit-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: method1:*/
-method1<T>(dynamic o) {
-  /*fields=[T,o],free=[T,o]*/
-  dynamic local() => o is T;
-  return local;
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// Explicit as-cast is required even with --omit-implicit-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: method2:*/
-method2<T>(dynamic o) {
-  /*fields=[T,o],free=[T,o]*/
-  dynamic local() => o as T;
-  return local;
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// Implicit as-cast is not required with --omit-implicit-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: method3:*/
-method3<T>(dynamic o) {
-  /*fields=[o],free=[o]*/
-  T local() => o;
-  return local;
-}
-
-main() {
-  method1<int>(0).call();
-  method2<int>(0).call();
-  method3<int>(0).call();
-}
diff --git a/tests/compiler/dart2js/closure/data/test_type_trust.dart b/tests/compiler/dart2js/closure/data/test_type_trust.dart
deleted file mode 100644
index 7ed8dc1..0000000
--- a/tests/compiler/dart2js/closure/data/test_type_trust.dart
+++ /dev/null
@@ -1,51 +0,0 @@
-// 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.
-
-////////////////////////////////////////////////////////////////////////////////
-/// Explicit is-test is required even with --omit-implicit-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class1.:hasThis*/
-class Class1<T> {
-  /*element: Class1.method1:hasThis*/
-  method1(dynamic o) {
-    /*fields=[o,this],free=[o,this],hasThis*/
-    dynamic local() => o is T;
-    return local;
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// Explicit as-cast is required even with --omit-implicit-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class2.:hasThis*/
-class Class2<T> {
-  /*element: Class2.method2:hasThis*/
-  method2(dynamic o) {
-    /*fields=[o,this],free=[o,this],hasThis*/
-    dynamic local() => o as T;
-    return local;
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// Implicit as-cast is not required with --omit-implicit-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class3.:hasThis*/
-class Class3<T> {
-  /*element: Class3.method3:hasThis*/
-  method3(dynamic o) {
-    /*fields=[o],free=[o],hasThis*/
-    T local() => o;
-    return local;
-  }
-}
-
-main() {
-  new Class1<int>().method1(0).call();
-  new Class2<int>().method2(0).call();
-  new Class3<int>().method3(0).call();
-}
diff --git a/tests/compiler/dart2js/closure/data/type_annotations.dart b/tests/compiler/dart2js/closure/data/type_annotations.dart
index 112565e..a891048 100644
--- a/tests/compiler/dart2js/closure/data/type_annotations.dart
+++ b/tests/compiler/dart2js/closure/data/type_annotations.dart
@@ -48,7 +48,7 @@
 class Class2<T> {
   /*element: Class2.method2:hasThis*/
   method2() {
-    /*kernel.hasThis*/
+    /*!strong.hasThis*/
     /*strong.fields=[this],free=[this],hasThis*/
     dynamic local(T t) => t;
     return local;
@@ -63,7 +63,7 @@
 class Class3<T> {
   /*element: Class3.method3:hasThis*/
   method3(dynamic o) {
-    /*kernel.fields=[o],free=[o],hasThis*/
+    /*!strong.fields=[o],free=[o],hasThis*/
     /*strong.fields=[o,this],free=[o,this],hasThis*/
     T local() => o;
     return local;
@@ -106,7 +106,7 @@
 class Class6<T> {
   /*element: Class6.method6:hasThis*/
   method6() {
-    /*kernel.hasThis*/
+    /*!strong.hasThis*/
     /*strong.fields=[this],free=[this],hasThis*/
     dynamic local(T t) {
       /*fields=[t],free=[t],hasThis*/
@@ -126,7 +126,7 @@
 class Class7<T> {
   /*element: Class7.method7:hasThis*/
   method7(dynamic o) {
-    /*kernel.fields=[o],free=[o],hasThis*/
+    /*!strong.fields=[o],free=[o],hasThis*/
     /*strong.fields=[o,this],free=[o,this],hasThis*/
     T local() {
       /*fields=[o],free=[o],hasThis*/
diff --git a/tests/compiler/dart2js/closure/data/type_annotations_strong.dart b/tests/compiler/dart2js/closure/data/type_annotations_strong.dart
index 3b4c2a6..878e3bd 100644
--- a/tests/compiler/dart2js/closure/data/type_annotations_strong.dart
+++ b/tests/compiler/dart2js/closure/data/type_annotations_strong.dart
@@ -21,7 +21,8 @@
 ////////////////////////////////////////////////////////////////////////////////
 
 method2<T>() {
-  /*fields=[T],free=[T]*/
+  /*strong.fields=[T],free=[T]*/
+  /*omit.*/
   dynamic local(T t) => t;
   return local;
 }
@@ -31,7 +32,8 @@
 ////////////////////////////////////////////////////////////////////////////////
 
 method3<T>(dynamic o) {
-  /*fields=[T,o],free=[T,o]*/
+  /*strong.fields=[T,o],free=[T,o]*/
+  /*omit.fields=[o],free=[o]*/
   T local() => o;
   return local;
 }
@@ -61,7 +63,8 @@
 ////////////////////////////////////////////////////////////////////////////////
 
 method6<T>() {
-  /*fields=[T],free=[T]*/
+  /*strong.fields=[T],free=[T]*/
+  /*omit.*/
   dynamic local(T t) {
     /*fields=[t],free=[t]*/
     dynamic inner() => t;
@@ -76,7 +79,8 @@
 ////////////////////////////////////////////////////////////////////////////////
 
 method7<T>(dynamic o) {
-  /*fields=[T,o],free=[T,o]*/
+  /*strong.fields=[T,o],free=[T,o]*/
+  /*omit.fields=[o],free=[o]*/
   T local() {
     /*fields=[o],free=[o]*/
     dynamic inner() => o;
diff --git a/tests/compiler/dart2js/closure/data/type_annotations_strong_trust.dart b/tests/compiler/dart2js/closure/data/type_annotations_strong_trust.dart
deleted file mode 100644
index 1ec0bf1..0000000
--- a/tests/compiler/dart2js/closure/data/type_annotations_strong_trust.dart
+++ /dev/null
@@ -1,97 +0,0 @@
-// 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.
-
-////////////////////////////////////////////////////////////////////////////////
-/// A sound assignment to a local variable doesn't capture the type variable.
-////////////////////////////////////////////////////////////////////////////////
-
-method1<T>(T o) {
-  /*fields=[o],free=[o]*/
-  dynamic local() {
-    T t = o;
-    return t;
-  }
-
-  return local;
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function parameter type is with --omit-type-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-method2<T>() {
-  /**/
-  dynamic local(T t) => t;
-  return local;
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function return type is not captured with --omit-type-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-method3<T>(dynamic o) {
-  /*fields=[o],free=[o]*/
-  T local() => o;
-  return local;
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A member parameter type is not captured.
-////////////////////////////////////////////////////////////////////////////////
-
-method4<T>(T o) {
-  /*fields=[o],free=[o]*/
-  dynamic local() => o;
-  return local;
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A member return type is not captured.
-////////////////////////////////////////////////////////////////////////////////
-
-T method5<T>(dynamic o) {
-  /*fields=[o],free=[o]*/
-  dynamic local() => o;
-  return local();
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function parameter type is not captured by an inner local function.
-////////////////////////////////////////////////////////////////////////////////
-
-method6<T>() {
-  /**/
-  dynamic local(T t) {
-    /*fields=[t],free=[t]*/
-    dynamic inner() => t;
-    return inner;
-  }
-
-  return local;
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function return type is not captured by an inner local function.
-////////////////////////////////////////////////////////////////////////////////
-
-method7<T>(dynamic o) {
-  /*fields=[o],free=[o]*/
-  T local() {
-    /*fields=[o],free=[o]*/
-    dynamic inner() => o;
-    return inner();
-  }
-
-  return local;
-}
-
-main() {
-  method1<int>(0).call();
-  method2<int>().call(0);
-  method3<int>(0).call();
-  method4<int>(0).call();
-  method5<int>(0);
-  method6<int>().call(0).call();
-  method7<int>(0).call().call();
-}
diff --git a/tests/compiler/dart2js/closure/data/type_annotations_trust.dart b/tests/compiler/dart2js/closure/data/type_annotations_trust.dart
deleted file mode 100644
index ff0ee55..0000000
--- a/tests/compiler/dart2js/closure/data/type_annotations_trust.dart
+++ /dev/null
@@ -1,125 +0,0 @@
-// 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.
-
-////////////////////////////////////////////////////////////////////////////////
-/// A sound assignment to a local variable doesn't capture the type variable.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class1.:hasThis*/
-class Class1<T> {
-  /*element: Class1.method1:hasThis*/
-  method1(T o) {
-    /*fields=[o],free=[o],hasThis*/
-    dynamic local() {
-      T t = o;
-      return t;
-    }
-
-    return local;
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function parameter type is with --omit-type-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class2.:hasThis*/
-class Class2<T> {
-  /*element: Class2.method2:hasThis*/
-  method2() {
-    /*hasThis*/
-    dynamic local(T t) => t;
-    return local;
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function return type is not captured with --omit-type-checks.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class3.:hasThis*/
-class Class3<T> {
-  /*element: Class3.method3:hasThis*/
-  method3(dynamic o) {
-    /*fields=[o],free=[o],hasThis*/
-    T local() => o;
-    return local;
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A member parameter type is not captured.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class4.:hasThis*/
-class Class4<T> {
-  /*element: Class4.method4:hasThis*/
-  method4(T o) {
-    /*fields=[o],free=[o],hasThis*/
-    dynamic local() => o;
-    return local;
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A member return type is not captured.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class5.:hasThis*/
-class Class5<T> {
-  /*element: Class5.method5:hasThis*/
-  T method5(dynamic o) {
-    /*fields=[o],free=[o],hasThis*/
-    dynamic local() => o;
-    return local();
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function parameter type is not captured by an inner local function.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class6.:hasThis*/
-class Class6<T> {
-  /*element: Class6.method6:hasThis*/
-  method6() {
-    /*hasThis*/
-    dynamic local(T t) {
-      /*fields=[t],free=[t],hasThis*/
-      dynamic inner() => t;
-      return inner;
-    }
-
-    return local;
-  }
-}
-
-////////////////////////////////////////////////////////////////////////////////
-/// A local function return type is not captured by an inner local function.
-////////////////////////////////////////////////////////////////////////////////
-
-/*element: Class7.:hasThis*/
-class Class7<T> {
-  /*element: Class7.method7:hasThis*/
-  method7(dynamic o) {
-    /*fields=[o],free=[o],hasThis*/
-    T local() {
-      /*fields=[o],free=[o],hasThis*/
-      dynamic inner() => o;
-      return inner();
-    }
-
-    return local;
-  }
-}
-
-main() {
-  new Class1<int>().method1(0).call();
-  new Class2<int>().method2().call(0);
-  new Class3<int>().method3(0).call();
-  new Class4<int>().method4(0).call();
-  new Class5<int>().method5(0);
-  new Class6<int>().method6().call(0).call();
-  new Class7<int>().method7(0).call().call();
-}
diff --git a/tests/compiler/dart2js/equivalence/id_equivalence_helper.dart b/tests/compiler/dart2js/equivalence/id_equivalence_helper.dart
index ee303c1..45cab1b 100644
--- a/tests/compiler/dart2js/equivalence/id_equivalence_helper.dart
+++ b/tests/compiler/dart2js/equivalence/id_equivalence_helper.dart
@@ -484,7 +484,8 @@
     ComputeClassDataFunction computeClassDataFromKernel,
     int shards: 1,
     int shardIndex: 0,
-    bool testOmit: false}) async {
+    bool testOmit: false,
+    void onTest(Uri uri)}) async {
   args = args.toList();
   bool verbose = args.remove('-v');
   bool shouldContinue = args.remove('-c');
@@ -523,6 +524,9 @@
       trustTypeAnnotations = true;
     }
 
+    if (onTest != null) {
+      onTest(entity.uri);
+    }
     print('----------------------------------------------------------------');
     print('Test file: ${entity.uri}');
     // Pretend this is a dart2js_native test to allow use of 'native' keyword
diff --git a/tests/compiler/dart2js/generic_methods/generic_method_test.dart b/tests/compiler/dart2js/generic_methods/generic_method_test.dart
index e907015..ae1e4fd 100644
--- a/tests/compiler/dart2js/generic_methods/generic_method_test.dart
+++ b/tests/compiler/dart2js/generic_methods/generic_method_test.dart
@@ -113,8 +113,6 @@
   new Class2().method5<int>(0);
   new Class3().method6<int>(0);
   dynamic c3 = args != null ? new Class3() : new Class2();
-  // TODO(johnniwinther): Expected bounds should be `dynamic` when CFE supports
-  // instantiate-to-bound.
   c3.method6(0); // Missing type arguments.
   try {
     dynamic c2 = args == null ? new Class3() : new Class2();
@@ -162,8 +160,8 @@
 "foo" is int = false
 
 Class3.method6:
-0 is Object = true
-"foo" is Object = true
+0 is dynamic = true
+"foo" is dynamic = true
 
 Class2.method6:
 0 is int = true
diff --git a/tests/compiler/dart2js/inference/data/field_type.dart b/tests/compiler/dart2js/inference/data/field_type.dart
index 51b672d..44168f3 100644
--- a/tests/compiler/dart2js/inference/data/field_type.dart
+++ b/tests/compiler/dart2js/inference/data/field_type.dart
@@ -202,7 +202,8 @@
 
   /*element: A9.:[exact=A9]*/
   A9(/*[exact=JSBool]*/ x) {
-    if (x) {} else {
+    if (x) {
+    } else {
       /*update: [exact=A9]*/ f9 = "1";
     }
   }
@@ -727,7 +728,8 @@
   /*element: A29.:[exact=A29]*/
   A29(/*[exact=JSUInt31]*/ x) {
     this. /*update: [exact=A29]*/ f29a = x;
-    if (x /*invoke: [exact=JSUInt31]*/ == 0) {} else {
+    if (x /*invoke: [exact=JSUInt31]*/ == 0) {
+    } else {
       return;
     }
     this. /*update: [exact=A29]*/ f29b = x;
diff --git a/tests/compiler/dart2js/inference/data/general.dart b/tests/compiler/dart2js/inference/data/general.dart
index ea317d5..1b2d806 100644
--- a/tests/compiler/dart2js/inference/data/general.dart
+++ b/tests/compiler/dart2js/inference/data/general.dart
@@ -306,7 +306,8 @@
 
 /*element: testIsCheck26:[subclass=JSInt]*/
 testIsCheck26(/*[null|subclass=Object]*/ a) {
-  if (a is int) {} else {
+  if (a is int) {
+  } else {
     throw 42;
   }
   return a;
@@ -314,7 +315,8 @@
 
 /*element: testIsCheck27:[subclass=JSInt]*/
 testIsCheck27(/*[null|subclass=Object]*/ a) {
-  if (a is int) {} else {
+  if (a is int) {
+  } else {
     return 42;
   }
   return a;
@@ -322,7 +324,8 @@
 
 /*element: testIsCheck28:[null|subclass=Object]*/
 testIsCheck28(/*[null|subclass=Object]*/ a) {
-  if (a is int) {} else {}
+  if (a is int) {
+  } else {}
   return a;
 }
 
@@ -344,7 +347,8 @@
 /*element: testIf2:[null|exact=JSUInt31]*/
 testIf2(/*[null|subclass=Object]*/ a) {
   var c = null;
-  if (a) {} else {
+  if (a) {
+  } else {
     c = 10;
   }
   return c;
diff --git a/tests/compiler/dart2js/inference/data/use_static_types.dart b/tests/compiler/dart2js/inference/data/use_static_types.dart
new file mode 100644
index 0000000..7e40669
--- /dev/null
+++ b/tests/compiler/dart2js/inference/data/use_static_types.dart
@@ -0,0 +1,532 @@
+// 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.
+
+/*element: A.:[exact=A]*/
+class A {}
+
+/*element: B.:[exact=B]*/
+class B extends A {}
+
+/*element: C.:[exact=C]*/
+class C {}
+
+/*element: main:[null]*/
+main() {
+  invokeFunctions();
+  invokeGenericClasses();
+  invokeGenericMethods();
+}
+
+/*kernel.element: invokeFunction1:[null|subclass=Object]*/
+/*strong.element: invokeFunction1:[null|subclass=A]*/
+invokeFunction1(A Function() /*[subclass=Closure]*/ f) {
+  return f();
+}
+
+/*kernel.element: invokeFunction2:[null|subclass=Object]*/
+/*strong.element: invokeFunction2:[null|exact=B]*/
+invokeFunction2(B Function() /*[subclass=Closure]*/ f) {
+  return f();
+}
+
+/*kernel.element: invokeFunction3:[null|subclass=Object]*/
+/*strong.element: invokeFunction3:[null|exact=C]*/
+invokeFunction3(C Function() /*[subclass=Closure]*/ f) {
+  return f();
+}
+
+/*element: genericFunction:[null|subclass=Object]*/
+T genericFunction<T>(T Function() /*[subclass=Closure]*/ f) => f();
+
+/*kernel.element: invokeGenericFunction1:[null|subclass=Object]*/
+/*strong.element: invokeGenericFunction1:[null|subclass=A]*/
+invokeGenericFunction1() {
+  return genericFunction<A>(/*[exact=A]*/ () => new A());
+}
+
+/*kernel.element: invokeGenericFunction2:[null|subclass=Object]*/
+/*strong.element: invokeGenericFunction2:[null|exact=B]*/
+invokeGenericFunction2() {
+  return genericFunction<B>(/*[exact=B]*/ () => new B());
+}
+
+/*kernel.element: invokeGenericFunction3:[null|subclass=Object]*/
+/*strong.element: invokeGenericFunction3:[null|exact=C]*/
+invokeGenericFunction3() {
+  return genericFunction<C>(/*[exact=C]*/ () => new C());
+}
+
+/*kernel.element: invokeGenericLocalFunction1:[null|subclass=Object]*/
+/*strong.element: invokeGenericLocalFunction1:[null|subclass=A]*/
+invokeGenericLocalFunction1() {
+  /*[null|subclass=Object]*/
+  T local<T>(T Function() /*[subclass=Closure]*/ f) => f();
+  return local<A>(/*[exact=A]*/ () => new A());
+}
+
+/*kernel.element: invokeGenericLocalFunction2:[null|subclass=Object]*/
+/*strong.element: invokeGenericLocalFunction2:[null|exact=B]*/
+invokeGenericLocalFunction2() {
+  /*[null|subclass=Object]*/
+  T local<T>(T Function() /*[subclass=Closure]*/ f) => f();
+  return local<B>(/*[exact=B]*/ () => new B());
+}
+
+/*kernel.element: invokeGenericLocalFunction3:[null|subclass=Object]*/
+/*strong.element: invokeGenericLocalFunction3:[null|exact=C]*/
+invokeGenericLocalFunction3() {
+  /*[null|subclass=Object]*/
+  T local<T>(T Function() /*[subclass=Closure]*/ f) => f();
+  return local<C>(/*[exact=C]*/ () => new C());
+}
+
+/*element: invokeFunctions:[null]*/
+invokeFunctions() {
+  invokeFunction1(/*[exact=A]*/ () => new A());
+  invokeFunction2(/*[exact=B]*/ () => new B());
+  invokeFunction3(/*[exact=C]*/ () => new C());
+  invokeGenericFunction1();
+  invokeGenericFunction2();
+  invokeGenericFunction3();
+  invokeGenericLocalFunction1();
+  invokeGenericLocalFunction2();
+  invokeGenericLocalFunction3();
+}
+
+class GenericClass<T> {
+  /*element: GenericClass.field:Union([exact=C], [subclass=A])*/
+  final T field;
+
+  /*element: GenericClass.functionTypedField:[subclass=Closure]*/
+  final T Function() functionTypedField;
+
+  /*element: GenericClass.:[exact=GenericClass]*/
+  GenericClass(this. /*Union([exact=C], [subclass=A])*/ field)
+      : functionTypedField = (/*Union([exact=C], [subclass=A])*/ () => field);
+
+  /*element: GenericClass.getter:Union([exact=C], [subclass=A])*/
+  T get getter => /*[subclass=GenericClass]*/ field;
+
+  /*element: GenericClass.functionTypedGetter:[subclass=Closure]*/
+  T Function()
+      get functionTypedGetter => /*[subclass=GenericClass]*/ functionTypedField;
+
+  /*element: GenericClass.method:Union([exact=C], [subclass=A])*/
+  T method() => /*[subclass=GenericClass]*/ field;
+
+  /*element: GenericClass.functionTypedMethod:[subclass=Closure]*/
+  T Function()
+      functionTypedMethod() => /*[subclass=GenericClass]*/ functionTypedField;
+}
+
+class GenericSubclass<T> extends GenericClass<T> {
+  /*element: GenericSubclass.:[exact=GenericSubclass]*/
+  GenericSubclass(T /*Union([exact=C], [subclass=A])*/ field) : super(field);
+
+  /*element: GenericSubclass.superField:Union([exact=C], [subclass=A])*/
+  superField() => super.field;
+
+  /*element: GenericSubclass.superGetter:Union([exact=C], [subclass=A])*/
+  superGetter() => super.getter;
+
+  /*element: GenericSubclass.superMethod:Union([exact=C], [subclass=A])*/
+  superMethod() => super.method();
+
+  /*element: GenericSubclass.superFieldInvoke:[null|subclass=Object]*/
+  superFieldInvoke() => super.functionTypedField();
+
+  /*element: GenericSubclass.superGetterInvoke:[null|subclass=Object]*/
+  superGetterInvoke() => super.functionTypedGetter();
+
+  /*element: GenericSubclass.superMethodInvoke:[null|subclass=Object]*/
+  superMethodInvoke() => super.functionTypedMethod()();
+}
+
+/*kernel.element: invokeInstanceMethod1:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeInstanceMethod1:[subclass=A]*/
+invokeInstanceMethod1(GenericClass<A> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ method();
+
+/*kernel.element: invokeInstanceMethod2:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeInstanceMethod2:[exact=B]*/
+invokeInstanceMethod2(GenericClass<B> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ method();
+
+/*kernel.element: invokeInstanceMethod3:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeInstanceMethod3:[exact=C]*/
+invokeInstanceMethod3(GenericClass<C> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ method();
+
+/*kernel.element: invokeInstanceGetter1:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeInstanceGetter1:[subclass=A]*/
+invokeInstanceGetter1(GenericClass<A> /*[exact=GenericClass]*/ c) =>
+    c. /*[exact=GenericClass]*/ getter;
+
+/*kernel.element: invokeInstanceGetter2:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeInstanceGetter2:[exact=B]*/
+invokeInstanceGetter2(GenericClass<B> /*[exact=GenericClass]*/ c) =>
+    c. /*[exact=GenericClass]*/ getter;
+
+/*kernel.element: invokeInstanceGetter3:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeInstanceGetter3:[exact=C]*/
+invokeInstanceGetter3(GenericClass<C> /*[exact=GenericClass]*/ c) =>
+    c. /*[exact=GenericClass]*/ getter;
+
+/*kernel.element: accessInstanceField1:Union([exact=C], [subclass=A])*/
+/*strong.element: accessInstanceField1:[subclass=A]*/
+accessInstanceField1(GenericClass<A> /*[exact=GenericClass]*/ c) =>
+    c. /*[exact=GenericClass]*/ field;
+
+/*kernel.element: accessInstanceField2:Union([exact=C], [subclass=A])*/
+/*strong.element: accessInstanceField2:[exact=B]*/
+accessInstanceField2(GenericClass<B> /*[exact=GenericClass]*/ c) =>
+    c. /*[exact=GenericClass]*/ field;
+
+/*kernel.element: accessInstanceField3:Union([exact=C], [subclass=A])*/
+/*strong.element: accessInstanceField3:[exact=C]*/
+accessInstanceField3(GenericClass<C> /*[exact=GenericClass]*/ c) =>
+    c. /*[exact=GenericClass]*/ field;
+
+/*element: invokeSuperMethod1:Union([exact=C], [subclass=A])*/
+invokeSuperMethod1(GenericSubclass<A> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superMethod();
+
+/*element: invokeSuperMethod2:Union([exact=C], [subclass=A])*/
+invokeSuperMethod2(GenericSubclass<B> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superMethod();
+
+/*element: invokeSuperMethod3:Union([exact=C], [subclass=A])*/
+invokeSuperMethod3(GenericSubclass<C> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superMethod();
+
+/*element: invokeSuperGetter1:Union([exact=C], [subclass=A])*/
+invokeSuperGetter1(GenericSubclass<A> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superGetter();
+
+/*element: invokeSuperGetter2:Union([exact=C], [subclass=A])*/
+invokeSuperGetter2(GenericSubclass<B> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superGetter();
+
+/*element: invokeSuperGetter3:Union([exact=C], [subclass=A])*/
+invokeSuperGetter3(GenericSubclass<C> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superGetter();
+
+/*element: accessSuperField1:Union([exact=C], [subclass=A])*/
+accessSuperField1(GenericSubclass<A> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superField();
+
+/*element: accessSuperField2:Union([exact=C], [subclass=A])*/
+accessSuperField2(GenericSubclass<B> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superField();
+
+/*element: accessSuperField3:Union([exact=C], [subclass=A])*/
+accessSuperField3(GenericSubclass<C> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superField();
+
+/*kernel.element: invokeFunctionTypedInstanceMethod1:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceMethod1:[null|subclass=A]*/
+invokeFunctionTypedInstanceMethod1(
+        GenericClass<A> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedMethod()();
+
+/*kernel.element: invokeFunctionTypedInstanceMethod2:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceMethod2:[null|exact=B]*/
+invokeFunctionTypedInstanceMethod2(
+        GenericClass<B> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedMethod()();
+
+/*kernel.element: invokeFunctionTypedInstanceMethod3:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceMethod3:[null|exact=C]*/
+invokeFunctionTypedInstanceMethod3(
+        GenericClass<C> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedMethod()();
+
+/*kernel.element: invokeFunctionTypedInstanceGetter1:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceGetter1:[null|subclass=A]*/
+invokeFunctionTypedInstanceGetter1(
+        GenericClass<A> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedGetter();
+
+/*kernel.element: invokeFunctionTypedInstanceGetter2:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceGetter2:[null|exact=B]*/
+invokeFunctionTypedInstanceGetter2(
+        GenericClass<B> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedGetter();
+
+/*kernel.element: invokeFunctionTypedInstanceGetter3:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceGetter3:[null|exact=C]*/
+invokeFunctionTypedInstanceGetter3(
+        GenericClass<C> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedGetter();
+
+/*kernel.element: invokeFunctionTypedInstanceField1:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceField1:[null|subclass=A]*/
+invokeFunctionTypedInstanceField1(GenericClass<A> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedField();
+
+/*kernel.element: invokeFunctionTypedInstanceField2:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceField2:[null|exact=B]*/
+invokeFunctionTypedInstanceField2(GenericClass<B> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedField();
+
+/*kernel.element: invokeFunctionTypedInstanceField3:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedInstanceField3:[null|exact=C]*/
+invokeFunctionTypedInstanceField3(GenericClass<C> /*[exact=GenericClass]*/ c) =>
+    c. /*invoke: [exact=GenericClass]*/ functionTypedField();
+
+/*element: invokeFunctionTypedSuperMethod1:[null|subclass=Object]*/
+invokeFunctionTypedSuperMethod1(
+        GenericSubclass<A> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superMethodInvoke();
+
+/*element: invokeFunctionTypedSuperMethod2:[null|subclass=Object]*/
+invokeFunctionTypedSuperMethod2(
+        GenericSubclass<B> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superMethodInvoke();
+
+/*element: invokeFunctionTypedSuperMethod3:[null|subclass=Object]*/
+invokeFunctionTypedSuperMethod3(
+        GenericSubclass<C> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superMethodInvoke();
+
+/*element: invokeFunctionTypedSuperGetter1:[null|subclass=Object]*/
+invokeFunctionTypedSuperGetter1(
+        GenericSubclass<A> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superGetterInvoke();
+
+/*element: invokeFunctionTypedSuperGetter2:[null|subclass=Object]*/
+invokeFunctionTypedSuperGetter2(
+        GenericSubclass<B> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superGetterInvoke();
+
+/*element: invokeFunctionTypedSuperGetter3:[null|subclass=Object]*/
+invokeFunctionTypedSuperGetter3(
+        GenericSubclass<C> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superGetterInvoke();
+
+/*element: invokeFunctionTypedSuperField1:[null|subclass=Object]*/
+invokeFunctionTypedSuperField1(
+        GenericSubclass<A> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superFieldInvoke();
+
+/*element: invokeFunctionTypedSuperField2:[null|subclass=Object]*/
+invokeFunctionTypedSuperField2(
+        GenericSubclass<B> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superFieldInvoke();
+
+/*element: invokeFunctionTypedSuperField3:[null|subclass=Object]*/
+invokeFunctionTypedSuperField3(
+        GenericSubclass<C> /*[exact=GenericSubclass]*/ c) =>
+    c. /*invoke: [exact=GenericSubclass]*/ superFieldInvoke();
+
+/*element: invokeGenericClasses:[null]*/
+invokeGenericClasses() {
+  invokeInstanceMethod1(new GenericClass<A>(new A()));
+  invokeInstanceMethod2(new GenericClass<B>(new B()));
+  invokeInstanceMethod3(new GenericClass<C>(new C()));
+  invokeInstanceGetter1(new GenericClass<A>(new A()));
+  invokeInstanceGetter2(new GenericClass<B>(new B()));
+  invokeInstanceGetter3(new GenericClass<C>(new C()));
+  accessInstanceField1(new GenericClass<A>(new A()));
+  accessInstanceField2(new GenericClass<B>(new B()));
+  accessInstanceField3(new GenericClass<C>(new C()));
+
+  invokeSuperMethod1(new GenericSubclass<A>(new A()));
+  invokeSuperMethod2(new GenericSubclass<B>(new B()));
+  invokeSuperMethod3(new GenericSubclass<C>(new C()));
+  invokeSuperGetter1(new GenericSubclass<A>(new A()));
+  invokeSuperGetter2(new GenericSubclass<B>(new B()));
+  invokeSuperGetter3(new GenericSubclass<C>(new C()));
+  accessSuperField1(new GenericSubclass<A>(new A()));
+  accessSuperField2(new GenericSubclass<B>(new B()));
+  accessSuperField3(new GenericSubclass<C>(new C()));
+
+  invokeFunctionTypedInstanceMethod1(new GenericClass<A>(new A()));
+  invokeFunctionTypedInstanceMethod2(new GenericClass<B>(new B()));
+  invokeFunctionTypedInstanceMethod3(new GenericClass<C>(new C()));
+  invokeFunctionTypedInstanceGetter1(new GenericClass<A>(new A()));
+  invokeFunctionTypedInstanceGetter2(new GenericClass<B>(new B()));
+  invokeFunctionTypedInstanceGetter3(new GenericClass<C>(new C()));
+  invokeFunctionTypedInstanceField1(new GenericClass<A>(new A()));
+  invokeFunctionTypedInstanceField2(new GenericClass<B>(new B()));
+  invokeFunctionTypedInstanceField3(new GenericClass<C>(new C()));
+
+  invokeFunctionTypedSuperMethod1(new GenericSubclass<A>(new A()));
+  invokeFunctionTypedSuperMethod2(new GenericSubclass<B>(new B()));
+  invokeFunctionTypedSuperMethod3(new GenericSubclass<C>(new C()));
+  invokeFunctionTypedSuperGetter1(new GenericSubclass<A>(new A()));
+  invokeFunctionTypedSuperGetter2(new GenericSubclass<B>(new B()));
+  invokeFunctionTypedSuperGetter3(new GenericSubclass<C>(new C()));
+  invokeFunctionTypedSuperField1(new GenericSubclass<A>(new A()));
+  invokeFunctionTypedSuperField2(new GenericSubclass<B>(new B()));
+  invokeFunctionTypedSuperField3(new GenericSubclass<C>(new C()));
+}
+
+/*element: genericMethod:Union([exact=C], [subclass=A])*/
+T genericMethod<T>(T /*Union([exact=C], [subclass=A])*/ t) => t;
+
+/*element: functionTypedGenericMethod:[subclass=Closure]*/
+T Function() functionTypedGenericMethod<T>(
+        T /*Union([exact=C], [subclass=A])*/ t) =>
+    /*Union([exact=C], [subclass=A])*/ () => t;
+
+/*element: Class.:[exact=Class]*/
+class Class {
+  /*element: Class.genericMethod:Union([exact=C], [subclass=A])*/
+  T genericMethod<T>(T /*Union([exact=C], [subclass=A])*/ t) => t;
+
+  /*element: Class.functionTypedGenericMethod:[subclass=Closure]*/
+  T Function() functionTypedGenericMethod<T>(
+          T /*Union([exact=C], [subclass=A])*/ t) =>
+      /*Union([exact=C], [subclass=A])*/ () => t;
+}
+
+/*element: Subclass.:[exact=Subclass]*/
+class Subclass extends Class {
+  /*kernel.element: Subclass.superMethod1:Union([exact=C], [subclass=A])*/
+  /*strong.element: Subclass.superMethod1:[subclass=A]*/
+  superMethod1() {
+    return super.genericMethod<A>(new A());
+  }
+
+  /*kernel.element: Subclass.superMethod2:Union([exact=C], [subclass=A])*/
+  /*strong.element: Subclass.superMethod2:[exact=B]*/
+  superMethod2() {
+    return super.genericMethod<B>(new B());
+  }
+
+  /*kernel.element: Subclass.superMethod3:Union([exact=C], [subclass=A])*/
+  /*strong.element: Subclass.superMethod3:[exact=C]*/
+  superMethod3() {
+    return super.genericMethod<C>(new C());
+  }
+
+  /*kernel.element: Subclass.functionTypedSuperMethod1:[null|subclass=Object]*/
+  /*strong.element: Subclass.functionTypedSuperMethod1:[null|subclass=A]*/
+  functionTypedSuperMethod1() {
+    return super.functionTypedGenericMethod<A>(new A())();
+  }
+
+  /*kernel.element: Subclass.functionTypedSuperMethod2:[null|subclass=Object]*/
+  /*strong.element: Subclass.functionTypedSuperMethod2:[null|exact=B]*/
+  functionTypedSuperMethod2() {
+    return super.functionTypedGenericMethod<B>(new B())();
+  }
+
+  /*kernel.element: Subclass.functionTypedSuperMethod3:[null|subclass=Object]*/
+  /*strong.element: Subclass.functionTypedSuperMethod3:[null|exact=C]*/
+  functionTypedSuperMethod3() {
+    return super.functionTypedGenericMethod<C>(new C())();
+  }
+}
+
+/*kernel.element: invokeGenericMethod1:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericMethod1:[subclass=A]*/
+invokeGenericMethod1(A /*[exact=A]*/ a) => genericMethod<A>(a);
+
+/*kernel.element: invokeGenericMethod2:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericMethod2:[exact=B]*/
+invokeGenericMethod2(B /*[exact=B]*/ b) => genericMethod<B>(b);
+
+/*kernel.element: invokeGenericMethod3:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericMethod3:[exact=C]*/
+invokeGenericMethod3(C /*[exact=C]*/ c) => genericMethod<C>(c);
+
+/*kernel.element: invokeGenericInstanceMethod1:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericInstanceMethod1:[subclass=A]*/
+invokeGenericInstanceMethod1() =>
+    new Class(). /*invoke: [exact=Class]*/ genericMethod<A>(new A());
+
+/*kernel.element: invokeGenericInstanceMethod2:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericInstanceMethod2:[exact=B]*/
+invokeGenericInstanceMethod2() =>
+    new Class(). /*invoke: [exact=Class]*/ genericMethod<B>(new B());
+
+/*kernel.element: invokeGenericInstanceMethod3:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericInstanceMethod3:[exact=C]*/
+invokeGenericInstanceMethod3() =>
+    new Class(). /*invoke: [exact=Class]*/ genericMethod<C>(new C());
+
+/*kernel.element: invokeGenericSuperMethod1:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericSuperMethod1:[subclass=A]*/
+invokeGenericSuperMethod1() =>
+    new Subclass(). /*invoke: [exact=Subclass]*/ superMethod1();
+
+/*kernel.element: invokeGenericSuperMethod2:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericSuperMethod2:[exact=B]*/
+invokeGenericSuperMethod2() =>
+    new Subclass(). /*invoke: [exact=Subclass]*/ superMethod2();
+
+/*kernel.element: invokeGenericSuperMethod3:Union([exact=C], [subclass=A])*/
+/*strong.element: invokeGenericSuperMethod3:[exact=C]*/
+invokeGenericSuperMethod3() =>
+    new Subclass(). /*invoke: [exact=Subclass]*/ superMethod3();
+
+/*kernel.element: invokeFunctionTypedGenericMethod1:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericMethod1:[null|subclass=A]*/
+invokeFunctionTypedGenericMethod1(A /*[exact=A]*/ a) =>
+    functionTypedGenericMethod<A>(a)();
+
+/*kernel.element: invokeFunctionTypedGenericMethod2:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericMethod2:[null|exact=B]*/
+invokeFunctionTypedGenericMethod2(B /*[exact=B]*/ b) =>
+    functionTypedGenericMethod<B>(b)();
+
+/*kernel.element: invokeFunctionTypedGenericMethod3:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericMethod3:[null|exact=C]*/
+invokeFunctionTypedGenericMethod3(C /*[exact=C]*/ c) =>
+    functionTypedGenericMethod<C>(c)();
+
+/*kernel.element: invokeFunctionTypedGenericInstanceMethod1:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericInstanceMethod1:[null|subclass=A]*/
+invokeFunctionTypedGenericInstanceMethod1() => new Class()
+    . /*invoke: [exact=Class]*/ functionTypedGenericMethod<A>(new A())();
+
+/*kernel.element: invokeFunctionTypedGenericInstanceMethod2:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericInstanceMethod2:[null|exact=B]*/
+invokeFunctionTypedGenericInstanceMethod2() => new Class()
+    . /*invoke: [exact=Class]*/ functionTypedGenericMethod<B>(new B())();
+
+/*kernel.element: invokeFunctionTypedGenericInstanceMethod3:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericInstanceMethod3:[null|exact=C]*/
+invokeFunctionTypedGenericInstanceMethod3() => new Class()
+    . /*invoke: [exact=Class]*/ functionTypedGenericMethod<C>(new C())();
+
+/*kernel.element: invokeFunctionTypedGenericSuperMethod1:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericSuperMethod1:[null|subclass=A]*/
+invokeFunctionTypedGenericSuperMethod1() =>
+    new Subclass(). /*invoke: [exact=Subclass]*/ functionTypedSuperMethod1();
+
+/*kernel.element: invokeFunctionTypedGenericSuperMethod2:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericSuperMethod2:[null|exact=B]*/
+invokeFunctionTypedGenericSuperMethod2() =>
+    new Subclass(). /*invoke: [exact=Subclass]*/ functionTypedSuperMethod2();
+
+/*kernel.element: invokeFunctionTypedGenericSuperMethod3:[null|subclass=Object]*/
+/*strong.element: invokeFunctionTypedGenericSuperMethod3:[null|exact=C]*/
+invokeFunctionTypedGenericSuperMethod3() =>
+    new Subclass(). /*invoke: [exact=Subclass]*/ functionTypedSuperMethod3();
+
+/*element: invokeGenericMethods:[null]*/
+invokeGenericMethods() {
+  invokeGenericMethod1(new A());
+  invokeGenericMethod2(new B());
+  invokeGenericMethod3(new C());
+  invokeGenericInstanceMethod1();
+  invokeGenericInstanceMethod2();
+  invokeGenericInstanceMethod3();
+  invokeGenericSuperMethod1();
+  invokeGenericSuperMethod2();
+  invokeGenericSuperMethod3();
+
+  invokeFunctionTypedGenericMethod1(new A());
+  invokeFunctionTypedGenericMethod2(new B());
+  invokeFunctionTypedGenericMethod3(new C());
+  invokeFunctionTypedGenericInstanceMethod1();
+  invokeFunctionTypedGenericInstanceMethod2();
+  invokeFunctionTypedGenericInstanceMethod3();
+  invokeFunctionTypedGenericSuperMethod1();
+  invokeFunctionTypedGenericSuperMethod2();
+  invokeFunctionTypedGenericSuperMethod3();
+}
diff --git a/tests/compiler/dart2js/inference/inference_test_helper.dart b/tests/compiler/dart2js/inference/inference_test_helper.dart
index 94d458e..4788158 100644
--- a/tests/compiler/dart2js/inference/inference_test_helper.dart
+++ b/tests/compiler/dart2js/inference/inference_test_helper.dart
@@ -14,6 +14,7 @@
 import 'package:compiler/src/js_model/locals.dart';
 import 'package:compiler/src/kernel/element_map.dart';
 import 'package:compiler/src/kernel/kernel_backend_strategy.dart';
+import 'package:compiler/src/inferrer/builder_kernel.dart';
 import 'package:kernel/ast.dart' as ir;
 import '../equivalence/id_equivalence.dart';
 import '../equivalence/id_equivalence_helper.dart';
@@ -51,7 +52,9 @@
         skipForKernel: skipForKernel,
         skipForStrong: skipForStrong,
         shardIndex: shardIndex ?? 0,
-        shards: shardIndex != null ? 2 : 1);
+        shards: shardIndex != null ? 2 : 1, onTest: (Uri uri) {
+      useStaticResultTypes = uri.path.endsWith('/use_static_types.dart');
+    });
   });
 }
 
diff --git a/tests/compiler/dart2js/rti/data/instantiation1.dart b/tests/compiler/dart2js/rti/data/instantiation1.dart
new file mode 100644
index 0000000..1b8e7cd
--- /dev/null
+++ b/tests/compiler/dart2js/rti/data/instantiation1.dart
@@ -0,0 +1,20 @@
+// 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.
+
+/*strong.element: f:deps=[B],direct,explicit=[f.T],needsArgs,needsInst=[<B.S>]*/
+/*omit.element: f:deps=[B]*/
+int f<T>(T a) => null;
+
+typedef int F<R>(R a);
+
+/*strong.class: B:explicit=[int Function(B.S)],indirect,needsArgs*/
+class B<S> {
+  F<S> c;
+
+  B() : c = f;
+}
+
+main() {
+  new B();
+}
diff --git a/tests/compiler/dart2js/rti/data/instantiation2.dart b/tests/compiler/dart2js/rti/data/instantiation2.dart
new file mode 100644
index 0000000..fd7022c
--- /dev/null
+++ b/tests/compiler/dart2js/rti/data/instantiation2.dart
@@ -0,0 +1,21 @@
+// 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.
+
+/*kernel.element: f:direct,explicit=[f.T]*/
+/*!kernel.element: f:deps=[B],direct,explicit=[f.T],needsArgs,needsInst=[<B.S>]*/
+bool f<T>(T a) => a is T;
+
+typedef bool F<R>(R a);
+
+/*strong.class: B:explicit=[bool Function(B.S)],indirect,needsArgs*/
+/*omit.class: B:indirect,needsArgs*/
+class B<S> {
+  F<S> c;
+
+  B() : c = f;
+}
+
+main() {
+  new B();
+}
diff --git a/tests/compiler/dart2js/rti/data/instantiation3.dart b/tests/compiler/dart2js/rti/data/instantiation3.dart
new file mode 100644
index 0000000..7d3df34
--- /dev/null
+++ b/tests/compiler/dart2js/rti/data/instantiation3.dart
@@ -0,0 +1,24 @@
+// 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.
+
+/*strong.element: f:deps=[B],direct,explicit=[f.T],needsArgs,needsInst=[<B.S>]*/
+/*omit.element: f:deps=[B]*/
+int f<T>(T a) => null;
+
+typedef int F<R>(R a);
+
+/*strong.class: B:direct,explicit=[int Function(B.S)],needsArgs*/
+class B<S> {
+  F<S> c;
+
+  method() {
+    return () {
+      c = f;
+    };
+  }
+}
+
+main() {
+  new B().method();
+}
diff --git a/tests/compiler/dart2js/rti/data/instantiation4.dart b/tests/compiler/dart2js/rti/data/instantiation4.dart
new file mode 100644
index 0000000..b9f1a78
--- /dev/null
+++ b/tests/compiler/dart2js/rti/data/instantiation4.dart
@@ -0,0 +1,25 @@
+// 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.
+
+/*kernel.element: f:direct,explicit=[f.T]*/
+/*!kernel.element: f:deps=[B],direct,explicit=[f.T],needsArgs,needsInst=[<B.S>]*/
+bool f<T>(T a) => a is T;
+
+typedef bool F<R>(R a);
+
+/*strong.class: B:direct,explicit=[bool Function(B.S)],needsArgs*/
+/*omit.class: B:indirect,needsArgs*/
+class B<S> {
+  F<S> c;
+
+  method() {
+    return () {
+      c = f;
+    };
+  }
+}
+
+main() {
+  new B().method();
+}
diff --git a/tests/compiler/dart2js/rti/data/instantiation5.dart b/tests/compiler/dart2js/rti/data/instantiation5.dart
new file mode 100644
index 0000000..c69f333
--- /dev/null
+++ b/tests/compiler/dart2js/rti/data/instantiation5.dart
@@ -0,0 +1,23 @@
+// 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.
+
+/*strong.element: f:deps=[method],direct,explicit=[f.T],needsArgs,needsInst=[<method.S>]*/
+/*omit.element: f:deps=[method]*/
+int f<T>(T a) => null;
+
+typedef int F<R>(R a);
+
+/*strong.element: method:indirect,needsArgs*/
+method<S>() {
+  F<S> c;
+
+  return () {
+    c = f;
+    return c;
+  };
+}
+
+main() {
+  method();
+}
diff --git a/tests/compiler/dart2js/rti/data/instantiation6.dart b/tests/compiler/dart2js/rti/data/instantiation6.dart
new file mode 100644
index 0000000..feb9e52
--- /dev/null
+++ b/tests/compiler/dart2js/rti/data/instantiation6.dart
@@ -0,0 +1,23 @@
+// 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.
+
+/*kernel.element: f:direct,explicit=[f.T]*/
+/*!kernel.element: f:deps=[method],direct,explicit=[f.T],needsArgs,needsInst=[<method.S>]*/
+bool f<T>(T a) => a is T;
+
+typedef bool F<R>(R a);
+
+/*!kernel.element: method:indirect,needsArgs*/
+method<S>() {
+  F<S> c;
+
+  return () {
+    c = f;
+    return c;
+  };
+}
+
+main() {
+  method();
+}
diff --git a/tests/compiler/dart2js/rti/data/instantiation7.dart b/tests/compiler/dart2js/rti/data/instantiation7.dart
new file mode 100644
index 0000000..d8af322
--- /dev/null
+++ b/tests/compiler/dart2js/rti/data/instantiation7.dart
@@ -0,0 +1,37 @@
+// 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.
+
+/*strong.element: f1:deps=[method],direct,explicit=[f1.T],needsArgs,needsInst=[<method.X>]*/
+/*omit.element: f1:deps=[method]*/
+int f1<T>(T a, T b, T c) => null;
+
+/*strong.element: f2:deps=[method],direct,explicit=[f2.S,f2.T],needsArgs,needsInst=[<method.X,method.Y>]*/
+/*omit.element: f2:deps=[method]*/
+int f2<T, S>(T a, S b, S c) => null;
+
+/*strong.element: f3:deps=[method],direct,explicit=[f3.S,f3.T,f3.U],needsArgs,needsInst=[<method.X,method.Y,method.Z>]*/
+/*omit.element: f3:deps=[method]*/
+int f3<T, S, U>(T a, S b, U c) => null;
+
+typedef int F1<R>(R a, R b, R c);
+typedef int F2<R, P>(R a, P b, P c);
+typedef int F3<R, P, Q>(R a, P b, Q c);
+
+/*strong.element: method:indirect,needsArgs*/
+method<X, Y, Z>() {
+  F1<X> c1;
+  F2<X, Y> c2;
+  F3<X, Y, Z> c3;
+
+  return () {
+    c1 = f1;
+    c2 = f2;
+    c3 = f3;
+    return c1 ?? c2 ?? c3;
+  };
+}
+
+main() {
+  method();
+}
diff --git a/tests/compiler/dart2js/rti/data/local_function_signatures_strong.dart b/tests/compiler/dart2js/rti/data/local_function_signatures_strong.dart
index ce07bec..8d4dd9b 100644
--- a/tests/compiler/dart2js/rti/data/local_function_signatures_strong.dart
+++ b/tests/compiler/dart2js/rti/data/local_function_signatures_strong.dart
@@ -77,7 +77,7 @@
 }
 
 method10() {
-  /*strong.direct,explicit=[local.T],needsArgs,needsSignature*/
+  /*strong.direct,explicit=[local.T],needsArgs,needsInst=[<dynamic>,<num>,<num>],needsSignature*/
   /*omit.needsSignature*/
   num local<T>(T n) => null;
   return local;
@@ -90,7 +90,7 @@
 }
 
 method12() {
-  /*strong.direct,explicit=[local.T],needsArgs*/
+  /*strong.direct,explicit=[local.T],needsArgs,needsInst=[<dynamic>,<num>,<num>]*/
   /*omit.*/
   num local<T>(num n, T t) => null;
   return local;
@@ -103,7 +103,7 @@
 }
 
 num Function(num) method14() {
-  /*strong.direct,explicit=[local.T],needsArgs,needsSignature*/
+  /*strong.direct,explicit=[local.T],needsArgs,needsInst=[<dynamic>,<num>,<num>],needsSignature*/
   /*omit.needsSignature*/
   num local<T>(T n) => null;
   return local;
diff --git a/tests/compiler/dart2js/rti/data/method_signatures_strong.dart b/tests/compiler/dart2js/rti/data/method_signatures_strong.dart
index 03650b8..afca40f5 100644
--- a/tests/compiler/dart2js/rti/data/method_signatures_strong.dart
+++ b/tests/compiler/dart2js/rti/data/method_signatures_strong.dart
@@ -16,7 +16,7 @@
 }
 
 class Class2 {
-  /*strong.element: Class2.method4:direct,explicit=[method4.T],needsArgs*/
+  /*strong.element: Class2.method4:direct,explicit=[method4.T],needsArgs,needsInst=[<num>,<num>]*/
   /*omit.element: Class2.method4:*/
   num method4<T>(T n) => null;
 }
@@ -27,19 +27,19 @@
 }
 
 class Class4 {
-  /*strong.element: Class4.method6:direct,explicit=[method6.T],needsArgs*/
+  /*strong.element: Class4.method6:direct,explicit=[method6.T],needsArgs,needsInst=[<num>,<num>]*/
   /*omit.element: Class4.method6:*/
   num method6<T>(num n, T t) => null;
 }
 
-/*strong.element: method7:direct,explicit=[method7.T],needsArgs*/
+/*strong.element: method7:direct,explicit=[method7.T],needsArgs,needsInst=[<num>,<num>]*/
 /*omit.element: method7:*/
 num method7<T>(T n) => null;
 
 /*element: method8:*/
 T method8<T>(num n) => null;
 
-/*strong.element: method9:direct,explicit=[method9.T],needsArgs*/
+/*strong.element: method9:direct,explicit=[method9.T],needsArgs,needsInst=[<num>,<num>]*/
 /*omit.element: method9:*/
 num method9<T>(num n, T t) => null;
 
diff --git a/tests/compiler/dart2js/rti/rti_need_test_helper.dart b/tests/compiler/dart2js/rti/rti_need_test_helper.dart
index 7386d6a..3e809b1 100644
--- a/tests/compiler/dart2js/rti/rti_need_test_helper.dart
+++ b/tests/compiler/dart2js/rti/rti_need_test_helper.dart
@@ -15,6 +15,7 @@
 import 'package:compiler/src/kernel/element_map.dart';
 import 'package:compiler/src/kernel/kernel_backend_strategy.dart';
 import 'package:compiler/src/kernel/kernel_strategy.dart';
+import 'package:compiler/src/universe/feature.dart';
 import 'package:compiler/src/universe/selector.dart';
 import 'package:compiler/src/universe/world_builder.dart';
 import 'package:kernel/ast.dart' as ir;
@@ -56,6 +57,7 @@
   static const String indirectTypeArgumentTest = 'indirect';
   static const String typeLiteral = 'exp';
   static const String selectors = 'selectors';
+  static const String instantiationsNeedTypeArguments = 'needsInst';
 }
 
 abstract class ComputeValueMixin<T> {
@@ -162,6 +164,13 @@
             features.addElement(Tags.selectors, selector);
           }
         });
+        rtiNeedBuilder.instantiationsNeedingTypeArgumentsForTesting?.forEach(
+            (GenericInstantiation instantiation, Set<Entity> targets) {
+          if (targets.contains(entity)) {
+            features.addElement(
+                Tags.instantiationsNeedTypeArguments, instantiation.shortText);
+          }
+        });
       }
 
       if (frontendClosure != null) {
diff --git a/tests/compiler/dart2js_extra/bounds_check1a_test.dart b/tests/compiler/dart2js_extra/bounds_check1a_test.dart
new file mode 100644
index 0000000..20136a7
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check1a_test.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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+
+main() {
+  dynamic c = new Class();
+  c.method();
+}
+
+class Class {
+  @NoInline()
+  method<T extends num>() => null;
+}
diff --git a/tests/compiler/dart2js_extra/bounds_check1b_test.dart b/tests/compiler/dart2js_extra/bounds_check1b_test.dart
new file mode 100644
index 0000000..8fad189
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check1b_test.dart
@@ -0,0 +1,16 @@
+// 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';
+
+main() {
+  dynamic c = new Class();
+  c.method();
+}
+
+class Class {
+  method<T extends num>() => null;
+}
diff --git a/tests/compiler/dart2js_extra/bounds_check2a_test.dart b/tests/compiler/dart2js_extra/bounds_check2a_test.dart
new file mode 100644
index 0000000..74bc928
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check2a_test.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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+
+main() {
+  dynamic c = new Class<int>();
+  c.method();
+}
+
+class Class<T> {
+  @NoInline()
+  method<S extends T>() => null;
+}
diff --git a/tests/compiler/dart2js_extra/bounds_check2b_test.dart b/tests/compiler/dart2js_extra/bounds_check2b_test.dart
new file mode 100644
index 0000000..07cd595
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check2b_test.dart
@@ -0,0 +1,16 @@
+// 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';
+
+main() {
+  dynamic c = new Class<int>();
+  c.method();
+}
+
+class Class<T> {
+  method<S extends T>() => null;
+}
diff --git a/tests/compiler/dart2js_extra/bounds_check3a_test.dart b/tests/compiler/dart2js_extra/bounds_check3a_test.dart
new file mode 100644
index 0000000..103ab95
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check3a_test.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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+
+main() {
+  dynamic c = new Class();
+  Expect.equals(c.method(), num);
+}
+
+class Class {
+  @NoInline()
+  method<S extends num>() => S;
+}
diff --git a/tests/compiler/dart2js_extra/bounds_check3b_test.dart b/tests/compiler/dart2js_extra/bounds_check3b_test.dart
new file mode 100644
index 0000000..af34397
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check3b_test.dart
@@ -0,0 +1,16 @@
+// 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';
+
+main() {
+  dynamic c = new Class();
+  Expect.equals(c.method(), num);
+}
+
+class Class {
+  method<S extends num>() => S;
+}
diff --git a/tests/compiler/dart2js_extra/bounds_check4a_test.dart b/tests/compiler/dart2js_extra/bounds_check4a_test.dart
new file mode 100644
index 0000000..f230b2f
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check4a_test.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.
+
+// dart2jsOptions=--strong
+
+import 'package:expect/expect.dart';
+
+main() {
+  dynamic c = new Class<int>();
+  Expect.equals(c.method(), int);
+}
+
+class Class<T> {
+  @NoInline()
+  method<S extends T>() => S;
+}
diff --git a/tests/compiler/dart2js_extra/bounds_check4b_test.dart b/tests/compiler/dart2js_extra/bounds_check4b_test.dart
new file mode 100644
index 0000000..fdb7863
--- /dev/null
+++ b/tests/compiler/dart2js_extra/bounds_check4b_test.dart
@@ -0,0 +1,16 @@
+// 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';
+
+main() {
+  dynamic c = new Class<int>();
+  Expect.equals(c.method(), int);
+}
+
+class Class<T> {
+  method<S extends T>() => S;
+}
diff --git a/tests/compiler/dart2js_extra/dart2js_extra.status b/tests/compiler/dart2js_extra/dart2js_extra.status
index 0040688..bf6a661 100644
--- a/tests/compiler/dart2js_extra/dart2js_extra.status
+++ b/tests/compiler/dart2js_extra/dart2js_extra.status
@@ -3,6 +3,8 @@
 # BSD-style license that can be found in the LICENSE file.
 
 [ $compiler == dart2js ]
+bounds_check4a_test: RuntimeError # Issue 32741
+bounds_check4b_test: RuntimeError # Issue 32741
 class_test: Fail
 constant_javascript_semantics4_test: Fail, OK
 generic_class_is_test: Fail # Issue 32004
diff --git a/tests/compiler/dart2js_extra/generic_instantiation1_test.dart b/tests/compiler/dart2js_extra/generic_instantiation1_test.dart
new file mode 100644
index 0000000..fcfb79f
--- /dev/null
+++ b/tests/compiler/dart2js_extra/generic_instantiation1_test.dart
@@ -0,0 +1,19 @@
+// 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
+
+int f<T>(T a) => null;
+
+typedef int F<R>(R a);
+
+class B<S> {
+  F<S> c;
+
+  B() : c = f;
+}
+
+main() {
+  new B<int>().c(0);
+}
diff --git a/tests/compiler/dart2js_extra/generic_instantiation2_test.dart b/tests/compiler/dart2js_extra/generic_instantiation2_test.dart
new file mode 100644
index 0000000..047d221
--- /dev/null
+++ b/tests/compiler/dart2js_extra/generic_instantiation2_test.dart
@@ -0,0 +1,19 @@
+// 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 --omit-implicit-checks
+
+int f<T>(T a) => null;
+
+typedef int F<R>(R a);
+
+class B<S> {
+  F<S> c;
+
+  B() : c = f;
+}
+
+main() {
+  new B<int>().c(0);
+}
diff --git a/tests/compiler/dart2js_extra/generic_instantiation3_test.dart b/tests/compiler/dart2js_extra/generic_instantiation3_test.dart
new file mode 100644
index 0000000..3152565
--- /dev/null
+++ b/tests/compiler/dart2js_extra/generic_instantiation3_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';
+
+bool f<T, S>(T a, S b) => a is S;
+
+typedef bool F<P, Q>(P a, Q b);
+
+class B<X, Y> {
+  F<X, Y> c;
+
+  B() : c = f;
+}
+
+main() {
+  Expect.isTrue(new B<int, int>().c(0, 0));
+  Expect.isFalse(new B<int, String>().c(0, ''));
+}
diff --git a/tests/compiler/dart2js_extra/generic_instantiation4_test.dart b/tests/compiler/dart2js_extra/generic_instantiation4_test.dart
new file mode 100644
index 0000000..d5f8eb9
--- /dev/null
+++ b/tests/compiler/dart2js_extra/generic_instantiation4_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 --omit-implicit-checks
+
+import 'package:expect/expect.dart';
+
+bool f<T, S>(T a, S b) => a is S;
+
+typedef bool F<P, Q>(P a, Q b);
+
+class B<X, Y> {
+  F<X, Y> c;
+
+  B() : c = f;
+}
+
+main() {
+  Expect.isTrue(new B<int, int>().c(0, 0));
+  Expect.isFalse(new B<int, String>().c(0, ''));
+}
diff --git a/tests/corelib_2/bigint_test.dart b/tests/corelib_2/bigint_test.dart
index 030e59f..f4e9865 100644
--- a/tests/corelib_2/bigint_test.dart
+++ b/tests/corelib_2/bigint_test.dart
@@ -5,7 +5,7 @@
 // Testing Bigints with and without intrinsics.
 // VMOptions=
 // VMOptions=--no_intrinsify
-// VMOptions=--optimization_counter_threshold=10 --no-background_compilation
+// VMOptions=--optimization_counter_threshold=5 --no-background_compilation
 
 import "package:expect/expect.dart";
 
@@ -109,6 +109,66 @@
       BigInt.parse("123456789012345678901234567890"),
       BigInt.parse("123456789012345678901234567899"),
       BigInt.parse("40128068573873018143207285483"));
+  test(
+      BigInt.parse(
+          "-7003a3cac2bac4e494d749ae101f7ede8f11dac594fea5f51e15826021d734df6ec"
+          "b6f67d74e2bb0f47ee39cb79fae059734c95d1eacb0340af64c05b83a4f70a737363"
+          "c3799d38c23b7833622d89036b4649bcc7b749037f4954dac6abe5566c97cb6ac81f"
+          "f8a09f8c71c7f08061720483b592517a608088ddb4c2e460ad1a73abbadbda077922"
+          "1751cf22f1191e3be531505c833fede908a17581a9ae96f3c0258edcfe71786b7cf3"
+          "07f67eb9ecd8656d0fd397b0215bfb79efb314299d3e9db70b31a34f5f67e6c5e166"
+          "cfa3e0bf45837c5d64fa3930a91a06b94840b4773d81280ed2af141747a6ac99d882"
+          "a59f47b15ce8c1d716ead646b139b928869902225c85ea220b90e290181f271ed087"
+          "bb6972dfe7d674b09e44c268128340d9172182732990a70af51d589c89f39d8f5dac"
+          "659161aa0a32774728e15e25bad2960b4eacb8b670581b1c431201192c8bdbcc9256"
+          "ef9e863b589f22813158050cdaf5da69f83819639f5a183c7ffe61ba1582d6ace35c"
+          "8318dfdc597d016e70b7bb115fc1a7a3481c3a6296f1504e5ccd9b14e641acb2aa32"
+          "9c3d69b5e8f1609eec8b5b5a2b0192e9f21e7e3960c52975a70cf934c32e67799c40"
+          "863b23c9579a551df4b179e6e2094f86c9fffa4bb5634202e094d380565b44cec833"
+          "db25721010dd5df766204ae8d1e8680075f261801aee047d0ac576b9b10710de54e6"
+          "eaa94648a7fba1576e66ea44f4bb7f6b941268a8d920bfc2727f82457f92cc2a016c"
+          "b",
+          radix: 16),
+      BigInt.parse(
+          "73ac14b30fe9cb8275a7410a06ce5de8a60fe0a02e236197182996ca5886fd4e6937"
+          "555f1f02ed4183ff7f097f76051f286dbb1b24751795cb793b1b81ac259",
+          radix: 16),
+      BigInt.parse(
+          "ffffffffffffffffc90fdaa22168c234c4c6628b80dc1cd129024e088a67cc74020b"
+          "bea63b139b22514a08798e3404ddef9519b3cd3a431b302b0a6df25f14374fe1356d"
+          "6d51c245e485b576625e7ec6f44c42e9a637ed6b0bff5cb6f406b7edee386bfb5a89"
+          "9fa5ae9f24117c4b1fe649286651ece45b3dc2007cb8a163bf0598da48361c55d39a"
+          "69163fa8fd24cf5f83655d23dca3ad961c62f356208552bb9ed529077096966d670c"
+          "354e4abc9804f1746c08ca18217c32905e462e36ce3be39e772c180e86039b2783a2"
+          "ec07a28fb5c55df06f4c52c9de2bcbf6955817183995497cea956ae515d2261898fa"
+          "051015728e5a8aaac42dad33170d04507a33a85521abdf1cba64ecfb850458dbef0a"
+          "8aea71575d060c7db3970f85a6e1e4c7abf5ae8cdb0933d71e8c94e04a25619dcee3"
+          "d2261ad2ee6bf12ffa06d98a0864d87602733ec86a64521f2b18177b200cbbe11757"
+          "7a615d6c770988c0bad946e208e24fa074e5ab3143db5bfce0fd108e4b82d120a921"
+          "08011a723c12a787e6d788719a10bdba5b2699c327186af4e23c1a946834b6150bda"
+          "2583e9ca2ad44ce8dbbbc2db04de8ef92e8efc141fbecaa6287c59474e6bc05d99b2"
+          "964fa090c3a2233ba186515be7ed1f612970cee2d7afb81bdd762170481cd0069127"
+          "d5b05aa993b4ea988d8fddc186ffb7dc90a6c08f4df435c934063199ffffffffffff"
+          "ffff",
+          radix: 16),
+      BigInt.parse(
+          "b1b35af289290c92fcd3d22fca66016f6db7aa21508991c97f0e53fddc2f7ece7088"
+          "5e935259c28d317be14c0378e2ebd103600e2e1f55b111703fc75217836e24f9bfd8"
+          "63d47cdb26882f491949b1906c2cb016c0e9e9d77c3a9c4a3e85b9ac34057eeb993d"
+          "d048d8ed90b1eea78f84ee48febb1281384c739b1c60dda475395e3928b7081af890"
+          "d2c58eac70d11d7f14c0e98fd168735425d233b7c07506b54149482261067079f82a"
+          "b531a072ede523aca1765c1a587c160f638aa3ccab8cd1f3358c5bac3ed0a6062e92"
+          "94df2322864f6a8e58b4a2d40b600a0f09065d34bd49e60b5656d2c6dcb3af751f4a"
+          "9c10dc7df46215f3043b4077fc2be7f648d388843db9cf94f31b2eb376cf22033a23"
+          "e8984b5b1702f9e5af99507ad3d8d624a104c18af275949e7e88c16651103a2a7620"
+          "c5c8356f1f2311a9cab2c61d30b0af22d7961e42cb13679bf0d52f35b41a0f7c341a"
+          "c414a76a9a85408c39836657594180ffbb4d5a38e4b6eeea125fcde370478f6b7cd8"
+          "903fc8a822075f6e766d83337e6db2eb6605d514327294ec1e076d576eee08220acd"
+          "f4f9ffa31f1aa7b4639eb11797c8f39956b5e4dbca98a0a15eb29136b66917cfdbfb"
+          "dd8ba20475ad401a6f1022a04bed3c8d5227cd7385e9b67096261fcc2ccf2632a4c2"
+          "f5ef640b1f37966f855f8314c97c8ef7a136e54565e95bfe253e579753f5a14c2a01"
+          "6c1",
+          radix: 16));
 }
 
 testModInverse() {
@@ -970,7 +1030,7 @@
 }
 
 main() {
-  for (int i = 0; i < 10; i++) {
+  for (int i = 0; i < 8; i++) {
     Expect.equals(BigInt.parse("1234567890123456789"), foo());
     Expect.equals(BigInt.parse("12345678901234567890"), bar());
     testModPow();
diff --git a/tests/corelib_2/cast_test.dart b/tests/corelib_2/cast_test.dart
index 552032d..36efe9e 100644
--- a/tests/corelib_2/cast_test.dart
+++ b/tests/corelib_2/cast_test.dart
@@ -90,7 +90,7 @@
 
   // Regression test.
   var list3 = <num>[4, 3, 2, 1];
-  var dList3 = list3.retype<int>();
+  var dList3 = list3.cast<int>();
   dList3.sort(null);
   Expect.listEquals([1, 2, 3, 4], list3);
 }
diff --git a/tests/corelib_2/corelib_2.status b/tests/corelib_2/corelib_2.status
index a6970b9..8200941 100644
--- a/tests/corelib_2/corelib_2.status
+++ b/tests/corelib_2/corelib_2.status
@@ -20,7 +20,6 @@
 num_sign_test: Crash, Pass # Issue 31768
 
 [ $compiler == dart2js ]
-apply_generic_function_test: RuntimeError # Issue 32691
 bigint_from_test: RuntimeError # Issue 32589
 date_time11_test: RuntimeError, Pass # Fails when US is on winter time, issue 31285.
 iterable_where_type_test: RuntimeError # issue 31718
@@ -37,6 +36,7 @@
 string_from_environment3_test/03: Crash
 
 [ $compiler == precompiler ]
+bigint_test: Pass, Timeout # --no_intrinsify
 int_parse_radix_test: Pass, Timeout # --no_intrinsify
 integer_parsed_mul_div_vm_test: Pass, Timeout # --no_intrinsify
 regexp/stack-overflow_test: RuntimeError, OK # Smaller limit with irregex interpreter
@@ -213,6 +213,7 @@
 cast_test: RuntimeError
 error_stack_trace1_test: RuntimeError
 growable_list_test: RuntimeError
+int_parse_radix_test/02: RuntimeError
 integer_to_radix_string_test/01: RuntimeError
 integer_to_radix_string_test/02: RuntimeError
 integer_to_radix_string_test/none: RuntimeError
@@ -239,6 +240,7 @@
 cast_test: RuntimeError
 error_stack_trace1_test: RuntimeError # Issue 12399
 growable_list_test: RuntimeError # Concurrent modifications test always runs
+int_parse_radix_test/02: RuntimeError
 integer_to_radix_string_test/01: RuntimeError
 integer_to_radix_string_test/02: RuntimeError
 integer_to_radix_string_test/none: RuntimeError
@@ -319,6 +321,7 @@
 apply_test/01: RuntimeError
 
 [ $compiler == dartkp && $runtime == dart_precompiled && $strong ]
+bigint_test: Pass, Timeout # --no_intrinsify
 iterable_fold_test/02: RuntimeError
 iterable_reduce_test/01: CompileTimeError # Issue 31533
 iterable_reduce_test/none: RuntimeError
@@ -540,7 +543,7 @@
 
 [ $arch == simarm || $arch == simarm64 || $arch == simdbc64 ]
 bigint_parse_radix_test: Pass, Slow # Bigint computations are slow on simulated architectures.
-bigint_test: Pass, Slow # Bigint computations are slow on simulated architectures.
+bigint_test: Pass, Slow, Timeout # Bigint computations are slow on simulated architectures.
 
 [ $arch == simdbc || $arch == simdbc64 ]
 regexp/stack-overflow_test: RuntimeError, OK # Smaller limit with irregex interpreter
@@ -605,5 +608,5 @@
 
 [ $hot_reload || $hot_reload_rollback ]
 bigint_parse_radix_test: Pass, Timeout # Issue 31659
-bigint_test: Pass, Crash # Issue 31660
+bigint_test: Pass, Timeout # Issue 31659
 integer_parsed_mul_div_vm_test: Pass, Slow # Slow
diff --git a/tests/corelib_2/growable_list_test.dart b/tests/corelib_2/growable_list_test.dart
index ebe04bc..8c3443ae 100644
--- a/tests/corelib_2/growable_list_test.dart
+++ b/tests/corelib_2/growable_list_test.dart
@@ -37,9 +37,6 @@
   // Avoid warnings because we don't actually implement Set.
   noSuchMethod(i) => super.noSuchMethod(i);
   Set<R> cast<R>() => throw "not used by test";
-
-  @Deprecated("Use cast instead.")
-  Set<R> retype<R>() => cast<R>();
 }
 
 class CallbackIterator implements Iterator<int> {
diff --git a/tests/corelib_2/list_unmodifiable_cast_test.dart b/tests/corelib_2/list_unmodifiable_cast_test.dart
index 58815bb..7b5a3bc 100644
--- a/tests/corelib_2/list_unmodifiable_cast_test.dart
+++ b/tests/corelib_2/list_unmodifiable_cast_test.dart
@@ -19,11 +19,6 @@
   test(new UnmodifiableListView<Object>(<num>[37]).cast<int>());
   test(new UnmodifiableListView<Object>(<int>[37]).cast<num>());
 
-  test(new UnmodifiableListView<num>(<num>[37]).retype<int>());
-  test(new UnmodifiableListView<num>(<int>[37]).retype<int>());
-  test(new UnmodifiableListView<Object>(<num>[37]).retype<int>());
-  test(new UnmodifiableListView<Object>(<int>[37]).retype<num>());
-
   var m2 = new List<num>.unmodifiable([37]);
   test(m2);
   test(m2.cast<int>());
diff --git a/tests/corelib_2/map_unmodifiable_cast_test.dart b/tests/corelib_2/map_unmodifiable_cast_test.dart
index ec5b419..8e4270f 100644
--- a/tests/corelib_2/map_unmodifiable_cast_test.dart
+++ b/tests/corelib_2/map_unmodifiable_cast_test.dart
@@ -10,16 +10,13 @@
 void main() {
   testNum(const {1: 37}, "const");
   testNum(const <num, num>{1: 37}.cast<int, int>(), "const.cast");
-  testNum(const <num, num>{1: 37}.retype<int, int>(), "const.retype");
 
   testNum(new UnmodifiableMapView({1: 37}), "unmod");
   testNum(new UnmodifiableMapView<num, num>(<num, num>{1: 37}), "unmod.cast");
-  testNum(new UnmodifiableMapView<num, num>(<int, int>{1: 37}), "unmod.retype");
-
   testNum(new UnmodifiableMapView<num, num>(<num, num>{1: 37}).cast<int, int>(),
-      "unmodView<num>.cast<int>");
+      "unmodView<num>(num).cast<int>");
   testNum(new UnmodifiableMapView<num, num>(<int, int>{1: 37}).cast<int, int>(),
-      "unmodView<int>.cast<int>");
+      "unmodView<num>(int).cast<int>");
   testNum(
       new UnmodifiableMapView<Object, Object>(<num, num>{1: 37})
           .cast<int, int>(),
@@ -29,21 +26,6 @@
           .cast<num, num>(),
       "unmodView<Object>(int).cast<num>");
 
-  testNum(
-      new UnmodifiableMapView<num, num>(<num, num>{1: 37}).retype<int, int>(),
-      "unmodView<num>(num).retype<int>");
-  testNum(
-      new UnmodifiableMapView<num, num>(<int, int>{1: 37}).retype<int, int>(),
-      "unmodView<num>(int).retype<int>");
-  testNum(
-      new UnmodifiableMapView<Object, Object>(<num, num>{1: 37})
-          .retype<int, int>(),
-      "unmodView<Object>(num).retype<int>");
-  testNum(
-      new UnmodifiableMapView<Object, Object>(<int, int>{1: 37})
-          .retype<num, num>(),
-      "unmodView<Object>(int).retype<num>");
-
   var m2 = new Map<num, num>.unmodifiable({1: 37});
   testNum(m2, "Map<num>.unmod");
   testNum(m2.cast<int, int>(), "Map<num>.unmod.cast<int>");
@@ -51,7 +33,6 @@
   Map<Symbol, dynamic> nsm = new NsmMap().foo(a: 0);
   test(nsm, #a, 0, "nsm", noSuchMethodMap: true);
   test(nsm.cast<Object, int>(), #a, 0, "nsm.cast", noSuchMethodMap: true);
-  test(nsm.retype<Object, int>(), #a, 0, "nsm.retype", noSuchMethodMap: true);
 }
 
 void testNum(Map<Object, Object> map, String name) {
diff --git a/tests/isolate/isolate.status b/tests/isolate/isolate.status
index d7fd1a0..1c23b98 100644
--- a/tests/isolate/isolate.status
+++ b/tests/isolate/isolate.status
@@ -2,6 +2,9 @@
 # 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.
 
+# No longer supported in dart 2
+scenarios/package_relative_root: Fail
+
 [ $compiler == dart2analyzer ]
 browser/typed_data_message_test: StaticWarning
 
diff --git a/tests/isolate/package_resolve_test.dart b/tests/isolate/package_resolve_test.dart
index 82e0de6..89b22ea 100644
--- a/tests/isolate/package_resolve_test.dart
+++ b/tests/isolate/package_resolve_test.dart
@@ -23,10 +23,10 @@
       print(msg.runtimeType);
       throw "Failure return from spawned isolate:\n\n$msg";
     }
-    if (msg[0] != SPAWN_PACKAGE_ROOT) {
+    if (msg[0] != null) {
       throw "Bad package root in child isolate: ${msg[0]}";
     }
-    if (msg[1] != PACKAGE_PATH) {
+    if (msg[1] != null) {
       throw "Package path not matching: ${msg[1]}";
     }
     print("SUCCESS");
diff --git a/tests/isolate/package_root_test.dart b/tests/isolate/package_root_test.dart
index 3567456..7d6e7b6 100644
--- a/tests/isolate/package_root_test.dart
+++ b/tests/isolate/package_root_test.dart
@@ -17,7 +17,7 @@
       packageRoot: Uri.parse(SPAWN_PACKAGE_ROOT));
   p.handler = (msg) {
     p.close();
-    if (msg != SPAWN_PACKAGE_ROOT) {
+    if (msg != null) {
       throw "Bad package root in child isolate: $msg";
     }
     print("SUCCESS");
@@ -28,5 +28,5 @@
 testPackageRoot(port) async {
   var packageRoot = await Isolate.packageRoot;
   print("Spawned isolate's package root: $packageRoot");
-  port.send(packageRoot.toString());
+  port.send(packageRoot);
 }
diff --git a/tests/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart b/tests/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart
index 4679254..bbcb3d3 100644
--- a/tests/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart
+++ b/tests/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart
@@ -21,15 +21,13 @@
       print(msg.runtimeType);
       throw "Failure return from spawned isolate:\n\n$msg";
     }
-    var child_pkg_root = Platform.script.resolve("packages/");
-    if (msg[0] != child_pkg_root.toString()) {
+    if (msg[0] != null) {
       throw "Bad package root in child isolate: ${msg[0]}.\n"
-          "Expected: $child_pkg_root";
+          "Expected: null";
     }
-    var child_pkg_path = child_pkg_root.resolve("foo/bar.dart");
-    if (msg[1] != child_pkg_path.toString()) {
+    if (msg[1] != null) {
       throw "Package path not matching: ${msg[1]}\n"
-          "Expected $child_pkg_path";
+          "Expected null";
     }
     print("SUCCESS");
   };
diff --git a/tests/isolate/scenarios/package_relative_root/package_relative_root_test.dart b/tests/isolate/scenarios/package_relative_root/package_relative_root_test.dart
index 3f90563..3e28d99 100644
--- a/tests/isolate/scenarios/package_relative_root/package_relative_root_test.dart
+++ b/tests/isolate/scenarios/package_relative_root/package_relative_root_test.dart
@@ -30,9 +30,9 @@
       throw "Bad package config in child isolate: ${msg[0]}\n"
           "Expected: 'Foo'";
     }
-    if (msg[1] != "Bar2") {
+    if (msg[1] != "Bar1") {
       throw "Package path not matching: ${msg[1]}\n"
-          "Expected: 'Bar2'";
+          "Expected: 'Bar1'";
     }
     print("SUCCESS");
   };
diff --git a/tests/language_2/function_apply_generic2_test.dart b/tests/language_2/function_apply_generic2_test.dart
new file mode 100644
index 0000000..caa7375
--- /dev/null
+++ b/tests/language_2/function_apply_generic2_test.dart
@@ -0,0 +1,47 @@
+// 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.
+
+import "package:expect/expect.dart";
+
+makeFn() {
+  return <T extends num>({T a1, T a2, T a3, T a4, T a5}) {
+    return <T>[a1, a2, a3, a4, a5];
+  };
+}
+
+staticFn<T extends num>({T a1, T a2, T a3, T a4, T a5, T xx}) {
+  return <T>[a1, a2, a3, a4, a5, xx];
+}
+
+class CCC {
+  memberFn<T extends num>({T a1, T a2, T a3, T a4, T a5, T yy}) {
+    return <T>[a1, a2, a3, a4, a5, yy];
+  }
+}
+
+check(a, b) {
+  print('a: $a\nb: $b');
+  Expect.equals(a.toString(), b.toString());
+}
+
+main() {
+  check('[null, 33, null, 11, 22, null]',
+      Function.apply(new CCC().memberFn, [], {#a4: 11, #a5: 22, #a2: 33}));
+
+  Expect.throwsTypeError(
+      () => Function.apply(new CCC().memberFn, [], {#a3: 'hi'}));
+
+  check('[11, 22, 33, null, null]',
+      Function.apply(makeFn(), [], {#a1: 11, #a2: 22, #a3: 33}));
+
+  check('[null, 33, null, 11, 22]',
+      Function.apply(makeFn(), [], {#a4: 11, #a5: 22, #a2: 33}));
+
+  Expect.throwsTypeError(() => Function.apply(makeFn(), [], {#a3: 'hi'}));
+
+  check('[null, 33, null, 11, 22, null]',
+      Function.apply(staticFn, [], {#a4: 11, #a5: 22, #a2: 33}));
+
+  Expect.throwsTypeError(() => Function.apply(staticFn, [], {#a3: 'hi'}));
+}
diff --git a/tests/language_2/function_call_generic_test.dart b/tests/language_2/function_call_generic_test.dart
index b98584e..db40488 100644
--- a/tests/language_2/function_call_generic_test.dart
+++ b/tests/language_2/function_call_generic_test.dart
@@ -1,6 +1,7 @@
 // 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=-Ddart.isdart2js=true
 
 import "package:expect/expect.dart";
 
@@ -21,7 +22,8 @@
   print('a:  $expected');
   print('b:  $actual');
   if (((actual[0] == Object && expected[0] == dynamic) ||
-      (actual[0] == dynamic && expected[0] == Object))) {
+          (actual[0] == dynamic && expected[0] == Object)) &&
+      !const bool.fromEnvironment('dart.isdart2js')) {
     // TODO(32483): dartdevk sometimes defaults type to 'Object' when 'dynamic'
     // is required. Remove this hack when fixed.
     // TODO(31581): dart2js needs instantiate-to-bound to generic 'dynamic'
diff --git a/tests/language_2/language_2_analyzer.status b/tests/language_2/language_2_analyzer.status
index 3c2b597..b22bdfb 100644
--- a/tests/language_2/language_2_analyzer.status
+++ b/tests/language_2/language_2_analyzer.status
@@ -102,6 +102,7 @@
 parameter_initializer3_negative_test: CompileTimeError
 parameter_initializer4_negative_test: CompileTimeError
 parameter_initializer6_negative_test: CompileTimeError
+part_of_multiple_libs_test/01: MissingCompileTimeError # Issue 33227
 part_refers_to_core_library_test/01: MissingCompileTimeError # Issue 29709
 prefix_shadow_test/01: MissingCompileTimeError # Issue 33005
 private_member1_negative_test: Fail # Issue 14021
diff --git a/tests/language_2/language_2_dartdevc.status b/tests/language_2/language_2_dartdevc.status
index b6bc7b9..79b883b 100644
--- a/tests/language_2/language_2_dartdevc.status
+++ b/tests/language_2/language_2_dartdevc.status
@@ -142,6 +142,7 @@
 override_inheritance_generic_test/02: CompileTimeError
 override_inheritance_method_test/28: CompileTimeError
 override_inheritance_method_test/29: CompileTimeError
+part_of_multiple_libs_test/01: MissingCompileTimeError
 part_refers_to_core_library_test/01: Crash
 prefix_shadow_test/01: MissingCompileTimeError # Issue 33005
 regress_23089_test: MissingCompileTimeError
diff --git a/tests/language_2/part_of_multiple_libs_lib.dart b/tests/language_2/part_of_multiple_libs_lib.dart
new file mode 100644
index 0000000..7c71bcb
--- /dev/null
+++ b/tests/language_2/part_of_multiple_libs_lib.dart
@@ -0,0 +1,11 @@
+// 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.
+
+library ambiguous_lib;
+
+part "part_of_multiple_libs_part.dart";
+
+test() {
+  foo();
+}
diff --git a/tests/language_2/part_of_multiple_libs_part.dart b/tests/language_2/part_of_multiple_libs_part.dart
new file mode 100644
index 0000000..4ac530b
--- /dev/null
+++ b/tests/language_2/part_of_multiple_libs_part.dart
@@ -0,0 +1,11 @@
+// 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.
+
+part of ambiguous_lib;
+
+bar() {}
+
+foo() {
+  bar();
+}
diff --git a/tests/language_2/part_of_multiple_libs_test.dart b/tests/language_2/part_of_multiple_libs_test.dart
new file mode 100644
index 0000000..73fd235
--- /dev/null
+++ b/tests/language_2/part_of_multiple_libs_test.dart
@@ -0,0 +1,13 @@
+// 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.
+
+library ambiguous_lib;
+
+import 'part_of_multiple_libs_lib.dart'; //# 01: compile-time error
+
+part "part_of_multiple_libs_part.dart";
+
+main() {
+  foo();
+}
diff --git a/tests/lib_2/isolate/package_resolve_test.dart b/tests/lib_2/isolate/package_resolve_test.dart
index 82e0de6..89b22ea 100644
--- a/tests/lib_2/isolate/package_resolve_test.dart
+++ b/tests/lib_2/isolate/package_resolve_test.dart
@@ -23,10 +23,10 @@
       print(msg.runtimeType);
       throw "Failure return from spawned isolate:\n\n$msg";
     }
-    if (msg[0] != SPAWN_PACKAGE_ROOT) {
+    if (msg[0] != null) {
       throw "Bad package root in child isolate: ${msg[0]}";
     }
-    if (msg[1] != PACKAGE_PATH) {
+    if (msg[1] != null) {
       throw "Package path not matching: ${msg[1]}";
     }
     print("SUCCESS");
diff --git a/tests/lib_2/isolate/package_root_test.dart b/tests/lib_2/isolate/package_root_test.dart
index 3567456..7d6e7b6 100644
--- a/tests/lib_2/isolate/package_root_test.dart
+++ b/tests/lib_2/isolate/package_root_test.dart
@@ -17,7 +17,7 @@
       packageRoot: Uri.parse(SPAWN_PACKAGE_ROOT));
   p.handler = (msg) {
     p.close();
-    if (msg != SPAWN_PACKAGE_ROOT) {
+    if (msg != null) {
       throw "Bad package root in child isolate: $msg";
     }
     print("SUCCESS");
@@ -28,5 +28,5 @@
 testPackageRoot(port) async {
   var packageRoot = await Isolate.packageRoot;
   print("Spawned isolate's package root: $packageRoot");
-  port.send(packageRoot.toString());
+  port.send(packageRoot);
 }
diff --git a/tests/lib_2/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart b/tests/lib_2/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart
index 4679254..eb3cbf7 100644
--- a/tests/lib_2/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart
+++ b/tests/lib_2/isolate/scenarios/automatic_resolution_root/package_resolve_test.dart
@@ -21,15 +21,13 @@
       print(msg.runtimeType);
       throw "Failure return from spawned isolate:\n\n$msg";
     }
-    var child_pkg_root = Platform.script.resolve("packages/");
-    if (msg[0] != child_pkg_root.toString()) {
+    if (msg[0] != null) {
       throw "Bad package root in child isolate: ${msg[0]}.\n"
-          "Expected: $child_pkg_root";
+          "Expected: null";
     }
-    var child_pkg_path = child_pkg_root.resolve("foo/bar.dart");
-    if (msg[1] != child_pkg_path.toString()) {
+    if (msg[1] != null) {
       throw "Package path not matching: ${msg[1]}\n"
-          "Expected $child_pkg_path";
+          "Expected: null";
     }
     print("SUCCESS");
   };
diff --git a/tests/lib_2/isolate/scenarios/package_relative_root/.packages b/tests/lib_2/isolate/scenarios/package_relative_root/.packages
new file mode 100644
index 0000000..32bc5eee
--- /dev/null
+++ b/tests/lib_2/isolate/scenarios/package_relative_root/.packages
@@ -0,0 +1,2 @@
+foo:packages/foo
+bar:packages/bar
diff --git a/tests/lib_2/isolate/scenarios/package_relative_root/package_relative_root_test.dart b/tests/lib_2/isolate/scenarios/package_relative_root/package_relative_root_test.dart
index 3f90563..3e28d99 100644
--- a/tests/lib_2/isolate/scenarios/package_relative_root/package_relative_root_test.dart
+++ b/tests/lib_2/isolate/scenarios/package_relative_root/package_relative_root_test.dart
@@ -30,9 +30,9 @@
       throw "Bad package config in child isolate: ${msg[0]}\n"
           "Expected: 'Foo'";
     }
-    if (msg[1] != "Bar2") {
+    if (msg[1] != "Bar1") {
       throw "Package path not matching: ${msg[1]}\n"
-          "Expected: 'Bar2'";
+          "Expected: 'Bar1'";
     }
     print("SUCCESS");
   };
diff --git a/tests/standalone/standalone.status b/tests/standalone/standalone.status
index beb2ac3..5444e3d 100644
--- a/tests/standalone/standalone.status
+++ b/tests/standalone/standalone.status
@@ -6,6 +6,10 @@
 # listed in tests/lib/analyzer/analyze_tests.status without the "standalone"
 # prefix.
 
+# Obsolete behavior. We want to test that it fails.
+# TODO(mfairhurst) delete this test.
+isolate/scenarios/package_relative_root/package_relative_root_test: Fail
+
 [ $builder_tag == no_ipv6 ]
 io/raw_datagram_socket_test: SkipByDesign
 
diff --git a/tests/standalone_2/http_launch_data/.packages b/tests/standalone_2/http_launch_data/.packages
new file mode 100644
index 0000000..4d7ff27
--- /dev/null
+++ b/tests/standalone_2/http_launch_data/.packages
@@ -0,0 +1 @@
+simple:the_packages/simple
diff --git a/tests/standalone_2/http_launch_data/packages/simple/simple.dart b/tests/standalone_2/http_launch_data/the_packages/simple/simple.dart
similarity index 100%
rename from tests/standalone_2/http_launch_data/packages/simple/simple.dart
rename to tests/standalone_2/http_launch_data/the_packages/simple/simple.dart
diff --git a/tests/standalone_2/http_launch_test.dart b/tests/standalone_2/http_launch_test.dart
index a8852fd..9717974 100644
--- a/tests/standalone_2/http_launch_test.dart
+++ b/tests/standalone_2/http_launch_test.dart
@@ -8,7 +8,8 @@
 // OtherResources=http_launch_data/http_isolate_main.dart
 // OtherResources=http_launch_data/http_launch_main.dart
 // OtherResources=http_launch_data/http_spawn_main.dart
-// OtherResources=http_launch_data/packages/simple/simple.dart
+// OtherResources=http_launch_data/the_packages/simple/simple.dart
+// OtherResources=http_launch_data/.packages
 //
 // Test:
 //   *) Launching a script fetched over HTTP.
@@ -54,7 +55,7 @@
   Future<ProcessResult> http_run = Process
       .run(pathToExecutable, ['http://127.0.0.1:$port/http_launch_main.dart']);
   Future<ProcessResult> http_pkg_root_run = Process.run(pathToExecutable, [
-    '--package-root=http://127.0.0.1:$port/packages/',
+    '--package-root=http://127.0.0.1:$port/the_packages/',
     'http://127.0.0.1:$port/http_launch_main.dart'
   ]);
   Future<ProcessResult> isolate_run = Process.run(pathToExecutable,
diff --git a/tests/standalone_2/package/package_isolate_test.dart b/tests/standalone_2/package/package_isolate_test.dart
index c090179..2a30cb5 100644
--- a/tests/standalone_2/package/package_isolate_test.dart
+++ b/tests/standalone_2/package/package_isolate_test.dart
@@ -2,11 +2,9 @@
 // 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.
 
-// PackageRoot=packages/
-
 library package_isolate_test;
 
-import 'package:shared.dart' as shared;
+import 'packages/shared.dart' as shared;
 import 'dart:isolate';
 import '../../../pkg/async_helper/lib/async_helper.dart';
 import '../../../pkg/expect/lib/expect.dart';
diff --git a/tests/standalone_2/standalone_2.status b/tests/standalone_2/standalone_2.status
index 57e4fee..1475337 100644
--- a/tests/standalone_2/standalone_2.status
+++ b/tests/standalone_2/standalone_2.status
@@ -9,6 +9,8 @@
 io/raw_socket_test: Pass, RuntimeError # Issue 28288
 issue14236_test: Pass # Do not remove this line. It serves as a marker for Issue 14516 comment #4.
 package/invalid_uri_test: Fail, OK # CompileTimeErrors intentionally
+package/package1_test: Fail # imports 'package:foo.dart' which is no longer valid
+package/package_test: Fail # imports 'package:foo.dart' which is no longer valid
 package/scenarios/empty_packages_file/empty_packages_file_discovery_test: Fail, OK # CompileTimeErrors intentionally
 package/scenarios/empty_packages_file/empty_packages_file_option_test: Fail, OK # CompileTimeErrors intentionally
 package/scenarios/invalid/invalid_package_name_test: RuntimeError, CompileTimeError # Errors intentionally
@@ -72,6 +74,11 @@
 [ $compiler != app_jitk && $compiler != dart2analyzer && $compiler != dartdevc && $compiler != dartk && $compiler != dartkp && $runtime != none && $strong ]
 float_array_static_test: MissingCompileTimeError
 
+# We want to confirm that this behavior no longer works. Works in kernel though.
+# TODO(mfairhurst) delete this test.
+[ $compiler != dartk && !$fasta ]
+package/scenarios/packages_dir_only/packages_dir_only_test: Fail
+
 [ $compiler == none && $runtime == vm && $system == fuchsia ]
 *: Skip # Not yet triaged.
 
diff --git a/tests/standalone_2/standalone_2_analyzer.status b/tests/standalone_2/standalone_2_analyzer.status
index 65c0150..2740805 100644
--- a/tests/standalone_2/standalone_2_analyzer.status
+++ b/tests/standalone_2/standalone_2_analyzer.status
@@ -11,7 +11,6 @@
 io/web_socket_protocol_processor_test: Pass, StaticWarning, CompileTimeError # Issue 28843
 package/package1_test: StaticWarning
 package/package1_test: CompileTimeError
-package/package_isolate_test: CompileTimeError
 package/package_test: StaticWarning
 package/package_test: CompileTimeError
 package/scenarios/both_dir_and_file/prefers_packages_file_test: StaticWarning
@@ -28,7 +27,6 @@
 package/scenarios/packages_file_only/packages_file_only_test: CompileTimeError
 
 [ $compiler == dart2analyzer && $system == windows ]
-package/package_isolate_test: Crash # Issue 28645
 package/scenarios/empty_packages_file/empty_packages_file_option_test: Crash, Pass # Issue 28645
 package/scenarios/packages_file_strange_formatting/empty_package_dir_test: Crash # Issue 28645
 
@@ -38,6 +36,7 @@
 io/raw_secure_server_socket_argument_test: CompileTimeError
 io/secure_socket_argument_test: CompileTimeError
 io/stdout_bad_argument_test: CompileTimeError
+package/package_isolate_test: CompileTimeError
 
 [ $compiler == dart2analyzer && !$strong ]
 io/directory_invalid_arguments_test: StaticWarning
diff --git a/tests/standalone_2/standalone_2_kernel.status b/tests/standalone_2/standalone_2_kernel.status
index f3d8db5..347c7ad 100644
--- a/tests/standalone_2/standalone_2_kernel.status
+++ b/tests/standalone_2/standalone_2_kernel.status
@@ -46,7 +46,6 @@
 [ $fasta ]
 deferred_transitive_import_error_test: CompileTimeError
 package/package1_test: CompileTimeError
-package/package_isolate_test: Crash
 package/package_test: CompileTimeError
 package/scenarios/invalid/same_package_twice_test: CompileTimeError
 
@@ -204,5 +203,8 @@
 io/secure_socket_argument_test: CompileTimeError
 io/web_socket_protocol_processor_test: CompileTimeError
 
+[ $fasta && $strong ]
+package/package_isolate_test: CompileTimeError
+
 [ $fasta && !$strong ]
 regress_29350_test/none: MissingCompileTimeError
diff --git a/tools/VERSION b/tools/VERSION
index 9fbb187..ffb6364 100644
--- a/tools/VERSION
+++ b/tools/VERSION
@@ -27,5 +27,5 @@
 MAJOR 2
 MINOR 0
 PATCH 0
-PRERELEASE 61
+PRERELEASE 62
 PRERELEASE_PATCH 0
diff --git a/tools/apps/update_homebrew/lib/update_homebrew.dart b/tools/apps/update_homebrew/lib/update_homebrew.dart
index 3db0e68..2e251bb 100644
--- a/tools/apps/update_homebrew/lib/update_homebrew.dart
+++ b/tools/apps/update_homebrew/lib/update_homebrew.dart
@@ -234,7 +234,7 @@
   def shim_script(target)
     <<~EOS
       #!/usr/bin/env bash
-      exec "#{prefix}/#{target}" "$@"
+      exec "#{prefix}/#{target}" "\$@"
     EOS
   end
 
@@ -258,7 +258,6 @@
 end
 ''';
 
-
 Future runGit(List<String> args, String repository,
     Map<String, String> gitEnvironment) async {
   print("git ${args.join(' ')}");
diff --git a/tools/bots/test_matrix.json b/tools/bots/test_matrix.json
index 0ed7709..2007e17 100644
--- a/tools/bots/test_matrix.json
+++ b/tools/bots/test_matrix.json
@@ -150,6 +150,7 @@
           "arguments": [
             "--checked",
             "--compiler=none",
+            "--no-preview-dart-2",
             "--runtime=vm",
             "--timeout=240",
             "pkg/(kernel|front_end|fasta)"
@@ -167,6 +168,7 @@
           "name": "fasta legacy mode sdk tests",
           "arguments": [
             "--compiler=fasta",
+            "--no-preview-dart-2",
             "--runtime=none"
           ]
         }
@@ -189,7 +191,7 @@
         },
         {
           "name": "vm tests",
-          "arguments": ["--builder-tag=swarming"]
+          "arguments": ["--builder-tag=swarming", "--no-preview-dart-2"]
         }
       ]
     },
@@ -224,11 +226,15 @@
         },
         {
           "name": "vm tests",
-          "arguments": ["--builder-tag=swarming"]
+          "arguments": ["--builder-tag=swarming", "--no-preview-dart-2"]
         },
         {
           "name": "checked vm tests",
-          "arguments": ["--builder-tag=swarming", "--checked"]
+          "arguments": [
+            "--builder-tag=swarming",
+            "--checked",
+            "--no-preview-dart-2"
+          ]
         }
       ]
     },
@@ -247,11 +253,11 @@
         },
         {
           "name": "vm ia32 tests",
-          "arguments": ["--arch=ia32", "vm"]
+          "arguments": ["--arch=ia32", "--no-preview-dart-2", "vm"]
         },
         {
           "name": "vm x64 tests",
-          "arguments": ["--arch=x64", "vm"]
+          "arguments": ["--arch=x64", "--no-preview-dart-2", "vm"]
         }
       ]
     },
@@ -270,7 +276,7 @@
         },
         {
           "name": "vm legacy tests",
-          "arguments": ["--compiler=dartk"],
+          "arguments": ["--compiler=dartk", "--no-preview-dart-2"],
           "fileset": "vm-kernel",
           "shards": 10
         }
@@ -384,7 +390,7 @@
         },
         {
           "name": "vm tests",
-          "arguments": ["--timeout=240"],
+          "arguments": ["--timeout=240", "--no-preview-dart-2"],
           "environment": {
             "ASAN_OPTIONS": "handle_segv=0:detect_stack_use_after_return=0",
             "ASAN_SYMBOLIZER_PATH": "buildtools/toolchain/clang+llvm-x86_64-linux/bin/llvm-symbolizer"
@@ -392,7 +398,7 @@
         },
         {
           "name": "checked vm tests",
-          "arguments": ["--checked","--timeout=240"],
+          "arguments": ["--checked", "--no-preview-dart-2", "--timeout=240"],
           "environment": {
             "ASAN_OPTIONS": "handle_segv=0:detect_stack_use_after_return=0",
             "ASAN_SYMBOLIZER_PATH": "buildtools/toolchain/clang+llvm-x86_64-linux/bin/llvm-symbolizer"
@@ -448,7 +454,7 @@
         },
         {
           "name": "vm tests",
-          "arguments": ["--compiler=app_jit"]
+          "arguments": ["--compiler=app_jit", "--no-preview-dart-2"]
         }
       ]
     },
@@ -638,6 +644,7 @@
           "name": "vm tests",
           "arguments": [
             "--compiler=precompiler",
+            "--no-preview-dart-2",
             "--runtime=dart_precompiled",
             "--use-blobs"]
         }
@@ -660,6 +667,7 @@
           "name": "vm tests",
           "arguments": [
             "--compiler=precompiler",
+            "--no-preview-dart-2",
             "--runtime=dart_precompiled",
             "--system=android",
             "--use-blobs"]
@@ -685,16 +693,18 @@
         {
           "name": "vm tests",
           "arguments": [
-            "--vm-options=--optimization-counter-threshold=5",
-            "--builder-tag=optimization_counter_threshold"
+            "--builder-tag=optimization_counter_threshold",
+            "--no-preview-dart-2",
+            "--vm-options=--optimization-counter-threshold=5"
           ]
         },
         {
           "name": "checked vm tests",
           "arguments": [
+            "--builder-tag=optimization_counter_threshold",
             "--checked",
-            "--vm-options=--optimization-counter-threshold=5",
-            "--builder-tag=optimization_counter_threshold"
+            "--no-preview-dart-2",
+            "--vm-options=--optimization-counter-threshold=5"
           ]
         }
       ]
@@ -745,11 +755,11 @@
         },
         {
           "name": "vm tests",
-          "arguments": ["--hot-reload"]
+          "arguments": ["--hot-reload", "--no-preview-dart-2"]
         },
         {
           "name": "checked vm tests",
-          "arguments": ["--checked","--hot-reload"]
+          "arguments": ["--checked", "--hot-reload", "--no-preview-dart-2"]
         }
       ]
     },
@@ -791,11 +801,15 @@
         },
         {
           "name": "vm tests",
-          "arguments": ["--hot-reload-rollback"]
+          "arguments": ["--hot-reload-rollback", "--no-preview-dart-2"]
         },
         {
           "name": "checked vm tests",
-          "arguments": ["--checked","--hot-reload-rollback"]
+          "arguments": [
+            "--checked",
+            "--hot-reload-rollback",
+            "--no-preview-dart-2"
+          ]
         }
       ]
     },
@@ -837,8 +851,9 @@
           "arguments": [
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--host-checked"
+            "--host-checked",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "exclude_tests": ["observatory_ui", "co19"]
         },
@@ -847,8 +862,9 @@
           "arguments": [
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--host-checked"
+            "--host-checked",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["pkg"]
         },
@@ -857,8 +873,9 @@
           "arguments": [
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--host-checked"
+            "--host-checked",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["observatory_ui"]
         },
@@ -867,8 +884,9 @@
           "arguments": [
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--host-checked"
+            "--host-checked",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         },
@@ -877,73 +895,80 @@
           "arguments": [
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--host-checked"
+            "--host-checked",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["co19"]
         },
         {
           "name": "dart2js checked tests",
           "arguments": [
+            "--checked",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--host-checked",
-            "--checked"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "exclude_tests": ["observatory_ui", "co19"]
         },
         {
           "name": "dart2js checked package tests",
           "arguments": [
+            "--checked",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--host-checked",
-            "--checked"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "dart2js checked observatory-ui tests",
           "arguments": [
+            "--checked",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--host-checked",
-            "--checked"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["observatory_ui"]
         },
         {
           "name": "dart2js checked extra tests",
           "arguments": [
+            "--checked",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--host-checked",
-            "--checked"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         },
         {
           "name": "dart2js checked co19 tests",
           "arguments": [
+            "--checked",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--host-checked",
-            "--checked"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["co19"]
         },
         {
           "name": "dart2js checked unit tests",
           "arguments": [
+            "--checked",
             "--compiler=none",
-            "--runtime=vm",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--checked"
+            "--runtime=vm"
           ],
           "tests": ["dart2js"]
         }
@@ -973,10 +998,11 @@
         {
           "name": "dart2js tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "exclude_tests": ["observatory_ui", "co19"],
           "shards": 4,
@@ -985,10 +1011,11 @@
         {
           "name": "dart2js co19 tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["co19"],
           "shards": 4,
@@ -997,30 +1024,33 @@
         {
           "name": "dart2js package tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "dart2js observatory-ui tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["observatory_ui"]
         },
         {
           "name": "dart2js extra tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         }
@@ -1043,11 +1073,12 @@
         {
           "name": "dart2js fast-startup tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--fast-startup",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--fast-startup"
+            "--use-sdk"
           ],
           "exclude_tests": ["observatory_ui", "co19"],
           "shards": 4,
@@ -1056,11 +1087,12 @@
         {
           "name": "dart2js fast-startup co19 tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--fast-startup",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--fast-startup"
+            "--use-sdk"
           ],
           "tests": ["co19"],
           "shards": 4,
@@ -1069,33 +1101,36 @@
         {
           "name": "dart2js fast-startup package tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--fast-startup",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--fast-startup"
+            "--use-sdk"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "dart2js fast-startup observatory-ui tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--fast-startup",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--fast-startup"
+            "--use-sdk"
           ],
           "tests": ["observatory_ui"]
         },
         {
           "name": "dart2js fast-startup extra tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--fast-startup",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--fast-startup"
+            "--use-sdk"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         }
@@ -1115,11 +1150,12 @@
         {
           "name": "dart2js tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--minified",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--minified"
+            "--use-sdk"
           ],
           "exclude_tests": ["observatory_ui", "co19"],
           "shards": 4,
@@ -1128,11 +1164,12 @@
         {
           "name": "dart2js co19 tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--minified",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--minified"
+            "--use-sdk"
           ],
           "tests": ["co19"],
           "shards": 4,
@@ -1141,12 +1178,13 @@
         {
           "name": "dart2js fast-startup tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
+            "--fast-startup",
             "--minified",
-            "--fast-startup"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "exclude_tests": ["observatory_ui", "co19"],
           "shards": 4,
@@ -1158,9 +1196,10 @@
             "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
+            "--fast-startup",
             "--minified",
-            "--fast-startup"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration"
           ],
           "tests": ["co19"],
           "shards": 4,
@@ -1169,69 +1208,75 @@
         {
           "name": "dart2js package tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--minified",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--minified"
+            "--use-sdk"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "dart2js observatory-ui tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--minified",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--minified"
+            "--use-sdk"
           ],
           "tests": ["observatory_ui"]
         },
         {
           "name": "dart2js extra tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
+            "--minified",
+            "--no-preview-dart-2",
             "--reset-browser-configuration",
-            "--minified"
+            "--use-sdk"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         },
         {
           "name": "dart2js fast-startup pkg tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
+            "--fast-startup",
             "--minified",
-            "--fast-startup"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "dart2js fast-startup observatory-ui tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
+            "--fast-startup",
             "--minified",
-            "--fast-startup"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["observatory_ui"]
         },
         {
           "name": "dart2js fast-startup extra tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
             "--dart2js-batch",
-            "--reset-browser-configuration",
+            "--fast-startup",
             "--minified",
-            "--fast-startup"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         }
@@ -1251,12 +1296,13 @@
         {
           "name": "dart2js tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
+            "--csp",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--minified",
-            "--csp"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "exclude_tests": ["observatory_ui", "co19"],
           "shards": 4,
@@ -1265,12 +1311,13 @@
         {
           "name": "dart2js co19 tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
+            "--csp",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--minified",
-            "--csp"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["co19"],
           "shards": 4,
@@ -1279,13 +1326,14 @@
         {
           "name": "dart2js fast-startup tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
-            "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--minified",
             "--csp",
-            "--fast-startup"
+            "--dart2js-batch",
+            "--fast-startup",
+            "--minified",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "exclude_tests": ["observatory_ui", "co19"],
           "shards": 4,
@@ -1294,13 +1342,14 @@
         {
           "name": "dart2js fast-startup co19 tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
-            "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--minified",
             "--csp",
-            "--fast-startup"
+            "--dart2js-batch",
+            "--fast-startup",
+            "--minified",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["co19"],
           "shards": 4,
@@ -1309,75 +1358,81 @@
         {
           "name": "dart2js package tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
+            "--csp",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--minified",
-            "--csp"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "dart2js observatory-ui tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
+            "--csp",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--minified",
-            "--csp"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["observatory_ui"]
         },
         {
           "name": "dart2js extra tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
+            "--csp",
             "--dart2js-batch",
-            "--reset-browser-configuration",
             "--minified",
-            "--csp"
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         },
         {
           "name": "dart2js fast-startup pkg tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
-            "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--minified",
             "--csp",
-            "--fast-startup"
+            "--dart2js-batch",
+            "--fast-startup",
+            "--minified",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "dart2js fast-startup observatory-ui tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
-            "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--minified",
             "--csp",
-            "--fast-startup"
+            "--dart2js-batch",
+            "--fast-startup",
+            "--minified",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["observatory_ui"]
         },
         {
           "name": "dart2js fast-startup extra tests",
           "arguments": [
-            "--use-sdk",
             "--compiler=dart2js",
-            "--dart2js-batch",
-            "--reset-browser-configuration",
-            "--minified",
             "--csp",
-            "--fast-startup"
+            "--dart2js-batch",
+            "--fast-startup",
+            "--minified",
+            "--no-preview-dart-2",
+            "--reset-browser-configuration",
+            "--use-sdk"
           ],
           "tests": ["dart2js_extra","dart2js_native"]
         }
@@ -1446,21 +1501,36 @@
         },
         {
           "name": "analyze tests",
-          "arguments": ["--compiler=dart2analyzer", "--use-sdk"]
+          "arguments": [
+            "--compiler=dart2analyzer",
+            "--no-preview-dart-2",
+            "--use-sdk"
+          ]
         },
         {
           "name": "analyze pkg tests",
-          "arguments": ["--compiler=dart2analyzer", "--use-sdk", "pkg"]
+          "arguments": [
+            "--compiler=dart2analyzer",
+            "--no-preview-dart-2",
+            "--use-sdk",
+            "pkg"
+          ]
         },
         {
           "name": "analyze tests checked",
-          "arguments": ["--checked", "--compiler=dart2analyzer", "--use-sdk"]
+          "arguments": [
+            "--checked",
+            "--compiler=dart2analyzer",
+            "--no-preview-dart-2",
+            "--use-sdk"
+          ]
         },
         {
           "name": "analyze pkg tests checked",
           "arguments": [
             "--checked",
             "--compiler=dart2analyzer",
+            "--no-preview-dart-2",
             "--use-sdk",
             "pkg"
           ]
@@ -1470,6 +1540,7 @@
           "arguments": [
             "--checked",
             "--compiler=none",
+            "--no-preview-dart-2",
             "--use-sdk",
             "pkg/analyzer"
           ]
@@ -1479,6 +1550,7 @@
           "arguments": [
             "--checked",
             "--compiler=none",
+            "--no-preview-dart-2",
             "--use-sdk",
             "pkg/analysis_server"
           ]
@@ -1488,6 +1560,7 @@
           "arguments": [
             "--checked",
             "--compiler=none",
+            "--no-preview-dart-2",
             "--use-sdk",
             "pkg/analyzer_cli"
           ]
@@ -1497,102 +1570,7 @@
           "arguments": [
             "--checked",
             "--compiler=none",
-            "--use-sdk",
-            "pkg/analyzer_plugin"
-          ]
-        }
-      ]
-    },
-    {
-      "builders": [
-        "analyzer-linux-release-strong-hostchecked"
-      ],
-      "meta": {
-        "description": "This configuration is used by the analyzer CQ builder running in strong and hostchecked mode."
-      },
-      "steps": [
-        {
-          "name": "build dart",
-          "script": "tools/build.py",
-          "arguments": ["create_sdk"]
-        },
-        {
-          "name": "analyze tests",
-          "arguments": [
-            "--compiler=dart2analyzer",
-            "--host-checked",
-            "--strong"
-          ]
-        },
-        {
-          "name": "analyze pkg tests",
-          "arguments": [
-            "--compiler=dart2analyzer",
-            "--host-checked",
-            "--strong",
-            "pkg"
-          ]
-        },
-        {
-          "name": "analyze tests checked",
-          "arguments": [
-            "--checked",
-            "--compiler=dart2analyzer",
-            "--host-checked",
-            "--strong"
-          ]
-        },
-        {
-          "name": "analyze pkg tests checked",
-          "arguments": [
-            "--checked",
-            "--compiler=dart2analyzer",
-            "--host-checked",
-            "--strong",
-            "pkg"
-          ]
-        },
-        {
-          "name": "analyze tests preview-dart2",
-          "arguments": [
-            "--compiler=dart2analyzer",
-            "--host-checked",
-            "--strong",
-            "--preview-dart-2"
-          ]
-        },
-        {
-          "name": "analyzer unit tests",
-          "arguments": [
-            "--checked",
-            "--compiler=none",
-            "--use-sdk",
-            "pkg/analyzer"
-          ]
-        },
-        {
-          "name": "analysis_server unit tests",
-          "arguments": [
-            "--checked",
-            "--compiler=none",
-            "--use-sdk",
-            "pkg/analysis_server"
-          ]
-        },
-        {
-          "name": "analyzer_cli unit tests",
-          "arguments": [
-            "--checked",
-            "--compiler=none",
-            "--use-sdk",
-            "pkg/analyzer_cli"
-          ]
-        },
-        {
-          "name": "analyzer_plugin unit tests",
-          "arguments": [
-            "--checked",
-            "--compiler=none",
+            "--no-preview-dart-2",
             "--use-sdk",
             "pkg/analyzer_plugin"
           ]
@@ -1615,44 +1593,22 @@
           "arguments": ["create_sdk"]
         },
         {
-          "name": "analyze tests",
-          "arguments": ["--compiler=dart2analyzer", "--strong", "--use-sdk"]
-        },
-        {
           "name": "analyze pkg tests",
           "arguments": [
             "--compiler=dart2analyzer",
+            "--preview-dart-2",
             "--strong",
             "--use-sdk",
             "pkg"
           ]
         },
         {
-          "name": "analyze tests checked",
-          "arguments": [
-            "--checked",
-            "--compiler=dart2analyzer",
-            "--strong",
-            "--use-sdk"
-          ]
-        },
-        {
-          "name": "analyze pkg tests checked",
-          "arguments": [
-            "--checked",
-            "--compiler=dart2analyzer",
-            "--use-sdk",
-            "--strong",
-            "pkg"
-          ]
-        },
-        {
           "name": "analyze tests preview-dart2",
           "arguments": [
             "--compiler=dart2analyzer",
+            "--preview-dart-2",
             "--strong",
-            "--use-sdk",
-            "--preview-dart-2"
+            "--use-sdk"
           ]
         }
       ]
@@ -1696,21 +1652,23 @@
         {
           "name": "package unit tests",
           "arguments": [
-            "--use-sdk",
-            "--compiler=none",
-            "--runtime=vm",
             "--checked",
-            "--timeout=120"
+            "--compiler=none",
+            "--no-preview-dart-2",
+            "--runtime=vm",
+            "--timeout=120",
+            "--use-sdk"
           ],
           "tests": ["pkg"]
         },
         {
           "name": "third_party/pkg_tested unit tests",
           "arguments": [
-            "--use-sdk",
+            "--checked",
             "--compiler=none",
+            "--no-preview-dart-2",
             "--runtime=vm",
-            "--checked"
+            "--use-sdk"
           ],
           "tests": ["pkg_tested"]
         },
diff --git a/tools/create_tarball.py b/tools/create_tarball.py
index 46ea0b9..918f532 100755
--- a/tools/create_tarball.py
+++ b/tools/create_tarball.py
@@ -101,6 +101,10 @@
     f.write(' -- Dart Team <misc@dartlang.org>  %s\n' %
             datetime.datetime.utcnow().strftime('%a, %d %b %Y %X +0000'))
 
+def GenerateEmpty(filename):
+  f = open(filename, 'w')
+  f.close()
+
 def GenerateGitRevision(filename, git_revision):
   with open(filename, 'w') as f:
     f.write(str(git_revision))
@@ -137,6 +141,11 @@
       GenerateChangeLog(change_log, version)
       tar.add(change_log, arcname='%s/debian/changelog' % versiondir)
 
+      # For generated version file build dependency, add fake git reflog.
+      empty = join(temp_dir, 'empty')
+      GenerateEmpty(empty)
+      tar.add(empty, arcname='%s/dart/.git/logs/HEAD' % versiondir)
+
       # For bleeding_edge add the GIT_REVISION file.
       if utils.GetChannel() == 'be':
         git_revision = join(temp_dir, 'GIT_REVISION')
diff --git a/tools/dom/src/AttributeMap.dart b/tools/dom/src/AttributeMap.dart
index a6e79f3..19c9f88 100644
--- a/tools/dom/src/AttributeMap.dart
+++ b/tools/dom/src/AttributeMap.dart
@@ -16,10 +16,6 @@
   }
 
   Map<K, V> cast<K, V>() => Map.castFrom<String, String, K, V>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<K, V> retype<K, V>() => cast<K, V>();
-
   bool containsValue(Object value) {
     for (var v in this.values) {
       if (value == v) {
@@ -181,10 +177,6 @@
   }
 
   Map<K, V> cast<K, V>() => Map.castFrom<String, String, K, V>(this);
-
-  @Deprecated("Use cast instead.")
-  Map<K, V> retype<K, V>() => cast<K, V>();
-
   // TODO: Use lazy iterator when it is available on Map.
   bool containsValue(Object value) => values.any((v) => v == value);
 
diff --git a/tools/infra/config/cq.cfg b/tools/infra/config/cq.cfg
index 508d716..9c3f0bf 100644
--- a/tools/infra/config/cq.cfg
+++ b/tools/infra/config/cq.cfg
@@ -19,7 +19,8 @@
   try_job {
     buckets {
       name: "luci.dart.try"
-      builders { name: "analyzer-linux-release-strong-hostchecked-try" }
+      builders { name: "analyzer-linux-release-try" }
+      builders { name: "analyzer-strong-linux-release-try" }
       builders { name: "benchmark-linux-try" }
       builders { name: "dart-sdk-windows-try" }
       builders { name: "dart2js-linux-d8-hostchecked-try" }
@@ -30,7 +31,6 @@
       builders { name: "front-end-linux-release-x64-try" }
       builders { name: "pkg-linux-release-try" }
       builders { name: "vm-canary-linux-debug-try" }
-      builders { name: "vm-kernel-legacy-linux-release-x64-try" }
       builders { name: "vm-kernel-linux-release-simdbc64-try" }
       builders { name: "vm-kernel-linux-release-x64-try" }
       builders { name: "vm-kernel-mac-release-x64-try" experiment_percentage: 100 }
diff --git a/tools/testing/dart/options.dart b/tools/testing/dart/options.dart
index e52f9cb..5bb7760 100644
--- a/tools/testing/dart/options.dart
+++ b/tools/testing/dart/options.dart
@@ -167,6 +167,9 @@
         'Only run tests that are not marked `Slow` or `Timeout`.'),
     new _Option.bool('enable_asserts',
         'Pass the --enable-asserts flag to dart2js or to the vm.'),
+    new _Option.bool(
+        'no_preview_dart_2', 'Pass the --no-preview-dart-2 flag for Dart1 mode',
+        hide: true),
     new _Option.bool('preview_dart_2',
         'Pass the --preview-dart-2 flag to analyzer, or pass --no-preview-dart-2 if false.',
         hide: true),
diff --git a/utils/bazel/kernel_summary_worker.dart b/utils/bazel/kernel_summary_worker.dart
index 2b1246b..9ac2ab9 100644
--- a/utils/bazel/kernel_summary_worker.dart
+++ b/utils/bazel/kernel_summary_worker.dart
@@ -138,9 +138,7 @@
     for (fe.FormattedMessage message in context) {
       out.println(message.formatted);
     }
-    if (severity != fe.Severity.nit) {
-      succeeded = false;
-    }
+    succeeded = false;
   }
 
   var summary = await fe.compile(state, sources, onProblem);